Expand Basic Richese and Terror interactions
Verify and publish checkpoint container / container (push) Successful in 11m25s

This commit is contained in:
Quintine committed 2026-10-29 09:59:45 +11:00
1 parent 605cb2a32f
commit 9ab9b9a613
10 files changed
+426 -9

No files matched your search

+21 -6
View File
@@ -2017,6 +2017,7 @@ export type Game = {
owner: string;
entry: NonNullable<Game['pendingTerrorEntry']>;
discardedHandSize: number;
wormCursor?: string;
}
| {
kind: 'terrorAtomics';
@@ -9627,7 +9628,7 @@ function supportedRicheseTruthLot(g: Game): boolean {
!g.currentAuctionSale && !g.auction && !g.ixAuction;
}
/** Bind a parked native ride to its original remaining Spice Blow sequence. */
function ambassadorWormDiscardCursor(g: Game): string {
function wormDiscardCursor(g: Game): string {
return JSON.stringify([g.turn, g.phase, g.wormRides, g.spiceSequence,
g.spiceResolution, g.nexus, g.summonedNexusBeforeRides, g.greatMaker]);
}
@@ -9734,7 +9735,7 @@ function semutaOfferSupported(
ambassadorTerrorEntryMatches(g, continuation.entry);
const ambassadorWormDiscard = ambassadorDiscard && continuation.entry.resume === 'wormRide' &&
continuation.entry.arrivalCause === 'wormRide' && g.phase === 1 &&
!!continuation.wormCursor && continuation.wormCursor === ambassadorWormDiscardCursor(g) &&
!!continuation.wormCursor && continuation.wormCursor === wormDiscardCursor(g) &&
validAmbassadorResume(g, continuation.entry) && !g.pendingArrivalOverlap &&
(!g.pendingTreacheryDiscard || !!g.pendingTreacheryDiscard.reaction);
if (ambassadorDiscard &&
@@ -9879,14 +9880,22 @@ function semutaOfferSupported(
(continuation.kind === 'battleResolved' && !bareBasicSemutaProfile(g) &&
!basicIndependentRecruitsSemutaProfile(g)))) ||
g.pendingIxSubstitution)) return false;
const terrorWormDiscard = continuation.kind === 'terrorDiscard' &&
(bareBasicSemutaProfile(g) || basicIndependentRecruitsSemutaProfile(g)) &&
continuation.entry.cause === 'wormRide' && continuation.entry.resume === 'wormRide' &&
continuation.entry.turn === g.turn && continuation.entry.phase === 1 && g.phase === 1 &&
g.players.some(player => player.id === continuation.entry.entrant && player.faction === 'fremen') &&
!!continuation.wormCursor && continuation.wormCursor === wormDiscardCursor(g) &&
!g.pendingArrivalOverlap && !g.pendingAmbassador && !g.pendingArrivalReaction?.length &&
(!g.pendingTreacheryDiscard || !!g.pendingTreacheryDiscard.reaction);
if (continuation.kind === 'terrorDiscard' &&
(!childTerrorDiscard && (continuation.entry.resume !== 'none' ||
(!childTerrorDiscard && !terrorWormDiscard && (continuation.entry.resume !== 'none' ||
(continuation.entry.cause !== 'shipment' && continuation.entry.cause !== 'movement') ||
(g.pendingArrivalOverlap && (!bareBasicSemutaProfile(g) ||
!overlapOwnsTerrorDiscard(g, continuation.entry, continuation.owner)))) ||
g.pendingChoamMove || g.pendingIxMove ||
g.pendingFremenMove || g.ornithopter || g.summonedWorm ||
g.wormRides.length > 0)) return false;
!terrorWormDiscard && g.wormRides.length > 0)) return false;
if (continuation.kind === 'terrorAtomics' &&
(g.advanced || g.phase !== 5 || continuation.entry.resume !== 'none' ||
!['shipment', 'movement'].includes(continuation.entry.cause) ||
@@ -27439,7 +27448,7 @@ function decideAmbassador(g: Game, p: Player, action: Action) {
kind: 'ambassador',
entry,
...(entry.resume === 'wormRide' && entry.arrivalCause === 'wormRide'
? { wormCursor: ambassadorWormDiscardCursor(g) } : {}),
? { wormCursor: wormDiscardCursor(g) } : {}),
});
}
}
@@ -27854,6 +27863,8 @@ function decideTerror(g: Game, p: Player, action: Action) {
owner: owner.id,
entry,
discardedHandSize,
...(entry.cause === 'wormRide' && entry.resume === 'wormRide'
? { wormCursor: wormDiscardCursor(g) } : {}),
},
);
} else {
@@ -27878,7 +27889,9 @@ function decideTerror(g: Game, p: Player, action: Action) {
g.pendingTerrorEntry = null;
stageTreacheryDiscard(g, 'terror:sabotageGiftOverflow',
[{ card, discardedBy: p.id, publicFace: false }],
{ kind: 'terrorDiscard', source: 'sabotageGiftOverflow', owner: owner.id, entry, discardedHandSize });
{ kind: 'terrorDiscard', source: 'sabotageGiftOverflow', owner: owner.id, entry, discardedHandSize,
...(entry.cause === 'wormRide' && entry.resume === 'wormRide'
? { wormCursor: wormDiscardCursor(g) } : {}) });
return;
}
if (entry.stage === 'sneakAttack') {
@@ -28013,6 +28026,8 @@ function decideTerror(g: Game, p: Player, action: Action) {
owner: owner.id,
entry,
discardedHandSize,
...(entry.cause === 'wormRide' && entry.resume === 'wormRide'
? { wormCursor: wormDiscardCursor(g) } : {}),
},
);
} else {