Uncharted 2 State Scripting
Uncharted 2 State Scripting
Jason Gregory
Generalist Programmer
Naughty Dog, Inc.
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
1
Agenda
Introduction to game scripting
Extending the game object model
State script syntax
Case studies from
Uncharted 2: Among Thieves
Implementation discussion
Summary and some tips
Monday, April 6, 2009
Introduction to State Scripts
4
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Brief History of State Scripts
Script system on Uncharted: Drakes Fortune originally developed
for in-game cinematics (IGCs)
Evolved into general gameplay scripting system
5
Monday, April 6, 2009
UDF IGC system revamped for heavy
use on Uncharted 2: Among Thieves
Inspirations:
! GOAL language used on Crash and Jak series
! State objects from God of War engine
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Brief History of State Scripts
6
78
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Why Script?
Scripting languages used in games since Quake C
Primary benets of script:
! Takes pressure off engineering team
! Code becomes datarapid iteration
! Empowers content creators
! Key enabler of mod community
9
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Why Script?
Scripting languages used in games since Quake C
Primary benets of script:
! Takes pressure off engineering team
! Code becomes datarapid iteration
! Empowers content creators
! Key enabler of mod community
9
I fee| empowered!
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Scripting Language Characteristics
Two kinds of game scripting languages:
! data denition languages
! runtime languages
Runtime scripting languages typically:
! interpreted by virtual machine (VM)
! simple and smalllow overhead
! accessible to designers and other non-programmers
! powerfulone line of code = big impact
:
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Choice of Language
At Naughty Dog, we make heavy use of both data denition
and runtime script
! Both based on PLT Scheme (a Lisp variant)
Key benets of Lisp-like languages:
! Easy to parse
! Data def and runtime code can be freely intermixed
! Powerful macro systemeasy to dene custom syntax
! Naughty Dog has a rich Lisp heritagecomfortable
;
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Choice of Language
Of course you dont have to use Lisp!
Data denition languages:
! custom text format,
! Excel comma-separated values (.csv),
! XML, ...
Runtime languages:
! Python, Lua, Pawn (Small C), OCaml, F#, ...
Many popular engines already provide a scripting language:
! Quake C, UnrealScript, C# (XNA), ...
3
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Extending the Game Object Model
<2
Every game engine has some kind of game object model
! Denes all object types in game world
! Often (but not always) written in an object-oriented language
Scripting language often used to extend the native object model
Many ways to accomplish this...
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Game Object Model References
Rob Fermier, Creating a Data Driven Engine, GDC, 2002
Scott Bilas, A Data-Driven Game Object System, GDC, 2002
(http://www.drizzle.com/~scottb/gdc/game-objects.ppt)
Alex Duran, Building Object Systems: Features, Tradeoffs and
Pitfalls, GDC, 2003
Doug Church, Object Systems, presented at a game development
conference in Seoul, Korea, 2003
(http://chrishecker.com/images/6/6f/ObjSys.ppt)
Jason Gregory, Game Engine Architecture, AK Peters, 2009
(http://gameenginebook.com)
<<
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Unreals Approach
UnrealScript tightly integrated with C++ object model
! Single-root class hierarchy with some add-on components
! Classes dened in UnrealScript (.uc)
! C++ header le (.h) automatically generated
! Implementation in C++ or entirely in UnrealScript
<1
awn.h
awn.cpp
generate
|mp|ement
awn.uc
|mp|ement
Actor
Info awn |ckup
Scout Veh|c|e
...
...
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Property-Centric / Componentized Designs
Property-centric design used on Thief, Dungeon Siege, Age of
Mythology, Deus Ex 2 and others
! Game object just a unique id (UID)
! Decorated with various properties
(health, armor, weaponry, etc.)
! Property encapsulates data + behavior
<4
Cb[ect
(UID)
nea|th: 200
Armor: L|ght
AI: |ayerA||y
Weapon: 8IG
Weapon: |sto|
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
Monday, April 6, 2009
=>?$0@,
@A"@ B*C"@$
)'$+ D#$
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
=>?$0@,
EF@A @+".,/)+#
".C #$,A
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
G",$ 0(",, /)+
"(( 0A"+"0@$+,
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
HF#*($
".F#"D.I
)>?$0@
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
8"."I$, " H@"@$
H0+F*@ F.,@".0$
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess rocessGameCb[ect CameraContro|
Character S|mp|eLnnty
...
...
DynL|ght Ss1rackGrouprocess
...
8"."I$, "
0AB.J )/
+B..F.I ,0+F*@
0)C$
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
Ssrocess
SsInstance
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted Engines Object Model
Uncharted class hierarchy:
! relatively shallow, single-root
! host of add-on components
<5
rocess
rocessGameCb[ect
SsInstance DrawContro| An|mContro|
...
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Charter
World editor for
Uncharted is called
Charter
! Place game objects
! Edit object
properties
! Control level
streaming
<6
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Uncharted State Scripts
State scripts similar in many respects to property-centric model...
! adds nite state machine (FSM) support
! not specically tied to properties
! coarser-grained (one script per object)
More like scripted extension to existing entity type...
! ... or a director that orchestrates actions of other entities
<9
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Anatomy of a State Script
A state script is comprised of:
! attributes
! states
States dene objects behavior via runtime script code:
! response to events
! natural behavior over time (update event)
! transitional actions between states (begin/end events)
<:
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
<;
Anatomy of a State Script
State Scr|pt 1
H@"@$ K
L"+F">($,
H@"@$ G
State Scr|pt 2
H@"@$ -
L"+F">($,
On Update
On Event1
On Begin On Event4
On Begin
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
<;
Anatomy of a State Script
State Scr|pt 1
H@"@$ K
L"+F">($,
H@"@$ G
M'$.@<
State Scr|pt 2
H@"@$ -
L"+F">($,
On Update
On Event1
On Begin On Event4
On Begin
Monday, April 6, 2009
I) @)
H@"@$ G
!"#$ &$'$()*$+, -)./$+$.0$ 1223
<;
Anatomy of a State Script
State Scr|pt 1
H@"@$ K
L"+F">($,
H@"@$ G
M'$.@<
State Scr|pt 2
H@"@$ -
L"+F">($,
On Update
On Event1
On Begin On Event4
On Begin
Monday, April 6, 2009
I) @)
H@"@$ G
!"#$ &$'$()*$+, -)./$+$.0$ 1223
<;
Anatomy of a State Script
State Scr|pt 1
H@"@$ K
L"+F">($,
H@"@$ G
M'$.@<
State Scr|pt 2
H@"@$ -
L"+F">($,
M'$.@5
On Update
On Event1
On Begin On Event4
On Begin
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Instantiating a State Script
<3
Game
Cb[ect
State Scr|pt 1
Attached to a native (C++) game object:
! designers extend or modify native
C++ object type
! dene entirely new object types
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Instantiating a State Script
Attached to a trigger region:
! convex volume
! detects enter, exit and occupancy
<3
Game
Cb[ect
State Scr|pt 1
1r|gger keg|on
State Scr|pt 2
Attached to a native (C++) game object:
! designers extend or modify native
C++ object type
! dene entirely new object types
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Instantiating State Scripts
Placed as stand-alone object:
! director orchestrates actions of
other objects (e.g. IGC)
12
Ssrocess
State Scr|pt 3
(stand-a|one)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Instantiating State Scripts
Placed as stand-alone object:
! director orchestrates actions of
other objects (e.g. IGC)
12
1ask A
1ask 81 1ask 82
1ask C
1ask D
State Scr|pt 4
Ssrocess
State Scr|pt 3
(stand-a|one)
Associated with a task:
! task = check point
! script manages associated task
! orchestrates AI encounters
! controls player objectives
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Instantiating State Scripts
Placed as stand-alone object:
! director orchestrates actions of
other objects (e.g. IGC)
12
1ask A
1ask 81 1ask 82
1ask C
1ask D
State Scr|pt 4
Ssrocess
State Scr|pt 3
(stand-a|one)
Associated with a task:
! task = check point
! script manages associated task
! orchestrates AI encounters
! controls player objectives
Spawned by another state script
Monday, April 6, 2009
State Script Syntax
1<
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
11
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
State Script Syntax
State script dened as follows:
! Dont let Lisp syntax throw you!
! Lisp syntax is all (parentheses)
! Think C/C++ { } blocks
Parenthesized blocks highly
context-sensitive in Lisp/Scheme
14
(dene-state-script ("kickable-gate")
(state ("locked")
...
)
(state ("opening")
...
)
(state ("open")
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
State Script Syntax
State script dened as follows:
! Dont let Lisp syntax throw you!
! Lisp syntax is all (parentheses)
! Think C/C++ { } blocks
Parenthesized blocks highly
context-sensitive in Lisp/Scheme
14
(dene-state-script ("kickable-gate")
(state ("locked")
...
)
(state ("opening")
...
)
(state ("open")
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
State Script Syntax
State script dened as follows:
! Dont let Lisp syntax throw you!
! Lisp syntax is all (parentheses)
! Think C/C++ { } blocks
Parenthesized blocks highly
context-sensitive in Lisp/Scheme
14
(dene-state-script ("kickable-gate")
(state ("locked")
...
)
(state ("opening")
...
)
(state ("open")
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
State Script Syntax
State script dened as follows:
! Dont let Lisp syntax throw you!
! Lisp syntax is all (parentheses)
! Think C/C++ { } blocks
Parenthesized blocks highly
context-sensitive in Lisp/Scheme
14
(dene-state-script ("kickable-gate")
(state ("locked")
...
)
(state ("opening")
...
)
(state ("open")
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Event Handler Blocks
Each state contains zero or more
event handler blocks
15
(dene-state-script ("kickable-gate")
(state ("locked")
(on (event "kick")
... ;; handle "kick" event
)
(on (begin)
... ;; do when state entered
)
(on (update)
... ;; do every frame
)
(on (end)
... ;; do when state exited
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Event Handler Blocks
Each state contains zero or more
event handler blocks
15
(dene-state-script ("kickable-gate")
(state ("locked")
(on (event "kick")
... ;; handle "kick" event
)
(on (begin)
... ;; do when state entered
)
(on (update)
... ;; do every frame
)
(on (end)
... ;; do when state exited
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Event Handler Blocks
Each state contains zero or more
event handler blocks
15
(dene-state-script ("kickable-gate")
(state ("locked")
(on (event "kick")
... ;; handle "kick" event
)
(on (begin)
... ;; do when state entered
)
(on (update)
... ;; do every frame
)
(on (end)
... ;; do when state exited
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Event Handler Blocks
Each state contains zero or more
event handler blocks
15
(dene-state-script ("kickable-gate")
(state ("locked")
(on (event "kick")
... ;; handle "kick" event
)
(on (begin)
... ;; do when state entered
)
(on (update)
... ;; do every frame
)
(on (end)
... ;; do when state exited
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Event Handler Blocks
Each state contains zero or more
event handler blocks
15
(dene-state-script ("kickable-gate")
(state ("locked")
(on (event "kick")
... ;; handle "kick" event
)
(on (begin)
... ;; do when state entered
)
(on (update)
... ;; do every frame
)
(on (end)
... ;; do when state exited
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Runtime Script Code
Runtime script code inside (on ...)
blocks
Simplied Scheme/Lisp
! Most commands are native calls
into C++ code
! Conditional expressions
! Simple looping via label/goto
16
(state ("locked")
(on (begin)
[print-string "Starting idle!"]
[animate "self" "locked-idle"]
)
(on (event "kicked")
[when [lock-broken?]
[print-string "BAM!"]
]
[if [task-complete? "wave2"]
[print-string "Complete!"]
[print-string "NOT!!!"]
]
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Runtime Script Code
Runtime script code inside (on ...)
blocks
Simplied Scheme/Lisp
! Most commands are native calls
into C++ code
! Conditional expressions
! Simple looping via label/goto
16
(state ("locked")
(on (begin)
[print-string "Starting idle!"]
[animate "self" "locked-idle"]
)
(on (event "kicked")
[when [lock-broken?]
[print-string "BAM!"]
]
[if [task-complete? "wave2"]
[print-string "Complete!"]
[print-string "NOT!!!"]
]
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Runtime Script Code
Runtime script code inside (on ...)
blocks
Simplied Scheme/Lisp
! Most commands are native calls
into C++ code
! Conditional expressions
! Simple looping via label/goto
16
(state ("locked")
(on (begin)
[print-string "Starting idle!"]
[animate "self" "locked-idle"]
)
(on (event "kicked")
[when [lock-broken?]
[print-string "BAM!"]
]
[if [task-complete? "wave2"]
[print-string "Complete!"]
[print-string "NOT!!!"]
]
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Runtime Script Code
Runtime script code inside (on ...)
blocks
Simplied Scheme/Lisp
! Most commands are native calls
into C++ code
! Conditional expressions
! Simple looping via label/goto
16
(state ("locked")
(on (begin)
[print-string "Starting idle!"]
[animate "self" "locked-idle"]
)
(on (event "kicked")
[when [lock-broken?]
[print-string "BAM!"]
]
[if [task-complete? "wave2"]
[print-string "Complete!"]
[print-string "NOT!!!"]
]
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
User-Dened Functions
Script functions can be dened
and called by script programmer
19
(defun verbose-anim ((anim string))
[print-string "Starting " anim]
[animate "self" anim]
)
(dene-state-script ("kickable-gate")
(state ("locked")
(on (begin)
[verbose-anim "locked-idle"]
)
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
User-Dened Functions
Script functions can be dened
and called by script programmer
19
(defun verbose-anim ((anim string))
[print-string "Starting " anim]
[animate "self" anim]
)
(dene-state-script ("kickable-gate")
(state ("locked")
(on (begin)
[verbose-anim "locked-idle"]
)
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
User-Dened Functions
Script functions can be dened
and called by script programmer
19
(defun verbose-anim ((anim string))
[print-string "Starting " anim]
[animate "self" anim]
)
(dene-state-script ("kickable-gate")
(state ("locked")
(on (begin)
[verbose-anim "locked-idle"]
)
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
User-Dened Functions
Script functions can be dened
and called by script programmer
19
(defun verbose-anim ((anim string))
[print-string "Starting " anim]
[animate "self" anim]
)
(dene-state-script ("kickable-gate")
(state ("locked")
(on (begin)
[verbose-anim "locked-idle"]
)
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
User-Dened Functions
Script functions can be dened
and called by script programmer
19
(defun verbose-anim ((anim string))
[print-string "Starting " anim]
[animate "self" anim]
)
(dene-state-script ("kickable-gate")
(state ("locked")
(on (begin)
[verbose-anim "locked-idle"]
)
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
The Self Argument
Any command operating on a game object takes its unique id
(UID) as its rst argument
Magic UID "self" refers to the object to which script is attached
1:
Game
Cb[ect
State Scr|pt 1
I"@$N<:
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
The Self Argument
Any command operating on a game object takes its unique id
(UID) as its rst argument
Magic UID "self" refers to the object to which script is attached
1:
Game
Cb[ect
State Scr|pt 1
(on (begin)
[animate "self" "locked-idle"]
)
,$(/
I"@$N<:
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
The Self Argument
Any command operating on a game object takes its unique id
(UID) as its rst argument
Magic UID "self" refers to the object to which script is attached
1:
Game
Cb[ect
State Scr|pt 1
I"@$N<: (on (begin)
[animate "gate-17" "locked-idle"]
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
The Self Argument
Any command operating on a game object takes its unique id
(UID) as its rst argument
Magic UID "self" refers to the object to which script is attached
1:
Game
Cb[ect
State Scr|pt 1
I"@$N<:
Game
Cb[ect
()0JN9
(on (begin)
[animate "lock-6" "fall-off"]
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Changing States
Transitions to other states via
(go "state-name") command
State transitions cause current
states (on ...) blocks to be
aborted
Use (on (exit) ...) block for
clean-up
1;
(dene-state-script ("kickable-gate")
(state ("locked")
...
(on (event "kicked")
[when [lock-broken?]
[go "opening"]
]
)
)
(state ("opening")
(on (begin)
...
)
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Changing States
Transitions to other states via
(go "state-name") command
State transitions cause current
states (on ...) blocks to be
aborted
Use (on (exit) ...) block for
clean-up
1;
(dene-state-script ("kickable-gate")
(state ("locked")
...
(on (event "kicked")
[when [lock-broken?]
[go "opening"]
]
)
)
(state ("opening")
(on (begin)
...
)
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Changing States
Transitions to other states via
(go "state-name") command
State transitions cause current
states (on ...) blocks to be
aborted
Use (on (exit) ...) block for
clean-up
1;
(dene-state-script ("kickable-gate")
(state ("locked")
...
(on (event "kicked")
[when [lock-broken?]
[go "opening"]
]
)
)
(state ("opening")
(on (begin)
...
)
...
)
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
(on ...) blocks contain one or more tracks
A track is a bit like a thread or ber
Tracks can be put to sleep
! Wait for duration
e.g., wait 5 seconds,
wait until frame 23, ...
! Wait for an action to be done
duration-agnostic
Tracks can be synchronized via signals
13
Monday, April 6, 2009
H@"@$ O,A"J$NA".C,O
=. G$IF.
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
42
7+"0J
P
7+"0J
H
,N"NE
*N"NE
(state ("shake-hands")
(on (begin)
(track ("player"))
[wait-move-to "player" "waypoint7"]
[signal "player-at-waypoint"]
[wait-for-signal "sully-at-waypoint"]
[wait-animate "player" "shake-sullys-hand"]
)
(track ("sullivan"))
[wait-move-to "sullivan" "waypoint7"]
[signal "sully-at-waypoint"]
[wait-for-signal "player-at-waypoint"]
[wait-animate "sullivan" "shake-drakes-hand"]
)
)
)
Monday, April 6, 2009
H@"@$ O,A"J$NA".C,O
=. G$IF.
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
42
7+"0J
P
7+"0J
H
,N"NE
*N"NE
(state ("shake-hands")
(on (begin)
(track ("player"))
[wait-move-to "player" "waypoint7"]
[signal "player-at-waypoint"]
[wait-for-signal "sully-at-waypoint"]
[wait-animate "player" "shake-sullys-hand"]
)
(track ("sullivan"))
[wait-move-to "sullivan" "waypoint7"]
[signal "sully-at-waypoint"]
[wait-for-signal "player-at-waypoint"]
[wait-animate "sullivan" "shake-drakes-hand"]
)
)
)
7+"0J
P
7+"0J
H
Monday, April 6, 2009
H@"@$ O,A"J$NA".C,O
=. G$IF.
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
42
7+"0J
P
7+"0J
H
,N"NE
*N"NE
(state ("shake-hands")
(on (begin)
(track ("player"))
[wait-move-to "player" "waypoint7"]
[signal "player-at-waypoint"]
[wait-for-signal "sully-at-waypoint"]
[wait-animate "player" "shake-sullys-hand"]
)
(track ("sullivan"))
[wait-move-to "sullivan" "waypoint7"]
[signal "sully-at-waypoint"]
[wait-for-signal "player-at-waypoint"]
[wait-animate "sullivan" "shake-drakes-hand"]
)
)
)
Monday, April 6, 2009
H@"@$ O,A"J$NA".C,O
=. G$IF.
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
42
7+"0J
P
7+"0J
H
,N"NE
*N"NE
(state ("shake-hands")
(on (begin)
(track ("player"))
[wait-move-to "player" "waypoint7"]
[signal "player-at-waypoint"]
[wait-for-signal "sully-at-waypoint"]
[wait-animate "player" "shake-sullys-hand"]
)
(track ("sullivan"))
[wait-move-to "sullivan" "waypoint7"]
[signal "sully-at-waypoint"]
[wait-for-signal "player-at-waypoint"]
[wait-animate "sullivan" "shake-drakes-hand"]
)
)
)
Monday, April 6, 2009
H@"@$ O,A"J$NA".C,O
=. G$IF.
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Tracks
42
(state ("shake-hands")
(on (begin)
(track ("player"))
[wait-move-to "player" "waypoint7"]
[signal "player-at-waypoint"]
[wait-for-signal "sully-at-waypoint"]
[wait-animate "player" "shake-sullys-hand"]
)
(track ("sullivan"))
[wait-move-to "sullivan" "waypoint7"]
[signal "sully-at-waypoint"]
[wait-for-signal "player-at-waypoint"]
[wait-animate "sullivan" "shake-drakes-hand"]
)
)
)
7+"0J
P
7+"0J
H
*N"NE
,N"NE
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Track Execution Over Time
4<
Rules for execution of code within a track:
! Greedily consume instructions sequentially...
! ... until a [wait* ...] command encountered...
! ... then relinquish control until the action is complete
NOTE: A [wait* ...] command doesnt have to wait; for example:
! [wait-seconds 0]
! [wait-npc-move-to "pos-4"] when shes already there
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Options and Variable Declarations
Options declared at top of
script:
! initial state
! variable declarations
! debugging options
41
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
...
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Options and Variable Declarations
Options declared at top of
script:
! initial state
! variable declarations
! debugging options
41
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
...
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
Options and Variable Declarations
Options declared at top of
script:
! initial state
! variable declarations
! debugging options
41
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
...
)
...
)
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
44
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
(on (begin)
[when [get-boolean "is-locked"]
[set-int32 "num-attempts"
[+ 1 [get-int32 "num-attempts"]]
]
[wait-animate "self" "kick-failure"]
[go "closed"]
]
;; else...
[wait-animate "self" "kick-success"]
[go "open"]
)
)
...
Manipulating Variables
Simple commands for reading
and writing variables
Lisp/Scheme uses prex notation
(a.k.a. Polish notation)
! [+ a b] calculates (a + b)
! [set "x" [+ 1 [get "x"]]]
increments variable x
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
44
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
(on (begin)
[when [get-boolean "is-locked"]
[set-int32 "num-attempts"
[+ 1 [get-int32 "num-attempts"]]
]
[wait-animate "self" "kick-failure"]
[go "closed"]
]
;; else...
[wait-animate "self" "kick-success"]
[go "open"]
)
)
...
Manipulating Variables
Simple commands for reading
and writing variables
Lisp/Scheme uses prex notation
(a.k.a. Polish notation)
! [+ a b] calculates (a + b)
! [set "x" [+ 1 [get "x"]]]
increments variable x
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
44
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
(on (begin)
[when [get-boolean "is-locked"]
[set-int32 "num-attempts"
[+ 1 [get-int32 "num-attempts"]]
]
[wait-animate "self" "kick-failure"]
[go "closed"]
]
;; else...
[wait-animate "self" "kick-success"]
[go "open"]
)
)
...
Manipulating Variables
Simple commands for reading
and writing variables
Lisp/Scheme uses prex notation
(a.k.a. Polish notation)
! [+ a b] calculates (a + b)
! [set "x" [+ 1 [get "x"]]]
increments variable x
Monday, April 6, 2009
!"#$ &$'$()*$+, -)./$+$.0$ 1223
44
(dene-state-script ("kickable-gate")
:initial-state "closed"
:declarations (decl-list
(var "num-attempts" :type int32)
(var "is-locked" :type boolean :default #t)
)
(state ("kicked")
(on (begin)
[when [get-boolean "is-locked"]
[set-int32 "num-attempts"
[+ 1 [get-int32 "num-attempts"]]
]
[wait-animate "self" "kick-failure"]
[go "closed"]
]
;; else...
[wait-animate "self" "kick-success"]
[go "open"]
)
)
...
Manipulating Variables
Simple commands for reading
and writing variables
Lisp/Scheme uses prex notation
(a.k.a. Polish notation)
! [+ a b] calculates (a + b)
! [set "x" [+ 1 [get "x"]]]
increments variable x