diff --git a/ui/raidboss/data/07-dt/raid/r12s.ts b/ui/raidboss/data/07-dt/raid/r12s.ts new file mode 100644 index 0000000000..58d5066218 --- /dev/null +++ b/ui/raidboss/data/07-dt/raid/r12s.ts @@ -0,0 +1,1252 @@ +import Conditions from '../../../../../resources/conditions'; +import { UnreachableCode } from '../../../../../resources/not_reached'; +import Outputs from '../../../../../resources/outputs'; +import { Responses } from '../../../../../resources/responses'; +import { Directions } from '../../../../../resources/util'; +import ZoneId from '../../../../../resources/zone_id'; +import { RaidbossData } from '../../../../../types/data'; +import { TriggerSet } from '../../../../../types/trigger'; + +export type Phase = 'doorboss' | 'curtainCall' | 'slaughtershed' | 'two'; + +export interface Data extends RaidbossData { + phase: Phase; + // Phase 1 + grotesquerieCleave?: + | 'rightCleave' + | 'leftCleave' + | 'frontCleave' + | 'rearCleave'; + myFleshBonds?: 'alpha' | 'beta'; + inLine: { [name: string]: number }; + blobTowerDirs: string[]; + fleshBondsCount: number; + skinsplitterCount: number; + cellChainCount: number; + myMitoticPhase?: string; + hasRot: boolean; + // Phase 2 +} + +const headMarkerData = { + // Phase 1 + // VFX: com_share3t + 'stack': '00A1', + // VFX: tank_lockonae_6m_5s_01t + 'tankbuster': '0158', + // VFX: VFX: x6rc_cellchain_01x + 'cellChain': '0291', + // VFX: com_share3_7s0p + 'slaughterStack': '013D', + // VFX: target_ae_s7k1 + 'slaughterSpread': '0177', + 'cellChainTether': '016E', + // Phase 2 +} as const; + +const center = { + x: 100, + y: 100, +} as const; + +const phaseMap: { [id: string]: Phase } = { + 'BEC0': 'curtainCall', + 'B4C6': 'slaughtershed', +}; + +const triggerSet: TriggerSet = { + id: 'AacHeavyweightM4Savage', + zoneId: ZoneId.AacHeavyweightM4Savage, + timelineFile: 'r12s.txt', + initData: () => ({ + phase: 'doorboss', + // Phase 1 + inLine: {}, + blobTowerDirs: [], + skinsplitterCount: 0, + fleshBondsCount: 0, + cellChainCount: 0, + hasRot: false, + // Phase 2 + }), + triggers: [ + { + id: 'R12S Phase Tracker', + type: 'StartsUsing', + netRegex: { id: Object.keys(phaseMap), source: 'Lindwurm' }, + suppressSeconds: 1, + run: (data, matches) => { + const phase = phaseMap[matches.id]; + if (phase === undefined) + throw new UnreachableCode(); + + data.phase = phase; + }, + }, + { + id: 'R12S The Fixer', + type: 'StartsUsing', + netRegex: { id: 'B4D7', source: 'Lindwurm', capture: false }, + durationSeconds: 4.7, + response: Responses.bigAoe('alert'), + }, + { + id: 'R12S Directed Grotesquerie Direction Collect', + // Unknown_DE6 spell contains data in its count: + // 40C, Front Cone + // 40D, Right Cone + // 40E, Rear Cone + // 40F, Left Cone + type: 'GainsEffect', + netRegex: { effectId: 'DE6', capture: true }, + condition: Conditions.targetIsYou(), + run: (data, matches) => { + switch (matches.count) { + case '40C': + data.grotesquerieCleave = 'frontCleave'; + return; + case '40D': + data.grotesquerieCleave = 'rightCleave'; + return; + case '40E': + data.grotesquerieCleave = 'rearCleave'; + return; + case '40F': + data.grotesquerieCleave = 'leftCleave'; + return; + } + }, + }, + { + id: 'R12S Shared Grotesquerie', + type: 'GainsEffect', + netRegex: { effectId: '129A', capture: true }, + delaySeconds: 0.2, + durationSeconds: 17, + infoText: (data, matches, output) => { + const cleave = data.grotesquerieCleave; + const target = matches.target; + if (target === data.me) { + if (cleave === undefined) + return output.baitThenStack!({ stack: output.stackOnYou!() }); + return output.baitThenStackCleave!({ + stack: output.stackOnYou!(), + cleave: output[cleave]!(), + }); + } + + const player = data.party.member(target); + const isDPS = data.party.isDPS(target); + if (isDPS && data.role === 'dps') { + if (cleave === undefined) + return output.baitThenStack!({ + stack: output.stackOnPlayer!({ player: player }), + }); + return output.baitThenStackCleave!({ + stack: output.stackOnPlayer!({ player: player }), + cleave: output[cleave]!(), + }); + } + if (!isDPS && data.role !== 'dps') { + if (cleave === undefined) + return output.baitThenStack!({ + stack: output.stackOnPlayer!({ player: player }), + }); + return output.baitThenStackCleave!({ + stack: output.stackOnPlayer!({ player: player }), + cleave: output[cleave]!(), + }); + } + }, + outputStrings: { + stackOnYou: Outputs.stackOnYou, + stackOnPlayer: Outputs.stackOnPlayer, + frontCleave: { + en: 'Front Cleave', + de: 'Kegel Aoe nach Vorne', + fr: 'Cleave Avant', + ja: '口からおくび', + cn: '前方扇形', + ko: '전방 부채꼴 장판', + tc: '前方扇形', + }, + rearCleave: { + en: 'Rear Cleave', + de: 'Kegel Aoe nach Hinten', + fr: 'Cleave Arrière', + ja: '尻からおなら', + cn: '背后扇形', + ko: '후방 부채꼴 장판', + tc: '背後扇形', + }, + leftCleave: { + en: 'Left Cleave', + de: 'Linker Cleave', + fr: 'Cleave gauche', + ja: '左半面へ攻撃', + cn: '左刀', + ko: '왼쪽 공격', + tc: '左刀', + }, + rightCleave: { + en: 'Right Cleave', + de: 'Rechter Cleave', + fr: 'Cleave droit', + ja: '右半面へ攻撃', + cn: '右刀', + ko: '오른쪽 공격', + tc: '右刀', + }, + baitThenStack: { + en: 'Bait 4x Puddles => ${stack}', + }, + baitThenStackCleave: { + en: 'Bait 4x Puddles => ${stack} + ${cleave}', + }, + }, + }, + { + id: 'R12S Bursting Grotesquerie', + type: 'GainsEffect', + netRegex: { effectId: '1299', capture: true }, + condition: Conditions.targetIsYou(), + delaySeconds: 0.2, + durationSeconds: 17, + infoText: (data, _matches, output) => { + const cleave = data.grotesquerieCleave; + if (cleave === undefined) + return data.phase === 'doorboss' + ? output.baitThenSpread!() + : output.spreadCurtain!(); + return data.phase === 'doorboss' + ? output.baitThenSpreadCleave!({ cleave: output[cleave]!() }) + : output.spreadCurtain!(); + }, + outputStrings: { + frontCleave: { + en: 'Front Cleave', + de: 'Kegel Aoe nach Vorne', + fr: 'Cleave Avant', + ja: '口からおくび', + cn: '前方扇形', + ko: '전방 부채꼴 장판', + tc: '前方扇形', + }, + rearCleave: { + en: 'Rear Cleave', + de: 'Kegel Aoe nach Hinten', + fr: 'Cleave Arrière', + ja: '尻からおなら', + cn: '背后扇形', + ko: '후방 부채꼴 장판', + tc: '背後扇形', + }, + leftCleave: { + en: 'Left Cleave', + de: 'Linker Cleave', + fr: 'Cleave gauche', + ja: '左半面へ攻撃', + cn: '左刀', + ko: '왼쪽 공격', + tc: '左刀', + }, + rightCleave: { + en: 'Right Cleave', + de: 'Rechter Cleave', + fr: 'Cleave droit', + ja: '右半面へ攻撃', + cn: '右刀', + ko: '오른쪽 공격', + tc: '右刀', + }, + baitThenSpread: { + en: 'Bait 4x Puddles => Spread', + }, + baitThenSpreadCleave: { + en: 'Bait 4x Puddles => Spread + ${cleave}', + }, + spreadCurtain: { + en: 'Spread Debuff on YOU', + }, + }, + }, + { + id: 'R12S Ravenous Reach 1 Safe Side', + // These two syncs indicate the animation of where the head will go to cleave + // B49A => West Safe + // B49B => East Safe + type: 'Ability', + netRegex: { id: ['B49A', 'B49B'], source: 'Lindwurm', capture: true }, + condition: (data) => data.phase === 'doorboss', + infoText: (_data, matches, output) => { + if (matches.id === 'B49A') + return output.goWest!(); + return output.goEast!(); + }, + outputStrings: { + goEast: Outputs.east, + goWest: Outputs.west, + }, + }, + { + id: 'R12S Fourth-wall Fusion Stack', + type: 'HeadMarker', + netRegex: { id: headMarkerData['stack'], capture: true }, + condition: (data) => { + if (data.role === 'tank') + return false; + return true; + }, + durationSeconds: 5.1, + response: Responses.stackMarkerOn(), + }, + { + id: 'R12S Tankbuster', + type: 'HeadMarker', + netRegex: { id: headMarkerData['tankbuster'], capture: true }, + condition: Conditions.targetIsYou(), + durationSeconds: 5.1, + response: Responses.tankBuster(), + }, + { + id: 'R12S In Line Debuff Collector', + type: 'GainsEffect', + netRegex: { effectId: ['BBC', 'BBD', 'BBE', 'D7B'] }, + run: (data, matches) => { + const effectToNum: { [effectId: string]: number } = { + BBC: 1, + BBD: 2, + BBE: 3, + D7B: 4, + } as const; + const num = effectToNum[matches.effectId]; + if (num === undefined) + return; + data.inLine[matches.target] = num; + }, + }, + { + id: 'R12S Bonds of Flesh Flesh α/β Collect', + // Bonds of Flesh has the following timings: + // 1st - 26s + // 2nd - 31s + // 3rd - 36s + // 4rth - 41s + type: 'GainsEffect', + netRegex: { effectId: ['1290', '1292'], capture: true }, + condition: Conditions.targetIsYou(), + run: (data, matches) => { + data.myFleshBonds = matches.effectId === '1290' ? 'alpha' : 'beta'; + }, + }, + { + id: 'R12S In Line Debuff', + type: 'GainsEffect', + netRegex: { effectId: ['BBC', 'BBD', 'BBE', 'D7B'], capture: false }, + delaySeconds: 0.5, + durationSeconds: 10, + suppressSeconds: 1, + infoText: (data, _matches, output) => { + const myNum = data.inLine[data.me]; + if (myNum === undefined) + return; + const flesh = data.myFleshBonds; + if (flesh === undefined) + return output.order!({ num: myNum }); + if (flesh === 'alpha') { + switch (myNum) { + case 1: + return output.alpha1!(); + case 2: + return output.alpha2!(); + case 3: + return output.alpha3!(); + case 4: + return output.alpha4!(); + } + } + switch (myNum) { + case 1: + return output.beta1!(); + case 2: + return output.beta2!(); + case 3: + return output.beta3!(); + case 4: + return output.beta4!(); + } + }, + outputStrings: { + alpha1: { + en: '1α: Wait for Tether 1', + }, + alpha2: { + en: '2α: Wait for Tether 2', + }, + alpha3: { + en: '3α: Blob Tower 1', + }, + alpha4: { + en: '4α: Blob Tower 2', + }, + beta1: { + en: '1β: Wait for Tether 1', + }, + beta2: { + en: '2β: Wait for Tether 2', + }, + beta3: { + en: '3β: Chain Tower 1', + }, + beta4: { + en: '4β: Chain Tower 2', + }, + order: { + en: '${num}', + de: '${num}', + fr: '${num}', + ja: '${num}', + cn: '${num}', + ko: '${num}', + tc: '${num}', + }, + unknown: Outputs.unknown, + }, + }, + { + id: 'R12S Phagocyte Spotlight Blob Tower Location Collect', + // StartsUsing and StartsUsingExtra can have bad data, there is enough time that Ability is sufficient + // Pattern 1 + // Blob 1: (104, 104) SE Inner + // Blob 2: (96, 96) NW Inner + // Blob 3: (85, 110) SW Outer + // Blob 4: (115, 90) NE Outer + // Pattern 2 + // Blob 1: (104, 96) NE Inner + // Blob 2: (96, 104) SW Inner + // Blob 3: (85, 90) NW Outer + // Blob 4: (115, 110) SE Outer + // Pattern 3 + // Blob 1: (96, 96) NW Inner + // Blob 2: (104, 104) SE Inner + // Blob 3: (115, 90) NE Outer + // Blob 4: (85, 110) SW Outer + // Pattern 4 + // Blob 1: (96, 104) SW Inner + // Blob 2: (104, 96) NE Inner + // Blob 3: (115, 110) SE Outer + // Blob 4: (86, 90) NW Outer + type: 'Ability', + netRegex: { id: 'B4B6', capture: true }, + suppressSeconds: 10, + run: (data, matches) => { + const x = parseFloat(matches.x); + const y = parseFloat(matches.y); + const dir = Directions.xyToIntercardDirOutput(x, y, center.x, center.y); + data.blobTowerDirs.push(dir); + + if (dir === 'dirSE') { + data.blobTowerDirs.push('dirNW'); + data.blobTowerDirs.push('dirSW'); + data.blobTowerDirs.push('dirNE'); + } else if (dir === 'dirNE') { + data.blobTowerDirs.push('dirSW'); + data.blobTowerDirs.push('dirNW'); + data.blobTowerDirs.push('dirSE'); + } else if (dir === 'dirNW') { + data.blobTowerDirs.push('dirSE'); + data.blobTowerDirs.push('dirNE'); + data.blobTowerDirs.push('dirSW'); + } else if (dir === 'dirSW') { + data.blobTowerDirs.push('dirNE'); + data.blobTowerDirs.push('dirSE'); + data.blobTowerDirs.push('dirNW'); + } + }, + }, + { + id: 'R12S Phagocyte Spotlight Blob Tower Location (Early)', + // 23.8s until B4B7 Rolling Mass Blob Tower Hit + // Only need to know first blob location + type: 'Ability', + netRegex: { id: 'B4B6', capture: false }, + condition: (data) => data.myFleshBonds === 'alpha', + delaySeconds: 0.1, + durationSeconds: (data) => { + const myNum = data.inLine[data.me]; + // Timings based on next trigger + switch (myNum) { + case 1: + return 17; + case 2: + return 22; + case 3: + return 18; + case 4: + return 18; + } + }, + suppressSeconds: 10, + infoText: (data, _matches, output) => { + const myNum = data.inLine[data.me]; + if (myNum === undefined) + return; + + type index = { + [key: number]: number; + }; + const myNumToDirIndex: index = { + 1: 2, + 2: 3, + 3: 0, + 4: 1, + }; + const dirIndex = myNumToDirIndex[myNum]; + if (dirIndex === undefined) + return; + const towerNum = dirIndex + 1; + + const dir = data.blobTowerDirs[dirIndex]; + if (dir === undefined) + return; + + if (myNum > 2) + return output.innerBlobTower!({ + num: towerNum, + dir: output[dir]!(), + }); + return output.outerBlobTower!({ num: towerNum, dir: output[dir]!() }); + }, + outputStrings: { + ...Directions.outputStringsIntercardDir, + innerBlobTower: { + en: 'Blob Tower ${num} Inner ${dir} (later)', + }, + outerBlobTower: { + en: 'Blob Tower ${num} Outer ${dir} (later)', + }, + }, + }, + { + id: 'R12S Cursed Coil Bind Knocbkack', + // Using Phagocyte Spotlight, 1st one happens 7s before bind + // Delayed additionally to reduce overlap with alpha tower location calls + type: 'Ability', + netRegex: { id: 'B4B6', capture: false }, + delaySeconds: 3, // 5s warning + suppressSeconds: 10, + response: Responses.knockback(), + }, + { + id: 'R12S Skinsplitter Counter', + // These occur every 5s + // Useful for blob tower tracking that happen 2s after + // 2: Tether 1 + // 3: Tether 2 + Blob Tower 1 + // 4: Tether 3 + Blob Tower 2 + // 5: Tether 4 + Blob Tower 3 + // 6: Blob Tower 4 + // 7: Last time to exit + type: 'Ability', + netRegex: { id: 'B4BC', capture: false }, + suppressSeconds: 1, + run: (data) => data.skinsplitterCount = data.skinsplitterCount + 1, + }, + { + id: 'R12S Cell Chain Counter', + type: 'Tether', + netRegex: { id: headMarkerData['cellChainTether'], capture: false }, + condition: (data) => data.phase === 'doorboss', + run: (data) => data.cellChainCount = data.cellChainCount + 1, + }, + { + id: 'R12S Cell Chain Tether Number', + // Helpful for players to keep track of which chain tower is next + // Does not output when it is their turn to break the tether + type: 'Tether', + netRegex: { id: headMarkerData['cellChainTether'], capture: false }, + condition: (data) => { + if (data.phase === 'doorboss' && data.myFleshBonds === 'beta') + return true; + return false; + }, + infoText: (data, _matches, output) => { + const myNum = data.inLine[data.me]; + const num = data.cellChainCount; + if (myNum !== num) { + if (myNum === 1 && num === 3) + return output.beta1Tower!({ + tether: output.tether!({ num: num }), + }); + if (myNum === 2 && num === 4) + return output.beta2Tower!({ + tether: output.tether!({ num: num }), + }); + if (myNum === 3 && num === 1) + return output.beta3Tower!({ + tether: output.tether!({ num: num }), + }); + if (myNum === 4 && num === 2) + return output.beta4Tower!({ + tether: output.tether!({ num: num }), + }); + + return output.tether!({ num: num }); + } + + if (myNum === undefined) + return output.tether!({ num: num }); + }, + outputStrings: { + tether: { + en: 'Tether ${num}', + de: 'Verbindung ${num}', + fr: 'Lien ${num}', + ja: '線 ${num}', + cn: '线 ${num}', + ko: '선 ${num}', + tc: '線 ${num}', + }, + beta1Tower: { + en: '${tether} => Chain Tower 3', + }, + beta2Tower: { + en: '${tether} => Chain Tower 4', + }, + beta3Tower: { + en: '${tether} => Chain Tower 1', + }, + beta4Tower: { + en: '${tether} => Chain Tower 2', + }, + }, + }, + { + id: 'R12S Chain Tower Number', + // Using B4B4 Dramatic Lysis to detect chain broken + type: 'Ability', + netRegex: { id: 'B4B4', capture: false }, + condition: (data) => { + if (data.phase === 'doorboss' && data.myFleshBonds === 'beta') + return true; + return false; + }, + suppressSeconds: 1, + alertText: (data, _matches, output) => { + const mechanicNum = data.cellChainCount; + const myNum = data.inLine[data.me]; + if (myNum === undefined) + return; + + type index = { + [key: number]: number; + }; + const myNumToOrder: index = { + 1: 3, + 2: 4, + 3: 1, + 4: 2, + }; + + const myOrder = myNumToOrder[myNum]; + if (myOrder === undefined) + return; + + if (myOrder === mechanicNum) + return output.tower!({ num: mechanicNum }); + }, + outputStrings: { + tower: { + en: 'Get Chain Tower ${num}', + }, + }, + }, + { + id: 'R12S Bonds of Flesh Flesh α First Two Towers', + // These are not dependent on player timings and so can be hard coded by duration + type: 'GainsEffect', + netRegex: { effectId: '1290', capture: true }, + condition: (data, matches) => { + if (matches.target === data.me) { + const duration = parseFloat(matches.duration); + if (duration < 35) + return false; + return true; + } + return false; + }, + delaySeconds: (_data, matches) => { + const duration = parseFloat(matches.duration); + // The following gives 5s warning to take tower + if (duration > 37) + return 31; // Alpha4 Time + return 26; // Alpha3 Time + }, + alertText: (data, matches, output) => { + const duration = parseFloat(matches.duration); + const dir = data.blobTowerDirs[duration > 40 ? 1 : 0]; + if (duration > 40) { + if (dir !== undefined) + return output.alpha4Dir!({ dir: output[dir]!() }); + return output.alpha4!(); + } + if (dir !== undefined) + return output.alpha3Dir!({ dir: output[dir]!() }); + return output.alpha3!(); + }, + outputStrings: { + ...Directions.outputStringsIntercardDir, + alpha3: { + en: 'Get Blob Tower 1', + }, + alpha4: { + en: 'Get Blob Tower 2', + }, + alpha3Dir: { + en: 'Get Blob Tower 1 (Inner ${dir})', + }, + alpha4Dir: { + en: 'Get Blob Tower 2 (Inner ${dir})', + }, + }, + }, + { + id: 'R12S Unbreakable Flesh α/β Chains and Last Two Towers', + type: 'GainsEffect', + netRegex: { effectId: ['1291', '1293'], capture: true }, + condition: (data, matches) => { + if (matches.target === data.me && data.phase === 'doorboss') + return true; + return false; + }, + alertText: (data, matches, output) => { + const myNum = data.inLine[data.me]; + const flesh = matches.effectId === '1291' ? 'alpha' : 'beta'; + if (flesh === 'alpha') { + if (myNum === 1) { + const dir = data.blobTowerDirs[2]; + if (dir !== undefined) + return output.alpha1Dir!({ + chains: output.breakChains!(), + dir: output[dir]!(), + }); + } + if (myNum === 2) { + const dir = data.blobTowerDirs[3]; + if (dir !== undefined) + return output.alpha2Dir!({ + chains: output.breakChains!(), + dir: output[dir]!(), + }); + } + + // dir undefined or 3rd/4rth in line + switch (myNum) { + case 1: + return output.alpha1!({ chains: output.breakChains!() }); + case 2: + return output.alpha2!({ chains: output.breakChains!() }); + case 3: + return output.alpha3!({ chains: output.breakChains!() }); + case 4: + return output.alpha4!({ chains: output.breakChains!() }); + } + } + switch (myNum) { + case 1: + return output.beta1!({ chains: output.breakChains!() }); + case 2: + return output.beta2!({ chains: output.breakChains!() }); + case 3: + return output.beta3!({ chains: output.breakChains!() }); + case 4: + return output.beta4!({ chains: output.breakChains!() }); + } + return output.getTowers!(); + }, + outputStrings: { + ...Directions.outputStringsIntercardDir, + breakChains: Outputs.breakChains, + getTowers: Outputs.getTowers, + alpha1: { + en: '${chains} 1 + Blob Tower 3 (Outer)', + }, + alpha1Dir: { + en: '${chains} 1 + Blob Tower 3 (Outer ${dir})', + }, + alpha2: { + en: '${chains} 2 + Blob Tower 4 (Outer)', + }, + alpha2Dir: { + en: '${chains} 2 + Blob Tower 4 (Outer ${dir})', + }, + alpha3: { + en: '${chains} 3 + Get Out', + }, + alpha4: { + en: '${chains} 4 + Get Out', + }, + beta1: { + en: '${chains} 1 => Get Middle', + }, + beta2: { + en: '${chains} 2 => Get Middle', + }, + beta3: { + en: '${chains} 3 => Wait for last pair', + }, + beta4: { + en: '${chains} 4 => Get Out', + }, + }, + }, + { + id: 'R12S Chain Tower Followup', + // Using B4B3 Roiling Mass to detect chain tower soak + // Beta player leaving early may get hit by alpha's chain break aoe + type: 'Ability', + netRegex: { id: 'B4B3', capture: true }, + condition: (data, matches) => { + if (data.myFleshBonds === 'beta' && data.me === matches.target) + return true; + return false; + }, + infoText: (data, _matches, output) => { + // Possibly the count could be off if break late (giving damage and damage down) + // Ideal towers are soaked: + // Beta 1 at 5th Skinsplitter + // Beta 2 at 6th Skinsplitter + // Beta 3 at 3rd Skinsplitter + // Beta 4 at 4rth Skinsplitter + const mechanicNum = data.skinsplitterCount; + const myNum = data.inLine[data.me]; + if (myNum === undefined) { + // This can be corrected by the player later + if (mechanicNum < 5) + return output.goIntoMiddle!(); + return output.getOut!(); + } + + if (mechanicNum < 5) { + if (myNum === 1) + return output.beta1Middle!(); + if (myNum === 2) + return output.beta2Middle!(); + if (myNum === 3) + return output.beta3Middle!(); + if (myNum === 4) + return output.beta4Middle!(); + } + if (myNum === 1) + return output.beta1Out!(); + if (myNum === 2) + return output.beta2Out!(); + if (myNum === 3) + return output.beta3Out!(); + if (myNum === 4) + return output.beta4Out!(); + }, + outputStrings: { + getOut: { + en: 'Get Out', + de: 'Raus da', + fr: 'Sortez', + ja: '外へ', + cn: '远离', + ko: '밖으로', + tc: '遠離', + }, + goIntoMiddle: Outputs.goIntoMiddle, + beta1Middle: Outputs.goIntoMiddle, + beta2Middle: Outputs.goIntoMiddle, // Should not happen under ideal situation + beta3Middle: Outputs.goIntoMiddle, + beta4Middle: Outputs.goIntoMiddle, + beta1Out: { // Should not happen under ideal situation + en: 'Get Out', + de: 'Raus da', + fr: 'Sortez', + ja: '外へ', + cn: '远离', + ko: '밖으로', + tc: '遠離', + }, + beta2Out: { + en: 'Get Out', + de: 'Raus da', + fr: 'Sortez', + ja: '外へ', + cn: '远离', + ko: '밖으로', + tc: '遠離', + }, + beta3Out: { // Should not happen under ideal situation + en: 'Get Out', + de: 'Raus da', + fr: 'Sortez', + ja: '外へ', + cn: '远离', + ko: '밖으로', + tc: '遠離', + }, + beta4Out: { // Should not happen under ideal situation + en: 'Get Out', + de: 'Raus da', + fr: 'Sortez', + ja: '外へ', + cn: '远离', + ko: '밖으로', + tc: '遠離', + }, + }, + }, + { + id: 'R12S Blob Tower Followup', + // Using B4B7 Roiling Mass to detect chain tower soak + // Alpha 3 and Alpha 4 get the inner towers before their chains + type: 'Ability', + netRegex: { id: 'B4B7', capture: true }, + condition: (data, matches) => { + if (data.myFleshBonds === 'alpha' && data.me === matches.target) + return true; + return false; + }, + infoText: (data, _matches, output) => { + const mechanicNum = data.skinsplitterCount; + const myNum = data.inLine[data.me]; + if (myNum === undefined) + return; + + if (myNum === mechanicNum) + return output.goIntoMiddle!(); + }, + outputStrings: { + goIntoMiddle: Outputs.goIntoMiddle, + }, + }, + { + id: 'R12S Splattershed', + type: 'StartsUsing', + netRegex: { id: ['B9C3', 'B9C4'], source: 'Lindwurm', capture: false }, + response: Responses.aoe(), + }, + { + id: 'R12S Mitotic Phase Direction Collect', + // Unknown_DE6 spell contains data in its count + type: 'GainsEffect', + netRegex: { effectId: 'DE6', capture: true }, + condition: Conditions.targetIsYou(), + durationSeconds: 10, + infoText: (data, matches, output) => { + data.myMitoticPhase = matches.count; + switch (matches.count) { + case '436': + return output.frontTower!(); + case '437': + return output.rightTower!(); + case '438': + return output.rearTower!(); + case '439': + return output.leftTower!(); + } + }, + outputStrings: { + frontTower: { + en: 'Tower (S/SW)', + }, + rearTower: { + en: 'Tower (N/NE)', + }, + leftTower: { + en: 'Tower (E/SE)', + }, + rightTower: { + en: 'Tower (W/NW)', + }, + }, + }, + { + id: 'R12S Grand Entrance Intercards/Cardinals', + // B4A1 is only cast when cardinals are safe + // B4A2 is only cast when intercardinals are safe + // These casts more than once, so just capture first event + type: 'StartsUsing', + netRegex: { id: ['B4A1', 'B4A2'], capture: true }, + suppressSeconds: 5, + infoText: (data, matches, output) => { + const count = data.myMitoticPhase; + if (count === undefined) + return; + if (matches.id === 'B4A1') { + switch (count) { + case '436': + return output.frontCardinals!(); + case '437': + return output.rightCardinals!(); + case '438': + return output.rearCardinals!(); + case '439': + return output.leftCardinals!(); + } + } + switch (count) { + case '436': + return output.frontIntercards!(); + case '437': + return output.rightIntercards!(); + case '438': + return output.rearIntercards!(); + case '439': + return output.leftIntercards!(); + } + }, + outputStrings: { + frontIntercards: Outputs.southwest, + rearIntercards: Outputs.northeast, + leftIntercards: Outputs.southeast, + rightIntercards: Outputs.northwest, + frontCardinals: Outputs.south, + rearCardinals: Outputs.north, + leftCardinals: Outputs.east, + rightCardinals: Outputs.west, + }, + }, + { + id: 'R12S Rotting Flesh', + type: 'GainsEffect', + netRegex: { effectId: '129B', capture: true }, + condition: Conditions.targetIsYou(), + durationSeconds: 10, + infoText: (_data, _matches, output) => output.text!(), + outputStrings: { + text: { + en: 'Rotting Flesh on YOU', + }, + }, + }, + { + id: 'R12S Rotting Flesh Collect', + type: 'GainsEffect', + netRegex: { effectId: '129B', capture: true }, + condition: Conditions.targetIsYou(), + run: (data) => data.hasRot = true, + }, + { + id: 'R12S Ravenous Reach 2', + // These two syncs indicate the animation of where the head will go to cleave + // B49A => West Safe + // B49B => East Safe + type: 'Ability', + netRegex: { id: ['B49A', 'B49B'], source: 'Lindwurm', capture: true }, + condition: (data) => data.phase === 'curtainCall', + alertText: (data, matches, output) => { + if (matches.id === 'B49A') { + return data.hasRot ? output.getHitEast!() : output.safeWest!(); + } + return data.hasRot ? output.getHitWest!() : output.safeEast!(); + }, + outputStrings: { + getHitWest: { + en: 'Spread in West Cleave', + }, + getHitEast: { + en: 'Spread in East Cleave', + }, + safeEast: { + en: 'Spread East', + }, + safeWest: { + en: 'Spread West', + }, + }, + }, + { + id: 'R12S Split Scourge and Venomous Scourge', + // B4AB Split Scourge and B4A8 Venomous Scourge are instant casts + // This actor control happens along with boss becoming targetable + type: 'ActorControl', + netRegex: { command: '8000000D', data0: '1E01', capture: false }, + durationSeconds: 9, + suppressSeconds: 1, + infoText: (data, _matches, output) => { + if (data.role === 'tank') + return output.tank!(); + return output.party!(); + }, + outputStrings: { + tank: { + en: 'Bait Line AoE from heads', + }, + party: { + en: 'Spread, Away from heads', + }, + }, + }, + { + id: 'R12S Grotesquerie: Curtain Call Spreads', + type: 'StartsUsing', + netRegex: { id: 'BEC0', source: 'Lindwurm', capture: false }, + infoText: (_data, _matches, output) => output.text!(), + outputStrings: { + text: 'Bait 5x Puddles', + }, + }, + { + id: 'R12S Curtain Call: Unbreakable Flesh α/β Chains', + // TODO: Find safe spots + type: 'GainsEffect', + netRegex: { effectId: ['1291', '1293'], capture: true }, + condition: (data, matches) => { + if (matches.target === data.me && data.phase === 'curtainCall') + return true; + return false; + }, + infoText: (_data, matches, output) => { + const flesh = matches.effectId === '1291' ? 'alpha' : 'beta'; + if (flesh === 'alpha') + return output.alphaChains!({ + chains: output.breakChains!(), + safe: output.safeSpots!(), + }); + if (flesh === 'beta') + return output.betaChains!({ + chains: output.breakChains!(), + safe: output.breakChains!(), + }); + return output.unknownChains!({ + chains: output.breakChains!(), + safe: output.breakChains!(), + }); + }, + outputStrings: { + breakChains: Outputs.breakChains, + safeSpots: { + en: 'Avoid Blobs', + }, + alphaChains: { + en: '${chains} => ${safe}', + }, + betaChains: { + en: '${chains} => ${safe}', + }, + unknownChains: { + en: '${chains} => ${safe}', + }, + }, + }, + { + id: 'R12S Slaughtershed', + type: 'StartsUsing', + netRegex: { id: ['B4C6', 'B4C3'], source: 'Lindwurm', capture: false }, + response: Responses.bigAoe('alert'), + }, + { + id: 'R12S Slaughtershed Stack', + // TODO: Get Safe spot + type: 'HeadMarker', + netRegex: { id: headMarkerData['slaughterStack'], capture: true }, + condition: (data, matches) => { + const isDPS = data.party.isDPS(matches.target); + if (isDPS && data.role === 'dps') + return true; + if (!isDPS && data.role !== 'dps') + return true; + return false; + }, + durationSeconds: 5.1, + response: Responses.stackMarkerOn(), + }, + { + id: 'R12S Slaughtershed Spread', + // TODO: Get Safe spot + type: 'HeadMarker', + netRegex: { id: headMarkerData['slaughterSpread'], capture: true }, + condition: Conditions.targetIsYou(), + durationSeconds: 5.1, + suppressSeconds: 1, + response: Responses.spread(), + }, + { + id: 'R12S Serpintine Scourge Right Hand First', + // Left Hand first, then Right Hand + type: 'Ability', + netRegex: { id: 'B4CB', source: 'Lindwurm', capture: false }, + condition: (data) => data.phase === 'slaughtershed', + durationSeconds: 12, + infoText: (_data, _matches, output) => output.rightThenLeft!(), + outputStrings: { + rightThenLeft: Outputs.rightThenLeft, + }, + }, + { + id: 'R12S Serpintine Scourge Left Hand First', + // Right Hand first, then Left Hand + type: 'Ability', + netRegex: { id: 'B4CD', source: 'Lindwurm', capture: false }, + condition: (data) => data.phase === 'slaughtershed', + durationSeconds: 12, + infoText: (_data, _matches, output) => output.leftThenRight!(), + outputStrings: { + leftThenRight: Outputs.leftThenRight, + }, + }, + { + id: 'R12S Raptor Knuckles Right Hand First', + // Right Hand first, then Left Hand + type: 'Ability', + netRegex: { id: 'B4CC', source: 'Lindwurm', capture: false }, + condition: (data) => data.phase === 'slaughtershed', + durationSeconds: 15, + infoText: (_data, _matches, output) => output.text!(), + outputStrings: { + text: { + en: 'Northwest: Knockback to Northeast', + }, + }, + }, + { + id: 'R12S Raptor Knuckles Left Hand First', + // Left Hand first, then Right Hand + type: 'Ability', + netRegex: { id: 'B4CE', source: 'Lindwurm', capture: false }, + condition: (data) => data.phase === 'slaughtershed', + durationSeconds: 15, + infoText: (_data, _matches, output) => output.text!(), + outputStrings: { + text: { + en: 'Northeast: Knockback to Northwest', + }, + }, + }, + { + id: 'R12S Refreshing Overkill', + // 10s castTime that could end with enrage or raidwide + type: 'StartsUsing', + netRegex: { id: 'B538', source: 'Lindwurm', capture: true }, + delaySeconds: (_data, matches) => parseFloat(matches.castTime) - 4, + durationSeconds: 4.7, + response: Responses.bigAoe('alert'), + }, + // Phase 2 + { + id: 'R12S Arcadia Aflame', + type: 'StartsUsing', + netRegex: { id: 'B528', source: 'Lindwurm', capture: false }, + response: Responses.bigAoe('alert'), + }, + { + id: 'R12S Snaking Kick', + type: 'StartsUsing', + netRegex: { id: 'B527', source: 'Lindwurm', capture: false }, + response: Responses.getBehind(), + }, + { + id: 'R12S Double Sobat', + type: 'StartsUsing', + netRegex: { id: 'B520', source: 'Lindwurm', capture: true }, + response: Responses.tankCleave(), + }, + ], + timelineReplace: [], +}; + +export default triggerSet; diff --git a/ui/raidboss/data/07-dt/raid/r12s.txt b/ui/raidboss/data/07-dt/raid/r12s.txt new file mode 100644 index 0000000000..e72d73a4de --- /dev/null +++ b/ui/raidboss/data/07-dt/raid/r12s.txt @@ -0,0 +1,465 @@ +### AAC HEAVYWEIGHT M4 (SAVAGE) +# ZoneId: 1327 + +hideall "--Reset--" +hideall "--sync--" + +0.0 "--Reset--" ActorControl { command: "4000000F" } window 0,100000 jump 0 + +### Phase 1: Lindwurm +# -ii B4D3 B495 B4B2 B4B4 B4B3 B4BD B4BE B53E B4B5 B4B1 BE0A B570 B56F B4AD B76A B469 B769 +# -it "Lindwurm" + +0.0 "--sync--" InCombat { inGameCombat: "1" } window 0,1 +1.0 "--sync--" AddedCombatant { npcNameId: "14378", name: "Lindwurm", job: "00", level: "1", ownerId: "0{4}", worldId: "00" } window 10,3 jump "r12s-p2-start" # Sync to P2 immediately through AddCombatant. +15.6 "The Fixer" Ability { id: "B4D7", source: "Lindwurm" } window 20,10 +25.8 "--sync--" Ability { id: "B7C4", source: "Lindwurm" } +40.9 "Mortal Slayer 1" Ability { id: ["B496", "B498"], source: "Lindwurm" } +43.9 "Mortal Slayer 2" Ability { id: ["B496", "B498"], source: "Lindwurm" } +46.9 "Mortal Slayer 3" Ability { id: ["B496", "B498"], source: "Lindwurm" } +49.9 "Mortal Slayer 4" Ability { id: ["B496", "B498"], source: "Lindwurm" } +52.9 "--sync--" Ability { id: "B7C5", source: "Lindwurm" } +61.0 "--sync--" Ability { id: "B9DB", source: "Lindwurm" } + +70.0 "Grotesquerie: Act 1" Ability { id: "BEBD", source: "Lindwurm" } window 70,5 +77.2 "--sync--" Ability { id: ["B49A", "B49B"], source: "Lindwurm" } +79.2 "Phagocyte Spotlight 1" #Ability { id: "B49E", source: "Lindwurm" } +81.2 "Phagocyte Spotlight 2" #Ability { id: "B49E", source: "Lindwurm" } +83.2 "Phagocyte Spotlight 3" #Ability { id: "B49E", source: "Lindwurm" } +85.2 "Phagocyte Spotlight 4" #Ability { id: "B49E", source: "Lindwurm" } +87.3 "--sync--" #Ability { id: "B46E", source: "Lindwurm" } +87.7 "Ravenous Reach" Ability { id: "B49D", source: "Lindwurm" } +88.0 "Hemorrhagic Projection x8" #Ability { id: "B4AF", source: "Lindwurm" } +88.0 "Dramatic Lysis x4" #Ability { id: "B4AA", source: "Lindwurm" } +88.0 "Fourth-wall Fusion" Ability { id: "B4AE", source: "Lindwurm" } +96.7 "Burst" Ability { id: "B49F", source: "Lindwurm" } +97.3 "Visceral Burst x2" #Ability { id: "B4D6", source: "Lindwurm" } +97.3 "Fourth-wall Fusion" Ability { id: "B9B9", source: "Lindwurm" } +107.3 "The Fixer" Ability { id: "B4D7", source: "Lindwurm" } + +119.5 "Grotesquerie: Act 2" Ability { id: "BEBE", source: "Lindwurm" } window 120,5 +128.7 "Phagocyte Spotlight 1" #Ability { id: "B4B6", source: "Lindwurm" } +130.7 "Phagocyte Spotlight 2" #Ability { id: "B4B6", source: "Lindwurm" } +132.7 "Phagocyte Spotlight 3" #Ability { id: "B4B6", source: "Lindwurm" } +134.7 "Cruel Coil" Ability { id: ["B4B9", "B4B8"], source: "Lindwurm" } +134.7 "Phagocyte Spotlight 4" #Ability { id: "B4B6", source: "Lindwurm" } +135.7 "--bind--" Ability { id: "B472", source: "Lindwurm" } duration 5 +140.7 "Skinsplitter 1" Ability { id: "B4BC", source: "Lindwurm" } +143.7 "--sync--" Ability { id: "B4C1", source: "Lindwurm" } +145.7 "Skinsplitter 2" Ability { id: "B4BC", source: "Lindwurm" } +145.7 "--tether 1--" +150.7 "Skinsplitter 3" Ability { id: "B4BC", source: "Lindwurm" } +150.7 "--tether 2--" +152.7 "Roiling Mass 1" Ability { id: "B4B7", source: "Blood Vessel" } +155.7 "Skinsplitter 4" Ability { id: "B4BC", source: "Lindwurm" } +155.7 "--tether 3--" +157.7 "Roiling Mass 2" Ability { id: "B4B7", source: "Blood Vessel" } +160.7 "Skinsplitter 5" Ability { id: "B4BC", source: "Lindwurm" } +160.7 "--tether 4--" +162.7 "Roiling Mass 3" Ability { id: "B4B7", source: "Blood Vessel" } +165.7 "Skinsplitter 6" Ability { id: "B4BC", source: "Lindwurm" } +167.7 "Roiling Mass 4" Ability { id: "B4B7", source: "Blood Vessel" } +170.7 "Skinsplitter 7" Ability { id: "B4BC", source: "Lindwurm" } +176.7 "Constrictor" Ability { id: "B4C2", source: "Lindwurm" } +185.8 "Splattershed (castbar)" Ability { id: "B9C4", source: "Lindwurm" } +188.2 "Splattershed" Ability { id: "B9C6", source: "Lindwurm" } +189.9 "--sync--" Ability { id: "B4CB", source: "Lindwurm" } + +205.9 "Grotesquerie: Act 3" Ability { id: "BEBF", source: "Lindwurm" } window 205,5 +209.0 "--untargetable--" +211.0 "Feral Fission" Ability { id: "BE09", source: "Lindwurm" } +212.0 "Grand Entrance" #Ability { id: ["B4A1", "B4A0"], source: "Lindwurm" } +212.3 "Grand Entrance" #Ability { id: ["B4A1", "B4A2"], source: "Lindwurm" } +212.4 "Grand Entrance" #Ability { id: "B4A3", source: "Lindwurm" } +212.5 "Grand Entrance" Ability { id: "B4A0", source: "Lindwurm" } +212.6 "Grand Entrance" #Ability { id: "B4A3", source: "Lindwurm" } +212.7 "Grand Entrance" #Ability { id: ["B4A1", "B4A2"], source: "Lindwurm" } +212.8 "Grand Entrance" #Ability { id: "B4A3", source: "Lindwurm" } +212.8 "Grand Entrance" #Ability { id: ["B4A1", "B4A2"], source: "Lindwurm" } +213.0 "Grand Entrance" #Ability { id: "B4A3", source: "Lindwurm" } +213.2 "Grand Entrance" #Ability { id: "B4A3", source: "Lindwurm" } +215.6 "Bring Down the House" Ability { id: ["B4A5", "B4A4"], source: "Lindwurm" } +218.0 "Dramatic Lysis x8" #Ability { id: "B4B0", source: "Lindwurm" } +218.2 "Metamitosis x8" Ability { id: "B923", source: "Lindwurm" } +220.6 "--targetable--" +226.9 "Split Scourge (cast)" Ability { id: "B4A7", source: "Lindwurm" } +228.0 "Split Scourge" Ability { id: "B4AB", source: "Lindwurm" } +230.4 "Venomous Scourge" Ability { id: "B4A8", source: "Lindwurm" } +231.5 "--sync--" Ability { id: "B479", source: "Lindwurm" } +239.6 "The Fixer" Ability { id: "B4D7", source: "Lindwurm" } + +251.7 "Grotesquerie: Curtain Call" Ability { id: "BEC0", source: "Lindwurm" } window 251,5 +255.7 "Phagocyte Spotlight 1" #Ability { id: "B49E", source: "Lindwurm" } +255.8 "--sync--" Ability { id: ["B49A", "B49B"], source: "Lindwurm" } +257.6 "Phagocyte Spotlight 2" #Ability { id: "B49E", source: "Lindwurm" } +259.6 "Phagocyte Spotlight 3" #Ability { id: "B49E", source: "Lindwurm" } +261.6 "Phagocyte Spotlight 4" #Ability { id: "B49E", source: "Lindwurm" } +263.6 "Phagocyte Spotlight 5" #Ability { id: "B49E", source: "Lindwurm" } +265.9 "--sync--" Ability { id: "B46E", source: "Lindwurm" } +266.5 "Ravenous Reach" Ability { id: "B49D", source: "Lindwurm" } +266.6 "Cell Shedding x4" #Ability { id: "B4AC", source: "Lindwurm" } +266.8 "Dramatic Lysis x4" #Ability { id: "B4AA", source: "Lindwurm" } +279.4 "Burst" Ability { id: "B49F", source: "Lindwurm" } +286.1 "Splattershed (castbar)" Ability { id: "B9C3", source: "Lindwurm" } +288.5 "Splattershed" Ability { id: "B9C6", source: "Lindwurm" } +290.2 "--sync--" Ability { id: "B4CC", source: "Lindwurm" } +299.3 "--sync--" Ability { id: "B7C4", source: "Lindwurm" } +314.4 "Mortal Slayer 1" Ability { id: ["B496", "B498"], source: "Lindwurm" } +317.4 "Mortal Slayer 2" Ability { id: ["B496", "B498"], source: "Lindwurm" } +320.4 "Mortal Slayer 3" Ability { id: ["B496", "B498"], source: "Lindwurm" } +323.4 "Mortal Slayer 4" Ability { id: ["B496", "B498"], source: "Lindwurm" } +326.4 "--sync--" Ability { id: "B7C5", source: "Lindwurm" } + +# Slaughershed 1 +338.5 "Slaughtershed 1 (castbar)" Ability { id: ["B4C3", "B4C6"], source: "Lindwurm" } window 338,5 +340.9 "Slaughtershed 1" Ability { id: "ADC9", source: "Lindwurm" } +342.6 "--sync--" Ability { id: "B4CB", source: "Lindwurm" } jump "r12s-p1-scourge-left-1" +342.6 "--sync--" Ability { id: "B4CD", source: "Lindwurm" } jump "r12s-p1-scourge-right-1" +342.6 "--sync--" Ability { id: "B4CE", source: "Lindwurm" } jump "r12s-p1-raptor-left-1" +342.6 "--sync--" Ability { id: "B4CC", source: "Lindwurm" } jump "r12s-p1-raptor-right-1" +349.6 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +349.6 "Fourth-wall Fusion" #Ability { id: "B4D5", source: "Lindwurm" } +350.0 "Burst" #Ability { id: "B49F", source: "Lindwurm" } +355.1 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D1", "B4D2", "B4CD", "B4CE"], source: "Lindwurm" } +356.1 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +359.8 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D2", "B4D1", "B4CE", "B4CD"], source: "Lindwurm" } +360.8 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +367.4 "Slaughtershed 2 (castbar)" #Ability { id: ["B4C3", "B4C6"], source: "Lindwurm" } +369.8 "Slaughtershed 2" #Ability { id: "ADC9", source: "Lindwurm" } + +# Serpentine Scourge Left First +442.6 label "r12s-p1-scourge-left-1" +449.6 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +449.6 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +450.0 "Burst" Ability { id: "B49F", source: "Lindwurm" } +455.1 "Serpentine Scourge Left" Ability { id: "B4D1", source: "Lindwurm" } +456.1 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +459.8 "Serpentine Scourge Right" Ability { id: "B4D2", source: "Lindwurm" } +460.8 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +464.4 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed2" + +# Serpentine Scourge Right First +540.6 label "r12s-p1-scourge-right-1" +547.6 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +547.6 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +548.0 "Burst" Ability { id: "B49F", source: "Lindwurm" } +553.1 "Serpentine Scourge Right" Ability { id: "B4D2", source: "Lindwurm" } +554.1 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +557.7 "Serpentine Scourge Left" Ability { id: "B4D1", source: "Lindwurm" } +558.7 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +562.4 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed2" + +# Raptor Knuckles Left First +641.1 label "r12s-p1-raptor-left-1" +648.1 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +648.1 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +648.5 "Burst" Ability { id: "B49F", source: "Lindwurm" } +653.6 "Raptor Knuckles Northeast" Ability { id: "B4D0", source: "Lindwurm" } +654.4 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +658.3 "Raptor Knuckles Northwest" Ability { id: "B4CF", source: "Lindwurm" } +659.1 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +662.9 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed2" + +# Raptor Knuckles Right First +742.7 label "r12s-p1-raptor-right-1" +749.7 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +749.7 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +750.1 "Burst" Ability { id: "B49F", source: "Lindwurm" } +755.2 "Raptor Knuckles Northwest" Ability { id: "B4CF", source: "Lindwurm" } +756.1 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +759.9 "Raptor Knuckles Northeast" Ability { id: "B4D0", source: "Lindwurm" } +760.7 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +764.5 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed2" + +# Slaughtershed 2 +864.4 label "r12s-p1-slaughtershed2" +867.4 "Slaughtershed 2 (castbar)" Ability { id: ["B4C3", "B4C6"], source: "Lindwurm" } +869.8 "Slaughtershed 2" Ability { id: "ADC9", source: "Lindwurm" } + +871.5 "--sync--" Ability { id: "B4CB", source: "Lindwurm" } jump "r12s-p1-scourge-left-2" +871.5 "--sync--" Ability { id: "B4CD", source: "Lindwurm" } jump "r12s-p1-scourge-right-2" +871.5 "--sync--" Ability { id: "B4CE", source: "Lindwurm" } jump "r12s-p1-raptor-left-2" +871.5 "--sync--" Ability { id: "B4CC", source: "Lindwurm" } jump "r12s-p1-raptor-right-2" +878.5 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +878.5 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +878.9 "Burst" Ability { id: "B49F", source: "Lindwurm" } +884.0 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D1", "B4D2", "B4CD", "B4CE"], source: "Lindwurm" } +884.8 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +888.6 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D2", "B4D1", "B4CE", "B4CD"], source: "Lindwurm" } +889.4 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +896.3 "Slaughtershed 3 (castbar)" #Ability { id: ["B4C3", "B4C6"], source: "Lindwurm" } +898.7 "Slaughtershed 3" #Ability { id: "ADC9", source: "Lindwurm" } + +# Serpentine Scourge Left Second +971.6 label "r12s-p1-scourge-left-2" +978.6 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +978.6 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +979.0 "Burst" Ability { id: "B49F", source: "Lindwurm" } +984.1 "Serpentine Scourge Left" Ability { id: "B4D1", source: "Lindwurm" } +985.1 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +988.7 "Serpentine Scourge Right" Ability { id: "B4D2", source: "Lindwurm" } +989.7 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +993.3 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed3" + +# Serpentine Scourge Right Second +1069.9 label "r12s-p1-scourge-right-2" +1076.9 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1076.9 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1077.3 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1082.4 "Serpentine Scourge Right" Ability { id: "B4D2", source: "Lindwurm" } +1083.4 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1087.0 "Serpentine Scourge Left" Ability { id: "B4D1", source: "Lindwurm" } +1088.0 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1091.7 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed3" + +# Raptor Knuckles Left Second +1171.5 label "r12s-p1-raptor-left-2" +1178.5 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1178.5 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1178.9 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1184.0 "Raptor Knuckles Northeast" Ability { id: "B4D0", source: "Lindwurm" } +1184.8 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1188.6 "Raptor Knuckles Northwest" Ability { id: "B4CF", source: "Lindwurm" } +1189.4 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1193.3 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed3" + +# Raptor Knuckles Right Second +1271.5 label "r12s-p1-raptor-right-2" +1278.5 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1278.5 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1278.9 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1284.0 "Raptor Knuckles Right" Ability { id: "B4CF", source: "Lindwurm" } +1284.8 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1288.6 "Raptor Knuckles Left" Ability { id: "B4D0", source: "Lindwurm" } +1289.4 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1293.3 "--sync--" StartsUsing { id: ["B4C3", "B4C6"], source: "Lindwurm" } forcejump "r12s-p1-slaughtershed3" + +# Slaughtershed 3 +1393.3 label "r12s-p1-slaughtershed3" +1396.3 "Slaughtershed 3 (castbar)" Ability { id: ["B4C3", "B4C6"], source: "Lindwurm" } +1398.7 "Slaughtershed 3" Ability { id: "ADC9", source: "Lindwurm" } + +1400.4 "--sync--" Ability { id: "B4CB", source: "Lindwurm" } jump "r12s-p1-scourge-left-3" +1400.4 "--sync--" Ability { id: "B4CD", source: "Lindwurm" } jump "r12s-p1-scourge-right-3" +1400.4 "--sync--" Ability { id: "B4CE", source: "Lindwurm" } jump "r12s-p1-raptor-left-3" +1400.4 "--sync--" Ability { id: "B4CC", source: "Lindwurm" } jump "r12s-p1-raptor-right-3" +1407.4 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1407.4 "Fourth-wall Fusion" #Ability { id: "B4D5", source: "Lindwurm" } +1407.8 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1412.9 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D1", "B4D2", "B4CD", "B4CE"], source: "Lindwurm" } +1413.9 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +1417.6 "Serpentine Scourge/Raptor Knuckles?" #Ability { id: ["B4D2", "B4D1", "B4CE", "B4CD"], source: "Lindwurm" } +1418.6 "Serpentine Scourge/--knockback--?" #Ability { id: ["B9BC", "B9C7"], source: "Lindwurm" } +1431.5 "The Fixer (Enrage)?" #Ability { id: "B2C7", source: "Lindwurm" } +1436.7 "Refreshing Overkill (Enrage)?" #Ability { id: "B538", source: "Lindwurm" } + +# Serpentine Scourge Left Third +1498.8 label "r12s-p1-scourge-left-3" +1505.8 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1505.8 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1506.2 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1511.3 "Serpentine Scourge Left" Ability { id: "B4D1", source: "Lindwurm" } +1512.3 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1515.9 "Serpentine Scourge Right" Ability { id: "B4D2", source: "Lindwurm" } +1516.9 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1526.5 "--sync--" StartsUsing { id: "B2C7", source: "Lindwurm" } jump "r12s-p1-enrage-alt" +1526.5 "--untargetable?--" +1526.7 "--sync--" StartsUsing { id: "B538", source: "Lindwurm" } jump "r12s-p1-enrage" +1531.5 "The Fixer (Enrage)?" #Ability { id: "B2C7", source: "Lindwurm" } +1536.7 "Refreshing Overkill (Enrage)?" #Ability { id: "B538", source: "Lindwurm" } +1536.8 "--untargetable?--" +1536.8 "Refreshing Overkill (Enrage)?" #Ability { id: "B53A", source: "Lindwurm" } + +# Serpentine Scourge Right Third +1600.4 label "r12s-p1-scourge-right-3" +1607.4 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1607.4 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1607.8 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1612.9 "Serpentine Scourge Left/Right" Ability { id: "B4D2", source: "Lindwurm" } +1613.9 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1617.6 "Serpentine Scourge Right/Left" Ability { id: "B4D1", source: "Lindwurm" } +1618.6 "Serpentine Scourge" Ability { id: "B9BC", source: "Lindwurm" } +1626.5 "--sync--" StartsUsing { id: "B2C7", source: "Lindwurm" } jump "r12s-p1-enrage-alt" +1626.5 "--untargetable?--" +1626.7 "--sync--" StartsUsing { id: "B538", source: "Lindwurm" } jump "r12s-p1-enrage" +1631.5 "The Fixer (Enrage)?" #Ability { id: "B2C7", source: "Lindwurm" } +1636.7 "Refreshing Overkill (Enrage)?" #Ability { id: "B538", source: "Lindwurm" } +1636.8 "--untargetable?--" +1636.8 "Refreshing Overkill (Enrage)?" #Ability { id: "B53A", source: "Lindwurm" } + +# Raptor Knuckles Left Third +1700.4 label "r12s-p1-raptor-left-3" +1707.4 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1707.4 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1707.8 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1712.9 "Raptor Knuckles Northeast" Ability { id: "B4D0", source: "Lindwurm" } +1713.7 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1717.5 "Raptor Knuckles Northwest" Ability { id: "B4CF", source: "Lindwurm" } +1718.3 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1726.5 "--sync--" StartsUsing { id: "B2C7", source: "Lindwurm" } jump "r12s-p1-enrage-alt" +1726.5 "--untargetable?--" +1726.7 "--sync--" StartsUsing { id: "B538", source: "Lindwurm" } jump "r12s-p1-enrage" +1731.5 "The Fixer (Enrage)?" #Ability { id: "B2C7", source: "Lindwurm" } +1736.7 "Refreshing Overkill (Enrage)?" #Ability { id: "B538", source: "Lindwurm" } +1736.8 "--untargetable?--" +1736.8 "Refreshing Overkill (Enrage)?" #Ability { id: "B53A", source: "Lindwurm" } + +# Raptor Knuckles Right Third +1800.4 label "r12s-p1-raptor-right-3" +1807.4 "Dramatic Lysis x4" #Ability { id: "B4D4", source: "Lindwurm" } +1807.4 "Fourth-wall Fusion" Ability { id: "B4D5", source: "Lindwurm" } +1807.8 "Burst" Ability { id: "B49F", source: "Lindwurm" } +1812.9 "Raptor Knuckles Northwest" Ability { id: "B4CF", source: "Lindwurm" } +1813.7 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1817.5 "Raptor Knuckles Northeast" Ability { id: "B4D0", source: "Lindwurm" } +1818.3 "--knockback--" Ability { id: "B9C7", source: "Lindwurm" } +1826.5 "--sync--" StartsUsing { id: "B2C7", source: "Lindwurm" } jump "r12s-p1-enrage-alt" +1826.5 "--untargetable?--" +1826.7 "--sync--" StartsUsing { id: "B538", source: "Lindwurm" } jump "r12s-p1-enrage" +1831.5 "The Fixer (Enrage)?" #Ability { id: "B2C7", source: "Lindwurm" } +1836.7 "Refreshing Overkill (Enrage)?" #Ability { id: "B538", source: "Lindwurm" } +1836.8 "--untargetable?--" +1836.8 "Refreshing Overkill (Enrage)?" #Ability { id: "B53A", source: "Lindwurm" } + +# Enrage sequence (Above 20%?) +1926.5 label "r12s-p1-enrage-alt" +1931.5 "The Fixer (Enrage)" Ability { id: "B2C7", source: "Lindwurm" } + +# Enrage sequence +2027.7 label "r12s-p1-enrage" +2036.7 "Refreshing Overkill (Enrage)?" Ability { id: "B538", source: "Lindwurm" } +2036.8 "--untargetable--" +2036.8 "Refreshing Overkill (Enrage)?" Ability { id: "B53A", source: "Lindwurm" } + +# Kill/Transition sequence +2036.8 "Refreshing Overkill" Ability { id: "B539", source: "Lindwurm" } +2073.0 "--sync--" Ability { id: "BB9C", source: "Lindwurm" } +2073.5 "Down for the Count" duration 42 +2075.7 "--sync--" Ability { id: "B53B", source: "Lindwurm" } +2117.7 "--targetable--" + + +### Phase 2: Lindwurm II +# -p B528:3012.1 +# -ii B51F +# -it "Lindwurm" +3000.5 label "r12s-p2-start" +3007.1 "--sync--" StartsUsing { id: "B528", source: "Lindwurm" } window 3100,10 +3012.1 "Arcadia Aflame" Ability { id: "B528", source: "Lindwurm" } +3019.3 "--middle--" Ability { id: "B4D9", source: "Lindwurm" } +3024.4 "Replication" Ability { id: "B4D8", source: "Lindwurm" } +# TBD + +# IGNORED ABILITIES +# Phase 1 +# B4D3 --sync--: Attack autos +# B495 Mortal Slayer: VFX +# B4B2 Unmitigated Explosion: Missed blob tower +# B4B4 Dramatic Lysis: Damage from breaking a tether; These can be broken at various times +# B4B5 Dramatic Lysis: 6s to break tether, else this applies every 1s, doing damage and giving a damage down +# B4B3 Roiling Mass: Damage from soaking a tether-created tower; The towers can be created at various times +# B4BE Constrictor: VFX Ending of Cruel Coil B4B8 +# B4BD Constrictor: VFX Ending of Cruel Coil B4B9 +# B4B1 Metamitosis: VFX +# B469 Ravenous Reach: VFX +# B769 Ravenous Reach: VFX +# B76A Ravenous Reach: VFX +# B56F --sync--: These happen same time as Bring Down the House BE0A +# B570 --sync--: These happen same time as Bring Down the House BE0A +# BE0A Bring Down the House: VFX +# B4CF Raptor Knuckles: VFX for knockback from NW +# B4D0 Raptor Knuckles: VFX for knockback from NE +# B4AD Cell Death: Failing Cell Shedding by not getting hit by Ravenous Reach + +# Phase 2 +# B51F --sync--: Attack autos + +# ALL ENCOUNTER ABILITIES +# Phase 1 +# ADC9 Slaughtershed +# B2C7 The Fixer: Alternative enrage +# B469 Ravenous Reach: VFX +# B46E --sync-- +# B472 --sync-- Animation coinciding with boss jumping to middle and binding the players +# B479 --sync-- +# B495 Mortal Slayer +# B496 Mortal Slayer: Green (DPS/Healer) Orbs +# B498 Mortal Slayer: Purple (Tank) Orbs +# B49A --sync--: Animation for Wyrm moving West (Cleaving East) +# B49B --sync--: Animation for Wyrm moving East (Cleaving West) +# B49D Ravenous Reach +# B49E Phagocyte Spotlight +# B49F Burst +# B4A0 Grand Entrance: Small circle aoe of wyrm going into ground? Does a knockback and gives damage down +# B4A1 Grand Entrance: Only cast when caradinals are safe; Small circle aoe of wyrm coming out of ground? Does a knockback and gives damage down +# B4A2 Grand Entrance: Only cast when intercardinal are safe +# B4A3 Grand Entrance +# B4A4 Bring Down the House +# B4A5 Bring Down the House +# B4A6 Bring Down the House +# B4A7 Split Scourge +# B4A8 Venomous Scourge +# B4AA Dramatic Lysis: Spread AoE damage +# B4AB Split Scourge +# B4AC Cell Shedding +# B4AD Cell Death +# B4AE Fourth-wall Fusion +# B4AF Hemorrhagic Projection +# B4B0 Dramatic Lysis +# B4B1 Metamitosis +# B4B2 Unmitigated Explosion +# B4B3 Roiling Mass: Chain Tower soaks +# B4B4 Dramatic Lysis +# B4B5 Dramatic Lysis +# B4B6 Phagocyte Spotlight +# B4B7 Roiling Mass: Blob Tower Soaks +# B4B8 Cruel Coil: Boss starting one way? +# B4B9 Cruel Coil: Boss starting the other way? +# B4BA Cruel Coil +# B4BC Skinsplitter +# B4BE Constrictor: VFX Ending of Cruel Coil B4B8 +# B4BD Constrictor: VFX Ending of Cruel Coil B4B9 +# B4BF Constrictor +# B4C1 --sync-- +# B4C2 Constrictor: "soft enrage" damage for Cruel Coil +# B4C3 Slaughtershed +# B4C6 Slaughtershed +# B4CB --sync--: Animation that indicates B4D1 Serpintine Scourge (Left Hand/E) is first +# B4CC --sync--: Animation that indicates B4CF Raptor Knuckles (Right Hand/NW) is first +# B4CD --sync--: Animation that indicates B4D2 Serpintine Scourge (Right hand/W) is first +# B4CE --sync--: Animation that indicates B4D0 Raptor Knuckles (Left Hand/NE) is first +# B4CF Raptor Knuckles +# B4D0 Raptor Knuckles +# B4D1 Serpentine Scourge +# B4D2 Serpentine Scourge +# B4D3 --sync-- +# B4D4 Dramatic Lysis +# B4D5 Fourth-wall Fusion +# B4D6 Visceral Burst +# B4D7 The Fixer +# B538 Refreshing Overkill: Enrage castbar +# B53A Refreshing Overkill: Enrage +# B53E Skinsplitter: Damage from running into snake during Cruel Coil +# B56F --sync-- +# B570 --sync-- +# B571 --sync-- +# B769 Ravenous Reach: VFX +# B76A Ravenous Reach: VFX +# B7C4 --sync-- +# B7C5 --sync-- +# B923 Metamitosis +# B9B9 Fourth-wall Fusion +# B9BC Serpentine Scourge +# B9C3 Splattershed +# B9C4 Splattershed +# B9C6 Splattershed +# B9C7 Raptor Knuckles: Damage +# B9DB --sync-- +# BE09 Feral Fission +# BE0A Bring Down the House +# BEBD Grotesquerie: Act 1 +# BEBE Grotesquerie: Act 2 +# BEBF Grotesquerie: Act 3 +# BEC0 Grotesquerie: Curtain Call + +# Phase 2