Using the Full-Screen Exclusive Mode API in Java, Page 2
Run the Program
I encourage you to copy the code from Listing 26 and Listing 27 into your text editor, compile it, and execute it. Experiment with it, making changes, and observing the results of your changes.
You will need some images
Figure 4 contains links to the image files that you will need to run the program named FullScreen02.
Figure 4. GIF image files that you will need.
You should be able to capture the images by right-clicking on them individually, and then saving them into files on your local disk. Having done that, you will need to rename the files to match the names that are hard-coded into the program.
Resize the background image
In addition, you will need to resize the background image to cause it to match the size of your computer screen. You will need an image processing program such as LView to resize the image. In case you don't already have one, a trial version is available for downloading.
Image resizing within the program
As you will see in the comments in the program, it is supposed to be possible to cause the image file to be resized when it is loaded by the program. I was unable to get that to work properly, but I didn't spend much time troubleshooting the problem.
Summary
In this lesson, I showed you how to use the Full-Screen Exclusive Mode API to write programs that take over the entire screen, as shown by the output from the animation program in Figure 3.
I also showed you how to use active rendering as opposed to passive rendering to eliminate the overhead associated with passive rendering.
References
The program named FullScreen02 is an update to a program named Animate03, first published in the last lesson in the following list.
- 1450 Fun with Java: Sprite Animation, Part 1
- 1452 Fun with Java: Sprite Animation, Part 2
- 1454 Fun with Java: Sprite Animation, Part 3
- 1456 Fun with Java: Sprite Animation, Part 4
- 1458 Fun with Java: Sprite Animation, Part 5
- 1460 Fun with Java: Sprite Animation, Part 6
- 1462 Fun with Java: Sprite Animation, Part 7
- 1464 Fun with Java: Frame Animation
- 1466 Fun with Java: Animated Sea Worms
The program named Animate03 uses material published in the earlier lessons in the above list.
Complete Program Listings
/*FullScreen01.java
This is a skeleton program that implements the
Full-Screen Exclusive Mode
The program places an undecorated non-resizable JFrame
object on the screen in the Full-Screen Exclusive Mode.
A JButton appears in the North location of the JFrame.
Clicking the button causes the program to exit the full-
screen mode, restore the original graphics mode, and
terminate.
The program places red, green, and white JLabels in the
East, West, South, and Center locations solely to
demonstrate that the graphics object is an undecorated
non-resizable JFrame object.
The program displays a list of the available graphics
devices solely for information purposes in the command-
line window. However, that window is hidden behind the
full-screen version of the JFrame object and isn't visible
until the full-screen mode is terminated.
Even though the program displays a list of all of the
graphics devices, it operates only on the first graphics
device in the list.
Tested using J2SE5.0 under WinXP. J2SE 1.4 or later is
required for the setFullScreenWindow method of the
GraphicsDevice object.
**********************************************************/
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.event.*;
public class FullScreen01 extends JFrame
implements ActionListener{
private GraphicsDevice graphicsDevice;
private DisplayMode origDisplayMode;
private JButton exitButton = new JButton(
"Exit Full-Screen Mode");
public static void main(String[] args){
//Get and display a list of graphics devices solely for
// information purposes.
GraphicsEnvironment graphicsEnvironment =
GraphicsEnvironment.getLocalGraphicsEnvironment();
GraphicsDevice[] devices =
graphicsEnvironment.getScreenDevices();
for(int cnt = 0;cnt < 1;cnt++){
System.out.println(devices[cnt]);
}//end for loop
//Construct a full-screen object using
// graphicsDevice 0.
new FullScreen01(devices[0]);
}//end main
//Constructor
public FullScreen01(GraphicsDevice graphicsDevice){
//Save a reference to the graphics device as an
// instance variable so that it can be used later to
// exit the full-screen mode.
this.graphicsDevice = graphicsDevice;
setTitle("This title will be hidden (undecorated)");
//Get and save a reference to the original display
// mode as an instance variable so that it can be
// restored later.
origDisplayMode = graphicsDevice.getDisplayMode();
//Register an action listener on the exitButton.
exitButton.addActionListener(this);
//Place the exitButton in the JFrame
getContentPane().add(exitButton, BorderLayout.NORTH);
//Place four labels in the JFrame solely for the
// purpose of showing that it is a full-screen
// undecorated JFrame.
JLabel eastLabel = new JLabel(" East ");
eastLabel.setOpaque(true);
eastLabel.setBackground(Color.RED);
getContentPane().add(eastLabel,BorderLayout.EAST);
JLabel southLabel =
new JLabel("South",SwingConstants.CENTER);
southLabel.setOpaque(true);
southLabel.setBackground(Color.GREEN);
getContentPane().add(southLabel,BorderLayout.SOUTH);
JLabel westLabel = new JLabel(" West ");
westLabel.setOpaque(true);
westLabel.setBackground(Color.RED);
getContentPane().add(westLabel,BorderLayout.WEST);
JLabel centerLabel =
new JLabel("Center",SwingConstants.CENTER);
centerLabel.setOpaque(true);
centerLabel.setBackground(Color.WHITE);
getContentPane().add(centerLabel,BorderLayout.CENTER);
if (graphicsDevice.isFullScreenSupported()){
// Enter full-screen mode witn an undecorated,
// non-resizable JFrame object.
setUndecorated(true);
setResizable(false);
//Make it happen!
graphicsDevice.setFullScreenWindow(this);
validate();
}else{
System.out.println("Full-screen mode not supported");
}//end else
}//end constructor
//The following method is invoked when the used clicks
// the exitButton
public void actionPerformed(ActionEvent evt){
//Restore the original display mode
graphicsDevice.setDisplayMode(origDisplayMode);
//Terminate the program
System.exit(0);
}//end actionPerformed
}//end class
|
/*FullScreen02.java
Copyright 2006, R.G.Baldwin
The purpose of this program is to demonstrate the use of
the Full-Screen Exclusive Mode API for simulation and
animation.
This program is an update to the earlier program named
Animate03 as described in the earlier lesson number
Java1466. This program has been modernized to
make use of the Swing Timer class as an animation timer,
and also to use Active Rendering (as opposed to Passive
Rendering) in Full-Screen Exclusive Mode. It has also been
modernized to use generics.
The program animates colored worms on a background image
in Full-Screen Exclusive mode. See the discussion of
Active Rendering versus Passive Rendering in The Java
Tutorial at:
http://java.sun.com/docs/books/tutorial/extra/fullscreen/
index.html
Using Active Rendering, the program does not call the
repaint method to ask the operating system to call the
update method. Rather, the program invokes a method named
activeRenderer, which draws the animated sprites on the
screen without concern for sharing the screen with other
applications. (There are no other applications on the
screen in full-screen mode.)
The program places an undecorated non-resizable JFrame
object on the screen in Full-Screen Exclusive Mode.
A JButton appears in the North location of the JFrame.
Clicking the button causes the program to exit the full-
screen mode, restore the original graphics mode, and
terminate.
A JPanel appears in the center of the JFrame object.
The colored worms are animated as sprites on the JPanel.
A background image is drawn on the JPanel at the beginning
of each animation cycle. This image erases the sprites
that were previously there creating a clean slate for
drawing the sprites in their new positions. If the
background image is eliminated, the worms turn into long
tubes because the old sprite images are never erased.
The background image that is used fits a 1024 x 768
screen in Full-Screen Exclusive mode. If the screen is
a different size, a different size background image is
needed.
Tested using J2SE5.0 under WinXP. J2SE 1.4 or later is
required for the setFullScreenWindow method of the
GraphicsDevice object. J2SE 5.0 or later is required
to support generics.
**********************************************************/
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.event.*;
import java.util.*;
class FullScreen02 extends JFrame
implements ActionListener{
private GraphicsDevice graphicsDevice;
private DisplayMode origDisplayMode;
private JButton exitButton = new JButton(
"Exit Full-Screen Mode Copyright 2006, R.G.Baldwin");
public static void main(String[] args){
//Get a list of available graphics devices.
GraphicsEnvironment graphicsEnvironment =
GraphicsEnvironment.getLocalGraphicsEnvironment();
GraphicsDevice[] devices =
graphicsEnvironment.getScreenDevices();
//Construct a full-screen object using the first
// graphics device in the array. Ignore the others, if
// there are any.
new FullScreen02(devices[0]);
}//end main
//-----------------------------------------------------//
//Constructor
public FullScreen02(GraphicsDevice graphicsDevice){
//Save a reference to the graphics device as an
// instance variable so that it can be used later to
// exit the full-screen mode.
this.graphicsDevice = graphicsDevice;
setTitle("This title will be hidden (undecorated)");
//Get and save a reference to the original display
// mode as an instance variable so that it can be
// restored later.
origDisplayMode = graphicsDevice.getDisplayMode();
//Register an action listener on the exitButton.
exitButton.addActionListener(this);
//Place the exitButton at the top of the JFrame
getContentPane().add(exitButton,BorderLayout.NORTH);
//Create an animation panel and place it in the center
// of the JFrame.
getContentPane().add(new AnimationPanel());
if(graphicsDevice.isFullScreenSupported()){
// Enter full-screen mode witn an undecorated,
// non-resizable JFrame object.
setUndecorated(true);
setResizable(false);
graphicsDevice.setFullScreenWindow(this);
validate();
}else{
System.out.println("Full-screen mode not supported");
}//end else
}//end constructor
//-----------------------------------------------------//
//The following method is invoked when the used clicks
// the exitButton
public void actionPerformed(ActionEvent evt){
//Restore the original display mode
graphicsDevice.setDisplayMode(origDisplayMode);
//Terminate the program
System.exit(0);
}//end actionPerformed
//-----------------------------------------------------//
}//end class FullScreen02
//=======================================================//
//This is a convenience class that makes it a little
// easier to deal with the background image. Note that
// much of the impetus for this class went away when the
// animation program named Animate 03 was converted to
// full-screen mode. Several convenience methods having to
// do with the size of the background image were eliminated
// at that time.
class BackgroundImage{
private Image image;
private Component component;
public BackgroundImage(Component component,Image image){
this.component = component;
this.image = image;
}//end construtor
public void drawBackgroundImage(Graphics g){
//Note that component is an ImageObserver in the
// following statement.
g.drawImage(image,0,0,component);
}//end drawBackgroundImage()
}//end class BackgroundImage
//=======================================================//
//An object of this class manages a collection of animated
// sprites stored in an ArrayList object. (A Vector
// object was used in the earlier version named Animate03.)
// Note that this class also underwent some modernization
// with respect to the use of generics as released in
// J2SE 5.0.
class SpriteManager{
private ArrayList <Sprite> theSprites =
new ArrayList<Sprite>();
private BackgroundImage backgroundImage;
private int panelWidth;
private int panelHeight;
//-----------------------------------------------------//
public SpriteManager(BackgroundImage backgroundImage,
int panelWidth,
int panelHeight){
this.backgroundImage = backgroundImage;
this.panelWidth = panelWidth;
this.panelHeight = panelHeight;
}//end constructor
//-----------------------------------------------------//
public Point getEmptyPosition(Dimension spriteSize){
Rectangle trialSpaceOccupied = new Rectangle(
0,0,spriteSize.width,spriteSize.height);
Random rand = new Random(System.currentTimeMillis());
boolean empty = false;
int numTries = 0;
//Search for an empty position. If an empty position
// can't be found after 100 tries, give up and allow
// two sprites to occupy the same initial location.
while(!empty && numTries++ < 100){
// Get a trial position
trialSpaceOccupied.x = Math.abs(
rand.nextInt() % panelWidth);
trialSpaceOccupied.y = Math.abs(
rand.nextInt() % panelHeight);
// Iterate through existing sprites, checking if
// position is empty
boolean collision = false;
for(int cnt = 0;cnt < theSprites.size();cnt++){
Rectangle testSpaceOccupied =
theSprites.get(cnt).getSpaceOccupied();
if(trialSpaceOccupied.intersects(
testSpaceOccupied)){
collision = true;
}//end if
}//end for loop
empty = !collision;
}//end while loop
return new Point(trialSpaceOccupied.x,
trialSpaceOccupied.y);
}//end getEmptyPosition()
//-----------------------------------------------------//
//This method updates the state information for each of
// the sprites.
public void updateSprites(){
Sprite sprite;
//Iterate through sprite list
for(int cnt = 0;cnt <
|
Copyright 2006, Richard G. Baldwin. Reproduction in whole or in part in any form or medium without express written permission from Richard Baldwin is prohibited.
About the author
Richard Baldwin is a college professor (at Austin Community College in Austin, TX) and private consultant whose primary focus is a combination of Java, C#, and XML. In addition to the many platform and/or language independent benefits of Java and C# applications, he believes that a combination of Java, C#, and XML will become the primary driving force in the delivery of structured information on the Web.Richard has participated in numerous consulting projects and he frequently provides onsite training at the high-tech companies located in and around Austin, Texas. He is the author of Baldwin's Programming Tutorials, which have gained a worldwide following among experienced and aspiring programmers. He has also published articles in JavaPro magazine.
In addition to his programming expertise, Richard has many years of practical experience in Digital Signal Processing (DSP). His first job after he earned his Bachelor's degree was doing DSP in the Seismic Research Department of Texas Instruments. (TI is still a world leader in DSP.) In the following years, he applied his programming and DSP expertise to other interesting areas including sonar and underwater acoustics.
Richard holds an MSEE degree from Southern Methodist University and has many years of experience in the application of computer technology to real-world problems.

