UserInterface vs Main Threads Instructor Prasun Dewan Prerequisite Animation Threads Commands Animations from Main public static void mainString args PlottedShuttle ID: 386822
Download Presentation The PPT/PDF document "Comp 401" is the property of its rightful owner. Permission is granted to download and print the materials on this web site for personal, non-commercial use only, and to display it on your personal computer provided you do not modify the materials and that you retain all copyright notices contained in the materials. By downloading content from our website, you accept the terms of this agreement.
Slide1
Comp 401User-Interface vs. Main Threads
Instructor: Prasun DewanSlide2
Prerequisite
Animation Threads CommandsSlide3
Animations from Main
public
static
void
main(String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel(); oeFrame.setSize (450, 450); ShuttleAnimator shuttleAnimator = new AShuttleAnimator(); shuttleAnimator.animateFromOrigin(aShuttle, 5, 100);}
No thread as single animationSlide4
Animations from Main
public
static
void
main(String[] args) { PlottedShuttle shuttle1 = new AnObservablePlottedShuttle(50, 100); OEFrame oeFrame1 = ObjectEditor.edit(shuttle1); oeFrame1.hideMainPanel(); oeFrame1.setLocation(0, 0); oeFrame1.setSize(400, 400); PlottedShuttle shuttle2 = new AnObservablePlottedShuttle(100, 50); OEFrame oeFrame2 = ObjectEditor.edit(shuttle2); oeFrame2.hideMainPanel(); oeFrame2.setLocation(400
, 0); oeFrame2.setSize(400, 400); ShuttleAnimator
shuttleAnimator1 =
new AShuttleAnimator(); ShuttleAnimator shuttleAnimator2 = new AShuttleAnimator(); concurrentDemoShuttleAnimation(shuttleAnimator1, shuttle1); concurrentDemoShuttleAnimation(shuttleAnimator2, shuttle2);}
Threads created, as multiple independent animations wantedSlide5
Single Animation From Main: No Special Thread
APlotted
Shuttle
AShuttleAnimator
main
animate Shuttle()
setShuttleX(Y)()Main ClassJPanelrepaint()
paint()
Main ThreadSlide6
Consider Single Animation
public
static
void
main(String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel(); oeFrame.setSize (450, 450); ShuttleAnimator shuttleAnimator = new AShuttleAnimator(); shuttleAnimator.animateFromOrigin(aShuttle, 5, 100);}
Start animation from the user interface?
Extension of
ShuttleAnimator
that allows parameters to be propertiesWe can edit these properties interactively and start animation with them as parametersSlide7
GUISlide8
Main vs. Interactive Animation
public
static
void
main(String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel(); oeFrame.setSize (450, 450); ShuttleAnimator shuttleAnimator = new AShuttleAnimator(); shuttleAnimator.animateFromOrigin(aShuttle, 5, 100);}
public static
void
main (String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel();
oeFrame.setSize (450, 450); FancyShuttleAnimator
shuttleAnimator
=
new
AFancyShuttleAnimator
();
ObjectEditor.edit
(
shuttleAnimator
);
}Slide9
Fancy Animator
public
class
AFancyShuttleAnimator
extends AShuttleAnimator implements FancyShuttleAnimator { int animationStep = 5; int animationPauseTime = 100; PlottedShuttle shuttle; public AFancyShuttleAnimator(PlottedShuttle theShuttle) { shuttle = theShuttle; } public
int getAnimationStep() { return
animationStep
; } public void setAnimationStep(int animationStep) { this.animationStep = animationStep; }
public int getAnimationPauseTime
() {
return
animationPauseTime
;
}
public
void
setAnimationPauseTime
(
int
animationPauseTime
) {
this
.
animationPauseTime
=
animationPauseTime
;
}
public
void
animateShuttle
() {
animateFromOrigin
(
shuttle, animationStep, animationPauseTime); }}Slide10
VideoSlide11
When does Main Terminate?
public
static
void
main(String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel(); oeFrame.setSize (450, 450); ShuttleAnimator shuttleAnimator = new AShuttleAnimator(); shuttleAnimator.animateFromOrigin(aShuttle, 5, 100);}
public static
void
main (String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel();
oeFrame.setSize (450, 450); FancyShuttleAnimator
shuttleAnimator
=
new
AFancyShuttleAnimator
();
ObjectEditor.edit
(
shuttleAnimator
);
}
Main thread executes loop
Main thread starts UI
UI Thread (created by Java) executes loop
Main thread terminates
Main thread terminatesSlide12
Consider Single Animation
UI Thread (created by Java) executes loop
Main thread executes loop
Main thread starts UI and terminatesSlide13
Interactive Animation: No special Thread
APlotted
Shuttle
AFancy
ShuttleAnimator
mainsetShuttleX(Y)()Main ClassJPanelrepaint()
paint()
Main Thread
JFrame
setVisible
()
AWT Thread
setVisible
()
JFrame
animate
FromOrigin
()
animate Shuttle()Slide14
Single Animation From Main: No Special Thread
APlotted
Shuttle
AShuttleAnimator
main
setShuttleX
(Y)()Main ClassJPanelrepaint()paint()
Main Thread
setVisible
()
JFrame
AWT Thread
animate
FromOrigin
()
animate Shuttle()Slide15
Interleaving With UI Thread
w
hile
(
true
) {
//wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }Slide16
Loop Executes
while
(
curY
<
originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } while (true) {
//wait for and process paint, // menu and other events
waitForAndProcessNextQueuedUIEvent
();
}Slide17
Looping Thread Updates Shuttle and Enqueues Repaint Event
while
(
curY
<
originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } //in Java component showing //the shuttlepublic void repaint() { enqueueRepaintEvent(this );}
w
hile
(true) { //wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }Slide18
Loop Re-Executes
while
(
curY
<
originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } while (true) {
//wait for and process paint, // menu and other events
waitForAndProcessNextQueuedUIEvent
();
}Slide19
Looping Thread Updates Shuttle and Enqueues Another Repaint Event
w
hile
(
true
) {
//wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
//in Java
compoent
showing
//the shuttlepublic void repaint() { enqueueRepaintEvent(this );} Slide20
Loop Finishes
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }Slide21
UI Thread Processes Enqueued Paints
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }public void paint(Graphics g) { //draw shuttle } Slide22
UI Thread Waits for Next Event
w
hile
(
true
) {
//wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }Slide23
Concurrent Fancy Animator
public
class
AConcurrentShuttleAnimator
extends AFancyShuttleAnimator { public AConcurrentShuttleAnimator(PlottedShuttle theShuttle) { super(theShuttle); } public void animateShuttle() { Thread thread = new Thread( (new AShuttleAnimationCommand( this, shuttle, animationStep,
animationPauseTime)));
thread.start
();
}Slide24
Starting Concurrent Fancy Animator
public
static
void
main (String[] args) { PlottedShuttle shuttle = new APlottedShuttle(50, 100); OEFrame oeFrame = ObjectEditor.edit(shuttle); oeFrame.hideMainPanel(); oeFrame.setSize (450, 450); FancyShuttleAnimator shuttleAnimator = new AConcurrentShuttleAnimator(); ObjectEditor.edit(shuttleAnimator);}Slide25
Interactive Animation: Special Thread
APlotted
Shuttle
AConcurrentFancy
ShuttleAnimator
mainsetShuttleX(Y)()Main ClassJPanelrepaint()paint()
Main Thread
JFrame
setVisible
()
AWT Thread
setVisible
()
JFrame
Shuttle Animation Thread
AShuttleAnimation
Command
r
un()
animate
FromOrigin
()
animate Shuttle()Slide26
UI Event Loop
w
hile
(
true
) {
//wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }AWT ThreadEvent LoopMouse ClickSlide27
UI Event Loop and Animations
w
hile
(
true
) {
//wait for and process paint, // menu and other events waitForAndProcessNextQueuedUIEvent(); }AWT Threadwhile (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY
+= animationStep; shuttle.setShuttleY(
curY
);
} Listener CodeEvent LoopMouse ClickMouse Click
Repaint
Repaint
New UI event not processed until listeners for previous event finish
Animating listener should create new thread for animation codeSlide28
Interactive Animation: Special Thread
APlotted
Shuttle
AConcurrentFancy
ShuttleAnimator
mainsetShuttleX(Y)()Main ClassJPanelrepaint()paint()
Main Thread
JFrame
setVisible
()
AWT Thread
setVisible
()
JFrame
Shuttle Animation Thread
AShuttleAnimation
Command
r
un()
animate
FromOrigin
()
animate Shuttle()Slide29
Video
The animation method is synchronizedSlide30
GUI Processing
Even if main thread terminates, the application continues to run as long as a GUI has been created, which creates the GUI thread.A single GUI thread is created for processing the controller (menu/button/… processing)
and
view (repaint)
actions of all models
.
View updates cannot occur until controller returns.Controller action should result in a new thread if it starts an animation .If a single animation is started from main then no thread needs to be created a main thread executes loop and separate GUI thread updates view. Slide31
Extra SlidesSlide32
New Looping Thread Created
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } Slide33
Wait for Next Event Without Blocking
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } Slide34
Looping Thread Becomes Current
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } Slide35
Looping Thread Updates Shuttle and Enqueues Repaint Event
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
//in Java panel showing
//the shuttle
public void
repaint() { enqueueRepaintEvent(this );} Slide36
New Thread Executes Sleep
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } Slide37
UI Thread Becomes Current and Executes Paint
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
public void
paint(Graphics g) {
//draw shuttle } Slide38
Animation Thread Becomes Current
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); } Slide39
Looping Thread Updates Shuttle and Enqueues Repaint Event
w
hile
(
true
) {
//wait for and process paint, // menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep( animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
//in Java panel showing
//the shuttle
public void
repaint() { enqueueRepaintEvent(this );} Slide40
Interactive Animation: No special Thread
APlotted
Shuttle
AFancy
ShuttleAnimator
mainsetShuttleX(Y)()Main ClassJPanelrepaint()
paint()
Main Thread
JFrame
setVisible
()
AWT Thread
setVisible
()
JFrame
animate
FromOrigin
()
animate Shuttle()Slide41
Single Animation From Main: No Special Thread
APlotted
Shuttle
AShuttleAnimator
main
setShuttleX
(Y)()Main ClassJPanelrepaint()paint()
Main Thread
setVisible
()
JFrame
AWT Thread
animate
FromOrigin
()
animate Shuttle()Slide42
Interactive Animation: No special Thread
APlotted
Shuttle
AFancy
ShuttleAnimator
mainanimate Shuttle()setShuttleX(Y)()Main ClassJPanel
repaint()paint()
Main Thread
JFrame
setVisible
()
AWT Thread
setVisible
()
JFrame
animate Shuttle()
Shuttle Animation Thread
AShuttleAnimation
Command
r
un()Slide43
Synchronization
Methods that access global state and can be executed by multiple threads should be made synchronizedThe synchronized keyword should also be used in declaration of all methods that access variables changed by the animation method.Slide44
Animation StepsAnimation consists of one or more animation steps
An animation step updates one or more animating graphical properties such as size, location, and icon of one or more graphical objects and then pauses executionSlide45
Pausing Execution
Execution can be paused using busy waiting or a sleep call provided by the operating systemBusy waiting has the problem that it is platform-specific and does not allow other activity to proceed while the animation is paused
Therefore using the sleep call is preferableSlide46
Incremental Updates
After each animation step, all displays of the animation must be updated The refresh operation can be used to do ensure these updates are
made.
Or The observable-observer concept can be used to ensure these updates are made
for each graphical property changed by the animation, the class of the property should allow observers to be registered and the setter of the property informs the observers about the update
ObjectEditor
requires the JavaBeans observer-observer approach based around the PropertyChangeListener interfaceSlide47
Threads
If we want multiple animations then we must create our own threadsThreads use command objects.Command objects represent method callsSlide48
UI Processing
w
hile
(
true
) {
//process paint, menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep(animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
//in Java panel showing the shuttle
public void
repaint() {
enqueueRepaintEvent(this );} UI Thread will not process queued paint event until called method returnsSlide49
Concurrent Animation
w
hile
(
true
) {
//process paint, menu and other events processNextQueuedUIEvent(); }while (curY < originalY) { ThreadSupport.sleep(animationPauseTime); curY += animationStep; shuttle.setShuttleY(curY); }
//in Java panel showing the shuttle
public void
repaint() {
enqueueRepaintEvent(this );} UI Thread will not process queued paint event until called method returnsSlide50
Architecture
ASynchronizedShuttleAnimator
AShuttleAnimation
Command
Main Thread
AShuttleAnimation
CommandShuttle Animation Thread 1Shuttle Animation Thread 2JFramer
un()
r
un()
mainanimate Shuttle()setVisible()
AWT Thread
setShuttleX
(Y)()
ASynchronizedShuttleAnimator
setVisible
()
animate Shuttle()
JPanel
repaint()
paint()
JFrame
APlotted
Shuttle
Main ClassSlide51
GUI