james 0.0.12-universal-darwin-10 → 0.1.0-universal-darwin-10

Sign up to get free protection for your applications and to get access to all the features.
data/aux/james/cli.rb CHANGED
@@ -4,24 +4,23 @@ module James
4
4
 
5
5
  class CLI
6
6
 
7
- def execute *given_dialogues
8
- dialogues = find_dialogues
9
- dialogues.select! { |dialogue| given_dialogues.any? { |given| dialogue =~ %r{#{given}_dialog(ue)?.rb$} } } unless given_dialogues.empty?
7
+ def execute *patterns
8
+ dialogs = find_dialogs_for patterns
10
9
 
11
- puts "James: I haven't found anything to talk about (No *_dialog{ue,}.rb files found). Exiting." or exit!(1) if dialogues.empty?
10
+ puts "James: I haven't found anything to talk about (No files found). Exiting." or exit!(1) if dialogs.empty?
11
+ puts "James: Using dialogs in #{dialogs.join(', ')} for our conversation, Sir."
12
12
 
13
- puts "James: Using #{dialogues.join(', ')} for our conversation, Sir."
14
-
15
- require_all dialogues
13
+ load_all dialogs
16
14
 
17
15
  James.listen
18
16
  end
19
- def find_dialogues
20
- Dir["**/*_dialog{,ue}.rb"]
17
+ def find_dialogs_for patterns
18
+ patterns = ["**/*_dialog{,ue}.rb"] if patterns.empty?
19
+ Dir[*patterns]
21
20
  end
22
- def require_all dialogues
23
- dialogues.each do |dialogue|
24
- require File.expand_path dialogue, Dir.pwd
21
+ def load_all dialogs
22
+ dialogs.each do |dialog|
23
+ load File.expand_path dialog, Dir.pwd
25
24
  end
26
25
  end
27
26
 
data/bin/james CHANGED
@@ -1,9 +1,11 @@
1
1
  #!/usr/bin/env ruby
2
2
  #
3
3
 
4
- # james joke phonebook quote # Uses just the described ones.
4
+ # james joke_dialog.rb phonebook_dialog.rb quote_dialog.rb # Uses just the described ones.
5
5
  # OR
6
- # james # Uses all it can find.
6
+ # james j*.rb # Uses all the dialogs matching the pattern.
7
+ # OR
8
+ # james # Uses all dialogs it can find in this dir and subdirs.
7
9
  #
8
10
 
9
11
  begin
data/lib/james.rb CHANGED
@@ -8,10 +8,10 @@ require File.expand_path '../james/state_internals', __FILE__
8
8
  require File.expand_path '../james/visitor', __FILE__
9
9
  require File.expand_path '../james/visitors', __FILE__
10
10
 
11
- require File.expand_path '../james/dialogue_api', __FILE__
12
- require File.expand_path '../james/dialogue_internals', __FILE__
11
+ require File.expand_path '../james/dialog_api', __FILE__
12
+ require File.expand_path '../james/dialog_internals', __FILE__
13
13
 
14
- require File.expand_path '../james/dialogues', __FILE__
14
+ require File.expand_path '../james/dialogs', __FILE__
15
15
 
16
16
  require File.expand_path '../james/inputs/base', __FILE__
17
17
  require File.expand_path '../james/inputs/audio', __FILE__
@@ -20,20 +20,33 @@ require File.expand_path '../james/inputs/terminal', __FILE__
20
20
  require File.expand_path '../james/outputs/audio', __FILE__
21
21
  require File.expand_path '../james/outputs/terminal', __FILE__
22
22
 
23
- require File.expand_path '../james/builtin/core_dialogue', __FILE__
23
+ require File.expand_path '../james/builtin/core_dialog', __FILE__
24
24
 
25
+ require File.expand_path '../james/framework', __FILE__
25
26
  require File.expand_path '../james/controller', __FILE__
26
27
 
27
28
  module James
28
29
 
30
+ # Use the given dialogs.
31
+ #
32
+ # If called twice or more, will just add more dialogs.
33
+ #
34
+ def self.use *dialogs
35
+ dialogs.each { |dialog| controller.add_dialog dialog }
36
+ end
37
+
29
38
  # Start a new controller and listen.
30
39
  #
31
40
  # Will not listen again if already listening.
32
41
  #
33
42
  def self.listen
34
- return if @controller && @controller.listening?
43
+ controller.listen unless controller.listening?
44
+ end
45
+
46
+ # Controller instance.
47
+ #
48
+ def self.controller
35
49
  @controller ||= Controller.new
36
- @controller.listen
37
50
  end
38
51
 
39
52
  end
@@ -1,20 +1,20 @@
1
- # This is the core dialogue every dialogue will be hooking into.
1
+ # This is the core dialog every dialog will be hooking into.
2
2
  #
3
3
  # Eventually, the design should be such that everyone can use
4
- # the design and core dialogue they like best.
4
+ # the design and core dialog they like best.
5
5
  #
6
6
  # But to get going, this suffices for now.
7
7
  #
8
- class CoreDialogue
8
+ class CoreDialog
9
9
 
10
- include James::Dialogue
10
+ include James::Dialog
11
11
 
12
12
  # The alert state.
13
13
  # When James is in this state, he should be
14
- # open for user dialogues.
14
+ # open for user dialogs.
15
15
  #
16
16
  state :awake do
17
- # If James is awake, he offers more dialogues
17
+ # If James is awake, he offers more dialogs
18
18
  # on this state, if there are any hooked into this state.
19
19
  #
20
20
  chainable
@@ -26,7 +26,7 @@ class CoreDialogue
26
26
  end
27
27
 
28
28
  # The away state. James does not listen to any
29
- # user dialogue hooks, but only for his name
29
+ # user dialog hooks, but only for his name
30
30
  # or the good night, i.e. exit phrase.
31
31
  #
32
32
  state :away do
@@ -1,18 +1,18 @@
1
- framework 'AppKit'
2
-
3
1
  module James
4
2
 
5
3
  class Controller
6
4
 
7
5
  attr_reader :visitor
8
6
 
9
- # This puts together the core dialogue and the user
7
+ # This puts together the core dialog and the user
10
8
  # ones that are hooked into it.
11
9
  #
10
+ # TODO Rewrite this. Design needs some refactoring.
11
+ #
12
12
  def initialize
13
- user_visitor = initialize_dialogues.visitor
14
- system_visitor = Visitor.new CoreDialogue.new.state_for(:awake)
15
- @visitor = Visitors.new system_visitor, user_visitor
13
+ @user_dialogs = Dialogs.new
14
+ system_visitor = Visitor.new CoreDialog.new.state_for(:awake)
15
+ @visitor = Visitors.new system_visitor, @user_dialogs.visitor
16
16
  end
17
17
 
18
18
  def applicationDidFinishLaunching notification
@@ -30,14 +30,12 @@ module James
30
30
  # TODO
31
31
  end
32
32
 
33
- # Initialize and "parse" the
34
- # dialogues.
33
+ # Add a dialog to the current system.
35
34
  #
36
- def initialize_dialogues
37
- dialogues = Dialogues.new
38
- dialogues.resolve
39
- dialogues
35
+ def add_dialog dialog
36
+ @user_dialogs << dialog
40
37
  end
38
+
41
39
  # Start recognizing words.
42
40
  #
43
41
  def start_input
@@ -50,18 +48,18 @@ module James
50
48
  @output = Outputs::Audio.new
51
49
  end
52
50
 
53
- # Callback method from dialogue.
51
+ # Callback method from dialog.
54
52
  #
55
53
  def say text
56
54
  @output.say text
57
55
  end
58
56
  def hear text
59
- @visitor.hear text do |response|
57
+ visitor.hear text do |response|
60
58
  say response
61
59
  end
62
60
  end
63
61
  def expects
64
- @visitor.expects
62
+ visitor.expects
65
63
  end
66
64
 
67
65
  def listen
@@ -87,12 +85,14 @@ module James
87
85
  # window.display
88
86
  # window.orderFrontRegardless
89
87
 
88
+ @listening = true
89
+
90
90
  app.run
91
91
  end
92
- # Simply put, if there is a controller, it is listening.
92
+ # If listen has been called, it is listening.
93
93
  #
94
94
  def listening?
95
- true
95
+ !!@listening
96
96
  end
97
97
 
98
98
  end
@@ -0,0 +1,34 @@
1
+ module James
2
+
3
+ # A dialog can be instantiated in two ways:
4
+ #
5
+ # The simple way, will directly add itself to James.
6
+ #
7
+ # James.use_dialog(optional_args_for_initialize) do
8
+ # # Your dialog.
9
+ # #
10
+ # end
11
+ #
12
+ # class MyDialog
13
+ # include James::Dialog
14
+ #
15
+ # # Your dialog.
16
+ # #
17
+ # end
18
+ #
19
+ # James.use MyDialog.new
20
+ #
21
+ module Dialog; end
22
+
23
+ class << self
24
+
25
+ def use_dialog *args, &block
26
+ dialog = Class.new { include James::Dialog }
27
+ dialog.class_eval &block
28
+ use dialog.new(*args)
29
+ dialog
30
+ end
31
+
32
+ end
33
+
34
+ end
@@ -1,13 +1,12 @@
1
1
  module James
2
2
 
3
- # A dialogue is just a container object
3
+ # A dialog is just a container object
4
4
  # for defining states and executing methods.
5
5
  #
6
- module Dialogue
6
+ module Dialog
7
7
 
8
8
  def self.included into
9
9
  into.extend ClassMethods
10
- Dialogues << into unless into == CoreDialogue # TODO Dirty as hell.
11
10
  end
12
11
 
13
12
  #
@@ -0,0 +1,43 @@
1
+ module James
2
+
3
+ # Registers dialogs and connects their states.
4
+ #
5
+ class Dialogs
6
+
7
+ attr_reader :initial
8
+
9
+ def initialize
10
+ @initial = State.new :__initial_plugin_state__, nil
11
+ end
12
+
13
+ # Generate the graph for the dialogs.
14
+ #
15
+ # Hooks up the entry phrases of the dialog
16
+ # into the main dialog.
17
+ #
18
+ # It raises if the hook phrase of a dialog
19
+ # is already used.
20
+ #
21
+ def << dialog
22
+ resolved_entries = {}
23
+
24
+ dialog.entries.each do |(phrases, state)|
25
+ resolved_entries[phrases] = state.respond_to?(:phrases) ? state : dialog.state_for(state)
26
+ end
27
+
28
+ # Hook the dialog into the initial state.
29
+ #
30
+ initial.hear resolved_entries
31
+ end
32
+
33
+ # Get the visitor.
34
+ #
35
+ # Initialized on the initial state.
36
+ #
37
+ def visitor
38
+ @visitor ||= Visitor.new initial
39
+ end
40
+
41
+ end
42
+
43
+ end
@@ -0,0 +1 @@
1
+ framework 'AppKit'
@@ -13,7 +13,7 @@ module James
13
13
  # Call this method if you heard something in the subclass.
14
14
  #
15
15
  def heard command
16
- # Call dialogue.
16
+ # Call dialog.
17
17
  #
18
18
  controller.hear command
19
19
  end
@@ -1,6 +1,6 @@
1
1
  module James
2
2
 
3
- # A state is defined in a dialogue.
3
+ # A state is defined in a dialog.
4
4
  #
5
5
  # It has a name with which it can be targeted.
6
6
  #
@@ -58,16 +58,10 @@ module James
58
58
  @exit_block = block
59
59
  end
60
60
 
61
- #
62
- #
63
- def transition &block
64
-
65
- end
66
-
67
61
  # By default, a state is not chainable.
68
62
  #
69
63
  def chainable?
70
- @chainable
64
+ !!@chainable
71
65
  end
72
66
  def chainable
73
67
  @chainable = true
data/lib/james/visitor.rb CHANGED
@@ -72,7 +72,7 @@ module James
72
72
  def expects
73
73
  current.phrases
74
74
  end
75
- # Does the current state allow penetration into another dialogue?
75
+ # Does the current state allow penetration into another dialog?
76
76
  #
77
77
  def chainable?
78
78
  current.chainable?
@@ -1,7 +1,7 @@
1
1
  module James
2
2
 
3
3
  # The visitors class has a number of visitors, whose
4
- # dialogues are visited in order of preference.
4
+ # dialogs are visited in order of preference.
5
5
  #
6
6
  # Why?
7
7
  # Discussions have multiple points where they can be.
@@ -22,6 +22,10 @@ module James
22
22
  @visitors = visitors
23
23
  end
24
24
 
25
+ def add_dialog dialog
26
+
27
+ end
28
+
25
29
  # Hear tries all visitors in order
26
30
  # until one hears a phrase he knows.
27
31
  #
@@ -39,13 +43,13 @@ module James
39
43
  end
40
44
  end
41
45
 
42
- # Enter enters the first dialogue.
46
+ # Enter enters the first dialog.
43
47
  #
44
48
  def enter
45
49
  visitors.first.enter
46
50
  end
47
51
 
48
- # Simply returns the sum of what phrases all dialogues expect.
52
+ # Simply returns the sum of what phrases all dialogs expect.
49
53
  #
50
54
  # Stops as soon as a visitor is not in a chainable state anymore.
51
55
  #
@@ -5,14 +5,14 @@ require File.expand_path '../../../../aux/james/cli', __FILE__
5
5
  describe James::CLI do
6
6
 
7
7
  before(:each) do
8
- Dir.stub! :[] => ['test_dialogue.rb', 'test_dialog.rb', 'test/test_dialogue.rb']
8
+ Dir.stub! :[] => ['test_dialog.rb', 'test_dialog.rb', 'test/test_dialog.rb']
9
9
  end
10
10
 
11
11
  let(:cli) { James::CLI.new }
12
12
 
13
- describe 'find_dialogues' do
13
+ describe 'find_dialogs' do
14
14
  it 'returns the right ones' do
15
- cli.find_dialogues.should == ['test_dialogue.rb', 'test_dialog.rb', 'test/test_dialogue.rb']
15
+ cli.find_dialogs.should == ['test_dialog.rb', 'test_dialog.rb', 'test/test_dialog.rb']
16
16
  end
17
17
  end
18
18
 
@@ -2,10 +2,10 @@
2
2
  #
3
3
  require File.expand_path '../../../lib/james', __FILE__
4
4
 
5
- describe 'TestDialogue' do
5
+ describe 'TestDialog' do
6
6
 
7
7
  context 'unit' do
8
- let(:dialogue) do
8
+ let(:dialog) do
9
9
 
10
10
  Class.new do
11
11
  include James::Dialog
@@ -23,7 +23,7 @@ describe 'TestDialogue' do
23
23
 
24
24
  end
25
25
  let(:visitor) do
26
- James::Visitor.new dialogue.state_for(:first)
26
+ James::Visitor.new dialog.state_for(:first)
27
27
  end
28
28
 
29
29
  describe "integration" do
@@ -40,8 +40,8 @@ describe 'TestDialogue' do
40
40
  end
41
41
 
42
42
  # context 'integration' do
43
- # let(:dialogue) do
44
- # dialogue = Class.new do
43
+ # let(:dialog) do
44
+ # dialog = Class.new do
45
45
  # include James::Dialog
46
46
  #
47
47
  # hear ['test1', 'test2'] => :first
@@ -54,13 +54,13 @@ describe 'TestDialogue' do
54
54
  # end.new
55
55
  # end
56
56
  # it 'works correctly' do
57
- # dialogue.state.name.should == :awake
58
- # dialogue.hear 'sleep'
59
- # dialogue.state.name.should == :sleeping
57
+ # dialog.state.name.should == :awake
58
+ # dialog.hear 'sleep'
59
+ # dialog.state.name.should == :sleeping
60
60
  # end
61
61
  # it 'delegates correctly' do
62
- # dialogue.state.name.should == :awake
63
- # dialogue.hear 'test1'
62
+ # dialog.state.name.should == :awake
63
+ # dialog.hear 'test1'
64
64
  # end
65
65
  # end
66
66
 
@@ -1,15 +1,32 @@
1
1
  # encoding: utf-8
2
2
  #
3
+ require File.expand_path '../../../../lib/james/dialog_api', __FILE__
4
+ require File.expand_path '../../../../lib/james/dialog_internals', __FILE__
5
+ require File.expand_path '../../../../lib/james/builtin/core_dialog', __FILE__
6
+ require File.expand_path '../../../../lib/james/visitors', __FILE__
7
+ require File.expand_path '../../../../lib/james/visitor', __FILE__
8
+ require File.expand_path '../../../../lib/james/state_api', __FILE__
9
+ require File.expand_path '../../../../lib/james/dialogs', __FILE__
3
10
  require File.expand_path '../../../../lib/james/controller', __FILE__
4
11
 
5
12
  describe James::Controller do
6
13
 
7
- # let(:controller) { described_class.new }
8
- #
9
- # describe 'listening?' do
10
- # it 'is correct' do
11
- # controller.listening?.should == true
12
- # end
13
- # end
14
+ let(:controller) { described_class.new }
15
+
16
+ describe 'listening?' do
17
+ it 'is correct' do
18
+ controller.listening?.should == false
19
+ end
20
+ end
21
+ describe 'expects' do
22
+ it 'delegates' do
23
+ visitor = stub! :visitor
24
+ controller.stub! :visitor => visitor
25
+
26
+ visitor.should_receive(:expects).once.with()
27
+
28
+ controller.expects
29
+ end
30
+ end
14
31
 
15
32
  end
@@ -1,20 +1,21 @@
1
1
  # encoding: utf-8
2
2
  #
3
+ require File.expand_path '../../../../lib/james', __FILE__
3
4
  require File.expand_path '../../../../lib/james/state_api', __FILE__
4
- require File.expand_path '../../../../lib/james/dialogue_api', __FILE__
5
- require File.expand_path '../../../../lib/james/dialogue_internals', __FILE__
6
- require File.expand_path '../../../../lib/james/builtin/core_dialogue', __FILE__
7
- require File.expand_path '../../../../lib/james/dialogues', __FILE__
5
+ require File.expand_path '../../../../lib/james/dialog_api', __FILE__
6
+ require File.expand_path '../../../../lib/james/dialog_internals', __FILE__
7
+ require File.expand_path '../../../../lib/james/builtin/core_dialog', __FILE__
8
+ require File.expand_path '../../../../lib/james/dialogs', __FILE__
8
9
 
9
- describe James::Dialogue do
10
+ describe James::Dialog do
10
11
 
11
12
  it 'can haz merkin spellink' do
12
- James::Dialogue.should == James::Dialog
13
+ James::Dialog.should == James::Dialog
13
14
  end
14
15
 
15
16
  context 'units' do
16
- let(:dialogue) do
17
- James.dialogue do
17
+ let(:dialog) do
18
+ James.use_dialog do
18
19
 
19
20
  hear 'something' => :first
20
21
 
@@ -34,21 +35,21 @@ describe James::Dialogue do
34
35
  end
35
36
  describe 'state_for' do
36
37
  it 'delegates to the class, adding itself' do
37
- new_dialogue = dialogue.new
38
- dialogue.should_receive(:state_for).once.with :some_name, new_dialogue
38
+ new_dialog = dialog.new
39
+ dialog.should_receive(:state_for).once.with :some_name, new_dialog
39
40
 
40
- new_dialogue.state_for :some_name
41
+ new_dialog.state_for :some_name
41
42
  end
42
43
  it 'returns nil on not found' do
43
- dialogue.new.state_for(:nonexistent).should == nil
44
+ dialog.new.state_for(:nonexistent).should == nil
44
45
  end
45
46
  end
46
47
  end
47
48
 
48
49
  describe 'hear with lambda' do
49
- let(:dialogue) do
50
+ let(:dialog) do
50
51
  class Test
51
- include James::Dialogue
52
+ include James::Dialog
52
53
 
53
54
  def initialize
54
55
  @bla = 'some bla'
@@ -61,7 +62,7 @@ describe James::Dialogue do
61
62
  Test.new
62
63
  end
63
64
  it "is instance eval'd" do
64
- test_state = dialogue.state_for :test
65
+ test_state = dialog.state_for :test
65
66
  test_state.hear 'bla' do |result|
66
67
  result.should == 'some bla'
67
68
  end
@@ -72,7 +73,7 @@ describe James::Dialogue do
72
73
  it 'can be included' do
73
74
  expect do
74
75
  class Test
75
- include James::Dialogue
76
+ include James::Dialog
76
77
 
77
78
  hear 'something' => :some_state
78
79
  end
@@ -81,7 +82,7 @@ describe James::Dialogue do
81
82
 
82
83
  it 'can be defined' do
83
84
  expect do
84
- James.dialogue do
85
+ James.dialog do
85
86
 
86
87
  hear 'something' => :some_state
87
88
 
metadata CHANGED
@@ -2,14 +2,14 @@
2
2
  name: james
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 0.0.12
5
+ version: 0.1.0
6
6
  platform: universal-darwin-10
7
7
  authors:
8
8
  - Florian Hanke
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2011-05-17 00:00:00 +10:00
12
+ date: 2011-05-21 00:00:00 +10:00
13
13
  default_executable: james
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -28,19 +28,20 @@ dependencies:
28
28
  - - '>='
29
29
  - !ruby/object:Gem::Version
30
30
  version: "0"
31
- description: Modular Electronic Butler. Using a simple dialogue system where you can
32
- easily add more dialogues.
31
+ description: Modular Electronic Butler. Using a simple dialog system where you can
32
+ easily add more dialogs.
33
33
  email: florian.hanke+james@gmail.com
34
34
  executables:
35
35
  - james
36
36
  extensions: []
37
37
  extra_rdoc_files: []
38
38
  files:
39
- - lib/james/builtin/core_dialogue.rb
39
+ - lib/james/builtin/core_dialog.rb
40
40
  - lib/james/controller.rb
41
- - lib/james/dialogue_api.rb
42
- - lib/james/dialogue_internals.rb
43
- - lib/james/dialogues.rb
41
+ - lib/james/dialog_api.rb
42
+ - lib/james/dialog_internals.rb
43
+ - lib/james/dialogs.rb
44
+ - lib/james/framework.rb
44
45
  - lib/james/inputs/audio.rb
45
46
  - lib/james/inputs/base.rb
46
47
  - lib/james/inputs/terminal.rb
@@ -56,7 +57,7 @@ files:
56
57
  - spec/aux/james/cli_spec.rb
57
58
  - spec/integration/test_dialogue_spec.rb
58
59
  - spec/lib/james/controller_spec.rb
59
- - spec/lib/james/dialogue_spec.rb
60
+ - spec/lib/james/dialog_spec.rb
60
61
  - spec/lib/james/state_spec.rb
61
62
  - spec/lib/james/visitor_spec.rb
62
63
  - spec/lib/james/visitors_spec.rb
@@ -85,12 +86,12 @@ rubyforge_project:
85
86
  rubygems_version: 1.4.2
86
87
  signing_key:
87
88
  specification_version: 3
88
- summary: 'James: Modular Electronic Butler with modular Dialogues.'
89
+ summary: 'James: Modular Electronic Butler with modular Dialogs.'
89
90
  test_files:
90
91
  - spec/aux/james/cli_spec.rb
91
92
  - spec/integration/test_dialogue_spec.rb
92
93
  - spec/lib/james/controller_spec.rb
93
- - spec/lib/james/dialogue_spec.rb
94
+ - spec/lib/james/dialog_spec.rb
94
95
  - spec/lib/james/state_spec.rb
95
96
  - spec/lib/james/visitor_spec.rb
96
97
  - spec/lib/james/visitors_spec.rb
@@ -1,34 +0,0 @@
1
- module James
2
-
3
- # A dialog(ue) can be instantiated in two ways:
4
- #
5
- # James.dialogue do
6
- # # Your dialogue.
7
- # #
8
- # end
9
- #
10
- # class MyDialogue
11
- # include James::Dialogue
12
- #
13
- # # Your dialogue.
14
- # #
15
- # end
16
- #
17
- module Dialogue; end
18
-
19
- # We don't care about the spelling.
20
- #
21
- Dialog = Dialogue
22
-
23
- class << self
24
-
25
- def dialogue &block
26
- dialogue = Class.new { include James::Dialogue }
27
- dialogue.class_eval &block
28
- dialogue
29
- end
30
- alias dialog dialogue
31
-
32
- end
33
-
34
- end
@@ -1,58 +0,0 @@
1
- module James
2
-
3
- # Registers all dialogues and connects their states.
4
- #
5
- class Dialogues
6
-
7
- attr_reader :initial, :dialogues
8
-
9
- def initialize
10
- @initial = State.new :__initial_plugin_state__, nil
11
- @dialogues = self.class.dialogues.map &:new
12
- end
13
-
14
- class << self
15
-
16
- attr_reader :dialogues
17
-
18
- def << dialogue
19
- @dialogues ||= []
20
- @dialogues << dialogue
21
- end
22
-
23
- end
24
-
25
- # Generate the graph for the dialogues.
26
- #
27
- # Hooks up the entry phrases of all dialogues
28
- # into the main dialogue.
29
- #
30
- # It raises if the hook phrase of a dialogue
31
- # is already used.
32
- #
33
- def resolve
34
- # Hook dialogues into initial state.
35
- #
36
- resolved_entries = {}
37
- dialogues.each do |dialogue|
38
- dialogue.entries.each do |(phrases, state)|
39
- resolved_entries[phrases] = state.respond_to?(:phrases) ? state : dialogue.state_for(state)
40
- end
41
- end
42
-
43
- # Hook all user dialogues into the initial state.
44
- #
45
- initial.hear resolved_entries
46
- end
47
-
48
- # Get the visitor.
49
- #
50
- # Initialized on the initial state.
51
- #
52
- def visitor
53
- @visitor ||= Visitor.new initial
54
- end
55
-
56
- end
57
-
58
- end