pakyow-presenter/lib/presenter/binder.rb in pakyow-presenter-0.8.0 vs pakyow-presenter/lib/presenter/binder.rb in pakyow-presenter-0.9.0

- old
+ new

@@ -1,79 +1,89 @@ +require 'singleton' + module Pakyow module Presenter - # A singleton that manages route sets. + # A singleton that manages BinderSet instances for an app. It handles + # the creation / registration of sets and provides a mechanism + # to augment data to be bound with values from the sets. # class Binder include Singleton - include Helpers + # Access to the registered binder sets for an app. + # attr_reader :sets def initialize @sets = {} end - #TODO want to do this for all sets? + # Resets the registered binder sets. + # + # @return [Binder] the reset instance + # def reset @sets = {} self end - # Creates a new set. + # Creates and registers a new binder set by name. A block should be passed + # that defines the bindings. This block will be evaluated in context + # of the created binder set. # + # @see BinderSet + # + # @param name [Symbol] the name of the binder set to be created + # def set(name, &block) - @sets[name] = BinderSet.new - @sets[name].instance_exec(&block) + @sets[name] = BinderSet.new(&block) end - def value_for_prop(prop, scope, bindable, bindings = {}, context) - @context = context - binding = nil - @sets.each {|set| - binding = set[1].match_for_prop(prop, scope, bindable, bindings) - break if binding + # Returns the value for the scope->prop by applying any defined bindings to the data. + # + # @param scope [Symbol] the scope name + # @param prop [Symbol] the prop name + # @param bindable [Symbol] the data being bound + # @param bindings [Symbol] additional bindings to take into consideration when determining the value + # @param context [Symbol] context passed through to the defined bindings + # + def value_for_scoped_prop(scope, prop, bindable, bindings, context) + binding_fn = @sets.lazy.map { |set| + set[1].match_for_prop(prop, scope, bindable, bindings) + }.find { |match| + !match.nil? } - if binding + if binding_fn binding_eval = BindingEval.new(prop, bindable, context) - - case binding.arity - when 0 - binding_eval.instance_exec(&binding) - when 1 - self.instance_exec(bindable, &binding) - when 2 - self.instance_exec(bindable, binding_eval.value, &binding) + binding_eval.instance_exec(binding_eval.value, bindable, context, &binding_fn) + else # default value + if bindable.is_a?(Hash) + bindable[prop] + elsif bindable.class.method_defined?(prop) + bindable.send(prop) end - else - # default - prop_value_for_bindable(bindable, prop) end end - def prop_value_for_bindable(bindable, prop) - return bindable[prop] if bindable.is_a?(Hash) - return bindable.send(prop) if bindable.class.method_defined?(prop) - end - - def options_for_prop(*args) - match = nil - @sets.each {|set| - match = set[1].options_for_prop(*args) - break if match + # Returns true if a binding is defined for the scope->prop. + # + def has_scoped_prop?(scope, prop, bindings) + @sets.lazy.map { |set| + set[1].has_prop?(scope, prop, bindings) + }.find { |has_prop| + has_prop } - - return match end - def has_prop?(*args) - has = nil - @sets.each {|set| - has = set[1].has_prop?(*args) - break if has + # Returns options for the scope->prop. + # + def options_for_scoped_prop(scope, prop, bindable, context) + @sets.lazy.map { |set| + set[1].options_for_prop(scope, prop, bindable, context) + }.find { |options| + !options.nil? } - - return has end end end end