diff --git a/gui/include/DataSource/DataSourceTreeWidgetHelper.h b/gui/include/DataSource/DataSourceTreeWidgetHelper.h new file mode 100644 index 0000000..9e1e849 --- /dev/null +++ b/gui/include/DataSource/DataSourceTreeWidgetHelper.h @@ -0,0 +1,23 @@ +#ifndef SCIQLOP_DATASOURCETREEWIDGETHELPER_H +#define SCIQLOP_DATASOURCETREEWIDGETHELPER_H + +#include + +class DataSourceTreeWidgetItem; +class QTreeWidget; + +class DataSourceTreeWidgetHelper { +public: + /// Signature of the function associated to the filtering action + using FilterFunction = std::function; + + /** + * Filters a tree widget according to a function. If an item is valid according to this + * function, all of its ancestors and children are shown + * @param treeWidget the widget to filter + * @param fun the filter function + */ + static void filter(QTreeWidget &treeWidget, FilterFunction fun) noexcept; +}; + +#endif // SCIQLOP_DATASOURCETREEWIDGETHELPER_H diff --git a/gui/src/DataSource/DataSourceTreeWidgetHelper.cpp b/gui/src/DataSource/DataSourceTreeWidgetHelper.cpp new file mode 100644 index 0000000..b5b969b --- /dev/null +++ b/gui/src/DataSource/DataSourceTreeWidgetHelper.cpp @@ -0,0 +1,36 @@ +#include "DataSource/DataSourceTreeWidgetHelper.h" +#include "DataSource/DataSourceTreeWidgetItem.h" + +namespace { + +bool filterTreeItem(DataSourceTreeWidgetItem &treeItem, + DataSourceTreeWidgetHelper::FilterFunction fun, bool parentValid = false) +{ + auto selfValid = parentValid || fun(treeItem); + + auto childValid = false; + auto childCount = treeItem.childCount(); + for (auto i = 0; i < childCount; ++i) { + if (auto childItem = dynamic_cast(treeItem.child(i))) { + childValid |= filterTreeItem(*childItem, fun, selfValid); + } + } + + auto valid = selfValid || childValid; + + treeItem.setHidden(!valid); + + return valid; +} + +} // namespace + +void DataSourceTreeWidgetHelper::filter(QTreeWidget &treeWidget, FilterFunction fun) noexcept +{ + auto itemCount = treeWidget.topLevelItemCount(); + for (auto i = 0; i < itemCount; ++i) { + if (auto item = dynamic_cast(treeWidget.topLevelItem(i))) { + filterTreeItem(*item, fun); + } + } +}