From fd569f371890909dc35c09d1275d9204b39d77f9 Mon Sep 17 00:00:00 2001
From: hxp <ale99527@vip.qq.com>
Date: 星期五, 19 四月 2024 11:41:09 +0800
Subject: [PATCH] 10054 【后端】任务系统(支持功能开启任务条件;支持任务分组如主线、支线等;)

---
 ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/Player/PlayerTask.py |  221 +++++++++++++++++++++++++++++++++++++-----------------
 1 files changed, 150 insertions(+), 71 deletions(-)

diff --git a/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/Player/PlayerTask.py b/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/Player/PlayerTask.py
index ace7d8a..40b36eb 100644
--- a/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/Player/PlayerTask.py
+++ b/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/Player/PlayerTask.py
@@ -9,7 +9,7 @@
 # @date 2023-12-20
 # @version 1.0
 #
-# 详细描述: 玩家任务,简化版任务,有且仅有一个进行中的任务
+# 详细描述: 玩家任务
 #
 #-------------------------------------------------------------------------------
 #"""Version = 2023-12-20 12:30"""
@@ -22,38 +22,39 @@
 import ChPyNetSendPack
 import ItemControler
 import IPY_GameWorld
+import GameFuncComm
 import ShareDefine
 import ChConfig
 
 def OnPlayerLogin(curPlayer):
-    __giveNewTask(curPlayer)
-    SyncTaskInfo(curPlayer)
+    if not __giveNewTask(curPlayer, ChConfig.TaskGroup_Main):
+        SyncTaskInfo(curPlayer)
     return
 
-def __giveNewTask(curPlayer):
+def __giveNewTask(curPlayer, taskGroup=ChConfig.TaskGroup_Main):
     ## 给新任务
-    taskIDList = GetTaskIDList()
+    taskIDList = GetTaskIDList(taskGroup)
     if not taskIDList:
         return
     playerID = curPlayer.GetPlayerID()
-    taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID)
-    lastTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskIDLast)
+    taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+    lastTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskIDLast % taskGroup)
     newTaskID = 0
     if not taskID and not lastTaskID:
         newTaskID = taskIDList[0]
-        GameWorld.DebugLog("给第一个任务: newTaskID=%s" % (newTaskID), playerID)
+        GameWorld.DebugLog("给第一个任务: taskGroup=%s,newTaskID=%s" % (taskGroup, newTaskID), playerID)
         
     elif not taskID and lastTaskID:
         # 没有当前任务,给下一个任务
         if lastTaskID not in taskIDList:
-            GameWorld.ErrLog("找不到上一次完成的任务ID! lastTaskID=%s" % lastTaskID, playerID)
+            GameWorld.ErrLog("找不到上一次完成的任务ID! taskGroup=%s,lastTaskID=%s" % (taskGroup, lastTaskID), playerID)
             return
         lastIndex = taskIDList.index(lastTaskID)
         if lastIndex >= len(taskIDList) - 1:
-            GameWorld.DebugLog("已经完成了所有任务: lastTaskID=%s" % (lastTaskID), playerID)
+            GameWorld.DebugLog("已经完成了所有任务: lastTaskID=%s,lastTaskID=%s" % (lastTaskID, lastTaskID), playerID)
             return
         newTaskID = taskIDList[lastIndex + 1]
-        GameWorld.DebugLog("给下一个任务: newTaskID=%s,lastTaskID=%s" % (newTaskID, lastTaskID), playerID)
+        GameWorld.DebugLog("给下一个任务: lastTaskID=%s,newTaskID=%s,lastTaskID=%s" % (lastTaskID, newTaskID, lastTaskID), playerID)
         
     if not newTaskID:
         return
@@ -62,7 +63,6 @@
         return
     taskType = ipyData.GetTaskType()
     conds = ipyData.GetTaskConds()
-    needValue = ipyData.GetNeedValue()
     taskValue = 0
     
     if taskType == ChConfig.TaskType_LV:
@@ -74,102 +74,181 @@
         grade = GameWorld.GetDictValueByBit(curPlayer, ChConfig.Def_Player_Dict_PlayerFBStar_MapId, lineID, False, [mapID])
         taskValue = 1 if grade > 0 else 0
         
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskIDLast, taskID)
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskID, newTaskID)
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue, taskValue)
-    GameWorld.DebugLog("接到新任务: newTaskID=%s,taskValue=%s/%s" % (newTaskID, taskValue, needValue), playerID)
-    return
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskID % taskGroup, newTaskID)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue % taskGroup, 0)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskState % taskGroup, ChConfig.TaskState_Doing)
+    GameWorld.DebugLog("接到新任务: taskGroup=%s,newTaskID=%s" % (taskGroup, newTaskID), playerID)
+    return SetTaskValue(curPlayer, ipyData, taskValue)
 
-def GetTaskIDList():
-    ## 获取所有的任务ID列表
-    key = "TaskIDList"
-    taskIDList = IpyGameDataPY.GetConfigEx(key)
-    if not taskIDList:
-        taskIDList = []
+def GetTaskIDList(taskGroup):
+    ## 获取某个任务分组所有任务ID列表
+    key = "TaskIDListDict"
+    taskIDListDict = IpyGameDataPY.GetConfigEx(key)
+    if not taskIDListDict:
+        taskIDListDict = {}
         ipyDataMgr = IpyGameDataPY.IPY_Data()
         for index in xrange(ipyDataMgr.GetTaskCount()):
             ipyData = ipyDataMgr.GetTaskByIndex(index)
-            taskIDList.append(ipyData.GetTaskID())
-        IpyGameDataPY.SetConfigEx(key, taskIDList)
-        GameWorld.Log("任务ID列表: %s" % taskIDList)
-    return taskIDList
+            taskGroup = ipyData.GetTaskGroup()
+            taskID = ipyData.GetTaskID()
+            if taskGroup not in taskIDListDict:
+                taskIDListDict[taskGroup] = []
+            taskIDList = taskIDListDict[taskGroup]
+            if taskID not in taskIDList:
+                taskIDList.append(taskID)
+        IpyGameDataPY.SetConfigEx(key, taskIDListDict)
+        GameWorld.Log("任务ID列表: %s" % taskIDListDict)
+    return taskIDListDict.get(taskGroup, [])
 
-def UpdTaskValue(curPlayer, taskType, setValue):
+def UpdTaskValue(curPlayer, taskType, setValue, conds=None):
     ## 更新任务进度
-    taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID)
-    if not taskID:
-        return
-    ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
-    if not ipyData:
-        return
-    if ipyData.GetTaskType() != taskType:
-        return
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue, setValue)
-    SyncTaskInfo(curPlayer)
-    GameWorld.DebugLog("更新任务进度: taskType=%s,taskID=%s,setValue=%s" % (taskType, taskID, setValue), curPlayer.GetPlayerID())
+    for taskGroup in ChConfig.TaskGroupList:
+        taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+        if not taskID:
+            continue
+        ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
+        if not ipyData:
+            continue
+        if ipyData.GetTaskType() != taskType:
+            continue
+        if not __CheckTaskCondition(ipyData, conds):
+            continue
+        SetTaskValue(curPlayer, ipyData, setValue)
     return
 
-def AddTaskValue(curPlayer, taskType, addValue=1, conds=[]):
+def AddTaskValue(curPlayer, taskType, addValue=1, conds=None):
     ## 增加任务进度
-    taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID)
-    if not taskID:
-        return
-    ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
-    if not ipyData:
-        return
-    if ipyData.GetTaskType() != taskType:
-        return
+    for taskGroup in ChConfig.TaskGroupList:
+        taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+        if not taskID:
+            continue
+        ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
+        if not ipyData:
+            continue
+        if ipyData.GetTaskType() != taskType:
+            continue
+        if not __CheckTaskCondition(ipyData, conds):
+            continue
+        curValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue % taskGroup) + addValue
+        SetTaskValue(curPlayer, ipyData, curValue)
+    return
+
+def __CheckTaskCondition(ipyData, conds=None):
+    ## 检查任务条件是否满足
+    taskType = ipyData.GetTaskType()
     if taskType == ChConfig.TaskType_FBPass:
         taskConds = ipyData.GetTaskConds()
-        if len(conds) != 2 or len(taskConds) != 2:
+        if not conds or len(conds) != 2 or len(taskConds) != 2:
             return
         if conds[0] != taskConds[0]:
             return
         if conds[1] < taskConds[1]:
             return
-    finishNeedValue = ipyData.GetNeedValue()
-    curValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue)
-    if curValue >= finishNeedValue:
+        
+    return True
+
+def SetTaskValue(curPlayer, taskIpyData, value=0):
+    ## 设置当前任务进度值,统一处理任务状态、触发额外逻辑等
+    if not taskIpyData:
         return
-    updValue = min(curValue + addValue, ShareDefine.Def_UpperLimit_DWord)
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue, updValue)
-    SyncTaskInfo(curPlayer)
-    GameWorld.DebugLog("增加任务进度: taskType=%s,taskID=%s,addValue=%s,updValue=%s" % (taskType, taskID, addValue, updValue), curPlayer.GetPlayerID())
+    playerID = curPlayer.GetPlayerID()
+    taskGroup = taskIpyData.GetTaskGroup()
+    taskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+    if taskIpyData.GetTaskID() != taskID:
+        return
+    curState = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskState % taskGroup)
+    if curState == ChConfig.TaskState_Finish:
+        return
+    taskType = taskIpyData.GetTaskType()
+    finishNeedValue = taskIpyData.GetNeedValue()
+    value = min(value, finishNeedValue, ShareDefine.Def_UpperLimit_DWord)
+    GameWorld.DebugLog("更新任务进度: taskGroup=%s,taskType=%s,taskID=%s,value=%s/%s" 
+                       % (taskGroup, taskType, taskID, value, finishNeedValue), playerID)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue % taskGroup, value)
+    if value >= finishNeedValue:
+        __OnTaskFinish(curPlayer, taskGroup, taskID, taskIpyData)
+        
+    SyncTaskInfo(curPlayer, taskGroup)
+    return True
+
+def __OnTaskFinish(curPlayer, taskGroup, taskID, taskIpyData):
+    GameWorld.DebugLog("任务完成: taskGroup=%s,taskID=%s" % (taskGroup, taskID), curPlayer.GetPlayerID())
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskState % taskGroup, ChConfig.TaskState_Finish)
+    GameFuncComm.DoFuncOpenLogic(curPlayer, [taskID])
     return
+
+def IsTaskFinish(curPlayer, taskID):
+    ## 任务是否已完成
+    ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
+    if not ipyData:
+        return
+    taskGroup = ipyData.GetTaskGroup()
+    nowTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+    if nowTaskID and curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskState % taskGroup) == ChConfig.TaskState_Finish:
+        finishTaskID = nowTaskID
+    else:
+        finishTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskIDLast % taskGroup)
+        
+    if taskID == finishTaskID:
+        return True
+    
+    taskIDList = GetTaskIDList(taskGroup)
+    if finishTaskID not in taskIDList or taskID not in taskIDList:
+        return
+    return taskIDList.index(finishTaskID) >= taskIDList.index(taskID)
 
 def GetTaskAward(curPlayer, taskID):
     ## 领取任务奖励
     playerID = curPlayer.GetPlayerID()
-    curTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID)
-    if taskID != curTaskID:
-        GameWorld.DebugLog("非当前任务: curTaskID=%s" % curTaskID, playerID)
-        return
     ipyData = IpyGameDataPY.GetIpyGameData("Task", taskID)
     if not ipyData:
         return
+    taskGroup = ipyData.GetTaskGroup()
+    curTaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+    if taskID != curTaskID:
+        GameWorld.DebugLog("非当前任务: curTaskID=%s" % curTaskID, playerID)
+        return
     needValue = ipyData.GetNeedValue()
     awardItemList = ipyData.GetAwardItemList()
-    curValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue)
-    if curValue < needValue:
-        GameWorld.DebugLog("任务进度不足无法领奖: taskID=%s,curValue=%s < %s" % (taskID, curValue, needValue), playerID)
+    curState = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskState % taskGroup)
+    curValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue % taskGroup)
+    if curState != ChConfig.TaskState_Finish:
+        GameWorld.DebugLog("任务未完成无法领奖: taskID=%s,curValue=%s/%s,curState=%s" % (taskID, curValue, needValue, curState), playerID)
         return
     if not ItemControler.CheckPackSpaceEnough(curPlayer, awardItemList):
         return
     
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskIDLast, taskID)
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskID, 0)
-    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue, 0)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskIDLast % taskGroup, taskID)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskID % taskGroup, 0)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskValue % taskGroup, 0)
+    PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_TaskState % taskGroup, 0)
     
     for itemID, itemCount, isAuctionItem in awardItemList:
         ItemControler.GivePlayerItem(curPlayer, itemID, itemCount, isAuctionItem, [IPY_GameWorld.rptItem])
         
-    __giveNewTask(curPlayer)
-    SyncTaskInfo(curPlayer)
+    if not __giveNewTask(curPlayer, taskGroup):
+        SyncTaskInfo(curPlayer, taskGroup)
     return
 
-def SyncTaskInfo(curPlayer):
+def SyncTaskInfo(curPlayer, taskGroup=None):
+    syncGroupList = [taskGroup] if taskGroup != None else ChConfig.TaskGroupList
+    if not syncGroupList:
+        return
+    
+    taskList = []
+    for taskGroup in syncGroupList:
+        task = ChPyNetSendPack.tagMCTask()
+        task.TaskGroup = taskGroup
+        task.TaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID % taskGroup)
+        task.CurValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue % taskGroup)
+        task.State = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskState % taskGroup)
+        taskList.append(task)
+        
+    if not taskList:
+        return
+    
     clientPack = ChPyNetSendPack.tagMCTaskInfo()
-    clientPack.TaskID = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskID)
-    clientPack.CurValue = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_TaskValue)
+    clientPack.TaskList = taskList
+    clientPack.TaskCount = len(clientPack.TaskList)
     NetPackCommon.SendFakePack(curPlayer, clientPack)
     return

--
Gitblit v1.8.0