diff --git a/src/gui/auto_match_panel.py b/src/gui/auto_match_panel.py index e802060..3b3080c 100644 --- a/src/gui/auto_match_panel.py +++ b/src/gui/auto_match_panel.py @@ -112,18 +112,18 @@ class AutoMatchPanel: # Search input self.components['search_var'] = tk.StringVar() - search_entry = ttk.Entry(search_frame, textvariable=self.components['search_var'], width=20) - search_entry.grid(row=0, column=0, sticky=(tk.W, tk.E), padx=(0, 5)) + self.components['search_entry'] = ttk.Entry(search_frame, textvariable=self.components['search_var'], width=20, state='disabled') + self.components['search_entry'].grid(row=0, column=0, sticky=(tk.W, tk.E), padx=(0, 5)) # Search buttons - search_btn = ttk.Button(search_frame, text="Search", width=8, command=self._apply_search_filter) - search_btn.grid(row=0, column=1, padx=(0, 5)) + self.components['search_btn'] = ttk.Button(search_frame, text="Search", width=8, command=self._apply_search_filter, state='disabled') + self.components['search_btn'].grid(row=0, column=1, padx=(0, 5)) - clear_btn = ttk.Button(search_frame, text="Clear", width=6, command=self._clear_search_filter) - clear_btn.grid(row=0, column=2) + self.components['clear_btn'] = ttk.Button(search_frame, text="Clear", width=6, command=self._clear_search_filter, state='disabled') + self.components['clear_btn'].grid(row=0, column=2) # Search help label - self.components['search_help_label'] = ttk.Label(search_frame, text="Type Last Name", + self.components['search_help_label'] = ttk.Label(search_frame, text="Search disabled - click 'Start Auto-Match' first", font=("Arial", 8), foreground="gray") self.components['search_help_label'].grid(row=1, column=0, columnspan=3, sticky=tk.W, pady=(2, 0)) @@ -309,20 +309,21 @@ class AutoMatchPanel: self.original_checkbox_states_per_person = {} self.identified_count = 0 + # Enable search controls now that auto-match has started + self.components['search_entry'].config(state='normal') + self.components['search_btn'].config(state='normal') + self.components['clear_btn'].config(state='normal') + # Check if there's only one person - disable search if so has_only_one_person = len(self.matched_ids) == 1 if has_only_one_person: self.components['search_var'].set("") - search_entry = None - for widget in self.components['left_panel'].winfo_children(): - if isinstance(widget, ttk.Frame) and len(widget.winfo_children()) > 0: - for child in widget.winfo_children(): - if isinstance(child, ttk.Entry): - search_entry = child - break - if search_entry: - search_entry.config(state='disabled') + self.components['search_entry'].config(state='disabled') + self.components['search_btn'].config(state='disabled') + self.components['clear_btn'].config(state='disabled') self.components['search_help_label'].config(text="(Search disabled - only one person found)") + else: + self.components['search_help_label'].config(text="Type Last Name") # Enable controls self._update_control_states() @@ -873,20 +874,12 @@ class AutoMatchPanel: self.components['select_all_btn'].config(state='disabled') self.components['clear_all_btn'].config(state='disabled') - # Clear search + # Clear search and disable search controls self.components['search_var'].set("") - self.components['search_help_label'].config(text="Type Last Name") - - # Re-enable search entry - search_entry = None - for widget in self.components['left_panel'].winfo_children(): - if isinstance(widget, ttk.Frame) and len(widget.winfo_children()) > 0: - for child in widget.winfo_children(): - if isinstance(child, ttk.Entry): - search_entry = child - break - if search_entry: - search_entry.config(state='normal') + self.components['search_entry'].config(state='disabled') + self.components['search_btn'].config(state='disabled') + self.components['clear_btn'].config(state='disabled') + self.components['search_help_label'].config(text="Search disabled - click 'Start Auto-Match' first") self.is_active = False diff --git a/src/gui/dashboard_gui.py b/src/gui/dashboard_gui.py index 8631691..7a5e503 100644 --- a/src/gui/dashboard_gui.py +++ b/src/gui/dashboard_gui.py @@ -755,39 +755,22 @@ class SearchPanel: if not vals or len(vals) < 6: return - # Determine column offsets based on search type - is_name_search = (self.search_type_var.get() == self.SEARCH_TYPES[0]) - is_photos_without_faces = (self.search_type_var.get() == self.SEARCH_TYPES[6]) + # Get the actual column name from the displaycolumns + display_columns = self.tree["displaycolumns"] + col_index = int(col_id[1:]) - 1 # Convert '#1' to 0, '#2' to 1, etc. - if is_name_search: - # Name search: all columns visible including person (processed column hidden) - select_col = "#1" # select is column 1 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 - path_col = "#6" # path is column 6 - path_index = 6 # path is at index 6 in values array (still same since processed is hidden from display) - elif is_photos_without_faces: - # Photos without faces: person and people icon columns are hidden - select_col = "#1" # select is column 1 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 (but hidden) - path_col = "#5" # path is column 5 (since people icon is hidden) - path_index = 6 # path is at index 6 in values array - else: - # All other searches: person column is hidden, people icon visible - select_col = "#1" # select is column 1 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 - path_col = "#6" # path is column 6 - path_index = 6 # path is at index 6 in values array + if col_index < 0 or col_index >= len(display_columns): + return + + column_name = display_columns[col_index] + path = vals[6] # Photo path is always at index 6 in values array - path = vals[path_index] # Photo path - if col_id == open_dir_col: # Open directory column + if column_name == "open_dir": # Open directory column self.open_dir(path) - elif col_id == face_col: # Face icon column + elif column_name == "open_photo": # Face icon column # No popup needed, just tooltip pass - elif col_id == path_col: # Photo path column - clickable to open photo + elif column_name == "path": # Photo path column - clickable to open photo try: import os import sys @@ -801,7 +784,7 @@ class SearchPanel: subprocess.run(["xdg-open", path], check=False) except Exception: messagebox.showerror("Open Photo", "Failed to open the selected photo.", parent=self.parent_frame) - elif col_id == select_col: # Checkbox column + elif column_name == "select": # Checkbox column self.toggle_photo_selection(row_id, vals) def on_tree_motion(self, event): @@ -814,33 +797,18 @@ class SearchPanel: col_id = self.tree.identify_column(event.x) row_id = self.tree.identify_row(event.y) - # Determine column offsets based on search type - is_name_search = (self.search_type_var.get() == self.SEARCH_TYPES[0]) - is_photos_without_faces = (self.search_type_var.get() == self.SEARCH_TYPES[6]) + # Get the actual column name from the displaycolumns + display_columns = self.tree["displaycolumns"] + col_index = int(col_id[1:]) - 1 # Convert '#1' to 0, '#2' to 1, etc. - if is_name_search: - # Name search: all columns visible including person (processed column hidden) - tags_col = "#3" # tags is column 3 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 - path_col = "#6" # path is column 6 - path_index = 6 # path is at index 6 in values array (still same since processed is hidden from display) - elif is_photos_without_faces: - # Photos without faces: person and people icon columns are hidden - tags_col = "#2" # tags is column 2 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 (but hidden) - path_col = "#5" # path is column 5 (since people icon is hidden) - path_index = 6 # path is at index 6 in values array - else: - # All other searches: person column is hidden, people icon visible - tags_col = "#2" # tags is column 2 - open_dir_col = "#4" # open_dir is column 4 - face_col = "#5" # open_photo is column 5 - path_col = "#6" # path is column 6 - path_index = 6 # path is at index 6 in values array + if col_index < 0 or col_index >= len(display_columns): + self.tree.config(cursor="") + self.hide_tooltip() + return + + column_name = display_columns[col_index] - if col_id == tags_col: # Tags column + if column_name == "tags": # Tags column self.tree.config(cursor="") # Show tags tooltip if row_id: @@ -849,19 +817,19 @@ class SearchPanel: # Tags are at index 2 for all search types (after select, person is hidden in most) tags_text = vals[2] self.show_tooltip(self.tree, event.x_root, event.y_root, f"Tags: {tags_text}") - elif col_id == open_dir_col: # Open directory column + elif column_name == "open_dir": # Open directory column self.tree.config(cursor="hand2") self.show_tooltip(self.tree, event.x_root, event.y_root, "Open file location") - elif col_id == face_col: # Face icon column + elif column_name == "open_photo": # Face icon column self.tree.config(cursor="hand2") # Show people tooltip if row_id: vals = self.tree.item(row_id, "values") - if len(vals) >= 5: - path = vals[path_index] + if len(vals) >= 6: + path = vals[6] # Photo path is always at index 6 people_text = self.get_photo_people_tooltip(path) self.show_tooltip(self.tree, event.x_root, event.y_root, people_text) - elif col_id == path_col: # Photo path column + elif column_name == "path": # Photo path column self.tree.config(cursor="hand2") self.show_tooltip(self.tree, event.x_root, event.y_root, "Open photo") else: