I am trying to create a game in which objects spawn on a timer then start moving. I would like to keep the frame rate independent of the game speed, so I have tried to implement delta time:
lastTime = thisTime;
thisTime = (int) SystemClock.currentThreadTimeMillis();
deltaTime = thisTime - lastTime;
for (int i = 0;i < objectList.size();i++) {
objectList.get(i).updatePosition(deltaTime);
objectList.get(i).display(bitmapCanvas);
}
And my updatePosition method:
public void updatePosition(float deltaTime) {
this.y += 10/1000 * deltaTime;
}
From my understanding, the rate (10 in this case) should be divided by 1000 since deltaTime is in milliseconds, but I have tried it with various other values as well, and the objects just spawn on the screen and do not move. I had no issues making them move before trying to implement interpolation.
If it helps any, I was logging the delta time and it was usually around 20/30. Is this normal?
I have looked at probably 5 or 6 questions on GameDev and a couple on Stack Overflow but I think I must be misunderstanding something as I cannot get this to work.
So this doesn't appear unanswered, Jon Skeet was (obviously) correct:
The calculation of 10/1000 is being performing (at compile time) in integer arithmetic, so it's 0... Try 10/1000f, or just 0.01f.
Related
Consider this Game Loop:
double nextTime = (double)System.nanoTime() / 1000000000.0;
while(runFlag)
{
double currTime = (double)System.nanoTime() / 1000000000.0;
if(currTime >= nextTime)
{
nextTime += delta;
update();
draw();
}
else
{
int sleepTime = (int)(1000.0 * (nextTime - currTime));
if(sleepTime > 0)
{
try
{
Thread.sleep(sleepTime);
}
catch(InterruptedException e)
{
}
How should I calculate an appropriate value of delta (the time that has to pass before the next update and render). I have seen it been calculated different ways but I am still not sure how or what exactly is really going on. This is a fixed time step loop, so for instance if i wanted to calculate delta for a constant fps of 30 of 60, what would I have to set it as and why? I am unable to grasp some of the explanations I have come across on the Internet. Thanks.
If you want to produce a particular frame per second rate, consider the following:
You want to produce a new frame every 1/frames-per-second seconds.
It may take you p seconds to produce a frame (processing)
The "free time" between frame productions, delta, would be 1/frames-per-second - p
You might use the following pseudo-code:
frameTimeMilliseconds = 1000 / frames-per-second
Loop(condition) {
startFrameTime = system current time in milliseonds
do frame production
endFrameTime = system current time in milliseconds
sleepTime = frameTimeMilliseconds - (endFrameTime - startFrameTime)
sleep for sleepTime milliseconds
}
You may want to handle the condition where the actual frame production time is longer than the required frame production time (i.e. where sleepTime is <= 0)
I have recently started on developing my own game engines for fun. I implemented a method to load Blender .OBJ models from files, and I am successfully rendering them. However, when doing a stress-test I ran into an unusual predicament with my Delta-time based fps system. While running at 1500FPS, it takes me 4 seconds to look from one end of a wall of models to another. If I cap the FPS at 120FPS, however, it only takes my 0.84 seconds to look from one end of the wall to another. As I explored further it would seem that, in fact, the game-movement speed decreases as FPS increases.
Here is my Timer class:
class Timer
{
long lastFrame;
int fps;
long lastFPS;
int delta;
int fpsToReturn;
public Timer()
{
lastFPS = getTime();
}
public long getTime()
{
return (Sys.getTime() * 1000) / Sys.getTimerResolution();
}
public int getDelta()
{
long time = getTime();
delta = (int) (time - lastFrame);
lastFrame = time;
return delta;
}
public void updateFPS()
{
if (getTime() - lastFPS > 1000)
{
fpsToReturn = fps;
fps = 0;
lastFPS += 1000;
}
fps++;
}
public int getFPS()
{
return fpsToReturn;
}
}
And of course movement is just something along the lines of:
camera.rotX += (0.5 * timer.getDelta());
Does anyone have any ideas? Is this how delta-time is supposed to work? When running at 16FPS it returns around 65, at 120FPS Delta is returning around 8-9, while uncapped FPS it always returns 0 or 1 if that makes a difference or helps you spot if something is wrong with the uncapped FPS. I really appreciate any help, thank you guys.
Solved my own question, and glad I learned in the process.
My issue, which I later discovered when I was implementing angular movement, was that I was using the method getDelta() and getFPS() every time i needed it more than once-per-frame, which was throwing off the delta variable. I solved the issue by using a static variable, one for FPS and one for Delta, and updating each variable at the end of each frame.
Pseudo Code:
public static double globalDelta;
while(nextFrame) //Loops once per frame
{
updateGame();
globalDelta = calculateDelta();
}
I'm making a 2D platformer / shooter with LibGDX. I'm having this loop where holding fire-button down causes bullets to fly from the main character's gun the whole duration while the fire-button is pressed down (rapid fire). That part works perfectly and as intended. However, I'd like the rate of fire to be a bit slower. Currently the loop just adds a bullet to the world on each game frame which means the rate of fire is ridiculously high.
I've been trying to find a good way to do this, to no avail. Any suggestions would be vastly appreciated.
the loop:
if (keys.get(Keys.FIRE)) {
player.setState(State.FIRING);
world.addBullet(new Bullet(1f,1f,0));
}
You can use a delay mechanism by having a variable which counts down the time and every time it hits 0, you make one shot and reset the time, for example to 0.2f when you want the player to shoot every 0.2s:
private float fireDelay;
public void render(float deltaTime) {
fireDelay -= deltaTime;
if (keys.get(Keys.FIRE)) {
player.setState(State.FIRING);
if (fireDelay <= 0) {
world.addBullet(new Bullet(1f,1f,0));
fireDelay += 0.2;
}
}
}
Use a constant to hold the fire rate and add a timing mechanism, like so:
public static final long FIRE_RATE = 200000000L;
public long lastShot;
if(System.nanoTime() - lastShot >= FIRE_RATE) {
world.addBullet(new Bullet(1f,1f,0));
lastShot = System.nanoTime();
}
I have seen #noone s answer and it is correct. I just answer you, because i had to add the same to my game. What i did: I had a variable boolean attacking, which stores if you are holding firebutton. Then i had 2 more variables: float bps, which stores how many bullets you can shoot per second and float reloadTime, which stores how long it takes to reload an empty magazin, if you use one. I also store a long time and a boolean reloading. Time stores the TimeUtils.millis() of your last shot, the reloading stores if you are reloading the magazin or just shooting. Then in the attack method i call a method: public boolean readyToAttack(), in which i compare TimeUtils.millis() to my variable time. If reloading = true, TimeUtils.millis() - reloadTime has to bigger then time. If not, TimeUtils.millis() - (1000 / bps) has to be bigger then time. If this is the case the method returns true and i can shoot. Noones solution is simpler, but for me bps is easier to understand so i used this.
Hope it helps
I'm writing a game, and I saw the FPS algorithm doesn't work correctly (when he have to calculate more, he sleeps longer...) So, the question is very simple: how to calculate the sleeptime for having correct FPS?
I know how long it took to update the game one frame in microseconds and of course the FPS I want to reach.
I'm searching crazy for a simple example, but I can't find one....
The code may be in Java, C++ or pseudo....
The time you should spend on rendering one frame is 1/FPS seconds (if you're aiming for, say 10 FPS, you should spend 1/10 = 0.1 seconds on each frame). So if it took X seconds to render, you should "sleep" for 1/FPS - X seconds.
Translating that to for instance milliseconds, you get
ms_to_sleep = 1000 / FPS - elapsed_ms;
If it, for some reason took more than 1/FPS to render the frame, you'll get a negative sleep time in which case you obviously just skip the sleeping.
The number of microseconds per frame is 1000000 / frames_per_second. If you know that you've spent elapsed_microseconds calculating, then the time that you need to sleep is:
(1000000 / frames_per_second) - elapsed_microseconds
Try...
static const int NUM_FPS_SAMPLES = 64;
float fpsSamples[NUM_FPS_SAMPLES]
int currentSample = 0;
float CalcFPS(int dt)
{
fpsSamples[currentSample % NUM_FPS_SAMPLES] = 1.0f / dt;
float fps = 0;
for (int i = 0; i < NUM_FPS_SAMPLES; i++)
fps += fpsSamples[i];
fps /= NUM_FPS_SAMPLES;
return fps;
}
... as per http://www.gamedev.net/community/forums/topic.asp?topic_id=510019
Take a look at this article about different FPS handling methods.
UPDATE: use this link from Web Archive as original website disappeared: https://web.archive.org/web/20161202094710/http://dewitters.koonsolo.com/gameloop.html
I'm working in J2ME, I have my gameloop doing the following:
public void run() {
Graphics g = this.getGraphics();
while (running) {
long diff = System.currentTimeMillis() - lastLoop;
lastLoop = System.currentTimeMillis();
input();
this.level.doLogic();
render(g, diff);
try {
Thread.sleep(10);
} catch (InterruptedException e) {
stop(e);
}
}
}
So it's just a basic gameloop, the doLogic() function calls for all the logic functions of the characters in the scene and render(g, diff) calls the animateChar function of every character on scene, following this, the animChar function in the Character class sets up everything in the screen as this:
protected void animChar(long diff) {
this.checkGravity();
this.move((int) ((diff * this.dx) / 1000), (int) ((diff * this.dy) / 1000));
if (this.acumFrame > this.framerate) {
this.nextFrame();
this.acumFrame = 0;
} else {
this.acumFrame += diff;
}
}
This ensures me that everything must to move according to the time that the machine takes to go from cycle to cycle (remember it's a phone, not a gaming rig). I'm sure it's not the most efficient way to achieve this behavior so I'm totally open for criticism of my programming skills in the comments, but here my problem: When I make I character jump, what I do is that I put his dy to a negative value, say -200 and I set the boolean jumping to true, that makes the character go up, and then I have this function called checkGravity() that ensure that everything that goes up has to go down, checkGravity also checks for the character being over platforms so I will strip it down a little for the sake of your time:
public void checkGravity() {
if (this.jumping) {
this.jumpSpeed += 10;
if (this.jumpSpeed > 0) {
this.jumping = false;
this.falling = true;
}
this.dy = this.jumpSpeed;
}
if (this.falling) {
this.jumpSpeed += 10;
if (this.jumpSpeed > 200) this.jumpSpeed = 200;
this.dy = this.jumpSpeed;
if (this.collidesWithPlatform()) {
this.falling = false;
this.standing = true;
this.jumping = false;
this.jumpSpeed = 0;
this.dy = this.jumpSpeed;
}
}
}
So, the problem is, that this function updates the dy regardless of the diff, making the characters fly like Superman in slow machines, and I have no idea how to implement the diff factor so that when a character is jumping, his speed decrement in a proportional way to the game speed. Can anyone help me fix this issue? Or give me pointers on how to make a 2D Jump in J2ME the right way.
Shouldn't you be adjusting the jumpSpeed based on the elapsed time? That is, perhaps the speed changes by -75/sec, so your diff should be a weight for the amount of change applied to the jumpSpeed.
So pass in diff to checkGrav and do something like... jumpSpeed += (diff * (rate_per_second)) / 1000;
(assuming diff in milliseconds)
(Ideally, this would make it just like real gravity :D)
Why not just scale all constants by diff?
By the way, I'm embarrassed to say this, but I worked on a commercial game where gravity was twice as strong on characters going down as going up. For some reason, people preferred this.
This seems to be more of a question about game design than the math of a jump. It is a common problem that in games running on different processors one game will be executed faster and on other games it will be executed slower (thus changing the entire speed of the game). I'm not sure what common practice is in games, but whenever I made home-brewed 2D games (they were fun to make) I would have the concept of a game-tick. On faster machines
long diff = System.currentTimeMillis() - lastLoop;
lastLoop = System.currentTimeMillis();
Would be lower. A wait time would be derived from the diff so that the game would run at the same speed on most machines. I would also have the render method in a separate thread so that the game speed isn't dependent on the graphics.
I can give a formula like this (I use it everywhere). The X is the parameter of it starting from zero and ending on the length of jump.
if you want someone to jump at some Height (H) and at some Length (L), then function of the jump will look like this (and it won't' be able to ever look different):
y = minus(power(x - Length of Jump divided by two) multiply by 4 and
multiply by Height of the jump) divide by power of Length and add
Height of jump in the very end.
y = -(x-l/2)(x-l/2)*4*h/(l*l) + h
And if you want the jumping object to land on something, then you can check every new X if it's approximately standing on a platform and if it is standing on something, then don't make it just stop, make it's Y position exactly equal to the Y of platform.
If you're using something like Flash or other base which has inverted y axis, then multiply the function output by -1;