@@ -11,6 +11,7 @@ import * as Utils from '../../tools/util.js';
11
11
12
12
import logger from '../../tools/logger.js' ;
13
13
import { logClue } from '../../tools/log.js' ;
14
+ import { ActualCard } from '../../basics/Card.js' ;
14
15
15
16
/**
16
17
* @typedef {import('../h-group.js').default } Game
@@ -187,8 +188,9 @@ export function early_game_clue(game, playerIndex) {
187
188
* @param {FixClue[][] } fix_clues
188
189
* @param {Clue[][] } stall_clues
189
190
* @param {Card[][] } playable_priorities
191
+ * @param {ActualCard } finessed_card
190
192
*/
191
- export function find_urgent_actions ( game , play_clues , save_clues , fix_clues , stall_clues , playable_priorities ) {
193
+ export function find_urgent_actions ( game , play_clues , save_clues , fix_clues , stall_clues , playable_priorities , finessed_card ) {
192
194
const { common, me, state, tableID } = game ;
193
195
const prioritySize = Object . keys ( PRIORITY ) . length ;
194
196
const urgent_actions = /** @type {PerformAction[][] } */ ( Array . from ( { length : prioritySize * 2 + 1 } , _ => [ ] ) ) ;
@@ -216,19 +218,19 @@ export function find_urgent_actions(game, play_clues, save_clues, fix_clues, sta
216
218
// They are locked, we should try to unlock
217
219
if ( common . thinksLocked ( state , target ) ) {
218
220
const unlock_order = find_unlock ( game , target ) ;
219
- if ( unlock_order !== undefined ) {
221
+ if ( unlock_order !== undefined && ( ! finessed_card || finessed_card . order == unlock_order ) ) {
220
222
urgent_actions [ PRIORITY . UNLOCK + nextPriority ] . push ( { tableID, type : ACTION . PLAY , target : unlock_order } ) ;
221
223
continue ;
222
224
}
223
225
224
226
const play_over_save = find_play_over_save ( game , target , play_clues . flat ( ) ) ;
225
- if ( play_over_save !== undefined ) {
227
+ if ( ! finessed_card && play_over_save !== undefined ) {
226
228
urgent_actions [ PRIORITY . PLAY_OVER_SAVE + nextPriority ] . push ( play_over_save ) ;
227
229
continue ;
228
230
}
229
231
230
232
const trash_fixes = fix_clues [ target ] . filter ( clue => clue . trash ) ;
231
- if ( trash_fixes . length > 0 ) {
233
+ if ( ! finessed_card && trash_fixes . length > 0 ) {
232
234
const trash_fix = Utils . maxOn ( trash_fixes , ( { result } ) => find_clue_value ( result ) ) ;
233
235
urgent_actions [ PRIORITY . TRASH_FIX + nextPriority ] . push ( Utils . clueToAction ( trash_fix , tableID ) ) ;
234
236
continue ;
@@ -254,7 +256,7 @@ export function find_urgent_actions(game, play_clues, save_clues, fix_clues, sta
254
256
// Try to see if they have a playable card that connects directly through our hand
255
257
// Although this is only optimal for the next player, it is often a "good enough" action for future players.
256
258
const unlock_order = find_unlock ( game , target ) ;
257
- if ( unlock_order !== undefined ) {
259
+ if ( unlock_order !== undefined && ( ! finessed_card || finessed_card . order == unlock_order ) ) {
258
260
urgent_actions [ PRIORITY . UNLOCK + nextPriority ] . push ( { tableID, type : ACTION . PLAY , target : unlock_order } ) ;
259
261
continue ;
260
262
}
@@ -263,14 +265,14 @@ export function find_urgent_actions(game, play_clues, save_clues, fix_clues, sta
263
265
264
266
// Give them a fix clue with known trash if possible (TODO: Re-examine if this should only be urgent fixes)
265
267
const trash_fixes = fix_clues [ target ] . filter ( clue => clue . trash ) ;
266
- if ( trash_fixes . length > 0 ) {
268
+ if ( ! finessed_card && trash_fixes . length > 0 ) {
267
269
const trash_fix = Utils . maxOn ( trash_fixes , ( { result } ) => find_clue_value ( result ) ) ;
268
270
urgent_actions [ PRIORITY . TRASH_FIX + nextPriority ] . push ( Utils . clueToAction ( trash_fix , tableID ) ) ;
269
271
continue ;
270
272
}
271
273
272
274
// Check if Order Chop Move is available - 4 (unknown card) must be highest priority, they must be 1s, and this cannot be a playable save
273
- if ( game . level >= LEVEL . BASIC_CM &&
275
+ if ( ! finessed_card && game . level >= LEVEL . BASIC_CM &&
274
276
playable_priorities . every ( ( cards , priority ) => priority >= 4 || cards . length === 0 ) &&
275
277
! save . playable
276
278
) {
@@ -301,7 +303,7 @@ export function find_urgent_actions(game, play_clues, save_clues, fix_clues, sta
301
303
}
302
304
303
305
// Check if Scream/Shout Discard is available (only to next player)
304
- if ( game . level >= LEVEL . LAST_RESORTS && playable_priorities . some ( p => p . length > 0 ) && target === state . nextPlayerIndex ( state . ourPlayerIndex ) ) {
306
+ if ( ! finessed_card && game . level >= LEVEL . LAST_RESORTS && playable_priorities . some ( p => p . length > 0 ) && target === state . nextPlayerIndex ( state . ourPlayerIndex ) ) {
305
307
const trash = me . thinksTrash ( state , state . ourPlayerIndex ) . filter ( c => c . clued && me . thoughts [ c . order ] . inferred . every ( i => state . isBasicTrash ( i ) ) ) ;
306
308
307
309
if ( trash . length > 0 ) {
@@ -371,7 +373,7 @@ export function find_urgent_actions(game, play_clues, save_clues, fix_clues, sta
371
373
}
372
374
373
375
// They require a fix clue
374
- if ( fix_clues [ target ] . length > 0 ) {
376
+ if ( ! finessed_card && fix_clues [ target ] . length > 0 ) {
375
377
const urgent_fixes = fix_clues [ target ] . filter ( clue => clue . urgent ) ;
376
378
377
379
// Urgent fix on the next player is particularly urgent, but we should prioritize urgent fixes for others too
0 commit comments