1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-28 15:05:08 +00:00

VisualBuilder: Add a table view with the selected widget's properties.

This commit is contained in:
Andreas Kling 2019-04-11 21:41:09 +02:00
parent c57cf9834b
commit 707bfe848d
11 changed files with 113 additions and 6 deletions

View file

@ -2,6 +2,7 @@ OBJS = \
VBForm.o \
VBWidget.o \
VBWidgetRegistry.o \
VBWidgetPropertyModel.o \
VBProperty.o \
main.o

View file

@ -105,6 +105,8 @@ void VBForm::mousedown_event(GMouseEvent& event)
if (!widget) {
if (m_selected_widget) {
m_selected_widget = nullptr;
if (on_widget_selected)
on_widget_selected(nullptr);
update();
}
return;
@ -113,6 +115,8 @@ void VBForm::mousedown_event(GMouseEvent& event)
m_selected_widget = widget->make_weak_ptr();
m_transform_event_origin = event.position();
m_transform_widget_origin_rect = widget->rect();
if (on_widget_selected)
on_widget_selected(widget);
update();
}
}

View file

@ -22,6 +22,8 @@ public:
void insert_widget(VBWidgetType);
Function<void(VBWidget*)> on_widget_selected;
protected:
virtual void paint_event(GPaintEvent&) override;
virtual void second_paint_event(GPaintEvent&) override;

View file

@ -9,6 +9,7 @@ public:
~VBProperty();
String name() const { return m_name; }
const GVariant& value() const { return m_value; }
bool is_readonly() const { return m_readonly; }
void set_readonly(bool b) { m_readonly = b; }

View file

@ -2,11 +2,13 @@
#include "VBForm.h"
#include "VBProperty.h"
#include "VBWidgetRegistry.h"
#include "VBWidgetPropertyModel.h"
#include <LibGUI/GPainter.h>
VBWidget::VBWidget(VBWidgetType type, VBForm& form)
: m_type(type)
, m_form(form)
, m_property_model(VBWidgetPropertyModel::create(*this))
{
m_gwidget = VBWidgetRegistry::build_gwidget(type, &form, m_properties);
}
@ -69,6 +71,6 @@ Direction VBWidget::grabber_at(const Point& position) const
void VBWidget::for_each_property(Function<void(VBProperty&)> callback)
{
for (auto& it : m_properties) {
callback(*it.value);
callback(*it);
}
}

View file

@ -12,6 +12,7 @@ class GPainter;
class GWidget;
class VBForm;
class VBProperty;
class VBWidgetPropertyModel;
enum class Direction { None, Left, UpLeft, Up, UpRight, Right, DownRight, Down, DownLeft };
template<typename Callback>
@ -28,6 +29,7 @@ inline void for_each_direction(Callback callback)
}
class VBWidget : public Retainable<VBWidget>, public Weakable<VBWidget> {
friend class VBWidgetPropertyModel;
public:
static Retained<VBWidget> create(VBWidgetType type, VBForm& form) { return adopt(*new VBWidget(type, form)); }
~VBWidget();
@ -47,6 +49,8 @@ public:
void for_each_property(Function<void(VBProperty&)>);
VBWidgetPropertyModel& property_model() { return *m_property_model; }
protected:
VBWidget(VBWidgetType, VBForm&);
@ -54,5 +58,6 @@ private:
VBWidgetType m_type { VBWidgetType::None };
VBForm& m_form;
GWidget* m_gwidget { nullptr };
HashMap<String, OwnPtr<VBProperty>> m_properties;
Vector<OwnPtr<VBProperty>> m_properties;
Retained<VBWidgetPropertyModel> m_property_model;
};

View file

@ -0,0 +1,52 @@
#include "VBWidgetPropertyModel.h"
#include "VBWidget.h"
#include "VBProperty.h"
VBWidgetPropertyModel::VBWidgetPropertyModel(VBWidget& widget)
: m_widget(widget)
{
}
VBWidgetPropertyModel::~VBWidgetPropertyModel()
{
ASSERT_NOT_REACHED();
}
int VBWidgetPropertyModel::row_count(const GModelIndex&) const
{
dbgprintf("row count: %d\n", m_widget.m_properties.size());
return m_widget.m_properties.size();
}
String VBWidgetPropertyModel::column_name(int column) const
{
switch (column) {
case Column::Name: return "Name";
case Column::Value: return "Value";
default: ASSERT_NOT_REACHED();
}
}
GModel::ColumnMetadata VBWidgetPropertyModel::column_metadata(int column) const
{
UNUSED_PARAM(column);
return { 100, TextAlignment::CenterLeft };
}
GVariant VBWidgetPropertyModel::data(const GModelIndex& index, Role role) const
{
if (role == Role::Display) {
dbgprintf("Accessing prop #%d (size=%d) column %d\n", index.row(), m_widget.m_properties.size(), index.column());
auto& property = *m_widget.m_properties[index.row()];
auto value = property.value();
dbgprintf("value type=%u\n", (unsigned)value.type());
dbgprintf("value impl=%x\n", (unsigned)value.to_string().impl());
dbgprintf("value len=%x\n", (unsigned)value.to_string().impl()->length());
dbgprintf("for value='%s'\n", value.to_string().characters());
switch (index.column()) {
case Column::Name: return property.name();
case Column::Value: return property.value();
}
}
return { };
}

View file

@ -0,0 +1,30 @@
#pragma once
#include <LibGUI/GModel.h>
class VBWidget;
class VBProperty;
class VBWidgetPropertyModel : public GModel {
public:
enum Column {
Name = 0,
Value,
__Count
};
static Retained<VBWidgetPropertyModel> create(VBWidget& widget) { return adopt(*new VBWidgetPropertyModel(widget)); }
virtual ~VBWidgetPropertyModel() override;
virtual int row_count(const GModelIndex&) const override;
virtual int column_count(const GModelIndex&) const override { return Column::__Count; }
virtual String column_name(int column) const override;
virtual ColumnMetadata column_metadata(int column) const override;
virtual GVariant data(const GModelIndex&, Role = Role::Display) const override;
virtual void update() override { }
private:
explicit VBWidgetPropertyModel(VBWidget&);
VBWidget& m_widget;
};

View file

@ -74,13 +74,13 @@ static GWidget* build_gwidget(VBWidgetType type, GWidget* parent)
}
GWidget* VBWidgetRegistry::build_gwidget(VBWidgetType type, GWidget* parent, HashMap<String, OwnPtr<VBProperty>>& properties)
GWidget* VBWidgetRegistry::build_gwidget(VBWidgetType type, GWidget* parent, Vector<OwnPtr<VBProperty>>& properties)
{
auto* gwidget = ::build_gwidget(type, parent);
auto add_property = [&properties] (const String& name, const GVariant& value, bool is_readonly) {
auto property = make<VBProperty>(name, value);
property->set_readonly(is_readonly);
properties.set(name, move(property));
properties.append(move(property));
};
add_property("ClassName", to_class_name(type), true);
return gwidget;

View file

@ -16,5 +16,5 @@ public:
callback((VBWidgetType)i);
}
static GWidget* build_gwidget(VBWidgetType, GWidget* parent, HashMap<String, OwnPtr<VBProperty>>&);
static GWidget* build_gwidget(VBWidgetType, GWidget* parent, Vector<OwnPtr<VBProperty>>&);
};

View file

@ -5,8 +5,10 @@
#include <LibGUI/GMenuBar.h>
#include <LibGUI/GAction.h>
#include <LibGUI/GButton.h>
#include <LibGUI/GTableView.h>
#include "VBForm.h"
#include "VBWidget.h"
#include "VBWidgetPropertyModel.h"
#include <unistd.h>
#include <stdio.h>
#include <signal.h>
@ -15,11 +17,18 @@
static GWindow* make_toolbox_window();
static GWindow* make_properties_window();
GTableView* g_property_table_view;
int main(int argc, char** argv)
{
GApplication app(argc, argv);
auto* propbox = make_properties_window();
auto* form1 = new VBForm("Form1");
form1->on_widget_selected = [] (VBWidget* widget) {
g_property_table_view->set_model(widget ? &widget->property_model() : nullptr);
};
auto menubar = make<GMenuBar>();
auto app_menu = make<GMenu>("Visual Builder");
@ -53,7 +62,6 @@ int main(int argc, char** argv)
auto* toolbox = make_toolbox_window();
toolbox->show();
auto* propbox = make_properties_window();
propbox->show();
return app.exec();
@ -141,5 +149,7 @@ GWindow* make_properties_window()
widget->set_layout(make<GBoxLayout>(Orientation::Vertical));
window->set_main_widget(widget);
g_property_table_view = new GTableView(widget);
return window;
}