summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLeena Miettinen <riitta-leena.miettinen@qt.io>2016-05-11 17:37:26 +0200
committerAlex Blasche <alexander.blasche@theqtcompany.com>2016-05-17 09:19:18 +0000
commit14a54e65bfa23620074563821f030d78550b42ba (patch)
tree709b220bacfa0e9f3476c299516664fc092c3a3c
parent3394ef1186f7ee30860f87dc6878da05a010b9eb (diff)
Doc: Edit Pinball example docs
- Edit for grammar and style. - Add state chart images to improve readability. - Add subtitles to improve readability. Change-Id: I1429adf098e868388489f361caa5265b32c33a45 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io> Reviewed-by: Topi Reiniƶ <topi.reinio@theqtcompany.com>
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-global.pngbin0 -> 2925 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-guicontrol.pngbin0 -> 3618 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-internalstate.pngbin0 -> 2987 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-logicalstate.pngbin0 -> 7613 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-modestate.pngbin0 -> 3546 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-onstate.pngbin0 -> 7139 bytes
-rw-r--r--examples/scxml/pinball/doc/images/pinball-statechart-workflow.pngbin0 -> 4433 bytes
-rw-r--r--examples/scxml/pinball/doc/src/pinball.qdoc552
8 files changed, 256 insertions, 296 deletions
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-global.png b/examples/scxml/pinball/doc/images/pinball-statechart-global.png
new file mode 100644
index 0000000..630c678
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-global.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-guicontrol.png b/examples/scxml/pinball/doc/images/pinball-statechart-guicontrol.png
new file mode 100644
index 0000000..b79e343
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-guicontrol.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-internalstate.png b/examples/scxml/pinball/doc/images/pinball-statechart-internalstate.png
new file mode 100644
index 0000000..3bd9d1b
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-internalstate.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-logicalstate.png b/examples/scxml/pinball/doc/images/pinball-statechart-logicalstate.png
new file mode 100644
index 0000000..7a3395a
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-logicalstate.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-modestate.png b/examples/scxml/pinball/doc/images/pinball-statechart-modestate.png
new file mode 100644
index 0000000..e8b6df9
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-modestate.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-onstate.png b/examples/scxml/pinball/doc/images/pinball-statechart-onstate.png
new file mode 100644
index 0000000..db9459c
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-onstate.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/images/pinball-statechart-workflow.png b/examples/scxml/pinball/doc/images/pinball-statechart-workflow.png
new file mode 100644
index 0000000..dfcf3f2
--- /dev/null
+++ b/examples/scxml/pinball/doc/images/pinball-statechart-workflow.png
Binary files differ
diff --git a/examples/scxml/pinball/doc/src/pinball.qdoc b/examples/scxml/pinball/doc/src/pinball.qdoc
index 09210dc..b3566eb 100644
--- a/examples/scxml/pinball/doc/src/pinball.qdoc
+++ b/examples/scxml/pinball/doc/src/pinball.qdoc
@@ -27,190 +27,152 @@
/*!
\example pinball
- \title Qt SCXML: Pinball Example
+ \title Qt SCXML Pinball Example
\ingroup examples-qtscxml
- \brief Demonstrates how the internal
- logic of the application can be encapsulated in a scxml file.
+ \brief Encapsulates the internal logic of an application in an SCXML file.
- This example demonstrates a clear separation
- between chosen user interface, which may be easily replaced,
- and internal logic encapsulated in the scxml file,
- which may stay the same for different user interface.
+ \e {Pinball} demonstrates a clear separation between the user interface,
+ which may be easily replaced, and the internal logic encapsulated in an
+ SCXML file, which could also be used with another user interface.
+
+ \include examples-run.qdocinc
\section1 Pinball Features
\image pinball.png Screenshot of the Pinball example
- \e {Pinball Example} mimics a pinball game.
- The targets on the pinball table are substituted here by GUI controls,
- mainly by push buttons. Display elements, including current
- score, highscore and targets' lights are substituted by labels.
- Usually targets' lights state changes very often during game:
- they get turned on or off, they blink slowly, fast or
- with any intermediate speed indicating a game (or a certain target)
- entered some temporary state. The state of each target light
- is presented here as an enabled or a disabled label.
- There is no real ball here, but one can easily imagine that
- pressing a target's button can mimic hitting a real pinball
- target with a ball.
+ The Pinball example mimics a pinball game. The targets on the pinball table
+ are substituted by GUI controls, mainly by push buttons. Display elements,
+ including current score, highscore, and targets' lights, are substituted by
+ labels. Usually, the state of the targets' lights changes very often during
+ a game: the lights get turned on or off permanently or they blink at varying
+ speed indicating a game (or a certain target) entered a temporary state. The
+ state of each target light is presented as an enabled or a disabled label.
+ There is no real ball, but clicking a target's button represents hitting a
+ real pinball target with a ball.
Our pinball contains the following features:
\list
- \li Initially and when the game ends the pinball table
- goes into \c offState. In that state all lights on the table
- blink slowly (with 1s interval).
- \li After pressing the \uicontrol START button the pinball table
- goes into \c onState. All lights get turned off and the
+ \li Initially and when the game ends, the pinball table
+ enters \c offState. In that state, all lights on the table
+ blink slowly (at intervals of 1 second).
+ \li After clicking the \uicontrol START button, the pinball table
+ enters \c onState. All lights are turned off and the
pinball table is ready to be played.
- \li Whenever the table is in \c onState and the inattentive player
- presses the \uicontrol {BALL OUT} button, the game ends
- and enters into the \c offState. If the player's score is
+ \li When the table is in \c onState and the players
+ click the \uicontrol {BALL OUT} button, the game ends
+ and enters \c offState. If the players' score is
higher than the current highscore, the highscore is updated.
\li The goal is to collect the \uicontrol JACKPOT. In order to do that,
- the player must hit all five \uicontrol CRAZY letters twice.
- He has unlimited time for collecting it for the first time.
- However, after he has collected all the letters for the first time,
- he enters the \c hurryState and he must quickly collect
- all the letters again within 5s. If the time passed and
- the letters were not collected again, the player must
+ the players must hit all five \uicontrol CRAZY letters twice.
+ They have unlimited time for hitting them for the first time.
+ However, after they have collected all the letters for the first time,
+ they enter the \c hurryState and must collect
+ them again within 5 seconds. If the time has passed and
+ the letters were not collected again, the players must
start collecting the letters from scratch.
\li Scores:
\list
\li 1.000 per letter hit when not in \c hurryState.
\li 10.000 per letter hit when in \c hurryState.
\li 100.000 bonus for all 5 letters when not in \c hurryState.
- \li 1.000.000 bonus for all 5 letters when in \c hurryState (\uicontrol JACKPOT)
+ \li 1.000.000 bonus for all 5 letters when in \c hurryState
+ (\uicontrol JACKPOT).
\endlist
\li When not in \c hurryState, the letters already hit should blink
- with intermediate speed (500ms). Letters not hit yet should stay off.
+ at intermediate speed (500ms). Letters not hit yet should stay off.
\li When in \c hurryState, the letters already hit should
stay on. Letters not hit yet should blink fast (200ms).
- In addition the \uicontrol HURRY light should blink with the same speed.
- \li When jackpot gets collected the \uicontrol JACKPOT light should stay on.
+ In addition, the \uicontrol HURRY light should blink at the same speed.
+ \li When the jackpot gets collected, the \uicontrol JACKPOT light should
+ stay on.
\endlist
\section1 SCXML Part: Internal Logic Description
- The pinball.scxml file describes the internal logic implemented for
- pinball game.
+ The \e pinball.scxml file describes the internal logic implemented for the
+ pinball game. In this example, we have chosen the ECMAScript data model:
\quotefromfile pinball/pinball.scxml
\skipto scxml
- \printuntil guiControl
- \dots 12
- \skipto /^\ {8}<\//
- \printuntil internalState
- \dots 12
- \skipto /^\ {8}<\//
- \printuntil scxml
-
- In this example we've chosen ecmascript data model
- ("datamodel" attribute of \c <scxml> element).
- This data model enables declaring variables with
- initial values, which can be modified later.
- We declare two variables in our model: "highscore" and "score",
- with initial values of 0 (two \c <data> elements inside \c <datamodel> element).
- We also define a root parallel state "global",
- with two child states: \c guiControl and \c internalState,
- which are also parallel. Since the top \c global state is
- parallel, it means that whenever a \c global state is active
- all of its direct children are also active. In fact,
- the top level \c global is always active, meaning
- all of its children are always active, too.
- The \c global state in our example doesn't play any other role apart from
- collecting its two children and making them both active at a time.
+ \printuntil ecmascript
- \quotefromfile pinball/pinball.scxml
- \skipto guiControl
- \printuntil rLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil aLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil zLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil yLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil hurryLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil jackpotLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil gameOverLight
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil /^\ {8}<\//
-
- The \c guiControl part is responsible for maintaining the current
- state of every light control, which is visible on the pinball table.
- We have eight different lights, five for letters: C, R, A, Z and Y,
- and three for whole texts: \uicontrol HURRY!, \uicontrol JACKPOT
- and \uicontrol {GAME OVER}. Every light
- corresponds to its state, e.g. for light of letter \uicontrol C we have
- a \c cLight state and so on. Every light state has two child states
- indicating whether the light is on or off, e.g. \c cLight state
- contains \c cLightOn and \c cLightOff states. The content
- for other light states, which is omitted here, is analogous.
- As mentioned before, \c guiControl state is always active, and since
+ The ECMAScript data model enables declaring variables with initial values
+ that can be modified later. We declare the \c "highscore" and \c "score"
+ variables with the initial values of 0:
+
+ \printuntil </datamodel>
+
+ We define a root parallel state \c "global", with two child states,
+ \c guiControl and \c internalState, which are also parallel. Because the top
+ \c global state is parallel, all of its direct children are active when it
+ is active. In this example, the role of \c global is to collect the child
+ states and make them both active at a time.
+
+ \image pinball-statechart-global.png
+
+ \section2 Maintaining Light State
+
+ The \c guiControl element is responsible for maintaining the current
+ state of each light control that is visible on the pinball table.
+ Each light has a corresponding state.
+
+ \image pinball-statechart-guicontrol.png
+
+ For example, the light of the letter
+ \uicontrol C corresponds to the \c cLight state. Each light state has two
+ child states indicating whether the light is on or off:
+
+ \printuntil target="cLightOn"
+ \printuntil /^\ {12}<\//
+
+ As mentioned before, the \c guiControl state is always active, and since
it is of parallel type, all its direct children are always active too.
- So, \c cLight state is always active, however,
- only one of \c cLightOn or \c cLightOff is active at a time.
- The same applies to other children of \c guiControl state.
- In addition, we define transitions between on and off substates, e.g.
- whenever the active state is \c cLightOn and someone posts \c turnOffC event,
- we change the active substate of \c cLight into \c cLightOff, and vice versa:
- whenever the active state is \c cLightOff and we receive \c turnOnC event,
- we change the active substate of \c cLight into \c cLightOn.
-
- In case of our application, we use instances of QLabel class in C++
- to pretend real lights on the table. Whenever the light transitions
- into "on" or "off" state we enable or disable the particular label
- accordingly. The glue connection between the state machine and the GUI
- part of the application will be shown in \l {cpp} {cpp code} later on. For now
+ Therefore, the \c cLight state is always active. However,
+ only one of its children, \c cLightOn or \c cLightOff, is active at a time.
+ The same applies to the other children of the \c guiControl state.
+ In addition, we define transitions between on and off substates. For example,
+ whenever the active state is \c cLightOn and a \c turnOffC event is received,
+ we change the active substate of \c cLight to \c cLightOff.
+ Whenever the active state is \c cLightOff and we receive a \c turnOnC event,
+ we change the active substate of \c cLight to \c cLightOn.
+
+ In our application, we use instances of QLabel class in C++
+ to represent real lights on the table. When the light transitions
+ into the \e on or \e off state, we enable or disable the particular label
+ accordingly. The connection between the state machine and the GUI
+ part of the application will be shown in the \l {cpp}{C++ code} later on. For now,
it is enough to realize that changes to active states inside
- the state machine will serve as external interface of the state machine,
- so that other parts of the application (e.g. GUI part) can listen to.
+ the state machine will serve as the external interface of the state machine
+ that the other parts of the application (such as the GUI part) can listen to.
- All of the mentioned events which switch the state of every light
- will be generated by this state machine inside \c internalState
- in reaction to running timers or to external triggers.
+ All of the mentioned events that switch the state of a light
+ will be generated by this state machine inside the \c internalState
+ in reaction to running timers or external triggers.
- \quotefromfile pinball/pinball.scxml
- \skipto internalState
- \printuntil logicalState
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil workflow
- \dots 16
- \skipto /^\ {12}<\//
- \printuntil /^\ {8}<\//
-
- The \c internalState consists of two main parts: \c logicalState and \c workflow.
- The \c logicalState holds the definitions for modes the game is able
- to go into and logical states of collected targets, while \c workflow state
- implements generator for light blinking and calculates most of new states
- machine should go into depending on incoming events and on currently active states.
+ \section2 Maintaining Game State
+
+ The \c internalState state consists of two main parts: \c logicalState and \c workflow.
+
+ \image pinball-statechart-internalstate.png
+
+ The \c logicalState state holds the definitions for the modes that the game is able
+ to go into and for the logical states of collected targets. The \c workflow state
+ implements a generator for light blinking and calculates most of the new states
+ the machine should go into depending on incoming events and on currently active states.
As mentioned already, \c internalState is always active, and since
- it is of a parallel type, \c logicalState and \c workflow children are always active too.
+ it is of a parallel type, \c logicalState and \c workflow are always active too.
- \quotefromfile pinball/pinball.scxml
- \skipto logicalState
- \printuntil letterState
- \dots 20
- \skipto /^\ {16}<\//
- \printuntil modeState
- \dots 20
- \skipto /^\ {16}<\//
- \printuntil /^\ {12}<\//
+ \section2 Maintaining Logical State of Buttons
+
+ The \c logicalState state consist of two parts: \c letterState and \c modeState.
+
+ \image pinball-statechart-logicalstate.png
- The \c logicalState consist of two parts: \c letterState and \c modeState.
As previously mentioned, \c logicalState is always active, and since
- it is of parallel type, \c letterState and \c modeState children are always active too.
- Now let's look at the first part of it, the \c letterState:
+ it is of parallel type, the \c letterState and \c modeState children are always
+ active too. Now let us look at the first part, the \c letterState, which contains
+ one parallel \c lettersState:
\quotefromfile pinball/pinball.scxml
\skipto letterState
@@ -229,57 +191,54 @@
\skipto /^\ {24}<\//
\printuntil /^\ {16}<\//
- It contains one parallel \c lettersState.
- The \c lettersState maintains the logical state of
- buttons pretending targets which were pressed by the user.
- Please notice the difference between lettersStates and lightStates
- which were mentioned earlier. E.g. the letter state for \uicontrol C letter
- holds the info if the target for \uicontrol C letter was hit or not,
- while the light state for \uicontrol C letter holds the info if the
- light for the target for \uicontrol C letter should be currently on or off.
- In the real pinball game these states are usually orthogonal,
- e.g. if you didn't hit any target yet, the target is blinking,
- indicating that it's currently worth to hit it. This blinking
- means the light state switches between on or off in some short time interval,
- while the target state is continouosly off, since it was not hit yet.
- The author of a pinball table can decide e.g. that
- after hitting the target (so after the target state goes to on)
- he turns target's light continouosly off or on or just increase
- of decrease the interval of blinking.
-
- As mentioned before, \c letterState is always active, so it means
+ The \c lettersState state maintains the logical state of the buttons pretending to
+ be targets that were clicked by the players. The letter state for the letter
+ \uicontrol C holds whether the target for the letter \uicontrol C was hit,
+ while the light state for the letter \uicontrol C holds whether the light
+ for the target for the letter \uicontrol C should be currently on or off.
+ In a real pinball game, these states are usually orthogonal,
+ which means that if you have not hit a target yet, the target is blinking,
+ indicating that it is currently worth hitting. This blinking
+ means that the light state switches between on and off at short intervals,
+ while the target state is continouosly off, because it has not been hit yet.
+ The author of a pinball table can decide that
+ after a target is hit (that is, after the target state switches to on)
+ the target's light is continuously turned off or on or the intervals between
+ lights blinking become shorter or longer.
+
+ As mentioned before, \c letterState is always active, which means
that its only child \c lettersState should always be active too. However,
- there is an exception here: for a short while the \c lettersState may
+ there is one exception: for a short while the \c lettersState may
end up being \e {not active}. This happens when the transition for
\c lettersState is being performed. This transition is triggered when
- the \c resetLetters event will appear and it instructs the state machine
+ the \c resetLetters event occurs, and it instructs the state machine
to exit \c lettersState and all its descendant states and reenter
\c lettersState and set up all its descendant states with their initial states.
In short, the \c resetLetters event resets the \c lettersState and all its
descendant states to the default configuration.
- The \c lettersState contains five direct substates which
- correspond to five different letters. The content
- for other letters states than C, which is omitted here, is analogous.
+ The \c lettersState contains five direct substates that
+ correspond to five different letters. The content for other letters' states
+ than C is not shown here, but it is analogous to the content for C's state.
- The \c {letter.C} contains two substates reflecting its off and on states:
+ The \c {letter.C} state contains two substates reflecting its off and on states:
\c cLetterOff and \c cLetterOn. The \c {letter.C} state inside its parallel
parent \c lettersState is always active (under the condition that
- \c lettersState is active, too, what was described before), however,
+ \c lettersState is active, as described before). However,
only one of its child states is active at a time: \c cLetterOff or \c cLetterOn.
- The initial substate of \c {letter.C} state is \c cLetterOff meaning
- that whenever \c {letter.C} state is being activated (what happens
- initially and after \c resetLetters event) its active
+ The initial substate of the \c {letter.C} state is \c cLetterOff meaning
+ that whenever the \c {letter.C} state is being activated (which happens
+ initially and after the \c resetLetters event) its active
substate will be set to \c cLetterOff.
- The \c cLetterOff defines a transition, which will be triggered by
- the \c {cLetterTriggered} event. This transition activates the \c cLetterOn,
+ The \c cLetterOff state defines a transition, which will be triggered by
+ the \c {cLetterTriggered} event. This transition activates \c cLetterOn,
the other child of \c {letter.C}, only when the machine is in \c onState
- (which will be defined later, but in short: when the pinball game is running).
+ (that is, when the pinball game is running).
The \c {cLetterTriggered} event is expected to be an event posted into the state machine
from outside of the state machine. This event should be generated when
- the ball hits the \uicontrol C letter target. In our example we mimic
- it by the pressing \uicontrol C letter button.
+ the ball hits the letter \uicontrol C target. In our example we mimic
+ it by the clicking the letter \uicontrol C button.
The \c cLetterOn state is defined as a final state, which means that
whenever this state is activated the \c {done.state.letter.C} event
@@ -287,87 +246,92 @@
later for updating the current score.
Moreover, when all \c lettersState children reach their final state,
- the state machine will automatically post \c {done.state.lettersState} event.
+ the state machine will automatically post the \c {done.state.lettersState} event.
This event will be used later, too, for updating the current score
and for turning on or off the hurry state.
- \quotefromfile pinball/pinball.scxml
- \skipto modeState
- \printuntil offState
- \dots 24
- \skipto /^\ {20}<\//
- \printuntil onState
- \dots 24
- \skipto /^\ {20}<\//
- \printuntil /^\ {16}<\//
+ \section2 Maintaining Game Modes
+
+ The \c modeState state consists of two substates, \c offState and \c onState.
- The \c modeState consists of two substates, \c offState and \c onState.
- The \c offState describes what should happen when the pinball game
- is not yet started or when it is over,
+ \image pinball-statechart-modestate.png
+
+ The \c offState state describes what should happen before the pinball game
+ is started and when it is over,
while \c onState represents the logic appropriate for the active game.
\quotefromfile pinball/pinball.scxml
\skipto offState
\printuntil /^\ {20}<\//
- Whenever the pinball application starts or when the game ends the machine goes into the
+ When the pinball application starts or a game ends, the machine goes into
\c offState. Entering that state invokes some actions, which are
- enclosed inside <onentry> element. First, we update the highScore
- variable in case the current highScore value is less than current score value.
- This is being checked inside the "cond" attribute of <if> element
- (please note that we need to escape the "<" character with "&lt;").
- When being in off state, we still want to show the last reached score,
- so we don't clear it here - we will do that when we enter the on state.
- Next, we raise two events: \c resetLetters for logical reset of
- all letter which were possibly hit during last game and \c update
- for immediate generation of light blink and update of all lights.
- When the machine is in \c offState it is ready to go into the
+ enclosed inside an \c <onentry> element. First, we update the \c highScore
+ variable in case the current \c highScore value is less than current \c score value.
+ This is being checked inside the \c "cond" attribute of the \c <if> element
+ (note that we need to escape the "<" character with "&lt;").
+ Even in the \c off state, we want to show the last reached score,
+ so we do not clear it here; we will do that when we enter the \c on state.
+ Next, we raise two events: \c resetLetters to logically reset
+ all letters that might have been hit during the last game and \c update
+ to immediately activate the blinking and updating of all lights.
+ When the machine is in \c offState, it is ready to transition into the
\c onState if only the \c startTriggered event occurs, which is described
- by <transition> element. This event is expected to be generated externally
- after pressing the \uicontrol START button on the pinball table.
+ by the <transition> element. This event is expected to be generated externally
+ after clicking the \uicontrol START button on the pinball table.
\skipto onState
\printuntil /^\ {20}<\//
- The fist thing which is being done by the state machine after in enters
- the \c onState is clearing the current score variable. The \c onState
- is of parallel type and consists of two direct child states:
- \c hurryState and \c jackpotState, which both are always active as long as
- their parent "onState" is active too. Both \c hurryState and \c jackpotState
- contain two substates which reflects the off and the on state of each of them.
+ \section2 Game On
+
+ When the state machine enters \c onState, it first clears the current score
+ variable. The \c onState state is of the parallel type and has two direct child states:
+ \c hurryState and \c jackpotState. They are active as long as
+ their parent, \c onState, is active. Both \c hurryState and \c jackpotState
+ contain two substates that reflect their off and on states.
Only one substate of \c hurryState and one substate of \c jackpotState
- can be acitve at a time and initially the off substates are active.
+ can be active at a time. Initially, the off substates are active.
- Whenever we enter \c hurryStateOff or \c hurryStateOn we generate two events:
- \c resetLetters and \c update (the same as we generate when entering the \c onState).
- In addition when we enter the \c hurryStateOn we send a delayed event
- \c goToHurryOff with a delay of 5s, marked with \c hurryId. It means, that after 5s we just
+ \image pinball-statechart-onstate.png
+
+ Whenever we enter \c hurryStateOff or \c hurryStateOn, we generate the same
+ two events we generate when entering the \c onState state: \c resetLetters and
+ \c update. In addition, when we enter the \c hurryStateOn state, we send a delayed
+ event, \c goToHurryOff, with a delay of five seconds, marked with \c hurryId.
+ This means that after five seconds we just
switch the state back to \c hurryStateOff without granting the bonus points.
- In this way we implement the five seconds hurry feature of the pinball table.
- We also define transitions: \c hurryStateOff -> \c hurryStateOn
- when \c goToHurryOn event occurs and the opposite,
- \c hurryStateOn -> \c hurryStateOff when \c goToHurryOff event occurs.
- When we exit the \c hurryStateOn we cancel possibly pending delayed
- event which was marked with \c hurryId. This is important in case
- the 5s time hasn't elapsed yet, but we've collected all the five letters
- in the hurry state - we then collect the jackpot and want the pending
- timer to finish.
-
- The substates of \c jackpotState generate the request for update the state
- of lights. The \c jackpotStateOff defines the transition to \c jackpotStateOn
- when the \c goForJackpot event occurs. The opposite transition isn't
- needed, since when the jackpot gets collected the corresponding light
- is left lit until the end of game. When the new game starts, the \c jackpotState
- is entered again which causes that its initial active substate will be
+ In this way, we implement the five-second hurry feature of the pinball table.
+ We also define transitions from \c hurryStateOff to \c hurryStateOn when the
+ \c goToHurryOn event occurs and from \c hurryStateOn to \c hurryStateOff
+ when the \c goToHurryOff event occurs. When we exit the \c hurryStateOn
+ state, we cancel the possibly pending delayed event that was marked with
+ \c hurryId. This is important in case the five secons have not elapsed yet,
+ but players have collected all the five letters in the hurry state. We then
+ collect the jackpot and want the pending timer to finish.
+
+ The substates of \c jackpotState generate the request to update the state
+ of lights. The \c jackpotStateOff state defines the transition to \c jackpotStateOn
+ when the \c goForJackpot event occurs. The opposite transition is not
+ needed, because when the jackpot gets collected, the corresponding light
+ remains lit until the end of game. When a new game starts, the \c jackpotState
+ is entered again which causes its initial active substate to be
\c jackpotStateOff.
- In addition, the \c onState defines one transition in reaction to
+ In addition, the \c onState state defines one transition in reaction to the
\c ballOutTriggered event which instructs the machine to go into the \c offState.
The \c ballOutTriggered event is expected to be an event posted into the state machine
from outside of the state machine. This event should be generated when
the ball gets out of playing area of the table. In our example we mimic
- it by the pressing \uicontrol {BALL OUT} button. Posting the event from outside of state
- machine will be shown in \l {cpp} {cpp code} later on.
+ it by the clicking \uicontrol {BALL OUT} button. Posting the event from outside of state
+ machine will be shown in the \l{cpp}{C++ code} later on.
+
+ \section2 Generating Blinking Lights
+
+ The \c workflow state is responsible for generating the blinking lights. The
+ generator is defined in its \c lightImpulseGenerator substate. In addition,
+ it is responsible for reacting to events that have been posted so far from
+ the other parts of the state machine.
\quotefromfile pinball/pinball.scxml
\skipto workflow
@@ -382,31 +346,29 @@
\skipto /^\ {16}<\//
\printuntil /^\ {12}<\//
- The \c workflow state is responsible for generator for light blinking,
- which is defined in its \c lightImpulseGenerator substate, and
- for reacting for events which were posted so far from other parts
- of the state machine.
-
The \c lightImpulseGenerator contains two child states:
\c lightImpulseOn and \c lightImpulseOff, with only one active at a time.
+
+ \image pinball-statechart-workflow.png
+
Whenever the delayed \c lightImpulse event is being delivered, it immediately
- cause the transition from \c lightImpluseOn into \c lightImpulseOff or vice versa,
+ causes the transition from \c lightImpluseOn into \c lightImpulseOff or vice versa,
depending on the state the machine was in. In effect, the \c lightImpulseGenerator
toggles between its on and off state. These transitions are defined inside
\c lightImpulseGenerator, so it means that during this toggling the machine
also exits \c lightImpulseGenerator and reenters it immediately afterwards.
- Entering \c lightImpulseGenerator cause generation of the \c update event.
- The \c update event triggers the targetless transition and posts two other
+ Entering \c lightImpulseGenerator causes the generation of the \c update event.
+ The \c update event triggers a targetless transition and posts two other
events: \c scheduleNewImpulse and \c updateLights. The first one,
- \c scheduleNewImpulse returns back to the \c lightImpulseGenerator and
- it posts delayed \c lightImpulse event. After the desired delay,
- the \c lightImpulse gets delivered to \c lightImpulseGenerator back
- and it causes to toggle its substate again. In this way the machine
- gets into the cycle. The current delay of the \c lightImpulse
- event depends on the state in which the machine was in time of posting that delayed event.
- Please also notice, that the next \c scheduleNewImpulse
- event may occur on demand, before the next delayed \c lightImpulse
- event gets delivered, so for that case we cancel any possible pending event.
+ \c scheduleNewImpulse, returns back to the \c lightImpulseGenerator, which
+ posts a delayed \c lightImpulse event. After the delay,
+ the \c lightImpulse event gets delivered back to \c lightImpulseGenerator,
+ which causes it to toggle its substate again. In this way, the machine
+ enters into a cycle. The current delay of the \c lightImpulse
+ event depends on the state in which the machine was in the time of posting
+ the delayed event. If a \c scheduleNewImpulse event occurs on demand, before
+ the next delayed \c lightImpulse event gets delivered, we cancel any
+ possible pending events.
\quotefromfile pinball/pinball.scxml
\skipto workflow
@@ -415,30 +377,30 @@
\printuntil /^\ {16}<\//
Whenever we receive the event the name of which matches the
- \c {done.state.letter.*} we update the current score.
- When the machine enters the final substate of the \c {letter.C}
+ \c {done.state.letter.*}, we update the current score.
+ When the machine enters the final substate of the \c {letter.C},
it emits the \c {done.state.letter.C} event. The same happens for
- all other letters we have previously defined. We capture here
- the events for all letters, that is why we've used an asterisk
+ all other letters we have previously defined. We capture the events for all
+ letters, that is why we have used an asterisk
after a dot in the event name.
The transition above is targetless, since we just
listen for matching events and update the internal data accordingly
without changing any active state. The new score is being
- increased by 1.000 or 10.000 points, depending if we currently are
+ increased by 1.000 or 10.000 points, depending on whether we currently are
in \c hurryStateOff or \c hurryStateOn.
- After the score is updated we generate the \c updateLights event
- in order to update immediately letters' lights accordingly.
- We don't generate "update" here, since we don't want to toggle
- light impulse now, but just update the lights according to
+ After the score is updated, we generate the \c updateLights event
+ in order to immediately update the letters' lights accordingly.
+ We do not generate the \c update event here, since we do not want to toggle
+ the light impulse now, but just update the lights according to
the current impulse state.
We also intercept the \c {done.state.lettersState} event,
- which is being generated when all the letters were hit.
- Depending on which state we are currently in, we grant
+ which is being generated when all the letters have been hit.
+ Depending on which state we are currently in, we grant the players either
a small bonus of 100.000 or a big one of 1.000.000 (jackpot).
- In addition we toggle \c hurryState substate by
- sending \c goToHurryOn or \c goToHurryOff event.
- When all letters were collected being in \c hurryStateOn
+ In addition, we toggle the \c hurryState substate by
+ sending the \c goToHurryOn or \c goToHurryOff event.
+ When all letters have been collected while in \c hurryStateOn,
we also raise the \c goForJackpot event which instructs
the machine to activate the \c jackpotStateOn.
@@ -469,43 +431,42 @@
\skipto /^\ {28}<\//
\printuntil /^\ {16}<\//
- When we receive \c updateLights event, we first want to send a
+ When we receive the \c updateLights event, we first want to send a
\c updateScore signal outside of the state machine. We pass
- the current value of highscore and score variables to the signal.
- This signal is received by the cpp part.
+ the current values of the \c highScore and \c score variables to the signal.
+ This signal is received by the C++ part.
- Next, depending if we are in \c jackpotStateOn or \c jackpotStateOff
+ Next, depending on whether we are in \c jackpotStateOn or \c jackpotStateOff,
we send the \c turnOnJackpot or the \c turnOffJackpot signal,
which instructs the \c guiControl state to transition to
- \c jackpotLightOn or \c jackpotLightOff respectively.
+ \c jackpotLightOn or \c jackpotLightOff, respectively.
- When the machine is in \e idle state, i.e. in off state
- or when the game is on, but no interaction is being performed,
+ When the machine is in \e idle state, (that is, in the off state)
+ or when the game is on, but no interaction occurs,
the \c updateLights event is delivered periodically
- during the game, each time with \c lightImpulseOn or
+ during the game, each time with the \c lightImpulseOn or
\c lightImpulseOff state toggled. Depending on the
- current state of light impulse, and depending also
- on which of \c offState, \c hurryStateOff or \c hurryStateOn
- is active we turn on or off all the lights accordingly
- to the description of the pinball table.
+ current state of the light impulse and on the active state (\c offState,
+ \c hurryStateOff or \c hurryStateOn), we turn on or off all the lights
+ according to the description of the pinball table.
\section1 GUI Part: User Interface Description
- The GUI part of the application consists of a mainwindow.ui
+ The GUI part of the application consists of a \e mainwindow.ui
file which describes the static user interface of the game.
\target cpp
- \section1 CPP Part: Glue GUI with SCXML
+ \section1 C++ Part: Glue GUI with SCXML
- The CPP part of the application consists of a
- MainWindow class which glues the GUI part with the SCXML part.
- The class is declared in mainwindow.h.
+ The C++ part of the application consists of a
+ \c MainWindow class which glues the GUI part with the SCXML part.
+ The class is declared in \e mainwindow.h.
\quotefromfile pinball/mainwindow.h
\skipto Pinball
\printuntil };
- The MainWindow class holds the pointer to the
+ The \c MainWindow class holds the pointer to the
\c {Pinball *m_machine} which is the state machine
class automatically generated by Qt out of SCMXL file
and the pointer to the \c {Ui::MainWindow *m_ui} which
@@ -515,20 +476,20 @@
\skipto #include
\printuntil /\}$/
- The constructor of the MainWindow class
+ The constructor of the \c MainWindow class
instantiates the GUI part of the application
and stores the pointer to the passed \c Pinball state machine.
It also initializes the GUI part and glues the
- GUI part with the state machine by connecting
+ GUI part to the state machine by connecting
their communication interfaces together.
The \c initAndConnect() method connects
the state with the corresponding GUI widget by
- binding its activity with the enablement of the widget,
- so that whenever the state is active its corresponding
- widget is enabled and whenever the state is inactive
- the widget is disabled. We do that for all lights, targets
- and description lables.
+ binding its activity with the enabling of the widget,
+ so that whenever the state is active, its corresponding
+ widget is enabled and whenever the state is inactive,
+ the widget is disabled. We do that for all lights, targets,
+ and description labels.
We also connect to the \c eventOccurred() signal, propagated
by the state machine and intercept the \c updateScore
@@ -538,15 +499,14 @@
The info about hitting any GUI target needs to be passed
to the state machine and we do that by connecting
all target buttons' \c clicked signals to the lambda expressions
- which submit corresponding event into the state machine.
+ which submit the corresponding event into the state machine.
\quotefromfile pinball/main.cpp
\skipto #include
\printuntil /\}$/
- Finally, there is main.cpp file with the main() function
- inside which we instantiate the
- \c app application object, \c Pinball state machine
+ In the \c main() function in the \e main.cpp file, we instantiate the
+ \c app application object, \c Pinball state machine,
and \c MainWindow GUI class. We initialize and start the state machine,
- show the main window and execute the application.
+ show the main window, and execute the application.
*/