def _apply_to_subject_and_target(self, subject, target, resolver): bucks_multiplier = self._bucks_multipliers.get_multiplier(resolver) for buck_type_tuning in self._bucks_types: amount = BucksRecycling.get_recycling_value_for_object( buck_type_tuning.buck_type, target) if amount == 0: continue final_multiplier = bucks_multiplier * buck_type_tuning.buck_multiplier.get_multiplier( resolver) amount *= final_multiplier tracker = BucksUtils.get_tracker_for_bucks_type( buck_type_tuning.buck_type, owner_id=subject.id, add_if_none=True) if tracker is None: logger.error( 'Attempting to apply a BucksLoot op to the subject {} of amount {} but they have no tracker for that bucks type {}.', subject, amount, buck_type_tuning.buck_type) else: result = tracker.try_modify_bucks(buck_type_tuning.buck_type, int(amount)) if not result: logger.error( "Failed to modify the Sim {}'s bucks of type {} by amount {}.", subject, buck_type_tuning.buck_type, self._amount) resolver = SingleActorAndObjectResolver(subject, target, self) for loot_action in target.recycling_data.recycling_loot: loot_action.apply_to_resolver(resolver)
def modify_influence(self, sim_info, delta): if delta == 0: return tracker = BucksUtils.get_tracker_for_bucks_type(self.INFLUENCE_BUCK_TYPE, owner_id=sim_info.id, add_if_none=True) if tracker is None: return tracker.try_modify_bucks(self.INFLUENCE_BUCK_TYPE, delta)
def max_funds(self, sim, *args): sim_id = None if sim is None else sim.id tracker = BucksUtils.get_tracker_for_bucks_type( self.bucks_type, sim_id) if tracker is None: return 0 return tracker.get_bucks_amount_for_type(self.bucks_type)
def _on_rank_down(self): current_rank = self.rank_level self.send_rank_change_update_message(current_rank + 1, current_rank) sim_info = self.tracker.owner.sim_info rank_data = self.rank_tuning.get(current_rank) rank_down_data = self.rank_down_notification_tuning.get(current_rank) if rank_data is None: logger.error( 'Sim {}: {} is trying to rank down to level {} but there is no rank tuning.', sim_info, self, current_rank) return if self.can_show_notification(rank_down_data): if rank_down_data.rank_down_notification is not None: notification = rank_down_data.rank_down_notification( sim_info, resolver=SingleSimResolver(sim_info)) icon_override = None if rank_data.icon is None else IconInfoData( icon_resource=rank_data.icon) notification.show_dialog(icon_override=icon_override, secondary_icon_override=IconInfoData( obj_instance=sim_info), additional_tokens=(current_rank, )) if rank_down_data.rank_down_screen_slam is not None: rank_down_data.rank_down_screen_slam.send_screen_slam_message( sim_info, sim_info, rank_data.rank_name, current_rank) for bucks_type in self.associated_bucks_types: bucks_tracker = BucksUtils.get_tracker_for_bucks_type( bucks_type, owner_id=self.tracker.owner.id) bucks_tracker.validate_perks(bucks_type, self.rank_level)
def reset_bucks(self): for bucks_type in self.associated_bucks_types: bucks_tracker = BucksUtils.get_tracker_for_bucks_type( bucks_type, self.tracker.owner.id) if bucks_tracker is not None: bucks_tracker.try_modify_bucks( bucks_type, -bucks_tracker.get_bucks_amount_for_type(bucks_type))
def get_bucks_tracker(bucks_type, owner_id, _connection, add_if_none=False): tracker = BucksUtils.get_tracker_for_bucks_type(bucks_type, owner_id, add_if_none=add_if_none) if tracker is None: sims4.commands.output( 'Unable to find bucks tracker to unlock perk for Buck Type {} using Owner ID {}.' .format(get_short_buck_type(bucks_type), owner_id), _connection) return tracker
def request_bucks_amounts(owner_id: int = None, _connection=None): for bucks_type in get_bucks_types_without_invalid_gen(): tracker = BucksUtils.get_tracker_for_bucks_type(bucks_type, owner_id) bucks_amount_string = 'No Tracker Found' if tracker is not None: bucks_amount_string = '{} bucks'.format( tracker.get_bucks_amount_for_type(bucks_type)) sims4.commands.output( '{} : {}'.format(get_short_buck_type(bucks_type), bucks_amount_string), _connection)
def generate_bucks_perks_view(sim_id: int = None, filter=None): filter_list = parse_filter_to_list(filter) bucks_perks_data = [] perks_instance_manager = services.get_instance_manager( sims4.resources.Types.BUCKS_PERK) previous_bucks_type = None for perk in perks_instance_manager.types.values(): if perk.associated_bucks_type != previous_bucks_type: perk_specific_bucks_tracker = BucksUtils.get_tracker_for_bucks_type( perk.associated_bucks_type, sim_id) previous_bucks_type = perk.associated_bucks_type if 'Unlocked Only' in filter_list: if not perk_specific_bucks_tracker is None: if not perk_specific_bucks_tracker.is_perk_unlocked(perk): continue if len(filter_list) > 1 and str( perk.associated_bucks_type) not in filter_list: continue bucks_perks_data.append({ 'sim_id': str(sim_id), 'name': perk.__name__, 'bucks_type': str(perk.associated_bucks_type), 'bucks_type_value': int(perk.associated_bucks_type), 'bucks_tracker_name': str(perk_specific_bucks_tracker), 'is_unlocked': perk_specific_bucks_tracker.is_perk_unlocked(perk) if perk_specific_bucks_tracker is not None else False }) elif str(perk.associated_bucks_type) not in filter_list: continue bucks_perks_data.append({ 'sim_id': str(sim_id), 'name': perk.__name__, 'bucks_type': str(perk.associated_bucks_type), 'bucks_type_value': int(perk.associated_bucks_type), 'bucks_tracker_name': str(perk_specific_bucks_tracker), 'is_unlocked': perk_specific_bucks_tracker.is_perk_unlocked(perk) if not filter_list is not None or perk_specific_bucks_tracker is not None else False }) return bucks_perks_data
def __call__(self, test_targets=(), bucks_data=None, objective_guid64=None, tooltip=None): for target in test_targets: current_bucks = 0 bucks_tracker = BucksUtils.get_tracker_for_bucks_type(self.bucks_type, owner_id=target.id) if objective_guid64 is not None and bucks_data is not None: current_bucks = bucks_data.get_bucks_earned(self.bucks_type) relative_start_values = bucks_data.get_starting_values(objective_guid64) if relative_start_values is not None: current_bucks -= relative_start_values[0] elif bucks_tracker is not None: current_bucks = bucks_tracker.get_bucks_amount_for_type(self.bucks_type) if not self.value_threshold.compare(current_bucks): return TestResult(False, 'Bucks type {} value does not pass the value threshold.', self.bucks_type, tooltip=self.tooltip) return TestResult.TRUE
def try_remove_funds(self, sim, amount, resolver=None): if resolver is None: return sim_id = None if sim is None else sim.id tracker = BucksUtils.get_tracker_for_bucks_type(self.bucks_type, owner_id=sim_id, add_if_none=amount > 0) if tracker is None: logger.error( 'Attempting to make a Bucks payment to {} of amount {} but they have no tracker for that bucks type {}.', sim, amount, self.bucks_type) return result = tracker.try_modify_bucks(self.bucks_type, -amount) return result
def open_reward(self, sim_info, **kwargs): if self.bucks_type is None or not ( self.bucks_type == BucksType.INVALID or not is_available_pack( _get_pack_from_enum_value(int(self.bucks_type)))): return if sim_info.is_npc: return tracker = BucksUtils.get_tracker_for_bucks_type(self.bucks_type, sim_info.id, add_if_none=True) if tracker is None: logger.error( 'Failed to open a TunableRewardBucks of buck type {} for Sim {}.', self.bucks_type, sim_info) return tracker.try_modify_bucks(self.bucks_type, self.amount)
def on_activate(self, reader=None): self.owner.lock_save() super().on_activate(reader) for sim in services.active_household().instanced_sims_gen(): for si in sim.si_state: if self.owner.sleep_category_tag in si.affordance.interaction_category_tags: si.add_liability(UNCANCELABLE_LIABILITY, UncancelableLiability()) vampire_sim = self.owner.vampire_sim() bucks_tracker = BucksUtils.get_tracker_for_bucks_type( self.owner.power_buck_type, owner_id=vampire_sim.id) if bucks_tracker is not None: for active_power in self.owner.active_powers: if bucks_tracker.is_perk_unlocked(active_power.power): vampire_sim.add_buff_from_op( buff_type=active_power.buff_to_add.buff_type, buff_reason=active_power.buff_to_add.buff_reason)
def _apply_to_subject_and_target(self, subject, target, resolver): tracker = BucksUtils.get_tracker_for_bucks_type( self._bucks_type, owner_id=subject.id, add_if_none=self._amount > 0) if tracker is None: logger.error( 'Attempting to apply a BucksLoot op to the subject {} of amount {} but they have no tracker for that bucks type {}.', subject, self._amount, self._bucks_type) return result = tracker.try_modify_bucks(self._bucks_type, self._amount, force_refund=self._force_refund) if not result: logger.error( "Failed to modify the Sim {}'s bucks of type {} by amount {}.", subject, self._bucks_type, self._amount)
def add_fame_points(points: int = 0, opt_sim: OptionalTargetParam = None, _connection=None): if FameTunables.FAME_PERKS_BUCKS_TYPE is None: sims4.commands.output( 'The DLC that is necessary for this cheat is not loaded.', _connection) return sim = get_optional_target(opt_sim, _connection) if sim is None: sims4.commands.output('No Target Sim to add the fame points too.', _connection) bucks_tracker = BucksUtils.get_tracker_for_bucks_type( FameTunables.FAME_PERKS_BUCKS_TYPE, sim.id, add_if_none=True) bucks_tracker.try_modify_bucks(FameTunables.FAME_PERKS_BUCKS_TYPE, points) sims4.commands.output( '{} Fame Points have been added to {}'.format(points, sim), _connection)
def _apply_to_subject_and_target(self, subject, target, resolver): if subject is None: logger.error('Subject {} is None for the loot {}.', self.subject, self) return False bucks_tracker = BucksUtils.get_tracker_for_bucks_type( self._perk.associated_bucks_type, subject.sim_id, add_if_none=True) if bucks_tracker is None: logger.error( "Subject {} doesn't have a perk bucks tracker of type {} for the loot {}.", self.subject, self._bucks_type, self) return False show_dialog = self._award_strategy.try_unlock_perk( subject, bucks_tracker, self._perk) if show_dialog and self._notification_on_successful_unlock is not None: notification = self._notification_on_successful_unlock( subject, resolver=SingleSimResolver(subject)) notification.show_dialog()
def payout_lifestyle_brand(self): if not self.active: return if FameTunables.LIFESTYLE_BRAND_PERK is None: self.clear_brand() return bucks_tracker = BucksUtils.get_tracker_for_bucks_type( FameTunables.LIFESTYLE_BRAND_PERK.associated_bucks_type, self._sim_info.id) if bucks_tracker is None or not bucks_tracker.is_perk_unlocked( FameTunables.LIFESTYLE_BRAND_PERK): self.clear_brand() return payout = self.get_payout_amount() if payout > 0: self._sim_info.household.funds.add( payout, Consts_pb2.FUNDS_LIFESTYLE_BRAND) self._display_earnings_notification(payout) self.update_days_active()
def register_calbacks(self): if self.update_on_game_option_changed: services.get_event_manager().register_single_event( self, TestEvent.TestedGameOptionChanged) if self.update_if_stat_or_buck_changes: resolver = SingleObjectResolver(self.owner) always_true_threshold = Threshold(-1, operator.ne) for custom_tooltip in self.custom_tooltips: for tooltip_value in custom_tooltip.tooltip_fields.values(): if tooltip_value.text_tokens is not None: for text_token in tooltip_value.text_tokens.tokens: if text_token.token_type == LocalizationTokens.TOKEN_STATISTIC: participant = text_token.participant statistic = text_token.statistic for obj in resolver.get_participants( participant): if obj.has_component( objects.components.types. STATISTIC_COMPONENT): statistic_tracker = obj.get_component( objects.components.types. STATISTIC_COMPONENT ).get_statistic_tracker() statistic_listener = statistic_tracker.create_and_add_listener( statistic, always_true_threshold, lambda _: self. update_object_tooltip()) self._stat_update_listeners[ statistic_tracker].append( statistic_listener) if text_token.token_type == LocalizationTokens.TOKEN_BUCK: participant = text_token.participant bucks_type = text_token.bucks_type for obj in resolver.get_participants( participant): tracker = BucksUtils.get_tracker_for_bucks_type( bucks_type, owner_id=obj.id) callback = lambda: self.update_object_tooltip( ) tracker.add_bucks_modified_callback( bucks_type, callback) self._buck_callback_datas.append( (tracker, bucks_type, callback))
def _get_token(self, resolver, token_data): if token_data.token_type == self.TOKEN_PARTICIPANT: participants = token_data.objects.get_objects(resolver) return token_data.formatter(participants) if token_data.token_type == self.TOKEN_PARTICIPANT_COUNT: participants = token_data.objects.get_objects(resolver) if not participants: return 0 return len(participants) if token_data.token_type == self.TOKEN_DEFINITION: return token_data.definition elif token_data.token_type == self.TOKEN_MONEY: interaction = getattr(resolver, 'interaction', None) if interaction is not None: from interactions.money_payout import MoneyLiability money_liability = interaction.get_liability( MoneyLiability.LIABILITY_TOKEN) if money_liability is not None: return money_liability.amounts[token_data.participant] return 0 return 0 if token_data.token_type == self.TOKEN_BUCK: participant = resolver.get_participant( participant_type=token_data.participant) tracker = BucksUtils.get_tracker_for_bucks_type( token_data.bucks_type, owner_id=participant.id) if not tracker: return 0 return tracker.get_bucks_amount_for_type(token_data.bucks_type) if token_data.token_type == self.TOKEN_STATISTIC: participant = resolver.get_participant( participant_type=token_data.participant) if participant is not None: tracker = participant.get_tracker(token_data.statistic) if tracker is not None: return tracker.get_value(token_data.statistic) if token_data.token_type == self.TOKEN_OBJECT_PROPERTY: participant = resolver.get_participant(ParticipantType.Object) if participant is None: return return participant.get_object_property(token_data.obj_property) if token_data.token_type == self.TOKEN_INTERACTION_COST: interaction = getattr(resolver, 'interaction', None) if interaction is not None: return interaction.get_simoleon_cost() affordance = getattr(resolver, 'affordance', None) if affordance is not None: return affordance.get_simoleon_cost(target=resolver.target, context=resolver.context) if token_data.token_type == self.TOKEN_INTERACTION_PAYOUT: interaction = getattr(resolver, 'interaction', None) if interaction is not None: return interaction.get_simoleon_payout() affordance = getattr(resolver, 'affordance', None) if affordance is not None: return affordance.get_simoleon_payout(target=resolver.target, context=resolver.context) if token_data.token_type == self.TOKEN_ASSOCIATED_CLUB: if resolver.interaction is not None: club = getattr(resolver.interaction, 'associated_club') else: club = resolver.interaction_parameters.get('associated_club') if club is not None: return club.name if token_data.token_type == self.TOKEN_CAREER_DATA: participant = resolver.get_participant( participant_type=token_data.participant) if participant is not None: if participant.career_tracker is None: return career = participant.career_tracker.get_career_by_uid( token_data.career_type.guid64) if career is not None: if token_data.career_data == self.TOKEN_CAREER_DATA_CURRENT_LEVEL_NAME: current_level = career.current_level_tuning return current_level.get_title(participant) if token_data.career_data == self.TOKEN_CAREER_DATA_CURRENT_LEVEL_SALARY: current_level = career.current_level_tuning return current_level.simoleons_per_hour if token_data.career_data == self.TOKEN_CAREER_DATA_NEXT_LEVEL_NAME: next_level = career.next_level_tuning if next_level is not None: return next_level.get_title(participant) elif token_data.career_data == self.TOKEN_CAREER_DATA_NEXT_LEVEL_SALARY: next_level = career.next_level_tuning if next_level is not None: return next_level.simoleons_per_hour elif token_data.career_data == self.TOKEN_CAREER_DATA_PREVIOUS_LEVEL_NAME: previous_level = career.previous_level_tuning if previous_level is not None: return previous_level.get_title(participant) elif token_data.career_data == self.TOKEN_CAREER_DATA_PREVIOUS_LEVEL_SALARY: previous_level = career.previous_level_tuning if previous_level is not None: return previous_level.simoleons_per_hour if token_data.token_type == self.TOKEN_GAME_COMPONENT: participant = resolver.get_participant( participant_type=token_data.participant) if participant is not None: game = participant.game_component if game is None: return if token_data.game_component_data == self.TOKEN_GAME_COMPONENT_DATA_HIGH_SCORE and game.high_score is not None: return game.high_score if token_data.game_component_data == self.TOKEN_GAME_COMPONENT_DATA_HIGH_SCORE_SIM and game.high_score_sim_ids: high_score_sim_id = game.high_score_sim_ids[0] return services.sim_info_manager().get(high_score_sim_id) if token_data.token_type == self.TOKEN_SCHOLARSHIP_LETTER: participant = resolver.get_participant( participant_type=token_data.participant) if participant is not None: scholarship_letter_component = participant.scholarship_letter_component if scholarship_letter_component is None: return if token_data.scholarship_letter_component_data == self.TOKEN_SCHOLARSHIP_LETTER_APPLICANT_NAME: return scholarship_letter_component.get_applicant_name() if token_data.scholarship_letter_component_data == self.TOKEN_SCHOLARSHIP_LETTER_DATA_AMOUNT: return scholarship_letter_component.get_scholarship_amount( ) if token_data.scholarship_letter_component_data == self.TOKEN_SCHOLARSHIP_LETTER_DATA_NAME: return scholarship_letter_component.get_scholarship_name() if token_data.scholarship_letter_component_data == self.TOKEN_SCHOLARSHIP_LETTER_DATA_DESCRIPTION: return scholarship_letter_component.get_scholarship_description( ) if token_data.token_type == self.TOKEN_SICKNESS: participant = resolver.get_participant( participant_type=token_data.participant) if participant is None or not participant.is_sim: return current_sickness = participant.current_sickness if current_sickness is None: return return current_sickness.display_name(participant) if token_data.token_type == self.TOKEN_GLOBAL_POLICY: global_policy = services.global_policy_service().get_global_policy( token_data.global_policy, create=False) if global_policy is None: return token_data.global_policy.get_non_active_display( token_data) return global_policy.get_active_policy_display(token_data) if token_data.token_type == self.TOKEN_HOLIDAY: active_household = services.active_household() if active_household.holiday_tracker is None: return holiday_id = active_household.holiday_tracker.get_active_or_upcoming_holiday( ) if holiday_id is None: return return services.holiday_service().get_holiday_display_name( holiday_id) if token_data.token_type == self.TOKEN_CURRENT_TRENDS: trend_service = services.trend_service() if trend_service is None: return return trend_service.get_current_trends_loc_string() if token_data.token_type == self.TOKEN_LIFESTYLE_BRAND: participant = resolver.get_participant( participant_type=token_data.participant) lifestyle_brand_tracker = participant.lifestyle_brand_tracker if lifestyle_brand_tracker is None: return return lifestyle_brand_tracker.brand_name if token_data.token_type == self.TOKEN_PICKED_PART: participant = resolver.get_participant(ParticipantType.Object) if participant is None: return context = getattr(resolver, 'context', None) if context is not None and context.pick is not None: target_objects = participant.get_closest_parts_to_position( context.pick.location, has_name=True) if target_objects: part = target_objects.pop() return part.part_name if token_data.token_type == self.TOKEN_CIVIC_POLICY: if token_data.civic_policy_data == self.TOKEN_CIVIC_POLICY_VOTING_START_TIME: return services.street_service().voting_open_time if token_data.civic_policy_data == self.TOKEN_CIVIC_POLICY_VOTING_END_TIME: return services.street_service().voting_close_time if token_data.token_type == self.TOKEN_STREET: if token_data.street_data == self.TOKEN_STREET_POLICY_NAME_UP_FOR_REPEAL: provider = token_data.street.get_street_provider() if provider is not None: policies = provider.get_up_for_repeal_policies() if policies: return list(policies)[0].display_name() if token_data.street_data == self.TOKEN_STREET_POLICY_NAME_BALLOTED_RANDOM_LOSING: provider = token_data.street.get_street_provider() if provider is None: return policies = list(provider.get_balloted_policies()) if policies and len(policies) > 1: winning_policy = max( policies, key=lambda policy: provider.get_stat_value( policy.vote_count_statistic)) policies.remove(winning_policy) random_losing_policy = random.choice(policies) return random_losing_policy.display_name() if token_data.street_data == self.TOKEN_STREET_POLICY_NAME_BALLOTED_WINNING: provider = token_data.street.get_street_provider() if provider is None: return policies = list(provider.get_balloted_policies()) if policies: winning_policy = max( policies, key=lambda policy: provider.get_stat_value( policy.vote_count_statistic)) return winning_policy.display_name() if token_data.token_type == self.TOKEN_VENUE: if token_data.venue_data == self.TOKEN_VENUE_ACTIVE_VENUE_NAME: raw_active_venue_tuning_id = build_buy.get_current_venue( services.current_zone_id(), allow_ineligible=True) raw_active_venue_tuning = services.venue_manager().get( raw_active_venue_tuning_id) if raw_active_venue_tuning is None: return source_venue_tuning = type( services.venue_service().source_venue) if source_venue_tuning is raw_active_venue_tuning and source_venue_tuning.variable_venues is not None: return raw_active_venue_tuning.variable_venues.variable_venue_display_name( ) return raw_active_venue_tuning.display_name elif token_data.venue_data == self.TOKEN_VENUE_SOURCE_VENUE_NAME: source_venue_tuning = type( services.venue_service().source_venue) if source_venue_tuning is not None: return source_venue_tuning.display_name
def _sim_is_stannable(self, sim): bucks_tracker = BucksUtils.get_tracker_for_bucks_type( FanTuning.STAN_PERK.associated_bucks_type, owner_id=sim.sim_id) if bucks_tracker is None: return False return bucks_tracker.is_perk_unlocked(FanTuning.STAN_PERK)
def get_influence(self, sim_info): tracker = BucksUtils.get_tracker_for_bucks_type(self.INFLUENCE_BUCK_TYPE, owner_id=sim_info.id, add_if_none=False) if tracker is None: return 0 return tracker.get_bucks_amount_for_type(self.INFLUENCE_BUCK_TYPE)