#include "vpropertyformwidget.h" #include #include "vpropertyformwidget_p.h" #include "plugins/vwidgetproperty.h" #include #include #include "vproperty.h" #include using namespace VPE; VPropertyFormWidget::VPropertyFormWidget(const QString &title, const QString &description, const QList& properties, QWidget *parent) : QGroupBox(title, parent), d_ptr(new VPropertyFormWidgetPrivate(properties)) { build(); setToolTip(description); setWhatsThis(description); } VPropertyFormWidget::VPropertyFormWidget(VProperty *parent_property, QWidget *parent) : QGroupBox(parent), d_ptr(new VPropertyFormWidgetPrivate()) { if(parent_property) { d_ptr->Properties = parent_property->getChildren(); build(); setTitle(parent_property->getName()); setToolTip(parent_property->getDescription()); setWhatsThis(parent_property->getDescription()); } } VPropertyFormWidget::VPropertyFormWidget(VPropertyFormWidgetPrivate *d_pointer, QWidget *parent, const QString &title, const QString &description) : QGroupBox(title, parent), d_ptr(d_pointer) { build(); setToolTip(description); setWhatsThis(description); } VPropertyFormWidget::~VPropertyFormWidget() { delete d_ptr; } void VPropertyFormWidget::build() { // Clear the old content, delete old widgets d_ptr->EditorWidgets.clear(); if(layout()) { QLayoutItem *child; while (layout()->count() > 0 && (child = layout()->takeAt(0)) != 0) { if(child->widget()) delete child->widget(); delete child; } delete layout(); } // Create new content if(d_ptr->Properties.isEmpty()) return; //... only if there are properties QFormLayout* tmpFormLayout = new QFormLayout(this); setLayout(tmpFormLayout); for(int i = 0; i < d_ptr->Properties.count(); ++i) { // Get the current property VProperty* tmpProperty = d_ptr->Properties.value(i, nullptr); if(!tmpProperty) continue; if(tmpProperty->getRowCount() > 0) { // Child properties, the property itself is not being added VPropertyFormWidget* tmpNewFormWidget = new VPropertyFormWidget(tmpProperty, this); tmpFormLayout->addRow(tmpNewFormWidget); d_ptr->EditorWidgets.append(VPropertyFormWidgetPrivate::SEditorWidget(tmpNewFormWidget)); tmpNewFormWidget->setCommitBehaviour(d_ptr->UpdateEditors); } else if(tmpProperty->type() == "widget") { VWidgetProperty* tmpWidgetProperty = static_cast(tmpProperty); tmpFormLayout->addRow(tmpWidgetProperty->getWidget()); d_ptr->EditorWidgets.append(VPropertyFormWidgetPrivate::SEditorWidget(tmpWidgetProperty->getWidget())); } else { // Add property (no child properties) // Create the editor (if it doesn't work, create empty widget) QWidget* tmpEditor = tmpProperty->createEditor(this, QStyleOptionViewItem(), nullptr); if(!tmpEditor) tmpEditor = new QWidget(this); // set tooltip and whats this tmpEditor->setToolTip(tmpProperty->getDescription()); tmpEditor->setWhatsThis(tmpProperty->getDescription()); // Install event filter tmpEditor->installEventFilter(this); // Set the editor data tmpProperty->setEditorData(tmpEditor); // add new row tmpFormLayout->addRow(tmpProperty->getName(), tmpEditor); d_ptr->EditorWidgets.append(VPropertyFormWidgetPrivate::SEditorWidget(tmpEditor)); } } } void VPropertyFormWidget::commitData() { for(int i = 0; i < d_ptr->Properties.count(); ++i) commitData(i); } void VPropertyFormWidget::loadData() { for(int i = 0; i < d_ptr->Properties.count(); ++i) loadData(i); } void VPropertyFormWidget::commitData(int row) { if(row < 0 || row >= d_ptr->EditorWidgets.count() || row >= d_ptr->Properties.count()) return; VPropertyFormWidgetPrivate::SEditorWidget& tmpEditorWidget = d_ptr->EditorWidgets[row]; VProperty* tmpProperty = d_ptr->Properties[row]; if(tmpEditorWidget.FormWidget) tmpEditorWidget.FormWidget->commitData(); else if(tmpEditorWidget.Editor && tmpProperty) { QVariant newValue = tmpProperty->getEditorData(tmpEditorWidget.Editor); QVariant oldValue = tmpProperty->data(VProperty::DPC_Data, Qt::EditRole); if (oldValue != newValue) { tmpProperty->setValue(newValue); emit propertyDataSubmitted(tmpProperty); } } } void VPropertyFormWidget::loadData(int row) { if(row < 0 || row >= d_ptr->EditorWidgets.count() || row >= d_ptr->Properties.count()) return; VPropertyFormWidgetPrivate::SEditorWidget& tmpEditorWidget = d_ptr->EditorWidgets[row]; VProperty* tmpProperty = d_ptr->Properties[row]; if(tmpEditorWidget.FormWidget) tmpEditorWidget.FormWidget->loadData(); else if(tmpEditorWidget.Editor && tmpProperty) { tmpProperty->setEditorData(tmpEditorWidget.Editor); } } void VPropertyFormWidget::setCommitBehaviour(bool auto_commit) { d_ptr->UpdateEditors = auto_commit; QList tmpChildFormWidgets = getChildPropertyFormWidgets(); foreach(VPropertyFormWidget* tmpChild, tmpChildFormWidgets) { if(tmpChild) tmpChild->setCommitBehaviour(auto_commit); } } QList VPropertyFormWidget::getChildPropertyFormWidgets() const { QList tmpResult; foreach(const VPropertyFormWidgetPrivate::SEditorWidget& tmpEditorWidget, d_ptr->EditorWidgets) { if(tmpEditorWidget.FormWidget) tmpResult.append(tmpEditorWidget.FormWidget); } return tmpResult; } bool VPropertyFormWidget::eventFilter(QObject *object, QEvent *event) { if(!d_ptr->UpdateEditors) return false; QWidget* editor = qobject_cast(object); if (!editor) return false; if (event->type() == QEvent::KeyPress) { switch (static_cast(event)->key()) { case Qt::Key_Tab: case Qt::Key_Backtab: case Qt::Key_Enter: case Qt::Key_Return: case Qt::Key_Escape: commitData(editor); event->accept(); return true; default: return false; } } else if (event->type() == QEvent::FocusOut || (event->type() == QEvent::Hide && editor->isWindow())) { commitData(editor); return false; } else if (event->type() == QEvent::ShortcutOverride) { if (static_cast(event)->key() == Qt::Key_Escape) { commitData(editor); event->accept(); return true; } } else if (event->type() == MyCustomEventType) { commitData(editor); event->accept(); return true; } else { return QGroupBox::eventFilter(object, event); } // Default: return false; } void VPropertyFormWidget::commitData(QWidget *editor) { if(!editor) return; for(int i = 0; i < d_ptr->EditorWidgets.count(); ++i) { VPropertyFormWidgetPrivate::SEditorWidget& tmpEditorWidget = d_ptr->EditorWidgets[i]; if(tmpEditorWidget.Editor == editor) commitData(i); } }