Tizen 2.1 base
[framework/uifw/ecore.git] / src / lib / ecore_x / xlib / ecore_x_cursor.c
1 #ifdef HAVE_CONFIG_H
2 # include <config.h>
3 #endif /* ifdef HAVE_CONFIG_H */
4
5 #include <stdlib.h>
6
7 #include "ecore_x_private.h"
8
9 EAPI Eina_Bool
10 ecore_x_cursor_color_supported_get(void)
11 {
12    return _ecore_x_xcursor;
13 }
14
15 EAPI Ecore_X_Cursor
16 ecore_x_cursor_new(Ecore_X_Window win,
17                    int *pixels,
18                    int w,
19                    int h,
20                    int hot_x,
21                    int hot_y)
22 {
23 #ifdef ECORE_XCURSOR
24    LOGFN(__FILE__, __LINE__, __FUNCTION__);
25    if (_ecore_x_xcursor)
26      {
27         Cursor c;
28         XcursorImage *xci;
29
30         xci = XcursorImageCreate(w, h);
31         if (xci)
32           {
33              int i;
34
35              xci->xhot = hot_x;
36              xci->yhot = hot_y;
37              xci->delay = 0;
38              for (i = 0; i < (w * h); i++)
39                {
40 //                int r, g, b, a;
41 //
42 //                a = (pixels[i] >> 24) & 0xff;
43 //                r = (((pixels[i] >> 16) & 0xff) * a) / 0xff;
44 //                g = (((pixels[i] >> 8 ) & 0xff) * a) / 0xff;
45 //                b = (((pixels[i]      ) & 0xff) * a) / 0xff;
46                   xci->pixels[i] = pixels[i];
47 //                  (a << 24) | (r << 16) | (g << 8) | (b);
48                }
49              c = XcursorImageLoadCursor(_ecore_x_disp, xci);
50              XcursorImageDestroy(xci);
51              return c;
52           }
53      }
54    else
55 #endif /* ifdef ECORE_XCURSOR */
56    {
57       XColor c1, c2;
58       Cursor c;
59       Pixmap pmap, mask;
60       GC gc;
61       XGCValues gcv;
62       XImage *xim;
63       unsigned int *pix;
64       int fr, fg, fb, br, bg, bb;
65       int brightest = 0;
66       int darkest = 255 * 3;
67       int x, y;
68       const int dither[2][2] =
69       {
70          {0, 2},
71          {3, 1}
72       };
73
74       pmap = XCreatePixmap(_ecore_x_disp, win, w, h, 1);
75       mask = XCreatePixmap(_ecore_x_disp, win, w, h, 1);
76       xim = XCreateImage(_ecore_x_disp,
77                          DefaultVisual(_ecore_x_disp, 0),
78                          1, ZPixmap, 0, NULL, w, h, 32, 0);
79       xim->data = malloc(xim->bytes_per_line * xim->height);
80
81       fr = 0x00; fg = 0x00; fb = 0x00;
82       br = 0xff; bg = 0xff; bb = 0xff;
83       pix = (unsigned int *)pixels;
84       for (y = 0; y < h; y++)
85         {
86            for (x = 0; x < w; x++)
87              {
88                 int r, g, b, a;
89
90                 a = (pix[0] >> 24) & 0xff;
91                 r = (pix[0] >> 16) & 0xff;
92                 g = (pix[0] >> 8) & 0xff;
93                 b = (pix[0]) & 0xff;
94                 if (a > 0)
95                   {
96                      if ((r + g + b) > brightest)
97                        {
98                           brightest = r + g + b;
99                           br = r;
100                           bg = g;
101                           bb = b;
102                        }
103
104                      if ((r + g + b) < darkest)
105                        {
106                           darkest = r + g + b;
107                           fr = r;
108                           fg = g;
109                           fb = b;
110                        }
111                   }
112
113                 pix++;
114              }
115         }
116
117       pix = (unsigned int *)pixels;
118       for (y = 0; y < h; y++)
119         {
120            for (x = 0; x < w; x++)
121              {
122                 int v;
123                 int r, g, b;
124                 int d1, d2;
125
126                 r = (pix[0] >> 16) & 0xff;
127                 g = (pix[0] >> 8) & 0xff;
128                 b = (pix[0]) & 0xff;
129                 d1 =
130                   ((r - fr) * (r - fr)) +
131                   ((g - fg) * (g - fg)) +
132                   ((b - fb) * (b - fb));
133                 d2 =
134                   ((r - br) * (r - br)) +
135                   ((g - bg) * (g - bg)) +
136                   ((b - bb) * (b - bb));
137                 if (d1 + d2)
138                   {
139                      v = (((d2 * 255) / (d1 + d2)) * 5) / 256;
140                      if (v > dither[x & 0x1][y & 0x1])
141                        v = 1;
142                      else
143                        v = 0;
144                   }
145                 else
146                   v = 0;
147
148                 XPutPixel(xim, x, y, v);
149                 pix++;
150              }
151         }
152       gc = XCreateGC(_ecore_x_disp, pmap, 0, &gcv);
153       XPutImage(_ecore_x_disp, pmap, gc, xim, 0, 0, 0, 0, w, h);
154       XFreeGC(_ecore_x_disp, gc);
155
156       pix = (unsigned int *)pixels;
157       for (y = 0; y < h; y++)
158         {
159            for (x = 0; x < w; x++)
160              {
161                 int v;
162
163                 v = (((pix[0] >> 24) & 0xff) * 5) / 256;
164                 if (v > dither[x & 0x1][y & 0x1])
165                   v = 1;
166                 else
167                   v = 0;
168
169                 XPutPixel(xim, x, y, v);
170                 pix++;
171              }
172         }
173       gc = XCreateGC(_ecore_x_disp, mask, 0, &gcv);
174       XPutImage(_ecore_x_disp, mask, gc, xim, 0, 0, 0, 0, w, h);
175       XFreeGC(_ecore_x_disp, gc);
176
177       free(xim->data);
178       xim->data = NULL;
179       XDestroyImage(xim);
180
181       c1.pixel = 0;
182       c1.red = fr << 8 | fr;
183       c1.green = fg << 8 | fg;
184       c1.blue = fb << 8 | fb;
185       c1.flags = DoRed | DoGreen | DoBlue;
186
187       c2.pixel = 0;
188       c2.red = br << 8 | br;
189       c2.green = bg << 8 | bg;
190       c2.blue = bb << 8 | bb;
191       c2.flags = DoRed | DoGreen | DoBlue;
192
193       c = XCreatePixmapCursor(_ecore_x_disp,
194                               pmap, mask,
195                               &c1, &c2,
196                               hot_x, hot_y);
197       XFreePixmap(_ecore_x_disp, pmap);
198       XFreePixmap(_ecore_x_disp, mask);
199       return c;
200    }
201
202    return 0;
203 }
204
205 EAPI void
206 ecore_x_cursor_free(Ecore_X_Cursor c)
207 {
208    LOGFN(__FILE__, __LINE__, __FUNCTION__);
209    XFreeCursor(_ecore_x_disp, c);
210 }
211
212 /*
213  * Returns the cursor for the given shape.
214  * Note that the return value must not be freed with
215  * ecore_x_cursor_free()!
216  */
217 EAPI Ecore_X_Cursor
218 ecore_x_cursor_shape_get(int shape)
219 {
220    LOGFN(__FILE__, __LINE__, __FUNCTION__);
221    /* Shapes are defined in Ecore_X_Cursor.h */
222    return XCreateFontCursor(_ecore_x_disp, shape);
223 }
224
225 EAPI void
226 ecore_x_cursor_size_set(int size)
227 {
228 #ifdef ECORE_XCURSOR
229    LOGFN(__FILE__, __LINE__, __FUNCTION__);
230    XcursorSetDefaultSize(_ecore_x_disp, size);
231 #else /* ifdef ECORE_XCURSOR */
232    size = 0;
233 #endif /* ifdef ECORE_XCURSOR */
234 }
235
236 EAPI int
237 ecore_x_cursor_size_get(void)
238 {
239 #ifdef ECORE_XCURSOR
240    LOGFN(__FILE__, __LINE__, __FUNCTION__);
241    return XcursorGetDefaultSize(_ecore_x_disp);
242 #else /* ifdef ECORE_XCURSOR */
243    return 0;
244 #endif /* ifdef ECORE_XCURSOR */
245 }
246