/* ui/widget.cc This file is part of the Osirion project and is distributed under the terms of the GNU General Public License version 2 */ #include "auxiliary/functions.h" #include "sys/sys.h" #include "ui/paint.h" #include "ui/ui.h" #include "ui/widget.h" namespace ui { Widget::Widget(Widget *parent) { widget_visible = true; widget_border = true; widget_background = false; widget_palette = 0; widget_font = 0; widget_label.assign("widget"); if (!parent) { widget_parent = root(); } else { widget_parent = parent; } if (widget_parent) widget_parent->add_child(this); } Widget::~Widget() { for (Children::iterator it = widget_children.begin(); it != widget_children.end(); it++) { delete (*it); (*it) = 0; } widget_children.clear(); } size_t Widget::list(size_t indent) { print(indent); size_t n = 1; for (Children::iterator it = widget_children.begin(); it != widget_children.end(); it++) { n += (*it)->list(indent+1); } return n; } void Widget::print(size_t indent) { std::string marker(""); con_print << aux::pad_left(marker, indent*2) << label() << std::endl; } Palette const *Widget::palette() const { if (widget_palette) { return widget_palette; } else { return parent()->palette(); } } Font const *Widget::font() const { if (widget_font) { return widget_font; } else { return parent()->font(); } } void Widget::lower() { if (!parent()) return; Children::iterator it = parent()->find_child(this); if (it != parent()->children().end()) { parent()->children().erase(it); parent()->children().push_front(this); } } void Widget::raise() { if (!parent()) return; Children::iterator it = parent()->find_child(this); if (it != parent()->children().end()) { parent()->children().erase(it); parent()->children().push_back(this); } } void Widget::show() { widget_visible = true; } void Widget::hide() { widget_visible = false; } void Widget::set_visible(bool visible) { widget_visible = visible; } void Widget::set_border(bool border) { widget_border = border; } void Widget::set_background(bool background) { widget_background = background; } void Widget::set_label(std::string const & label) { set_label(label.c_str()); } void Widget::set_label(char const *label) { widget_label.assign(label); aux::to_label(widget_label); } void Widget::set_palette(Palette *palette) { widget_palette = palette; } void Widget::set_font(Font *font) { widget_font = font; } void Widget::set_location(float const x, float const y) { widget_location.assign(x, y); } void Widget::set_size(float const w, float const h) { widget_size.assign(w, h); } void Widget::set_size(math::Vector2f const &size) { widget_size.assign(size); } void Widget::set_width(float const w) { widget_size.x = w; } void Widget::set_height(float const h) { widget_size.y = h; } Widget::Children::iterator Widget::find_child(Widget *child) { Children::iterator it; for (it = widget_children.begin(); it != widget_children.end(); it++) { if ((*it) == child) return it; } return it; } void Widget::add_child(Widget *child) { Children::iterator it = find_child(child); if (it == widget_children.end()) { widget_children.push_back(child); } } void Widget::remove_child(Widget *child) { Children::iterator it = find_child(child); if (it != widget_children.end()) { delete (*it); widget_children.erase(it); } } void Widget::event_resize() { resize(); for (Children::iterator it = widget_children.begin(); it != widget_children.end(); it++) { (*it)->event_resize(); } } void Widget::resize() { } void Widget::event_draw() { if (!widget_visible) return; draw(); for (Children::iterator it = widget_children.begin(); it != widget_children.end(); it++) { if ((*it)->visible()) (*it)->event_draw(); } } void Widget::draw() { draw_background(); draw_border(); } void Widget::draw_background() { if (!widget_background) return; paint::color(palette()->background()); paint::rectangle(global_location(), size()); } void Widget::draw_border() { if (!widget_border) return; paint::color(palette()->border()); paint::border(global_location(), size()); } Widget *Widget::event_focus(math::Vector2f const & pos) { // this widget is not visible if (!visible()) return 0; // pos is outside this if ((pos.x < 0) || (pos.y < 0) || (pos.x > size().x) || (pos.y > size().y)) return 0; // reverse-iterate children for (Children::reverse_iterator rit = widget_children.rbegin(); rit != widget_children.rend(); ++rit) { Widget *w = (*rit); if (w->visible()) { Widget *f = w->event_focus(pos - w->location()); if (f) return f; } } // no child has focus return this; } bool Widget::has_focus() const { return (root()->focus() == this); } bool Widget::event_key(bool pressed, unsigned int key, unsigned int modifier) { bool handled; if (pressed) { handled = keypress(key, modifier); } else { handled = keyrelease(key, modifier); } if (!handled && parent()) handled = parent()->event_key(pressed, key, modifier); return handled; } bool Widget::keypress(unsigned int key, unsigned int modifier) { return false; } bool Widget::keyrelease(unsigned int key, unsigned int modifier) { return false; } }