93 lines
3.1 KiB
Markdown
93 lines
3.1 KiB
Markdown
|
|
## 主线任务完成卷 (贡献者: Trim)
|
|||
|
|
|
|||
|
|
> 首先我们先在dp_s文件夹中建立一个项目文件夹 MyProject 方便管理
|
|||
|
|
|
|||
|
|

|
|||
|
|
|
|||
|
|
> 然后我们建立一个新文件 主线任务完成卷.nut 用于编写我们的代码
|
|||
|
|
|
|||
|
|

|
|||
|
|
|
|||
|
|
> 然后我们在主线任务完成卷.nut中写入以下代码
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
//本例子由 Trim 提供
|
|||
|
|
|
|||
|
|
|
|||
|
|
|
|||
|
|
//主线任务完成卷ID
|
|||
|
|
CrossoverId <- 7577;
|
|||
|
|
|
|||
|
|
Cb_Use_Item_Sp_Func[CrossoverId] <- function(SUser, ItemId) {
|
|||
|
|
// 不需要完成的任务ID数组
|
|||
|
|
local skippedQuestIDs = [674]; //将不要清理的任务ID写入数组内即可
|
|||
|
|
|
|||
|
|
// 获取角色任务信息和等级
|
|||
|
|
local userQuest = SUser.GetQuest();
|
|||
|
|
local questIsClear = NativePointer(userQuest).add(4);
|
|||
|
|
local characLevel = SUser.GetCharacLevel();
|
|||
|
|
local allClearQuest = 0;
|
|||
|
|
|
|||
|
|
// 获取 pvf 数据
|
|||
|
|
local DataManager = Sq_CallFunc(S_Ptr("0x80CC19B"), "pointer", []);
|
|||
|
|
|
|||
|
|
// 判断任务是否需要跳过
|
|||
|
|
function shouldSkip(questID) {
|
|||
|
|
return skippedQuestIDs.find(questID) != null;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 判断任务是否为主线并且角色等级符合要求
|
|||
|
|
function isMainQuestAndLevelValid(pvfQuest, characLevel) {
|
|||
|
|
local questGrade = NativePointer(pvfQuest).add(8).readInt();
|
|||
|
|
local questLv = NativePointer(pvfQuest).add(0x20).readInt();
|
|||
|
|
return questGrade == 0 && questLv <= characLevel;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 判断任务是否已完成
|
|||
|
|
function isQuestCleared(questID) {
|
|||
|
|
return Sq_CallFunc(S_Ptr("0x808BAE0"), "bool", ["pointer", "int"], questIsClear.C_Object, questID);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 设置任务为已完成
|
|||
|
|
function clearQuest(questID) {
|
|||
|
|
Sq_CallFunc(S_Ptr("0x808BA78"), "int", ["pointer", "int"], questIsClear.C_Object, questID);
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 循环处理任务
|
|||
|
|
for (local questID = 1; questID< 30000; questID++) {
|
|||
|
|
// 从 pvf 中获取任务数据
|
|||
|
|
local pvfQuest = Sq_CallFunc(S_Ptr("0x835FDC6"), "pointer", ["pointer", "int"], DataManager, questID);
|
|||
|
|
if (!pvfQuest || shouldSkip(questID)) continue; // 跳过空任务或不需要完成的任务
|
|||
|
|
|
|||
|
|
// 判断是否为主线任务且等级符合要求
|
|||
|
|
if (!isMainQuestAndLevelValid(pvfQuest, characLevel)) continue;
|
|||
|
|
|
|||
|
|
// 判断任务是否已完成,若未完成则清理任务
|
|||
|
|
if (!isQuestCleared(questID)) {
|
|||
|
|
clearQuest(questID);
|
|||
|
|
allClearQuest++;
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
|
|||
|
|
local Pack = Packet();
|
|||
|
|
//通知客户端刷新任务列表
|
|||
|
|
Sq_CallFunc(S_Ptr("0x86ABBA8"), "int", ["pointer", "pointer"], userQuest, Pack.C_Object);
|
|||
|
|
SUser.Send(Pack);
|
|||
|
|
Pack.Delete();
|
|||
|
|
|
|||
|
|
// 发送通知
|
|||
|
|
SUser.SendNotiPacketMessage("已清理:" + allClearQuest + "个主线任务!", 8);
|
|||
|
|
}
|
|||
|
|
```
|
|||
|
|
|
|||
|
|

|
|||
|
|
|
|||
|
|
> 最后我们回到dp_s文件夹中,打开Main.nut 加载我们刚才编写的逻辑
|
|||
|
|
|
|||
|
|
```
|
|||
|
|
sq_RunScript("MyProject/主线任务完成卷.nut");
|
|||
|
|
```
|
|||
|
|

|
|||
|
|
|
|||
|
|
> 至此一个简单的主线任务完成卷的逻辑就写完了,然后我们就可以在游戏中使用道具7577来完成主线任务了
|