def set_up_transition_gen(timeline): (old_carry_posture, new_posture, _, transition, var_map) = create_exit_carry_posture(sim, target, interaction, use_posture_animations) if transition is None: yield element_utils.run_child(timeline, sequence) return exited_carry = False if not use_posture_animations: def event_handler_exit_carry(event_data): nonlocal exited_carry exited_carry = True arb = animation.arb.Arb() old_carry_posture.append_exit_to_arb(arb, None, new_posture, var_map, exit_while_holding=True) new_posture.append_transition_to_arb(arb, old_carry_posture, in_xevt_handler=True) ArbElement(arb, master=sim).distribute() interaction.animation_context.register_event_handler(event_handler_exit_carry, handler_id=SCRIPT_EVENT_ID_STOP_CARRY) if callback is not None: interaction.animation_context.register_event_handler(callback, handler_id=SCRIPT_EVENT_ID_STOP_CARRY) def maybe_do_transition(timeline): if not use_posture_animations and not exited_carry: event_handler_exit_carry(None) if callback is not None: callback() if use_posture_animations or exited_carry: interaction_target_was_target = False si_target_was_target = False if interaction.target == target: interaction_target_was_target = True interaction.set_target(None) if old_carry_posture.target_is_transient and si.target == target: si_target_was_target = True si.set_target(None) if carry_system_target is not None: old_carry_posture.carry_system_target = carry_system_target def do_transition(timeline): result = yield element_utils.run_child(timeline, transition) if result: interaction_target_was_target = False si_target_was_target = False new_posture.source_interaction = None return True return False def post_transition(_): if interaction_target_was_target: interaction.set_target(target) if si_target_was_target: si.set_target(target) if carry_system_target is not None: old_carry_posture.carry_system_target = None yield element_utils.run_child(timeline, must_run(build_critical_section_with_finally(do_transition, post_transition))) new_sequence = disable_asm_auto_exit(sim, sequence) yield element_utils.run_child(timeline, build_critical_section(build_critical_section(new_sequence, flush_all_animations), maybe_do_transition))
def set_up_transition_gen(timeline): nonlocal sequence (new_posture_state, new_posture, new_source_aop, var_map) = create_enter_carry_posture(sim, sim.posture_state, obj, track) got_callback = False def event_handler_enter_carry(event_data): nonlocal got_callback if got_callback: logger.warn('Animation({}) calling to start a carry multiple times', event_data.event_data.get('clip_name')) return got_callback = True arb = animation.arb.Arb() locked_params = new_posture.get_locked_params(None) old_carry_posture = sim.posture_state.get_aspect(track) if old_carry_posture is not None: old_carry_posture.append_exit_to_arb(arb, new_posture_state, new_posture, var_map) new_posture.append_transition_to_arb(arb, old_carry_posture, locked_params=locked_params, in_xevt_handler=True) ArbElement(arb).distribute() si.animation_context.register_event_handler(event_handler_enter_carry, handler_id=SCRIPT_EVENT_ID_START_CARRY) def maybe_do_transition_gen(timeline): def push_si_gen(timeline): context = InteractionContext(sim, InteractionContext.SOURCE_POSTURE_GRAPH, si.priority, run_priority=si.run_priority, insert_strategy=QueueInsertStrategy.NEXT, must_run_next=True, group_id=si.group_id) result = new_source_aop.interaction_factory(context) if not result: return result source_interaction = result.interaction new_posture.source_interaction = source_interaction owning_interaction = None if create_si_fn is not None: (aop, context) = create_si_fn() if aop is not None and context is not None and aop.test(context): result = aop.interaction_factory(context) if result: owning_interaction = result.interaction owning_interaction.acquire_posture_ownership(new_posture) aop.execute_interaction(owning_interaction) if owning_interaction is None: si.acquire_posture_ownership(new_posture) yield source_interaction.run_direct_gen(timeline) return result def call_callback(_): if callback is not None: callback(new_posture, new_posture.source_interaction) if got_callback: result = yield element_utils.run_child(timeline, must_run([PostureTransition(new_posture, new_posture_state, context, var_map), push_si_gen, call_callback])) return result return True sequence = disable_asm_auto_exit(sim, sequence) with si.cancel_deferred((si,)): yield element_utils.run_child(timeline, must_run(build_critical_section(build_critical_section(sequence, flush_all_animations), maybe_do_transition_gen)))
def _run(self, timeline): sequence = self.sequence if self.start_outfit_change_and_index is not None: start_change = build_critical_section(self.subject_sim_outfits.get_change_outfit_element(self.start_outfit_change_and_index, do_spin=True), flush_all_animations) sequence = build_critical_section(start_change, sequence) if self.end_outfit_change_and_index is not None: end_change = build_critical_section(self.subject_sim_outfits.get_change_outfit_element(self.end_outfit_change_and_index, do_spin=True), flush_all_animations) end_change_varification = lambda _: self.subject_sim_outfits.exit_change_verification(self.end_outfit_change_and_index) sequence = build_critical_section(sequence, end_change) sequence = build_critical_section_with_finally(sequence, end_change_varification) return timeline.run_child(sequence)
def get_on_entry_change(self, interaction, sim_info=DEFAULT, do_spin=True, **kwargs): if not self.on_entry: return sim_info = interaction.sim.sim_info if sim_info is DEFAULT else sim_info do_spin &= self.on_entry.do_spin for trait in sim_info.get_traits(): outfit_change_reason = trait.get_outfit_change_reason(None) if outfit_change_reason is not None: return sim_info.get_outfit_change(interaction, outfit_change_reason, do_spin=do_spin, **kwargs) (category, index) = self.on_entry.outfit_to_modify(sim_info, self.on_entry.generator) return build_critical_section( sim_info.get_change_outfit_element_and_archive_change_reason( (category, index), do_spin=do_spin, interaction=interaction, change_reason=interaction, **kwargs), flush_all_animations)
def exit_clothing_change(self, interaction, *, sim=DEFAULT, do_spin=True, **kwargs): if self._saved_exit_clothing_change is None or interaction is None: return if sim is DEFAULT: sim = interaction.sim sim_info = sim.sim_info return build_critical_section(sim_info.sim_outfits.get_change_outfit_element(self._saved_exit_clothing_change, do_spin=do_spin), flush_all_animations)
def unholster_object(carry_posture, flush_before_sequence=False, sequence=None): carry_object = carry_posture.target def _set_unholster(): carry_posture.holstered = False return True def unholster(timeline): arb_unholster = animation.arb.Arb() def start_carry(*_, **__): idle_arb = animation.arb.Arb() carry_posture.asm.request(carry_posture._state_name, idle_arb) ArbElement(idle_arb).distribute() arb_unholster.register_event_handler(start_carry, handler_id=SCRIPT_EVENT_ID_START_CARRY) carry_posture.asm.context.register_custom_event_handler(functools.partial(hide_held_props, carry_posture.sim), None, 0, allow_stub_creation=True) carry_posture.asm.set_current_state('entry') carry_posture.asm.request(carry_posture._enter_state_name, arb_unholster) unholster_element = create_run_animation(arb_unholster) if flush_before_sequence: unholster_element = (unholster_element, flush_all_animations) yield element_utils.run_child(timeline, unholster_element) return build_critical_section(interact_with_carried_object(carry_posture.sim, carry_object, animation_context=carry_posture.asm.context, interaction=carry_posture.source_interaction, must_run=True, sequence=build_critical_section(unholster, lambda _: _set_unholster())), sequence, flush_all_animations)
def holster_object(carry_posture, flush_before_sequence=False, sequence=None): carry_object = carry_posture.target def _set_holster(): carry_posture.holstered = True return True import postures.posture_interactions carry_nothing_posture = create_posture(postures.posture_interactions.HoldNothing.CARRY_NOTHING_POSTURE_TYPE, carry_posture.sim, None, track=carry_posture.track) def holster(timeline): def stop_carry(*_, **__): idle_arb = animation.arb.Arb() carry_nothing_posture.asm.request(carry_nothing_posture._state_name, idle_arb) ArbElement(idle_arb).distribute() arb_holster = animation.arb.Arb() arb_holster.register_event_handler(stop_carry, handler_id=SCRIPT_EVENT_ID_STOP_CARRY) carry_posture.asm.context.register_custom_event_handler(functools.partial(hide_held_props, carry_posture.sim), None, 0, allow_stub_creation=True) setup_asm_fn_carry = _get_holstering_setup_asm_func(carry_posture, carry_object) setup_asm_fn_carry(carry_posture.asm) carry_posture.asm.request(carry_posture._exit_state_name, arb_holster) carry_nothing_posture.setup_asm_posture(carry_nothing_posture.asm, carry_nothing_posture.sim, None) setup_asm_fn_carry_nothing = _get_holstering_setup_asm_func(carry_nothing_posture, carry_object) setup_asm_fn_carry_nothing(carry_nothing_posture.asm) carry_nothing_posture.asm.request(carry_nothing_posture._enter_state_name, arb_holster) holster_element = create_run_animation(arb_holster) if flush_before_sequence: holster_element = (holster_element, flush_all_animations) yield element_utils.run_child(timeline, holster_element) return (lambda _: _set_holster(), build_critical_section(interact_with_carried_object(carry_posture.sim, carry_object, interaction=carry_posture.source_interaction, animation_context=carry_posture.asm.context, must_run=True, sequence=holster), sequence, flush_all_animations))
def get_auto_exit(actors, asm=None, interaction=None, required_actors=()): arb_exit = None contexts_to_release_all = [] for actor in actors: if actor.is_sim: if actor.asm_auto_exit.asm is not None: asm_to_exit = actor.asm_auto_exit.asm[0] if asm_to_exit is asm: continue if required_actors: asm_actors = set(asm_to_exit.actors_gen()) if not all(a in asm_actors for a in required_actors): continue else: if arb_exit is None: arb_exit = animation.arb.Arb() if interaction is not None: if gsi_handlers.interaction_archive_handlers.is_archive_enabled(interaction): prev_state = asm_to_exit.current_state try: asm_to_exit.request('exit', arb_exit, debug_context=(interaction, asm)) finally: if gsi_handlers.interaction_archive_handlers.is_archive_enabled(interaction): gsi_handlers.interaction_archive_handlers.add_animation_data(interaction, asm_to_exit, prev_state, 'exit', 'arb_exit is empty' if arb_exit.empty else arb_exit.get_contents_as_string()) contexts_to_release = release_auto_exit(actor) contexts_to_release_all.extend(contexts_to_release) release_contexts_fn = get_release_contexts_fn(contexts_to_release_all, AUTO_EXIT_REF_TAG) if arb_exit is not None and not arb_exit.empty: element = build_critical_section_with_finally(build_critical_section(create_run_animation(arb_exit), flush_all_animations), release_contexts_fn) return must_run(element) elif contexts_to_release_all: return must_run(build_element(release_contexts_fn))
def conditional_animation(interaction, value, xevt_id, animation): target = interaction.target did_set = False kill_handler = False def check_fn(): return target.get_state(value.state).value != value.value def set_fn(_): nonlocal did_set if did_set: return target.set_state(value.state, value) did_set = True if animation is None: return maybe(check_fn, set_fn) def set_handler(*_, **__): if kill_handler: return set_fn(None) def setup_asm(asm): if xevt_id is not None: asm.context.register_event_handler(set_handler, handler_id=xevt_id) def cleanup_asm(asm): nonlocal kill_handler if xevt_id is not None: kill_handler = True return maybe(check_fn, build_critical_section(animation(interaction, setup_asm=setup_asm, cleanup_asm=cleanup_asm), flush_all_animations, set_fn))
def build_basic_elements(self, sequence=()): sequence = super().build_basic_elements(sequence=sequence) if self.xevt_id is None: outfit = self.sim.get_current_outfit() generate_outfit_fn = functools.partial(self._generate_outfit, self.sim.sim_info, self.outfit_change_category, outfit_index=0, tag_list=self.outfit_tags) if outfit == (self.outfit_change_category, 0): self.sim.sim_info.set_outfit_dirty(outfit[0]) generate_outfit_element = lambda _: generate_outfit_fn() else: generate_outfit_element = None generate_outfit_fn() new_outfit = self.outfit_change_type.get_outfit_for_clothing_change(self.sim.sim_info, self.outfit_change_category) sequence = build_critical_section(sequence, self.sim.sim_info.get_change_outfit_element_and_archive_change_reason(new_outfit, interaction=self, change_reason=self), flush_all_animations) return build_critical_section(sequence, generate_outfit_element) else: outfit_change_element = _XevtOutfitChangeElement(self, sequence, self.xevt_id, self.outfit_change_category, self.outfit_tags, self.filter_flag, self.body_type_chance_overrides, self.body_type_match_not_found_policy) return outfit_change_element
def unholster_object(carry_posture, flush_before_sequence=False, sequence=None): carry_object = carry_posture.target def _set_unholster(): carry_posture.holster_count = 0 return True def unholster(timeline): if carry_object.is_sim: return if not carry_posture.holster_count: return arb_unholster = animation.arb.Arb() def start_carry(*_, **__): idle_arb = animation.arb.Arb() carry_posture.asm.request(carry_posture._state_name, idle_arb) distribute_arb_element(idle_arb) arb_unholster.register_event_handler( start_carry, handler_id=SCRIPT_EVENT_ID_START_CARRY) carry_posture.asm.context.register_custom_event_handler( functools.partial(hide_held_props, carry_posture.sim), None, 0, allow_stub_creation=True) carry_posture.asm.set_current_state('entry') carry_posture.asm.request(carry_posture._enter_state_name, arb_unholster) unholster_element = create_run_animation(arb_unholster) if flush_before_sequence: unholster_element = (unholster_element, flush_all_animations) yield from element_utils.run_child(timeline, unholster_element) return build_critical_section( interact_with_carried_object( carry_posture.sim, carry_object, animation_context=carry_posture.asm.context, interaction=carry_posture.source_interaction, must_run=True, sequence=build_critical_section(unholster, lambda _: _set_unholster())), sequence, flush_all_animations)
def get_on_entry_change(self, interaction, sim=DEFAULT, **kwargs): sim_info = interaction.sim.sim_info if sim is DEFAULT else sim.sim_info for trait in sim_info.trait_tracker: outfit_change_reason = trait.get_outfit_change_reason(None) while outfit_change_reason is not None: return sim_info.sim_outfits.get_change(interaction, outfit_change_reason, sim=sim, **kwargs) sim_info.generate_outfit(OutfitCategory.SPECIAL, 0, tag_list=self.tag_set) return build_critical_section(sim_info.sim_outfits.get_change_outfit_element((OutfitCategory.SPECIAL, 0), **kwargs), flush_all_animations)
def build_basic_elements(self, sequence=()): sequence = super().build_basic_elements(sequence=sequence) outfit_category_and_index = (self.outfit_category, self.outfit_index) exit_change = build_critical_section( sequence, self.sim.sim_info.sim_outfits.get_change_outfit_element( outfit_category_and_index, do_spin=True), flush_all_animations) return exit_change
def crafting_sequence(timeline): nonlocal sequence sequence = super_build_basic_content(sequence, **kwargs) sequence = build_critical_section(sequence, flush_all_animations) sequence = self._build_sequence_with_callback(callback, sequence=sequence) result = yield from element_utils.run_child(timeline, sequence) return result yield
def _run_interaction_gen(self, timeline): result = yield from element_utils.run_child( timeline, build_critical_section_with_finally( self._start_route_goal_suppression, build_critical_section( build_critical_section( self.ensure_state(self.affordance.required_channel), objects.components.state.with_on_state_changed( self.target, self.affordance.required_channel.state, self._changed_state_callback, super()._run_interaction_gen)), maybe( lambda: len(self.target.get_users(sims_only=True)) == 1, self.ensure_state(self.off_channel))), self._stop_route_goal_suppression)) return result yield
def holster_object(carry_posture, flush_before_sequence=False, sequence=None): carry_object = carry_posture.target def _set_holster(): carry_posture.holstered = True return True import postures.posture_interactions carry_nothing_posture = create_posture( postures.posture_interactions.HoldNothing.CARRY_NOTHING_POSTURE_TYPE, carry_posture.sim, None, track=carry_posture.track) def holster(timeline): def stop_carry(*_, **__): idle_arb = animation.arb.Arb() carry_nothing_posture.asm.request( carry_nothing_posture._state_name, idle_arb) ArbElement(idle_arb).distribute() arb_holster = animation.arb.Arb() arb_holster.register_event_handler( stop_carry, handler_id=SCRIPT_EVENT_ID_STOP_CARRY) carry_posture.asm.context.register_custom_event_handler( functools.partial(hide_held_props, carry_posture.sim), None, 0, allow_stub_creation=True) setup_asm_fn_carry = _get_holstering_setup_asm_func( carry_posture, carry_object) setup_asm_fn_carry(carry_posture.asm) carry_posture.asm.request(carry_posture._exit_state_name, arb_holster) carry_nothing_posture.setup_asm_posture(carry_nothing_posture.asm, carry_nothing_posture.sim, None) setup_asm_fn_carry_nothing = _get_holstering_setup_asm_func( carry_nothing_posture, carry_object) setup_asm_fn_carry_nothing(carry_nothing_posture.asm) carry_nothing_posture.asm.request( carry_nothing_posture._enter_state_name, arb_holster) holster_element = create_run_animation(arb_holster) if flush_before_sequence: holster_element = (holster_element, flush_all_animations) yield element_utils.run_child(timeline, holster_element) return (lambda _: _set_holster(), build_critical_section( interact_with_carried_object( carry_posture.sim, carry_object, interaction=carry_posture.source_interaction, animation_context=carry_posture.asm.context, must_run=True, sequence=holster), sequence, flush_all_animations))
def _get_outfit_change(self, interaction, sim_info=DEFAULT, **kwargs): outfit = self._get_outfit(interaction) if outfit is not None: sim_info = interaction.sim.sim_info if sim_info is DEFAULT else sim_info return build_critical_section( sim_info. get_change_outfit_element_and_archive_change_reason( outfit, interaction=interaction, change_reason=interaction, **kwargs), flush_all_animations)
def _run_interaction_gen(self, timeline): result = yield from element_utils.run_child( timeline, build_critical_section( self.ensure_state(self.required_station), objects.components.state.with_on_state_changed( self.target, self.required_station.state, self._changed_state_callback, super()._run_interaction_gen))) return result yield
def enter_carry(timeline): result = yield from element_utils.run_child( timeline, enter_carry_while_holding( self.interaction, obj=self.interaction.created_target, carry_track_override=self.location.carry_track_override, owning_affordance=None, sequence=build_critical_section(sequence, flush_all_animations))) return result yield
def disable_asm_auto_exit(sim, sequence): was_locked = None def lock(_): nonlocal was_locked was_locked = sim.asm_auto_exit.locked sim.asm_auto_exit.locked = True def unlock(_): sim.asm_auto_exit.locked = was_locked return build_critical_section(lock, sequence, unlock)
def with_event_handlers(animation_context, handler, clip_event_type, sequence=None, tag=None): handle = None def begin(_): nonlocal handle handle = animation_context.register_event_handler(handler, clip_event_type, tag=tag) def end(_): if handle is not None: handle.release() return build_critical_section(begin, sequence, end)
def _run(self, timeline): sequence = self._sequence def register_xevt(_): self._xevt_handle = self._interaction.animation_context.register_event_handler(lambda _: self._run_xevt_outfit_change(), handler_id=self._xevt_id) def release_xevt(_): self._xevt_handle.release() self._xevt_handle = None sequence = build_critical_section(register_xevt, sequence, release_xevt) return timeline.run_child(sequence)
def _run(self, timeline): sequence = self.sequence resolver = self.interaction.get_resolver() if self.tests and not self.tests.run_tests(resolver): return timeline.run_child(sequence) if self.entry_outfit is not None: sequence = build_critical_section( self.outfit_change.get_on_entry_change(self.interaction, sim_info=self.sim_info), sequence) if self.exit_outfit is not None: def on_oufit_change_exit(_): if self.sim_info._current_outfit != self.exit_outfit and self.outfit_change_exit_test.run_tests( resolver): self.sim_info.set_current_outfit(self.exit_outfit) sequence = build_critical_section_with_finally( build_critical_section( sequence, maybe( lambda: self.outfit_change_exit_test.run_tests(resolver ), self.outfit_change.get_on_exit_change( self.interaction, sim_info=self.sim_info))), on_oufit_change_exit) if self.xevt_outfit is not None: def register_xevt(_): self._xevt_handle = self.interaction.animation_context.register_event_handler( lambda _: self._run_xevt_outfit_change(), handler_id=self.xevt_outfit_change.xevt_id) def release_xevt(_): self._xevt_handle.release() self._xevt_handle = None sequence = build_critical_section(register_xevt, sequence, release_xevt) return timeline.run_child(sequence)
def enter_carry(timeline): result = yield element_utils.run_child( timeline, enter_carry_while_holding( self, self.created_target, callback=claim_object, create_si_fn=self._get_create_continuation_affordance(), track=self.track, sequence=build_critical_section( super_build_basic_content(sequence, **kwargs), flush_all_animations))) return result
def get_idle_behavior(self): if self.idle_animation is None: logger.error('{} has no idle animation tuning! This tuning is required for all body postures!', self) return if self.source_interaction is None: logger.error('Posture({}) on sim:{} has no source interaction.', self, self.sim, owner='Maxr', trigger_breakpoint=True) return if self.owning_interactions and not self.multi_sim: interaction = list(self.owning_interactions)[0] else: interaction = self.source_interaction idle = self.idle_animation(interaction) auto_exit = get_auto_exit((self.sim,), asm=idle.get_asm()) return build_critical_section(auto_exit, idle, flush_all_animations)
def get_outfit_change(self, interaction, change_reason, resolver=None, **kwargs): if change_reason is not None: outfit_category_and_index = self.get_outfit_for_clothing_change( interaction, change_reason, resolver=resolver) return build_critical_section( self.get_change_outfit_element_and_archive_change_reason( outfit_category_and_index, interaction=interaction, change_reason=change_reason, **kwargs), flush_all_animations)
def behavior_element(self, timeline): total_constraint = ANYWHERE for (relative_participant, constraints) in self.route_constraints.items(): relative_object = self.interaction.get_participant( relative_participant) if relative_object is None: continue for constraint in constraints: relative_constraint = constraint.create_constraint( self.interaction.sim, relative_object, objects_to_ignore=[relative_object]) total_constraint = total_constraint.intersect( relative_constraint) if not total_constraint.valid: logger.error( 'Routing Element cannot resolve constraints for {}', self.interaction) return False yield sim = self.interaction.sim goals = [] handles = total_constraint.get_connectivity_handles(sim) for handle in handles: goals.extend(handle.get_goals()) if not goals: return False yield route = routing.Route(sim.routing_location, goals, routing_context=sim.routing_context) plan_primitive = PlanRoute(route, sim, interaction=self.interaction) result = yield from element_utils.run_child(timeline, plan_primitive) if not result: return False yield if not (plan_primitive.path.nodes and plan_primitive.path.nodes.plan_success): return False yield route = get_route_element_for_path(sim, plan_primitive.path, interaction=self.interaction) result = yield from element_utils.run_child( timeline, build_critical_section(route)) return result yield
def _factory(interaction, life_event_category, participants, sequence=None, **kwargs): def trigger(_): msg = Social_pb2.LifeEventMessage() msg.type = life_event_category participant_ids = [] for participant_types in participants: participant = interaction.get_participant(participant_types) if participant is None: participant_ids.append(0) else: participant_ids.append(participant.id) msg.sim_ids.extend(participant_ids) distributor = Distributor.instance() distributor.add_op_with_no_owner(GenericProtocolBufferOp(Operation.LIFE_EVENT_SEND, msg)) return build_critical_section(sequence, trigger)
def _run(self, timeline): if self.timing == self.AT_BEGINNING: if self.offset_time is None: sequence = [self._behavior_element, self.sequence] else: delayed_sequence = build_element([elements.SleepElement(clock.interval_in_sim_minutes(self.offset_time)), self._behavior_element]) if self.sequence: sequence = elements.AllElement([delayed_sequence, self.sequence]) else: sequence = delayed_sequence elif self.timing == self.AT_END: sequence = [self.sequence, self._behavior_element] elif self.timing == self.ON_XEVT: sequence = [build_critical_section(self._register_event_handler, self.sequence, self._release_event_handler), self._behavior_element] child_element = build_element(sequence, critical=self.criticality) child_element = self._build_outer_elements(child_element) return timeline.run_child(child_element)
def get_on_entry_change(self, interaction, sim_info=DEFAULT, **kwargs): sim_info = interaction.sim.sim_info if sim_info is DEFAULT else sim_info for trait in sim_info.get_traits(): outfit_change_reason = trait.get_outfit_change_reason(None) if outfit_change_reason is not None: return sim_info.get_outfit_change(interaction, outfit_change_reason, **kwargs) outfit_change = self._get_outfit_change_internal( interaction, sim_info) if outfit_change is not None: return build_critical_section( sim_info. get_change_outfit_element_and_archive_change_reason( outfit_change.entry_outfit, interaction=interaction, change_reason=interaction, **kwargs), flush_all_animations)
def get_on_exit_change(self, interaction, sim_info=DEFAULT, **kwargs): sim_info = interaction.sim.sim_info if sim_info is DEFAULT else sim_info if not self.on_exit and self.on_entry is not None and self.on_entry.auto_undo_on_exit: return sim_info.get_outfit_change( interaction, OutfitChangeReason.CurrentOutfit, **kwargs) if self.on_exit: choice = self.choose_on_exit_clothing_change(sim_info) if choice is None: return else: (category, index) = choice.outfit_to_modify(sim_info, choice.generator) return build_critical_section( sim_info. get_change_outfit_element_and_archive_change_reason( (category, index), interaction=interaction, change_reason=interaction, **kwargs), flush_all_animations)
def build_basic_content(self, sequence=(), *args, **kwargs): def _perform_teleport(timeline): active_multiplier = self.sim.sim_info.get_active_teleport_multiplier( ) (teleport_style_data, cost) = self.sim.sim_info.get_teleport_data_and_cost( self.teleport_style_tuning, active_multiplier) (sequence, animation_interaction ) = TeleportHelper.generate_teleport_sequence( self.sim, teleport_style_data, self._teleport_location.position, self._teleport_location.orientation, self._teleport_location.routing_surface, cost) if sequence is not None and animation_interaction is not None: try: result = yield from element_utils.run_child( timeline, element_utils.build_critical_section( sequence, flush_all_animations)) finally: animation_interaction.on_removed_from_queue() return result yield def _set_up_teleport_style_interaction(_): if self._destination_jig_object is not None: self.sim.routing_context.ignore_footprint_contour( self._destination_jig_object.routing_context. object_footprint_id) def _clean_up_teleport_style_interaction(_): self._try_destroy_jig_object() sequence = element_utils.build_critical_section( sequence, _perform_teleport) sequence = super().build_basic_content(sequence, **kwargs) sequence = element_utils.build_critical_section_with_finally( _set_up_teleport_style_interaction, sequence, _clean_up_teleport_style_interaction) return sequence
def _perform_teleport(timeline): active_multiplier = self.sim.sim_info.get_active_teleport_multiplier( ) (teleport_style_data, cost) = self.sim.sim_info.get_teleport_data_and_cost( self.teleport_style_tuning, active_multiplier) (sequence, animation_interaction ) = TeleportHelper.generate_teleport_sequence( self.sim, teleport_style_data, self._teleport_location.position, self._teleport_location.orientation, self._teleport_location.routing_surface, cost) if sequence is not None and animation_interaction is not None: try: result = yield from element_utils.run_child( timeline, element_utils.build_critical_section( sequence, flush_all_animations)) finally: animation_interaction.on_removed_from_queue() return result yield
def conditional_animation(interaction, value, xevt_id, animation): target = interaction.target did_set = False kill_handler = False def check_fn(): return target.get_state(value.state).value != value.value def set_fn(_): nonlocal did_set if did_set: return target.set_state(value.state, value) did_set = True if animation is None: return maybe(check_fn, set_fn) def set_handler(*_, **__): if kill_handler: return set_fn(None) def setup_asm(asm): if xevt_id is not None: asm.context.register_event_handler(set_handler, handler_id=xevt_id) def cleanup_asm(asm): nonlocal kill_handler if xevt_id is not None: kill_handler = True return maybe( check_fn, build_critical_section( animation(interaction, setup_asm=setup_asm, cleanup_asm=cleanup_asm), flush_all_animations, set_fn))
def _run(self, timeline): if not self._should_do_behavior: return timeline.run_child(build_element(self.sequence)) if self.timing == self.AT_BEGINNING: if self.offset_time is None: sequence = [self._behavior_element, self.sequence] else: sequence = build_delayed_element(self.sequence, clock.interval_in_sim_minutes( self.offset_time), self._behavior_element, soft_sleep=True) elif self.timing == self.AT_END: sequence = [self.sequence, self._behavior_element] elif self.timing == self.ON_XEVT: sequence = [ build_critical_section(self._register_event_handler, self.sequence, self._release_event_handler), self._behavior_element ] child_element = build_element(sequence, critical=self.criticality) child_element = self._build_outer_elements(child_element) return timeline.run_child(child_element)
def build_basic_elements(self, sequence=()): sequence = super().build_basic_elements(sequence=sequence) outfit_category_and_index = (self.outfit_category, self.outfit_index) exit_change = build_critical_section(sequence, self.sim.sim_info.sim_outfits.get_change_outfit_element(outfit_category_and_index, do_spin=True), flush_all_animations) return exit_change
def set_up_transition(timeline): (original_carry_posture, carry_nothing_posture, carry_nothing_posture_state, transition_to_carry_nothing, carry_nothing_var_map) = create_exit_carry_posture(sim, original_carry_target, interaction, False) if transition_to_carry_nothing is None: return False (final_posture_state, final_posture, final_source_aop, final_var_map) = create_enter_carry_posture(sim, carry_nothing_posture_state, new_carry_object, original_carry_posture.track) got_callback = False def event_handler_swap_carry(event_data): nonlocal got_callback if got_callback: logger.warn('Animation({}) calling to start a carry multiple times', event_data.event_data.get('clip_name')) return got_callback = True arb_exit = animation.arb.Arb() original_carry_posture.append_exit_to_arb(arb_exit, None, carry_nothing_posture, carry_nothing_var_map, exit_while_holding=True) carry_nothing_posture.append_transition_to_arb(arb_exit, original_carry_posture, in_xevt_handler=True) ArbElement(arb_exit).distribute() original_carry_posture.target.transient = True original_carry_posture.target.clear_parent(sim.transform, sim.routing_surface) original_carry_posture.target.remove_from_client() arb_enter = animation.arb.Arb() locked_params = final_posture.get_locked_params(None) if carry_nothing_posture is not None: carry_nothing_posture.append_exit_to_arb(arb_enter, final_posture_state, final_posture, final_var_map) final_posture.append_transition_to_arb(arb_enter, carry_nothing_posture, locked_params=locked_params, in_xevt_handler=True) ArbElement(arb_enter).distribute() interaction.animation_context.register_event_handler(event_handler_swap_carry, handler_id=SCRIPT_EVENT_ID_START_CARRY) if callback is not None: interaction.animation_context.register_event_handler(callback, handler_id=SCRIPT_EVENT_ID_START_CARRY) def maybe_do_transition(timeline): def push_si(_): context = InteractionContext(sim, InteractionContext.SOURCE_POSTURE_GRAPH, si.priority, run_priority=si.run_priority, insert_strategy=QueueInsertStrategy.NEXT, must_run_next=True, group_id=si.group_id) result = final_source_aop.interaction_factory(context) if not result: return result final_source_interaction = result.interaction si.acquire_posture_ownership(final_posture) yield final_source_interaction.run_direct_gen(timeline) final_posture.source_interaction = final_source_interaction return result if not got_callback: event_handler_swap_carry(None) if callback is not None: callback() if original_carry_posture.target_is_transient: if interaction.target == original_carry_target: interaction_target_was_target = True interaction.set_target(None) else: interaction_target_was_target = False if si.target == original_carry_target: si_target_was_target = True si.set_target(None) else: si_target_was_target = False else: interaction_target_was_target = False si_target_was_target = False if carry_system_target is not None: original_carry_posture.carry_system_target = carry_system_target def do_transition(timeline): nonlocal interaction_target_was_target, si_target_was_target result = yield element_utils.run_child(timeline, transition_to_carry_nothing) if not result: return False interaction_target_was_target = False si_target_was_target = False carry_nothing_posture.source_interaction = None return True def post_transition(_): if interaction_target_was_target: interaction.set_target(original_carry_target) if si_target_was_target: si.set_target(original_carry_target) if carry_system_target is not None: original_carry_posture.carry_system_target = None exit_carry_result = yield element_utils.run_child(timeline, must_run(build_critical_section_with_finally(do_transition, post_transition))) if not (got_callback and exit_carry_result): raise RuntimeError('[maxr] Failed to exit carry: {}'.format(original_carry_posture)) if got_callback: context = si.context.clone_for_sim(sim) yield element_utils.run_child(timeline, (PostureTransition(final_posture, final_posture_state, context, final_var_map), push_si)) new_sequence = disable_asm_auto_exit(sim, sequence) yield element_utils.run_child(timeline, build_critical_section(build_critical_section(new_sequence, flush_all_animations), maybe_do_transition))
def enter_carry(timeline): result = yield element_utils.run_child(timeline, enter_carry_while_holding(self, self.created_target, callback=claim_object, create_si_fn=self._get_create_continuation_affordance(), track=self.track, sequence=build_critical_section(super_build_basic_content(sequence, **kwargs), flush_all_animations))) return result
def _run_interaction_gen(self, timeline): result = yield element_utils.run_child(timeline, build_critical_section_with_finally(self._start_route_goal_suppression, build_critical_section(build_critical_section(self.ensure_state(self.affordance.required_channel), objects.components.state.with_on_state_changed(self.target, self.affordance.required_channel.state, self._changed_state_callback, super()._run_interaction_gen)), maybe(lambda : len(self.target.get_users(sims_only=True)) == 1, self.ensure_state(Television.TV_OFF_STATE))), self._stop_route_goal_suppression)) return result
def _run_interaction_gen(self, timeline): result = yield element_utils.run_child(timeline, build_critical_section(self.ensure_state(self.affordance.required_station), objects.components.state.with_on_state_changed(self.target, self.affordance.required_station.state, self._changed_state_callback, super()._run_interaction_gen))) return result
def _get_behavior(self): posture = self._posture sim = posture.sim multi_sim_posture_transition = posture.multi_sim and not posture.is_puppet prev_posture_state = sim.posture_state self._prev_posture = prev_posture_state.get_aspect(posture.track) animate_in = None if multi_sim_posture_transition or self._animate_in is not None and not self._animate_in.empty: animate_in = create_run_animation(self._animate_in) my_stage = self._stage() def posture_change(timeline): posture.log_info('Change', msg='{}'.format(posture.track.name if posture.track is not None else 'NO TRACK!')) prev_posture_state = sim.posture_state prev_posture = prev_posture_state.get_aspect(posture.track) sim.posture_state = self._dest_state sim.on_posture_event(PostureEvent.POSTURE_CHANGED, self._dest_state, posture.track, prev_posture, posture) yield sim.si_state.notify_posture_change_and_remove_incompatible_gen(timeline, prev_posture_state, self._dest_state) prev_posture.clear_owning_interactions() if multi_sim_posture_transition: linked_posture_begin = posture.linked_posture.begin(self._animate_in, self._dest_state.linked_posture_state, posture._context) self._dest_state = None yield element_utils.run_child(timeline, linked_posture_begin) else: self._dest_state = None return True def end_posture_on_same_track(timeline): if self._prev_posture is not None and self._prev_posture is not posture: prev_posture = self._prev_posture self._prev_posture = None result = yield element_utils.run_child(timeline, build_element(prev_posture.end())) return result return True if services.current_zone().animate_instantly: flush = flush_all_animations_instantly else: flush = flush_all_animations sequence = (posture_change, animate_in, flush, end_posture_on_same_track, my_stage) sequence = build_element(sequence, critical=CleanupType.RunAll) sequence = build_critical_section_with_finally(sequence, lambda _: posture._release_animation_context()) if self._posture.jig is not None and self._posture.target is not None and self._posture.slot_constraint is not None: def create_and_place_jig(_): self._jig = objects.system.create_object(self._posture.jig) for constraint in self._posture.slot_constraint: self._jig.transform = constraint.containment_transform break sim.routing_context.ignore_footprint_contour(self._jig.routing_context.object_footprint_id) def destroy_jig(_): if self._jig is not None: sim.routing_context.remove_footprint_contour_override(self._jig.routing_context.object_footprint_id) self._jig.destroy(source=self, cause='Destroying jig for posture.') sequence = build_critical_section_with_finally(create_and_place_jig, sequence, destroy_jig) sequence = elements.GeneratorElement(self.with_censor_grid(sim, sequence)) if posture.target is not None: reserver = create_reserver(sim, posture.target, reserver=posture, handler=MultiReserveObjectHandler) sequence = reserver.do_reserve(sequence=sequence) def stage_on_fail(timeline): if not self.has_staged: yield element_utils.run_child(timeline, self._stage_fail()) sequence = element_utils.build_critical_section(sequence, stage_on_fail) sequence = maybe(posture.test, sequence) return sequence
def get_change(self, interaction, change_reason, sim=DEFAULT, **kwargs): if change_reason is not None: return build_critical_section(self.get_clothing_change(interaction, change_reason, **kwargs), flush_all_animations)
def _build_outcome_sequence(self, *args, **kwargs): sequence = super()._build_outcome_sequence(*args, **kwargs) return element_utils.build_critical_section(self._name_and_create_adoptee_gen, sequence)