Created attachment 163125 [details] ksortfilter-bug.qml SUMMARY KSortFilterProxyModel exhibits "race condition" bug: depending on order of property initialization (which isn't quite defined in QML, except that more "complex" expressions are known to evaluate later than the simple literals and enums), it may end up with filterRole reset to 0 (thus the whole filtering not working, as currently in Flatpak KCM -> application list), or a model emits inappropriate rowsAdded signal which causes a view (e.g. ListView) to create a phantom and empty delegate which won't even ever be deleted. STEPS TO REPRODUCE 1. Run the attached file with qml or kqml tool. It uses plasma-pa/SinkModel as an example, so make sure you have some functional speakers/headphones or replace it with some other model. 2. Type in anything in the search field. 3. Toggle ON the "Set model" check box. 4. Click the "Set filter role" button. 5. Clear the search field. OBSERVED RESULT After step 4, an empty delegate appears in the ListView. After step 5, an empty delegate remains alive at the bottom of the list of your audio devices. EXPECTED RESULT No empty glitched delegates. No races between filterRole and model properties. SOFTWARE/OS VERSIONS Operating System: Arch Linux KDE Plasma Version: 5.81.0 KDE Frameworks Version: 5.245.0 Qt Version: 6.6.0 Kernel Version: 6.6.1-arch1-1 (64-bit) Graphics Platform: X11
Created attachment 163127 [details] automated and animated version A more interactive demo with a button to run the whole sequence. Uncomment `Component.onCompleted` handler to run on start. Note that with small timer delays on start the bug sometimes does not happen, probably because timer triggers or animation finishes before the component is completed which masks the issue.
A possibly relevant merge request was started @ https://invent.kde.org/frameworks/kitemmodels/-/merge_requests/85
Git commit 4a9df06bc89e7c23a16832f7300e2efc7e9a1ee8 by ivan tkachenko. Committed on 14/11/2023 at 22:14. Pushed by ratijas into branch 'master'. KSortFilterProxyModel: Fix multiple sources of truth confusion Sort and filter roles may come from upstream model's properties (by ID) or from our class (by role name), and it is important to keep track which one was set explicitly and thus should be considered the source of truth at any given moment in time -- especially if/when source model is set afterwards such that these pairs of properties can not sync immediately and have to be delayed instead. To solve this problem, the an object now stores a flag which determined the source of truth per each pair, and another flag to prevent recursion and switch to "Role ID" source when *RoleChanged signals are emitted NOT as a side-effect of us updating a corresponding *RoleName. M +93 -3 autotests/ksortfilterproxymodel_qml.cpp M +96 -39 src/qml/ksortfilterproxymodel.cpp M +24 -3 src/qml/ksortfilterproxymodel.h https://invent.kde.org/frameworks/kitemmodels/-/commit/4a9df06bc89e7c23a16832f7300e2efc7e9a1ee8
Git commit 077f49e294e999e8e927bc745576aa472beee2e5 by ivan tkachenko. Committed on 14/11/2023 at 22:14. Pushed by ratijas into branch 'master'. KSortFilterProxyModel: Don't recurse into syncRoleNames Row count of a proxy model changes as it filters its source model, but that's not a good reason to refresh role names every time. Instead we are only interested in source model's changes. This reduces amount of insert/remove back and forth signals during filtering, and fixes the permanent "ghost delegate" at the end of a ListView. M +18 -3 src/qml/ksortfilterproxymodel.cpp M +3 -0 src/qml/ksortfilterproxymodel.h https://invent.kde.org/frameworks/kitemmodels/-/commit/077f49e294e999e8e927bc745576aa472beee2e5
*** Bug 464116 has been marked as a duplicate of this bug. ***