unit 6 object-oriented simulation Object-oriented simulation Used for simulation of physical systems Key idea: the physical world consists of objects Chemical plants Air combat Ecologies Objects have their own state Objects act on one another Make a simulation which has one data object per physical object Give each object fields that mirror the state of the physical objects Give objects methods to implement the forces/actions that change objects Object-oriented programming Means many things to many people Least common denominator: Divide data into objects with fields Provide some mechanism to allow objects to specify their own methods for implementing different procedures ( a.k.a. “messages”) OOP with class-based inheritance Objects are divided into classes (types) Fields and methods determined are by an object’s class Subclasses inherit fields and methods from parent classes But can selectively override particular methods of the parent class OOP in Meta [class [Name fields …] Parent more-fields …] Makes a new object of type Type And sets its fields based on args Defines a method for initializing an object of type Type before it’s returned by new Makes a procedure that can be specialized with methods [define-method [generic [Type arg] …] body …] [define-method [initialize [Type arg]] [generic-procedure] [new Type args …] Creates a new class named Name With parent class Parent And fields fields … and more-fields … Adds/modifies a method for generic procedure generic Matches only those calls whose args have their corresponding Types When a match is found, executes body [call-next-method] When used inside a method, calls the method of the parent class Adventure games One of the oldest computer game genres Based on wandering through a set of rooms interacting with objects and characters Solving puzzles or mysteries Subgenres Point-and-click adventures (Myst, Syberia) Text adventure games (Zork, Infocom games) RPGs (Final Fantasy, Everquest, Baldur’s gate) Ontology of adventure games Things Persons Player Items Monsters NPCs Portals Game state: Spatiality Things have locations (places) Places have contents (sets of things) Inventory Equipment Consumables (health, gold, potions, etc.) Key items “Unlock” parts of the game Allowing the narrative to progress Key items Supplies Equipment Places Inventory Rooms An adventure game in Meta Supports Pictures (for point-and-click style) Text output Sound You can decide which of these you want to use Basic ontology Things (have name, location) Places (have name, contents) Player Portals (have name, location, destination) The Thing class Things have: Name Location A string describing the object May be null Place in which the Thing can be found May be null Adjectives List of strings describing the object May be null [define Thing [class [Thing name location] Object adjectives]] [define-method [initialize [Thing x]] [move x x.location]] The Place class Places have Contents A list of Things inside them Sound Sound-loop? If true, the sound plays continuously Image Buffer to play when the user enters the room Can be null if no sound Bitmap to display when the user enters the room Hotspots A list of places in the image the player can click and handlers (procedures to call) for when they’re clicked [define Place [class [Place name] Thing contents hotspots sound sound-loop? image]] [define-method [initialize [Place p]] [call-next-method] [p.contents ← [new ArrayList]]] Trivial example (Based on a randomly chosen picture from my hard drive) One room Two Things in it The Player A group of Nerds Trivial example [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Trivial example Make the Place object [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Trivial example Set up its attributes [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Trivial example Make Player object [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Trivial example Make Nerds object [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Trivial example Open window and start game [define trivial-example [→ [with great-hall = [new Place “the Great Hall”] [great-hall.adjectives ← [list “big” “pink”]] [great-hall.image ← [image-file “Aaron talk.jpg”]] [great-hall.sound ← [sound-file “dog-bark4.wav”]] [great-hall.hotspots ← [list [list 640 320 760 450 [→ [print “Aaron says Mythica was great until they killed the project.”]]]]] [the-player ← [new Player “Emily” great-hall]] [with nerds = [new Nerds null great-hall] [nerds.adjectives ← [list “many”]]] [start-game “Sample game” 800 600 100 100]]]] Moving objects We need to make sure that We make generic procedures for If a thing T says place P is its location Then P lists T in its contents And vice-versa Adding and removing objects from locations Moving objects between locations This allows us to define special behavior for particular kinds of Places and Things [define move [generic-procedure]] [define remove [generic-procedure]] [define add [generic-procedure]] [define-method [move thing place] [remove thing thing.location] [add thing place]] Adding and removing Some Things can have null as their location [define-method [remove thing [null place]] «Do nothing» null] So we need to be careful to specialize the behavior of add and remove [define-method [remove thing [Place place]] [thing.location ← null] [place.contents.Remove thing]] Fortunately, you can specify null as the class of an argument [define-method [add thing [null place]] [thing.location ← null]] [define-method [add thing [Place place]] [thing.location ← place] [place.contents.Add thing]] Describing objects For text adventures We need a way to generate text to describe objects [define description “Returns a string describing the object” [generic-procedure]] [define-method [description [Thing t]] [with type-name = [[type-of t].Name.ToLower] The name of the object (if any) modifiers = [maybe-pad It’s type [comma-separate t.adjectives Its adjectives (if any) false]] name-string = [if [null? t.name] “” Examples [concat “ named ” t.name]] [description [new Cat]] [concat “a ” “a cat” modifiers [description [new Cat “Harry” null]] type-name “a cat named Harry” name-string]]] [with h = [new Cat “Harry” null] We want to base it on [h.adjectives ← [list “big” “black”]] [describe h]] “a big, black cat named Harry” Notes Concat is a procedure that appends strings together Stuff in gray is black magic we haven’t taught you about yet Describing scenes [define-method [view-description [Place p]] [with stuff = [filter [t → [≠ t the-player]] «Everything in the room except the player» p.contents] [concat “You are in ” [description p] “. ” [cond [[= [length stuff] 1] [concat “You see ” [description [first stuff]] “.”]] [[empty? stuff] “”] [else [concat “ You see ” [comma-separate [map description stuff] true] “.”]]]]]] Describing scenes [describe great-hall] “You are in a big, pink place named the Great Hall. You see a many nerds.” Choosing the sound to play [define background-sound “Returns the sound buffer for the background noise of this Place, if any” [generic-procedure]] [define-method [background-sound [Place p]] p.sound] The window code calls background-sound on the player’s location to choose what sound to play Why did we do it this way? Why not just have it play p.sound directly? Choosing the image to show [define view-image [generic-procedure]] [define-method [view-image [Place p]] p.image] Again: why bother with a procedure like this? Handling clicks of the mouse The hotspots of a Place is a field with a list of lists: [list left top right bottom proc] Where: Left and top give the coordinates of the upper-left corner of an area of the image Right and bottom give the coordinates of its lower-right corner Proc gives a procedure to call when the user clicks there But again, you can change the behavior of clicking by Making a new kind of place (i.e. a subclass of Place) and defining a new method for it [define click [generic-procedure]] [define-method [click [Place p] mouseEventArgs] [with x = mouseEventArgs.X y = mouseEventArgs.Y [unless [null? p.hotspots] [for-each [hotspot → [when [and [≥ x [first hotspot]] [≥ y [second hotspot]] [≤ x [third hotspot]] [≤ y [fourth hotspot]]] [[fifth hotspot]]]] p.hotspots]]]]