]> rtime.felk.cvut.cz Git - l4.git/blob - l4/pkg/scout-gfx/include/horizontal_shadow
Inital import
[l4.git] / l4 / pkg / scout-gfx / include / horizontal_shadow
1 // vi:ft=cpp
2
3 #pragma once
4
5 #include <l4/scout-gfx/widget>
6
7 namespace Scout_gfx { namespace Pt {
8
9 template <typename PT>
10 class Horizontal_shadow : public Widget
11 {
12 private:
13   int const _intensity;
14   int const _h;
15
16 public:
17
18   explicit Horizontal_shadow(int height, int intensity)
19   : _intensity(intensity), _h(height)
20   { _size = Area(0, height); }
21
22   /**
23    * Element interface
24    */
25   void draw(Canvas *c, Point const &p);
26   Widget *find(Point const &) { return 0; }
27
28   Area min_size() const { return Area(0, _h); }
29   Area preferred_size() const { return Area(0, _h); }
30   Area max_size() const { return Area(Area::Max_w, _h); }
31   bool empty() const { return false; }
32   Orientations expanding() const { return Horizontal; }
33   Rect geometry() const { return Rect(_pos, _size); }
34   void set_geometry(Rect const &s)
35   {
36     Area x = s.area().max(min_size()).max(min_size());
37     _pos = s.p1(); _size = x;
38   }
39
40 };
41
42
43 /***********************
44  ** Horizontal shadow **
45  ***********************/
46
47 template <typename PT>
48 void Horizontal_shadow<PT>::draw(Canvas *c, Point const &_p)
49 {
50   typedef typename PT::Pixel Pixel;
51   typedef typename PT::Color Color;
52
53   char *addr = (char *)c->buffer();
54
55   if (!addr)
56     return;
57
58   Rect clip = c->clip();
59   Rect cr = (Rect(_size) + _p) & clip;
60
61   if (!cr.valid())
62     return;
63
64   int curr_a = _intensity;
65   int step   = _size.h() ? (curr_a/_size.h()) : 0;
66
67   int bpl = c->bytes_per_line();
68
69   addr += bpl * cr.y1() + cr.x1() * sizeof(Pixel);
70
71   Color shadow_color(0,0,0);
72
73   int h = cr.h();
74   for (int j = 0; j < h; j++, addr += bpl)
75     {
76       Pixel *d = reinterpret_cast<Pixel*>(addr);
77       int w = cr.w();
78
79       for (int i = 0; i < w; i++, d++)
80         *d = PT::mix(*d, shadow_color, curr_a);
81
82       curr_a -= step;
83     }
84 }
85
86 }}