def __init__(self, name='<buff_noname>', value=0, duration=0, mtype='att', morder=None, modifier=None, hidden=False, source=None): self.name = name self.__value = value self.duration = duration self.mod_type = mtype self.mod_order = morder or ('chance' if self.mod_type == 'crit' else 'buff') self.bufftype = 'misc' if hidden else 'self' self.source = source if self.source is not None and source[0] != 's' and source[0:2] != 'ds': self.bufftime = self._ex_bufftime else: self.bufftime = self._bufftime self.buff_end_timer = Timer(self.buff_end_proc) if modifier: self.modifier = modifier self.get = self.modifier.get elif mtype != 'effect': self.modifier = Modifier('mod_' + self.name, self.mod_type, self.mod_order, 0) self.modifier.get = self.get else: self.modifier = None self.dmg_test_event = Event('dmg_formula') self.dmg_test_event.dmg_coef = 1 self.dmg_test_event.dname = 'test' self.hidden = hidden self.__stored = 0 self.__active = 0 self.buffevent = Event('buff')
def oninit(self, adv): super().oninit(adv) adv.styx_spirit = 0 adv.csd_buff = SingleActionBuff("d_compounding_sd", 0.0, -1, "s", "buff") def add_csd(e): if not adv.csd_buff.get(): adv.csd_buff.set(min(2.00, adv.csd_buff.get() + 0.50)) adv.csd_buff.on() else: adv.csd_buff.value(min(2.00, adv.csd_buff.get() + 0.50)) csd_timer = Timer(add_csd, 15, True).on() def add_spirit(e): if e.index == 3: adv.styx_spirit = min(3, adv.styx_spirit + 1) log("dx_spirit", adv.styx_spirit) Event("dx").listener(add_spirit) def reset_spirit(e): adv.styx_spirit = 0 Event("ds").listener(reset_spirit) Event("dragon_end").listener(reset_spirit)
def configure_divine_shift(self, shift_name, max_gauge=1800, shift_cost=560, drain=40, buffs=None): self.shift_name = shift_name self.comment = f"dragon damage does not work on {shift_name}" setattr( self, shift_name, self.dragonform.set_dragondrive( ModeManager( group="ddrive", buffs=buffs, x=True, s1=True, s2=True, ), max_gauge=max_gauge, shift_cost=shift_cost, drain=drain, ), ) Event("dragondrive").listener(self.a_dragondrive_on) Event("dragondrive_end").listener(self.a_dragondrive_off)
def set_dragondrive(self, dd_buff): self.is_dragondrive = True self.shift_event = Event('dragondrive') self.dragondrive_end_event = Event('dragondrive_end') self.max_gauge = 3000 self.shift_cost = 1200 # does not deduct, but need to have this much pt to shift self.dragondrive_buff = dd_buff self.dragondrive_timer = Timer(self.d_dragondrive_end)
def config_actions(self): if self.dform_mode == 1: return super().config_actions() # should maybe take the actual shift action from the modes self.name = "Dragondrive" self.d_shift = Shift("dshift", self.name, self.conf.dshift) self.shift_event = Event("dragondrive") self.end_event = Event("dragondrive_end")
def oninit(self, adv): if not super().oninit(adv): self.adv.blood_moon = 0 self.adv.moonlit_rage = 0 self.blood_moon_timer = Timer(self.d_moon_repeat, 3.5, True) self.dragon_strike_timer = Timer(self.add_rage, 1.0, True) Event("dfs_start").listener(self.dfs_start) Event("dfs_charged").listener(self.dfs_charged)
def __init__(self, name, conf, adv, ds_proc): self.name = name self.conf = conf self.adv = adv self.cancel_by = [] self.interrupt_by = [] self.disabled = False self.shift_event = Event('dragon') self.end_event = Event('dragon_end') self.ds_proc = ds_proc self.ds_reset() self.act_list = [] self.act_sum = [] self.dx_list = [ 'dx{}'.format(i) for i in range(1, 6) if 'dmg' in self.conf['dx{}'.format(i)] ] self.ds_event = Event('s') self.ds_event.name = 'ds' self.action_timer = None self.shift_start_time = 0 self.shift_damage_sum = 0 self.shift_end_timer = Timer(self.d_shift_end) self.idle_event = Event('idle') self.c_act_name = None self.c_act_conf = None self.dracolith_mod = self.adv.Modifier('dracolith', 'att', 'dragon', 0) self.dracolith_mod.off() self.off_ele_mod = None if self.adv.slots.c.ele != self.adv.slots.d.ele: self.off_ele_mod = self.adv.Modifier('off_ele', 'att', 'dragon', -1 / 3) self.off_ele_mod.off() self.dragon_gauge = 0 self.dragon_gauge_val = self.conf.gauge_val self.dragon_gauge_timer = Timer(self.auto_gauge, timeout=max(1, self.conf.gauge_iv), repeat=1).on() self.dragon_gauge_pause_timer = None self.dragon_gauge_timer_diff = 0 self.max_gauge = 1000 self.shift_cost = 500 self.shift_count = 0 self.shift_silence = False self.is_dragondrive = False self.can_end = True
def effect_on(self): value = self.get() if self.mod_type == "defense" and value > 0: db = Event("defchain") db.source = self.source db.on() if self.bufftype == "team": log("buff", "doublebuff", 15 * self.bufftime()) if self.bufftime == self._bufftime: self._static.adv.slots.c.set_need_bufftime() elif self.mod_type == "maxhp": if self._static.adv.sub_mod("maxhp", "buff") < Buff.MAXHP_BUFF_CAP: self.modifier.on() percent = value * 100 log("heal", self.name, self._static.adv.max_hp * value, "team" if self.bufftype == "team" else "self") self._static.adv.add_hp(percent) # FIXME: heal formula 1day twust elif self.mod_type == "regen" and value != 0: self.set_hp_event = Event("set_hp") self.set_hp_event.delta = value self.regen_timer = Timer(self.hp_regen, 3.9, True).on() elif self.mod_type == "heal" and value != 0: self.set_hp_event = Event("heal_make") self.set_hp_event.name = self.name self.set_hp_event.delta = self._static.adv.heal_formula( self.source, value) self.set_hp_event.target = "team" if self.bufftype == "team" else "self" self.regen_timer = Timer(self.hp_regen, 2.9, True).on() else: return self.modifier and self.modifier.on()
def set_dragondrive(self, dd_buff, max_gauge=3000, shift_cost=1200, drain=150): self.disabled = False self.is_dragondrive = True self.shift_event = Event('dragondrive') self.dragondrive_end_event = Event('dragondrive_end') ratio = max_gauge / self.max_gauge self.dragon_gauge *= ratio self.dragon_gauge_val *= ratio self.max_gauge = max_gauge self.shift_cost = shift_cost # does not deduct, but need to have this much pt to shift self.drain = drain self.dragondrive_buff = dd_buff self.dragondrive_timer = Timer(self.d_dragondrive_end) return self.dragondrive_buff
def __init__(self, name, mod): # self.adv = adv # self.o_dmg_make = adv.dmg_make # self.adv.dmg_make = self.dmg_make self.name = name self.modifier = mod self.modifier.off() self.add_event = Event(name) self.end_event = Event(f"{name}_end") self.stack = 0 self.queued_stack = 0 self.has_stack = Selfbuff("has_" + self.name, 1, -1, "effect") self.active = set() self.disabled = False self.extra_tensionable = set()
def on(self, duration=None): if self.mod_type == 'maxhp': max_hp = self._static.adv.mod('maxhp') if max_hp >= Buff.MAXHP_CAP: return self value = self.__value mod_val = min(value, max(Buff.MAXHP_CAP - max_hp, 0)) self._static.adv.set_hp( (self._static.adv.hp * max_hp + value * 100) / (max_hp + mod_val)) d = max(-1, (duration or self.duration) * self.bufftime()) if self.__active == 0: self.__active = 1 if self.__stored == 0: self._static.all_buffs.append(self) self.__stored = 1 if d >= 0: self.buff_end_timer.on(d) proc_type = 'start' else: if d >= 0: self.buff_end_timer.on(d) proc_type = 'refresh' self.logwrapper( self.name, f'{self.mod_type}({self.mod_order}): {self.value():.02f}', f'buff {proc_type} <{d:.02f}s>') value, stack = self.valuestack() if stack > 1: log('buff', self.name, f'{self.mod_type}({self.mod_order}): {value:.02f}', f'buff stack <{stack}>') if self.mod_type == 'defense': Event('defchain').on() if self.bufftype == 'team': log('buff', 'team_defense', 'proc team doublebuffs') if self.mod_type == 'regen': # may need to make this part global since game always regen all stacks at same ticks self.set_hp_event = Event('set_hp') self.set_hp_event.delta = self.get() self.regen_timer = Timer(self.hp_regen, 3.9, True) else: self.effect_on() return self
def oninit(self, adv): super().oninit(adv) def shift_end_prep(e): adv.charge_p("shift_end", 100) Event("dragon_end").listener(shift_end_prep)
def oninit(self, adv): super().oninit(adv) from core.advbase import Event, SingleActionBuff Event('dragon_end').listener(self.shift_end_trickery) self.trickery = 15 self.threshold = 25 self.trickery_buff = SingleActionBuff('d_trickery_buff', 1.80, 1, 's', 'buff', end_proc=self.check_trickery) self.check_trickery() if adv.condition('always connect hits'): self.dmg_proc_o = adv.dmg_proc self.thit = 0 def dmg_proc(name, amount): n_thit = adv.hits // self.threshold if n_thit > self.thit: self.add_trickery(n_thit - self.thit) self.thit = n_thit self.dmg_proc_o(name, amount) adv.dmg_proc = dmg_proc
def __init__(self, name, conf, adv, dragon): utp_params = adv.conf.c.utp # dform_modes # 0: ddrive as adventurer # 1: ddrive as dragon # 2: ddrive as adventurer, with servant super().__init__(name, conf, adv, dragon, dform_mode=utp_params[0], unique_dform=True) self.shift_mods = [] self.shift_cost = 0 self.utp_gauge = 0 self.ds_final = None self.max_utp_gauge = utp_params[1] self.utp_shift_req = utp_params[2] self.utp_drain = utp_params[3] self.utp_infinte = False self.utp_event = Event("utp") self.log_utp = True if self.dform_mode == 1: g_logs.log_dact_as_act = True for ds in self.shift_skills: try: del self.adv.conf[ds]["uses"] except KeyError: pass else: self.ddrive_fs_list = [fsn for fsn, _ in self.adv.conf.find(f"^fs\d*_{DDRIVE}$")] self.shift_skills = [sn.split("_")[0] for sn, _ in self.adv.conf.find(f"^s\d*_{DDRIVE}$")] self.l_ddrive_end = Listener("act_end", self.d_dragondrive_end, order=0) self.l_ddrive_end.off() self.ddrive_end_reason = None
def oninit(self, adv): super().oninit(adv) adv.summer_sakuya_flowers = 0 self.flower_buffs = Summer_Konohana_Sakuya.FLOWER_BUFFS if adv.nihilism: self.flower_buffs = dict(self.flower_buffs) del self.flower_buffs[1] del self.flower_buffs[2] del self.flower_buffs[3] def add_flower(t=None): if adv.summer_sakuya_flowers >= 6: return adv.summer_sakuya_flowers += 1 try: adv.Selfbuff( f"d_sakuya_flower_{adv.summer_sakuya_flowers}", *self.flower_buffs[adv.summer_sakuya_flowers], ).on() except KeyError: pass add_flower() Timer(add_flower, 60, True).on() Event("ds").listener(add_flower)
def oninit(self, adv): super().oninit(adv) def add_gauge_and_time(t): adv.dragonform.charge_gauge(200, dhaste=False) adv.dragonform.set_shift_end(5, percent=False, addition=True) Event("ds").listener(add_gauge_and_time)
def oninit(self, adv): super().oninit(adv) adv.trickery = Gala_Cat_Sith.MAX_TRICKERY if not adv.nihilism: self.thit = 0 self.trickery_buff = SingleActionBuff("d_trickery_buff", 1.80, 1, "s", "buff").on() self.l_hit = Event("hit").listener(self.combo_trickery)
def oninit(self, adv): super().oninit(adv) sp_regen_timer = Timer( lambda _: adv.charge_p("ds_sp", 0.0075, target=["s1", "s2"]), 0.99, True) sp_regen_buff = EffectBuff("ds_sp", 90, lambda: sp_regen_timer.on(), lambda: sp_regen_timer.off()) Event("ds").listener(lambda _: sp_regen_buff.on())
def __init__( self, name="<buff_noname>", value=0, duration=0, mtype="att", morder=None, modifier=None, hidden=False, source=None, ): self.name = name self.__value = value self.duration = duration self.mod_type = mtype self.mod_order = morder or ("chance" if self.mod_type == "crit" else "buff") self.bufftype = "misc" if hidden else "self" self.source = source if self.source is not None and source[0] != "s" and source[0:2] != "ds": self.bufftime = self._ex_bufftime else: self.bufftime = self._bufftime self.buff_end_timer = Timer(self.buff_end_proc) if modifier: self.modifier = modifier self.get = self.modifier.get elif mtype != "effect": self.modifier = Modifier("mod_" + self.name, self.mod_type, self.mod_order, 0) self.modifier.get = self.get else: self.modifier = None self.dmg_test_event = Event("dmg_formula") self.dmg_test_event.dmg_coef = 1 self.dmg_test_event.dname = "test" self.hidden = hidden self.__stored = 0 self.__active = 0 self.buffevent = Event("buff") self.pause_time = -1 self.refresh_time = -1
def oninit(self, adv, buff_name, buff_ele): super().oninit(adv) self.dp_count = 0 Event("dp").listener(self.dp_reborn_buff) self.reborn_buff = adv.Selfbuff(buff_name, 0.3, 45, buff_ele, "ele").no_bufftime() setattr( adv, buff_name, adv.Selfbuff(buff_name, 0.3, 45, buff_ele, "ele").no_bufftime())
def oninit(self, adv): from core.advbase import Repeat, Fs super().oninit(adv) adv.gozu_tenno_buff = adv.Selfbuff("gozu_tenno_buff", 0.3, 30, "flame", "ele").no_bufftime() def fs_end(e): fs_action = adv.action.getdoing() if not isinstance(fs_action, Fs): fs_action = adv.action.getprev() if isinstance(fs_action, Repeat): fs_action = fs_action.parent fs_elapsed = now() - fs_action.startup_start if fs_elapsed >= 3.0: adv.gozu_tenno_buff.on(30) Event("fs_end").listener(fs_end, order=0) Event("repeat").listener(fs_end, order=0)
def oninit(self, adv): super().oninit(adv) charge_timer = Timer( lambda _: adv.charge_p("ds", 0.091, no_autocharge=True), 0.9, True) ds_buff = EffectBuff( "ds_sp_regen_zone", 10, lambda: charge_timer.on(), lambda: charge_timer.off(), ) Event("ds").listener(lambda _: ds_buff.on())
def oninit(self, adv): super().oninit(adv) self.dm_count = 2 def dragon_might(t): if self.dm_count > 0: self.dm_count -= 1 self.adv.Buff('dc', 0.10, -1).on() from core.timeline import Event Event('dragon').listener(dragon_might)
def oninit(self, adv): super().oninit(adv) if not adv.nihilism: self.joyful_radiance_buff = adv.Selfbuff("joyful_radiance", 0.8, -1, "att", "passive").on() adv.joyful_radiance = 4 Event("buffskills").listener(self.add_joyful_radiance) Timer(self.expire_joyful_radiance, 20, True).on()
def __init__(self, name, conf, adv, dragon, dform_mode=-1, unique_dform=False): self.name = name self.conf = conf self.adv = adv self.dragon = dragon self.dform_mode = dform_mode self.unique_dform = unique_dform self.shift_start_proc = None self.shift_end_proc = None self.config_actions() # events self.status = False self.disabled_reasons = set() self.dp_event = Event("dp") self.shift_end_timer = Timer(self.d_shift_end) self.shift_silence_timer = Timer(None, 10) self.can_end = True self.l_shift = Listener("dshift", self.d_shift_start, order=2) self.l_s = Listener("s", self.l_ds_pause, order=0) self.l_s_end = Listener("s_end", self.l_ds_resume, order=0) self.l_s_final_end = Listener("s_end", self.d_shift_end, order=0) self.l_s.off() self.l_s_end.off() self.l_s_final_end.off() self.shift_skills = ("ds1", "ds2") self.allow_end_cd = self.conf.allow_end + self.dstime() self.shift_end_reason = None # mods self.dracolith_mod = self.adv.Modifier("dracolith", "ex", "dragon", 0) self.dracolith_mod.get = self.ddamage self.dracolith_mod.off() self.shift_mods = [self.dracolith_mod] self.shift_spd_mod = None self.off_ele = self.adv.slots.c.ele != self.conf.d.ele self.previous_x = DEFAULT # gauge self.auto_gauge_val = 0.1 # percent self.auto_gauge_iv = min(int(self.adv.duration / 12), 15) self.dragon_gauge_timer = Timer(self.auto_gauge, timeout=max(1, self.auto_gauge_iv), repeat=1).on() self.dragon_gauge_pause_timer = None self.dragon_gauge_timer_diff = 0 self.dragon_gauge = 0 self.max_dragon_gauge = 1000 self.shift_cost = 500 self.log_utp = False # dragonbattle self.is_dragonbattle = False
def oninit(self, adv): super().oninit(adv) def chariot_energy(t): adv.energy.add(1) Timer(chariot_energy, 5, True).on() def shift_end_energy(e): adv.energy.add(5, team=True) Event("dragon_end").listener(shift_end_energy)
def oninit(self, adv): super().oninit(adv) def permanent_curse(e): if hasattr(adv, 'afflict_guard') and adv.afflict_guard > 0: adv.afflict_guard -= 1 else: adv.skill._static.silence = 1 adv.dragonform.disabled = True from core.log import log log('debug', 'permanent_curse') from core.timeline import Event Event('dragon').listener(permanent_curse)
def __init__(self, meta_args, amp_values, source=None): self.amp_id, self.publish_level, self.max_team_level, self.extend_time, self.mod_type, self.mod_order = meta_args self.publish_level -= 1 self.buffs = [] self.name = f"{self.mod_type}_amp" for idx, buffargs in enumerate(amp_values): buff = Teambuff(f"{self.name}_seq{idx}", *buffargs, self.mod_type, self.mod_order, source=source).no_bufftime() buff.hidden = True buff.modifier.buff_capped = False self.buffs.append(buff) self.max_len = self.publish_level + self.max_team_level self.amp_event = Event("amp")
def __init__(self, name, conf, adv): self.name = name self.conf = conf self.adv = adv self.cancel_by = [] self.interrupt_by = [] self.disabled = False self.shift_event = Event('dragon') self.act_event = Event('dact') self.end_event = Event('dragon_end') self.delayed = set() self.ds_reset() self.act_list = [] self.act_sum = [] self.repeat_act = False self.dx_list = [dx for dx, _ in self.conf.find(r'^dx\d+$')] self.ds_event = Event('ds') self.ds_event.name = 'ds' self.dx_event = Event('dx') self.action_timer = None self.shift_start_time = 0 self.shift_end_timer = Timer(self.d_shift_end) self.idle_event = Event('idle') self.c_act_name = None self.c_act_conf = None self.dracolith_mod = self.adv.Modifier('dracolith', 'att', 'dragon', 0) self.dracolith_mod.get = self.ddamage self.dracolith_mod.off() self.shift_mods = [self.dracolith_mod] self.shift_spd_mod = None self.off_ele_mod = None if self.adv.slots.c.ele != self.adv.slots.d.ele: self.off_ele_mod = self.adv.Modifier('off_ele', 'att', 'dragon', -1/3) self.off_ele_mod.off() self.dragon_gauge = 0 self.dragon_gauge_val = self.conf.gauge_val self.conf.gauge_iv = min(int(self.adv.duration/12), 15) self.dragon_gauge_timer = Timer(self.auto_gauge, timeout=max(1, self.conf.gauge_iv), repeat=1).on() self.dragon_gauge_pause_timer = None self.dragon_gauge_timer_diff = 0 self.max_gauge = 1000 self.shift_cost = 500 self.shift_count = 0 self.shift_silence = False self.is_dragondrive = False self.can_end = True self.allow_end_cd = self.conf.allow_end + (self.conf.ds.startup + self.conf.ds.startup) / self.speed() self.allow_force_end_timer = Timer(self.set_allow_end, timeout=self.allow_end_cd) self.allow_end = False
def config_actions(self): # merge confs into adv conf self.dx_max = 0 for dx, dxconf in self.conf.find(r"^dx\d+$"): self.adv.conf[dx] = dxconf self.dx_max = max(self.dx_max, int(dx[2:])) self.default_x_loop = self.conf["default_x_loop"] or self.dx_max # the default combo idx to end combo on for fs, fsconf in self.conf.find(r"^dfs\d*(_[A-Za-z0-9]+)?$"): self.adv.conf[fs] = fsconf if not self.unique_dform: for sfn in ("before", "proc"): self.adv.rebind_function(self.dragon, f"{fs}_{sfn}", f"{fs}_{sfn}", overwrite=False) self.ds_final = None for ds, dsconf in self.conf.find(r"^ds\d*(_[A-Za-z0-9]+)?$"): self.adv.conf[ds] = dsconf ds_base = ds.split("_")[0] if not self.unique_dform: for sfn in ("before", "proc"): self.adv.rebind_function(self.dragon, f"{ds_base}_{sfn}", f"{ds_base}_{sfn}", overwrite=False) if ds.startswith("ds99") or dsconf.get("final"): self.ds_final = ds.split("_")[0] # make separate dodge action, may want to handle forward/backward later self.d_dodge = Dodge("dodge", self.conf.dodge) self.d_shift = Shift("dshift", self.name, self.conf.dshift) self.d_end = Shift("dend", self.name, self.conf.dend) self.shift_event = Event("dragon") self.end_event = Event("dragon_end") if abs(self.dform_mode) == 1: try: self.shift_start_proc = self.dragon.shift_start_proc except AttributeError: pass try: self.shift_end_proc = self.dragon.shift_end_proc except AttributeError: pass