]> rtime.felk.cvut.cz Git - l4.git/blob - l4/pkg/mag/include/server/view_stack
update
[l4.git] / l4 / pkg / mag / include / server / view_stack
1 // vi:ft=cpp
2 /*
3  * (c) 2010 Alexander Warg <warg@os.inf.tu-dresden.de>
4  *     economic rights: Technische Universität Dresden (Germany)
5  *
6  * This file is part of TUD:OS and distributed under the terms of the
7  * GNU General Public License 2.
8  * Please see the COPYING-GPL-2 file for details.
9  */
10 #pragma once
11
12 #include <l4/cxx/dlist>
13 #include <l4/re/video/view>
14
15 #include <l4/mag-gfx/canvas>
16 #include <l4/mag/server/view>
17 #include <l4/cxx/observer>
18
19 #include <cassert>
20
21 namespace Mag_server {
22
23 using namespace Mag_gfx;
24
25 class View_stack
26 {
27 private:
28   class Dummy_view : public View
29   {
30   public:
31     Dummy_view() : View(Rect(Point(0,0), Area(0,0)), F_ignore) {}
32     void draw(Canvas *, View_stack const *, Mode) const {}
33   };
34
35   Dummy_view _no_stay_top_v;
36
37   Canvas *_canvas;
38   View *const _no_stay_top;
39   cxx::D_list<View> _top;
40   View *const _background;
41   View *_focused;
42
43   Mode _mode;
44
45   L4Re::Video::View *_canvas_view;
46   Font const *_label_font;
47   cxx::Notifier _mode_notifier;
48
49   Rect outline(View const *v) const;
50
51   void draw_frame(View const *v) const;
52   void draw_label(View const *v) const;
53
54   void insert_before(View *o, View *p)
55   { o->l_add_before(p); }
56
57   void insert_after(View *o, View *p)
58   { o->l_add_after(p); }
59
60 public:
61   explicit View_stack(Canvas *canvas, L4Re::Video::View *canvas_view, View *bg,
62                       Font const *label_font)
63   : _canvas(canvas), _no_stay_top(&_no_stay_top_v),  _top(&_no_stay_top_v),
64     _background(bg), _canvas_view(canvas_view), _label_font(label_font)
65   {
66     bg->l_add_after(_no_stay_top);
67   }
68
69   View *top() const { return _top.first(); }
70
71   virtual
72   void refresh_view(View const *v, View const *dst, Rect const &rect) const;
73
74   /**
75    * Draw whole view stack
76    */
77   void update_all_views() const
78   {
79     Rect r(Point(), _canvas->size());
80     place_labels(r);
81     refresh_view(0, 0, r);
82   }
83
84   virtual void flush();
85
86   Canvas *canvas() const { return _canvas; }
87
88   Mode mode() const { return _mode; }
89
90   void toggle_mode(Mode::Mode_flag m, bool update = false)
91   {
92     _mode.toggle(m);
93     if (update)
94       update_all_views();
95     _mode_notifier.notify();
96   }
97
98   void set_mode(Mode::Mode_flag m, bool on, bool update = false)
99   {
100     _mode.set(m, on);
101     if (update)
102       update_all_views();
103     _mode_notifier.notify();
104   }
105
106   void set_focused(View *v);
107   View *focused() const { return _focused; }
108
109   virtual
110   void viewport(View *v, Rect const &pos, bool redraw) const;
111
112   void draw_recursive(View const *v, View const *dst, Rect const &,
113                       View const *bg) const;
114
115   virtual
116   void draw_recursive(View const *v, View const *dst, Rect const &) const;
117
118   virtual
119   void stack(View *v, View *pivot, bool behind = true);
120
121   void push_top(View *v, bool stay_top = false)
122   { stack(v, _no_stay_top, !stay_top); }
123
124   void push_bottom(View *v);
125
126   void remove(View *v)
127   { v->l_remove(); }
128
129   void forget_view(View *v)
130   {
131     assert (v != _no_stay_top);
132     assert (v != _background);
133     remove(v);
134     refresh_view(0, 0, outline(v));
135   }
136
137   bool on_top(View const *v) const
138   { return _top.next(_no_stay_top) == v; }
139
140   View *next_view(View *c) const { return _top.next(c); }
141
142   void add_mode_observer(cxx::Observer *o) { _mode_notifier.add(o); }
143
144   virtual
145   View *find(Point const &pos) const;
146
147   virtual ~View_stack() {}
148
149 private:
150   View *current_background() const
151   {
152     Session *current_session = focused() ? focused()->session() : 0;
153     return current_session ? current_session->background() : 0;
154   }
155
156   View const *next_view(View const*, View const *bg) const;
157   View *next_view(View *v, View const *bg) const
158   { return const_cast<View*>(next_view(const_cast<View const *>(v), bg)); }
159
160   void optimize_label_rec(View *cv, View *lv, Rect const &rect, Rect *optimal,
161                           View *bg) const;
162   void do_place_labels(Rect const &rect) const;
163
164   void place_labels(Rect const &rect) const
165   {
166     if (_mode.flat())
167       return;
168
169     do_place_labels(rect);
170   }
171 };
172
173 }