import { lib, game, ui, get, ai, _status } from "../../noname.js";
/** @type { importCharacterConfig['skill'] } */
const skills = {
//李丰
dctunchu: {
audio: 2,
/*
trigger: { global: "gameDrawBegin" },
forced: true,
content() {
const me = player,
numx = trigger.num;
const sum = game.players.slice().concat(game.dead).length * 4;
trigger.num = function (player) {
return player == me ? sum : typeof numx == "function" ? numx(player) : numx;
};
},
*/
trigger: {
global: "phaseBefore",
player: "enterGame",
},
filter(event, player) {
const sum = game.players.slice().concat(game.dead).length * 4;
return player.countCards("h") < sum && (event.name != "phase" || game.phaseNumber == 0);
},
forced: true,
content() {
player.drawTo(game.players.slice().concat(game.dead).length * 4);
},
mod: {
cardDiscardable(card, player) {
if (get.position(card) == "h") return false;
},
},
group: "dctunchu_limit",
subSkill: {
limit: {
audio: "dctunchu",
trigger: { player: "phaseZhunbeiBegin" },
filter(event, player) {
return player.countCards("h") > player.getHp();
},
forced: true,
content() {
player.addTempSkill("dctunchu_debuff");
player.addMark("dctunchu_debuff", 3, false);
},
},
debuff: {
mark: true,
intro: {
markcount(storage) {
return (storage || 0).toString();
},
content(storage) {
return "还可使用" + (storage || 0).toString() + "张牌";
},
},
charlotte: true,
onremove: true,
trigger: { player: "useCard0" },
filter(event, player) {
return player.hasMark("dctunchu_debuff");
},
forced: true,
popup: false,
firstDo: true,
content() {
player.removeMark("dctunchu_debuff", 1, false);
},
mod: {
cardEnabled(card, player) {
if (player.hasMark("dctunchu_debuff")) return;
if (get.itemtype(card) == "card" && get.position(card) == "h") return false;
if (card.cards && (card.cards || []).some(i => get.position(i) == "h")) return false;
},
cardSavable() {
return lib.skill.dctunchu.subSkill.debuff.mod.cardEnabled.apply(this, arguments);
},
},
},
},
},
dcshuliang: {
audio: 2,
trigger: { global: "phaseEnd" },
filter(event, player) {
return player.countCards("h") && game.hasPlayer(target => !target.countCards("h"));
},
async cost(event, trigger, player) {
const num = Math.min(
player.countCards("h"),
game.countPlayer(target => !target.countCards("h"))
);
let list = [];
while (num - list.length > 0) {
const {
result: { bool, targets, cards },
} = await player
.chooseCardTarget({
prompt: list.length ? "是否继续发动【输粮】?" : get.prompt("dcshuliang"),
prompt2: lib.translate.dcshuliang_info,
position: "h",
animate: false,
filterCard(card, player) {
return !get.event("list").some(list => list[1] == card);
},
filterTarget(card, player, target) {
return !target.countCards("h") && !get.event("list").some(list => list[0] == target);
},
ai1(card) {
if (!ui.selected.targets.length) return false;
const target = ui.selected.targets[0];
if (card.name == "du" && !target.hasSkillTag("nodu") && get.attitude(player, target) < 0) return 200;
if (target.canUse(card, target) && get.attitude(player, target) > 0) return 5 + target.getUseValue(card);
return 1 + Math.random();
},
ai2(target) {
const player = get.event("player"),
att = get.attitude(player, target);
if (
player.hasCard(card => {
return card.name == "du" && !get.event("list").some(list => list[1] == card);
}, "h") &&
!target.countCards("h") &&
!get.event("list").some(list => list[0] == target) &&
!target.hasSkillTag("nodu")
)
return -200 * att;
return att;
},
})
.set("list", list);
if (bool) {
list.push([targets[0], cards[0]]);
player.addGaintag(cards, "olsujian_given");
} else break;
}
event.result = {
bool: Boolean(list.length),
targets: list.slice().map(list => list[0]),
cards: list.slice().map(list => list[1]),
cost_data: list,
};
},
async content(event, trigger, player) {
const list = event.cost_data;
await game
.loseAsync({
gain_list: list,
player: player,
cards: event.cards,
giver: player,
animate: "giveAuto",
})
.setContent("gaincardMultiple");
for (let i = 0; i < list.length; i++) {
const target = event.targets[i],
card = event.cards[i];
if (get.owner(card) == target && get.position(card) == "h" && target.canUse(card, target)) {
await target.chooseUseTarget(card);
}
}
},
},
//吴普
dcduanti: {
audio: 2,
trigger: {
player: ["useCardAfter", "respondAfter"],
},
forced: true,
filter(event, player) {
return event._copdcduanti;
},
onremove: ["dcduanti", "dcduanti_counter"],
group: "dcduanti_counter",
async content(event, trigger, player) {
await player.recover();
if (player.countMark("dcduanti") >= 5) return;
player.addMark("dcduanti", 1, false);
await player.gainMaxHp();
},
subSkill: {
counter: {
trigger: {
player: ["useCard1", "respond"],
},
forced: true,
charlotte: true,
popup: false,
firstDo: true,
async content(event, trigger, player) {
if (!player.countMark("dcduanti_counter")) {
const num = game.getAllGlobalHistory("everything", evt => {
return evt.player === player && ["useCard", "respond"].includes(evt.name) && evt !== trigger;
}).length;
if (num) player.addMark("dcduanti_counter", num, false);
}
player.addMark("dcduanti_counter", 1, false);
if (player.countMark("dcduanti_counter") % 5 === 0) trigger._copdcduanti = true;
player.markSkill("dcduanti");
},
},
},
intro: {
markcount(storage, player) {
return player.countMark("dcduanti_counter");
},
content(storage, player) {
return `
已使用过${get.cnNumber(player.countMark("dcduanti_counter"))}张牌
已以此法增加${player.countMark("dcduanti")}点体力上限`;
},
},
},
dcshicao: {
audio: 2,
enable: "phaseUse",
onremove: ["dcshicao_aiRecord"],
chooseButton: {
dialog(event, player) {
return ui.create.dialog("###识草###选择一种类型与要摸牌的来源", [["basic", "trick", "equip"].map(type => [type, get.translation(type)]), "tdnodes"], [["牌堆顶", "牌堆底"], "tdnodes"]);
},
check(button) {
const player = get.player();
const bottom = player.storage.dcshicao_bottom,
aiStorage = player.getStorage("dcshicao_aiRecord");
if (bottom && aiStorage.length > 0 && get.name(ui.cardPile.lastChild, false) === get.name(aiStorage.lastItem, false)) {
if (button.link === "牌堆底" || button.link === get.type2(aiStorage.lastItem, false)) return 20;
}
if (button.link === "牌堆顶" || button.link === "basic") return 10;
return 5 + Math.random();
},
filter(button, player) {
if (!ui.selected.buttons.length) return true;
return ui.selected.buttons[0].parentNode != button.parentNode;
},
select: 2,
backup(links, player) {
if (links[0].includes("牌堆")) links.reverse();
return {
audio: "dcshicao",
type: links[0],
pos: links[1],
filterCard: () => false,
selectCard: -1,
async content(event, trigger, player) {
let { type, pos } = lib.skill.dcshicao_backup;
game.log(player, "声明了", `#y${get.translation(type)}牌`);
const next = player.draw();
const bottom = pos === "牌堆底";
if (bottom) {
next.set("bottom", true);
if (player.getStorage("dcshicao_aiRecord").length > 0) {
player.storage.dcshicao_aiRecord.pop();
}
}
const drawnCards = await next.forResult();
if (get.type2(drawnCards[0], player) === type) return;
let cards;
if (!bottom) {
cards = get.bottomCards(2);
cards.reverse();
} else cards = get.cards(2);
await game.cardsGotoOrdering(cards);
await player.viewCards(`${bottom ? "牌堆顶" : "牌堆底"}的两张牌(靠左的在牌堆更靠上)`, cards);
player.storage.dcshicao_record = cards.slice();
player.storage.dcshicao_aiRecord = cards.slice();
player.storage.dcshicao_bottom = !bottom;
const func = lib.skill.dctongguan.localMark,
skill = "dcshicao";
if (event.player.isUnderControl(true)) func(skill, player);
else if (event.isOnline()) player.send(func, skill, player);
if (bottom) cards.reverse();
await game.cardsGotoPile(cards, bottom ? "insert" : null);
player.tempBanSkill("dcshicao");
},
ai: {
result: { player: 1 },
},
};
},
prompt(links, player) {
return `点击“确定”,从${links[1]}摸一张牌`;
},
},
intro: {
mark(dialog, content, player) {
var cards = player.getStorage("dcshicao_record");
if (cards && cards.length) {
if (player.isUnderControl(true)) {
dialog.addText(`上一次观看的${player.storage.dcshicao_bottom ? "牌堆底" : "牌堆顶"}的牌:`);
dialog.addAuto(cards);
} else {
return "不给看";
}
}
},
},
subSkill: {
backup: {},
},
ai: {
order: 8,
result: {
player: 1,
},
},
},
//新杀曹爽
dcjianzhuan: {
audio: 2,
trigger: { player: "useCard" },
filter(event, player) {
const evtx = event.getParent("phaseUse");
return (
player.isPhaseUsing() &&
player.getHistory("useSkill", evt => {
return evt.skill == "dcjianzhuan" && evt.event.getParent("phaseUse") == evtx;
}).length <
4 - player.getStorage("dcjianzhuan").length
);
},
forced: true,
derivation: "dcjianzhuan_faq",
async content(event, trigger, player) {
const evtx = event.getParent("phaseUse"),
num = player.getHistory("useSkill", evt => {
return evt.skill == "dcjianzhuan" && evt.event.getParent("phaseUse") == evtx;
}).length,
info = get.info("dcjianzhuan").choices;
let choices = [],
choiceList = [],
map = {};
for (const i in info) {
map[info[i].intro] = i;
if (player.getStorage("dcjianzhuan").includes(i) || player.getStorage("dcjianzhuan_used").includes(i)) continue;
choices.push(info[i].intro);
choiceList.push(info[i].introx(num));
}
const {
result: { control },
} = await player
.chooseControl(choices)
.set("choiceList", choiceList)
.set("ai", () => {
const player = get.event("player"),
num = get.event("num"),
info = get.info("dcjianzhuan").choices;
let choices = get.event("controls").slice(),
map = get.event("map");
return choices.sort((a, b) => info[map[b]].ai_effect(player, num) - info[map[a]].ai_effect(player, num))[0];
})
.set("num", num)
.set("map", map)
.set("prompt", "渐专:请选择一项执行");
if (control) {
if (!player.storage.dcjianzhuan_used) {
player.when("phaseUseAfter").then(() => delete player.storage.dcjianzhuan_used);
}
player.markAuto("dcjianzhuan_used", [map[control]]);
await info[map[control]].content(player, num);
}
},
choices: {
discard_target: {
intro: "拆牌",
introx: num => "令一名角色弃置" + num + "张牌",
weight: 1,
ai_effect(player, num) {
return game.hasPlayer(target => {
return get.effect(target, { name: "guohe_copy2" }, player, player) > 0;
})
? 2 + num
: 0;
},
async content(player, num = 1) {
const {
result: { bool, targets },
} = await player
.chooseTarget("令一名角色弃置" + num + "张牌", true)
.set("ai", target => {
return get.effect(target, { name: "guohe_copy2" }, get.event("player"), get.event("player")) * Math.sqrt(Math.min(get.event("num"), target.countDiscardableCards(target, "he")));
})
.set("num", num);
if (bool) {
const target = targets[0];
player.line(target);
await target.chooseToDiscard(num, "he", true);
}
},
},
draw_self: {
intro: "摸牌",
introx: num => "摸" + num + "张牌",
weight: 1,
ai_effect(player, num) {
return 3;
},
async content(player, num = 1) {
await player.draw(num);
},
},
recast_self: {
intro: "重铸",
introx: num => "重铸" + num + "张牌",
weight: 1,
ai_effect(player, num) {
return 1;
},
async content(player, num = 1) {
if (!player.hasCard(lib.filter.cardRecastable, "he")) return;
const {
result: { bool, cards },
} = await player.chooseCard("重铸" + num + "张牌", "he", num, lib.filter.cardRecastable, true).set("ai", lib.skill.zhiheng.check);
if (bool) await player.recast(cards);
},
},
discard_self: {
intro: "弃牌",
introx: num => "弃置" + num + "张牌",
weight: "90%",
ai_effect(player, num) {
let cards = player.getCards("hs");
cards.sort((a, b) => get.value(b) - get.value(a));
cards = cards.slice(0, -Math.min(num, cards.length));
return cards.some(card => player.hasValueTarget(card, true, true)) ? 4 : -4;
},
async content(player, num = 1) {
await player.chooseToDiscard(num, "he", true);
},
},
},
group: "dcjianzhuan_remove",
subSkill: {
remove: {
audio: "dcjianzhuan",
trigger: { player: "phaseUseEnd" },
filter(event, player) {
if (player.getStorage("dcjianzhuan").length >= 4) return false;
return player.getStorage("dcjianzhuan_used").length >= 4 - player.getStorage("dcjianzhuan").length;
},
forced: true,
async content(event, trigger, player) {
const info = get.info("dcjianzhuan").choices;
let map = {};
let unfixedWeightTotal = 0,
remainedWeight = 100;
let entries = [];
for (const i in info) {
const infox = info[i];
map[infox.intro] = i;
if (player.getStorage("dcjianzhuan").includes(i)) continue;
let weight = (infox.weight || 1).toString();
if (weight.endsWith("%")) {
weight = Math.min(remainedWeight, parseInt(weight.slice(0, -1)));
entries.push([infox.intro, weight]);
remainedWeight -= weight;
} else {
weight = parseInt(weight);
unfixedWeightTotal += weight;
entries.push([infox.intro, -weight]);
}
}
entries = entries.map(entry => {
let weight = entry[1];
if (weight < 0) weight = (-remainedWeight / unfixedWeightTotal) * weight;
return [entry[0], weight];
});
let rand = Math.random() * 100;
let removeChoice = entries.find(entry => {
rand -= entry[1];
return rand < 0;
})[0];
if (get.isLuckyStar(player) && Object.keys(entries).includes("弃牌")) removeChoice = "弃牌";
player.markAuto("dcjianzhuan", [map[removeChoice]]);
player.popup(removeChoice);
game.log(player, "移去了", "#g" + removeChoice, "项");
},
},
},
mark: true,
intro: {
markcount(storage) {
return 4 - (storage || []).length;
},
content(storage) {
if (!(storage || []).length) return "暂未移去任何项";
const info = get.info("dcjianzhuan").choices;
let str = "";
for (const i of storage) {
str += info[i].intro;
str += "、";
}
str = str.slice(0, -1);
return "已移去" + str + "项";
},
},
},
dcfanshi: {
unique: true,
audio: 2,
trigger: { player: "phaseJieshuBegin" },
filter(event, player) {
return 4 - player.getStorage("dcjianzhuan").length < 2;
},
forced: true,
juexingji: true,
skillAnimation: true,
animationColor: "thunder",
async content(event, trigger, player) {
player.awakenSkill("dcfanshi");
const info = get.info("dcjianzhuan").choices;
let choices = [];
for (const i in info) {
if (!player.getStorage("dcjianzhuan").includes(i)) choices.push(i);
}
if (choices.length) {
for (const choice of choices) {
for (let i = 1; i <= 3; i++) {
await info[choice].content(player, 1);
}
}
}
await player.gainMaxHp(2);
await player.recover(2);
await player.changeSkills(["dcfudou"], ["dcjianzhuan"]);
},
derivation: "dcfudou",
ai: {
combo: "dcjianzhuan",
},
},
dcfudou: {
audio: 2,
trigger: { player: "useCardToPlayered" },
filter(event, player) {
if (event.targets.length != 1 || event.target == player) return false;
const color = get.color(event.card);
if (!["black", "red"].includes(color)) return false;
const damage = event.target.getAllHistory("sourceDamage", evt => evt.player == player).length;
return Math.min(1, damage) == (color == "black");
},
check(event, player) {
const color = get.color(event.card);
if (color == "red") return get.attitude(player, event.target) > 0;
if (player.getHp() + player.countCards("hs", card => player.canSaveCard(card, player)) <= 1) return false;
return get.effect(player, { name: "losehp" }, player, player) >= get.effect(event.target, { name: "losehp" }, player, player);
},
prompt2(event, player) {
return "与" + get.translation(event.target) + "各" + (get.color(event.card) == "black" ? "失去1点体力" : "摸一张牌");
},
logTarget: "target",
async content(event, trigger, player) {
const color = get.color(trigger.card),
target = trigger.target;
if (color == "red") {
await player.draw("nodelay");
await target.draw();
} else {
await player.loseHp();
await target.loseHp();
}
},
},
//司马师
dcsanshi: {
audio: 2,
trigger: { global: "roundStart" },
forced: true,
filter(event, player) {
return game.roundNumber === 1;
},
group: ["dcsanshi_gain", "dcsanshi_directHit"],
async content(event, trigger, player) {
const recordedNumbers = [];
let num = get.rand(0, ui.cardPile.childNodes.length - 1);
for (let i = 0; i < ui.cardPile.childNodes.length; i++) {
let j = i + num;
if (j >= ui.cardPile.childNodes.length) j -= ui.cardPile.childNodes.length;
const card = ui.cardPile.childNodes[j],
number = get.number(card, false);
if (!recordedNumbers.includes(number)) {
recordedNumbers.add(number);
card.storage.dcsanshi = true;
num = get.rand(0, ui.cardPile.childNodes.length - 1);
}
}
player.addSkill("dcsanshi_mark");
},
subSkill: {
gain: {
audio: "dcsanshi",
trigger: { global: "phaseEnd" },
filter(event, player) {
return game.hasGlobalHistory("cardMove", evt => {
if (evt.name == "lose") {
if (evt.position !== ui.discardPile) return false;
} else if (evt.name !== "cardsDiscard") return false;
if (lib.skill.dcsanshi_gain.notUseOrRespond(evt, player)) {
return evt.cards.some(card => {
return card.storage.dcsanshi && get.position(card) === "d";
});
}
return false;
});
},
forced: true,
notUseOrRespond(event, player) {
if (event.name !== "cardsDiscard") return true;
const evtx = event.getParent();
if (evtx.name !== "orderingDiscard") return true;
const evt2 = evtx.relatedEvent || evtx.getParent();
return !["useCard", "respond"].includes(evt2.name) || evt2.player !== player;
},
async content(event, trigger, player) {
const cards = [];
game.checkGlobalHistory("cardMove", evt => {
if (evt.name == "lose") {
if (evt.position !== ui.discardPile) return false;
} else if (evt.name !== "cardsDiscard") return false;
if (lib.skill.dcsanshi_gain.notUseOrRespond(evt, player)) {
cards.addArray(
evt.cards.filter(card => {
return card.storage.dcsanshi && get.position(card) === "d";
})
);
}
});
if (cards.length) player.gain(cards, "gain2");
},
},
directHit: {
audio: "dcsanshi",
trigger: { player: "useCard" },
forced: true,
filter(event, player) {
return (
event.cards &&
event.cards.some(card => {
return card.storage.dcsanshi;
})
);
},
async content(event, trigger, player) {
trigger.directHit.addArray(game.filterPlayer());
game.log(trigger.card, "不可被响应");
},
},
mark: {
trigger: {
player: "gainEnd",
global: "loseAsyncEnd",
},
forced: true,
popup: false,
silent: true,
lastDo: true,
filter(event, player) {
if (!["dcsanshi", "dcchenlve"].every(skill => player.hasSkill(skill, null, false, false))) return false;
const cards = event.getg(player);
if (!cards.length) return false;
return cards.some(card => card.storage.dcsanshi);
},
async content(event, trigger, player) {
var cards = trigger.getg(player);
if (cards.length) {
cards = cards.filter(card => card.storage.dcsanshi);
player.addGaintag(cards, "dcsanshi_tag");
}
},
},
},
ai: {
threaten: 3,
},
},
dczhenrao: {
audio: 2,
trigger: { global: "useCardToPlayered" },
filter(event, player) {
if (
(() => {
if (event.player === player) {
if (!event.isFirstTarget) return false;
return event.targets.some(target => target !== player);
}
return event.target === player;
})()
) {
return event.targets.concat(event.player).some(target => {
return target.countCards("h") > player.countCards("h") && !player.getStorage("dczhenrao").includes(target);
});
}
return false;
},
direct: true,
async content(event, trigger, player) {
const result = await player
.chooseTarget(get.prompt("dczhenrao"), "对一名可选角色造成1点伤害", (card, player, target) => {
return get.event("targets").includes(target) && !player.getStorage("dczhenrao").includes(target);
})
.set(
"targets",
trigger.targets.concat(trigger.player).filter(target => target.countCards("h") > player.countCards("h"))
)
.set("ai", target => {
const player = get.player();
return get.damageEffect(target, player, player);
})
.forResult();
if (!result.bool) return;
const target = result.targets[0];
player.logSkill("dczhenrao", target);
await target.damage();
await game.asyncDelayx();
if (!player.storage.dczhenrao) {
player.when({ global: "phaseAfter" }).then(() => player.unmarkSkill("dczhenrao"));
}
player.markAuto("dczhenrao", target);
},
intro: {
content: "已以此法对$造成过伤害",
onunmark: true,
},
ai: {
expose: 0.2,
threaten: 3,
},
},
dcchenlve: {
audio: 2,
enable: "phaseUse",
limited: true,
skillAnimation: true,
animationColor: "thunder",
filterCard: () => false,
selectCard: [-2, -1],
async content(event, trigger, player) {
player.awakenSkill("dcchenlve");
const cards = ["cardPile", "discardPile"].map(pos => Array.from(ui[pos].childNodes)).flat();
const sishiList = [];
const isSishi = card => card.storage.dcsanshi;
const lose_list = [],
players = game.filterPlayer();
players.forEach(current => {
const pos = "ej" + (current === player ? "h" : "");
const sishis = current.getCards(pos, isSishi);
if (sishis.length > 0) {
current.$throw(sishis);
lose_list.push([current, sishis]);
sishiList.addArray(sishis);
}
});
if (lose_list.length) {
await game.loseAsync({ lose_list }).setContent("chooseToCompareLose");
}
sishiList.addArray(cards.filter(isSishi));
if (lose_list.length) await game.asyncDelayx();
player.gain(sishiList, "gain2");
player
.when("phaseEnd")
.filter(evt => evt === event.getParent("phase"))
.vars({
sishiList,
})
.then(() => {
const lose_list = [],
players = game.filterPlayer();
players.forEach(current => {
const cards = current.getCards("hej").filter(card => sishiList.includes(card));
if (cards.length > 0) {
current.$throw(cards);
lose_list.push([current, cards]);
}
});
if (lose_list.length) {
game.loseAsync({ lose_list }).setContent("chooseToCompareLose");
}
})
.then(() => {
game.cardsGotoSpecial(sishiList);
game.log(sishiList, "被移出了游戏");
});
player
.when("die")
.vars({
sishiList,
})
.assign({
forceDie: true,
})
.then(() => {
game.cardsDiscard(sishiList);
game.log(sishiList, "被置入了弃牌堆");
});
},
ai: {
order: 0.5,
result: {
player(player) {
if (player.getHp(true) > 1 && player.countCards("he") > 1) return 0;
if (!player.isDamaged() && (player.countCards("h") > 1 || player.countCards("e") > 0)) return 0;
return 13;
},
},
combo: "dcsanshi",
},
},
//王凌
dcjichou: {
audio: 2,
trigger: { player: "phaseUseEnd" },
filter(event, player) {
const evts = player.getHistory("useCard", evt => evt.getParent("phaseUse") === event);
const names = evts.map(evt => evt.card.name).unique();
return evts.length > 0 && evts.length === names.length && evts.some(evt => evt.cards.some(card => get.position(card) === "d"));
},
async content(event, trigger, player) {
const cards = [];
player.checkHistory("useCard", evt => {
if (evt.getParent("phaseUse") !== trigger) return;
cards.addArray(evt.cards.filterInD("d"));
});
const num = Math.min(cards.length, game.countPlayer());
if (_status.connectMode)
game.broadcastAll(() => {
_status.noclearcountdown = true;
});
const [bool, links] = await player
.chooseButton([`集筹:将${num < cards.length ? "至多" + get.cnNumber(num) + "张牌" : "任意张牌"}交给等量角色`, cards])
.set("selectButton", [1, num])
.set("population", [game.countPlayer(current => get.attitude(player, current) > 0), game.countPlayer(current => get.attitude(player, current) < 0)])
.set("ai", button => {
const card = button.link,
population = get.event("population");
if (ui.selected.buttons.length > population[0] + population[1]) return 0;
if (ui.selected.buttons.length > get.event("population")[0]) return 2 - get.value(card);
return 2 + get.value(card);
})
.forResult("bool", "links");
if (bool) {
const [bool, targets] = await player
.chooseTarget(`集筹:请选择${get.cnNumber(links.length)}名角色`, `操作提示:请按照顺序选择要交给牌的目标,令这些角色按顺序获得这些牌:${get.translation(links)}`, true, links.length)
.set(
"values",
links.map(i => get.value(i))
)
.set("ai", target => {
const att = get.attitude(get.player(), target);
const chosenNum = ui.selected.targets.length,
values = get.event("values");
if (values[chosenNum] > 0) return att;
return 0.01 - att;
})
.forResult("bool", "targets");
if (_status.connectMode) {
game.broadcastAll(() => {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
if (bool) {
const gain_list = [],
givenCards = [];
targets.forEach((target, i) => {
player.line(target, "green");
gain_list.push([target, links[i]]);
givenCards.push(links[i]);
game.log(player, "将", links[i], "交给了", target);
});
event.getParent().set("givenCards", givenCards);
await game
.loseAsync({
gain_list,
player: player,
cards: givenCards,
giver: player,
animate: "gain2",
})
.setContent("gaincardMultiple");
const toDraw = player.getAllHistory("useSkill", evt => {
const evtx = evt.event;
return evt.skill === "dcjichou" && evtx.givenCards && evtx.givenCards.length;
})[0].event.givenCards.length;
await game.asyncDelayx();
await player.draw(toDraw);
}
}
if (_status.connectMode) {
game.broadcastAll(() => {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
},
},
dcmouli: {
audio: 2,
trigger: { player: "phaseEnd" },
filter(event, player) {
const names = [];
player.checkAllHistory("useSkill", evt => {
if (evt.skill !== "dcjichou") return;
const evtx = evt.event;
if (evtx.givenCards) names.addArray(evtx.givenCards.map(card => get.name(card, false)));
});
return names.length > 5;
},
forced: true,
juexingji: true,
skillAnimation: true,
animationColor: "water",
derivation: ["dczifu"],
async content(event, trigger, player) {
player.awakenSkill("dcmouli");
await player.gainMaxHp();
await player.recover();
await player.addSkills("dczifu");
},
ai: {
combo: "dcjichou",
},
},
dczifu: {
audio: 2,
trigger: { player: "phaseUseBegin" },
forced: true,
async content(event, trigger, player) {
const maxLimit = Math.min(5, player.maxHp);
let count = player.countCards("h");
if (count < maxLimit) {
await player.draw(maxLimit - count);
}
if (!player.hasHistory("gain", evt => evt.getParent(2) === event)) return;
count = player.countCards("h");
const toKeepCount = player
.getCards("h")
.map(card => get.name(card))
.unique();
if (count > toKeepCount) {
const [bool, cards] = await player
.chooseCard("自缚:选择要保留的手牌", "选择不同牌名的手牌各一张,然后弃置其余手牌", toKeepCount)
.set("filterCard", card => {
if (!ui.selected.cards.length) return true;
const name = get.name(card, player);
if (ui.selected.cards.some(card => get.name(card, player) === name)) return false;
return true;
})
.set("complexCard", true)
.set("ai", get.value)
.forResult("bool", "cards");
if (!bool) return;
const toDiscard = player.getCards("h").removeArray(cards);
if (toDiscard.length) player.discard(toDiscard);
}
},
ai: {
halfneg: true,
},
},
//蒋济
dcshiju: {
audio: 2,
global: "dcshiju_global",
subSkill: {
global: {
audio: "dcshiju",
forceaudio: true,
enable: "phaseUse",
usable: 1,
filter(event, player) {
return game.hasPlayer(current => {
if (current == player || !current.hasSkill("dcshiju")) return false;
return player.countCards("he");
});
},
filterTarget(card, player, target) {
return target != player && target.hasSkill("dcshiju");
},
selectTarget() {
const num = game.countPlayer(current => {
return current.hasSkill("dcshiju");
});
return num > 1 ? 1 : -1;
},
filterCard: true,
position: "he",
check(card) {
const player = get.player();
if (get.type(card) === "equip") {
const subtype = get.subtype(card);
let valueFix = 0;
if (
game.hasPlayer(current => {
if (current == player || !current.hasSkill("dcshiju")) return false;
if (current.hasUseTarget(card) && !player.countEmptySlot(subtype)) return true;
})
)
valueFix += 5;
if (player.countCards("he", { subtype }) > 1) {
return valueFix + 12 - get.equipValue(card);
}
return valueFix + 6 - get.value(card);
}
return 4 - get.value(card);
},
prompt() {
const list = game.filterPlayer(current => {
return current.hasSkill("dcshiju");
});
return `将一张牌交给${get.translation(list)}${list.length > 1 ? "中的一人" : ""},若此牌为装备牌,其可以使用之,且你本回合的攻击范围+X(X为其装备区的牌数)。若其以此法替换了装备,你与其各摸两张牌。`;
},
discard: false,
lose: false,
prepare(cards, player, targets) {
player.$give(cards, targets[0], false);
},
async content(event, trigger, player) {
const card = event.cards[0],
target = event.target;
await player.give(card, target);
if (!target.getCards("h").includes(card) || get.type(card) !== "equip") return;
const bool = await target.chooseUseTarget(card).forResultBool();
if (!bool) return;
const count = target.countCards("e");
if (count > 0) {
player.addTempSkill("dcshiju_range");
player.addMark("dcshiju_range", count, false);
if (
target.hasHistory("lose", evt => {
return evt.getParent().name === "equip" && evt.getParent(5) === event && evt.es && evt.es.length > 0;
})
) {
for (const current of [player, target]) await current.draw(2);
}
}
},
ai: {
order: 10,
result: {
target(player, target) {
const card = ui.selected.cards[0];
if (!card) return;
if (target.hasSkillTag("nogain") && get.type(card) != "equip") return 0;
if (card.name == "du" && target.hasSkillTag("nodu")) return 0;
if (get.value(card) < 0) return -5;
const nh = target.countCards("h");
return Math.max(1, 5 - nh);
},
},
},
},
range: {
charlotte: true,
onremove: true,
mod: {
attackRange: function (player, num) {
return num + player.countMark("dcshiju_range");
},
},
intro: { content: "本回合攻击范围+#" },
},
},
},
dcyingshi: {
audio: 2,
trigger: { player: "useCardToPlayered" },
filter(event, player) {
if (!event.isFirstTarget) return false;
if (get.type(event.card) !== "trick") return false;
return true;
},
direct: true,
async content(event, trigger, player) {
const result = await player
.chooseTarget()
.set("prompt", get.prompt("dcyingshi"))
.set("prompt2", `令其中一名角色选择本回合未被选择过的一项:⒈令你于此牌结算结束后视为对其使用一张${get.translation(trigger.card.name)};⒉弃置${get.cnNumber(player.countCards("e"))}张牌,此牌对其无效。`)
.set("filterTarget", (card, player, target) => {
return get.event("targets").includes(target);
})
.set("targets", trigger.targets)
.set(
"toFriends",
(() => {
const isPositive = trigger.targets.some(current => {
return get.effect(current, trigger.card, trigger.player, player) > 0;
}),
isNegative = trigger.targets.some(current => {
return get.effect(current, trigger.card, trigger.player, player) < -5;
});
if ((player.hasSkill("dcyingshi_choice1") || player.countCards("e") < 2) && isNegative) return true;
if (!player.hasSkill("dcyingshi_choice1") && ((get.tag(trigger.card, "norepeat") && isNegative) || isPositive)) return true;
return false;
})()
)
.set("ai", target => {
const player = get.player(),
count = player.countCards("e"),
att = get.attitude(player, target);
if (att > 0 && get.event("toFriends")) {
if (target.countCards("he", card => get.value(card) < 5) < count) return 0;
return att;
}
if (player.hasSkill("dcyingshi_choice1") && !count) return 0;
return -get.attitude(player, target);
})
.forResult();
if (!result.bool) return;
const target = result.targets[0];
player.logSkill("dcyingshi", target);
let bool;
if (!player.hasSkill(`dcyingshi_choice2`)) {
const count = player.countCards("e"),
forced = player.hasSkill("dcyingshi_choice1");
if (count > 0) {
const prompt = `###${get.translation(player)}对你发动了【应时】###${forced ? "请" : "是否"}弃置${get.cnNumber(count)}张牌,令${get.translation(trigger.card)}对你无效${forced ? "。" : "?或点击“取消”,令其与此牌结算后视为对你使用一张同名牌。"}`;
bool = await target
.chooseToDiscard(prompt, count, forced, "he")
.set("ai", card => {
if (get.event("goon")) return 5.5 - get.value(card);
return 0;
})
.set("goon", !get.tag(trigger.card, "norepeat") && get.effect(target, trigger.card, trigger.player, target) < -5)
.forResultBool();
} else bool = false;
} else bool = player.hasSkill("dcyingshi_choice1");
if (bool) {
trigger.excluded.add(target);
} else {
player
.when({ global: "useCardAfter" })
.filter(evt => evt === trigger.getParent())
.vars({
targetx: target,
cardx: {
name: trigger.card.name,
nature: trigger.card.nature,
isCard: true,
storage: { dcyingshi: true },
},
})
.then(() => {
const next = player.useCard(get.copy(cardx), targetx, false);
if (trigger.addedTarget) next.addedTarget = trigger.addedTarget;
if (trigger.addedTargets && trigger.addedTargets.length) next.addedTargets = trigger.addedTargets.slice(0);
});
}
player.addTempSkill(`dcyingshi_choice${bool + 1}`);
},
subSkill: {
choice1: { charlotte: true },
choice2: { charlotte: true },
},
},
//公孙修
dcgangu: {
audio: 2,
trigger: { global: "loseHpAfter" },
filter(event, player) {
return event.player !== player;
},
usable: 1,
forced: true,
async content(event, trigger, player) {
await player.draw(2);
await player.loseHp();
},
ai: {
halfneg: true,
},
},
dckuizhen: {
audio: 2,
enable: "phaseUse",
filter(event, player) {
return game.hasPlayer(current => {
return lib.skill.dckuizhen.filterTarget(null, player, current);
});
},
filterTarget(card, player, target) {
return target.countCards("h") > player.countCards("h") || target.getHp() > player.getHp();
},
usable: 1,
forced: true,
async content(event, trigger, player) {
const { target } = event,
juedou = new lib.element.VCard({ name: "juedou" });
if (target.canUse(juedou, player, false)) {
await target.useCard(juedou, player, "noai");
}
if (
player.hasHistory("damage", evt => {
return evt.getParent(3) === event;
})
) {
await player.viewHandcards(target);
const shas = target.getGainableCards(player, "h").filter(card => get.name(card) === "sha");
if (shas.length) {
player.addTempSkill("dckuizhen_effect");
await player.gain(shas, "give", target).gaintag.add("dckuizhen");
}
} else {
await target.loseHp();
}
},
ai: {
result: {
target(player, target) {
const [juedouEff, loseEff] = [get.effect(player, { name: "juedou" }, target, player), get.effect(target, { name: "losehp" }, target, player)];
if (juedouEff > 0) return (loseEff * get.attitude(player, target)) / 10;
return 0;
},
},
},
subSkill: {
effect: {
trigger: { player: "useCard1" },
forced: true,
popup: false,
firstDo: true,
charlotte: true,
filter: function (event, player) {
if (event.addCount === false) return false;
return player.hasHistory("lose", evt => {
if (evt.getParent() != event) return false;
for (const i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("dckuizhen")) return true;
}
return false;
});
},
async content(event, trigger, player) {
trigger.addCount = false;
var stat = player.getStat().card,
name = trigger.card.name;
if (typeof stat[name] == "number") stat[name]--;
},
mod: {
cardUsable(card) {
if (!card.cards) return;
if (card.cards.some(card => card.hasGaintag("dckuizhen"))) return Infinity;
},
},
},
},
},
//刘理
dcfuli: {
audio: 2,
enable: "phaseUse",
filter(event, player) {
return player.countDiscardableCards(player, "h");
},
usable: 1,
async content(event, trigger, player) {
await player.showHandcards(get.translation(player) + "发动了【抚黎】");
const getNum = type => {
let num = ["basic", "trick", "equip"].indexOf(type);
if (num === -1) num = 3;
return num;
};
const types = player
.getDiscardableCards(player, "h")
.reduce((list, card) => {
return list.add(get.type2(card));
}, [])
.sort((a, b) => getNum(a) - getNum(b));
if (types.length) {
const {
result: { control },
} = await player
.chooseControl(types)
.set("ai", () => {
const player = get.event("player"),
types = get.event("controls").slice();
const getNum = type => {
const cards = player.getDiscardableCards(player, "h").filter(card => get.type2(card) == type);
const countCards = (target, player, cards) => {
return target.countCards("h") - (target == player ? cards.length : 0);
};
const max = game
.findPlayer(target => {
return !game.hasPlayer(target2 => {
return countCards(target2, player, cards) > countCards(target, player, cards);
});
})
.countCards("h");
return (
Math.min(
max,
cards.reduce((sum, card) => sum + get.cardNameLength(card), 0)
) / cards.length
);
};
return types.sort((a, b) => {
return getNum(b) - getNum(a);
})[0];
})
.set("prompt", "弃置一种类别的所有手牌,然后摸这些牌的名字字数之和的牌");
if (control) {
const cards = player.getDiscardableCards(player, "h").filter(card => get.type2(card) == control);
await player.discard(cards);
const max = game.findPlayer(target => target.isMaxHandcard()).countCards("h");
const num = Math.min(
max,
cards.reduce((sum, card) => sum + get.cardNameLength(card), 0)
);
if (num) await player.draw(num);
if (cards.some(card => card.name != "shandian" && get.tag(card, "damage"))) {
const {
result: { bool, targets },
} = await player.chooseTarget("抚黎:是否令一名角色的攻击范围-1直到你的下个回合开始?").set("ai", target => {
const player = get.event("player"),
num = target.getAttackRange();
return -get.sgn(get.attitude(player, target)) * (target.getAttackRange() + (num <= 0 ? -num + 0.5 : num));
});
if (bool) {
const target = targets[0];
player.line(target);
target.addSkill("dcfuli_range");
target.addMark("dcfuli_range", 1, false);
player
.when(["phaseBegin", "dieBegin"])
.then(() => {
target.removeMark("dcfuli_range", 1, false);
if (!target.hasMark("dcfuli_range")) target.removeSkill("dcfuli_range");
})
.vars({ target: target });
}
}
}
}
},
ai: {
order: 1,
result: {
player(player) {
const types = player.getDiscardableCards(player, "h").reduce((list, card) => {
return list.add(get.type2(card));
}, []);
if (
!types.some(type => {
const cards = player.getDiscardableCards(player, "h").filter(card => get.type2(card) == type);
const countCards = (target, player, cards) => {
return target.countCards("h") - (target == player ? cards.length : 0);
};
return !game
.filterPlayer(target => {
return !game.hasPlayer(target2 => {
return countCards(target2, player, cards) > countCards(target, player, cards);
});
})
.includes(player);
})
)
return 0;
return 1;
},
},
},
subSkill: {
range: {
charlotte: true,
onremove: true,
mod: {
attackRange(player, num) {
return num - player.countMark("dcfuli_range");
},
},
marktext: " - ",
intro: { content: "攻击范围-#" },
},
},
},
dcdehua: {
audio: 2,
trigger: { global: "roundStart" },
forced: true,
async content(event, trigger, player) {
const list = lib.inpile.filter(name => {
if (get.type(name) === "delay") return false;
const card = new lib.element.VCard({ name: name });
return get.tag(card, "damage") && player.hasUseTarget(card);
});
if (list.length) {
const {
result: { bool, links },
} = await player.chooseButton(['###德化###视为使用一张仍可以使用的伤害类卡牌
', [list, "vcard"]], true).set("ai", button => {
const name = button.link[2],
player = get.player();
let value = player.getUseValue({ name, isCard: true }, null, true);
if (player.countCards("h", card => get.name(card) === name && player.hasUseTarget(card))) value /= 3;
if (name === "sha") value /= 2;
if (player.getStorage("dcdehua").includes("sha")) value = Math.max(0.1, value);
return value;
});
if (bool) {
const name = links[0][2],
card = new lib.element.VCard({ name: name });
await player.chooseUseTarget(card, true);
player.markAuto("dcdehua", [name]);
}
}
if (
!lib.inpile.some(name => {
if (get.type(name) === "delay") return false;
const card = new lib.element.VCard({ name: name });
return get.tag(card, "damage") && !player.getStorage("dcdehua").includes(name);
})
)
player.removeSkills("dcdehua");
},
mod: {
maxHandcard(player, num) {
return num + player.getStorage("dcdehua").length;
},
cardEnabled(card, player) {
if (player.getStorage("dcdehua").includes(card.name) && (get.position(card) == "h" || (card.cards && card.cards.some(i => get.position(i) == "h")))) return false;
},
cardSavable(card, player) {
if (player.getStorage("dcdehua").includes(card.name) && (get.position(card) == "h" || (card.cards && card.cards.some(i => get.position(i) == "h")))) return false;
},
aiValue(player, card) {
if (player.getStorage("dcdehua").includes(get.name(card))) return 0;
},
aiUseful() {
return lib.skill.dcdehua.mod.aiValue.apply(this, arguments);
},
},
intro: {
content(storage) {
return "手牌上限+" + storage.length + "
不能从手牌中使用" + get.translation(storage);
},
},
},
//蒋琬费祎
dcshengxi: {
inherit: "reshengxi",
trigger: { player: "phaseDiscardEnd" },
},
dcshoucheng: {
audio: "shoucheng",
global: "dcshoucheng_ai",
trigger: {
global: ["equipAfter", "addJudgeAfter", "loseAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
filter(event, player) {
const target = _status.currentPhase;
return game.hasPlayer(current => {
if (target && current == target) return false;
let evt = event.getl(current);
return evt && evt.hs && evt.hs.length && current.countCards("h") == 0;
});
},
async cost(event, trigger, player) {
const targetx = _status.currentPhase;
const targets = game
.filterPlayer(current => {
if ((targetx && current == targetx) || !current.isIn()) return false;
let evt = trigger.getl(current);
return evt && evt.hs && evt.hs.length && current.countCards("h") == 0;
})
.sortBySeat(targetx || player);
event.result = await player
.chooseTarget("是否对" + (targets.length > 1 ? "其中一名角色" : get.translation(targets[0])) + "发动【守成】?", "令其摸两张牌", (card, player, target) => {
return get.event("targets").includes(target);
})
.set("targets", targets)
.set("ai", target => get.attitude(get.event("player"), target))
.forResult();
},
usable: 1,
async content(event, trigger, player) {
const target = event.targets[0];
if (get.mode() != "identity" || player.identity != "nei") player.addExpose(0.2);
target.draw(2);
},
subSkill: {
ai: {
ai: {
noh: true,
skillTagFilter(player, tag, arg) {
if (player === _status.currentPhase || player.countCards("h") != 1) return false;
return game.hasPlayer(current => {
return current.hasSkill("dcshoucheng") && get.attitude(current, player) > 0;
});
},
},
},
},
},
//乐大乔
dczixi: {
init() {
game.addGlobalSkill("dczixi_judge");
game.broadcastAll(() => lib.skill.dczixi.video());
},
video() {
const list = lib.skill.dczixi.zixiList;
for (const name of list) {
const namex = "dczixi_" + name;
if (!lib.card[namex]) {
lib.card[namex] = {
type: "special_delay",
fullskin: true,
noEffect: true,
wuxieable: false,
};
lib.card[namex].cardimage = name;
lib.translate[namex] = lib.translate[name] + "·姊希";
lib.translate[namex + "_info"] = "由【姊希】技能创造的无效果【" + lib.translate[name] + "】";
}
}
},
audio: 2,
trigger: { player: ["phaseUseBegin", "phaseUseEnd"] },
filter(event, player) {
return (
player.countCards("h", card => {
return (
card.hasGaintag("dcqiqin_tag") &&
lib.skill.dczixi.zixiList.some(name => {
return game.hasPlayer(target => target.canAddJudge(get.autoViewAs({ name: "dczixi_" + name }, [card])));
})
);
}) > 0
);
},
zixiList: ["lebu", "bingliang", "shandian"],
direct: true,
async content(event, trigger, player) {
game.addVideo("skill", player, ["dczixi", []]);
const names = lib.skill.dczixi.zixiList.filter(name => {
return player.countCards("h", card => {
return card.hasGaintag("dcqiqin_tag") && game.hasPlayer(target => target.canAddJudge(get.autoViewAs({ name: "dczixi_" + name }, [card])));
});
});
let map = {};
for (const name of names) {
map[get.translation(name)] = name;
}
const {
result: { bool, links },
} = await player
.chooseButton(2, ["###" + get.prompt("dczixi") + '###将一张“琴”以你选择的牌名置于一名角色的判定区
', player.getCards("h"), [Object.keys(map), "tdnodes"]])
.set("filterButton", button => {
const type = typeof button.link,
card = button.link;
if (ui.selected.buttons.length && type == typeof ui.selected.buttons[0].link) return false;
if (type == "string") return true;
return (
card.hasGaintag("dcqiqin_tag") &&
lib.skill.dczixi.zixiList.some(name => {
return game.hasPlayer(target => target.canAddJudge(get.autoViewAs({ name: "dczixi_" + name }, [card])));
})
);
})
.set("ai", button => {
const player = get.event("player"),
list = Object.keys(get.event("map"));
if (typeof button.link == "string") {
const card = player
.getCards("h", card => {
if (get.value(card) >= 7) return false;
return card.hasGaintag("dcqiqin_tag") && game.hasPlayer(target => target.canAddJudge(get.autoViewAs({ name: "dczixi_" + name }, [card])));
})
.sort((a, b) => get.value(a) - get.value(b))[0];
if (
game.hasPlayer(current => {
return get.attitude(player, current) < 0 && lib.skill.dczixi.zixiList.some(name => current.canAddJudge(get.autoViewAs({ name: "dczixi_" + name }, [card])));
})
)
return list.indexOf(button.link) + 1;
return 1 / (list.indexOf(button.link) + 1);
}
return 7 - get.value(button.link);
})
.set("map", map);
if (bool) {
const name = links.find(i => typeof i == "string"),
card = links.find(j => j != name),
cardname = map[name];
const {
result: { bool, targets },
} = await player
.chooseTarget(
"请选择【" + name + "(" + get.translation(card) + ")】置入的目标",
(cardx, player, target) => {
return target.canAddJudge(get.autoViewAs({ name: "dczixi_" + get.event("cardname") }, [get.event("card")]));
},
true
)
.set("ai", target => {
const player = get.event("player"),
card = get.event("card");
if (
game.hasPlayer(current => {
return get.attitude(player, current) < 0 && current.canAddJudge(get.autoViewAs({ name: "dczixi_" + get.event("cardname") }, [card]));
})
)
return -target.countCards("j") - 1;
return target.countCards("j") + 1;
})
.set("card", card)
.set("cardname", cardname);
if (bool) {
const target = targets[0];
player.logSkill("dczixi", target);
player.$give(card, target, false);
await game.asyncDelay(0.5);
target.addJudge({ name: "dczixi_" + cardname }, [card]);
}
}
},
group: "dczixi_effect",
subSkill: {
judge: {
mod: {
targetEnabled(card, player, target) {
const list = lib.skill.dczixi.zixiList;
const name = typeof card == "string" ? card : card.viewAs ? card.viewAs : card.name;
if (name.indexOf("dczixi_") == 0) {
const namex = name.slice("dczixi_".length);
if (list.includes(namex) && target.hasJudge(namex)) return false;
} else if (list.includes(name) && target.hasJudge("dczixi_" + name)) return false;
},
},
ai: {
threaten(player, target) {
if (!player.hasSkill("dczixi") || ![1, 2, 3].includes(target.countCards("j"))) return;
return 3 + target.countCards("j");
},
},
},
effect: {
audio: "dczixi",
trigger: { player: "useCardToTargeted" },
filter(event, player) {
return event.isFirstTarget && event.targets.length == 1 && [1, 2, 3].includes(event.target.countCards("j")) && (get.type(event.card) == "basic" || get.type(event.card) == "trick");
},
prompt2(event, player) {
const target = event.target,
str = get.translation(target);
return ["令" + get.translation(event.card) + "对" + str + "额外结算一次", "摸两张牌", "弃置" + str + "判定区里的所有牌,对其造成3点伤害"][target.countCards("j") - 1];
},
check(event, player) {
const target = event.target,
num = target.countCards("j");
if (num == 2) return true;
if (num == 1) return get.effect(target, event.card, player, player) > 0;
return get.attitude(player, target) < 0 && get.damageEffect(target, player, player) > 0;
},
logTarget: "target",
async content(event, trigger, player) {
const target = trigger.target,
num = target.countCards("j");
switch (num) {
case 1:
trigger.getParent().effectCount++;
game.log(trigger.card, "额外结算一次");
break;
case 2:
player.draw(2);
break;
case 3:
target.discard(target.getCards("j")).discarder = player;
target.damage(3);
break;
}
},
},
},
},
//孔融
dckrmingshi: {
audio: "mingshi",
trigger: { player: "damageBegin4" },
filter(event, player) {
return event.source && event.source.countCards("h") > player.countCards("h");
},
forced: true,
logTarget: "source",
async content(event, trigger, player) {
const target = trigger.source;
const {
result: { bool },
} = await target
.chooseToDiscard("名士:弃置一张手牌,或防止对" + get.translation(player) + "造成的伤害")
.set("ai", card => {
if (get.event("goon")) return 0;
return 6 - get.value(card);
})
.set("goon", get.damageEffect(player, target, target) <= 0);
if (!bool) trigger.cancel();
},
ai: {
effect: {
target_use(card, player, target, current) {
if (get.tag(card, "damage") && target != player) {
if (_status.event.name == "dckrmingshi") return;
if (get.attitude(player, target) > 0 && current < 0) return "zerotarget";
var bs = player.getCards("h");
bs.remove(card);
if (card.cards) bs.removeArray(card.cards);
else bs.removeArray(ui.selected.cards);
if (bs.length > target.countCards("h")) {
if (bs.some(bsi => get.value(bsi) < 7)) return [1, 0, 1, -0.5];
return [1, 0, 0.3, 0];
}
return [1, 0, 1, -0.5];
}
},
},
},
},
//新服SP孟获
dcmanwang: {
audio: "spmanwang",
inherit: "spmanwang",
check: function (card) {
var player = _status.event.player;
var max = Math.min(player.isDamaged() ? 3 : 2, 4 - player.countMark("dcmanwang"));
if (!max && !player.hasSkill("dcpanqin")) return 0;
if (max == 0 && ui.selected.length > 0) return 0;
return 7 - ui.selected.cards.length - get.value(card);
},
content: function () {
var num = Math.min(cards.length, 4 - player.countMark("dcmanwang"));
if (num >= 1) player.addSkills("dcpanqin");
if (num >= 2) player.draw();
if (num >= 3) player.recover();
if (num >= 4) {
player.draw(2);
player.removeSkills("dcpanqin");
}
},
ai: {
order: 2,
result: {
player: function (player, target) {
if (player.getUseValue({ name: "nanman" }) <= 0) return 0;
if (player.getStat("skill").spmanwang && player.hasSkill("dcpanqin")) return 0;
return 1;
},
},
},
derivation: "dcpanqin",
},
dcpanqin: {
audio: "sppanqin",
inherit: "sppanqin",
content: function () {
var cards = [];
player.getHistory("lose", function (evt) {
if (evt.type != "discard" || evt.getParent(trigger.name) != trigger) return false;
for (var i of evt.cards2) {
if (get.position(i, true) == "d") {
cards.add(i);
}
}
});
player.chooseUseTarget(true, { name: "nanman" }, cards);
player.addTempSkill("dcpanqin_eff");
},
subSkill: {
eff: {
charlotte: true,
trigger: { player: "useCard" },
filter: function (event, player) {
return event.card.name == "nanman" && event.getParent(2).name == "dcpanqin" && player.countMark("dcmanwang") < 4 && player.hasSkill("dcmanwang", null, null, false) && event.cards.length <= event.targets.length;
},
forced: true,
popup: false,
content: function () {
"step 0";
player.addMark("dcmanwang", 1, false);
switch (player.countMark("dcmanwang")) {
case 1:
player.draw(2);
player.removeSkills("dcpanqin");
break;
case 2:
player.recover();
break;
case 3:
player.draw();
break;
case 4:
player.addSkills("dcpanqin");
break;
}
"step 1";
player.gainMaxHp();
player.recover();
},
},
},
},
//凌操
dcdufeng: {
audio: 2,
trigger: { player: "phaseUseBegin" },
forced: true,
async content(event, trigger, player) {
const list = [];
for (let i = 1; i < 6; i++) {
if (player.isDisabled(i)) continue;
list.push("equip" + i);
}
list.push("cancel2");
const next = player.chooseControl(list);
next.set("prompt", "独锋:请废除一个装备栏,或点击“取消”失去1点体力");
next.set("ai", () => {
const list = get.event().list.slice(),
player = get.player();
if (player.hp <= 2 && list.length > 1) list.remove("cancel2");
const listx = list.filter(subtype => !player.getEquips(subtype).length);
if (listx.length) return listx.randomGet();
return list.randomGet();
});
next.set("list", list);
const { result } = await next;
if (result.control == "cancel2") await player.loseHp();
else await player.disableEquip(result.control);
if (!player.isIn()) return;
const num = Math.min(player.countDisabled() + player.getDamagedHp(), player.maxHp);
await player.draw(num);
player.addTempSkill("dcdufeng_effect");
player.addMark("dcdufeng_effect", num, false);
},
subSkill: {
effect: {
charlotte: true,
onremove: true,
intro: {
content: "本回合攻击范围与使用【杀】的次数上限均为#",
},
mod: {
attackRangeBase(player, num) {
return player.countMark("dcdufeng_effect");
},
cardUsable(card, player, num) {
if (card.name == "sha") return player.countMark("dcdufeng_effect");
},
},
},
},
},
//小乔
dcqiqin: {
audio: 2,
audioname: ["yue_daqiao"],
trigger: {
global: "phaseBefore",
player: "enterGame",
},
filter: function (event, player) {
return event.name != "phase" || game.phaseNumber == 0;
},
forced: true,
content: function () {
let cards = player.getCards("h");
player.addGaintag(cards, "dcqiqin_tag");
player.markAuto("dcqiqin", cards);
},
group: "dcqiqin_restore",
subSkill: {
tag: {},
restore: {
audio: "dcqiqin",
audioname: ["yue_daqiao"],
trigger: { player: "phaseZhunbeiBegin" },
filter: function (event, player) {
const targets = game.players.slice().concat(game.dead);
return targets.some(target => target.getStorage("dcqiqin").filterInD("d").length);
},
forced: true,
content: function () {
const targets = game.players.slice().concat(game.dead);
const cards = targets.reduce((list, target) => list.addArray(target.getStorage("dcqiqin").filterInD("d")), []);
player.gain(cards, "gain2").gaintag.add("dcqiqin_tag");
},
},
},
mod: {
ignoredHandcard: function (card, player) {
if (card.hasGaintag("dcqiqin_tag")) return true;
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && card.hasGaintag("dcqiqin_tag")) return false;
},
},
},
dcweiwan: {
audio: 2,
enable: "phaseUse",
filter: (event, player) => {
return (
player.countCards(lib.skill.dcweiwan.position, card => {
return lib.skill.dcweiwan.filterCard(card, player);
}) &&
game.hasPlayer(target => {
return lib.skill.dcweiwan.filterTarget(null, player, target);
})
);
},
filterCard: (card, player) => {
return card.hasGaintag("dcqiqin_tag") && lib.filter.cardDiscardable(card, player);
},
filterTarget: (card, player, target) => {
return target != player && target.countCards("he");
},
position: "h",
check: card => {
const player = _status.event.player;
const target = game.players.reduce(
(result, current) => {
if (current === player) return result;
const effect = Math.abs(lib.skill.dcweiwan.ai.result.target(player, current));
return effect > result[1] ? [current, effect] : result;
},
[null, 0]
)[0];
return target ? lib.skill.dcweiwan.getWeiWanEffect(player, card, target) : 0;
},
usable: 1,
content: function* (event, map) {
let player = map.player,
target = event.target;
let suit = get.suit(event.cards[0], player);
let cards = target.getCards("hej", card => get.suit(card, target) != suit && lib.filter.canBeGained(card, player, target));
if (!cards.length) {
player.chat("无牌可得!!");
return;
}
let suits = lib.suit.slice();
suits.reverse();
suits.add("none");
suits.forEach(suit2 => {
let cards2 = cards.filter(card => get.suit(card, target) == suit2);
if (cards2.length) {
cards2.randomRemove();
cards.removeArray(cards2);
}
});
if (!cards.length) {
player.chat("无牌可得!!");
return;
}
player.gain(cards, target, "give");
switch (cards.length) {
case 1:
target.loseHp();
break;
case 2:
player.addTempSkill("tanbei_effect3");
target.addTempSkill("tanbei_effect1");
break;
case 3:
player.addTempSkill("tanbei_effect3");
target.addTempSkill("tanbei_effect2");
break;
}
},
ai: {
order: 9,
result: {
target: (player, target) => {
const att = get.sgn(get.attitude(player, target)) - 1;
const cards = player.getCards(lib.skill.dcweiwan.position, card => lib.skill.dcweiwan.filterCard(card, player));
return (
att *
cards.reduce((result, card) => {
const effect = lib.skill.dcweiwan.getWeiWanEffect(player, card, target);
return effect > result ? effect : result;
}, 0)
);
},
},
combo: "dcqiqin",
},
getWeiWanEffect: (player, cardx, target) => {
const suit = get.suit(cardx, player);
const cards = target.getCards("hej", card => get.suit(card, target) !== suit && lib.filter.canBeGained(card, player, target));
const num = lib.suits.filter(suit => cards.some(card => get.suit(card, target) === suit)).length;
switch (num) {
case 1:
return num + Math.max(0, get.sgn(get.effect(target, { name: "losehp" }, player, player)));
case 2:
return num + player.countCards("he", card => player.canUse(card, target, false) && get.effect(target, card, player, player) > 0);
case 3:
return Math.ceil(num / 2);
default:
return num;
}
},
},
//董昭
dcyijia: {
audio: 2,
trigger: { global: "damageEnd" },
filter: function (event, player) {
if (!event.player.isIn()) return false;
if (get.distance(player, event.player) > 1) return false;
return player.canMoveCard(
null,
true,
game.filterPlayer(i => i != event.player),
event.player,
"canReplace"
);
},
check: function (event, player) {
return player.canMoveCard(
true,
true,
game.filterPlayer(i => i != event.player),
event.player,
"canReplace"
);
},
prompt2: function (event, player) {
return `将场上一张装备牌移动至${get.translation(event.player)}的装备区内(替换原装备)。然后若其因此脱离了一名角色的攻击范围,你摸一张牌。`;
},
logTarget: "player",
line: false,
content: function* (event, map) {
const player = map.player,
trigger = map.trigger,
target = trigger.player;
const inRangeList = game.filterPlayer(current => current.inRange(target));
yield player.moveCard(
true,
game.filterPlayer(i => i != target),
target,
"canReplace"
);
const leaveSomeone = inRangeList.some(current => !current.inRange(target));
if (leaveSomeone) player.draw();
},
ai: {
maixie: true,
expose: 0.2,
threaten: 3.3,
},
},
dcdingji: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
direct: true,
content: function* (event, map) {
const player = map.player;
let result;
result = yield player.chooseTarget(get.prompt2("dcdingji")).set("ai", target => {
let att = get.attitude(get.player(), target) / 2;
const delta = 5 - target.countCards("h");
let fix = 1;
const hs = target.getCards("h");
outer: for (let i = 0; i < hs.length - 1; i++) {
const name1 = get.name(hs[i]);
for (let j = i + 1; j < hs.length; j++) {
const name2 = get.name(hs[j]);
if (name1 == name2) {
fix = 0.5;
break outer;
}
}
}
if (delta > 0) {
if (target.hasSkillTag("nogain")) att /= 3;
return Math.sqrt(delta) * att * fix;
}
if (delta > -2 && att > 0) return fix == 0.5 ? 0.1 : -1;
return (-Math.sqrt(-delta) * att) / 2;
});
if (!result.bool) return event.finish();
const target = result.targets[0];
player.logSkill("dcdingji", target);
if (target != player) player.addExpose(0.3);
const delta = 5 - target.countCards("h");
if (delta != 0) {
yield target[delta > 0 ? "draw" : "chooseToDiscard"](Math.abs(delta), true);
}
target.showHandcards();
const hs = target.getCards("h");
let hasSame = false;
outer: for (let i = 0; i < hs.length - 1; i++) {
const name1 = get.name(hs[i]);
for (let j = i + 1; j < hs.length; j++) {
const name2 = get.name(hs[j]);
if (name1 == name2) {
hasSame = true;
break outer;
}
}
}
game.delayex();
if (hasSame) return event.finish();
const list = get.inpileVCardList(info => {
if (!["basic", "trick"].includes(info[0])) return false;
if (!target.hasUseTarget(new lib.element.VCard({ name: info[2], nature: info[3], isCard: true }))) return false;
return hs.some(card => {
return get.name(card) == info[2] && get.is.sameNature([card, info[3]], true);
});
});
if (!list.length) return event.finish();
result = yield target.chooseButton(["是否视为使用其中一张牌?", [list, "vcard"]]).set("ai", button => {
return get.player().getUseValue({ name: button.link[2] });
});
if (result.bool) {
target.chooseUseTarget(
new lib.element.VCard({
name: result.links[0][2],
nature: result.links[0][3],
isCard: true,
}),
true,
false
);
}
},
},
//蒯祺
dcliangxiu: {
audio: 2,
enable: "phaseUse",
filter: function (event, player) {
return player.hasCard(card => {
const type = get.type2(card, player);
return player.hasCard(cardx => {
if (card == cardx) return false;
return get.type2(cardx, player) != type;
}, "he");
}, "he");
},
filterCard: function (card, player) {
if (!ui.selected.cards.length) return true;
return get.type2(ui.selected.cards[0], player) != get.type2(card, player);
},
selectCard: 2,
check: function (card) {
const player = get.player();
const bannedTypes = [];
bannedTypes.addArray(player.getStorage("dcliangxiu"));
if (!ui.selected.cards.length) {
let val = get.value(card);
if (val > 5.5) return 0;
if (bannedTypes.includes(get.type2(card, player))) return 7.5 - val;
return 5.5 - val;
}
bannedTypes.addArray(ui.selected.cards.map(card => get.type2(card, player)));
bannedTypes.add(get.type2(card, player));
const filter = card => !bannedTypes.includes(get.type2(card, player));
if (!get.cardPile(filter)) return 0;
return 6 - get.value(card);
},
position: "he",
complexCard: true,
onremove: true,
content: function* (event, map) {
const player = map.player;
const cards = [];
const bannedTypes = [];
bannedTypes.addArray(event.cards.map(card => get.type2(card, player)));
bannedTypes.addArray(player.getStorage("dcliangxiu"));
const filter = card => !bannedTypes.includes(get.type2(card, player));
const piles = ["cardPile", "discardPile"];
for (const pile of piles) {
for (let i = 0; i < ui[pile].childNodes.length; i++) {
const card = ui[pile].childNodes[i];
if (filter(card)) {
cards.add(card);
if (cards.length >= 2) break;
}
}
if (cards.length >= 2) break;
}
let result;
if (!cards.length) {
player.chat("没牌了…");
game.log("但是哪里都找不到没有符合条件的牌!");
event.finish();
return;
} else if (cards.length == 1) result = { bool: true, links: cards };
else result = yield player.chooseButton(["良秀:获得一张牌", cards], true).set("ai", get.buttonValue);
if (result.bool) {
const toGain = result.links;
player.markAuto("dcliangxiu", get.type2(toGain[0], false));
player.when({ global: "phaseChange" }).then(() => {
player.unmarkSkill("dcliangxiu");
});
player.gain(toGain, "gain2");
}
},
intro: {
content: "已因此技能获得过$牌",
onunmark: true,
},
ai: {
order: 2,
result: { player: 1 },
},
},
dcxunjie: {
audio: 2,
trigger: { global: "phaseEnd" },
filter: function (event, player) {
if (["handcard", "hp"].every(i => player.isTempBanned(`dcxunjie_${i}`))) return false;
return player.hasHistory("gain", evt => {
return !evt.getParent("phaseDraw", true);
});
},
direct: true,
content: function* (event, map) {
const player = map.player;
const choices = [];
const choiceList = ["令一名角色将手牌数摸或弃置至与其体力值相同", "令一名角色将体力回复或失去至与其手牌数相同"];
if (!player.isTempBanned("dcxunjie_handcard")) choices.push("选项一");
else choiceList[0] = '' + choiceList[0] + "(已被选择过)";
if (!player.isTempBanned("dcxunjie_hp")) choices.push("选项二");
else choiceList[1] = '' + choiceList[1] + "(已被选择过)";
let result;
if (_status.connectMode)
game.broadcastAll(() => {
_status.noclearcountdown = true;
});
if (choices.length == 1) result = { control: choices[0] };
else
result = yield player
.chooseControl(choices, "cancel2")
.set("choiceList", choiceList)
.set("prompt", get.prompt("dcxunjie"))
.set("ai", () => {
return get.event("choice");
})
.set(
"choice",
(() => {
const getValue = (index, target) => {
let att = get.attitude(player, target);
att = Math.sign(att) * Math.sqrt(Math.abs(att));
let delt = target.getHp(true) - target.countCards("h");
if (index == 1 && delt < 0) delt = 0;
return (1 - 3 * index) * att * delt;
};
const list = game
.filterPlayer()
.map(current => {
const val0 = getValue(0, current),
val1 = getValue(1, current);
return [val0, val1, Math.max(val0, val1)];
})
.sort((a, b) => {
return b[2] - a[2];
});
const toChoose = list[0];
if (toChoose[2] <= 0) return "cancel2";
return toChoose[0] > toChoose[1] ? 0 : 1;
})()
);
if (result.control == "cancel2") {
if (_status.connectMode) {
game.broadcastAll(() => {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
return event.finish();
}
let prompt = "";
const choice = result.control,
index = choice == "选项一" ? 0 : 1;
if (choices.length == 1) {
prompt = `###${get.prompt("dcxunjie")}###${choiceList[index]}
`;
} else prompt = `###殉节:请选择一名角色###${choiceList[index].replace("一名", "该")}
`;
result = yield player
.chooseTarget(prompt)
.set("ai", target => {
const player = get.player(),
index = get.event("index");
let att = get.attitude(player, target);
att = Math.sign(att) * Math.sqrt(Math.abs(att));
let delt = target.getHp(true) - target.countCards("h");
if (index == 1 && delt < 0) delt = 0;
return (1 - 2 * index) * att * delt;
})
.set("index", index);
if (_status.connectMode) {
game.broadcastAll(() => {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
if (!result.bool) return event.finish();
const target = result.targets[0];
player.logSkill("dcxunjie", target);
player.tempBanSkill(`dcxunjie_${index == 0 ? "handcard" : "hp"}`, "roundStart", false);
const delt = (target.getHp(true) - target.countCards("h")) * (1 - 2 * index);
if (delt == 0) event.finish();
else if (index == 0) target[delt > 0 ? "draw" : "chooseToDiscard"](Math.abs(delt), true);
else target[delt > 0 ? "recover" : "loseHp"](Math.abs(delt));
},
},
//乐蔡邕
dcjiaowei: {
audio: 2,
trigger: {
global: "phaseBefore",
player: "enterGame",
},
forced: true,
filter: function (event, player) {
return event.name != "phase" || game.phaseNumber == 0;
},
group: "dcjiaowei_prevent",
content: function* (event, map) {
const player = map.player;
var cards = player.getCards("h");
player.addGaintag(cards, "dcjiaowei_tag");
},
mod: {
ignoredHandcard: function (card, player) {
if (card.hasGaintag("dcjiaowei_tag")) return true;
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && card.hasGaintag("dcjiaowei_tag")) return false;
},
},
subSkill: {
prevent: {
audio: "dcjiaowei",
trigger: {
player: "damageBegin4",
},
forced: true,
filter: function (event, player) {
if (!event.source || !event.source.isIn()) return false;
return event.source.countCards("h") <= player.countCards("h", card => card.hasGaintag("dcjiaowei_tag"));
},
content: function* (event, map) {
map.trigger.cancel();
},
ai: {
effect: {
target: function (card, player, target) {
if (get.tag(card, "damage")) {
const num = target.countCards("h", card => card.hasGaintag("dcjiaowei_tag"));
let cards = [];
if (card.cards) cards.addArray(card.cards);
if (ui.selected.cards) cards.addArray(ui.selected.cards);
cards = cards.filter(card => {
if (get.itemtype(card) != "card") return false;
return get.owner(card) == player && get.position(card) == "e";
});
if (player.countCards("h") - cards.length <= num) return "zeroplayertarget";
}
},
},
},
},
},
},
dcfeibai: {
audio: 2,
trigger: { player: "useCardAfter" },
usable: 1,
locked: false,
filter: function (event, player) {
return player.getHistory("useCard").indexOf(event) > 0;
},
prompt2: function (event, player) {
const history = player.getHistory("useCard");
const ind = history.indexOf(event) - 1,
evt = history[ind];
const len = get.cardNameLength(event.card) + get.cardNameLength(evt.card);
return `随机获得一张字数为${len}的牌`;
},
check: function (event, player) {
const history = player.getHistory("useCard");
const ind = history.indexOf(event) - 1,
evt = history[ind];
const len = get.cardNameLength(event.card) + get.cardNameLength(evt.card);
return (
player.countCards("h", card => card.hasGaintag("dcjiaowei_tag")) <= len ||
get.cardPile(card => {
return get.cardNameLength(card, false) == len;
})
);
},
content: function* (event, map) {
const player = map.player,
trigger = map.trigger;
const history = player.getHistory("useCard");
const ind = history.indexOf(trigger) - 1,
evt = history[ind];
const len = get.cardNameLength(trigger.card) + get.cardNameLength(evt.card);
const card = get.cardPile(card => {
return get.cardNameLength(card, false) == len;
});
if (card) {
yield player.gain(card, "gain2");
} else {
let str = `没有${len}字的牌…`;
if (len == 5 && Math.random() <= 0.2) str = "五字不行哇";
player.chat(str);
game.log(`但是找不到字数为${len}的牌!`);
}
if (player.countCards("h", card => card.hasGaintag("dcjiaowei_tag")) <= len) {
player.storage.counttrigger.dcfeibai--;
game.log(player, "重置了", "#【飞白】");
}
},
mod: {
aiOrder: function (player, card, num) {
const evt = player.getLastUsed();
if (!evt) return;
const len = get.cardNameLength(card) + get.cardNameLength(evt.card);
const cardx = get.cardPile(card => {
return get.cardNameLength(card, false) == len;
});
if (cardx) return num + 8 + (len == 2 || len == 4 ? 2 : 0);
},
},
},
//庞山民
dccaisi: {
audio: 2,
trigger: { player: "useCardAfter" },
filter: function (event, player) {
return get.type(event.card) == "basic" && _status.currentPhase;
},
prompt2: function (event, player) {
const num = player.countMark("dccaisi_more") + 1;
return `从${player == _status.currentPhase ? "牌堆" : "弃牌"}堆中随机获得${get.cnNumber(num)}张非基本牌`;
},
content: function* (event, map) {
const player = map.player,
trigger = map.trigger;
const position = player == _status.currentPhase ? "cardPile" : "discardPile";
let cards = [],
num = player.countMark("dccaisi_more") + 1;
while (num > 0) {
num--;
let card = get[position](card => get.type(card) != "basic" && !cards.includes(card));
if (card) cards.add(card);
else break;
}
if (cards.length) yield player.gain(cards, "gain2");
else {
player.chat("没有非基本牌…");
game.log(`但是${position == "discardPile" ? "弃" : ""}牌堆里没有非基本牌!`);
}
const sum = player.getHistory("useSkill", evt => evt.skill == "dccaisi").length;
if (sum < player.maxHp) {
player.addTempSkill("dccaisi_more");
player.addMark("dccaisi_more", 1, false);
} else player.tempBanSkill("dccaisi");
},
subSkill: { more: { charlotte: true, onremove: true } },
},
dczhuoli: {
audio: 2,
trigger: { global: "phaseEnd" },
forced: true,
filter: function (event, player) {
return player.getHistory("useCard").length > player.getHp() || player.getHistory("gain").reduce((sum, evt) => sum + evt.cards.length, 0) > player.getHp();
},
content: function* (event, map) {
const player = map.player;
if (player.maxHp < game.countPlayer2()) {
yield player.gainMaxHp();
}
yield player.recover();
},
},
//魏贾充
dcbeini: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterCard: function (card, player) {
const delt = player.countCards("h") - player.maxHp;
return delt > 0;
},
selectCard: function () {
const player = get.player();
const delt = player.countCards("h") - player.maxHp;
return delt > 0 ? delt : -1;
},
promptfunc: () => {
const player = get.player();
const delt = player.countCards("h") - player.maxHp;
let str = "";
if (delt > 0) str += `弃置${get.cnNumber(delt)}张牌`;
else if (delt == 0) str += `点击“确定”`;
else str += `摸${get.cnNumber(-delt)}张牌`;
return `${str},然后选择两名角色,前者视为对后者使用一张【杀】,且这两者的非锁定技失效。`;
},
content: function* (event, map) {
var player = map.player;
if (player.countCards("h") < player.maxHp) yield player.drawTo(player.maxHp);
if (game.countPlayer() < 2) {
event.finish();
return;
}
var result = yield player
.chooseTarget("悖逆:请选择两名角色", "前者视为对后者使用一张【杀】,且这两名角色的非锁定技失效直到回合结束。", true, 2, (card, player, target) => {
var sha = new lib.element.VCard({ name: "sha", isCard: true });
if (ui.selected.targets.length) {
var targetx = ui.selected.targets[0];
return targetx.canUse(sha, target, false);
}
return lib.filter.cardEnabled(sha, target);
})
.set("targetprompt", ["打人", "被打"])
.set("multitarget", true)
.set("ai", target => {
var aiTargets = get.event("aiTargets");
if (aiTargets) {
return aiTargets[ui.selected.targets.length] == target ? 10 : 0;
}
return 0;
})
.set(
"aiTargets",
(() => {
var targets = [],
eff = 0;
var sha = new lib.element.VCard({ name: "sha", isCard: true });
for (var user of game.filterPlayer()) {
for (var target of game.filterPlayer()) {
if (user == target) continue;
var targetsx = [user, target];
targetsx.forEach(i => i.addSkill("dcbeini_fengyin2"));
var effx = get.effect(target, sha, user, player);
targetsx.forEach(i => i.removeSkill("dcbeini_fengyin2"));
if (user == player) effx += 1;
if (get.attitude(player, user) > 0) effx -= 0.1;
if (effx > eff) {
eff = effx;
targets = targetsx;
}
}
}
if (targets.length) return targets;
return null;
})()
);
if (result.bool) {
var user = result.targets[0],
target = result.targets[1];
result.targets.forEach(i => i.addTempSkill("dcbeini_fengyin"));
var sha = new lib.element.VCard({ name: "sha", isCard: true });
if (user.canUse(sha, target, false)) user.useCard(sha, target, false, "noai");
}
},
ai: {
order: 0.1,
result: {
player: function (player) {
if (player.countCards("h") - player.maxHp >= 3) return 1;
return game.hasPlayer(current => get.attitude(player, current) <= 0) ? 1 : 0;
},
},
},
subSkill: {
fengyin: {
inherit: "fengyin",
},
fengyin2: {
inherit: "fengyin",
},
},
},
dcshizong: {
audio: 2,
enable: "chooseToUse",
hiddenCard: function (player, name) {
if (get.type(name) != "basic") return false;
return player.countCards("he") >= player.countMark("dcshizong") + 1;
},
filter: function (event, player) {
if (event.type == "wuxie" || event.dcshizong) return false;
if (player.countCards("he") < player.countMark("dcshizong") + 1) return false;
for (const name of lib.inpile) {
if (get.type(name) != "basic") continue;
const card = { name: name, isCard: true };
if (event.filterCard(card, player, event)) return true;
if (name == "sha") {
for (const nature of lib.inpile_nature) {
card.nature = nature;
if (event.filterCard(card, player, event)) return true;
}
}
}
return false;
},
chooseButton: {
dialog: function (event, player) {
const vcards = get.inpileVCardList(info => {
if (info[0] != "basic") return;
const card = { name: info[2], nature: info[3], isCard: true };
return event.filterCard(card, player, event);
});
return ui.create.dialog("恃纵", [vcards, "vcard"], "hidden");
},
check: function (button) {
if (get.event().getParent().type != "phase") return 1;
const player = get.player();
const card = { name: button.link[2], nature: button.link[3] };
if (
game.hasPlayer(current => {
return player.canUse(card, current) && get.effect(current, card, player, player) > 0;
})
) {
switch (button.link[2]) {
case "tao":
return 5;
case "jiu":
return 3.01;
case "sha":
if (button.link[3] == "fire") return 2.95;
else if (button.link[3] == "thunder") return 2.92;
else return 2.9;
}
}
return 0;
},
backup: function (links, player) {
return {
filterCard: true,
filterTarget: lib.filter.notMe,
selectTarget: 1,
selectCard: () => get.player().countMark("dcshizong") + 1,
viewAs: {
name: links[0][2],
nature: links[0][3],
suit: "none",
number: null,
isCard: true,
},
position: "he",
popname: true,
ignoreMod: true,
ai1: function (card) {
return 1 / (1.1 + Math.max(-1, get.value(card)));
},
ai2: function (target) {
return get.attitude(get.player(), target);
},
precontent: function* (event, map) {
var player = map.player,
target = event.result.targets[0];
player.logSkill("dcshizong", target);
if (!player.countMark("dcshizong")) player.when({ global: "phaseAfter" }).then(() => delete player.storage.dcshizong);
player.addMark("dcshizong", 1, false);
yield player.give(event.result.cards.slice(), target);
var viewAs = new lib.element.VCard({
name: event.result.card.name,
nature: event.result.card.nature,
isCard: true,
});
var result = yield target
.chooseCard("恃纵:是否将一张牌置于牌堆底?", `若如此做,${get.translation(player)}视为使用一张${get.translation(viewAs.nature)}【${get.translation(viewAs.name)}】`, "he")
.set("ai", card => {
if (get.event("goon")) return 7 - get.value(card);
return 0;
})
.set("goon", get.attitude(target, player) * (player.getUseValue(viewAs) || 1) >= 1);
var card = event.result.cards[0];
if (result.bool) {
var card = result.cards[0];
game.delayex();
var next = target.loseToDiscardpile(card, ui.cardPile);
next.log = false;
if (get.position(card) == "e") {
game.log(target, "将", card, "置于了牌堆底");
} else {
next.blank = true;
game.log(target, "将一张牌置于了牌堆底");
}
result = yield next;
game.broadcastAll(viewAs => {
lib.skill.dcshizong_backup2.viewAs = viewAs;
}, lib.skill.dcshizong_backup.viewAs);
var evt = event.getParent();
evt.set("_backupevent", "dcshizong_backup2");
evt.set("openskilldialog", `请选择${get.translation(viewAs.nature)}${get.translation(viewAs.name)}的目标`);
evt.backup("dcshizong_backup2");
evt.set("norestore", true);
evt.set("custom", {
add: {},
replace: { window: function () {} },
});
evt.goto(0);
if (target != _status.currentPhase) player.tempBanSkill("dcshizong");
} else {
target.chat("不放!");
game.log(target, "选择不将牌置于牌堆底");
var evt = event.getParent();
evt.set("dcshizong", true);
evt.goto(0);
}
game.delayx();
},
ai: {
order: 10,
},
};
},
prompt: function (links, player) {
return `###恃纵:选择要交出的牌和目标角色###将${get.cnNumber(player.countMark("dcshizong") + 1)}张牌交给一名其他角色,其可以选择将一张牌置于牌堆底,视为你使用一张${get.translation(links[0][3] || "")}${get.translation(links[0][2])}。`;
},
},
ai: {
order: function () {
const player = get.player(),
event = get.event();
if (event.filterCard({ name: "jiu" }, player, event) && get.effect(player, { name: "jiu" }) > 0) {
return get.order({ name: "jiu" }) + 0.1;
}
return get.order({ name: "sha" }) + 0.1;
},
respondSha: true,
fireAttack: true,
respondShan: true,
skillTagFilter: function (player, tag, arg) {
if (tag == "fireAttack") return true;
if (player.countCards("he") < player.countMark("dcshizong") + 1) return false;
if (tag == "respondSha" && arg != "use") return false;
},
result: {
player: function (player) {
if (_status.event.dying) return get.attitude(player, _status.event.dying);
return 1;
},
},
},
subSkill: {
backup: {},
backup2: {
filterCard: () => false,
selectCard: -1,
precontent: function () {
delete event.result.skill;
},
},
},
},
//张曼成
dclvecheng: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: lib.filter.notMe,
content: function () {
player.addTempSkill("dclvecheng_xiongluan");
player.markAuto("dclvecheng_xiongluan", [target]);
var cards = player.getCards("h", "sha");
if (cards.length) player.addGaintag(cards, "dclvecheng_xiongluan");
},
ai: {
threaten: 3.1,
order: 3.5,
expose: 0.2,
result: {
target: function (player, target) {
if (player.getStorage("dclvecheng_xiongluan").includes(target)) return 0;
if (
target.hasSkillTag(
"freeShan",
false,
{
player: player,
},
true
)
)
return -0.6;
var hs = player.countCards("h", card => {
if (!player.canUse(card, target)) return false;
return get.name(card) == "sha" && get.effect(target, card, player, player) > 0;
});
var ts = target.hp;
if (hs >= ts && ts > 1) return -2;
return -1;
},
},
},
subSkill: {
xiongluan: {
trigger: { player: "phaseEnd" },
charlotte: true,
forced: true,
popup: false,
onremove: function (player, skill) {
player.removeGaintag("dclvecheng_xiongluan");
delete player.storage[skill];
},
filter: function (event, player) {
return player.getStorage("dclvecheng_xiongluan").some(i => i.isIn());
},
content: function () {
"step 0";
event.targets = player.getStorage("dclvecheng_xiongluan").slice();
event.targets.sortBySeat();
"step 1";
if (!event.targets.length) {
event.finish();
return;
}
var target = event.targets.shift();
event.target = target;
target.showHandcards();
var cards = target.getCards("h", "sha");
if (!cards.length) event.redo();
else event.forced = false;
"step 2";
var forced = event.forced;
var prompt2 = forced ? "掠城:选择对" + get.translation(player) + "使用的【杀】" : "掠城:是否依次对" + get.translation(player) + "使用所有的【杀】?";
target
.chooseToUse(
forced,
function (card, player, event) {
if (get.itemtype(card) != "card" || get.name(card) != "sha") return false;
return lib.filter.filterCard.apply(this, arguments);
},
prompt2
)
.set("targetRequired", true)
.set("complexSelect", true)
.set("filterTarget", function (card, player, target) {
if (target != _status.event.sourcex && !ui.selected.targets.includes(_status.event.sourcex)) return false;
return lib.filter.targetEnabled.apply(this, arguments);
})
.set("sourcex", player);
"step 3";
if (result.bool) {
if (target.countCards("h", "sha")) {
event.forced = true;
event.goto(2);
return;
}
}
event.forced = false;
event.goto(1);
},
intro: {
content: "对$使用“掠城”【杀】无任何次数限制",
},
mod: {
cardUsableTarget: function (card, player, target) {
if (!card.cards || card.cards.length != 1) return;
if (card.name == "sha" && card.cards[0].hasGaintag("dclvecheng_xiongluan") && player.getStorage("dclvecheng_xiongluan").includes(target)) return true;
},
},
},
},
},
dczhongji: {
audio: 2,
trigger: { player: "useCard" },
filter: function (event, player) {
if (player.countCards("h") >= player.maxHp) return false;
var suit = get.suit(event.card);
return !lib.suit.includes(suit) || !player.countCards("h", { suit: suit });
},
check: function (event, player) {
var num = Math.min(20, player.maxHp - player.countCards("h"));
if (num <= 0) return false;
var numx =
player.getHistory("useSkill", evt => {
return evt.skill == "dczhongji";
}).length + 1;
if (numx > num) return false;
if (_status.currentPhase != player) return true;
if (
player.hasCard(card => {
var suit = get.suit(card);
return (
player.hasValueTarget(card) &&
!player.hasCard(cardx => {
return cardx != card && get.suit(cardx) == suit;
})
);
})
)
return false;
return true;
},
prompt2: function (event, player) {
var num = Math.min(20, player.maxHp - player.countCards("h"));
var str = num > 0 ? "摸" + get.cnNumber(num) + "张牌,然后" : "";
return (
str +
"弃置" +
get.cnNumber(
1 +
player.getHistory("useSkill", evt => {
return evt.skill == "dczhongji";
}).length
) +
"张牌"
);
},
content: function () {
"step 0";
var num = Math.min(20, player.maxHp - player.countCards("h"));
if (num > 0) player.draw(num);
"step 1";
var num = player.getHistory("useSkill", evt => {
return evt.skill == "dczhongji";
}).length;
player.chooseToDiscard("螽集:请弃置" + get.cnNumber(num) + "张牌", "he", true, num).set("ai", get.unuseful);
},
ai: {
threaten: 3.2,
},
},
//乐周妃
dclingkong: {
audio: 2,
trigger: {
global: "phaseBefore",
player: "enterGame",
},
forced: true,
filter: function (event, player) {
return event.name != "phase" || game.phaseNumber == 0;
},
content: function () {
"step 0";
var cards = player.getCards("h");
player.addGaintag(cards, "dclingkong_tag");
},
mod: {
ignoredHandcard: function (card, player) {
if (card.hasGaintag("dclingkong_tag")) {
return true;
}
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && card.hasGaintag("dclingkong_tag")) {
return false;
}
},
},
group: "dclingkong_marker",
subSkill: {
marker: {
audio: "dclingkong",
trigger: { player: ["gainAfter", "loseAsyncAfter"] },
forced: true,
filter: (event, player) => {
const phaseDraw = event.getParent("phaseDraw");
if (phaseDraw && phaseDraw.player === player) return false;
const evt = player.getHistory("gain").find(i => {
const phaseDraw = i.getParent("phaseDraw");
return !phaseDraw || phaseDraw.player !== player;
});
if (!evt) return false;
if (event.name == "gain") {
if (evt != event || event.getlx === false) return false;
} else if (evt.getParent() != event) return false;
const hs = player.getCards("h");
if (!hs.length) return false;
const cards = event.getg(player);
return cards.some(card => hs.includes(card));
},
content: function () {
var hs = player.getCards("h"),
cards = trigger.getg(player);
cards = cards.filter(card => hs.includes(card));
player.addGaintag(cards, "dclingkong_tag");
game.delayx();
},
},
},
},
dcxianshu: {
audio: 2,
enable: "phaseUse",
filter: (event, player) => {
return game.hasPlayer(current => current != player) && player.hasCard(card => card.hasGaintag("dclingkong_tag"), "h");
},
filterCard: card => card.hasGaintag("dclingkong_tag"),
filterTarget: lib.filter.notMe,
discard: false,
lose: false,
delay: false,
position: "h",
check: card => {
const player = _status.event.player,
event = _status.event,
color = get.color(card);
if (color == "red") {
return (event.getTempCache("dcxianshu", "red") ||
event.putTempCache(
"dcxianshu",
"red",
game
.hasPlayer(current => {
return current != player && current.hp <= player.hp && current.isDamaged() && get.recoverEffect(current, player, player) > 0;
})
.toString()
)) == "true"
? 7 - get.value(card)
: 0;
} else if (color == "black") {
return (event.getTempCache("dcxianshu", "black") ||
event.putTempCache(
"dcxianshu",
"black",
game
.hasPlayer(current => {
return current != player && current.hp >= player.hp && get.effect(current, { name: "losehp" }, player, player) > 0;
})
.toString()
)) == "true"
? 7 - get.value(card)
: 0;
}
return 6 - get.value(card);
},
content: function () {
"step 0";
player.give(cards, target, true);
event.color = get.color(cards[0], player);
"step 1";
if (target.isIn()) {
var num = Math.min(Math.abs(target.getHp() - player.getHp()), 5);
if (num > 0) player.draw(num);
}
"step 2";
if (event.color == "red") {
if (target.getHp() <= player.getHp() && target.isDamaged()) target.recover();
} else if (event.color == "black") {
if (target.getHp() >= player.getHp()) target.loseHp();
}
},
ai: {
combo: "dclingkong",
order: 10,
result: {
player: function (player, target) {
if (!ui.selected.cards.length) return 0;
let num = target.getHp() - player.getHp();
const card = ui.selected.cards[0],
color = get.color(card);
if (color == "red" && target.getHp() <= player.getHp() && target.isDamaged()) num++;
else if (color == "black" && target.getHp() >= player.getHp()) num--;
return Math.min(Math.abs(num), 5) * 1.1;
},
target: function (player, target) {
if (!ui.selected.cards.length) return 0;
const card = ui.selected.cards[0],
color = get.color(card),
val = get.value(card, target);
if (color == "red" && target.getHp() <= player.getHp() && target.isDamaged()) return get.recoverEffect(target, player, target) + val / 1.4;
else if (color == "black" && target.getHp() >= player.getHp()) return get.effect(target, { name: "losehp" }, player, target) + val / 1.4;
return val / 1.4;
},
},
},
},
//吴班
dcyouzhan: {
audio: 2,
trigger: {
global: ["loseAfter", "equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
direct: true,
filter: function (event, player) {
if (player != _status.currentPhase) return false;
return game.hasPlayer(current => {
if (current == player) return false;
var evt = event.getl(current);
return evt && evt.cards2.length;
});
},
content: function () {
"step 0";
var targets = game.filterPlayer(current => {
if (current == player) return false;
var evt = trigger.getl(current);
return evt && evt.cards2.length;
});
event.targets = targets;
player.logSkill("dcyouzhan", targets);
"step 1";
event.target = targets.shift();
event.num = trigger.getl(event.target).cards2.length;
"step 2";
player.draw().gaintag = ["dcyouzhan"];
player.addTempSkill("dcyouzhan_limit");
target.addTempSkill("dcyouzhan_effect");
target.addMark("dcyouzhan_effect", 1, false);
target.addTempSkill("dcyouzhan_draw");
if (--event.num) event.redo();
"step 3";
if (targets.length) {
event.goto(1);
}
},
ai: {
damageBonus: true,
skillTagFilter: function (player, tag, arg) {
if (!arg || !arg.target || !arg.target.hasSkill("dcyouzhan_effect")) return false;
},
},
subSkill: {
effect: {
audio: "dcyouzhan",
trigger: {
player: "damageBegin3",
},
filter: function (event, player) {
return player.hasMark("dcyouzhan_effect");
},
forced: true,
charlotte: true,
onremove: true,
content: function () {
"step 0";
trigger.num += player.countMark("dcyouzhan_effect");
player.removeSkill("dcyouzhan_effect");
},
mark: true,
intro: {
content: "本回合下一次受到的伤害+#",
},
ai: {
effect: {
target: function (card, player, target) {
if (get.tag(card, "damage")) return 1 + 0.5 * target.countMark("dcyouzhan_effect");
},
},
},
},
draw: {
trigger: {
global: "phaseJieshuBegin",
},
forced: true,
charlotte: true,
filter: function (event, player) {
return !player.getHistory("damage").length;
},
content: function () {
player.draw(Math.min(3, player.getHistory("lose").length));
},
},
limit: {
charlotte: true,
onremove: function (player) {
player.removeGaintag("dcyouzhan");
},
mod: {
ignoredHandcard: function (card, player) {
if (card.hasGaintag("dcyouzhan")) return true;
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && card.hasGaintag("dcyouzhan")) return false;
},
},
},
},
},
//乐蔡文姬
dcshuangjia: {
audio: 2,
trigger: {
global: "phaseBefore",
player: "enterGame",
},
forced: true,
filter: function (event, player) {
return event.name != "phase" || game.phaseNumber == 0;
},
content: function () {
"step 0";
var cards = player.getCards("h");
player.addGaintag(cards, "dcshuangjia_tag");
},
mod: {
ignoredHandcard: function (card, player) {
if (card.hasGaintag("dcshuangjia_tag")) {
return true;
}
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && card.hasGaintag("dcshuangjia_tag")) {
return false;
}
},
globalTo: function (from, to, distance) {
return (
distance +
Math.min(
5,
to.countCards("h", card => card.hasGaintag("dcshuangjia_tag"))
)
);
},
},
},
dcbeifen: {
audio: 2,
trigger: {
player: ["loseAfter"],
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
filter: function (event, player) {
var evt = event.getl(player);
if (!evt || !evt.hs || !evt.hs.length) return false;
if (event.name == "lose") {
for (var i in event.gaintag_map) {
if (event.gaintag_map[i].includes("dcshuangjia_tag")) return true;
}
return false;
}
return player.hasHistory("lose", evt => {
if (event != evt.getParent()) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("dcshuangjia_tag")) return true;
}
return false;
});
},
forced: true,
content: function () {
var suits = lib.suit.slice();
player.countCards("h", card => {
if (!card.hasGaintag("dcshuangjia_tag")) return false;
suits.remove(get.suit(card));
});
var cards = [];
while (suits.length) {
var suit = suits.shift();
var card = get.cardPile(cardx => {
return get.suit(cardx, false) == suit;
});
if (card) cards.push(card);
}
if (cards.length) {
player.gain(cards, "gain2");
}
},
mod: {
cardUsable: function (card, player) {
var len = player.countCards("h");
var cnt = player.countCards("h", card => card.hasGaintag("dcshuangjia_tag"));
if (2 * cnt < len) return Infinity;
},
targetInRange: function (card, player) {
var len = player.countCards("h");
var cnt = player.countCards("h", card => card.hasGaintag("dcshuangjia_tag"));
if (2 * cnt < len) return true;
},
aiOrder: function (player, card, num) {
if (get.itemtype(card) == "card" && card.hasGaintag("dcshuangjia_tag")) {
var suits = lib.suit.slice();
player.countCards("h", cardx => {
if (!cardx.hasGaintag("dcshuangjia_tag")) return false;
if (card == cardx) return false;
suits.remove(get.suit(cardx));
});
if (suits.length) return num + suits.length * 2.5;
}
},
},
},
//孟优
dcmanzhi: {
audio: 2,
trigger: { player: ["phaseZhunbeiBegin", "phaseJieshuBegin"] },
filter: function (event, player) {
if (event.name == "phaseJieshu") {
var del = 0;
game.getGlobalHistory("changeHp", evt => {
if (evt.player != player) return;
for (var phase of lib.phaseName) {
var evtx = evt.getParent(phase);
if (evtx && evtx.name == phase) {
del += evt.num;
break;
}
}
});
if (del != 0) return false;
}
return game.hasPlayer(current => {
if (current == player) return false;
return (!player.hasSkill("dcmanzhi_1") && current.countCards("he")) || (!player.hasSkill("dcmanzhi_2") && current.countCards("hej"));
});
},
direct: true,
content: function () {
"step 0";
if (_status.connectMode)
game.broadcastAll(function () {
_status.noclearcountdown = true;
});
player
.chooseTarget(get.prompt2("dcmanzhi"), (card, player, target) => {
if (player == target) return false;
return (!player.hasSkill("dcmanzhi_1") && target.countCards("he")) || (!player.hasSkill("dcmanzhi_2") && target.countCards("hej"));
})
.set("ai", target => {
return 1 - get.attitude(get.player(), target);
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
var choices = [];
var choiceList = ["令其交给你两张牌,然后其视为使用一张无距离限制的【杀】", "你获得其区域内的至多两张牌,然后交给其等量的牌并摸一张牌"];
var chosen = [player.hasSkill("dcmanzhi_1"), player.hasSkill("dcmanzhi_2")];
if (target.countCards("he") && (!chosen[0] || trigger.name == "phaseZhunbei")) choices.push("选项一");
else choiceList[0] = '' + choiceList[0] + (chosen[0] ? "(已被选择过)" : "") + "";
if (target.countCards("hej") && (!chosen[1] || trigger.name == "phaseZhunbei")) choices.push("选项二");
else choiceList[1] = '' + choiceList[1] + (chosen[1] ? "(已被选择过)" : "") + "";
if (trigger.name == "phaseJieshu") choices.push("cancel2");
player
.chooseControl(choices)
.set("choiceList", choiceList)
.set("ai", () => {
return _status.event.choice;
})
.set(
"choice",
(function () {
if (target.getUseValue({ name: "sha" }, false) > 5 && !player.hasShan() && trigger.name == "phaseZhunbei") return 1;
return 0;
})()
)
.set("prompt", "蛮智:请选择一项");
} else {
if (_status.connectMode) {
game.broadcastAll(function () {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
event.finish();
}
"step 2";
if (_status.connectMode) {
game.broadcastAll(function () {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
if (result.control == "cancel2") {
event.finish();
return;
}
player.logSkill("dcmanzhi", target);
if (result.control == "选项一") {
player.addTempSkill("dcmanzhi_1");
target.chooseCard(Math.min(2, target.countCards("he")), "he", "蛮智:请交给" + get.translation(player) + "两张牌", true);
} else {
player.addTempSkill("dcmanzhi_2");
player.gainPlayerCard(target, "hej", [1, 2], true);
event.goto(5);
}
"step 3";
if (result.bool) {
target.give(result.cards, player);
} else event.finish();
"step 4";
target.chooseUseTarget("sha", true, "nodistance");
event.finish();
"step 5";
if (result.bool && target.isIn()) {
var num = result.cards.length,
hs = player.getCards("he");
if (!hs.length) event.finish();
else if (hs.length < num) event._result = { bool: true, cards: hs };
else player.chooseCard("he", true, num, "交给" + get.translation(target) + get.cnNumber(num) + "张牌");
} else event.finish();
"step 6";
if (result.bool) {
player.give(result.cards, target);
player.draw();
}
},
subSkill: {
1: { charlotte: true },
2: { charlotte: true },
},
},
//孙綝
dczigu: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterCard: true,
position: "he",
selectCard: 1,
check: function (card) {
var player = _status.event.player;
if (!player.hasSkill("dczuowei")) return 6 - get.value(card);
if (player.countCards("h") == player.countCards("e") + 1 && !player.hasCard(card => player.hasValueTarget(card), "h")) {
if (get.position(card) == "e") return 0;
return 8 - get.value(card);
}
return 6 - get.value(card);
},
content: function () {
"step 0";
var targets = game.filterPlayer(current => {
return current.countGainableCards(player, "e");
});
if (targets.length == 0) event._result = { bool: false };
else if (targets.length == 1) event._result = { bool: true, targets: targets };
else
player
.chooseTarget("自固:获得一名角色装备区里的一张牌", true, (card, player, target) => {
return target.countGainableCards(player, "e");
})
.set("ai", target => {
if (target == _status.event.player) return 10;
if (get.attitude(_status.event.player, target) < 0) {
if (
target.hasCard(card => {
return get.value(card, player) >= 6;
})
)
return 12;
return 8;
}
return 0;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.gainPlayerCard("e", target, true);
}
"step 2";
if (!result.bool || target == player || !result.cards || !result.cards.some(i => get.owner(i) == player)) player.draw();
},
ai: {
order: function (item, player) {
if (!player.hasSkill("dczuowei")) return 9;
if (player.countCards("h") == player.countCards("e") + 1 && !player.hasCard(card => player.hasValueTarget(card), "h")) return 9;
return 1;
},
result: {
player: 1,
},
},
},
dczuowei: {
audio: 2,
trigger: { player: "useCard" },
filter: function (event, player) {
if (_status.currentPhase != player) return false;
if (!player.hasSkill("dczuowei_ban")) return true;
return Math.sign(player.countCards("h") - Math.max(1, player.countCards("e"))) >= 0;
},
direct: true,
locked: false,
content: function () {
"step 0";
var hs = player.countCards("h");
var es = Math.max(1, player.countCards("e"));
var sign = Math.sign(hs - es);
event.sign = sign;
if (sign > 0) player.chooseBool(get.prompt("dczuowei"), "令" + get.translation(trigger.card) + "不可被响应").set("ai", () => 1);
else if (sign == 0)
player.chooseTarget(get.prompt("dczuowei"), "对一名其他角色造成1点伤害", lib.filter.notMe).set("ai", target => {
return get.damageEffect(target, _status.event.player, _status.event.player);
});
else player.chooseBool(get.prompt("dczuowei"), "摸两张牌,然后本回合你不能再触发该分支").set("ai", () => 1);
"step 1";
if (!result.bool) event.finish();
else if (event.sign <= 0 && !event.isMine() && !event.isOnline()) game.delayx();
"step 2";
var sign = event.sign;
if (sign > 0) {
player.logSkill("dczuowei");
trigger.directHit.addArray(game.players);
event.finish();
} else if (sign == 0) {
var target = result.targets[0];
player.logSkill("dczuowei", target);
target.damage();
} else {
player.logSkill("dczuowei");
player.draw(2);
player.addTempSkill("dczuowei_ban");
}
},
subSkill: {
ban: { charlotte: true },
},
mod: {
aiValue: function (player, card, num) {
if (_status.currentPhase != player) return;
const event = get.event();
if (!player.isPhaseUsing()) return;
if (event.type != "phase") return;
const cardsh = [],
cardse = [];
for (const cardx of ui.selected.cards) {
const pos = get.position(cardx);
if (pos == "h") cardsh.add(cardx);
else if (pos == "e") cardse.add(cardx);
}
const hs = player.countCards("h") - cardsh.length,
es = Math.max(1, player.countCards("e") - cardse.length);
const delt = hs - es;
if (delt <= 0) return;
if (get.position(card) == "h" && delt == 1) return num / 1.25;
},
aiUseful: function () {
return lib.skill.dczuowei.mod.aiValue.apply(this, arguments);
},
aiOrder: function (player, card, num) {
if (player.hasSkill("dczuowei_ban") || _status.currentPhase != player) return;
const cardsh = [],
cardse = [];
const pos = get.position(card);
if (pos == "h") cardsh.add(card);
else if (pos == "e") cardse.add(card);
if (get.tag(card, "draw") || get.tag(card, "gain")) {
const hs = player.countCards("h") - cardsh.length,
es = Math.max(1, player.countCards("e") - cardse.length + (get.type(card) == "equip"));
if ((player.hasSkill("dczuowei_ban") && hs < es) || hs == es) return num + 10;
return num / 5;
}
},
},
ai: {
threaten: 3,
reverseEquip: true,
effect: {
player_use: function (card, player, target, current) {
if (_status.currentPhase != player) return;
if (get.type(card) == "equip" && get.cardtag(card, "gifts")) return;
if (player.countCards("h") > Math.max(1, player.countCards("e"))) return [1, 3];
},
},
},
},
//刘宠骆俊
dcminze: {
audio: 2,
enable: "phaseUse",
filterTarget: function (card, player, target) {
if (player.getStorage("dcminze_targeted").includes(target)) return false;
return target.countCards("h") < player.countCards("h");
},
filterCard: function (card, player) {
if (!ui.selected.cards.length) return true;
return get.name(ui.selected.cards[0]) != get.name(card);
},
selectCard: [1, 2],
complexCard: true,
position: "he",
discard: false,
lose: false,
delay: false,
group: "dcminze_draw",
content: function () {
player.give(cards, target);
player.addTempSkill("dcminze_targeted", "phaseUseAfter");
player.markAuto("dcminze_targeted", [target]);
player.addTempSkill("dcminze_given");
player.markAuto(
"dcminze_given",
cards.map(i => get.name(i, player))
);
},
ai: {
order: 6.5,
expose: 0.2,
},
subSkill: {
targeted: { onremove: true, charlotte: true },
given: {
charlotte: true,
onremove: true,
intro: {
content: "本回合以此法交出的牌名:$",
},
},
draw: {
trigger: { player: "phaseJieshuBegin" },
filter: function (event, player) {
return player.getStorage("dcminze_given").length;
},
forced: true,
locked: false,
content: function () {
var num = Math.min(5, player.getStorage("dcminze_given").length) - player.countCards("h");
if (num > 0) player.draw(num);
},
},
},
},
dcjini: {
audio: 2,
trigger: { player: "damageEnd" },
direct: true,
filter: function (event, player) {
return player.maxHp - player.countMark("dcjini_counted") > 0;
},
content: function () {
"step 0";
player.chooseCard(get.prompt2("dcjini"), [1, player.maxHp - player.countMark("dcjini_counted")], lib.filter.cardRecastable).set("ai", card => {
return 6 - get.value(card);
});
"step 1";
if (result.bool) {
var cards = result.cards;
player.logSkill("dcjini");
player.addTempSkill("dcjini_counted");
player.addMark("dcjini_counted", cards.length, false);
event.recast = player.recast(cards);
} else event.finish();
"step 2";
if (trigger.source && trigger.source.isIn() && player.hasHistory("gain", evt => evt.getParent(2) == event.recast && evt.cards.some(value => get.name(value) == "sha"))) {
player
.chooseToUse(function (card) {
if (get.name(card) != "sha") return false;
return lib.filter.filterCard.apply(this, arguments);
}, "击逆:是否对" + get.translation(trigger.source) + "使用一张不可被响应的杀?")
.set("complexSelect", true)
.set("filterTarget", function (card, player, target) {
if (target != _status.event.sourcex && !ui.selected.targets.includes(_status.event.sourcex)) return false;
return lib.filter.targetEnabled.apply(this, arguments);
})
.set("sourcex", trigger.source)
.set("oncard", () => {
_status.event.directHit.addArray(game.players);
});
}
},
subSkill: {
counted: {
onremove: true,
charlotte: true,
},
},
},
//乐綝
dcporui: {
audio: 2,
trigger: { global: "phaseJieshuBegin" },
filter: function (event, player) {
if (player == event.player) return false;
if (player.countMark("dcporui_round") >= (player.hasMark("dcgonghu_basic") ? 2 : 1) || player.countCards("h") == 0) return false;
return (
game.hasPlayer(current => {
if (current == player || current == event.player) return false;
return current.hasHistory("lose", function (evt) {
return evt.cards2.length > 0;
});
}) && player.countCards("he") > 0
);
},
direct: true,
content: function () {
"step 0";
var map = {};
game.countPlayer(function (current) {
if (current == player || current == trigger.player) return false;
if (
current.hasHistory("lose", function (evt) {
return evt.cards2.length > 0;
})
)
map[current.playerid] =
Math.min(
5,
current.getHistory("lose").reduce(function (num, evt) {
return num + evt.cards2.length;
}, 0)
) + 1;
});
player
.chooseCardTarget({
prompt: get.prompt("dcporui"),
prompt2: get.skillInfoTranslation("dcporui", player),
filterCard: function (card, player) {
return lib.filter.cardDiscardable(card, player, "dcporui");
},
position: "he",
filterTarget: function (card, player, target) {
return Object.keys(_status.event.map).includes(target.playerid);
},
ai1: function (card) {
return 7 - get.value(card);
},
ai2: function (target) {
return get.effect(target, { name: "sha" }, _status.event.player, _status.event.player) * _status.event.map[target.playerid];
},
})
.set("map", map);
"step 1";
if (result.bool) {
var target = result.targets[0],
cards = result.cards;
event.target = target;
player.logSkill("dcporui", target);
player.discard(cards);
event.num2 = Math.min(
5,
target.getHistory("lose").reduce(function (num, evt) {
return num + evt.cards2.length;
}, 0)
);
event.num = event.num2 + 1;
player.addTempSkill("dcporui_round", "roundStart");
player.addMark("dcporui_round", 1, false);
} else event.finish();
"step 2";
var card = { name: "sha", isCard: true, storage: { dcporui: true } };
if (player.canUse(card, target, false) && target.isIn()) {
player.useCard(card, target);
event.num--;
} else event.goto(4);
"step 3";
if (event.num > 0) event.goto(2);
"step 4";
if (!player.hasMark("dcgonghu_damage") && target.isIn()) {
var cards = player.getCards("h");
if (cards.length == 0) event._result = { bool: false };
else if (cards.length <= event.num2) event._result = { bool: true, cards: cards };
else player.chooseCard("破锐:交给" + get.translation(target) + get.cnNumber(event.num2) + "张手牌", true, event.num2);
} else event.finish();
"step 5";
if (result.bool) {
player.give(result.cards, target);
}
event.finish();
"step 6";
if (player.hasMark("dcgonghu_basic")) {
if (
!target.hasHistory("damage", evt => {
return evt.card && evt.card.storage && evt.card.storage.dcporui && evt.getParent("dcporui") == event;
})
) {
player.recover();
}
}
},
subSkill: {
round: { charlotte: true, onremove: true },
},
ai: {
expose: 0.4,
threaten: 3.8,
},
},
dcgonghu: {
audio: 2,
trigger: {
player: ["loseAfter", "damageEnd"],
source: "damageSource",
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
filter: function (event, player) {
if (event.name == "damage") {
if (player.hasMark("dcgonghu_damage")) return false;
var num = 0;
player.getHistory("damage", evt => (num += evt.num));
player.getHistory("sourceDamage", evt => (num += evt.num));
return num > 1;
}
if (!_status.currentPhase || _status.currentPhase == player) return false;
if (player.hasMark("dcgonghu_basic")) return false;
if (_status.currentPhase && _status.currentPhase == player) return false;
var evt = event.getl(player);
if (!evt || !evt.cards2 || !evt.cards2.some(i => get.type2(i, player) == "basic")) return false;
var num = 0;
player.getHistory("lose", function (evtx) {
if (num < 2) {
if (evtx && evtx.cards2) num += evtx.cards2.filter(i => get.type2(i, player) == "basic").length;
}
});
return num >= 2;
},
group: ["dcgonghu_basic", "dcgonghu_trick"],
content: function () {
player.addMark("dcgonghu_" + (trigger.name == "damage" ? "damage" : "basic"), 1, false);
game.log(player, "修改了技能", "#g【破锐】");
},
ai: {
combo: "dcporui",
},
subSkill: {
trick: {
audio: "dcgonghu",
trigger: { player: "useCard2" },
direct: true,
locked: true,
filter: function (event, player) {
if (!player.hasMark("dcgonghu_basic") || !player.hasMark("dcgonghu_damage")) return false;
var card = event.card;
if (get.color(card, false) != "red" || get.type(card, null, true) != "trick") return false;
var info = get.info(card);
if (info.allowMultiple == false) return false;
if (event.targets && !info.multitarget) {
if (
game.hasPlayer(function (current) {
return !event.targets.includes(current) && lib.filter.targetEnabled2(card, player, current);
})
) {
return true;
}
}
return false;
},
content: function () {
"step 0";
var prompt2 = "为" + get.translation(trigger.card) + "增加一个目标";
player
.chooseTarget(get.prompt("dcgonghu_trick"), function (card, player, target) {
var player = _status.event.player;
return !_status.event.targets.includes(target) && lib.filter.targetEnabled2(_status.event.card, player, target);
})
.set("prompt2", prompt2)
.set("ai", function (target) {
var trigger = _status.event.getTrigger();
var player = _status.event.player;
return get.effect(target, trigger.card, player, player);
})
.set("card", trigger.card)
.set("targets", trigger.targets);
"step 1";
if (result.bool) {
if (!event.isMine() && !event.isOnline()) game.delayx();
event.targets = result.targets;
} else {
event.finish();
}
"step 2";
if (event.targets) {
player.logSkill("dcgonghu_trick", event.targets);
trigger.targets.addArray(event.targets);
}
},
},
basic: {
audio: "dcgonghu",
trigger: { player: "useCard" },
forced: true,
filter: function (event, player) {
if (!player.hasMark("dcgonghu_basic") || !player.hasMark("dcgonghu_damage")) return false;
var card = event.card;
return get.color(card, false) == "red" && get.type(card, null, false) == "basic";
},
content: function () {
trigger.directHit.addArray(game.filterPlayer());
game.log(trigger.card, "不可被响应");
},
},
},
},
//张闿
dcxiangshu: {
audio: 2,
trigger: { global: "phaseUseBegin" },
direct: true,
filter: function (event, player) {
return event.player != player && event.player.countCards("h") >= event.player.hp;
},
content: function () {
"step 0";
var list = [0, 1, 2, 3, 4, 5, "cancel2"];
player
.chooseControl(list)
.set("prompt", get.prompt2("dcxiangshu"))
.set("ai", () => {
return _status.event.choice;
})
.set(
"choice",
(function () {
if (get.attitude(player, trigger.player) > 0) return "cancel2";
var cards = trigger.player.getCards("h");
var num = 0;
for (var card of cards) {
if (!trigger.player.hasValueTarget(card)) {
num++;
if (num >= 5) break;
}
}
if (cards.length >= 3 && Math.random() < 0.5) num = Math.max(0, num - 1);
return num;
})()
);
"step 1";
if (result.control != "cancel2") {
player.logSkill("dcxiangshu", trigger.player);
var num = result.index;
player.storage.dcxiangshu_lottery = num;
player.addTempSkill("dcxiangshu_lottery", "phaseUseAfter");
} else event.finish();
"step 2";
player.chooseToDiscard("相鼠:是否弃置一张牌不公布此数字?").set("ai", card => 2 - get.value(card));
"step 3";
if (!result.bool) {
var num = player.storage.dcxiangshu_lottery;
player.markSkill("dcxiangshu_lottery");
player.popup(num);
game.log(player, "选择了数字", "#g" + num);
}
},
subSkill: {
lottery: {
audio: "dcxiangshu",
trigger: { global: "phaseUseEnd" },
charlotte: true,
forced: true,
onremove: true,
logTarget: "player",
filter: function (event, player) {
return typeof player.storage.dcxiangshu_lottery == "number" && Math.abs(event.player.countCards("h") - player.storage.dcxiangshu_lottery) <= 1;
},
content: function () {
var delt = Math.abs(trigger.player.countCards("h") - player.storage.dcxiangshu_lottery);
if (delt <= 1 && trigger.player.countGainableCards("he", player) > 0) {
player.gainPlayerCard(trigger.player, "he", true);
}
if (delt == 0) {
trigger.player.damage(player);
}
},
intro: { content: "猜测的数字为#" },
},
},
},
//裴元绍
dcmoyu: {
audio: 2,
init() {
game.addGlobalSkill("dcmoyu_ai");
},
onremove() {
if (!game.hasPlayer(i => i.hasSkill("dcmoyu"), true)) game.removeGlobalSkill("dcmoyu_ai");
},
enable: "phaseUse",
filter(event, player) {
return game.hasPlayer(current => lib.skill.dcmoyu.filterTarget(null, player, current));
},
filterTarget(card, player, target) {
return player != target && !player.getStorage("dcmoyu_clear").includes(target) && target.countGainableCards(player, "hej");
},
async content(event, trigger, player) {
const target = event.target;
player.addTempSkill("dcmoyu_clear");
player.markAuto("dcmoyu_clear", [target]);
await player.gainPlayerCard(target, "hej", true, 1 + player.hasSkill("dcmoyu_add"));
player.removeSkill("dcmoyu_add");
const num = player.getStorage("dcmoyu_clear").length;
const result = await target
.chooseToUse(function (card, player, event) {
if (get.name(card) != "sha") return false;
return lib.filter.filterCard.apply(this, arguments);
}, "是否对" + get.translation(player) + "使用一张无距离限制的【杀】?")
.set("targetRequired", true)
.set("complexSelect", true)
.set("filterTarget", function (card, player, target) {
if (target != _status.event.sourcex && !ui.selected.targets.includes(_status.event.sourcex)) return false;
return lib.filter.targetEnabled.apply(this, arguments);
})
.set("sourcex", player)
.set("num", num)
.set("oncard", card => {
_status.event.baseDamage = _status.event.getParent().num;
})
.forResult();
if (result.bool) {
if (
player.hasHistory("damage", evt => {
return evt.card && evt.card.name == "sha" && evt.getParent(4) == event;
})
) {
player.tempBanSkill("dcmoyu");
} else {
player.addTempSkill("dcmoyu_add", "phaseChange");
}
}
},
subSkill: {
clear: {
charlotte: true,
onremove: true,
},
ban: {
charlotte: true,
mark: true,
marktext: "欲",
intro: { content: "偷马贼被反打了!" },
},
add: {
charlotte: true,
mark: true,
marktext: "欲",
intro: { content: "欲望加速,下次抢两张!" },
},
ai: {
trigger: { player: "dieAfter" },
filter: () => {
return !game.hasPlayer(i => i.hasSkill("dcmoyu"), true);
},
silent: true,
forceDie: true,
content: () => {
game.removeGlobalSkill("dcmoyu_ai");
},
ai: {
effect: {
target: function (card, player, target, current) {
if (get.type(card) == "delay" && current < 0) {
var currentx = _status.currentPhase;
if (!currentx || !currentx.isIn()) return;
var list = game.filterPlayer(current => {
if (current == target) return true;
if (!current.hasSkill("dcmoyu")) return false;
if (current.hasJudge("lebu")) return false;
return get.attitude(current, target) > 0;
});
list.sortBySeat(currentx);
if (list.indexOf(target) != 0) return "zerotarget";
}
},
},
},
},
},
ai: {
order: 9,
threaten: 2.4,
result: {
target: function (player, target) {
var num = get.sgn(get.attitude(player, target));
var eff = get.effect(target, { name: "shunshou" }, player, player) * num;
if (eff * num > 0) return eff / 10;
if (
player.hasShan() &&
!target.hasSkillTag(
"directHit_ai",
true,
{
target: player,
card: { name: "sha" },
},
true
)
)
return eff;
if (
target.hasSha() &&
player.hp +
player.countCards("hs", function (card) {
var mod2 = game.checkMod(card, player, "unchanged", "cardEnabled2", player);
if (mod2 != "unchanged") return mod2;
var mod = game.checkMod(card, player, player, "unchanged", "cardSavable", player);
if (mod != "unchanged") return mod;
var savable = get.info(card).savable;
if (typeof savable == "function") savable = savable(card, player, player);
return savable;
}) <=
1
)
return 0;
return eff;
},
},
},
},
oldmoyu: {
audio: "dcmoyu",
init: () => {
game.addGlobalSkill("oldmoyu_ai");
},
onremove: () => {
if (!game.hasPlayer(i => i.hasSkill("oldmoyu"), true)) game.removeGlobalSkill("oldmoyu_ai");
},
enable: "phaseUse",
filter: function (event, player) {
return !player.hasSkill("oldmoyu_ban") && game.hasPlayer(current => lib.skill.oldmoyu.filterTarget(null, player, current));
},
filterTarget: function (card, player, target) {
return player != target && !player.getStorage("oldmoyu_clear").includes(target) && target.countGainableCards(player, "hej");
},
content: function () {
"step 0";
player.addTempSkill("oldmoyu_clear");
player.markAuto("oldmoyu_clear", [target]);
player.gainPlayerCard(target, "hej", true);
"step 1";
var num = player.getStorage("oldmoyu_clear").length;
target
.chooseToUse(function (card, player, event) {
if (get.name(card) != "sha") return false;
return lib.filter.filterCard.apply(this, arguments);
}, "是否对" + get.translation(player) + "使用一张无距离限制的【杀】(伤害基数为" + num + ")?")
.set("targetRequired", true)
.set("complexSelect", true)
.set("filterTarget", function (card, player, target) {
if (target != _status.event.sourcex && !ui.selected.targets.includes(_status.event.sourcex)) return false;
return lib.filter.targetEnabled.apply(this, arguments);
})
.set("sourcex", player)
.set("num", num)
.set("oncard", card => {
_status.event.baseDamage = _status.event.getParent().num;
});
"step 2";
if (result.bool) {
if (
player.hasHistory("damage", evt => {
return evt.card && evt.card.name == "sha" && evt.getParent(4) == event;
})
)
player.addTempSkill("oldmoyu_ban");
}
},
subSkill: {
clear: {
charlotte: true,
onremove: true,
},
ban: {
charlotte: true,
mark: true,
marktext: "欲",
intro: { content: "偷马贼被反打了!" },
},
ai: {
trigger: { player: "dieAfter" },
filter: () => {
return !game.hasPlayer(i => i.hasSkill("oldmoyu"), true);
},
silent: true,
forceDie: true,
content: () => {
game.removeGlobalSkill("oldmoyu_ai");
},
ai: {
effect: {
target: function (card, player, target, current) {
if (get.type(card) == "delay" && current < 0) {
var currentx = _status.currentPhase;
if (!currentx || !currentx.isIn()) return;
var list = game.filterPlayer(current => {
if (current == target) return true;
if (!current.hasSkill("oldmoyu")) return false;
if (current.hasJudge("lebu")) return false;
return get.attitude(current, target) > 0;
});
list.sortBySeat(currentx);
if (list.indexOf(target) != 0) return "zerotarget";
}
},
},
},
},
},
ai: {
order: 9,
threaten: 2.4,
result: {
target: function (player, target) {
var num = get.sgn(get.attitude(player, target));
var eff = get.effect(target, { name: "shunshou" }, player, player) * num;
if (eff * num > 0) return eff / 10;
if (
player.hasShan() &&
!target.hasSkillTag(
"directHit_ai",
true,
{
target: player,
card: { name: "sha" },
},
true
)
)
return eff;
if (
target.hasSha() &&
player.hp +
player.countCards("hs", function (card) {
var mod2 = game.checkMod(card, player, "unchanged", "cardEnabled2", player);
if (mod2 != "unchanged") return mod2;
var mod = game.checkMod(card, player, player, "unchanged", "cardSavable", player);
if (mod != "unchanged") return mod;
var savable = get.info(card).savable;
if (typeof savable == "function") savable = savable(card, player, player);
return savable;
}) <=
player.getStorage("oldmoyu_clear").length + 1
)
return 0;
return eff;
},
},
},
},
//张楚
dcjizhong: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: lib.filter.notMe,
selectTarget: 1,
content: function () {
"step 0";
target.draw(2);
"step 1";
var marked = target.hasMark("dcjizhong");
var cards = target.getCards("h");
if (marked) {
if (cards.length <= 3) event._result = { bool: true, cards: cards };
else target.chooseCard(`集众:交给${get.translation(player)}三张手牌`, 3, true);
} else {
target
.chooseCard(`集众:交给${get.translation(player)}三张手牌,或点击“取消”获得“信众”标记`, 3)
.set("ai", card => {
if (get.event("goon")) return 20 - get.value(card);
return 1 - get.value(card);
})
.set("goon", get.attitude(target, player) > 0);
}
"step 2";
if (!result.bool) {
target.addMark("dcjizhong", 1);
} else {
target.give(result.cards, player);
}
},
marktext: "信",
intro: {
name: "信众",
name2: "信众",
markcount: () => 0,
content: "已成为信徒",
},
ai: {
order: 9.5,
result: {
target: function (player, target) {
var num = target.countCards("h");
if (num <= 1) return -num;
if (get.attitude(player, target) > 0) return 1;
return -1 / (num / 2 + 1);
},
},
},
},
dcrihui: {
audio: 2,
trigger: { player: "useCardAfter" },
usable: 1,
filter: function (event, player) {
if (!event.targets || event.targets.length != 1 || event.targets[0] == player) return false;
var card = event.card;
var target = event.targets[0];
var marked = target.hasMark("dcjizhong");
return (get.type(card) == "trick" || (get.color(card) == "black" && get.type(card) == "basic")) && (marked || (!marked && game.hasPlayer(current => current.hasMark("dcjizhong"))));
},
logTarget: event => event.targets[0],
prompt2(event, player) {
const target = event.targets[0];
if (target.hasMark("dcjizhong")) return "获得该角色区域内的一张牌";
else {
const card = { name: event.card.name, nature: event.card.nature, isCard: true };
return "令所有有“信众”的角色依次视为对其使用一张" + get.translation(card);
}
},
check(event, player) {
const target = event.targets[0];
if (target.hasMark("dcjizhong")) {
return get.effect(target, { name: "shunshou_copy" }, event, player) > 0;
} else {
const card = { name: event.card.name, nature: event.card.nature, isCard: true };
let eff = 0;
game.countPlayer(current => {
if (!current.hasMark("dcjizhong") || !current.canUse(card, player, false)) return;
eff += get.effect(target, card, current, player);
});
return eff > 0;
}
},
async content(event, trigger, player) {
const target = trigger.targets[0];
if (target.hasMark("dcjizhong")) {
await player.gainPlayerCard(target, "hej", true);
} else {
const card = { name: trigger.card.name, nature: trigger.card.nature, isCard: true };
const targets = game.filterPlayer(current => current.hasMark("dcjizhong")).sortBySeat(_status.currentPhase);
for (const current of targets) {
if (target.isIn() && current.isIn() && current.canUse(card, target, false)) {
await current.useCard(card, target, false);
}
}
}
},
ai: {
combo: "dcjizhong",
},
},
dcguangshi: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
filter: function (event, player) {
return !game.hasPlayer(current => current != player && !current.hasMark("dcjizhong"));
},
forced: true,
content: function () {
player.draw(2);
player.loseHp();
},
ai: {
combo: "dcjizhong",
},
},
//董绾
dcshengdu: {
audio: 2,
trigger: { player: "phaseBegin" },
direct: true,
content: function () {
"step 0";
player.chooseTarget(get.prompt2("dcshengdu"), lib.filter.notMe).set("ai", target => {
var player = _status.event.player;
var att = get.attitude(player, target);
var eff = get.effect(
target,
{
name: "sha",
storage: { dcjieling: true },
},
player,
player
);
var value = att / 5;
if (value < 0) value = -value / 1.3;
value = Math.max(value - eff / 20, 0.01);
return value;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcshengdu", target);
target.addMark("dcshengdu", 1);
}
},
intro: { content: "mark" },
group: "dcshengdu_effect",
subSkill: {
effect: {
audio: "dcshengdu",
trigger: { global: "gainAfter" },
filter: function (event, player) {
return event.getParent(2).name == "phaseDraw" && event.player.hasMark("dcshengdu");
},
forced: true,
logTarget: "player",
content: function () {
var num = trigger.player.countMark("dcshengdu");
player.draw(num * trigger.cards.length);
trigger.player.removeMark("dcshengdu", num);
},
},
},
},
dcjieling: {
audio: 2,
enable: "phaseUse",
position: "hs",
viewAs: {
name: "sha",
storage: { dcjieling: true },
},
filterCard: function (card, player) {
if (player.getStorage("dcjieling_count").includes(get.suit(card))) return false;
if (ui.selected.cards.length) {
return get.suit(card) != get.suit(ui.selected.cards[0]);
}
return true;
},
selectCard: 2,
complexCard: true,
check: function (card) {
return 6 - get.value(card);
},
precontent: function () {
player.addTempSkill("dcjieling_after");
event.getParent().addCount = false;
player.addTempSkill("dcjieling_count", "phaseUseAfter");
player.markAuto(
"dcjieling_count",
event.result.cards.reduce((list, card) => list.add(get.suit(card, player)), [])
);
},
ai: {
order: function (item, player) {
return get.order({ name: "sha" }) + 0.1;
},
},
locked: false,
mod: {
targetInRange: function (card) {
if (card.storage && card.storage.dcjieling) return true;
},
cardUsable: function (card, player, num) {
if (card.storage && card.storage.dcjieling) return Infinity;
},
},
subSkill: {
after: {
charlotte: true,
audio: "dcjieling",
trigger: { global: "useCardAfter" },
filter: function (event, player) {
return event.card.name == "sha" && event.card.storage && event.card.storage.dcjieling;
},
direct: true,
content: function () {
"step 0";
var damaged = game.hasPlayer2(current => {
return current.hasHistory("damage", evt => evt.card == trigger.card);
});
var targets = trigger.targets.filter(i => i.isIn());
player.logSkill("dcjieling_after", targets);
if (damaged) {
for (var target of targets) {
target.loseHp();
}
} else {
for (var target of targets) {
target.addMark("dcshengdu", 1);
}
}
},
},
count: {
intro: {
content: function (s, p) {
let str = "此阶段已转化过的卡牌花色:";
for (let i = 0; i < s.length; i++) {
str += get.translation(s[i]);
}
return str;
},
},
charlotte: true,
onremove: true,
},
},
},
//袁胤
dcmoshou: {
audio: 2,
trigger: { target: "useCardToTargeted" },
init: function (player, skill) {
if (typeof player.storage[skill] != "number") player.storage[skill] = 0;
},
filter: function (event, player) {
return get.color(event.card) == "black" && event.player != player;
},
frequent: true,
prompt2: function (event, player) {
var num = (player.getAllHistory("useSkill", evt => evt.skill == "dcmoshou").length % 3) + 1;
return "摸" + get.cnNumber(num) + "张牌";
},
content: function () {
var num = player.getAllHistory("useSkill", evt => evt.skill == "dcmoshou").length;
player.storage.dcmoshou = num;
player.syncStorage("dcmoshou");
player.markSkill("dcmoshou");
num = ((num - 1) % 3) + 1;
player.draw(num);
},
mark: true,
marktext: "守",
intro: {
markcount: function (storage, player) {
if (typeof storage != "number") return 1;
return (storage % 3) + 1;
},
content: "本局游戏已发动过$次技能",
},
},
dcyunjiu: {
audio: 2,
trigger: { global: "dieAfter" },
direct: true,
content: function () {
"step 0";
var evt = trigger.player.getHistory("lose", evtx => {
return evtx.getParent(2) == trigger;
})[0];
if (!evt) event.finish();
else {
var cards = [];
//冷知识,角色死亡后只有手牌区和装备区的牌是被系统弃置的,其余牌的处理方式均为置入弃牌堆
cards.addArray(evt.hs).addArray(evt.es);
event.cards = cards.filterInD("d");
var num = cards.length;
if (num) {
event.videoId = lib.status.videoId++;
var func = function (cards, id) {
var num = cards.length;
var dialog = ui.create.dialog(get.prompt("dcyunjiu"), '弃置' + get.cnNumber(num) + "张牌,令一名其他角色获得以下这些牌
", cards);
dialog.videoId = id;
return dialog;
};
if (player.isOnline2()) {
player.send(func, cards, event.videoId);
}
event.dialog = func(cards, event.videoId);
if (player != game.me || _status.auto) {
event.dialog.style.display = "none";
}
player.chooseCardTarget({
prompt: false,
filterTarget: lib.filter.notMe,
filterCard: lib.filter.cardDiscardable,
selectCard: num,
position: "he",
goon: (function () {
if (!game.hasPlayer(current => get.attitude(player, current)) > 0) return false;
var value = 0;
for (var card of cards) {
value += get.value(card, player, "raw") - 1.2;
}
return value > 0;
})(),
ai1: function (card) {
if (_status.event.goon) {
if (ui.selected.cards.length == _status.event.selectCard[1] - 1 && ui.selected.cards.length > 0) return 7 - get.value(card);
return 5.5 - get.value(card);
}
return 0;
},
ai2: function (target) {
return get.attitude(_status.event.player, target) / Math.sqrt(target.countCards("h") + 1);
},
});
} else event.finish();
}
"step 1";
if (player.isOnline2()) {
player.send("closeDialog", event.videoId);
}
event.dialog.close();
if (result.bool) {
var cardsx = result.cards,
target = result.targets[0];
player.logSkill("dcyunjiu", target);
player.discard(cardsx);
target.gain(cards.filterInD("d"), "gain2").giver = player;
} else event.finish();
"step 2";
player.gainMaxHp();
player.recover();
},
},
//高翔
dcchiying: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
return target.hp <= player.hp;
},
content: function () {
"step 0";
var targets = game.filterPlayer(current => target.inRange(current) && current != player).sortBySeat(player);
event.targets = targets;
if (!targets.length) event.finish();
"step 1";
var current = targets.shift();
if (current.countCards("he")) current.chooseToDiscard("驰应:请弃置一张牌", "he", true);
if (targets.length) event.redo();
"step 2";
if (target != player) {
var cards = [];
game.getGlobalHistory("cardMove", evt => {
if (evt.getParent(3) == event) {
cards.addArray(evt.cards.filter(card => get.type(card) == "basic"));
}
});
cards = cards.filterInD("d");
if (cards.length) target.gain(cards, "gain2");
}
},
ai: {
order: 6,
result: {
target: function (player, target) {
var targets = game.filterPlayer(current => target.inRange(current) && current != player);
var eff = 0;
for (var targetx of targets) {
var effx = get.effect(targetx, { name: "guohe_copy2" }, player, target);
if (get.attitude(player, targetx) < 0) effx /= 2;
eff += effx;
}
return (target == player ? 0.5 : 1) * eff * (get.attitude(player, target) <= 0 ? 0.75 : 1);
},
},
},
},
//霍峻
dcgue: {
audio: 2,
enable: ["chooseToUse", "chooseToRespond"],
hiddenCard: function (player, name) {
if (player.hasSkill("dcgue_blocker", null, null, false)) return false;
return name == "sha" || name == "shan";
},
filter: function (event, player) {
if (event.dcgue || event.type == "wuxie" || player == _status.currentPhase) return false;
if (player.hasSkill("dcgue_blocker", null, null, false)) return false;
for (var name of ["sha", "shan"]) {
if (event.filterCard({ name: name, isCard: true }, player, event)) return true;
}
return false;
},
chooseButton: {
dialog: function (event, player) {
var vcards = [];
for (var name of ["sha", "shan"]) {
var card = { name: name, isCard: true };
if (event.filterCard(card, player, event)) vcards.push(["基本", "", name]);
}
return ui.create.dialog("孤扼", [vcards, "vcard"], "hidden");
},
check: function (button) {
if (_status.event.player.countCards("h", { name: ["sha", "shan"] }) > 1) return 0;
return 1;
},
backup: function (links, player) {
return {
filterCard: () => false,
selectCard: -1,
viewAs: {
name: links[0][2],
isCard: true,
},
popname: true,
precontent: function () {
"step 0";
player.logSkill("dcgue");
player.addTempSkill("dcgue_blocker");
if (player.countCards("h")) player.showHandcards();
delete event.result.skill;
"step 1";
if (player.countCards("h", { name: ["sha", "shan"] }) > 1) {
var evt = event.getParent();
evt.set("dcgue", true);
evt.goto(0);
delete evt.openskilldialog;
return;
}
game.delayx();
},
};
},
prompt: function (links, player) {
return (player.countCards ? "展示所有手牌" : "") + (player.countCards("h", { name: ["sha", "shan"] }) <= 1 ? ",然后视为使用【" + get.translation(links[0][2]) + "】" : "");
},
},
subSkill: { blocker: { charlotte: true } },
ai: {
order: 1,
respondSha: true,
respondShan: true,
skillTagFilter: function (player) {
if (player.hasSkill("dcgue_blocker", null, null, false)) return false;
},
result: {
player: function (player) {
if (player.countCards("h", { name: ["sha", "shan"] }) > 1) return 0;
return 1;
},
},
},
},
dcsigong: {
audio: 2,
trigger: { global: "phaseEnd" },
filter: function (event, player) {
if (player.hasSkill("dcsigong_round")) return false;
if (event.player == player || !event.player.isIn()) return false;
if (!player.canUse("sha", event.player, false)) return false;
var respondEvts = [];
game.countPlayer2(current => respondEvts.addArray(current.getHistory("useCard")).addArray(current.getHistory("respond")));
respondEvts = respondEvts.filter(i => i.respondTo).map(evt => evt.respondTo);
return event.player.hasHistory("useCard", evt => {
return respondEvts.some(list => list[1] == evt.card);
});
},
direct: true,
content: function () {
"step 0";
var num = 1 - player.countCards("h");
event.num = num;
var prompt2 = "";
if (num >= 0) {
var next = player.chooseBool().set("ai", () => _status.event.goon);
prompt2 += (num > 0 ? "摸一张牌," : "") + "视为对" + get.translation(trigger.player) + "使用一张【杀】(伤害基数+1)";
} else {
var next = player
.chooseToDiscard(-num)
.set("ai", card => {
if (_status.event.goon) return 5.2 - get.value(card);
return 0;
})
.set("logSkill", ["dcsigong", trigger.player]);
prompt2 += "将手牌数弃置至1,视为对" + get.translation(trigger.player) + "使用一张【杀】(伤害基数+1)";
}
next.set("prompt", get.prompt("dcsigong", trigger.player));
next.set("prompt2", prompt2);
next.set("goon", get.effect(trigger.player, { name: "sha" }, player, player) > 0);
"step 1";
if (result.bool) {
if (num >= 0) player.logSkill("dcsigong", trigger.player);
if (num > 0) player.draw(num, "nodelay");
event.num = Math.max(1, Math.abs(num));
} else event.finish();
"step 2";
if (player.canUse("sha", trigger.player, false)) {
player.addTempSkill("dcsigong_check");
player
.useCard({ name: "sha", isCard: true }, trigger.player, false)
.set("shanReq", num)
.set("oncard", card => {
var evt = _status.event;
evt.baseDamage++;
for (var target of game.filterPlayer(null, null, true)) {
var id = target.playerid;
var map = evt.customArgs;
if (!map[id]) map[id] = {};
map[id].shanRequired = evt.shanReq;
}
});
}
},
subSkill: {
round: { charlotte: true },
check: {
charlotte: true,
forced: true,
popup: false,
trigger: { source: "damageSource" },
filter: function (event, player) {
return event.card && event.card.name == "sha" && event.getParent(3).name == "dcsigong";
},
content: function () {
player.addTempSkill("dcsigong_round", "roundStart");
},
},
},
},
//孙寒华
dchuiling: {
audio: 2,
trigger: { player: "useCard" },
forced: true,
direct: true,
filter: function () {
return ui.discardPile.childNodes.length > 0;
},
onremove: true,
mark: true,
marktext: "灵",
intro: {
name2: "灵",
mark: function (dialog, storage, player) {
dialog.addText("共有" + (storage || 0) + "个标记");
dialog.addText("注:图标的颜色代表弃牌堆中较多的颜色");
},
},
global: "dchuiling_hint",
content: function () {
"step 0";
var mark = false;
var red = 0,
black = 0;
for (var i = 0; i < ui.discardPile.childNodes.length; i++) {
var color = get.color(ui.discardPile.childNodes[i]);
if (color == "red") red++;
if (color == "black") black++;
}
if (red == black) event.finish();
else if (red > black) {
player.logSkill("dchuiling");
player.recover();
event.finish();
if (get.color(trigger.card) == "black") mark = true;
event.logged = true;
} else {
if (!event.isMine() && !event.isOnline()) game.delayx();
player
.chooseTarget(get.prompt("dchuiling"), "弃置一名角色的一张牌", (card, player, target) => {
return target.countDiscardableCards(player, "he") > 0;
})
.set("ai", target => {
return get.effect(target, { name: "guohe_copy2" }, _status.event.player);
});
if (get.color(trigger.card) == "red") mark = true;
}
if (mark) {
if (!event.logged) player.logSkill("dchuiling");
player.addMark("dchuiling", 1);
event.logged = true;
}
"step 1";
if (result.bool) {
var target = result.targets[0];
if (!event.logged) player.logSkill("dchuiling", target);
else player.line(target);
player.discardPlayerCard(target, "he", true);
}
},
subSkill: {
hint: {
trigger: {
global: ["loseAfter", "loseAsyncAfter", "cardsDiscardAfter", "equipAfter"],
},
forced: true,
popup: false,
lastDo: true,
forceDie: true,
forceOut: true,
filter: function (event, player) {
if (event._dchuiling_checked) return false;
event._dchuiling_checked = true;
var cards = event.getd();
if (!cards.filterInD("d").length) return false;
return true;
},
markColor: [
["rgba(241, 42, 42, 0.75)", "black"],
["", ""],
["rgba(18, 4, 4, 0.75)", "rgb(200, 200, 200)"],
],
content: function () {
"step 0";
var red = 0,
black = 0;
for (var i = 0; i < ui.discardPile.childNodes.length; i++) {
var color = get.color(ui.discardPile.childNodes[i]);
if (color == "red") red++;
if (color == "black") black++;
}
if (trigger.name.indexOf("lose") == 0) {
var cards = trigger.getd().filterInD("d");
for (var i = 0; i < cards.length; i++) {
var color = get.color(cards[i]);
if (color == "red") red++;
if (color == "black") black++;
}
}
game.broadcastAll(function (ind) {
var bgColor = lib.skill.dchuiling_hint.markColor[ind][0],
text = '灵';
for (var player of game.players) {
if (player.marks.dchuiling) {
player.marks.dchuiling.firstChild.style.backgroundColor = bgColor;
player.marks.dchuiling.firstChild.innerHTML = text;
}
}
}, Math.sign(black - red) + 1);
},
},
},
mod: {
aiOrder: function (player, card, num) {
if (get.itemtype(card) != "card") return;
var len = ui.discardPile.childNodes.length;
if (!len) {
var type = get.type(card);
if (type == "basic" || type == "trick") {
if (player.getDamagedHp() > 0) {
return num + (get.color(card) == "red" ? 15 : 10);
}
return num + 10;
}
return;
}
if (len > 40) return;
var red = 0,
black = 0;
for (var i = 0; i < ui.discardPile.childNodes.length; i++) {
var color = get.color(ui.discardPile.childNodes[i]);
if (color == "red") red++;
if (color == "black") black++;
}
if (red == black) {
var type = get.type(card);
if (type == "basic" || type == "trick") {
if (player.getDamagedHp() > 0) {
return num + (get.color(card) == "red" ? 15 : 10);
}
return num + 10;
}
return;
} else {
var color = get.color(card);
if ((color == "red" && red < black) || (color == "black" && red > black)) return num + 10;
}
},
},
},
dcchongxu: {
audio: 2,
enable: "phaseUse",
limited: true,
skillAnimation: true,
animationColor: "wood",
derivation: ["dctaji", "dcqinghuang"],
filterCard: () => false,
selectCard: [0, 1],
prompt: function () {
return "限定技。你可以失去〖汇灵〗,增加" + Math.min(game.countPlayer(), _status.event.player.countMark("dchuiling")) + "点体力上限,然后获得〖踏寂〗和〖清荒〗。";
},
filter: function (event, player) {
return player.countMark("dchuiling") >= 4;
},
content: function () {
"step 0";
player.awakenSkill("dcchongxu");
player.removeSkills("dchuiling");
player.gainMaxHp(Math.min(game.countPlayer(), player.countMark("dchuiling")));
"step 1";
player.addSkills(["dctaji", "dcqinghuang"]);
},
ai: {
combo: "dchuiling",
order: function (itemp, player) {
if (
player.hasCard(card => {
return get.type(card) != "equip" && player.getUseValue(card) > 1;
}, "h")
)
return 12;
return 0.1;
},
result: {
player: function (player) {
var count = player.countMark("dchuiling");
if (count >= game.countPlayer() - 1) return 1;
return count >= 6 || player.hp <= 2 ? 1 : 0;
},
},
},
},
dctaji: {
audio: 2,
trigger: {
player: "loseAfter",
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
locked: false,
filter: function (event, player) {
var evt = event.getl(player);
return evt && evt.hs && evt.hs.length;
},
content: function () {
"step 0";
var evt = trigger.getParent();
var effects = [
[
"useCard",
function () {
"step 0";
var targets = game.filterPlayer(current => {
return current.countDiscardableCards(player, "he") && current != player;
});
if (!targets.length) event.finish();
else
player
.chooseTarget("踏寂:弃置其他角色一张牌", true, (card, player, target) => {
return _status.event.targets.includes(target);
})
.set("targets", targets)
.set("ai", target => {
return get.effect(target, { name: "guohe_copy2" }, _status.event.player);
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.line(target);
player.discardPlayerCard(target, "he", true);
}
},
],
[
"respond",
function () {
player.draw();
},
],
[
"discard",
function () {
player.recover();
},
],
[
"other",
function () {
player.addSkill("dctaji_damage");
player.addMark("dctaji_damage", 1, false);
game.log(player, "下一次对其他角色造成的伤害", "#g+1");
},
],
];
var name = evt.name;
if (trigger.name == "loseAsync") name = evt.type;
var list = ["useCard", "respond", "discard", "other"];
if (!list.includes(name)) name = "other";
for (var i = 0; i < 1 + player.countMark("dcqinghuang_add"); i++) {
if (!list.length) break;
if (!list.includes(name)) name = list.randomRemove(1)[0];
if (name == "useCard") list.remove("useCard");
for (var effect of effects) {
if (effect[0] == name) {
list.remove(name);
var next = game.createEvent("dctaji_" + name);
next.player = player;
next.setContent(effect[1]);
break;
}
}
}
},
subSkill: {
damage: {
trigger: { source: "damageBegin1" },
forced: true,
charlotte: true,
onremove: true,
filter: function (event, player) {
return event.player != player;
},
content: function () {
trigger.num += player.countMark("dctaji_damage");
player.removeSkill("dctaji_damage");
},
intro: {
content: "下次对其他角色造成伤害时,此伤害+#",
},
},
},
},
dcqinghuang: {
audio: 2,
trigger: { player: "phaseUseBegin" },
filter: function (event, player) {
return player.maxHp > 1;
},
check: function (event, player) {
var num1 = player.countCards("h");
var num2 = player.countCards("h", card => player.hasValueTarget(card));
var num3 = player.getHandcardLimit();
if (player.isDamaged()) {
return num2 > 1 || num1 - num2 - num3 > 0;
} else {
return num2 > 2 + Math.max(0, 3 - player.hp) || (player.hp > 2 && num1 - num2 - num3 > 2);
}
},
content: function () {
player.loseMaxHp();
player.addTempSkill("dcqinghuang_add");
player.addMark("dcqinghuang_add", 1, false);
},
ai: {
combo: "dctaji",
},
subSkill: {
add: {
charlotte: true,
onremove: true,
},
},
},
//孟节
dcyinlu: {
audio: 2,
trigger: {
global: "phaseBefore",
player: "enterGame",
},
forced: true,
locked: false,
derivation: ["dcyinlu_lequan", "dcyinlu_huoxi", "dcyinlu_zhangqi", "dcyinlu_yunxiang"],
global: ["dcyinlu_lequan", "dcyinlu_huoxi", "dcyinlu_zhangqi", "dcyinlu_yunxiang"],
group: "dcyinlu_move",
filter: function (event, player) {
return event.name != "phase" || game.phaseNumber == 0;
},
hasMark: function (target) {
return lib.skill.dcyinlu.derivation.some(i => target.hasMark(i));
},
content: function () {
"step 0";
event.marks = lib.skill.dcyinlu.derivation.slice(0, 3);
if (game.countPlayer() <= 2) event.goto(3);
"step 1";
player
.chooseTarget("引路:令三名角色分别获得〖引路〗标记", true, 3)
.set("targetprompt", () => {
return get.translation(lib.skill.dcyinlu.derivation[ui.selected.targets.length - 1]);
})
.set("complexSelect", true)
.set("ai", target => {
var player = _status.event.player;
if (ui.selected.targets.length == 2) return get.effect(target, { name: "losehp" }, player, player);
return get.attitude(player, target);
});
"step 2";
if (result.bool) {
var targets = result.targets;
player.line(targets);
for (var i = 0; i < targets.length; i++) {
targets[i].addMark(event.marks[i]);
}
}
event.goto(5);
"step 3";
player.logSkill("dcyinlu", game.players);
var list = [];
for (var mark of event.marks) {
list.push([mark, '"]);
}
var target = game.filterPlayer(i => i != player)[0];
if (!game.hasPlayer(current => current != player)) target = player;
event.target = target;
player
.chooseButton(["引路:令" + get.translation(target) + "获得2枚〖引路〗标记", [list, "textbutton"]])
.set("ai", button => {
var mark = button.link;
if (mark == "dcyinlu_lequan") return 9;
if (mark == "dcyinlu_zhangqi") return 10;
return 8;
})
.set("forced", true)
.set("selectButton", 2)
.set("forcebutton", true);
"step 4";
if (result.bool) {
var marks = result.links;
for (var mark of marks) target.addMark(mark, 1);
event.marks.removeArray(marks);
for (var mark of event.marks) player.addMark(mark, 1);
}
"step 5";
player.addMark("dcyinlu_yunxiang", 1);
player.addMark("dcyinlu_xiang", 1);
game.log(player, "获得了1点芸香值");
},
subSkill: {
move: {
audio: "dcyinlu",
trigger: {
player: "phaseZhunbeiBegin",
global: "die",
},
direct: true,
filter: function (event, player) {
if (event.name == "die") {
return lib.skill.dcyinlu.hasMark(event.player);
}
return game.hasPlayer(current => {
return lib.skill.dcyinlu.hasMark(current);
});
},
content: function () {
"step 0";
if (trigger.name == "die") {
var marks = lib.skill.dcyinlu.derivation.filter(mark => trigger.player.hasMark(mark));
event.marks = marks;
event.goto(3);
} else {
if (_status.connectMode)
game.broadcastAll(function () {
_status.noclearcountdown = true;
});
player
.chooseTarget(get.prompt("dcyinlu_move"), "移动一名角色的〖引路〗标记", 2, (card, player, target) => {
if (ui.selected.targets.length == 0) return lib.skill.dcyinlu.hasMark(target);
return true;
})
.set("ai", target => {
var player = _status.event.player;
if (ui.selected.targets.length == 0) {
var owned = lib.skill.dcyinlu.derivation.filter(i => target.hasMark(i));
var att = get.attitude(player, target);
if (att > 0) {
if (owned.includes("dcyinlu_zhangqi")) return target.hasCard({ suit: "spade" }, "he") ? 5 : 10;
if (
owned.includes("dcyinlu_lequan") &&
target.isHealthy() &&
game.hasPlayer(current => {
return current != target && get.recoverEffect(current, player, player) > 0;
})
)
return 2;
return 0;
}
if (att < 0) {
if (owned.some(i => i != "dcyinlu_zhangqi")) return 8;
return 0;
}
if (
owned.includes("dcyinlu_zhangqi") &&
game.hasPlayer(current => {
return current != target && get.effect(current, { name: "losehp" }, player, player) > 0;
})
)
return 3;
return 1;
} else {
var targetx = ui.selected.targets[0];
var att = get.attitude(player, targetx),
att2 = get.attitude(player, target);
var owned = lib.skill.dcyinlu.derivation.filter(i => targetx.hasMark(i));
if (att > 0) {
if (owned.includes("dcyinlu_zhangqi")) return -att2;
if (owned.includes("dcyinlu_lequan")) return get.recoverEffect(target, player, player);
} else if (att < 0) {
if (owned.some(i => i != "dcyinlu_zhangqi")) return att2;
} else {
if (owned.includes("dcyinlu_zhangqi")) return get.effect(target, { name: "losehp" }, player, player);
return att2;
}
}
return Math.random();
})
.set("complexTarget", true);
}
"step 1";
if (result.bool) {
var marks = lib.skill.dcyinlu.derivation;
var targets = result.targets,
owned = marks.filter(mark => targets[0].hasMark(mark));
event.targets = targets;
if (owned.length == 1) event._result = { bool: true, control: owned[0] };
else {
player
.chooseControl(owned)
.set("prompt", "引路:选择要移动" + get.translation(targets[0]) + "的标记")
.set(
"choiceList",
owned.map(mark => {
return '【' + get.translation(mark) + "】
" + lib.translate[mark + "_info"] + "
";
})
)
.set("displayIndex", false)
.set("ai", () => {
return _status.event.choice;
})
.set(
"choice",
(function () {
var att = get.attitude(player, targets[0]),
att2 = get.attitude(player, targets[1]);
if (att > 0) {
if (owned.includes("dcyinlu_zhangqi") && att2 < 0) return "dcyinlu_zhangqi";
if (owned.includes("dcyinlu_lequan") && att2 > 0) return "dcyinlu_lequan";
} else if (att < 0) {
var marksx = owned.filter(i => i != "dcyinlu_zhangqi");
if (marksx.length && att2 > 0) return marksx[0];
return owned[0];
} else {
if (owned.includes("dcyinlu_zhangqi")) return "dcyinlu_zhangqi";
}
if (owned.length > 1) owned.remove("dcyinlu_zhangqi");
return owned[0];
})()
);
}
} else {
if (_status.connectMode)
game.broadcastAll(function () {
delete _status.noclearcountdown;
game.stopCountChoose();
});
event.finish();
}
"step 2";
if (_status.connectMode)
game.broadcastAll(function () {
delete _status.noclearcountdown;
game.stopCountChoose();
});
var mark = result.control,
count = targets[0].countMark(mark);
player.logSkill("dcyinlu_move", targets, false);
player.line2(targets, mark == "dcyinlu_zhangqi" ? "fire" : "green");
targets[0].removeMark(mark, count);
targets[1].addMark(mark, count);
event.finish();
"step 3";
player
.chooseTarget("引路:是否转移“" + get.translation(event.marks[0]) + "”标记?")
.set("ai", target => {
var player = _status.event.player,
mark = _status.event.mark;
if (mark == "dcyinlu_zhangqi") return get.effect(target, { name: "losehp" }, player, player) + 0.1;
if (mark == "dcyinlu_lequan") return get.recoverEffect(target, player, player) + get.attitude(player, target) / 5;
return get.attitude(player, target);
})
.set("mark", event.marks[0]);
"step 4";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcyinlu_move", target);
var count = trigger.player.countMark(event.marks[0]);
trigger.player.removeMark(event.marks[0], count, false);
target.addMark(event.marks[0], count);
}
"step 5";
event.marks.shift();
if (event.marks.length) event.goto(3);
},
},
lequan: {
trigger: { player: "phaseJieshuBegin" },
direct: true,
charlotte: true,
filter: function (event, player) {
return player.hasMark("dcyinlu_lequan") && game.hasPlayer(current => current.hasSkill("dcyinlu"));
},
marktext: "乐",
intro: {
name: "乐泉",
name2: "乐泉",
markcount: () => 0,
content: "结束阶段,你可以弃置一张♦牌并回复1点体力。",
},
content: function () {
"step 0";
player
.chooseToDiscard("乐泉:是否弃置一张♦牌并回复1点体力?", { suit: "diamond" }, "he")
.set("ai", card => {
if (_status.event.goon) return 7 - get.value(card);
return 0;
})
.set("logSkill", "dcyinlu_lequan")
.set("goon", get.recoverEffect(player, player));
"step 1";
if (result.bool) {
player.recover();
}
},
},
huoxi: {
trigger: { player: "phaseJieshuBegin" },
direct: true,
charlotte: true,
filter: function (event, player) {
return player.hasMark("dcyinlu_huoxi") && game.hasPlayer(current => current.hasSkill("dcyinlu"));
},
marktext: "藿",
intro: {
name: "藿溪",
name2: "藿溪",
markcount: () => 0,
content: "结束阶段,你可以弃置一张♥牌并摸两张牌。",
},
content: function () {
"step 0";
player
.chooseToDiscard("藿溪:是否弃置一张♥牌并摸两张牌?", { suit: "heart" }, "he")
.set("ai", card => {
return 6 - get.value(card);
})
.set("logSkill", "dcyinlu_huoxi");
"step 1";
if (result.bool) {
player.draw(2);
}
},
},
zhangqi: {
trigger: { player: "phaseJieshuBegin" },
forced: true,
direct: true,
charlotte: true,
filter: function (event, player) {
return player.hasMark("dcyinlu_zhangqi") && game.hasPlayer(current => current.hasSkill("dcyinlu"));
},
marktext: "瘴",
intro: {
name: "瘴气",
name2: "瘴气",
markcount: () => 0,
content: "锁定技。结束阶段,你须弃置一张♠牌,否则失去1点体力。",
},
content: function () {
"step 0";
player
.chooseToDiscard("瘴气:弃置一张♠牌,或失去1点体力", { suit: "spade" }, "he")
.set("ai", card => {
if (_status.event.goon) return 7 - get.value(card);
return 0;
})
.set("logSkill", "dcyinlu_zhangqi")
.set("goon", get.effect(player, { name: "losehp" }, player) < 0);
"step 1";
if (!result.bool) {
player.logSkill("dcyinlu_zhangqi");
player.loseHp();
}
},
},
yunxiang: {
trigger: { player: ["phaseJieshuBegin", "damageBegin4"] },
direct: true,
charlotte: true,
filter: function (event, player) {
if (!game.hasPlayer(current => current.hasSkill("dcyinlu"))) return false;
if (event.name == "phaseJieshu") return player.hasMark("dcyinlu_yunxiang");
return player.hasMark("dcyinlu_yunxiang") && player.hasMark("dcyinlu_xiang");
},
onremove: function (player) {
delete player.storage.dcyinlu_xiang;
},
marktext: "芸",
intro: {
name: "芸香",
name2: "芸香",
markcount: function (storage, player) {
return player.countMark("dcyinlu_xiang");
},
content: function (storage, player) {
return "①结束阶段,你可以弃置一张♣牌,获得1点“芸香”值。②当你受到伤害时,你可以扣减所有“芸香”值,减少等量的伤害。当前芸香值:" + player.countMark("dcyinlu_xiang");
},
},
content: function () {
"step 0";
if (trigger.name == "phaseJieshu") {
player
.chooseToDiscard("芸香:是否弃置一张♣牌,获得1枚“香”?", { suit: "club" }, "he")
.set("ai", card => {
return 6 - get.value(card) + 2.5 * _status.event.player.countMark("dcyinlu_xiang");
})
.set("logSkill", "dcyinlu_yunxiang");
} else {
player
.chooseBool("芸香:是否移去所有“香”,令此伤害-" + player.countMark("dcyinlu_xiang") + "?")
.set("ai", () => {
return _status.event.bool;
})
.set("bool", get.damageEffect(player, trigger.source, player) < 0);
}
"step 1";
if (result.bool) {
if (trigger.name == "phaseJieshu") {
player.addMark("dcyinlu_xiang", 1, false);
game.log(player, "获得了1点芸香值");
} else {
player.logSkill("dcyinlu_yunxiang");
var num = player.countMark("dcyinlu_xiang");
player.removeMark("dcyinlu_xiang", num, false);
game.log(player, "扣减了", num, "点芸香值");
trigger.num = Math.max(0, trigger.num - num);
}
}
},
},
},
},
dcyouqi: {
audio: 2,
trigger: { global: "loseAfter" },
filter: function (event, player) {
if (event.getParent(3).name.indexOf("dcyinlu_") != 0 || player == event.player) return false;
return true;
},
derivation: "dcyouqi_faq",
direct: true,
forced: true,
content: function () {
if (Math.random() < 1.25 - 0.25 * get.distance(player, trigger.player) || get.isLuckyStar(player)) {
player.logSkill("dcyouqi");
player.gain(trigger.cards.filterInD("d"), "gain2");
}
},
ai: {
combo: "dcyinlu",
},
},
//孙资刘放
dcqinshen: {
audio: 2,
trigger: { player: "phaseDiscardEnd" },
frequent: true,
prompt2: function () {
return "摸" + get.cnNumber(lib.skill.dcqinshen.getNum()) + "张牌";
},
getNum: function () {
var list = lib.suit.slice();
game.getGlobalHistory("cardMove", function (evt) {
if (evt.name != "lose" && evt.name != "cardsDiscard") return false;
if (evt.name == "lose" && evt.position != ui.discardPile) return false;
for (var card of evt.cards) list.remove(get.suit(card, false));
});
return list.length;
},
filter: function (event, player) {
return lib.skill.dcqinshen.getNum() > 0;
},
content: function () {
player.draw(lib.skill.dcqinshen.getNum());
},
},
dcweidang: {
audio: 2,
trigger: { global: "phaseJieshuBegin" },
/**
* @deprecated
*/
getLength: card => get.cardNameLength(card),
direct: true,
filter: function (event, player) {
var num = lib.skill.dcqinshen.getNum();
return event.player != player && (_status.connectMode ? player.countCards("he") : player.hasCard(card => get.cardNameLength(card) == num, "he"));
},
content: function () {
"step 0";
var num = lib.skill.dcqinshen.getNum();
event.num = num;
player
.chooseCard(get.prompt("dcweidang"), "将一张字数为" + num + "的牌置于牌堆底,然后获得一张字数为" + num + "的牌。若你能使用此牌,你使用之。", "he", (card, player, target) => {
return get.cardNameLength(card) == _status.event.num;
})
.set("num", num)
.set("ai", card => {
return 5 - get.value(card);
});
"step 1";
if (result.bool) {
player.logSkill("dcweidang"), player.lose(result.cards[0], ui.cardPile);
game.broadcastAll(function (player) {
var cardx = ui.create.card();
cardx.classList.add("infohidden");
cardx.classList.add("infoflip");
player.$throw(cardx, 1000, "nobroadcast");
}, player);
game.delayx();
} else event.finish();
"step 2";
var card = get.cardPile(cardx => get.cardNameLength(cardx) == num);
if (card) {
player.gain(card, "gain2");
if (player.hasUseTarget(card)) {
player.chooseUseTarget(card, true);
}
}
},
},
//三袁
dcneifa: {
audio: 2,
trigger: { player: "phaseUseBegin" },
content: function () {
"step 0";
player.draw(3);
player.chooseToDiscard(true, "he").set("ai", function (cardx) {
var player = _status.event.player;
var num = 0;
var hs = player.getCards("h");
var muniu = player.getEquip("muniu");
if (muniu && muniu.cards) hs = hs.concat(muniu.cards);
if (get.type(cardx) == "basic") {
var shas = hs.filter(function (card) {
return card != cardx && get.name(card, player) == "sha" && player.hasValueTarget(card, false);
});
var numx = player.countCards("h", function (card) {
return get.type2(card, player) == "trick";
});
num += Math.min(numx, Math.max(0, shas.length - player.getCardUsable("sha"))) * 0.65;
num +=
Math.min(
player.getCardUsable("sha") + numx,
shas.filter(function (card) {
return (
game.countPlayer(function (current) {
return player.canUse(card, current) && get.effect(current, card, player, player) > 0;
}) > 1
);
}).length
) * 1.1;
var taos = Math.min(
player.maxHp - player.hp,
hs.filter(function (card) {
return cardx != card && get.name(card, player) == "tao";
}).length
);
num += taos * player.getDamagedHp() * 1.2;
} else if (get.type2(cardx) == "trick") {
var numx = Math.sqrt(
Math.min(
5,
player.countCards("h", function (card) {
return get.type(card, player) == "basic";
})
)
);
num +=
hs.filter(function (card) {
return card != cardx && get.type2(card) == "trick" && player.hasValueTarget(card);
}).length * 0.65;
} else num = 4;
return num * 1.5 - get.value(cardx);
});
"step 1";
if (result.bool && result.cards && result.cards.length && get.type(result.cards[0]) != "equip") {
var name = get.type(result.cards[0]) == "basic" ? "dcneifa_basic" : "dcneifa_trick";
player.addTempSkill(name, "phaseUseAfter");
var num = Math.min(
5,
player.countCards("h", function (cardx) {
var type = get.type(cardx, player);
return (name == "dcneifa_basic") != (type == "basic") && type != "equip";
})
);
if (num > 0) player.addMark(name, num, false);
else player.storage[name] = 0;
}
},
ai: {
threaten: 2.33,
},
},
dcneifa_basic: {
mark: true,
marktext: "伐",
onremove: true,
intro: {
name: "内伐 - 基本牌",
content: "本回合内不能使用锦囊牌,使用【杀】选择目标时可以额外指定一个目标且使用【杀】的目标次数上限+#。",
},
mod: {
cardEnabled: function (card, player) {
if (get.type(card, "trick") == "trick") return false;
},
cardSavable: function (card, player) {
if (get.type(card, "trick") == "trick") return false;
},
cardUsable: function (card, player, num) {
if (card.name == "sha") {
return num + player.countMark("dcneifa_basic");
}
},
},
trigger: { player: "useCard2" },
filter: function (event, player) {
if (event.card.name != "sha") return false;
return game.hasPlayer(function (current) {
return !event.targets.includes(current) && player.canUse(event.card, current, false);
});
},
direct: true,
content: function () {
"step 0";
player
.chooseTarget(get.prompt("dcneifa"), "为" + get.translation(trigger.card) + "额外指定一个目标", function (card, player, target) {
return !_status.event.sourcex.includes(target) && player.canUse(_status.event.card, target, false);
})
.set("sourcex", trigger.targets)
.set("ai", function (target) {
var player = _status.event.player;
return get.effect(target, _status.event.card, player, player);
})
.set("card", trigger.card);
"step 1";
if (result.bool) {
if (!event.isMine() && !event.isOnline()) game.delayx();
event.targets = result.targets;
} else {
event.finish();
}
"step 2";
player.logSkill("dcneifa", event.targets);
trigger.targets.addArray(event.targets);
},
},
dcneifa_trick: {
trigger: { player: "useCard2" },
direct: true,
mark: true,
marktext: "伐",
onremove: true,
mod: {
cardEnabled: function (card, player) {
if (get.type(card) == "basic") return false;
},
cardSavable: function (card, player) {
if (get.type(card) == "basic") return false;
},
},
intro: {
name: "内伐 - 锦囊牌",
content: "本回合内不能使用基本牌,且使用普通锦囊牌选择目标时可以增加或减少一个目标。",
},
filter: function (event, player) {
if (get.type(event.card) != "trick") return false;
if (event.targets && event.targets.length > 0) return true;
var info = get.info(event.card);
if (info.allowMultiple == false) return false;
if (event.targets && !info.multitarget) {
if (
game.hasPlayer(function (current) {
return !event.targets.includes(current) && lib.filter.targetEnabled2(event.card, player, current);
})
) {
return true;
}
}
return false;
},
content: function () {
"step 0";
var prompt2 = "为" + get.translation(trigger.card) + "增加或减少一个目标";
player
.chooseTarget(get.prompt("dcneifa"), function (card, player, target) {
var player = _status.event.player;
if (_status.event.targets.includes(target)) return true;
return lib.filter.targetEnabled2(_status.event.card, player, target);
})
.set("prompt2", prompt2)
.set("ai", function (target) {
var trigger = _status.event.getTrigger();
var player = _status.event.player;
return get.effect(target, trigger.card, player, player) * (_status.event.targets.includes(target) ? -1 : 1);
})
.set("targets", trigger.targets)
.set("card", trigger.card);
"step 1";
if (result.bool) {
if (!event.isMine() && !event.isOnline()) game.delayx();
event.targets = result.targets;
} else {
event.finish();
}
"step 2";
if (event.targets) {
player.logSkill("dcneifa", event.targets);
if (trigger.targets.includes(event.targets[0])) trigger.targets.removeArray(event.targets);
else trigger.targets.addArray(event.targets);
}
},
},
//桥蕤
dcaishou: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
filter: function (event, player) {
return player.hasCard(card => card.hasGaintag("dcaishou_tag"), "h");
},
forced: true,
locked: false,
group: ["dcaishou_draw", "dcaishou_lose"],
subfrequent: ["draw"],
content: function () {
"step 0";
player.discard(player.getCards("h", card => card.hasGaintag("dcaishou_tag")));
"step 1";
var len = 0;
player.getHistory("lose", evt => {
if (evt.getParent(2) == event) len += evt.cards.length;
});
if (len > Math.max(0, player.hp) && player.maxHp < 9) {
player.gainMaxHp();
}
},
subSkill: {
draw: {
audio: "dcaishou",
trigger: { player: "phaseJieshuBegin" },
frequent: function (event, player) {
return player.maxHp > 1;
},
prompt2: function (event, player) {
return "摸" + get.cnNumber(player.maxHp) + "张牌,称为“隘”";
},
check: function (event, player) {
return player.maxHp > 1;
},
content: function () {
player.draw(player.maxHp).gaintag = ["dcaishou_tag"];
},
},
lose: {
audio: "dcaishou",
trigger: {
player: "loseAfter",
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
locked: false,
filter: function (event, player) {
if (player == _status.currentPhase) return false;
var evt = event.getl(player);
if (!evt || !evt.hs || !evt.hs.length || player.hasCard(card => card.hasGaintag("dcaishou_tag"), "h")) return false;
if (event.name == "lose") {
for (var i in event.gaintag_map) {
if (event.gaintag_map[i].includes("dcaishou_tag")) return true;
}
return false;
}
return player.hasHistory("lose", function (evt) {
if (event != evt.getParent()) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("dcaishou_tag")) return true;
}
return false;
});
},
content: function () {
player.loseMaxHp();
},
},
},
},
dcsaowei: {
audio: 2,
trigger: { global: "useCardAfter" },
filter: function (event, player) {
return event.player != player && event.card.name == "sha" && event.targets.length && !event.targets.includes(player) && event.targets.every(current => player.inRange(current) && current.isIn()) && player.hasCard(card => card.hasGaintag("dcaishou_tag"), "h");
},
direct: true,
content: function () {
"step 0";
player.chooseCardTarget({
position: "hs",
prompt: get.prompt("dcsaowei"),
prompt2: "将一张“隘”当做【杀】对" + get.translation(trigger.targets) + "使用",
targets: trigger.targets,
filterCard: function (card, player) {
if (get.itemtype(card) == "card" && !card.hasGaintag("dcaishou_tag")) return false;
return _status.event.targets.every(current => player.canUse(get.autoViewAs({ name: "sha" }, [card]), current, false));
},
filterTarget: function (card, player, target) {
if (!_status.event.targets.includes(target)) return false;
card = get.autoViewAs({ name: "sha" }, [card]);
return lib.filter.filterTarget.apply(this, arguments);
},
selectTarget: -1,
ai1: function (card) {
var player = _status.event.player;
if (player.isHealthy() && player.hasSkill("dcaishou") && player.countCards("h", card => card.hasGaintag("dcaishou_tag") == 1)) return 0;
var eff = 0;
for (var target of _status.event.targets) {
eff += get.effect(target, get.autoViewAs({ name: "sha" }, [card]), player, player);
}
if (eff > 0) return 6.5 + eff / 10 - get.value(card);
return 0;
},
ai2: () => 1,
});
"step 1";
if (result.bool) {
var cards = result.cards,
targets = result.targets;
event.cards = cards;
var next = player.useCard({ name: "sha" }, cards, targets, false, "dcsaowei");
player
.when("useCardAfter")
.filter(event => event == next)
.then(() => {
if (player.hasHistory("sourceDamage", evt => evt.card == trigger.card)) {
var cards = trigger.cards.filterInD();
if (cards.length > 0) player.gain(cards, "gain2");
}
});
}
},
},
//向朗
dckanji: {
audio: 2,
enable: "phaseUse",
usable: 2,
filter: function (event, player) {
return player.countCards("h");
},
content: function () {
"step 0";
player.showHandcards();
"step 1";
var suits = [];
player.getCards("h", card => suits.add(get.suit(card)));
if (suits.length == player.countCards("h")) {
player.draw(2);
event.suitsLength = suits.length;
player.addTempSkill("dckanji_check");
}
},
subSkill: {
check: {
trigger: { player: "gainAfter" },
filter: function (event, player) {
if (event.getParent(2).name != "dckanji") return false;
var len = event.getParent(2).suitsLength;
var suits = [];
player.getCards("h", card => suits.add(get.suit(card)));
return suits.length >= 4 && len < 4;
},
charlotte: true,
forced: true,
popup: false,
content: function () {
player.skip("phaseDiscard");
game.log(player, "跳过了", "#y弃牌阶段");
},
},
},
ai: {
order: 9,
result: {
player: function (player, target) {
var count = player.countCards("h");
if (count > 4) return false;
var suits = [];
player.getCards("h", card => suits.add(get.suit(card)));
return suits.length == count ? 1 : 0;
},
},
},
},
dcqianzheng: {
audio: 2,
trigger: { target: "useCardToTargeted" },
usable: 2,
filter: function (event, player) {
return event.player != player && (get.type(event.card) == "trick" || event.card.name == "sha") && player.countCards("he") > 1;
},
async cost(event, trigger, player) {
const str = ",若重铸的牌中没有" + get.translation(get.type2(trigger.card)) + "牌,你于" + get.translation(trigger.cards) + "进入弃牌堆后获得之";
event.result = await player
.chooseCard(get.prompt("dcqianzheng"), "重铸两张牌" + (trigger.cards.length ? str : "") + "。", 2, "he", lib.filter.cardRecastable)
.set("ai", card => {
var val = get.value(card);
if (get.type2(card) == _status.event.type) val += 0.5;
return 6 - val;
})
.set("type", get.type2(trigger.card))
.forResult();
},
async content(event, trigger, player) {
if (event.cards.every(card => get.type2(card) != get.type2(trigger.card))) {
trigger.getParent().dcqianzheng = true;
player.addTempSkill("dcqianzheng_gain");
}
await player.recast(event.cards);
},
subSkill: {
gain: {
trigger: { global: "cardsDiscardAfter" },
filter: function (event, player) {
var evt = event.getParent();
if (evt.name != "orderingDiscard") return false;
return evt.relatedEvent.dcqianzheng && event.cards.filterInD("d").length;
},
charlotte: true,
forced: true,
popup: false,
content: function () {
player.gain(trigger.cards.filterInD("d"), "gain2");
},
},
},
},
//秦朗
dchaochong: {
audio: 2,
trigger: { player: "useCardAfter" },
filter: function (event, player) {
return player.getHandcardLimit() != player.countCards("h");
},
direct: true,
locked: false,
content: function () {
"step 0";
var del = player.getHandcardLimit() - player.countCards("h");
event.delta = del;
if (del > 0) {
player.chooseBool(get.prompt("dchaochong"), "摸" + get.cnNumber(Math.min(5, del)) + "张牌,然后令你的手牌上限-1").set("ai", () => {
var player = _status.event.player;
if (player.isPhaseUsing() && player.hasCard(cardx => player.hasUseTarget(cardx) && player.hasValueTarget(cardx), "hs")) return false;
return true;
});
} else if (del < 0) {
player
.chooseToDiscard(get.prompt("dchaochong"), "弃置" + get.cnNumber(-del) + "张手牌,然后令你的手牌上限+1", -del)
.set("ai", card => {
var player = _status.event.player;
if (player.isPhaseUsing() && player.hasCard(cardx => player.hasValueTarget(cardx), "hs")) return 6 - player.getUseValue(card);
return 5 - get.value(card);
})
.set("logSkill", "dchaochong");
}
"step 1";
if (result.bool) {
if (event.delta > 0) {
player.logSkill("dchaochong");
player.draw(Math.min(5, event.delta));
lib.skill.dchaochong.change(player, -1);
} else if (event.delta < 0) {
lib.skill.dchaochong.change(player, 1);
}
}
},
change: function (player, num) {
if (typeof player.storage.dchaochong !== "number") player.storage.dchaochong = 0;
if (!num) return;
player.storage.dchaochong += num;
player.markSkill("dchaochong");
game.log(player, "的手牌上限", "#g" + (num > 0 ? "+" : "") + num);
},
markimage: "image/card/handcard.png",
intro: {
content: function (storage, player) {
var num = player.storage.dchaochong;
return "手牌上限" + (num >= 0 ? "+" : "") + num;
},
},
mod: {
maxHandcard: function (player, num) {
return num + player.countMark("dchaochong");
},
},
ai: { threaten: 2.2 },
},
dcjinjin: {
audio: 2,
trigger: {
source: "damageSource",
player: "damageEnd",
},
usable: 2,
logTarget: "source",
check: function (event, player) {
if (typeof player.storage.dchaochong != "number" || player.storage.dchaochong == 0) return true;
var evt = event.getParent("useCard");
if (evt && evt.player == player && event.source == player) return false;
if (player.isPhaseUsing() && player.storage.dchaochong == -1) return true;
return Math.abs(player.storage.dchaochong) >= 2;
},
prompt2: function (event, player) {
var str = "";
if (typeof player.storage.dchaochong == "number" && player.storage.dchaochong != 0) {
str += "重置因〖佞宠〗增加或减少的手牌上限,";
}
var num = Math.abs(player.countMark("dchaochong")) || 1;
if (event.source && event.source.isIn()) {
str += "令伤害来源弃置至多" + get.cnNumber(num) + "张牌,然后你摸" + num + "-X张牌(X为其弃置的牌数)";
} else str += "你摸" + get.cnNumber(num) + "张牌";
return str;
},
content: function () {
"step 0";
var del = Math.abs(player.countMark("dchaochong")) || 1;
event.delta = del;
player.storage.dchaochong = 0;
if (player.hasSkill("dchaochong", null, false, false)) player.markSkill("dchaochong");
game.log(player, "重置了手牌上限");
if (trigger.source && trigger.source.isIn()) {
trigger.source
.chooseToDiscard(get.translation(player) + "对你发动了【矜谨】", "弃置至多" + get.cnNumber(del) + "张牌,然后" + get.translation(player) + "摸" + del + "-X张牌(X为你弃置的牌数)。", [1, del], "he")
.set("ai", card => {
if (_status.event.goon) return 5.5 - get.value(card);
return 0;
})
.set("goon", get.attitude(trigger.source, player) < 0);
}
"step 1";
var num = event.delta;
if (result.bool) num -= result.cards.length;
if (num > 0) player.draw(num);
},
ai: {
combo: "dchaochong",
maixie: true,
maixie_hp: true,
threaten: 0.85,
effect: {
target: function (card, player, target) {
if (get.tag(card, "damage")) {
if (player.hasSkillTag("jueqing", false, target)) return [1, -2];
if (!target.hasFriend()) return;
var num = 0;
if (typeof target.storage.dcninchong == "number") num = Math.abs(target.storage.dcninchong);
if (num <= 0) return;
return [1, Math.min(1, num / 3)];
}
},
},
},
},
//二傅
dcxuewei: {
audio: 2,
trigger: { player: "phaseJieshuBegin" },
direct: true,
content: function () {
"step 0";
player
.chooseTarget(get.prompt2("dcxuewei"), (card, player, target) => {
return target.hp <= player.hp;
})
.set("ai", target => {
var player = _status.event.player;
return get.effect(target, { name: "tao" }, player, player) + 0.1;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcxuewei", target);
player.addTempSkill("dcxuewei_shelter", { player: "phaseBegin" });
player.markAuto("dcxuewei_shelter", [target]);
}
},
ai: { threaten: 1.1 },
subSkill: {
shelter: {
audio: "dcxuewei",
trigger: { global: "damageBegin4" },
filter: function (event, player) {
return player.getStorage("dcxuewei_shelter").includes(event.player);
},
charlotte: true,
forced: true,
onremove: true,
logTarget: "player",
marktext: "卫",
intro: { content: "保护对象:$" },
content: function () {
"step 0";
trigger.cancel();
"step 1";
player.loseHp();
if (trigger.player != player) game.asyncDraw([player, trigger.player]);
else player.draw("nodelay");
"step 2";
game.delayx();
},
ai: {
filterDamage: true,
skillTagFilter: function (player, tag, arg) {
if (arg && arg.player && arg.player.hasSkillTag("jueqing", false, player)) return false;
return true;
},
},
},
},
},
dcyuguan: {
audio: 2,
trigger: { global: "phaseEnd" },
filter: function (event, player) {
var num = player.getDamagedHp();
if (num == 0) return false;
return !game.hasPlayer(current => {
return current.getDamagedHp() > num;
});
},
check: function (event, player) {
var num = player.getDamagedHp() - 1;
if (num <= 0) return false;
return game.hasPlayer(target => {
return get.attitude(player, target) > 0 && target.maxHp - target.countCards("h") > 1;
});
},
content: function () {
"step 0";
player.loseMaxHp();
"step 1";
var num = player.getDamagedHp();
if (!player.isIn() || !num) event.finish();
else
player.chooseTarget("御关:令至多" + get.cnNumber(num) + "名角色将手牌摸至体力上限", Math.min(game.countPlayer(), [1, num]), true).set("ai", target => {
return get.attitude(_status.event.player, target) * Math.max(0.1, target.maxHp - target.countCards("h"));
});
"step 2";
if (result.bool) {
var targets = result.targets.sortBySeat(_status.currentPhase);
player.line(targets);
for (var target of targets) {
target.drawTo(target.maxHp);
}
}
},
},
//郑浑
dcqiangzhi: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
if (target == player) return false;
return target.countDiscardableCards(player, "he") + player.countDiscardableCards(player, "he") >= 3;
},
content: function () {
"step 0";
var dialog = [];
dialog.push("强峙:弃置你与" + get.translation(target) + "的共计三张牌");
if (player.countCards("h")) dialog.addArray(['你的手牌
', player.getCards("h")]);
if (player.countCards("e")) dialog.addArray(['你的装备
', player.getCards("e")]);
if (target.countCards("h")) {
dialog.add('' + get.translation(target) + "的手牌
");
if (player.hasSkillTag("viewHandcard", null, target, true)) dialog.push(target.getCards("h"));
else dialog.push([target.getCards("h"), "blank"]);
}
if (target.countCards("e")) dialog.addArray(['' + get.translation(target) + "的装备
", target.getCards("e")]);
player
.chooseButton(3, true)
.set("createDialog", dialog)
.set("filterButton", button => {
if (!lib.filter.canBeDiscarded(button.link, _status.event.player, get.owner(button.link))) return false;
return true;
})
.set("filterOk", () => {
return ui.selected.buttons.length == 3;
})
.set("ai", button => {
var player = _status.event.player;
var target = _status.event.getParent().target;
var card = button.link;
if (get.owner(card) == player) {
if (_status.event.damage) return 15 - get.value(card);
if (player.hp >= 3 || get.damageEffect(player, target, player) >= 0 || (player.hasSkill("dcpitian") && player.getHandcardLimit() - player.countCards("h") >= 1 && player.hp > 1)) return 0;
if (ui.selected.buttons.length == 0) return 10 - get.value(card);
return 0;
} else {
if (_status.event.damage) return 0;
return -(get.sgnAttitude(player, target) || 1) * get.value(card);
}
})
.set(
"damage",
get.damageEffect(target, player, player) > 10 &&
player.countCards("he", card => {
return lib.filter.canBeDiscarded(card, player, player) && get.value(card) < 5;
}) >= 3
);
"step 1";
if (result.bool) {
var links = result.links;
var list1 = [],
list2 = [];
event.players = [player, target];
for (var card of links) {
if (get.owner(card) == player) list1.push(card);
else list2.push(card);
}
if (list1.length && list2.length) {
game.loseAsync({
lose_list: [
[player, list1],
[target, list2],
],
discarder: player,
}).setContent("discardMultiple");
event.finish();
} else if (list2.length) target.discard(list2);
else player.discard(list1);
if (list2.length >= 3) event.players.reverse();
} else event.finish();
"step 2";
event.players[0].line(event.players[1]);
event.players[1].damage(event.players[0]);
},
ai: {
expose: 0.2,
order: 4,
result: {
target: function (player, target) {
return (get.effect(target, { name: "guohe_copy2" }, player, target) / 2) * (target.countDiscardableCards(player, "he") >= 2 ? 1.25 : 1) + get.damageEffect(target, player, target) / 3;
},
},
},
},
dcpitian: {
audio: 2,
trigger: {
player: ["loseAfter", "damageEnd"],
global: "loseAsyncAfter",
},
forced: true,
locked: false,
group: "dcpitian_draw",
filter: function (event, player) {
if (event.name == "damage") return true;
return event.type == "discard" && event.getl(player).cards2.length > 0;
},
content: function () {
player.addMark("dcpitian_handcard", 1, false);
player.addSkill("dcpitian_handcard");
game.log(player, "的手牌上限", "#y+1");
},
subSkill: {
draw: {
audio: "dcpitian",
trigger: { player: "phaseJieshuBegin" },
filter: function (event, player) {
return player.countCards("h") < player.getHandcardLimit();
},
prompt2: function (event, player) {
return "摸" + get.cnNumber(Math.min(5, player.getHandcardLimit() - player.countCards("h"))) + "张牌,重置因〖辟田〗增加的手牌上限";
},
check: function (event, player) {
return player.getHandcardLimit() - player.countCards("h") > Math.min(2, player.hp - 1);
},
content: function () {
"step 0";
var num = Math.min(5, player.getHandcardLimit() - player.countCards("h"));
if (num > 0) player.draw(num);
"step 1";
player.removeMark("dcpitian_handcard", player.countMark("dcpitian_handcard"), false);
game.log(player, "重置了", "#g【辟田】", "增加的手牌上限");
},
},
handcard: {
markimage: "image/card/handcard.png",
intro: {
content: function (storage, player) {
return "手牌上限+" + storage;
},
},
charlotte: true,
mod: {
maxHandcard: function (player, num) {
return num + player.countMark("dcpitian_handcard");
},
},
},
},
ai: {
effect: {
target: function (card, player, target) {
if (get.tag(card, "discard")) return 0.9;
if (get.tag(card, "damage")) return 0.95;
},
},
},
},
//新服二赵
dcqingren: {
audio: 2,
trigger: { player: "phaseJieshuBegin" },
frequent: true,
filter: function (event, player) {
return player.hasHistory("useSkill", evt => ["yizan_use", "yizan_use_backup"].includes(evt.sourceSkill || evt.skill));
},
content: function () {
player.draw(player.getHistory("useSkill", evt => ["yizan_use", "yizan_use_backup"].includes(evt.sourceSkill || evt.skill)).length);
},
ai: {
combo: "yizan_use",
},
},
dclongyuan: {
audio: "xinfu_longyuan",
forced: true,
unique: true,
juexingji: true,
trigger: {
global: "phaseEnd",
},
skillAnimation: true,
animationColor: "orange",
filter: function (event, player) {
return player.countMark("yizan_use") >= 3;
},
content: function () {
player.awakenSkill("dclongyuan");
player.draw(2);
player.recover();
player.storage.yizan = true;
},
derivation: "yizan_rewrite",
ai: {
combo: "yizan_use",
},
},
//黄皓
dcqinqing: {
audio: 2,
trigger: { player: "phaseJieshuBegin" },
direct: true,
filter: function (event, player) {
var zhu = game.filterPlayer(current => current.getSeatNum() == 1)[0];
if (!zhu || !zhu.isIn()) return false;
return game.hasPlayer(current => {
return current != player && current.inRange(zhu);
});
},
content: function () {
"step 0";
player
.chooseTarget(get.prompt2("dcqinqing"), function (card, player, target) {
var zhu = game.filterPlayer(current => current.getSeatNum() == 1)[0];
return target != player && target.inRange(zhu) && target.countDiscardableCards(player, "he") > 0;
})
.set("ai", function (target) {
var zhu = game.filterPlayer(current => current.getSeatNum() == 1)[0];
var he = target.countCards("he");
if (get.attitude(_status.event.player, target) > 0) {
if (target.countCards("h") > zhu.countCards("h") + 1) return 0.1;
} else {
if (he > zhu.countCards("h") + 1) return 2;
if (he > 0) return 1;
}
return 0;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.logSkill("dcqinqing", target);
if (target.countCards("he")) player.discardPlayerCard(target, "he", true);
} else {
event.finish();
}
"step 2";
var zhu = game.filterPlayer(current => current.getSeatNum() == 1)[0];
if (zhu && zhu.isIn()) {
if (target.countCards("h") > zhu.countCards("h")) player.draw();
}
},
},
dccunwei: {
audio: 2,
trigger: { target: "useCardToTargeted" },
forced: true,
filter: function (event, player) {
return player != event.player && get.type2(event.card) == "trick" && (event.targets.length == 1 || player.countCards("he") > 0);
},
content: function () {
if (trigger.targets.length == 1) player.draw();
else if (player.countCards("he") > 0) player.chooseToDiscard("he", true, "存畏:请弃置一张牌");
},
ai: {
halfneg: true,
},
},
//刘辟
dcjuying: {
audio: 2,
trigger: { player: "phaseUseEnd" },
filter: function (event, player) {
return (
player.getCardUsable("sha", true) >
player.getHistory("useCard", evt => {
return evt.getParent("phaseUse") == event && evt.card.name == "sha" && evt.addCount !== false;
}).length
);
},
direct: true,
content: function () {
"step 0";
player
.chooseButton([
get.prompt("dcjuying"),
[
[
["sha", "你于下回合使用【杀】的次数上限+1"],
["hand", "本回合手牌上限+2"],
["draw", "摸三张牌"],
],
"textbutton",
],
])
.set("ai", function (button) {
var player = _status.event.player,
choice = button.link;
if (choice == "draw") return 10;
if (choice == "sha") return 9;
var del = 3 - player.hp;
if (choice == "hand" && player.needsToDiscard() > 0 && del <= 0) return 8;
return 0;
})
.set("selectButton", [1, 3]);
"step 1";
if (result.bool) {
player.logSkill("dcjuying");
var choices = result.links;
event.choices = choices;
if (choices.includes("sha")) {
player.addMark("dcjuying_sha", 1, false);
player.addSkill("dcjuying_sha");
}
if (choices.includes("hand")) {
player.addMark("dcjuying_hand", 1, false);
player.addTempSkill("dcjuying_hand");
}
if (choices.includes("draw")) {
player.draw(3);
}
} else event.finish();
"step 2";
var num = event.choices.length - Math.max(0, player.hp);
if (num > 0) {
player.chooseToDiscard(true, "he");
}
},
ai: {
effect: {
player_use: function (card, player, target) {
if (typeof card == "object" && player.isPhaseUsing() && card.name == "sha" && player.getCardUsable("sha") == 1) return "zeroplayertarget";
},
target_use: function (card, player, target) {
if (card.name == "jiu" && player.getCardUsable("sha") == 2) return [1, 1];
},
},
},
subSkill: {
sha: {
trigger: { player: "phaseBegin" },
filter: function (event, player) {
return player.countMark("dcjuying_sha") > 0;
},
silent: true,
firstDo: true,
charlotte: true,
onremove: true,
content: function () {
player.addMark("dcjuying_effect", player.countMark("dcjuying_sha"), false);
player.addTempSkill("dcjuying_effect");
player.removeSkill("dcjuying_sha");
},
intro: { content: "下回合使用【杀】的次数上限+#" },
},
effect: {
onremove: true,
charlotte: true,
mod: {
cardUsable: function (card, player, num) {
if (card.name == "sha") return num + player.countMark("dcjuying_effect");
},
},
intro: { content: "本回合使用【杀】的次数上限+#" },
},
hand: {
onremove: true,
charlotte: true,
mod: {
maxHandcard: function (player, num) {
return num + 2 * player.countMark("dcjuying_hand");
},
},
},
},
},
//新服加强魏贾诩
dcjianshu: {
audio: "jianshu",
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return player.countCards("h", { color: "black" }) > 0;
},
filterTarget: function (card, player, target) {
if (target == player) return false;
if (ui.selected.targets.length) {
return ui.selected.targets[0] != target && !ui.selected.targets[0].hasSkillTag("noCompareSource") && target.countCards("h") && !target.hasSkillTag("noCompareTarget");
}
return true;
},
targetprompt: ["发起者", "拼点目标"],
filterCard: { color: "black" },
discard: false,
lose: false,
delay: false,
check: function (card) {
if (_status.event.player.hp == 1) return 8 - get.value(card);
return 6 - get.value(card);
},
selectTarget: 2,
multitarget: true,
content: function () {
"step 0";
player.give(cards, targets[0], "give");
"step 1";
if (targets[0].canCompare(targets[1])) targets[0].chooseToCompare(targets[1]);
else event.finish();
"step 2";
player.addTempSkill("dcjianshu_check", "phaseUseAfter");
if (result.bool) {
var cards = targets[0].getCards("he", function (card) {
return lib.filter.cardDiscardable(card, targets[0], "dcjianshu");
});
if (cards.length > 0) targets[0].discard(cards.randomGet());
targets[1].loseHp();
} else if (result.tie) {
targets[0].loseHp();
targets[1].loseHp();
} else {
var cards = targets[1].getCards("he", function (card) {
return lib.filter.cardDiscardable(card, targets[1], "dcjianshu");
});
if (cards.length > 0) targets[1].discard(cards.randomGet());
targets[0].loseHp();
}
},
subSkill: {
check: {
trigger: { global: "dieAfter" },
charlotte: true,
forced: true,
popup: false,
filter: function (event, player) {
return event.getParent(3).name == "dcjianshu";
},
content: function () {
delete player.getStat("skill").dcjianshu;
},
},
},
ai: {
expose: 0.4,
order: 4,
result: {
target: function (player, target) {
if (ui.selected.targets.length) return -1;
return -0.5;
},
},
},
},
dcyongdi: {
audio: "yongdi",
audioname: ["xinping"],
unique: true,
limited: true,
enable: "phaseUse",
filterTarget: function (card, player, target) {
return target.hasSex("male");
},
animationColor: "thunder",
skillAnimation: "legend",
mark: true,
intro: {
content: "limited",
},
content: function () {
"step 0";
player.awakenSkill("dcyongdi");
//player.logSkill('dcyongdi',target);
if (!game.hasPlayer(current => current.maxHp < target.maxHp)) {
target.gainMaxHp();
}
"step 1";
if (target.isMinHp()) {
target.recover();
}
"step 2";
if (target.isMinHandcard()) {
target.draw(Math.min(5, target.maxHp));
}
"step 3";
game.delayx();
},
ai: {
expose: 0.3,
order: 1,
result: {
target: function (player, target) {
var val = 0;
var bool1 = !game.hasPlayer(current => current.maxHp < target.maxHp),
bool2 = target.isMinHp(),
bool3 = target.isMinHandcard();
if (bool1) val += 6.5;
if (bool2) {
if (bool1) target.maxHp++;
val += Math.max(0, get.recoverEffect(target, player, player));
if (bool1) target.maxHp--;
}
if (bool3) {
var num = Math.max(0, Math.min(5, target.maxHp + (bool1 ? 1 : 0)));
val += 5 * num;
}
return val;
},
},
},
},
//雷普
dcsilve: {
audio: 2,
trigger: {
player: "enterGame",
global: "phaseBefore",
},
forced: true,
locked: false,
direct: true,
onremove: ["dcsilve", "dcsilve_self"],
filter: function (event, player) {
return game.hasPlayer(current => current != player) && (event.name != "phase" || game.phaseNumber == 0);
},
content: function () {
"step 0";
player
.chooseTarget("私掠:请选择一名其他角色", "选择一名其他角色(暂时仅你可见),称为“私掠”角色,且你获得后续效果", true, (card, player, target) => {
return target != player && !player.getStorage("dcsilve").includes(target);
})
.set("ai", target => {
var att = get.attitude(_status.event.player, target);
if (att > 0) return att + 1;
if (att == 0) return Math.random();
return att;
})
.set("animate", false);
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcsilve");
player.markAuto("dcsilve", [target]);
player.addSkill("dcsilve_rob");
player.addSkill("dcsilve_revenge");
target.addSkill("dcsilve_target");
if (!target.storage.dcsilve_target) target.storage.dcsilve_target = [];
target.storage.dcsilve_target.push(player);
}
},
subSkill: {
rob: {
audio: "dcsilve",
trigger: { global: "damageSource" },
filter: function (event, player) {
if (!player.getStorage("dcsilve").includes(event.source)) return false;
if (!event.player.isIn() || event.player == player) return false;
if (player.getStorage("dcsilve_robbed").includes(event.player)) return false;
return event.player.countCards("he") > 0;
},
charlotte: true,
prompt2: function (event, player) {
return "获得" + get.translation(event.player) + "一张牌";
},
logTarget: "player",
content: function () {
player.addTempSkill("dcsilve_robbed");
player.markAuto("dcsilve_self", [trigger.player]);
if (trigger.player.countGainableCards(player, "he") > 0) {
player.markAuto("dcsilve_robbed", [trigger.player]);
player.gainPlayerCard(trigger.player, "he", true);
}
if (trigger.source && trigger.source != player) trigger.source.markSkill("dcsilve_target");
},
},
revenge: {
audio: "dcsilve",
trigger: { global: "damageEnd" },
filter: function (event, player) {
if (!player.getStorage("dcsilve").includes(event.player)) return false;
if (!event.player.isIn() || !event.source || !event.source.isIn() || event.source == player) return false;
return true;
},
forced: true,
locked: false,
charlotte: true,
direct: true,
content: function () {
"step 0";
if (trigger.player && trigger.player != player) trigger.player.markSkill("dcsilve_target");
player.markAuto("dcsilve_self", [trigger.player]);
player
.chooseToUse("私掠:对" + get.translation(trigger.source) + "使用一张【杀】,或弃置一张手牌", function (card, player, event) {
if (get.name(card) != "sha") return false;
return lib.filter.filterCard.apply(this, arguments);
})
.set("targetRequired", true)
.set("complexSelect", true)
.set("filterTarget", function (card, player, target) {
if (target != _status.event.source && !ui.selected.targets.includes(_status.event.source)) return false;
return lib.filter.targetEnabled.apply(this, arguments);
})
.set("source", trigger.source)
.set("logSkill", "dcsilve_revenge");
"step 1";
if (!result.bool) {
if (player.countCards("h") > 0) player.chooseToDiscard("h", true).set("logSkill", "dcsilve_revenge");
}
},
},
self: {
marktext: "私",
intro: {
name: "私掠",
content: function (storage, player) {
if (!storage || !storage.length) return "没有打劫对象";
if (storage[0] == player) return "已绑定" + get.translation(player) + "自己";
return "打劫对象:" + get.translation(storage);
},
},
},
target: {
marktext: "掠",
intro: {
name: "私掠",
content: function (storage, player) {
return "被" + get.translation(storage) + "盯上了!";
},
},
},
robbed: { onremove: true, charlotte: true },
},
},
dcshuaijie: {
audio: 2,
enable: "phaseUse",
limited: true,
skillAnimation: true,
animationColor: "thunder",
filter: function (event, player) {
var targets = player.getStorage("dcsilve").filter(i => i.isIn());
if (!targets.length) return true;
return (
targets.filter(target => {
return player.hp > target.hp && player.countCards("e") > target.countCards("e");
}).length == targets.length
);
},
content: function () {
"step 0";
player.awakenSkill("dcshuaijie");
player.loseMaxHp();
var choices = [];
var choiceList = ["获得“私掠”角色至多三张牌", "从牌堆中获得三张类型各不相同的牌"];
var targets = player.getStorage("dcsilve").filter(i => i.isIn());
event.targets = targets;
if (targets.length) choices.push("选项一");
else choiceList[0] = '' + choiceList[0] + "";
choices.push("选项二");
player
.chooseControl(choices)
.set("prompt", "衰劫:选择一项")
.set("choiceList", choiceList)
.set("ai", () => _status.event.choice)
.set(
"choice",
(function () {
var eff = 0;
for (var target of targets) {
eff += get.effect(target, { name: "shunshou_copy2" }, player, player) * 2;
}
eff -= get.effect(player, { name: "dongzhuxianji" }, player, player);
return eff > 0 && choices.includes("选项一") ? "选项一" : "选项二";
})()
);
"step 1";
if (result.control == "选项一") {
if (targets.length) {
for (var target of targets) {
if (target.countGainableCards(player, "he") > 0) {
player.line(target);
player.gainPlayerCard(target, "he", true, [1, 3]);
}
}
}
} else {
var cards = [];
for (var i = 0; i < 3; i++) {
var card = get.cardPile(cardx => {
return cards.filter(cardxx => get.type2(cardxx) == get.type2(cardx)).length == 0;
});
if (card) cards.push(card);
}
if (cards.length) player.gain(cards, "gain2");
}
"step 2";
var targets = player.getStorage("dcsilve").filter(i => i.isIn());
for (var target of targets) {
target.unmarkAuto("dcsilve_target", [player]);
}
delete player.storage.dcsilve;
delete player.storage.dcsilve_self;
player.markAuto("dcsilve", [player]);
player.markAuto("dcsilve_self", [player]);
},
ai: {
combo: "dcsilve",
order: 8,
result: {
player: function (player) {
var targets = player.getStorage("dcsilve").filter(i => i.isIn());
if (!targets.length) return 1;
var att = 0;
targets.forEach(i => (att += get.attitude(player, i)));
if (att < 0) return 1;
return 0;
},
},
},
},
//庞会
dcyiyong: {
audio: 2,
trigger: {
source: "damageBegin1",
},
//usable:2,
filter: function (event, player) {
return player.countDiscardableCards(player, "he") > 0 && player != event.player;
},
check: function (event, player) {
return get.attitude(player, event.player) < 0 && player.countCards("he", card => lib.filter.cardDiscardable(card, player, "dcyiyong") && get.value(card, player) < 7) > 0;
},
logTarget: "player",
content: function () {
"step 0";
event.list = [player];
event.cards0 = [];
event.cards1 = [];
if (trigger.player.countDiscardableCards(trigger.player, "he") > 0) {
event.list.push(trigger.player);
}
if (!event.isMine() && !event.isOnline()) game.delayx();
player
.chooseCardOL(event.list, "he", true, [1, Infinity], "异勇:弃置任意张牌", (card, player, target) => {
return lib.filter.cardDiscardable(card, player, "dcyiyong");
})
.set("ai", card => {
var evt = _status.event.getParent(2);
var source = evt.player,
player = _status.event.player,
target = evt.list[1];
if (!target) return get.unuseful(card);
if (player == source) {
var total = 0,
need = 0;
target.countCards("he", card => {
if (lib.filter.cardDiscardable(card, target, "dcyiyong") && get.value(card) < 5) need += get.number(card);
});
for (var i of ui.selected.cards) total += get.number(i);
if (total >= need + 5) return 0;
var val = 6;
if (
target.hp <= 2 &&
!target.hasSkillTag("filterDamage", null, {
player: player,
card: evt.getTrigger().card,
})
)
val += 2 + get.number(card) / 5;
if (target.countCards("he", card => get.value(card) < 5) >= 3) val -= 3 + get.number(card) / 5;
return val - get.value(card);
}
if (ui.selected.cards.length > 1 && ui.selected.cards.length + 2 >= source.countCards("he")) return 0;
if (
player.hp <= 2 &&
!target.hasSkillTag("filterDamage", null, {
player: player,
card: evt.getTrigger().card,
})
)
return 10 - get.value(card);
return 5 - get.value(card);
});
"step 1";
var lose_list = [],
cards = [];
for (var i = 0; i < result.length; i++) {
var current = event.list[i],
cards2 = result[i].cards;
cards.push(cards2);
event["cards" + i] = cards2;
event.cards = cards;
lose_list.push([current, cards2]);
}
game.loseAsync({ lose_list: lose_list }).setContent("discardMultiple");
"step 2";
var getn = function (cards) {
return cards.map(i => get.number(i, false)).reduce((p, c) => p + c, 0);
};
var num0 = getn(event.cards0),
num1 = getn(event.cards1);
if (num0 <= num1) {
player.draw(event.cards1.length);
}
if (num0 >= num1) {
trigger.num++;
}
},
},
//乐就
dccuijin: {
audio: 2,
trigger: { global: "useCard" },
filter: function (event, player) {
return (event.card.name == "sha" || event.card.name == "juedou") && (event.player == player || player.inRange(event.player)) && player.countCards("he") > 0;
},
direct: true,
content: function () {
"step 0";
if (player != game.me && !player.isOnline()) game.delayx();
var target = trigger.player;
event.target = target;
player
.chooseToDiscard("he", get.prompt("dccuijin", target), "弃置一张牌并令" + get.translation(trigger.player) + "使用的" + get.translation(trigger.card) + "伤害+1,但若其未造成伤害,则你摸两张牌并对其造成1点伤害。")
.set("ai", function (card) {
if (_status.event.goon) return 7 - get.value(card);
return 0;
})
.set("goon", lib.skill.cuijin.checkx(trigger, player)).logSkill = ["dccuijin", target];
"step 1";
if (result.bool) {
if (typeof trigger.baseDamage != "number") trigger.baseDamage = 1;
trigger.baseDamage++;
player.addSkill("dccuijin_damage");
player.markAuto("dccuijin_damage", [trigger.card]);
if (!player.storage.dccuijin_map) player.storage.dccuijin_map = { cards: [], targets: [] };
player.storage.dccuijin_map.cards.push(trigger.card);
player.storage.dccuijin_map.targets.push(trigger.targets.slice());
}
},
subSkill: {
damage: {
trigger: {
global: ["damage", "damageCancelled", "damageZero", "shaMiss", "useCardToExcluded", "useCardToEnd", "eventNeutralized", "useCardAfter", "shaCancelled"],
},
forced: true,
silent: true,
firstDo: true,
charlotte: true,
onremove: true,
filter: function (event, player, name) {
if (!event.card) return false;
var cards = player.getStorage("dccuijin_damage");
if (!cards.includes(event.card)) return false;
return true;
},
content: function () {
"step 0";
var card = trigger.card,
idx = player.storage.dccuijin_map.cards.indexOf(card);
if (event.triggername == "useCardAfter") {
var cards = player.getStorage("dccuijin_damage");
cards = cards.remove(card);
if (!cards.length) {
player.removeSkill("dccuijin_damage");
delete player.storage.dccuijin_map;
} else if (idx !== -1) {
player.storage.dccuijin_map.cards.splice(idx, 1);
player.storage.dccuijin_map.targets.splice(idx, 1);
}
event.finish();
} else if (idx !== -1) {
var target, source;
if (trigger.name.indexOf("damage") == 0) {
target = trigger.player;
source = trigger.source;
} else {
target = trigger.target;
source = trigger.player;
}
if (
player.storage.dccuijin_map.targets[idx].includes(target) &&
!target.hasHistory("damage", evt => {
return evt.card == card;
})
) {
player.logSkill("dccuijin_damage", source);
player.storage.dccuijin_map.targets[idx].remove(target);
player.draw(2);
if (source && source.isIn()) {
player.line(trigger.player, "green");
trigger.player.damage();
}
}
}
"step 1";
game.delayx();
},
},
},
},
//陈矫
dcxieshou: {
trigger: {
global: "damageEnd",
},
usable: 1,
filter: function (event, player) {
return get.distance(player, event.player) <= 2 && event.player.isIn();
},
check: function (event, player) {
return get.attitude(player, event.player) > 4;
},
locked: false,
logTarget: "player",
onremove: true,
change: function (player, num) {
player.addSkill("dcxieshoux");
if (typeof player.storage.dcxieshoux !== "number") player.storage.dcxieshoux = 0;
if (!num) return;
player.storage.dcxieshoux += num;
if (player.storage.dcxieshoux != 0) player.markSkill("dcxieshoux");
else player.unmarkSkill("dcxieshoux");
game.log(player, "的手牌上限", (num > 0 ? "+" : "") + num);
},
content: function () {
"step 0";
lib.skill.dcxieshou.change(player, -1);
"step 1";
var list = [],
target = trigger.player;
event.target = target;
var choiceList = ["回复1点体力", "复原,摸两张牌"];
if (target.getDamagedHp() == 0) choiceList[0] = '' + choiceList[0] + "";
else list.push("选项一");
list.push("选项二");
target
.chooseControl(list)
.set("choiceList", choiceList)
.set("prompt", get.translation(player) + "对你发动了【协守】,请选择一项");
"step 2";
if (result.control == "选项一") {
target.recover();
} else {
target.link(false);
target.draw(2);
}
},
ai: {
expose: 0.3,
},
},
dcxieshoux: {
markimage: "image/card/handcard.png",
intro: {
content: function (storage, player) {
var num = player.storage.dcxieshoux;
return "手牌上限" + (num >= 0 ? "+" : "") + num;
},
},
charlotte: true,
mod: {
maxHandcard: function (player, num) {
return num + (player.storage.dcxieshoux || 0);
},
},
},
dcqingyan: {
trigger: {
target: "useCardToTargeted",
},
filter: function (event, player) {
return event.player != player && get.color(event.card) == "black";
},
usable: 2,
async cost(event, trigger, player) {
if (player.countCards("h") < player.hp) {
event.result = await player
.chooseBool(get.prompt("dcqingyan"), "将手牌摸至体力上限(摸" + get.cnNumber(player.maxHp - player.countCards("h")) + "张牌)")
.set("ai", () => 1)
.forResult();
} else {
event.result = await player
.chooseToDiscard(get.prompt("dcqingyan"), "弃置一张手牌令你的手牌上限+1", "chooseonly")
.set("ai", card => 6 - get.value(card))
.forResult();
}
},
async content(event, trigger, player) {
if (event.cards && event.cards.length) {
await player.discard(event.cards);
lib.skill.dcxieshou.change(player, 1);
} else {
player.drawTo(player.maxHp);
}
},
},
dcqizi: {
mod: {
cardSavable: function (card, player, target) {
if (get.distance(player, target) > 2 && card.name == "tao" && target == _status.event.dying) return false;
},
},
ai: {
neg: true,
},
},
//公孙度
dczhenze: {
audio: 2,
trigger: { player: "phaseDiscardBegin" },
direct: true,
content: function () {
"step 0";
var getCond = player => Math.sign(player.countCards("h") - Math.max(0, player.hp));
var me = getCond(player);
var recovers = game.filterPlayer(current => getCond(current) == me),
loses = game.filterPlayer().removeArray(recovers);
event.recovers = recovers;
event.loses = loses;
var list = [];
if (loses.length) list.push("选项一");
if (recovers.length) list.push("选项二");
list.push("cancel2");
var sign = [
["≥", "<"],
["≠", "="],
["≤", ">"],
];
var choiceList = ["令所有手牌数" + sign[me + 1][0] + "体力值的角色失去1点体力" + (loses.length ? "(" + get.translation(loses) + ")" : ""), "令所有手牌数" + sign[me + 1][1] + "体力值的角色回复1点体力" + (recovers.length ? "(" + get.translation(recovers) + ")" : "")];
if (!loses.length) choiceList[0] = '' + choiceList[0] + "";
if (!recovers.length) choiceList[1] = '' + choiceList[1] + "";
player
.chooseControl(list)
.set("choiceList", choiceList)
.set("prompt", get.prompt("dczhenze"))
.set("ai", () => _status.event.choice)
.set(
"choice",
(() => {
var effect = 0;
if (list.length == 2) {
if (list.includes("选项一")) {
loses.forEach(i => (effect += get.effect(i, { name: "losehp" }, player, player)));
if (effect > 0) return "选项一";
} else {
recovers.forEach(i => (effect += get.recoverEffect(i, player, player)));
if (effect > 0) return "选项二";
}
} else {
loses.forEach(i => (effect += get.effect(i, { name: "losehp" }, player, player)));
recovers.forEach(i => (effect += get.recoverEffect(i, player, player)));
if (effect > 0) return "选项二";
return "选项一";
}
})()
);
"step 1";
if (result.control == "cancel2") {
event.finish();
} else {
var lose = result.control == "选项一",
targets = event[lose ? "loses" : "recovers"];
player.logSkill("dczhenze", targets);
for (var i of targets) {
i[lose ? "loseHp" : "recover"]();
}
}
},
},
dcanliao: {
audio: 2,
enable: "phaseUse",
filter: function (event, player) {
if ((player.getStat().skill.dcanliao || 0) >= game.countPlayer(current => current.group == "qun")) return false;
return true;
},
filterTarget: function (card, player, target) {
return target.countCards("he");
},
content: function () {
"step 0";
player
.choosePlayerCard(target, "he", true)
.set("filterButton", function (button) {
var card = button.link,
owner = get.owner(card);
return !owner || owner.canRecast(card, _status.event.player);
})
.set("ai", function (card) {
if (get.attitude(_status.event.player, _status.event.getParent().target) >= 0) return -get.buttonValue(card);
return get.buttonValue(card);
});
"step 1";
if (result.bool) target.recast(result.links);
},
ai: {
expose: 0.1,
result: {
target: function (player, target) {
if (target.hasCard(card => get.value(card) >= 6, "e") && get.attitude(player, target) < 0) return -1;
return 1;
},
},
},
},
//王烈
dcchongwang: {
audio: 2,
trigger: { global: "useCard" },
direct: true,
filter: function (event, player) {
if (player == event.player) return false;
var type = get.type(event.card);
if (type != "basic" && type != "trick") return false;
var history = game.getAllGlobalHistory("useCard");
var index = history.indexOf(event);
if (index > 0) return history[index - 1].player == player;
return false;
},
content: function () {
"step 0";
var source = trigger.player;
var list = [["exclude", "令" + get.translation(trigger.card) + "无效"]];
var cards = trigger.cards.filterInD();
if (source.isIn() && cards.length > 0) list.push(["gain", "令" + get.translation(source) + "收回" + get.translation(cards)]);
player.chooseButton([get.prompt("dcchongwang", source), [list, "textbutton"], "noforcebutton"]).set("ai", function (button) {
var player = _status.event.player,
choice = button.link;
var evt = _status.event.getTrigger();
if (choice == "exclude") {
var effect = 0;
if (!evt.targets.length && get.info(evt.card, false).notarget) effect -= get.effect(evt.player, evt.card, evt.player, player);
for (var i of evt.targets) {
effect -= get.effect(i, evt.card, evt.player, player);
}
return effect;
} else {
var cards = evt.cards.filterInD();
return get.value(cards, evt.player) * get.attitude(player, evt.player);
}
});
"step 1";
if (result.bool) {
if (!event.isMine() && !event.isOnline()) game.delayx();
} else event.finish();
"step 2";
if (result.bool) {
player.logSkill("dcchongwang", trigger.player);
if (result.links[0] == "gain") {
player.addTempSkill("dcchongwang_gain");
trigger._dcchongwang = true;
} else {
trigger.targets.length = 0;
trigger.all_excluded = true;
game.log(trigger.card, "被无效了");
}
}
},
ai: {
threaten: 3.5,
directHit_ai: true,
},
subSkill: {
gain: {
trigger: { global: "useCardAfter" },
charlotte: true,
forced: true,
popup: false,
filter: function (event, player) {
return event._dcchongwang;
},
content: function () {
trigger.player.gain(trigger.cards.filterInD(), "gain2");
},
},
},
},
dchuagui: {
audio: 2,
trigger: { player: "phaseUseBegin" },
direct: true,
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current != player && current.countCards("he") > 0;
});
},
content: function () {
"step 0";
var min = Math.max.apply(
Math,
game.filterPlayer().map(function (current) {
return 1 + current.getFriends().length;
})
);
var max = Math.min(
min,
game.countPlayer(function (current) {
return current != player && current.countCards("he") > 0;
})
);
player
.chooseTarget(get.prompt("dchuagui"), "令至多" + get.cnNumber(max) + "名角色进行囚徒困境选择", [1, max], function (card, player, target) {
return target != player && target.countCards("he") > 0;
})
.set("animate", false)
.set("ai", function (target) {
return -get.attitude(_status.event.player, target);
});
"step 1";
if (result.bool) {
player.logSkill("dchuagui");
event.players = result.targets.slice(0);
event._global_waiting = true;
} else event.finish();
"step 2";
var send = function (source) {
var next = game.createEvent("dchuagui_choose", false);
next.player = game.me;
next.source = source;
next.setContent(lib.skill.dchuagui.contentx);
game.resume();
};
var sendback = function (result, player) {
if (!Array.isArray(result)) {
result = [Math.random() < 0.5 ? "仅展示牌" : "交出牌", player.getCards("he").randomGet()];
}
event.results.push([player, result]);
};
event.ai_targets = [];
event.results = [];
var players = game
.filterPlayer(function (current) {
return current != player;
})
.sortBySeat();
var time = 10000;
if (lib.configOL && lib.configOL.choose_timeout) time = parseInt(lib.configOL.choose_timeout) * 1000;
for (var i = 0; i < players.length; i++) {
players[i].showTimer(time);
if (!event.players.includes(players[i])) continue;
if (players[i].isOnline()) {
event.withol = true;
players[i].send(send, player);
players[i].wait(sendback);
} else if (players[i] == game.me) {
event.withme = true;
var next = game.createEvent("dchuagui_choose", false);
next.player = game.me;
next.source = player;
next.setContent(lib.skill.dchuagui.contentx);
if (_status.connectMode) game.me.wait(sendback);
} else {
event.ai_targets.push(players[i]);
}
}
if (event.ai_targets.length) {
event.ai_targets.randomSort();
setTimeout(function () {
event.interval = setInterval(
function () {
var target = event.ai_targets.shift();
var att = get.attitude(target, player),
hs = target.getCards("he");
hs.sort((b, a) => get.value(b, target) - get.value(a, target));
var choice = "仅展示牌",
card = hs[0];
if (att < -2 && Math.random() > (get.value(card, target) - 3) / 5) choice = "交出牌";
sendback([choice, card], target);
if (!event.ai_targets.length) {
clearInterval(event.interval);
if (event.withai) game.resume();
}
},
_status.connectMove ? 750 : 75
);
}, 500);
}
"step 3";
if (event.withme) {
if (_status.connectMode) game.me.unwait(result, game.me);
else {
if (!Array.isArray(result)) {
result = [Math.random() < 0.5 ? "仅展示牌" : "交出牌", player.getCards("he").randomGet()];
}
event.results.push([player, result]);
}
}
"step 4";
if (event.withol && !event.resultOL) {
game.pause();
}
"step 5";
if (event.ai_targets.length > 0) {
event.withai = true;
game.pause();
}
"step 6";
delete event._global_waiting;
for (var i of game.players) i.hideTimer();
event.videoId = lib.status.videoId++;
game.broadcastAll(
function (name, id, results) {
var dialog = ui.create.dialog(name + "发动了技能【化归】", "hidden", "forcebutton");
dialog.videoId = id;
dialog.classList.add("scroll1");
dialog.classList.add("scroll2");
dialog.classList.add("fullwidth");
dialog.classList.add("fullheight");
dialog.buttonss = [];
var list = ["仅展示牌的玩家", "交出牌的玩家"];
for (var i = 0; i < list.length; i++) {
dialog.add('' + list[i] + "
");
var buttons = ui.create.div(".buttons", dialog.content);
dialog.buttonss.push(buttons);
buttons.classList.add("popup");
buttons.classList.add("guanxing");
}
dialog.open();
var getx = function () {
var item = results.shift();
var card = item[1][1],
index = item[1][0] == "仅展示牌" ? 0 : 1;
var button = ui.create.button(card, "card", dialog.buttonss[index]);
button.querySelector(".info").innerHTML = (function (target) {
if (target._tempTranslate) return target._tempTranslate;
var name = target.name;
if (lib.translate[name + "_ab"]) return lib.translate[name + "_ab"];
return get.translation(name);
})(item[0]);
if (results.length > 0) setTimeout(getx, 500);
};
setTimeout(getx, 500);
},
get.translation(player),
event.videoId,
event.results.slice(0)
);
game.delay(0, 2000 + event.results.length * 500);
"step 7";
game.broadcastAll("closeDialog", event.videoId);
var shown = [],
given = [];
for (var i of event.results) {
(i[1][0] == "仅展示牌" ? shown : given).push(i);
}
var list = given.length > 0 ? given : shown;
var cards = [],
targets = [];
for (var i of list) {
cards.push(i[1][1]);
targets.push(i[0]);
//i[0].$give(i[1][1],player);
}
player.line(targets);
player.gain(cards, "give");
//step 8
//game.delayx();
},
contentx: function () {
"step 0";
event._global_waiting = true;
event.result = ["仅展示牌", player.getCards("he").randomGet()];
var str = get.translation(source);
player
.chooseControl("仅展示牌", "交出牌")
.set("choiceList", ["仅展示一张牌。但如果所有人都选择了仅展示,则" + str + "获得这张牌", "将一张牌交给" + str])
.set("_global_waiting", true);
"step 1";
event.result[0] = result.control;
player.chooseCard("he", true).set("_global_waiting", true);
"step 2";
event.result[1] = result.cards[0];
},
},
//陈珪
dcyingtu: {
audio: 2,
trigger: {
global: ["gainAfter", "loseAsyncAfter"],
},
usable: 1,
getIndex(event, player) {
var targets = [];
if (lib.skill.dcyingtu.filterx(event, player, player.getNext())) targets.add(player.getNext());
if (lib.skill.dcyingtu.filterx(event, player, player.getPrevious())) targets.add(player.getPrevious());
return targets.sortBySeat(_status.currentPhase);
},
filterx: function (event, player, target) {
var evt = event.getParent("phaseDraw");
if (evt && target == evt.player) return false;
return (
event.getg(target).length > 0 &&
target.hasCard(function (card) {
return lib.filter.canBeGained(card, target, player);
}, "he")
);
},
logTarget(event, player, triggername, target) {
return target;
},
check(event, player, triggername, source) {
var target = source == player.getNext() ? player.getPrevious() : player.getNext();
return Math.min(0, get.attitude(player, target)) >= get.attitude(player, source);
},
prompt2: "获得该角色的一张牌,然后将一张牌交给该角色的对位角色。若你给出的是装备牌,则其使用其得到的牌。",
content: function () {
"step 0";
var target = event.targets[0];
event.target = target;
event.side = target == player.getPrevious() ? "getNext" : "getPrevious";
player.gainPlayerCard(target, true, "he");
"step 1";
var he = player.getCards("he");
if (he.length > 0) {
var target = player[event.side]();
event.target = target;
if (he.length == 1) event._result = { bool: true, cards: he };
else player.chooseCard("he", true, "交给" + get.translation(target) + "一张牌");
} else event.finish();
"step 2";
if (result.bool) {
var card = result.cards[0];
event.card = card;
player.line(target);
player.give(card, target);
} else event.finish();
"step 3";
if (target.getCards("h").includes(card) && get.type(card, null, target) == "equip" && target.canUse(card, target)) target.chooseUseTarget(card, true, "nopopup");
},
},
dccongshi: {
audio: 2,
trigger: { global: "useCardAfter" },
forced: true,
filter: function (event, player) {
return get.type(event.card, null, false) == "equip" && event.player.isMaxEquip();
},
content: function () {
player.draw();
},
},
//黄权
dcquanjian: {
audio: 2,
enable: "phaseUse",
usable: 2,
filter: function (event, player) {
return game.hasPlayer(current => current != player);
},
chooseButton: {
dialog: function (event, player) {
var dialog = ui.create.dialog("劝谏:令一名其他角色…", "hidden");
dialog.add([
[
["damage", "对其攻击范围内的一名角色造成1点伤害"],
["draw", "将其手牌数调整至手牌上限(至多摸至五张),且其本回合内不能使用手牌"],
],
"textbutton",
]);
return dialog;
},
filter: function (button, player) {
return !player.hasSkill("dcquanjian_" + button.link, null, null, false);
},
check: () => 1 + Math.random(),
backup: function (links) {
return get.copy(lib.skill["dcquanjian_" + links[0]]);
},
prompt: function (links) {
if (links[0] == "damage") return "令一名其他角色对攻击范围内的另一名角色造成1点伤害";
return "令一名其他角色将手牌数调整至手牌上限(至多摸至五张)且本回合内不能使用手牌";
},
},
ai: {
order: 2,
result: { player: 1 },
},
subSkill: {
backup: { audio: "dcquanjian" },
damage: {
audio: "dcquanjian",
selectTarget: 2,
filterTarget: function (card, player, target) {
if (!ui.selected.targets.length) return target != player;
return ui.selected.targets[0].inRange(target);
},
complexTarget: true,
complexSelect: true,
filterCard: () => false,
selectCard: -1,
targetprompt: ["造成伤害", "受到伤害"],
multitarget: true,
content: function () {
"step 0";
player.addTempSkill("dcquanjian_damage", "phaseUseAfter");
targets[0]
.chooseControl()
.set("choiceList", ["对" + get.translation(targets[1]) + "造成1点伤害", "本回合下次受到的伤害+1"])
.set("ai", function () {
return _status.event.eff >= 0 ? 0 : 1;
})
.set("eff", get.damageEffect(targets[1], targets[0], targets[0]));
"step 1";
if (result.index == 0) {
targets[1].damage(targets[0]);
} else {
target.addMark("dcquanjian_effect", 1, false);
target.addTempSkill("dcquanjian_effect");
}
},
ai: {
result: {
player: function (player, target) {
if (ui.selected.targets.length == 0) {
if (!game.hasPlayer(current => current.inRangeOf(target) && get.damageEffect(current, target, player) > 0)) return 0;
if (get.attitude(player, target) > 0) return 2;
return 1;
}
return get.damageEffect(target, ui.selected.targets[0], player, player);
},
},
},
},
draw: {
audio: "dcquanjian",
filterTarget: function (card, player, target) {
if (target == player) return false;
var num = target.countCards("h");
if (num > target.getHandcardLimit()) return true;
return num < Math.min(5, target.getHandcardLimit());
},
filterCard: () => false,
selectCard: -1,
content: function () {
"step 0";
player.addTempSkill("dcquanjian_draw", "phaseUseAfter");
var num1 = target.countCards("h"),
num2 = target.getHandcardLimit();
var num = 0;
if (num1 > num2) {
event.index = 0;
num = num1 - num2;
target
.chooseControl()
.set("choiceList", ["弃置" + get.cnNumber(num) + "张手牌", "本回合下次受到的伤害+1"])
.set("ai", function () {
var player = _status.event.player;
if (
_status.event.number == 1 &&
player.hasCard(function (card) {
return lib.filter.cardDiscardable(card, player, "dcquanjian_draw") && get.value(card) < 5;
}, "h")
)
return 0;
return 1;
})
.set("number", num);
} else {
event.index = 1;
num = Math.min(num2, 5) - num1;
if (num <= 0) event.finish();
else
target
.chooseControl()
.set("choiceList", ["摸" + get.cnNumber(num) + "张牌,且本回合内不能使用或打出手牌", "本回合下次受到的伤害+1"])
.set("ai", function () {
return 0;
});
}
event.num = num;
"step 1";
if (result.index == 0) {
if (event.index == 0) target.chooseToDiscard("h", true, num);
else target.draw(num);
} else {
target.addMark("dcquanjian_effect", 1, false);
target.addTempSkill("dcquanjian_effect");
event.finish();
}
"step 2";
target.addTempSkill("dcquanjian_disable");
},
ai: {
result: {
target: function (player, target) {
var num1 = target.countCards("h"),
num2 = target.getHandcardLimit();
if (num1 > num2) return -1;
return Math.min(5, num2) - num1;
},
},
},
},
effect: {
charlotte: true,
trigger: { player: "damageBegin3" },
forced: true,
onremove: true,
marktext: "谏",
content: function () {
trigger.num += player.countMark(event.name);
player.removeSkill(event.name);
},
intro: { content: "下次受到的伤害+#" },
ai: { threaten: 2.5 },
},
disable: {
charlotte: true,
mod: {
cardEnabled(card, player) {
if (card.cards) {
const hs = player.getCards("h");
if (card.cards.some(card => hs.includes(card))) return false;
}
},
cardSavable(card, player) {
if (card.cards) {
const hs = player.getCards("h");
if (card.cards.some(card => hs.includes(card))) return false;
}
},
},
mark: true,
marktext: "禁",
intro: { content: "不能使用或打出手牌" },
ai: { threaten: 2.5 },
},
},
},
dctujue: {
audio: 2,
trigger: { player: "dying" },
direct: true,
limited: true,
skillAnimation: true,
animationColor: "gray",
filter: function (event, player) {
return player.countCards("he") > 0;
},
content: function () {
"step 0";
player
.chooseTarget(lib.filter.notMe, get.prompt2("dctujue"))
.set("ai", function (target) {
if (_status.event.skip) return 0;
return 200 + get.attitude(_status.event.player, target);
})
.set("skip", player.countCards("hs", { name: ["tao", "jiu"] }) + player.hp > 0);
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dctujue", target);
player.awakenSkill("dctujue");
var cards = player.getCards("he");
player.give(cards, target);
player.recover(cards.length);
player.draw(cards.length);
}
},
},
//尹夫人
dcyingyu: {
audio: 2,
trigger: { player: ["phaseZhunbeiBegin", "phaseJieshuBegin"] },
direct: true,
filter: function (event, player) {
if (event.name == "phaseJieshu" && !player.storage.dcyingyu) return false;
return (
game.countPlayer(function (current) {
return current.countCards("h") > 0;
}) > 1
);
},
content: function () {
"step 0";
player
.chooseTarget(2, get.prompt("dcyingyu"), "展示两名角色的各一张手牌。若这两张牌花色不同,则你可以令其中一名角色获得另一名角色的展示牌。", function (card, player, target) {
return target.countCards("h") > 0;
})
.set("ai", function (target) {
var player = _status.event.player;
if (!ui.selected.targets.length) return get.attitude(player, target);
return 1 - get.attitude(player, target);
});
"step 1";
if (result.bool) {
var targets = result.targets.sortBySeat();
event.targets = targets;
event.cards = [];
player.logSkill("dcyingyu", targets);
player.choosePlayerCard(targets[0], true, "h");
} else event.finish();
"step 2";
var card = result.cards[0];
player.line(targets[0]);
player.showCards(card, get.translation(player) + "对" + get.translation(targets[0]) + "发动了【媵予】");
event.cards.push(card);
player.choosePlayerCard(targets[1], true, "h");
"step 3";
var card = result.cards[0];
player.line(targets[1]);
player.showCards(card, get.translation(player) + "对" + get.translation(targets[1]) + "发动了【媵予】");
event.cards.push(card);
if (get.suit(cards[0], targets[0]) == get.suit(cards[1], targets[1])) event.finish();
"step 4";
var str1 = get.translation(targets[0]),
str2 = get.translation(targets[1]);
player
.chooseControl("cancel2")
.set("choiceList", ["令" + str1 + "获得" + str2 + "的" + get.translation(cards[1]), "令" + str2 + "获得" + str1 + "的" + get.translation(cards[0])])
.set("goon", get.attitude(player, targets[0]) > 0 ? 0 : 1)
.set("ai", () => _status.event.goon);
"step 5";
if (result.control != "cancel2") {
var i = result.index;
targets[1 - i].give(cards[1 - i], targets[i], "give");
}
},
onremove: true,
},
dcyongbi: {
audio: 2,
enable: "phaseUse",
filter: function (event, player) {
return player.countCards("h") > 0 && game.hasPlayer(current => lib.skill.dcyongbi.filterTarget(null, player, current));
},
filterTarget: function (card, player, target) {
return target != player && target.hasSex("male");
},
selectCard: -1,
filterCard: true,
position: "h",
limited: true,
skillAnimation: true,
animationColor: "fire",
discard: false,
lose: false,
content: function () {
"step 0";
player.awakenSkill("dcyongbi");
if (player.hasSkill("dcyingyu", null, null, false)) player.storage.dcyingyu = true;
player.give(cards, target);
"step 1";
var list = [];
for (var i of cards) {
list.add(get.suit(i, player));
if (list.length >= 3) break;
}
if (list.length >= 2) {
player.addMark("dcyongbi_eff1", 2, false);
player.addSkill("dcyongbi_eff1");
target.addMark("dcyongbi_eff1", 2, false);
target.addSkill("dcyongbi_eff1");
}
if (list.length >= 3) {
player.addMark("dcyongbi_eff2", 1, false);
player.addSkill("dcyongbi_eff2");
target.addMark("dcyongbi_eff2", 1, false);
target.addSkill("dcyongbi_eff2");
}
},
ai: {
order: 1,
result: {
target: function (player, target) {
if (player.hasUnknown()) return 0;
var zhu = get.zhu(player);
if (zhu && get.attitude(player, zhu) > 0) {
if (target == zhu) return 4;
}
return 1;
},
},
},
subSkill: {
eff1: {
mod: {
maxHandcard: (player, num) => num + player.countMark("dcyongbi_eff1"),
},
charlotte: true,
onremove: true,
marktext: "拥",
intro: { content: "手牌上限+#" },
},
eff2: {
trigger: { player: "damageBegin4" },
forced: true,
filter: function (event, player) {
return event.num > 1;
},
content: function () {
trigger.num -= player.countMark("dcyongbi_eff2");
},
charlotte: true,
onremove: true,
marktext: "嬖",
intro: { content: "受到大于1的伤害时,此伤害-#" },
},
},
},
//吕旷吕翔
dcshuhe: {
audio: 2,
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return player.countCards("h") > 0;
},
filterCard: true,
position: "h",
discard: false,
lose: false,
delay: false,
check: function (cardx) {
var player = _status.event.player;
var num1 = get.number(cardx),
players = game.filterPlayer();
var goon = false,
effect = 0;
for (var current of players) {
var cards = current.getCards("ej", function (card) {
var num = get.number(card);
return num == num1;
});
if (cards.length) {
goon = true;
var att = get.attitude(player, current);
for (var card of cards) {
if (get.position(card) == "e") {
var val = get.value(card, current);
if (att <= 0) effect += val;
else effect -= val / 2;
} else {
var eff = get.effect(current, { name: card.viewAs || card.name }, player, player);
effect -= get.sgn(att) * eff;
}
}
}
}
if (goon) {
if (effect > 0) return 6 + effect - get.value(cardx);
return 0;
}
return game.hasPlayer(function (current) {
return current != player && get.attitude(player, current) > 0;
})
? 6 - get.value(cardx)
: 0;
},
content: function () {
"step 0";
player.showCards(cards, get.translation(player) + "发动了【数合】");
player.addMark("dcliehou", 1);
"step 1";
event.cards2 = [];
var num1 = get.number(cards[0], player);
var lose_list = [],
players = game.filterPlayer();
for (var current of players) {
var cards = current.getCards("ej", function (card) {
var num = get.number(card);
return num == num1;
});
if (cards.length > 0) {
player.line(current, "thunder");
current.$throw(cards);
lose_list.push([current, cards]);
event.cards2.addArray(cards);
}
}
if (lose_list.length) {
event.lose_list = lose_list;
game.loseAsync({
lose_list: lose_list,
}).setContent("chooseToCompareLose");
} else {
event.goto(3);
player.chooseTarget(true, lib.filter.notMe, "将" + get.translation(event.cards[0]) + "交给一名其他角色").set("ai", function (target) {
return get.attitude(_status.event.player, target);
});
}
"step 2";
var cards = event.cards2;
if (cards.length > 0) {
if (event.lose_list) game.delayx();
player.gain(cards, "gain2");
}
event.finish();
"step 3";
if (result.bool) {
var target = result.targets[0];
player.line(target, "green");
player.give(cards, target);
}
},
ai: {
order: 2,
result: {
player: 1,
},
},
},
dcliehou: {
audio: 2,
trigger: { player: "phaseDrawBegin2" },
forced: true,
filter: function (event, player) {
return !event.numFixed;
},
content: function () {
var num = Math.min(5, 1 + player.countMark("dcliehou"));
trigger.num += num;
trigger._dcliehou = num;
},
group: "dcliehou_discard",
subSkill: {
discard: {
trigger: { player: "phaseDrawEnd" },
forced: true,
filter: function (event, player) {
return typeof event._dcliehou == "number";
},
content: function () {
"step 0";
var num = trigger._dcliehou;
player
.chooseToDiscard(num, "he", "弃置" + get.cnNumber(num) + "张牌,或失去1点体力")
.set("ai", function (card) {
if (_status.event.goon) return 6 - get.value(card);
return 26 - get.value(card);
})
.set("goon", player.hp > Math.max(1, 4 - num) || get.effect(player, { name: "losehp" }, player, player) > 0);
"step 1";
if (!result.bool) player.loseHp();
},
},
},
marktext: "爵",
intro: {
name: "列侯(爵)",
name2: "爵",
content: "〖列侯〗的摸牌数+#",
},
},
//管亥
suoliang: {
audio: 2,
trigger: { source: "damageSource" },
logTarget: "player",
usable: 1,
filter: function (event, player) {
return event.player != player && event.player.maxHp > 0 && event.player.countCards("he") > 0;
},
check: function (event, player) {
return get.attitude(player, event.player) <= 0;
},
content: function () {
"step 0";
var target = trigger.player;
event.target = target;
player.choosePlayerCard(target, true, "he", [1, target.maxHp], "选择" + get.translation(target) + "的至多" + get.cnNumber(target.maxHp) + "张牌");
"step 1";
if (result.bool) {
player.showCards(result.cards, get.translation(player) + "对" + get.translation(target) + "发动了【索粮】");
var cards = result.cards.filter(function (card) {
var suit = get.suit(card, target);
if (suit != "heart" && suit != "club") return false;
return lib.filter.canBeGained(card, target, player);
});
if (cards.length) player.gain(cards, target, "giveAuto", "bySelf");
else {
var cards = result.cards.filter(function (card) {
return lib.filter.canBeDiscarded(card, target, player);
});
if (cards.length) target.discard(cards, "notBySelf");
}
}
},
},
qinbao: {
audio: 2,
trigger: { player: "useCard" },
forced: true,
filter: function (event, player) {
return (
(event.card.name == "sha" || get.type(event.card, null, false) == "trick") &&
game.hasPlayer(function (current) {
return current != player && current.countCards("h") >= player.countCards("h");
})
);
},
content: function () {
var hs = player.countCards("h");
trigger.directHit.addArray(
game.filterPlayer(function (current) {
return current != player && current.countCards("h") >= hs;
})
);
},
ai: {
threaten: 1.4,
directHit_ai: true,
skillTagFilter: function (player, tag, arg) {
return (
player.countCards("h", function (card) {
return !ui.selected.cards.includes(card);
}) <= arg.target.countCards("h")
);
},
},
},
//胡昭
midu: {
audio: 2,
enable: "phaseUse",
usable: 1,
chooseButton: {
dialog: function (event, player) {
var dialog = ui.create.dialog("弥笃:选择要废除或恢复的装备栏或判定区", "hidden");
dialog.classList.add("withbg");
dialog.noforcebutton = true;
var list1 = [],
list2 = [];
for (var i = 1; i < 6; i++) {
for (var j = 0; j < player.countEnabledSlot(i); j++) {
list1.push(i);
}
if (player.hasDisabledSlot(i)) list2.push(i);
}
(player.isDisabledJudge() ? list2 : list1).push(-1);
var addTable = function (list, bool) {
const adds = [];
for (var i of list) {
adds.push([[i, bool], i > 0 ? get.translation("equip" + i) + "栏" : "判定区"]);
}
dialog.add([adds, "tdnodes"]);
};
if (list1.length) {
dialog.addText("未废除");
addTable(list1, true);
}
if (list2.length) {
dialog.addText("已废除");
addTable(list2, false);
}
return dialog;
},
filter: function (button, player) {
if (!ui.selected.buttons.length) return true;
if (!ui.selected.buttons[0].link[1]) return false;
return button.link[1];
},
check: function (button) {
var player = _status.event.player;
if (!button.link[1]) {
if (button.link[0] <= 0) return -10;
if (
player.hasCard(function (card) {
return get.subtype(card) == "equip" + button.link[0];
}, "hs")
)
return 15;
return 10;
}
if (
button.link[0] <= 0 ||
(player.hasEmptySlot(button.link[0]) &&
!player.hasCard(function (card) {
return get.subtype(card) == "equip" + button.link[0] && player.canUse(card, player) && get.effect(player, card, player, player) > 0;
}, "hs"))
)
return 5;
return 0;
},
select: [1, Infinity],
backup: function (links, player) {
if (!links[0][1]) {
return {
audio: "midu",
selectCard: -1,
selectTarget: -1,
filterCard: () => false,
filterTarget: () => false,
equip: links[0][0],
content: function () {
var pos = lib.skill.midu_backup.equip;
if (pos <= 0) player.enableJudge();
else player.enableEquip(pos);
player.addTempSkills("rehuomo", { player: "phaseBegin" });
},
};
} else {
return {
audio: "midu",
selectCard: -1,
filterCard: () => false,
filterTarget: true,
equip: links.map(i => i[0]).sort(),
content: function () {
var list = lib.skill.midu_backup.equip,
num = list.length,
bool = false;
if (list.includes(-1)) {
list.remove(-1);
bool = true;
}
if (list.length > 0) player.disableEquip(list);
if (bool) player.disableJudge();
target.draw(num);
},
ai: {
tag: {
draw: 1,
},
result: {
target: 2,
},
},
};
}
},
prompt: function (links, player) {
if (!links[0][1]) {
return "恢复一个装备栏或判定区并获得〖活墨〗";
}
var numc = get.cnNumber(links.length);
return "废除" + numc + "个区域并令一名角色摸" + numc + "张牌";
},
},
derivation: "rehuomo",
ai: {
order: 8,
result: { player: 1 },
},
subSkill: { backup: {} },
},
xianwang: {
mod: {
globalTo: function (source, player, distance) {
var num = player.countDisabledSlot();
if (num > 0) return distance + (num > 2 ? 2 : 1);
},
globalFrom: function (source, player, distance) {
var num = source.countDisabledSlot();
if (num > 0) return distance - (num > 2 ? 2 : 1);
},
},
},
//刘巴
dczhubi: {
audio: 2,
trigger: {
global: ["loseAfter", "loseAsyncAfter"],
},
filter: function (event, player) {
if (event.type != "discard" || event.getlx === false) return false;
for (var i of event.cards) {
if (get.suit(i, event.player) == "diamond") return true;
}
return false;
},
prompt2: "检索一张【无中生有】并置于牌堆顶",
content: function () {
var card = get.cardPile(function (card) {
return card.name == "wuzhong" && get.suit(card) != "diamond";
});
if (card) {
game.log(player, "将", card, "置于牌堆顶");
card.fix();
ui.cardPile.insertBefore(card, ui.cardPile.firstChild);
game.updateRoundNumber();
game.delayx();
}
},
},
dcliuzhuan: {
audio: 2,
group: ["dcliuzhuan_mark", "dcliuzhuan_gain"],
mod: {
targetEnabled: function (card) {
if (card.cards) {
for (var i of card.cards) {
if (i.hasGaintag("dcliuzhuan_tag")) return false;
}
} else if (get.itemtype(card) == "card") {
if (card.hasGaintag("dcliuzhuan_tag")) return false;
}
},
},
subSkill: {
gain: {
audio: "dcliuzhuan",
trigger: { global: ["loseAfter", "loseAsyncAfter", "cardsDiscardAfter"] },
forced: true,
logTarget: () => _status.currentPhase,
filter: function (event, player) {
var current = _status.currentPhase;
if (!current) return false;
if (event.name == "cardsDiscard") {
var evtx = event.getParent();
if (evtx.name != "orderingDiscard") return false;
var evtx2 = evtx.relatedEvent || evtx.getParent();
return current.hasHistory("lose", function (evtx3) {
var evtx4 = evtx3.relatedEvent || evtx3.getParent();
if (evtx2 != evtx4) return false;
for (var i in evtx3.gaintag_map) {
if (evtx3.gaintag_map[i].includes("dcliuzhuan_tag")) return true;
}
});
//return false;
} else if (event.name == "lose") {
if (event.player != current || event.position != ui.discardPile) return false;
for (var i in event.gaintag_map) {
if (event.gaintag_map[i].includes("dcliuzhuan_tag")) return true;
}
return false;
}
return current.hasHistory("lose", function (evt) {
if (evt.getParent() != event || evt.position != ui.discardPile) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("dcliuzhuan_tag")) return true;
}
});
},
content: function () {
var cards,
current = _status.currentPhase;
if (trigger.name == "lose")
cards = trigger.hs.filter(function (i) {
return trigger.gaintag_map[i.cardid] && trigger.gaintag_map[i.cardid].includes("dcliuzhuan_tag") && get.position(i, true) == "d";
});
else if (trigger.name == "cardsDiscard") {
var evtx = trigger.getParent();
var evtx2 = evtx.relatedEvent || evtx.getParent();
var bool = false;
var history = current.getHistory("lose", function (evtx3) {
var evtx4 = evtx3.relatedEvent || evtx3.getParent();
if (evtx2 != evtx4) return false;
for (var i in evtx3.gaintag_map) {
if (evtx3.gaintag_map[i].includes("dcliuzhuan_tag")) return true;
}
});
cards = trigger.cards.filter(function (i) {
for (var evt of history) {
if (evt.gaintag_map[i.cardid] && evt.gaintag_map[i.cardid].includes("dcliuzhuan_tag") && get.position(i, true) == "d") return true;
}
return false;
});
} else {
cards = [];
current.getHistory("lose", function (evt) {
if (evt.getParent() != trigger || evt.position != ui.discardPile) return false;
for (var card of evt.hs) {
if (get.position(card, true) != "d") continue;
var i = card.cardid;
if (evt.gaintag_map[i] && evt.gaintag_map[i].includes("dcliuzhuan_tag")) cards.push(card);
}
});
}
if (cards && cards.length > 0) player.gain(cards, "gain2");
},
},
mark: {
trigger: { global: "gainBegin" },
forced: true,
popup: false,
silent: true,
lastDo: true,
filter: function (event, player) {
if (player == event.player || event.player != _status.currentPhase) return false;
var evt = event.getParent("phaseDraw");
if (evt && evt.name == "phaseDraw") return false;
return true;
},
content: function () {
trigger.gaintag.add("dcliuzhuan_tag");
trigger.player.addTempSkill("dcliuzhuan_tag");
},
},
tag: {
charlotte: true,
onremove: (player, skill) => player.removeGaintag(skill),
},
},
},
//张勋
suizheng: {
audio: 2,
trigger: { player: "phaseJieshuBegin" },
direct: true,
content: function () {
"step 0";
player.chooseTarget(get.prompt("suizheng"), "令一名角色下回合内获得〖随征〗效果").set("", function (target) {
var player = _status.event.player,
att = get.attitude(player, target);
if (target.hasJudge("lebu")) return att / 2;
return att * get.threaten(target) * Math.sqrt(2 + player == target ? player.countCards("h", "sha") * 2 : target.countCards("h"));
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("suizheng", target);
target.addMark("suizheng_effect", 1, false);
target.markAuto("suizheng_source", [player]);
target.addTempSkill("suizheng_effect", {
player: player == target ? "phaseJieshuBefore" : "phaseAfter",
});
}
},
subSkill: {
effect: {
audio: "suizheng",
charlotte: true,
mod: {
targetInRange: function (card) {
if (card.name == "sha") return true;
},
cardUsable: function (card, player, num) {
if (card.name == "sha") return num + player.countMark("suizheng_effect");
},
},
trigger: { player: "phaseUseEnd" },
forced: true,
popup: false,
filter: function (event, player) {
var list = player.getStorage("suizheng_source");
if (!list.filter(i => i.isIn().length)) return false;
return player.hasHistory("sourceDamage", function (evt) {
return evt.player.isIn() && evt.getParent("phaseUse") == event;
});
},
content: function () {
"step 0";
var targets = player.getStorage("suizheng_source").slice(0).sortBySeat();
event.targets = targets;
"step 1";
var target = targets.shift();
event.target = target;
var list = [];
player.getHistory("sourceDamage", function (evt) {
if (evt.player.isIn() && evt.getParent("phaseUse") == trigger) list.add(evt.player);
});
if (!list.length) event.finish();
else if (target.isIn()) {
list = list.filter(function (i) {
return target.canUse("sha", i, false);
});
if (list.length > 0)
target
.chooseTarget("随征:是否对一名角色使用【杀】?", function (card, player, target) {
return _status.event.targets.includes(target);
})
.set("targets", list)
.set("ai", function (target) {
var player = _status.event.player;
return get.effect(target, { name: "sha" }, player, player);
});
} else event._result = { bool: false };
"step 2";
if (result.bool) {
target.useCard(
{
name: "sha",
isCard: true,
},
result.targets,
false,
"suizheng_effect"
);
}
if (targets.length > 0) event.goto(1);
},
onremove: function (player) {
delete player.storage.suizheng_effect;
delete player.storage.suizheng_source;
},
intro: { content: "使用【杀】无距离限制且次数上限+#" },
},
},
},
//纪灵
dcshuangren: {
audio: 2,
trigger: { player: "phaseUseBegin" },
direct: true,
preHidden: true,
filter: function (event, player) {
return (
player.countCards("h") > 0 &&
game.hasPlayer(function (current) {
return current != player && player.canCompare(current);
})
);
},
content: function () {
"step 0";
var goon;
if (player.needsToDiscard() > 1) {
goon = player.hasCard(function (card) {
return card.number > 10 && get.value(card) <= 5;
});
} else if (player.hasSha()) {
goon = player.hasCard(function (card) {
return (card.number >= 9 && get.value(card) <= 5) || get.value(card) <= 3;
});
} else {
goon = player.hasCard(function (card) {
return get.value(card) <= 5;
});
}
player
.chooseTarget(get.prompt2("dcshuangren"), function (card, player, target) {
return player.canCompare(target);
})
.set("ai", function (target) {
var player = _status.event.player;
if (_status.event.goon && get.attitude(player, target) < 0) {
return get.effect(target, { name: "sha" }, player, player);
}
return 0;
})
.set("goon", goon)
.setHiddenSkill(event.name);
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.logSkill("dcshuangren", target);
player.chooseToCompare(target);
} else {
event.finish();
}
"step 2";
if (result.bool) {
var target = event.target;
if (
game.hasPlayer(function (current) {
if (target == current || target.group != current.group) return false;
return player.canUse("sha", current, false);
})
) {
var str = "请选择视为使用【杀】的目标";
var str2 = "操作提示:选择一名角色B,或选择包含A(" + get.translation(target) + ")在内的两名角色A和B(B的势力需为" + get.translation(target.group) + "势力)";
player
.chooseTarget([1, 2], str, str2, true, function (card, player, target) {
if (!player.canUse("sha", target, false)) return false;
var current = _status.event.target;
if (target == current) return true;
if (target.group != current.group) return false;
if (!ui.selected.targets.length) return true;
return ui.selected.targets[0] == current;
//return current==target;
})
.set("ai", function (target) {
var player = _status.event.player;
return get.effect(target, { name: "sha" }, player, player);
})
.set("target", target)
.set("complexTarget", true);
} else {
player.useCard({ name: "sha", isCard: true }, target, false);
event.finish();
}
} else {
player.addTempSkill("dcshuangren_debuff", "phaseUseAfter");
event.finish();
}
"step 3";
if (result.bool && result.targets && result.targets.length) {
player.useCard({ name: "sha", isCard: true }, result.targets, false);
}
},
subSkill: {
debuff: {
charlotte: true,
mod: {
cardEnabled: function (card) {
if (card.name == "sha") return false;
},
},
},
},
},
//羊祜
dcdeshao: {
audio: 2,
usable: 2,
trigger: { target: "useCardToTargeted" },
filter: function (event, player) {
return player != event.player && get.color(event.card) == "black";
},
logTarget: "player",
check: function (event, player) {
var eff = get.effect(player, { name: "draw" }, player, player);
if (player.countCards("h") + 1 <= event.player.countCards("h") && event.player.countCards("he") > 0) eff += get.effect(event.player, { name: "guohe_copy2" }, player, player);
return eff;
},
content: function () {
"step 0";
player.draw();
"step 1";
var target = trigger.player;
if (player.countCards("h") <= target.countCards("h") && target.countCards("he") > 0) {
player.discardPlayerCard(target, true, "he");
player.addExpose(0.2);
}
},
},
dcmingfa: {
audio: 2,
trigger: { player: "useCardAfter" },
direct: true,
filter: function (event, player) {
return player.isPhaseUsing() && (event.card.name == "sha" || get.type(event.card) == "trick") && event.cards.filterInD().length > 0 && !player.getExpansions("dcmingfa").length;
},
content: function () {
"step 0";
var str,
cards = trigger.cards.filterInD(),
card = trigger.card;
if (cards.length == 1 && card.name == cards[0].name && (card.nature || false) == (cards[0].nature || false)) str = get.translation(cards[0]);
else str = get.translation(trigger.card) + "(" + get.translation(cards) + ")";
var cardx = {
name: trigger.card.name,
nature: trigger.card.nature,
isCard: true,
};
player
.chooseTarget(lib.filter.notMe, get.prompt("dcmingfa"), "将" + str + "作为“明伐”牌置于武将牌上,并选择一名其他角色。该角色下回合结束时对其执行〖明伐〗的后续效果。")
.set("card", cardx)
.set(
"goon",
(function () {
var getMax = function (card) {
return Math.max.apply(
Math,
game
.filterPlayer(function (current) {
return current != player && lib.filter.targetEnabled2(card, player, current);
})
.map(function (i) {
return get.effect(i, card, player, player) * Math.sqrt(Math.min(i.getHandcardLimit(), 1 + i.countCards("h")));
})
.concat([0])
);
};
var eff1 = getMax(cardx);
if (
player.hasCard(function (card) {
if ((card.name != "sha" && get.type(card) != "trick") || !player.hasValueTarget(card, null, true)) return false;
return (
getMax({
name: get.name(card),
nature: get.nature(card),
isCard: true,
}) >= eff1
);
}, "hs")
)
return false;
return true;
})()
)
.set("ai", function (target) {
if (!_status.event.goon) return 0;
var player = _status.event.player,
card = _status.event.card;
if (!lib.filter.targetEnabled2(card, player, target)) return 0;
return get.effect(target, card, player, player) * Math.sqrt(Math.min(target.getHandcardLimit(), 1 + target.countCards("h")));
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcmingfa", target);
var card = {
name: trigger.card.name,
nature: trigger.card.nature,
isCard: true,
};
player.storage.dcmingfa_info = [card, target];
player.addToExpansion(trigger.cards.filterInD(), "gain2").gaintag.add("dcmingfa");
}
},
group: "dcmingfa_use",
ai: { expose: 0.2 },
intro: {
mark: function (dialog, storage, player) {
var cards = player.getExpansions("dcmingfa");
if (!cards.length) return "没有“明伐”牌";
else dialog.add(cards);
var info = player.storage.dcmingfa_info;
if (info) {
dialog.addText("记录牌:" + get.translation(info[0]) + "
记录目标:" + get.translation(info[1]));
}
},
content: "expansion",
},
onremove: function (player, skill) {
var cards = player.getExpansions(skill);
if (cards.length) player.loseToDiscardpile(cards);
delete player.storage.dcmingfa_info;
},
subSkill: {
use: {
audio: "dcmingfa",
trigger: { global: ["phaseEnd", "die"] },
forced: true,
filter: function (event, player) {
if (!player.storage.dcmingfa_info || !player.getExpansions("dcmingfa").length) return false;
return event.player == player.storage.dcmingfa_info[1];
},
content: function () {
"step 0";
var target = trigger.player;
event.target = target;
var card = player.storage.dcmingfa_info[0];
delete player.storage.dcmingfa_info;
event.card = card;
event.count = Math.max(1, Math.min(5, target.countCards("h")));
if (!event.player.isIn()) event.goto(2);
"step 1";
event.count--;
if (target.isIn() && lib.filter.targetEnabled2(card, player, target)) {
player.useCard(get.copy(card), target);
if (event.count > 0) event.redo();
}
"step 2";
var cards = player.getExpansions("dcmingfa");
if (cards.length > 0) player.loseToDiscardpile(cards);
},
},
},
},
//蔡瑁张允
lianzhou: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
forced: true,
filter: function (event, player) {
if (!player.isLinked()) return true;
return game.hasPlayer(function (current) {
return current != player && current.hp == player.hp && !current.isLinked();
});
},
content: function () {
"step 0";
if (!player.isLinked()) player.link();
"step 1";
var num = game.countPlayer(function (current) {
return current != player && current.hp == player.hp && !current.isLinked();
});
if (num > 0) {
player
.chooseTarget([1, num], "选择横置任意名体力值等于你的角色", function (card, player, current) {
return current != player && current.hp == player.hp && !current.isLinked();
})
.set("ai", function (target) {
var player = _status.event.player;
return get.effect(target, { name: "tiesuo" }, player, player);
});
} else event.finish();
"step 2";
if (result.bool) {
var targets = result.targets.sortBySeat();
player.line(targets, "green");
for (var i of targets) i.link();
}
},
ai: { halfneg: true },
},
jinglan: {
audio: 2,
trigger: { source: "damageSource" },
forced: true,
content: function () {
var delta = player.countCards("h") - player.hp;
if (delta > 0) player.chooseToDiscard("h", 4, true);
else if (delta == 0) {
player.chooseToDiscard("he", true);
player.recover();
} else {
player.damage("fire", "nosource");
player.draw(5);
}
},
ai: { halfneg: true },
},
//滕公主
xingchong: {
audio: 2,
trigger: { global: "roundStart" },
direct: true,
filter: function (event, player) {
return player.maxHp > 0;
},
content: function () {
"step 0";
var list = [];
for (var i = 0; i <= Math.min(5, player.maxHp); i++) {
list.push(get.cnNumber(i) + "张");
}
list.push("cancel2");
player
.chooseControl(list)
.set("prompt", get.prompt("xingchong"))
.set("prompt2", "请首先选择摸牌的张数")
.set("ai", function () {
var player = _status.event.player,
num1 = player.maxHp,
num2 = player.countCards("h");
if (num1 <= num2) return 0;
return Math.ceil((num1 - num2) / 2);
});
"step 1";
if (result.control != "cancel2") {
player.logSkill("xingchong");
var num2 = result.index;
if (num2 > 0) player.draw(num2);
var num = Math.min(5, player.maxHp) - num2;
if (num == 0) event.finish();
else event.num = num;
} else event.finish();
"step 2";
if (player.countCards("h") > 0) {
player.chooseCard("h", [1, Math.min(player.countCards("h"), event.num)], "请选择要展示的牌").set("ai", () => 1 + Math.random());
} else event.finish();
"step 3";
if (result.bool) {
var cards = result.cards;
player.showCards(cards, get.translation(player) + "发动了【幸宠】");
player.addGaintag(cards, "xingchong");
player.addTempSkill("xingchong_effect", "roundStart");
}
},
subSkill: {
effect: {
audio: "xingchong",
trigger: {
player: ["loseAfter"],
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
filter: function (event, player) {
var evt = event.getl(player);
if (!evt || !evt.cards2 || !evt.cards2.length) return false;
if (event.name == "lose") {
for (var i in event.gaintag_map) {
if (event.gaintag_map[i].includes("xingchong")) return true;
}
return false;
}
return player.hasHistory("lose", function (evt) {
if (event != evt.getParent()) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("xingchong")) return true;
}
return false;
});
},
forced: true,
popup: false,
charlotte: true,
onremove: function (player) {
player.removeGaintag("xingchong");
},
content: function () {
"step 0";
if (trigger.delay === false) game.delayx();
"step 1";
player.logSkill("xingchong_effect");
var num = 0;
if (trigger.name == "lose") {
for (var i in trigger.gaintag_map) {
if (trigger.gaintag_map[i].includes("xingchong")) num++;
}
} else
player.getHistory("lose", function (evt) {
if (trigger != evt.getParent()) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("xingchong")) num++;
}
});
player.draw(2 * num);
},
},
},
},
liunian: {
audio: 2,
trigger: { global: "phaseEnd" },
forced: true,
filter: function (event, player) {
return game.hasGlobalHistory("cardMove", function (evt) {
return evt.washCard && (evt.shuffleNumber == 1 || evt.shuffleNumber == 2);
});
},
content: function () {
"step 0";
if (
game.hasGlobalHistory("cardMove", function (evt) {
return evt.washCard && evt.shuffleNumber == 1;
})
) {
player.gainMaxHp();
game.delayx();
}
"step 1";
if (
game.hasGlobalHistory("cardMove", function (evt) {
return evt.washCard && evt.shuffleNumber == 2;
})
) {
player.recover();
game.delayx();
} else event.finish();
"step 2";
player.addSkill("liunian_effect");
player.addMark("liunian_effect", 10, false);
},
subSkill: {
effect: {
charlotte: true,
mod: {
maxHandcard: function (player, num) {
return num + player.countMark("liunian_effect");
},
},
marktext: "年",
intro: {
content: "手牌上限+#",
},
},
},
},
//黄承彦
dcjiezhen: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
return target != player;
},
content: function () {
var skills = target.getSkills(null, false, false).filter(function (i) {
if (i == "bazhen") return;
var info = get.info(i);
return info && !get.is.locked(i) && !info.limited && !info.juexingji && !info.zhuSkill && !info.charlotte;
});
target.addAdditionalSkills("dcjiezhen_blocker", "bazhen");
target.addSkill("dcjiezhen_blocker");
target.markAuto("dcjiezhen_blocker", skills);
player.addSkill("dcjiezhen_clear");
player.markAuto("dcjiezhen_clear", [target]);
},
ai: {
order: 1,
result: {
target: function (player, target) {
var skills = target.getSkills(null, false, false).filter(function (i) {
if (i == "bazhen") return;
var info = get.info(i);
return info && !get.is.locked(i) && !info.limited && !info.juexingji && !info.zhuSkill && !info.charlotte;
});
if (!skills.length && target.hasEmptySlot(2)) return 1;
return -0.5 * skills.length;
},
},
},
subSkill: {
blocker: {
init: function (player, skill) {
player.addSkillBlocker(skill);
},
onremove: function (player, skill) {
player.removeSkillBlocker(skill);
player.removeAdditionalSkill(skill);
delete player.storage.dcjiezhen_blocker;
},
charlotte: true,
locked: true,
skillBlocker: function (skill, player) {
return skill != "bazhen" && skill != "dcjiezhen_blocker" && !lib.skill[skill].charlotte && player.getStorage("dcjiezhen_blocker").includes(skill);
},
mark: true,
marktext: "阵",
intro: {
markcount: () => 0,
content: function (storage, player, skill) {
if (storage.length) return "失效技能:" + get.translation(storage);
return "无失效技能";
},
},
},
clear: {
audio: "dcjiezhen",
charlotte: true,
trigger: {
global: ["judgeAfter", "die"],
player: "phaseBegin",
},
forced: true,
forceDie: true,
onremove: true,
filter: function (event, player) {
if (event.name == "die") {
return player == event.player || player.getStorage("dcjiezhen_clear").includes(event.player);
} else if (event.name == "judge") {
return event.skill == "bagua" && player.getStorage("dcjiezhen_clear").includes(event.player);
}
return player.getStorage("dcjiezhen_clear").length > 0;
},
logTarget: function (event, player) {
if (event.name != "phase") return event.player;
return player.getStorage("dcjiezhen_clear");
},
content: function () {
"step 0";
var targets = player.getStorage("dcjiezhen_clear");
if (trigger.name == "die" && player == trigger.player) {
for (var target of targets) {
target.removeSkill("dcjiezhen_blocker");
}
player.removeSkill("dcjiezhen_clear");
event.finish();
return;
}
if (trigger.name == "phase") event.targets = targets.slice(0).sortBySeat();
else event.targets = [trigger.player];
"step 1";
var target = targets.shift();
var storage = player.getStorage("dcjiezhen_clear");
if (storage.includes(target)) {
storage.remove(target);
target.removeSkill("dcjiezhen_blocker");
if (target.isIn() && target.countGainableCards(player, "hej") > 0) player.gainPlayerCard(target, "hej", true);
}
if (targets.length > 0) {
event.redo();
} else {
player.removeSkill("dcjiezhen_clear");
}
},
},
},
derivation: "bazhen",
},
dczecai: {
audio: 2,
trigger: { global: "roundStart" },
limited: true,
skillAnimation: true,
direct: true,
animationColor: "soil",
filter: function (event, player) {
return game.roundNumber > 1;
},
getMax: function () {
var getNum = function (current) {
var history = current.actionHistory;
var num = 0;
for (var i = history.length - 2; i >= 0; i--) {
for (var j = 0; j < history[i].useCard.length; j++) {
if (get.type2(history[i].useCard[j].card, false) == "trick") num++;
}
if (history[i].isRound) break;
}
return num;
};
var max = 0,
current = false,
targets = game.filterPlayer();
for (var target of targets) {
var num = getNum(target);
if (num > max) {
max = num;
current = target;
} else if (num == max) current = false;
}
return current;
},
content: function () {
"step 0";
event.target = lib.skill.dczecai.getMax();
var str = "令一名其他角色于本轮内获得〖集智〗";
if (event.target && event.target != player) str += ";若选择的目标为" + get.translation(event.target) + ",则其获得一个额外的回合";
player
.chooseTarget(lib.filter.notMe, get.prompt("dczecai"), str)
.set("maximum", event.target)
.set("ai", function (target) {
if (target != _status.event.maximum) return 0;
return get.attitude(_status.event.player, target);
});
"step 1";
if (result.bool) {
player.awakenSkill("dczecai");
var target = result.targets[0];
player.logSkill("dczecai", target);
target.addAdditionalSkills("dczecai_effect", "rejizhi");
target.addTempSkill("dczecai_effect", "roundStart");
if (target == event.target) {
var evt = trigger;
target.insertPhase();
if (evt.player != target && !evt._finished) {
evt.finish();
evt._triggered = 5;
var evtx = evt.player.insertPhase();
delete evtx.skill;
}
}
}
},
derivation: "rejizhi",
subSkill: {
effect: {
charlotte: true,
mark: true,
marktext: "才",
intro: { content: "已拥有技能〖集智〗" },
},
},
},
dcyinshi: {
audio: 2,
trigger: { player: "damageBegin" },
usable: 1,
filter: function (event, player) {
return !event.card || get.color(event.card) == "none";
},
forced: true,
content: function () {
trigger.cancel();
},
group: "dcyinshi_gain",
subSkill: {
gain: {
audio: "dcyinshi",
trigger: { global: "judgeEnd" },
forced: true,
filter: function (event, player) {
return event.skill == "bagua" && event.result.card && get.position(event.result.card, true) == "o";
},
content: function () {
player.gain(trigger.result.card, "gain2");
},
},
},
},
//高览
xizhen: {
audio: 2,
trigger: { player: "phaseUseBegin" },
direct: true,
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current != player && (player.canUse("sha", current, false) || player.canUse("juedou", current, false));
});
},
content: function () {
"step 0";
player
.chooseTarget(get.prompt("xizhen"), "视为对一名角色使用【杀】或【决斗】", function (card, player, target) {
return target != player && (player.canUse("sha", target, false) || player.canUse("juedou", target, false));
})
.set("ai", function (target) {
var player = _status.event.player;
var eff1 = 0,
eff2 = 0;
if (player.canUse("sha", target, false)) eff1 = get.effect(target, { name: "sha" }, player, player);
if (player.canUse("juedou", target, false)) eff2 = get.effect(target, { name: "juedou" }, player, player);
var effx = Math.max(eff1, eff2);
if (effx <= 0) return 0;
if (target.isHealthy()) effx *= 3;
if (get.attitude(player, target) > 0) effx *= 1.6;
return effx;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.logSkill("xizhen", target);
var list = [];
if (player.canUse("sha", target, false)) list.push("sha");
if (player.canUse("juedou", target, false)) list.push("juedou");
if (list.length == 1) event._result = { control: list[0] };
else
player
.chooseControl(list)
.set("prompt", "视为对" + get.translation(target) + "使用…")
.set("ai", function () {
var player = _status.event.player,
target = _status.event.getParent().target;
var eff1 = get.effect(target, { name: "sha" }, player, player),
eff2 = get.effect(target, { name: "juedou" }, player, player);
return eff1 > eff2 ? 0 : 1;
});
} else event.finish();
"step 2";
player.useCard({ name: result.control, isCard: true }, target, false);
"step 3";
if (target.isIn()) {
player.storage.xizhen_effect = target;
player.addTempSkill("xizhen_effect", "phaseUseAfter");
}
},
subSkill: {
effect: {
audio: "xizhen",
charlotte: true,
onremove: true,
trigger: { global: ["useCard", "respond"] },
logTarget: function (event, player) {
return player.storage.xizhen_effect;
},
forced: true,
filter: function (event, player) {
return Array.isArray(event.respondTo) && event.respondTo[0] == player && player.storage.xizhen_effect && player.storage.xizhen_effect.isIn();
},
content: function () {
"step 0";
var target = player.storage.xizhen_effect;
event.target = target;
target.recover();
"step 1";
player.draw(target.isHealthy() ? 2 : 1);
},
mark: "character",
intro: { content: "已指定$为目标" },
},
},
},
//管宁
dunshi: {
audio: 2,
enable: ["chooseToUse", "chooseToRespond"],
usable: 1,
init: function (player, skill) {
if (!player.storage[skill]) player.storage[skill] = [["sha", "shan", "tao", "jiu"], 0];
},
hiddenCard: function (player, name) {
if (player.storage.dunshi && player.storage.dunshi[0].includes(name) && !player.getStat("skill").dunshi) return true;
return false;
},
marktext: "席",
mark: true,
intro: {
markcount: function (storage) {
return storage[1];
},
content: function (storage, player) {
if (!storage) return;
var str = "";
if (!storage[0].length) {
str += "已无可用牌";
} else {
str += "剩余可用牌:";
str += get.translation(storage[0]);
}
str += "
“席”标记数量:";
str += storage[1];
return str;
},
},
filter: function (event, player) {
if (event.type == "wuxie") return false;
var storage = player.storage.dunshi;
if (!storage || !storage[0].length) return false;
for (var i of storage[0]) {
var card = { name: i, isCard: true };
if (event.filterCard(card, player, event)) return true;
}
return false;
},
chooseButton: {
dialog: function (event, player) {
var list = [];
var storage = player.storage.dunshi;
for (var i of storage[0]) list.push(["基本", "", i]);
return ui.create.dialog("遁世", [list, "vcard"], "hidden");
},
filter: function (button, player) {
var evt = _status.event.getParent();
return evt.filterCard({ name: button.link[2], isCard: true }, player, evt);
},
check: function (button) {
var card = { name: button.link[2] },
player = _status.event.player;
if (_status.event.getParent().type != "phase") return 1;
if (card.name == "jiu") return 0;
if (card.name == "sha" && player.hasSkill("jiu")) return 0;
return player.getUseValue(card, null, true);
},
backup: function (links, player) {
return {
audio: "dunshi",
filterCard: function () {
return false;
},
popname: true,
viewAs: {
name: links[0][2],
isCard: true,
},
selectCard: -1,
precontent: function () {
player.addTempSkill("dunshi_damage");
player.storage.dunshi_damage = event.result.card.name;
},
};
},
prompt: function (links, player) {
return "选择【" + get.translation(links[0][2]) + "】的目标";
},
},
ai: {
respondSha: true,
respondShan: true,
skillTagFilter: function (player, tag, arg) {
var storage = player.storage.dunshi;
if (!storage || !storage[0].length) return false;
if (player.getStat("skill").dunshi) return false;
switch (tag) {
case "respondSha":
return (_status.event.type != "phase" || player == game.me || player.isUnderControl() || player.isOnline()) && storage[0].includes("sha");
case "respondShan":
return storage[0].includes("shan");
case "save":
if (arg == player && storage[0].includes("jiu")) return true;
return storage[0].includes("tao");
}
},
order: 2,
result: {
player: function (player) {
if (_status.event.type == "dying") {
return get.attitude(player, _status.event.dying);
}
return 1;
},
},
},
initList: function () {
var list,
skills = [];
var banned = ["xunyi", "mbyilie"];
if (get.mode() == "guozhan") {
list = [];
for (var i in lib.characterPack.mode_guozhan) list.push(i);
} else if (_status.connectMode) list = get.charactersOL();
else {
list = [];
for (var i in lib.character) {
if (lib.filter.characterDisabled2(i) || lib.filter.characterDisabled(i)) continue;
list.push(i);
}
}
for (var i of list) {
if (i.indexOf("gz_jun") == 0) continue;
for (var j of lib.character[i][3]) {
var skill = lib.skill[j];
if (!skill || skill.zhuSkill || banned.includes(j)) continue;
if (skill.ai && (skill.ai.combo || skill.ai.notemp || skill.ai.neg)) continue;
var info = get.translation(j);
for (var ix = 0; ix < info.length; ix++) {
if (/仁|义|礼|智|信/.test(info[ix]) == true) {
skills.add(j);
break;
}
}
}
}
_status.dunshi_list = skills;
},
subSkill: {
backup: { audio: "dunshi" },
damage: {
audio: "dunshi",
trigger: { global: "damageBegin2" },
forced: true,
charlotte: true,
filter: function (event, player) {
return event.source == _status.currentPhase;
},
onremove: true,
logTarget: "source",
content: function () {
"step 0";
event.cardname = player.storage.dunshi_damage;
player.removeSkill("dunshi_damage");
event.target = trigger.source;
var card = get.translation(trigger.source),
card2 = get.translation(event.cardname),
card3 = get.translation(trigger.player);
var list = ["防止即将对" + card3 + "造成的伤害,并令" + card + "获得一个技能名中包含“仁/义/礼/智/信”的技能", "从〖遁世〗中删除【" + card2 + "】并获得一枚“席”", "减1点体力上限,然后摸等同于“席”数的牌"];
var next = player.chooseButton([
"遁世:请选择两项",
[
list.map((item, i) => {
return [i, item];
}),
"textbutton",
],
]);
next.set("forced", true);
next.set("selectButton", 2);
next.set("ai", function (button) {
var player = _status.event.player;
switch (button.link) {
case 0:
if (get.attitude(player, _status.currentPhase) > 0) return 3;
return 0;
case 1:
return 1;
case 2:
var num = player.storage.dunshi[1];
for (var i of ui.selected.buttons) {
if (i.link == 1) num++;
}
if (num > 0 && player.isDamaged()) return 2;
return 0;
}
});
"step 1";
event.links = result.links.sort();
for (var i of event.links) {
game.log(player, "选择了", "#g【遁世】", "的", "#y选项" + get.cnNumber(i + 1, true));
}
if (event.links.includes(0)) {
trigger.cancel();
if (!_status.dunshi_list) lib.skill.dunshi.initList();
var list = _status.dunshi_list
.filter(function (i) {
return !target.hasSkill(i, null, null, false);
})
.randomGets(3);
if (list.length == 0) event.goto(3);
else {
event.videoId = lib.status.videoId++;
var func = function (skills, id, target) {
var dialog = ui.create.dialog("forcebutton");
dialog.videoId = id;
dialog.add("令" + get.translation(target) + "获得一个技能");
for (var i = 0; i < skills.length; i++) {
dialog.add('");
}
dialog.addText("
");
};
if (player.isOnline()) player.send(func, list, event.videoId, target);
else if (player == game.me) func(list, event.videoId, target);
player.chooseControl(list).set("ai", function () {
var controls = _status.event.controls;
if (controls.includes("cslilu")) return "cslilu";
return controls[0];
});
}
} else event.goto(3);
"step 2";
game.broadcastAll("closeDialog", event.videoId);
target.addSkills(result.control);
"step 3";
var storage = player.storage.dunshi;
if (event.links.includes(1)) {
storage[0].remove(event.cardname);
storage[1]++;
player.markSkill("dunshi");
}
if (event.links.includes(2)) {
player.loseMaxHp();
if (storage[1] > 0) player.draw(storage[1]);
}
},
},
},
},
//吉本
xunli: {
audio: 2,
trigger: {
global: ["loseAfter", "loseAsyncAfter"],
},
forced: true,
filter: function (event, player) {
if (event.type != "discard" || event.getlx === false || player.getExpansions("xunli").length >= 9) return false;
for (var i of event.cards) {
if (get.position(i, true) == "d" && get.color(i, event.cards2 && event.cards2.includes(i) ? event.player : false) == "black") return true;
}
return false;
},
content: function () {
"step 0";
var num = 9 - player.getExpansions("xunli").length;
var cards = [];
for (var i of trigger.cards) {
if (get.position(i, true) == "d" && get.color(i, trigger.cards2 && trigger.cards2.includes(i) ? trigger.player : false) == "black") cards.push(i);
}
if (cards.length <= num)
event._result = {
bool: true,
links: cards,
};
else
player
.chooseButton(true, num, ["寻疠:将" + get.cnNumber(num) + "张牌置于武将牌上", cards])
.set("forceAuto", true)
.set("ai", function (button) {
return get.value(button.link, _status.event.player);
});
"step 1";
if (result.bool) {
player.addToExpansion("gain2", result.links).gaintag.add("xunli");
}
},
marktext: "疠",
intro: {
content: "expansion",
markcount: "expansion",
},
group: "xunli_exchange",
subSkill: {
exchange: {
audio: "xunli",
trigger: { player: "phaseUseBegin" },
direct: true,
filter: function (event, player) {
return player.getExpansions("xunli").length > 0 && player.hasCard(card => get.color(card, player) == "black", "h");
},
content: function () {
"step 0";
var cards = player.getExpansions("xunli");
if (!cards.length || !player.countCards("h")) {
event.finish();
return;
}
var next = player.chooseToMove("寻疠:是否交换“疠”和手牌?");
next.set("list", [
[get.translation(player) + "(你)的疠", cards],
["手牌区", player.getCards("h", card => get.color(card, player) == "black")],
]);
next.set("filterMove", function (from, to) {
return typeof to != "number";
});
next.set("processAI", function (list) {
var player = _status.event.player;
var getv = function (card) {
if (get.info(card).toself) return 0;
return player.getUseValue(card, false);
};
var cards = list[0][1].concat(list[1][1]).sort(function (a, b) {
return getv(b) - getv(a);
}),
cards2 = cards.splice(0, player.getExpansions("xunli").length);
return [cards2, cards];
});
"step 1";
if (result.bool) {
var pushs = result.moved[0],
gains = result.moved[1];
pushs.removeArray(player.getExpansions("xunli"));
gains.removeArray(player.getCards("h"));
if (!pushs.length || pushs.length != gains.length) return;
player.logSkill("xunli_exchange");
player.addToExpansion(pushs, player, "giveAuto").gaintag.add("xunli");
game.log(player, "将", pushs, "作为“疠”置于武将牌上");
player.gain(gains, "gain2");
}
},
},
},
},
zhishi: {
audio: 2,
trigger: { player: "phaseJieshuBegin" },
direct: true,
content: function () {
"step 0";
player.chooseTarget(get.prompt2("zhishi")).set("ai", function (target) {
var player = _status.event.player;
var att = get.attitude(player, target);
if (att <= 4) return 0;
if (target.hasSkillTag("nogain")) att /= 10;
return att;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("zhishi", target);
player.storage.zhishi_mark = target;
player.addTempSkill("zhishi_mark", { player: "phaseBegin" });
}
},
ai: {
combo: "xunli",
expose: 0.3,
},
subSkill: {
mark: {
trigger: {
global: ["dying", "useCardToTargeted"],
},
direct: true,
charlotte: true,
filter: function (event, player) {
if (!player.getExpansions("xunli").length) return false;
var target = player.storage.zhishi_mark;
if (event.name == "dying") return event.player == target;
return event.card.name == "sha" && event.target == target;
},
content: function () {
"step 0";
var target = player.storage.zhishi_mark;
event.target = target;
player.chooseButton([get.prompt("zhishi", target), '弃置任意张“疠”并令其摸等量的牌
', player.getExpansions("xunli")], [1, Infinity]).set("ai", function (button) {
var player = _status.event.player,
target = player.storage.zhishi_mark;
if (target.hp < 1 && target != get.zhu(player)) return 0;
if (target.hasSkillTag("nogain")) return 0;
return 3 - player.getUseValue(card, false);
});
"step 1";
if (result.bool) {
player.logSkill("zhishi", target);
player.loseToDiscardpile(result.links);
target.draw(result.links.length);
}
},
mark: "character",
intro: {
content: "决定帮助$,具体帮不帮另说",
},
},
},
},
lieyi: {
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return player.getExpansions("xunli").length > 0;
},
filterTarget: lib.filter.notMe,
content: function () {
"step 0";
var cards = player.getExpansions("xunli");
var cards2 = cards.filter(function (card) {
return target.isIn() && player.canUse(card, target, false);
});
if (cards2.length) {
player.chooseButton(["对" + get.translation(target) + "使用一张牌", cards2], true).set("ai", function (button) {
return get.order(button.link);
});
} else {
event.finish();
if (cards.length) player.loseToDiscardpile(cards);
if (
target.isIn() &&
!target.hasHistory("damage", function (evt) {
return evt.getParent("lieyi") == event && evt._dyinged;
})
)
player.loseHp();
}
"step 1";
player.useCard(result.links[0], target, false);
event.goto(0);
},
ai: {
order: 2,
result: {
target: function (player, target) {
var cards = player.getExpansions("xunli");
var effect = 0,
damage = 0;
for (var i of cards) {
if (player.canUse(i, target, false)) {
effect += get.effect(target, i, player, target);
damage += get.tag(i, "damage");
}
}
if (damage >= target.hp) return effect;
if (player.hp > 2 && cards.length > 3) return effect / 3;
return 0;
},
},
combo: "xunli",
},
},
//马日磾
bingjie: {
trigger: { player: "phaseUseBegin" },
check: function (event, player) {
return (
player.maxHp > 3 &&
player.isDamaged() &&
player.hasCard(function (card) {
return (
game.hasPlayer(function (current) {
return current != player && get.attitude(player, current) < 0 && player.canUse(card, current, null, true) && get.effect(current, card, player, player) > 0;
}) && player.hasValueTarget(card)
);
}, "hs")
);
},
content: function () {
"step 0";
player.loseMaxHp();
"step 1";
player.addTempSkill("bingjie_effect");
game.delayx();
},
subSkill: {
effect: {
audio: "bingjie",
trigger: { player: "useCardToPlayered" },
forced: true,
charlotte: true,
logTarget: "target",
filter: function (event, player) {
return event.target != player && (event.card.name == "sha" || get.type(event.card, false) == "trick") && event.target.countCards("he") > 0;
},
content: function () {
"step 0";
trigger.target.chooseToDiscard("he", true);
"step 1";
if (result.bool && result.cards.length && get.color(result.cards[0], trigger.target) == get.color(trigger.card)) {
game.log(trigger.target, "不能响应", trigger.card);
trigger.directHit.push(trigger.target);
}
},
ai: {
effect: {
player_use(card, player, target) {
if (player !== target && get.itemtype(target) === "player" && (card.name === "sha" || get.type(card, false) === "trick") && target.countCards("he") && !target.hasSkillTag("noh")) return [1, 0, 1, -1];
},
},
},
},
},
},
zhengding: {
audio: 2,
trigger: { player: ["useCard", "respond"] },
forced: true,
filter: function (event, player) {
if (player == _status.currentPhase) return false;
if (!Array.isArray(event.respondTo)) return false;
if (player == event.respondTo[0]) return false;
var color = get.color(event.card);
if (color == "none") return false;
return color == get.color(event.respondTo[1]);
},
content: function () {
player.gainMaxHp();
player.recover();
},
},
//孙茹
xiecui: {
audio: 2,
trigger: { global: "damageBegin1" },
filter: function (event, player) {
var source = event.source;
if (!source || source != _status.currentPhase || event.getParent().type != "card") return false;
return !source.hasHistory("sourceDamage", function (evt) {
return evt.getParent().type == "card";
});
},
logTarget: "source",
prompt2: function (event, player) {
var str = "令" + get.translation(event.player) + "即将受到的";
str += "" + event.num + "点";
if (event.hasNature("linked")) {
str += get.translation(event.nature) + "属性";
}
str += "伤害+1";
if (event.source.group == "wu") {
var cards = event.cards.filterInD();
if (cards.length) {
str += ";然后" + get.translation(event.source) + "获得" + get.translation(cards) + ",且本回合的手牌上限+1";
}
}
return str;
},
check: function (event, player) {
var att = get.attitude(player, event.player);
if (att < 0) {
if (event.source.group != "wu" || !event.cards.filterInD().length) return true;
return get.attitude(player, event.source) > 0;
}
return false;
},
content: function () {
trigger.num++;
var source = trigger.source;
if (source.group == "wu") {
var cards = trigger.cards.filterInD();
if (cards.length > 0) {
source.gain(cards, "gain2");
source.addMark("xiecui_effect", 1, false);
source.addTempSkill("xiecui_effect");
}
}
},
subSkill: {
effect: {
charlotte: true,
mod: {
maxHandcard: (player, num) => num + player.countMark("xiecui_effect"),
},
marktext: "翠",
onremove: true,
intro: { content: "手牌上限+#" },
},
},
ai: { threaten: 1.75 },
},
youxu: {
audio: 2,
trigger: { global: "phaseEnd" },
logTarget: "player",
filter: function (event, player) {
return event.player.countCards("h") > event.player.hp;
},
check: function (event, player) {
if (get.attitude(player, event.player) <= 0) return true;
else
return game.hasPlayer(function (current) {
return current != event.player && current.isDamaged() && current.isMinHp() && get.attitude(player, current) > 0 && get.recoverEffect(current, player, player) > 0;
});
},
content: function () {
"step 0";
if (player == trigger.player) {
player.chooseCard("h", true, "请展示一张手牌");
} else {
player.choosePlayerCard(trigger.player, true, "h");
}
"step 1";
if (result.bool) {
var card = result.cards[0];
event.card = card;
var str = get.translation(player);
if (player != trigger.player) str += "对" + get.translation(trigger.player);
str += "发动了【忧恤】";
player.showCards(card, str);
player
.chooseTarget("令一名角色获得" + get.translation(card), "若其体力值为全场最少,则其回复1点体力", function (card, player, target) {
return target != _status.event.getTrigger().player;
})
.set("ai", function (target) {
var player = _status.event.player,
att = get.attitude(player, target);
if (att < 0) return 0;
if (target.isDamaged() && target.isMinHp && get.recoverEffect(target, player, player) > 0) return 4 * att;
return att;
});
} else event.finish();
"step 2";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.line(target, "green");
target.gain(card, trigger.player, "give").giver = player;
} else event.finish();
"step 3";
if (target.isMinHp()) target.recover();
},
},
//夏侯令女
fuping: {
audio: 2,
hiddenCard: function (player, name) {
var list = player.getStorage("fuping").slice(0);
list.removeArray(player.getStorage("fuping_round"));
return list.includes(name) && player.hasCard(card => get.type(card) != "basic", "ehs");
},
enable: "chooseToUse",
locked: false,
filter: function (event, player) {
var list = player.getStorage("fuping").slice(0);
list.removeArray(player.getStorage("fuping_round"));
if (!list.length) return false;
if (!player.hasCard(card => get.type(card) != "basic", "ehs")) return false;
for (var i of list) {
var type = get.type2(i, false);
if ((type == "basic" || type == "trick") && event.filterCard(get.autoViewAs({ name: i }, "unsure"), player, event)) return true;
}
return false;
},
chooseButton: {
dialog: function (event, player) {
var list = player.getStorage("fuping").slice(0);
list.removeArray(player.getStorage("fuping_round"));
var list2 = [];
for (var i of list) {
var type = get.type2(i, false);
if ((type == "basic" || type == "trick") && event.filterCard(get.autoViewAs({ name: i }, "unsure"), player, event)) list2.push([type, "", i]);
}
return ui.create.dialog("浮萍", [list2, "vcard"]);
},
check: function (button) {
if (_status.event.getParent().type != "phase") return 1;
return _status.event.player.getUseValue({ name: button.link[2] }, null, true);
},
backup: function (links, player) {
return {
audio: "fuping",
filterCard: card => get.type(card) != "basic",
position: "he",
popname: true,
viewAs: {
name: links[0][2],
},
check: function (card) {
return 8 - get.value(card);
},
precontent: function () {
player.addTempSkill("fuping_round");
player.markAuto("fuping_round", [event.result.card.name]);
},
};
},
prompt: function (links, player) {
return "将一张非基本牌当做【" + get.translation(links[0][2]) + "】使用";
},
},
ai: {
order: 8,
result: { player: 1 },
respondSha: true,
skillTagFilter: function (player) {
var list = player.getStorage("fuping").slice(0);
list.removeArray(player.getStorage("fuping_round"));
return list.includes("sha");
},
},
mod: {
targetInRange: function (card, player, target) {
if (!player.hasEnabledSlot()) return true;
},
},
marktext: "萍",
intro: { content: "已记录$" },
group: "fuping_mark",
subSkill: {
mark: {
trigger: { global: "useCardAfter" },
filter: function (event, player) {
return player != event.player && event.targets.includes(player) && player.hasEnabledSlot() && !player.getStorage("fuping").includes(event.card.name);
},
logTarget: "player",
prompt2: event => "废除一个装备栏并记录【" + get.translation(event.card.name) + "】",
check: function (event, player) {
var list = ["tao", "juedou", "guohe", "shunshou", "wuzhong", "xietianzi", "yuanjiao", "wanjian", "nanman", "huoshaolianying", "chuqibuyi", "zhujinqiyuan", "lebu", "bingliang"];
if (!list.includes(event.card.name)) return false;
if (["nanman", "wanjian"].includes(event.card.name) && !player.hasValueTarget({ name: event.card.name })) return false;
var list = [3, 5, 4, 1, 2];
for (var i of list) {
if (player.hasEnabledSlot(i)) {
var card = player.getEquip(i);
if (!card || player.hasEmptySlot(i)) return true;
if (get.value(card, player) <= 0) return true;
}
}
return false;
},
content: function () {
player.markAuto("fuping", [trigger.card.name]);
game.log(player, "记录了", "#y" + get.translation(trigger.card.name));
player.chooseToDisable().set("ai", function (event, player, list) {
var list = [3, 5, 4, 1, 2];
for (var i of list) {
if (player.hasEnabledSlot(i)) {
var card = player.getEquip(i);
if (!card || player.hasEmptySlot(i)) return "equip" + i;
if (get.value(card, player) <= 0) return "equip" + i;
}
}
return list.randomGet();
});
},
},
backup: { audio: "fuping" },
round: { charlotte: true, onremove: true },
},
},
weilie: {
audio: 2,
enable: "phaseUse",
filter: function (event, player) {
return player.countMark("weilie") <= player.getStorage("fuping").length && player.countCards("he") > 0 && game.hasPlayer(current => current.isDamaged());
},
filterCard: true,
position: "he",
filterTarget: (card, player, target) => target.isDamaged(),
check: function (card) {
return 8 - get.value(card);
},
content: function () {
"step 0";
player.addMark("weilie", 1, false);
target.recover();
"step 1";
if (target.isDamaged()) target.draw();
},
onremove: true,
ai: {
order: 1,
result: {
player: function (player, target) {
var eff = get.recoverEffect(target, player, player);
if (target.getDamagedHp() > 1) eff += get.effect(target, { name: "draw" }, player, player);
return eff;
},
},
},
},
//张瑶
//Partly powered by 烟雨墨染
yuanyu: {
audio: 2,
enable: "phaseUse",
usable: 1,
content: function () {
"step 0";
player.draw();
"step 1";
if (player.countCards("h") > 0 && game.hasPlayer(current => current != player)) {
var suits = lib.suit.slice(0),
cards = player.getExpansions("yuanyu");
for (var i of cards) suits.remove(get.suit(i, false));
var str = "选择一张手牌,作为“怨”置于武将牌上;同时选择一名其他角色,令该角色获得〖怨语〗的后续效果。";
if (suits.length) {
str += "目前“怨”中未包含的花色:";
for (var i of suits) str += get.translation(i);
}
player.chooseCardTarget({
filterCard: true,
filterTarget: lib.filter.notMe,
position: "h",
prompt: "怨语:选择置于武将牌上的牌和目标",
prompt2: str,
suits: suits,
forced: true,
ai1: function (card) {
var val = get.value(card),
evt = _status.event;
if (evt.suits.includes(get.suit(card, false))) return 8 - get.value(card);
return 5 - get.value(card);
},
ai2: function (target) {
var player = _status.event.player;
if (player.storage.yuanyu_damage && player.storage.yuanyu_damage.includes(target)) return 0;
return -get.attitude(player, target);
},
});
} else event.finish();
"step 2";
var target = result.targets[0];
player.addSkill("yuanyu_damage");
player.markAuto("yuanyu_damage", result.targets);
player.line(target, "green");
if (!target.storage.yuanyu_mark) {
target.storage.yuanyu_mark = player;
target.markSkillCharacter("yuanyu_mark", player, "怨语", "已获得〖怨语〗效果");
target.addSkill("yuanyu_mark");
}
player.addToExpansion(result.cards, player, "give").gaintag.add("yuanyu");
},
intro: {
content: "expansion",
markcount: "expansion",
},
onremove: function (player, skill) {
var cards = player.getExpansions(skill);
if (cards.length) player.loseToDiscardpile(cards);
player.removeSkill("yuanyu_damage");
},
ai: {
order: 7,
result: {
player: 1,
},
},
subSkill: {
mark: {
mark: "character",
charlotte: true,
intro: {
content: "已获得〖怨语〗效果",
onunmark: true,
},
},
damage: {
trigger: { global: ["damageSource", "phaseDiscardBegin"] },
forced: true,
charlotte: true,
onremove: function (player, skill) {
if (player.storage[skill]) {
for (var i of player.storage[skill]) {
if (i.storage.yuanyu_mark == player) i.unmarkSkill("yuanyu_mark");
}
}
delete player.storage[skill];
},
filter: function (event, player) {
if (event.name == "damage") {
var source = event.source;
return source && player.getStorage("yuanyu_damage").includes(source) && source.countCards("h") > 0;
} else {
if (player == event.player) {
return player.getStorage("yuanyu_damage").some(function (target) {
return target.isIn() && target.countCards("h") > 0;
});
} else if (player.getStorage("yuanyu_damage").includes(event.player)) {
return event.player.countCards("h") > 0;
}
return false;
}
},
content: function () {
"step 0";
if (trigger.name == "phaseDiscard") {
if (trigger.player == player) {
event.targets = player
.getStorage("yuanyu_damage")
.filter(function (target) {
return target.isIn() && target.countCards("h") > 0;
})
.sortBySeat();
} else event.targets = [trigger.player];
} else event.targets = [trigger.source];
"step 1";
event.target = event.targets.shift();
event.count = trigger.name == "damage" ? trigger.num : 1;
"step 2";
event.count--;
var suits = lib.suit.slice(0),
cards = player.getExpansions("yuanyu");
for (var i of cards) suits.remove(get.suit(i, false));
var next = target.chooseCard("h", true, "将一张手牌置于" + get.translation(player) + "的武将牌上");
next.set("suits", suits);
next.set("ai", function (card) {
var val = get.value(card),
evt = _status.event;
if (evt.suits.includes(get.suit(card, false))) return 5 - get.value(card);
return 8 - get.value(card);
});
if (suits.length) {
var str = "目前未包含的花色:";
for (var i of suits) str += get.translation(i);
next.set("prompt2", str);
}
"step 3";
player.addToExpansion(result.cards, target, "give").gaintag.add("yuanyu");
"step 4";
if (!player.hasSkill("yuanyu_damage")) event.finish();
else if (event.count > 0 && target.countCards("h") > 0) event.goto(2);
else if (event.targets.length > 0) event.goto(1);
},
},
},
},
xiyan: {
audio: 2,
trigger: { player: "addToExpansionAfter" },
filter: function (event, player) {
if (!event.gaintag.includes("yuanyu")) return false;
var cards = player.getExpansions("yuanyu");
if (cards.length < lib.suit.length) return false;
var suits = lib.suit.slice(0);
for (var i of cards) {
suits.remove(get.suit(i));
if (!suits.length) return true;
}
return false;
},
logTarget: () => _status.currentPhase,
prompt2: "获得所有“怨”",
check: () => true,
content: function () {
"step 0";
player.removeSkill("yuanyu_damage");
var cards = player.getExpansions("yuanyu");
player.gain(cards, "gain2");
"step 1";
var target = _status.currentPhase;
if (player == target) {
player.addMark("xiyan_buff", 4, false);
player.addTempSkill("xiyan_buff");
delete player.getStat("skill").yuanyu;
event.finish();
} else {
player
.chooseBool("夕颜:是否令" + get.translation(target) + "本回合的手牌上限-4且不能使用基本牌?")
.set("ai", function () {
return _status.event.bool;
})
.set("bool", get.attitude(player, target) < 0);
}
"step 2";
if (result.bool) {
var target = _status.currentPhase;
target.addMark("xiyan_debuff", 4, false);
target.addTempSkill("xiyan_debuff");
}
},
subSkill: {
buff: {
charlotte: true,
mark: true,
marktext: " + ",
intro: {
content: "本回合手牌上限+#且使用牌无次数限制",
},
mod: {
maxHandcard: function (player, num) {
return num + player.countMark("xiyan_buff");
},
cardUsable: function (card, player) {
return Infinity;
},
},
sub: true,
},
debuff: {
charlotte: true,
mark: true,
marktext: " - ",
intro: {
content: "本回合手牌上限-#且不能使用基本牌",
},
mod: {
maxHandcard: function (player, num) {
return num - player.countMark("xiyan_debuff");
},
cardEnabled: function (card) {
if (get.type(card) == "basic") return false;
},
cardSavable: function (card) {
if (get.type(card) == "basic") return false;
},
},
sub: true,
},
},
ai: {
combo: "yuanyu",
},
},
//滕胤
chenjian: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
prompt2: function (event, player) {
return "亮出牌堆顶的" + get.cnNumber(3 + player.countMark("chenjian")) + "张牌,然后执行以下一至两项:⒈弃置一张牌,然后令一名角色获得与你弃置牌花色相同的牌。⒉使用其中剩余的一张牌。若你执行了所有选项,则你获得一枚“陈见”并重铸所有手牌";
},
content: function () {
"step 0";
var cards = get.cards(3 + player.countMark("chenjian"));
event.cards = cards;
player.showCards(cards, get.translation(player) + "发动了【陈见】");
"step 1";
var list = [];
if (
player.countCards("he", i => {
return lib.filter.cardDiscardable(i, player, "chenjian");
})
)
list.push("选项一");
if (
event.cards.some(i => {
return player.hasUseTarget(i);
})
)
list.push("选项二");
if (list.length === 1) event._result = { control: list[0] };
else if (list.length > 1)
player
.chooseControl(list)
.set("choiceList", ["弃置一张牌,然后令一名角色获得与你弃置牌花色相同的牌", "使用" + get.translation(event.cards) + "中的一张牌"])
.set("prompt", "陈见:请选择一项")
.set("ai", () => {
let player = _status.event.player,
cards = _status.event.getParent().cards;
if (
cards.some(i => {
return player.getUseValue(i) > 0;
})
)
return "选项二";
return "选项一";
});
else event.finish();
"step 2";
event.goon = 0;
event.choosed = result.control;
if (result.control === "cancel2") event.finish();
else if (result.control === "选项二") event.goto(6);
"step 3";
if (
player.countCards("he", i => {
return lib.filter.cardDiscardable(i, player, "chenjian");
})
)
player
.chooseToDiscard("he", !event.goon)
.set("ai", function (card) {
let evt = _status.event.getParent(),
val = event.goon && evt.player.countMark("chenjian") < 2 ? 0 : -get.value(card),
suit = get.suit(card);
for (let i of evt.cards) {
if (get.suit(i, false) == suit) val += get.value(i, "raw");
}
return val;
})
.set("prompt", "陈见:" + (event.goon ? "是否" : "请") + "弃置一张牌,然后令一名角色获得" + get.translation(event.cards) + "中花色与之相同的牌" + (event.goon ? "?" : ""));
else if (event.choosed === "选项一") event.goto(6);
else event.finish();
"step 4";
if (result.bool) {
event.goon++;
var suit = get.suit(result.cards[0], player);
var cards2 = event.cards.filter(function (i) {
return get.suit(i, false) == suit;
});
if (cards2.length) {
event.cards2 = cards2;
player.chooseTarget(true, "选择一名角色获得" + get.translation(cards2)).set("ai", function (target) {
var att = get.attitude(_status.event.player, target);
if (att > 0) {
return att + Math.max(0, 5 - target.countCards("h"));
}
return att;
});
} else if (event.choosed === "选项一") event.goto(6);
else event.goto(8);
} else event.finish();
"step 5";
if (result.bool) {
var target = result.targets[0];
player.line(target, "green");
target.gain(event.cards2, "gain2");
event.cards.removeArray(event.cards2);
}
if (event.choosed === "选项二") event.goto(8);
"step 6";
var cards2 = cards.filter(function (i) {
return player.hasUseTarget(i);
});
if (cards2.length)
player.chooseButton(["陈见:" + (event.goon ? "是否" : "请") + "使用其中一张牌" + (event.goon ? "?" : ""), cards2], !event.goon).set("ai", function (button) {
return player.getUseValue(button.link);
});
else if (event.choosed === "选项二") event.goto(3);
else event.finish();
"step 7";
if (result.bool) {
player.chooseUseTarget(true, result.links[0], false);
event.cards.removeArray(result.links);
event.goon += 2;
if (event.choosed === "选项二") event.goto(3);
} else event.finish();
"step 8";
if (event.goon > 2) {
if (player.countMark("chenjian") < 2) player.addMark("chenjian", 1, false);
player.recast(player.getCards("h", lib.filter.cardRecastable));
}
},
marktext: "见",
intro: { content: "展示牌数量+#" },
},
xixiu: {
mod: {
canBeDiscarded: function (card, player, target) {
if (player != target && get.position(card) == "e" && target.countCards("e") == 1) return false;
},
},
audio: 2,
trigger: { target: "useCardToTargeted" },
forced: true,
filter: function (event, player) {
if (player == event.player || !player.countCards("e")) return false;
var suit = get.suit(event.card, false);
if (suit == "none") return false;
return player.hasCard(function (card) {
return get.suit(card, player) == suit;
}, "e");
},
content: function () {
player.draw();
},
ai: {
effect: {
target_use(card, player, target) {
if (typeof card == "object" && player != target) {
var suit = get.suit(card);
if (suit == "none") return;
if (
player.hasCard(function (card) {
return get.suit(card, player) == suit;
}, "e")
)
return [1, 0.08];
}
},
},
},
},
//张嫙
tongli: {
audio: 2,
trigger: { player: "useCardToPlayered" },
filter: function (event, player) {
if (!event.isFirstTarget || (event.card.storage && event.card.storage.tongli)) return false;
var type = get.type(event.card);
if (type != "basic" && type != "trick") return false;
var hs = player.getCards("h");
if (!hs.length) return false;
var evt = event.getParent("phaseUse");
if (!evt || evt.player != player) return false;
var num1 = player.getHistory("useCard", function (evtx) {
if (evtx.getParent("phaseUse") != evt) return false;
return !evtx.card.storage || !evtx.card.storage.tongli;
}).length;
if (hs.length < num1) return false;
var list = [];
for (var i of hs) list.add(get.suit(i, player));
return list.length == num1;
},
prompt2: function (event, player) {
var evt = event.getParent("phaseUse");
var num = player.getHistory("useCard", function (evtx) {
if (evtx.getParent("phaseUse") != evt) return false;
return !evtx.card.storage || !evtx.card.storage.tongli;
}).length;
//var str='视为额外使用'+get.cnNumber(num)+'张'
var str = "额外结算" + get.cnNumber(num) + "次";
if (event.card.name == "sha" && game.hasNature(event.card)) str += get.translation(event.card.nature);
return str + "【" + get.translation(event.card.name) + "】";
},
check: function (event, player) {
return !get.tag(event.card, "norepeat");
},
content: function () {
//player.addTempSkill('tongli_effect');
var evt = trigger.getParent("phaseUse");
var num = player.getHistory("useCard", function (evtx) {
if (evtx.getParent("phaseUse") != evt) return false;
return true;
//return !evtx.card.storage||!evtx.card.storage.tongli;
}).length;
trigger.getParent().effectCount += num;
},
/*subSkill:{
effect:{
trigger:{player:'useCardAfter'},
forced:true,
charlotte:true,
filter:function(event,player){
return event.tongli_effect!=undefined;
},
content:function(){
'step 0'
event.card=trigger.tongli_effect[0];
event.count=trigger.tongli_effect[1];
'step 1'
event.count--;
for(var i of trigger.targets){
if(!i.isIn()||!player.canUse(card,i,false)) return;
}
if(trigger.addedTarget&&!trigger.addedTarget.isIn()) return;
if(trigger.addedTargets&&trigger.addedTargets.length){
for(var i of trigger.addedTargets){
if(!i.isIn()) return;
}
}
var next=player.useCard(get.copy(card),trigger.targets,false);
if(trigger.addedTarget) next.addedTarget=trigger.addedTarget;
if(trigger.addedTargets&&trigger.addedTargets.length) next.addedTargets=trigger.addedTargets.slice(0);
if(event.count>0) event.redo();
},
},
},*/
},
shezang: {
audio: 2,
round: 1,
trigger: { global: "dying" },
frequent: true,
filter: function (event, player) {
return event.player == player || player == _status.currentPhase;
},
content: function () {
var cards = [];
for (var i of lib.suit) {
var card = get.cardPile2(function (card) {
return get.suit(card, false) == i;
});
if (card) cards.push(card);
}
if (cards.length) player.gain(cards, "gain2");
},
},
//王桃王悦
huguan: {
audio: 2,
audioname: ["wangyue"],
init: function (player) {
game.addGlobalSkill("huguan_all");
},
trigger: { global: "useCard" },
direct: true,
filter: function (event, player) {
if (get.color(event.card, false) != "red") return false;
var evt = event.getParent("phaseUse");
if (!evt || evt.player != event.player) return false;
return (
event.player
.getHistory("useCard", function (event) {
return event.getParent("phaseUse") == evt;
})
.indexOf(event) == 0
);
},
content: function () {
"step 0";
player
.chooseControl(lib.suit, "cancel2")
.set("prompt", get.prompt("huguan", trigger.player))
.set("prompt2", "令某种花色的手牌不计入其本回合的手牌上限")
.set("ai", function () {
var player = _status.event.player,
target = _status.event.getTrigger().player,
att = get.attitude(player, target);
if (att <= 0) {
if (
!player.hasSkill("yaopei") ||
player.hasHistory("useSkill", function (evt) {
return evt.skill == "huguan" && evt.targets.includes(target);
}) ||
target.needsToDiscard() - target.needsToDiscard(-target.countCards("h") / 4) > (att > -2 ? 1.6 : 1)
)
return "cancel2";
}
let list = lib.suit.slice(0);
if (att <= 0 && target.getStorage("huguan_add"))
for (let i of target.getStorage("huguan_add")) {
if (list.includes(i)) return i;
}
list.removeArray(target.getStorage("huguan_add"));
if (list.length) return list.randomGet();
return "cancel2";
});
"step 1";
if (result.control != "cancel2") {
var target = trigger.player;
player.logSkill("huguan", target);
game.log(player, "选择了", "#g" + get.translation(result.control), "花色");
target.addTempSkill("huguan_add");
target.markAuto("huguan_add", [result.control]);
}
},
subSkill: {
add: {
charlotte: true,
onremove: true,
mod: {
ignoredHandcard: function (card, player) {
if (player.getStorage("huguan_add").includes(get.suit(card, player))) return true;
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && player.getStorage("huguan_add").includes(get.suit(card, player))) return false;
},
},
intro: { content: "本回合$花色的牌不计入手牌上限" },
},
all: {
mod: {
aiValue: function (player, card, num) {
if (player && player.storage.huguan_all > 0 && get.itemtype(card) == "card" && get.color(card, player) == "red") return num + player.storage.huguan_all;
},
},
trigger: {
player: ["phaseUseBegin", "useCard"],
},
filter: function (event, player) {
if (event.name === "useCard") return player.storage.huguan_all;
return true;
},
silent: true,
charlotte: true,
content: function () {
"step 0";
if (trigger.name === "useCard") {
player.storage.huguan_all = 0;
event.finish();
}
"step 1";
let num = -157;
game.countPlayer(function (current) {
if (current.hasSkill("huguan")) num = Math.max(num, get.attitude(_status.event.player, current));
}, true);
if (num === -157) game.removeGlobalSkill("huguan_all");
else if (num === 0) player.storage.huguan_all = 6;
else if (num > 0) player.storage.huguan_all = 9;
},
},
},
},
yaopei: {
audio: 2,
trigger: { global: "phaseDiscardEnd" },
direct: true,
filter: function (event, player) {
if (player == event.player || !event.player.isIn()) return false;
if (
!player.hasAllHistory("useSkill", function (evt) {
return evt.skill == "huguan" && evt.targets.includes(event.player);
})
)
return false;
var suits = [];
event.player.getHistory("lose", function (evt) {
if (evt.type == "discard" && evt.getParent("phaseDiscard") == event) {
for (var i of evt.cards2) suits.add(get.suit(i, evt.hs.includes(i) ? evt.player : false));
}
});
if (suits.length >= lib.suit.length) return false;
if (_status.connectMode && player.countCards("h") > 0) return true;
return player.hasCard(function (card) {
return !suits.includes(get.suit(card));
}, "he");
},
content: function () {
"step 0";
var suits = [];
trigger.player.getHistory("lose", function (evt) {
if (evt.type == "discard" && evt.getParent("phaseDiscard") == trigger) {
for (var i of evt.cards2) suits.add(get.suit(i, evt.hs.includes(i) ? evt.player : false));
}
});
player.chooseCardTarget({
prompt: get.prompt("yaopei", trigger.player),
prompt2: "操作提示:选择要弃置的牌,并选择执行摸牌选项的角色,另一名角色执行回复体力的选项。",
suits: suits,
position: "he",
filterCard: function (card, player) {
return !_status.event.suits.includes(get.suit(card)) && lib.filter.cardDiscardable(card, player, "yaopei");
},
filterTarget: function (card, player, target) {
return target == player || target == _status.event.getTrigger().player;
},
ai1: function (card) {
let player = _status.event.player,
source = _status.event.getTrigger().player;
if (get.attitude(player, source) > 0 && (get.recoverEffect(player, player, player) > 0 || get.recoverEffect(source, player, player) > 0)) return 12 - get.value(card);
return 8 - get.value(card);
},
ai2: function (target) {
let player = _status.event.player,
source = _status.event.getTrigger().player;
let recoverer = player === target ? source : player;
if (recoverer.isHealthy()) return get.attitude(player, target);
let att = get.attitude(player, recoverer),
rec = get.recoverEffect(recoverer, player, player);
if (rec > 0) return Math.abs(att) + get.attitude(player, target);
return 0;
},
});
"step 1";
if (result.bool) {
var target = trigger.player;
player.logSkill("yaopei", target);
player.discard(result.cards);
if (player == result.targets[0]) {
if (target.isDamaged() && target.hp < player.hp && (get.mode() != "identity" || player.identity != "nei")) player.addExpose(0.15);
target.recover();
player.draw(2);
} else {
if ((player.isHealthy() || player.hp > target.hp) && (get.mode() != "identity" || player.identity != "nei")) player.addExpose(0.15);
target.draw(2);
player.recover();
}
}
},
ai: {
combo: "huguan",
},
},
mingluan: {
audio: 2,
trigger: { global: "phaseJieshuBegin" },
direct: true,
filter: function (event, player) {
return player != event.player && event.player.isIn() && player.hasSkill("mingluan_mark") && player.countCards("he") > 0;
},
content: function () {
"step 0";
let he = player.getCards("he"),
disval = 0,
dis = 0,
spare = 30,
use = true;
for (let i of he) {
let val = get.value(i, player);
if (val < 6 && get.position(i) == "h") {
dis++;
disval += val;
} else if (val < spare) spare = val;
}
if (!dis) {
dis = 1;
disval = spare;
spare = -1;
}
let draw = Math.min(trigger.player.countCards("h"), 5 + dis - player.countCards("h"));
if (6 * draw < disval) use = false;
player
.chooseToDiscard("he", get.prompt("mingluan"), "弃置任意张牌,并摸等同于" + get.translation(trigger.player) + "手牌数的牌(至多摸至五张)", [1, Infinity])
.set("ai", function (card) {
let val = get.value(card, player);
if (val < 0 && card.name !== "du") return 30;
if (!_status.event.use) return 0;
if (ui.selected.cards.length) {
if (get.position(card) !== "h") return 0;
return 6 - val;
}
if (_status.event.spare < 0 || get.position(card) === "h") return 30 - val;
return 0;
})
.set("spare", spare)
.set("use", use).logSkill = ["mingluan", trigger.player];
"step 1";
if (result.bool) {
var num = trigger.player.countCards("h"),
num2 = 5 - player.countCards("h");
if (num > 0 && num2 > 0) player.draw(Math.min(num, num2));
}
},
group: "mingluan_count",
subSkill: {
count: {
charlotte: true,
trigger: { global: "recoverEnd" },
silent: true,
popup: false,
firstDo: true,
filter: function (event, player) {
var current = _status.currentPhase;
return current && current != player && !player.hasSkill("mingluan_mark");
},
content: function () {
player.addTempSkill("mingluan_mark");
},
},
mark: {
charlotte: true,
},
},
},
//赵嫣
jinhui: {
audio: 2,
enable: "phaseUse",
usable: 1,
content: function () {
"step 0";
var cards = [];
while (cards.length < 3) {
var card = get.cardPile2(function (card) {
for (var i of cards) {
if (i.name == card.name) return false;
}
var info = get.info(card, false);
if (info.ai && info.ai.tag && info.ai.tag.damage) return false;
return !info.notarget && (info.toself || info.singleCard || !info.selectTarget || info.selectTarget == 1);
});
if (card) cards.push(card);
else break;
}
if (!cards.length) event.finish();
else {
player.showCards(cards, get.translation(player) + "发动了【锦绘】");
event.cards = cards;
game.cardsGotoOrdering(cards);
if (game.hasPlayer(current => current != player))
player.chooseTarget("选择【锦绘】的目标", true, lib.filter.notMe).set("ai", function (target) {
var player = _status.event.player,
cards = _status.event.getParent().cards.slice(0);
var max_effect = 0,
max_effect_player = 0;
for (var i of cards) {
var targetx = lib.skill.jinhui.getUsableTarget(i, target, player);
if (targetx) {
var effect2 = get.effect(targetx, i, target, target);
var effect3 = get.effect(targetx, i, target, player);
if (effect2 > max_effect) {
max_effect = effect2;
max_effect_player = effect3;
}
}
}
return max_effect_player;
});
else event.finish();
}
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.line(target, "green");
var cards = cards.filter(function (card) {
return lib.skill.jinhui.getUsableTarget(card, target, player);
});
if (cards.length) {
if (cards.length == 1) event._result = { bool: true, links: cards };
else
target.chooseButton(["选择按“锦绘”规则使用一张牌", cards], true).set("ai", function (button) {
var player = _status.event.player,
target = _status.event.getParent().player,
card = button.link;
var targetx = lib.skill.jinhui.getUsableTarget(card, player, target);
var effect = get.effect(targetx, card, player, player),
cards = _status.event.getParent().cards.slice(0);
var effect2 = 0,
effect3 = 0;
cards.remove(button.link);
for (var i of cards) {
var targetx = lib.skill.jinhui.getUsableTarget(i, target, player);
if (targetx) {
effect2 += get.effect(targetx, i, target, target);
effect3 += get.effect(targetx, i, target, player);
}
}
if (effect2 > 0) effect += effect3;
return effect;
});
} else event.goto(3);
} else event.finish();
"step 2";
if (result.bool) {
var card = result.links[0];
event.cards.remove(card);
var targetx = lib.skill.jinhui.getUsableTarget(card, target, player);
target.useCard(card, targetx, false, "noai");
}
"step 3";
var cards = cards.filter(function (card) {
return lib.skill.jinhui.getUsableTarget(card, player, target);
});
if (cards.length) {
player.chooseButton(["是否按“锦绘”规则使用其中一张牌?", cards]).set("ai", function (button) {
var player = _status.event.player,
target = _status.event.getParent().target;
var card = button.link,
targetx = lib.skill.jinhui.getUsableTarget(card, player, target);
return get.effect(targetx, card, player, player);
});
} else event.finish();
"step 4";
if (result.bool) {
var card = result.links[0];
cards.remove(card);
var targetx = lib.skill.jinhui.getUsableTarget(card, player, target);
if (targetx) {
player.useCard(card, targetx, false, "noai");
}
if (cards.length) event.goto(3);
} else event.finish();
},
getUsableTarget: function (card, player, target) {
var info = get.info(card, false);
if (info.toself) return player.canUse(card, player, false) ? player : false;
return target.isIn() && player.canUse(card, target, false) ? target : false;
},
ai: {
order: 5,
result: { player: 1 },
},
},
qingman: {
audio: 2,
trigger: { global: "phaseEnd" },
forced: true,
logTarget: "player",
filter: function (event, player) {
if (!event.player.isIn()) return false;
var num = player.countCards("h");
if (num >= 5) return false;
var num2 = 0;
for (var i = 1; i <= 5; i++) {
num2 += event.player.countEmptySlot(i);
}
return num < num2;
},
content: function () {
var num2 = 0;
for (var i = 1; i <= 5; i++) {
num2 += trigger.player.countEmptySlot(i);
}
player.drawTo(num2);
},
},
//何晏
yachai: {
audio: 2,
trigger: { player: "damageEnd" },
filter: function (event, player) {
return event.source && event.source.isIn();
},
logTarget: "source",
check: function (event, player) {
return get.attitude(player, event.source) < 0;
},
content: function () {
"step 0";
var target = trigger.source,
str = get.translation(player);
event.target = target;
var th = target.countCards("h");
if (th > 0) {
event.num = Math.ceil(th / 2);
var list = ["本回合不能使用手牌,然后" + str + "摸两张牌", "展示所有手牌,并将其中一种花色的所有牌交给" + str, "弃置" + get.cnNumber(event.num) + "张手牌"];
target
.chooseControl()
.set("choiceList", list)
.set("ai", function () {
return get.rand(0, 2);
});
} else event._result = { index: 0 };
"step 1";
switch (result.index) {
case 0:
target.addTempSkill("yachai_block");
player.draw(2);
event.finish();
break;
case 1:
target.showHandcards();
break;
case 2:
event.goto(4);
break;
}
"step 2";
var map = {},
hs = target.getCards("h");
for (var i of hs) {
map[get.suit(i, target)] = true;
}
var list = [];
for (var i of lib.suit) {
if (map[i]) list.push(i);
}
if (!list.length) event.finish();
else if (list.length == 1) event._result = { control: list[0] };
else target.chooseControl(list).set("prompt", "将一种花色的牌交给" + get.translation(player));
"step 3";
var cards = target.getCards("h", function (card) {
return get.suit(card, target) == result.control && lib.filter.cardDiscardable(card, target, "yachai");
});
if (cards.length) target.give(cards, player, "give");
event.finish();
"step 4";
target.chooseToDiscard("h", true, num);
},
subSkill: {
block: {
mark: true,
intro: { content: "不能使用手牌" },
charlotte: true,
mod: {
cardEnabled: function (card, player) {
let hs = player.getCards("h"),
cards = [card];
if (Array.isArray(card.cards)) cards.addArray(card.cards);
for (let i of cards) {
if (hs.includes(i)) return false;
}
},
cardSavable: function (card, player) {
let hs = player.getCards("h"),
cards = [card];
if (Array.isArray(card.cards)) cards.addArray(card.cards);
for (let i of cards) {
if (hs.includes(i)) return false;
}
},
},
},
},
},
qingtan: {
audio: 2,
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return game.hasPlayer(current => current.countCards("h") > 0);
},
filterTarget: function (card, player, target) {
return target.countCards("h") > 0;
},
selectTarget: -1,
multitarget: true,
multiline: true,
content: function () {
"step 0";
targets.sortBySeat();
var next = player
.chooseCardOL(targets, "请选择要展示的牌", true)
.set("ai", function (card) {
return -get.value(card);
})
.set("source", player);
next.aiCard = function (target) {
var hs = target.getCards("h");
return { bool: true, cards: [hs.randomGet()] };
};
next._args.remove("glow_result");
"step 1";
var cards = [];
event.videoId = lib.status.videoId++;
for (var i = 0; i < targets.length; i++) cards.push(result[i].cards[0]);
event.cards = cards;
game.log(player, "展示了", targets, "的", cards);
game.broadcastAll(
function (targets, cards, id, player) {
var dialog = ui.create.dialog(get.translation(player) + "发动了【清谈】", cards);
dialog.videoId = id;
var getName = function (target) {
if (target._tempTranslate) return target._tempTranslate;
var name = target.name;
if (lib.translate[name + "_ab"]) return lib.translate[name + "_ab"];
return get.translation(name);
};
for (var i = 0; i < targets.length; i++) {
dialog.buttons[i].querySelector(".info").innerHTML = getName(targets[i]) + get.translation(cards[i].suit);
}
},
targets,
cards,
event.videoId,
player
);
game.delay(4);
"step 2";
game.broadcastAll("closeDialog", event.videoId);
var list = [],
map = {};
for (var i of cards) {
var suit = get.suit(i);
if (!map[suit]) map[suit] = [];
map[suit].push(i);
}
var dialog = ["选择获得一种花色的所有牌"];
for (var suit of lib.suit) {
if (map[suit]) {
var targetsx = map[suit].map(function (card) {
return targets[cards.indexOf(card)];
});
dialog.push('' + get.translation(targetsx) + "
");
dialog.push(map[suit]);
list.push(suit);
}
}
if (list.length)
player
.chooseControl(list, "cancel2")
.set("dialog", dialog)
.set("list", list)
.set("map", map)
.set("ai", function () {
let max = 0,
res = "cancel2";
for (let s of _status.event.list) {
let temp = 0;
for (let i of _status.event.map[s]) {
temp += get.value(i, _status.event.player) + get.sgn(get.attitude(_status.event.player, get.owner(i))) * (6 - get.value(i, get.owner(i)));
}
for (let i in _status.event.map) {
if (i === s) continue;
for (let j of _status.event.map[i]) {
temp -= get.sgn(get.attitude(_status.event.player, get.owner(j))) * get.value(j, get.owner(j));
}
}
if (temp > max) {
res = s;
max = temp;
}
}
return res;
});
else event.finish();
"step 3";
if (result.control != "cancel2") {
event.cards2 = cards.filter(function (i) {
return get.suit(i) == result.control;
});
for (var i = 0; i < cards.length; i++) {
if (event.cards2.includes(cards[i])) {
targets[i].$give(cards[i], player, false);
}
}
player.gain(event.cards2, "log");
} else event.finish();
"step 4";
var draws = [];
for (var i = 0; i < cards.length; i++) {
if (!event.cards2.includes(cards[i])) {
targets[i].discard(cards[i]).delay = false;
} else draws.push(targets[i]);
}
if (draws.length) game.asyncDraw(draws);
"step 5";
game.delayx();
},
ai: {
order: 7,
result: {
player: 0.3,
target: -1,
},
},
},
//邓芝
jianliang: {
audio: 2,
trigger: { player: "phaseDrawBegin2" },
filter: function (event, player) {
return !player.isMaxHandcard();
},
direct: true,
content: function () {
"step 0";
player.chooseTarget(get.prompt("jianliang"), "令至多两名角色各摸一张牌", [1, 2]).set("ai", function (target) {
return Math.sqrt(5 - Math.min(4, target.countCards("h"))) * get.attitude(_status.event.player, target);
});
"step 1";
if (result.bool) {
var targets = result.targets.sortBySeat();
player.logSkill("jianliang", targets);
if (targets.length == 1) {
targets[0].draw();
event.finish();
} else game.asyncDraw(targets);
} else event.finish();
"step 2";
game.delayx();
},
},
weimeng: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
return player.hp > 0 && target != player && target.countGainableCards(player, "h") > 0;
},
content: function () {
"step 0";
player.gainPlayerCard(target, "h", true, [1, player.hp]);
"step 1";
if (result.bool && target.isIn()) {
var num = result.cards.length,
hs = player.getCards("he");
var numx = 0;
for (var i of result.cards) numx += get.number(i, player);
event.num = numx;
event.cards = result.cards;
if (!hs.length) event.finish();
else if (hs.length <= num) event._result = { bool: true, cards: hs };
else player.chooseCard("he", true, "选择交给" + get.translation(target) + get.cnNumber(num) + "张牌", "(已得到牌的点数和:" + numx + ")", num);
} else event.finish();
"step 2";
player.give(result.cards, target);
var numx = 0;
for (var i of result.cards) numx += get.number(i, player);
if (numx > num) player.draw();
else if (numx < num) player.discardPlayerCard(target, true, "hej");
},
ai: {
order: 6,
tag: {
lose: 1,
loseCard: 1,
gain: 1,
},
result: {
target: function (player, target) {
return -Math.pow(Math.min(player.hp, target.countCards("h")), 2) / 4;
},
},
},
},
//冯熙
yusui: {
audio: 2,
trigger: { target: "useCardToTargeted" },
filter: function (event, player) {
return event.player != player && event.player.isIn() && get.color(event.card) == "black";
},
logTarget: "player",
check: function (event, player) {
var target = event.player;
if (player.hp < 3 || get.attitude(player, target) > -3) return false;
if (player.hp < target.hp) return true;
if (Math.min(target.countCards("h") - player.countCards("h"), target.countCards("h")) > 3) return true;
return false;
},
preHidden: true,
content: function () {
"step 0";
player.loseHp();
event.target = trigger.player;
"step 1";
event.addIndex = 0;
var list = [],
num = target.countCards("h") - player.countCards("h");
event.num = num;
if (num > 0 && target.countCards("h") > 0) list.push("令其弃置" + get.cnNumber(num) + "张手牌");
else event.addIndex++;
if (target.hp > player.hp) list.push("令其失去" + get.cnNumber(target.hp - player.hp) + "点体力");
if (!list.length) event.finish();
else if (list.length == 1) event._result = { index: 0 };
else
player
.chooseControl()
.set("choiceList", list)
.set("prompt", "令" + get.translation(target) + "执行一项")
.set("ai", function () {
var player = _status.event.player,
target = _status.event.getParent().target;
return target.hp - player.hp > Math.min(_status.event.getParent().num, target.countCards("h")) / 2 ? 1 : 0;
});
"step 2";
if (result.index + event.addIndex == 0) target.chooseToDiscard(num, true, "h");
else target.loseHp(target.hp - player.hp);
},
},
boyan: {
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
return target != player;
},
content: function () {
"step 0";
target.drawTo(Math.min(5, target.maxHp));
"step 1";
target.addTempSkill("boyan_block");
},
subSkill: {
block: {
mark: true,
intro: { content: "不能使用或打出手牌" },
charlotte: true,
mod: {
cardEnabled2: function (card) {
if (get.position(card) == "h") return false;
},
},
},
},
ai: {
order: 4,
result: {
target: function (player, target) {
if (get.attitude(player, target) > 0) return Math.max(0, Math.min(5, target.maxHp) - target.countCards("h"));
if (
Math.max(0, Math.min(5, target.maxHp) - target.countCards("h")) <= 1 &&
target.countCards("h", "shan") &&
!target.hasSkillTag("respondShan", true, null, true) &&
player.countCards("h", function (card) {
return get.tag(card, "respondShan") && player.getUseValue(card, null, true) > 0 && get.effect(target, card, player, player) > 0;
})
)
return -2;
},
},
},
},
//祢衡
rekuangcai: {
audio: 2,
forced: true,
trigger: { player: "phaseDiscardBegin" },
filter: function (event, player) {
return !player.getHistory("useCard").length || !player.getHistory("sourceDamage").length;
},
content: function () {
lib.skill.rekuangcai.change(player, player.getHistory("useCard").length ? -1 : 1);
},
mod: {
targetInRange: function (card, player) {
if (player == _status.currentPhase) return true;
},
cardUsable: function (card, player) {
if (player == _status.currentPhase) return Infinity;
},
},
change: function (player, num) {
if (typeof player.storage.rekuangcai_change != "number") player.storage.rekuangcai_change = 0;
player.storage.rekuangcai_change += num;
player.addSkill("rekuangcai_change");
},
group: "rekuangcai_draw",
subSkill: {
draw: {
audio: "rekuangcai",
trigger: { player: "phaseJieshuBegin" },
forced: true,
filter: function (event, player) {
return player.getHistory("sourceDamage").length > 0;
},
content: function () {
player.draw(Math.min(5, player.getStat("damage")));
},
},
change: {
mod: {
maxHandcard: function (player, num) {
if (typeof player.storage.rekuangcai_change == "number") return num + player.storage.rekuangcai_change;
},
},
charlotte: true,
mark: true,
intro: {
content: num => "手牌上限" + (num < 0 ? "" : "+") + num,
},
},
},
},
reshejian: {
audio: 2,
trigger: { target: "useCardToTargeted" },
filter: function (event, player) {
if (player == event.player || event.targets.length != 1) return false;
return player.countCards("h") >= 2;
},
usable: 2,
async cost(event, trigger, player) {
event.result = await player
.chooseToDiscard("he", [2, Infinity], get.prompt("reshejian", trigger.player), '弃置至少两张手牌,然后选择一项:
⒈弃置其等量的牌。⒉对其造成1点伤害。
')
.set(
"ai",
function (card) {
if (_status.event.goon && ui.selected.cards.length < 2) return 5.6 - get.value(card);
return 0;
},
"chooseonly"
)
.set(
"goon",
(function () {
var target = trigger.player;
if (get.damageEffect(target, player, player) > 0) return true;
if (
target.countCards("he", function (card) {
return get.value(card, target) > 6;
}) >= 2
)
return true;
return false;
})()
)
.forResult();
},
logTarget: "player",
content: function () {
"step 0";
player.discard(cards);
"step 1";
var num = cards.length;
event.num = num;
var target = targets[0],
str = get.translation(target);
event.target = target;
if (!target.isIn()) event.finish();
else if (
!target.hasCard(function (card) {
return lib.filter.canBeDiscarded(card, player, target);
}, "he")
)
event._result = { index: 1 };
else
player
.chooseControl()
.set("choiceList", ["弃置" + str + "的" + get.cnNumber(num) + "张牌", "对" + str + "造成1点伤害"])
.set("ai", function () {
var player = _status.event.player;
var eff0 = get.effect(target, { name: "guohe_copy2" }, player, player) * Math.min(1.7, target.countCards("he"));
var eff1 = get.damageEffect(target, player, player);
return eff0 > eff1 ? 0 : 1;
});
"step 2";
if (result.index == 0) player.discardPlayerCard(target, num, true, "he");
else target.damage();
},
},
//陈登
refuyuan: {
audio: 2,
trigger: { global: "useCardToTargeted" },
logTarget: "target",
filter: function (event, player) {
return (
event.card.name == "sha" &&
event.target.isIn() &&
!game.hasPlayer2(function (current) {
return current.hasHistory("useCard", function (evt) {
return evt.card != event.card && get.color(evt.card, false) == "red" && evt.targets && evt.targets.includes(event.target);
});
})
);
},
check: function (event, player) {
return get.attitude(player, event.target) > 0;
},
content: function () {
trigger.target.draw();
},
},
reyingshui: {
audio: 2,
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return player.countCards("he") > 0 && game.hasPlayer(current => player.inRange(current));
},
position: "he",
filterCard: true,
filterTarget: function (card, player, target) {
return player.inRange(target);
},
discard: false,
lose: false,
delay: false,
check: function (card) {
if (get.type(card) == "equip") return 3 - get.value(card);
return 6.5 - get.value(card);
},
content: function () {
"step 0";
player.give(cards, target);
"step 1";
var next = target.chooseCard("he", [2, Infinity], "交给" + get.translation(player) + "至少两张装备牌,否则受到1点伤害", { type: "equip" });
if (get.damageEffect(target, player, target) >= 0) next.set("ai", () => -1);
else next.set("ai", card => (ui.selected.cards.length < 2 ? 6 - get.value(card) : 0));
"step 2";
if (result.bool) target.give(result.cards, player);
else target.damage("nocard");
},
ai: {
order: 5,
tag: {
damage: 0.5,
},
result: {
target: -1.5,
},
},
},
rewangzu: {
audio: 2,
trigger: { player: "damageBegin1" },
filter: function (event, player) {
return event.source && player != event.source && player.hasCard(card => lib.filter.cardDiscardable(card, player, "rewangzu"), "h");
},
usable: 1,
async cost(event, trigger, player) {
var num = player.getFriends().length;
if (
!game.hasPlayer(function (current) {
return current != player && current.getFriends().length > num;
})
) {
event.result = await player
.chooseToDiscard("h", get.prompt("rewangzu"), "弃置一张牌并令伤害-1", "chooseonly")
.set("ai", function (card) {
return 7 - get.value(card);
})
.forResult();
} else {
event.result = await player.chooseBool(get.prompt("rewangzu"), "随机弃置一张牌并令伤害-1").forResult();
}
},
async content(event, trigger, player) {
trigger.num--;
if (!event.cards || !event.cards.length) {
const cards = player.getCards("h", card => lib.filter.cardDiscardable(card, player, "rewangzu"));
if (cards.length) player.discard(cards.randomGet());
} else {
player.discard(event.cards);
}
},
},
//万年公主
zhenge: {
audio: 2,
trigger: { player: "phaseZhunbeiBegin" },
direct: true,
content: function () {
"step 0";
player.chooseTarget(get.prompt("zhenge"), "令一名角色的攻击范围+1").set("ai", function (target) {
var player = _status.event.player,
att = get.attitude(player, target);
if (att > 0) {
if (!target.hasMark("zhenge_effect")) att *= 1.5;
if (
!game.hasPlayer(function (current) {
return get.distance(target, current, "attack") > 2;
})
) {
var usf = Math.max.apply(
Math,
game.filterPlayer().map(function (current) {
if (target.canUse("sha", current, false)) return get.effect(current, { name: "sha" }, target, player);
return 0;
})
);
return att + usf;
}
return att;
}
return 0;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.logSkill("zhenge", target);
target.addSkill("zhenge_effect");
if (target.countMark("zhenge_effect") < 5) target.addMark("zhenge_effect", 1, false);
if (
!game.hasPlayer(function (current) {
return current != target && !target.inRange(current);
})
) {
player
.chooseTarget("是否令" + get.translation(target) + "视为对另一名角色使用【杀】?", function (card, player, target) {
return _status.event.source.canUse("sha", target);
})
.set("source", target)
.set("ai", function (target) {
var evt = _status.event;
return get.effect(target, { name: "sha" }, evt.source, evt.player);
});
} else {
game.delayx();
event.finish();
}
} else event.finish();
"step 2";
if (result.bool) {
target.useCard({ name: "sha", isCard: true }, result.targets[0], false);
}
"step 3";
game.delayx();
},
subSkill: {
effect: {
charlotte: true,
onremove: true,
mod: {
attackRange: function (player, num) {
return num + player.countMark("zhenge_effect");
},
},
intro: { content: "攻击范围+#" },
},
},
},
xinghan: {
audio: 2,
init: function (player) {
player.addSkill("xinghan_count");
},
onremove: function (player) {
player.removeSkill("xinghan_count");
},
trigger: { global: "damageSource" },
forced: true,
filter: function (event, player) {
return event.card && event.card == player.storage.xinghan_temp && event.source && event.source.hasMark("zhenge_effect");
},
logTarget: "source",
content: function () {
player.draw(player.isMaxHandcard(true) ? 1 : Math.min(5, trigger.source.getAttackRange()));
},
subSkill: {
count: {
trigger: { global: "useCard1" },
forced: true,
charlotte: true,
popup: false,
firstDo: true,
filter: function (event, player) {
return (
event.card.name == "sha" &&
!game.hasPlayer2(function (current) {
return current.hasHistory("useCard", function (evt) {
return evt != event && evt.card.name == "sha";
});
})
);
},
content: function () {
player.addTempSkill("xinghan_temp");
player.storage.xinghan_temp = trigger.card;
},
},
temp: { onremove: true },
},
ai: { combo: "zhenge" },
},
//荀谌
refenglve: {
audio: 2,
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return (
player.countCards("h") > 0 &&
!player.hasSkillTag("noCompareSource") &&
game.hasPlayer(function (current) {
return current != player && current.countCards("h") > 0 && !current.hasSkillTag("noCompareTarget");
})
);
},
filterTarget: function (card, player, target) {
return target != player && target.countCards("h") > 0 && !target.hasSkillTag("noCompareTarget");
},
content: function () {
"step 0";
player.chooseToCompare(target);
"step 1";
if (result.bool) {
if (!target.countCards("hej")) event.finish();
else {
// event.giver = target;
// event.gainner = player;
player.gainPlayerCard(target, true, "hej", 2, "获得" + get.translation(target) + "区域里的两张牌");
}
} else if (result.tie) {
delete player.getStat("skill").refenglve;
if (get.position(result.player, true) == "d") player.gain(result.player, "gain2");
// event.finish();
} else {
if (get.position(result.player, true) == "d") target.gain(result.player, "gain2");
// event.finish();
/*if(!player.countCards('he')) event.finish();
else{
event.giver=player;
event.gainner=target;
player.chooseCard(true,'he','交给'+get.translation(target)+'一张牌');
}*/
}
"step 2";
// if (result.bool) event.giver.give(result.cards, event.gainner);
},
ai: {
order: 8,
result: {
target: function (player, target) {
if (
!player.hasCard(function (card) {
if (get.position(card) != "h") return false;
var val = get.value(card);
if (val < 0) return true;
if (val <= 5) {
return card.number >= 11;
}
if (val <= 6) {
return card.number >= 13;
}
return false;
})
)
return 0;
return -Math.sqrt(1 + target.countCards("he")) / (1 + target.countCards("j"));
},
},
},
},
anyong: {
audio: 2,
trigger: { global: "damageSource" },
direct: true,
filter: function (event, player) {
return (
event.source &&
event.source == _status.currentPhase &&
event.num == 1 &&
// event.player != event.source &&
event.player.isIn() &&
player.countCards("he") > 0 &&
event.source
.getHistory("sourceDamage", function (evt) {
return evt.player != event.source;
})
.indexOf(event) == 0
);
},
content: function () {
"step 0";
player
.chooseToDiscard("he", get.prompt("anyong", trigger.player), "弃置一张牌并对其造成1点伤害")
.set("goon", get.damageEffect(trigger.player, player, player) > 0)
.set("ai", function (card) {
if (_status.event.goon) return 7 - get.value(card);
return 0;
}).logSkill = ["anyong", trigger.player];
"step 1";
if (result.bool) trigger.player.damage();
},
},
//刘永
zhuning: {
audio: 2,
enable: "phaseUse",
usable: 2,
filter: function (event, player) {
if (!player.countCards("he")) return false;
return !player.getStat("skill").zhuning || player.hasSkill("zhuning_double");
},
filterCard: true,
position: "he",
filterTarget: lib.filter.notMe,
selectCard: [1, Infinity],
delay: false,
lose: false,
discard: false,
check: function (card) {
if (ui.selected.cards.length && ui.selected.cards[0].name == "du") return 0;
if (!ui.selected.cards.length && card.name == "du") return 20;
var player = get.owner(card);
if (ui.selected.cards.length >= Math.max(1, player.countCards("h") - player.hp)) return 0;
return 10 - get.value(card);
},
content: function () {
"step 0";
player.give(cards, target).gaintag.add("fengxiang_tag");
"step 1";
var list = [];
for (var name of lib.inpile) {
var type = get.type(name);
if (type != "basic" && type != "trick") continue;
var card = { name: name, isCard: true };
if (get.tag(card, "damage") > 0 && player.hasUseTarget(card)) {
list.push([type, "", name]);
}
if (name == "sha") {
for (var i of lib.inpile_nature) {
card.nature = i;
if (player.hasUseTarget(card)) list.push([type, "", name, i]);
}
}
}
if (list.length) {
player.chooseButton(["是否视为使用一张伤害牌?", [list, "vcard"]]).set("ai", function (button) {
return _status.event.player.getUseValue({ name: button.link[2] });
});
} else event.finish();
"step 2";
if (result.bool) {
player.chooseUseTarget({ name: result.links[0][2], nature: result.links[0][3], isCard: true }, true, false);
} else event.finish();
"step 3";
if (
!player.hasHistory("sourceDamage", function (evt) {
if (!evt.card) return false;
var evtx = evt.getParent("useCard");
return evtx.card == evt.card && evtx.getParent(2) == event;
})
)
player.addTempSkill("zhuning_double");
},
subSkill: {
double: {},
},
ai: {
fireAttack: true,
order: 4,
result: {
target: function (player, target) {
if (target.hasSkillTag("nogain")) return 0;
if (ui.selected.cards.length && ui.selected.cards[0].name == "du") {
if (target.hasSkillTag("nodu")) return 0;
return -10;
}
if (target.hasJudge("lebu")) return 0;
var nh = target.countCards("h");
var np = player.countCards("h");
if (player.hp == player.maxHp || player.storage.rerende < 0 || player.countCards("h") <= 1) {
if (nh >= np - 1 && np <= player.hp && !target.hasSkill("haoshi")) return 0;
}
return Math.max(1, 5 - nh);
},
},
},
},
fengxiang: {
getMax: function (event) {
var max = 0,
max2 = null,
players = game.filterPlayer();
for (var current of players) {
var num = 0,
cards = current.getCards("h", function (card) {
return card.hasGaintag("fengxiang_tag");
});
if (event) {
if (event.name == "gain" && event.gaintag.includes("fengxiang_tag")) cards.removeArray(event.cards);
var evt = event.getl(current);
if (evt && evt.gaintag_map) {
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("fengxiang_tag")) num++;
}
}
}
num += cards.length;
if (num > max) {
max = num;
max2 = current;
} else if (num == max) max2 = null;
}
return max2;
},
audio: 2,
init: function (player) {
game.addGlobalSkill("fengxiang_use");
},
onremove: function (player) {
if (!game.hasPlayer(current => current.hasSkill("fengxiang"), true)) game.removeGlobalSkill("fengxiang_use");
},
trigger: { player: "damageEnd" },
forced: true,
filter: function (event, player) {
var target = lib.skill.fengxiang.getMax();
return !target || target.isDamaged();
},
logTarget: function (event, player) {
return lib.skill.fengxiang.getMax() || player;
},
content: function () {
var target = lib.skill.fengxiang.getMax();
if (target) target.recover();
else player.draw();
},
group: "fengxiang_draw",
subSkill: {
draw: {
trigger: {
global: ["equipAfter", "addJudgeAfter", "loseAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
filter: function (event, player) {
if (event.name == "lose" && event.getlx === false) return false;
return lib.skill.fengxiang.getMax() != lib.skill.fengxiang.getMax(event);
},
content: function () {
if (trigger.delay === false) game.delayx();
player.draw();
},
},
use: {
mod: {
aiOrder: function (player, card, num) {
if (
num > 0 &&
get.itemtype(card) === "card" &&
card.hasGaintag("fengxiang_tag") &&
game.hasPlayer(current => {
return current.hasSkill("fengxiang") && get.attitude(player, current) > 0;
})
)
return num + 10;
},
},
trigger: { player: "dieAfter" },
filter: function (event, player) {
return !game.hasPlayer(current => current.hasSkill("fengxiang"), true);
},
silent: true,
forceDie: true,
charlotte: true,
content: function () {
game.removeGlobalSkill("fengxiang_use");
},
},
},
},
//阚泽
rekuanshi: {
audio: "kuanshi",
trigger: { player: "phaseJieshuBegin" },
direct: true,
content: function () {
"step 0";
player
.chooseTarget(get.prompt2("rekuanshi"))
.set("animate", false)
.set("ai", function (target) {
var att = get.attitude(player, target);
if (target.hp < 3) att /= 1.5;
return att;
});
"step 1";
if (result.bool) {
player.logSkill("rekuanshi");
player.addTempSkill("rekuanshi_effect", { player: "phaseBegin" });
player.storage.rekuanshi_effect = result.targets[0];
game.delayx();
}
},
subSkill: {
effect: {
audio: "kuanshi",
mark: true,
intro: {
content: "每回合限一次,当$于一回合内受到第2点伤害后,其回复1点体力。",
},
trigger: { global: "damageEnd" },
forced: true,
charlotte: true,
logTarget: "player",
usable: 1,
filter: function (event, player) {
if (event.player != player.storage.rekuanshi_effect || event.player.isHealthy()) return false;
var history = event.player.getHistory("damage", null, event),
num = 0;
for (var i of history) num += i.num;
return num > 1 && num - event.num < 2;
},
content: function () {
trigger.player.recover();
},
},
},
},
//吕玲绮
guowu: {
trigger: { player: "phaseUseBegin" },
filter: function (event, player) {
return player.countCards("h") > 0;
},
preHidden: true,
content: function () {
"step 0";
var hs = player.getCards("h");
player.showCards(hs, get.translation(player) + "发动了【帼舞】");
var list = [];
for (var i of hs) {
list.add(get.type2(i, player));
if (list.length >= 3) break;
}
if (list.length >= 1) {
var card = get.discardPile(function (i) {
return i.name == "sha";
});
if (card) player.gain(card, "gain2");
}
if (list.length >= 2) player.addTempSkill("guowu_dist", "phaseUseAfter");
if (list.length >= 3) player.addTempSkill("guowu_add", "phaseUseAfter");
},
subSkill: {
dist: {
charlotte: true,
mod: { targetInRange: () => true },
},
add: {
charlotte: true,
trigger: { player: "useCard1" },
direct: true,
filter: function (event, player) {
var info = get.info(event.card, false);
if (info.allowMultiple == false) return false;
if (event.card.name != "sha" && (info.type != "trick" || get.mode() == "guozhan")) return false;
if (event.targets && !info.multitarget) {
if (
game.hasPlayer(function (current) {
return !event.targets.includes(current) && lib.filter.targetEnabled2(event.card, player, current) && lib.filter.targetInRange(event.card, player, current);
})
) {
return true;
}
}
return false;
},
content: function () {
"step 0";
var num = game.countPlayer(function (current) {
return !trigger.targets.includes(current) && lib.filter.targetEnabled2(trigger.card, player, current) && lib.filter.targetInRange(trigger.card, player, current);
});
player
.chooseTarget("帼舞:是否为" + get.translation(trigger.card) + "增加" + (num > 1 ? "至多两个" : "一个") + "目标?", [1, Math.min(2, num)], function (card, player, target) {
var trigger = _status.event.getTrigger();
var card = trigger.card;
return !trigger.targets.includes(target) && lib.filter.targetEnabled2(card, player, target) && lib.filter.targetInRange(card, player, target);
})
.set("ai", function (target) {
var player = _status.event.player;
var card = _status.event.getTrigger().card;
return get.effect(target, card, player, player);
});
"step 1";
if (result.bool) {
if (player != game.me && !player.isOnline()) game.delayx();
} else event.finish();
"step 2";
var targets = result.targets.sortBySeat();
player.logSkill("guowu_add", targets);
trigger.targets.addArray(targets);
//if(get.mode()=='guozhan') player.removeSkill('guowu_add');
},
},
},
},
zhuangrong: {
derivation: ["llqshenwei", "wushuang"],
trigger: { global: "phaseEnd" },
forced: true,
juexingji: true,
skillAnimation: true,
animationColor: "gray",
filter: function (event, player) {
return player.hp == 1 || player.countCards("h") == 1;
},
content: function () {
"step 0";
player.awakenSkill("zhuangrong");
player.loseMaxHp();
"step 1";
if (player.maxHp > player.hp) player.recover(player.maxHp - player.hp);
"step 2";
player.drawTo(Math.min(5, player.maxHp));
player.addSkills(["llqshenwei", "wushuang"]);
},
},
llqshenwei: {
audio: 2,
trigger: { player: "phaseDrawBegin2" },
forced: true,
filter: event => !event.numFixed,
content: function () {
trigger.num += 2;
},
mod: {
maxHandcard: (player, num) => num + 2,
},
},
cuijian: {
audio: 2,
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return game.hasPlayer(current => lib.skill.cuijian.filterTarget(null, player, current));
},
filterTarget: function (card, player, target) {
return target != player && target.countCards("h") > 0;
},
content: function () {
"step 0";
var hs = target.getCards("h", "shan");
if (hs.length) {
hs.addArray(
target.getCards("he", function (card) {
return get.subtype(card) == "equip2";
})
);
player.gain(hs, target, "give", "bySelf");
if (player.hasMark("zhtongyuan_basic")) event.finish();
else event.num = hs.length;
} else {
if (player.hasMark("zhtongyuan_trick")) player.draw(2);
event.finish();
}
"step 1";
var hs = player.getCards("he");
if (!hs.length || !target.isIn()) event.finish();
else if (hs.length <= num) event._result = { bool: true, cards: hs };
else player.chooseCard("he", true, "选择交给" + get.translation(target) + get.cnNumber(num) + "张牌", num);
"step 2";
if (result.bool && result.cards && result.cards.length) player.give(result.cards, target);
},
ai: {
order: 4,
result: {
player: function (player, target) {
if (!target.countCards("h", "shan")) return player.hasMark("zhtongyuan_trick") ? 2 : 0;
return 0;
},
target: function (player, target) {
if (target.countCards("h", "shan")) {
var num = -target.countCards("h") / 2;
var card = target.getEquip(2);
if (card) num -= get.value(card, target) / 2;
return num;
}
return -0.01;
},
},
},
},
tongyuan: { audio: 2 },
zhtongyuan: {
audio: "tongyuan",
trigger: { player: ["useCardAfter", "respondAfter"] },
forced: true,
filter: function (event, player) {
var type = get.type2(event.card, false);
return (type == "basic" || type == "trick") && get.color(event.card, false) == "red" && !player.hasMark("zhtongyuan_" + type);
},
content: function () {
var type = get.type2(trigger.card, false);
if (!player.hasMark("zhtongyuan_" + type)) {
player.addMark("zhtongyuan_" + type, 1, false);
game.log(player, "修改了技能", "#g【摧坚】");
}
},
group: ["zhtongyuan_basic", "zhtongyuan_trick"],
subSkill: {
basic: {
trigger: { player: "useCard2" },
direct: true,
locked: true,
filter: function (event, player) {
if (!player.hasMark("zhtongyuan_basic") || !player.hasMark("zhtongyuan_trick")) return false;
var card = event.card;
if (get.color(card, false) != "red" || get.type(card, null, true) != "basic") return false;
var info = get.info(card);
if (info.allowMultiple == false) return false;
if (event.targets && !info.multitarget) {
if (
game.hasPlayer(function (current) {
return !event.targets.includes(current) && lib.filter.targetEnabled2(card, player, current);
})
) {
return true;
}
}
return false;
},
content: function () {
"step 0";
var prompt2 = "为" + get.translation(trigger.card) + "增加一个目标";
player
.chooseTarget(get.prompt("zhtongyuan"), function (card, player, target) {
var player = _status.event.player;
return !_status.event.targets.includes(target) && lib.filter.targetEnabled2(_status.event.card, player, target);
})
.set("prompt2", prompt2)
.set("ai", function (target) {
var trigger = _status.event.getTrigger();
var player = _status.event.player;
return get.effect(target, trigger.card, player, player);
})
.set("card", trigger.card)
.set("targets", trigger.targets);
"step 1";
if (result.bool) {
if (!event.isMine() && !event.isOnline()) game.delayx();
event.targets = result.targets;
} else {
event.finish();
}
"step 2";
if (event.targets) {
player.logSkill("zhtongyuan", event.targets);
trigger.targets.addArray(event.targets);
}
},
},
trick: {
audio: "zhtongyuan",
trigger: { player: "useCard" },
forced: true,
filter: function (event, player) {
if (!player.hasMark("zhtongyuan_basic") || !player.hasMark("zhtongyuan_trick")) return false;
var card = event.card;
return get.color(card, false) == "red" && get.type(card, null, false) == "trick";
},
content: function () {
trigger.directHit.addArray(game.filterPlayer());
game.log(trigger.card, "不可被响应");
},
},
},
},
//陆郁生
zhente: {
audio: 2,
trigger: { target: "useCardToTargeted" },
logTarget: "player",
usable: 1,
preHidden: true,
filter: function (event, player) {
var color = get.color(event.card);
if (player == event.player || event.player.isDead() || color == "none" || (get.mode() == "guozhan" && color != "black")) return false;
var type = get.type(event.card);
return type == "basic" || type == "trick";
},
check: function (event, player) {
return !event.excluded.includes(player) && get.effect(player, event.card, event.player, player) < 0;
},
content: function () {
"step 0";
trigger.player
.chooseControl()
.set("choiceList", ["本回合内不能再使用" + get.translation(get.color(trigger.card)) + "牌", "令" + get.translation(trigger.card) + "对" + get.translation(player) + "无效"])
.set("prompt", get.translation(player) + "发动了【贞特】,请选择一项")
.set("ai", function () {
var player = _status.event.player;
var target = _status.event.getParent().player;
var card = _status.event.getTrigger().card,
color = get.color(card);
if (get.effect(target, card, player, player) <= 0) return 1;
var hs = player.countCards("h", function (card) {
return get.color(card, player) == color && player.hasValueTarget(card, null, true);
});
if (!hs.length) return 0;
if (hs > 1) return 1;
return Math.random() > 0.5 ? 0 : 1;
});
"step 1";
if (result.index == 0) {
trigger.player.addTempSkill("zhente2");
trigger.player.storage.zhente2.add(get.color(trigger.card));
trigger.player.markSkill("zhente2");
} else trigger.excluded.add(player);
},
},
zhente2: {
mod: {
cardEnabled(card, player) {
const color = get.color(card);
if (color != "unsure" && player.getStorage("zhente2").includes(color)) return false;
},
cardSavable(card, player) {
const color = get.color(card);
if (color != "unsure" && player.getStorage("zhente2").includes(color)) return false;
},
},
charlotte: true,
onremove: true,
init: function (player, skill) {
if (!player.storage[skill]) player.storage[skill] = [];
},
intro: { content: "本回合内不能使用$牌" },
},
zhiwei: {
audio: 2,
trigger: {
player: ["enterGame", "showCharacterAfter", "phaseBegin"],
global: ["phaseBefore"],
},
direct: true,
filter: function (event, player, name) {
if (player.hasSkill("zhiwei2")) return false;
if (!game.hasPlayer(current => current != player)) return false;
if (get.mode() == "guozhan")
return (
event.name == "showCharacter" &&
event.toShow.some(name => {
return get.character(name, 3).includes("zhiwei");
})
);
return event.name != "showCharacter" && (name != "phaseBefore" || game.phaseNumber == 0);
},
content: function () {
"step 0";
player.chooseTarget("请选择【至微】的目标", "选择一名其他角色。该角色造成伤害后,你摸一张牌,该角色受到伤害后,你随机弃置一张手牌。你弃牌阶段弃置的牌均被该角色获得。", true, lib.filter.notMe).set("ai", function (target) {
var att = get.attitude(_status.event.player, target);
if (att > 0) return 1 + att;
return Math.random();
});
"step 1";
if (result.bool) {
var target = result.targets[0];
player.logSkill("zhiwei", target);
player.storage.zhiwei2 = target;
player.addSkill("zhiwei2");
}
},
},
zhiwei2: {
group: ["zhiwei2_draw", "zhiwei2_discard", "zhiwei2_gain", "zhiwei2_clear"],
charlotte: true,
onremove: true,
mark: "character",
intro: {
content: "$造成伤害后你摸一张牌;$受到伤害后你弃置一张牌;你于弃牌阶段弃置牌后交给$",
},
subSkill: {
draw: {
audio: "zhiwei",
trigger: { global: "damageSource" },
forced: true,
filter: function (event, player) {
return event.source == player.storage.zhiwei2;
},
logTarget: "source",
content: function () {
player.draw();
},
},
discard: {
audio: "zhiwei",
trigger: { global: "damageEnd" },
forced: true,
filter: function (event, player) {
return (
event.player == player.storage.zhiwei2 &&
player.countCards("h", function (card) {
return lib.filter.cardDiscardable(card, player, "zhiwei2_discard");
})
);
},
logTarget: "player",
content: function () {
player.discard(
player
.getCards("h", function (card) {
return lib.filter.cardDiscardable(card, player, "zhiwei2_discard");
})
.randomGet()
);
},
},
gain: {
audio: "zhiwei",
trigger: {
player: "loseAfter",
global: "loseAsyncAfter",
},
forced: true,
filter: function (event, player) {
if (event.type != "discard" || event.getlx === false || event.getParent("phaseDiscard").player != player || !player.storage.zhiwei2 || !player.storage.zhiwei2.isIn()) return false;
var evt = event.getl(player);
return evt && evt.cards2.filterInD("d").length > 0;
},
logTarget: function (event, player) {
return player.storage.zhiwei2;
},
content: function () {
if (trigger.delay === false) game.delay();
player.storage.zhiwei2.gain(trigger.getl(player).cards2.filterInD("d"), "gain2");
},
},
clear: {
audio: "zhiwei",
trigger: {
global: "die",
player: ["hideCharacterEnd", "removeCharacterEnd"],
},
forced: true,
filter: function (event, player) {
if (event.name == "die") return event.player == player.storage.zhiwei2;
if (event.name == "removeCharacter") return event.toRemove == "luyusheng" || event.toRemove == "gz_luyusheng";
return event.toHide == "luyusheng" || event.toHide == "gz_luyusheng";
},
content: function () {
"step 0";
player.removeSkill("zhiwei2");
if (trigger.name != "die" || get.mode() != "guozhan") event.finish();
"step 1";
if (get.character(player.name1, 3).includes("zhiwei")) player.hideCharacter(0);
if (get.character(player.name2, 3).includes("zhiwei")) player.hideCharacter(1);
},
},
},
},
//华歆
spwanggui: {
audio: "wanggui",
trigger: { source: "damageSource" },
usable: 1,
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current.group != player.group;
});
},
async cost(event, trigger, player) {
event.result = await player
.chooseTarget(get.prompt("spwanggui"), "对一名势力不同的其他角色造成1点伤害", function (card, player, target) {
return target.group != player.group;
})
.set("ai", function (target) {
var player = _status.event.player;
return get.damageEffect(target, player, player);
})
.forResult();
},
async content(event, trigger, player) {
const target = event.targets[0];
target.damage();
},
group: "spwanggui_draw",
subSkill: {
draw: {
trigger: { player: "damageEnd" },
async cost(event, trigger, player) {
event.result = await player
.chooseTarget(get.prompt("spwanggui"), "令自己摸一张牌,或和一名势力相同的其他角色各摸一张牌", function (card, player, target) {
return target.group == player.group;
})
.set("ai", function (target) {
var player = _status.event.player,
att = get.attitude(player, target);
if (target != player) att *= 2;
if (target.hasSkillTag("nogain")) att /= 1.7;
return att;
})
.forResult();
},
content: function () {
"step 0";
var target = targets[0];
if (player == target) {
player.draw();
event.finish();
} else {
var list = [player, target].sortBySeat();
game.asyncDraw(list);
}
"step 1";
game.delayx();
},
},
},
},
wanggui: {
audio: 2,
trigger: {
player: "damageEnd",
source: "damageSource",
},
filter: function (event, player) {
if (player.isUnseen()) return false;
if (!player.isUnseen(2)) return true;
return (!player.isUnseen(0) && get.character(player.name1, 3).includes("wanggui")) || (!player.isUnseen(1) && get.character(player.name2, 3).includes("wanggui"));
},
usable: 1,
preHidden: true,
async cost(event, trigger, player) {
if (player.isUnseen(2))
event.result = await player
.chooseTarget(get.prompt("wanggui"), "望归:是否对与你势力不同的一名角色造成1点伤害?", (card, player, target) => {
return target.isEnemyOf(player);
})
.set("ai", target => {
let player = _status.event.player;
return get.damageEffect(target, player, player);
})
.setHiddenSkill("wanggui")
.forResult();
else
event.result = await player
.chooseBool("望归:是否令与你势力相同的角色各摸一张牌?")
.setHiddenSkill("wanggui")
.set("logSkill", [
"wanggui",
game.filterPlayer(current => {
return current.isFriendOf(player);
}),
])
.forResult();
},
async content(event, trigger, player) {
if (player.isUnseen(2)) {
const target = event.targets[0];
target.damage("nocard");
} else {
const targets = game.filterPlayer(current => {
return current.isFriendOf(player);
});
targets.sortBySeat();
game.asyncDraw(targets);
}
},
},
xibing: {
audio: 2,
trigger: { global: "useCardToPlayered" },
filter: function (event, player) {
if (player == event.player || event.targets.length != 1) return false;
var bool = function (card) {
return (card.name == "sha" || get.type(card, false) == "trick") && get.color(card, false) == "black";
};
if (!bool(event.card)) return false;
var evt = event.getParent("phaseUse");
if (evt.player != event.player) return false;
return true;
},
usable: 1,
logTarget: "player",
check: function (event, player) {
var target = event.player;
var att = get.attitude(player, target);
var num2 = Math.min(5, target.hp) - target.countCards("h");
if (num2 <= 0) return false;
var num = target.countCards("h", function (card) {
return target.hasValueTarget(card, null, true);
});
if (!num) return att > 0;
return (num - num2) * att < 0;
},
preHidden: true,
content: function () {
"step 0";
var num = Math.min(5, trigger.player.hp) - trigger.player.countCards("h");
if (num > 0) {
trigger.player.draw(num);
trigger.player.addTempSkill("xibing_banned");
}
},
subSkill: {
banned: {
mod: {
cardEnabled(card) {
return false;
},
cardSavable(card) {
return false;
},
},
},
},
},
//小虎
remeibu: {
audio: "meibu",
trigger: {
global: "phaseUseBegin",
},
filter: function (event, player) {
return event.player != player && event.player.isIn() && event.player.inRange(player) && player.countCards("he") > 0;
},
direct: true,
derivation: ["rezhixi"],
checkx: function (event, player) {
if (get.attitude(player, event.player) >= 0) return false;
return event.player.countCards("h") > event.player.hp;
},
content: function () {
"step 0";
var check = lib.skill.new_meibu.checkx(trigger, player);
player
.chooseToDiscard(get.prompt2("remeibu", trigger.player), "he")
.set("ai", function (card) {
if (_status.event.check) return 6 - get.value(card);
return 0;
})
.set("check", check)
.set("logSkill", ["remeibu", trigger.player]);
"step 1";
if (result.bool) {
var target = trigger.player;
var card = result.cards[0];
player.line(target, "green");
player.markAuto("remeibu_gain", [get.suit(card, player)]);
player.addTempSkill("remeibu_gain");
target.addTempSkills("rezhixi", "phaseUseEnd");
}
},
ai: {
expose: 0.2,
},
subSkill: {
gain: {
trigger: { global: "loseAfter" },
forced: true,
charlotte: true,
popup: false,
onremove: true,
filter: function (event, player) {
return event.getParent(3).name == "rezhixi" && player.getStorage("remeibu_gain").includes(get.suit(event.cards[0], event.player)) && get.position(event.cards[0]) == "d";
},
content: function () {
player.gain(trigger.cards[0], "gain2");
},
},
},
},
remumu: {
audio: "mumu",
trigger: {
player: "phaseUseBegin",
},
direct: true,
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current.countCards("e") > 0;
});
},
content: function () {
"step 0";
player
.chooseTarget(get.prompt2("remumu"), function (card, player, target) {
return target.countCards("e") > 0;
})
.set("ai", function (target) {
var player = _status.event.player,
att = get.attitude(player, target),
es = target.getCards("e"),
val = 0;
for (var i of es) {
var eff = -(get.value(i, target) - 0.1) * att;
if (eff > val) val = eff;
}
return eff;
});
"step 1";
if (result.bool) {
var target = result.targets[0];
event.target = target;
player.logSkill("remumu", target);
if (player == target) event._result = { index: 1 };
else {
var str = get.translation(target);
player
.chooseControl()
.set("choiceList", ["弃置" + str + "装备区的一张牌且本阶段使用【杀】的次数上限+1", "获得" + str + "装备区的一张牌且本阶段使用【杀】的次数上限-1"])
.set("ai", function () {
var player = _status.event.player;
if (
player.countCards("hs", function (card) {
return get.name(card, player) == "sha" && player.hasValueTarget(card);
}) < Math.max(1, player.getCardUsable("sha"))
)
return 1;
return 0;
});
}
} else event.finish();
"step 2";
if (result.index == 0) {
player.addTempSkill("remumu3", "phaseUseAfter");
player.discardPlayerCard(target, "e", true);
} else {
player.addTempSkill("remumu2", "phaseUseAfter");
player.gainPlayerCard(target, "e", true);
}
},
},
remumu2: {
mod: {
cardUsable: function (card, player, num) {
if (card.name == "sha") return num - 1;
},
},
},
remumu3: {
mod: {
cardUsable: function (card, player, num) {
if (card.name == "sha") return num + 1;
},
},
},
rezhixi: {
trigger: {
player: "useCard",
},
forced: true,
filter: function (event, player) {
return (event.card.name == "sha" || get.type(event.card) == "trick") && player.countCards("h") > 0;
},
content: function () {
player.chooseToDiscard("h", true);
},
ai: {
halfneg: true,
nokeep: true,
},
},
//董白
relianzhu: {
audio: "lianzhu",
enable: "phaseUse",
usable: 1,
filter: function (event, player) {
return player.countCards("he") > 0;
},
filterCard: true,
discard: false,
lose: false,
delay: false,
position: "he",
filterTarget: lib.filter.notMe,
check: function (card) {
var num = get.value(card);
if (get.color(card) == "black") {
if (num >= 6) return 0;
return 9 - num;
} else {
return 7 - num;
}
},
content: function () {
"step 0";
player.give(cards, target);
"step 1";
if (get.color(cards[0], player) == "red") {
player.draw();
event.finish();
} else {
target
.chooseToDiscard("he", 2, "弃置两张牌,或令" + get.translation(player) + "摸两张牌")
.set("goon", get.attitude(target, player) < 0)
.set("ai", function (card) {
if (!_status.event.goon) return -get.value(card);
return 6 - get.value(card);
});
}
"step 2";
if (!result.bool) player.draw(2);
},
ai: {
order: 3,
expose: 0.2,
result: {
target: function (player, target) {
if (ui.selected.cards.length && get.color(ui.selected.cards[0]) == "red") {
if (target.countCards("h") < player.countCards("h")) return 1;
return 0.5;
}
return -1;
},
},
},
},
rexiahui: {
audio: "xiahui",
mod: {
ignoredHandcard: function (card, player) {
if (get.color(card, player) == "black") return true;
},
cardDiscardable: function (card, player, name) {
if (name == "phaseDiscard" && get.color(card, player) == "black") return false;
},
},
trigger: { global: "phaseEnd" },
forced: true,
logTarget: "player",
filter: function (event, player) {
var target = event.player;
return (
target != player &&
target.countCards("h", function (card) {
return card.hasGaintag("rexiahui");
}) == 0 &&
target.getHistory("lose", function (evt) {
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("rexiahui")) return true;
}
}).length > 0
);
},
content: function () {
trigger.player.loseHp();
},
group: "rexiahui_gain",
subSkill: {
gain: {
trigger: { global: "gainEnd" },
forced: true,
popup: false,
filter: function (event, player) {
if (player == event.player) return false;
var evt = event.getl(player);
return (
evt &&
evt.cards2 &&
evt.cards2.filter(function (card) {
return get.color(card, player) == "black";
}).length > 0
);
},
content: function () {
trigger.player.addSkill("rexiahui_block");
var cards = trigger.getl(player).cards2.filter(function (card) {
return get.color(card, player) == "black";
});
trigger.player.addGaintag(cards, "rexiahui");
},
},
block: {
mod: {
cardEnabled2: function (card) {
if (get.itemtype(card) == "card" && card.hasGaintag("rexiahui")) return false;
},
cardDiscardable: function (card) {
if (card.hasGaintag("rexiahui")) return false;
},
},
charlotte: true,
forced: true,
popup: false,
trigger: { player: "changeHp" },
filter: function (event, player) {
return event.num < 0;
},
content: function () {
player.removeSkill("rexiahui_block");
},
onremove: function (player) {
player.removeGaintag("rexiahui");
},
},
},
},
//周善
dcmiyun: {
audio: 2,
trigger: { global: "roundStart" },
forced: true,
direct: true,
group: "dcmiyun_lose",
content: function () {
"step 0";
if (player.hasCard(card => card.hasGaintag("dcmiyun_tag"), "h")) {
player.chooseCardTarget({
prompt: "密运:将包括“安”在内的任意张手牌交给一名其他角色",
forced: true,
filterTarget: lib.filter.notMe,
selectCard: [1, Infinity],
filterOk: function () {
for (var card of ui.selected.cards) {
if (card.hasGaintag("dcmiyun_tag")) return true;
}
return false;
},
goon: game.hasPlayer(current => player != current && get.attitude(player, current) > 0),
ai1: function (card) {
if (get.itemtype(card) != "card") return 0;
if (card.hasGaintag("dcmiyun_tag")) return 100;
if (_status.event.goon) return 8 - get.value(card);
return -get.value(card);
},
ai2: function (target) {
return get.attitude(_status.event.player, target);
},
});
} else event.goto(3);
"step 1";
if (result.bool) {
var target = result.targets[0],
cards = result.cards;
player.logSkill("dcmiyun", target);
player.give(cards, target);
} else event.goto(3);
"step 2";
player.drawTo(player.maxHp);
"step 3";
if (game.hasPlayer(current => current != player && current.countGainableCards(player, "he"))) {
player
.chooseTarget("密运:获得一名其他角色的一张牌,称为“安”", true, (card, player, target) => {
return target != player && target.countGainableCards(player, "he");
})
.set("ai", target => {
return get.effect(target, { name: "shunshou" }, _status.event.player, _status.event.player);
});
} else event.finish();
"step 4";
if (result.bool) {
var target = result.targets[0];
player.logSkill("dcmiyun", target);
player.gainPlayerCard(target, true, "visibleMove").chooseonly = true;
} else event.finish();
"step 5";
if (result.bool) {
player.gain(result.cards).gaintag.add("dcmiyun_tag");
}
},
mod: {
aiValue: function (player, card, num) {
if (get.itemtype(card) == "card" && card.hasGaintag("dcmiyun_tag")) return Math.abs(num) * 10;
},
aiUseful: function () {
return lib.skill.dcmiyun.mod.aiValue.apply(this, arguments);
},
aiOrder: function (player, card, num) {
if (get.itemtype(card) == "card" && card.hasGaintag("dcmiyun_tag")) return 0;
},
},
subSkill: {
lose: {
audio: "dcmiyun",
trigger: {
player: "loseAfter",
global: ["equipAfter", "addJudgeAfter", "gainAfter", "loseAsyncAfter", "addToExpansionAfter"],
},
forced: true,
filter: function (event, player) {
if (event.getParent().name == "dcmiyun") return false;
var evt = event.getl(player);
if (!evt || !evt.cards2 || !evt.cards2.length) return false;
if (event.name == "lose") {
for (var i in event.gaintag_map) {
if (event.gaintag_map[i].includes("dcmiyun_tag")) return true;
}
return false;
}
return player.hasHistory("lose", evt => {
if (event != evt.getParent()) return false;
for (var i in evt.gaintag_map) {
if (evt.gaintag_map[i].includes("dcmiyun_tag")) return true;
}
return false;
});
},
content: function () {
player.loseHp();
},
},
},
},
dcdanying: {
audio: 2,
mod: {
aiOrder: function (player, card, num) {
if (num <= 0 || (card.name !== "sha" && card.name !== "shan") || !player.hasCard(i => i.hasGaintag("dcmiyun_tag"), "h")) return;
return Math.max(0.12, num / 25);
},
},
locked: false,
enable: ["chooseToUse", "chooseToRespond"],
usable: 1,
hiddenCard: function (player, name) {
if (!_status.connectMode && !player.hasCard(card => card.hasGaintag("dcmiyun_tag"), "h")) return false;
return name == "sha" || name == "shan";
},
filter: function (event, player) {
if (event.type == "wuxie" || !player.hasCard(card => card.hasGaintag("dcmiyun_tag"), "h")) return false;
for (var name of ["sha", "shan"]) {
if (event.filterCard({ name: name, isCard: true }, player, event)) return true;
}
return false;
},
chooseButton: {
dialog: function (event, player) {
var vcards = [];
for (var name of ["sha", "shan"]) {
var card = { name: name, isCard: true };
if (event.filterCard(card, player, event)) vcards.push(["基本", "", name]);
}
var dialog = ui.create.dialog("胆迎", [vcards, "vcard"], "hidden");
dialog.direct = true;
return dialog;
},
backup: function (links, player) {
return {
filterCard: () => false,
selectCard: -1,
viewAs: {
name: links[0][2],
isCard: true,
},
popname: true,
precontent: function () {
player.logSkill("dcdanying");
player.showCards(
player.getCards("h", card => card.hasGaintag("dcmiyun_tag")),
get.translation(player) + "的“安”"
);
player.addTempSkill("dcdanying_discard");
},
};
},
prompt: function (links, player) {
return "展示“安”,然后视为使用【" + get.translation(links[0][2]) + "】";
},
},
ai: {
order: function (item, player) {
var o1 = get.order({ name: "sha" }),
o2 = get.order({ name: "shan" });
if (player.countCards("h") > 3 || player == _status.currentPhase) return Math.max(o1, o2) + 0.1;
return Math.min(o1, o2) - 0.1;
},
combo: "dcmiyun",
respondSha: true,
respondShan: true,
skillTagFilter: function (player, tag, arg) {
if (!player.hasCard(card => card.hasGaintag("dcmiyun_tag"), "h")) return false;
},
result: {
player: 1,
},
},
subSkill: {
discard: {
trigger: { target: "useCardToTargeted" },
charlotte: true,
forced: true,
filter: function (event, player) {
return player.countDiscardableCards(event.player, "he");
},
content: function () {
trigger.player.discardPlayerCard(player, "he", true);
player.removeSkill("dcdanying_discard");
},
ai: {
effect: {
target_use(card, player, target) {
if (_status._dcdanying_aiChecking) return;
_status._dcdanying_aiChecking = true;
let eff = get.effect(target, { name: "guohe_copy2" }, player, player);
delete _status._dcdanying_aiChecking;
return [1, get.sgn(eff)];
},
},
},
},
},
},
//蔡阳
dcxunji: {
audio: 2,
enable: "phaseUse",
usable: 1,
filterTarget: function (card, player, target) {
return target != player && !player.getStorage("dcxunji_effect").includes(target);
},
content: function () {
player.markAuto("dcxunji_effect", [target]);
player.addTempSkill("dcxunji_effect", { player: "die" });
target.addTempSkill("dcxunji_mark", { player: "phaseEnd" });
},
ai: {
order: 1,
result: {
player: function (player, target) {
if (player.hp < 2) return 0;
return get.effect(target, { name: "juedou" }, player, player);
},
},
},
subSkill: {
mark: {
mark: true,
marktext: "嫉",
intro: { content: "你已经被盯上了!" },
},
effect: {
audio: "dcxunji",
charlotte: true,
trigger: { global: "phaseJieshuBegin" },
forced: true,
popup: false,
onremove: true,
filter: function (event, player) {
return player.getStorage("dcxunji_effect").includes(event.player);
},
content: function () {
"step 0";
var target = trigger.player;
event.target = target;
if (target.getHistory("useCard", evt => get.color(evt.card) == "black").length > 0 && player.canUse("juedou", target)) {
player.useCard({ name: "juedou", isCard: true }, target, "dcxunji_effect");
}
"step 1";
player.unmarkAuto("dcxunji_effect", [target]);
if (!player.storage.dcxunji_effect.length) player.removeSkill("dcxunji_effect");
},
group: "dcxunji_loseHp",
},
loseHp: {
trigger: { source: "damageSource" },
forced: true,
popup: false,
filter: function (event, player) {
return event.card && event.card.name == "juedou" && event.getParent().skill == "dcxunji_effect" && event.player.isIn();
},
content: function () {
trigger.player.line(player);
player.damage(trigger.num, trigger.player);
},
},
},
},
dcjiaofeng: {
audio: 2,
trigger: { source: "damageBegin1" },
forced: true,
usable: 1,
filter: function (event, player) {
return player.isDamaged() && !player.getHistory("sourceDamage").length;
},
content: function () {
var num = player.getDamagedHp();
if (num > 0) player.draw();
if (num > 1) trigger.num++;
if (num > 2) player.recover();
},
},
//夏侯杰
liedan: {
audio: 2,
trigger: { global: "phaseZhunbeiBegin" },
forced: true,
filter: function (event, player) {
return (player != event.player || player.countMark("liedan") > 4) && !player.hasSkill("zhuangdan_mark");
},
logTarget: "player",
content: function () {
if (player == trigger.player) {
player.die();
return;
}
var num = 0;
if (player.hp > trigger.player.hp) num++;
if (player.countCards("h") > trigger.player.countCards("h")) num++;
if (player.countCards("e") > trigger.player.countCards("e")) num++;
if (num) {
player.draw(num);
if (num == 3 && player.maxHp < 8) player.gainMaxHp();
} else {
player.addMark("liedan", 1);
player.loseHp();
}
},
intro: { content: "mark" },
},
zhuangdan: {
audio: 2,
trigger: { global: "phaseEnd" },
forced: true,
filter: function (event, player) {
return player != event.player && player.isMaxHandcard(true);
},
content: function () {
player.addTempSkill("zhuangdan_mark", { player: "phaseEnd" });
},
ai: {
combo: "zhuangdan",
},
},
zhuangdan_mark: {
mark: true,
marktext: "胆",
intro: { content: "我超勇的" },
},
//乌巢酒仙
recangchu: {
audio: 2,
trigger: { global: "phaseBefore", player: "enterGame" },
marktext: "粮",
forced: true,
filter: function (event, player) {
if (event.name == "phase" && game.phaseNumber != 0) return false;
return player.countMark("recangchu") < game.countPlayer();
},
content: function () {
player.addMark("recangchu", Math.min(3, game.countPlayer() - player.countMark("recangchu")));
},
intro: { content: "mark", name: "粮" },
mod: {
maxHandcard: function (player, num) {
return num + player.countMark("recangchu");
},
},
group: ["recangchu2", "recangchu3"],
},
recangchu2: {
audio: "recangchu",
trigger: {
player: "gainAfter",
global: "loseAsyncAfter",
},
forced: true,
usable: 1,
filter: function (event, player) {
return player != _status.currentPhase && player.countMark("recangchu") < game.countPlayer() && event.getg(player).length > 0;
},
content: function () {
player.addMark("recangchu", 1);
},
},
recangchu3: {
audio: "recangchu",
trigger: { global: "die" },
forced: true,
filter: function (event, player) {
return player.countMark("recangchu") > game.countPlayer();
},
content: function () {
player.removeMark("recangchu", player.countMark("recangchu") - game.countPlayer());
},
},
reliangying: {
audio: 2,
trigger: { player: "phaseDiscardBegin" },
filter(event, player) {
return player.hasMark("recangchu");
},
direct: true,
async content(event, trigger, player) {
const draws = Array.from({ length: player.countMark("recangchu") }).map((_, i) => get.cnNumber(i + 1) + "张");
const {
result: { control },
} = await player
.chooseControl(draws, "cancel2")
.set("prompt", get.prompt("reliangying"))
.set("prompt2", "摸至多" + get.cnNumber(player.countMark("recangchu")) + "张牌,然后交给等量的角色各一张牌")
.set("ai", () => {
const player = get.event("player");
const num = Math.min(
player.countMark("recangchu"),
game.countPlayer(current => get.attitude(player, current) > 0)
);
if (num > 0) return get.cnNumber(num) + "张";
return "cancel2";
});
if (control != "cancel2") {
player.logSkill("reliangying");
const num = draws.indexOf(control) + 1,
max = Math.min(
num,
player.countCards("he"),
game.countPlayer(target => target != player)
);
await player.draw(num);
let list = [];
if (_status.connectMode) game.broadcastAll(() => (_status.noclearcountdown = true));
while (max - list.length > 0) {
const {
result: { bool, cards, targets },
} = await player
.chooseCardTarget({
prompt: "粮营:将" + get.cnNumber(max - 1) + "至" + get.cnNumber(max) + "张牌交给其他角色",
position: "he",
animate: false,
filterCard(card, player) {
return !get.event("list").some(list => list[1] == card);
},
filterTarget(card, player, target) {
return target != player && !get.event("list").some(list => list[0] == target);
},
ai1(card) {
if (card.name == "shan") return 1;
return Math.random();
},
ai2(target) {
return get.attitude(get.event("player"), target);
},
})
.set("list", list)
.set("forced", max - list.length > 1);
if (bool) {
list.push([targets[0], cards[0]]);
player.addGaintag(cards, "olsujian_given");
} else break;
}
if (_status.connectMode) {
game.broadcastAll(() => {
delete _status.noclearcountdown;
game.stopCountChoose();
});
}
if (list.length) {
await game
.loseAsync({
gain_list: list,
player: player,
cards: list.slice().map(list => list[1]),
giver: player,
animate: "giveAuto",
})
.setContent("gaincardMultiple");
}
}
},
ai: {
combo: "recangchu"
},
},
reshishou: {
audio: 2,
trigger: { player: ["useCard", "damageEnd"] },
forced: true,
filter: function (event, player) {
if (!player.countMark("recangchu")) return false;
return event.name == "damage" ? event.hasNature("fire") : event.card && event.card.name == "jiu";
},
content: function () {
player.removeMark("recangchu", Math.min(player.countMark("recangchu"), trigger.num || 1));
},
ai: {
combo: "recangchu",
neg: true,
},
group: "reshishou2",
},
reshishou2: {
audio: "reshishou",
trigger: { player: "phaseZhunbeiBegin" },
forced: true,
filter: function (event, player) {
return !player.countMark("recangchu");
},
content: function () {
player.loseHp();
},
},
//曹性
cxliushi: {
audio: 2,
enable: "phaseUse",
filter: function (event, player) {
return player.countCards("he", { suit: "heart" }) > 0;
},
filterCard: { suit: "heart" },
position: "he",
filterTarget: function (card, player, target) {
return player.canUse("sha", target, false);
},
check: function (card) {
var player = _status.event.player;
var next = player.getNext();
var att = get.attitude(player, next);
if (att > 0) {
var js = next.getCards("j");
if (js.length) return get.judge(js[0]) + 10 - get.value(card);
return 9 - get.value(card);
}
return 6 - get.value(card);
},
discard: false,
prepare: "throw",
loseTo: "cardPile",
visible: true,
insert: true,
content: function () {
game.log(player, "将", cards, "置于牌堆顶");
player.useCard({ name: "sha", isCard: true }, false, targets).card.cxliushi = true;
},
group: "cxliushi_damage",
subSkill: {
damage: {
trigger: { source: "damageSource" },
forced: true,
popup: false,
filter: function (event, player) {
return event.card && event.card.cxliushi == true && event.player.isIn() && event.getParent(3).name == "cxliushi";
},
content: function () {
trigger.player.addMark("cxliushi2", 1);
trigger.player.addSkill("cxliushi2");
},
},
},
ai: {
order: function () {
return get.order({ name: "sha" }) - 0.4;
},
result: {
target: function (player, target) {
var eff = get.effect(target, { name: "sha" }, player, target);
var damageEff = get.damageEffect(target, player, player);
if (eff > 0) return damageEff > 0 ? 0 : eff;
if (target.hasSkill("bagua_skill") || target.hasSkill("rw_bagua_skill") || target.hasSkill("bazhen")) return 0;
return eff;
},
},
},
},
cxliushi2: {
mod: {
maxHandcard: function (player, num) {
return num - player.countMark("cxliushi2");
},
},
onremove: true,
charlotte: true,
intro: {
name2: "流",
content: "手牌上限-#",
},
},
zhanwan: {
audio: 2,
trigger: { global: "phaseDiscardEnd" },
forced: true,
filter: function (event, player) {
return (
event.player.hasSkill("cxliushi2") &&
event.player.getHistory("lose", function (evt) {
if (evt.type == "discard" && evt.getParent("phaseDiscard") == event) return true;
}).length > 0
);
},
logTarget: "player",
content: function () {
trigger.player.removeSkill("cxliushi2");
var num = 0;
trigger.player.getHistory("lose", function (evt) {
if (evt.type == "discard" && evt.getParent("phaseDiscard") == trigger) num += evt.cards2.length;
});
player.draw(num);
},
ai: {
combo: "cxliushi",
},
},
//说出吾名吓汝一跳
xuxie: {
audio: 2,
trigger: { player: "phaseUseBegin" },
logTarget: function (event, player) {
return game
.filterPlayer(function (current) {
return get.distance(player, current) <= 1;
})
.sortBySeat();
},
check: function (event, player) {
if (player.isHealthy()) return false;
var list = game.filterPlayer(function (current) {
return get.distance(player, current) <= 1;
});
var draw = 0;
var discard = 0;
var num = 2 / player.getDamagedHp();
while (list.length) {
var target = list.shift();
var att = get.attitude(player, target);
if (att > 0) {
draw++;
if (target.countDiscardableCards(player, "he") > 0) discard--;
}
if (att == 0) {
draw--;
if (target.countDiscardableCards(player, "he") > 0) discard--;
}
if (att < 0) {
draw--;
if (target.countDiscardableCards(player, "he") > 0) discard++;
}
}
return draw >= num || discard >= num;
},
content: function () {
"step 0";
player.loseMaxHp();
"step 1";
var targets = game
.filterPlayer(function (current) {
return get.distance(player, current) <= 1;
})
.sortBySeat();
if (!targets.length) event.finish();
else {
event.targets = targets;
player
.chooseControl()
.set("choiceList", ["弃置" + get.translation(targets) + "的各一张牌", "令" + get.translation(targets) + "各摸一张牌"])
.set("ai", function () {
var player = _status.event.player;
var list = _status.event.getParent().targets.slice(0);
var draw = 0;
var discard = 0;
while (list.length) {
var target = list.shift();
var att = get.attitude(player, target);
if (att > 0) {
draw++;
if (target.countDiscardableCards(player, "he") > 0) discard--;
}
if (att < 0) {
draw--;
if (target.countDiscardableCards(player, "he") > 0) discard++;
}
}
if (draw > discard) return 1;
return 0;
});
}
"step 2";
event.index = result.index;
if (result.index == 1) {
game.asyncDraw(targets);
} else event.goto(4);
"step 3";
game.delay();
event.finish();
"step 4";
var target = targets.shift();
if (target.countDiscardableCards(player, "he") > 0) player.discardPlayerCard(target, "he", true);
if (targets.length) event.redo();
},
group: "xuxie_add",
},
xuxie_add: {
audio: "xuxie",
trigger: { player: "phaseUseEnd" },
forced: true,
locked: false,
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current.maxHp > player.maxHp;
});
},
content: function () {
player.gainMaxHp();
player.chooseDrawRecover(2, true);
},
},
//新潘凤
xinkuangfu: {
enable: "phaseUse",
usable: 1,
audio: 2,
delay: false,
filterTarget: function (card, player, target) {
if (player == target)
return (
player.countCards("e", function (card) {
return lib.filter.cardDiscardable(card, player);
}) > 0
);
return target.countDiscardableCards(player, "e") > 0;
},
filter: function (event, player) {
return game.hasPlayer(function (current) {
return current.countCards("e") > 0;
});
},
content: function () {
"step 0";
if (player == target) player.chooseToDiscard("e", true);
else player.discardPlayerCard(target, "e", true);
"step 1";
player.chooseUseTarget("sha", true, false, "nodistance");
"step 2";
var bool = game.hasPlayer2(function (current) {
return (
current.getHistory("damage", function (evt) {
return evt.getParent("xinkuangfu") == event;
}).length > 0
);
});
if (player == target && bool) player.draw(2);
else if (player != target && !bool) player.chooseToDiscard("h", 2, true);
},
ai: {
order: function () {
return get.order({ name: "sha" }) + 0.3;
},
result: {
target: function (player, target) {
var att = get.attitude(player, target);
var max = 0;
var min = 1;
target.countCards("e", function (card) {
var val = get.value(card, target);
if (val > max) max = val;
if (val < min) min = val;
});
if (att > 0 && min <= 0) return target.hasSkillTag("noe") ? 3 : 1;
if (att <= 0 && max > 0) {
if (target.hasSkillTag("noe")) return max > 6 ? -max / 3 : 0;
return -max;
}
if (player === target && !player.hasSha()) {
let ph = player.countCards("h");
if (
game.hasPlayer(i => {
if (!player.canUse("sha", i, true, true) || get.effect(i, { name: "sha" }, player, player) <= 0) return false;
return (
!ph ||
!i.mayHaveShan(
player,
"use",
i.getCards("h", i => {
return i.hasGaintag("sha_notshan");
})
)
);
})
)
return 1;
}
return 0;
},
},
},
},
};
export default skills;