Skip to content

Instantly share code, notes, and snippets.

@mirichi

mirichi/component.rb Secret

Last active Mar 5, 2016
Embed
What would you like to do?
コンポーネントの基本クラス
class AttributeInitialValueError < StandardError
end
# 基本コンポーネントのベースモジュール
module ComponentModule
def initialize(*args)
init_component(*args)
end
# 初期化メソッド
# extendで追加した時は明示的にこれを呼ぶ。
def init_component(*args)
@_components = []
@_event_handlers = {}
@_attributes = {}
@_initial_values = {}
end
# イベントを投げ込む
def post_event(event_name, *args)
if @_event_handlers[event_name]
@_event_handlers[event_name].each do |h|
h.call(*args)
end
end
return nil
end
# イベントキューに入れる
def send_event(event_name)
end
# イベントハンドラを設定する
# イベントハンドラを返す。後で解除する場合は保存しといてそれで指定する。
def add_event_handler(event_name, handler=proc)
if @_event_handlers.has_key?(event_name)
@_event_handlers[event_name] << handler
else
@_event_handlers[event_name] = [handler]
end
return handler
end
# イベントハンドラを解除する
def remove_event_handler(event_name, handler)
end
# 機能コンポーネントを追加する
# 機能コンポーネントのインスタンスを返す。後で削除する場合は保存しといてそれで指定する。
def add_component(component_class)
component_instance = component_class.new
@_components << component_instance
component_instance.added_component(self)
return component_instance
end
# 機能コンポーネントを削除する
def remove_component(component_instance)
end
# 属性を作成する
# 属性は最初に作成されたときにのみ初期化される。
# 同じ属性を使うコンポーネントがぶつかった場合に2回目以降の実行は初期化されない。
# 初期値の違う属性を同じ名前で作成しようとすると例外が発生する。
def init_attribute(attribute_name, initial_value)
if @_attributes.has_key?(attribute_name)
if @_initial_values[attribute_name] != initial_value
raise AttributeInitialValueError
end
else
@_attributes[attribute_name] = @_initial_values[attribute_name] = initial_value
end
return nil
end
# 属性の追加。init_attributeとは違ってこっちは無条件に設定される。
def set_attribute(attribute_name, value)
@_attributes[attribute_name] = value
end
# 属性を取得する
def get_attribute(attribute_name)
@_attributes[attribute_name]
end
end
# コンポーネントのベースクラス
class Component
include ComponentModule
end
# 機能コンポーネントのクラス
class FeatureComponent
attr_reader :parent
# 親に追加された時に呼ばれる。
# 基本的には初期化はここで行う。@parentに親が入るのはこれ以降。
def init_component
end
# 親コンポーネントに追加された時に呼ばれる。内部処理。
def added_component(parent)
@parent = parent
self.init_component
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment