diff --git a/src/backend/backend.py b/src/backend/backend.py index 012fe355..caafb2de 100644 --- a/src/backend/backend.py +++ b/src/backend/backend.py @@ -284,6 +284,11 @@ class Backend: history = await self.history.read() theme = await Theme(self, settings["theme"]).read() + state_data = self.ui_state._data + if state_data: + for user, collapse in state_data["collapseAccounts"].items(): + self.models["all_rooms"].set_account_collapse(user, collapse) + return (settings, ui_state, history, theme) @@ -320,3 +325,7 @@ class Backend: raise TypeError("model_id must point to a FieldSubstringFilter") model.filter = value + + + async def set_account_collapse(self, user_id: str, collapse: bool) -> None: + self.models["all_rooms"].set_account_collapse(user_id, collapse) diff --git a/src/backend/models/special_models.py b/src/backend/models/special_models.py index 9e278e59..d6642670 100644 --- a/src/backend/models/special_models.py +++ b/src/backend/models/special_models.py @@ -1,9 +1,10 @@ # SPDX-License-Identifier: LGPL-3.0-or-later from dataclasses import asdict +from typing import Set from .filters import FieldSubstringFilter, ModelFilter -from .items import Account, AccountOrRoom +from .items import Account, AccountOrRoom, Room from .model import Model from .model_item import ModelItem @@ -13,6 +14,21 @@ class AllRooms(FieldSubstringFilter): super().__init__(sync_id="all_rooms", fields=("display_name",)) self.items_changed_callbacks.append(self.refilter_accounts) + self._collapsed: Set[str] = set() + + + def set_account_collapse(self, user_id: str, collapsed: bool) -> None: + def only_if(item): + return item.type is Room and item.for_account == user_id + + if collapsed and user_id not in self._collapsed: + self._collapsed.add(user_id) + self.refilter(only_if) + + if not collapsed and user_id in self._collapsed: + self._collapsed.remove(user_id) + self.refilter(only_if) + def accept_source(self, source: Model) -> bool: return source.sync_id == "accounts" or ( @@ -27,9 +43,16 @@ class AllRooms(FieldSubstringFilter): def accept_item(self, item: ModelItem) -> bool: + assert isinstance(item, AccountOrRoom) # nosec + + if not self.filter and \ + item.type is Room and \ + item.for_account in self._collapsed: + return False + matches_filter = super().accept_item(item) - if item.type is not Account or not self.filter: # type: ignore + if item.type is not Account or not self.filter: return matches_filter return next( @@ -38,9 +61,7 @@ class AllRooms(FieldSubstringFilter): def refilter_accounts(self) -> None: - self.refilter( - lambda i: isinstance(i, AccountOrRoom) and i.type is Account, - ) + self.refilter(lambda i: i.type is Account) # type: ignore class MatchingAccounts(ModelFilter): diff --git a/src/gui/MainPane/Account.qml b/src/gui/MainPane/Account.qml index b15fcc86..0419456f 100644 --- a/src/gui/MainPane/Account.qml +++ b/src/gui/MainPane/Account.qml @@ -116,6 +116,8 @@ HTileDelegate { function setCollapse(collapse) { window.uiState.collapseAccounts[model.id] = collapse window.uiStateChanged() + + py.callCoro("set_account_collapse", [model.id, collapse]) } function toggleCollapse() {