clawtan 0.2.4 → 0.2.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/clawtan/cli.py +57 -12
- package/package.json +1 -1
package/clawtan/cli.py
CHANGED
|
@@ -391,7 +391,11 @@ def _print_opponents(opponents: list):
|
|
|
391
391
|
|
|
392
392
|
|
|
393
393
|
def _format_trade_tuple(val: list) -> str:
|
|
394
|
-
"""Decode
|
|
394
|
+
"""Decode trade resources (first 10 elements) into 'give X for Y' text.
|
|
395
|
+
|
|
396
|
+
Works for 10-element (OFFER_TRADE) and 11-element (current_trade,
|
|
397
|
+
ACCEPT/REJECT/CONFIRM) tuples — extra elements are ignored.
|
|
398
|
+
"""
|
|
395
399
|
giving = {RESOURCES[i]: val[i] for i in range(5) if val[i]}
|
|
396
400
|
wanting = {RESOURCES[i]: val[i + 5] for i in range(5) if val[i + 5]}
|
|
397
401
|
give_str = ", ".join(f"{n}x {r}" for r, n in giving.items()) or "nothing"
|
|
@@ -424,16 +428,20 @@ _ACTION_HINTS = {
|
|
|
424
428
|
" CLI: clawtan act OFFER_TRADE '[0,0,0,1,0,0,1,0,0,0]' # give 1 KELP, want 1 CORAL"
|
|
425
429
|
),
|
|
426
430
|
"ACCEPT_TRADE": (
|
|
427
|
-
"Accept a trade offer. Value =
|
|
428
|
-
"
|
|
431
|
+
"Accept a trade offer. Value = 11-element current_trade tuple\n"
|
|
432
|
+
" (10 resource ints + offerer's turn index, echoed from the offer).\n"
|
|
433
|
+
" Just use the value shown in your available actions.\n"
|
|
434
|
+
" CLI: clawtan act ACCEPT_TRADE '[0,0,0,1,0,0,1,0,0,0,0]'"
|
|
429
435
|
),
|
|
430
436
|
"REJECT_TRADE": (
|
|
431
|
-
"Reject a trade offer. Value =
|
|
432
|
-
"
|
|
437
|
+
"Reject a trade offer. Value = 11-element current_trade tuple\n"
|
|
438
|
+
" (10 resource ints + offerer's turn index, echoed from the offer).\n"
|
|
439
|
+
" Just use the value shown in your available actions.\n"
|
|
440
|
+
" CLI: clawtan act REJECT_TRADE '[0,0,0,1,0,0,1,0,0,0,0]'"
|
|
433
441
|
),
|
|
434
442
|
"CONFIRM_TRADE": (
|
|
435
443
|
"Confirm trade with a specific acceptee. Value = 11-element list:\n"
|
|
436
|
-
" the 10
|
|
444
|
+
" the 10 resource ints + the accepting player's color.\n"
|
|
437
445
|
" CLI: clawtan act CONFIRM_TRADE '[0,0,0,1,0,0,1,0,0,0,\"BLUE\"]'"
|
|
438
446
|
),
|
|
439
447
|
"CANCEL_TRADE": (
|
|
@@ -599,6 +607,37 @@ def _print_actions(actions: list, my_color: str | None = None, state: dict | Non
|
|
|
599
607
|
print(f"\n (other players still need to act: {', '.join(sorted(other_colors))})")
|
|
600
608
|
|
|
601
609
|
|
|
610
|
+
def _print_trade_context(state: dict, my_color: str):
|
|
611
|
+
"""Show the active trade offer and who has accepted so far."""
|
|
612
|
+
trade = state.get("current_trade")
|
|
613
|
+
if not trade or not isinstance(trade, list) or len(trade) < 10:
|
|
614
|
+
return
|
|
615
|
+
|
|
616
|
+
prompt = state.get("current_prompt", "")
|
|
617
|
+
colors = state.get("colors", [])
|
|
618
|
+
offerer_idx = trade[10] if len(trade) > 10 else None
|
|
619
|
+
offerer = colors[offerer_idx] if offerer_idx is not None and offerer_idx < len(colors) else "?"
|
|
620
|
+
|
|
621
|
+
_section("Active Trade")
|
|
622
|
+
print(f" Offered by: {offerer}")
|
|
623
|
+
print(f" Trade: {_format_trade_tuple(trade)}")
|
|
624
|
+
|
|
625
|
+
if prompt == "DECIDE_TRADE":
|
|
626
|
+
if offerer == my_color:
|
|
627
|
+
print(" Waiting for other players to accept or reject.")
|
|
628
|
+
else:
|
|
629
|
+
print(" You must ACCEPT_TRADE or REJECT_TRADE.")
|
|
630
|
+
elif prompt == "DECIDE_ACCEPTEES":
|
|
631
|
+
acceptees = state.get("acceptees", [])
|
|
632
|
+
accepted = [colors[i] for i, a in enumerate(acceptees) if a and i < len(colors)]
|
|
633
|
+
if accepted:
|
|
634
|
+
print(f" Accepted by: {', '.join(accepted)}")
|
|
635
|
+
else:
|
|
636
|
+
print(" No one accepted.")
|
|
637
|
+
if offerer == my_color:
|
|
638
|
+
print(" You may CONFIRM_TRADE with an acceptee or CANCEL_TRADE.")
|
|
639
|
+
|
|
640
|
+
|
|
602
641
|
def _unpack_record(r):
|
|
603
642
|
"""Unpack an action record into (color, action_type, value).
|
|
604
643
|
|
|
@@ -709,12 +748,12 @@ def _format_live_action(color, action, val, state=None, pre_resources=None):
|
|
|
709
748
|
return f" [{ts}] {color} offered a trade"
|
|
710
749
|
|
|
711
750
|
if action == "ACCEPT_TRADE":
|
|
712
|
-
if isinstance(val, list) and len(val)
|
|
751
|
+
if isinstance(val, list) and len(val) >= 10:
|
|
713
752
|
return f" [{ts}] {color} accepted trade: {_format_trade_tuple(val)}"
|
|
714
753
|
return f" [{ts}] {color} accepted a trade"
|
|
715
754
|
|
|
716
755
|
if action == "REJECT_TRADE":
|
|
717
|
-
if isinstance(val, list) and len(val)
|
|
756
|
+
if isinstance(val, list) and len(val) >= 10:
|
|
718
757
|
return f" [{ts}] {color} rejected trade: {_format_trade_tuple(val)}"
|
|
719
758
|
return f" [{ts}] {color} rejected a trade"
|
|
720
759
|
|
|
@@ -957,6 +996,9 @@ def cmd_wait(args):
|
|
|
957
996
|
except (APIError, Exception):
|
|
958
997
|
pass
|
|
959
998
|
|
|
999
|
+
if state.get("is_resolving_trade"):
|
|
1000
|
+
_print_trade_context(state, color)
|
|
1001
|
+
|
|
960
1002
|
actions = state.get("current_playable_actions", [])
|
|
961
1003
|
if actions:
|
|
962
1004
|
_print_actions(actions, my_color=color, state=state)
|
|
@@ -1106,14 +1148,17 @@ def cmd_act(args):
|
|
|
1106
1148
|
_section("Resources")
|
|
1107
1149
|
_print_resources(my["resources"])
|
|
1108
1150
|
|
|
1151
|
+
if state.get("is_resolving_trade"):
|
|
1152
|
+
_print_trade_context(state, color)
|
|
1153
|
+
|
|
1109
1154
|
if my_actions:
|
|
1110
1155
|
_print_actions(actions, my_color=color, state=state)
|
|
1111
1156
|
else:
|
|
1112
1157
|
print("\n No actions available.")
|
|
1113
1158
|
elif my_actions:
|
|
1114
|
-
# We have actions even though current_color is someone else
|
|
1115
|
-
# (e.g. we also need to discard on a 7)
|
|
1116
1159
|
print(f" Prompt: {prompt}")
|
|
1160
|
+
if state.get("is_resolving_trade"):
|
|
1161
|
+
_print_trade_context(state, color)
|
|
1117
1162
|
_print_actions(actions, my_color=color, state=state)
|
|
1118
1163
|
else:
|
|
1119
1164
|
print(f"\n Action done. No more actions available. Run 'clawtan wait' for your next turn or action required.")
|
|
@@ -1412,8 +1457,8 @@ def main():
|
|
|
1412
1457
|
" PLAY_CURRENT_BUILDING Road Building\n"
|
|
1413
1458
|
" OFFER_TRADE <val> Player trade: 10-element list [give5, want5]\n"
|
|
1414
1459
|
" e.g. '[0,0,0,1,0,0,1,0,0,0]' = give 1 KELP, want 1 CORAL\n"
|
|
1415
|
-
" ACCEPT_TRADE <val> Accept
|
|
1416
|
-
" REJECT_TRADE <val> Reject
|
|
1460
|
+
" ACCEPT_TRADE <val> Accept trade (echo the 11-element value from actions)\n"
|
|
1461
|
+
" REJECT_TRADE <val> Reject trade (echo the 11-element value from actions)\n"
|
|
1417
1462
|
" CONFIRM_TRADE <val> Confirm with acceptee: 10 ints + color, e.g.\n"
|
|
1418
1463
|
" '[0,0,0,1,0,0,1,0,0,0,\"BLUE\"]'\n"
|
|
1419
1464
|
" CANCEL_TRADE Cancel your pending trade offer\n"
|