Skip to content

Commit 088d8e8

Browse files
gruckionJameskmonger
authored andcommitted
refactor: convert woodcuitting tasks to use new task system
1 parent 1997d0a commit 088d8e8

File tree

3 files changed

+119
-102
lines changed

3 files changed

+119
-102
lines changed

src/engine/world/skill-util/harvest-skill.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,11 @@ import { findItem } from '@engine/config/config-handler';
1313
import { activeWorld } from '@engine/world';
1414
import { loopingEvent } from '@engine/plugins';
1515

16+
/**
17+
* Check if a player can harvest a given {@link IHarvestable}
18+
*
19+
* @returns a {@link HarvestTool} if the player can harvest the object, or undefined if they cannot.
20+
*/
1621
export function canInitiateHarvest(player: Player, target: IHarvestable, skill: Skill): undefined | HarvestTool {
1722
if (!target) {
1823
switch (skill) {

src/plugins/skills/woodcutting/index.ts

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import {
22
ObjectInteractionActionHook,
33
} from '@engine/action';
44
import { getTreeIds } from '@engine/world/config/harvestable-object';
5-
import { activate, canActivate, onComplete } from './woodcutting-task';
5+
import { runWoodcuttingTask } from './woodcutting-task';
66

77

88
export default {
@@ -12,12 +12,8 @@ export default {
1212
type: 'object_interaction',
1313
options: [ 'chop down', 'chop' ],
1414
objectIds: getTreeIds(),
15-
strength: 'normal',
16-
task: {
17-
canActivate,
18-
activate,
19-
onComplete,
20-
interval: 1
15+
handler: ({ player, object }) => {
16+
runWoodcuttingTask(player, object);
2117
}
2218
} as ObjectInteractionActionHook
2319
]
Lines changed: 111 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -1,126 +1,142 @@
1-
2-
import {
3-
ObjectInteractionAction,
4-
TaskExecutor
5-
} from '@engine/action';
61
import { Skill } from '@engine/world/actor/skills';
72
import { canInitiateHarvest } from '@engine/world/skill-util/harvest-skill';
8-
import { getTreeFromHealthy, getTreeIds, IHarvestable } from '@engine/world/config/harvestable-object';
3+
import { getTreeFromHealthy, IHarvestable } from '@engine/world/config/harvestable-object';
94
import { randomBetween } from '@engine/util/num';
105
import { colorText } from '@engine/util/strings';
116
import { colors } from '@engine/util/colors';
127
import { rollBirdsNestType } from '@engine/world/skill-util/harvest-roll';
138
import { soundIds } from '@engine/world/config/sound-ids';
14-
import { Axe, getAxe, HarvestTool } from '@engine/world/config/harvest-tool';
15-
import { findItem } from '@engine/config/config-handler';
9+
import { findItem, findObject } from '@engine/config/config-handler';
1610
import { activeWorld } from '@engine/world';
1711
import { canCut } from './chance';
18-
19-
export const canActivate = (task: TaskExecutor<ObjectInteractionAction>, taskIteration: number): boolean => {
20-
const { actor, actionData: { position, object, player } } = task;
21-
const tree = getTreeFromHealthy(object.objectId);
22-
23-
if(!tree) {
24-
return false;
25-
}
26-
27-
const tool = actor.isPlayer ? canInitiateHarvest(player, tree, Skill.WOODCUTTING) : getAxe(Axe.STEEL);
28-
29-
if(!tool) {
30-
return false;
31-
}
32-
33-
task.session.tool = tool;
34-
task.session.tree = tree;
35-
36-
if(taskIteration === 0) {
37-
// First run
38-
39-
if(actor.isPlayer) {
40-
player.sendMessage('You swing your axe at the tree.');
12+
import { ActorLandscapeObjectInteractionTask } from '@engine/task/impl';
13+
import { Player } from '@engine/world/actor';
14+
import { LandscapeObject } from '@runejs/filestore';
15+
import { logger } from '@runejs/common';
16+
17+
class WoodcuttingTask extends ActorLandscapeObjectInteractionTask<Player> {
18+
private treeInfo: IHarvestable;
19+
private elapsedTicks = 0;
20+
21+
constructor(
22+
player: Player,
23+
landscapeObject: LandscapeObject,
24+
sizeX: number,
25+
sizeY: number
26+
) {
27+
super(
28+
player,
29+
landscapeObject,
30+
sizeX,
31+
sizeY
32+
);
33+
34+
if (!landscapeObject) {
35+
this.stop();
36+
return;
4137
}
4238

43-
actor.face(position);
44-
actor.playAnimation(tool.animation);
39+
this.treeInfo = getTreeFromHealthy(landscapeObject.objectId);
40+
if (!this.treeInfo) {
41+
this.stop();
42+
return;
43+
}
4544
}
4645

47-
return true;
48-
};
49-
50-
51-
export const activate = (task: TaskExecutor<ObjectInteractionAction>, taskIteration: number): boolean => {
52-
const { actor, player, actionData, session } = task.getDetails();
53-
const { position: objectPosition, object: actionObject } = actionData;
54-
const tree: IHarvestable = session.tree;
55-
const tool: HarvestTool = session.tool;
46+
public execute(): void {
47+
super.execute();
5648

57-
// Cancel if the actor no longer has their tool or level requirements.
58-
if(!tool || !tree) {
59-
return false;
60-
}
49+
if (!this.isActive || !this.landscapeObject) {
50+
return;
51+
}
6152

62-
// Grab the tree manually every loop so that we can make sure it's still alive.
63-
const { object } = activeWorld.findObjectAtLocation(actor, actionObject.objectId, objectPosition);
53+
// store the tick count before incrementing so we don't need to keep track of it in all the separate branches
54+
const taskIteration = this.elapsedTicks++;
6455

65-
if(!object) {
66-
// Tree has been chopped down, cancel.
67-
return false;
68-
}
56+
const tool = canInitiateHarvest(this.actor, this.treeInfo, Skill.WOODCUTTING);
6957

70-
// Check if the amount of ticks passed equal the tools pulses.
71-
if(taskIteration % 3 === 0 && taskIteration != 0) {
58+
if (!tool) {
59+
this.stop();
60+
return;
61+
}
7262

73-
let toolLevel = tool.level - 1;
74-
if(tool.itemId === 1349 || tool.itemId === 1267) {
75-
toolLevel = 2;
63+
if(taskIteration === 0) {
64+
this.actor.sendMessage('You swing your axe at the tree.');
65+
this.actor.face(this.landscapeObjectPosition);
66+
this.actor.playAnimation(tool.animation);
67+
return;
7668
}
7769

78-
const succeeds = canCut(tree, toolLevel, actor.skills.woodcutting.level);
79-
if(succeeds) {
80-
const targetName: string = findItem(tree.itemId).name.toLowerCase();
81-
82-
if(actor.inventory.hasSpace()) {
83-
const itemToAdd = tree.itemId;
84-
const roll = randomBetween(1, 256);
85-
86-
if(roll === 1) { // Bird nest chance
87-
player?.sendMessage(colorText(`A bird's nest falls out of the tree.`, colors.red));
88-
activeWorld.globalInstance.spawnWorldItem(rollBirdsNestType(), actor.position,
89-
{ owner: player || null, expires: 300 });
90-
} else { // Standard log chopper
91-
player?.sendMessage(`You manage to chop some ${targetName}.`);
92-
actor.giveItem(itemToAdd);
93-
}
70+
if(taskIteration % 3 === 0) {
9471

95-
player?.skills.woodcutting.addExp(tree.experience);
72+
let toolLevel = tool.level - 1;
73+
if(tool.itemId === 1349 || tool.itemId === 1267) {
74+
toolLevel = 2;
75+
}
9676

97-
if(randomBetween(0, 100) <= tree.break) {
98-
player?.playSound(soundIds.oreDepeleted);
99-
actor.instance.replaceGameObject(tree.objects.get(actionObject.objectId),
100-
object, randomBetween(tree.respawnLow, tree.respawnHigh));
101-
return false;
77+
const succeeds = canCut(this.treeInfo, toolLevel, this.actor.skills.woodcutting.level);
78+
if(succeeds) {
79+
const targetName: string = findItem(this.treeInfo.itemId).name.toLowerCase();
80+
81+
if(this.actor.inventory.hasSpace()) {
82+
const itemToAdd = this.treeInfo.itemId;
83+
const roll = randomBetween(1, 256);
84+
85+
if(roll === 1) { // Bird nest chance
86+
this.actor.sendMessage(colorText(`A bird's nest falls out of the tree.`, colors.red));
87+
activeWorld.globalInstance.spawnWorldItem(rollBirdsNestType(), this.actor.position,
88+
{ owner: this.actor || null, expires: 300 });
89+
} else { // Standard log chopper
90+
this.actor.sendMessage(`You manage to chop some ${targetName}.`);
91+
this.actor.giveItem(itemToAdd);
92+
}
93+
94+
this.actor.skills.woodcutting.addExp(this.treeInfo.experience);
95+
96+
if(randomBetween(0, 100) <= this.treeInfo.break) {
97+
this.actor.playSound(soundIds.oreDepeleted);
98+
this.actor.instance.replaceGameObject(this.treeInfo.objects.get(this.landscapeObject.objectId),
99+
this.landscapeObject, randomBetween(this.treeInfo.respawnLow, this.treeInfo.respawnHigh));
100+
this.stop();
101+
return;
102+
}
103+
} else {
104+
this.actor.sendMessage(`Your inventory is too full to hold any more ${targetName}.`, true);
105+
this.actor.playSound(soundIds.inventoryFull);
106+
this.stop();
107+
return;
102108
}
103-
} else {
104-
player?.sendMessage(
105-
`Your inventory is too full to hold any more ${targetName}.`, true);
106-
player?.playSound(soundIds.inventoryFull);
107-
return false;
109+
}
110+
} else {
111+
if(taskIteration % 1 === 0) {
112+
const randomSoundIdx = Math.floor(Math.random() * soundIds.axeSwing.length);
113+
this.actor.playSound(soundIds.axeSwing[randomSoundIdx], 7, 0);
108114
}
109115
}
110-
} else {
111-
if(taskIteration % 1 === 0 && taskIteration !== 0) {
112-
const randomSoundIdx = Math.floor(Math.random() * soundIds.axeSwing.length);
113-
player?.playSound(soundIds.axeSwing[randomSoundIdx], 7, 0);
116+
117+
if(taskIteration % 3 === 0) {
118+
this.actor.playAnimation(tool.animation);
114119
}
120+
121+
}
122+
123+
public onStop(): void {
124+
super.onStop();
125+
126+
this.actor.stopAnimation();
115127
}
128+
}
129+
130+
export function runWoodcuttingTask(player: Player, landscapeObject: LandscapeObject): void {
131+
const objectConfig = findObject(landscapeObject.objectId);
116132

117-
if(taskIteration % 3 === 0 && taskIteration !== 0) {
118-
actor.playAnimation(tool.animation);
133+
if (!objectConfig) {
134+
logger.warn(`Player ${player.username} attempted to run a woodcutting task on an invalid object (id: ${landscapeObject.objectId})`);
135+
return;
119136
}
120137

121-
return true;
122-
};
138+
const sizeX = objectConfig.rendering.sizeX;
139+
const sizeY = objectConfig.rendering.sizeY;
123140

124-
export const onComplete = (task: TaskExecutor<ObjectInteractionAction>): void => {
125-
task.actor.stopAnimation();
126-
};
141+
player.enqueueTask(WoodcuttingTask, [ landscapeObject, sizeX, sizeY ]);
142+
}

0 commit comments

Comments
 (0)