xy-server/game/object/TaskState.ts

426 lines
18 KiB
TypeScript
Raw Permalink Normal View History

2025-04-23 09:34:08 +08:00
import GameUtil from "../core/GameUtil";
import TalkEventState from "../event/TalkEventState";
import GatherNpcState from "../event/GatherNpcState";
import KillDynamicNpcState from "../event/KillDynamicNpcState";
import ActionAreaEventState from "../event/ActionAreaEventState";
import ArriveAreaState from "../event/ArriveAreaState";
import GatherItemToNpcEventState from "../event/GatherItemToNpcEventState";
import FailEventPlayerDeadState from "../event/FailEventPlayerDeadState";
import FailEventTimeOutState from "../event/FailEventTimeOutState";
import TaskConfigMgr from "../task/TaskConfigMgr";
import NpcMgr from "../core/NpcMgr";
import DynamicNpc from "../core/DynamicNpc";
import TeamMgr from "../core/TeamMgr";
import Player from "./Player";
import SKLogger from "../gear/SKLogger";
import { EEventType, ENpcCreater, ETaskKind, ETaskState } from "../role/EEnum";
import Task from "../task/Task";
import Npc from "../core/Npc";
import EventStateBase from "../event/EventStateBase";
import SKDataUtil from "../gear/SKDataUtil";
import e from "express";
export default class TaskState {
nTaskID: any;
nKind: any;
nTaskGrop: any;
nTaskFinish: ETaskState;
vecEventState: any[];
vecFailEvent: any;
player: any;
constructor() {
this.nTaskID = 0;
this.nKind = 0;
this.nTaskGrop = 0;
this.nTaskFinish = 0;
this.vecEventState = [];
this.vecFailEvent = [];
this.player = null;
}
initState(task: Task, step: number) {
this.nTaskID = task.nTaskID;
this.nKind = task.nKind;
this.nTaskGrop = task.nTaskGrop;
for (let i = 0; i < task.vecEvent.length; i++) {
let taskState = null;
if (task.vecEvent[i].nEventType == EEventType.PLAYER_TALK_NPC) {
taskState = new TalkEventState();
taskState.vecRemainNpc = [];
}
if (task.vecEvent[i].nEventType == EEventType.PLAYER_GATHER_NPC) {
taskState = new GatherNpcState();
taskState.vecRemainNpc = [];
}
if (task.vecEvent[i].nEventType == EEventType.PLAYER_KILL_NPC) {
taskState = new KillDynamicNpcState();
taskState.vecRemainNpc = [];
}
if (task.vecEvent[i].nEventType == EEventType.PLAYER_DO_ACITION) {
taskState = new ActionAreaEventState();
}
if (task.vecEvent[i].nEventType == EEventType.PLAYER_ARRIVE_AREA) {
taskState = new ArriveAreaState();
taskState.nMap = task.vecEvent[i].nMap;
taskState.nX = task.vecEvent[i].nX;
taskState.nY = task.vecEvent[i].nY;
}
if (task.vecEvent[i].nEventType == EEventType.PLAYER_GIVE_NPC_ITEM) {
taskState = new GatherItemToNpcEventState();
}
if (taskState) {
taskState.nEventType = task.vecEvent[i].nEventType;
taskState.nState = ETaskState.LOCK;
if (i < step) {
taskState.nState = ETaskState.DONE;
}
this.vecEventState.push(taskState);
}
}
for (let i = 0; i < task.vecFailEvent.length; i++) {
let failEvent = null;
if (task.vecFailEvent[i].nEventType == EEventType.PLAYER_DEAD) {
failEvent = new FailEventPlayerDeadState();
failEvent.nDeadCnt = 0;
}
if (task.vecFailEvent[i].nEventType == EEventType.TIMEOUT) {
failEvent = new FailEventTimeOutState();
failEvent.nStartTime = GameUtil.getTime();
}
if (failEvent) {
this.vecFailEvent.push(failEvent);
}
}
this.reconCurrentEvent();
}
BuildCreaterInfo() {
if (TaskConfigMgr.shared.isTeamTask(this.nTaskID))
return {
nKind: ENpcCreater.TEAM,
nID: this.player.teamid
}
else
return {
nKind: ENpcCreater.PLAYER,
nID: this.player.roleid
}
}
IsBangMap(nMap: any) {
if (nMap == 3002)
return true;
return false;
}
reconCurrentEvent() {
for (let i = 0; i < this.vecEventState.length; i++) {
let taskState: EventStateBase = this.vecEventState[i];
if (taskState.nState == ETaskState.DONE) {
continue;
}
if (taskState.nState == ETaskState.DOING) {
break;
}
this.vecEventState[i].nState = ETaskState.DOING;
let stepConf: any = TaskConfigMgr.shared.getTaskStepInfo(this.nTaskID, i);
if (stepConf.hasOwnProperty("vecCreateNpc") && stepConf.vecCreateNpc.length > 0) {
for (let itCreate in stepConf.vecCreateNpc) {
let stData = stepConf.vecCreateNpc[itCreate];
let nOnlyID = NpcMgr.shared.CreateNpc(stData.nNpc, stData.nMap, stData.nX, stData.nY, this.BuildCreaterInfo(), this.IsBangMap(stData.nMap) ? this.player.bangid : 0);
let npc: DynamicNpc = new DynamicNpc(nOnlyID, stData.nNpc);
this.vecEventState[i].vecRemainNpc.push(npc);
}
} else {
for (let key in stepConf.vecNpc) {
let confId: number = stepConf.vecNpc[key];
let worldNpc: Npc = NpcMgr.shared.getNpcByConfigID(confId);
if (worldNpc == null) {
SKLogger.debug(`找不到NPC[${confId}]`);
continue;
}
this.vecEventState[i].vecRemainNpc.push(new DynamicNpc(worldNpc.onlyid, worldNpc.configid));
}
}
if (stepConf.nEventType == EEventType.PLAYER_KILL_NPC &&
stepConf.bAutoTrigle == 1 &&
this.vecEventState[i].vecRemainNpc.length > 0 &&
this.player.getTaskMgr().bCanAutoFight == 1) {
let npcOnlyId = this.vecEventState[i].vecRemainNpc[0].nOnlyID;
let npc: Npc = NpcMgr.shared.findNpc(npcOnlyId);
if (npc == null) {
SKLogger.debug(`找不到NPC[${npcOnlyId}]`);
return;
}
let battle = this.player.monsterBattle(npc.monster_group,this.nTaskGrop);
if (battle == null) {
return;
}
battle.source = this.vecEventState[i].vecRemainNpc[0].nOnlyID;
}
break;
}
}
// 事件完成
onEventDone(step: any) {
let task: Task = TaskConfigMgr.shared.getTaskConf(this.nTaskID);
let vecPrize = task.vecEvent[step].vecPrize;
let playerList: Player[];
if (TaskConfigMgr.shared.isTeamTask(this.nTaskID) && this.player.isleader) {
playerList = TeamMgr.shared.getTeamPlayer(this.player.teamid);
} else {
playerList = [this.player];
}
for (let key in playerList) {
let member: Player = playerList[key];
if (member == null || member.getTaskMgr() == null || member.pause == 1) {
continue;
}
if (task.nKind == ETaskKind.FUBEN && member.getTaskMgr().GetFuBenCnt(this.nTaskID) > step) {
member.send('s2c_notice', {
strRichText: '此关卡已完成,无法再次获得任务奖励'
});
SKLogger.debug(`玩家[${member.roleid}:${member.name}][${this.nTaskID}:${task.strTaskName}]步骤[${step}]此关卡已完成,无法再次获得任务奖励,跳过`);
continue;
}
let list: any = [];
for (let it in vecPrize) {
if (task.nKind == ETaskKind.DAILY && member.getTaskMgr().getKindTaskCnt(task.nTaskGrop) >= TaskConfigMgr.shared.getDailyMaxCount(task.nTaskGrop)) {
let flag = list.indexOf(member.roleid);
if (flag == -1){
member.send('s2c_notice', {
strRichText: `您的任务[${task.strTaskName}]已完成,本次无法获得任务奖励!`
});
list.push(member.roleid);
SKLogger.debug(`玩家[${member.roleid}:${member.name}][${this.nTaskID}:${task.strTaskName}]已完成,本次无法获得任务奖励!`);
}
continue;
}
if (vecPrize[it].nKey == 'exp') {
let exp = parseInt(vecPrize[it].nValue);
if(task.nTaskGrop == 2){
member.addMoney(GameUtil.goldKind.bang_Score,500,'帮派任务');
member.send('s2c_you_money', {
nKind: GameUtil.goldKind.bang_Score,
nNum: member.bangscore,
nChange: 500
});
}
if(task.nTaskGrop == 3){
member.addMoney(GameUtil.goldKind.shi_Score,500,'师门任务');
member.send('s2c_you_money', {
nKind: GameUtil.goldKind.shi_Score,
nNum: member.shiscore,
nChange: 500
});
}
if(task.nTaskGrop == 9){
member.addMoney(GameUtil.goldKind.di_Score,500,'地宫任务');
member.send('s2c_you_money', {
nKind: GameUtil.goldKind.di_Score,
nNum: member.discore,
nChange: 500
});
}
if(task.nTaskGrop == 8 || task.nTaskGrop == 12){
member.addMoney(GameUtil.goldKind.xiu_Score,500,'修罗');
member.send('s2c_you_money', {
nKind: GameUtil.goldKind.xiu_Score,
nNum: member.xiuscore,
nChange: 500
});
}
if(member.doublecnt > 0 && (task.nTaskGrop == 6 || task.nTaskGrop == 7)){
exp = exp * 2;
}
if(member.isleader){
exp = exp + exp * 0.1;
member.send_notice("队长额外获得10%经验加成")
}
member.addExp(exp);
} else if (vecPrize[it].nKey == 'petexp') {
if (member.curPet) {
let nExp = parseInt(vecPrize[it].nValue);
if (nExp > 0) {
member.curPet.addExp(nExp);
}
}
}
if(member.getTaskMgr().getKindTaskCnt(task.nTaskGrop) < TaskConfigMgr.shared.getDailyMaxCount(task.nTaskGrop)){
if (vecPrize[it].nKey == 'exp') {
continue;
} else if (vecPrize[it].nKey == 'petexp') {
continue;
} else if (vecPrize[it].nKey == 'money') {
member.addMoney(GameUtil.goldKind.Money, parseInt(vecPrize[it].nValue), '任务奖励');
} else if (vecPrize[it].nKey == 'jade') {
member.addMoney(GameUtil.goldKind.Jade, parseInt(vecPrize[it].nValue), '任务奖励');
} else if (vecPrize[it].nKey == 'item') {
member.addItem(parseInt(vecPrize[it].nValue), 1, true);
}
else if (vecPrize[it].nKey == 'active') {
member.getTaskMgr().AddActive(this.getThisTaskActiveScoreKind(), parseFloat(vecPrize[it].nValue));
} else {
member.addItem(vecPrize[it].nKey, vecPrize[it].nValue, true, '任务奖励');
}
}
}
}
this.vecEventState[step].nState = ETaskState.DONE;
if (this.nKind == ETaskKind.FUBEN) {
if (this.player.getTaskMgr()) {
let nCurStep = GameUtil.getDefault(this.player.getTaskMgr().mapFuBenCnt[this.nTaskID], 0);
this.player.getTaskMgr().mapFuBenCnt[this.nTaskID] = Math.max(nCurStep, parseInt(step) + 1);
}
}
SKLogger.debug(`玩家[${this.player.roleid}:${this.player.name}]完成任务[${this.nTaskID}:${task.strTaskName}]步骤[${step}]`);
}
getThisTaskActiveScoreKind(): number {
let task: Task = TaskConfigMgr.shared.getTaskConf(this.nTaskID);
if (task == null) {
return 0;
}
if (task.nKind == ETaskKind.DAILY) {
return task.nTaskGrop;
}
if (task.nKind == ETaskKind.FUBEN) {
return task.nTaskID;
}
return 0;
}
TaskOnFialEvent(nEventType: any, stData: any): boolean {
for (let it in this.vecFailEvent) {
if (this.vecFailEvent[it].nEventType != nEventType)
continue;
let pInfo = TaskConfigMgr.shared.GetFailEventInfo(this.nTaskID, it);
if (null == pInfo)
continue;
if (this.vecFailEvent[it].nEventType == EEventType.PLAYER_DEAD) {
this.vecFailEvent[it].nDeadCnt += 1;
if (this.vecFailEvent[it].nDeadCnt >= pInfo.nDeadCnt) {
this.nTaskFinish = ETaskState.FALIED;
return true;
}
}
if (this.vecFailEvent[it].nEventType == EEventType.TIMEOUT) {
if (stData - this.vecFailEvent[it].nStartTime > pInfo.nMaxTime) {
this.nTaskFinish = ETaskState.FALIED;
return true;
}
}
}
return false;
}
//获取任务信息及进度
getTaskStepByNpcOnlyid(npcOnlyid: number) {
for (let it in this.vecEventState) {
if (this.vecEventState[it].nEventType == EEventType.PLAYER_KILL_NPC) {
for (let nIndex in this.vecEventState[it].vecRemainNpc) {
if (this.vecEventState[it].vecRemainNpc[nIndex].nOnlyID == npcOnlyid) {
return it;
}
}
}
}
return null;
}
// 游戏任务事件
taskOnGameEvent(nEventType: EEventType, data: any): boolean {
let stepChange = false;
for (let key in this.vecEventState) {
let taskState: EventStateBase = this.vecEventState[key];
if (taskState.nState != ETaskState.DOING) {
continue;
}
if (taskState.nEventType != nEventType) {
continue;
}
if (taskState.nEventType == EEventType.PLAYER_TALK_NPC && data.nTaskID == this.nTaskID && data.nStep == key) {
let temp: TalkEventState = <TalkEventState>taskState;
this.onEventDone(key);
stepChange = true;
} else if (taskState.nEventType == EEventType.PLAYER_GATHER_NPC) {
let temp: GatherNpcState = <GatherNpcState>taskState;
for (let index in this.vecEventState[key].vecRemainNpc) {
if (temp.vecRemainNpc[index].nOnlyID == data) {
temp.vecRemainNpc.splice(index, 1);
stepChange = true;
break;
}
}
if (this.vecEventState[key].vecRemainNpc.length == 0) {
this.onEventDone(key);
stepChange = true;
}
} else if (taskState.nEventType == EEventType.PLAYER_DO_ACITION) {
let temp: ActionAreaEventState = <ActionAreaEventState>taskState;
this.onEventDone(key);
stepChange = true;
} else if (this.vecEventState[key].nEventType == EEventType.PLAYER_ARRIVE_AREA) {
let temp: ArriveAreaState = <ArriveAreaState>taskState;
if (data.mapid == temp.nMap && GameUtil.getDistance({
x: data.x,
y: data.y
}, {
x: temp.nX,
y: temp.nY
}) < 10) {
this.onEventDone(key);
stepChange = true;
}
} else if (taskState.nEventType == EEventType.PLAYER_GIVE_NPC_ITEM) {
let temp: GatherItemToNpcEventState = <GatherItemToNpcEventState>taskState;
this.onEventDone(key);
stepChange = true;
} else if (taskState.nEventType == EEventType.PLAYER_KILL_NPC) {
let temp: KillDynamicNpcState = <KillDynamicNpcState>taskState;
for (let key in temp.vecRemainNpc) {
if (temp.vecRemainNpc[key].nOnlyID == data) {
let index = SKDataUtil.numberBy(key);
temp.vecRemainNpc.splice(index, 1);
stepChange = true;
break;
}
}
if (temp.vecRemainNpc.length == 0) {
this.onEventDone(key);
stepChange = true;
}
}
}
if (stepChange == false) {
return false;
}
this.player.getTaskMgr().bCanAutoFight = 1;
this.reconCurrentEvent();
this.CheckAndFinish();
return true;
}
CheckAndFinish() {
let bAllOK = true;
for (let it in this.vecEventState) {
if (this.vecEventState[it].nState != ETaskState.DONE) {
bAllOK = false;
break;
}
}
if (bAllOK == true) {
this.nTaskFinish = ETaskState.DONE;
}
return bAllOK;
}
}