Support Moritani assassination of captured and foreign-ghola targets
Retain printed native identity and valid original custody while projecting only uniform potential bounty before commitment. Resolve living/dead targets once, clear selected capture/concealment and retain ordinary Ghola return custody. Selected concealed-outcome disclosure is explicitly provisional. Verified: 14 affected offline files100/100, types/lint and production build; six actual choice/gameplay/GameTable SSR journeys and twelve profile paths. Native capture source47 actions; actual paid Ghola prefix140 actions followed by explicit conserved seven-action battle. No saved-room/D1/reset/restart or deployment operation. Runtime-only driver fixes reused unchanged passed checks.
This commit is contained in:
1 parent
61828150b9
commit
eff668b202
25 files changed
+1041
-57
No files matched your search
+12
-5
@@ -62,7 +62,7 @@ import { captureFremenCunningOccurrence, quoteFremenCunning, quoteFremenCunningR
|
||||
import { fremenNexusModeSupported } from './fremen-nexus-profile';
|
||||
import { createNexusFremenProtection, currentNexusFremenProtectionOwner, answerNexusFremenProtection, validateNexusFremenProtection, type NexusFremenProtectionFrame, type NexusFremenProtectionInput } from './nexus-fremen-protection';
|
||||
import { truthKnowledgeOf } from './truthtrance-knowledge';
|
||||
import { createMoritaniAssassinateOpportunity, moritaniAssassinateTrigger, moritaniAssassinateChoices, quoteMoritaniAssassinate, moritaniAssassinateSignature, validateMoritaniAssassinate, type MoritaniAssassinateState, type MoritaniAssassinateReceipt } from './moritani-assassinate';
|
||||
import { createMoritaniAssassinateOpportunity, moritaniAssassinateTrigger, projectedMoritaniAssassinateChoices, quoteMoritaniAssassinate, moritaniAssassinateSignature, validateMoritaniAssassinate, type MoritaniAssassinateState, type MoritaniAssassinateReceipt } from './moritani-assassinate';
|
||||
import { moritaniTerrorAssassinationPool, moritaniTerrorAssassinationValue } from './moritani-terror-assassination';
|
||||
import { createNexusGuildSecretAlly, validateNexusGuildSecretAlly, quoteNexusGuildSecretShipment, type NexusGuildSecretAllyReceipt } from './nexus-guild-secret-ally';
|
||||
import { shipmentAvailable } from './shipment-opportunity';
|
||||
@@ -8845,7 +8845,7 @@ function moritaniAssassinateModeSupported(g: Game) {
|
||||
function moritaniAssassinateContext(g: Game, receipt: MoritaniAssassinateReceipt) {
|
||||
const p = getPlayer(g,receipt.owner), opponent = getPlayer(g,receipt.opponent);
|
||||
return {state:g.moritaniAssassinate!,receipt,held:p.traitors,
|
||||
normallyRevealed:p.revealedTraitors ?? [],leaders:opponent.leaders};
|
||||
normallyRevealed:p.revealedTraitors ?? [],leaders:opponent.leaders,custodians:g.players};
|
||||
}
|
||||
function moritaniAssassinateIntegrity(g: Game) {
|
||||
const state = g.moritaniAssassinate, resume = g.moritaniAssassinateResume;
|
||||
@@ -8945,7 +8945,7 @@ function projectedMoritaniAssassinate(g: Game, viewer: string) {
|
||||
if (!state) return null;
|
||||
const pending = state.opportunities.find(r => r.stage === 'choice');
|
||||
const own = viewer === state.owner;
|
||||
const choices = pending && own ? nexusRule(() => moritaniAssassinateChoices(moritaniAssassinateContext(g,pending))) : null;
|
||||
const choices = pending && own ? nexusRule(() => projectedMoritaniAssassinateChoices(moritaniAssassinateContext(g,pending))) : null;
|
||||
return {owner:state.owner,blocked:own && state.normalTraitorCall
|
||||
? 'Moritani forfeited Assassinate Leaders for the rest of this game after revealing its Traitor Card normally.' : null,
|
||||
pending:pending ? {event:pending.event,opponent:pending.opponent,territory:pending.territory,
|
||||
@@ -8973,9 +8973,16 @@ function actMoritaniAssassinate(g: Game, decision: Extract<Decision,{kind:'morit
|
||||
target.dead = true;
|
||||
target.deaths++;
|
||||
delete target.usedAt;
|
||||
if (getPlayer(g, r.opponent).faction === 'harkonnen') returnCaptives(g, getPlayer(g, r.opponent));
|
||||
finishLeaderSkillCustody(g);
|
||||
}
|
||||
// The selected public reveal settles this original disc even if a hidden
|
||||
// execution already killed it. Ordinary foreign-ghola return custody stays.
|
||||
delete target.capturedBy;
|
||||
delete target.concealed;
|
||||
if (quote.kill) {
|
||||
const harkonnen = byFaction(g, 'harkonnen');
|
||||
if (harkonnen) returnCaptives(g, harkonnen);
|
||||
}
|
||||
finishLeaderSkillCustody(g);
|
||||
const owner = getPlayer(g,r.owner);
|
||||
requireRule(Number.isSafeInteger(owner.spice + quote.bounty), 'Assassination income exceeds the supported spice balance.');
|
||||
owner.spice += quote.bounty;
|
||||
|
||||
Reference in new issue
Block a user