ICRA/colorcalc/app.py

79 lines
2.1 KiB
Python

"""Application composition root."""
from __future__ import annotations
import tkinter as tk
from .color_picker import ColorPickerMixin
from .constants import DEFAULTS
from .exclusions import ExclusionMixin
from .image_processing import ImageProcessingMixin
from .reset import ResetMixin
from .theme import ThemeMixin
from .ui import UIBuilderMixin
class PurpleTunerApp(
ThemeMixin,
UIBuilderMixin,
ImageProcessingMixin,
ExclusionMixin,
ColorPickerMixin,
ResetMixin,
):
"""Tkinter based application for highlighting purple hues in images."""
def __init__(self, root: tk.Tk):
self.root = root
self.root.title("Purple Tuner — Bild + Overlay")
try:
self.root.state("zoomed")
except Exception:
pass
self.root.configure(bg="#f2f2f7")
# Theme and styling
self.init_theme()
# Tkinter state variables
self.DEFAULTS = DEFAULTS.copy()
self.hue_min = tk.DoubleVar(value=self.DEFAULTS["hue_min"])
self.hue_max = tk.DoubleVar(value=self.DEFAULTS["hue_max"])
self.sat_min = tk.DoubleVar(value=self.DEFAULTS["sat_min"])
self.val_min = tk.DoubleVar(value=self.DEFAULTS["val_min"])
self.val_max = tk.DoubleVar(value=self.DEFAULTS["val_max"])
self.alpha = tk.IntVar(value=self.DEFAULTS["alpha"])
self.ref_hue = None
# Debounce for heavy preview updates
self.update_delay_ms = 400
self._update_job = None
# Exclusion rectangles (preview coordinates)
self.exclude_rects: list[tuple[int, int, int, int]] = []
self._rubber_start = None
self._rubber_id = None
self.pick_mode = False
# Image references
self.image_path = None
self.orig_img = None
self.preview_img = None
self.preview_tk = None
self.overlay_tk = None
# Build UI
self.setup_ui()
self._init_copy_menu()
self.bring_to_front()
def start_app() -> None:
"""Entry point used by the CLI script."""
root = tk.Tk()
app = PurpleTunerApp(root)
root.mainloop()
__all__ = ["PurpleTunerApp", "start_app"]