Support Uno4kSE
[vuplus_dvbapp] / lib / driver / rcinput.cpp
1 #include <lib/driver/rcinput.h>
2
3 #include <lib/base/eerror.h>
4
5 #include <sys/ioctl.h>
6 #include <linux/input.h>
7 #include <sys/stat.h>
8
9 #include <lib/base/ebase.h>
10 #include <lib/base/init.h>
11 #include <lib/base/init_num.h>
12 #include <lib/driver/input_fake.h>
13
14 #ifdef VUPLUS_USE_RCKBD 
15 #include <lib/driver/rcconsole.h>
16 extern eRCConsole* g_ConsoleDevice;
17 #define CODE_RC    0
18 #define CODE_ASCII 1
19
20 #define KEY_LALT        56
21 #define KEY_RALT        100
22 #define KEY_LSHIFT      42
23 static int special_key_mode = 0;
24
25 int getType(int code)
26 {
27         switch(code)
28         {
29         case 2:   // 1
30         case 3:   // 2
31         case 4:   // 3
32         case 5:   // 4
33         case 6:   // 5
34         case 7:   // 6
35         case 8:   // 7
36         case 9:   // 8
37         case 10:  // 9
38         case 11:  // 0
39         case 14:  // backspace
40         case 102: // home
41         case 103: // up
42         case 105: // left
43         case 106: // right
44         case 107: // end
45         case 108: // down
46         case 113: // mute
47         case 114: // volume down
48         case 115: // vulume up
49         case 116: // power
50         case 128: // stop
51         case 138: // help
52         case 139: // menu
53         case 163: // FF
54         case 208: // FF
55         case 164: // pause
56         case 165: // RW
57         case 168: // RW
58         case 167: // record
59         case 174: // exit
60         case 176: // timer edit
61         case 207: // play
62         case 352: // ok
63         case 358: // epg
64         case 370: // _subtitle selection
65         case 377: // tv
66         case 384: // tape
67         case 385: // radio
68         case 388: // =text
69         case 392: // audio
70         case 393: // =recorded files
71         case 398: // red
72         case 399: // green
73         case 400: // yellow
74         case 401: // blue
75         case 402: // channel up
76         case 403: // channel down
77         case 407: // >
78         case 412: // <
79                 return CODE_RC;
80         }
81         return CODE_ASCII;
82 }
83 #endif /*VUPLUS_USE_RCKBD*/
84
85 void eRCDeviceInputDev::handleCode(long rccode)
86 {
87         struct input_event *ev = (struct input_event *)rccode;
88         if (ev->type!=EV_KEY)
89                 return;
90 #ifdef VUPLUS_USE_RCKBD
91         //eDebug("value : %d, code : %d, type : %d, type : %s", ev->value, ev->code, ev->type, getType(ev->code)?"ASCII":"RC");
92         if(getType(ev->code) || special_key_mode)
93         {
94                 switch(ev->value)
95                 {
96                         case 0:
97                                 if(ev->code == KEY_RALT || ev->code == KEY_LSHIFT || ev->code == KEY_LALT)
98                                 {
99                                         special_key_mode = 0;
100                                         g_ConsoleDevice->handleCode(0);
101                                 }
102                                 break;
103                         case 1: 
104                                 if(ev->code == KEY_RALT || ev->code == KEY_LSHIFT || ev->code == KEY_LALT)
105                                         special_key_mode = 1;
106                                 g_ConsoleDevice->handleCode(ev->code);
107                                 break;
108                         case 2: break;
109                 }
110                 return;
111         }
112 #endif /*VUPLUS_USE_RCKBD*/
113
114 //      eDebug("%x %x %x", ev->value, ev->code, ev->type);
115         int km = iskeyboard ? input->getKeyboardMode() : eRCInput::kmNone;
116
117 //      eDebug("keyboard mode %d", km);
118         
119         if (km == eRCInput::kmAll)
120                 return;
121
122         if (km == eRCInput::kmAscii)
123         {
124 //              eDebug("filtering.. %d", ev->code);
125                 bool filtered = ( ev->code > 0 && ev->code < 61 );
126                 switch (ev->code)
127                 {
128                         case KEY_RESERVED:
129                         case KEY_ESC:
130                         case KEY_TAB:
131                         case KEY_BACKSPACE:
132                         case KEY_ENTER:
133                         case KEY_LEFTCTRL:
134                         case KEY_RIGHTSHIFT:
135                         case KEY_LEFTALT:
136                         case KEY_CAPSLOCK:
137                         case KEY_INSERT:
138                         case KEY_DELETE:
139                         case KEY_MUTE:
140                                 filtered=false;
141                         default:
142                                 break;
143                 }
144                 if (filtered)
145                         return;
146 //              eDebug("passed!");
147         }
148
149         switch (ev->value)
150         {
151         case 0:
152                 /*emit*/ input->keyPressed(eRCKey(this, ev->code, eRCKey::flagBreak));
153                 break;
154         case 1:
155                 /*emit*/ input->keyPressed(eRCKey(this, ev->code, 0));
156                 break;
157         case 2:
158                 /*emit*/ input->keyPressed(eRCKey(this, ev->code, eRCKey::flagRepeat));
159                 break;
160         }
161 }
162
163 eRCDeviceInputDev::eRCDeviceInputDev(eRCInputEventDriver *driver)
164         :eRCDevice(driver->getDeviceName(), driver), iskeyboard(false)
165 {
166         if (strcasestr(id.c_str(), "keyboard") != NULL)
167                 iskeyboard = true;
168         setExclusive(true);
169         eDebug("Input device \"%s\" is %sa keyboard.", id.c_str(), iskeyboard ? "" : "not ");
170 }
171
172 void eRCDeviceInputDev::setExclusive(bool b)
173 {
174         if (!iskeyboard)
175                 driver->setExclusive(b);
176 }
177
178 const char *eRCDeviceInputDev::getDescription() const
179 {
180         return id.c_str();
181 }
182
183 class eInputDeviceInit
184 {
185         ePtrList<eRCInputEventDriver> m_drivers;
186         ePtrList<eRCDeviceInputDev> m_devices;
187 public:
188         eInputDeviceInit()
189         {
190                 int i = 0;
191                 while (1)
192                 {
193                         struct stat s;
194                         char filename[128];
195                         sprintf(filename, "/dev/input/event%d", i);
196                         if (stat(filename, &s))
197                                 break;
198                         eRCInputEventDriver *p;
199                         m_drivers.push_back(p = new eRCInputEventDriver(filename));
200                         m_devices.push_back(new eRCDeviceInputDev(p));
201                         ++i;
202                 }
203                 eDebug("Found %d input devices!", i);
204         }
205         
206         ~eInputDeviceInit()
207         {
208                 while (m_drivers.size())
209                 {
210                         delete m_devices.back();
211                         m_devices.pop_back();
212                         delete m_drivers.back();
213                         m_drivers.pop_back();
214                 }
215         }
216 };
217
218 eAutoInitP0<eInputDeviceInit> init_rcinputdev(eAutoInitNumbers::rc+1, "input device driver");