gamefic 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
 - data/lib/gamefic/action.rb +61 -0
 - data/lib/gamefic/action_ext/container.rb +36 -0
 - data/lib/gamefic/action_ext/inventory.rb +37 -0
 - data/lib/gamefic/action_ext/look.rb +52 -0
 - data/lib/gamefic/action_ext/meta.rb +10 -0
 - data/lib/gamefic/action_ext/traversal.rb +39 -0
 - data/lib/gamefic/base.rb +10 -0
 - data/lib/gamefic/character.rb +72 -0
 - data/lib/gamefic/core_ext/array.rb +40 -0
 - data/lib/gamefic/core_ext/string.rb +42 -0
 - data/lib/gamefic/describable.rb +27 -0
 - data/lib/gamefic/director.rb +133 -0
 - data/lib/gamefic/engine.rb +18 -0
 - data/lib/gamefic/entity.rb +76 -0
 - data/lib/gamefic/entity_ext/container.rb +9 -0
 - data/lib/gamefic/entity_ext/fixture.rb +9 -0
 - data/lib/gamefic/entity_ext/item.rb +11 -0
 - data/lib/gamefic/entity_ext/itemized.rb +7 -0
 - data/lib/gamefic/entity_ext/portable.rb +33 -0
 - data/lib/gamefic/entity_ext/portal.rb +47 -0
 - data/lib/gamefic/entity_ext/room.rb +31 -0
 - data/lib/gamefic/entity_ext/scenery.rb +7 -0
 - data/lib/gamefic/entity_ext/zone.rb +8 -0
 - data/lib/gamefic/keywords.rb +39 -0
 - data/lib/gamefic/node.rb +62 -0
 - data/lib/gamefic/plot.rb +188 -0
 - data/lib/gamefic/query.rb +187 -0
 - data/lib/gamefic/syntax.rb +117 -0
 - data/lib/gamefic/user.rb +64 -0
 - data/lib/gamefic.rb +12 -0
 - metadata +73 -0
 
    
        checksums.yaml
    ADDED
    
    | 
         @@ -0,0 +1,7 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            ---
         
     | 
| 
      
 2 
     | 
    
         
            +
            SHA1:
         
     | 
| 
      
 3 
     | 
    
         
            +
              metadata.gz: d39e0e4c0bdd08258174c87bfe75b1a44ab60643
         
     | 
| 
      
 4 
     | 
    
         
            +
              data.tar.gz: 201eb4941dc0d59a784992c35068a379287d9e0e
         
     | 
| 
      
 5 
     | 
    
         
            +
            SHA512:
         
     | 
| 
      
 6 
     | 
    
         
            +
              metadata.gz: 4939cd6592c098ce8d407b654c38c1ba75583b95b0581c8c834c3d973e9e415d36095317f837888b937e0ceb2231cfc80e003b3c59e9ff0c75b8547af4c8eb98
         
     | 
| 
      
 7 
     | 
    
         
            +
              data.tar.gz: eece7938f58fdbf2746061eb85c2eb932fe0773afd966f544c3cb9c7ac87131da403b339cedd46bdc2ffb07fc4dda5a7626c675ed7b2dc569aa05698ea2a30f0
         
     | 
| 
         @@ -0,0 +1,61 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	class Action
         
     | 
| 
      
 4 
     | 
    
         
            +
            		attr_reader :command
         
     | 
| 
      
 5 
     | 
    
         
            +
            		@@defaults = Array.new
         
     | 
| 
      
 6 
     | 
    
         
            +
            		def initialize(story, command, *queries, &proc)
         
     | 
| 
      
 7 
     | 
    
         
            +
            			if (command.kind_of?(Symbol) == false)
         
     | 
| 
      
 8 
     | 
    
         
            +
            				raise "Action commands must be symbols"
         
     | 
| 
      
 9 
     | 
    
         
            +
            			end
         
     | 
| 
      
 10 
     | 
    
         
            +
            			if (queries.length + 1 != proc.arity) and (queries.length == 0 and proc.arity != -1)
         
     | 
| 
      
 11 
     | 
    
         
            +
            				raise "Number of contexts is not compatible with proc arguments"
         
     | 
| 
      
 12 
     | 
    
         
            +
            			end
         
     | 
| 
      
 13 
     | 
    
         
            +
            			@command = command
         
     | 
| 
      
 14 
     | 
    
         
            +
            			@queries = queries
         
     | 
| 
      
 15 
     | 
    
         
            +
            			@proc = proc
         
     | 
| 
      
 16 
     | 
    
         
            +
            			if story == nil
         
     | 
| 
      
 17 
     | 
    
         
            +
            				@@defaults.push self
         
     | 
| 
      
 18 
     | 
    
         
            +
            			else
         
     | 
| 
      
 19 
     | 
    
         
            +
            				story.send :add_action, self
         
     | 
| 
      
 20 
     | 
    
         
            +
            			end
         
     | 
| 
      
 21 
     | 
    
         
            +
            		end
         
     | 
| 
      
 22 
     | 
    
         
            +
            		def self.defaults
         
     | 
| 
      
 23 
     | 
    
         
            +
            			@@defaults.clone
         
     | 
| 
      
 24 
     | 
    
         
            +
            		end
         
     | 
| 
      
 25 
     | 
    
         
            +
            		def specificity
         
     | 
| 
      
 26 
     | 
    
         
            +
            			spec = 0
         
     | 
| 
      
 27 
     | 
    
         
            +
            			magnitude = 1
         
     | 
| 
      
 28 
     | 
    
         
            +
            			@queries.each { |q|
         
     | 
| 
      
 29 
     | 
    
         
            +
            				if q.kind_of?(Query)
         
     | 
| 
      
 30 
     | 
    
         
            +
            					spec += (q.specificity * magnitude)
         
     | 
| 
      
 31 
     | 
    
         
            +
            				else
         
     | 
| 
      
 32 
     | 
    
         
            +
            					spec += magnitude
         
     | 
| 
      
 33 
     | 
    
         
            +
            				end
         
     | 
| 
      
 34 
     | 
    
         
            +
            				magnitude = magnitude * 10
         
     | 
| 
      
 35 
     | 
    
         
            +
            			}
         
     | 
| 
      
 36 
     | 
    
         
            +
            			return spec
         
     | 
| 
      
 37 
     | 
    
         
            +
            		end
         
     | 
| 
      
 38 
     | 
    
         
            +
            		def key
         
     | 
| 
      
 39 
     | 
    
         
            +
            			@key
         
     | 
| 
      
 40 
     | 
    
         
            +
            		end
         
     | 
| 
      
 41 
     | 
    
         
            +
            		def queries
         
     | 
| 
      
 42 
     | 
    
         
            +
            			@queries
         
     | 
| 
      
 43 
     | 
    
         
            +
            		end
         
     | 
| 
      
 44 
     | 
    
         
            +
            		def proc
         
     | 
| 
      
 45 
     | 
    
         
            +
            			@proc
         
     | 
| 
      
 46 
     | 
    
         
            +
            		end
         
     | 
| 
      
 47 
     | 
    
         
            +
            		private
         
     | 
| 
      
 48 
     | 
    
         
            +
            			def self.explode(entity)
         
     | 
| 
      
 49 
     | 
    
         
            +
            				arr = Array.new
         
     | 
| 
      
 50 
     | 
    
         
            +
            				arr.push entity
         
     | 
| 
      
 51 
     | 
    
         
            +
            				cls = entity.class
         
     | 
| 
      
 52 
     | 
    
         
            +
            				while cls != Object
         
     | 
| 
      
 53 
     | 
    
         
            +
            					arr.push cls
         
     | 
| 
      
 54 
     | 
    
         
            +
            					cls = cls.superclass
         
     | 
| 
      
 55 
     | 
    
         
            +
            				end
         
     | 
| 
      
 56 
     | 
    
         
            +
            				arr.push String
         
     | 
| 
      
 57 
     | 
    
         
            +
            				arr.push nil
         
     | 
| 
      
 58 
     | 
    
         
            +
            			end
         
     | 
| 
      
 59 
     | 
    
         
            +
            	end
         
     | 
| 
      
 60 
     | 
    
         
            +
             
     | 
| 
      
 61 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,36 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	Action.new nil, :look_inside, Query.new(:family, Container) do |actor, container|
         
     | 
| 
      
 4 
     | 
    
         
            +
            		if container.children.length == 0
         
     | 
| 
      
 5 
     | 
    
         
            +
            			actor.tell "You don't find anything."
         
     | 
| 
      
 6 
     | 
    
         
            +
            		else
         
     | 
| 
      
 7 
     | 
    
         
            +
            			actor.tell "#{container.longname} contains: #{container.children.join(', ')}"
         
     | 
| 
      
 8 
     | 
    
         
            +
            		end
         
     | 
| 
      
 9 
     | 
    
         
            +
            	end
         
     | 
| 
      
 10 
     | 
    
         
            +
            	Syntax.new nil, "look inside :container", :look_inside, :container
         
     | 
| 
      
 11 
     | 
    
         
            +
            	Syntax.new nil, "search :container", :look_inside, :container
         
     | 
| 
      
 12 
     | 
    
         
            +
            	Syntax.new nil, "look in :container", :look_inside, :container
         
     | 
| 
      
 13 
     | 
    
         
            +
             
     | 
| 
      
 14 
     | 
    
         
            +
            	Action.new nil, :look_in_at, Query.new(:family, Container), Subquery.new(:children, Entity) do |actor, container, item|
         
     | 
| 
      
 15 
     | 
    
         
            +
            		actor.tell item.description
         
     | 
| 
      
 16 
     | 
    
         
            +
            	end
         
     | 
| 
      
 17 
     | 
    
         
            +
            	Syntax.new nil, "look at :item in :container", :look_in_at, :container, :item
         
     | 
| 
      
 18 
     | 
    
         
            +
            	Syntax.new nil, "look :item in :container", :look_in_at, :container, :item
         
     | 
| 
      
 19 
     | 
    
         
            +
             
     | 
| 
      
 20 
     | 
    
         
            +
            	Action.new nil, :take_from, Query.new(:family, Container), Subquery.new(:children, Item) do |actor, container, item|
         
     | 
| 
      
 21 
     | 
    
         
            +
            		item.parent = actor
         
     | 
| 
      
 22 
     | 
    
         
            +
            		actor.tell "You take #{item.longname} from #{container.longname}."
         
     | 
| 
      
 23 
     | 
    
         
            +
            	end
         
     | 
| 
      
 24 
     | 
    
         
            +
            	Syntax.new nil, "take :item from :container", :take_from, :container, :item
         
     | 
| 
      
 25 
     | 
    
         
            +
            	Syntax.new nil, "get :item from :container", :take_from, :container, :item
         
     | 
| 
      
 26 
     | 
    
         
            +
            	Syntax.new nil, "remove :item from :container", :take_from, :container, :item
         
     | 
| 
      
 27 
     | 
    
         
            +
             
     | 
| 
      
 28 
     | 
    
         
            +
            	Action.new nil, :drop_in, Query.new(:family, Container), Query.new(:children) do |actor, container, item|
         
     | 
| 
      
 29 
     | 
    
         
            +
            		item.parent = container
         
     | 
| 
      
 30 
     | 
    
         
            +
            		actor.tell "You put #{item.longname} in #{container.longname}."
         
     | 
| 
      
 31 
     | 
    
         
            +
            	end
         
     | 
| 
      
 32 
     | 
    
         
            +
            	Syntax.new nil, "drop :item in :container", :drop_in, :container, :item
         
     | 
| 
      
 33 
     | 
    
         
            +
            	Syntax.new nil, "put :item in :container", :drop_in, :container, :item
         
     | 
| 
      
 34 
     | 
    
         
            +
            	Syntax.new nil, "place :item in :container", :drop_in, :container, :item
         
     | 
| 
      
 35 
     | 
    
         
            +
             
     | 
| 
      
 36 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,37 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	Action.new nil, :inventory do |actor|
         
     | 
| 
      
 4 
     | 
    
         
            +
            		if actor.children.length > 0
         
     | 
| 
      
 5 
     | 
    
         
            +
            			actor.tell actor.children.join(', ')
         
     | 
| 
      
 6 
     | 
    
         
            +
            		else
         
     | 
| 
      
 7 
     | 
    
         
            +
            			actor.tell "You aren't carrying anything."
         
     | 
| 
      
 8 
     | 
    
         
            +
            		end
         
     | 
| 
      
 9 
     | 
    
         
            +
            	end
         
     | 
| 
      
 10 
     | 
    
         
            +
            	Syntax.new nil, "i", :inventory
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
            	Action.new nil, :take, Query.new(:siblings, Portable) do |actor, thing|
         
     | 
| 
      
 13 
     | 
    
         
            +
            		thing.parent = actor
         
     | 
| 
      
 14 
     | 
    
         
            +
            		actor.tell "You take #{thing.longname}.", true
         
     | 
| 
      
 15 
     | 
    
         
            +
            	end
         
     | 
| 
      
 16 
     | 
    
         
            +
             
     | 
| 
      
 17 
     | 
    
         
            +
            	Action.new nil, :take, Query.new(:siblings) do |actor, thing|
         
     | 
| 
      
 18 
     | 
    
         
            +
            		actor.tell "You can't carry #{thing.longname}."
         
     | 
| 
      
 19 
     | 
    
         
            +
            	end
         
     | 
| 
      
 20 
     | 
    
         
            +
             
     | 
| 
      
 21 
     | 
    
         
            +
            	Action.new nil, :take, String do |actor, thing|
         
     | 
| 
      
 22 
     | 
    
         
            +
            		actor.tell "You don't see anything called \"#{thing}\" here."
         
     | 
| 
      
 23 
     | 
    
         
            +
            	end
         
     | 
| 
      
 24 
     | 
    
         
            +
             
     | 
| 
      
 25 
     | 
    
         
            +
            	Action.new nil, :drop, Query.new(:children) do |actor, thing|
         
     | 
| 
      
 26 
     | 
    
         
            +
            		thing.parent = actor.parent
         
     | 
| 
      
 27 
     | 
    
         
            +
            		actor.tell "You drop #{thing.longname}.", true
         
     | 
| 
      
 28 
     | 
    
         
            +
            	end
         
     | 
| 
      
 29 
     | 
    
         
            +
             
     | 
| 
      
 30 
     | 
    
         
            +
            	Syntax.new nil, "get :thing", :take, :thing
         
     | 
| 
      
 31 
     | 
    
         
            +
            	Syntax.new nil, "pick :thing up", :take, :thing
         
     | 
| 
      
 32 
     | 
    
         
            +
            	Syntax.new nil, "pick up :thing", :take, :thing
         
     | 
| 
      
 33 
     | 
    
         
            +
             
     | 
| 
      
 34 
     | 
    
         
            +
            	Syntax.new nil, "put down :thing", :drop, :thing
         
     | 
| 
      
 35 
     | 
    
         
            +
            	Syntax.new nil, "put :thing down", :drop, :thing
         
     | 
| 
      
 36 
     | 
    
         
            +
             
     | 
| 
      
 37 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,52 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	Action.new nil, :look do |actor|
         
     | 
| 
      
 4 
     | 
    
         
            +
            		actor.perform "itemize room full"
         
     | 
| 
      
 5 
     | 
    
         
            +
            	end
         
     | 
| 
      
 6 
     | 
    
         
            +
             
     | 
| 
      
 7 
     | 
    
         
            +
            	Action.new nil, :look_around do |actor|
         
     | 
| 
      
 8 
     | 
    
         
            +
            		actor.perform "look"
         
     | 
| 
      
 9 
     | 
    
         
            +
            	end
         
     | 
| 
      
 10 
     | 
    
         
            +
             
     | 
| 
      
 11 
     | 
    
         
            +
            	Action.new nil, :itemize_room, Query.new(:string) do |actor, option|
         
     | 
| 
      
 12 
     | 
    
         
            +
            		actor.tell "#{actor.parent.longname.cap_first}"
         
     | 
| 
      
 13 
     | 
    
         
            +
            		if option == "full"
         
     | 
| 
      
 14 
     | 
    
         
            +
            			actor.tell actor.parent.description
         
     | 
| 
      
 15 
     | 
    
         
            +
            		end
         
     | 
| 
      
 16 
     | 
    
         
            +
            		chars = actor.parent.children.that_are(Character) - [actor]
         
     | 
| 
      
 17 
     | 
    
         
            +
            		if chars.length > 0
         
     | 
| 
      
 18 
     | 
    
         
            +
            			actor.tell "Others here: #{chars.join(", ")}"
         
     | 
| 
      
 19 
     | 
    
         
            +
            		end
         
     | 
| 
      
 20 
     | 
    
         
            +
            		#items = actor.parent.children.that_are(Itemized) - [chars] - [actor] - actor.parent.children.that_are(Portal)
         
     | 
| 
      
 21 
     | 
    
         
            +
            		items = actor.parent.children.that_are(Itemized)
         
     | 
| 
      
 22 
     | 
    
         
            +
            		if items.length > 0
         
     | 
| 
      
 23 
     | 
    
         
            +
            			actor.tell "Visible items: #{items.join(", ")}"
         
     | 
| 
      
 24 
     | 
    
         
            +
            		end
         
     | 
| 
      
 25 
     | 
    
         
            +
            		portals = actor.parent.children.that_are(Portal)
         
     | 
| 
      
 26 
     | 
    
         
            +
            		if portals.length > 0
         
     | 
| 
      
 27 
     | 
    
         
            +
            			actor.tell "Obvious exits: #{portals.join(', ')}"
         
     | 
| 
      
 28 
     | 
    
         
            +
            		else
         
     | 
| 
      
 29 
     | 
    
         
            +
            			actor.tell "Obvious exits: none"	
         
     | 
| 
      
 30 
     | 
    
         
            +
            		end
         
     | 
| 
      
 31 
     | 
    
         
            +
            	end
         
     | 
| 
      
 32 
     | 
    
         
            +
            	Syntax.new nil, "itemize room", :itemize_room, "short"
         
     | 
| 
      
 33 
     | 
    
         
            +
            	Syntax.new nil, "itemize room :option", :itemize_room, :option
         
     | 
| 
      
 34 
     | 
    
         
            +
             
     | 
| 
      
 35 
     | 
    
         
            +
            	Action.new nil, :look, Query.new(:family) do |actor, thing|
         
     | 
| 
      
 36 
     | 
    
         
            +
            		actor.tell thing.description
         
     | 
| 
      
 37 
     | 
    
         
            +
            	end
         
     | 
| 
      
 38 
     | 
    
         
            +
             
     | 
| 
      
 39 
     | 
    
         
            +
            	Action.new nil, :look, Query.new(:parent) do |actor, thing|
         
     | 
| 
      
 40 
     | 
    
         
            +
            		actor.perform "look"
         
     | 
| 
      
 41 
     | 
    
         
            +
            	end
         
     | 
| 
      
 42 
     | 
    
         
            +
             
     | 
| 
      
 43 
     | 
    
         
            +
            	Action.new nil, :look, String do |actor, string|
         
     | 
| 
      
 44 
     | 
    
         
            +
            		actor.tell "You don't see any \"#{string}\" here."
         
     | 
| 
      
 45 
     | 
    
         
            +
            	end
         
     | 
| 
      
 46 
     | 
    
         
            +
             
     | 
| 
      
 47 
     | 
    
         
            +
            	Syntax.new nil, "look at :thing", :look, :thing
         
     | 
| 
      
 48 
     | 
    
         
            +
            	Syntax.new nil, "examine :thing", :look, :thing
         
     | 
| 
      
 49 
     | 
    
         
            +
            	Syntax.new nil, "exam :thing", :look, :thing
         
     | 
| 
      
 50 
     | 
    
         
            +
            	Syntax.new nil, "x :thing", :look, :thing
         
     | 
| 
      
 51 
     | 
    
         
            +
             
     | 
| 
      
 52 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,39 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	Action.new nil, :go, Query.new(:siblings, Portal) do |actor, portal|
         
     | 
| 
      
 4 
     | 
    
         
            +
            		actor.parent = portal.destination
         
     | 
| 
      
 5 
     | 
    
         
            +
            		actor.tell "You go #{portal.name}."
         
     | 
| 
      
 6 
     | 
    
         
            +
            		actor.perform "itemize room"
         
     | 
| 
      
 7 
     | 
    
         
            +
            	end
         
     | 
| 
      
 8 
     | 
    
         
            +
             
     | 
| 
      
 9 
     | 
    
         
            +
            	Action.new nil, :go, String do |actor, string|
         
     | 
| 
      
 10 
     | 
    
         
            +
            		actor.tell "You don't see any exit \"#{string}\" from here."
         
     | 
| 
      
 11 
     | 
    
         
            +
            	end
         
     | 
| 
      
 12 
     | 
    
         
            +
             
     | 
| 
      
 13 
     | 
    
         
            +
            	Action.new nil, :go do |actor|
         
     | 
| 
      
 14 
     | 
    
         
            +
            		actor.tell "Where do you want to go?"
         
     | 
| 
      
 15 
     | 
    
         
            +
            	end
         
     | 
| 
      
 16 
     | 
    
         
            +
             
     | 
| 
      
 17 
     | 
    
         
            +
            	Syntax.new nil, "north", :go, "north"
         
     | 
| 
      
 18 
     | 
    
         
            +
            	Syntax.new nil, "south", :go, "south"
         
     | 
| 
      
 19 
     | 
    
         
            +
            	Syntax.new nil, "west", :go, "west"
         
     | 
| 
      
 20 
     | 
    
         
            +
            	Syntax.new nil, "east", :go, "east"
         
     | 
| 
      
 21 
     | 
    
         
            +
            	Syntax.new nil, "up", :go, "up"
         
     | 
| 
      
 22 
     | 
    
         
            +
            	Syntax.new nil, "down", :go, "down"
         
     | 
| 
      
 23 
     | 
    
         
            +
            	Syntax.new nil, "northwest", :go, "northwest"
         
     | 
| 
      
 24 
     | 
    
         
            +
            	Syntax.new nil, "northeast", :go, "northeast"
         
     | 
| 
      
 25 
     | 
    
         
            +
            	Syntax.new nil, "southwest", :go, "southwest"
         
     | 
| 
      
 26 
     | 
    
         
            +
            	Syntax.new nil, "southeast", :go, "southeast"
         
     | 
| 
      
 27 
     | 
    
         
            +
             
     | 
| 
      
 28 
     | 
    
         
            +
            	Syntax.new nil, "n", :go, "north"
         
     | 
| 
      
 29 
     | 
    
         
            +
            	Syntax.new nil, "s", :go, "south"
         
     | 
| 
      
 30 
     | 
    
         
            +
            	Syntax.new nil, "w", :go, "west"
         
     | 
| 
      
 31 
     | 
    
         
            +
            	Syntax.new nil, "e", :go, "east"
         
     | 
| 
      
 32 
     | 
    
         
            +
            	Syntax.new nil, "u", :go, "up"
         
     | 
| 
      
 33 
     | 
    
         
            +
            	Syntax.new nil, "d", :go, "down"
         
     | 
| 
      
 34 
     | 
    
         
            +
            	Syntax.new nil, "nw", :go, "northwest"
         
     | 
| 
      
 35 
     | 
    
         
            +
            	Syntax.new nil, "ne", :go, "northeast"
         
     | 
| 
      
 36 
     | 
    
         
            +
            	Syntax.new nil, "sw", :go, "southwest"
         
     | 
| 
      
 37 
     | 
    
         
            +
            	Syntax.new nil, "se", :go, "southeast"
         
     | 
| 
      
 38 
     | 
    
         
            +
             
     | 
| 
      
 39 
     | 
    
         
            +
            end
         
     | 
    
        data/lib/gamefic/base.rb
    ADDED
    
    
| 
         @@ -0,0 +1,72 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	class Character < Entity
         
     | 
| 
      
 4 
     | 
    
         
            +
            		attr_reader :state, :queue, :user
         
     | 
| 
      
 5 
     | 
    
         
            +
            		def post_initialize
         
     | 
| 
      
 6 
     | 
    
         
            +
            			@state = CharacterState.new(self)
         
     | 
| 
      
 7 
     | 
    
         
            +
            			@queue = Array.new
         
     | 
| 
      
 8 
     | 
    
         
            +
            		end
         
     | 
| 
      
 9 
     | 
    
         
            +
            		def connect(user)
         
     | 
| 
      
 10 
     | 
    
         
            +
            			@user = user
         
     | 
| 
      
 11 
     | 
    
         
            +
            		end
         
     | 
| 
      
 12 
     | 
    
         
            +
            		def disconnect
         
     | 
| 
      
 13 
     | 
    
         
            +
            			# TODO: We might need some cleanup here. Like, move the character out of the game, or set a timeout to allow dropped users to reconnect... figure it out.
         
     | 
| 
      
 14 
     | 
    
         
            +
            			@user = nil
         
     | 
| 
      
 15 
     | 
    
         
            +
            		end
         
     | 
| 
      
 16 
     | 
    
         
            +
            		def perform(command)
         
     | 
| 
      
 17 
     | 
    
         
            +
            			#if command != nil
         
     | 
| 
      
 18 
     | 
    
         
            +
            			#	@queue.push command
         
     | 
| 
      
 19 
     | 
    
         
            +
            			#end
         
     | 
| 
      
 20 
     | 
    
         
            +
            			if state.busy? == false
         
     | 
| 
      
 21 
     | 
    
         
            +
            				Director.dispatch(self, command)
         
     | 
| 
      
 22 
     | 
    
         
            +
            			else
         
     | 
| 
      
 23 
     | 
    
         
            +
            				@queue.push command
         
     | 
| 
      
 24 
     | 
    
         
            +
            			end
         
     | 
| 
      
 25 
     | 
    
         
            +
            		end
         
     | 
| 
      
 26 
     | 
    
         
            +
            		#def inject(command)
         
     | 
| 
      
 27 
     | 
    
         
            +
            		#	Director.dispatch(self, command)
         
     | 
| 
      
 28 
     | 
    
         
            +
            		#end
         
     | 
| 
      
 29 
     | 
    
         
            +
            		def tell(message, refresh = false)
         
     | 
| 
      
 30 
     | 
    
         
            +
            			if user != nil and message.to_s != ''
         
     | 
| 
      
 31 
     | 
    
         
            +
            				user.stream.send "#{message}\n"
         
     | 
| 
      
 32 
     | 
    
         
            +
            				if (refresh == true)
         
     | 
| 
      
 33 
     | 
    
         
            +
            					user.refresh
         
     | 
| 
      
 34 
     | 
    
         
            +
            				end
         
     | 
| 
      
 35 
     | 
    
         
            +
            			end
         
     | 
| 
      
 36 
     | 
    
         
            +
            		end
         
     | 
| 
      
 37 
     | 
    
         
            +
            		def state=(new_state)
         
     | 
| 
      
 38 
     | 
    
         
            +
            			@state = new_state
         
     | 
| 
      
 39 
     | 
    
         
            +
            		end
         
     | 
| 
      
 40 
     | 
    
         
            +
            		def destroy
         
     | 
| 
      
 41 
     | 
    
         
            +
            			if @user != nil
         
     | 
| 
      
 42 
     | 
    
         
            +
            				@user.quit
         
     | 
| 
      
 43 
     | 
    
         
            +
            			end
         
     | 
| 
      
 44 
     | 
    
         
            +
            			super
         
     | 
| 
      
 45 
     | 
    
         
            +
            		end
         
     | 
| 
      
 46 
     | 
    
         
            +
            		def update
         
     | 
| 
      
 47 
     | 
    
         
            +
            			super
         
     | 
| 
      
 48 
     | 
    
         
            +
            			@state.update
         
     | 
| 
      
 49 
     | 
    
         
            +
            		end
         
     | 
| 
      
 50 
     | 
    
         
            +
            	end
         
     | 
| 
      
 51 
     | 
    
         
            +
            	class CharacterState
         
     | 
| 
      
 52 
     | 
    
         
            +
            		def initialize(character)
         
     | 
| 
      
 53 
     | 
    
         
            +
            			@character = character
         
     | 
| 
      
 54 
     | 
    
         
            +
            			post_initialize
         
     | 
| 
      
 55 
     | 
    
         
            +
            		end
         
     | 
| 
      
 56 
     | 
    
         
            +
            		def post_initialize
         
     | 
| 
      
 57 
     | 
    
         
            +
            			# TODO: Required by subclasses?
         
     | 
| 
      
 58 
     | 
    
         
            +
            		end
         
     | 
| 
      
 59 
     | 
    
         
            +
            		def busy?
         
     | 
| 
      
 60 
     | 
    
         
            +
            			false
         
     | 
| 
      
 61 
     | 
    
         
            +
            		end
         
     | 
| 
      
 62 
     | 
    
         
            +
            		def update
         
     | 
| 
      
 63 
     | 
    
         
            +
            			while (line = @character.queue.shift)
         
     | 
| 
      
 64 
     | 
    
         
            +
            				@character.perform line
         
     | 
| 
      
 65 
     | 
    
         
            +
            				if @character.state != self
         
     | 
| 
      
 66 
     | 
    
         
            +
            					break
         
     | 
| 
      
 67 
     | 
    
         
            +
            				end
         
     | 
| 
      
 68 
     | 
    
         
            +
            			end
         
     | 
| 
      
 69 
     | 
    
         
            +
            		end
         
     | 
| 
      
 70 
     | 
    
         
            +
            	end
         
     | 
| 
      
 71 
     | 
    
         
            +
             
     | 
| 
      
 72 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,40 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            class Array
         
     | 
| 
      
 2 
     | 
    
         
            +
            	def that_are(cls)
         
     | 
| 
      
 3 
     | 
    
         
            +
            		if (cls.kind_of?(Class) or cls.kind_of?(Module))
         
     | 
| 
      
 4 
     | 
    
         
            +
            			return self.clone.delete_if { |i| i.kind_of?(cls) == false }
         
     | 
| 
      
 5 
     | 
    
         
            +
            		else
         
     | 
| 
      
 6 
     | 
    
         
            +
            			if self.include?(cls)
         
     | 
| 
      
 7 
     | 
    
         
            +
            				return [cls]
         
     | 
| 
      
 8 
     | 
    
         
            +
            			end
         
     | 
| 
      
 9 
     | 
    
         
            +
            			return Array.new
         
     | 
| 
      
 10 
     | 
    
         
            +
            		end
         
     | 
| 
      
 11 
     | 
    
         
            +
            	end
         
     | 
| 
      
 12 
     | 
    
         
            +
            	def that_are_not(cls)
         
     | 
| 
      
 13 
     | 
    
         
            +
            		if (cls.kind_of?(Class) or cls.kind_of?(Module))
         
     | 
| 
      
 14 
     | 
    
         
            +
            			return self.clone.delete_if { |i| i.kind_of?(cls) == true }
         
     | 
| 
      
 15 
     | 
    
         
            +
            		else
         
     | 
| 
      
 16 
     | 
    
         
            +
            			return self.clone - [cls]
         
     | 
| 
      
 17 
     | 
    
         
            +
            		end
         
     | 
| 
      
 18 
     | 
    
         
            +
            	end
         
     | 
| 
      
 19 
     | 
    
         
            +
            	def random
         
     | 
| 
      
 20 
     | 
    
         
            +
            		return self[rand(self.length)]
         
     | 
| 
      
 21 
     | 
    
         
            +
            	end
         
     | 
| 
      
 22 
     | 
    
         
            +
            	def shuffle
         
     | 
| 
      
 23 
     | 
    
         
            +
            		self.sort { |a, b|
         
     | 
| 
      
 24 
     | 
    
         
            +
            			rand(3) <=> rand(3)
         
     | 
| 
      
 25 
     | 
    
         
            +
            		}
         
     | 
| 
      
 26 
     | 
    
         
            +
            	end
         
     | 
| 
      
 27 
     | 
    
         
            +
            	def shuffle!
         
     | 
| 
      
 28 
     | 
    
         
            +
            		self.sort! { |a, b|
         
     | 
| 
      
 29 
     | 
    
         
            +
            			rand(3) <=> rand(3)
         
     | 
| 
      
 30 
     | 
    
         
            +
            		}
         
     | 
| 
      
 31 
     | 
    
         
            +
            	end
         
     | 
| 
      
 32 
     | 
    
         
            +
            	def join_and(sep = ', ', andSep = ' and ', serial = true)
         
     | 
| 
      
 33 
     | 
    
         
            +
            		if self.length < 3
         
     | 
| 
      
 34 
     | 
    
         
            +
            			self.join(andSep)
         
     | 
| 
      
 35 
     | 
    
         
            +
            		else
         
     | 
| 
      
 36 
     | 
    
         
            +
            			start = self - [self.last]
         
     | 
| 
      
 37 
     | 
    
         
            +
            			start.join(sep) + "#{serial ? sep.strip : ''}#{andSep}#{self.last}"
         
     | 
| 
      
 38 
     | 
    
         
            +
            		end
         
     | 
| 
      
 39 
     | 
    
         
            +
            	end
         
     | 
| 
      
 40 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,42 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            class String
         
     | 
| 
      
 2 
     | 
    
         
            +
            	def capitalize_first
         
     | 
| 
      
 3 
     | 
    
         
            +
            		"#{self[0,1].upcase}#{self[1,self.length]}"
         
     | 
| 
      
 4 
     | 
    
         
            +
            	end
         
     | 
| 
      
 5 
     | 
    
         
            +
            	def cap_first
         
     | 
| 
      
 6 
     | 
    
         
            +
            		self.capitalize_first
         
     | 
| 
      
 7 
     | 
    
         
            +
            	end
         
     | 
| 
      
 8 
     | 
    
         
            +
              def specify
         
     | 
| 
      
 9 
     | 
    
         
            +
                if self[0,2] == 'a ' or self[0,3] == 'an '
         
     | 
| 
      
 10 
     | 
    
         
            +
                  "the #{self.split(' ').shift.join(' ')}"
         
     | 
| 
      
 11 
     | 
    
         
            +
                end
         
     | 
| 
      
 12 
     | 
    
         
            +
                if self[0,2] == 'A ' or self[0,3] == 'An '
         
     | 
| 
      
 13 
     | 
    
         
            +
                  "The #{self.split(' ').shift.join(' ')}"
         
     | 
| 
      
 14 
     | 
    
         
            +
                end
         
     | 
| 
      
 15 
     | 
    
         
            +
                "#{self}"
         
     | 
| 
      
 16 
     | 
    
         
            +
              end
         
     | 
| 
      
 17 
     | 
    
         
            +
            	def terminalize
         
     | 
| 
      
 18 
     | 
    
         
            +
            		output = ''
         
     | 
| 
      
 19 
     | 
    
         
            +
            		lines = self.split("\n")
         
     | 
| 
      
 20 
     | 
    
         
            +
            		lines.each { |line|
         
     | 
| 
      
 21 
     | 
    
         
            +
            			if line.size > 79
         
     | 
| 
      
 22 
     | 
    
         
            +
            				while (line.size > 79)
         
     | 
| 
      
 23 
     | 
    
         
            +
            					offset = line.rindex(/[\s\W]/, 79)
         
     | 
| 
      
 24 
     | 
    
         
            +
            					if (offset == 0 or offset == nil)
         
     | 
| 
      
 25 
     | 
    
         
            +
            						output = output + line + "\n"
         
     | 
| 
      
 26 
     | 
    
         
            +
            						line = ''
         
     | 
| 
      
 27 
     | 
    
         
            +
            					else
         
     | 
| 
      
 28 
     | 
    
         
            +
            						output = output + line[0,offset + 1] + "\n"
         
     | 
| 
      
 29 
     | 
    
         
            +
            						line = line[offset + 1, line.size - offset]
         
     | 
| 
      
 30 
     | 
    
         
            +
            					end
         
     | 
| 
      
 31 
     | 
    
         
            +
            				end
         
     | 
| 
      
 32 
     | 
    
         
            +
            				output = output + line + "\n"
         
     | 
| 
      
 33 
     | 
    
         
            +
            			else
         
     | 
| 
      
 34 
     | 
    
         
            +
            				output = output + line + "\n"
         
     | 
| 
      
 35 
     | 
    
         
            +
            			end
         
     | 
| 
      
 36 
     | 
    
         
            +
            		}
         
     | 
| 
      
 37 
     | 
    
         
            +
            		return output.strip
         
     | 
| 
      
 38 
     | 
    
         
            +
            	end
         
     | 
| 
      
 39 
     | 
    
         
            +
            	def split_words
         
     | 
| 
      
 40 
     | 
    
         
            +
            		self.gsub(/ +/, ' ').strip.split
         
     | 
| 
      
 41 
     | 
    
         
            +
            	end
         
     | 
| 
      
 42 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,27 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require "gamefic/keywords"
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 4 
     | 
    
         
            +
             
     | 
| 
      
 5 
     | 
    
         
            +
            	module Describable
         
     | 
| 
      
 6 
     | 
    
         
            +
            		attr_accessor :name, :longname, :synonyms
         
     | 
| 
      
 7 
     | 
    
         
            +
            		def keywords
         
     | 
| 
      
 8 
     | 
    
         
            +
            			Keywords.new "#{name} #{longname} #{synonyms}"
         
     | 
| 
      
 9 
     | 
    
         
            +
            		end
         
     | 
| 
      
 10 
     | 
    
         
            +
            		def keywords=(value)
         
     | 
| 
      
 11 
     | 
    
         
            +
            			@keywords = value
         
     | 
| 
      
 12 
     | 
    
         
            +
            		end
         
     | 
| 
      
 13 
     | 
    
         
            +
            		def longname
         
     | 
| 
      
 14 
     | 
    
         
            +
            			@longname.to_s != '' ? @longname : name
         
     | 
| 
      
 15 
     | 
    
         
            +
            		end
         
     | 
| 
      
 16 
     | 
    
         
            +
            		def longname=(value)
         
     | 
| 
      
 17 
     | 
    
         
            +
            			@longname = value
         
     | 
| 
      
 18 
     | 
    
         
            +
            		end
         
     | 
| 
      
 19 
     | 
    
         
            +
            		def description
         
     | 
| 
      
 20 
     | 
    
         
            +
            			@description.to_s != '' ? @description : "Nothing special."
         
     | 
| 
      
 21 
     | 
    
         
            +
            		end
         
     | 
| 
      
 22 
     | 
    
         
            +
            		def description=(value)
         
     | 
| 
      
 23 
     | 
    
         
            +
            			@description = value
         
     | 
| 
      
 24 
     | 
    
         
            +
            		end
         
     | 
| 
      
 25 
     | 
    
         
            +
            	end
         
     | 
| 
      
 26 
     | 
    
         
            +
             
     | 
| 
      
 27 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,133 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	class Director
         
     | 
| 
      
 4 
     | 
    
         
            +
            		def self.dispatch(actor, command)
         
     | 
| 
      
 5 
     | 
    
         
            +
            			command.strip!
         
     | 
| 
      
 6 
     | 
    
         
            +
            			handlers = Syntax.match(command, actor.plot.syntaxes)
         
     | 
| 
      
 7 
     | 
    
         
            +
            			options = Array.new
         
     | 
| 
      
 8 
     | 
    
         
            +
            			handlers.each { |handler|
         
     | 
| 
      
 9 
     | 
    
         
            +
            				actions = actor.plot.commands[handler.command]
         
     | 
| 
      
 10 
     | 
    
         
            +
            				if actions != nil
         
     | 
| 
      
 11 
     | 
    
         
            +
            					actions.each { |action|
         
     | 
| 
      
 12 
     | 
    
         
            +
            						orders = bind_contexts_in_result(actor, handler, action)
         
     | 
| 
      
 13 
     | 
    
         
            +
            						orders.each { |order|
         
     | 
| 
      
 14 
     | 
    
         
            +
            							args = Array.new
         
     | 
| 
      
 15 
     | 
    
         
            +
            							args.push actor
         
     | 
| 
      
 16 
     | 
    
         
            +
            							order.arguments.each { |a|
         
     | 
| 
      
 17 
     | 
    
         
            +
            								if a.length > 1
         
     | 
| 
      
 18 
     | 
    
         
            +
            									longnames = Array.new
         
     | 
| 
      
 19 
     | 
    
         
            +
            									a.each { |b|
         
     | 
| 
      
 20 
     | 
    
         
            +
            										longnames.push b.longname
         
     | 
| 
      
 21 
     | 
    
         
            +
            									}
         
     | 
| 
      
 22 
     | 
    
         
            +
            									actor.tell "I don't know which you mean: #{longnames.join(', ')}"
         
     | 
| 
      
 23 
     | 
    
         
            +
            									return
         
     | 
| 
      
 24 
     | 
    
         
            +
            								end
         
     | 
| 
      
 25 
     | 
    
         
            +
            								args.push a[0]
         
     | 
| 
      
 26 
     | 
    
         
            +
            							}
         
     | 
| 
      
 27 
     | 
    
         
            +
            							options.push [order.action.proc, args]
         
     | 
| 
      
 28 
     | 
    
         
            +
            						}
         
     | 
| 
      
 29 
     | 
    
         
            +
            					}
         
     | 
| 
      
 30 
     | 
    
         
            +
            				end
         
     | 
| 
      
 31 
     | 
    
         
            +
            			}
         
     | 
| 
      
 32 
     | 
    
         
            +
            			options.push([
         
     | 
| 
      
 33 
     | 
    
         
            +
            				Proc.new { |actor|
         
     | 
| 
      
 34 
     | 
    
         
            +
            					actor.tell "I don't know what you mean by '#{command}.'"
         
     | 
| 
      
 35 
     | 
    
         
            +
            				}, [actor], -1
         
     | 
| 
      
 36 
     | 
    
         
            +
            			])
         
     | 
| 
      
 37 
     | 
    
         
            +
            			del = Delegate.new(options)
         
     | 
| 
      
 38 
     | 
    
         
            +
            			del.execute
         
     | 
| 
      
 39 
     | 
    
         
            +
            		end
         
     | 
| 
      
 40 
     | 
    
         
            +
            		private
         
     | 
| 
      
 41 
     | 
    
         
            +
            		def self.bind_contexts_in_result(actor, handler, action)
         
     | 
| 
      
 42 
     | 
    
         
            +
            			objects = Array.new
         
     | 
| 
      
 43 
     | 
    
         
            +
            			valid = true
         
     | 
| 
      
 44 
     | 
    
         
            +
            			prepared = Array.new
         
     | 
| 
      
 45 
     | 
    
         
            +
            			arguments = handler.arguments.clone
         
     | 
| 
      
 46 
     | 
    
         
            +
            			action.queries.each { |context|
         
     | 
| 
      
 47 
     | 
    
         
            +
            				arg = arguments.shift
         
     | 
| 
      
 48 
     | 
    
         
            +
            				if arg == nil or arg == ''
         
     | 
| 
      
 49 
     | 
    
         
            +
            					valid = false
         
     | 
| 
      
 50 
     | 
    
         
            +
            					next
         
     | 
| 
      
 51 
     | 
    
         
            +
            				end
         
     | 
| 
      
 52 
     | 
    
         
            +
            				if context == String
         
     | 
| 
      
 53 
     | 
    
         
            +
            					prepared.push [arg]
         
     | 
| 
      
 54 
     | 
    
         
            +
            				elsif context.kind_of?(Query)
         
     | 
| 
      
 55 
     | 
    
         
            +
            					if context.kind_of?(Subquery)
         
     | 
| 
      
 56 
     | 
    
         
            +
            						last = prepared.last
         
     | 
| 
      
 57 
     | 
    
         
            +
            						if last == nil or last.length > 1
         
     | 
| 
      
 58 
     | 
    
         
            +
            							valid = false
         
     | 
| 
      
 59 
     | 
    
         
            +
            							next
         
     | 
| 
      
 60 
     | 
    
         
            +
            						end
         
     | 
| 
      
 61 
     | 
    
         
            +
            						result = context.execute(last[0], arg)
         
     | 
| 
      
 62 
     | 
    
         
            +
            					else
         
     | 
| 
      
 63 
     | 
    
         
            +
            						result = context.execute(actor, arg)
         
     | 
| 
      
 64 
     | 
    
         
            +
            					end
         
     | 
| 
      
 65 
     | 
    
         
            +
            					if result.objects.length == 0
         
     | 
| 
      
 66 
     | 
    
         
            +
            						valid = false
         
     | 
| 
      
 67 
     | 
    
         
            +
            						next
         
     | 
| 
      
 68 
     | 
    
         
            +
            					else
         
     | 
| 
      
 69 
     | 
    
         
            +
            						prepared.push result.objects
         
     | 
| 
      
 70 
     | 
    
         
            +
            						if result.remainder
         
     | 
| 
      
 71 
     | 
    
         
            +
            							arguments.push result.remainder
         
     | 
| 
      
 72 
     | 
    
         
            +
            						end
         
     | 
| 
      
 73 
     | 
    
         
            +
            					end
         
     | 
| 
      
 74 
     | 
    
         
            +
            				else
         
     | 
| 
      
 75 
     | 
    
         
            +
            					# TODO: Better message
         
     | 
| 
      
 76 
     | 
    
         
            +
            					raise "Invalid object"
         
     | 
| 
      
 77 
     | 
    
         
            +
            				end
         
     | 
| 
      
 78 
     | 
    
         
            +
            			}
         
     | 
| 
      
 79 
     | 
    
         
            +
            			if valid == true
         
     | 
| 
      
 80 
     | 
    
         
            +
            				prepared.each { |p|
         
     | 
| 
      
 81 
     | 
    
         
            +
            					p.uniq!
         
     | 
| 
      
 82 
     | 
    
         
            +
            				}
         
     | 
| 
      
 83 
     | 
    
         
            +
            				objects.push Order.new(action, prepared)
         
     | 
| 
      
 84 
     | 
    
         
            +
            			end
         
     | 
| 
      
 85 
     | 
    
         
            +
            			return objects
         
     | 
| 
      
 86 
     | 
    
         
            +
            		end
         
     | 
| 
      
 87 
     | 
    
         
            +
            	end
         
     | 
| 
      
 88 
     | 
    
         
            +
            	
         
     | 
| 
      
 89 
     | 
    
         
            +
            	class Director
         
     | 
| 
      
 90 
     | 
    
         
            +
            		class Delegate
         
     | 
| 
      
 91 
     | 
    
         
            +
            			@@delegation_stack = Array.new
         
     | 
| 
      
 92 
     | 
    
         
            +
            			def initialize(options)
         
     | 
| 
      
 93 
     | 
    
         
            +
            				@options = options
         
     | 
| 
      
 94 
     | 
    
         
            +
            			end
         
     | 
| 
      
 95 
     | 
    
         
            +
            			def execute
         
     | 
| 
      
 96 
     | 
    
         
            +
            				@@delegation_stack.push @options
         
     | 
| 
      
 97 
     | 
    
         
            +
            				if @options.length > 0
         
     | 
| 
      
 98 
     | 
    
         
            +
            					opt = @options.shift
         
     | 
| 
      
 99 
     | 
    
         
            +
            					if opt[1].length == 1
         
     | 
| 
      
 100 
     | 
    
         
            +
            						opt[0].call(opt[1][0])
         
     | 
| 
      
 101 
     | 
    
         
            +
            					else
         
     | 
| 
      
 102 
     | 
    
         
            +
            						opt[0].call(opt[1])
         
     | 
| 
      
 103 
     | 
    
         
            +
            					end
         
     | 
| 
      
 104 
     | 
    
         
            +
            				end
         
     | 
| 
      
 105 
     | 
    
         
            +
            				@@delegation_stack.pop
         
     | 
| 
      
 106 
     | 
    
         
            +
            			end
         
     | 
| 
      
 107 
     | 
    
         
            +
            			def self.passthru
         
     | 
| 
      
 108 
     | 
    
         
            +
            				if @@delegation_stack.last != nil
         
     | 
| 
      
 109 
     | 
    
         
            +
            					if @@delegation_stack.last.length > 0
         
     | 
| 
      
 110 
     | 
    
         
            +
            						opt = @@delegation_stack.last.shift
         
     | 
| 
      
 111 
     | 
    
         
            +
            						if opt[1].length == 1
         
     | 
| 
      
 112 
     | 
    
         
            +
            							opt[0].call(opt[1][0])
         
     | 
| 
      
 113 
     | 
    
         
            +
            						else
         
     | 
| 
      
 114 
     | 
    
         
            +
            							opt[0].call(opt[1])
         
     | 
| 
      
 115 
     | 
    
         
            +
            						end
         
     | 
| 
      
 116 
     | 
    
         
            +
            					end
         
     | 
| 
      
 117 
     | 
    
         
            +
            				end
         
     | 
| 
      
 118 
     | 
    
         
            +
            			end
         
     | 
| 
      
 119 
     | 
    
         
            +
            		end
         
     | 
| 
      
 120 
     | 
    
         
            +
            		class Order
         
     | 
| 
      
 121 
     | 
    
         
            +
            			attr_reader :action, :arguments
         
     | 
| 
      
 122 
     | 
    
         
            +
            			def initialize(action, arguments)
         
     | 
| 
      
 123 
     | 
    
         
            +
            				@action = action
         
     | 
| 
      
 124 
     | 
    
         
            +
            				@arguments = arguments
         
     | 
| 
      
 125 
     | 
    
         
            +
            			end
         
     | 
| 
      
 126 
     | 
    
         
            +
            		end
         
     | 
| 
      
 127 
     | 
    
         
            +
            	end
         
     | 
| 
      
 128 
     | 
    
         
            +
             
     | 
| 
      
 129 
     | 
    
         
            +
            	def self.passthru
         
     | 
| 
      
 130 
     | 
    
         
            +
            		Director::Delegate.passthru
         
     | 
| 
      
 131 
     | 
    
         
            +
            	end
         
     | 
| 
      
 132 
     | 
    
         
            +
             
     | 
| 
      
 133 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,18 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
      
 3 
     | 
    
         
            +
            	class Engine
         
     | 
| 
      
 4 
     | 
    
         
            +
            		def initialize(plot)
         
     | 
| 
      
 5 
     | 
    
         
            +
            			@plot = plot
         
     | 
| 
      
 6 
     | 
    
         
            +
            		end
         
     | 
| 
      
 7 
     | 
    
         
            +
            		def run
         
     | 
| 
      
 8 
     | 
    
         
            +
            			user = User.new @plot
         
     | 
| 
      
 9 
     | 
    
         
            +
            			@plot.introduce user.character
         
     | 
| 
      
 10 
     | 
    
         
            +
            			while true
         
     | 
| 
      
 11 
     | 
    
         
            +
            				user.stream.select
         
     | 
| 
      
 12 
     | 
    
         
            +
            				user.state.update
         
     | 
| 
      
 13 
     | 
    
         
            +
            				@plot.update
         
     | 
| 
      
 14 
     | 
    
         
            +
            			end
         
     | 
| 
      
 15 
     | 
    
         
            +
            		end
         
     | 
| 
      
 16 
     | 
    
         
            +
            	end
         
     | 
| 
      
 17 
     | 
    
         
            +
             
     | 
| 
      
 18 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,76 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require "digest/md5"
         
     | 
| 
      
 2 
     | 
    
         
            +
            require "gamefic/node"
         
     | 
| 
      
 3 
     | 
    
         
            +
            require "gamefic/describable"
         
     | 
| 
      
 4 
     | 
    
         
            +
            require "gamefic/plot"
         
     | 
| 
      
 5 
     | 
    
         
            +
             
     | 
| 
      
 6 
     | 
    
         
            +
            module Gamefic
         
     | 
| 
      
 7 
     | 
    
         
            +
            	
         
     | 
| 
      
 8 
     | 
    
         
            +
            	class Entity
         
     | 
| 
      
 9 
     | 
    
         
            +
            		include Branch
         
     | 
| 
      
 10 
     | 
    
         
            +
            		include Describable
         
     | 
| 
      
 11 
     | 
    
         
            +
            		attr_reader :session, :plot
         
     | 
| 
      
 12 
     | 
    
         
            +
            		def initialize(plot, args = {})
         
     | 
| 
      
 13 
     | 
    
         
            +
            			if (plot.kind_of?(Plot) == false)
         
     | 
| 
      
 14 
     | 
    
         
            +
            				raise "First argument must be a Plot"
         
     | 
| 
      
 15 
     | 
    
         
            +
            			end
         
     | 
| 
      
 16 
     | 
    
         
            +
            			pre_initialize
         
     | 
| 
      
 17 
     | 
    
         
            +
            			#self.state = State
         
     | 
| 
      
 18 
     | 
    
         
            +
            			#@story = Subplot.current
         
     | 
| 
      
 19 
     | 
    
         
            +
            			@plot = plot
         
     | 
| 
      
 20 
     | 
    
         
            +
            			@plot.send :add_entity, self
         
     | 
| 
      
 21 
     | 
    
         
            +
            			#@story.add_entity self
         
     | 
| 
      
 22 
     | 
    
         
            +
            			args.each { |key, value|
         
     | 
| 
      
 23 
     | 
    
         
            +
            				send "#{key}=", value
         
     | 
| 
      
 24 
     | 
    
         
            +
            			}
         
     | 
| 
      
 25 
     | 
    
         
            +
            			@update_procs = Array.new
         
     | 
| 
      
 26 
     | 
    
         
            +
            			@session = Hash.new
         
     | 
| 
      
 27 
     | 
    
         
            +
            			post_initialize
         
     | 
| 
      
 28 
     | 
    
         
            +
            		end
         
     | 
| 
      
 29 
     | 
    
         
            +
            		#def self.present(args = {})
         
     | 
| 
      
 30 
     | 
    
         
            +
            		#	story = Plot.Loading
         
     | 
| 
      
 31 
     | 
    
         
            +
            		#	if story == nil
         
     | 
| 
      
 32 
     | 
    
         
            +
            		#		raise "No plot loading"
         
     | 
| 
      
 33 
     | 
    
         
            +
            		#	end
         
     | 
| 
      
 34 
     | 
    
         
            +
            		#	return self.new(story, args)
         
     | 
| 
      
 35 
     | 
    
         
            +
            		#end
         
     | 
| 
      
 36 
     | 
    
         
            +
            		def uid
         
     | 
| 
      
 37 
     | 
    
         
            +
            			if @uid == nil
         
     | 
| 
      
 38 
     | 
    
         
            +
            				@uid = Digest::MD5.hexdigest(self.object_id.to_s)[0,8]
         
     | 
| 
      
 39 
     | 
    
         
            +
            			end
         
     | 
| 
      
 40 
     | 
    
         
            +
            			@uid
         
     | 
| 
      
 41 
     | 
    
         
            +
            		end
         
     | 
| 
      
 42 
     | 
    
         
            +
            		def pre_initialize
         
     | 
| 
      
 43 
     | 
    
         
            +
            			# raise NotImplementedError, "#{self.class} must implement post_initialize"		
         
     | 
| 
      
 44 
     | 
    
         
            +
            		end
         
     | 
| 
      
 45 
     | 
    
         
            +
            		def post_initialize
         
     | 
| 
      
 46 
     | 
    
         
            +
            			# raise NotImplementedError, "#{self.class} must implement post_initialize"
         
     | 
| 
      
 47 
     | 
    
         
            +
            		end
         
     | 
| 
      
 48 
     | 
    
         
            +
            		def tell(message, refresh = false)
         
     | 
| 
      
 49 
     | 
    
         
            +
            			#TODO: Should this even be here? In all likelihood, only Characters receive tells, right?
         
     | 
| 
      
 50 
     | 
    
         
            +
            			#TODO: On second thought, it might be interesting to see logs from an npc point of view.
         
     | 
| 
      
 51 
     | 
    
         
            +
            		end
         
     | 
| 
      
 52 
     | 
    
         
            +
            		def to_s
         
     | 
| 
      
 53 
     | 
    
         
            +
            			name
         
     | 
| 
      
 54 
     | 
    
         
            +
            		end
         
     | 
| 
      
 55 
     | 
    
         
            +
            		def update
         
     | 
| 
      
 56 
     | 
    
         
            +
            			@update_procs.each { |p|
         
     | 
| 
      
 57 
     | 
    
         
            +
            				p.call self
         
     | 
| 
      
 58 
     | 
    
         
            +
            			}
         
     | 
| 
      
 59 
     | 
    
         
            +
            		end
         
     | 
| 
      
 60 
     | 
    
         
            +
            		def on_update(&block)
         
     | 
| 
      
 61 
     | 
    
         
            +
            			@update_procs.push block
         
     | 
| 
      
 62 
     | 
    
         
            +
            		end
         
     | 
| 
      
 63 
     | 
    
         
            +
            		def parent=(node)
         
     | 
| 
      
 64 
     | 
    
         
            +
            			if node != nil and node.kind_of?(Entity) == false and node.kind_of?(Zone) == false
         
     | 
| 
      
 65 
     | 
    
         
            +
            				raise "Entity's parent must be an Entity or a Zone"
         
     | 
| 
      
 66 
     | 
    
         
            +
            			end
         
     | 
| 
      
 67 
     | 
    
         
            +
            			super
         
     | 
| 
      
 68 
     | 
    
         
            +
            		end
         
     | 
| 
      
 69 
     | 
    
         
            +
            		def destroy
         
     | 
| 
      
 70 
     | 
    
         
            +
            			self.parent = nil
         
     | 
| 
      
 71 
     | 
    
         
            +
            			# TODO: Need to call this private method here?
         
     | 
| 
      
 72 
     | 
    
         
            +
            			@plot.send(:rem_entity, self)
         
     | 
| 
      
 73 
     | 
    
         
            +
            		end
         
     | 
| 
      
 74 
     | 
    
         
            +
            	end
         
     | 
| 
      
 75 
     | 
    
         
            +
             
     | 
| 
      
 76 
     | 
    
         
            +
            end
         
     |