libram 0.8.28 → 0.8.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/Clan.d.ts +128 -0
- package/dist/Clan.js +300 -0
- package/dist/Copier.d.ts +9 -0
- package/dist/Copier.js +15 -0
- package/dist/Dungeon.d.ts +45 -0
- package/dist/Dungeon.js +115 -0
- package/dist/Kmail.d.ts +133 -0
- package/dist/Kmail.js +259 -0
- package/dist/actions/ActionSource.d.ts +131 -0
- package/dist/actions/ActionSource.js +178 -0
- package/dist/actions/Banish.d.ts +16 -0
- package/dist/actions/Banish.js +121 -0
- package/dist/actions/FreeKill.d.ts +16 -0
- package/dist/actions/FreeKill.js +94 -0
- package/dist/actions/FreeRun.d.ts +16 -0
- package/dist/actions/FreeRun.js +81 -0
- package/dist/actions/index.d.ts +4 -0
- package/dist/actions/index.js +4 -0
- package/dist/ascend.d.ts +83 -0
- package/dist/ascend.js +268 -0
- package/dist/challengePaths/2014/HeavyRains.d.ts +22 -0
- package/dist/challengePaths/2014/HeavyRains.js +75 -0
- package/dist/challengePaths/2015/CommunityService.d.ts +125 -0
- package/dist/challengePaths/2015/CommunityService.js +334 -0
- package/dist/challengePaths/2016/NuclearAutumn.d.ts +13 -0
- package/dist/challengePaths/2016/NuclearAutumn.js +21 -0
- package/dist/challengePaths/index.d.ts +4 -0
- package/dist/challengePaths/index.js +4 -0
- package/dist/combat.d.ts +414 -0
- package/dist/combat.js +711 -0
- package/dist/console.d.ts +12 -0
- package/dist/console.js +14 -0
- package/dist/counter.d.ts +22 -0
- package/dist/counter.js +37 -0
- package/dist/diet/index.d.ts +80 -0
- package/dist/diet/index.js +682 -0
- package/dist/diet/knapsack.d.ts +8 -0
- package/dist/diet/knapsack.js +128 -0
- package/dist/index.d.ts +29 -0
- package/dist/index.js +26 -0
- package/dist/lib.d.ts +508 -0
- package/dist/lib.js +970 -0
- package/dist/logger.d.ts +35 -0
- package/dist/logger.js +62 -0
- package/dist/maximize.d.ts +122 -0
- package/dist/maximize.js +531 -0
- package/dist/modifier.d.ts +41 -0
- package/dist/modifier.js +160 -0
- package/dist/modifierTypes.d.ts +16 -0
- package/dist/modifierTypes.js +9 -0
- package/dist/mood.d.ts +105 -0
- package/dist/mood.js +349 -0
- package/dist/moonSign.d.ts +13 -0
- package/dist/moonSign.js +25 -0
- package/dist/overlappingNames.d.ts +3 -0
- package/dist/overlappingNames.js +42 -0
- package/dist/property.d.ts +222 -0
- package/dist/property.js +385 -0
- package/dist/propertyTypes.d.ts +19 -0
- package/dist/propertyTypes.js +10 -0
- package/dist/propertyTyping.d.ts +65 -0
- package/dist/propertyTyping.js +91 -0
- package/dist/resources/2007/CandyHearts.d.ts +9 -0
- package/dist/resources/2007/CandyHearts.js +24 -0
- package/dist/resources/2008/DivineFavors.d.ts +9 -0
- package/dist/resources/2008/DivineFavors.js +27 -0
- package/dist/resources/2008/Stickers.d.ts +49 -0
- package/dist/resources/2008/Stickers.js +84 -0
- package/dist/resources/2009/Bandersnatch.d.ts +56 -0
- package/dist/resources/2009/Bandersnatch.js +93 -0
- package/dist/resources/2009/LoveSongs.d.ts +9 -0
- package/dist/resources/2009/LoveSongs.js +24 -0
- package/dist/resources/2009/SpookyPutty.d.ts +31 -0
- package/dist/resources/2009/SpookyPutty.js +49 -0
- package/dist/resources/2010/Brickos.d.ts +9 -0
- package/dist/resources/2010/Brickos.js +21 -0
- package/dist/resources/2010/CrownOfThrones.d.ts +68 -0
- package/dist/resources/2010/CrownOfThrones.js +418 -0
- package/dist/resources/2010/LookingGlass.d.ts +29 -0
- package/dist/resources/2010/LookingGlass.js +89 -0
- package/dist/resources/2011/Gygaxian.d.ts +9 -0
- package/dist/resources/2011/Gygaxian.js +24 -0
- package/dist/resources/2011/ObtuseAngel.d.ts +33 -0
- package/dist/resources/2011/ObtuseAngel.js +51 -0
- package/dist/resources/2011/StompingBoots.d.ts +37 -0
- package/dist/resources/2011/StompingBoots.js +57 -0
- package/dist/resources/2012/RainDoh.d.ts +25 -0
- package/dist/resources/2012/RainDoh.js +37 -0
- package/dist/resources/2012/ReagnimatedGnome.d.ts +31 -0
- package/dist/resources/2012/ReagnimatedGnome.js +46 -0
- package/dist/resources/2012/Resolutions.d.ts +9 -0
- package/dist/resources/2012/Resolutions.js +28 -0
- package/dist/resources/2013/Florist.d.ts +81 -0
- package/dist/resources/2013/Florist.js +245 -0
- package/dist/resources/2013/JungMan.d.ts +33 -0
- package/dist/resources/2013/JungMan.js +69 -0
- package/dist/resources/2013/PulledTaffy.d.ts +9 -0
- package/dist/resources/2013/PulledTaffy.js +33 -0
- package/dist/resources/2014/CrimboShrub.d.ts +42 -0
- package/dist/resources/2014/CrimboShrub.js +89 -0
- package/dist/resources/2014/DNALab.d.ts +56 -0
- package/dist/resources/2014/DNALab.js +162 -0
- package/dist/resources/2014/WinterGarden.d.ts +23 -0
- package/dist/resources/2014/WinterGarden.js +35 -0
- package/dist/resources/2015/BarrelShrine.d.ts +8 -0
- package/dist/resources/2015/BarrelShrine.js +25 -0
- package/dist/resources/2015/ChateauMantegna.d.ts +54 -0
- package/dist/resources/2015/ChateauMantegna.js +100 -0
- package/dist/resources/2015/DeckOfEveryCard.d.ts +29 -0
- package/dist/resources/2015/DeckOfEveryCard.js +122 -0
- package/dist/resources/2015/Dinseylandfill.d.ts +89 -0
- package/dist/resources/2015/Dinseylandfill.js +205 -0
- package/dist/resources/2015/MayoClinic.d.ts +23 -0
- package/dist/resources/2015/MayoClinic.js +49 -0
- package/dist/resources/2016/GingerBread.d.ts +32 -0
- package/dist/resources/2016/GingerBread.js +73 -0
- package/dist/resources/2016/SourceTerminal.d.ts +181 -0
- package/dist/resources/2016/SourceTerminal.js +275 -0
- package/dist/resources/2016/Witchess.d.ts +19 -0
- package/dist/resources/2016/Witchess.js +48 -0
- package/dist/resources/2017/AsdonMartin.d.ts +59 -0
- package/dist/resources/2017/AsdonMartin.js +238 -0
- package/dist/resources/2017/Horsery.d.ts +19 -0
- package/dist/resources/2017/Horsery.js +42 -0
- package/dist/resources/2017/MummingTrunk.d.ts +8 -0
- package/dist/resources/2017/MummingTrunk.js +33 -0
- package/dist/resources/2017/Pantogram.d.ts +92 -0
- package/dist/resources/2017/Pantogram.js +174 -0
- package/dist/resources/2017/Robortender.d.ts +30 -0
- package/dist/resources/2017/Robortender.js +90 -0
- package/dist/resources/2017/Spacegate.d.ts +86 -0
- package/dist/resources/2017/Spacegate.js +178 -0
- package/dist/resources/2017/TunnelOfLove.d.ts +39 -0
- package/dist/resources/2017/TunnelOfLove.js +120 -0
- package/dist/resources/2018/LatteLoversMembersMug.d.ts +392 -0
- package/dist/resources/2018/LatteLoversMembersMug.js +303 -0
- package/dist/resources/2018/SongBoom.d.ts +33 -0
- package/dist/resources/2018/SongBoom.js +55 -0
- package/dist/resources/2019/BeachComb.d.ts +72 -0
- package/dist/resources/2019/BeachComb.js +118 -0
- package/dist/resources/2019/CampAway.d.ts +39 -0
- package/dist/resources/2019/CampAway.js +72 -0
- package/dist/resources/2019/Snapper.d.ts +33 -0
- package/dist/resources/2019/Snapper.js +73 -0
- package/dist/resources/2020/Cartography.d.ts +16 -0
- package/dist/resources/2020/Cartography.js +48 -0
- package/dist/resources/2020/Guzzlr.d.ts +160 -0
- package/dist/resources/2020/Guzzlr.js +275 -0
- package/dist/resources/2020/RetroCape.d.ts +51 -0
- package/dist/resources/2020/RetroCape.js +115 -0
- package/dist/resources/2021/CrystalBall.d.ts +14 -0
- package/dist/resources/2021/CrystalBall.js +41 -0
- package/dist/resources/2021/DaylightShavings.d.ts +40 -0
- package/dist/resources/2021/DaylightShavings.js +74 -0
- package/dist/resources/2022/AutumnAton.d.ts +78 -0
- package/dist/resources/2022/AutumnAton.js +182 -0
- package/dist/resources/2022/CombatLoversLocket.d.ts +46 -0
- package/dist/resources/2022/CombatLoversLocket.js +83 -0
- package/dist/resources/2022/GreyGoose.d.ts +59 -0
- package/dist/resources/2022/GreyGoose.js +90 -0
- package/dist/resources/2022/JuneCleaver.d.ts +47 -0
- package/dist/resources/2022/JuneCleaver.js +69 -0
- package/dist/resources/2022/TrainSet.d.ts +146 -0
- package/dist/resources/2022/TrainSet.js +228 -0
- package/dist/resources/2023/AugustScepter.d.ts +25 -0
- package/dist/resources/2023/AugustScepter.js +40 -0
- package/dist/resources/2023/BurningLeaves.d.ts +25 -0
- package/dist/resources/2023/BurningLeaves.js +74 -0
- package/dist/resources/2023/CinchoDeMayo.d.ts +25 -0
- package/dist/resources/2023/CinchoDeMayo.js +45 -0
- package/dist/resources/2023/ClosedCircuitPayphone.d.ts +80 -0
- package/dist/resources/2023/ClosedCircuitPayphone.js +129 -0
- package/dist/resources/2023/CursedMonkeyPaw.d.ts +46 -0
- package/dist/resources/2023/CursedMonkeyPaw.js +113 -0
- package/dist/resources/2024/AprilingBandHelmet.d.ts +57 -0
- package/dist/resources/2024/AprilingBandHelmet.js +118 -0
- package/dist/resources/2024/ChestMimic.d.ts +43 -0
- package/dist/resources/2024/ChestMimic.js +125 -0
- package/dist/resources/LibramSummon.d.ts +18 -0
- package/dist/resources/LibramSummon.js +74 -0
- package/dist/resources/index.d.ts +54 -0
- package/dist/resources/index.js +54 -0
- package/dist/resources/putty-likes.d.ts +21 -0
- package/dist/resources/putty-likes.js +33 -0
- package/dist/session.d.ts +169 -0
- package/dist/session.js +284 -0
- package/dist/since.d.ts +51 -0
- package/dist/since.js +108 -0
- package/dist/template-string.d.ts +324 -0
- package/dist/template-string.js +265 -0
- package/dist/url.d.ts +35 -0
- package/dist/url.js +67 -0
- package/dist/utils.d.ts +185 -0
- package/dist/utils.js +264 -0
- package/package.json +2 -2
package/dist/combat.js
ADDED
|
@@ -0,0 +1,711 @@
|
|
|
1
|
+
import { adv1, choiceFollowsFight, Class, Effect, getAutoAttack, inMultiFight, Item, Location, Monster, removeProperty, runCombat, setAutoAttack, Skill, Stat, urlEncode, visitUrl, xpath, } from "kolmafia";
|
|
2
|
+
import { getTodaysHolidayWanderers } from "./lib";
|
|
3
|
+
import { overlappingItemNames, overlappingSkillNames, } from "./overlappingNames";
|
|
4
|
+
import { get, set } from "./property";
|
|
5
|
+
const MACRO_NAME = "Script Autoattack Macro";
|
|
6
|
+
/**
|
|
7
|
+
* Get the KoL native ID of the macro with name name.
|
|
8
|
+
*
|
|
9
|
+
* @param name Name of the macro
|
|
10
|
+
* @category Combat
|
|
11
|
+
* @returns {number} The macro ID.
|
|
12
|
+
*/
|
|
13
|
+
export function getMacroId(name = MACRO_NAME) {
|
|
14
|
+
const macroMatches = xpath(visitUrl("account_combatmacros.php"), `//select[@name="macroid"]/option[text()="${name}"]/@value`);
|
|
15
|
+
if (macroMatches.length === 0) {
|
|
16
|
+
visitUrl("account_combatmacros.php?action=new");
|
|
17
|
+
const newMacroText = visitUrl(`account_combatmacros.php?macroid=0&name=${name}¯otext=abort&action=save`);
|
|
18
|
+
return parseInt(xpath(newMacroText, `//input[@name=${name}]/@value`)[0], 10);
|
|
19
|
+
}
|
|
20
|
+
else {
|
|
21
|
+
return parseInt(macroMatches[0], 10);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Converts an item name to a Item, or passes through an existing instance of Item
|
|
26
|
+
*
|
|
27
|
+
* @param itemOrName Item name or Item instance
|
|
28
|
+
* @returns KoLmafia Item instance
|
|
29
|
+
*/
|
|
30
|
+
function itemOrNameToItem(itemOrName) {
|
|
31
|
+
return typeof itemOrName === "string" ? Item.get(itemOrName) : itemOrName;
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Create a string of the item or items provided that is compatible with BALLS syntax and is non-ambiguous
|
|
35
|
+
*
|
|
36
|
+
* @param itemOrItems Item name, item instance, or 2-tuple of item name or item instance
|
|
37
|
+
* @returns BALLS macro-compatible value for item or items provided
|
|
38
|
+
*/
|
|
39
|
+
function itemOrItemsBallsMacroName(itemOrItems) {
|
|
40
|
+
if (Array.isArray(itemOrItems)) {
|
|
41
|
+
return itemOrItems.map(itemOrItemsBallsMacroName).join(", ");
|
|
42
|
+
}
|
|
43
|
+
else {
|
|
44
|
+
const item = itemOrNameToItem(itemOrItems);
|
|
45
|
+
return !overlappingItemNames.includes(item.name)
|
|
46
|
+
? item.name
|
|
47
|
+
: item.id.toFixed(0);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Generate a BALLS macro condition to check wither the player has either a single or a 2-tuple of combat items
|
|
52
|
+
*
|
|
53
|
+
* @param itemOrItems Single or 2-tuple of combat items
|
|
54
|
+
* @returns BALLS macro condition
|
|
55
|
+
*/
|
|
56
|
+
function itemOrItemsBallsMacroPredicate(itemOrItems) {
|
|
57
|
+
if (Array.isArray(itemOrItems)) {
|
|
58
|
+
return itemOrItems.map(itemOrItemsBallsMacroPredicate).join(" && ");
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
return `hascombatitem ${itemOrItems}`;
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Converts a skill name to a Skill, or passes through an existing instance of Skill
|
|
66
|
+
*
|
|
67
|
+
* @param skillOrName Skill name or Skill instance
|
|
68
|
+
* @returns KoLmafia Skill instance
|
|
69
|
+
*/
|
|
70
|
+
function skillOrNameToSkill(skillOrName) {
|
|
71
|
+
if (typeof skillOrName === "string") {
|
|
72
|
+
return Skill.get(skillOrName);
|
|
73
|
+
}
|
|
74
|
+
else {
|
|
75
|
+
return skillOrName;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Get a skill name in a form that is appropriate for BALLS macros
|
|
80
|
+
*
|
|
81
|
+
* @param skillOrName Skill name or Skill instance
|
|
82
|
+
* @returns BALLS macro-suitable skill name
|
|
83
|
+
*/
|
|
84
|
+
function skillBallsMacroName(skillOrName) {
|
|
85
|
+
const skill = skillOrNameToSkill(skillOrName);
|
|
86
|
+
return skill.name.match(/^[A-Za-z ]+$/) &&
|
|
87
|
+
!overlappingSkillNames.includes(skill.name)
|
|
88
|
+
? skill.name
|
|
89
|
+
: skill.id;
|
|
90
|
+
}
|
|
91
|
+
export class InvalidMacroError extends Error {
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* BALLS macro builder for direct submission to KoL.
|
|
95
|
+
* Create a new macro with `new Macro()` and add steps using the instance methods.
|
|
96
|
+
* Uses a fluent interface, so each step returns the object for easy chaining of steps.
|
|
97
|
+
* Each method is also defined as a static method that creates a new Macro with only that step.
|
|
98
|
+
* For example, you can do `Macro.skill('Saucestorm').attack()`.
|
|
99
|
+
*/
|
|
100
|
+
export class Macro {
|
|
101
|
+
static SAVED_MACRO_PROPERTY = "libram_savedMacro";
|
|
102
|
+
static cachedMacroIds = new Map();
|
|
103
|
+
static cachedAutoAttacks = new Map();
|
|
104
|
+
components = [];
|
|
105
|
+
name = MACRO_NAME;
|
|
106
|
+
/**
|
|
107
|
+
* Convert macro to string.
|
|
108
|
+
*
|
|
109
|
+
* @returns BALLS macro
|
|
110
|
+
*/
|
|
111
|
+
toString() {
|
|
112
|
+
return (this.components.join(";") + ";").replace(/;;+/g, ";");
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* Gives your macro a new name to be used when saving an autoattack.
|
|
116
|
+
*
|
|
117
|
+
* @param name The name to be used when saving as an autoattack.
|
|
118
|
+
* @returns The macro in question
|
|
119
|
+
*/
|
|
120
|
+
rename(name) {
|
|
121
|
+
this.name = name;
|
|
122
|
+
return this;
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Creates a new Macro with a name other than the default name.
|
|
126
|
+
*
|
|
127
|
+
* @param name The name to assign this macro.
|
|
128
|
+
* @returns A new Macro with the assigned name.
|
|
129
|
+
*/
|
|
130
|
+
static rename(name) {
|
|
131
|
+
return new this().rename(name);
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* Save a macro to a Mafia property for use in a consult script.
|
|
135
|
+
*/
|
|
136
|
+
save() {
|
|
137
|
+
set(Macro.SAVED_MACRO_PROPERTY, this.toString());
|
|
138
|
+
}
|
|
139
|
+
/**
|
|
140
|
+
* Load a saved macro from the Mafia property.
|
|
141
|
+
*
|
|
142
|
+
* @returns Loaded macro text
|
|
143
|
+
*/
|
|
144
|
+
static load() {
|
|
145
|
+
return new this().step(...get(Macro.SAVED_MACRO_PROPERTY).split(";"));
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* Clear the saved macro in the Mafia property.
|
|
149
|
+
*/
|
|
150
|
+
static clearSaved() {
|
|
151
|
+
removeProperty(Macro.SAVED_MACRO_PROPERTY);
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Statefully add one or several steps to a macro.
|
|
155
|
+
*
|
|
156
|
+
* @param nextSteps The steps to add to the macro.
|
|
157
|
+
* @returns {Macro} This object itself.
|
|
158
|
+
*/
|
|
159
|
+
step(...nextSteps) {
|
|
160
|
+
const nextStepsStrings = [].concat(...nextSteps.map((x) => (x instanceof Macro ? x.components : [x])));
|
|
161
|
+
this.components.push(...nextStepsStrings.filter(Boolean));
|
|
162
|
+
return this;
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* Statefully add one or several steps to a macro.
|
|
166
|
+
*
|
|
167
|
+
* @param nextSteps The steps to add to the macro.
|
|
168
|
+
* @returns {Macro} This object itself.
|
|
169
|
+
*/
|
|
170
|
+
static step(...nextSteps) {
|
|
171
|
+
return new this().step(...nextSteps);
|
|
172
|
+
}
|
|
173
|
+
/**
|
|
174
|
+
* Submit the built macro to KoL. Only works inside combat.
|
|
175
|
+
*
|
|
176
|
+
* @returns Contents of the fight page after macro submission
|
|
177
|
+
*/
|
|
178
|
+
submit() {
|
|
179
|
+
const final = this.toString();
|
|
180
|
+
return visitUrl(`fight.php?action=macro¯otext=${urlEncode(final)}`, true, true);
|
|
181
|
+
}
|
|
182
|
+
/**
|
|
183
|
+
* Set this macro as a KoL native autoattack.
|
|
184
|
+
*/
|
|
185
|
+
setAutoAttack() {
|
|
186
|
+
let id = Macro.cachedMacroIds.get(this.name);
|
|
187
|
+
if (id === undefined) {
|
|
188
|
+
id = getMacroId(this.name);
|
|
189
|
+
Macro.cachedMacroIds.set(this.name, id);
|
|
190
|
+
}
|
|
191
|
+
if (getAutoAttack() === 99000000 + id &&
|
|
192
|
+
this.toString() === Macro.cachedAutoAttacks.get(this.name)) {
|
|
193
|
+
// This macro is already set. Don"t make the server request.
|
|
194
|
+
return;
|
|
195
|
+
}
|
|
196
|
+
visitUrl(`account_combatmacros.php?macroid=${id}&name=${urlEncode(this.name)}¯otext=${urlEncode(this.toString())}&action=save`, true, true);
|
|
197
|
+
visitUrl(`account.php?am=1&action=autoattack&value=${99000000 + id}&ajax=1`);
|
|
198
|
+
Macro.cachedAutoAttacks.set(this.name, this.toString());
|
|
199
|
+
}
|
|
200
|
+
/**
|
|
201
|
+
* Renames the macro, then sets it as an autoattack.
|
|
202
|
+
*
|
|
203
|
+
* @param name The name to save the macro under as an autoattack.
|
|
204
|
+
*/
|
|
205
|
+
setAutoAttackAs(name) {
|
|
206
|
+
this.name = name;
|
|
207
|
+
this.setAutoAttack();
|
|
208
|
+
}
|
|
209
|
+
/**
|
|
210
|
+
* Clear all cached autoattacks, and delete all stored macros server-side.
|
|
211
|
+
*/
|
|
212
|
+
static clearAutoAttackMacros() {
|
|
213
|
+
for (const name of Macro.cachedAutoAttacks.keys()) {
|
|
214
|
+
const id = Macro.cachedMacroIds.get(name) ?? getMacroId(name);
|
|
215
|
+
visitUrl(`account_combatmacros.php?macroid=${id}&action=edit&what=Delete&confirm=1`);
|
|
216
|
+
Macro.cachedAutoAttacks.delete(name);
|
|
217
|
+
Macro.cachedMacroIds.delete(name);
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
/**
|
|
221
|
+
* Add an "abort" step to this macro.
|
|
222
|
+
*
|
|
223
|
+
* @returns {Macro} This object itself.
|
|
224
|
+
*/
|
|
225
|
+
abort() {
|
|
226
|
+
return this.step("abort");
|
|
227
|
+
}
|
|
228
|
+
/**
|
|
229
|
+
* Create a new macro with an "abort" step.
|
|
230
|
+
*
|
|
231
|
+
* @returns {Macro} This object itself.
|
|
232
|
+
*/
|
|
233
|
+
static abort() {
|
|
234
|
+
return new this().abort();
|
|
235
|
+
}
|
|
236
|
+
/**
|
|
237
|
+
* Adds an "abort" step to this macro, with a warning message to print
|
|
238
|
+
*
|
|
239
|
+
* @param warning The warning message to print
|
|
240
|
+
* @returns {Macro} This object itself.
|
|
241
|
+
*/
|
|
242
|
+
abortWithWarning(warning) {
|
|
243
|
+
return this.step(`abort "${warning}"`);
|
|
244
|
+
}
|
|
245
|
+
/**
|
|
246
|
+
* Create a new macro with an "abort" step to this macro, with a warning message to print
|
|
247
|
+
*
|
|
248
|
+
* @param warning The warning message to print
|
|
249
|
+
* @returns {Macro} This object itself.
|
|
250
|
+
*/
|
|
251
|
+
static abortWithWarning(warning) {
|
|
252
|
+
return new this().abortWithWarning(warning);
|
|
253
|
+
}
|
|
254
|
+
/**
|
|
255
|
+
* Add a "runaway" step to this macro.
|
|
256
|
+
*
|
|
257
|
+
* @returns {Macro} This object itself.
|
|
258
|
+
*/
|
|
259
|
+
runaway() {
|
|
260
|
+
return this.step("runaway");
|
|
261
|
+
}
|
|
262
|
+
/**
|
|
263
|
+
* Create a new macro with an "runaway" step.
|
|
264
|
+
*
|
|
265
|
+
* @returns {Macro} This object itself.
|
|
266
|
+
*/
|
|
267
|
+
static runaway() {
|
|
268
|
+
return new this().runaway();
|
|
269
|
+
}
|
|
270
|
+
static makeBALLSPredicate(condition) {
|
|
271
|
+
let ballsCondition = "";
|
|
272
|
+
if (condition instanceof Monster) {
|
|
273
|
+
ballsCondition = `monsterid ${condition.id}`;
|
|
274
|
+
}
|
|
275
|
+
else if (condition instanceof Array) {
|
|
276
|
+
ballsCondition = condition
|
|
277
|
+
.map((mon) => `monsterid ${mon.id}`)
|
|
278
|
+
.join(" || ");
|
|
279
|
+
ballsCondition = `(${ballsCondition})`;
|
|
280
|
+
}
|
|
281
|
+
else if (condition instanceof Effect) {
|
|
282
|
+
ballsCondition = `haseffect ${condition.id}`;
|
|
283
|
+
}
|
|
284
|
+
else if (condition instanceof Skill) {
|
|
285
|
+
ballsCondition = `hasskill ${skillBallsMacroName(condition)}`;
|
|
286
|
+
}
|
|
287
|
+
else if (condition instanceof Item) {
|
|
288
|
+
if (!condition.combat) {
|
|
289
|
+
throw new InvalidMacroError(`Item ${condition} cannot be made a valid BALLS predicate (it is not combat-usable)`);
|
|
290
|
+
}
|
|
291
|
+
ballsCondition = `hascombatitem ${itemOrItemsBallsMacroName(condition)}`;
|
|
292
|
+
}
|
|
293
|
+
else if (condition instanceof Location) {
|
|
294
|
+
const snarfblat = condition.id;
|
|
295
|
+
if (snarfblat < 1) {
|
|
296
|
+
throw new InvalidMacroError(`Location ${condition} cannot be made a valid BALLS predicate (it has no location id)`);
|
|
297
|
+
}
|
|
298
|
+
ballsCondition = `snarfblat ${snarfblat}`;
|
|
299
|
+
}
|
|
300
|
+
else if (condition instanceof Class) {
|
|
301
|
+
if (condition.id > 6) {
|
|
302
|
+
throw new InvalidMacroError(`Class ${condition} cannot be made a valid BALLS predicate (it is not a standard class)`);
|
|
303
|
+
}
|
|
304
|
+
ballsCondition = condition.toString().replaceAll(" ", "").toLowerCase();
|
|
305
|
+
}
|
|
306
|
+
else if (condition instanceof Stat) {
|
|
307
|
+
ballsCondition = `${condition.toString().toLowerCase()}class`;
|
|
308
|
+
}
|
|
309
|
+
else {
|
|
310
|
+
ballsCondition = condition;
|
|
311
|
+
}
|
|
312
|
+
return ballsCondition;
|
|
313
|
+
}
|
|
314
|
+
/**
|
|
315
|
+
* Add an "if" statement to this macro.
|
|
316
|
+
*
|
|
317
|
+
* @param condition The BALLS condition for the if statement.
|
|
318
|
+
* @param ifTrue Continuation if the condition is true.
|
|
319
|
+
* @returns {Macro} This object itself.
|
|
320
|
+
*/
|
|
321
|
+
if_(condition, ifTrue) {
|
|
322
|
+
return this.step(`if ${Macro.makeBALLSPredicate(condition)}`)
|
|
323
|
+
.step(ifTrue)
|
|
324
|
+
.step("endif");
|
|
325
|
+
}
|
|
326
|
+
/**
|
|
327
|
+
* Create a new macro with an "if" statement.
|
|
328
|
+
*
|
|
329
|
+
* @param condition The BALLS condition for the if statement.
|
|
330
|
+
* @param ifTrue Continuation if the condition is true.
|
|
331
|
+
* @returns {Macro} This object itself.
|
|
332
|
+
*/
|
|
333
|
+
static if_(condition, ifTrue) {
|
|
334
|
+
return new this().if_(condition, ifTrue);
|
|
335
|
+
}
|
|
336
|
+
/**
|
|
337
|
+
* Add an "if" statement to this macro, inverting the condition.
|
|
338
|
+
*
|
|
339
|
+
* @param condition The BALLS condition for the if statement.
|
|
340
|
+
* @param ifTrue Continuation if the condition is true.
|
|
341
|
+
* @returns {Macro} This object itself.
|
|
342
|
+
*/
|
|
343
|
+
ifNot(condition, ifTrue) {
|
|
344
|
+
return this.step(`if !(${Macro.makeBALLSPredicate(condition)})`)
|
|
345
|
+
.step(ifTrue)
|
|
346
|
+
.step("endif");
|
|
347
|
+
}
|
|
348
|
+
/**
|
|
349
|
+
* Create a new macro with an "if" statement, inverting the condition.
|
|
350
|
+
*
|
|
351
|
+
* @param condition The BALLS condition for the if statement.
|
|
352
|
+
* @param ifTrue Continuation if the condition is true.
|
|
353
|
+
* @returns {Macro} This object itself.
|
|
354
|
+
*/
|
|
355
|
+
static ifNot(condition, ifTrue) {
|
|
356
|
+
return new this().ifNot(condition, ifTrue);
|
|
357
|
+
}
|
|
358
|
+
/**
|
|
359
|
+
* Add a "while" statement to this macro.
|
|
360
|
+
*
|
|
361
|
+
* @param condition The BALLS condition for the if statement.
|
|
362
|
+
* @param contents Loop to repeat while the condition is true.
|
|
363
|
+
* @returns {Macro} This object itself.
|
|
364
|
+
*/
|
|
365
|
+
while_(condition, contents) {
|
|
366
|
+
return this.step(`while ${condition}`).step(contents).step("endwhile");
|
|
367
|
+
}
|
|
368
|
+
/**
|
|
369
|
+
* Create a new macro with a "while" statement.
|
|
370
|
+
*
|
|
371
|
+
* @param condition The BALLS condition for the if statement.
|
|
372
|
+
* @param contents Loop to repeat while the condition is true.
|
|
373
|
+
* @returns {Macro} This object itself.
|
|
374
|
+
*/
|
|
375
|
+
static while_(condition, contents) {
|
|
376
|
+
return new this().while_(condition, contents);
|
|
377
|
+
}
|
|
378
|
+
/**
|
|
379
|
+
* Conditionally add a step to a macro based on a condition evaluated at the time of building the macro.
|
|
380
|
+
*
|
|
381
|
+
* @param condition The JS condition.
|
|
382
|
+
* @param ifTrue Continuation to add if the condition is true.
|
|
383
|
+
* @param ifFalse Optional input to turn this into an if...else statement.
|
|
384
|
+
* @returns {Macro} This object itself.
|
|
385
|
+
*/
|
|
386
|
+
externalIf(condition, ifTrue, ifFalse) {
|
|
387
|
+
if (condition)
|
|
388
|
+
return this.step(ifTrue);
|
|
389
|
+
else if (ifFalse)
|
|
390
|
+
return this.step(ifFalse);
|
|
391
|
+
else
|
|
392
|
+
return this;
|
|
393
|
+
}
|
|
394
|
+
/**
|
|
395
|
+
* Create a new macro with a condition evaluated at the time of building the macro.
|
|
396
|
+
*
|
|
397
|
+
* @param condition The JS condition.
|
|
398
|
+
* @param ifTrue Continuation to add if the condition is true.
|
|
399
|
+
* @param ifFalse Optional input to turn this into an if...else statement.
|
|
400
|
+
* @returns {Macro} This object itself.
|
|
401
|
+
*/
|
|
402
|
+
static externalIf(condition, ifTrue, ifFalse) {
|
|
403
|
+
return new this().externalIf(condition, ifTrue, ifFalse);
|
|
404
|
+
}
|
|
405
|
+
/**
|
|
406
|
+
* Add a repeat step to the macro.
|
|
407
|
+
*
|
|
408
|
+
* @returns {Macro} This object itself.
|
|
409
|
+
*/
|
|
410
|
+
repeat() {
|
|
411
|
+
return this.step("repeat");
|
|
412
|
+
}
|
|
413
|
+
/**
|
|
414
|
+
* Add one or more skill cast steps to the macro.
|
|
415
|
+
*
|
|
416
|
+
* @param skills Skills to cast.
|
|
417
|
+
* @returns {Macro} This object itself.
|
|
418
|
+
*/
|
|
419
|
+
skill(...skills) {
|
|
420
|
+
return this.step(...skills.map((skill) => {
|
|
421
|
+
return `skill ${skillBallsMacroName(skill)}`;
|
|
422
|
+
}));
|
|
423
|
+
}
|
|
424
|
+
/**
|
|
425
|
+
* Create a new macro with one or more skill cast steps.
|
|
426
|
+
*
|
|
427
|
+
* @param skills Skills to cast.
|
|
428
|
+
* @returns {Macro} This object itself.
|
|
429
|
+
*/
|
|
430
|
+
static skill(...skills) {
|
|
431
|
+
return new this().skill(...skills);
|
|
432
|
+
}
|
|
433
|
+
/**
|
|
434
|
+
* Add one or more skill cast steps to the macro, where each step checks if you have the skill first.
|
|
435
|
+
*
|
|
436
|
+
* @param skills Skills to try casting.
|
|
437
|
+
* @returns {Macro} This object itself.
|
|
438
|
+
*/
|
|
439
|
+
trySkill(...skills) {
|
|
440
|
+
return this.step(...skills.map((skill) => {
|
|
441
|
+
return Macro.if_(`hasskill ${skillBallsMacroName(skill)}`, Macro.skill(skill));
|
|
442
|
+
}));
|
|
443
|
+
}
|
|
444
|
+
/**
|
|
445
|
+
* Create a new macro with one or more skill cast steps, where each step checks if you have the skill first.
|
|
446
|
+
*
|
|
447
|
+
* @param skills Skills to try casting.
|
|
448
|
+
* @returns {Macro} This object itself.
|
|
449
|
+
*/
|
|
450
|
+
static trySkill(...skills) {
|
|
451
|
+
return new this().trySkill(...skills);
|
|
452
|
+
}
|
|
453
|
+
/**
|
|
454
|
+
* Add one or more skill-cast-and-repeat steps to the macro, where each step checks if you have the skill first.
|
|
455
|
+
*
|
|
456
|
+
* @param skills Skills to try repeatedly casting.
|
|
457
|
+
* @returns {Macro} This object itself.
|
|
458
|
+
*/
|
|
459
|
+
trySkillRepeat(...skills) {
|
|
460
|
+
return this.step(...skills.map((skill) => {
|
|
461
|
+
return Macro.if_(`hasskill ${skillBallsMacroName(skill)}`, Macro.skill(skill).repeat());
|
|
462
|
+
}));
|
|
463
|
+
}
|
|
464
|
+
/**
|
|
465
|
+
* Create a new macro with one or more skill-cast-and-repeat steps, where each step checks if you have the skill first.
|
|
466
|
+
*
|
|
467
|
+
* @param skills Skills to try repeatedly casting.
|
|
468
|
+
* @returns {Macro} This object itself.
|
|
469
|
+
*/
|
|
470
|
+
static trySkillRepeat(...skills) {
|
|
471
|
+
return new this().trySkillRepeat(...skills);
|
|
472
|
+
}
|
|
473
|
+
/**
|
|
474
|
+
* Add one or more item steps to the macro.
|
|
475
|
+
*
|
|
476
|
+
* @param items Items to use. Pass a tuple [item1, item2] to funksling.
|
|
477
|
+
* @returns {Macro} This object itself.
|
|
478
|
+
*/
|
|
479
|
+
item(...items) {
|
|
480
|
+
return this.step(...items.map((itemOrItems) => {
|
|
481
|
+
return `use ${itemOrItemsBallsMacroName(itemOrItems)}`;
|
|
482
|
+
}));
|
|
483
|
+
}
|
|
484
|
+
/**
|
|
485
|
+
* Create a new macro with one or more item steps.
|
|
486
|
+
*
|
|
487
|
+
* @param items Items to use. Pass a tuple [item1, item2] to funksling.
|
|
488
|
+
* @returns {Macro} This object itself.
|
|
489
|
+
*/
|
|
490
|
+
static item(...items) {
|
|
491
|
+
return new this().item(...items);
|
|
492
|
+
}
|
|
493
|
+
/**
|
|
494
|
+
* Add one or more item steps to the macro, where each step checks to see if you have the item first.
|
|
495
|
+
*
|
|
496
|
+
* @param items Items to try using. Pass a tuple [item1, item2] to funksling.
|
|
497
|
+
* @returns {Macro} This object itself.
|
|
498
|
+
*/
|
|
499
|
+
tryItem(...items) {
|
|
500
|
+
return this.step(...items.map((item) => {
|
|
501
|
+
return Macro.if_(itemOrItemsBallsMacroPredicate(item), `use ${itemOrItemsBallsMacroName(item)}`);
|
|
502
|
+
}));
|
|
503
|
+
}
|
|
504
|
+
/**
|
|
505
|
+
* Create a new macro with one or more item steps, where each step checks to see if you have the item first.
|
|
506
|
+
*
|
|
507
|
+
* @param items Items to try using. Pass a tuple [item1, item2] to funksling.
|
|
508
|
+
* @returns {Macro} This object itself.
|
|
509
|
+
*/
|
|
510
|
+
static tryItem(...items) {
|
|
511
|
+
return new this().tryItem(...items);
|
|
512
|
+
}
|
|
513
|
+
/**
|
|
514
|
+
* Add an attack step to the macro.
|
|
515
|
+
*
|
|
516
|
+
* @returns {Macro} This object itself.
|
|
517
|
+
*/
|
|
518
|
+
attack() {
|
|
519
|
+
return this.step("attack");
|
|
520
|
+
}
|
|
521
|
+
/**
|
|
522
|
+
* Create a new macro with an attack step.
|
|
523
|
+
*
|
|
524
|
+
* @returns {Macro} This object itself.
|
|
525
|
+
*/
|
|
526
|
+
static attack() {
|
|
527
|
+
return new this().attack();
|
|
528
|
+
}
|
|
529
|
+
/**
|
|
530
|
+
* Create an if_ statement based on what holiday of loathing it currently is. On non-holidays, returns the original macro, unmutated.
|
|
531
|
+
*
|
|
532
|
+
* @param macro The macro to place in the if_ statement
|
|
533
|
+
* @returns This macro with supplied macro wapped in if statement matching holiday wanderers
|
|
534
|
+
*/
|
|
535
|
+
ifHolidayWanderer(macro) {
|
|
536
|
+
const todaysWanderers = getTodaysHolidayWanderers();
|
|
537
|
+
if (todaysWanderers.length === 0)
|
|
538
|
+
return this;
|
|
539
|
+
return this.if_(todaysWanderers.map((monster) => `monsterid ${monster.id}`).join(" || "), macro);
|
|
540
|
+
}
|
|
541
|
+
/**
|
|
542
|
+
* Create a new macro starting with an ifHolidayWanderer step.
|
|
543
|
+
*
|
|
544
|
+
* @param macro The macro to place inside the if_ statement
|
|
545
|
+
* @returns New macro with supplied macro wrapped in if statement matching holiday wanderers
|
|
546
|
+
*/
|
|
547
|
+
static ifHolidayWanderer(macro) {
|
|
548
|
+
return new this().ifHolidayWanderer(macro);
|
|
549
|
+
}
|
|
550
|
+
/**
|
|
551
|
+
* Create an if_ statement based on what holiday of loathing it currently is. On non-holidays, returns the original macro, with the input macro appended.
|
|
552
|
+
*
|
|
553
|
+
* @param macro The macro to place in the if_ statement.
|
|
554
|
+
* @returns This macro with supplied macro wrapped in if statement matching monsters that are not holiday wanderers
|
|
555
|
+
*/
|
|
556
|
+
ifNotHolidayWanderer(macro) {
|
|
557
|
+
const todaysWanderers = getTodaysHolidayWanderers();
|
|
558
|
+
if (todaysWanderers.length === 0)
|
|
559
|
+
return this.step(macro);
|
|
560
|
+
return this.if_(todaysWanderers.map((monster) => `!monsterid ${monster.id}`).join(" && "), macro);
|
|
561
|
+
}
|
|
562
|
+
/**
|
|
563
|
+
* Create a new macro starting with an ifNotHolidayWanderer step.
|
|
564
|
+
*
|
|
565
|
+
* @param macro The macro to place inside the if_ statement
|
|
566
|
+
* @returns New macro with supplied macro wrapped in if statement matching monsters that are not holiday wanderers
|
|
567
|
+
*/
|
|
568
|
+
static ifNotHolidayWanderer(macro) {
|
|
569
|
+
return new this().ifNotHolidayWanderer(macro);
|
|
570
|
+
}
|
|
571
|
+
}
|
|
572
|
+
/**
|
|
573
|
+
* Adventure in a location and handle all combats with a given macro.
|
|
574
|
+
* To use this function you will need to create a consult script that runs Macro.load().submit() and a CCS that calls that consult script.
|
|
575
|
+
* See examples/consult.ts for an example.
|
|
576
|
+
*
|
|
577
|
+
* @category Combat
|
|
578
|
+
* @param loc Location to adventure in.
|
|
579
|
+
* @param macro Macro to execute.
|
|
580
|
+
*/
|
|
581
|
+
export function adventureMacro(loc, macro) {
|
|
582
|
+
macro.save();
|
|
583
|
+
setAutoAttack(0);
|
|
584
|
+
try {
|
|
585
|
+
adv1(loc, 0, "");
|
|
586
|
+
while (inMultiFight())
|
|
587
|
+
runCombat();
|
|
588
|
+
if (choiceFollowsFight())
|
|
589
|
+
visitUrl("choice.php");
|
|
590
|
+
}
|
|
591
|
+
finally {
|
|
592
|
+
Macro.clearSaved();
|
|
593
|
+
}
|
|
594
|
+
}
|
|
595
|
+
/**
|
|
596
|
+
* Adventure in a location and handle all combats with a given autoattack and manual macro.
|
|
597
|
+
* To use the nextMacro parameter you will need to create a consult script that runs Macro.load().submit() and a CCS that calls that consult script.
|
|
598
|
+
* See examples/consult.ts for an example.
|
|
599
|
+
*
|
|
600
|
+
* @category Combat
|
|
601
|
+
* @param loc Location to adventure in.
|
|
602
|
+
* @param autoMacro Macro to execute via KoL autoattack.
|
|
603
|
+
* @param nextMacro Macro to execute manually after autoattack completes.
|
|
604
|
+
*/
|
|
605
|
+
export function adventureMacroAuto(loc, autoMacro, nextMacro = null) {
|
|
606
|
+
nextMacro = nextMacro ?? Macro.abort();
|
|
607
|
+
autoMacro.setAutoAttack();
|
|
608
|
+
nextMacro.save();
|
|
609
|
+
try {
|
|
610
|
+
adv1(loc, 0, "");
|
|
611
|
+
while (inMultiFight())
|
|
612
|
+
runCombat();
|
|
613
|
+
if (choiceFollowsFight())
|
|
614
|
+
visitUrl("choice.php");
|
|
615
|
+
}
|
|
616
|
+
finally {
|
|
617
|
+
Macro.clearSaved();
|
|
618
|
+
}
|
|
619
|
+
}
|
|
620
|
+
export class StrictMacro extends Macro {
|
|
621
|
+
/**
|
|
622
|
+
* Add one or more skill cast steps to the macro.
|
|
623
|
+
*
|
|
624
|
+
* @param skills Skills to cast.
|
|
625
|
+
* @returns {StrictMacro} This object itself.
|
|
626
|
+
*/
|
|
627
|
+
skill(...skills) {
|
|
628
|
+
return super.skill(...skills);
|
|
629
|
+
}
|
|
630
|
+
/**
|
|
631
|
+
* Create a new macro with one or more skill cast steps.
|
|
632
|
+
*
|
|
633
|
+
* @param skills Skills to cast.
|
|
634
|
+
* @returns {StrictMacro} This object itself.
|
|
635
|
+
*/
|
|
636
|
+
static skill(...skills) {
|
|
637
|
+
return new this().skill(...skills);
|
|
638
|
+
}
|
|
639
|
+
/**
|
|
640
|
+
* Add one or more item steps to the macro.
|
|
641
|
+
*
|
|
642
|
+
* @param items Items to use. Pass a tuple [item1, item2] to funksling.
|
|
643
|
+
* @returns {StrictMacro} This object itself.
|
|
644
|
+
*/
|
|
645
|
+
item(...items) {
|
|
646
|
+
return super.item(...items);
|
|
647
|
+
}
|
|
648
|
+
/**
|
|
649
|
+
* Create a new macro with one or more item steps.
|
|
650
|
+
*
|
|
651
|
+
* @param items Items to use. Pass a tuple [item1, item2] to funksling.
|
|
652
|
+
* @returns {StrictMacro} This object itself.
|
|
653
|
+
*/
|
|
654
|
+
static item(...items) {
|
|
655
|
+
return new this().item(...items);
|
|
656
|
+
}
|
|
657
|
+
/**
|
|
658
|
+
* Add one or more skill cast steps to the macro, where each step checks if you have the skill first.
|
|
659
|
+
*
|
|
660
|
+
* @param skills Skills to try casting.
|
|
661
|
+
* @returns {StrictMacro} This object itself.
|
|
662
|
+
*/
|
|
663
|
+
trySkill(...skills) {
|
|
664
|
+
return super.trySkill(...skills);
|
|
665
|
+
}
|
|
666
|
+
/**
|
|
667
|
+
* Create a new macro with one or more skill cast steps, where each step checks if you have the skill first.
|
|
668
|
+
*
|
|
669
|
+
* @param skills Skills to try casting.
|
|
670
|
+
* @returns {StrictMacro} This object itself.
|
|
671
|
+
*/
|
|
672
|
+
static trySkill(...skills) {
|
|
673
|
+
return new this().trySkill(...skills);
|
|
674
|
+
}
|
|
675
|
+
/**
|
|
676
|
+
* Add one or more item steps to the macro, where each step checks to see if you have the item first.
|
|
677
|
+
*
|
|
678
|
+
* @param items Items to try using. Pass a tuple [item1, item2] to funksling.
|
|
679
|
+
* @returns {StrictMacro} This object itself.
|
|
680
|
+
*/
|
|
681
|
+
tryItem(...items) {
|
|
682
|
+
return super.tryItem(...items);
|
|
683
|
+
}
|
|
684
|
+
/**
|
|
685
|
+
* Create a new macro with one or more item steps, where each step checks to see if you have the item first.
|
|
686
|
+
*
|
|
687
|
+
* @param items Items to try using. Pass a tuple [item1, item2] to funksling.
|
|
688
|
+
* @returns {StrictMacro} This object itself.
|
|
689
|
+
*/
|
|
690
|
+
static tryItem(...items) {
|
|
691
|
+
return new this().tryItem(...items);
|
|
692
|
+
}
|
|
693
|
+
/**
|
|
694
|
+
* Add one or more skill-cast-and-repeat steps to the macro, where each step checks if you have the skill first.
|
|
695
|
+
*
|
|
696
|
+
* @param skills Skills to try repeatedly casting.
|
|
697
|
+
* @returns {StrictMacro} This object itself.
|
|
698
|
+
*/
|
|
699
|
+
trySkillRepeat(...skills) {
|
|
700
|
+
return super.trySkillRepeat(...skills);
|
|
701
|
+
}
|
|
702
|
+
/**
|
|
703
|
+
* Create a new macro with one or more skill-cast-and-repeat steps, where each step checks if you have the skill first.
|
|
704
|
+
*
|
|
705
|
+
* @param skills Skills to try repeatedly casting.
|
|
706
|
+
* @returns {StrictMacro} This object itself.
|
|
707
|
+
*/
|
|
708
|
+
static trySkillRepeat(...skills) {
|
|
709
|
+
return new this().trySkillRepeat(...skills);
|
|
710
|
+
}
|
|
711
|
+
}
|