mirror of
https://github.com/mwisnowski/mtg_python_deckbuilder.git
synced 2025-12-17 08:00:13 +01:00
Started remaking the builder module, Currently up through adding the standard/staple lands
This commit is contained in:
parent
a69a4c8384
commit
a8a181c4af
7 changed files with 1337 additions and 1742 deletions
File diff suppressed because it is too large
Load diff
|
|
@ -122,6 +122,23 @@ OTHER_COLOR_MAP: Final[Dict[str, Tuple[str, List[str], List[str]]]] = {
|
||||||
'bant', 'jeskai', 'glint', 'dune', 'witch', 'yore', 'ink', 'wubrg'])
|
'bant', 'jeskai', 'glint', 'dune', 'witch', 'yore', 'ink', 'wubrg'])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Card category validation rules
|
||||||
|
CREATURE_VALIDATION_RULES: Final[Dict[str, Dict[str, Union[str, int, float, bool]]]] = {
|
||||||
|
'power': {'type': ('str', 'int', 'float'), 'required': True},
|
||||||
|
'toughness': {'type': ('str', 'int', 'float'), 'required': True},
|
||||||
|
'creatureTypes': {'type': 'list', 'required': True}
|
||||||
|
}
|
||||||
|
|
||||||
|
SPELL_VALIDATION_RULES: Final[Dict[str, Dict[str, Union[str, int, float, bool]]]] = {
|
||||||
|
'manaCost': {'type': 'str', 'required': True},
|
||||||
|
'text': {'type': 'str', 'required': True}
|
||||||
|
}
|
||||||
|
|
||||||
|
LAND_VALIDATION_RULES: Final[Dict[str, Dict[str, Union[str, int, float, bool]]]] = {
|
||||||
|
'type': {'type': ('str', 'object'), 'required': True},
|
||||||
|
'text': {'type': ('str', 'object'), 'required': False}
|
||||||
|
}
|
||||||
|
|
||||||
# Price checking configuration
|
# Price checking configuration
|
||||||
DEFAULT_PRICE_DELAY: Final[float] = 0.1 # Delay between price checks in seconds
|
DEFAULT_PRICE_DELAY: Final[float] = 0.1 # Delay between price checks in seconds
|
||||||
MAX_PRICE_CHECK_ATTEMPTS: Final[int] = 3 # Maximum attempts for price checking
|
MAX_PRICE_CHECK_ATTEMPTS: Final[int] = 3 # Maximum attempts for price checking
|
||||||
|
|
@ -435,3 +452,20 @@ CARD_TYPE_SORT_ORDER: Final[List[str]] = [
|
||||||
'Planeswalker', 'Battle', 'Creature', 'Instant', 'Sorcery',
|
'Planeswalker', 'Battle', 'Creature', 'Instant', 'Sorcery',
|
||||||
'Artifact', 'Enchantment', 'Land'
|
'Artifact', 'Enchantment', 'Land'
|
||||||
]
|
]
|
||||||
|
|
||||||
|
# Game changer cards, used to help determine bracket
|
||||||
|
GAME_CHANGERS: Final[List[str]] = [
|
||||||
|
'Ad Nauseum', 'Ancient Tomb', 'Aura Shards', 'Bolas\'s Citadel', 'Braids, Cabal Minion',
|
||||||
|
'Chrome Mox', 'Coalition Victory', 'Consecrated Sphinx', 'Crop Rotation', 'Cyclonic Rift',
|
||||||
|
'Deflecting Swat', 'Demonic Tutor', 'Drannith Magistrate', 'Enlightened Tutor', 'Expropriate',
|
||||||
|
'Field of the Dead', 'Fierce Guardianship', 'Food Chain', 'Force of Will', 'Gaea\'s Cradle',
|
||||||
|
'Gamble', 'Gifts Ungiven', 'Glacial Chasm', 'Grand Arbiter Augustin IV', 'Grim Monolith', 'Humility',
|
||||||
|
'Imperial Seal', 'Intuition', 'Jeska\'s Will', 'Jin-Gitaxias, Core Augur', 'Kinnan, Bonder Prodigy',
|
||||||
|
'Lion\'s Eye Diamond', 'Mana Vault', 'Mishra\'s Workshop', 'Mox Diamond', 'Mystical Tutor',
|
||||||
|
'Narset, Parter of Veils', 'Natural Order', 'Necropotence', 'Notion Thief', 'Opposition Agent',
|
||||||
|
'Orcish Bowmasters', 'Panoptic Mirror', 'Rhystic Study', 'Seedborn Muse', 'Serra\'s Sanctum',
|
||||||
|
'Smother Tithe', 'Survival of the Fittest', 'Sway of the Stars', 'Teferi\'s Protection',
|
||||||
|
'Tergrid, God of Fright', 'Thassa\'s Oracle', 'The One Ring', 'The Tabernacle at Pendrell Vale',
|
||||||
|
'Underworld Breach', 'Urza, Lord High Artificer', 'Vampiric Tutor', 'Vorinclex, Voice of Hunger',
|
||||||
|
'Winota, Joiner of Forces', 'Worldly Tutor', 'Yuriko, the Tiger\'s Shadow'
|
||||||
|
]
|
||||||
File diff suppressed because it is too large
Load diff
|
|
@ -17,18 +17,18 @@ __all__ = [
|
||||||
BANNED_CARDS: List[str] = [
|
BANNED_CARDS: List[str] = [
|
||||||
# Commander banned list
|
# Commander banned list
|
||||||
'Ancestral Recall', 'Balance', 'Biorhythm', 'Black Lotus',
|
'Ancestral Recall', 'Balance', 'Biorhythm', 'Black Lotus',
|
||||||
'Braids, Cabal Minion', 'Chaos Orb', 'Coalition Victory',
|
'Chaos Orb', 'Channel', 'Dockside Extortionist',
|
||||||
'Channel', 'Dockside Extortionist', 'Emrakul, the Aeons Torn',
|
'Emrakul, the Aeons Torn',
|
||||||
'Erayo, Soratami Ascendant', 'Falling Star', 'Fastbond',
|
'Erayo, Soratami Ascendant', 'Falling Star', 'Fastbond',
|
||||||
'Flash', 'Gifts Ungiven', 'Golos, Tireless Pilgrim',
|
'Flash', 'Golos, Tireless Pilgrim',
|
||||||
'Griselbrand', 'Hullbreacher', 'Iona, Shield of Emeria',
|
'Griselbrand', 'Hullbreacher', 'Iona, Shield of Emeria',
|
||||||
'Karakas', 'Jeweled Lotus', 'Leovold, Emissary of Trest',
|
'Karakas', 'Jeweled Lotus', 'Leovold, Emissary of Trest',
|
||||||
'Library of Alexandria', 'Limited Resources', 'Lutri, the Spellchaser',
|
'Library of Alexandria', 'Limited Resources', 'Lutri, the Spellchaser',
|
||||||
'Mana Crypt', 'Mox Emerald', 'Mox Jet', 'Mox Pearl', 'Mox Ruby',
|
'Mana Crypt', 'Mox Emerald', 'Mox Jet', 'Mox Pearl', 'Mox Ruby',
|
||||||
'Mox Sapphire', 'Nadu, Winged Wisdom', 'Panoptic Mirror',
|
'Mox Sapphire', 'Nadu, Winged Wisdom',
|
||||||
'Paradox Engine', 'Primeval Titan', 'Prophet of Kruphix',
|
'Paradox Engine', 'Primeval Titan', 'Prophet of Kruphix',
|
||||||
'Recurring Nightmare', 'Rofellos, Llanowar Emissary', 'Shahrazad',
|
'Recurring Nightmare', 'Rofellos, Llanowar Emissary', 'Shahrazad',
|
||||||
'Sundering Titan', 'Sway of the Stars', 'Sylvan Primordial',
|
'Sundering Titan', 'Sylvan Primordial',
|
||||||
'Time Vault', 'Time Walk', 'Tinker', 'Tolarian Academy',
|
'Time Vault', 'Time Walk', 'Tinker', 'Tolarian Academy',
|
||||||
'Trade Secrets', 'Upheaval', "Yawgmoth's Bargain",
|
'Trade Secrets', 'Upheaval', "Yawgmoth's Bargain",
|
||||||
# Problematic / culturally sensitive or banned in other formats
|
# Problematic / culturally sensitive or banned in other formats
|
||||||
|
|
|
||||||
39
code/non_interactive_test.py
Normal file
39
code/non_interactive_test.py
Normal file
|
|
@ -0,0 +1,39 @@
|
||||||
|
from deck_builder.builder import DeckBuilder
|
||||||
|
|
||||||
|
# Non-interactive harness: chooses specified commander, first tag, first bracket, accepts defaults
|
||||||
|
|
||||||
|
def run(command_name: str = "Finneas, Ace Archer"):
|
||||||
|
scripted_inputs = []
|
||||||
|
# Commander query
|
||||||
|
scripted_inputs.append(command_name) # initial query
|
||||||
|
# After showing matches, choose first candidate (index 1)
|
||||||
|
scripted_inputs.append("1") # select first candidate to inspect
|
||||||
|
scripted_inputs.append("y") # confirm commander
|
||||||
|
# Tag selection: choose eleventh tag as primary
|
||||||
|
scripted_inputs.append("11")
|
||||||
|
# Stop after primary (secondary prompt enters 1)
|
||||||
|
scripted_inputs.append("1")
|
||||||
|
# Stop after primary (tertiary prompt enters 0)
|
||||||
|
scripted_inputs.append("0")
|
||||||
|
# Bracket selection: choose 3 (Typical Casual mid default) else 2 maybe; pick 3
|
||||||
|
scripted_inputs.append("3")
|
||||||
|
# Ideal counts prompts (8 prompts) -> press Enter (empty) to accept defaults
|
||||||
|
for _ in range(8):
|
||||||
|
scripted_inputs.append("")
|
||||||
|
|
||||||
|
def scripted_input(prompt: str) -> str:
|
||||||
|
if scripted_inputs:
|
||||||
|
return scripted_inputs.pop(0)
|
||||||
|
raise RuntimeError("Ran out of scripted inputs for prompt: " + prompt)
|
||||||
|
|
||||||
|
b = DeckBuilder(input_func=scripted_input)
|
||||||
|
b.run_initial_setup()
|
||||||
|
b.run_deck_build_step1()
|
||||||
|
b.run_deck_build_step2()
|
||||||
|
b.run_land_step1()
|
||||||
|
b.run_land_step2()
|
||||||
|
b.print_card_library()
|
||||||
|
return b
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
run()
|
||||||
|
|
@ -7,6 +7,7 @@ tqdm>=4.66.0
|
||||||
scrython>=1.10.0
|
scrython>=1.10.0
|
||||||
numpy>=1.24.0
|
numpy>=1.24.0
|
||||||
requests>=2.31.0
|
requests>=2.31.0
|
||||||
|
prettytable>=3.9.0
|
||||||
|
|
||||||
# Development dependencies
|
# Development dependencies
|
||||||
mypy>=1.3.0
|
mypy>=1.3.0
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue