🎨 PVE文件夹重构,根据BOSS文件进行分包

📝 新增术樱包武将
This commit is contained in:
2026-08-11 15:59:31 +08:00
parent 6735fc2d35
commit 690e55736d
47 changed files with 4439 additions and 2725 deletions
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
+12
View File
@@ -0,0 +1,12 @@
const characters = {
zuoci_shuying: {
sex: "male",
group: "qun",
hp: 3,
skills: ["huashen_shuying", "xinsheng_shuying", "jihun_shuying"],
img: "extension/术樱包/character/images/zuoci_shuying.jpg",
dieAudios: ["ext:术樱包/character/audio/zuoci/zuoci_shuying.mp3"]
},
};
export default characters;
+3
View File
@@ -0,0 +1,3 @@
const characterFilters = {};
export default characterFilters;
+3
View File
@@ -0,0 +1,3 @@
const characterTitles = {};
export default characterTitles;
+3
View File
@@ -0,0 +1,3 @@
const dynamicTranslates = {};
export default dynamicTranslates;
Binary file not shown.

After

Width:  |  Height:  |  Size: 217 KiB

+28
View File
@@ -0,0 +1,28 @@
import characters from "./character.js";
import skills from "./skill.js";
import translates from "./translate.js";
import characterFilters from "./characterFilter.js";
import characterTitles from "./characterTitle.js";
import characterIntros from "./intro.js";
import dynamicTranslates from "./dynamicTranslate.js";
import perfectPairs from "./perfectPairs.js";
import voices from "./voices.js";
import { characterSort, characterSortTranslate } from "./sort.js";
const shuying_character = {
name: "shuYing_character",
connect: true,
character: { ...characters },
characterSort: {
shuYing_character: characterSort,
},
characterFilter: { ...characterFilters },
characterTitle: { ...characterTitles },
dynamicTranslate: { ...dynamicTranslates },
characterIntro: { ...characterIntros },
skill: { ...skills },
perfectPair: { ...perfectPairs },
translate: { ...translates, ...voices, ...characterSortTranslate },
};
export default shuying_character;
+3
View File
@@ -0,0 +1,3 @@
const characterIntros = {};
export default characterIntros;
+3
View File
@@ -0,0 +1,3 @@
const perfectPairs = {};
export default perfectPairs;
+388
View File
@@ -0,0 +1,388 @@
import { lib, game, ui, get, ai, _status } from "../../../noname.js";
const skills = {
huashen_shuying: {
audio: "ext:术樱包/character/audio/zuoci:2",
inherit: "rehuashen",
unique: true,
init(player, skill) {
if (!player.storage.rehuashen) {
player.storage.rehuashen = {
character: [],
choosed: [],
map: {},
};
}
player.storage[skill] = player.storage.rehuashen;
},
async content(event, trigger, player) {
const oldCharacter = player.storage.rehuashen?.current;
const oldSkill = player.storage.rehuashen?.current2;
const transitionKey = "jihun_shuying_transition";
// 单独处理重铸,保留本次实际移除的化身牌信息
if (event.cost_data === "制衡其他化身") {
_status.noclearcountdown = true;
const id = lib.status.videoId++;
const prompt = "化身:选择制衡至多两张武将牌";
const cards = player.storage.rehuashen.character;
if (player.isOnline2()) {
player.send(
(cards, prompt, id) => {
const dialog = ui.create.dialog(
prompt,
[cards, lib.skill.rehuashen.$createButton]
);
dialog.videoId = id;
},
cards,
prompt,
id
);
}
const dialog = ui.create.dialog(
prompt,
[cards, lib.skill.rehuashen.$createButton]
);
dialog.videoId = id;
if (!event.isMine()) {
dialog.style.display = "none";
}
const result = await player
.chooseButton(true)
.set("dialog", id)
.set("selectButton", [1, 2])
.set(
"filterButton",
button => button.link !== get.event().current
)
.set("current", player.storage.rehuashen.current)
.forResult();
if (player.isOnline2()) {
player.send("closeDialog", id);
}
dialog.close();
delete _status.noclearcountdown;
if (!_status.noclearcountdown) {
game.stopCountChoose();
}
const removedCharacters = result.links || [];
lib.skill.rehuashen.removeHuashen(
player,
removedCharacters
);
if (
player.storage.jihun_shuying_retainedCharacter &&
removedCharacters.includes(
player.storage.jihun_shuying_retainedCharacter
)
) {
delete player.storage.jihun_shuying_retained;
delete player.storage.jihun_shuying_retainedCharacter;
delete player.storage.jihun_shuying_ignoredEvents;
await player.removeAdditionalSkills(
"jihun_shuying_retained"
);
}
lib.skill.rehuashen.addHuashens(
player,
removedCharacters.length
);
player.storage.huashen_shuying =
player.storage.rehuashen;
player.syncStorage("huashen_shuying");
player.updateMarks("huashen_shuying");
return;
}
// 切换前为当前技能增加临时所有权。官方化身移除旧来源时,
// getRemovableAdditionalSkills 会因此保留技能本体及全部状态。
const protectOldSkill = Boolean(
oldSkill && player.hasSkill("jihun_shuying")
);
if (
protectOldSkill &&
!player.additionalSkills[transitionKey]?.includes(oldSkill)
) {
if (!Array.isArray(player.additionalSkills[transitionKey])) {
player.additionalSkills[transitionKey] = [];
}
player.additionalSkills[transitionKey].push(oldSkill);
game.broadcast(
(player, map) => {
player.additionalSkills = map;
},
player,
player.additionalSkills
);
_status.event.clearStepCache();
}
await lib.skill.rehuashen.content(event, trigger, player);
const storage = player.storage.rehuashen;
const changed = Boolean(
oldSkill &&
(
oldCharacter !== storage?.current ||
oldSkill !== storage?.current2
)
);
if (
changed &&
player.hasSkill("jihun_shuying")
) {
// 过渡来源会阻止官方流程物理移除旧技能,因此这里仅删除
// rehuashen 对旧技能的映射,不触发 removeSkill/onremove。
if (
oldSkill !== storage.current2 &&
player.additionalSkills.rehuashen?.includes(oldSkill)
) {
player.$removeAdditionalSkills("rehuashen", oldSkill);
_status.event.clearStepCache();
}
// 新的当前技能已经登记完毕后,再结束上一次羁魂保留。
if (player.additionalSkills.jihun_shuying_retained) {
await player.removeAdditionalSkills(
"jihun_shuying_retained"
);
}
delete player.storage.jihun_shuying_retained;
delete player.storage.jihun_shuying_retainedCharacter;
delete player.storage.jihun_shuying_ignoredEvents;
player.logSkill("jihun_shuying");
if (oldSkill && oldSkill !== storage.current2) {
const ignoredEvents = player
.getAllHistory("useSkill", history => {
return get.sourceSkillFor(history) === oldSkill;
})
.map(history => history.event)
.filter(Boolean);
let currentEvent = _status.event;
while (currentEvent) {
const eventSkill = currentEvent.sourceSkill ||
currentEvent.skill ||
(lib.skill[currentEvent.name] ? currentEvent.name : null);
if (
eventSkill &&
get.sourceSkillFor(eventSkill) === oldSkill &&
!ignoredEvents.includes(currentEvent)
) {
ignoredEvents.push(currentEvent);
}
currentEvent = currentEvent.parent;
}
player.storage.jihun_shuying_retained = oldSkill;
player.storage.jihun_shuying_retainedCharacter =
oldCharacter;
player.storage.jihun_shuying_ignoredEvents = ignoredEvents;
// 此时 oldSkill 仍由过渡键持有,增加羁魂来源不会重新
// 初始化技能,也不会影响牌、标记和 storage。
const retainedKey = "jihun_shuying_retained";
if (!Array.isArray(player.additionalSkills[retainedKey])) {
player.additionalSkills[retainedKey] = [];
}
if (!player.additionalSkills[retainedKey].includes(oldSkill)) {
player.additionalSkills[retainedKey].push(oldSkill);
}
game.broadcast(
(player, map) => {
player.additionalSkills = map;
},
player,
player.additionalSkills
);
_status.event.clearStepCache();
}
}
// 最终所有权建立完毕后再撤销过渡来源。
if (player.additionalSkills[transitionKey]) {
await player.removeAdditionalSkills(transitionKey);
}
player.storage.huashen_shuying = storage;
player.syncStorage("huashen_shuying");
player.updateMarks("huashen_shuying");
},
onremove(player) {
player.removeAdditionalSkill("rehuashen");
player.removeAdditionalSkill("jihun_shuying_retained");
player.removeAdditionalSkill("jihun_shuying_transition");
delete player.storage.rehuashen;
delete player.storage.huashen_shuying;
delete player.storage.jihun_shuying_retained;
delete player.storage.jihun_shuying_retainedCharacter;
delete player.storage.jihun_shuying_ignoredEvents;
},
ai: {
threaten: 2,
},
},
xinsheng_shuying: {
audio: "ext:术樱包/character/audio/zuoci:2",
unique: true,
trigger: {
player: "damageEnd",
},
filter(event, player) {
return event.num > 0 &&
player.hasSkill("huashen_shuying") &&
player.storage.rehuashen;
},
async cost(event, trigger, player) {
const controls = ["获得一张新化身"];
if (player.storage.rehuashen.character?.length) {
controls.push("更换所展示的化身");
}
controls.push("cancel2");
const result = await player
.chooseControl(controls)
.set("prompt", get.prompt(event.skill))
.set("prompt2", "获得一张新化身牌,或更换所展示的化身牌")
.set("ai", () => {
const player = get.player();
const controls = get.event().controls;
if (!controls.includes("更换所展示的化身")) {
return "获得一张新化身";
}
const storage = player.storage.rehuashen;
const currentRank = storage.current2 ?
get.skillRank(storage.current2, "in") : 0;
const skills = storage.character
.flatMap(name => storage.map[name] || [])
.unique();
const bestRank = skills.reduce((max, skill) => {
return Math.max(max, get.skillRank(skill, "in"));
}, 0);
if (bestRank > currentRank + 1) {
return "更换所展示的化身";
}
return "获得一张新化身";
})
.forResult();
event.result = {
bool: result.control !== "cancel2",
cost_data: result.control,
};
},
async content(event, trigger, player) {
if (event.cost_data === "获得一张新化身") {
lib.skill.rehuashen.addHuashens(player, 1);
player.storage.huashen_shuying = player.storage.rehuashen;
player.syncStorage("huashen_shuying");
player.updateMarks("huashen_shuying");
return;
}
const next = game.createEvent("huashen_shuying_change");
next.player = player;
next.skill = "huashen_shuying";
next.cost_data = "替换当前化身";
next.setContent(lib.skill.huashen_shuying.content);
await next;
},
ai: {
combo: "huashen_shuying",
maixie: true,
maixie_hp: true,
effect: {
target(card, player, target) {
if (
get.tag(card, "damage") &&
target.hasSkill("huashen_shuying")
) {
return [1, 0.7];
}
},
},
},
},
jihun_shuying: {
audio: "ext:术樱包/character/audio/zuoci:2",
locked: true,
group: "jihun_shuying_clear",
onremove(player) {
player.removeAdditionalSkill("jihun_shuying_retained");
player.removeAdditionalSkill("jihun_shuying_transition");
delete player.storage.jihun_shuying_retained;
delete player.storage.jihun_shuying_retainedCharacter;
delete player.storage.jihun_shuying_ignoredEvents;
},
ai: {
combo: "huashen_shuying",
},
subSkill: {
clear: {
charlotte: true,
silent: true,
lastDo: true,
priority: -Infinity,
trigger: {
player: [
"useSkillAfter",
"useCardAfter",
"respondAfter",
"triggerAfter",
"skillAfter",
],
},
hookTrigger: {
after(event, player) {
const retained =
player.storage.jihun_shuying_retained;
return Boolean(
retained &&
event.skill &&
get.sourceSkillFor(event.skill) === retained
);
},
},
filter(event, player) {
const retained =
player.storage.jihun_shuying_retained;
if (
!retained ||
!event.skill ||
get.sourceSkillFor(event.skill) !== retained
) {
return false;
}
const ignoredEvents =
player.storage.jihun_shuying_ignoredEvents || [];
return !ignoredEvents.includes(event);
},
async content(event, trigger, player) {
delete player.storage.jihun_shuying_retained;
delete player.storage.jihun_shuying_retainedCharacter;
delete player.storage.jihun_shuying_ignoredEvents;
await player.removeAdditionalSkills(
"jihun_shuying_retained"
);
},
},
},
},
};
export default skills;
+4
View File
@@ -0,0 +1,4 @@
const characterSort = {};
const characterSortTranslate = {};
export { characterSort, characterSortTranslate };
+11
View File
@@ -0,0 +1,11 @@
const translates = {
zuoci_shuying: "术左慈",
huashen_shuying: "化身",
huashen_shuying_info: "游戏开始时,你随机获得三张未加入游戏的武将牌,选一张置于你面前并声明该武将的一项技能,你拥有该技能且同时将性别和势力属性变为与该武将相同,直到该化身被替换。回合开始时或结束时,你可以选择一项:①弃置至多两张未展示的化身并重新获得等量化身;②更换所展示的化身牌或技能。(你不可以声明限定技、觉醒技、隐匿技、使命技、主公技等特殊技能)",
xinsheng_shuying: "新生",
xinsheng_shuying_info: "若你拥有技能〖化身〗,当你受到伤害后,你可以选择一项:①获得一张新化身牌;②更换所展示的化身牌。",
jihun_shuying: "羁魂",
jihun_shuying_info: "若你拥有技能〖化身〗,当你更换所展示的化身牌或技能时,保留上次声明的技能,直至该技能下次触发、再次更换所展示的化身牌或技能、重铸该技能对应的化身牌。",
};
export default translates;
+3
View File
@@ -0,0 +1,3 @@
const voices = {};
export default voices;