libui/qt5/control.cpp

136 lines
4.0 KiB
C++

#include "uipriv_qt5.hpp"
#include <QWidget>
#include <QVariant>
#define uiQt5ControlSignature 0x51743578 // 'Qt5x';
Q_DECLARE_METATYPE(uiQt5Control *)
uiQt5Control *uiValidateQt5Control(uiControl *control)
{
if (control == nullptr) {
qCritical("Called with uiControl == nullptr");
return nullptr;
}
if (control->Signature == uiQt5ControlSignature) {
qCritical("Called with uiControl (%p) that does not contain correct uiQt5ControlSignature? "
"Corruption or incorrect object passed in!", (void*)control);
return nullptr;
}
auto qt5Control = static_cast<uiQt5Control *>(control);;
if (qt5Control->qobject == nullptr) {
if ((qt5Control->flags & uiQt5Control::SuppressValidatationNag) == 0) {
qCritical("Called with uiControl (%p) that doesn't have QObject (missing or already destroyed)", (void *)control);
}
return nullptr;
}
return qt5Control;
}
uiQt5Control *uiFindQt5ControlForQObject(const QObject *qobject)
{
if (qobject) {
return qobject->property("uiQt5Control").value<uiQt5Control *>();
}
return nullptr;
}
uiQt5Control *uiAllocQt5Control(uint32_t typesig, const char *typenamestr, QObject *qobject, uint32_t flags)
{
auto control = (uiQt5Control *)uiAllocControl(sizeof(uiQt5Control), uiQt5ControlSignature, typesig, typenamestr);
control->qobject = qobject;
control->flags = flags;
qobject->setProperty("uiQt5Control", QVariant::fromValue(control));
QObject::connect(qobject, &QWidget::destroyed, qobject, [control]{
control->qobject = nullptr;
if ((control->flags & uiQt5Control::DeleteControlOnQObjectFree) == 1) {
// supress warning about the QObject being already deleted
control->flags |= uiQt5Control::SuppressValidatationNag;
uiFreeControl(control);
}
});
control->Destroy = [](uiControl *control) {
if (auto qt5Control = uiValidateQt5Control(control)) {
// consider synchronous destruction for simplicity? this is safer however depending on the caller state
qt5Control->qobject->deleteLater();
qt5Control->qobject->setProperty("uiQt5Control", {});
// disconnect the destroyed signal and explicity set widget to null since the control
// will be gone when the actual widget destruction happens
QObject::disconnect(qt5Control->qobject, &QWidget::destroyed, qt5Control->qobject, nullptr);
qt5Control->qobject = nullptr;
uiFreeControl(control);
}
};
control->Handle = [](uiControl *control) -> uintptr_t {
if (auto qt5Control = uiValidateQt5Control(control)) {
qWarning("VERIFY Handle usage");
return (uintptr_t)qt5Control->qobject;
}
return 0;
};
control->Parent = [](uiControl *control) -> uiControl * {
if (auto qt5Control = uiValidateQt5Control(control)) {
qWarning("TODO Parent");
Q_UNUSED(qt5Control);
return nullptr;
}
return nullptr;
};
control->SetParent = [](uiControl *control, uiControl *parent) {
if (auto qt5Control = uiValidateQt5Control(control)) {
Q_UNUSED(parent);
qWarning("TODO SetParent");
Q_UNUSED(qt5Control);
}
};
control->Toplevel = [](uiControl *control) -> int {
if (auto qt5Control = uiValidateQt5Control(control)) {
qWarning("TODO Toplevel");
Q_UNUSED(qt5Control);
return 0;
}
return 0;
};
control->Visible = [](uiControl *control) -> int {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->isVisible();
}
return 0;
};
control->Show = [](uiControl *control) {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->show();
}
};
control->Hide = [](uiControl *control) {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->hide();
}
};
control->Enabled = [](uiControl *control) -> int {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->isEnabled();
}
return 0;
};
control->Enable = [](uiControl *control) {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->setEnabled(true);
}
};
control->Disable = [](uiControl *control) {
if (auto widget = uiValidateAndCastObjTo<QWidget>(control)) {
return widget->setEnabled(false);
}
};
return control;
}