Added more code for handling tuio server stuff with liblo.
[xf86-input-tuio.git] / src / tuio.c
blob3149f11d0c07e251acd784658d2c320f6a8df3c3
1 /*
2 * Copyright (c) 2009 Ryan Huffman
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20 * THE SOFTWARE.
22 * Authors:
23 * Ryan Huffman (ryanhuffman@gmail.com)
26 #include <unistd.h>
28 #include <xf86Xinput.h>
29 #include <X11/extensions/XIproto.h>
30 #include <X11/extensions/XInput2.h>
31 #include <xf86_OSlib.h>
33 #include "tuio.h"
35 #ifdef HAVE_CONFIG_H
36 #include "config.h"
37 #endif
39 /* Module Functions */
40 static pointer
41 TuioPlug(pointer, pointer, int *, int *);
43 static void
44 TuioUnplug(pointer);
46 /* Driver Functions */
47 static InputInfoPtr
48 TuioPreInit(InputDriverPtr, IDevPtr, int);
50 static void
51 TuioUnInit(InputDriverPtr, InputInfoPtr, int);
53 static void
54 TuioReadInput(InputInfoPtr);
56 static int
57 TuioControl(DeviceIntPtr, int);
59 /* Internal Functions */
60 static int
61 _tuio_lo_cur2d_handle(const char *path,
62 const char *types,
63 lo_arg **argv,
64 int argc,
65 void *data,
66 void *user_data);
68 static void
69 lo_error(int num,
70 const char *msg,
71 const char *path);
74 static XF86ModuleVersionInfo TuioVersionRec =
76 "tuio",
77 MODULEVENDORSTRING,
78 MODINFOSTRING1,
79 MODINFOSTRING2,
80 XORG_VERSION_CURRENT,
81 PACKAGE_VERSION_MAJOR, PACKAGE_VERSION_MINOR, PACKAGE_VERSION_PATCHLEVEL,
82 ABI_CLASS_XINPUT,
83 ABI_XINPUT_VERSION,
84 MOD_CLASS_XINPUT,
85 {0, 0, 0, 0}
88 _X_EXPORT InputDriverRec TUIO =
91 "tuio",
92 NULL,
93 TuioPreInit,
94 TuioUnInit,
95 NULL,
99 _X_EXPORT XF86ModuleData tuioModuleData =
101 &TuioVersionRec,
102 TuioPlug,
103 TuioUnplug
106 static pointer
107 TuioPlug(pointer module,
108 pointer options,
109 int *errmaj,
110 int *errmin)
112 xf86AddInputDriver(&TUIO, module, 0);
113 return module;
116 static void
117 TuioUnplug(pointer p)
122 * Pre-initialization of new device
124 * TODO:
125 * - Parse configuration options
126 * - Setup internal data
128 static InputInfoPtr
129 TuioPreInit(InputDriverPtr drv,
130 IDevPtr dev,
131 int flags)
133 InputInfoPtr pInfo;
134 TuioDevicePtr pTuio;
135 const char *device;
137 if (!(pInfo = xf86AllocateInput(drv, 0)))
138 return NULL;
140 pTuio = xcalloc(1, sizeof(TuioDeviceRec));
141 if (!pTuio) {
142 pInfo->private = NULL;
143 xf86DeleteInput(pInfo, 0);
144 return NULL;
147 pInfo->private = pTuio;
149 pInfo->name = xstrdup(dev->identifier);
150 pInfo->flags = 0;
151 pInfo->type_name = XI_TOUCHSCREEN; /* FIXME: Correct type? */
152 pInfo->conf_idev = dev;
153 pInfo->read_input = TuioReadInput; /* Set callback */
154 pInfo->switch_mode = NULL;
155 pInfo->device_control = TuioControl; /* Set callback */
157 /* Process common device options */
158 xf86CollectInputOptions(pInfo, NULL, NULL);
159 xf86ProcessCommonOptions(pInfo, pInfo->options);
161 pInfo->flags |= XI86_OPEN_ON_INIT;
162 pInfo->flags |= XI86_CONFIGURED;
164 return pInfo;
167 static void
168 TuioUnInit(InputDriverPtr drv,
169 InputInfoPtr pInfo,
170 int flags)
172 TuioDevicePtr pTuio = pInfo->private;
174 xfree(pTuio);
175 xf86DeleteInput(pInfo, 0);
179 * Handle new data on the socket
181 static void
182 TuioReadInput(InputInfoPtr pInfo)
184 TuioDevicePtr pTuio = pInfo->private;
185 char data;
187 xf86Msg(X_INFO, "%s: Reading input\n", pInfo->name);
189 lo_server_recv_noblock(pTuio->server, 0);
191 //while(xf86WaitForInput(pInfo->fd, 0) > 0)
193 /* Read Input */
195 /* xf8PostMotionEvent() */
200 * Handle device state changes
202 static int
203 TuioControl(DeviceIntPtr device,
204 int what)
206 InputInfoPtr pInfo = device->public.devicePrivate;
207 TuioDevicePtr pTuio = pInfo->private;
209 switch (what)
211 case DEVICE_INIT:
212 xf86Msg(X_INFO, "%s: Init\n", pInfo->name);
213 break;
215 case DEVICE_ON: /* Open device socket and start listening! */
216 xf86Msg(X_INFO, "%s: On.\n", pInfo->name);
217 if (device->public.on) /* already on! */
218 break;
220 pTuio->server = lo_server_new_with_proto("3333", LO_UDP, lo_error);
221 if (pTuio->server == NULL) {
222 xf86Msg(X_ERROR, "%s: Error allocating new lo_server\n",
223 pInfo->name);
224 return BadAlloc;
227 /* Register to receive all /tuio/2Dcur messages */
228 lo_server_add_method(pTuio->server, "/tuio/2Dcur", NULL,
229 _tuio_lo_cur2d_handle, pInfo);
231 pInfo->fd = lo_server_get_socket_fd(pTuio->server);
232 xf86Msg(X_INFO, "%s: Socket = %n\n", pInfo->name, pInfo->fd);
234 //xf86FlushInput(pInfo->fd);
235 xf86AddEnabledDevice(pInfo);
236 device->public.on = TRUE;
237 break;
239 case DEVICE_OFF:
240 xf86Msg(X_INFO, "%s: Off\n", pInfo->name);
241 if (!device->public.on)
242 break;
244 lo_server_free(pTuio->server);
246 xf86RemoveEnabledDevice(pInfo);
247 pInfo->fd = -1;
248 device->public.on = FALSE;
249 break;
251 case DEVICE_CLOSE:
252 xf86Msg(X_INFO, "%s: Close\n", pInfo->name);
254 lo_server_free(pTuio->server);
255 pInfo->fd = -1;
256 device->public.on = FALSE;
257 break;
260 return Success;
263 static int
264 _tuio_create_master() {
265 //XICreateMasterInfo ci;
266 //unsigned int blobid;
267 //char cur_name[21]; /* Max len: 20 char + \0 */
269 //sprintf(cur_name, "tuio_blob_%u", blobid);
271 //c.type = XICreateMaster;
272 //c.name = cur_name;
276 * Handles OSC messages in the /tuio/2Dcur address space
278 static int
279 _tuio_lo_cur2d_handle(const char *path,
280 const char *types,
281 lo_arg **argv,
282 int argc,
283 void *data,
284 void *user_data)
286 InputInfoPtr pInfo = user_data;
287 TuioDevicePtr pTuio = pInfo->private;
289 if (argc < 1) {
290 xf86Msg(X_ERROR, "%s: \n", pInfo->name);
291 return 1;
294 /* Parse message type */
295 if (strcmp(&argv[0]->s, "set")) {
297 } else if (strcmp(&argv[0]->s, "alive")) {
299 } else if (strcmp(&argv[0]->s, "fseq")) {
302 return 0;
306 * liblo error handler
308 static void
309 lo_error(int num,
310 const char *msg,
311 const char *path)
313 xf86Msg(X_ERROR, "liblo: %s\n", msg);