SlideShare a Scribd company logo
1 of 102
Download to read offline
CONTENTS
Chapter Page No.
Project Title
Project Certificate
Acknowledgement
Abstract
Tables and figures
1. Introduction 1
1.1 Activity Diagram for the Game 2
1.2.States Of the Game 3
4. Output shots and sourcecode of Project 14
2. Related Theory 23
3. Diagrams Related Theory 29
7. Action Listener in Java 35
8. Key Listener In Java 41
9. Java Multithreading 49
10. Java 2D 66
11. Conclusion 100
12. Bibliography 101
System Requirement Analysis and Specification
System Requirement Analysis And Specifications
Introduction
1. PURPOSE:
The purpose of this SRS document is to specify software
requirements of the Game Tron. It is intended to be a complete
specification of what functionality the game provides.
2. PROJECT SCOPE:
 To develop a platform independent gaming system
 Providing an interactive and rich GUI to users
 Developing a game that is easy to play and interesting
3. ABBREVIATIONS:
 S/W – software
 H/W - hardware
 TCP/IP – Transmission control Protocol/Internet Protocol
4. REFERENCES:
 Complete Reference :java 2 by Herbert Schildt
 http://java.sun.com/
 http://www.networkcomputing.com/
5. OVERVIEW:
SRS will include 2 sections
Overall description will describe major components of the system,
interconnection and external interfaces.
Specific Requirements will describe the functions of actors, their
roles in the system and constraints.
Overall Description
Product Perspective:
The product is viewed with a sense of providing better, efficient
and less time consuming system for connecting and sharing
information over the network.
1. Hardware Interface
USER SIDE
PROCESSOR RAM DISK SPACE
OS (windows
or linux or
mac)
Pentium II at
400 MHz
44 MB 4 GB
SYSTEM SIDE
OS(windows
or linux or
mac)
Pentium II at 1
GHz
412 MB 4 GB
Table.1
2. Software Interface
USER
Software Platform
JRE1
Windows, Mac, Linux
SYSTEM
Software Platform
JRE1
Windows
JDK 4 Windows
Netbeans7.0 Windows
Table.2
3. User Interface
Game Window with easy to use features
Keys Provided for two user
4. Operation
The Two players start the game , playing against each other. The
player who traps the other one wins. The player must also not
touch the walls of the screen and also not touch his ownself.
Constraints
Availability NetBeans7.0 for the system to work
JRE 1.4 or above
Specific Requirements
This section contains the s/w requirements to a level of detail sufficient
to enable designers to design the system and analyze the system.
External Interface
1) User interfaces
1. New Game screen of the Game
2. Player Name enter field option
3. The window for Playing the Game
4. The window for Restarting Or Playing Again
5. It also shows the rules and controls along with the about screen.
2) Hardware Interfaces
1. Screen resolution of at least 800x400 required for proper and
complete view
3) Software interface
1. Windows/mac/linux operating system
2. Netbeans 7.0 to run the file
System Features
1. Fast and efficient process
2. Free
3. Platform independent
Performance requirements
1. Use of latest processor
2. Use of larger amount of memory for storing larger details of data
3. Speedier net connections for improving the speed of process
Software system attributes
1. Maintainability
The system is maintainable as it has been implemented using object
oriented concepts that allow the further modifications to be made
without disturbing the original structure of the system
2. Portability
The s/w being developed in JAVA makes it portable. It is generic in
that it can be used on different platforms.
ABSTRACT
Set during the era between the two TRON films, TRON: Evolution conveys the story of
significant events within the TRON mythology. The game features an epic adventure across a
massive digital world filled with high-mobility disc-based combat and advanced light cycles.
TRON: Evolution is one of the keys to unlocking the TRON mythology. The game's story takes
place before the "TRON: Legacy" events and provides insight into the film's past. As an
integrated entertainment experience, the film will reference elements of the game's story. Fans
will want to play the game to learn more about the TRON mythology seen in the film, but each
entertainment experience will stand on its own...."
CHAPTER ONE
INTRODUCTION
INTRODUCTION
Similar to the classic game “Snake” in that you want to maneuver your wall building cycle until
you run your opponent into wall before they do the same to you.
Tron is a coin-operated arcade video game manufactured and distributed by Bally
Midway in1982. It is based on the Walt Disney Productions motion picture Tron released in the
same year. The game consists of four sub games inspired by the events of the science fiction
film. It features some characters and equipment seen in the film, e.g. the Light Cycles, battle
tanks, the Input/output Tower. The game earned more than the film's initial release.
In 1983, Midway released the sequel arcade game Discs of Tron, which was inspired by the disc
throwing combat sequence of the film. Another sequel followed in 2003 with the computer
game Tron 2.0. On January 10, 2008 the game was released for Xbox Live Arcade ported
from Digital Eclipse and branded by Disney Interactive.
In the 2010 film Tron: Legacy, the arcade game makes a brief appearance, but is displayed as
being manufactured and distributed by the in-universe company ENCOM International instead of
Bally Midway. It is also displayed as such on the "ENCOM International" promotional website
for the film.
1
Activity Diagram For The Game
2
States Of The Game
3
OUTPUTSHOTS AND WORKING
(AS PER USER’S PERSRECTIVE)
Main Menu Of The Game
The user is supposed to click one of the options available as per
his/her choice. If the user has clicked the wrong option, he/she
can move to the previous menu using BACK option. The game
can be exited using EXIT option.
As soon as the user clicks the NEW GAME option, the above
screen is invoked, where the two users can enter their respective
names. The user can switch back to the Main Menu using
BACK option. The START option starts the game.
The above screen gets invoked when the user clicks the START
option. The two users are ready to operate and play the game.
The controls for the two users can be seen using the HELP
option.
The Players try to trap each other using a path. The player who
gets trapped loses.
The above screen shows the working of the game where the two
players are playing, using their respective controls.
The above screen appears when the Red user traps the Blue user,
when the screen shows up the player who wins. Here Red player
wins.
The PLAY AGAIN option starts the game again.
The above screen appears when the Blue user traps the Red user,
when the screen shows up the player who wins. Here Blue
player wins.
The PLAY AGAIN option starts the game again.
The above screen appears when the users collide head-on, which
gives the condition for the game drawn.
The screen shows up the GAME DRAW message.
The game can be resumed by clicking the PLAY AGAIN
option.
The above screen shows up the HELP option, where the controls
have been mentioned for the two users. The user can go back to
the previous menu using BACK option.
CHAPTER TWO
RELATED THEORY
RELATED THEORY
2.1.THE JAVA’S MAGIC:
Java is a programming language originally developed by James Gosling at Sun Microsystems
(which is now a subsidiary of Oracle Corporation) and released in 1995 as a core component of
Sun Microsystems' Java platform. The language derives much of its syntax from C and C++ but
has a simpler object model and fewer low-level facilities. Java applications are typically
compiled to bytecode (class file) that can run on any Java Virtual Machine (JVM) regardless of
computer architecture. Java is a general-purpose, concurrent, class-based, object- oriented
language that is specifically designed to have as few implementation dependencies as possible.
It is intended to let application developers "write once, run anywhere". Java is currently one of
the most popular programming languages in use, and is widely used from application software
to web applications. The original and reference implementation Java compilers, virtual
machines, and class libraries were developed by Sun from 1995. As of May 2007, in
compliance with the specifications of the Java Community Process, Sun relicensed most of its
Java technologies under the GNU General Public License. Others have also developed
alternative implementations of these Sun technologies, such as the GNU Compiler for Java,
GNU Classpath,and Dalvik.James Gosling, Mike Sheridan, and Patrick Naughton initiated the
Java language project in June 1991. Java was originally designed for interactive television, but
it was too advanced for the digital cable television industry at the time. The language was
initially called Oak after an Oak tree that stood - outside Gosling's office; it went by the name
Green later, and was later renamed Java, from a list of random words. Gosling aimed to
implement a virtual machine and a language that had a familiar C/C++ style of notation. Sun
Microsystems released the first public implementation as Java 1.0 in 1995. It promised "Write
Once, Run Anywhere" (WORA), providing no- cost run-times on popular platforms. Fairly
secure and featuring configurable security, it allowed network- and file-access restrictions.
Major web browsers soon incorporated the ability to run Java applets within web pages, and
Java quickly became popular. With the advent of Java 2 (released initially as J2SE 1.2 in
December 1998–1999), new versions had multiple configurations built for different types of
platforms. For example, J2EE targeted enterprise applications and the greatly stripped-down
version J2MEfor mobile applications (Mobile Java). J2SE designated the Standard Edition. In
2006, for marketing purposes, Sun renamed new J2 versions as Java EE, Java ME, and Java SE,
respectively. In 1997, Sun Microsystems approached the ISO/IEC JTC1 standards body and
later the Ecma International to formalize Java.
4
At one time, Sun made most of its Java implementations available without charge, despite their
proprietary software status. Sun generated revenue from Java through the selling of licenses for
specialized products such as the Java Enterprise System. Sun distinguishes between its Software
Development Kit (SDK) and Runtime Environment (JRE) (a subset of the SDK); the primary
distinction involves the JRE's lack of the compiler, utility programs, and header files. On
November 13, 2006, Sun released much of Java as open source software under the terms of the
GNU General Public License (GPL). On May 8, 2007, Sun finished the process, making all of
Java's core code available under free software/open-source distribution terms, aside from a small
portion of code to which Sun did not hold the copyright. Sun's vice-president Rich Green has
said that Sun's ideal role with regards to Java is as an "evangelist." Following Oracle
Corporation's acquisition of Sun Microsystems in 2009–2010, Oracle has described itself as the
"steward of Java technology with a relentless commitment to fostering a community of
participation and transparency".
2.2 PRINCIPALS
There were five primary goals in the creation of the Java language:
1. It should be "simple, object-oriented and familiar".
2. It should be "robust and secure".
3. It should be "architecture-neutral and portable".
4. It should execute with "high performance".
5. It should be "interpreted, threaded, and dynamic".
One characteristic of Java is portability, which means that computer programs written in the
Java language must run - 37 - similarly on any supported hardware/operating-system platform.
This is achieved by compiling the Java language code to an intermediate representation called
Java bytecode, instead of directly to platform-specific machine code. Java bytecode instructions
are analogous to machine code, but are intended to be interpreted by a virtual machine (VM)
written specifically for the host hardware. End-users commonly use a Java Runtime
Environment (JRE) installed on their own machine for standalone Java applications, or in a Web
browser for Java applets. Standardized libraries provide a generic way to access host specific
features such as graphics, threading, and networking. A major benefit of using bytecode is
porting.
5
2.3.THE ANDROID’S MAGIC:
In July 2005, Google acquired Android Inc., a small startup company based in Palo Alto, CA.
Android's co-founders who went to work at Google included Andy Rubin (co-founder of
Danger), Rich Miner (co-founder of Wildfire Communications, Inc), Nick Sears (once VP at T-
Mobile), and Chris White (one of the first engineers at WebTV). At the time, little was known
about the functions of Android Inc. other than they made software for mobile phones.
Open Handset Alliance Founded
On 5 November 2007, the Open Handset Alliance, a consortium of several companies which
include Google, HTC, Intel, Motorola, Qualcomm, T-Mobile, Sprint Nextel and NVIDIA, was
unveiled with the goal to develop open standards for mobile devices. Along with the formation
of the Open Handset Alliance, the OHA also unveiled their first product, Android, an open
source mobile device platform based on the Linux operating system.
Hardware
Google has unveiled at least three prototypes for Android, at the Mobile World Congress on
February 12, 2008. One prototype at the ARM booth displayed several basic Google
applications. A 'd-pad' control zooming of items in the dock with a relatively quick response.
2.4 FEATURES OF ANDROID OS:
 Application framework enabling reuse and replacement of components
 Dalvik virtual machine optimized for mobile devices
 Integrated browser based on the open source WebKit engine
 Optimized graphics powered by a custom 2D graphics library; 3D graphics based on the
OpenGL ES 1.0 specification (hardware acceleration optional)
 SQLite for structured data storage
6
 Media support for common audio, video, and still image formats (MPEG4, H.264, MP3,
AAC, AMR, JPG, PNG, GIF)
I. GSM Telephony (hardware dependent)
II. Bluetooth, EDGE, 3G, and WiFi (hardware dependent)
III. Camera, GPS, compass, and accelerometer (hardware dependent)
IV. Rich development environment including a device emulator, tools for debugging,
memory and performance profiling, and a plugin for the Eclipse IDE
2.5 APPLICATION FRAMEWORK
Developers have full access to the same framework APIs used by the core applications. The
application architecture is designed to simplify the reuse of components; any application can
publish its capabilities and any other application may then make use of those capabilities (subject
to security constraints enforced by the framework). This same mechanism allows components to
be replaced by the user.
Underlying all applications is a set of services and systems, including:
 A rich and extensible set of Views that can be used to build an application, including
lists, grids, text boxes, buttons, and even an embeddable web browser.
 Content Providers that enable applications to access data from other applications (such as
Contacts), or to share their own data
 A Resource Manager, providing access to non-code resources such as localized strings,
graphics, and lat files
 A Notification Manager that enables all applications to display custom alerts in the status
bar
 An Activity Manager that manages the life cycle of applications and provides a common
navigation backstack.
7
2.6 ANDROID ARCHITECTURE
The following diagram shows the major components of Android
Figure 1: Architecture of Android OS
8
2.7 LIBRARIES
Android includes a set of C/C++ libraries used by various components of the Android system.
These capabilities are exposed to developers through the Android application framework. Some
of the core libraries are listed below:
 ·System C library - a BSD-derived implementation of the standard C system library
(libc), tuned for embedded Linux-based devices
 Media Libraries - based on PacketVideo's Open CORE; the libraries support playback
and recording of many popular audio and video formats, as well as static image files,
including MPEG4, H.264, MP3, AAC, AMR, JPG, and PNG
 Surface Manager - manages access to the display subsystem and seamlessly composites
2D and 3D graphic layers from multiple applications
 LibWebCore - a modern web browser engine which powers both the Android browser
and an embeddable web view
 SGL - the underlying 2D graphics engine
 3D libraries - an implementation based on OpenGL ES 1.0 APIs; the libraries use either
hardware 3D acceleration (where available) or the included, highly optimized 3D
software rasterizer
 Free Type - bitmap and vector font rendering
 SQLite - a powerful and lightweight relational database engine available to all
applications.
2.8 ANDROID RUNTIME :
Android includes a set of core libraries that provides most of the functionality available in the
core libraries of the Java programming language. Every Android application runs in its own
process, with its own instance of the Dalvik virtual machine. Dalvik has been written so that a
device can run multiple VMs efficiently. The Dalvik VM executes files in the Dalvik Executable
(.dex) format which is optimized for minimal memory footprint.
9
The VM is register-based, and runs classes compiled by a Java language compiler that have been
transformed into the .dex format by the included "dx" tool. The Dalvik VM relies on the Linux
kernel for underlying functionality such as threading and low-level memory management.
At the same level there is Android Runtime, where the main component Dalvik Virtual Machine
is located. It was designed specifically for Android running in limited environment, where the
limited battery, CPU, memory and data storage are the main issues. Android gives an integrated
tool “dx”, which converts generated byte code from .jar to .dex file, after this byte code becomes
much more efficient to run on the small processors.
Figure 2: Conversion from .java to .dex file
As the result, it is possible to have multiple instances of Dalvik virtual machine running on the
single device at the same time. The Core libraries are written in Java language and contains of
the collection classes, the utilities, IO and other tools.
10
CHAPTER THREE
DIAGRAM RELATED
THEORY
3.1 ACTIVITY DIAGRAMS
Activity diagrams describe the workflow behavior of a system. Activity diagrams are similar to
state diagrams because activities are the state of doing something. The diagrams describe the
state of activities by showing the sequence of activities performed. Activity diagrams can show
activities that are conditional or parallel.
When to Use: Activity Diagrams
Activity diagrams should be used in conjunction with other modeling techniques such as
interaction diagrams and state diagrams. The main reason to use activity diagrams is to model
the workflow behind the system being designed. Activity Diagrams are also useful for:
analyzing a use case by describing what actions need to take place and when they should
occur; describing a complicated sequential algorithm; and modeling applications with parallel
processes.
However, activity diagrams should not take the place of interaction diagrams and state
diagrams. Activity diagrams do not give detail about how objects behave or how objects
collaborate.
How to Draw: Activity Diagrams
Activity diagrams show the flow of activities through the system. Diagrams are read from top to
bottom and have branches and forks to describe conditions and parallel activities. A fork is used
when multiple activities are occurring at the same time. The diagram below shows a fork after
activity1. This indicates that both activity2 and activity3 are occurring at the same time. After
activity2 there is a branch. The branch describes what activities will take place based on a set of
conditions. All branches at some point are followed by a merge to indicate the end of the
conditional behavior started by that branch. After the merge all of the parallel activities must be
combined by a join before transitioning into the final activity state.
11
3.2STATE DIAGRAMS
State diagrams are used to describe the behavior of a system. State diagrams describe all of the
possible states of an object as events occur. Each diagram usually represents objects of a single
class and track the different states of its objects through the system.
When to Use: State Diagrams
Use state diagrams to demonstrate the behavior of an object through many use cases of the
system. Only use state diagrams for classes where it is necessary to understand the behavior of
the object through the entire system. Not all classes will require a state diagram and state
diagrams are not useful for describing the collaboration of all objects in a use case. State
diagrams are other combined with other diagrams such as interaction diagrams and activity
diagrams.
How to Draw: State Diagrams
State diagrams have very few elements. The basic elements are rounded boxes representing the
state of the object and arrows indicting the transition to the next state. The activity section of the
state symbol depicts what activities the object will be doing while it is in that state.
12
All state diagrams being with an initial state of the object. This is the state of the object when it
is created. After the initial state the object begins changing states. Conditions based on the
activities can determine what the next state the object transitions to.
Below is an example of a state diagram might look like for an Order object. When the object
enters the Checking state it performs the activity "check items." After the activity is completed
the object transitions to the next state based on the conditions [all items available] or [an item is
not available]. If an item is not available the order is canceled. If all items are available then the
order is dispatched. When the object transitions to the Dispatching state the activity "initiate
delivery" is performed. After this activity is complete the object transitions againDelivered state.
13
State diagrams can also show a super-state for the object. A super-state is used when many
transitions lead to a certain state. Instead of showing all of the transitions from each state to the
redundant state a super-state can be used to show that all of the states inside of the super-state
can transition to the redundant state. This helps make the state diagram easier to read.
The diagram below shows a super-state. Both the Checking and Dispatching states can transition
into the Canceled state, so a transition is shown from a super-state named Active to the state
Cancel. By contrast, the state Dispatching can only transition to the Delivered state, so we show
an arrow only from the Dispatching state to the Delivered state.
14
CHAPTER FOUR
ACTION LISTENER
IN JAVA
4.1 ACTION LISTENER IN JAVA
Action listeners are probably the easiest — and most common — event handlers to implement.
You implement an action listener to define what should be done when an user performs certain
operation.
An action event occurs, whenever an action is performed by the user. Examples: When the user
clicks a button , chooses a menu item , presses Enter in a text field . The result is that an
actionPerformed message is sent to all action listeners that are registered on the relevant
component.
To write an Action Listener, follow the steps given below:
Declare an event handler class and specify that the class either implements an ActionListener
interface or extends a class that implements an ActionListener interface. For example:
public class MyClass implements ActionListener {
Register an instance of the event handler class as a listener on one or more components. For
example:
someComponent.addActionListener(instanceOfMyClass);
Include code that implements the methods in listener interface. For example:
public void actionPerformed(ActionEvent e) {
...//code that reacts to the action...
}
In general, to detect when the user clicks an onscreen button (or does the keyboard equivalent), a
program must have an object that implements the ActionListener interface. The program must
register this object as an action listener on the button (the event source), using the
addActionListener method. When the user clicks the onscreen button, the button fires an action
event. This results in the invocation of the action listener's actionPerformed method (the only
method in the ActionListener interface). The single argument to the method is an ActionEvent
object that gives information about the event and its source.
Let us write a simple program which displays how many number of times a button is clicked by
the user. First, here is the code that sets up the TextField , button and numClicks variable:
public class AL extends Frame implements WindowListener,ActionListener
15
{
TextField text = new TextField(20);
Button b;
private int numClicks = 0;
In the above example, the event handler class is AL which implements ActionListener.
We would like to handle the button-click event, so we add an action listener to the button b as
below:
b = new Button("Click me");
b.addActionListener(this);
In the above code, Button b is a component upon which an instance of event handler class AL is
registered.
Now, we want to display the text as to how many number of times a user clicked button. We can
do this by writing the code as below:
public void actionPerformed(ActionEvent e) {
numClicks++;
text.setText("Button Clicked " + numClicks + " times");
Now, when the user clicks the Button b, the button fires an action event which invokes the action
listener's actionPerformed method. Each time the user presses the button, numClicks variable is
appended and the message is displayed in the text field.
Here is the complete program(AL.java):
import java.awt.*;
import java.awt.event.*;
public class AL extends Frame implements WindowListener,ActionListener
16
{
TextField text = new TextField(20);
Button b;
private int numClicks = 0;
public static void main(String[] args) {
AL myWindow = new AL("My first window");
myWindow.setSize(350,100);
myWindow.setVisible(true);
}
public AL(String title) {
super(title);
setLayout(new FlowLayout());
addWindowListener(this);
b = new Button("Click me");
add(b);
add(text);
b.addActionListener(this);
}
public void actionPerformed(ActionEvent e)
17
{
numClicks++;
text.setText("Button Clicked " + numClicks + " times");
}
public void windowClosing(WindowEvent e) {
dispose();
System.exit(0);
}
public void windowOpened(WindowEvent e) {}
public void windowActivated(WindowEvent e) {}
public void windowIconified(WindowEvent e) {}
public void windowDeiconified(WindowEvent e) {}
public void windowDeactivated(WindowEvent e) {}
public void windowClosed(WindowEvent e) {}
}
18
4.2THE ACTION LISTENER API
The ActionListener Interface has only one method, it has no corresponding adapter class.
Method Purpose
actionPerformed(actionEvent) Called just after the user performs an action.
The ActionEvent Class
Method Purpose
String
getActionCommand()
Returns the string associated with this action. Most objects that can fire
action events support a method called setActionCommand that lets you
set this string.
int getModifiers()
Returns an integer representing the modifier keys the user was pressing
when the action event occurred. You can use the ActionEvent-defined
constants SHIFT_MASK, CTRL_MASK, META_MASK, and
ALT_MASK to determine which keys were pressed. For example, if the
user Shift-selects a menu item, then the following expression is nonzero:
actionEvent.getModifiers() & ActionEvent.SHIFT_MASK
Object getSource()
(in
java.util.EventObject)
Returns the object that fired the event.
19
4.3EXAMPLES
The following table lists some of the many examples that use action listeners.
Example Where Described Notes
Beeper This section and
Introduction to
Event Listeners
Contains one button with one action listener that
beeps when you click the button.
MultiListener Introduction to
Event Listeners
Registers two different action listeners on one
button. Also registers the same action listener on
two different buttons.
RadioButtonDemo How to Use Radio
Buttons
Registers the same action listener on five radio
buttons. The listener uses the getActionCommand
method to determine which radio button fired the
event.
MenuDemo Getting Started Shows how to listen for action events on menu
items.
TextDemo Getting Started Loads an image in an action listener. Because
loading an image can take a while, this program
uses a SwingWorker to load the image in a
background thread.
TableDialogEditDemo Getting Started Registers an action listener through a factory
method on the OK button of a color chooser dialog.
SliderDemo Getting Started Registers an action listener on a timer that controls
an animation loop.
20
CHAPTER FIVE
KEY LISTENER
IN JAVA
5.1KEY LISTENER IN JAVA
Key events indicate when the user is typing at the keyboard. Specifically, key events are fired by
the component with the keyboard focus when the user presses or releases keyboard keys. For
detailed information about focus, see How to Use the Focus Subsystem.
Notifications are sent about two basic kinds of key events:
 The typing of a Unicode character
 The pressing or releasing of a key on the keyboard
The first kind of event is called a key-typed event. The second kind is either a key-pressed or
key-released event.
In general, you react to only key-typed events unless you need to know when the user presses
keys that do not correspond to characters. For example, to know when the user types a Unicode
character — whether by pressing one key such as 'a' or by pressing several keys in sequence —
you handle key-typed events. On the other hand, to know when the user presses the F1 key, or
whether the user pressed the '3' key on the number pad, you handle key-pressed events.
To make a component get the keyboard focus, follow these steps:
Make sure the component's isFocusable method returns true. This state allows the component to
receive the focus. For example, you can enable keyboard focus for a JLabel component by
calling the setFocusable(true) method on the label.
Make sure the component requests the focus when appropriate. For custom components,
implement a mouse listener that calls the requestFocusInWindow method when the component is
clicked.
You can obtain detailed information about a particular key-pressed event. For example, you can
query a key-pressed event to determine if it was fired from an action key. Examples of action
keys include Copy, Paste, Page Up, Undo, and the arrow and function keys. As of JDK release
1.4, you can also query a key-pressed or key-released event to determine the location of the key
that fired the event. Most key events are fired from the standard keyboard, but the events for
some keys, such as Shift, have information on whether the user pressed the Shift key on the left
or the right side of the keyboard. Likewise, the number '2' can be typed from either the standard
keyboard or from the number pad.
For key-typed events you can obtain the key character value as well as any modifiers used.
21
The following example demonstrates key events. It consists of a text field that you can type into,
followed by a text area that displays a message every time the text field fires a key event. A
button at the bottom of the window lets you clear both the text field and text area.
Here is the demo's key event handling code:
public class KeyEventDemo ... implements KeyListener ... {
...//where initialization occurs:
typingArea = new JTextField(20);
typingArea.addKeyListener(this);
//Uncomment this if you wish to turn off focus
//traversal. The focus subsystem consumes
//focus traversal keys, such as Tab and Shift Tab.
//If you uncomment the following line of code, this
//disables focus traversal and the Tab events
//become available to the key event listener.
//typingArea.setFocusTraversalKeysEnabled(false);
22
/** Handle the key typed event from the text field. */
public void keyTyped(KeyEvent e) {
displayInfo(e, "KEY TYPED: ");
}
/** Handle the key-pressed event from the text field. */
public void keyPressed(KeyEvent e) {
displayInfo(e, "KEY PRESSED: ");
}
/** Handle the key-released event from the text field. */
public void keyReleased(KeyEvent e) {
displayInfo(e, "KEY RELEASED: ");
}
...
private void displayInfo(KeyEvent e, String keyStatus){
//You should only rely on the key char if the event
//is a key typed event.
int id = e.getID();
String keyString;
if (id == KeyEvent.KEY_TYPED) {
char c = e.getKeyChar();
keyString = "key character = '" + c + "'";
23
} else {
int keyCode = e.getKeyCode();
keyString = "key code = " + keyCode
+ " ("
+ KeyEvent.getKeyText(keyCode)
+ ")";
}
int modifiersEx = e.getModifiersEx();
String modString = "extended modifiers = " + modifiersEx;
String tmpString = KeyEvent.getModifiersExText(modifiersEx);
if (tmpString.length() > 0) {
modString += " (" + tmpString + ")";
} else {
modString += " (no extended modifiers)";
}
String actionString = "action key? ";
if (e.isActionKey()) {
actionString += "YES";
} else {
actionString += "NO";
24
}
String locationString = "key location: ";
int location = e.getKeyLocation();
if (location == KeyEvent.KEY_LOCATION_STANDARD) {
locationString += "standard";
} else if (location == KeyEvent.KEY_LOCATION_LEFT) {
locationString += "left";
} else if (location == KeyEvent.KEY_LOCATION_RIGHT) {
locationString += "right";
} else if (location == KeyEvent.KEY_LOCATION_NUMPAD) {
locationString += "numpad";
} else { // (location == KeyEvent.KEY_LOCATION_UNKNOWN)
locationString += "unknown";
}
...//Display information about the KeyEvent...
}
}
25
5.2 THE KEY LISTENER API
The corresponding adapter class is KeyAdapter.
Method Purpose
keyTyped(KeyEvent)
Called just after the user types a Unicode character into the listened-to
component.
keyPressed(KeyEvent)
Called just after the user presses a key while the listened-to component
has the focus.
keyReleased(KeyEvent)
Called just after the user releases a key while the listened-to component
has the focus.
5.3 KEY EVENT CLASS
The KeyEvent class inherits many useful methods from the InputEvent class, such as
getModifiersEx, and a couple of useful methods from the ComponentEvent and AWTEvent
classes. See the InputEvent Class table in the mouse listener page for a complete list.
Method Purpose
int getKeyChar()
Obtains the Unicode character associated with this event. Only rely
on this value for key-typed events.
int getKeyCode()
Obtains the key code associated with this event. The key code
identifies the particular key on the keyboard that the user pressed or
released. The KeyEvent class defines many key code constants for
commonly seen keys. For example, VK_A specifies the key labeled
A, and VK_ESCAPE specifies the Escape key.
String getKeyText(int)
String
getKeyModifiersText(int)
Return text descriptions of the event's key code and modifier keys,
respectively.
int getModifiersEx()
String
getModifiersExText(int
Return the extended modifiers mask for this event. There are
methods inherited from the InputEvent class. Extended modifiers
represent the state of all modal keys. The getModifiersExText
method returns a string describing the extended modifier keys and
modifiers) mouse buttons. Since the getModifiersEx and getModifiersExText
methods provide more information about key events, they are
preferred over the getKeyText or getKeyModifiersText methods.
boolean isActionKey()
Returns true if the key firing the event is an action key. Examples of
action keys include Cut, Copy, Paste, Page Up, Caps Lock, the
arrow and function keys. This information is valid only for key-
pressed and key-released events.
int getKeyLocation()
Returns the location of the key that fired this event. This provides a
way to distinguish keys that occur more than once on a keyboard,
such as the two shift keys, for example. The possible values are
KEY_LOCATION_STANDARD, KEY_LOCATION_LEFT,
KEY_LOCATION_RIGHT, KEY_LOCATION_NUMPAD, or
KEY_LOCATION_UNKNOWN. This method always returns
KEY_LOCATION_UNKNOWN for key-typed events. Introduced
in JDK release 1.4.
27
CHAPTER SIX
MULTITHREADING
6.1JAVA MULTI-THREADING
Java provides built-in support for multithreaded programming. A multithreaded program
contains two or more parts that can run concurrently. Each part of such a program is called a
thread, and each thread defines a separate path of execution.
A multithreading is a specialized form of multitasking. Multitasking threads require less
overhead than multitasking processes.
I need to define another term related to threads: process: A process consists of the memory space
allocated by the operating system that can contain one or more threads. A thread cannot exist on
its own; it must be a part of a process. A process remains running until all of the non-daemon
threads are done executing.
Multithreading enables you to write very efficient programs that make maximum use of the
CPU, because idle time can be kept to a minimum.
Life Cycle of a Thread:
A thread goes through various stages in its life cycle. For example, a thread is born, started, runs,
and then dies. Following diagram shows complete life cycle of a thread.
28
Above mentioned stages are explained here:
 New: A new thread begins its life cycle in the new state. It remains in this state until the
program starts the thread. It is also referred to as a born thread.
 Runnable: After a newly born thread is started, the thread becomes runnable. A thread in
this state is considered to be executing its task.
 Waiting: Sometimes a thread transitions to the waiting state while the thread waits for
another thread to perform a task.A thread transitions back to the runnable state only when
another thread signals the waiting thread to continue executing.
 Timed waiting: A runnable thread can enter the timed waiting state for a specified
interval of time. A thread in this state transitions back to the runnable state when that
time interval expires or when the event it is waiting for occurs.
 Terminated: A runnable thread enters the terminated state when it completes its task or
otherwise terminates.
6.2 THREAD PRIORITIES
Every Java thread has a priority that helps the operating system determine the order in which
threads are scheduled.
Java priorities are in the range between MIN_PRIORITY (a constant of 1) and
MAX_PRIORITY (a constant of 10). By default, every thread is given priority
NORM_PRIORITY (a constant of 5).
Threads with higher priority are more important to a program and should be allocated processor
time before lower-priority threads. However, thread priorities cannot guarantee the order in
which threads execute and very much platform dependentant.
Creating a Thread:
Java defines two ways in which this can be accomplished:
You can implement the Runnable interface.
You can extend the Thread class, itself.
Create Thread by Implementing Runnable:
The easiest way to create a thread is to create a class that implements the Runnable interface.
29
To implement Runnable, a class need only implement a single method called run( ), which is
declared like this:
public void run( )
You will define the code that constitutes the new thread inside run() method. It is important to
understand that run() can call other methods, use other classes, and declare variables, just like the
main thread can.
After you create a class that implements Runnable, you will instantiate an object of type Thread
from within that class. Thread defines several constructors. The one that we will use is shown
here:
Thread(Runnable threadOb, String threadName);
Here threadOb is an instance of a class that implements the Runnable interface and the name of
the new thread is specified by threadName.
After the new thread is created, it will not start running until you call its start( ) method, which is
declared within Thread. The start( ) method is shown here:
void start( );
Example:
Here is an example that creates a new thread and starts it running:
// Create a new thread.
class NewThread implements Runnable {
Thread t;
NewThread() {
// Create a new, second thread
t = new Thread(this, "Demo Thread");
System.out.println("Child thread: " + t);
t.start(); // Start the thread
}
30
// This is the entry point for the second thread.
public void run() {
try {
for(int i = 5; i > 0; i--) {
System.out.println("Child Thread: " + i);
// Let the thread sleep for a while.
Thread.sleep(500);
}
} catch (InterruptedException e) {
System.out.println("Child interrupted.");
}
System.out.println("Exiting child thread.");
}
}
class ThreadDemo {
public static void main(String args[]) {
new NewThread(); // create a new thread
try {
for(int i = 5; i > 0; i--) {
System.out.println("Main Thread: " + i);
Thread.sleep(1000);
}
} catch (InterruptedException e)
31
{
System.out.println("Main thread interrupted.");
}
System.out.println("Main thread exiting.");
}
}
This would produce following result:
Child thread: Thread[Demo Thread,5,main]
Main Thread: 5
Child Thread: 5
Child Thread: 4
Main Thread: 4
Child Thread: 3
Child Thread: 2
Main Thread: 3
Child Thread: 1
Exiting child thread.
Main Thread: 2
Main Thread: 1
Main thread exiting.
Create Thread by Extending Thread:
The second way to create a thread is to create a new class that extends Thread, and then to create
an instance of that class.
The extending class must override the run( ) method, which is the entry point for the new thread.
It must also call start( ) to begin execution of the new thread.
32
Example:
Here is the preceding program rewritten to extend Thread:
// Create a second thread by extending Thread
class NewThread extends Thread {
NewThread() {
// Create a new, second thread
super("Demo Thread");
System.out.println("Child thread: " + this);
start(); // Start the thread
}
// This is the entry point for the second thread.
public void run() {
try {
for(int i = 5; i > 0; i--) {
System.out.println("Child Thread: " + i);
// Let the thread sleep for a while.
Thread.sleep(500);
}
} catch (InterruptedException e) {
System.out.println("Child interrupted.");
}
System.out.println("Exiting child thread.");
}
33
class ExtendThread {
public static void main(String args[]) {
new NewThread(); // create a new thread
try {
for(int i = 5; i > 0; i--) {
System.out.println("Main Thread: " + i);
Thread.sleep(1000);
}
} catch (InterruptedException e) {
System.out.println("Main thread interrupted.");
}
System.out.println("Main thread exiting.");
}
}
This would produce following result:
Child thread: Thread[Demo Thread,5,main]
Main Thread: 5
Child Thread: 5
Child Thread: 4
Main Thread: 4
Child Thread: 3
Child Thread: 2
Main Thread: 3
Child Thread: 1
34
Exiting child thread.
Main Thread: 2
Main Thread: 1
Main thread exiting.
Thread Methods:
Following is the list of important medthods available in the Thread class.
SN Methods with Description
1 public void start()
Starts the thread in a separate path of execution, then invokes the run() method on this Thread
object.
2 public void run()
If this Thread object was instantiated using a separate Runnable target, the run() method is
invoked on that Runnable object.
3 public final void setName(String name)
Changes the name of the Thread object. There is also a getName() method for retrieving the
name.
4 public final void setPriority(int priority)
Sets the priority of this Thread object. The possible values are between 1 and 10.
5 public final void setDaemon(boolean on)
A parameter of true denotes this Thread as a daemon thread.
6 public final void join(long millisec)
The current thread invokes this method on a second thread, causing the current thread to block
until the second thread terminates or the specified number of milliseconds passes.
7 public void interrupt()
Interrupts this thread, causing it to continue execution if it was blocked for any reason.
8 public final boolean isAlive()
35
Returns true if the thread is alive, which is any time after the thread has been started but before it
runs to completion.
The previous methods are invoked on a particular Thread object. The following methods in the
Thread class are static. Invoking one of the static methods performs the operation on the
currently running thread
SN Methods with Description
1 public static void yield()
Causes the currently running thread to yield to any other threads of the same priority that are
waiting to be scheduled
2 public static void sleep(long millisec)
Causes the currently running thread to block for at least the specified number of milliseconds
3 public static boolean holdsLock(Object x)
Returns true if the current thread holds the lock on the given Object.
4 public static Thread currentThread()
Returns a reference to the currently running thread, which is the thread that invokes this method.
5 public static void dumpStack()
Prints the stack trace for the currently running thread, which is useful when debugging a
multithreaded application.
Example:
The following ThreadClassDemo program demonstrates some of these methods of the Thread
class:
// File Name : DisplayMessage.java
// Create a thread to implement Runnable
public class DisplayMessage implements Runnable
{
private String message;
36
public DisplayMessage(String message)
{
this.message = message;
}
public void run()
{
while(true)
{
System.out.println(message);
}
}
}
// File Name : GuessANumber.java
// Create a thread to extentd Thread
public class GuessANumber extends Thread
{
private int number;
public GuessANumber(int number)
{
this.number = number;
}
public void run()
{
37
int counter = 0;
int guess = 0;
do
{
guess = (int) (Math.random() * 100 + 1);
System.out.println(this.getName()
+ " guesses " + guess);
counter++;
}while(guess != number);
System.out.println("** Correct! " + this.getName()
+ " in " + counter + " guesses.**");
}
}
// File Name : ThreadClassDemo.java
public class ThreadClassDemo
{
public static void main(String [] args)
{
Runnable hello = new DisplayMessage("Hello");
Thread thread1 = new Thread(hello);
thread1.setDaemon(true);
thread1.setName("hello");
System.out.println("Starting hello thread...");
38
thread1.start();
Runnable bye = new DisplayMessage("Goodbye");
Thread thread2 = new Thread(hello);
thread2.setPriority(Thread.MIN_PRIORITY);
thread2.setDaemon(true);
System.out.println("Starting goodbye thread...");
thread2.start();
System.out.println("Starting thread3...");
Thread thread3 = new GuessANumber(27);
thread3.start();
try
{
thread3.join();
}catch(InterruptedException e)
{
System.out.println("Thread interrupted.");
}
System.out.println("Starting thread4...");
Thread thread4 = new GuessANumber(75);
thread4.start();
System.out.println("main() is ending...");
39
}
This would produce following result. You can try this example again and again and you would
get different result every time.
Starting hello thread...
Starting goodbye thread...
Hello
Hello
Hello
Hello
Hello
Hello
Hello
Hello
Hello
Thread-2 guesses 27
Hello
** Correct! Thread-2 in 102 guesses.**
Hello
Starting thread4...
Hello
Hello
..........remaining result produced.
Major Thread Concepts:
While doing Multithreading programming, you would need to have following concepts very
handy:
40
Thread Synchronization
Inter thread Communication
Thread Deadlock
Thread Control: Suspend, Stop and Resume
Using Multithreading:
The key to utilizing multithreading support effectively is to think concurrently rather than
serially. For example, when you have two subsystems within a program that can execute
concurrently, make them individual threads.
With the careful use of multithreading, you can create very efficient programs. A word of
caution is in order, however: If you create too many threads, you can actually degrade the
performance of your program rather than enhance it.
Remember, some overhead is associated with context switching. If you create too many threads,
more CPU time will be spent changing contexts than executing your program!
41
CHAPTER SEVEN
JAVA METHODOLIGIES
7.1 OVERVIEW
In Java 1.2, the paintComponent method is supplied with a Graphics2D object (a subclass of
Graphics), which contains a much richer set of drawing operations. It includes pen widths,
dashed lines, image and gradient color fill patterns, the use of arbitrary local fonts, a floating
point coordinate system, and a number of coordinate transformation operations. However, to
maintain compatibility with Swing as used in Java 1.1, the declared type of the paintComponent
argument is Graphics, so you have to cast it to Graphics2D before using it.
Java 1.1 Java 1.2
public void paint(Graphics g) {
// Set pen parameters
g.setColor(someColor);
g.setFont(someLimitedFont);
// Draw a shape
g.drawString(...);
g.drawLine(...)
g.drawRect(...); // outline
g.fillRect(...); // solid
g.drawPolygon(...); // outline
g.fillPolygon(...); // solid
g.drawOval(...); // outline
g.fillOval(...); // solid
...
}
public void paintComponent(Graphics g) {
// Clear off-screen bitmap
super.paintComponent(g);
// Cast Graphics to Graphics2D
Graphics2D g2d = (Graphics2D)g;
// Set pen parameters
g2d.setPaint(fillColorOrPattern);
g2d.setStroke(penThicknessOrPattern);
g2d.setComposite(someAlphaComposite);
g2d.setFont(anyFont);
g2d.translate(...);
g2d.rotate(...);
g2d.scale(...);
g2d.shear(...);
g2d.setTransform(someAffineTransform);
// Allocate a shape
SomeShape s = new SomeShape(...);
42
g2d.draw(s); // outline
g2d.fill(s); // solid
}
 Main New Features
 Colors and patterns: gradient fills, fill patterns from tiled images, transparency
 Local fonts
 Pen thicknesses, dashing patterns, and segment connection styles
 Coordinate transformations
 General Approach
 Cast the Graphics object to a Graphics2D object
public void paintComponent(Graphics g) {
super.paintComponent(g); // Typical Swing approach
Graphics2D g2d = (Graphics2D)g;
g2d.doSomeStuff(...);
...
}
Create a Shape object
Rectangle2D.Double rect = ...;
Ellipse2D.Double ellipse = ...;
Polygon poly = ...;
GeneralPath path = ...;
SomeShapeYouDefined shape = ...; // Satisfies Shape interface
...
Optional: modify drawing parameters
43
g2d.setPaint(fillColorOrPattern);
g2d.setStroke(penThicknessOrPattern);
g2d.setComposite(someAlphaComposite);
g2d.setFont(someFont);
g2d.translate(...);
g2d.rotate(...);
g2d.scale(...);
g2d.shear(...);
g2d.setTransform(someAffineTransform);
Draw an outlined or solid version of the Shape
g2d.draw(someShape);
g2d.fill(someShape);
7.2 DRAWING SHAPES IN JAVA3D
OVERVIEW
With the AWT, you generally drew a shape by calling the drawXxx or fillXxx method of the
Graphics object. In Java2D, you generally create a Shape object, then call either the draw or fill
method of the Graphics2D object, supplying the Shape object as an argument. For example:
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
// Assume x, y, and diameter are instance variables
Ellipse2D.Double circle =
new Ellipse2D.double(x, y, diameter, diameter);
g2d.fill(circle);
44
}
You can still call the drawXxx methods if you like, however. This is necessary for drawString
and drawImage, and possibly convenient for draw3DRect. Several classes have similar versions
that store coordinates as either double precision numbers (Xxx.Double) or single precision
numbers (Xxx.Float). The idea is that single precision coordinates might be slightly faster to
manipulate on some platforms.
Shape Classes
Arguments to the Graphics2D draw and fill methods must implement the Shape interface. You
can create your own shapes, of course, but following are the major built-in ones. Except for
Rectangle and Polygon, which are Java 1.1 holdovers, these appear in the java.awt.geom
package.
Arc2D.Double, Arc2D.Float
Area (a shape built by adding/subtracting other shapes)
CubicCurve2D.Double, CubicCurve2D.Float
Ellipse2D.Double, Ellipse2D.Float
GeneralPath (a series of connected shapes)
Line2D.Double, Line2D.Float
Polygon
QuadCurve2D.Double, QuadCurve2D.Float
Rectangle2D.Double, Rectangle2D.Float, Rectangle
RoundRectangle2D.Double, RoundRectangle2D.Float
Drawing Shapes: Example Code
ShapeExample.java
import javax.swing.*; // For JPanel, etc.
import java.awt.*; // For Graphics, etc.
import java.awt.geom.*; // For Ellipse2D, etc.
45
/** An example of drawing/filling shapes with Java2D in Java 1.2.
public class ShapeExample extends JPanel {
private Ellipse2D.Double circle =
new Ellipse2D.Double(10, 10, 350, 350);
private Rectangle2D.Double square =
new Rectangle2D.Double(10, 10, 350, 350);
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
g2d.fill(circle);
g2d.draw(square);
}
// super.paintComponent clears offscreen pixmap,
// since we're using double buffering by default.
protected void clear(Graphics g) {
super.paintComponent(g);
}
protected Ellipse2D.Double getCircle() {
return(circle);
46
public static void main(String[] args) {
WindowUtilities.openInJFrame(new ShapeExample(), 380, 400);
}
}
WindowUtilities.java
import javax.swing.*;
import java.awt.*;
/** A few utilities that simplify testing of windows in Swing.
public class WindowUtilities {
public static void setNativeLookAndFeel() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch(Exception e) {
System.out.println("Error setting native LAF: " + e);
}
}
/** A simplified way to see a JPanel or other Container.
* Pops up a JFrame with specified Container as the content pane.
*/
47
public static JFrame openInJFrame(Container content,
int width,
int height,
String title,
Color bgColor) {
JFrame frame = new JFrame(title);
frame.setBackground(bgColor);
content.setBackground(bgColor);
frame.setSize(width, height);
frame.setContentPane(content);
frame.addWindowListener(new ExitListener());
frame.setVisible(true);
return(frame);
}
/** Uses Color.white as the background color. */
public static JFrame openInJFrame(Container content,
int width,
int height,
String title) {
return(openInJFrame(content, width, height, title, Color.white));
}
48
/** Uses Color.white as the background color, and the name of the Container's class as the
JFrame title.
public static JFrame openInJFrame(Container content,
int width,
int height) {
return(openInJFrame(content, width, height,
content.getClass().getName(),
Color.white));
}
}
ExitListener.java
import java.awt.*;
import java.awt.event.*;
public class ExitListener extends WindowAdapter {
public void windowClosing(WindowEvent event) {
System.exit(0);
}
}
49
Drawing Shapes: Example Output
50
7.3 PAINT STYLES IN JAVA 2D
PAINT STYLES OVERVIEW
When you fill a Shape, the current Paint attribute of the Graphics2D object is used. This can be a
Color (solid color), a GradientPaint (gradient fill gradually combining two colors), a
TexturePaint (tiled image), or a new version of Paint that you write yourself. Use setPaint and
getPaint to change and retrieve the Paint settings. Note that setPaint and getPaint supersede the
setColor and getColor methods that were used in Graphics.
Paint Classes
Arguments to the Graphics2D setPaint method (and return values of getPaint) must implement
the Paint interface. Here are the major built-in Paint classes:
Color
Has the same constants (Color.red, Color.yellow, etc.) as the AWT version, plus some extra
constructors.
GradientPaint
Constructors takes two points, two colors, and optionally a boolean flag that indicates that the
color pattern should cycle. The first color is used at the first point, the second color at the second
point, and points in between are colored based on how close they are to each of the points.
TexturePaint
Constructor takes a BufferedImage and a Rectangle2D, maps the image to the rectangle, then
tiles the rectangle. Creating a BufferedImage from a GIF or JPEG file is a pain. First load an
Image normally, get its size, create a BufferedImage that size with
BufferedImage.TYPE_INT_ARGB as the image type, get the BufferedImage's Graphics object
via createGraphics, then draw the Image into the BufferedImage using drawImage. An example
of this process is shown later.
Transparency
Transparency is not set in the Paint object, rather separately via an AlphaComposite object that is
applied via setComposite.
51
GRADIENT FILLS: EXAMPLE CODE
import java.awt.*;
/** An example of gradient fills with Java2D in Java 1.2.
public class GradientPaintExample extends ShapeExample {
// Red at (0,0), yellow at (175,175), changes gradually between.
private GradientPaint gradient =
new GradientPaint(0, 0, Color.red, 175, 175, Color.yellow,
true); // true means to repeat pattern
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
drawGradientCircle(g2d);
}
protected void drawGradientCircle(Graphics2D g2d) {
g2d.setPaint(gradient);
g2d.fill(getCircle());
g2d.setPaint(Color.black);
g2d.draw(getCircle());
}
52
public static void main(String[] args) {
WindowUtilities.openInJFrame(new GradientPaintExample(),
380, 400);
}
}
Gradient Fills: Example Output
TILED IMAGES AS FILL PATTERNS -- OVERVIEW
To use tiled images, you create a TexturePaint object and specify its use via the setPaint method
of Graphics2D, just as with solid colors and gradient fills. The TexturePaint constructor takes a
BufferedImage and a Rectangle2D as arguments. The BufferedImage specifies what to draw, and
the Rectangle2D specifies where the tiling starts. Creating a BufferedImage to hold custom
drawing is relatively straightforward: call the BufferedImage constructor with a width, a height,
and a type of BufferedImage.TYPE_INT_RGB, then call createGraphics on that to get a
Graphics2D with which to draw. It is a bit harder to create one from an image file.
53
First load an Image from an image file, then use MediaTracker to be sure it is done loading, then
create an empty BufferedImage using the Image width and height, then get the Graphics2D via
createGraphics, then draw the Image onto the BufferedImage. This process has been wrapped up
in the getBufferedImage method of my ImageUtilities class.
Tiled Images as Fill Patterns: Example Code
TiledImages.java
import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;
import java.awt.image.*;
/** An example of using TexturePaint to fill objects with tiled images. Uses the
getBufferedImage method of ImageUtilities to load an Image from a file and turn that into a
BufferedImage.
public class TiledImages extends JPanel {
private String dir = System.getProperty("user.dir");
private String imageFile1 = dir + "/images/marty.jpg";
private TexturePaint imagePaint1;
private Rectangle imageRect;
private String imageFile2 = dir + "/images/bluedrop.gif";
private TexturePaint imagePaint2;
private int[] xPoints = { 30, 700, 400 };
private int[] yPoints = { 30, 30, 600 };
private Polygon imageTriangle = new Polygon(xPoints, yPoints, 3);
54
public TiledImages() {
BufferedImage image =
ImageUtilities.getBufferedImage(imageFile1, this);
imageRect =
new Rectangle(235, 70, image.getWidth(), image.getHeight());
imagePaint1 =
new TexturePaint(image, imageRect);
image = ImageUtilities.getBufferedImage(imageFile2, this);
imagePaint2 =
new TexturePaint(image, new Rectangle(0, 0, 32, 32));
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
g2d.setPaint(imagePaint2);
g2d.fill(imageTriangle);
g2d.setPaint(Color.blue);
g2d.setStroke(new BasicStroke(5));
g2d.draw(imageTriangle);
g2d.setPaint(imagePaint1);
g2d.fill(imageRect);
g2d.setPaint(Color.black);
g2d.draw(imageRect);
}
55
public static void main(String[] args) {
WindowUtilities.openInJFrame(new TiledImages(), 750, 650);
}
}
ImageUtilities.java
import java.awt.*;
import java.awt.image.*;
/** A class that simplifies a few common image operations, in particular creating a
BufferedImage from an image file, and using MediaTracker to wait until an image or several
images are done loading.
public class ImageUtilities {
/** Create Image from a file, then turn that into a BufferedImage.
public static BufferedImage getBufferedImage(String imageFile, Component c)
{
Image image = c.getToolkit().getImage(imageFile);
waitForImage(image, c);
BufferedImage bufferedImage =
new BufferedImage(image.getWidth(c), image.getHeight(c),
BufferedImage.TYPE_INT_RGB);
Graphics2D g2d = bufferedImage.createGraphics();
g2d.drawImage(image, 0, 0, c);
return(bufferedImage);
}
56
/** Take an Image associated with a file, and wait until it is done loading. Just a simple
application of MediaTracker. If you are loading multiple images, don't use thisconsecutive times;
instead use the version that takes an array of images.
public static boolean waitForImage(Image image, Component c) {
MediaTracker tracker = new MediaTracker(c);
tracker.addImage(image, 0);
try {
tracker.waitForAll();
} catch(InterruptedException ie) {}
return(!tracker.isErrorAny());
}
/** Take some Images associated with files, and wait until they are done loading. Just a simple
application of MediaTracker.
public static boolean waitForImages(Image[] images, Component c) {
MediaTracker tracker = new MediaTracker(c);
for(int i=0; i<images.length; i++)
tracker.addImage(images[i], 0);
try {
tracker.waitForAll();
} catch(InterruptedException ie) {}
return(!tracker.isErrorAny());
}
}
57
7.4 TRANSPARENCY IN JAVA 2D
OVERVIEW
Java2D permits you to assign transparency (alpha) values to drawing operations so that the
underlying graphics partially shows through when you draw shapes or images. You set
transparency by creating an AlphaComposite object then passing it to the setComposite method
of the Graphics2D object. You create an AlphaComposite by calling
AlphaComposite.getInstance with a mixing rule designator and a transparency (or "alpha") value.
There are 8 built-in mixing rules (see the AlphaComposite API for details), but the one normally
used for drawing with transparency settings is AlphaComposite.SRC_OVER. Alpha values range
from 0.0F (completely transparent) to 1.0F (completely opaque).
Transparency: Example Code
import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;
/** An illustration of the use of AlphaComposite to make partially transparent drawings.
public class TransparencyExample extends JPanel {
private static int gap=10, width=60, offset=20,
deltaX=gap+width+offset;
private Rectangle
blueSquare = new Rectangle(gap+offset, gap+offset, width, width),
redSquare = new Rectangle(gap, gap, width, width);
private AlphaComposite makeComposite(float alpha) {
int type = AlphaComposite.SRC_OVER;
return(AlphaComposite.getInstance(type, alpha));
58
}
private void drawSquares(Graphics2D g2d, float alpha) {
Composite originalComposite = g2d.getComposite();
g2d.setPaint(Color.blue);
g2d.fill(blueSquare);
g2d.setComposite(makeComposite(alpha));
g2d.setPaint(Color.red);
g2d.fill(redSquare);
g2d.setComposite(originalComposite);
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
for(int i=0; i<11; i++) {
drawSquares(g2d, i*0.1F);
g2d.translate(deltaX, 0);
}
}
public static void main(String[] args) {
String title = "Transparency example: alpha of the top (red) " +
"square ranges from 0.0 at the left to 1.0 at " +
"the right. Bottom (blue) square is opaque.";
WindowUtilities.openInJFrame(new TransparencyExample(),
11*deltaX + 2*gap, deltaX + 3*gap,
59
title, Color.lightGray);
}
}
Transparency: Example Output
Using Local Fonts in Java2D
Local Fonts: Overview
You can use the same logical font names as in Java 1.1, namely Serif (e.g. Times), SansSerif
(e.g. Helvetica or Arial), Monospaced (e.g. Courier), Dialog, and DialogInput.
You can also use arbitrary local fonts if you first look up the entire list, which may take a few
seconds. Lookup the fonts via the getAvailableFontFamilyNames or getAllFonts methods of
GraphicsEnvironment. E.g.:
GraphicsEnvironment env =
GrapicsEnvironment.getLocalGraphicsEnvironment();
Then
env.getAvailableFontFamilyNames();
or
env.getAllFonts(); // Much slower!
The best approach would be to loop down getAvailableFontFamilyNames, checking for your
name, having several backup names to use if the first choice is not available. If you pass an
unavailable family name to the Font constructor, a default font (SansSerif) will be used.
60
EXAMPLE 1 -- PRINTING OUT ALL LOCAL FONT NAMES
import java.awt.*;
/** Lists the names of all available fonts with Java2D in Java 1.2.
public class ListFonts {
public static void main(String[] args) {
GraphicsEnvironment env =
GraphicsEnvironment.getLocalGraphicsEnvironment();
String[] fontNames = env.getAvailableFontFamilyNames();
System.out.println("Available Fonts:");
for(int i=0; i<fontNames.length; i++)
System.out.println(" " + fontNames[i]);
}
}
/** AN EXAMPLE OF USING LOCAL FONTS WITH JAVA2D IN JAVA
public class FontExample extends GradientPaintExample {
public FontExample() {
GraphicsEnvironment env =
GraphicsEnvironment.getLocalGraphicsEnvironment();
env.getAvailableFontFamilyNames();
setFont(new Font("Goudy Handtooled BT", Font.PLAIN, 100));
}
protected void drawBigString(Graphics2D g2d)
61
{
g2d.setPaint(Color.black);
g2d.drawString("Java 2D", 25, 215);
}
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
drawGradientCircle(g2d);
drawBigString(g2d);
}
public static void main(String[] args) {
WindowUtilities.openInJFrame(new FontExample(), 380, 400);
}
Drawing with Local Fonts: Example Output
62
7.5 STROKE STYLES IN JAVA2D
OVERVIEW
In the AWT, the drawXxx methods of Graphics resulted in solid, 1-pixel wide lines.
Furthermore, drawing commands that consisted of multiple line segments (e.g. drawRect and
drawPolygon) had a predefined way of joining the line segments together and terminating
segments that do not join to others. Java2D gives you much more flexibility. In addition to
setting the pen color or pattern (via setPaint, as discussed in the previous section), Java2D
permits you to set the pen thickness and dashing pattern, and to specify the way line segments
end and are joined together. You do this by creating a BasicStroke object, then telling the
Graphics2D object to use it via the setStroke method.
Stroke Attributes
Arguments to setStroke must implement the Stroke interface, and the BasicStroke class is the
sole builtin class that implements Stroke. Here are the BasicStroke constructors:
BasicStroke()
Creates a BasicStroke with a pen width of 1.0, the default cap style of CAP_SQUARE, and the
default join style of JOIN_MITER. See the following examples of pen widths and cap/join
styles.
BasicStroke(floatpenWidth)
Uses the specified pen width and the default cap/join styles (CAP_SQUARE and
JOIN_MITER).
BasicStroke(float penWidth, int capStyle, int joinStyle)
Uses the specified pen width, cap style, and join style. The cap style can be one of
CAP_SQUARE (make a square cap that extends past the end point by half the pen width -- this
is the default), CAP_BUTT (cut off segment exactly at end point -- use this one for dashed
lines), or CAP_ROUND (make a circular cap centered on the end point, with a diameter of the
pen width). The join style can be one of JOIN_MITER (extend outside edges of lines until they
meet -- this is the default), JOIN_BEVEL (connect outside corners of outlines with straight line),
or JOIN_ROUND (round off corner with circle with diameter equal to the pen width).
BasicStroke(float penWidth, int capStyle, int joinStyle, float miterLimit)
63
BasicStroke(float penWidth, int capStyle, int joinStyle, float miterLimit, float[]
dashPattern, float dashOffset)
Lets you make dashed lines by specifying an array of opaque (entries at even array indices) and
transparent (odd indices) segments. The offset, which is often 0.0, specifies where to start in the
dashing pattern.
Stroke Thickness: Example Code
import java.awt.*;
/** An example of Stroke (pen) widths with Java2D in Java 1.2.
public class StrokeThicknessExample extends FontExample {
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
drawGradientCircle(g2d);
drawBigString(g2d);
drawThickCircleOutline(g2d);
}
protected void drawThickCircleOutline(Graphics2D g2d) {
g2d.setPaint(Color.blue);
g2d.setStroke(new BasicStroke(8)); // 8-pixel wide pen
g2d.draw(getCircle());
}
public static void main(String[] args) {
WindowUtilities.openInJFrame(new StrokeThicknessExample(),
64
380, 400);
}
}
DASHED LINE EXAMPLE CODE:
import java.awt.*;
public class DashedStrokeExample extends FontExample {
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
drawGradientCircle(g2d);
drawBigString(g2d);
drawDashedCircleOutline(g2d);
}
protected void drawDashedCircleOutline(Graphics2D g2d) {
g2d.setPaint(Color.blue);
// 30 pixel line, 10 pixel gap, 10 pixel line, 10 pixel gap
float[] dashPattern = { 30, 10, 10, 10 };
g2d.setStroke(new BasicStroke(8, BasicStroke.CAP_BUTT,
BasicStroke.JOIN_MITER, 10,
dashPattern, 0));
g2d.draw(getCircle());
}
65
public static void main(String[] args) {
WindowUtilities.openInJFrame(new DashedStrokeExample(),
380, 400);
}
}
DASHED LINES: EXAMPLE OUTPUT
LINE CAP AND JOIN STYLES: EXAMPLE CODE
import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;
66
public class LineStyles extends JPanel {
private GeneralPath path;
private static int x = 30, deltaX = 150, y = 300, deltaY = 250,
thickness = 40;
private Circle p1Large, p1Small, p2Large, p2Small, p3Large, p3Small;
private int compositeType = AlphaComposite.SRC_OVER;
private AlphaComposite transparentComposite =
AlphaComposite.getInstance(compositeType, 0.4F);
private int[] caps =
{ BasicStroke.CAP_SQUARE, BasicStroke.CAP_BUTT,
BasicStroke.CAP_ROUND };
private String[] capNames =
{ "CAP_SQUARE", "CAP_BUTT", "CAP_ROUND" };
private int[] joins =
{ BasicStroke.JOIN_MITER, BasicStroke.JOIN_BEVEL,
BasicStroke.JOIN_ROUND };
private String[] joinNames =
{ "JOIN_MITER", "JOIN_BEVEL", "JOIN_ROUND" };
public LineStyles() {
path = new GeneralPath();
path.moveTo(x, y);
p1Large = new Circle(x, y, thickness/2);
p1Small = new Circle(x, y, 2);
path.lineTo(x + deltaX, y - deltaY);
67
p2Large = new Circle(x + deltaX, y - deltaY, thickness/2);
p2Small = new Circle(x + deltaX, y - deltaY, 2);
path.lineTo(x + 2*deltaX, y);
p3Large = new Circle(x + 2*deltaX, y, thickness/2);
p3Small = new Circle(x + 2*deltaX, y, 2);
setForeground(Color.blue);
setFont(new Font("SansSerif", Font.BOLD, 20));
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
g2d.setColor(Color.blue);
for(int i=0; i>caps.length; i++) {
BasicStroke stroke =
new BasicStroke(thickness, caps[i], joins[i]);
g2d.setStroke(stroke);
g2d.draw(path);
labelEndPoints(g2d, capNames[i], joinNames[i]);
g2d.translate(3*x + 2*deltaX, 0);
}
}
68
// Draw translcent circles to illustrate actual endpoints.
// Include text labels to shold cap/join style.
private void labelEndPoints(Graphics2D g2d,
String capLabel, String joinLabel) {
Paint origPaint = g2d.getPaint();
Composite origComposite = g2d.getComposite();
g2d.setPaint(Color.red);
g2d.setComposite(transparentComposite);
g2d.fill(p1Large);
g2d.fill(p2Large);
g2d.fill(p3Large);
g2d.setPaint(Color.yellow);
g2d.setComposite(origComposite);
g2d.fill(p1Small);
g2d.fill(p2Small);
g2d.fill(p3Small);
g2d.setPaint(Color.black);
g2d.drawString(capLabel, x + thickness - 5, y + 5);
g2d.drawString(joinLabel, x + deltaX + thickness - 5, y - deltaY);
g2d.setPaint(origPaint);
}
public static void main(String[] args) {
WindowUtilities.openInJFrame(new LineStyles(),
9*x + 6*deltaX, y + 60);
69
}
}
class Circle extends Ellipse2D.Double {
public Circle(double centerX, double centerY, double radius)
{
super(centerX - radius, centerY - radius, 2.0*radius, 2.0*radius);
}
}
Line Cap and Join Styles: Example Output
7.6 COORDINATE TRANSFORMATIONS
OVERVIEW
Java2D allows you to easily translate, rotate, scale, or shear the coordinate system. This is very
convenient: it is often much easier to move the coordinate system than to calculate new
coordinates for each of your points. Besides, for some data structures like ellipses and strings
there is no other way to get rotated or stretched versions. The meanings of translate, rotate, and
scale are clear: to move, to spin, or to stretch/shrink evenly in the x and/or y direction. Shear
means to stretch unevenly: an x shear moves points to the right based on how far they are from
the y axis; a y shear moves points down based on how far they are from the x axis.
70
The easiest way to picture what is happening is to imagine that the person doing the drawing has
a picture frame that he lays down on top of a sheet of paper. The drawer always sits at the bottom
of the frame. To apply a translation, you move the frame (moving the drawer with it), and do the
drawing in the new location. You then move the frame back to its original location, and what you
now see is the final result. Similarly, for a rotation, you spin the frame (and the drawer), draw,
then spin back to see the result. Similarly for scaling and shears; modify the frame without
touching the underlying sheet of paper, draw, then reverse the process to see the final result.
An outside observer watching this process would see the frame move in the direction specified
by the transformation, but see the sheet of paper stay fixed. This is illustrated in the second
column in the diagram below. The dotted rectangle represents the frame, while the gray rectangle
represents the sheet of paper. On the other hand, to the person doing the drawing it would appear
that the sheet of paper moved in the opposite way from that specified in the transformation, but
that he didn't move at all. This is illustrated in the third column in the following diagram. The
first column illustrates the starting configuration, and the fourth illustrates the final result.
Visualizing Transformations
You can also perform more complex transformations (e.g. creating a mirror image by flipping
around a line) by directly manipulating the underlying arrays that control the transformations.
This is a bit more complicated to envision than the basic translatation, rotation, scaling, and shear
transformations. The idea is that a new point (x2,y2) can be derived from an original point (x1,y1)
as follows:
71
[ x2] [ m00 m01 m02 ] [ x1 ] [ m00x1 + m01y1 + m02 ]
[ y2] = [ m10 m11 m12 ] [ y1 ] = [ m10x1 + m11y1 + m12 ]
[ 1 ] [ 0 0 1 ] [ 1 ] [ 1 ]
Note that you can only supply six of the nine values in the transformation array (the mxx values).
The bottom row is fixed at [ 0 0 1 ] to guarantee that the transformations preserve "straightness"
and "parallelness" of lines.
There are two basic ways to use transformations. You can create an AffineTransform object, set
its parameters, and then assign that AffineTransform to the Graphics2D object via setTransform.
This is your only choice if you want to do the more complex transformations permitted by setting
explicit transformation matrices. Alternatively, for the basic transformations you can call
translate, rotate, scale, and shear directly on the Graphics2D object.
COORDINATE TRANSLATIONS AND ROTATIONS: EXAMPLE CODE
import java.awt.*;
/** An example of coordinate translations and rotations with Java2D in Java 1.2.
public class RotationExample extends StrokeThicknessExample {
private Color[] colors = { Color.white, Color.black };
public void paintComponent(Graphics g) {
clear(g);
Graphics2D g2d = (Graphics2D)g;
drawGradientCircle(g2d);
drawThickCircleOutline(g2d);
// Move the origin to the center of the circle.
g2d.translate(185.0, 185.0);
for (int i=0; i<16; i++) {
// Rotate the coordinate system around current
72
// origin, which is at the center of the circle.
g2d.rotate(Math.PI/8.0);
g2d.setPaint(colors[i%2]);
g2d.drawString("Java", 0, 0);
}
}
public static void main(String[] args) {
WindowUtilities.openInJFrame(new RotationExample(), 380, 400);
}
}
Coordinate Translations and Rotations: Example Output
73
SHEAR TRANSFORMATIONS
If you specify a non-zero x shear, then x values will be more and more shifted to the right the
farther they are away from the y axis. For example, an x shear of 0.1 means that the x value will
be shifted 10% of the distance the point is away from the y axis. Y shears are similar: points are
shifted down in proportion to the distance they are away from the x axis.
SHEAR TRANSFORMATIONS: EXAMPLE CODE
import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;
/** An example of shear transformations with Java2D in Java 1.2.
public class ShearExample extends JPanel {
private static int gap=10, width=100;
private Rectangle rect = new Rectangle(gap, gap, 100, 100);
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
for (int i=0; i<5; i++) {
g2d.setPaint(Color.red);
g2d.fill(rect);
// Each new square gets 0.2 more x shear
g2d.shear(0.2, 0.0);
g2d.translate(2*gap + width, 0);
74
}
public static void main(String[] args) {
String title =
"Shear: x shear ranges from 0.0 for the leftmost 'square' " +
"to 0.8 for the rightmost one.";
WindowUtilities.openInJFrame(new ShearExample(),
20*gap + 5*width, 5*gap + width,
title);
}}
75
CHAPTER EIGHT
CONCLUSION
CONCLUSION
This project is designed to meet the requirements of window
based Game tron. It has been developed in J2SE (Version 6.0)
keeping in mind the specifications of the game.
Overall the project teaches us the essential skills like:
1. The use of Applets and Frames, where the designing can be
done. And the GUI can be developed using the Java and
Net beans.
2. The project also teaches the use of graphics 2D.
BIBLIOGRAPHY
Books Referred:-
JAVA The complete reference part 2
JAVA Projects Tony Martin, Dominic Sally
Related Websites:-
www.wikipedia.org
www.simba.com

More Related Content

What's hot

Unity introduction for programmers
Unity introduction for programmersUnity introduction for programmers
Unity introduction for programmersNoam Gat
 
Creating a serious game with the Unity 3D Game Engine and the importance of m...
Creating a serious game with the Unity 3D Game Engine and the importance of m...Creating a serious game with the Unity 3D Game Engine and the importance of m...
Creating a serious game with the Unity 3D Game Engine and the importance of m...danielandlubo
 
Presentasi Seminar Unity (AMIKOM Game Dev)
Presentasi Seminar Unity (AMIKOM Game Dev)Presentasi Seminar Unity (AMIKOM Game Dev)
Presentasi Seminar Unity (AMIKOM Game Dev)Mas Bram
 
Linux userguide
Linux userguideLinux userguide
Linux userguidelogan159
 
WEB310 CASE STUDY: COOKIE CLICKER by Angeline Hildreth
WEB310 CASE STUDY: COOKIE CLICKER by Angeline HildrethWEB310 CASE STUDY: COOKIE CLICKER by Angeline Hildreth
WEB310 CASE STUDY: COOKIE CLICKER by Angeline HildrethAngeline Hildreth
 
Windows phone 7 xna
Windows phone 7 xnaWindows phone 7 xna
Windows phone 7 xnaGlen Gordon
 
PRESENTATION ON Game Engine
PRESENTATION ON Game EnginePRESENTATION ON Game Engine
PRESENTATION ON Game EngineDiksha Bhargava
 
XNA and Windows Phone
XNA and Windows PhoneXNA and Windows Phone
XNA and Windows PhoneGlen Gordon
 
Casual and Social Games with Unity
Casual and Social Games with UnityCasual and Social Games with Unity
Casual and Social Games with UnityTadej Gregorcic
 
Unity Introduction
Unity IntroductionUnity Introduction
Unity IntroductionJuwal Bose
 
Game software development trends
Game software development trendsGame software development trends
Game software development trends_veronika_
 
One Handed Controller
One Handed ControllerOne Handed Controller
One Handed Controllerzaxxor1
 

What's hot (20)

Game development unity
Game development unityGame development unity
Game development unity
 
Unity introduction for programmers
Unity introduction for programmersUnity introduction for programmers
Unity introduction for programmers
 
Unity 3D, A game engine
Unity 3D, A game engineUnity 3D, A game engine
Unity 3D, A game engine
 
Unity
UnityUnity
Unity
 
Creating a serious game with the Unity 3D Game Engine and the importance of m...
Creating a serious game with the Unity 3D Game Engine and the importance of m...Creating a serious game with the Unity 3D Game Engine and the importance of m...
Creating a serious game with the Unity 3D Game Engine and the importance of m...
 
First-person Shooters
First-person ShootersFirst-person Shooters
First-person Shooters
 
Unity: Introduction
Unity: IntroductionUnity: Introduction
Unity: Introduction
 
Presentasi Seminar Unity (AMIKOM Game Dev)
Presentasi Seminar Unity (AMIKOM Game Dev)Presentasi Seminar Unity (AMIKOM Game Dev)
Presentasi Seminar Unity (AMIKOM Game Dev)
 
Linux userguide
Linux userguideLinux userguide
Linux userguide
 
project
projectproject
project
 
WEB310 CASE STUDY: COOKIE CLICKER by Angeline Hildreth
WEB310 CASE STUDY: COOKIE CLICKER by Angeline HildrethWEB310 CASE STUDY: COOKIE CLICKER by Angeline Hildreth
WEB310 CASE STUDY: COOKIE CLICKER by Angeline Hildreth
 
Unity 3D VS your team
Unity 3D VS your teamUnity 3D VS your team
Unity 3D VS your team
 
Unity 3d Basics
Unity 3d BasicsUnity 3d Basics
Unity 3d Basics
 
Windows phone 7 xna
Windows phone 7 xnaWindows phone 7 xna
Windows phone 7 xna
 
PRESENTATION ON Game Engine
PRESENTATION ON Game EnginePRESENTATION ON Game Engine
PRESENTATION ON Game Engine
 
XNA and Windows Phone
XNA and Windows PhoneXNA and Windows Phone
XNA and Windows Phone
 
Casual and Social Games with Unity
Casual and Social Games with UnityCasual and Social Games with Unity
Casual and Social Games with Unity
 
Unity Introduction
Unity IntroductionUnity Introduction
Unity Introduction
 
Game software development trends
Game software development trendsGame software development trends
Game software development trends
 
One Handed Controller
One Handed ControllerOne Handed Controller
One Handed Controller
 

Similar to Project Report Tron Legacy

Galactic Wars XNA Game
Galactic Wars XNA GameGalactic Wars XNA Game
Galactic Wars XNA GameSohil Gupta
 
The complete srs documentation of our developed game.
The complete srs documentation of our developed game. The complete srs documentation of our developed game.
The complete srs documentation of our developed game. Isfand yar Khan
 
Introduction to html5 game programming with impact js
Introduction to html5 game programming with impact jsIntroduction to html5 game programming with impact js
Introduction to html5 game programming with impact jsLuca Galli
 
Di3211291134
Di3211291134Di3211291134
Di3211291134IJMER
 
Michael Hughes - Y1 GD ngine_terminology
Michael Hughes - Y1 GD ngine_terminologyMichael Hughes - Y1 GD ngine_terminology
Michael Hughes - Y1 GD ngine_terminologyMike Hughes
 
Y1 gd engine_terminology -MPH (Michael P. Hughes)
Y1 gd engine_terminology -MPH (Michael P. Hughes)Y1 gd engine_terminology -MPH (Michael P. Hughes)
Y1 gd engine_terminology -MPH (Michael P. Hughes)Mike Hughes
 
Y1 gd engine_terminology
Y1 gd engine_terminologyY1 gd engine_terminology
Y1 gd engine_terminologyrosstapher
 
Enrique Duvós: Adobe Gaming Solutions
 Enrique Duvós: Adobe Gaming Solutions Enrique Duvós: Adobe Gaming Solutions
Enrique Duvós: Adobe Gaming SolutionsDevGAMM Conference
 
unity gaming programing basics for students ppt
unity gaming programing basics for students pptunity gaming programing basics for students ppt
unity gaming programing basics for students pptKathiriyaParthiv
 
Chapt 6 game testing and publishing
Chapt 6   game testing and publishingChapt 6   game testing and publishing
Chapt 6 game testing and publishingMuhd Basheer
 
Sony Erricson X1 Panel Development
Sony Erricson X1 Panel DevelopmentSony Erricson X1 Panel Development
Sony Erricson X1 Panel DevelopmentSeo Jinho
 
Y1 gd engine_terminology
Y1 gd engine_terminologyY1 gd engine_terminology
Y1 gd engine_terminologyBenWhite101
 
Introduction to Game Engine: Concepts & Components
Introduction to Game Engine: Concepts & ComponentsIntroduction to Game Engine: Concepts & Components
Introduction to Game Engine: Concepts & ComponentsPouya Pournasir
 
Porting unity games to windows - London Unity User Group
Porting unity games to windows - London Unity User GroupPorting unity games to windows - London Unity User Group
Porting unity games to windows - London Unity User GroupLee Stott
 
Beginning Game Development in XNA
Beginning Game Development in XNABeginning Game Development in XNA
Beginning Game Development in XNAguest9e9355e
 
Beginning Game Development in XNA
Beginning Game Development in XNABeginning Game Development in XNA
Beginning Game Development in XNAguest9e9355e
 

Similar to Project Report Tron Legacy (20)

Galactic Wars XNA Game
Galactic Wars XNA GameGalactic Wars XNA Game
Galactic Wars XNA Game
 
The complete srs documentation of our developed game.
The complete srs documentation of our developed game. The complete srs documentation of our developed game.
The complete srs documentation of our developed game.
 
Presentación Unity
Presentación UnityPresentación Unity
Presentación Unity
 
Introduction to html5 game programming with impact js
Introduction to html5 game programming with impact jsIntroduction to html5 game programming with impact js
Introduction to html5 game programming with impact js
 
Di3211291134
Di3211291134Di3211291134
Di3211291134
 
Michael Hughes - Y1 GD ngine_terminology
Michael Hughes - Y1 GD ngine_terminologyMichael Hughes - Y1 GD ngine_terminology
Michael Hughes - Y1 GD ngine_terminology
 
Shootemup report
Shootemup reportShootemup report
Shootemup report
 
Y1 gd engine_terminology -MPH (Michael P. Hughes)
Y1 gd engine_terminology -MPH (Michael P. Hughes)Y1 gd engine_terminology -MPH (Michael P. Hughes)
Y1 gd engine_terminology -MPH (Michael P. Hughes)
 
Y1 gd engine_terminology
Y1 gd engine_terminologyY1 gd engine_terminology
Y1 gd engine_terminology
 
Enrique Duvós: Adobe Gaming Solutions
 Enrique Duvós: Adobe Gaming Solutions Enrique Duvós: Adobe Gaming Solutions
Enrique Duvós: Adobe Gaming Solutions
 
unity gaming programing basics for students ppt
unity gaming programing basics for students pptunity gaming programing basics for students ppt
unity gaming programing basics for students ppt
 
Chapt 6 game testing and publishing
Chapt 6   game testing and publishingChapt 6   game testing and publishing
Chapt 6 game testing and publishing
 
Sony Erricson X1 Panel Development
Sony Erricson X1 Panel DevelopmentSony Erricson X1 Panel Development
Sony Erricson X1 Panel Development
 
Y1 gd engine_terminology
Y1 gd engine_terminologyY1 gd engine_terminology
Y1 gd engine_terminology
 
intern.pdf
intern.pdfintern.pdf
intern.pdf
 
Introduction to Game Engine: Concepts & Components
Introduction to Game Engine: Concepts & ComponentsIntroduction to Game Engine: Concepts & Components
Introduction to Game Engine: Concepts & Components
 
Porting unity games to windows - London Unity User Group
Porting unity games to windows - London Unity User GroupPorting unity games to windows - London Unity User Group
Porting unity games to windows - London Unity User Group
 
Black book
Black bookBlack book
Black book
 
Beginning Game Development in XNA
Beginning Game Development in XNABeginning Game Development in XNA
Beginning Game Development in XNA
 
Beginning Game Development in XNA
Beginning Game Development in XNABeginning Game Development in XNA
Beginning Game Development in XNA
 

Project Report Tron Legacy

  • 1. CONTENTS Chapter Page No. Project Title Project Certificate Acknowledgement Abstract Tables and figures 1. Introduction 1 1.1 Activity Diagram for the Game 2 1.2.States Of the Game 3 4. Output shots and sourcecode of Project 14 2. Related Theory 23 3. Diagrams Related Theory 29 7. Action Listener in Java 35 8. Key Listener In Java 41 9. Java Multithreading 49 10. Java 2D 66 11. Conclusion 100 12. Bibliography 101 System Requirement Analysis and Specification
  • 2. System Requirement Analysis And Specifications Introduction 1. PURPOSE: The purpose of this SRS document is to specify software requirements of the Game Tron. It is intended to be a complete specification of what functionality the game provides. 2. PROJECT SCOPE:  To develop a platform independent gaming system  Providing an interactive and rich GUI to users  Developing a game that is easy to play and interesting 3. ABBREVIATIONS:  S/W – software  H/W - hardware  TCP/IP – Transmission control Protocol/Internet Protocol 4. REFERENCES:  Complete Reference :java 2 by Herbert Schildt  http://java.sun.com/  http://www.networkcomputing.com/
  • 3. 5. OVERVIEW: SRS will include 2 sections Overall description will describe major components of the system, interconnection and external interfaces. Specific Requirements will describe the functions of actors, their roles in the system and constraints. Overall Description Product Perspective: The product is viewed with a sense of providing better, efficient and less time consuming system for connecting and sharing information over the network. 1. Hardware Interface
  • 4. USER SIDE PROCESSOR RAM DISK SPACE OS (windows or linux or mac) Pentium II at 400 MHz 44 MB 4 GB SYSTEM SIDE OS(windows or linux or mac) Pentium II at 1 GHz 412 MB 4 GB Table.1 2. Software Interface USER Software Platform JRE1 Windows, Mac, Linux SYSTEM Software Platform JRE1 Windows JDK 4 Windows Netbeans7.0 Windows Table.2 3. User Interface Game Window with easy to use features
  • 5. Keys Provided for two user 4. Operation The Two players start the game , playing against each other. The player who traps the other one wins. The player must also not touch the walls of the screen and also not touch his ownself. Constraints Availability NetBeans7.0 for the system to work JRE 1.4 or above Specific Requirements This section contains the s/w requirements to a level of detail sufficient to enable designers to design the system and analyze the system. External Interface
  • 6. 1) User interfaces 1. New Game screen of the Game 2. Player Name enter field option 3. The window for Playing the Game 4. The window for Restarting Or Playing Again 5. It also shows the rules and controls along with the about screen. 2) Hardware Interfaces 1. Screen resolution of at least 800x400 required for proper and complete view 3) Software interface 1. Windows/mac/linux operating system 2. Netbeans 7.0 to run the file System Features 1. Fast and efficient process 2. Free 3. Platform independent Performance requirements 1. Use of latest processor 2. Use of larger amount of memory for storing larger details of data 3. Speedier net connections for improving the speed of process
  • 7. Software system attributes 1. Maintainability The system is maintainable as it has been implemented using object oriented concepts that allow the further modifications to be made without disturbing the original structure of the system 2. Portability The s/w being developed in JAVA makes it portable. It is generic in that it can be used on different platforms.
  • 8. ABSTRACT Set during the era between the two TRON films, TRON: Evolution conveys the story of significant events within the TRON mythology. The game features an epic adventure across a massive digital world filled with high-mobility disc-based combat and advanced light cycles. TRON: Evolution is one of the keys to unlocking the TRON mythology. The game's story takes place before the "TRON: Legacy" events and provides insight into the film's past. As an integrated entertainment experience, the film will reference elements of the game's story. Fans will want to play the game to learn more about the TRON mythology seen in the film, but each entertainment experience will stand on its own...."
  • 10. INTRODUCTION Similar to the classic game “Snake” in that you want to maneuver your wall building cycle until you run your opponent into wall before they do the same to you. Tron is a coin-operated arcade video game manufactured and distributed by Bally Midway in1982. It is based on the Walt Disney Productions motion picture Tron released in the same year. The game consists of four sub games inspired by the events of the science fiction film. It features some characters and equipment seen in the film, e.g. the Light Cycles, battle tanks, the Input/output Tower. The game earned more than the film's initial release. In 1983, Midway released the sequel arcade game Discs of Tron, which was inspired by the disc throwing combat sequence of the film. Another sequel followed in 2003 with the computer game Tron 2.0. On January 10, 2008 the game was released for Xbox Live Arcade ported from Digital Eclipse and branded by Disney Interactive. In the 2010 film Tron: Legacy, the arcade game makes a brief appearance, but is displayed as being manufactured and distributed by the in-universe company ENCOM International instead of Bally Midway. It is also displayed as such on the "ENCOM International" promotional website for the film. 1
  • 11. Activity Diagram For The Game 2
  • 12. States Of The Game 3
  • 13. OUTPUTSHOTS AND WORKING (AS PER USER’S PERSRECTIVE) Main Menu Of The Game The user is supposed to click one of the options available as per his/her choice. If the user has clicked the wrong option, he/she can move to the previous menu using BACK option. The game can be exited using EXIT option.
  • 14. As soon as the user clicks the NEW GAME option, the above screen is invoked, where the two users can enter their respective names. The user can switch back to the Main Menu using BACK option. The START option starts the game.
  • 15. The above screen gets invoked when the user clicks the START option. The two users are ready to operate and play the game. The controls for the two users can be seen using the HELP option. The Players try to trap each other using a path. The player who gets trapped loses.
  • 16. The above screen shows the working of the game where the two players are playing, using their respective controls.
  • 17. The above screen appears when the Red user traps the Blue user, when the screen shows up the player who wins. Here Red player wins. The PLAY AGAIN option starts the game again.
  • 18. The above screen appears when the Blue user traps the Red user, when the screen shows up the player who wins. Here Blue player wins. The PLAY AGAIN option starts the game again.
  • 19. The above screen appears when the users collide head-on, which gives the condition for the game drawn. The screen shows up the GAME DRAW message. The game can be resumed by clicking the PLAY AGAIN option.
  • 20. The above screen shows up the HELP option, where the controls have been mentioned for the two users. The user can go back to the previous menu using BACK option.
  • 22. RELATED THEORY 2.1.THE JAVA’S MAGIC: Java is a programming language originally developed by James Gosling at Sun Microsystems (which is now a subsidiary of Oracle Corporation) and released in 1995 as a core component of Sun Microsystems' Java platform. The language derives much of its syntax from C and C++ but has a simpler object model and fewer low-level facilities. Java applications are typically compiled to bytecode (class file) that can run on any Java Virtual Machine (JVM) regardless of computer architecture. Java is a general-purpose, concurrent, class-based, object- oriented language that is specifically designed to have as few implementation dependencies as possible. It is intended to let application developers "write once, run anywhere". Java is currently one of the most popular programming languages in use, and is widely used from application software to web applications. The original and reference implementation Java compilers, virtual machines, and class libraries were developed by Sun from 1995. As of May 2007, in compliance with the specifications of the Java Community Process, Sun relicensed most of its Java technologies under the GNU General Public License. Others have also developed alternative implementations of these Sun technologies, such as the GNU Compiler for Java, GNU Classpath,and Dalvik.James Gosling, Mike Sheridan, and Patrick Naughton initiated the Java language project in June 1991. Java was originally designed for interactive television, but it was too advanced for the digital cable television industry at the time. The language was initially called Oak after an Oak tree that stood - outside Gosling's office; it went by the name Green later, and was later renamed Java, from a list of random words. Gosling aimed to implement a virtual machine and a language that had a familiar C/C++ style of notation. Sun Microsystems released the first public implementation as Java 1.0 in 1995. It promised "Write Once, Run Anywhere" (WORA), providing no- cost run-times on popular platforms. Fairly secure and featuring configurable security, it allowed network- and file-access restrictions. Major web browsers soon incorporated the ability to run Java applets within web pages, and Java quickly became popular. With the advent of Java 2 (released initially as J2SE 1.2 in December 1998–1999), new versions had multiple configurations built for different types of platforms. For example, J2EE targeted enterprise applications and the greatly stripped-down version J2MEfor mobile applications (Mobile Java). J2SE designated the Standard Edition. In 2006, for marketing purposes, Sun renamed new J2 versions as Java EE, Java ME, and Java SE, respectively. In 1997, Sun Microsystems approached the ISO/IEC JTC1 standards body and later the Ecma International to formalize Java. 4
  • 23. At one time, Sun made most of its Java implementations available without charge, despite their proprietary software status. Sun generated revenue from Java through the selling of licenses for specialized products such as the Java Enterprise System. Sun distinguishes between its Software Development Kit (SDK) and Runtime Environment (JRE) (a subset of the SDK); the primary distinction involves the JRE's lack of the compiler, utility programs, and header files. On November 13, 2006, Sun released much of Java as open source software under the terms of the GNU General Public License (GPL). On May 8, 2007, Sun finished the process, making all of Java's core code available under free software/open-source distribution terms, aside from a small portion of code to which Sun did not hold the copyright. Sun's vice-president Rich Green has said that Sun's ideal role with regards to Java is as an "evangelist." Following Oracle Corporation's acquisition of Sun Microsystems in 2009–2010, Oracle has described itself as the "steward of Java technology with a relentless commitment to fostering a community of participation and transparency". 2.2 PRINCIPALS There were five primary goals in the creation of the Java language: 1. It should be "simple, object-oriented and familiar". 2. It should be "robust and secure". 3. It should be "architecture-neutral and portable". 4. It should execute with "high performance". 5. It should be "interpreted, threaded, and dynamic". One characteristic of Java is portability, which means that computer programs written in the Java language must run - 37 - similarly on any supported hardware/operating-system platform. This is achieved by compiling the Java language code to an intermediate representation called Java bytecode, instead of directly to platform-specific machine code. Java bytecode instructions are analogous to machine code, but are intended to be interpreted by a virtual machine (VM) written specifically for the host hardware. End-users commonly use a Java Runtime Environment (JRE) installed on their own machine for standalone Java applications, or in a Web browser for Java applets. Standardized libraries provide a generic way to access host specific features such as graphics, threading, and networking. A major benefit of using bytecode is porting. 5
  • 24. 2.3.THE ANDROID’S MAGIC: In July 2005, Google acquired Android Inc., a small startup company based in Palo Alto, CA. Android's co-founders who went to work at Google included Andy Rubin (co-founder of Danger), Rich Miner (co-founder of Wildfire Communications, Inc), Nick Sears (once VP at T- Mobile), and Chris White (one of the first engineers at WebTV). At the time, little was known about the functions of Android Inc. other than they made software for mobile phones. Open Handset Alliance Founded On 5 November 2007, the Open Handset Alliance, a consortium of several companies which include Google, HTC, Intel, Motorola, Qualcomm, T-Mobile, Sprint Nextel and NVIDIA, was unveiled with the goal to develop open standards for mobile devices. Along with the formation of the Open Handset Alliance, the OHA also unveiled their first product, Android, an open source mobile device platform based on the Linux operating system. Hardware Google has unveiled at least three prototypes for Android, at the Mobile World Congress on February 12, 2008. One prototype at the ARM booth displayed several basic Google applications. A 'd-pad' control zooming of items in the dock with a relatively quick response. 2.4 FEATURES OF ANDROID OS:  Application framework enabling reuse and replacement of components  Dalvik virtual machine optimized for mobile devices  Integrated browser based on the open source WebKit engine  Optimized graphics powered by a custom 2D graphics library; 3D graphics based on the OpenGL ES 1.0 specification (hardware acceleration optional)  SQLite for structured data storage 6
  • 25.  Media support for common audio, video, and still image formats (MPEG4, H.264, MP3, AAC, AMR, JPG, PNG, GIF) I. GSM Telephony (hardware dependent) II. Bluetooth, EDGE, 3G, and WiFi (hardware dependent) III. Camera, GPS, compass, and accelerometer (hardware dependent) IV. Rich development environment including a device emulator, tools for debugging, memory and performance profiling, and a plugin for the Eclipse IDE 2.5 APPLICATION FRAMEWORK Developers have full access to the same framework APIs used by the core applications. The application architecture is designed to simplify the reuse of components; any application can publish its capabilities and any other application may then make use of those capabilities (subject to security constraints enforced by the framework). This same mechanism allows components to be replaced by the user. Underlying all applications is a set of services and systems, including:  A rich and extensible set of Views that can be used to build an application, including lists, grids, text boxes, buttons, and even an embeddable web browser.  Content Providers that enable applications to access data from other applications (such as Contacts), or to share their own data  A Resource Manager, providing access to non-code resources such as localized strings, graphics, and lat files  A Notification Manager that enables all applications to display custom alerts in the status bar  An Activity Manager that manages the life cycle of applications and provides a common navigation backstack. 7
  • 26. 2.6 ANDROID ARCHITECTURE The following diagram shows the major components of Android Figure 1: Architecture of Android OS 8
  • 27. 2.7 LIBRARIES Android includes a set of C/C++ libraries used by various components of the Android system. These capabilities are exposed to developers through the Android application framework. Some of the core libraries are listed below:  ·System C library - a BSD-derived implementation of the standard C system library (libc), tuned for embedded Linux-based devices  Media Libraries - based on PacketVideo's Open CORE; the libraries support playback and recording of many popular audio and video formats, as well as static image files, including MPEG4, H.264, MP3, AAC, AMR, JPG, and PNG  Surface Manager - manages access to the display subsystem and seamlessly composites 2D and 3D graphic layers from multiple applications  LibWebCore - a modern web browser engine which powers both the Android browser and an embeddable web view  SGL - the underlying 2D graphics engine  3D libraries - an implementation based on OpenGL ES 1.0 APIs; the libraries use either hardware 3D acceleration (where available) or the included, highly optimized 3D software rasterizer  Free Type - bitmap and vector font rendering  SQLite - a powerful and lightweight relational database engine available to all applications. 2.8 ANDROID RUNTIME : Android includes a set of core libraries that provides most of the functionality available in the core libraries of the Java programming language. Every Android application runs in its own process, with its own instance of the Dalvik virtual machine. Dalvik has been written so that a device can run multiple VMs efficiently. The Dalvik VM executes files in the Dalvik Executable (.dex) format which is optimized for minimal memory footprint. 9
  • 28. The VM is register-based, and runs classes compiled by a Java language compiler that have been transformed into the .dex format by the included "dx" tool. The Dalvik VM relies on the Linux kernel for underlying functionality such as threading and low-level memory management. At the same level there is Android Runtime, where the main component Dalvik Virtual Machine is located. It was designed specifically for Android running in limited environment, where the limited battery, CPU, memory and data storage are the main issues. Android gives an integrated tool “dx”, which converts generated byte code from .jar to .dex file, after this byte code becomes much more efficient to run on the small processors. Figure 2: Conversion from .java to .dex file As the result, it is possible to have multiple instances of Dalvik virtual machine running on the single device at the same time. The Core libraries are written in Java language and contains of the collection classes, the utilities, IO and other tools. 10
  • 30. 3.1 ACTIVITY DIAGRAMS Activity diagrams describe the workflow behavior of a system. Activity diagrams are similar to state diagrams because activities are the state of doing something. The diagrams describe the state of activities by showing the sequence of activities performed. Activity diagrams can show activities that are conditional or parallel. When to Use: Activity Diagrams Activity diagrams should be used in conjunction with other modeling techniques such as interaction diagrams and state diagrams. The main reason to use activity diagrams is to model the workflow behind the system being designed. Activity Diagrams are also useful for: analyzing a use case by describing what actions need to take place and when they should occur; describing a complicated sequential algorithm; and modeling applications with parallel processes. However, activity diagrams should not take the place of interaction diagrams and state diagrams. Activity diagrams do not give detail about how objects behave or how objects collaborate. How to Draw: Activity Diagrams Activity diagrams show the flow of activities through the system. Diagrams are read from top to bottom and have branches and forks to describe conditions and parallel activities. A fork is used when multiple activities are occurring at the same time. The diagram below shows a fork after activity1. This indicates that both activity2 and activity3 are occurring at the same time. After activity2 there is a branch. The branch describes what activities will take place based on a set of conditions. All branches at some point are followed by a merge to indicate the end of the conditional behavior started by that branch. After the merge all of the parallel activities must be combined by a join before transitioning into the final activity state.
  • 31. 11
  • 32. 3.2STATE DIAGRAMS State diagrams are used to describe the behavior of a system. State diagrams describe all of the possible states of an object as events occur. Each diagram usually represents objects of a single class and track the different states of its objects through the system. When to Use: State Diagrams Use state diagrams to demonstrate the behavior of an object through many use cases of the system. Only use state diagrams for classes where it is necessary to understand the behavior of the object through the entire system. Not all classes will require a state diagram and state diagrams are not useful for describing the collaboration of all objects in a use case. State diagrams are other combined with other diagrams such as interaction diagrams and activity diagrams. How to Draw: State Diagrams State diagrams have very few elements. The basic elements are rounded boxes representing the state of the object and arrows indicting the transition to the next state. The activity section of the state symbol depicts what activities the object will be doing while it is in that state. 12
  • 33. All state diagrams being with an initial state of the object. This is the state of the object when it is created. After the initial state the object begins changing states. Conditions based on the activities can determine what the next state the object transitions to. Below is an example of a state diagram might look like for an Order object. When the object enters the Checking state it performs the activity "check items." After the activity is completed the object transitions to the next state based on the conditions [all items available] or [an item is not available]. If an item is not available the order is canceled. If all items are available then the order is dispatched. When the object transitions to the Dispatching state the activity "initiate delivery" is performed. After this activity is complete the object transitions againDelivered state. 13
  • 34. State diagrams can also show a super-state for the object. A super-state is used when many transitions lead to a certain state. Instead of showing all of the transitions from each state to the redundant state a super-state can be used to show that all of the states inside of the super-state can transition to the redundant state. This helps make the state diagram easier to read. The diagram below shows a super-state. Both the Checking and Dispatching states can transition into the Canceled state, so a transition is shown from a super-state named Active to the state Cancel. By contrast, the state Dispatching can only transition to the Delivered state, so we show an arrow only from the Dispatching state to the Delivered state. 14
  • 36. 4.1 ACTION LISTENER IN JAVA Action listeners are probably the easiest — and most common — event handlers to implement. You implement an action listener to define what should be done when an user performs certain operation. An action event occurs, whenever an action is performed by the user. Examples: When the user clicks a button , chooses a menu item , presses Enter in a text field . The result is that an actionPerformed message is sent to all action listeners that are registered on the relevant component. To write an Action Listener, follow the steps given below: Declare an event handler class and specify that the class either implements an ActionListener interface or extends a class that implements an ActionListener interface. For example: public class MyClass implements ActionListener { Register an instance of the event handler class as a listener on one or more components. For example: someComponent.addActionListener(instanceOfMyClass); Include code that implements the methods in listener interface. For example: public void actionPerformed(ActionEvent e) { ...//code that reacts to the action... } In general, to detect when the user clicks an onscreen button (or does the keyboard equivalent), a program must have an object that implements the ActionListener interface. The program must register this object as an action listener on the button (the event source), using the addActionListener method. When the user clicks the onscreen button, the button fires an action event. This results in the invocation of the action listener's actionPerformed method (the only method in the ActionListener interface). The single argument to the method is an ActionEvent object that gives information about the event and its source. Let us write a simple program which displays how many number of times a button is clicked by the user. First, here is the code that sets up the TextField , button and numClicks variable: public class AL extends Frame implements WindowListener,ActionListener 15
  • 37. { TextField text = new TextField(20); Button b; private int numClicks = 0; In the above example, the event handler class is AL which implements ActionListener. We would like to handle the button-click event, so we add an action listener to the button b as below: b = new Button("Click me"); b.addActionListener(this); In the above code, Button b is a component upon which an instance of event handler class AL is registered. Now, we want to display the text as to how many number of times a user clicked button. We can do this by writing the code as below: public void actionPerformed(ActionEvent e) { numClicks++; text.setText("Button Clicked " + numClicks + " times"); Now, when the user clicks the Button b, the button fires an action event which invokes the action listener's actionPerformed method. Each time the user presses the button, numClicks variable is appended and the message is displayed in the text field. Here is the complete program(AL.java): import java.awt.*; import java.awt.event.*; public class AL extends Frame implements WindowListener,ActionListener 16
  • 38. { TextField text = new TextField(20); Button b; private int numClicks = 0; public static void main(String[] args) { AL myWindow = new AL("My first window"); myWindow.setSize(350,100); myWindow.setVisible(true); } public AL(String title) { super(title); setLayout(new FlowLayout()); addWindowListener(this); b = new Button("Click me"); add(b); add(text); b.addActionListener(this); } public void actionPerformed(ActionEvent e) 17
  • 39. { numClicks++; text.setText("Button Clicked " + numClicks + " times"); } public void windowClosing(WindowEvent e) { dispose(); System.exit(0); } public void windowOpened(WindowEvent e) {} public void windowActivated(WindowEvent e) {} public void windowIconified(WindowEvent e) {} public void windowDeiconified(WindowEvent e) {} public void windowDeactivated(WindowEvent e) {} public void windowClosed(WindowEvent e) {} } 18
  • 40. 4.2THE ACTION LISTENER API The ActionListener Interface has only one method, it has no corresponding adapter class. Method Purpose actionPerformed(actionEvent) Called just after the user performs an action. The ActionEvent Class Method Purpose String getActionCommand() Returns the string associated with this action. Most objects that can fire action events support a method called setActionCommand that lets you set this string. int getModifiers() Returns an integer representing the modifier keys the user was pressing when the action event occurred. You can use the ActionEvent-defined constants SHIFT_MASK, CTRL_MASK, META_MASK, and ALT_MASK to determine which keys were pressed. For example, if the user Shift-selects a menu item, then the following expression is nonzero: actionEvent.getModifiers() & ActionEvent.SHIFT_MASK Object getSource() (in java.util.EventObject) Returns the object that fired the event. 19
  • 41. 4.3EXAMPLES The following table lists some of the many examples that use action listeners. Example Where Described Notes Beeper This section and Introduction to Event Listeners Contains one button with one action listener that beeps when you click the button. MultiListener Introduction to Event Listeners Registers two different action listeners on one button. Also registers the same action listener on two different buttons. RadioButtonDemo How to Use Radio Buttons Registers the same action listener on five radio buttons. The listener uses the getActionCommand method to determine which radio button fired the event. MenuDemo Getting Started Shows how to listen for action events on menu items. TextDemo Getting Started Loads an image in an action listener. Because loading an image can take a while, this program uses a SwingWorker to load the image in a background thread. TableDialogEditDemo Getting Started Registers an action listener through a factory method on the OK button of a color chooser dialog. SliderDemo Getting Started Registers an action listener on a timer that controls an animation loop. 20
  • 43. 5.1KEY LISTENER IN JAVA Key events indicate when the user is typing at the keyboard. Specifically, key events are fired by the component with the keyboard focus when the user presses or releases keyboard keys. For detailed information about focus, see How to Use the Focus Subsystem. Notifications are sent about two basic kinds of key events:  The typing of a Unicode character  The pressing or releasing of a key on the keyboard The first kind of event is called a key-typed event. The second kind is either a key-pressed or key-released event. In general, you react to only key-typed events unless you need to know when the user presses keys that do not correspond to characters. For example, to know when the user types a Unicode character — whether by pressing one key such as 'a' or by pressing several keys in sequence — you handle key-typed events. On the other hand, to know when the user presses the F1 key, or whether the user pressed the '3' key on the number pad, you handle key-pressed events. To make a component get the keyboard focus, follow these steps: Make sure the component's isFocusable method returns true. This state allows the component to receive the focus. For example, you can enable keyboard focus for a JLabel component by calling the setFocusable(true) method on the label. Make sure the component requests the focus when appropriate. For custom components, implement a mouse listener that calls the requestFocusInWindow method when the component is clicked. You can obtain detailed information about a particular key-pressed event. For example, you can query a key-pressed event to determine if it was fired from an action key. Examples of action keys include Copy, Paste, Page Up, Undo, and the arrow and function keys. As of JDK release 1.4, you can also query a key-pressed or key-released event to determine the location of the key that fired the event. Most key events are fired from the standard keyboard, but the events for some keys, such as Shift, have information on whether the user pressed the Shift key on the left or the right side of the keyboard. Likewise, the number '2' can be typed from either the standard keyboard or from the number pad. For key-typed events you can obtain the key character value as well as any modifiers used. 21
  • 44. The following example demonstrates key events. It consists of a text field that you can type into, followed by a text area that displays a message every time the text field fires a key event. A button at the bottom of the window lets you clear both the text field and text area. Here is the demo's key event handling code: public class KeyEventDemo ... implements KeyListener ... { ...//where initialization occurs: typingArea = new JTextField(20); typingArea.addKeyListener(this); //Uncomment this if you wish to turn off focus //traversal. The focus subsystem consumes //focus traversal keys, such as Tab and Shift Tab. //If you uncomment the following line of code, this //disables focus traversal and the Tab events //become available to the key event listener. //typingArea.setFocusTraversalKeysEnabled(false); 22
  • 45. /** Handle the key typed event from the text field. */ public void keyTyped(KeyEvent e) { displayInfo(e, "KEY TYPED: "); } /** Handle the key-pressed event from the text field. */ public void keyPressed(KeyEvent e) { displayInfo(e, "KEY PRESSED: "); } /** Handle the key-released event from the text field. */ public void keyReleased(KeyEvent e) { displayInfo(e, "KEY RELEASED: "); } ... private void displayInfo(KeyEvent e, String keyStatus){ //You should only rely on the key char if the event //is a key typed event. int id = e.getID(); String keyString; if (id == KeyEvent.KEY_TYPED) { char c = e.getKeyChar(); keyString = "key character = '" + c + "'"; 23
  • 46. } else { int keyCode = e.getKeyCode(); keyString = "key code = " + keyCode + " (" + KeyEvent.getKeyText(keyCode) + ")"; } int modifiersEx = e.getModifiersEx(); String modString = "extended modifiers = " + modifiersEx; String tmpString = KeyEvent.getModifiersExText(modifiersEx); if (tmpString.length() > 0) { modString += " (" + tmpString + ")"; } else { modString += " (no extended modifiers)"; } String actionString = "action key? "; if (e.isActionKey()) { actionString += "YES"; } else { actionString += "NO"; 24
  • 47. } String locationString = "key location: "; int location = e.getKeyLocation(); if (location == KeyEvent.KEY_LOCATION_STANDARD) { locationString += "standard"; } else if (location == KeyEvent.KEY_LOCATION_LEFT) { locationString += "left"; } else if (location == KeyEvent.KEY_LOCATION_RIGHT) { locationString += "right"; } else if (location == KeyEvent.KEY_LOCATION_NUMPAD) { locationString += "numpad"; } else { // (location == KeyEvent.KEY_LOCATION_UNKNOWN) locationString += "unknown"; } ...//Display information about the KeyEvent... } } 25
  • 48. 5.2 THE KEY LISTENER API The corresponding adapter class is KeyAdapter. Method Purpose keyTyped(KeyEvent) Called just after the user types a Unicode character into the listened-to component. keyPressed(KeyEvent) Called just after the user presses a key while the listened-to component has the focus. keyReleased(KeyEvent) Called just after the user releases a key while the listened-to component has the focus. 5.3 KEY EVENT CLASS The KeyEvent class inherits many useful methods from the InputEvent class, such as getModifiersEx, and a couple of useful methods from the ComponentEvent and AWTEvent classes. See the InputEvent Class table in the mouse listener page for a complete list. Method Purpose int getKeyChar() Obtains the Unicode character associated with this event. Only rely on this value for key-typed events. int getKeyCode() Obtains the key code associated with this event. The key code identifies the particular key on the keyboard that the user pressed or released. The KeyEvent class defines many key code constants for commonly seen keys. For example, VK_A specifies the key labeled A, and VK_ESCAPE specifies the Escape key. String getKeyText(int) String getKeyModifiersText(int) Return text descriptions of the event's key code and modifier keys, respectively. int getModifiersEx() String getModifiersExText(int Return the extended modifiers mask for this event. There are methods inherited from the InputEvent class. Extended modifiers represent the state of all modal keys. The getModifiersExText method returns a string describing the extended modifier keys and
  • 49. modifiers) mouse buttons. Since the getModifiersEx and getModifiersExText methods provide more information about key events, they are preferred over the getKeyText or getKeyModifiersText methods. boolean isActionKey() Returns true if the key firing the event is an action key. Examples of action keys include Cut, Copy, Paste, Page Up, Caps Lock, the arrow and function keys. This information is valid only for key- pressed and key-released events. int getKeyLocation() Returns the location of the key that fired this event. This provides a way to distinguish keys that occur more than once on a keyboard, such as the two shift keys, for example. The possible values are KEY_LOCATION_STANDARD, KEY_LOCATION_LEFT, KEY_LOCATION_RIGHT, KEY_LOCATION_NUMPAD, or KEY_LOCATION_UNKNOWN. This method always returns KEY_LOCATION_UNKNOWN for key-typed events. Introduced in JDK release 1.4. 27
  • 51. 6.1JAVA MULTI-THREADING Java provides built-in support for multithreaded programming. A multithreaded program contains two or more parts that can run concurrently. Each part of such a program is called a thread, and each thread defines a separate path of execution. A multithreading is a specialized form of multitasking. Multitasking threads require less overhead than multitasking processes. I need to define another term related to threads: process: A process consists of the memory space allocated by the operating system that can contain one or more threads. A thread cannot exist on its own; it must be a part of a process. A process remains running until all of the non-daemon threads are done executing. Multithreading enables you to write very efficient programs that make maximum use of the CPU, because idle time can be kept to a minimum. Life Cycle of a Thread: A thread goes through various stages in its life cycle. For example, a thread is born, started, runs, and then dies. Following diagram shows complete life cycle of a thread. 28
  • 52. Above mentioned stages are explained here:  New: A new thread begins its life cycle in the new state. It remains in this state until the program starts the thread. It is also referred to as a born thread.  Runnable: After a newly born thread is started, the thread becomes runnable. A thread in this state is considered to be executing its task.  Waiting: Sometimes a thread transitions to the waiting state while the thread waits for another thread to perform a task.A thread transitions back to the runnable state only when another thread signals the waiting thread to continue executing.  Timed waiting: A runnable thread can enter the timed waiting state for a specified interval of time. A thread in this state transitions back to the runnable state when that time interval expires or when the event it is waiting for occurs.  Terminated: A runnable thread enters the terminated state when it completes its task or otherwise terminates. 6.2 THREAD PRIORITIES Every Java thread has a priority that helps the operating system determine the order in which threads are scheduled. Java priorities are in the range between MIN_PRIORITY (a constant of 1) and MAX_PRIORITY (a constant of 10). By default, every thread is given priority NORM_PRIORITY (a constant of 5). Threads with higher priority are more important to a program and should be allocated processor time before lower-priority threads. However, thread priorities cannot guarantee the order in which threads execute and very much platform dependentant. Creating a Thread: Java defines two ways in which this can be accomplished: You can implement the Runnable interface. You can extend the Thread class, itself. Create Thread by Implementing Runnable: The easiest way to create a thread is to create a class that implements the Runnable interface. 29
  • 53. To implement Runnable, a class need only implement a single method called run( ), which is declared like this: public void run( ) You will define the code that constitutes the new thread inside run() method. It is important to understand that run() can call other methods, use other classes, and declare variables, just like the main thread can. After you create a class that implements Runnable, you will instantiate an object of type Thread from within that class. Thread defines several constructors. The one that we will use is shown here: Thread(Runnable threadOb, String threadName); Here threadOb is an instance of a class that implements the Runnable interface and the name of the new thread is specified by threadName. After the new thread is created, it will not start running until you call its start( ) method, which is declared within Thread. The start( ) method is shown here: void start( ); Example: Here is an example that creates a new thread and starts it running: // Create a new thread. class NewThread implements Runnable { Thread t; NewThread() { // Create a new, second thread t = new Thread(this, "Demo Thread"); System.out.println("Child thread: " + t); t.start(); // Start the thread } 30
  • 54. // This is the entry point for the second thread. public void run() { try { for(int i = 5; i > 0; i--) { System.out.println("Child Thread: " + i); // Let the thread sleep for a while. Thread.sleep(500); } } catch (InterruptedException e) { System.out.println("Child interrupted."); } System.out.println("Exiting child thread."); } } class ThreadDemo { public static void main(String args[]) { new NewThread(); // create a new thread try { for(int i = 5; i > 0; i--) { System.out.println("Main Thread: " + i); Thread.sleep(1000); } } catch (InterruptedException e) 31
  • 55. { System.out.println("Main thread interrupted."); } System.out.println("Main thread exiting."); } } This would produce following result: Child thread: Thread[Demo Thread,5,main] Main Thread: 5 Child Thread: 5 Child Thread: 4 Main Thread: 4 Child Thread: 3 Child Thread: 2 Main Thread: 3 Child Thread: 1 Exiting child thread. Main Thread: 2 Main Thread: 1 Main thread exiting. Create Thread by Extending Thread: The second way to create a thread is to create a new class that extends Thread, and then to create an instance of that class. The extending class must override the run( ) method, which is the entry point for the new thread. It must also call start( ) to begin execution of the new thread. 32
  • 56. Example: Here is the preceding program rewritten to extend Thread: // Create a second thread by extending Thread class NewThread extends Thread { NewThread() { // Create a new, second thread super("Demo Thread"); System.out.println("Child thread: " + this); start(); // Start the thread } // This is the entry point for the second thread. public void run() { try { for(int i = 5; i > 0; i--) { System.out.println("Child Thread: " + i); // Let the thread sleep for a while. Thread.sleep(500); } } catch (InterruptedException e) { System.out.println("Child interrupted."); } System.out.println("Exiting child thread."); } 33
  • 57. class ExtendThread { public static void main(String args[]) { new NewThread(); // create a new thread try { for(int i = 5; i > 0; i--) { System.out.println("Main Thread: " + i); Thread.sleep(1000); } } catch (InterruptedException e) { System.out.println("Main thread interrupted."); } System.out.println("Main thread exiting."); } } This would produce following result: Child thread: Thread[Demo Thread,5,main] Main Thread: 5 Child Thread: 5 Child Thread: 4 Main Thread: 4 Child Thread: 3 Child Thread: 2 Main Thread: 3 Child Thread: 1 34
  • 58. Exiting child thread. Main Thread: 2 Main Thread: 1 Main thread exiting. Thread Methods: Following is the list of important medthods available in the Thread class. SN Methods with Description 1 public void start() Starts the thread in a separate path of execution, then invokes the run() method on this Thread object. 2 public void run() If this Thread object was instantiated using a separate Runnable target, the run() method is invoked on that Runnable object. 3 public final void setName(String name) Changes the name of the Thread object. There is also a getName() method for retrieving the name. 4 public final void setPriority(int priority) Sets the priority of this Thread object. The possible values are between 1 and 10. 5 public final void setDaemon(boolean on) A parameter of true denotes this Thread as a daemon thread. 6 public final void join(long millisec) The current thread invokes this method on a second thread, causing the current thread to block until the second thread terminates or the specified number of milliseconds passes. 7 public void interrupt() Interrupts this thread, causing it to continue execution if it was blocked for any reason. 8 public final boolean isAlive() 35
  • 59. Returns true if the thread is alive, which is any time after the thread has been started but before it runs to completion. The previous methods are invoked on a particular Thread object. The following methods in the Thread class are static. Invoking one of the static methods performs the operation on the currently running thread SN Methods with Description 1 public static void yield() Causes the currently running thread to yield to any other threads of the same priority that are waiting to be scheduled 2 public static void sleep(long millisec) Causes the currently running thread to block for at least the specified number of milliseconds 3 public static boolean holdsLock(Object x) Returns true if the current thread holds the lock on the given Object. 4 public static Thread currentThread() Returns a reference to the currently running thread, which is the thread that invokes this method. 5 public static void dumpStack() Prints the stack trace for the currently running thread, which is useful when debugging a multithreaded application. Example: The following ThreadClassDemo program demonstrates some of these methods of the Thread class: // File Name : DisplayMessage.java // Create a thread to implement Runnable public class DisplayMessage implements Runnable { private String message; 36
  • 60. public DisplayMessage(String message) { this.message = message; } public void run() { while(true) { System.out.println(message); } } } // File Name : GuessANumber.java // Create a thread to extentd Thread public class GuessANumber extends Thread { private int number; public GuessANumber(int number) { this.number = number; } public void run() { 37
  • 61. int counter = 0; int guess = 0; do { guess = (int) (Math.random() * 100 + 1); System.out.println(this.getName() + " guesses " + guess); counter++; }while(guess != number); System.out.println("** Correct! " + this.getName() + " in " + counter + " guesses.**"); } } // File Name : ThreadClassDemo.java public class ThreadClassDemo { public static void main(String [] args) { Runnable hello = new DisplayMessage("Hello"); Thread thread1 = new Thread(hello); thread1.setDaemon(true); thread1.setName("hello"); System.out.println("Starting hello thread..."); 38
  • 62. thread1.start(); Runnable bye = new DisplayMessage("Goodbye"); Thread thread2 = new Thread(hello); thread2.setPriority(Thread.MIN_PRIORITY); thread2.setDaemon(true); System.out.println("Starting goodbye thread..."); thread2.start(); System.out.println("Starting thread3..."); Thread thread3 = new GuessANumber(27); thread3.start(); try { thread3.join(); }catch(InterruptedException e) { System.out.println("Thread interrupted."); } System.out.println("Starting thread4..."); Thread thread4 = new GuessANumber(75); thread4.start(); System.out.println("main() is ending..."); 39
  • 63. } This would produce following result. You can try this example again and again and you would get different result every time. Starting hello thread... Starting goodbye thread... Hello Hello Hello Hello Hello Hello Hello Hello Hello Thread-2 guesses 27 Hello ** Correct! Thread-2 in 102 guesses.** Hello Starting thread4... Hello Hello ..........remaining result produced. Major Thread Concepts: While doing Multithreading programming, you would need to have following concepts very handy: 40
  • 64. Thread Synchronization Inter thread Communication Thread Deadlock Thread Control: Suspend, Stop and Resume Using Multithreading: The key to utilizing multithreading support effectively is to think concurrently rather than serially. For example, when you have two subsystems within a program that can execute concurrently, make them individual threads. With the careful use of multithreading, you can create very efficient programs. A word of caution is in order, however: If you create too many threads, you can actually degrade the performance of your program rather than enhance it. Remember, some overhead is associated with context switching. If you create too many threads, more CPU time will be spent changing contexts than executing your program! 41
  • 66. 7.1 OVERVIEW In Java 1.2, the paintComponent method is supplied with a Graphics2D object (a subclass of Graphics), which contains a much richer set of drawing operations. It includes pen widths, dashed lines, image and gradient color fill patterns, the use of arbitrary local fonts, a floating point coordinate system, and a number of coordinate transformation operations. However, to maintain compatibility with Swing as used in Java 1.1, the declared type of the paintComponent argument is Graphics, so you have to cast it to Graphics2D before using it. Java 1.1 Java 1.2 public void paint(Graphics g) { // Set pen parameters g.setColor(someColor); g.setFont(someLimitedFont); // Draw a shape g.drawString(...); g.drawLine(...) g.drawRect(...); // outline g.fillRect(...); // solid g.drawPolygon(...); // outline g.fillPolygon(...); // solid g.drawOval(...); // outline g.fillOval(...); // solid ... } public void paintComponent(Graphics g) { // Clear off-screen bitmap super.paintComponent(g); // Cast Graphics to Graphics2D Graphics2D g2d = (Graphics2D)g; // Set pen parameters g2d.setPaint(fillColorOrPattern); g2d.setStroke(penThicknessOrPattern); g2d.setComposite(someAlphaComposite); g2d.setFont(anyFont); g2d.translate(...); g2d.rotate(...); g2d.scale(...); g2d.shear(...); g2d.setTransform(someAffineTransform); // Allocate a shape SomeShape s = new SomeShape(...); 42
  • 67. g2d.draw(s); // outline g2d.fill(s); // solid }  Main New Features  Colors and patterns: gradient fills, fill patterns from tiled images, transparency  Local fonts  Pen thicknesses, dashing patterns, and segment connection styles  Coordinate transformations  General Approach  Cast the Graphics object to a Graphics2D object public void paintComponent(Graphics g) { super.paintComponent(g); // Typical Swing approach Graphics2D g2d = (Graphics2D)g; g2d.doSomeStuff(...); ... } Create a Shape object Rectangle2D.Double rect = ...; Ellipse2D.Double ellipse = ...; Polygon poly = ...; GeneralPath path = ...; SomeShapeYouDefined shape = ...; // Satisfies Shape interface ... Optional: modify drawing parameters 43
  • 68. g2d.setPaint(fillColorOrPattern); g2d.setStroke(penThicknessOrPattern); g2d.setComposite(someAlphaComposite); g2d.setFont(someFont); g2d.translate(...); g2d.rotate(...); g2d.scale(...); g2d.shear(...); g2d.setTransform(someAffineTransform); Draw an outlined or solid version of the Shape g2d.draw(someShape); g2d.fill(someShape); 7.2 DRAWING SHAPES IN JAVA3D OVERVIEW With the AWT, you generally drew a shape by calling the drawXxx or fillXxx method of the Graphics object. In Java2D, you generally create a Shape object, then call either the draw or fill method of the Graphics2D object, supplying the Shape object as an argument. For example: public void paintComponent(Graphics g) { super.paintComponent(g); Graphics2D g2d = (Graphics2D)g; // Assume x, y, and diameter are instance variables Ellipse2D.Double circle = new Ellipse2D.double(x, y, diameter, diameter); g2d.fill(circle); 44
  • 69. } You can still call the drawXxx methods if you like, however. This is necessary for drawString and drawImage, and possibly convenient for draw3DRect. Several classes have similar versions that store coordinates as either double precision numbers (Xxx.Double) or single precision numbers (Xxx.Float). The idea is that single precision coordinates might be slightly faster to manipulate on some platforms. Shape Classes Arguments to the Graphics2D draw and fill methods must implement the Shape interface. You can create your own shapes, of course, but following are the major built-in ones. Except for Rectangle and Polygon, which are Java 1.1 holdovers, these appear in the java.awt.geom package. Arc2D.Double, Arc2D.Float Area (a shape built by adding/subtracting other shapes) CubicCurve2D.Double, CubicCurve2D.Float Ellipse2D.Double, Ellipse2D.Float GeneralPath (a series of connected shapes) Line2D.Double, Line2D.Float Polygon QuadCurve2D.Double, QuadCurve2D.Float Rectangle2D.Double, Rectangle2D.Float, Rectangle RoundRectangle2D.Double, RoundRectangle2D.Float Drawing Shapes: Example Code ShapeExample.java import javax.swing.*; // For JPanel, etc. import java.awt.*; // For Graphics, etc. import java.awt.geom.*; // For Ellipse2D, etc. 45
  • 70. /** An example of drawing/filling shapes with Java2D in Java 1.2. public class ShapeExample extends JPanel { private Ellipse2D.Double circle = new Ellipse2D.Double(10, 10, 350, 350); private Rectangle2D.Double square = new Rectangle2D.Double(10, 10, 350, 350); public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; g2d.fill(circle); g2d.draw(square); } // super.paintComponent clears offscreen pixmap, // since we're using double buffering by default. protected void clear(Graphics g) { super.paintComponent(g); } protected Ellipse2D.Double getCircle() { return(circle); 46
  • 71. public static void main(String[] args) { WindowUtilities.openInJFrame(new ShapeExample(), 380, 400); } } WindowUtilities.java import javax.swing.*; import java.awt.*; /** A few utilities that simplify testing of windows in Swing. public class WindowUtilities { public static void setNativeLookAndFeel() { try { UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); } catch(Exception e) { System.out.println("Error setting native LAF: " + e); } } /** A simplified way to see a JPanel or other Container. * Pops up a JFrame with specified Container as the content pane. */ 47
  • 72. public static JFrame openInJFrame(Container content, int width, int height, String title, Color bgColor) { JFrame frame = new JFrame(title); frame.setBackground(bgColor); content.setBackground(bgColor); frame.setSize(width, height); frame.setContentPane(content); frame.addWindowListener(new ExitListener()); frame.setVisible(true); return(frame); } /** Uses Color.white as the background color. */ public static JFrame openInJFrame(Container content, int width, int height, String title) { return(openInJFrame(content, width, height, title, Color.white)); } 48
  • 73. /** Uses Color.white as the background color, and the name of the Container's class as the JFrame title. public static JFrame openInJFrame(Container content, int width, int height) { return(openInJFrame(content, width, height, content.getClass().getName(), Color.white)); } } ExitListener.java import java.awt.*; import java.awt.event.*; public class ExitListener extends WindowAdapter { public void windowClosing(WindowEvent event) { System.exit(0); } } 49
  • 75. 7.3 PAINT STYLES IN JAVA 2D PAINT STYLES OVERVIEW When you fill a Shape, the current Paint attribute of the Graphics2D object is used. This can be a Color (solid color), a GradientPaint (gradient fill gradually combining two colors), a TexturePaint (tiled image), or a new version of Paint that you write yourself. Use setPaint and getPaint to change and retrieve the Paint settings. Note that setPaint and getPaint supersede the setColor and getColor methods that were used in Graphics. Paint Classes Arguments to the Graphics2D setPaint method (and return values of getPaint) must implement the Paint interface. Here are the major built-in Paint classes: Color Has the same constants (Color.red, Color.yellow, etc.) as the AWT version, plus some extra constructors. GradientPaint Constructors takes two points, two colors, and optionally a boolean flag that indicates that the color pattern should cycle. The first color is used at the first point, the second color at the second point, and points in between are colored based on how close they are to each of the points. TexturePaint Constructor takes a BufferedImage and a Rectangle2D, maps the image to the rectangle, then tiles the rectangle. Creating a BufferedImage from a GIF or JPEG file is a pain. First load an Image normally, get its size, create a BufferedImage that size with BufferedImage.TYPE_INT_ARGB as the image type, get the BufferedImage's Graphics object via createGraphics, then draw the Image into the BufferedImage using drawImage. An example of this process is shown later. Transparency Transparency is not set in the Paint object, rather separately via an AlphaComposite object that is applied via setComposite. 51
  • 76. GRADIENT FILLS: EXAMPLE CODE import java.awt.*; /** An example of gradient fills with Java2D in Java 1.2. public class GradientPaintExample extends ShapeExample { // Red at (0,0), yellow at (175,175), changes gradually between. private GradientPaint gradient = new GradientPaint(0, 0, Color.red, 175, 175, Color.yellow, true); // true means to repeat pattern public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; drawGradientCircle(g2d); } protected void drawGradientCircle(Graphics2D g2d) { g2d.setPaint(gradient); g2d.fill(getCircle()); g2d.setPaint(Color.black); g2d.draw(getCircle()); } 52
  • 77. public static void main(String[] args) { WindowUtilities.openInJFrame(new GradientPaintExample(), 380, 400); } } Gradient Fills: Example Output TILED IMAGES AS FILL PATTERNS -- OVERVIEW To use tiled images, you create a TexturePaint object and specify its use via the setPaint method of Graphics2D, just as with solid colors and gradient fills. The TexturePaint constructor takes a BufferedImage and a Rectangle2D as arguments. The BufferedImage specifies what to draw, and the Rectangle2D specifies where the tiling starts. Creating a BufferedImage to hold custom drawing is relatively straightforward: call the BufferedImage constructor with a width, a height, and a type of BufferedImage.TYPE_INT_RGB, then call createGraphics on that to get a Graphics2D with which to draw. It is a bit harder to create one from an image file. 53
  • 78. First load an Image from an image file, then use MediaTracker to be sure it is done loading, then create an empty BufferedImage using the Image width and height, then get the Graphics2D via createGraphics, then draw the Image onto the BufferedImage. This process has been wrapped up in the getBufferedImage method of my ImageUtilities class. Tiled Images as Fill Patterns: Example Code TiledImages.java import javax.swing.*; import java.awt.*; import java.awt.geom.*; import java.awt.image.*; /** An example of using TexturePaint to fill objects with tiled images. Uses the getBufferedImage method of ImageUtilities to load an Image from a file and turn that into a BufferedImage. public class TiledImages extends JPanel { private String dir = System.getProperty("user.dir"); private String imageFile1 = dir + "/images/marty.jpg"; private TexturePaint imagePaint1; private Rectangle imageRect; private String imageFile2 = dir + "/images/bluedrop.gif"; private TexturePaint imagePaint2; private int[] xPoints = { 30, 700, 400 }; private int[] yPoints = { 30, 30, 600 }; private Polygon imageTriangle = new Polygon(xPoints, yPoints, 3); 54
  • 79. public TiledImages() { BufferedImage image = ImageUtilities.getBufferedImage(imageFile1, this); imageRect = new Rectangle(235, 70, image.getWidth(), image.getHeight()); imagePaint1 = new TexturePaint(image, imageRect); image = ImageUtilities.getBufferedImage(imageFile2, this); imagePaint2 = new TexturePaint(image, new Rectangle(0, 0, 32, 32)); } public void paintComponent(Graphics g) { super.paintComponent(g); Graphics2D g2d = (Graphics2D)g; g2d.setPaint(imagePaint2); g2d.fill(imageTriangle); g2d.setPaint(Color.blue); g2d.setStroke(new BasicStroke(5)); g2d.draw(imageTriangle); g2d.setPaint(imagePaint1); g2d.fill(imageRect); g2d.setPaint(Color.black); g2d.draw(imageRect); } 55
  • 80. public static void main(String[] args) { WindowUtilities.openInJFrame(new TiledImages(), 750, 650); } } ImageUtilities.java import java.awt.*; import java.awt.image.*; /** A class that simplifies a few common image operations, in particular creating a BufferedImage from an image file, and using MediaTracker to wait until an image or several images are done loading. public class ImageUtilities { /** Create Image from a file, then turn that into a BufferedImage. public static BufferedImage getBufferedImage(String imageFile, Component c) { Image image = c.getToolkit().getImage(imageFile); waitForImage(image, c); BufferedImage bufferedImage = new BufferedImage(image.getWidth(c), image.getHeight(c), BufferedImage.TYPE_INT_RGB); Graphics2D g2d = bufferedImage.createGraphics(); g2d.drawImage(image, 0, 0, c); return(bufferedImage); } 56
  • 81. /** Take an Image associated with a file, and wait until it is done loading. Just a simple application of MediaTracker. If you are loading multiple images, don't use thisconsecutive times; instead use the version that takes an array of images. public static boolean waitForImage(Image image, Component c) { MediaTracker tracker = new MediaTracker(c); tracker.addImage(image, 0); try { tracker.waitForAll(); } catch(InterruptedException ie) {} return(!tracker.isErrorAny()); } /** Take some Images associated with files, and wait until they are done loading. Just a simple application of MediaTracker. public static boolean waitForImages(Image[] images, Component c) { MediaTracker tracker = new MediaTracker(c); for(int i=0; i<images.length; i++) tracker.addImage(images[i], 0); try { tracker.waitForAll(); } catch(InterruptedException ie) {} return(!tracker.isErrorAny()); } } 57
  • 82. 7.4 TRANSPARENCY IN JAVA 2D OVERVIEW Java2D permits you to assign transparency (alpha) values to drawing operations so that the underlying graphics partially shows through when you draw shapes or images. You set transparency by creating an AlphaComposite object then passing it to the setComposite method of the Graphics2D object. You create an AlphaComposite by calling AlphaComposite.getInstance with a mixing rule designator and a transparency (or "alpha") value. There are 8 built-in mixing rules (see the AlphaComposite API for details), but the one normally used for drawing with transparency settings is AlphaComposite.SRC_OVER. Alpha values range from 0.0F (completely transparent) to 1.0F (completely opaque). Transparency: Example Code import javax.swing.*; import java.awt.*; import java.awt.geom.*; /** An illustration of the use of AlphaComposite to make partially transparent drawings. public class TransparencyExample extends JPanel { private static int gap=10, width=60, offset=20, deltaX=gap+width+offset; private Rectangle blueSquare = new Rectangle(gap+offset, gap+offset, width, width), redSquare = new Rectangle(gap, gap, width, width); private AlphaComposite makeComposite(float alpha) { int type = AlphaComposite.SRC_OVER; return(AlphaComposite.getInstance(type, alpha)); 58
  • 83. } private void drawSquares(Graphics2D g2d, float alpha) { Composite originalComposite = g2d.getComposite(); g2d.setPaint(Color.blue); g2d.fill(blueSquare); g2d.setComposite(makeComposite(alpha)); g2d.setPaint(Color.red); g2d.fill(redSquare); g2d.setComposite(originalComposite); } public void paintComponent(Graphics g) { super.paintComponent(g); Graphics2D g2d = (Graphics2D)g; for(int i=0; i<11; i++) { drawSquares(g2d, i*0.1F); g2d.translate(deltaX, 0); } } public static void main(String[] args) { String title = "Transparency example: alpha of the top (red) " + "square ranges from 0.0 at the left to 1.0 at " + "the right. Bottom (blue) square is opaque."; WindowUtilities.openInJFrame(new TransparencyExample(), 11*deltaX + 2*gap, deltaX + 3*gap, 59
  • 84. title, Color.lightGray); } } Transparency: Example Output Using Local Fonts in Java2D Local Fonts: Overview You can use the same logical font names as in Java 1.1, namely Serif (e.g. Times), SansSerif (e.g. Helvetica or Arial), Monospaced (e.g. Courier), Dialog, and DialogInput. You can also use arbitrary local fonts if you first look up the entire list, which may take a few seconds. Lookup the fonts via the getAvailableFontFamilyNames or getAllFonts methods of GraphicsEnvironment. E.g.: GraphicsEnvironment env = GrapicsEnvironment.getLocalGraphicsEnvironment(); Then env.getAvailableFontFamilyNames(); or env.getAllFonts(); // Much slower! The best approach would be to loop down getAvailableFontFamilyNames, checking for your name, having several backup names to use if the first choice is not available. If you pass an unavailable family name to the Font constructor, a default font (SansSerif) will be used. 60
  • 85. EXAMPLE 1 -- PRINTING OUT ALL LOCAL FONT NAMES import java.awt.*; /** Lists the names of all available fonts with Java2D in Java 1.2. public class ListFonts { public static void main(String[] args) { GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment(); String[] fontNames = env.getAvailableFontFamilyNames(); System.out.println("Available Fonts:"); for(int i=0; i<fontNames.length; i++) System.out.println(" " + fontNames[i]); } } /** AN EXAMPLE OF USING LOCAL FONTS WITH JAVA2D IN JAVA public class FontExample extends GradientPaintExample { public FontExample() { GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment(); env.getAvailableFontFamilyNames(); setFont(new Font("Goudy Handtooled BT", Font.PLAIN, 100)); } protected void drawBigString(Graphics2D g2d) 61
  • 86. { g2d.setPaint(Color.black); g2d.drawString("Java 2D", 25, 215); } public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; drawGradientCircle(g2d); drawBigString(g2d); } public static void main(String[] args) { WindowUtilities.openInJFrame(new FontExample(), 380, 400); } Drawing with Local Fonts: Example Output 62
  • 87. 7.5 STROKE STYLES IN JAVA2D OVERVIEW In the AWT, the drawXxx methods of Graphics resulted in solid, 1-pixel wide lines. Furthermore, drawing commands that consisted of multiple line segments (e.g. drawRect and drawPolygon) had a predefined way of joining the line segments together and terminating segments that do not join to others. Java2D gives you much more flexibility. In addition to setting the pen color or pattern (via setPaint, as discussed in the previous section), Java2D permits you to set the pen thickness and dashing pattern, and to specify the way line segments end and are joined together. You do this by creating a BasicStroke object, then telling the Graphics2D object to use it via the setStroke method. Stroke Attributes Arguments to setStroke must implement the Stroke interface, and the BasicStroke class is the sole builtin class that implements Stroke. Here are the BasicStroke constructors: BasicStroke() Creates a BasicStroke with a pen width of 1.0, the default cap style of CAP_SQUARE, and the default join style of JOIN_MITER. See the following examples of pen widths and cap/join styles. BasicStroke(floatpenWidth) Uses the specified pen width and the default cap/join styles (CAP_SQUARE and JOIN_MITER). BasicStroke(float penWidth, int capStyle, int joinStyle) Uses the specified pen width, cap style, and join style. The cap style can be one of CAP_SQUARE (make a square cap that extends past the end point by half the pen width -- this is the default), CAP_BUTT (cut off segment exactly at end point -- use this one for dashed lines), or CAP_ROUND (make a circular cap centered on the end point, with a diameter of the pen width). The join style can be one of JOIN_MITER (extend outside edges of lines until they meet -- this is the default), JOIN_BEVEL (connect outside corners of outlines with straight line), or JOIN_ROUND (round off corner with circle with diameter equal to the pen width). BasicStroke(float penWidth, int capStyle, int joinStyle, float miterLimit) 63
  • 88. BasicStroke(float penWidth, int capStyle, int joinStyle, float miterLimit, float[] dashPattern, float dashOffset) Lets you make dashed lines by specifying an array of opaque (entries at even array indices) and transparent (odd indices) segments. The offset, which is often 0.0, specifies where to start in the dashing pattern. Stroke Thickness: Example Code import java.awt.*; /** An example of Stroke (pen) widths with Java2D in Java 1.2. public class StrokeThicknessExample extends FontExample { public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; drawGradientCircle(g2d); drawBigString(g2d); drawThickCircleOutline(g2d); } protected void drawThickCircleOutline(Graphics2D g2d) { g2d.setPaint(Color.blue); g2d.setStroke(new BasicStroke(8)); // 8-pixel wide pen g2d.draw(getCircle()); } public static void main(String[] args) { WindowUtilities.openInJFrame(new StrokeThicknessExample(), 64
  • 89. 380, 400); } } DASHED LINE EXAMPLE CODE: import java.awt.*; public class DashedStrokeExample extends FontExample { public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; drawGradientCircle(g2d); drawBigString(g2d); drawDashedCircleOutline(g2d); } protected void drawDashedCircleOutline(Graphics2D g2d) { g2d.setPaint(Color.blue); // 30 pixel line, 10 pixel gap, 10 pixel line, 10 pixel gap float[] dashPattern = { 30, 10, 10, 10 }; g2d.setStroke(new BasicStroke(8, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 10, dashPattern, 0)); g2d.draw(getCircle()); } 65
  • 90. public static void main(String[] args) { WindowUtilities.openInJFrame(new DashedStrokeExample(), 380, 400); } } DASHED LINES: EXAMPLE OUTPUT LINE CAP AND JOIN STYLES: EXAMPLE CODE import javax.swing.*; import java.awt.*; import java.awt.geom.*; 66
  • 91. public class LineStyles extends JPanel { private GeneralPath path; private static int x = 30, deltaX = 150, y = 300, deltaY = 250, thickness = 40; private Circle p1Large, p1Small, p2Large, p2Small, p3Large, p3Small; private int compositeType = AlphaComposite.SRC_OVER; private AlphaComposite transparentComposite = AlphaComposite.getInstance(compositeType, 0.4F); private int[] caps = { BasicStroke.CAP_SQUARE, BasicStroke.CAP_BUTT, BasicStroke.CAP_ROUND }; private String[] capNames = { "CAP_SQUARE", "CAP_BUTT", "CAP_ROUND" }; private int[] joins = { BasicStroke.JOIN_MITER, BasicStroke.JOIN_BEVEL, BasicStroke.JOIN_ROUND }; private String[] joinNames = { "JOIN_MITER", "JOIN_BEVEL", "JOIN_ROUND" }; public LineStyles() { path = new GeneralPath(); path.moveTo(x, y); p1Large = new Circle(x, y, thickness/2); p1Small = new Circle(x, y, 2); path.lineTo(x + deltaX, y - deltaY); 67
  • 92. p2Large = new Circle(x + deltaX, y - deltaY, thickness/2); p2Small = new Circle(x + deltaX, y - deltaY, 2); path.lineTo(x + 2*deltaX, y); p3Large = new Circle(x + 2*deltaX, y, thickness/2); p3Small = new Circle(x + 2*deltaX, y, 2); setForeground(Color.blue); setFont(new Font("SansSerif", Font.BOLD, 20)); } public void paintComponent(Graphics g) { super.paintComponent(g); Graphics2D g2d = (Graphics2D)g; g2d.setColor(Color.blue); for(int i=0; i>caps.length; i++) { BasicStroke stroke = new BasicStroke(thickness, caps[i], joins[i]); g2d.setStroke(stroke); g2d.draw(path); labelEndPoints(g2d, capNames[i], joinNames[i]); g2d.translate(3*x + 2*deltaX, 0); } } 68
  • 93. // Draw translcent circles to illustrate actual endpoints. // Include text labels to shold cap/join style. private void labelEndPoints(Graphics2D g2d, String capLabel, String joinLabel) { Paint origPaint = g2d.getPaint(); Composite origComposite = g2d.getComposite(); g2d.setPaint(Color.red); g2d.setComposite(transparentComposite); g2d.fill(p1Large); g2d.fill(p2Large); g2d.fill(p3Large); g2d.setPaint(Color.yellow); g2d.setComposite(origComposite); g2d.fill(p1Small); g2d.fill(p2Small); g2d.fill(p3Small); g2d.setPaint(Color.black); g2d.drawString(capLabel, x + thickness - 5, y + 5); g2d.drawString(joinLabel, x + deltaX + thickness - 5, y - deltaY); g2d.setPaint(origPaint); } public static void main(String[] args) { WindowUtilities.openInJFrame(new LineStyles(), 9*x + 6*deltaX, y + 60); 69
  • 94. } } class Circle extends Ellipse2D.Double { public Circle(double centerX, double centerY, double radius) { super(centerX - radius, centerY - radius, 2.0*radius, 2.0*radius); } } Line Cap and Join Styles: Example Output 7.6 COORDINATE TRANSFORMATIONS OVERVIEW Java2D allows you to easily translate, rotate, scale, or shear the coordinate system. This is very convenient: it is often much easier to move the coordinate system than to calculate new coordinates for each of your points. Besides, for some data structures like ellipses and strings there is no other way to get rotated or stretched versions. The meanings of translate, rotate, and scale are clear: to move, to spin, or to stretch/shrink evenly in the x and/or y direction. Shear means to stretch unevenly: an x shear moves points to the right based on how far they are from the y axis; a y shear moves points down based on how far they are from the x axis. 70
  • 95. The easiest way to picture what is happening is to imagine that the person doing the drawing has a picture frame that he lays down on top of a sheet of paper. The drawer always sits at the bottom of the frame. To apply a translation, you move the frame (moving the drawer with it), and do the drawing in the new location. You then move the frame back to its original location, and what you now see is the final result. Similarly, for a rotation, you spin the frame (and the drawer), draw, then spin back to see the result. Similarly for scaling and shears; modify the frame without touching the underlying sheet of paper, draw, then reverse the process to see the final result. An outside observer watching this process would see the frame move in the direction specified by the transformation, but see the sheet of paper stay fixed. This is illustrated in the second column in the diagram below. The dotted rectangle represents the frame, while the gray rectangle represents the sheet of paper. On the other hand, to the person doing the drawing it would appear that the sheet of paper moved in the opposite way from that specified in the transformation, but that he didn't move at all. This is illustrated in the third column in the following diagram. The first column illustrates the starting configuration, and the fourth illustrates the final result. Visualizing Transformations You can also perform more complex transformations (e.g. creating a mirror image by flipping around a line) by directly manipulating the underlying arrays that control the transformations. This is a bit more complicated to envision than the basic translatation, rotation, scaling, and shear transformations. The idea is that a new point (x2,y2) can be derived from an original point (x1,y1) as follows: 71
  • 96. [ x2] [ m00 m01 m02 ] [ x1 ] [ m00x1 + m01y1 + m02 ] [ y2] = [ m10 m11 m12 ] [ y1 ] = [ m10x1 + m11y1 + m12 ] [ 1 ] [ 0 0 1 ] [ 1 ] [ 1 ] Note that you can only supply six of the nine values in the transformation array (the mxx values). The bottom row is fixed at [ 0 0 1 ] to guarantee that the transformations preserve "straightness" and "parallelness" of lines. There are two basic ways to use transformations. You can create an AffineTransform object, set its parameters, and then assign that AffineTransform to the Graphics2D object via setTransform. This is your only choice if you want to do the more complex transformations permitted by setting explicit transformation matrices. Alternatively, for the basic transformations you can call translate, rotate, scale, and shear directly on the Graphics2D object. COORDINATE TRANSLATIONS AND ROTATIONS: EXAMPLE CODE import java.awt.*; /** An example of coordinate translations and rotations with Java2D in Java 1.2. public class RotationExample extends StrokeThicknessExample { private Color[] colors = { Color.white, Color.black }; public void paintComponent(Graphics g) { clear(g); Graphics2D g2d = (Graphics2D)g; drawGradientCircle(g2d); drawThickCircleOutline(g2d); // Move the origin to the center of the circle. g2d.translate(185.0, 185.0); for (int i=0; i<16; i++) { // Rotate the coordinate system around current 72
  • 97. // origin, which is at the center of the circle. g2d.rotate(Math.PI/8.0); g2d.setPaint(colors[i%2]); g2d.drawString("Java", 0, 0); } } public static void main(String[] args) { WindowUtilities.openInJFrame(new RotationExample(), 380, 400); } } Coordinate Translations and Rotations: Example Output 73
  • 98. SHEAR TRANSFORMATIONS If you specify a non-zero x shear, then x values will be more and more shifted to the right the farther they are away from the y axis. For example, an x shear of 0.1 means that the x value will be shifted 10% of the distance the point is away from the y axis. Y shears are similar: points are shifted down in proportion to the distance they are away from the x axis. SHEAR TRANSFORMATIONS: EXAMPLE CODE import javax.swing.*; import java.awt.*; import java.awt.geom.*; /** An example of shear transformations with Java2D in Java 1.2. public class ShearExample extends JPanel { private static int gap=10, width=100; private Rectangle rect = new Rectangle(gap, gap, 100, 100); public void paintComponent(Graphics g) { super.paintComponent(g); Graphics2D g2d = (Graphics2D)g; for (int i=0; i<5; i++) { g2d.setPaint(Color.red); g2d.fill(rect); // Each new square gets 0.2 more x shear g2d.shear(0.2, 0.0); g2d.translate(2*gap + width, 0); 74
  • 99. } public static void main(String[] args) { String title = "Shear: x shear ranges from 0.0 for the leftmost 'square' " + "to 0.8 for the rightmost one."; WindowUtilities.openInJFrame(new ShearExample(), 20*gap + 5*width, 5*gap + width, title); }} 75
  • 101. CONCLUSION This project is designed to meet the requirements of window based Game tron. It has been developed in J2SE (Version 6.0) keeping in mind the specifications of the game. Overall the project teaches us the essential skills like: 1. The use of Applets and Frames, where the designing can be done. And the GUI can be developed using the Java and Net beans. 2. The project also teaches the use of graphics 2D.
  • 102. BIBLIOGRAPHY Books Referred:- JAVA The complete reference part 2 JAVA Projects Tony Martin, Dominic Sally Related Websites:- www.wikipedia.org www.simba.com