Tuesday, June 9, 2026
Import .pgn, list by frequency, and allow for adjustments.
This python code with the help of ChatGPT should lay out further important changes.
You bring in tournament games, you rank them, and then you allow the user to re-order.
"""
chessopenings1.py
Personal Opening Catalog Manager
Requires:
pip install python-chess
"""
import chess.pgn
from collections import Counter
import json
import os
JSON_FILE = "personal_openings.json"
def load_personal_list():
if os.path.exists(JSON_FILE):
with open(JSON_FILE, "r", encoding="utf-8") as f:
return json.load(f)
return None
def save_personal_list(openings):
with open(JSON_FILE, "w", encoding="utf-8") as f:
json.dump(openings, f, indent=4)
def extract_openings(filename):
counter = Counter()
game_count = 0
try:
with open(filename, "r", encoding="utf-8", errors="ignore") as pgn:
while True:
game = chess.pgn.read_game(pgn)
if game is None:
break
game_count += 1
eco = game.headers.get("ECO", "").strip()
opening = game.headers.get("Opening", "").strip()
variation = game.headers.get("Variation", "").strip()
if not opening:
opening = "Unknown Opening"
if variation:
name = f"{eco} | {opening} | {variation}"
else:
name = f"{eco} | {opening}"
counter[name] += 1
except Exception as e:
print("\nERROR READING FILE")
print(e)
return []
print(f"\nGames read: {game_count}")
print(f"Unique openings found: {len(counter)}")
return [opening for opening, count in counter.most_common()]
def display_list(title, openings):
print(f"\n{title}")
print("=" * 80)
for i, opening in enumerate(openings, start=1):
print(f"{i:3} {opening}")
def first_run(personal):
while True:
display_list("INITIAL OPENING LIST", personal)
print("\nCommands")
print("--------")
print("2=1 Move item 2 to position 1")
print("6=3 Move item 6 to position 3")
print("s Save list")
cmd = input("\nCommand: ").strip().lower()
if cmd == "s":
save_personal_list(personal)
print(
f"\nCreated {JSON_FILE}"
f" with {len(personal)} openings."
)
return personal
if "=" not in cmd:
print("Invalid command.")
continue
try:
source, destination = cmd.split("=")
source = int(source)
destination = int(destination)
if source < 1 or source > len(personal):
print("Source out of range.")
continue
if destination < 1 or destination > len(personal):
print("Destination out of range.")
continue
item = personal.pop(source - 1)
personal.insert(destination - 1, item)
except ValueError:
print("Invalid command.")
def update_existing_list(personal, ranked_openings):
new_openings = [
opening
for opening in ranked_openings
if opening not in personal
]
if not new_openings:
print("\nNo new openings found.")
return personal
while True:
display_list("PERSONAL OPENING LIST", personal)
display_list("NEW OPENINGS", new_openings)
print("\nCommands")
print("--------")
print("1=3 Insert NEW opening #1 into PERSONAL position #3")
print("s Save and finish this PGN")
cmd = input("\nCommand: ").strip().lower()
if cmd == "s":
save_personal_list(personal)
print("\nChanges saved.")
return personal
if "=" not in cmd:
print("Invalid command.")
continue
try:
left, right = cmd.split("=")
new_number = int(left)
insert_position = int(right)
if new_number < 1 or new_number > len(new_openings):
print("Opening number out of range.")
continue
if insert_position < 1 or insert_position > len(personal) + 1:
print("Insert position out of range.")
continue
opening = new_openings.pop(new_number - 1)
personal.insert(insert_position - 1, opening)
print(f"\nInserted:")
print(opening)
print(f"at position {insert_position}")
save_personal_list(personal)
if not new_openings:
print("\nNo remaining new openings.")
return personal
except ValueError:
print("Invalid command format.")
def process_pgn(personal):
name = input(
"\nPGN filename (WITHOUT .pgn) or q to quit: "
).strip()
if name.lower() == "q":
return personal, False
filename = name + ".pgn"
if not os.path.exists(filename):
print(f"\nFile not found: {filename}")
return personal, True
ranked_openings = extract_openings(filename)
if not ranked_openings:
print("\nNo openings found.")
return personal, True
#
# FIRST RUN
#
if personal is None:
personal = ranked_openings.copy()
personal = first_run(personal)
return personal, True
#
# LATER RUNS
#
personal = update_existing_list(
personal,
ranked_openings
)
return personal, True
def main():
personal = load_personal_list()
if personal is None:
print("\nNo personal_openings.json found.")
print("The first PGN will create it.")
else:
print(
f"\nLoaded {len(personal)} openings "
f"from personal_openings.json"
)
while True:
personal, keep_running = process_pgn(personal)
if not keep_running:
break
print("\nFinished.")
if __name__ == "__main__":
main()
Subscribe to:
Post Comments (Atom)
-
**See 6/22 post for adjustments.** Code can be tested at https://www.programiz.com/python-programming/online-compiler/ (Remove the 3 lines ...
-
The code below starts the bidding process. It's possible now to add graphics, that might be next as well as continuing with picking up. ...
No comments:
Post a Comment