Java-Gaming.org    
Featured games (79)
games approved by the League of Dukes
Games in Showcase (477)
Games in Android Showcase (107)
games submitted by our members
Games in WIP (536)
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  
  Simple Full screen/Windowed Framework  (Read 7142 times)
0 Members and 1 Guest are viewing this topic.
Offline JavaNoob

Senior Newbie





« Posted 2002-11-08 19:40:57 »

For my fellow noobs: this code shows how to implement a basic game loop.  It puts the display into full screen exclusive mode or, if that's not available, a window of a fixed size, then loops until the "game"  is over, then exits.  It should compile and run as-is (it does for me on my Windows boxen).

It uses double buffering, so animation is smooth and flicker-free.

For those who know oh so much more than I do (most of you I imagine):  is this code correct?  Am I missing anything?

This is what I came up with after many hours of looking at many different examples.  I was trying to boil them all down to the barest essentials.  I didn't really understand Jeff's code until I got mine working, then his made sense to me.  I figured other newbies like myself might like something simpler with more comments...

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  
import java.awt.*;
import java.awt.image.BufferStrategy;


public class Test
{
   // Our main method simply invokes an instance of our application. We pass it a boolean
  // argument that is TRUE if we want full screen exclusive mode, or false if we want a
  // window.

   public static void main( String[] args )
   {
      Test test = new Test( true );
      System.exit( 0 );
   }


   // This is an array of the desired full screen graphics modes, in the order we most
  // prefer them.  If we request full screen mode, and this system supports it, then the
  // first entry here that matches a supported mode will be used.

   private static DisplayMode[] PreferredModes = new DisplayMode[]
   {
      new DisplayMode( 800, 600, 32, 0 ),
      new DisplayMode( 800, 600, 16, 0 ),
      new DisplayMode( 800, 600, 8, 0 )
   };


   // This method finds the best matching full screen mode from the array above that is
  // supported on this system.

   private DisplayMode bestmode( GraphicsDevice gd )
   {
      // Get the list of supported modes on this system

      DisplayMode[] modes = gd.getDisplayModes();

      // For every mode we'd prefer to use...

      for( int j = 0; j < PreferredModes.length; j++ )
      {
         // ...we check it against each mode the system supports...

         for( int i = 0; i < modes.length; i++ )
         {
            // ...and if we find a matching entry we return it.

            if( modes[i].getWidth() == PreferredModes[j].getWidth()
                && modes[i].getHeight() == PreferredModes[j].getHeight()
                && modes[i].getBitDepth() == PreferredModes[j].getBitDepth() )
               return PreferredModes[j];
         }
      }

      // ...we couldn't find a matching mode, return null.

      return null;
   }


   // "Globals"

   Frame mainFrame;
   BufferStrategy bufferStrategy;

   int ScreenWidth;
   int ScreenHeight;

   boolean Running = true;


   // Our appliclation

   public Test( boolean fs )
   {
      GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
      GraphicsDevice gd = ge.getDefaultScreenDevice();
      GraphicsConfiguration gc = gd.getDefaultConfiguration();
      DisplayMode dm = bestmode( gd );

      // If we can't have one of our preferred display modes, or the system does not support
     // full screen exclusive mode, then we'll stick with a window.

      if( dm == null || gd.isFullScreenSupported() == false )
         fs = false;

      // Create our main frame and set attributes common to both FS and windowed modes.

      mainFrame = new Frame( gc );
      mainFrame.setLayout( null );
      mainFrame.setIgnoreRepaint( true );

      // If full screen is wanted (and possible), set it up.

      if( fs )
      {
         mainFrame.setUndecorated( true );      // No window decorations
        gd.setFullScreenWindow( mainFrame );   // Create a full screen window
        gd.setDisplayMode( dm );               // Change to our preferred mode
        ScreenWidth = dm.getWidth();           // Get the screen dimensions
        ScreenHeight = dm.getHeight();
      }

      // Otherwise we use a window with a fixed size

      else
      {
         ScreenWidth = 800;                     // Default window size
        ScreenHeight = 600;
         mainFrame.setSize( new Dimension( ScreenWidth, ScreenHeight ) );
         mainFrame.show();                      // Show it
     }

      // Set up our buffer strategy (with double buffering)

      mainFrame.createBufferStrategy( 2 );
      bufferStrategy = mainFrame.getBufferStrategy();

      // Main game loop

      while( Running )
      {
         // This is where you would call a method that updates your game state (ie: moves
        // objects, checks for collisions, etc.

         // updategame();

         // Call our render function to draw everything.

         render();

         // Sleep

         try
         {
            Thread.sleep( 30 );  // This should be replaced with proper frame rate limiting code
        } catch( InterruptedException e ) {}
      }
   }


   // A variable used with render()

   int i = 0;

   // This method is called once every frame to display the current state of our game.

   private void render()
   {
      // If we've lost our video memory, don't bother drawing anything

      if( !bufferStrategy.contentsLost() )
      {
         Graphics g = bufferStrategy.getDrawGraphics();

         // Clear the drawing buffer to white
        g.setColor( Color.white );
         g.fillRect( 0, 0, ScreenWidth, ScreenHeight );

         // Say hello
        g.setColor( Color.black );
         g.drawString( "Hello World!", i, i );

         // We'll stop after 400 frames.
        i++;
         if( i > 400 )
            Running = false;

         bufferStrategy.show();
         g.dispose();
      }
   }
}
Offline Jeff

JGO Coder




Got any cats?


« Reply #1 - Posted 2002-11-08 20:22:35 »

Well you might want to consider tripple buffering if you have the video RAM for it.  (I explained why over in the BufferFlipping thread)

Got a question about Java and game programming?  Just new to the Java Game Development Community?  Try my FAQ.  Its likely you'll learn something!

http://wiki.java.net/bin/view/Games/JeffFAQ
Offline JavaNoob

Senior Newbie





« Reply #2 - Posted 2002-11-08 20:38:13 »

Thanks for the tip. I've used triple buffering in other games in other languages but not in Java.

Am I correct to think that triple buffering is as simple as changing the 2 to a 3 in the call to createBufferStategy()?
Games published by our own members! Check 'em out!
Legends of Yore - The Casual Retro Roguelike
Offline Silicon_Munky

Senior Newbie




Java games rock!


« Reply #3 - Posted 2003-01-02 06:38:44 »

Yeah I beleive you are correct.
Offline talk2jelliott

Innocent Bystander




Java games rock!


« Reply #4 - Posted 2003-01-09 21:20:37 »

Tried your code sample and was unable to set Full-Screen Exclusive mode. I am assuming this capability is not supported under Linux. Anyone know for sure?
Offline darcone

Junior Member




Size matters


« Reply #5 - Posted 2003-03-14 12:00:43 »

Thanks alot m8, your code is worth gold, Smiley
Offline whome

Junior Member




Carte Noir Java


« Reply #6 - Posted 2003-04-13 15:28:59 »

I have infamous Millennium G400 card. I made few tests with your test program which could isolate few problems encountered in G400.

Env: Cel500Mhz/Win2k/256MB/G400 16MB driver v5.88.061/DirectX8.1

Original code does not work, but is freezed to black screen. I made tests and freezed on this call
"mainFrame.createBufferStrategy( 2 );". Changing param to 1 made success but I would not call it a smooth scrolling.
1  
2  
3  
4  
5  
6  
  private static DisplayMode[] PreferredModes = new DisplayMode[] 
   {
 new DisplayMode( 800, 600, 32, 0 ),
 new DisplayMode( 800, 600, 16, 0 ),
 new DisplayMode( 800, 600, 8, 0 )
   };



Tweaked code and this works in G400. Using only 800x600/8/0 mode displays the white screen and "hello world" text is scrolled down.
1  
2  
3  
4  
5  
6  
7  
8  
   private static DisplayMode[] PreferredModes = new DisplayMode[] { 
// DOES NOT WORK
//   new DisplayMode( 800, 600, 32, 0 )
// DOES WORK
    new DisplayMode( 800, 600, 8, 0 )
// DOES NOT WORK
//     new DisplayMode( 800, 600, 16, 0 )
  };


What does that mean? I don't know for sure, but maybe Java is fooled by G400 promising too much about its features.
Offline altair

Senior Newbie





« Reply #7 - Posted 2003-04-13 23:22:24 »

There is a bug that was fixed only in 1.4.2 beta that caused the system to freeze with MGA400 (reference 4738111). You might want to upgrade you JVM.

Id did the test with bufferstrategy 1 then 2 and 32 bit depth and both run smoothly. (Win XP, Atlhon 1700+, MGA 400, JVM 1.4.2 beta, drivers matrox 5.72.021).
Offline mill

Junior Member




popcorn freak


« Reply #8 - Posted 2003-04-14 12:16:12 »

Quote
Tried your code sample and was unable to set Full-Screen Exclusive mode. I am assuming this capability is not supported under Linux. Anyone know for sure?


no real fullscreen in linux unfortunately. you have to use an undecorated frame with the same size as the screen to make it look like it's fullscreen.

Offline whome

Junior Member




Carte Noir Java


« Reply #9 - Posted 2003-04-16 11:41:57 »

Tested with new Win2k/G400 v5.88.061/Sun JDK1.4.2beta and all three modes worked ok.
new DisplayMode( 800, 600, 32, 0 );
new DisplayMode( 800, 600, 8, 0 );
new DisplayMode( 800, 600, 16, 0 );
Games published by our own members! Check 'em out!
Legends of Yore - The Casual Retro Roguelike
Offline MisterBob

Senior Newbie




Developing: 2D Space Shooter &amp; RPG


« Reply #10 - Posted 2003-05-26 22:42:11 »

Tag in case i decide to do some non-applet games Smiley

Offline zulo

Junior Member




Java games rock!


« Reply #11 - Posted 2004-01-08 13:33:04 »

if you want to split it up a bit you can use this FullScreen.java class, and make the main app extend it.

if you see something weird then give me some hints about it so i can make it better.

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  
import java.awt.Dimension;
import java.awt.DisplayMode;
import java.awt.Frame;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.image.BufferStrategy;


public class FullScreen
  {
    //      "Globals"
   protected static Frame mainFrame;
    private static DisplayMode[] PreferredModes = new DisplayMode[]
        {
            new DisplayMode(640, 480, 32, 60),
        };
    protected BufferStrategy bufferStrategy;
    protected int ScreenWidth = 640;
    protected int ScreenHeight = 480;
    protected boolean Running = true;
    protected FpsCounter fps = new FpsCounter();
    private int delay = 5; // 12 fps++

    // Our appliclation
   public FullScreen (boolean fs)
      {
        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
        GraphicsDevice gd = ge.getDefaultScreenDevice();
        GraphicsConfiguration gc = gd.getDefaultConfiguration();
        DisplayMode dm = bestmode(gd);

        // If we can't have one of our preferred display modes, or the system does not support
       // full screen exclusive mode, then we'll stick with a window.
       if ((dm == null) || (gd.isFullScreenSupported() == false))
        {
            fs = false;
          }

        // Create our main frame and set attributes common to both FS and windowed modes.
       mainFrame = new Frame(gc);
        mainFrame.setLayout(null);
        mainFrame.setIgnoreRepaint(true);

        // If full screen is wanted (and possible), set it up.
       if (fs)
          {
            mainFrame.setUndecorated(true); // No window decorations
           gd.setFullScreenWindow(mainFrame); // Create a full screen window
           gd.setDisplayMode(dm); // Change to our preferred mode
           ScreenWidth = dm.getWidth(); // Get the screen dimensions
           ScreenHeight = dm.getHeight();
          }

        // Otherwise we use a window with a fixed size
       else
          {
            ScreenWidth = 320; // Default window size
           ScreenHeight = 200;
            mainFrame.setSize(new Dimension(ScreenWidth, ScreenHeight));
            mainFrame.show(); // Show it
         }

        // Set up our buffer strategy (with double buffering)
       mainFrame.createBufferStrategy(3);
        bufferStrategy = mainFrame.getBufferStrategy();
      }

    public static void main (String[] args)
      {
        FullScreen test = new FullScreen(true);
        System.exit(0);
      }

    private DisplayMode bestmode (GraphicsDevice gd)
      {
        // Get the list of supported modes on this system
       DisplayMode[] modes = gd.getDisplayModes();

        // For every mode we'd prefer to use...
       for (int j = 0; j < PreferredModes.length; j++)
          {
            // ...we check it against each mode the system supports...
           for (int i = 0; i < modes.length; i++)
              {
                // ...and if we find a matching entry we return it.
               if ((modes[i].getWidth() == PreferredModes[j].getWidth()) &&
                        (modes[i].getHeight() == PreferredModes[j].getHeight()) &&
                        (modes[i].getBitDepth() == PreferredModes[j].getBitDepth()))
                {
                    return PreferredModes[j];
                  }
              }
          }

        // ...we couldn't find a matching mode, return null.
       return null;
      }
  }


then extend it like this

public class MyGameApp extends FullScreen

and in the main loop

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  
while(running){

      move();

      //draw
     g = bufferStrategy.getDrawGraphics();
      g.setColor(Color.white);
                       
      try
      {
        render(g, map);
      }
      finally
      {
      g.dispose();
      }
      bufferStrategy.show();                                  
                                   
      //dispose
     g.dispose();
           
                        bufferStrategy.show();*/
           
      Thread.yield();
      }
}
Offline whome

Junior Member




Carte Noir Java


« Reply #12 - Posted 2005-05-11 11:15:26 »

specs: winxp/ATIMobilityRadeon9000-64MB

http://wiki.java.net/bin/view/Games/SimpleFullscreenWindowedFramework

Problems with contentsLost event. I just thought BufferStrategy should handle contentsLost event and recreate what needs to be done.

I run the example code in windowed mode, resize window to smaller, then resize window to larger. From now on contentsLost always return true and buffer is lost.

I then copied two init methods to recreate entire bufferstrategy instance. This fixed it but is it safe to do so in renderer loop.

How do you handle contentsLost event?

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  
  private void render() {
    // buffer lost, recreate
   if( bufferStrategy.contentsLost() ) {
       // if I comment createBuff.. and getBuffer methods
      // then it never recover the contentsLost state.
      mainFrame.createBufferStrategy( 2 ); // or use 3
      bufferStrategy = mainFrame.getBufferStrategy();
       return;
    }

    Graphics g = bufferStrategy.getDrawGraphics();

    // Clear the drawing buffer to white
   g.setColor( Color.white );
    g.fillRect( 0, 0, ScreenWidth, ScreenHeight );
 
    // Say hello
   g.setColor( Color.black );
    g.drawString( "Hello World!", i, i );
 
    // We'll stop after 400 frames.
   i++;
    if( i > 400 )
      Running = false;
 
    bufferStrategy.show();
    g.dispose();
 }


EDIT 2005-05-16: answered in an another thread.
Comment From Trembovetski: "This looks correct"
Offline triple-ace

Senior Newbie





« Reply #13 - Posted 2005-09-01 10:25:00 »

Well you might want to consider tripple buffering if you have the video RAM for it.  (I explained why over in the BufferFlipping thread)

sorry... just want to know, where do i can read those thread (BufferFlipping), i've been searching and didn't found it.

TiA
Offline Tzan

Junior Member





« Reply #14 - Posted 2005-09-01 17:25:25 »

Some links, this isnt what they were talking about but its good stuff Smiley

The demo code here is for 1.6, 1.5 and lower you still need to recreate the BufferStrategy when the contents are lost
There is an example of that in this thread above.
http://download.java.net/jdk6/docs/api/java/awt/image/BufferStrategy.html


http://java.sun.com/j2se/1.5.0/docs/guide/2d/new_features.html#ogl
http://today.java.net/cs/user/print/a/147
http://java.sun.com/j2se/1.5.0/docs/guide/2d/flags.html
http://weblogs.java.net/blog/chet/archive/2004/08/toolkitbuffered.html 
Offline jonask84

Senior Newbie




Can't make it? Simulate it!


« Reply #15 - Posted 2005-09-18 17:31:15 »

Very nice gode. Maybe i should make my next game for fullscreen
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.

Riven (12 views)
2014-07-29 18:09:19

Riven (8 views)
2014-07-29 18:08:52

Dwinin (9 views)
2014-07-29 10:59:34

E.R. Fleming (25 views)
2014-07-29 03:07:13

E.R. Fleming (10 views)
2014-07-29 03:06:25

pw (39 views)
2014-07-24 01:59:36

Riven (39 views)
2014-07-23 21:16:32

Riven (27 views)
2014-07-23 21:07:15

Riven (28 views)
2014-07-23 20:56:16

ctomni231 (59 views)
2014-07-18 06:55:21
HotSpot Options
by dleskov
2014-07-08 03:59:08

Java and Game Development Tutorials
by SwordsMiner
2014-06-14 00:58:24

Java and Game Development Tutorials
by SwordsMiner
2014-06-14 00:47:22

How do I start Java Game Development?
by ra4king
2014-05-17 11:13:37

HotSpot Options
by Roquen
2014-05-15 09:59:54

HotSpot Options
by Roquen
2014-05-06 15:03:10

Escape Analysis
by Roquen
2014-04-29 22:16:43

Experimental Toys
by Roquen
2014-04-28 13:24:22
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!