Class: Finity::Machine

Inherits:
Object
  • Object
show all
Defined in:
lib/finity/machine.rb

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(klass, options = {}, &block) ⇒ Machine

Initialize a new state machine within the provided class and define methods for querying the current state and initiating transitions.



29
30
31
32
33
34
35
36
37
38
# File 'lib/finity/machine.rb', line 29

def initialize klass, options = {}, &block
  @klass, @states, @events, @init = klass, {}, {}, options.delete(:init)
  @klass.send :define_method, :event! do |*args|
    klass.machine.update self, *args
  end
  @klass.send :define_method, :state? do |*args|
    klass.machine.current.name.eql? *args
  end
  instance_eval &block if block_given?
end

Instance Attribute Details

#currentObject

Returns the value of attribute current.



25
26
27
# File 'lib/finity/machine.rb', line 25

def current
  @current
end

#eventsObject

Returns the value of attribute events.



25
26
27
# File 'lib/finity/machine.rb', line 25

def events
  @events
end

#statesObject

Returns the value of attribute states.



25
26
27
# File 'lib/finity/machine.rb', line 25

def states
  @states
end

Instance Method Details

#event(name, options = {}, &block) ⇒ Object

Register an event and evaluate the block for transitions.



51
52
53
# File 'lib/finity/machine.rb', line 51

def event name, options = {}, &block
  @events[name] = Event.new name, options, &block
end

#initObject

Return the name of the initial state.



41
42
43
# File 'lib/finity/machine.rb', line 41

def init
  @init ||= @states.keys.first unless @states.first.nil?
end

#state(name, options = {}) ⇒ Object

Register a state.



46
47
48
# File 'lib/finity/machine.rb', line 46

def state name, options = {}
  @states[name] = State.new name, options
end

#update(object, event) ⇒ Object

An event occured, so update the state machine by evaluating the transition functions and notify the left and entered state.



57
58
59
60
61
62
63
64
65
66
67
# File 'lib/finity/machine.rb', line 57

def update object, event
  @current ||= @states[init]
  if (state = @events[event].handle object, @current)
    if @states[state].nil?
      raise InvalidState, "Invalid state '#{state}'"
    end
    @current.leave object
    @current = @states[state]
    @current.enter object
  end
end