fix dependency
[profile/ivi/ico-vic-carsimulator.git] / src / CJoyStickEV.cpp
1 /*
2  * Copyright (c) 2013, TOYOTA MOTOR CORPORATION.
3  *
4  * This program is licensed under the terms and conditions of the 
5  * Apache License, version 2.0.  The full text of the Apache License is at
6  * http://www.apache.org/licenses/LICENSE-2.0
7  *
8  */
9 /**
10  * @file    CJoyStickEV.h
11  *
12  * Note:
13  * processing in the value of the joystick-event in Tizen IVI 2.0
14  *  joystick-event
15  *    event-type is used JS_EVENT_BUTTON and JS_EVENT_AXIS 
16  *    axis/button number value is determine in configuration file
17  *      G27.conf G25.conf
18  *    event-value memo
19  *      Steering value: -32767(Right) <-> 32767(Left)
20  *      Accel value:0(full throttle) <-> 32767(free throttle)
21  *      Brake value:0(full throttle) <-> 32767(free throttle)
22  */
23 #include <unistd.h>
24 #include <iostream>
25 #include <string>
26 #include <vector>
27 #include <stdio.h>
28 #include <poll.h>
29 #include <sys/io.h>
30 #include <sys/ioctl.h>
31 #include <sys/types.h>
32 #include <sys/stat.h>
33 #include <fcntl.h>
34 #include <linux/input.h>
35 #include "CJoyStick.h"
36 #include "CJoyStickEV.h"
37 #include "CConf.h"
38
39 #include "ico-util/ico_log.h"
40 #include <errno.h>
41
42 using namespace std;
43
44 CJoyStickEV::CJoyStickEV()
45 {
46     // TODO Auto-generated constructor stub
47     memset(m_absInf, 0, sizeof(m_absInf));
48     m_devName = std::string(D_DEV_NAME_G27);
49 }
50
51 CJoyStickEV::~CJoyStickEV()
52 {
53     // TODO Auto-generated destructor stub
54 }
55
56 /**
57  * @brief joystick device(event) open
58  * @retval number of file descriptor / error
59  */
60 int CJoyStickEV::Open()
61 {
62     string dirpath(D_DEV_DIR_PATH);
63     string nameparts(D_DEV_NAME_PARTS_EV);
64     string devPath;
65     /**
66      * get device file
67      */
68     printf("Open Device Name is <%s>\n", m_devName.c_str());
69     int rfd = deviceOpen(dirpath, nameparts, m_devName, devPath);
70     if (0 > rfd) {
71         printf("Can't open device.\n");
72         return rfd;
73     }
74     m_nJoyStickID = rfd;
75
76     fds.fd = m_nJoyStickID;
77
78     if (pthread_create(&m_threadid, NULL, CJoyStickEV::loop,
79                        (void *) this) != 0) {
80         cerr << "Failed to create thread." << endl;
81         return -1;
82     }
83
84     return m_nJoyStickID;
85 }
86
87 /**
88  * @brief joystick device file close
89  * @return 0:close success
90  */
91 int CJoyStickEV::Close()
92 {
93     if (0 > m_nJoyStickID) {
94         return 0;
95     }
96     return CJoyStick::Close();
97 }
98
99 /**
100  * @brief joystick event read loop entrance
101  * @return
102  */
103 void *CJoyStickEV::loop(void *arg)
104 {
105     CJoyStickEV *src = reinterpret_cast < CJoyStickEV * >(arg);
106     return (void *) src->recvEV();
107 }
108
109 /**
110  * @brief joystick event read loop
111  * @return
112  */
113 bool CJoyStickEV::recvEV()
114 {
115     while(1) {
116         fds.events = POLLIN;
117         if (poll(&fds, 1, -1) < 0) {
118             ICO_ERR("poll error");
119             return false;
120         }
121         if (0 != (fds.revents & POLLIN)) {
122             /**
123              * read event
124              */
125             struct input_event ie;
126             int rc;
127             while ((rc = read(m_nJoyStickID, &ie, sizeof(ie))) > 0) {
128                 queue.push(ie);
129                 if (sizeof(ie) != rc) {
130                     ICO_DBG("data not enough [%d/%d]", rc, sizeof(ie));
131                 }
132             }
133             if (0 > rc && errno !=11) {  /* read error(errno:11=EAGAIN) */
134                 ICO_ERR("read error[ret=%d, errno=%d]", rc, errno);
135             }
136         }
137     }
138     return false;
139 }
140
141 /**
142  * @brief joystick event read
143  * @param nubmer joystick event data(convert input_event.code)
144  * @param value joystick event data(convert input_event.value)
145  * @return convert input_event.type
146  *         not -1:joystick event data -1:read data nothing
147  */
148 int CJoyStickEV::Read(int *num, int *val)
149 {
150     /**
151      * read event
152      */
153     struct input_event ie;
154     int ret;
155     ret = queue.pop(ie);
156     if (ret != 0) {
157         return -1;
158     }
159
160     /**
161      * event convert
162      */
163     int r = -1;
164     switch (ie.type) {
165     case EV_SYN:
166         break;
167     case EV_KEY:
168         r = getJS_EVENT_BUTTON(*num, *val, ie);
169         break;
170     case EV_REL:
171         break;
172     case EV_ABS:
173         r = getJS_EVENT_AXIS(*num, *val, ie);
174         break;
175     case EV_MSC:
176         break;
177     case EV_SW:
178         break;
179     case EV_LED:
180         break;
181     case EV_SND:
182         break;
183     case EV_REP:
184         break;
185     case EV_FF:
186         break;
187     case EV_PWR:
188         break;
189     case EV_FF_STATUS:
190         break;
191     }
192     return r;
193 }
194
195 /**
196  * test read
197  */
198 int CJoyStickEV::ReadData()
199 {
200     struct input_event ie;
201
202     int r = read(m_nJoyStickID, &ie, sizeof(ie));
203
204     return 0;
205 }
206
207 /**
208  * @brief change input_event value to js_event value
209  */
210 int CJoyStickEV::getJS_EVENT_BUTTON(int& num, int& val,
211                                     const struct input_event& s)
212 {
213 /*
214     if ((BTN_JOYSTICK <= s.code) && (s.code <= BTN_GEAR_UP)) {
215         num = s.code - BTN_JOYSTICK;
216         val = s.value;
217         return JS_EVENT_BUTTON;
218     }
219     return -1;
220 */
221     num = s.code;
222     val = s.value;
223     return JS_EVENT_BUTTON;
224 }
225
226 /**
227  * @brief change input_event value to js_event value
228  */
229 int CJoyStickEV::getJS_EVENT_AXIS(int& num, int& val,
230                                   const struct input_event& s)
231 {
232     int r = -1;
233     switch (s.code) {
234     case ABS_X:
235         // Convert value Steering
236         //    0 to 16353 -> -32766 to 32767
237         r = JS_EVENT_AXIS;
238         num = (int)s.code;
239         val = calc1pm32767((int)s.value, m_absInf[E_ABSX]);
240         break;
241     case ABS_Y:
242         r = JS_EVENT_AXIS;
243         num = (int)s.code;
244         val = calc1pm32767((int)s.value, m_absInf[E_ABSY]);
245         break;
246     case ABS_Z:
247         r = JS_EVENT_AXIS;
248         num = (int)s.code;
249         val = calc3p32767Reverse((int)s.value, m_absInf[E_ABSZ]);
250         break;
251     case ABS_RZ:
252         r = JS_EVENT_AXIS;
253         num = (int)s.code;
254         val = calc3p32767Reverse((int)s.value, m_absInf[E_ABSRZ]);
255         break;
256     case ABS_HAT0X:
257         r = JS_EVENT_AXIS;
258         num = (int)s.code;
259         val = (int)s.value;
260         break;
261     case ABS_HAT0Y:
262         r = JS_EVENT_AXIS;
263         num = (int)s.code;
264         val = (int)s.value;
265         break;
266     defaulr:
267         break;
268     }
269     return r;
270 }
271 /**
272  * @brief calc value case 1
273  *        change to -32767 <-> 32767
274  */
275 int CJoyStickEV::calc1pm32767(int val, const struct input_absinfo& ai)
276 {
277     int a = ai.maximum - ai.minimum;
278     double b = (double)val / (double)a;
279     int c = ((int) (b * 65534)) - 32767;
280     return c;
281 }
282
283 /**
284  * @brief calc value case 2
285  *        change to 0 <-> 65534
286  */
287 int CJoyStickEV::calc2p65535(int val, const struct input_absinfo& ai)
288 {
289     int a = ai.maximum - ai.minimum;
290     double b = (double)val / (double)a;
291     int c = (int) (b * 65534);
292     return c;
293 }
294
295 /**
296  * @brief calc value case 3
297  *        change to 0 <-> 32767
298  */
299 int CJoyStickEV::calc3p32767(int val, const struct input_absinfo& ai)
300 {
301     int a = ai.maximum - ai.minimum;
302     double b = (double)val / (double)a;
303     int c = (int) (b * 32767);
304     return c;
305 }
306
307 /**
308  * @brief calc value case 3
309  *        change to 32767 <-> 0
310  */
311 int CJoyStickEV::calc3p32767Reverse(int val, const struct input_absinfo& ai)
312 {
313     int a = ai.maximum - ai.minimum;
314     double b = (double)val / (double)a;
315     int c = abs(((int) (b * 32767)) - 32767);
316     return c;
317 }
318
319 /**
320  * get device name
321  */
322 bool CJoyStickEV::getDeviceName(int fd, char* devNM, size_t sz)
323 {
324     if (0 > fd) {
325         return false;
326     }
327     if (0 > ioctl(fd, EVIOCGNAME(sz), devNM)) {
328         return false;
329     }
330     return true;
331 }
332
333 /**
334  * End of File.(CJoyStickEV.cpp)
335  */