change gui

This commit is contained in:
VALLONGOL 2025-04-09 15:47:53 +02:00
parent 862e72b867
commit 801f5f208c
3 changed files with 171 additions and 308 deletions

38
app.py
View File

@ -330,7 +330,7 @@ class App:
# Store the completed LUT back into AppState
self.state.mfd_lut = new_lut
logging.info(
logging.debug(
f"{log_prefix} MFD LUT update complete and stored in AppState."
)
@ -578,7 +578,7 @@ class App:
self.state.mfd_params["categories"][category_name][
"intensity"
] = intensity
logging.info(
logging.debug(
f"{log_prefix} Intensity for '{category_name}' set to {intensity} in AppState."
)
self.update_mfd_lut()
@ -2169,25 +2169,25 @@ class App:
if self.state.sar_fps > 0
else "SAR:N/A"
)
mouse_txt = "Mouse: N/A"
if (
hasattr(self.control_panel, "mouse_latlon_label")
and self.control_panel.mouse_latlon_label.winfo_exists()
):
try:
mouse_label_text = self.control_panel.mouse_latlon_label.cget(
"text"
)
mouse_txt = (
mouse_label_text
if mouse_label_text.startswith("Mouse")
else f"Mouse: {mouse_label_text}"
)
except Exception:
mouse_txt = "Mouse: UI Error"
#mouse_txt = "Mouse: N/A"
#if (
# hasattr(self.control_panel, "mouse_latlon_label")
# and self.control_panel.mouse_latlon_label.winfo_exists()
#):
# try:
# mouse_label_text = self.control_panel.mouse_latlon_label.cget(
# "text"
# )
# mouse_txt = (
# mouse_label_text
# if mouse_label_text.startswith("Mouse")
# else f"Mouse: {mouse_label_text}"
# )
# except Exception:
# mouse_txt = "Mouse: UI Error"
status_prefix = f"Status: {mode}{map_stat}"
status_info = f"{mfd_fps} | {sar_fps} | {mouse_txt}"
status_info = f"{mfd_fps} | {sar_fps}"
full_status = f"{status_prefix} | {status_info}"
# Format Statistics Strings

401
ui.py
View File

@ -33,7 +33,7 @@ class ControlPanel(ttk.Frame):
Initializes UI elements and provides methods for updating specific labels.
"""
def __init__(self, parent: tk.Widget, app: "App", *args, **kwargs):
def __init__(self, parent: tk.Widget, app: 'App', *args, **kwargs):
"""
Initializes the ControlPanel frame.
@ -51,19 +51,21 @@ class ControlPanel(ttk.Frame):
self.init_ui()
logging.debug(f"{log_prefix} ControlPanel frame initialization complete.")
def init_ui(self):
"""Initializes and arranges the user interface widgets within the frame.
Includes SAR, SAR Info, MFD, and Map Parameters frames."""
Order: SAR Params, MFD Params, Map Params, SAR Info.
Compacted MFD Params and rearranged SAR Info."""
log_prefix = "[UI Setup]"
logging.debug(f"{log_prefix} Starting init_ui widget creation...")
# Configure main frame packing
self.pack(side=tk.TOP, fill=tk.BOTH, expand=True, padx=5, pady=5)
# --- SAR Parameters Frame ---
# --- 1. SAR Parameters Frame ---
logging.debug(f"{log_prefix} Creating SAR Parameters frame...")
self.sar_params_frame = ttk.Labelframe(self, text="SAR Parameters", padding=5)
self.sar_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=(5, 2))
self.sar_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=(5, 2)) # PACK ORDER 1
sar_row = 0 # Row counter for SAR frame grid
# Test Image Checkbox
@ -74,256 +76,147 @@ class ControlPanel(ttk.Frame):
variable=self.test_image_var,
command=self.app.update_image_mode, # Callback in App
)
self.test_image_check.grid(
row=sar_row, column=0, columnspan=4, sticky=tk.W, padx=5, pady=2
)
self.test_image_check.grid(row=sar_row, column=0, columnspan=4, sticky=tk.W, padx=5, pady=2)
sar_row += 1 # -> 1
# Row 1: Size and Palette
self.sar_size_label = ttk.Label(self.sar_params_frame, text="Size:")
self.sar_size_label.grid(
row=sar_row, column=0, sticky=tk.W, padx=(5, 2), pady=1
)
self.sar_size_label.grid(row=sar_row, column=0, sticky=tk.W, padx=(5, 2), pady=1)
self.sar_size_combo = ttk.Combobox(
self.sar_params_frame,
values=config.SAR_SIZE_FACTORS,
state="readonly",
width=6,
self.sar_params_frame, values=config.SAR_SIZE_FACTORS, state="readonly", width=6
)
try: # Set initial SAR size from AppState
initial_factor = (
config.SAR_WIDTH // self.app.state.sar_display_width
if self.app.state.sar_display_width > 0
else 1
)
initial_factor = (config.SAR_WIDTH // self.app.state.sar_display_width if self.app.state.sar_display_width > 0 else 1)
initial_size_str = f"1:{initial_factor}"
if initial_size_str not in config.SAR_SIZE_FACTORS:
initial_size_str = config.DEFAULT_SAR_SIZE
if initial_size_str not in config.SAR_SIZE_FACTORS: initial_size_str = config.DEFAULT_SAR_SIZE
self.sar_size_combo.set(initial_size_str)
except Exception as e:
logging.warning(f"{log_prefix} Error setting initial SAR size: {e}")
self.sar_size_combo.set(config.DEFAULT_SAR_SIZE)
self.sar_size_combo.grid(
row=sar_row, column=1, sticky=tk.EW, padx=(0, 10), pady=1
)
self.sar_size_combo.bind(
"<<ComboboxSelected>>", self.app.update_sar_size
) # Callback in App
except Exception as e: logging.warning(f"{log_prefix} Error setting initial SAR size: {e}"); self.sar_size_combo.set(config.DEFAULT_SAR_SIZE)
self.sar_size_combo.grid(row=sar_row, column=1, sticky=tk.EW, padx=(0, 10), pady=1)
self.sar_size_combo.bind("<<ComboboxSelected>>", self.app.update_sar_size) # Callback in App
self.palette_label = ttk.Label(self.sar_params_frame, text="Palette:")
self.palette_label.grid(row=sar_row, column=2, sticky=tk.W, padx=(0, 2), pady=1)
self.palette_combo = ttk.Combobox(
self.sar_params_frame,
values=config.COLOR_PALETTES,
state="readonly",
width=8,
self.sar_params_frame, values=config.COLOR_PALETTES, state="readonly", width=8
)
self.palette_combo.set(
self.app.state.sar_palette
) # Initial value from AppState
self.palette_combo.grid(
row=sar_row, column=3, sticky=tk.EW, padx=(0, 5), pady=1
)
self.palette_combo.bind(
"<<ComboboxSelected>>", self.app.update_sar_palette
) # Callback in App
self.palette_combo.set(self.app.state.sar_palette) # Initial value from AppState
self.palette_combo.grid(row=sar_row, column=3, sticky=tk.EW, padx=(0, 5), pady=1)
self.palette_combo.bind("<<ComboboxSelected>>", self.app.update_sar_palette) # Callback in App
sar_row += 1 # -> 2
# Row 2: Contrast and Brightness
self.contrast_label = ttk.Label(self.sar_params_frame, text="Contrast:")
self.contrast_label.grid(
row=sar_row, column=0, sticky=tk.W, padx=(5, 2), pady=1
)
self.contrast_label.grid(row=sar_row, column=0, sticky=tk.W, padx=(5, 2), pady=1)
self.contrast_scale = ttk.Scale(
self.sar_params_frame,
orient=tk.HORIZONTAL,
from_=0.1,
to=3.0,
self.sar_params_frame, orient=tk.HORIZONTAL, from_=0.1, to=3.0,
value=self.app.state.sar_contrast, # Initial value from AppState
command=self.app.update_contrast, # Callback in App
)
self.contrast_scale.grid(
row=sar_row, column=1, sticky=tk.EW, padx=(0, 10), pady=1
command=self.app.update_contrast # Callback in App
)
self.contrast_scale.grid(row=sar_row, column=1, sticky=tk.EW, padx=(0, 10), pady=1)
self.brightness_label = ttk.Label(self.sar_params_frame, text="Brightness:")
self.brightness_label.grid(
row=sar_row, column=2, sticky=tk.W, padx=(0, 2), pady=1
)
self.brightness_label.grid(row=sar_row, column=2, sticky=tk.W, padx=(0, 2), pady=1)
self.brightness_scale = ttk.Scale(
self.sar_params_frame,
orient=tk.HORIZONTAL,
from_=-100,
to=100,
self.sar_params_frame, orient=tk.HORIZONTAL, from_=-100, to=100,
value=self.app.state.sar_brightness, # Initial value from AppState
command=self.app.update_brightness, # Callback in App
)
self.brightness_scale.grid(
row=sar_row, column=3, sticky=tk.EW, padx=(0, 5), pady=1
command=self.app.update_brightness # Callback in App
)
self.brightness_scale.grid(row=sar_row, column=3, sticky=tk.EW, padx=(0, 5), pady=1)
# Configure column weights for expansion in SAR frame
self.sar_params_frame.columnconfigure(1, weight=1)
self.sar_params_frame.columnconfigure(3, weight=1)
logging.debug(f"{log_prefix} SAR Parameters frame created.")
logging.debug(f"{log_prefix} SAR Parameters frame created and packed.")
# --- SAR Info Frame ---
logging.debug(f"{log_prefix} Creating SAR Info frame...")
self.sar_info_frame = ttk.Labelframe(self, text="SAR Info", padding=5)
self.sar_info_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2)
# Labels within SAR Info frame (Text updated by App)
self.sar_center_label = ttk.Label(
self.sar_info_frame, text="Image Ref: Lat=N/A, Lon=N/A"
)
self.sar_center_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
self.sar_orientation_label = ttk.Label(
self.sar_info_frame, text="Image Orient: N/A"
)
self.sar_orientation_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
self.sar_size_label = ttk.Label(self.sar_info_frame, text="Image Size: N/A")
self.sar_size_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
self.mouse_latlon_label = ttk.Label(
self.sar_info_frame, text="Mouse : Lat=N/A, Lon=N/A"
)
self.mouse_latlon_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
self.dropped_label = ttk.Label(
self.sar_info_frame, text="Dropped (Q): S=0, M=0, Tk=0, Mo=0"
)
self.dropped_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
self.incomplete_label = ttk.Label(
self.sar_info_frame, text="Incomplete (RX): S=0, M=0"
)
self.incomplete_label.pack(side=tk.TOP, anchor=tk.W, padx=5, pady=1)
logging.debug(f"{log_prefix} SAR Info frame created.")
# --- MFD Parameters Frame ---
# --- 2. MFD Parameters Frame ---
logging.debug(f"{log_prefix} Creating MFD Parameters frame...")
self.mfd_params_frame = ttk.Labelframe(self, text="MFD Parameters", padding=5)
self.mfd_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2)
self.mfd_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2) # PACK ORDER 2
# Define categories in the desired display order for pairing
mfd_categories_ordered = ["Occlusion", "Cat A", "Cat B", "Cat C", "Cat C1", "Cat C2", "Cat C3"]
num_categories = len(mfd_categories_ordered)
logging.debug(f"{log_prefix} Creating compacted MFD category controls...")
for index, internal_name in enumerate(mfd_categories_ordered):
current_row = index // 2 # Integer division determines the row (0, 0, 1, 1, 2, 2, 3)
col_offset = 0 if (index % 2 == 0) else 4 # Start at column 0 for even index, 4 for odd
mfd_row = 0 # Row counter for MFD frame grid
# Define categories and labels concisely
mfd_categories_ui_setup = {
"Occlusion": {"label_text": "Occlusion:"},
"Cat A": {"label_text": "Cat A:"},
"Cat B": {"label_text": "Cat B:"},
"Cat C": {"label_text": "Cat C:"},
"Cat C1": {"label_text": "Cat C1:"},
"Cat C2": {"label_text": "Cat C2:"},
"Cat C3": {"label_text": "Cat C3:"},
}
for internal_name, params in mfd_categories_ui_setup.items():
# Label for category
label = ttk.Label(self.mfd_params_frame, text=params["label_text"])
label.grid(row=mfd_row, column=0, sticky=tk.W, padx=(5, 1), pady=1)
label_text = f"{internal_name}:"
label = ttk.Label(self.mfd_params_frame, text=label_text)
label.grid(row=current_row, column=0 + col_offset, sticky=tk.W, padx=(5, 1), pady=1)
# Intensity Slider
intensity_var_name = (
f"mfd_{internal_name.replace(' ', '_').lower()}_intensity_var"
)
intensity_var_name = f"mfd_{internal_name.replace(' ', '_').lower()}_intensity_var"
initial_intensity = config.DEFAULT_MFD_INTENSITY # Default
try: # Get initial from AppState
initial_intensity = self.app.state.mfd_params["categories"][
internal_name
]["intensity"]
except Exception as e:
logging.warning(
f"{log_prefix} Error getting initial MFD intensity for {internal_name}: {e}"
)
initial_intensity = self.app.state.mfd_params["categories"][internal_name]["intensity"]
except Exception as e: logging.warning(f"{log_prefix} Error getting MFD intensity for {internal_name}: {e}")
intensity_var = tk.IntVar(value=initial_intensity)
setattr(self, intensity_var_name, intensity_var) # Store variable reference
slider = ttk.Scale(
self.mfd_params_frame,
orient=tk.HORIZONTAL,
length=150,
from_=0,
to=255,
self.mfd_params_frame, orient=tk.HORIZONTAL, length=100, from_=0, to=255, # Shorter default length
variable=intensity_var,
# Use lambda to pass current value and category name to App callback
command=lambda v, name=internal_name, var=intensity_var: self.app.update_mfd_category_intensity(
name, var.get()
),
command=lambda v, name=internal_name, var=intensity_var: self.app.update_mfd_category_intensity(name, var.get())
)
slider.grid(row=mfd_row, column=1, sticky=tk.EW, padx=1, pady=1)
slider.grid(row=current_row, column=1 + col_offset, sticky=tk.EW, padx=1, pady=1)
# Color Chooser Button
color_button = ttk.Button(
self.mfd_params_frame,
text="Color",
width=5,
self.mfd_params_frame, text="Color", width=5,
# Use lambda to pass category name to App callback
command=lambda name=internal_name: self.app.choose_mfd_category_color(
name
),
command=lambda name=internal_name: self.app.choose_mfd_category_color(name)
)
color_button.grid(row=mfd_row, column=2, sticky=tk.W, padx=1, pady=1)
color_button.grid(row=current_row, column=2 + col_offset, sticky=tk.W, padx=1, pady=1)
# Color Preview Label
color_label = tk.Label(
self.mfd_params_frame, text="", width=3, relief=tk.SUNKEN, borderwidth=1
)
color_label = tk.Label(self.mfd_params_frame, text="", width=3, relief=tk.SUNKEN, borderwidth=1)
try: # Set initial color from AppState
initial_bgr = self.app.state.mfd_params["categories"][internal_name][
"color"
]
initial_hex = "#{:02x}{:02x}{:02x}".format(
initial_bgr[2], initial_bgr[1], initial_bgr[0]
)
initial_bgr = self.app.state.mfd_params["categories"][internal_name]["color"]
initial_hex = "#{:02x}{:02x}{:02x}".format(initial_bgr[2], initial_bgr[1], initial_bgr[0])
color_label.config(background=initial_hex)
except Exception as e:
logging.warning(
f"{log_prefix} Error setting initial MFD color for {internal_name}: {e}"
)
color_label.config(background="grey")
color_label.grid(row=mfd_row, column=3, sticky=tk.W, padx=(1, 5), pady=1)
except Exception as e: logging.warning(f"{log_prefix} Error setting MFD color for {internal_name}: {e}"); color_label.config(background="grey")
color_label.grid(row=current_row, column=3 + col_offset, sticky=tk.W, padx=(1, 5), pady=1)
self.mfd_color_labels[internal_name] = color_label # Store label reference
mfd_row += 1 # Increment row for next category
# Place Raw Map slider - it goes on the same row as the last odd-indexed category if one exists, or a new row
last_cat_row = (num_categories - 1) // 2
raw_map_start_col = 4 if (num_categories % 2 != 0) else 0 # Start at col 4 if last category was on left, else col 0
raw_map_row = last_cat_row if (num_categories % 2 != 0) else last_cat_row + 1 # Use same row if possible
# Raw Map Intensity Slider
raw_map_label = ttk.Label(self.mfd_params_frame, text="Raw Map:")
raw_map_label.grid(row=mfd_row, column=0, sticky=tk.W, padx=(5, 1), pady=1)
raw_map_label.grid(row=raw_map_row, column=0 + raw_map_start_col, sticky=tk.W, padx=(5, 1), pady=1)
initial_raw_intensity = config.DEFAULT_MFD_RAW_MAP_INTENSITY # Default
try:
initial_raw_intensity = self.app.state.mfd_params[
"raw_map_intensity"
] # Get initial from AppState
except Exception as e:
logging.warning(
f"{log_prefix} Error getting initial raw map intensity: {e}"
)
try: initial_raw_intensity = self.app.state.mfd_params["raw_map_intensity"] # Get initial from AppState
except Exception as e: logging.warning(f"{log_prefix} Error getting raw map intensity: {e}")
self.mfd_raw_map_intensity_var = tk.IntVar(value=initial_raw_intensity)
raw_map_slider = ttk.Scale(
self.mfd_params_frame,
orient=tk.HORIZONTAL,
length=150,
from_=0,
to=255,
self.mfd_params_frame, orient=tk.HORIZONTAL, length=100, from_=0, to=255, # Shorter default length
variable=self.mfd_raw_map_intensity_var,
# Use lambda to pass current value to App callback
command=lambda v: self.app.update_mfd_raw_map_intensity(
self.mfd_raw_map_intensity_var.get()
),
command=lambda v: self.app.update_mfd_raw_map_intensity(self.mfd_raw_map_intensity_var.get())
)
raw_map_slider.grid(row=mfd_row, column=1, sticky=tk.EW, padx=1, pady=1)
# Span the slider across remaining columns in its pair (1, 2, 3 or 5, 6, 7)
raw_map_slider.grid(row=raw_map_row, column=1 + raw_map_start_col, columnspan=3, sticky=tk.EW, padx=(1, 5), pady=1)
# Configure column weight for expansion in MFD frame
# Configure column weights for sliders in MFD frame (Cols 1 and 5)
self.mfd_params_frame.columnconfigure(1, weight=1)
logging.debug(f"{log_prefix} MFD Parameters frame created.")
self.mfd_params_frame.columnconfigure(5, weight=1) # Corresponds to the second slider column
logging.debug(f"{log_prefix} MFD Parameters frame created and packed.")
# --- NEW: Map Parameters Frame ---
# --- 3. Map Parameters Frame ---
logging.debug(f"{log_prefix} Creating Map Parameters frame...")
self.map_params_frame = ttk.Labelframe(self, text="Map Parameters", padding=5)
# Pack below MFD frame
self.map_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2)
self.map_params_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2) # PACK ORDER 3
map_row = 0 # Row counter for Map frame grid
# Map Size Combobox
self.map_size_label = ttk.Label(self.map_params_frame, text="Map Display Size:")
self.map_size_label.grid(
row=map_row, column=0, sticky=tk.W, padx=(5, 2), pady=1
)
self.map_size_label.grid(row=map_row, column=0, sticky=tk.W, padx=(5, 2), pady=1)
self.map_size_combo = ttk.Combobox(
self.map_params_frame,
@ -333,149 +226,119 @@ class ControlPanel(ttk.Frame):
)
# Set initial value from config default
self.map_size_combo.set(config.DEFAULT_MAP_SIZE)
self.map_size_combo.grid(
row=map_row, column=1, sticky=tk.EW, padx=(2, 5), pady=1
)
# Bind to the new App callback function (needs to be created in App class)
self.map_size_combo.grid(row=map_row, column=1, sticky=tk.EW, padx=(2, 5), pady=1)
# Bind to the App callback function
self.map_size_combo.bind("<<ComboboxSelected>>", self.app.update_map_size)
# Configure column weight for the combobox column to expand
self.map_params_frame.columnconfigure(1, weight=1)
logging.debug(f"{log_prefix} Map Parameters frame created.")
logging.debug(f"{log_prefix} Map Parameters frame created and packed.")
# --- 4. SAR Info Frame ---
logging.debug(f"{log_prefix} Creating SAR Info frame...")
self.sar_info_frame = ttk.Labelframe(self, text="SAR Info", padding=5)
self.sar_info_frame.pack(side=tk.TOP, fill=tk.X, padx=5, pady=2) # PACK ORDER 4
info_row = 0
# Row 1: Image Ref
self.sar_center_label = ttk.Label(self.sar_info_frame, text="Image Ref: Lat=N/A, Lon=N/A")
self.sar_center_label.grid(row=info_row, column=0, columnspan=4, sticky=tk.W, padx=5, pady=1)
info_row += 1
# Row 2: Image Orient & Image Size
self.sar_orientation_label = ttk.Label(self.sar_info_frame, text="Image Orient: N/A")
self.sar_orientation_label.grid(row=info_row, column=0, columnspan=2, sticky=tk.W, padx=5, pady=1) # Span 2 cols
self.sar_size_label = ttk.Label(self.sar_info_frame, text="Image Size: N/A")
self.sar_size_label.grid(row=info_row, column=2, columnspan=2, sticky=tk.W, padx=5, pady=1) # Span 2 cols
info_row += 1
# Row 3: Mouse Coordinates
self.mouse_latlon_label = ttk.Label(self.sar_info_frame, text="Mouse : Lat=N/A, Lon=N/A")
self.mouse_latlon_label.grid(row=info_row, column=0, columnspan=4, sticky=tk.W, padx=5, pady=1)
info_row += 1
# Row 4: Drop & Incomplete
self.dropped_label = ttk.Label(self.sar_info_frame, text="Drop (Q): S=0, M=0, Tk=0, Mo=0") # Shortened label
self.dropped_label.grid(row=info_row, column=0, columnspan=2, sticky=tk.W, padx=5, pady=1) # Span 2 cols
self.incomplete_label = ttk.Label(self.sar_info_frame, text="Incmpl (RX): S=0, M=0") # Shortened label
self.incomplete_label.grid(row=info_row, column=2, columnspan=2, sticky=tk.W, padx=5, pady=1) # Span 2 cols
# Configure column weights for SAR Info frame for better spacing if needed
self.sar_info_frame.columnconfigure(1, weight=1) # Add weight between Orient/Size
self.sar_info_frame.columnconfigure(3, weight=1) # Add weight after Size/Incmpl
logging.debug(f"{log_prefix} SAR Info frame created and packed.")
# --- End of init_ui ---
logging.debug(f"{log_prefix} init_ui widget creation complete.")
# --- Methods to update UI labels ---
def set_mouse_coordinates(self, latitude_str: str, longitude_str: str):
"""Updates the mouse coordinates label with pre-formatted DMS strings."""
log_prefix = "[UI Update]"
text_to_display = f"Mouse : Lat={latitude_str}, Lon={longitude_str}"
logging.debug(
f"{log_prefix} Setting mouse coordinates label to: '{text_to_display}'"
)
try:
if (
hasattr(self, "mouse_latlon_label")
and self.mouse_latlon_label.winfo_exists()
):
if hasattr(self, "mouse_latlon_label") and self.mouse_latlon_label.winfo_exists():
self.mouse_latlon_label.config(text=text_to_display)
# else: logging.warning(f"{log_prefix} Mouse coordinates label widget does not exist.")
except Exception as e:
logging.warning(f"{log_prefix} Error updating mouse coords UI: {e}")
except Exception as e: logging.warning(f"{log_prefix} Error updating mouse coords UI: {e}")
def set_sar_orientation(self, orientation_deg_str: str):
"""Updates the SAR orientation label."""
log_prefix = "[UI Update]"
text_to_display = f"Image Orient: {orientation_deg_str}"
logging.debug(
f"{log_prefix} Setting SAR orientation label to: '{text_to_display}'"
)
try:
if (
hasattr(self, "sar_orientation_label")
and self.sar_orientation_label.winfo_exists()
):
if hasattr(self, "sar_orientation_label") and self.sar_orientation_label.winfo_exists():
self.sar_orientation_label.config(text=text_to_display)
# else: logging.warning(f"{log_prefix} SAR orientation label widget does not exist.")
except Exception as e:
logging.warning(f"{log_prefix} Error updating SAR orientation UI: {e}")
except Exception as e: logging.warning(f"{log_prefix} Error updating SAR orientation UI: {e}")
def set_sar_size_km(self, size_text: str):
"""Updates the SAR image size label."""
log_prefix = "[UI Update]"
text_to_display = f"Image Size: {size_text}"
logging.debug(f"{log_prefix} Setting SAR size label to: '{text_to_display}'")
try:
if hasattr(self, "sar_size_label") and self.sar_size_label.winfo_exists():
self.sar_size_label.config(text=text_to_display)
# else: logging.warning(f"{log_prefix} SAR size label widget does not exist.")
except Exception as e:
logging.warning(f"{log_prefix} Error updating SAR size UI: {e}")
except Exception as e: logging.warning(f"{log_prefix} Error updating SAR size UI: {e}")
# Type hint the color tuple argument
def update_mfd_color_display(
self, category_name: str, color_bgr_tuple: Tuple[int, int, int]
):
def update_mfd_color_display(self, category_name: str, color_bgr_tuple: Tuple[int, int, int]):
"""Updates the background color of the specified MFD category's display label."""
log_prefix = "[UI Update]"
logging.debug(
f"{log_prefix} Updating MFD color display for '{category_name}' to BGR={color_bgr_tuple}"
)
if category_name in self.mfd_color_labels:
target_label = self.mfd_color_labels[category_name]
try:
if target_label.winfo_exists():
# Ensure values are ints and format hex color string
hex_color = "#{:02x}{:02x}{:02x}".format(
int(color_bgr_tuple[2]),
int(color_bgr_tuple[1]),
int(color_bgr_tuple[0]),
)
hex_color = "#{:02x}{:02x}{:02x}".format(int(color_bgr_tuple[2]), int(color_bgr_tuple[1]), int(color_bgr_tuple[0]))
target_label.config(background=hex_color)
# else: logging.warning(f"{log_prefix} MFD color label for '{category_name}' does not exist.")
except Exception as e:
logging.error(
f"{log_prefix} Error updating color display for {category_name}: {e}",
exc_info=True,
)
else:
logging.warning(
f"{log_prefix} Unknown category key for MFD color display: '{category_name}'"
)
except Exception as e: logging.error(f"{log_prefix} Error updating color display for {category_name}: {e}", exc_info=True)
else: logging.warning(f"{log_prefix} Unknown category key for MFD color display: '{category_name}'")
class StatusBar(ttk.Label):
"""
Represents the status bar at the bottom of the main window.
Provides a method to set its text content.
"""
""" Represents the status bar at the bottom of the main window. """
def __init__(self, parent: tk.Widget, *args, **kwargs):
"""Initializes the StatusBar label."""
log_prefix = "[UI Setup]"
logging.debug(f"{log_prefix} Initializing StatusBar...")
super().__init__(
parent,
text=config.INITIAL_STATUS_MESSAGE,
relief=tk.SUNKEN,
anchor=tk.W,
*args,
**kwargs,
)
log_prefix = "[UI Setup]"; logging.debug(f"{log_prefix} Initializing StatusBar...")
super().__init__(parent, text=config.INITIAL_STATUS_MESSAGE, relief=tk.SUNKEN, anchor=tk.W, *args, **kwargs)
self.pack(side=tk.BOTTOM, fill=tk.X)
logging.debug(f"{log_prefix} StatusBar initialization complete.")
def set_status_text(self, text: str):
"""Sets the text displayed in the status bar."""
log_prefix = "[UI Status]"
logging.debug(f"{log_prefix} Setting status bar text to: '{text}'")
try:
if self.winfo_exists():
self.config(text=text)
# else: logging.warning(f"{log_prefix} Status bar widget does not exist.")
except Exception as e:
logging.warning(f"{log_prefix} Error setting status bar text: {e}")
if self.winfo_exists(): self.config(text=text)
except Exception as e: logging.warning(f"{log_prefix} Error setting status bar text: {e}")
def create_main_window(
title: str, min_width: int, min_height: int, x_pos: int, y_pos: int
) -> tk.Tk:
def create_main_window(title: str, min_width: int, min_height: int, x_pos: int, y_pos: int) -> tk.Tk:
"""Creates and configures the main Tkinter root window."""
log_prefix = "[UI Setup]"
logging.debug(f"{log_prefix} Creating main Tkinter root window...")
log_prefix = "[UI Setup]"; logging.debug(f"{log_prefix} Creating main Tkinter root window...")
try:
root = tk.Tk()
root.title(title)
root.minsize(min_width, min_height)
# Initial position is set by App class after calculation
logging.debug(f"{log_prefix} Main Tkinter root window created successfully.")
root = tk.Tk(); root.title(title); root.minsize(min_width, min_height)
logging.debug(f"{log_prefix} Main Tkinter root window created.")
return root
except Exception as e:
logging.critical(
f"{log_prefix} Failed to create main Tkinter window: {e}", exc_info=True
)
raise
except Exception as e: logging.critical(f"{log_prefix} Failed to create main Tkinter window: {e}", exc_info=True); raise
# --- END OF FILE ui.py ---

View File

@ -87,7 +87,7 @@ def put_queue(queue_obj, item, queue_name="Unknown", app_instance=None):
)
except queue.Full:
# WARNING level is appropriate for dropped items due to full queue
logging.warning(
logging.debug(
f"{log_prefix} Queue '{queue_name}' is full (maxsize={queue_obj.maxsize}). Dropping item."
)
# Increment the counter via the AppState instance