summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 85ff2be)
raw | patch | inline | side by side (parent: 85ff2be)
author | Jon A. Cruz <jon@joncruz.org> | |
Sun, 14 Mar 2010 02:18:39 +0000 (18:18 -0800) | ||
committer | Jon A. Cruz <jon@joncruz.org> | |
Sun, 14 Mar 2010 02:18:39 +0000 (18:18 -0800) |
src/dialogs/input.cpp | patch | blob | history |
diff --git a/src/dialogs/input.cpp b/src/dialogs/input.cpp
index a8892bde428e5039c0a4c9de7470ab8757c606e5..d34655ecc9e9e1435fb399e0a7a1adcd86a52526 100644 (file)
--- a/src/dialogs/input.cpp
+++ b/src/dialogs/input.cpp
#include <gtk/gtksignal.h>
#include <gtk/gtkinputdialog.h>
#include <glibmm/ustring.h>
+#include <list>
#include "macros.h"
#include "verbs.h"
static gint x = -1000, y = -1000, w = 0, h = 0;
static Glib::ustring const prefs_path = "/dialogs/input/";
+#define noTEST_WITH_GOOD_TABLET 1
+#define noTEST_WITH_BAD_TABLET 1
+
+#if defined(TEST_WITH_GOOD_TABLET) || defined(TEST_WITH_BAD_TABLET)
+static int testDeviceCount = 0;
+static GdkDevice* testDevices = 0;
+
+// Defined at the end of the file to keep debugging out of the way.
+static void initTestDevices();
+#endif
+
+static std::list<GdkDevice *> getInputDevices()
+{
+ std::list<GdkDevice*> devices;
+
+#if defined(TEST_WITH_GOOD_TABLET) || defined(TEST_WITH_BAD_TABLET)
+ initTestDevices();
+ for (int i = 0; i < testDeviceCount; i++) {
+ devices.push_back(&testDevices[i]);
+ }
+#else
+ for (GList *ptr = gdk_devices_list(); ptr; ptr = ptr->next) {
+ GdkDevice *device = static_cast<GdkDevice *>(ptr->data);
+ devices.push_back(device);
+ }
+#endif
+
+ return devices;
+}
+
+// wrap these GDK calls to be able to intercept for testing.
+
+static bool setDeviceMode( GdkDevice *device, GdkInputMode mode )
+{
+#if defined(TEST_WITH_GOOD_TABLET) || defined(TEST_WITH_BAD_TABLET)
+ (void)device;
+ (void)mode;
+ bool retVal = true; // Can't let the Gdk call be called with bad data
+#else
+ bool retVal = gdk_device_set_mode(device, mode);
+#endif
+ return retVal;
+}
+
+static void setDeviceAxisUse( GdkDevice *device, guint index, GdkAxisUse use )
+{
+#if defined(TEST_WITH_GOOD_TABLET) && !defined(TEST_WITH_BAD_TABLET)
+ (void)device;
+ (void)index;
+ (void)use;
+#else
+ gdk_device_set_axis_use(device, index, use);
+#endif
+}
+
+static void setDeviceKey( GdkDevice* device, guint index, guint keyval, GdkModifierType modifiers )
+{
+#if defined(TEST_WITH_GOOD_TABLET) && !defined(TEST_WITH_BAD_TABLET)
+ (void)device;
+ (void)index;
+ (void)keyval;
+ (void)modifiers;
+#else
+ gdk_device_set_key(device, index, keyval, modifiers);
+#endif
+}
+
+
static void
sp_input_dialog_destroy (GtkObject */*object*/, gpointer /*data*/)
{
// This might break if someone has two tablets with broken names, but it's
// not possible to do anything 100% correct then.
bool broken = false;
- if (!str || *str == 0) {
+
+ if (!str || (*str == 0)) {
broken = true;
} else {
for (gchar const *s = str; *s; ++s) {
- if (*s < 0x20 || *s >= 0x7f) {
+ if ((*s < 0x20) || (*s >= 0x7f)) {
broken = true;
break;
}
return device_path;
}
-void
-sp_input_load_from_preferences (void)
+void sp_input_load_from_preferences(void)
{
Inkscape::Preferences *prefs = Inkscape::Preferences::get();
- for (GList *list_ptr = gdk_devices_list(); list_ptr != NULL; list_ptr = list_ptr->next) {
- GdkDevice *device = static_cast<GdkDevice *>(list_ptr->data);
+ std::list<GdkDevice *> devices = getInputDevices();
+ for (std::list<GdkDevice *>::iterator it = devices.begin(); it != devices.end(); ++it) {
+ GdkDevice *device = *it;
+
+// g_message(" s:%d m:%d hc:%d a:%d k:%d [%s]", device->source, device->mode, device->has_cursor, device->num_axes, device->num_keys, device->name);
+// for (int i = 0; i < device->num_axes; i++) {
+// GdkDeviceAxis &axis = device->axes[i];
+// g_message(" axis[%d] u:%d min:%f max:%f", i, axis.use, axis.min, axis.max);
+// }
Glib::ustring device_path = sanitized_device_path(device->name);
+// if (device_path != (Glib::ustring("/devices/") + device->name)) {
+// g_message(" re-name [%s]", device_path.c_str());
+// }
- GdkInputMode mode;
Glib::ustring device_mode = prefs->getString(device_path + "/mode");
- if (device_mode.empty())
- mode = GDK_MODE_DISABLED;
- else if (device_mode == "screen")
+ GdkInputMode mode = GDK_MODE_DISABLED;
+ if (device_mode == "screen") {
mode = GDK_MODE_SCREEN;
- else if (device_mode == "window")
+ } else if (device_mode == "window") {
mode = GDK_MODE_WINDOW;
- else
- mode = GDK_MODE_DISABLED;
+ }
if (device->mode != mode) {
- gdk_device_set_mode(device, mode);
+ setDeviceMode(device, mode);
}
Glib::ustring::size_type pos0, pos1;
pos0 = pos1 = 0;
for (gint i=0; i < device->num_axes; i++) {
pos1 = axes_str.find(';', pos0);
- if (pos1 == Glib::ustring::npos)
+ if (pos1 == Glib::ustring::npos) {
break; // Too few axis specifications
+ }
axis_use = GDK_AXIS_IGNORE;
- for (gint j=0; j < GDK_AXIS_LAST; j++)
+ for (gint j=0; j < GDK_AXIS_LAST; j++) {
if (!strcmp(axes_str.substr(pos0, pos1-pos0).c_str(), axis_use_strings[j])) {
axis_use = static_cast<GdkAxisUse>(j);
break;
}
- gdk_device_set_axis_use(device, i, axis_use);
+ }
+ setDeviceAxisUse(device, i, axis_use);
pos0 = pos1 + 1;
}
pos0 = pos1 = 0;
for (gint i=0; i < device->num_keys; i++) {
pos1 = keys_str.find(';', pos0);
- if (pos1 == Glib::ustring::npos)
+ if (pos1 == Glib::ustring::npos) {
break; // Too few key specifications
+ }
gtk_accelerator_parse(keys_str.substr(pos0, pos1-pos0).c_str(), &keyval, &modifier);
- gdk_device_set_key(device, i, keyval, modifier);
+ setDeviceKey(device, i, keyval, modifier);
pos0 = pos1 + 1;
}
}
}
-void
-sp_input_save_to_preferences (void)
+void sp_input_save_to_preferences(void)
{
Inkscape::Preferences *prefs = Inkscape::Preferences::get();
- for (GList *list_ptr = gdk_devices_list(); list_ptr != NULL; list_ptr = list_ptr->next) {
- GdkDevice *device = static_cast<GdkDevice *>(list_ptr->data);
+ std::list<GdkDevice *> devices = getInputDevices();
+ for (std::list<GdkDevice *>::iterator it = devices.begin(); it != devices.end(); ++it) {
+ GdkDevice *device = *it;
Glib::ustring device_path = sanitized_device_path(device->name);
gtk_window_present ((GtkWindow *) dlg);
}
+// /////////////////////////////////
+// For debugging:
+// /////////////////////////////////
+
+
+#if defined(TEST_WITH_GOOD_TABLET)
+static void initTestDevices()
+{
+ static bool init = false;
+ if (!init) {
+ static GdkDevice devs[5] = {};
+ int i = 0; // use variable instead of constant to allow devices to be moved around, commented out, etc.
+
+ {
+ // Laptop trackpad
+ devs[i].name = g_strdup("pointer");
+ devs[i].source = GDK_SOURCE_MOUSE;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Tablet stylus
+ devs[i].name = g_strdup("pen");
+ devs[i].source = GDK_SOURCE_PEN;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0},
+ {GDK_AXIS_PRESSURE, 0, 1},
+ {GDK_AXIS_XTILT, -1, 1},
+ {GDK_AXIS_YTILT, -1, 1}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Puck
+ devs[i].name = g_strdup("cursor");
+ devs[i].source = GDK_SOURCE_CURSOR;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0},
+ {GDK_AXIS_PRESSURE, 0, 1},
+ {GDK_AXIS_XTILT, -1, 1},
+ {GDK_AXIS_YTILT, -1, 1}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Back of tablet stylus
+ devs[i].name = g_strdup("eraser");
+ devs[i].source = GDK_SOURCE_ERASER;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0},
+ {GDK_AXIS_PRESSURE, 0, 1},
+ {GDK_AXIS_XTILT, -1, 1},
+ {GDK_AXIS_YTILT, -1, 1}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Main (composit) mouse device
+ devs[i].name = g_strdup("Core Pointer");
+ devs[i].source = GDK_SOURCE_MOUSE;
+ devs[i].mode = GDK_MODE_SCREEN;
+ devs[i].has_cursor = 1;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ testDeviceCount = i;
+ testDevices = devs;
+ init = true;
+ }
+}
+#elif defined(TEST_WITH_BAD_TABLET)
+
+/**
+ * Uses the current time in seconds to change a name to be unique from one
+ * run of the program to the next.
+ */
+void perturbName(gchar *str)
+{
+ if (str) {
+ GTimeVal when = {0,0};
+ g_get_current_time(&when);
+ gchar *tmp = g_strdup_printf("%ld", when.tv_sec);
+
+ size_t partLen = strlen(tmp);
+ size_t len = strlen(str);
+ if (len > (partLen + 4)) {
+ size_t pos = (len - partLen) / 2;
+ for (size_t i = 0; i < partLen; i++) {
+ str[pos + i] = tmp[i];
+ }
+ }
+ g_free(tmp);
+ }
+}
+
+static void initTestDevices()
+{
+ static bool init = false;
+ if (!init) {
+ static GdkDevice devs[5] = {};
+ int i = 0; // use variable instead of constant to allow devices to be moved around, commented out, etc.
+
+ {
+ // Main (composit) mouse device
+ devs[i].name = g_strdup("Core Pointer");
+ devs[i].source = GDK_SOURCE_MOUSE;
+ devs[i].mode = GDK_MODE_SCREEN;
+ devs[i].has_cursor = 1;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Back of tablet stylus
+ devs[i].name = g_strdup("\346\205\227\347\221\254\347\201\257\345\220\240\346\211\241\346\225\254t\303\265\006 \347\211\220\347\215\245\347\225\263\346\225\262\345\214\240\347\245\264\347\225\254s\357\227\230#\354\234\274C\356\232\210\307\255\350\271\214\310\201\350\222\200\310\201\356\202\250\310\200\350\223\260\310\201\356\202\250\310\200");
+ perturbName(devs[i].name);
+ devs[i].source = GDK_SOURCE_ERASER;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0},
+ {GDK_AXIS_PRESSURE, 0, 1},
+ {GDK_AXIS_XTILT, -1, 1},
+ {GDK_AXIS_YTILT, -1, 1}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ {
+ // Tablet stylus
+ devs[i].name = g_strdup("\346\205\227\347\221\254\347\201\257\345\220\240\346\211\241\346\225\254t\303\265\006 \347\211\220\347\215\245\347\225\263\346\225\262\345\214\240\347\245\264\347\225\254s\357\227\230#\354\234\274C\341\221\230\307\255\343\277\214\310\202\343\230\200\310\202\331\270\310\202\343\231\260\310\202\331\270\310\202");
+ perturbName(devs[i].name);
+ devs[i].source = GDK_SOURCE_PEN;
+ devs[i].mode = GDK_MODE_DISABLED;
+ devs[i].has_cursor = 0;
+ static GdkDeviceAxis tmp[] = {{GDK_AXIS_X, 0, 0},
+ {GDK_AXIS_Y, 0, 0},
+ {GDK_AXIS_PRESSURE, 0, 1},
+ {GDK_AXIS_XTILT, -1, 1},
+ {GDK_AXIS_YTILT, -1, 1}};
+ devs[i].num_axes = G_N_ELEMENTS(tmp);
+ devs[i].axes = tmp;
+ devs[i].num_keys = 0;
+ devs[i].keys = 0;
+ i++;
+ }
+
+ testDeviceCount = i;
+ testDevices = devs;
+ init = true;
+ }
+}
+#endif
+
/*
Local Variables: