diff --git a/MyTimeline.py b/MyTimeline.py index 207fcd2..b1512d5 100644 --- a/MyTimeline.py +++ b/MyTimeline.py @@ -431,7 +431,7 @@ class MyTimelineView(NavigationView): """ View for displaying a vertical timeline of all events in the database. Shows all events with modern design and interactivity, allowing selection - and filtering of events by type, category, person, and date range. + and filtering of events by type, category, and person. """ def __init__(self, pdata: Any, dbstate: Any, uistate: Any, nav_group: int = 0) -> None: @@ -486,8 +486,6 @@ class MyTimelineView(NavigationView): # Filter state self.filter_enabled: bool = False self.active_event_types: Set[EventType] = set() # Empty = all enabled - self.date_range_filter: Optional[Tuple[int, int]] = None # (min_date, max_date) in sort values - self.date_range_explicit: bool = False # Track if date range was explicitly set self.person_filter: Optional[Set[str]] = None # Set of person handles to include, None = all self.category_filter: Optional[Set[str]] = None # Set of event categories to include, None = all self.all_events: List[TimelineEvent] = [] # Store all events before filtering @@ -690,9 +688,6 @@ class MyTimelineView(NavigationView): response = self.filter_dialog.run() if response == Gtk.ResponseType.APPLY: self._apply_filter_dialog_settings() - elif response == Gtk.ResponseType.CLOSE: - pass # Just close - self.filter_dialog.hide() def _calculate_group_state(self, child_checkboxes: List[Gtk.CheckButton]) -> str: @@ -718,14 +713,22 @@ class MyTimelineView(NavigationView): return 'some' def _update_group_checkbox_state(self, group_checkbox: Gtk.CheckButton, - child_checkboxes: List[Gtk.CheckButton]) -> None: + child_checkboxes: List[Gtk.CheckButton], + updating_flag: Optional[List[bool]] = None) -> None: """ Update a group checkbox state based on child checkboxes. Args: group_checkbox: The parent group checkbox to update. child_checkboxes: List of child checkboxes. + updating_flag: Optional list with single boolean to prevent recursion. + If provided, will be set to True during update to prevent + the group checkbox's toggle handler from firing. """ + # Set updating flag to prevent recursion if provided + if updating_flag is not None: + updating_flag[0] = True + state = self._calculate_group_state(child_checkboxes) if state == 'all': @@ -736,6 +739,10 @@ class MyTimelineView(NavigationView): group_checkbox.set_inconsistent(False) else: # 'some' group_checkbox.set_inconsistent(True) + + # Clear updating flag after update + if updating_flag is not None: + updating_flag[0] = False def _make_group_toggle_handler(self, child_checkboxes: List[Gtk.CheckButton], updating_flag: List[bool]) -> Callable[[Gtk.Widget], None]: @@ -784,7 +791,7 @@ class MyTimelineView(NavigationView): def handler(widget: Gtk.Widget) -> None: if updating_flag[0]: return - self._update_group_checkbox_state(group_checkbox, child_checkboxes) + self._update_group_checkbox_state(group_checkbox, child_checkboxes, updating_flag) return handler @@ -831,10 +838,6 @@ class MyTimelineView(NavigationView): person_page = self._build_person_filter_page() notebook.append_page(person_page, Gtk.Label(label=_("Persons"))) - # Date Range Filter Page - date_page = self._build_date_range_filter_page() - notebook.append_page(date_page, Gtk.Label(label=_("Date Range"))) - content_area.show_all() return dialog @@ -869,6 +872,7 @@ class MyTimelineView(NavigationView): category_boxes = {} category_checkboxes = {} category_event_types = {} # Map category to list of event types + category_updating_flags = {} # Map category to updating flag list # First pass: collect event types by category for event_type_obj in EVENT_COLORS: @@ -905,6 +909,7 @@ class MyTimelineView(NavigationView): # Flag to prevent recursion between category and child checkboxes updating_category = [False] + category_updating_flags[category] = updating_category # Connect category checkbox to toggle all children category_checkbox.connect("toggled", @@ -918,6 +923,7 @@ class MyTimelineView(NavigationView): self._filter_widgets['event_type_checkboxes'] = event_type_checkboxes self._filter_widgets['category_checkboxes'] = category_checkboxes self._filter_widgets['category_event_types'] = category_event_types + self._filter_widgets['category_updating_flags'] = category_updating_flags scrolled.add(box) return scrolled @@ -978,182 +984,6 @@ class MyTimelineView(NavigationView): scrolled.add(box) return scrolled - def _create_date_calendar_widget(self, label: str, year_changed_handler: Callable, - date_selected_handler: Callable, - month_changed_handler: Callable, - calendar_key: str, spin_key: str, - current_year: int, min_year: int, max_year: int) -> Tuple[Gtk.Frame, Gtk.Calendar, Gtk.SpinButton]: - """ - Create a date calendar widget with year selector. - - Args: - label: Label for the frame. - year_changed_handler: Handler for year spin button changes. - date_selected_handler: Handler for calendar date selection. - month_changed_handler: Handler for calendar month changes. - calendar_key: Key to store calendar widget in _filter_widgets. - spin_key: Key to store spin button widget in _filter_widgets. - current_year: Initial year value. - min_year: Minimum year for the spin button. - max_year: Maximum year for the spin button. - - Returns: - Tuple containing (frame, calendar, spin_button). - """ - frame = Gtk.Frame(label=label) - frame.set_label_align(0.5, 0.5) - - container = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=CALENDAR_CONTAINER_SPACING) - container.set_margin_start(CALENDAR_CONTAINER_MARGIN) - container.set_margin_end(CALENDAR_CONTAINER_MARGIN) - container.set_margin_top(CALENDAR_CONTAINER_MARGIN) - container.set_margin_bottom(CALENDAR_CONTAINER_MARGIN) - - # Year selector - year_box = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=YEAR_SELECTOR_SPACING) - year_label = Gtk.Label(label=_("Year:")) - year_adjustment = Gtk.Adjustment( - value=current_year, - lower=min_year, - upper=max_year, - step_increment=1, - page_increment=10 - ) - year_spin = Gtk.SpinButton() - year_spin.set_adjustment(year_adjustment) - year_spin.set_numeric(True) - year_spin.set_update_policy(Gtk.SpinButtonUpdatePolicy.IF_VALID) - year_spin.set_width_chars(6) - year_spin.connect("value-changed", year_changed_handler) - - year_box.pack_start(year_label, False, False, 0) - year_box.pack_start(year_spin, False, False, 0) - container.pack_start(year_box, False, False, 0) - - # Calendar - calendar = Gtk.Calendar() - calendar.set_display_options( - Gtk.CalendarDisplayOptions.SHOW_HEADING | - Gtk.CalendarDisplayOptions.SHOW_DAY_NAMES | - Gtk.CalendarDisplayOptions.SHOW_WEEK_NUMBERS - ) - calendar.connect("day-selected", date_selected_handler) - calendar.connect("month-changed", month_changed_handler) - container.pack_start(calendar, True, True, 0) - - frame.add(container) - - # Store widgets - self._filter_widgets[calendar_key] = calendar - self._filter_widgets[spin_key] = year_spin - - return frame, calendar, year_spin - - def _build_date_range_filter_page(self) -> Gtk.Widget: - """ - Build the date range filter page with date chooser widgets. - - Returns: - Gtk.Widget: The date range filter page. - """ - scrolled = Gtk.ScrolledWindow() - scrolled.set_policy(Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC) - - box = Gtk.Box(orientation=Gtk.Orientation.VERTICAL, spacing=FILTER_PAGE_SPACING) - box.set_margin_start(FILTER_PAGE_MARGIN) - box.set_margin_end(FILTER_PAGE_MARGIN) - box.set_margin_top(FILTER_PAGE_MARGIN) - box.set_margin_bottom(FILTER_PAGE_MARGIN) - - info_label = Gtk.Label(label=_("Select date range to filter events. Leave unselected to show all dates.")) - info_label.set_line_wrap(True) - box.pack_start(info_label, False, False, 0) - - # Calendar container - calendar_box = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=CALENDAR_HORIZONTAL_SPACING) - calendar_box.set_homogeneous(True) - - # Year range for genealogical data - current_year = datetime.date.today().year - min_year = MIN_GENEALOGICAL_YEAR - max_year = current_year + 10 - - # Create From date calendar widget - from_frame, from_calendar, from_year_spin = self._create_date_calendar_widget( - label=_("From Date"), - year_changed_handler=self._on_from_year_changed, - date_selected_handler=self._on_from_date_selected, - month_changed_handler=self._on_from_calendar_changed, - calendar_key='date_from_calendar', - spin_key='date_from_year_spin', - current_year=current_year, - min_year=min_year, - max_year=max_year - ) - calendar_box.pack_start(from_frame, True, True, 0) - - # Create To date calendar widget - to_frame, to_calendar, to_year_spin = self._create_date_calendar_widget( - label=_("To Date"), - year_changed_handler=self._on_to_year_changed, - date_selected_handler=self._on_to_date_selected, - month_changed_handler=self._on_to_calendar_changed, - calendar_key='date_to_calendar', - spin_key='date_to_year_spin', - current_year=current_year, - min_year=min_year, - max_year=max_year - ) - calendar_box.pack_start(to_frame, True, True, 0) - - box.pack_start(calendar_box, True, True, 0) - - # Clear button - clear_button = Gtk.Button(label=_("Clear Dates")) - clear_button.connect("clicked", self._on_clear_date_range) - button_box = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL) - button_box.pack_start(clear_button, False, False, 0) - box.pack_start(button_box, False, False, 0) - - # Validation label - self.date_validation_label = Gtk.Label() - self.date_validation_label.set_line_wrap(True) - self.date_validation_label.set_markup("") - box.pack_start(self.date_validation_label, False, False, 0) - - scrolled.add(box) - return scrolled - - def _set_validation_message(self, message: str) -> None: - """ - Set the date validation label message. - - Args: - message: Message text to display (empty string to clear). - """ - if hasattr(self, 'date_validation_label'): - if message: - self.date_validation_label.set_markup( - f"{message}" - ) - else: - self.date_validation_label.set_text("") - - def _update_year_spin_button(self, spin_key: str, year: int, handler: Callable) -> None: - """ - Update a year spin button value, blocking signals during update. - - Args: - spin_key: Key to find the spin button in _filter_widgets. - year: Year value to set. - handler: Handler function to block/unblock during update. - """ - if spin_key in self._filter_widgets: - year_spin = self._filter_widgets[spin_key] - year_spin.handler_block_by_func(handler) - year_spin.set_value(year) - year_spin.handler_unblock_by_func(handler) - def _update_event_type_widgets(self) -> None: """ Update event type filter widgets to reflect current filter state. @@ -1170,6 +1000,7 @@ class MyTimelineView(NavigationView): # Update category checkboxes based on their children's states if 'category_checkboxes' in self._filter_widgets and 'category_event_types' in self._filter_widgets: + category_updating_flags = self._filter_widgets.get('category_updating_flags', {}) for category, category_checkbox in self._filter_widgets['category_checkboxes'].items(): # Get child checkboxes for this category event_types_in_category = self._filter_widgets['category_event_types'].get(category, []) @@ -1178,8 +1009,10 @@ class MyTimelineView(NavigationView): for et in event_types_in_category if et in self._filter_widgets['event_type_checkboxes'] ] + # Get the updating flag for this category to prevent recursion + updating_flag = category_updating_flags.get(category) # Update category checkbox state based on children - self._update_group_checkbox_state(category_checkbox, child_checkboxes) + self._update_group_checkbox_state(category_checkbox, child_checkboxes, updating_flag) def _update_person_filter_widgets(self) -> None: """ @@ -1282,7 +1115,7 @@ class MyTimelineView(NavigationView): self._make_child_toggle_handler(family_checkbox, child_checkboxes, updating_family)) # Initialize family checkbox state - self._update_group_checkbox_state(family_checkbox, child_checkboxes) + self._update_group_checkbox_state(family_checkbox, child_checkboxes, updating_family) expander.add(members_box) self._filter_widgets['family_expanders'][family_handle] = expander @@ -1292,47 +1125,6 @@ class MyTimelineView(NavigationView): except (AttributeError, KeyError) as e: logger.warning(f"Error updating person filter widgets in filter dialog: {e}", exc_info=True) - def _update_date_range_widgets(self) -> None: - """ - Update date range filter widgets to reflect current filter state. - """ - if 'date_from_calendar' not in self._filter_widgets or 'date_to_calendar' not in self._filter_widgets: - return - - from_calendar = self._filter_widgets['date_from_calendar'] - to_calendar = self._filter_widgets['date_to_calendar'] - - if self.date_range_filter and self.date_range_explicit: - min_sort, max_sort = self.date_range_filter - # Convert sort values back to dates for calendar display - # Approximate conversion: extract year from sort value - # Sort value is roughly: year * DATE_SORT_YEAR_MULTIPLIER + month * DATE_SORT_MONTH_MULTIPLIER + day - from_year = min_sort // DATE_SORT_YEAR_MULTIPLIER - to_year = max_sort // DATE_SORT_YEAR_MULTIPLIER - - # Set calendar years (approximate) - current_from_year, current_from_month, current_from_day = from_calendar.get_date() - current_to_year, current_to_month, current_to_day = to_calendar.get_date() - - from_calendar.select_month(current_from_month, from_year) - to_calendar.select_month(current_to_month, to_year) - - # Update year spin buttons - self._update_year_spin_button('date_from_year_spin', from_year, self._on_from_year_changed) - self._update_year_spin_button('date_to_year_spin', to_year, self._on_to_year_changed) - else: - # Reset to current date - now = datetime.date.today() - from_calendar.select_month(now.month - 1, now.year) - to_calendar.select_month(now.month - 1, now.year) - - # Reset year spin buttons - self._update_year_spin_button('date_from_year_spin', now.year, self._on_from_year_changed) - self._update_year_spin_button('date_to_year_spin', now.year, self._on_to_year_changed) - - # Clear validation message - self._set_validation_message("") - def _update_filter_dialog_state(self) -> None: """ Update the filter dialog widgets to reflect current filter state. @@ -1343,7 +1135,6 @@ class MyTimelineView(NavigationView): # Update each filter type's widgets self._update_event_type_widgets() self._update_person_filter_widgets() - self._update_date_range_widgets() def _on_filter_dialog_response(self, dialog: Gtk.Dialog, response_id: int) -> None: """ @@ -1358,8 +1149,6 @@ class MyTimelineView(NavigationView): self.filter_enabled = False self.active_event_types = set() self._update_normalized_active_event_types() # Invalidate cache - self.date_range_filter = None - self.date_range_explicit = False self.person_filter = None self.category_filter = None self.apply_filters() @@ -1372,10 +1161,23 @@ class MyTimelineView(NavigationView): # Update event type filter if 'event_type_checkboxes' in self._filter_widgets: active_types = set() + total_types = len(self._filter_widgets['event_type_checkboxes']) for event_type, checkbox in self._filter_widgets['event_type_checkboxes'].items(): if checkbox.get_active(): active_types.add(event_type) - self.active_event_types = active_types if len(active_types) < len(self._filter_widgets['event_type_checkboxes']) else set() + + # Logic: + # - If all types are selected: active_event_types = empty set (meaning "all enabled", no filtering) + # - If some types are unselected: active_event_types = set of selected types (filter to show only these) + # - If no types are selected: active_event_types = empty set, but filter_enabled will be False + # (unless other filters are active), so no events will show (correct behavior) + if len(active_types) == total_types: + # All types are selected - no filtering needed + self.active_event_types = set() + else: + # Some or no types are selected - filter to only show selected types + # (If active_types is empty, this means no events will match, which is correct) + self.active_event_types = active_types self._update_normalized_active_event_types() # Update cache # Update category filter @@ -1396,54 +1198,9 @@ class MyTimelineView(NavigationView): all_persons = set(self._filter_widgets['person_checkboxes']) self.person_filter = active_persons if active_persons != all_persons else None - # Update date range filter from calendar widgets - if 'date_from_calendar' in self._filter_widgets and 'date_to_calendar' in self._filter_widgets: - from_calendar = self._filter_widgets['date_from_calendar'] - to_calendar = self._filter_widgets['date_to_calendar'] - - # Check if dates were explicitly set (stored in widget data) - # We'll use a simple approach: if user clicked calendars, use the dates - # For now, we'll always use calendar dates if they're valid - # The "Clear Dates" button will reset the explicit flag - - # Get Date objects from calendar selections - from_date = self._create_date_from_calendar(from_calendar) - to_date = self._create_date_from_calendar(to_calendar) - - if from_date is None or to_date is None: - # Show error message for invalid dates - self._set_validation_message(_('Error: Invalid date in date range filter')) - logger.warning("Error parsing date range in filter dialog: invalid date from calendar") - self.date_range_filter = None - self.date_range_explicit = False - return - - min_sort = from_date.get_sort_value() - max_sort = to_date.get_sort_value() - - # Validate date range - if min_sort > max_sort: - # Show error message - self._set_validation_message(_('Error: From date must be before To date')) - self.date_range_filter = None - self.date_range_explicit = False - return - else: - # Clear error message - self._set_validation_message("") - - # Set filter - user has selected dates in calendars - self.date_range_filter = (min_sort, max_sort) - self.date_range_explicit = True - else: - # No calendar widgets, clear filter - self.date_range_filter = None - self.date_range_explicit = False - # Enable filter if any filter is active self.filter_enabled = ( self.active_event_types or - (self.date_range_filter is not None and self.date_range_explicit) or self.person_filter is not None or self.category_filter is not None ) @@ -1485,185 +1242,6 @@ class MyTimelineView(NavigationView): for checkbox in self._filter_widgets['event_type_checkboxes'].values(): checkbox.set_active(False) - def _sync_year_spin_from_calendar(self, calendar: Gtk.Calendar, spin_key: str, handler: Callable) -> None: - """ - Update year spin button to match calendar date. - - Args: - calendar: The calendar widget. - spin_key: Key to find the spin button in _filter_widgets. - handler: Handler function to block/unblock during update. - """ - if spin_key in self._filter_widgets: - year, month, day = calendar.get_date() - year_spin = self._filter_widgets[spin_key] - year_spin.handler_block_by_func(handler) - year_spin.set_value(year) - year_spin.handler_unblock_by_func(handler) - - def _sync_calendar_from_year_spin(self, calendar_key: str, new_year: int) -> None: - """ - Update calendar to match year spin button value. - - Args: - calendar_key: Key to find the calendar in _filter_widgets. - new_year: The new year value to set. - """ - if calendar_key in self._filter_widgets: - calendar = self._filter_widgets[calendar_key] - current_year, current_month, current_day = calendar.get_date() - # Update calendar to new year, keeping same month and day - calendar.select_month(current_month, new_year) - - def _create_date_from_calendar(self, calendar: Gtk.Calendar) -> Optional[Date]: - """ - Create a Date object from calendar selection. - - Args: - calendar: The calendar widget. - - Returns: - Optional[Date]: Date object if successful, None otherwise. - """ - try: - year, month, day = calendar.get_date() - # Note: month from calendar is 0-11, Date.set_yr_mon_day expects 1-12 - date_obj = Date() - date_obj.set_yr_mon_day(year, month + 1, day) - return date_obj - except (ValueError, AttributeError, TypeError) as e: - logger.debug(f"Error creating date from calendar: {e}") - return None - - def _on_from_date_selected(self, calendar: Gtk.Calendar) -> None: - """ - Handle From date calendar selection. - - Args: - calendar: The calendar widget that was selected. - """ - self._sync_year_spin_from_calendar(calendar, 'date_from_year_spin', self._on_from_year_changed) - self._validate_date_range() - - def _on_to_date_selected(self, calendar: Gtk.Calendar) -> None: - """ - Handle To date calendar selection. - - Args: - calendar: The calendar widget that was selected. - """ - self._sync_year_spin_from_calendar(calendar, 'date_to_year_spin', self._on_to_year_changed) - self._validate_date_range() - - def _on_from_calendar_changed(self, calendar: Gtk.Calendar) -> None: - """ - Handle From calendar month/year change. - - Args: - calendar: The calendar widget that changed. - """ - self._sync_year_spin_from_calendar(calendar, 'date_from_year_spin', self._on_from_year_changed) - - def _on_to_calendar_changed(self, calendar: Gtk.Calendar) -> None: - """ - Handle To calendar month/year change. - - Args: - calendar: The calendar widget that changed. - """ - self._sync_year_spin_from_calendar(calendar, 'date_to_year_spin', self._on_to_year_changed) - - def _on_from_year_changed(self, spin_button: Gtk.SpinButton) -> None: - """ - Handle From year spin button change. - - Args: - spin_button: The year spin button that changed. - """ - new_year = int(spin_button.get_value()) - self._sync_calendar_from_year_spin('date_from_calendar', new_year) - self._validate_date_range() - - def _on_to_year_changed(self, spin_button: Gtk.SpinButton) -> None: - """ - Handle To year spin button change. - - Args: - spin_button: The year spin button that changed. - """ - new_year = int(spin_button.get_value()) - self._sync_calendar_from_year_spin('date_to_calendar', new_year) - self._validate_date_range() - - def _on_clear_date_range(self, button: Gtk.Button) -> None: - """ - Clear the date range selection. - - Args: - button: The clear button that was clicked. - """ - if 'date_from_calendar' in self._filter_widgets and 'date_to_calendar' in self._filter_widgets: - from_calendar = self._filter_widgets['date_from_calendar'] - to_calendar = self._filter_widgets['date_to_calendar'] - - # Reset to current date (calendars always show a date) - # Get current date and set calendars to it - now = datetime.date.today() - from_calendar.select_month(now.month - 1, now.year) # month is 0-11 - from_calendar.select_day(now.day) - to_calendar.select_month(now.month - 1, now.year) - to_calendar.select_day(now.day) - - # Reset year spin buttons - if 'date_from_year_spin' in self._filter_widgets: - from_year_spin = self._filter_widgets['date_from_year_spin'] - from_year_spin.handler_block_by_func(self._on_from_year_changed) - from_year_spin.set_value(now.year) - from_year_spin.handler_unblock_by_func(self._on_from_year_changed) - - if 'date_to_year_spin' in self._filter_widgets: - to_year_spin = self._filter_widgets['date_to_year_spin'] - to_year_spin.handler_block_by_func(self._on_to_year_changed) - to_year_spin.set_value(now.year) - to_year_spin.handler_unblock_by_func(self._on_to_year_changed) - - # Clear validation message - self._set_validation_message("") - - # Mark that date range should not be applied - self.date_range_explicit = False - - def _validate_date_range(self) -> None: - """ - Validate that From date is not after To date. - """ - if 'date_from_calendar' not in self._filter_widgets or 'date_to_calendar' not in self._filter_widgets: - return - - from_calendar = self._filter_widgets['date_from_calendar'] - to_calendar = self._filter_widgets['date_to_calendar'] - - from_year, from_month, from_day = from_calendar.get_date() - to_year, to_month, to_day = to_calendar.get_date() - - # Use helper method to create dates - from_date = self._create_date_from_calendar(from_calendar) - to_date = self._create_date_from_calendar(to_calendar) - - if from_date is None or to_date is None: - return - - try: - from_sort = from_date.get_sort_value() - to_sort = to_date.get_sort_value() - - if from_sort > to_sort: - self._set_validation_message(_('Warning: From date is after To date')) - else: - self._set_validation_message("") - except (ValueError, AttributeError, TypeError): - pass - def build_tree(self) -> None: """ Rebuilds the current display. Called when the view becomes visible. @@ -1986,9 +1564,15 @@ class MyTimelineView(NavigationView): if not self.active_event_types: self._normalized_active_event_types = None else: - self._normalized_active_event_types = { - self._normalize_event_type(et) for et in self.active_event_types - } + # Normalize all event types and create a set + # Ensure we have at least one normalized type + normalized_set = {self._normalize_event_type(et) for et in self.active_event_types} + if normalized_set: + self._normalized_active_event_types = normalized_set + else: + # If normalization failed for all types, something is wrong + # Set to None to indicate no filtering (show all events) + self._normalized_active_event_types = None def _apply_event_type_filter(self, event: TimelineEvent) -> bool: """ @@ -2000,11 +1584,15 @@ class MyTimelineView(NavigationView): Returns: bool: True if event passes filter, False otherwise. """ + # If no event type filter is active (empty set means "all enabled"), pass all events if not self.active_event_types: return True # Use pre-computed normalized set if available, otherwise compute it if self._normalized_active_event_types is None: self._update_normalized_active_event_types() + # If normalized set is still None or empty, something went wrong - pass all events + if self._normalized_active_event_types is None or not self._normalized_active_event_types: + return True # Normalize event.event_type and compare with normalized active_event_types event_type_normalized = self._normalize_event_type(event.event_type) return event_type_normalized in self._normalized_active_event_types @@ -2043,10 +1631,6 @@ class MyTimelineView(NavigationView): if not self._apply_event_type_filter(event): continue - # Check date range filter - if not self._is_date_in_range(event.date_sort): - continue - # Check person filter person_handle = event.person.get_handle() if event.person else None if not self._is_person_included(person_handle): @@ -2109,21 +1693,6 @@ class MyTimelineView(NavigationView): normalized_type = self._normalize_event_type(event_type) return normalized_type in self._normalized_active_event_types - def _is_date_in_range(self, date_sort: int) -> bool: - """ - Check if a date is within the filter range. - - Args: - date_sort: The date sort value to check. - - Returns: - bool: True if date is in range (or no filter active), False otherwise. - """ - if not self.date_range_filter or not self.date_range_explicit: - return True - min_date, max_date = self.date_range_filter - return min_date <= date_sort <= max_date - def _is_person_included(self, person_handle: Optional[str]) -> bool: """ Check if a person is included in the filter.