File indexing completed on 2024-05-19 05:42:22
0001 // ct_lvtqtc_pluginmanagerutils.cpp -*-C++-*- 0002 0003 /* 0004 // Copyright 2023 Codethink Ltd <codethink@codethink.co.uk> 0005 // SPDX-License-Identifier: Apache-2.0 0006 // 0007 // Licensed under the Apache License, Version 2.0 (the "License"); 0008 // you may not use this file except in compliance with the License. 0009 // You may obtain a copy of the License at 0010 // 0011 // http://www.apache.org/licenses/LICENSE-2.0 0012 // 0013 // Unless required by applicable law or agreed to in writing, software 0014 // distributed under the License is distributed on an "AS IS" BASIS, 0015 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 0016 // See the License for the specific language governing permissions and 0017 // limitations under the License. 0018 */ 0019 0020 #include <QDockWidget> 0021 #include <QFormLayout> 0022 #include <QLabel> 0023 #include <QLineEdit> 0024 #include <QTreeView> 0025 #include <ct_lvtqtc_lakosentitypluginutils.h> 0026 #include <ct_lvtqtc_pluginmanagerutils.h> 0027 0028 namespace Codethink::lvtqtc { 0029 0030 using lvtplg::PluginManager; 0031 using QtUserDataMap = QMap<QString, void *>; 0032 0033 PluginTreeItemHandler PluginManagerQtUtils::createPluginTreeItemHandler( 0034 PluginManager *pm, QTreeView *treeView, QStandardItemModel *treeModel, QStandardItem *item, GraphicsScene *gs) 0035 { 0036 auto getPluginData = [pm](auto&& id) { 0037 return pm->getPluginData(id); 0038 }; 0039 auto addItem = [pm, treeView, treeModel, item, gs](std::string const& label) { 0040 auto *child = new QStandardItem(QString::fromStdString(label)); 0041 child->setData(QVariant::fromValue(QtUserDataMap{})); 0042 item->appendRow(child); 0043 return createPluginTreeItemHandler(pm, treeView, treeModel, child, gs); 0044 }; 0045 auto addOnClickAction = [pm, treeView, treeModel, item, gs]( 0046 std::function<void(PluginTreeItemClickedActionHandler * selectedItem)> const& f) { 0047 QObject::connect(treeView, 0048 &QTreeView::clicked, 0049 treeView, 0050 [pm, item, f, treeView, treeModel, gs](const QModelIndex& index) { 0051 auto *selectedItem = qobject_cast<QStandardItemModel *>(treeModel)->itemFromIndex(index); 0052 if (selectedItem != item) { 0053 return; 0054 } 0055 auto handler = createPluginTreeItemClickedActionHandler(pm, treeView, treeModel, item, gs); 0056 f(&handler); 0057 }); 0058 }; 0059 auto addUserData = [item](std::string const& dataId, void *userData) { 0060 auto userDataMap = item->data().value<QtUserDataMap>(); 0061 userDataMap[QString::fromStdString(dataId)] = userData; 0062 item->setData(QVariant::fromValue(userDataMap)); 0063 }; 0064 auto getUserData = [item](std::string const& dataId) { 0065 auto userDataMap = item->data().value<QtUserDataMap>(); 0066 return userDataMap[QString::fromStdString(dataId)]; 0067 }; 0068 return PluginTreeItemHandler{getPluginData, addItem, addUserData, getUserData, addOnClickAction}; 0069 } 0070 0071 PluginTreeWidgetHandler 0072 PluginManagerQtUtils::createPluginTreeWidgetHandler(PluginManager *pm, std::string const& id, GraphicsScene *gs) 0073 { 0074 auto getPluginData = [pm](auto&& id) { 0075 return pm->getPluginData(id); 0076 }; 0077 auto addRootItem = [pm, id, gs](std::string const& label) -> PluginTreeItemHandler { 0078 auto *treeView = dynamic_cast<QTreeView *>(pm->getPluginQObject(id + "::view")); 0079 auto *treeModel = dynamic_cast<QStandardItemModel *>(pm->getPluginQObject(id + "::model")); 0080 auto *item = new QStandardItem(QString::fromStdString(label)); 0081 item->setData(QVariant::fromValue(QtUserDataMap{})); 0082 treeModel->invisibleRootItem()->appendRow(item); 0083 return PluginManagerQtUtils::createPluginTreeItemHandler(pm, treeView, treeModel, item, gs); 0084 }; 0085 0086 auto clear = [pm, id]() { 0087 auto *treeModel = dynamic_cast<QStandardItemModel *>(pm->getPluginQObject(id + "::model")); 0088 treeModel->clear(); 0089 }; 0090 0091 return PluginTreeWidgetHandler{getPluginData, addRootItem, clear}; 0092 } 0093 0094 PluginTreeItemClickedActionHandler PluginManagerQtUtils::createPluginTreeItemClickedActionHandler( 0095 PluginManager *pm, QTreeView *treeView, QStandardItemModel *treeModel, QStandardItem *item, GraphicsScene *gs) 0096 { 0097 auto getPluginData = [pm](auto&& id) { 0098 return pm->getPluginData(id); 0099 }; 0100 auto getItem = [pm, treeView, treeModel, item, gs]() { 0101 return createPluginTreeItemHandler(pm, treeView, treeModel, item, gs); 0102 }; 0103 auto getGraphicsView = [gs]() { 0104 return createPluginGraphicsViewHandler(gs); 0105 }; 0106 0107 return PluginTreeItemClickedActionHandler{getPluginData, getItem, getGraphicsView}; 0108 } 0109 0110 PluginGraphicsViewHandler PluginManagerQtUtils::createPluginGraphicsViewHandler(GraphicsScene *gs) 0111 { 0112 auto getEntityByQualifiedName = [gs](std::string const& qualifiedName) -> std::optional<Entity> { 0113 auto *e = gs->entityByQualifiedName(qualifiedName); 0114 if (!e) { 0115 return std::nullopt; 0116 } 0117 return createWrappedEntityFromLakosEntity(e); 0118 }; 0119 auto getVisibleEntities = [gs]() { 0120 auto entities = std::vector<Entity>{}; 0121 for (auto&& e : gs->allEntities()) { 0122 entities.push_back(createWrappedEntityFromLakosEntity(e)); 0123 } 0124 return entities; 0125 }; 0126 auto getEdgeByQualifiedName = [gs](std::string const& fromQualifiedName, 0127 std::string const& toQualifiedName) -> std::optional<Edge> { 0128 auto *fromEntity = gs->entityByQualifiedName(fromQualifiedName); 0129 if (!fromEntity) { 0130 return std::nullopt; 0131 } 0132 auto *toEntity = gs->entityByQualifiedName(toQualifiedName); 0133 if (!toEntity) { 0134 return std::nullopt; 0135 } 0136 return createWrappedEdgeFromLakosEntity(fromEntity, toEntity); 0137 }; 0138 0139 return PluginGraphicsViewHandler{getEntityByQualifiedName, getVisibleEntities, getEdgeByQualifiedName}; 0140 } 0141 0142 PluginDockWidgetHandler PluginManagerQtUtils::createPluginDockWidgetHandler(PluginManager *pm, 0143 std::string const& dockId) 0144 { 0145 auto addDockWdgFileField = [pm, dockId](std::string const& label, std::string& dataModel) { 0146 auto *pluginDockWidget = dynamic_cast<QDockWidget *>(pm->getPluginQObject(dockId)); 0147 if (pluginDockWidget == nullptr) { 0148 return; 0149 } 0150 auto *lineEdit = new QLineEdit(); 0151 QObject::connect(lineEdit, &QLineEdit::textChanged, pluginDockWidget, [&dataModel](QString const& newText) { 0152 dataModel = newText.toStdString(); 0153 }); 0154 auto *formLayout = dynamic_cast<QFormLayout *>(pluginDockWidget->widget()->layout()); 0155 formLayout->addRow(new QLabel(QString::fromStdString(label)), lineEdit); 0156 }; 0157 auto addTree = [pm, dockId](std::string const& treeId) { 0158 auto *pluginDockWidget = dynamic_cast<QDockWidget *>(pm->getPluginQObject(dockId)); 0159 if (pluginDockWidget == nullptr) { 0160 return; 0161 } 0162 auto *treeView = new QTreeView(pluginDockWidget); 0163 auto *treeModel = new QStandardItemModel{treeView}; 0164 treeView->setHeaderHidden(true); 0165 treeView->setModel(treeModel); 0166 auto *formLayout = dynamic_cast<QFormLayout *>(pluginDockWidget->widget()->layout()); 0167 formLayout->addRow(treeView); 0168 pm->registerPluginQObject(treeId + "::view", treeView); 0169 pm->registerPluginQObject(treeId + "::model", treeModel); 0170 }; 0171 auto setVisible = [pm, dockId](bool visible) { 0172 auto *pluginDockWidget = dynamic_cast<QDockWidget *>(pm->getPluginQObject(dockId)); 0173 if (pluginDockWidget == nullptr) { 0174 return; 0175 } 0176 pluginDockWidget->setVisible(visible); 0177 }; 0178 0179 return PluginDockWidgetHandler{addDockWdgFileField, addTree, setVisible}; 0180 } 0181 0182 } // namespace Codethink::lvtqtc