3a062dae853616200a57a33901211a85b62a6971
[framework/uifw/ecore.git] / src / lib / ecore_fb / ecore_fb_ps2.c
1 typedef struct _Ecore_Fb_Ps2_Event Ecore_Fb_Ps2_Event;
2 struct _Ecore_Fb_Ps2_Event
3 {
4    unsigned char button;
5    unsigned char x;
6    unsigned char y;
7    unsigned char z;
8 };
9
10 static int _ecore_fb_ps2_event_byte_count = 0;
11 static Ecore_Fb_Ps2_Event _ecore_fb_ps2_event;
12 static int _ecore_fb_ps2_fd = 0;
13 static int _ecore_fb_ps2_fd_handler(void *data, Ecore_Fd_Handler *fd_handler);
14
15 int
16 ecore_fb_ps2_init(void)
17 {
18    _ecore_fb_ps2_fd = open("/dev/psaux", O_RDWR);
19    if (_ecore_fb_ps2_fd >= 0)
20      {
21         prev_flags = fcntl(_ecore_fb_ps2_fd, F_GETFL);
22         fcntl(_ecore_fb_ps2_fd, F_SETFL, prev_flags | O_NONBLOCK);
23         _ecore_fb_ts_fd_handler_handle = ecore_main_fd_handler_add(_ecore_fb_ps2_fd, 
24                                                                         ECORE_FD_READ,
25                                                                         _ecore_fb_ps2_fd_handler, NULL, NULL, NULL);
26         if (!_ecore_fb_ts_fd_handler_handle)
27          {
28            close(_ecore_fb_ps2_fd);
29            return 0;
30          }
31         return 1;
32      }
33   return 0;   
34 }
35
36 void
37 ecore_fb_ps2_shutdown(void)
38 {
39    if (_ecore_fb_ps2_fd > 0) close(_ecore_fb_ps2_fd);
40    _ecore_fb_ps2_fd = 0;
41 }
42
43 static int
44 _ecore_fb_ps2_fd_handler(void *data __UNUSED__, Ecore_Fd_Handler *fd_handler __UNUSED__)
45 {
46    static int prev_x = 0, prev_y = 0, prev_button = 0;
47    static double last_time = 0;
48    static double last_last_time = 0;
49    int v = 0;
50
51    do
52      {
53         int x, y, button, i;
54         int num;
55         char *ptr;
56         double t;
57         int did_triple = 0;
58         
59         ptr = (char *)&(_ecore_fb_ps2_event);
60         ptr += _ecore_fb_ps2_event_byte_count;
61         num = sizeof(Ecore_Fb_Ps2_Event) - _ecore_fb_ps2_event_byte_count;
62         v = read(_ecore_fb_ps2_fd, ptr, num);
63         if (v < 0) return 1;
64         _ecore_fb_ps2_event_byte_count += v;
65         if (v < num) return 1;
66         t = ecore_time_get();
67         _ecore_fb_ps2_event_byte_count = 0;
68         if (_ecore_fb_ps2_event.button & 0x10)
69           x = prev_x + (0xffffff00 | _ecore_fb_ps2_event.x);
70         else
71           x = prev_x + _ecore_fb_ps2_event.x;
72         if (_ecore_fb_ps2_event.button & 0x20)
73           y = prev_y - (0xffffff00 | _ecore_fb_ps2_event.y);
74         else
75           y = prev_y - _ecore_fb_ps2_event.y;
76         button = _ecore_fb_ps2_event.button & 0x7;
77         if (x < 0) x = 0;
78         if (y < 0) y = 0;
79         if (x >= _ecore_fb_console_w) x = _ecore_fb_console_w - 1;
80         if (y >= _ecore_fb_console_h) y = _ecore_fb_console_h - 1;
81         /* add event to queue */
82         /* always add a move event */
83         if (1)
84           {
85              /* MOVE: mouse is down and was */
86              Ecore_Fb_Event_Mouse_Move *e;
87              
88              e = calloc(1, sizeof(Ecore_Fb_Event_Mouse_Move));
89              if (!e) goto retry;
90              e->x = x;
91              e->y = y;
92              ecore_event_add(ECORE_FB_EVENT_MOUSE_MOVE, e, NULL, NULL);
93           }
94         for (i = 1; i <= 3; i++)
95           {
96              int mask;
97              
98              mask = 1 << (i - 1);
99              if (((button & mask)) && (!(prev_button & mask)))
100                {
101                   /* DOWN: mouse is down, but was not now */
102                   Ecore_Fb_Event_Mouse_Button_Down *e;
103                   
104                   e = calloc(1, sizeof(Ecore_Fb_Event_Mouse_Button_Down));
105                   if (!e) goto retry;
106                   e->x = x;
107                   e->y = y;
108                   e->button = 1;
109                   if ((t - last_time) <= _ecore_fb_double_click_time)
110                     e->double_click = 1;
111                   if ((t - last_last_time) <= (2 * _ecore_fb_double_click_time))
112                     {
113                        did_triple = 1;
114                        e->triple_click = 1;
115                     }
116                   ecore_event_add(ECORE_FB_EVENT_MOUSE_BUTTON_DOWN, e, NULL, NULL);
117                }
118              else if ((!(button & mask)) && ((prev_button & mask)))
119                {
120                   /* UP: mouse was down, but is not now */
121                   Ecore_Fb_Event_Mouse_Button_Up *e;
122                   
123                   e = calloc(1, sizeof(Ecore_Fb_Event_Mouse_Button_Up));
124                   if (!e) goto retry;
125                   e->x = x;
126                   e->y = y;
127                   e->button = 1;
128                   ecore_event_add(ECORE_FB_EVENT_MOUSE_BUTTON_UP, e, NULL, NULL);
129                }
130           }
131         if (did_triple)
132           {
133              last_time = 0;
134              last_last_time = 0;
135           }
136         else
137           {
138              last_last_time = last_time;
139              last_time = t;
140           }
141         retry:       
142         prev_x = x;
143         prev_y = y;
144         prev_button = button;
145      }
146    while (v > 0);
147    return 1;
148 }
149 /**
150  * @defgroup Ecore_FB_Click_Group Framebuffer Double Click Functions
151  *
152  * Functions that deal with the double click time of the framebuffer.
153  */
154
155 /**
156  * Sets the timeout for a double and triple clicks to be flagged.
157  * 
158  * This sets the time between clicks before the double_click flag is
159  * set in a button down event. If 3 clicks occur within double this
160  * time, the triple_click flag is also set.
161  *
162  * @param   t The time in seconds
163  * @ingroup Ecore_FB_Click_Group
164  */
165 EAPI void
166 ecore_fb_double_click_time_set(double t)
167 {
168    if (t < 0.0) t = 0.0;
169    _ecore_fb_double_click_time = t;
170 }
171
172 /**
173  * Retrieves the double and triple click flag timeout.
174  *
175  * See @ref ecore_x_double_click_time_set for more information.
176  *
177  * @return  The timeout for double clicks in seconds.
178  * @ingroup Ecore_FB_Click_Group
179  */
180 EAPI double
181 ecore_fb_double_click_time_get(void)
182 {
183    return _ecore_fb_double_click_time;
184 }
185