Browse Source

Start to pass events into top-level and subwidgets

Signed-off-by: falkTX <falktx@falktx.com>
pull/272/head
falkTX 4 years ago
parent
commit
d3c5705122
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
9 changed files with 98 additions and 59 deletions
  1. +3
    -1
      dgl/src/SubWidget.cpp
  2. +20
    -9
      dgl/src/TopLevelWidgetPrivateData.cpp
  3. +1
    -0
      dgl/src/TopLevelWidgetPrivateData.hpp
  4. +34
    -6
      dgl/src/WidgetPrivateData.cpp
  5. +1
    -3
      dgl/src/WidgetPrivateData.hpp
  6. +27
    -0
      dgl/src/WindowPrivateData.cpp
  7. +2
    -0
      dgl/src/WindowPrivateData.hpp
  8. +2
    -32
      tests/Demo.cpp
  9. +8
    -8
      tests/widgets/ExampleRectanglesWidget.hpp

+ 3
- 1
dgl/src/SubWidget.cpp View File

@@ -100,9 +100,11 @@ void SubWidget::setAbsolutePos(const Point<int>& pos) noexcept
pData->parentWidget->repaint();
}


void SubWidget::repaint() noexcept
{
if (! isVisible())
return;

if (TopLevelWidget* const topw = getTopLevelWidget())
topw->repaint(getConstrainedAbsoluteArea());
}


+ 20
- 9
dgl/src/TopLevelWidgetPrivateData.cpp View File

@@ -21,12 +21,6 @@

START_NAMESPACE_DGL

#define FOR_EACH_WIDGET(it) \
for (std::list<Widget*>::iterator it = widgets.begin(); it != widgets.end(); ++it)

#define FOR_EACH_WIDGET_INV(rit) \
for (std::list<Widget*>::reverse_iterator rit = widgets.rbegin(); rit != widgets.rend(); ++rit)

// -----------------------------------------------------------------------

TopLevelWidget::PrivateData::PrivateData(TopLevelWidget* const s, Window& w)
@@ -45,13 +39,10 @@ TopLevelWidget::PrivateData::~PrivateData()

void TopLevelWidget::PrivateData::display()
{
printf("TopLevelWidget::PrivateData::display INIT\n");

const Size<uint> size(window.getSize());
const uint width = size.getWidth();
const uint height = size.getHeight();
const double autoScaling = window.pData->autoScaling;
printf("TopLevelWidget::PrivateData::display %i %i\n", width, height);

// full viewport size
glViewport(0, -(height * autoScaling - height), width * autoScaling, height * autoScaling);
@@ -63,6 +54,26 @@ void TopLevelWidget::PrivateData::display()
selfw->pData->displaySubWidgets(width, height, autoScaling);
}

void TopLevelWidget::PrivateData::mouseEvent(const Events::MouseEvent& ev)
{
Events::MouseEvent rev = ev;

const double autoScaling = window.pData->autoScaling;

if (autoScaling != 1.0)
{
rev.pos.setX(ev.pos.getX() / autoScaling);
rev.pos.setY(ev.pos.getY() / autoScaling);
}

// give top-level widget chance to catch this event first
if (self->onMouse(ev))
return;

// propagate event to all subwidgets recursively
selfw->pData->giveMouseEventForSubWidgets(rev);
}

// -----------------------------------------------------------------------

END_NAMESPACE_DGL

+ 1
- 0
dgl/src/TopLevelWidgetPrivateData.hpp View File

@@ -33,6 +33,7 @@ struct TopLevelWidget::PrivateData {
explicit PrivateData(TopLevelWidget* const s, Window& w);
~PrivateData();
void display();
void mouseEvent(const Events::MouseEvent& ev);

DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(PrivateData)
};


+ 34
- 6
dgl/src/WidgetPrivateData.cpp View File

@@ -15,10 +15,17 @@
*/

#include "WidgetPrivateData.hpp"
#include "../SubWidget.hpp"
#include "../TopLevelWidget.hpp"

START_NAMESPACE_DGL

#define FOR_EACH_SUBWIDGET(it) \
for (std::list<SubWidget*>::iterator it = subWidgets.begin(); it != subWidgets.end(); ++it)

#define FOR_EACH_SUBWIDGET_INV(rit) \
for (std::list<SubWidget*>::reverse_iterator rit = subWidgets.rbegin(); rit != subWidgets.rend(); ++rit)

// -----------------------------------------------------------------------

Widget::PrivateData::PrivateData(Widget* const s, TopLevelWidget* const tlw)
@@ -48,17 +55,40 @@ Widget::PrivateData::~PrivateData()

void Widget::PrivateData::displaySubWidgets(const uint width, const uint height, const double scaling)
{
printf("Widget::PrivateData::displaySubWidgets INIT | %lu\n", subWidgets.size());

if (subWidgets.size() == 0)
return;

for (std::list<SubWidget*>::iterator it = subWidgets.begin(); it != subWidgets.end(); ++it)
{
SubWidget* const subwidget(*it);
printf("Widget::PrivateData::displaySubWidgets %i %i -> %p\n", width, height, subwidget);

subwidget->pData->display(width, height, scaling);
if (subwidget->isVisible())
subwidget->pData->display(width, height, scaling);
}
}

void Widget::PrivateData::giveMouseEventForSubWidgets(Events::MouseEvent& ev)
{
if (! visible)
return;
if (subWidgets.size() == 0)
return;

const double x = ev.pos.getX();
const double y = ev.pos.getY();

FOR_EACH_SUBWIDGET_INV(rit)
{
SubWidget* const widget(*rit);

if (! widget->isVisible())
continue;

ev.pos = Point<double>(x - widget->getAbsoluteX(),
y - widget->getAbsoluteY());

if (widget->onMouse(ev))
return;
}
}

@@ -66,8 +96,6 @@ void Widget::PrivateData::displaySubWidgets(const uint width, const uint height,

TopLevelWidget* Widget::PrivateData::findTopLevelWidget(Widget* const w)
{
// if (TopLevelWidget* const tlw = dynamic_cast<TopLevelWidget*>(w))
// return tlw;
if (w->pData->topLevelWidget != nullptr)
return w->pData->topLevelWidget;
if (w->pData->parentWidget != nullptr)


+ 1
- 3
dgl/src/WidgetPrivateData.hpp View File

@@ -41,10 +41,8 @@ struct Widget::PrivateData {
explicit PrivateData(Widget* const s, Widget* const pw);
~PrivateData();

// NOTE display function is different depending on build type, must call displaySubWidgets at the end
// void display(uint width, uint height, double autoScaling, bool renderingSubWidget);

void displaySubWidgets(uint width, uint height, double autoScaling);
void giveMouseEventForSubWidgets(Events::MouseEvent& ev);

static TopLevelWidget* findTopLevelWidget(Widget* const w);



+ 27
- 0
dgl/src/WindowPrivateData.cpp View File

@@ -323,6 +323,19 @@ void Window::PrivateData::onPuglClose()
close();
}

void Window::PrivateData::onPuglMouse(const Events::MouseEvent& ev)
{
DGL_DBGp("PUGL: onMouse : %i %i %f %f\n", ev.button, ev.press, ev.pos.getX(), ev.pos.getY());

// if (fModal.childFocus != nullptr)
// return fModal.childFocus->focus();

#ifndef DPF_TEST_WINDOW_CPP
if (topLevelWidget != nullptr)
topLevelWidget->pData->mouseEvent(ev);
#endif
}

static int printEvent(const PuglEvent* event, const char* prefix, const bool verbose);

PuglStatus Window::PrivateData::puglEventCallback(PuglView* const view, const PuglEvent* const event)
@@ -355,6 +368,20 @@ PuglStatus Window::PrivateData::puglEventCallback(PuglView* const view, const Pu
pData->onPuglCreate();
break;

case PUGL_BUTTON_PRESS: ///< Mouse button pressed, a #PuglEventButton
case PUGL_BUTTON_RELEASE: ///< Mouse button released, a #PuglEventButton
{
Events::MouseEvent ev;
ev.mod = event->button.state;
ev.flags = event->button.flags;
ev.time = static_cast<uint>(event->button.time * 1000.0 + 0.5);
ev.button = event->button.button;
ev.press = event->type == PUGL_BUTTON_PRESS;
ev.pos = Point<double>(event->button.x, event->button.y);
pData->onPuglMouse(ev);
break;
}

// TODO
default:
break;


+ 2
- 0
dgl/src/WindowPrivateData.hpp View File

@@ -18,6 +18,7 @@
#define DGL_WINDOW_PRIVATE_DATA_HPP_INCLUDED

#include "../Window.hpp"
#include "../Events.hpp"
#include "ApplicationPrivateData.hpp"

#include "pugl.hpp"
@@ -107,6 +108,7 @@ struct Window::PrivateData : IdleCallback {
void onPuglReshape(int width, int height);
void onPuglCreate();
void onPuglClose();
void onPuglMouse(const Events::MouseEvent& ev);

// Pugl event handling entry point
static PuglStatus puglEventCallback(PuglView* view, const PuglEvent* event);


+ 2
- 32
tests/Demo.cpp View File

@@ -80,7 +80,6 @@ protected:
void onDisplay() override
{
const int iconSize = bgIcon.getWidth();
printf("LEFT SIDE WIDGET onDisplay %i\n", iconSize);

glColor3f(0.027f, 0.027f, 0.027f);
Rectangle<uint>(0, 0, getSize()).draw();
@@ -201,8 +200,8 @@ protected:

void onResize(const ResizeEvent& ev) override
{
const int width = ev.size.getWidth();
const int height = ev.size.getHeight();
const uint width = ev.size.getWidth();
const uint height = ev.size.getHeight();

bgIcon.setWidth(width-4);
bgIcon.setHeight(width-4);
@@ -299,11 +298,6 @@ protected:

void onDisplay() override
{
static int counter = 0;
printf("print %i\n", ++counter);

glColor3f(0.471f, 0.971f, 0.171f);
Rectangle<uint>(0, 0, getSize()).draw();
}

void onReshape(uint width, uint height) override
@@ -340,28 +334,6 @@ private:
Widget* curWidget;
};

// --------------------------------------------------------------------------------------------------------------------
// Testing StandaloneWindow, for custom local widget drawing code

class TestingWidgetStandaloneWindow : public StandaloneWindow
{
public:
static constexpr const char* kExampleWidgetName = "Testing";

TestingWidgetStandaloneWindow(Application& app)
: StandaloneWindow(app)
{
}

protected:
void onDisplay() override
{
glColor3f(0.5f, 0.3f, 0.9f);
Rectangle<uint>(0, 0, 500, 500).draw();
// getWidth(), getHeight()
}
};

// --------------------------------------------------------------------------------------------------------------------
// Special handy function that runs a StandaloneWindow inside the function scope

@@ -396,8 +368,6 @@ int main(int argc, char* argv[])
createAndShowExampleWidgetStandaloneWindow<ExampleRectanglesStandaloneWindow>(app);
else if (std::strcmp(argv[1], "shapes") == 0)
createAndShowExampleWidgetStandaloneWindow<ExampleShapesStandaloneWindow>(app);
else if (std::strcmp(argv[1], "testing") == 0)
createAndShowExampleWidgetStandaloneWindow<TestingWidgetStandaloneWindow>(app);
else
d_stderr2("Invalid demo mode, must be one of: color, rectangles, shapes");
}


+ 8
- 8
tests/widgets/ExampleRectanglesWidget.hpp View File

@@ -56,7 +56,7 @@ public:

void init()
{
this->setSize(300, 300);
BaseWidget::setSize(300, 300);

for (int i=0; i<9; ++i)
clicked[i] = false;
@@ -65,8 +65,8 @@ public:
protected:
void onDisplay() override
{
const uint width = this->getWidth();
const uint height = this->getHeight();
const uint width = BaseWidget::getWidth();
const uint height = BaseWidget::getHeight();

Rectangle<double> r;

@@ -115,8 +115,8 @@ protected:
if (ev.button != 1 || ! ev.press)
return false;

const uint width = this->getWidth();
const uint height = this->getHeight();
const uint width = BaseWidget::getWidth();
const uint height = BaseWidget::getHeight();

Rectangle<double> r;

@@ -134,7 +134,7 @@ protected:
if (r.contains(ev.pos))
{
clicked[0+i] = !clicked[0+i];
this->repaint();
BaseWidget::repaint();
break;
}

@@ -144,7 +144,7 @@ protected:
if (r.contains(ev.pos))
{
clicked[3+i] = !clicked[3+i];
this->repaint();
BaseWidget::repaint();
break;
}

@@ -154,7 +154,7 @@ protected:
if (r.contains(ev.pos))
{
clicked[6+i] = !clicked[6+i];
this->repaint();
BaseWidget::repaint();
break;
}
}


Loading…
Cancel
Save