warcraft-3-w3ts-utils 0.1.13 → 0.1.15

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.
Files changed (53) hide show
  1. package/dist/index.lua +0 -2
  2. package/dist/index.lua.map +1 -0
  3. package/dist/package.json +3 -4
  4. package/dist/utils/abilities.lua +0 -2
  5. package/dist/utils/abilities.lua.map +1 -0
  6. package/dist/utils/camera.lua +0 -2
  7. package/dist/utils/camera.lua.map +1 -0
  8. package/dist/utils/chat-command.lua +0 -2
  9. package/dist/utils/chat-command.lua.map +1 -0
  10. package/dist/utils/color.lua +0 -2
  11. package/dist/utils/color.lua.map +1 -0
  12. package/dist/utils/index.lua +0 -2
  13. package/dist/utils/index.lua.map +1 -0
  14. package/dist/utils/item.lua +0 -2
  15. package/dist/utils/item.lua.map +1 -0
  16. package/dist/utils/math.lua +0 -2
  17. package/dist/utils/math.lua.map +1 -0
  18. package/dist/utils/minimapIcons.lua +0 -2
  19. package/dist/utils/minimapIcons.lua.map +1 -0
  20. package/dist/utils/misc.lua +0 -2
  21. package/dist/utils/misc.lua.map +1 -0
  22. package/dist/utils/physics.lua +0 -2
  23. package/dist/utils/physics.lua.map +1 -0
  24. package/dist/utils/players.lua +0 -2
  25. package/dist/utils/players.lua.map +1 -0
  26. package/dist/utils/point.lua +0 -2
  27. package/dist/utils/point.lua.map +1 -0
  28. package/dist/utils/quests.lua +0 -2
  29. package/dist/utils/quests.lua.map +1 -0
  30. package/dist/utils/textTag.lua +0 -2
  31. package/dist/utils/textTag.lua.map +1 -0
  32. package/dist/utils/timer.lua +0 -2
  33. package/dist/utils/timer.lua.map +1 -0
  34. package/dist/utils/units.lua +0 -2
  35. package/dist/utils/units.lua.map +1 -0
  36. package/package.json +3 -4
  37. package/src/index.ts +0 -1
  38. package/src/utils/abilities.ts +0 -158
  39. package/src/utils/camera.ts +0 -63
  40. package/src/utils/chat-command.ts +0 -22
  41. package/src/utils/color.ts +0 -139
  42. package/src/utils/index.ts +0 -15
  43. package/src/utils/item.ts +0 -163
  44. package/src/utils/math.ts +0 -14
  45. package/src/utils/minimapIcons.ts +0 -34
  46. package/src/utils/misc.ts +0 -179
  47. package/src/utils/physics.ts +0 -295
  48. package/src/utils/players.ts +0 -213
  49. package/src/utils/point.ts +0 -81
  50. package/src/utils/quests.ts +0 -38
  51. package/src/utils/textTag.ts +0 -80
  52. package/src/utils/timer.ts +0 -14
  53. package/src/utils/units.ts +0 -84
@@ -1,295 +0,0 @@
1
- // import { WTS_Units } from "src/enums/WTS_Enums";
2
- // import { PlayerIndex } from "src/player/player-data";
3
- import { Effect, Timer, Unit } from "w3ts";
4
- import { OrderId, Players } from "w3ts/globals";
5
-
6
- interface ApplyForceConfig {
7
- /**
8
- * Default: 0
9
- */
10
- sustainedForceDuration?: number;
11
- /**
12
- * Default: -2400 units per second
13
- */
14
- frictionConstant?: number;
15
- /**
16
- * The unit will not phase through unpathable areas
17
- */
18
- obeyPathing?: boolean;
19
- whileActive?: (currentSpeed?: number, timeElapsed?: number) => void;
20
- onStart?: (currentSpeed?: number, timeElapsed?: number) => void;
21
- onEnd?: (currentSpeed?: number, timeElapsed?: number) => void;
22
- /**
23
- *
24
- */
25
- targetSpeed?: number;
26
- /**
27
- * In seconds
28
- */
29
- accelerationTime?: number;
30
- /**
31
- * This will be used to decide if the unit the force is applied on is allowed to deviate from their current path.
32
- */
33
- strictPathing?: boolean;
34
- animationIndexNumber?: number;
35
- dummyUnitPlayerIndex: number;
36
- dummyUnitFourCC: number;
37
- }
38
-
39
- /**
40
- * @param angle degrees
41
- * @param unit
42
- * @param initialSpeed meters per second
43
- * @param affectHeight determines whether or not to change unit height whilst force is applied
44
- */
45
- export function applyForce(
46
- angle: number,
47
- unit: Unit,
48
- initialSpeed: number,
49
- config: ApplyForceConfig
50
- ) {
51
- const timer = Timer.create();
52
- const refreshInterval = 0.01;
53
- const updatesPerSecond = 1 / refreshInterval;
54
- const frictionConstant = 4800; //meters per second friction decay
55
- let currentSpeed = initialSpeed;
56
- let timeElapsed = 0;
57
-
58
- const clickMoveOrder = 851971;
59
- const moveOrders = [
60
- OrderId.Move,
61
- OrderId.Attackground,
62
- OrderId.Patrol,
63
- OrderId.Attack,
64
- clickMoveOrder,
65
- ];
66
-
67
- let forceDummyUnit: Unit | undefined = undefined;
68
- const defaultX = 11800;
69
- const defaultY = -5700;
70
-
71
- //Cancel unit commands - if a unit already has a move command and are applied a force, they will bug out sometimes and walk in the opposite direction
72
- // unit.issueImmediateOrder(OrderId.Stop);
73
-
74
- /**
75
- * Prematurely end the force effect
76
- */
77
- function destroyForceEffect(runOnEnd: boolean = false) {
78
- if (runOnEnd && config?.onEnd) {
79
- config.onEnd();
80
- }
81
-
82
- ResetUnitAnimation(unit.handle);
83
- forceDummyUnit?.destroy();
84
- timer.destroy();
85
- }
86
-
87
- /**
88
- * These are the positions the unit would be if there were no minor disturbances
89
- */
90
- let theoreticalX = unit.x;
91
- let theoreticalY = unit.y;
92
-
93
- /**
94
- * The distance the true unit position can be from the theoretical position. Helps stop sliding against walls, etc.
95
- */
96
- // const BREAK_DISTANCE = 100;
97
-
98
- if (!forceDummyUnit) {
99
- forceDummyUnit = Unit.create(
100
- Players[config.dummyUnitPlayerIndex],
101
- config.dummyUnitPlayerIndex,
102
- defaultX,
103
- defaultY
104
- );
105
- }
106
-
107
- // unit.issueImmediateOrder(OrderId.Stop);
108
-
109
- if (config?.animationIndexNumber) {
110
- ResetUnitAnimation(unit.handle);
111
- SetUnitAnimationByIndex(unit.handle, config.animationIndexNumber);
112
- }
113
-
114
- timer.start(refreshInterval, true, () => {
115
- //If for whatever reason the unit no longer exists.
116
- if (!unit) {
117
- destroyForceEffect();
118
- return destroyForceEffect;
119
- }
120
-
121
- // if (distanceBetweenPoints(unit.x, unit.y, theoreticalX, theoreticalY) > BREAK_DISTANCE) {
122
- // print("unit was to far away from theoretical distance");
123
- // const e = Effect.create("Abilities\\Spells\\Other\\TalkToMe\\TalkToMe", theoreticalX, theoreticalY);
124
- // e?.setScaleMatrix(2, 2, 2);
125
- // unit.issueImmediateOrder(OrderId.Stop);
126
-
127
- // destroyForceEffect(true);
128
- // return;
129
- // }
130
-
131
- //if the unit's move speed vector is greater than the remaining applied force vector then we may stop the applied force function; should only run while the unit has the move order
132
- // if (config?.obeyPathing && !config.strictPathing && currentSpeed > unit.moveSpeed) {
133
- // unit.issueImmediateOrder(OrderId.Stop);
134
- // }
135
-
136
- //should probably only do strict pathing so nothing else interfers with the unit moving
137
- if (forceDummyUnit && config?.strictPathing) {
138
- const isWindWalked = UnitHasBuffBJ(forceDummyUnit.handle, FourCC("BOwk"));
139
-
140
- if (!isWindWalked) {
141
- forceDummyUnit.issueImmediateOrder(OrderId.Windwalk);
142
- }
143
- // forceDummyUnit.issueImmediateOrder(OrderId.Stop);
144
-
145
- //Move dummy to the position we want the unit to be in
146
- forceDummyUnit.x = unit.x;
147
- forceDummyUnit.y = unit.y;
148
-
149
- forceDummyUnit.issueImmediateOrder(OrderId.Stop);
150
-
151
- //flooring values since it can be off sometimes by a thousandth
152
- if (
153
- Math.floor(forceDummyUnit.x) !== Math.floor(unit.x) ||
154
- Math.floor(forceDummyUnit.y) !== Math.floor(unit.y)
155
- ) {
156
- // print(`Collision detected! Dummy x: ${forceDummyUnit.x} y: ${forceDummyUnit.y} Unit x: ${unit.x} y: ${unit.y}`);
157
- const e = Effect.create(
158
- "Abilities\\Spells\\Other\\TalkToMe\\TalkToMe",
159
- forceDummyUnit.x,
160
- forceDummyUnit.y
161
- );
162
- e?.setScaleMatrix(2, 2, 2);
163
- destroyForceEffect(true);
164
- return;
165
- }
166
- }
167
-
168
- const xVelocity =
169
- (currentSpeed / updatesPerSecond) * Math.cos(Deg2Rad(angle));
170
- const yVelocity =
171
- (currentSpeed / updatesPerSecond) * Math.sin(Deg2Rad(angle));
172
-
173
- //Complete execution when current speed of the initial force has decayed
174
- if (currentSpeed <= 0) {
175
- destroyForceEffect(true);
176
- return;
177
- }
178
-
179
- //Runs when the force is first applied
180
- if (config?.onStart && currentSpeed === initialSpeed) {
181
- config.onStart(currentSpeed, timeElapsed);
182
- }
183
-
184
- //Runs at any point while the function is executing
185
- if (config?.whileActive) {
186
- config.whileActive(currentSpeed, timeElapsed);
187
- }
188
-
189
- theoreticalX += xVelocity;
190
- theoreticalY += yVelocity;
191
-
192
- //basically the same thing now since we are no longer issuing the stop command on the unit.
193
- //also the moment another force is applied to the unit the previous force will stop being applied.
194
- if (config?.strictPathing) {
195
- unit.x = theoreticalX;
196
- unit.y = theoreticalY;
197
- } else {
198
- unit.x += xVelocity;
199
- unit.y += yVelocity;
200
- }
201
-
202
- timeElapsed += refreshInterval;
203
-
204
- if (
205
- config?.sustainedForceDuration &&
206
- timeElapsed <= config.sustainedForceDuration
207
- ) {
208
- return;
209
- }
210
-
211
- currentSpeed -= frictionConstant / updatesPerSecond;
212
- });
213
-
214
- return { destroyForceEffect };
215
- }
216
-
217
- /**
218
- * @param angle degrees
219
- * @param effect
220
- * @param initialSpeed meters per second
221
- * @param affectHeight determines whether or not to change unit height whilst force is applied
222
- */
223
- export function applyForceForEffect(
224
- angle: number,
225
- effect: Effect,
226
- initialSpeed: number,
227
- config?: ApplyForceConfig
228
- ) {
229
- const timer = Timer.create();
230
- const refreshInterval = 0.01;
231
- const updatesPerSecond = 1 / refreshInterval;
232
- const frictionConstant = 1200; //meters per second friction decay
233
- let currentSpeed = initialSpeed;
234
- let timeElapsed = 0;
235
-
236
- //Cancel unit commands - if a unit already has a move command and are applied a force, they will bug out sometimes and walk in the opposite direction
237
-
238
- timer.start(refreshInterval, true, () => {
239
- //if the unit's move speed vector is greater than the remaining applied force vector then we may stop the applied force function; should only run while the unit has the move order
240
- const xVelocity =
241
- (currentSpeed / updatesPerSecond) * Math.cos(Deg2Rad(angle));
242
- const yVelocity =
243
- (currentSpeed / updatesPerSecond) * Math.sin(Deg2Rad(angle));
244
-
245
- //On end hook runs before the timer is destroyed and the function ends
246
- if (config?.onEnd && currentSpeed <= 0) {
247
- config.onEnd(currentSpeed, timeElapsed);
248
- }
249
-
250
- //Complete execution when current speed of the initial force has decayed
251
- if (currentSpeed <= 0) {
252
- timer.destroy();
253
- return;
254
- }
255
-
256
- //Runs when the force is first applied
257
- if (config?.onStart && currentSpeed === initialSpeed) {
258
- config.onStart(currentSpeed, timeElapsed);
259
- }
260
-
261
- //Runs at any point while the function is executing
262
- if (config?.whileActive) {
263
- config.whileActive(currentSpeed, timeElapsed);
264
- }
265
-
266
- effect.x += xVelocity;
267
- effect.y += yVelocity;
268
-
269
- timeElapsed += refreshInterval;
270
-
271
- if (
272
- config?.sustainedForceDuration &&
273
- timeElapsed <= config.sustainedForceDuration
274
- ) {
275
- return;
276
- }
277
-
278
- currentSpeed -= frictionConstant / updatesPerSecond;
279
- });
280
-
281
- function destroyForceEffect() {
282
- timer.destroy();
283
- }
284
-
285
- return { destroyForceEffect };
286
- }
287
-
288
- // const unitIsMovingVector_x = (unit.moveSpeed / updatesPerSecond) * Math.cos(Deg2Rad(unit.facing));
289
- // const unitIsMovingVector_y = (unit.moveSpeed / updatesPerSecond) * Math.sin(Deg2Rad(unit.facing));
290
- // if ((moveOrders.includes(unit.currentOrder) && unitIsMovingVector_x > xVelocity) || unitIsMovingVector_y > yVelocity) {
291
- // print("moving velocity exceeded applied force velocity");
292
- // timer.destroy();
293
-
294
- // return;
295
- // }
@@ -1,213 +0,0 @@
1
- import { Group, MapPlayer, Rectangle, Trigger, Unit } from "w3ts";
2
- import { Players } from "w3ts/globals";
3
-
4
- /**
5
- * Does a callback for every unit of the player that has the ability
6
- * @param player
7
- * @param abilityId
8
- * @param cb
9
- */
10
- export function forEachUnitOfPlayerWithAbility(player: MapPlayer, abilityId: number, cb: (unit: Unit) => void) {
11
- forEachUnitOfPlayer(player, (u) => {
12
- for (let x = 0; x < 12; x++) {
13
- const currentAbility = u.getAbilityByIndex(x);
14
-
15
- if (currentAbility && currentAbility === u.getAbility(abilityId) && u.isAlive()) {
16
- cb(u);
17
- }
18
- }
19
- });
20
- }
21
-
22
- /**
23
- * Calls a function for each player playing and is an ally of red.
24
- * @warning specific to map
25
- */
26
- export function forEachAlliedPlayer(cb: (player: MapPlayer, index: number) => void) {
27
- Players.forEach((player, index) => {
28
- //For testing purposes, include player[9] (the human ally) so their units can also be included when iterating the units OR i should make a separate function for all units.
29
- if (player.slotState === PLAYER_SLOT_STATE_PLAYING && player.isPlayerAlly(Players[0]) && player != Players[25] && player != Players[27]) {
30
- cb(player, index);
31
- }
32
- });
33
- }
34
-
35
- export function forEachPlayer(cb: (player: MapPlayer, index: number) => void) {
36
- Players.forEach((p, index) => {
37
- cb(p, index);
38
- });
39
- }
40
-
41
- /**
42
- * Executes the callback function for each unit matching the unit type for the player
43
- * @param unitType Unit Type Id or the Unit Type String "hcas", etc
44
- */
45
- export function forEachUnitTypeOfPlayer(unitType: number | string, player: MapPlayer, cb: (unit: Unit) => void) {
46
- if (typeof unitType === "string") {
47
- unitType = FourCC(unitType);
48
- }
49
-
50
- const g = Group.create();
51
-
52
- g?.enumUnitsOfPlayer(player, () => {
53
- const unit = Group.getFilterUnit();
54
-
55
- if (unit && unit?.typeId === unitType) {
56
- cb(unit);
57
- }
58
-
59
- return true;
60
- });
61
-
62
- g?.destroy();
63
- }
64
-
65
- /**
66
- * @broken
67
- * @param unitName
68
- * @param unitType
69
- * @param fn
70
- */
71
- export function forEachUnitOfType(unitName: string, unitType: number | string, fn: (unit: Unit) => void) {
72
- if (typeof unitType === "string") {
73
- unitType = FourCC(unitType);
74
- }
75
-
76
- print(unitName);
77
-
78
- const g = Group.create();
79
-
80
- g?.enumUnitsOfType(unitName, () => {
81
- const unit = Group.getFilterUnit();
82
-
83
- if (unit && unit?.typeId === unitType) {
84
- fn(unit);
85
- }
86
-
87
- return true;
88
- });
89
-
90
- print(`Total units of name ${unitName} found: ${g?.size}`);
91
-
92
- g?.destroy();
93
- }
94
-
95
- /**
96
- * @param unitType Unit Type Id or the Unit Type String "hcas", etc
97
- */
98
- export function forEachUnitOfPlayer(player: MapPlayer, cb: (unit: Unit) => void) {
99
- const g = Group.create();
100
-
101
- g?.enumUnitsOfPlayer(player, () => {
102
- const unit = Group.getFilterUnit();
103
-
104
- if (!unit) {
105
- print("Enumerating over a unit that doesn't exist!");
106
- }
107
- if (unit) {
108
- cb(unit);
109
- }
110
-
111
- return true;
112
- });
113
-
114
- g?.destroy();
115
- }
116
-
117
- /**
118
- * Executes the callback function for each unit matching the unit type for the player
119
- * @param unitType Unit Type Id or the Unit Type String "hcas", etc
120
- */
121
- export function forEachUnitInRectangle(rectangle: Rectangle, cb: (unit: Unit) => void) {
122
- const g = Group.create();
123
-
124
- g?.enumUnitsInRect(rectangle, () => {
125
- const unit = Group.getFilterUnit();
126
-
127
- if (unit) {
128
- cb(unit);
129
- }
130
-
131
- return true;
132
- });
133
-
134
- g?.destroy();
135
- }
136
-
137
- export function isPlaying(player: MapPlayer | player) {
138
- if (player instanceof MapPlayer) {
139
- return player.slotState === PLAYER_SLOT_STATE_PLAYING;
140
- }
141
-
142
- return GetPlayerSlotState(player) === PLAYER_SLOT_STATE_PLAYING;
143
- }
144
-
145
- export function isUser(player: MapPlayer | player) {
146
- if (player instanceof MapPlayer) {
147
- return GetPlayerController(player.handle) === MAP_CONTROL_USER;
148
- }
149
-
150
- return GetPlayerController(player) === MAP_CONTROL_USER;
151
- }
152
-
153
- export function isComputer(player: MapPlayer) {
154
- if (player instanceof MapPlayer) {
155
- return GetPlayerController(player.handle) === MAP_CONTROL_COMPUTER;
156
- }
157
-
158
- return GetPlayerController(player) === MAP_CONTROL_COMPUTER;
159
- }
160
-
161
- export function isPlayingUser(player: MapPlayer | player) {
162
- return isUser(player) && isPlaying(player);
163
- }
164
-
165
- export function adjustPlayerState(player: MapPlayer, whichState: playerstate, amount: number) {
166
- player.setState(whichState, player.getState(whichState) + amount);
167
- }
168
-
169
- export function adjustGold(player: MapPlayer, amount: number) {
170
- player.setState(PLAYER_STATE_RESOURCE_GOLD, player.getState(PLAYER_STATE_RESOURCE_GOLD) + amount);
171
- }
172
-
173
- export function adjustLumber(player: MapPlayer, amount: number) {
174
- player.setState(PLAYER_STATE_RESOURCE_LUMBER, player.getState(PLAYER_STATE_RESOURCE_LUMBER) + amount);
175
- }
176
-
177
- export function adjustFoodCap(player: MapPlayer, amount: number) {
178
- player.setState(PLAYER_STATE_RESOURCE_FOOD_CAP, player.getState(PLAYER_STATE_RESOURCE_FOOD_CAP) + amount);
179
- }
180
-
181
- export function adjustFoodUsed(player: MapPlayer, amount: number) {
182
- player.setState(PLAYER_STATE_RESOURCE_FOOD_USED, player.getState(PLAYER_STATE_RESOURCE_FOOD_USED) + amount);
183
- }
184
-
185
- export function playerHasResources(player: MapPlayer, data: { gold?: number; lumber?: number }) {
186
- let hasGold = true;
187
- let hasLumber = true;
188
-
189
- if (data.gold && data.gold != 0) {
190
- hasGold = player.getState(PLAYER_STATE_RESOURCE_GOLD) >= data.gold;
191
- }
192
-
193
- if (data.lumber && data.lumber != 0) {
194
- hasLumber = player.getState(PLAYER_STATE_RESOURCE_LUMBER) >= data.lumber;
195
- }
196
-
197
- return hasGold && hasLumber;
198
- }
199
-
200
- export function setPlayerName() {
201
- const t = Trigger.create();
202
- forEachPlayer((p) => {
203
- t.registerPlayerChatEvent(p, "-playername ", false);
204
-
205
- t.addAction(() => {
206
- const str = GetEventPlayerChatString();
207
- const newName = str?.replace("-playername", "");
208
- if (newName) {
209
- SetPlayerName(p.handle, newName);
210
- }
211
- });
212
- });
213
- }
@@ -1,81 +0,0 @@
1
- import { Point, Rectangle } from "w3ts";
2
- const MAP_EDGE_BUFFER_DIST = 300;
3
-
4
- export function createValidPoint(maxAttempts: number, validatorFn: (p: Point) => {}) {
5
- const MAX_ATTEMPTS = 65000; // 100 was about 10 seconds; 1000 gets good coverage
6
- let currentAttempts = 0;
7
- const worldBounds = Rectangle.fromHandle(GetWorldBounds());
8
- if (!worldBounds) return;
9
- const [maxX, maxY] = [GetCameraBoundMaxX(), GetCameraBoundMaxY()];
10
-
11
- while (currentAttempts <= MAX_ATTEMPTS) {
12
- const dirX = Math.floor(Math.random() * 100) >= 50 ? 1 : -1;
13
- const dirY = Math.floor(Math.random() * 100) >= 50 ? 1 : -1;
14
-
15
- //multiply dir by the buffer distance from max bounds since we can get a negative number
16
- const randX = dirX * Math.ceil(Math.random() * maxX) - dirX * MAP_EDGE_BUFFER_DIST;
17
- const randY = dirY * Math.ceil(Math.random() * maxY) - dirY * MAP_EDGE_BUFFER_DIST;
18
-
19
- const p = Point.create(randX, randY);
20
-
21
- const isValidPoint = validatorFn(p);
22
-
23
- if (isValidPoint) {
24
- // pointsChosen.push(p);
25
- return p;
26
- } else {
27
- //well add it here later, just testing for now
28
- currentAttempts++;
29
- }
30
- }
31
- }
32
-
33
- export function getRandomCoordinatesInCircularArea(relativeX: number, relativeY: number, radius: number) {
34
- const randomTheta = Math.random() * 360;
35
- const randomRadius = Math.random() * radius;
36
-
37
- const randomX = relativeX + randomRadius * Cos(randomTheta);
38
- const randomY = relativeY + randomRadius * Sin(randomTheta);
39
-
40
- return {
41
- x: randomX,
42
- y: randomY,
43
- };
44
- }
45
-
46
- export function getRandomCoordinatesOnCircle(relativeX: number, relativeY: number, radius: number) {
47
- const randomTheta = Math.random() * 360;
48
-
49
- const randomX = relativeX + radius * Cos(randomTheta);
50
- const randomY = relativeY + radius * Sin(randomTheta);
51
-
52
- return {
53
- x: randomX,
54
- y: randomY,
55
- };
56
- }
57
-
58
- /**
59
- * Returns degrees or radians?
60
- */
61
- export function getAngleBetweenPoints(x1: number, y1: number, x2: number, y2: number) {
62
- const locA = Location(x1, y1);
63
- const locB = Location(x2, y2);
64
-
65
- const angle = AngleBetweenPoints(locA, locB);
66
- //arc tan
67
- RemoveLocation(locA);
68
- RemoveLocation(locB);
69
-
70
- return angle;
71
- }
72
-
73
- export function distanceBetweenPoints(x1: number, y1: number, x2: number, y2: number) {
74
- const deltaX = x1 - x2;
75
- const deltaY = y1 - y2;
76
- const squaredDist = deltaX * deltaX + deltaY * deltaY;
77
- // const squaredDist = Math.pow(deltaX, 2) + Math.pow(deltaY, 2);
78
- const dist = Math.sqrt(squaredDist);
79
-
80
- return dist;
81
- }
@@ -1,38 +0,0 @@
1
- import { Quest, Timer } from "w3ts";
2
- import { tColor } from "./misc";
3
-
4
- export function setup_quests() {
5
- Timer.create().start(1, false, () => {
6
- addQuest(
7
- "Basic Game Info",
8
- `\nA roguelite base assault game. \nChoose from a wide variety of units that are trained in various schools of magic and skills.\n Outsmart and counter your opponent..
9
- `,
10
- "ReplaceableTextures\\CommandButtons\\BTNPeasant.blp"
11
- );
12
-
13
- // \n${tColor("-fixSpawns", "goldenrod")}: Player 1 can only use this. This will fix add all player's spawn units to their corresponding spawn pool.
14
- addQuest(
15
- "Commands",
16
- `
17
- \n${tColor("-cam ####", "goldenrod")}: Sets the camera distance.
18
- \n-playername xxxx This will change your name.
19
- `,
20
- "ReplaceableTextures\\WorldEditUI\\Doodad-Cinematic.blp",
21
- false
22
- );
23
-
24
- addQuest("|cffffcc00Evolution Castle Assault v0.01|r", "Created by JediMindTrix/NihilismIsDeath", "ReplaceableTextures\\CommandButtons\\BTNClayFigurine.blp", false);
25
- });
26
- }
27
-
28
- export function addQuest(title: string, description: string, iconPath?: string, required: boolean = true) {
29
- const q = Quest.create();
30
- if (q) {
31
- q.setTitle(title);
32
- q.required = required;
33
- q.setDescription(description);
34
- if (iconPath) {
35
- q.setIcon(iconPath);
36
- }
37
- }
38
- }
@@ -1,80 +0,0 @@
1
- import { TextTag, Trigger, Unit } from "w3ts";
2
- import { ptColor } from "./misc";
3
- import { delayedTimer } from "./timer";
4
-
5
- /**
6
- * https://www.hiveworkshop.com/threads/floating-text.149719/
7
- *
8
- * function CreateFloatingText takes string text, real x, real y, real heightOffset, real duration, real size returns nothing
9
- local texttag tt = CreateTextTag()
10
- call SetTextTagText(tt, text, size)
11
- call SetTextTagPos(tt, x, y, heightOffset)
12
- call SetTextTagColor(tt, 255, 255, 255, 255) // RGBA format
13
- call SetTextTagVisibility(tt, true)
14
- call SetTextTagLifespan(tt, duration)
15
- call SetTextTagPermanent(tt, false)
16
- endfunction
17
-
18
- function ExampleUsage takes nothing returns nothing
19
- call CreateFloatingText("Hello World", 0.0, 0.0, 25.0, 5.0, 10.0)
20
- endfunction
21
- * @param unit
22
- * @param text
23
- * @param duration
24
- */
25
- export function createFloatingTextTagOnUnit(unit: Unit, text: string, config?: { duration?: number; yVelocity?: number; xVelocity?: number; useFade?: boolean }) {
26
- const tag = TextTag.create();
27
- tag?.setVisible(true);
28
-
29
- tag?.setText(text, 10, true);
30
-
31
- tag?.setLifespan(config?.duration === undefined ? 2 : config.duration);
32
-
33
- if (config?.useFade !== false) {
34
- tag?.setFadepoint(0.01);
35
- }
36
-
37
- tag?.setVelocity(config?.xVelocity === undefined ? 0 : config.xVelocity, config?.yVelocity === undefined ? 0.025 : config.yVelocity);
38
- tag?.setPermanent(false);
39
-
40
- tag?.setPosUnit(unit, 10);
41
-
42
- if (config && config.duration && config.duration === 0) {
43
- return;
44
- }
45
-
46
- delayedTimer(config?.duration ?? 2, () => {
47
- tag?.destroy();
48
- });
49
- }
50
-
51
- export function createPermanentTextTagOnPoint(text: string, x: number, y: number) {
52
- const tag = TextTag.create();
53
- tag?.setVisible(true);
54
-
55
- tag?.setText(text, 20, true);
56
- tag?.setLifespan(2);
57
-
58
- tag?.setVelocity(0, 0);
59
- tag?.setPermanent(true);
60
- tag?.setPos(x, y, 20);
61
- }
62
-
63
- export function setup_createTextForSpellCast() {
64
- const t = Trigger.create();
65
-
66
- t.registerAnyUnitEvent(EVENT_PLAYER_UNIT_SPELL_EFFECT);
67
-
68
- t.addAction(() => {
69
- const u = Unit.fromEvent();
70
-
71
- if (u) {
72
- const spellNumber = GetSpellAbilityId();
73
- const spellName = GetAbilityName(spellNumber);
74
- if (!spellName || spellName === "Default String") return;
75
- //alt + 0164 ¤
76
- //alt + 0149 •
77
- createFloatingTextTagOnUnit(u, ptColor(u.owner, "¤ ") + spellName);
78
- }
79
- });
80
- }