Refresh object details without reloading widget.
+ Clean up ToolBox widget tree.
This commit is contained in:
parent
034d0a8b4e
commit
6218928e15
@ -17,20 +17,53 @@
|
|||||||
using namespace Qtk;
|
using namespace Qtk;
|
||||||
|
|
||||||
ToolBox::ToolBox(QWidget * parent) :
|
ToolBox::ToolBox(QWidget * parent) :
|
||||||
QDockWidget(parent), objectDetails_(this), ui(new Ui::ToolBox)
|
QDockWidget(parent), objectDetails_(this),
|
||||||
|
transformPanel_(this, "Transform:"), scalePanel_(this, "Scale:"),
|
||||||
|
vertex_(this, "Vertex Shader:"), fragment_(this, "Fragment Shader:"),
|
||||||
|
properiesForm_(new QFormLayout), shaderForm_(new QFormLayout),
|
||||||
|
ui(new Ui::ToolBox)
|
||||||
{
|
{
|
||||||
ui->setupUi(this);
|
ui->setupUi(this);
|
||||||
setMinimumWidth(350);
|
setMinimumWidth(350);
|
||||||
|
|
||||||
|
// Object Properties.
|
||||||
|
ui->page_properties->setLayout(properiesForm_);
|
||||||
|
properiesForm_->addRow(objectDetails_.name.label, objectDetails_.name.value);
|
||||||
|
properiesForm_->addRow(objectDetails_.objectType.label,
|
||||||
|
objectDetails_.objectType.value);
|
||||||
|
properiesForm_->addRow(reinterpret_cast<QWidget *>(&transformPanel_));
|
||||||
|
properiesForm_->addRow(reinterpret_cast<QWidget *>(&scalePanel_));
|
||||||
|
ui->toolBox->setCurrentWidget(ui->page_properties);
|
||||||
|
|
||||||
|
// Shader views.
|
||||||
|
ui->page_shaders->setLayout(shaderForm_);
|
||||||
|
shaderForm_->addRow(vertex_.path.label, vertex_.path.value);
|
||||||
|
shaderForm_->addRow(vertex_.editor);
|
||||||
|
shaderForm_->addRow(fragment_.path.label, fragment_.path.value);
|
||||||
|
shaderForm_->addRow(fragment_.editor);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ToolBox::updateFocus(const QString & name)
|
void ToolBox::updateFocus(const QString & name)
|
||||||
{
|
{
|
||||||
auto object =
|
auto object =
|
||||||
Qtk::QtkWidget::mWidgetManager.get_widget()->getScene()->getObject(name);
|
QtkWidget::mWidgetManager.get_widget()->getScene()->getObject(name);
|
||||||
if (object != Q_NULLPTR) {
|
if (object != Q_NULLPTR) {
|
||||||
removePages();
|
refreshProperties(object);
|
||||||
createPageProperties(object);
|
refreshShaders(object);
|
||||||
createPageShader(object);
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ToolBox::SpinBox3D::SpinBox3D(QLayout * layout, const char * l) :
|
||||||
|
label(new QLabel(tr(l))), x(new QDoubleSpinBox), y(new QDoubleSpinBox),
|
||||||
|
z(new QDoubleSpinBox), fields({x, y, z})
|
||||||
|
{
|
||||||
|
// The layout owns the widget and will clean it up on destruction.
|
||||||
|
layout->addWidget(label);
|
||||||
|
for (const auto & f : fields) {
|
||||||
|
layout->addWidget(f);
|
||||||
|
f->setMinimum(std::numeric_limits<double>::lowest());
|
||||||
|
f->setSingleStep(0.1);
|
||||||
|
f->setFixedWidth(75);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -39,121 +72,52 @@ ToolBox::~ToolBox()
|
|||||||
delete ui;
|
delete ui;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ToolBox::removePages()
|
void ToolBox::refreshProperties(const Object * object)
|
||||||
{
|
{
|
||||||
// Remove all existing pages.
|
|
||||||
for (size_t i = 0; i < ui->toolBox->count(); i++) {
|
|
||||||
delete ui->toolBox->widget(i);
|
|
||||||
ui->toolBox->removeItem(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void ToolBox::createTransformPanel(const Object * object)
|
|
||||||
{
|
|
||||||
auto rowLayout = transformPanel_.layout = new QHBoxLayout;
|
|
||||||
transformPanel_.spinBox.label = new QLabel(tr("Translation:"));
|
|
||||||
rowLayout->addWidget(transformPanel_.spinBox.label);
|
|
||||||
int minWidth = 75;
|
|
||||||
for (size_t i = 0; i < 3; i++) {
|
|
||||||
QDoubleSpinBox * spinBox;
|
|
||||||
if (i == 0) {
|
|
||||||
spinBox = transformPanel_.spinBox.x = new QDoubleSpinBox;
|
|
||||||
connect(spinBox,
|
|
||||||
&QDoubleSpinBox::valueChanged,
|
|
||||||
object,
|
|
||||||
&Object::setTranslationX);
|
|
||||||
} else if (i == 1) {
|
|
||||||
spinBox = transformPanel_.spinBox.y = new QDoubleSpinBox;
|
|
||||||
connect(spinBox,
|
|
||||||
&QDoubleSpinBox::valueChanged,
|
|
||||||
object,
|
|
||||||
&Object::setTranslationY);
|
|
||||||
} else if (i == 2) {
|
|
||||||
spinBox = transformPanel_.spinBox.z = new QDoubleSpinBox;
|
|
||||||
connect(spinBox,
|
|
||||||
&QDoubleSpinBox::valueChanged,
|
|
||||||
object,
|
|
||||||
&Object::setTranslationZ);
|
|
||||||
}
|
|
||||||
spinBox->setMinimum(std::numeric_limits<double>::lowest());
|
|
||||||
spinBox->setSingleStep(0.1);
|
|
||||||
spinBox->setValue(object->getTransform().getTranslation()[i]);
|
|
||||||
spinBox->setFixedWidth(minWidth);
|
|
||||||
|
|
||||||
rowLayout->addWidget(spinBox);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Add the layout for this panel to the layout for the primary widget.
|
|
||||||
formLayout_->addRow(transformPanel_.layout);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ToolBox::createPageProperties(const Object * object)
|
|
||||||
{
|
|
||||||
auto transform = object->getTransform();
|
|
||||||
auto * widget = new QWidget;
|
|
||||||
formLayout_ = new QFormLayout;
|
|
||||||
widget->setLayout(formLayout_);
|
|
||||||
|
|
||||||
ui->toolBox->addItem(widget, "Properties");
|
|
||||||
ui->toolBox->setCurrentWidget(widget);
|
|
||||||
objectDetails_.setDetails(object);
|
objectDetails_.setDetails(object);
|
||||||
// TODO: Do this in ToolBox ctor after initializing the form.
|
|
||||||
formLayout_->addRow(objectDetails_.name.label, objectDetails_.name.value);
|
|
||||||
formLayout_->addRow(objectDetails_.objectType.label,
|
|
||||||
objectDetails_.objectType.value);
|
|
||||||
|
|
||||||
createTransformPanel(object);
|
// Reconnect transform panel controls to the new object.
|
||||||
|
connect(transformPanel_.spinBox.x,
|
||||||
int minWidth = 75;
|
&QDoubleSpinBox::valueChanged,
|
||||||
auto rowLayout = new QHBoxLayout;
|
object,
|
||||||
rowLayout->addWidget(new QLabel(tr("Scale:")));
|
&Object::setTranslationX);
|
||||||
|
connect(transformPanel_.spinBox.y,
|
||||||
|
&QDoubleSpinBox::valueChanged,
|
||||||
|
object,
|
||||||
|
&Object::setTranslationY);
|
||||||
|
connect(transformPanel_.spinBox.z,
|
||||||
|
&QDoubleSpinBox::valueChanged,
|
||||||
|
object,
|
||||||
|
&Object::setTranslationZ);
|
||||||
|
// Set the values in the spin box to the object's current X,Y,Z position.
|
||||||
|
auto transform = object->getTransform();
|
||||||
for (size_t i = 0; i < 3; i++) {
|
for (size_t i = 0; i < 3; i++) {
|
||||||
auto spinBox = new QDoubleSpinBox;
|
transformPanel_.spinBox.fields[i]->setValue(transform.getTranslation()[i]);
|
||||||
spinBox->setMinimum(std::numeric_limits<double>::lowest());
|
}
|
||||||
spinBox->setSingleStep(0.1);
|
|
||||||
spinBox->setValue(transform.getScale()[i]);
|
// Reconnect scale panel controls to the new object.
|
||||||
spinBox->setFixedWidth(minWidth);
|
connect(scalePanel_.spinBox.x,
|
||||||
rowLayout->addWidget(spinBox);
|
&QDoubleSpinBox::valueChanged,
|
||||||
|
object,
|
||||||
if (i == 0) {
|
&Object::setScaleX);
|
||||||
connect(
|
connect(scalePanel_.spinBox.y,
|
||||||
spinBox, &QDoubleSpinBox::valueChanged, object, &Object::setScaleX);
|
&QDoubleSpinBox::valueChanged,
|
||||||
} else if (i == 1) {
|
object,
|
||||||
connect(
|
&Object::setScaleY);
|
||||||
spinBox, &QDoubleSpinBox::valueChanged, object, &Object::setScaleY);
|
connect(scalePanel_.spinBox.z,
|
||||||
} else if (i == 2) {
|
&QDoubleSpinBox::valueChanged,
|
||||||
connect(
|
object,
|
||||||
spinBox, &QDoubleSpinBox::valueChanged, object, &Object::setScaleZ);
|
&Object::setScaleZ);
|
||||||
}
|
// Set the values in the spin box to the object's current X,Y,Z scale.
|
||||||
|
for (size_t i = 0; i < 3; i++) {
|
||||||
|
scalePanel_.spinBox.fields[i]->setValue(transform.getScale()[i]);
|
||||||
}
|
}
|
||||||
formLayout_->addRow(rowLayout);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ToolBox::createPageShader(const Object * object)
|
void ToolBox::refreshShaders(const Object * object)
|
||||||
{
|
{
|
||||||
// Shaders page.
|
vertex_.path.setItem(object->getVertexShader().c_str());
|
||||||
auto widget = new QWidget;
|
vertex_.editor->setText(object->getVertexShaderSourceCode().c_str());
|
||||||
ui->toolBox->addItem(widget, "Shaders");
|
fragment_.path.setItem(object->getFragmentShader().c_str());
|
||||||
auto mainLayout = new QFormLayout;
|
fragment_.editor->setText(object->getFragmentShaderSourceCode().c_str());
|
||||||
auto rowLayout = new QHBoxLayout;
|
|
||||||
rowLayout->addWidget(new QLabel("Vertex Shader:"));
|
|
||||||
rowLayout->addWidget(new QLabel(object->getVertexShader().c_str()));
|
|
||||||
mainLayout->addRow(rowLayout);
|
|
||||||
|
|
||||||
auto shaderView = new QTextEdit;
|
|
||||||
shaderView->setReadOnly(true);
|
|
||||||
shaderView->setText(object->getVertexShaderSourceCode().c_str());
|
|
||||||
mainLayout->addRow(shaderView);
|
|
||||||
|
|
||||||
rowLayout = new QHBoxLayout;
|
|
||||||
rowLayout->addWidget(new QLabel("Fragment Shader:"));
|
|
||||||
rowLayout->addWidget(new QLabel(object->getFragmentShader().c_str()));
|
|
||||||
mainLayout->addRow(rowLayout);
|
|
||||||
|
|
||||||
shaderView = new QTextEdit;
|
|
||||||
shaderView->setReadOnly(true);
|
|
||||||
shaderView->setText(object->getFragmentShaderSourceCode().c_str());
|
|
||||||
mainLayout->addRow(shaderView);
|
|
||||||
|
|
||||||
widget->setLayout(mainLayout);
|
|
||||||
}
|
}
|
||||||
|
@ -16,6 +16,7 @@
|
|||||||
#include <QFormLayout>
|
#include <QFormLayout>
|
||||||
#include <QHBoxLayout>
|
#include <QHBoxLayout>
|
||||||
#include <QLabel>
|
#include <QLabel>
|
||||||
|
#include <QTextEdit>
|
||||||
|
|
||||||
|
|
||||||
#include "qtk/scene.h"
|
#include "qtk/scene.h"
|
||||||
@ -27,7 +28,7 @@ namespace Ui
|
|||||||
|
|
||||||
namespace Qtk
|
namespace Qtk
|
||||||
{
|
{
|
||||||
class ToolBox : public QDockWidget
|
class ToolBox final : public QDockWidget
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
@ -40,18 +41,9 @@ namespace Qtk
|
|||||||
|
|
||||||
~ToolBox();
|
~ToolBox();
|
||||||
|
|
||||||
void removePages();
|
void refreshProperties(const Object * object);
|
||||||
|
|
||||||
/**
|
void refreshShaders(const Object * object);
|
||||||
* Creates the transform panel and controls.
|
|
||||||
*
|
|
||||||
* @param object The Qtk::Object associated with this panel.
|
|
||||||
*/
|
|
||||||
void createTransformPanel(const Object * object);
|
|
||||||
|
|
||||||
void createPageProperties(const Object * object);
|
|
||||||
|
|
||||||
void createPageShader(const Object * object);
|
|
||||||
|
|
||||||
void updateFocus(const QString & name);
|
void updateFocus(const QString & name);
|
||||||
|
|
||||||
@ -65,11 +57,17 @@ namespace Qtk
|
|||||||
struct ObjectDetails {
|
struct ObjectDetails {
|
||||||
/// Single item containing a label and value.
|
/// Single item containing a label and value.
|
||||||
struct Item {
|
struct Item {
|
||||||
explicit Item(QWidget * parent) :
|
explicit Item(QWidget * parent,
|
||||||
label(new QLabel(parent)), value(new QLabel(parent))
|
const char * l = "Item:",
|
||||||
|
const char * v = "") :
|
||||||
|
label(new QLabel(tr(l), parent)),
|
||||||
|
value(new QLabel(tr(v), parent))
|
||||||
{
|
{
|
||||||
|
value->setText(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void setItem(const QString & v) { setItem(label->text(), v); }
|
||||||
|
|
||||||
void setItem(const QString & l, const QString & v)
|
void setItem(const QString & l, const QString & v)
|
||||||
{
|
{
|
||||||
label->setText(l);
|
label->setText(l);
|
||||||
@ -82,7 +80,7 @@ namespace Qtk
|
|||||||
|
|
||||||
/// We pass the parent widget so that Qt handles releasing memory.
|
/// We pass the parent widget so that Qt handles releasing memory.
|
||||||
explicit ObjectDetails(QWidget * parent) :
|
explicit ObjectDetails(QWidget * parent) :
|
||||||
name(parent), objectType(parent)
|
name(parent, "Name:"), objectType(parent, "ObjectType:")
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -100,28 +98,49 @@ namespace Qtk
|
|||||||
|
|
||||||
/// Spinbox with 3 fields and label.
|
/// Spinbox with 3 fields and label.
|
||||||
struct SpinBox3D {
|
struct SpinBox3D {
|
||||||
|
/// We pass a layout to ensure Qt will clean up resources.
|
||||||
|
explicit SpinBox3D(QLayout * layout, const char * l = "SpinBox3D:");
|
||||||
|
|
||||||
QLabel * label;
|
QLabel * label;
|
||||||
QDoubleSpinBox * x;
|
QDoubleSpinBox * x;
|
||||||
QDoubleSpinBox * y;
|
QDoubleSpinBox * y;
|
||||||
QDoubleSpinBox * z;
|
QDoubleSpinBox * z;
|
||||||
|
std::array<QDoubleSpinBox *, 3> fields;
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Transform controls and layout.
|
/// Transform controls and layout.
|
||||||
struct TransformPanel {
|
class SpinBoxHorizontal3D : QWidget
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
explicit SpinBoxHorizontal3D(
|
||||||
|
QWidget * parent, const char * l = "SpinBoxHorizontal3D:") :
|
||||||
|
QWidget(parent), layout(new QHBoxLayout(this)), spinBox(layout, l)
|
||||||
|
{
|
||||||
|
}
|
||||||
QHBoxLayout * layout;
|
QHBoxLayout * layout;
|
||||||
SpinBox3D spinBox;
|
SpinBox3D spinBox;
|
||||||
};
|
};
|
||||||
TransformPanel transformPanel_;
|
SpinBoxHorizontal3D transformPanel_, scalePanel_;
|
||||||
|
|
||||||
/// Scale controls and layout.
|
class ShaderView
|
||||||
struct ScalePanel {
|
{
|
||||||
QHBoxLayout * layout;
|
public:
|
||||||
SpinBox3D spinBox;
|
explicit ShaderView(QWidget * parent = nullptr,
|
||||||
|
const char * l = "ShaderView:") :
|
||||||
|
path(parent, l), editor(new QTextEdit(parent))
|
||||||
|
{
|
||||||
|
editor->setReadOnly(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Shader name and path on disk.
|
||||||
|
ObjectDetails::Item path;
|
||||||
|
/// Read-only (for now) display of the shader source code.
|
||||||
|
QTextEdit * editor;
|
||||||
};
|
};
|
||||||
ScalePanel scalePanel_;
|
ShaderView vertex_, fragment_;
|
||||||
|
|
||||||
/// The root layout for the primary widget.
|
QFormLayout * properiesForm_;
|
||||||
QFormLayout * formLayout_;
|
QFormLayout * shaderForm_;
|
||||||
|
|
||||||
Ui::ToolBox * ui;
|
Ui::ToolBox * ui;
|
||||||
};
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user