]> git.tdb.fi Git - libs/gltk.git/blob - source/panel.cpp
Make autosize_special const and add a const autosize overload
[libs/gltk.git] / source / panel.cpp
1 #include <algorithm>
2 #include <msp/core/maputils.h>
3 #include <msp/core/refptr.h>
4 #include "button.h"
5 #include "column.h"
6 #include "draghandle.h"
7 #include "dropdown.h"
8 #include "entry.h"
9 #include "grid.h"
10 #include "hslider.h"
11 #include "image.h"
12 #include "indicator.h"
13 #include "label.h"
14 #include "list.h"
15 #include "panel.h"
16 #include "part.h"
17 #include "row.h"
18 #include "stack.h"
19 #include "toggle.h"
20 #include "vslider.h"
21
22 using namespace std;
23
24 namespace Msp {
25 namespace GLtk {
26
27 Panel::Panel():
28         layout(0)
29 { }
30
31 Panel::~Panel()
32 {
33         delete layout;
34         layout = 0;
35 }
36
37 void Panel::set_layout(Layout *l)
38 {
39         l->set_container(*this);
40         delete layout;
41         layout = l;
42 }
43
44 void Panel::autosize_special(const Part &part, Geometry &ageom) const
45 {
46         if(part.get_name()=="children" && layout)
47                 layout->autosize(ageom);
48 }
49
50 void Panel::render_special(const Part &part, GL::Renderer &renderer) const
51 {
52         if(part.get_name()=="children")
53         {
54                 for(list<Container::Child *>::const_iterator i=children.begin(); i!=children.end(); ++i)
55                         if((*i)->widget->is_visible())
56                                 (*i)->widget->render(renderer);
57         }
58 }
59
60 void Panel::on_geometry_change()
61 {
62         if(layout)
63                 layout->update();
64 }
65
66 void Panel::on_child_added(Widget &wdg)
67 {
68         if(layout)
69         {
70                 layout->add_widget(wdg);
71                 signal_autosize_changed.emit();
72         }
73 }
74
75 void Panel::on_child_removed(Widget &wdg)
76 {
77         if(layout)
78         {
79                 layout->remove_widget(wdg);
80                 signal_autosize_changed.emit();
81         }
82 }
83
84
85 Panel::Loader::Loader(Panel &p, map<string, Widget *> &m):
86         DataFile::DerivedObjectLoader<Panel, Widget::Loader>(p),
87         wdg_map(m),
88         last_widget(0)
89 {
90         add("button",    &Loader::child<Button>);
91         add("column",    &Loader::arrangement<Column>);
92         add("constraint",&Loader::constraint);
93         add("draghandle",&Loader::child<DragHandle>);
94         add("dropdown",  &Loader::child<Dropdown>);
95         add("entry",     &Loader::child<Entry>);
96         add("expand",    &Loader::expand);
97         add("ghost",     &Loader::ghost);
98         add("gravity",   &Loader::gravity);
99         add("grid",      &Loader::grid);
100         add("hslider",   &Loader::child<HSlider>);
101         add("image",     &Loader::child<Image>);
102         add("indicator", &Loader::child<Indicator>);
103         add("label",     &Loader::child<Label>);
104         add("layout",    &Loader::layout);
105         add("list",      &Loader::child<List>);
106         add("panel",     &Loader::panel);
107         add("row",       &Loader::arrangement<Row>);
108         add("stack",     &Loader::arrangement<Stack>);
109         add("toggle",    &Loader::child<Toggle>);
110         add("vslider",   &Loader::child<VSlider>);
111 }
112
113 Layout &Panel::Loader::get_layout()
114 {
115         if(!obj.layout)
116                 obj.set_layout(new Layout);
117
118         return *obj.layout;
119 }
120
121 Widget &Panel::Loader::get_last_widget()
122 {
123         if(!last_widget)
124                 throw logic_error("no widget loaded");
125
126         return *last_widget;
127 }
128
129 template<typename T>
130 void Panel::Loader::arrangement()
131 {
132         T arr(get_layout());
133         ArrangedLoader<T> ldr(*this, arr);
134         load_sub_with(ldr);
135 }
136
137 template<typename T>
138 void Panel::Loader::child(const string &n)
139 {
140         RefPtr<T> chl = new T();
141         load_sub(*chl);
142         obj.add(*chl.get());
143         last_widget = wdg_map[n] = chl.release();
144 }
145
146 void Panel::Loader::constraint(Layout::ConstraintType type, const string &n)
147 {
148         Widget &src = get_last_widget();
149         Widget &tgt = *get_item(wdg_map, n);
150         get_layout().add_constraint(src, type, tgt);
151 }
152
153 void Panel::Loader::expand(bool h, bool v)
154 {
155         get_layout().set_expand(get_last_widget(), h, v);
156 }
157
158 void Panel::Loader::ghost(bool g)
159 {
160         get_layout().set_ghost(get_last_widget(), g);
161 }
162
163 void Panel::Loader::gravity(int h, int v)
164 {
165         get_layout().set_gravity(get_last_widget(), h, v);
166 }
167
168 void Panel::Loader::grid(unsigned cols)
169 {
170         Grid grd(get_layout(), cols);
171         ArrangedLoader<Grid> ldr(*this, grd);
172         load_sub_with(ldr);
173 }
174
175 void Panel::Loader::layout()
176 {
177         Layout::Loader ldr(get_layout(), wdg_map);
178         load_sub_with(ldr);
179 }
180
181 void Panel::Loader::panel(const string &n)
182 {
183         RefPtr<Panel> p = new Panel();
184         load_sub(*p, wdg_map);
185         obj.add(*p.get());
186         last_widget = wdg_map[n] = p.release();
187 }
188
189
190 template<typename T>
191 Panel::ArrangedLoader<T>::ArrangedLoader(Loader &ldr, T &arr):
192         arr_loader(arr)
193 {
194         add_auxiliary_loader(ldr);
195         add_auxiliary_loader(arr_loader);
196 }
197
198 } // namespace GLtk
199 } // namespace Msp