122 lines
2.2 KiB
C++
122 lines
2.2 KiB
C++
#ifndef UI_ELEMENT_H
|
|
#define UI_ELEMENT_H
|
|
|
|
#include "UIStructs.h"
|
|
#include "UIPainter.h"
|
|
|
|
#undef min
|
|
#undef max
|
|
#include <vector>
|
|
|
|
class UIElement {
|
|
|
|
protected:
|
|
|
|
UIRect rect;
|
|
bool _visible = true;
|
|
bool _needsRedraw = true;
|
|
|
|
std::vector<UIElement*> children;
|
|
|
|
static constexpr const char* TAG = "UIElement";
|
|
|
|
public:
|
|
|
|
void setRect(const UIRect r) {
|
|
this->rect = r;
|
|
setNeedsRedraw();
|
|
reLayout();
|
|
}
|
|
void setRect(const uint16_t x, const uint16_t y, const uint16_t w, const uint16_t h) {
|
|
this->rect = UIRect(x,y,w,h);
|
|
setNeedsRedraw();
|
|
reLayout();
|
|
}
|
|
const UIRect& getRect() const {
|
|
return rect;
|
|
}
|
|
|
|
void setVisible(bool visible) {
|
|
this->_visible = visible;
|
|
setNeedsRedraw();
|
|
}
|
|
bool isVisible() const {
|
|
return this->_visible;
|
|
}
|
|
|
|
void setNeedsRedraw() {
|
|
this->_needsRedraw = true;
|
|
}
|
|
bool needsRedraw() const {
|
|
return this->_needsRedraw;
|
|
}
|
|
|
|
void addChild(UIElement* e) {
|
|
children.push_back(e);
|
|
}
|
|
|
|
|
|
|
|
|
|
protected:
|
|
|
|
friend class UI;
|
|
|
|
virtual void draw(UIPainter& p) {;}
|
|
|
|
/** layout needs updating */
|
|
virtual void reLayout() {;}
|
|
|
|
virtual void onTouchDown(uint16_t, uint16_t) {;} // relative (x,y) coordinate
|
|
virtual void onTouch(uint16_t, uint16_t) {;} // relative (x,y) coordinate
|
|
virtual void onTouchUp() {;}
|
|
|
|
protected:
|
|
|
|
UIElement* _onTouch(const uint16_t x, const uint16_t y) {
|
|
|
|
|
|
// if i'm invisible, ignore for me and children
|
|
if (!isVisible()) {return nullptr;}
|
|
|
|
// touch outside of me, ignore for me and children
|
|
if (!getRect().contains(x,y)) {return nullptr;}
|
|
|
|
// find first child that takes the event
|
|
for (UIElement* e : children) {
|
|
UIElement* taken = e->_onTouch(x, y);
|
|
if (taken) {return taken;}
|
|
}
|
|
|
|
// take the event myself
|
|
const uint16_t x1 = x - getRect().x; // (x,y) relative to elements top-left
|
|
const uint16_t y1 = y - getRect().y;
|
|
debugMod2(TAG, "onTouchDown(%d,%d)", x1, y1);
|
|
onTouchDown(x1, y1);
|
|
return this;
|
|
|
|
}
|
|
|
|
void _draw(UIPainter& p) {
|
|
|
|
// if hidde, ignore for me and children
|
|
if (!_visible) {return;}
|
|
|
|
// draw myself (if needed)
|
|
if (_needsRedraw) {
|
|
draw(p);
|
|
_needsRedraw = false;
|
|
}
|
|
|
|
// call for children as well
|
|
for (UIElement* child : children) {
|
|
child->_draw(p);
|
|
}
|
|
|
|
}
|
|
|
|
|
|
};
|
|
|
|
#endif // UI_ELEMENT_H
|