Java-Gaming.org    
Featured games (81)
games approved by the League of Dukes
Games in Showcase (495)
Games in Android Showcase (114)
games submitted by our members
Games in WIP (563)
games currently in development
News: Read the Java Gaming Resources, or peek at the official Java tutorials
 
    Home     Help   Search   Login   Register   
Pages: [1]
  ignore  |  Print  
  Hi all,i have a question about my game engine?  (Read 2677 times)
0 Members and 1 Guest are viewing this topic.
Offline cypher_516

Junior Newbie





« Posted 2010-05-05 14:16:54 »

Hello, i just started to game programing with java, before that i was using c# Xna.I wrote my engine,and it is working fine.But i didn't use a canvas.You can see my game engine below.I'm wondering should i use canvas to draw (if so why?) or not?

And i saw nobody preferred using timers to a while loop and my fps should be fixed 60 but it is more than 60 so am i doing something wrong ?

1  
2  
3  
4  
5  
6  
7  
8  
9  
10  
11  
12  
13  
14  
15  
16  
17  
18  
19  
20  
21  
22  
23  
24  
25  
26  
27  
28  
29  
30  
31  
32  
33  
34  
35  
36  
37  
38  
39  
40  
41  
42  
43  
44  
45  
46  
47  
48  
49  
50  
51  
52  
53  
54  
55  
56  
57  
58  
59  
60  
61  
62  
63  
64  
65  
66  
67  
68  
69  
70  
71  
72  
73  
74  
75  
76  
77  
78  
79  
80  
81  
82  
83  
84  
85  
86  
87  
88  
89  
90  
91  
92  
93  
94  
95  
96  
package kutuyatopat;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsEnvironment;
import java.awt.Transparency;
import java.awt.image.BufferedImage;
import javax.swing.JFrame;
import java.util.Timer;
import java.util.TimerTask;
import java.util.Vector;
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JPanel;


public class Engine extends JFrame {
   
    int frameRate = 0;
    int frameCounter = 0;

    long StartTime = System.currentTimeMillis();
    long EndTime;
    long ElapsedTime = 0;

    JPanel panel;
    JLabel label;

    Vector<IComponent> Components;

    GraphicsConfiguration gc;

    public Engine(){
       
        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setSize(800,600);
        this.setLocationRelativeTo(null);
        panel = new JPanel();
        this.add(panel);
       
        label = new JLabel();
        panel.add(label);
        Components = new Vector<IComponent>();
        gc = GraphicsEnvironment.getLocalGraphicsEnvironment().
                             getDefaultScreenDevice().getDefaultConfiguration();
    }

    protected void Initialize(){
        Timer t = new Timer();
        TimerTask tt = new TimerTask(){
            @Override
            public void run() {
                EndTime = System.currentTimeMillis();
                long elapsedTime = EndTime - StartTime;
                GameLoop(elapsedTime);
                StartTime = System.currentTimeMillis();
            }
        };
        t.scheduleAtFixedRate(tt, 10, 1000 / 60);
    }
   
    void GameLoop(long elapsedTime){
        Update(elapsedTime);
        Draw();
    }

    public void Update(long elapsedTime){
        ElapsedTime += elapsedTime;
        if(ElapsedTime > 1000){
            ElapsedTime -= 1000;
            frameRate = frameCounter;
            frameCounter = 0;
        }
        for(IComponent c : Components){
            c.Update(ElapsedTime);
        }
    }

    public void Draw(){
        frameCounter++;
        String fps = "Fps: " + frameRate;
        BufferedImage i = gc.createCompatibleImage(this.getWidth(), this.getHeight(),Transparency.BITMASK);
        Graphics2D g2 = i.createGraphics();
        for(IComponent c : Components){
            c.Draw(g2);
        }
        g2.setColor(Color.white);
        g2.drawString(fps, 30, 40);
        g2.dispose();
        ImageIcon ic = new ImageIcon(i);
        label.setIcon(ic);
    }

}

Offline Riven
« League of Dukes »

JGO Overlord


Medals: 798
Projects: 4
Exp: 16 years


Hand over your head.


« Reply #1 - Posted 2010-05-05 14:33:31 »

t.scheduleAtFixedRate(tt, 10, 1000 / 60);

1000ms / 60fps = 16ms (not 16.6666)

1000ms / 16ms = 62.5fps

Hi, appreciate more people! Σ ♥ = ¾
Learn how to award medals... and work your way up the social rankings
Offline cypher_516

Junior Newbie





« Reply #2 - Posted 2010-05-05 14:40:26 »

yeah but i just executed it and fps was changed like 0-99-86-95-82-86-93-91-85 ... and there was no component.
Games published by our own members! Check 'em out!
Legends of Yore - The Casual Retro Roguelike
Offline Markus_Persson

JGO Wizard


Medals: 15
Projects: 19


Mojang Specifications


« Reply #3 - Posted 2010-05-07 09:28:53 »

1  
2  
3  
4  
5  
6  
            public void run() {
                EndTime = System.currentTimeMillis();
                long elapsedTime = EndTime - StartTime;
                GameLoop(elapsedTime);
                StartTime = System.currentTimeMillis();
            }


You're leaking time! What about the time the GameLoop() call takes? This means the time you measure is longer (potentially much longer) than the real life time, causing your frame rate calculation to be wrong.


If you only call System.currentTimeMillis() once per call, you won't leak any time:
1  
2  
3  
4  
5  
6  
            public void run() {
                now = System.currentTimeMillis();
                long elapsedTime = lastTime - now;
                lastTime = now;
                GameLoop(elapsedTime);
            }


Play Minecraft!
Offline Eli Delventhal

JGO Kernel


Medals: 42
Projects: 11
Exp: 10 years


Game Engineer


« Reply #4 - Posted 2010-05-07 14:48:39 »

Aaaaaahhhh! Time is leaking! It's the end of the universe!

See my work:
OTC Software
Offline cypher_516

Junior Newbie





« Reply #5 - Posted 2010-05-07 19:52:10 »

hehhe Grin My bad. I was so sleepy when i was writing it.Thanks for catching that leaking,it was stacking me.

In the meantime I did some changes too and i'm wondering is it ok now or am i doing somethings wrong again.

here, new engine

1  
2  
3  
4  
5  
6  
7  
8  
9  
10  
11  
12  
13  
14  
15  
16  
17  
18  
19  
20  
21  
22  
23  
24  
25  
26  
27  
28  
29  
30  
31  
32  
33  
34  
35  
36  
37  
38  
39  
40  
41  
42  
43  
44  
45  
46  
47  
48  
49  
50  
51  
52  
53  
54  
55  
56  
57  
58  
59  
60  
61  
62  
63  
64  
65  
66  
67  
68  
69  
70  
71  
72  
73  
74  
75  
76  
77  
78  
79  
80  
81  
82  
83  
84  
85  
86  
87  
88  
89  
90  
91  
92  
93  
94  
95  
96  
97  
98  
99  
100  
101  
102  
103  
104  
105  
106  
107  
108  
109  
110  
111  
112  
113  
114  
115  
116  
117  
118  
119  
120  
121  
122  
123  
124  
125  
126  
127  
128  
129  
130  
131  
132  
133  
134  
135  
136  
137  
138  
139  
140  
141  
142  
143  
144  
145  
146  
147  
148  
149  
150  
151  
152  
153  
154  
155  
156  
157  
158  
159  
160  
161  
162  
163  
164  
165  
166  
167  
168  
169  
170  
171  
172  
173  
174  
175  
176  
177  
178  
179  
180  
181  
182  
183  
184  
185  
186  
187  
188  
189  
package MyGame;

import java.awt.Canvas;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Toolkit;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.awt.image.BufferStrategy;
import java.util.ArrayList;
import javax.swing.JFrame;
import javax.swing.JPanel;
import MyGame.Input.Keyboard;
import java.awt.GraphicsConfiguration;
import java.awt.image.VolatileImage;
import java.util.Timer;
import java.util.TimerTask;
import net.phys2d.math.Vector2f;
import net.phys2d.raw.World;
import net.phys2d.raw.strategies.QuadSpaceStrategy;

public class Engine extends JFrame {

    protected float frameCounter = 0;

    long StartTime = System.currentTimeMillis();
    long EndTime;
    public long TotalGameRuningTime = 0;
    long elapsedTime = 0;

    JPanel panel;
    Canvas Canvas;
    BufferStrategy BackBuffer;

    ArrayList<IComponent> Components;

    /*
     * Desing resolution values.Set them as your design resolution,engine will handle scaling canvas to the active resolution
     */

    public int designX = 800,designY = 600;

    protected static ResourceManager ResourceManager;

    protected World world;

    public static Keyboard keyboard;

    private int FPS = 60;

    protected boolean DebugMode = true; //TODO: Make it false as default after fnished developing

    Toolkit toolkit; //for vsync syncronization

    public int WorldStepCount = 5;

    private static GraphicsConfiguration gc;

    private boolean isFullScreen = false;

    public Engine(){
        world = new World(new Vector2f(0f,9.8f), 100, new QuadSpaceStrategy(100, 100));
        ResourceManager = new ResourceManager();
        panel = (JPanel) this.getContentPane();
        panel.setLayout(null);
        Components = new ArrayList<IComponent>();
        keyboard = new Keyboard();
        Canvas = new Canvas();
        this.pack();
        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setSize(designX,designY);
        this.setLocationRelativeTo(null);
        Canvas.setBounds(0, 0, this.getWidth(), this.getHeight());
        Canvas.setIgnoreRepaint(true);
        panel.add(Canvas);
        Canvas.createBufferStrategy(2);
        BackBuffer = Canvas.getBufferStrategy();
        toolkit = Toolkit.getDefaultToolkit();
        gc = getGraphicsConfiguration();
    }

    public static VolatileImage createVolatileImage(int widht,int height,int transparancy){
        return gc.createCompatibleVolatileImage(widht, height, transparancy);
    }

    /*
     * Call before calling statLoop() to set avarage fps other than 60
     */

    public void setFPS(int FPS) {
        this.FPS = FPS;
    }

    /*
     * Call before calling statLoop() to sync avarage fps to screen refresh rate
     */

    public void SyncFPStoScreenRefreshRate(){
        this.FPS = gc.getDevice().getDisplayMode().getRefreshRate();
    }

    public void setFullScreen(boolean fullScreen){
        isFullScreen = fullScreen;
        gc.getDevice().setFullScreenWindow(isFullScreen ? this : null);
    }

    public void toogleFullScreen(){
        isFullScreen = !isFullScreen;
        gc.getDevice().setFullScreenWindow(isFullScreen ? this : null);
    }

    protected void StartLoop(){
        final Timer t = new Timer();
        TimerTask tt = new TimerTask(){
            @Override
            public void run() {
                GameLoop();
            }
        };
        //if fps = 0 loop immediately (this can use for a benchmark to calculate how many fps we can reach)
       t.scheduleAtFixedRate(tt, 0, FPS == 0 ? 1 : 1000 / FPS);
    }
    protected void GameLoop(){
        EndTime = System.currentTimeMillis();
        elapsedTime = EndTime - StartTime;
        StartTime = EndTime;

        Graphics2D g2 = (Graphics2D)BackBuffer.getDrawGraphics();
        Clear(g2);
        Update(elapsedTime);
        Draw(g2);
        if(DebugMode)DebugDraw(g2);
        Render();
        CheckCanvasSize();

        g2.dispose();
    }

    protected void Clear(Graphics2D g2){
        g2.setColor(Color.black);
        g2.fillRect(0, 0, this.getWidth(), this.getHeight());
    }

    protected void Update(long elapsedTime){
        TotalGameRuningTime += elapsedTime;
        for(int i = 0; i < WorldStepCount; i++) world.step();
        for(IComponent c : Components) c.Update(elapsedTime);
    }

    protected void Draw(Graphics2D g2){
        frameCounter++;
        if(this.getWidth() != designX && this.getHeight() != designY){
            double zoomX = this.getWidth() / 800.0;
            double zoomY = this.getHeight() / 600.0;
            g2.scale(zoomX, zoomY);
        }
        for(IComponent c : Components){
            c.Draw(g2);
        }
    }

    protected void DebugDraw(Graphics2D g2){
        g2.setColor(Color.white);
        g2.drawString("Fps: " + CalculateFPS(), 30, 40);
        g2.drawString("Total Energy: " + world.getTotalEnergy(), 30, 60);
        g2.drawString("Delta Time: " + elapsedTime, 30, 80);
        g2.drawString("Total Frame Count: " + frameCounter + "s", 30, 100);
        g2.drawString("Total Game Time: " + TotalGameRuningTime / 1000 + "s", 30, 120);
    }

    protected void Render(){
        if(!BackBuffer.contentsLost())
            BackBuffer.show();
        toolkit.sync();//i don't know is it really necessary,didn't notice any changes after putting this line here
   }

    /*
     * if frame and canvas size isn't equal,set canvas size to frame size
     */

    protected void CheckCanvasSize(){
        if(this.getSize()!= Canvas.getSize())Canvas.setSize(this.getSize());
    }

    protected float CalculateFPS(){
        return  frameCounter * 1000 / TotalGameRuningTime;
    }

    private int GetLostFrameCount(){
        float fps = CalculateFPS();
        return (int) (fps > 1000 / FPS ? 0 : 1000 / FPS - fps);
    }
}


And how can i catch when window bounds or size change except checking it on every loop to resize canvas?
Offline zoto

Senior Member


Medals: 4



« Reply #6 - Posted 2010-05-09 11:29:55 »

Quote
And how can i catch when window bounds or size change except checking it on every loop to resize canvas?
You can use a componentListener http://java.sun.com/docs/books/tutorial/uiswing/events/componentlistener.html.
Pages: [1]
  ignore  |  Print  
 
 
You cannot reply to this message, because it is very, very old.

 

Add your game by posting it in the WIP section,
or publish it in Showcase.

The first screenshot will be displayed as a thumbnail.

BurntPizza (14 views)
2014-09-19 03:14:18

Dwinin (32 views)
2014-09-12 09:08:26

Norakomi (58 views)
2014-09-10 13:57:51

TehJavaDev (80 views)
2014-09-10 06:39:09

Tekkerue (40 views)
2014-09-09 02:24:56

mitcheeb (62 views)
2014-09-08 06:06:29

BurntPizza (45 views)
2014-09-07 01:13:42

Longarmx (31 views)
2014-09-07 01:12:14

Longarmx (37 views)
2014-09-07 01:11:22

Longarmx (36 views)
2014-09-07 01:10:19
List of Learning Resources
by Longor1996
2014-08-16 10:40:00

List of Learning Resources
by SilverTiger
2014-08-05 19:33:27

Resources for WIP games
by CogWheelz
2014-08-01 16:20:17

Resources for WIP games
by CogWheelz
2014-08-01 16:19:50

List of Learning Resources
by SilverTiger
2014-07-31 16:29:50

List of Learning Resources
by SilverTiger
2014-07-31 16:26:06

List of Learning Resources
by SilverTiger
2014-07-31 11:54:12

HotSpot Options
by dleskov
2014-07-08 01:59:08
java-gaming.org is not responsible for the content posted by its members, including references to external websites, and other references that may or may not have a relation with our primarily gaming and game production oriented community. inquiries and complaints can be sent via email to the info‑account of the company managing the website of java‑gaming.org
Powered by MySQL Powered by PHP Powered by SMF 1.1.18 | SMF © 2013, Simple Machines | Managed by Enhanced Four Valid XHTML 1.0! Valid CSS!