def build_and(i, ex, args): ex.a_value = hive.attribute(("bool", ), False) ex.b_value = hive.attribute(("bool", ), False) i.a = hive.pull_in(ex.a_value) i.b = hive.pull_in(ex.b_value) ex.a = hive.antenna(i.a) ex.b = hive.antenna(i.b) def on_and(h): h._pull_inputs() if h.a_value and h.b_value: h.trig_out() i.trig_out = hive.triggerfunc() i.trig_in = hive.modifier(on_and) # Update attributes before calling modifier i.pull_inputs = hive.triggerfunc() hive.trigger(i.pull_inputs, i.a, pretrigger=True) hive.trigger(i.pull_inputs, i.b, pretrigger=True) ex.trig_out = hive.hook(i.trig_out) ex.trig_in = hive.entry(i.trig_in)
def build_instantiator(cls, i, ex, args, meta_args): """Instantiates a Hive class at runtime""" # If this is built now, then it won't perform matchmaking, so use meta hive bind_meta_class = hive.meta_hive("BindEnvironment", build_bind_environment, declare_build_environment, builder_cls=BindEnvironmentClass) #assert bind_meta_class._hive_object_class i.bind_meta_class = hive.property(cls, "bind_meta_class", "class", bind_meta_class) i.trig_instantiate = hive.triggerfunc(cls.instantiate) i.do_instantiate = hive.triggerable(i.trig_instantiate) i.hive_class = hive.property(cls, "hive_class", "class") i.pull_hive_class = hive.pull_in(i.hive_class) ex.hive_class = hive.antenna(i.pull_hive_class) ex.create = hive.entry(i.do_instantiate) hive.trigger(i.trig_instantiate, i.pull_hive_class, pretrigger=True) ex.process_id = hive.property(cls, "last_created_process_id", "int.process_id") i.pull_process_id = hive.pull_out(ex.process_id) ex.last_process_id = hive.output(i.pull_process_id) i.push_stop_process = hive.push_in(cls.stop_hive) ex.stop_process = hive.antenna(i.push_stop_process) # Bind class plugin ex.bind_on_created = hive.socket(cls.add_on_created, identifier="bind.on_created", policy=hive.MultipleOptional) ex.add_get_plugins = hive.socket(cls.add_get_plugins, identifier="bind.get_plugins", policy=hive.MultipleOptional) ex.add_get_config = hive.socket(cls.add_get_config, identifier="bind.get_config", policy=hive.MultipleOptional) # Bind instantiator if meta_args.bind_process == 'child': # Add startup and stop callbacks ex.on_stopped = hive.plugin(cls.stop_all_processes, identifier="on_stopped")
def build_unpack_tuple(i, ex, args, meta_args): """Unpack a tuple from individual inputs""" i.tuple_ = hive.attribute('tuple') i.push_tuple = hive.push_in(i.tuple_) ex.tuple_ = hive.antenna(i.push_tuple) for index, data_type in enumerate(meta_args.types): attr = hive.attribute(data_type) setattr(i, "attr_{}".format(index), attr) pull_out = hive.pull_out(attr) setattr(i, "pull_out_{}".format(index), pull_out) setattr(ex, "item_{}".format(index), hive.output(pull_out)) def do_unpack_tuple(self): tuple_ = self._tuple_ data_types = meta_args.types assert len(tuple_) == len(data_types) for index, item in enumerate(tuple_): setattr(self, "_attr_{}".format(index), item) i.do_unpack_tuple = hive.modifier(do_unpack_tuple) hive.trigger(i.push_tuple, i.do_unpack_tuple)
def build_scene(cls, i, ex, args): i.bge_scene = hive.property(cls, "scene") ex.get_entity_id = hive.plugin(cls.get_entity_id, identifier="entity.get") ex.get_position_absolute = hive.plugin( cls.get_position_absolute, identifier="entity.position.absolute.get") ex.get_position_relative = hive.plugin( cls.get_position_relative, identifier="entity.position.relative.get") ex.get_orientation_absolute = hive.plugin( cls.get_orientation_absolute, identifier="entity.orientation.absolute.get") ex.get_orientation_relative = hive.plugin( cls.get_orientation_relative, identifier="entity.orientation.relative.get") ex.spawn_entity = hive.plugin(cls.spawn_entity, identifier="entity.spawn") ex.get_scene = hive.plugin(cls.get_scene, identifier="entity.get_current") import dragonfly ex.on_tick = dragonfly.event.Tick() def f(self): print("I") if not hasattr(self, 'a'): self.a = 1 self.spawn_entity.plugin()("Cube", "c1") i.mod_tick = hive.modifier(f) hive.trigger(ex.on_tick, i.mod_tick)
def build_foreach(i, ex, args, meta_args): """Iterate over iterable object""" # Set iterable i.iterable = hive.variable("$iterable[int]") i.pull_iterable = hive.pull_in(i.iterable) ex.iterable = hive.antenna(i.pull_iterable) i.do_trig = hive.triggerfunc() i.trig_in = hive.triggerable(i.do_trig) ex.start = hive.entry(i.trig_in) i.break_ = hive.variable('bool', False) i.item = hive.variable(meta_args.data_type) i.push_item = hive.push_out(i.item) ex.item = hive.output(i.push_item) i.index = hive.variable('int', 0) i.pull_index = hive.pull_out(i.index) ex.index = hive.output(i.pull_index) i.finished = hive.triggerfunc() i.do_break = hive.modifier(do_break) ex.break_ = hive.entry(i.do_break) ex.finished = hive.hook(i.finished) i.iter = hive.modifier(do_iter) hive.trigger(i.do_trig, i.pull_iterable) hive.trigger(i.do_trig, i.iter)
def build_expression(i, ex, args, meta_args): """Execute bound expression for provided inputs and output result""" ast_node = ast.parse(meta_args.expression, mode='eval') visitor = NodeVisitor() visitor.visit(ast_node) visited_nodes = visitor.visited_nodes variable_names = [x.id for x in visited_nodes if isinstance(x, ast.Name)] i.result = hive.attribute(meta_args.result_type) i.pull_result = hive.pull_out(i.result) ex.result = hive.output(i.pull_result) for name in variable_names: attribute = hive.attribute() setattr(i, name, attribute) pull_in = hive.pull_in(attribute) setattr(ex, name, hive.antenna(pull_in)) hive.trigger(i.pull_result, pull_in, pretrigger=True) func = create_func(meta_args.expression, variable_names) i.modifier = hive.modifier(func) hive.trigger(i.pull_result, i.modifier, pretrigger=True)
def test_callable_triggerfunc(): """Trigger function will trigger associated triggerable, after first calling triggerfunc wrapped function""" hive_ping = hive.triggerfunc(print_ping) hive_pong = hive.triggerable(print_pong) hive.trigger(hive_ping, hive_pong) hive_ping()
def build_watch(cls, i, ex, args, meta_args): """Watch value and indicate when it is changed. Uses a tick callback. """ args.start_value = hive.parameter(meta_args.data_type, None) i.value = hive.property(cls, "current_value", meta_args.data_type, args.start_value) if meta_args.mode == 'pull': i.value_in = hive.pull_in(i.value) else: i.value_in = hive.push_in(i.value) ex.value = hive.antenna(i.value_in) i.on_changed = hive.triggerfunc() ex.on_changed = hive.hook(i.on_changed) if meta_args.mode == 'pull': ex.get_add_handler = hive.socket(cls.set_add_handler, identifier="event.add_handler") else: i.compare_values = hive.triggerable(cls.compare_values) hive.trigger(i.value_in, i.compare_values)
def build_mainloop(cls, i, ex, args): i.event_manager = EventManager(export_namespace=True) i.input_manager = InputHandler(export_namespace=True) i.entity_manager = EntityManager(export_namespace=True) i.transform_manager = TransformManager(export_namespace=True) i.physics_manager = PhysicsManager(export_namespace=True) # Connect input manager hive.connect(i.tick, i.input_manager.update) hive.connect(i.input_manager.event, i.event_manager.event_in) # Connect physics hive.connect(i.tick, i.physics_manager.tick) hive.connect(i.pull_tick_rate, i.physics_manager.tick_rate) # Send tick event and step Panda i.on_tick = hive.triggerable(cls.on_tick) hive.trigger(i.tick, i.on_tick) # Get read event ex.get_dispatcher = hive.socket(cls.set_event_dispatcher, "event.process") ex.get_add_handler = hive.socket(cls.set_add_handler, "event.add_handler") # Add startup and stop callbacks ex.main_on_started = hive.plugin(cls.on_started, identifier="on_started")
def test_empty_triggerfunc(): """Trigger function will trigger associated triggerable""" hive_pang = hive.triggerfunc() hive_pong = hive.triggerable(print_pong) hive.trigger(hive_pang, hive_pong) hive_pang()
def build_keyboard(cls, i, ex, args, meta_args): """Listen for keyboard event""" if meta_args.mode == 'single key': ex.on_event = hive.socket(cls.add_single_listener, identifier="event.add_handler") args.key = hive.parameter("str.keycode", "w") i.key = hive.property(cls, "key", "str.keycode", args.key) i.push_key = hive.push_in(i.key) ex.key = hive.antenna(i.push_key) i.on_key_changed = hive.triggerable(cls.change_listener_keys) hive.trigger(i.push_key, i.on_key_changed) i.on_pressed = hive.triggerfunc() ex.on_pressed = hive.hook(i.on_pressed) i.on_released = hive.triggerfunc() ex.on_released = hive.hook(i.on_released) i.is_pressed = hive.property(cls, "is_pressed", "bool") i.pull_is_pressed = hive.pull_out(i.is_pressed) ex.is_pressed = hive.output(i.pull_is_pressed) else: ex.on_event = hive.socket(cls.add_any_listener, identifier="event.add_handler") i.key_pressed = hive.property(cls, 'key_pressed', data_type='str.keycode') i.pull_key_pressed = hive.push_out(i.key_pressed) ex.key_pressed = hive.output(i.pull_key_pressed) i.key_released = hive.property(cls, 'key_released', data_type='str.keycode') i.pull_key_released = hive.push_out(i.key_released) ex.key_released = hive.output(i.pull_key_released)
def build_call(i, ex, args, meta_args): func = create_func(meta_args.declaration) spec = signature(func) for name, parameter in spec.parameters.items(): if parameter.annotation is parameter.empty: raise ValueError("Expected annotation for parameter '{}'".format(name)) attr = hive.attribute(parameter.annotation) pull_in = hive.pull_in(attr) antenna = hive.antenna(pull_in) setattr(i, name, attr) setattr(i, "pull_{}".format(name), pull_in) setattr(ex, name, antenna) wrapped_func = create_wrapper_func(meta_args.declaration, spec.parameters) i.modifier = hive.modifier(wrapped_func) return_type = spec.return_annotation if return_type is spec.empty: raise ValueError("Expected annotation for return parameter") i.result = hive.attribute(return_type) i.pull_result = hive.pull_out(i.result) ex.result = hive.output(i.pull_result) hive.trigger(i.pull_result, i.modifier, pretrigger=True)
def build_print(i, ex, args): """Output object to Python stdout""" ex.value = hive.variable() i.value_in = hive.push_in(ex.value) ex.value_in = hive.antenna(i.value_in) i.func = hive.modifier(lambda self: print(self.value)) hive.trigger(i.value_in, i.func)
def build_this(cls, i, ex, args): """Access to current bound entity""" ex.get_bound_entity = hive.socket(cls.set_get_entity_id, identifier="entity.get_bound") i.entity_id = hive.property(cls, "entity_id", "int.entity_id") i.pull_entity_id = hive.pull_out(i.entity_id) ex.entity_id = hive.output(i.pull_entity_id) i.do_get_entity_id = hive.triggerable(cls.get_entity_id) hive.trigger(i.pull_entity_id, i.do_get_entity_id, pretrigger=True)
def build_determinant(i, ex, args): """Calculate the determinant (length) of a vector""" i.vector = hive.variable("vector") i.pull_vector = hive.pull_in(i.vector) ex.vector = hive.antenna(i.pull_vector) i.result = hive.variable("float") i.pull_result = hive.pull_out(i.result) ex.result = hive.output(i.pull_result) i.calculate = hive.modifier(length_modifier) hive.trigger(i.pull_result, i.calculate, pretrigger=True)
def build_chessboard(cls, i, ex, args): prop_move = h.property(cls, "prop_move", "str") # TODO: make buffer i.make_move = h.push_in(prop_move) i.trig_make_move = h.triggerable(cls.trig_make_move) # TODO: make modifier h.trigger(i.make_move, i.trig_make_move) ex.make_move = h.antenna(i.make_move) ex.do_make_move = cls.make_move ex.p_make_move = h.plugin(cls.make_move) ex.prop_move = prop_move ex.set_turn = h.socket(cls.set_turn) ex.add_moveprocessor = h.socket(cls.add_moveprocessor)
def build_transistor(i, ex, args, meta_args): """Convert a pull output into a push output, using a trigger input""" i.value = hive.variable(meta_args.data_type) i.pull_value = hive.pull_in(i.value) ex.value = hive.antenna(i.pull_value) i.push_value = hive.push_out(i.value) ex.result = hive.output(i.push_value) ex.trigger = hive.entry(i.pull_value) hive.trigger(i.pull_value, i.push_value)
def build_normalise(i, ex, args): """Find the unit vector for a given vector""" i.vector = hive.variable("vector") i.pull_vector = hive.pull_in(i.vector) ex.vector = hive.antenna(i.pull_vector) i.result = hive.variable("vector") i.pull_result = hive.pull_out(i.result) ex.result = hive.output(i.pull_result) i.calculate = hive.modifier(normalise_modifier) hive.trigger(i.pull_result, i.calculate, pretrigger=True)
def build_apply(i, ex, args, meta_args): """Call callable object with provided inputs and output result""" i.callable = hive.attribute(("object", "callable")) i.pull_callable = hive.pull_in(i.callable) ex.callable = hive.antenna(i.pull_callable) i.modifier = hive.modifier(modifier) i.result = hive.attribute(meta_args.result_type) i.pull_result = hive.pull_out(i.result) ex.result = hive.output(i.pull_result) hive.trigger(i.pull_result, i.pull_callable, pretrigger=True) hive.trigger(i.pull_result, i.modifier, pretrigger=True)
def build_generator(i, ex, args): """Define and instantiate a new generator when pulled""" args.generator_body = hive.parameter(("str", "code")) ex.generator = hive.variable() ex.generator_body = hive.variable(("str", "code"), args.generator_body) i.create_generator = hive.modifier(on_new_generator) i.generator_out = hive.pull_out(ex.generator) ex.generator_out = hive.output(i.generator_out) hive.trigger(i.generator_out, i.create_generator, pretrigger=True)
def build_func(i, ex, args, meta_args): """Define callable object from expression""" # Get AST and parse ags ast_node = ast.parse(meta_args.definition, mode='exec') assert isinstance(ast_node, ast.Module) assert len(ast_node.body) == 1 func_def_ast = ast_node.body[0] assert isinstance(func_def_ast, ast.FunctionDef) visitor = FunctionDefinitionVisitor() visitor.visit(ast_node) # Build the function itself user_namespace = {} exec(meta_args.definition, user_namespace) user_func = user_namespace[func_def_ast.name] has_return = visitor.output_type_name is not function_no_return # Define modifier source code (here, we will lookup the "user_func" name later) function_call_str = "user_func({})".format(", ".join( ["self._{}".format(a) for a in visitor.antennae])) result_body = result_str if has_return else "" modifier_decl = modifier_str.format(function_call_str=function_call_str, result_body=result_body) # Build modifier function namespace = {'user_func': user_func} exec(modifier_decl, namespace) modifier_func = namespace['modifier'] # Create modifier bees i.modifier = hive.modifier(modifier_func) ex.trigger = hive.entry(i.modifier) i.pull_all_inputs = hive.triggerfunc() # Create IO pins for arg, (type_name, default) in visitor.antennae.items(): attr = hive.variable(type_name, start_value=default) setattr(i, arg, attr) pull_in = hive.pull_in(attr) setattr(ex, arg, hive.antenna(pull_in)) hive.trigger(i.pull_all_inputs, pull_in, pretrigger=True) if has_return: result_name = 'result' attr = hive.variable(visitor.output_type_name) setattr(i, result_name, attr) push_out = hive.push_out(attr) setattr(ex, result_name, hive.output(push_out))
def build_format(i, ex, args, meta_args): """Interface to Python string value formatting""" formatter = string.Formatter() format_string = meta_args.format_string fields = list(formatter.parse(format_string)) kwarg_fields = [] indexed_fields = [] i.result = hive.attribute('str') i.result_out = hive.pull_out(i.result) for index, field in enumerate(fields): literal_text = field[1] if literal_text is None: continue if not literal_text.isidentifier(): field_name = "field_{}".format(index) indexed_fields.append(field_name) else: field_name = literal_text kwarg_fields.append(field_name) # Create IO attr = hive.attribute() setattr(i, field_name, attr) in_attr = hive.pull_in(attr) setattr(i, "{}_in".format(field_name), in_attr) setattr(ex, field_name, hive.antenna(in_attr)) hive.trigger(i.result_out, in_attr, pretrigger=True) ex.result = hive.output(i.result_out) def do_format(self): args = [ getattr(self, "_{}".format(attr_name)) for attr_name in indexed_fields ] kwargs = { attr_name: getattr(self, "_{}".format(attr_name)) for attr_name in kwarg_fields } self._result = formatter.format(format_string, *args, **kwargs) i.func = hive.modifier(do_format) hive.trigger(i.result_out, i.func, pretrigger=True)
def build_range(i, ex, args): """A range iterator hive""" i.min_value = hive.variable("int") i.max_value = hive.variable("int") i.step = hive.variable("int") i.pull_min_value = hive.pull_in(i.min_value) i.pull_max_value = hive.pull_in(i.max_value) i.pull_step = hive.pull_in(i.step) ex.min_value = hive.antenna(i.pull_min_value) ex.max_value = hive.antenna(i.pull_max_value) ex.step = hive.antenna(i.pull_step) i.iterator = hive.variable("int") def get_range(self): self._iterator = range(self._min_value, self._max_value, self._step) i.get_range = hive.modifier(get_range) i.pull_iterator = hive.pull_out(i.iterator, "iterator") ex.iterator = hive.output(i.pull_iterator) hive.trigger(i.pull_iterator, i.pull_min_value, pretrigger=True) hive.trigger(i.pull_iterator, i.pull_max_value, pretrigger=True) hive.trigger(i.pull_iterator, i.pull_step, pretrigger=True) hive.trigger(i.pull_iterator, i.get_range, pretrigger=True)
def build_import(i, ex, args): """Interface to python import mechanism""" i.do_import = hive.modifier(do_import_from_path) i.import_path = hive.variable("str") i.pull_import_path = hive.pull_in(i.import_path) ex.import_path = hive.antenna(i.pull_import_path) i.module = hive.variable("module") i.pull_module = hive.pull_out(i.module) ex.module = hive.output(i.pull_module) hive.trigger(i.pull_module, i.pull_import_path, pretrigger=True) hive.trigger(i.pull_module, i.do_import, pretrigger=True)
def build_import(cls, i, ex, args): """Interface to python import mechanism, with respect to editor project path""" i.import_path = hive.property(cls, "import_path", 'str') i.pull_import_path = hive.pull_in(i.import_path) ex.import_path = hive.antenna(i.pull_import_path) i.do_import = hive.triggerable(cls.do_import_from_path) i.module = hive.property(cls, "module", "module") i.pull_module = hive.pull_out(i.module) ex.module = hive.output(i.pull_module) hive.trigger(i.pull_module, i.pull_import_path, pretrigger=True) hive.trigger(i.pull_module, i.do_import, pretrigger=True)
def build_house(cls, i, ex, args): i.brutus = dog("Brutus") i.fifi = dog("Fifi") i.dog_comes = h.triggerable(cls.dog_comes) h.trigger(i.brutus.call, i.dog_comes) i.mail = h.triggerfunc(cls.mail) h.trigger(i.mail, i.fifi.woof) ex.brutus = i.brutus ex.fifi = i.fifi ex.mail = h.hook(i.mail) ex.dog_comes = h.entry(i.dog_comes)
def build_iter(i, ex, args, meta_args): """Create iterator for object""" i.iterable = hive.attribute() i.pull_iterable = hive.pull_in(i.iterable) ex.iterable = hive.antenna(i.pull_iterable) i.iterator = hive.attribute("iterator") i.pull_iterator = hive.pull_out(i.iterator) ex.iterator = hive.output(i.pull_iterator) i.do_iter = hive.modifier(do_iter) hive.trigger(i.pull_iterator, i.pull_iterable, pretrigger=True) hive.trigger(i.pull_iterable, i.do_iter)
def build_house(cls, i, ex, args): i.brutus_ = DogHive("Brutus") i.fifi = DogHive("Fifi") i.dog_appeared = hive.triggerable(cls.dog_appeared) hive.trigger(i.brutus_.call, i.dog_appeared) i.mail_arrived = hive.triggerfunc(cls.mail_arrived) hive.trigger(i.mail_arrived, i.fifi.woof) ex.brutus = i.brutus_ ex.fifi = i.fifi ex.mail_arrived = hive.hook(i.mail_arrived) ex.dog_appeared = hive.entry(i.dog_appeared)
def build_len(i, ex, args): """Determine length of object""" i.object = hive.attribute() i.pull_object = hive.pull_in(i.object) ex.object = hive.antenna(i.pull_object) i.length = hive.attribute('int') i.pull_length = hive.pull_out(i.length) ex.length = hive.output(i.pull_object) i.do_length = hive.modifier(do_len) hive.trigger(i.pull_length, i.pull_object, pretrigger=True) hive.trigger(i.pull_object, i.do_length)
def build_convert(i, ex, args, meta_args): i.value_in = hive.variable(meta_args.from_data_type) i.value_out = hive.variable(meta_args.to_data_type) # For push in, push out if meta_args.mode == "push": i.ppin = hive.push_in(i.value_in) i.ppout = hive.push_out(i.value_out) hive.trigger(i.ppin, i.ppout) else: i.ppin = hive.pull_in(i.value_in) i.ppout = hive.pull_out(i.value_out) hive.trigger(i.ppout, i.ppin, pretrigger=True) ex.value_in = hive.antenna(i.ppin) ex.value_out = hive.output(i.ppout) # For casting (explicit conversion) if meta_args.conversion == "cast": to_base_type_name = hive.get_base_data_type(meta_args.to_data_type) value_cls = _type_map[to_base_type_name] def converter(self): self._value_out = value_cls(self._value_in) i.do_conversion = hive.modifier(converter) hive.trigger(i.ppout, i.do_conversion, pretrigger=True) # For duck typing, move value through else: i.move_value = hive.modifier(move_value) hive.trigger(i.ppin, i.move_value)