pp/CLAUDE.md
2026-06-17 16:45:21 +03:00

89 lines
4.0 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
## Project Purpose
Poker analysis tool for GGPoker using a Logitech StreamCam pointed at a 2560×1440 monitor. Captures the game via webcam, reads cards via OCR and color detection, calculates equity via Monte Carlo simulation.
## Running the Scripts
```bash
# Live camera viewer with settings panel (trackbars)
python3 main.py
# Poker analyzer — board OCR + Monte Carlo equity
python3 analyzer.py # auto OCR hero cards
python3 analyzer.py Qd Qc # manually specify hero cards (rank+suit)
# Webcam scraper using dickreuter_poker backend
python3 webcam_scraper.py
```
## Architecture
```
main.py — Camera viewer with OpenCV trackbars. Loads/saves settings.json.
analyzer.py — Main analysis pipeline: webcam → crop → OCR → Monte Carlo → advice.
webcam_scraper.py — Adapter connecting webcam to dickreuter_poker TableScraper.
virtualbox/ — Stub module: dickreuter_poker imports virtualbox which isn't needed.
files/ — Card sprite sheet (table_card.png + card.json) for future template matching.
settings.json — Persisted camera settings (auto-tuned, do not edit manually).
tmp/ — All temporary files, snapshots, debug images go here.
```
### External dependency: dickreuter_poker
Located at `/home/isaevea/python/dickreuter_poker`. Added to `sys.path` at runtime.
- `poker.decisionmaker.montecarlo_numpy2.Evaluation` — Monte Carlo equity calculator (CPU/numpy, no GPU).
- `poker.scraper.table_scraper.TableScraper` — Table state scraper (card templates from `https://dickreuter.com:7778/`).
- `poker.tools.mongo_manager.MongoManager` — Fetches GGPoker table config from remote API. Table name: `"Official GGPoker 6player"`.
GUI modules of dickreuter_poker (PyQt6) are stubbed out in `webcam_scraper.py` via `sys.modules` injection.
## Camera Hardware
- **Device**: Logitech StreamCam → `/dev/video2` (index 2). `/dev/video0` is UVC Camera.
- **Optimal settings** (auto-tuned, saved in `settings.json`): focus=60 (manual), sharpness=192, exposure=500 (manual).
- Qt font issue fix: Liberation Sans fonts copied to `.venv/lib/python3.12/site-packages/cv2/qt/fonts/`.
- Window titles must be ASCII-only — Cyrillic in `cv2.namedWindow()` causes NULL pointer crash. Trackbar labels support Cyrillic.
## Webcam Coordinate System
All coordinate constants in `analyzer.py` are in the **1280×720 webcam frame**:
```python
BOARD_AREA = (220, 370, 330, 640) # y1,y2,x1,x2 — entire flop/turn/river area
HERO_L_AREA = (438, 478, 472, 530) # left hole card
HERO_R_AREA = (438, 478, 530, 585) # right hole card
```
These are camera-position-dependent. If camera moves, recalibrate by running a snapshot and checking `tmp/` images.
In `webcam_scraper.py`, the GGPoker window boundary:
```python
TABLE_X1, TABLE_Y1 = 15, 55
TABLE_X2, TABLE_Y2 = 760, 685
```
This crops the GGPoker client from the webcam frame and scales to 1500×1100 (dickreuter's `CROP_WIDTH × CROP_HEIGHT`).
## Card Detection
**Board cards** (`read_board_cards`): BOARD_AREA is divided into 3 equal columns. Top-left corner of each is OCR'd via Tesseract (`tessedit_char_whitelist=23456789TJQKA`). Suit detected by mean red channel (>100 → hearts/diamonds, else spades).
**Hero cards** (`read_hero_cards`): Color-based suit detection in HSV space — blue hue → ♦, green → ♣, red → ♥, dark → ♠. GGPoker uses emoji-style colored card backgrounds.
**Tessdata path**: `/home/isaevea/python/dickreuter_poker/tessdata/`
## Monte Carlo Card Format
`montecarlo_numpy2.Evaluation.run_evaluation(card1, card2, tablecards, iterations, player_amount)`
Cards encoded as `[rank, suit]` where rank: 214 (A=14), suit: 0=clubs, 1=diamonds, 2=hearts, 3=spades.
```python
RANK_MAP = {'2':2,...,'T':10,'J':11,'Q':12,'K':13,'A':14}
SUIT_MAP = {'c':0,'d':1,'h':2,'s':3}
```
Returns float equity (0.01.0). Typical: >0.65 → raise, >0.45 → call, <0.25 fold.