Merge pull request #883 from PZ157/PR-Branch

修复段巧笑【彩妆】并优化ai
This commit is contained in:
Spmario233 2024-01-30 22:39:14 +08:00 committed by GitHub
commit 321837c9ce
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 115 additions and 31 deletions

View File

@ -7558,6 +7558,11 @@ game.import('character',function(lib,game,ui,get,ai,_status){
return current.hasSkill('drlt_jieying'); return current.hasSkill('drlt_jieying');
}); });
}, },
aiOrder(player,card,num){
if(player.hasMark('drlt_jieying_mark')&&game.hasPlayer(current=>{
return current.hasSkill('drlt_jieying')&&get.attitude(player,current)<=0;
})) return Math.max(num,0)+1;
}
}, },
audio:'drlt_jieying', audio:'drlt_jieying',
trigger:{ trigger:{
@ -7577,8 +7582,10 @@ game.import('character',function(lib,game,ui,get,ai,_status){
ai:{ ai:{
nokeep:true, nokeep:true,
skillTagFilter(player){ skillTagFilter(player){
if(!player.hasMark('drlt_jieying_mark')) return false; return player.hasMark('drlt_jieying_mark')&&game.hasPlayer(current=>{
}, return current.hasSkill('drlt_jieying')&&get.attitude(player,current)<=0;
});
}
}, },
}, },
'drlt_jieying':{ 'drlt_jieying':{
@ -7616,15 +7623,20 @@ game.import('character',function(lib,game,ui,get,ai,_status){
player.chooseTarget(get.prompt('drlt_jieying'),"将“营”交给一名角色;其摸牌阶段多摸一张牌,出牌阶段使用【杀】的次数上限+1且手牌上限+1。该角色回合结束后其移去“营”标记然后你获得其所有手牌。",function(card,player,target){ player.chooseTarget(get.prompt('drlt_jieying'),"将“营”交给一名角色;其摸牌阶段多摸一张牌,出牌阶段使用【杀】的次数上限+1且手牌上限+1。该角色回合结束后其移去“营”标记然后你获得其所有手牌。",function(card,player,target){
return target!=player; return target!=player;
}).ai=function(target){ }).ai=function(target){
if(get.attitude(player,target)>0) let th=target.countCards('h'),att=get.attitude(_status.event.player,target);
return 0.1; for(let i in target.skills){
if(get.attitude(player,target)<1&&(target.isTurnedOver()||target.countCards('h')<1)) let info=get.info(i);
return 0.2; if(info&&info.shaRelated) return Math.abs(att);
if(get.attitude(player,target)<1&&target.countCards('h')>0&&target.countCards('j',{name:'lebu'})>0) }
return target.countCards('h')*0.8+target.getHandcardLimit()*0.7+2; if(att>0){
if(get.attitude(player,target)<1&&target.countCards('h')>0) if(th>3&&target.hp>2) return 0.6*th;
return target.countCards('h')*0.8+target.getHandcardLimit()*0.7; }
return 1; if(att<1){
if(target.countCards('j',{name:'lebu'})) return 1+Math.min((1.5+th)*0.8,target.getHandcardLimit()*0.7);
if(!th||target.getEquip('zhangba')||target.getEquip('guanshi')) return 0;
if(!target.inRange(player)||player.countCards('hs',{name:'shan'})>1) return Math.min((1+th)*0.3,target.getHandcardLimit()*0.2);
}
return 0;
}; };
'step 1' 'step 1'
if(result.bool){ if(result.bool){
@ -7636,6 +7648,13 @@ game.import('character',function(lib,game,ui,get,ai,_status){
target.addMark('drlt_jieying_mark',mark); target.addMark('drlt_jieying_mark',mark);
} }
}, },
ai:{
effect:{
player(card,player,target){
if(get.name(card)==='lebu'&&get.attitude(player,target)<0) return 1+Math.min((target.countCards('h')+1.5)*0.8,target.getHandcardLimit()*0.7);
}
}
}
}, },
'3':{ '3':{
audio:'drlt_jieying', audio:'drlt_jieying',

View File

@ -3816,25 +3816,85 @@ game.import('character',function(lib,game,ui,get,ai,_status){
position:'he', position:'he',
filterCard:true, filterCard:true,
check:function(card){ check:function(card){
var player=_status.event.player; let cache=lib.skill.dccaizhuang.tempCache();
var suit=get.suit(card); if(!cache||cache.no) return 0;
if(get.position(card)!='h'&&player.countCards('h',{suit:suit})==1) return 0.1; let player=_status.event.player,suit=get.suit(card);
if(!player.hasCard(cardx=>cardx!=card&&get.suit(cardx)==suit)) return 7.5-get.value(card); if(ui.selected.cards.filter(i=>{
return 6-get.value(card); return get.suit(i)===suit;
}).length<(cache[suit]||0)){
if(get.position(card)==='h') return 15-get.value(card);
return 9-get.value(card);
}
return 0;
},
tempCache(){
let cache=_status.event.getTempCache('dccaizhuang','dsuits');
if(cache) return cache;
cache={no:true};
_status.event.putTempCache('dccaizhuang','dsuits',cache);
let player=_status.event.player,suits={};
lib.suit.forEach(i=>{
suits[i]=0;
});
player.getCards('h',i=>{
let suit=get.suit(i);
if(lib.suit.includes(suit)) suits[suit]++;
});
let sortedSuits=Object.fromEntries(Object.entries(suits).sort((a,b)=>b[1]-a[1]));
let dis=0,idx=0,dsuits=0,leave=0;
for(let i in sortedSuits){
idx++;
if(!sortedSuits[i]) continue;
let num=1;
if(idx>2||sortedSuits[i]<3) num=sortedSuits[i];
cache[i]=num;
dis+=num;
suits[i]-=num;
dsuits++;
}
for(let i in suits){
if(suits[i]) leave++;
}
player.getCards('e',i=>{
let suit=get.suit(i);
if(!cache[suit]){
dsuits++;
cache[suit]=1;
dis++;
}
});
let draw=0,e=[0,1,4/3,2,4];
if(dsuits<=leave) return false;
do{
draw+=e[dsuits--];
}while(dsuits>leave);
if(draw>dis){
delete cache.no;
_status.event.putTempCache('dccaizhuang','dsuits',cache);
return cache;
}
return false;
}, },
content:function(){ content:function(){
'step 0' 'step 0'
var suits=[]; var suits=[];
cards.forEach(i=>{
if(suits.length>=4) return;
let suit=get.suit(i,player);
if(lib.suit.includes(suit)) suits.add(suit);
});
event.num=suits.length;
'step 1'
var suits=[];
player.countCards('h',card=>{ player.countCards('h',card=>{
if(suits.length>=4) return; if(suits.length>=4) return;
var suit=get.suit(card); var suit=get.suit(card);
if(!lib.suit.includes(suit)) return; if(lib.suit.includes(suit)) suits.add(suit);
suits.add(suit);
}); });
if(suits.length>=cards.length) event.finish(); if(suits.length>=event.num) event.finish();
'step 1' 'step 2'
player.draw(); player.draw();
event.goto(0); event.goto(1);
}, },
ai:{ ai:{
order:2, order:2,
@ -9427,11 +9487,20 @@ game.import('character',function(lib,game,ui,get,ai,_status){
return true; return true;
}); });
next.set('processAI',function(list){ next.set('processAI',function(list){
var cards=list[0][1].slice(0).sort(function(a,b){ let cards=list[0][1].slice(0),player=_status.event.player;
if(b.name=='sha') return 1; cards.sort((a,b)=>{
return get.value(b)-get.value(a); return get.value(b,player)-get.value(a,player);
}); });
return [cards,cards.splice(0,_status.event.player.getDamagedHp())]; if(!player.storage.juetao&&player.hasSkill('juetao')&&player.hasSha()){
let gain,bottom,pai=cards.filter(card=>card.name!=='sha');
pai.sort((a,b)=>{
return get.value(b,player)-get.value(a,player);
});
gain=pai.splice(0,player.getDamagedHp());
bottom=pai;
return [bottom, gain];
}
return [cards,cards.splice(0,player.getDamagedHp())];
}); });
'step 1' 'step 1'
game.broadcastAll('closeDialog',event.videoId); game.broadcastAll('closeDialog',event.videoId);
@ -14006,7 +14075,7 @@ game.import('character',function(lib,game,ui,get,ai,_status){
dcjijiao_info:'限定技。出牌阶段,你可以令一名角色获得所有弃牌堆中你于本局游戏内使用或弃置过的普通锦囊牌,且这些牌不能被【无懈可击】响应。一名角色的回合结束后,若本回合牌堆洗过牌或有角色死亡,你重置〖继椒〗。', dcjijiao_info:'限定技。出牌阶段,你可以令一名角色获得所有弃牌堆中你于本局游戏内使用或弃置过的普通锦囊牌,且这些牌不能被【无懈可击】响应。一名角色的回合结束后,若本回合牌堆洗过牌或有角色死亡,你重置〖继椒〗。',
duanqiaoxiao:'段巧笑', duanqiaoxiao:'段巧笑',
dccaizhuang:'彩妆', dccaizhuang:'彩妆',
dccaizhuang_info:'出牌阶段限一次,你可以弃置任意张牌。然后若你手牌中的花色数小于你以此法弃置的牌数,你摸一张牌并重复此流程。', dccaizhuang_info:'出牌阶段限一次,你可以弃置任意张牌。然后若你手牌中的花色数小于你以此法弃置的牌的花色数,你摸一张牌并重复此流程。',
dchuayi:'华衣', dchuayi:'华衣',
dchuayi_info:'结束阶段,你可以判定,然后你获得如下效果直到你下回合开始时:红色,一名角色的回合结束时,你摸一张牌;黑色,当你受到伤害后,你摸两张牌。', dchuayi_info:'结束阶段,你可以判定,然后你获得如下效果直到你下回合开始时:红色,一名角色的回合结束时,你摸一张牌;黑色,当你受到伤害后,你摸两张牌。',
wu_zhugeliang:'武诸葛亮', wu_zhugeliang:'武诸葛亮',

View File

@ -8353,10 +8353,6 @@ export class Player extends HTMLDivElement {
return false; return false;
} }
hasSkillTag(tag, hidden, arg, globalskill) { hasSkillTag(tag, hidden, arg, globalskill) {
let cache = CacheContext.getCacheContext();
if(!cache){
cache = new CacheContext();
}
var skills = this.getSkills(hidden); var skills = this.getSkills(hidden);
if (globalskill) { if (globalskill) {
skills.addArray(lib.skill.global); skills.addArray(lib.skill.global);
@ -8366,7 +8362,7 @@ export class Player extends HTMLDivElement {
var info = lib.skill[skills[i]]; var info = lib.skill[skills[i]];
if (info && info.ai) { if (info && info.ai) {
if (info.ai.skillTagFilter && info.ai[tag] && if (info.ai.skillTagFilter && info.ai[tag] &&
info.ai.skillTagFilter(cache.delegate(this), tag, arg) === false) continue; info.ai.skillTagFilter(this, tag, arg) === false) continue;
if (typeof info.ai[tag] == 'string') { if (typeof info.ai[tag] == 'string') {
if (info.ai[tag] == arg) return true; if (info.ai[tag] == arg) return true;
} }