--- /dev/null
+/*
+ * (C) GraÅžvydas "notaz" Ignotas, 2011
+ *
+ * This work is licensed under the terms of any of these licenses
+ * (at your option):
+ * - GNU GPL, version 2 or later.
+ * - GNU LGPL, version 2.1 or later.
+ * See the COPYING file in the top-level directory.
+ */
+
+#include <stdio.h>
+#include <tslib.h>
+
+#include "common/input.h"
+#include "in_tsbutton.h"
+
+#define IN_TSBUTTON_PREFIX "tsbutton:"
+#define IN_TSBUTTON_COUNT 4
+static int tsbutton_down_id;
+static int last_tsbutton_id;
+
+#define TS_WIDTH 320
+#define TS_HEIGHT 240
+
+// HACK: stealing this from plugin_lib
+extern void *tsdev;
+extern int (*pts_read)(struct tsdev *dev, struct ts_sample *sample, int nr);
+extern int (*pts_fd)(struct tsdev *dev);
+
+static const char * const in_tsbutton_keys[IN_TSBUTTON_COUNT] = {
+ "TS1", "TS2", "TS3", "TS4",
+};
+
+static void in_tsbutton_probe(void)
+{
+ struct tsdev *dev = tsdev;
+ if (dev == NULL) {
+ fprintf(stderr, "in_tsbutton_probe: missing tsdev\n");
+ return;
+ }
+
+ in_register(IN_TSBUTTON_PREFIX "touchscreen as buttons",
+ pts_fd(dev), NULL, IN_TSBUTTON_COUNT, in_tsbutton_keys, 0);
+}
+
+static const char * const *
+in_tsbutton_get_key_names(int *count)
+{
+ *count = IN_TSBUTTON_COUNT;
+ return in_tsbutton_keys;
+}
+
+static int update_button(void)
+{
+ struct tsdev *dev = tsdev;
+ struct ts_sample sample;
+ int sx = 0, sy = 0, sp = 0, updated = 0;
+
+ if (dev == NULL)
+ return -1;
+
+ while (pts_read(dev, &sample, 1) > 0) {
+ sx = sample.x;
+ sy = sample.y;
+ sp = sample.pressure;
+ updated = 1;
+ }
+
+ if (updated) {
+ if (sp == 0)
+ tsbutton_down_id = -1;
+ else {
+ // 0 1
+ // 2 3
+ tsbutton_down_id = 0;
+ if (sx > TS_WIDTH / 2)
+ tsbutton_down_id++;
+ if (sy > TS_HEIGHT / 2)
+ tsbutton_down_id += 2;
+ }
+ }
+
+ return 0;
+}
+
+static int in_tsbutton_update(void *drv_data, const int *binds, int *result)
+{
+ int ret, t;
+
+ ret = update_button();
+ if (ret != 0)
+ return ret;
+
+ if (tsbutton_down_id >= 0)
+ for (t = 0; t < IN_BINDTYPE_COUNT; t++)
+ result[t] |= binds[IN_BIND_OFFS(tsbutton_down_id, t)];
+
+ return 0;
+}
+
+static int in_tsbutton_update_keycode(void *data, int *is_down)
+{
+ int ret, ret_kc = -1, ret_down = 0;
+
+ ret = update_button();
+ if (ret != 0)
+ return ret;
+
+ if (tsbutton_down_id == last_tsbutton_id)
+ return -1;
+
+ if (tsbutton_down_id >= 0) {
+ if (last_tsbutton_id >= 0) {
+ ret_kc = last_tsbutton_id;
+ last_tsbutton_id = -1;
+ }
+ else {
+ ret_down = 1;
+ ret_kc = tsbutton_down_id;
+ last_tsbutton_id = tsbutton_down_id;
+ }
+ }
+ else {
+ ret_kc = last_tsbutton_id;
+ last_tsbutton_id = -1;
+ }
+
+ if (is_down != NULL)
+ *is_down = ret_down;
+
+ return ret_kc;
+}
+
+static const in_drv_t in_tsbutton_drv = {
+ .prefix = IN_TSBUTTON_PREFIX,
+ .probe = in_tsbutton_probe,
+ .get_key_names = in_tsbutton_get_key_names,
+ .update = in_tsbutton_update,
+ .update_keycode = in_tsbutton_update_keycode,
+};
+
+void in_tsbutton_init(void)
+{
+ tsbutton_down_id = last_tsbutton_id = -1;
+ in_register_driver(&in_tsbutton_drv);
+}
+
static int gun_x, gun_y, gun_in;
static int ts_multiplier_x, ts_multiplier_y, ts_offs_x, ts_offs_y;
-static int (*pts_read)(struct tsdev *dev, struct ts_sample *sample, int nr);
+int (*pts_read)(struct tsdev *dev, struct ts_sample *sample, int nr);
+int (*pts_fd)(struct tsdev *dev);
#define limit(v, min, max) \
if (v < min) v = min; \
tsdevname = "/dev/input/touchscreen0";
// avoid hard dep on tslib
- ltsh = dlopen("/usr/lib/libts-1.0.so.0", RTLD_LAZY);
+ ltsh = dlopen("/usr/lib/libts-1.0.so.0", RTLD_NOW|RTLD_GLOBAL);
if (ltsh == NULL)
- ltsh = dlopen("/usr/lib/libts-0.0.so.0", RTLD_LAZY);
+ ltsh = dlopen("/usr/lib/libts-0.0.so.0", RTLD_NOW|RTLD_GLOBAL);
if (ltsh == NULL) {
fprintf(stderr, "%s\n", dlerror());
goto fail;
pts_open = dlsym(ltsh, "ts_open");
pts_config = dlsym(ltsh, "ts_config");
pts_read = dlsym(ltsh, "ts_read");
+ pts_fd = dlsym(ltsh, "ts_fd");
pts_close = dlsym(ltsh, "ts_close");
- if (pts_open == NULL || pts_config == NULL || pts_read == NULL || pts_close == NULL) {
+ if (pts_open == NULL || pts_config == NULL || pts_read == NULL
+ || pts_fd == NULL || pts_close == NULL) {
fprintf(stderr, "%s\n", dlerror());
goto fail_dlsym;
}
int in_a1[2] = { 127, 127 }, in_a2[2] = { 127, 127 };
int in_keystate, in_state_gun;
int pl_flip_cnt;
-static void *ts;
+void *tsdev;
void *pl_vout_buf;
static int pl_vout_w, pl_vout_h, pl_vout_bpp;
static int vsync_cnt, flips_per_sec, tick_per_sec;
void pl_update_gun(int *xn, int *xres, int *y, int *in)
{
- if (ts)
- pl_gun_ts_update(ts, xn, y, in);
+ if (tsdev)
+ pl_gun_ts_update(tsdev, xn, y, in);
*xres = pl_vout_w;
*y = *y * pl_vout_h >> 10;
pl_vout_w = pl_vout_h = 256;
pl_vout_bpp = 16;
- ts = pl_gun_ts_init();
+ tsdev = pl_gun_ts_init();
}