aboutsummaryrefslogtreecommitdiff
path: root/multitouch.c
diff options
context:
space:
mode:
authorHans-Christoph Steiner <eighthave@users.sourceforge.net>2009-10-25 04:11:05 +0000
committerHans-Christoph Steiner <eighthave@users.sourceforge.net>2009-10-25 04:11:05 +0000
commit029f0be8e4beea787feb984b2797f6e23f7964ac (patch)
tree40c321591bff2952a908926e0006c581deb563af /multitouch.c
parente95cc04a85be1ef67d9be53a8bb2cc05b1633231 (diff)
first version of object for private MultitouchSupport framework based on code from steide and fingerpinger
svn path=/trunk/externals/apple/; revision=12669
Diffstat (limited to 'multitouch.c')
-rw-r--r--multitouch.c148
1 files changed, 148 insertions, 0 deletions
diff --git a/multitouch.c b/multitouch.c
new file mode 100644
index 0000000..3118d8c
--- /dev/null
+++ b/multitouch.c
@@ -0,0 +1,148 @@
+/* --------------------------------------------------------------------------*/
+/* */
+/* get info from the multitouch trackpad on Apple Mac OS X */
+/* based on 'fingerpinger' */
+/* */
+/* Copyright (c) 2009 Hans-Christoph Steiner */
+/* Copyright (c) 2009 Michael & Max Egger */
+/* Copyright (c) 2008 Steike */
+/* */
+/* This program is free software; you can redistribute it and/or */
+/* modify it under the terms of the GNU General Public License */
+/* as published by the Free Software Foundation; either version 3 */
+/* of the License, or (at your option) any later version. */
+/* */
+/* See file LICENSE for further informations on licensing terms. */
+/* */
+/* This program is distributed in the hope that it will be useful, */
+/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
+/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
+/* GNU General Public License for more details. */
+/* */
+/* You should have received a copy of the GNU General Public License */
+/* along with this program; if not, write to the Free Software Foundation, */
+/* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA */
+/* */
+/* --------------------------------------------------------------------------*/
+
+#include <mach/mach.h>
+#include <IOKit/IOKitLib.h>
+#include <math.h>
+#include <unistd.h>
+#include <CoreFoundation/CoreFoundation.h>
+#include "MultitouchSupport.h"
+#include <m_pd.h>
+
+//#define DEBUG(x)
+#define DEBUG(x) x
+
+/*------------------------------------------------------------------------------
+ * CLASS DEF
+ */
+
+static t_class *multitouch_class;
+
+typedef struct _multitouch {
+ t_object x_obj;
+ t_outlet* data_outlet;
+ t_outlet* status_outlet;
+} t_multitouch;
+
+static MTDeviceRef dev; /* reference to the trackpad */
+static int fingerc; /* current count of Fingers */
+static Finger fingerv[32]; /* current list of Fingers */
+static int polling = 0; /* set when one instance is polling so others don't */
+
+/*------------------------------------------------------------------------------
+ * CALLBACK TO GET DATA
+ */
+
+static int callback(int device, Finger *data, int nFingers, double timestamp, int frame)
+{
+ DEBUG(post("callback"););
+ memcpy(fingerv, data, nFingers * sizeof(Finger));
+ fingerc = nFingers;
+ return 0;
+}
+
+/*------------------------------------------------------------------------------
+ * IMPLEMENTATION
+ */
+
+static void multitouch_output(t_multitouch* x)
+{
+ DEBUG(post("multitouch_output"););
+ int i;
+ t_atom output_list[12];
+ for (i=0; i < fingerc; i++) {
+ Finger *f = &fingerv[i];
+ SETFLOAT(output_list,i);
+ SETFLOAT(output_list + 1 , f->frame);
+ SETFLOAT(output_list + 2 , f->angle);
+ SETFLOAT(output_list + 3 , f->majorAxis);
+ SETFLOAT(output_list + 4 , f->minorAxis);
+ SETFLOAT(output_list + 5 , f->normalized.pos.x);
+ SETFLOAT(output_list + 6 , f->normalized.pos.y);
+ SETFLOAT(output_list + 7 , f->normalized.vel.x);
+ SETFLOAT(output_list + 8 , f->normalized.vel.y);
+ SETFLOAT(output_list + 9 , f->identifier);
+ SETFLOAT(output_list + 10 , f->state);
+ SETFLOAT(output_list + 11 , f->size);
+ outlet_list(x->data_outlet, &s_, 12, output_list);
+ }
+}
+
+
+static void multitouch_float(t_multitouch* x, t_float f)
+{
+ DEBUG(post("multitouch_float"););
+ if (f > 0) {
+ polling++;
+ /* if I am the first instance to poll, then set the callback up */
+ if (polling == 1) {
+ dev = MTDeviceCreateDefault();
+ MTRegisterContactFrameCallback(dev, callback);
+ MTDeviceStart(dev, 0);
+ }
+ } else {
+ polling--;
+ /* if I am the last instance, clean up the callback stuff */
+ if (polling == 0) {
+ MTDeviceStop(dev);
+ MTDeviceRelease(dev);
+ dev = NULL;
+ }
+ }
+}
+
+
+static void multitouch_free(t_multitouch* x)
+{
+ DEBUG(post("multitouch_free"););
+ /* make sure callback is released before deleting the object */
+ multitouch_float(x, 0);
+}
+
+static void *multitouch_new(void)
+{
+ DEBUG(post("multitouch_new"););
+ t_multitouch *x = (t_multitouch *)pd_new(multitouch_class);
+
+ x->data_outlet = outlet_new(&x->x_obj, &s_list);
+ x->status_outlet = outlet_new(&x->x_obj, &s_anything);
+
+ return (x);
+}
+
+void multitouch_setup(void)
+{
+ multitouch_class = class_new(gensym("multitouch"),
+ (t_newmethod)multitouch_new,
+ (t_method)multitouch_free,
+ sizeof(t_multitouch),
+ CLASS_DEFAULT,
+ 0);
+ /* add inlet datatype methods */
+ class_addbang(multitouch_class,(t_method) multitouch_output);
+ class_addfloat(multitouch_class,(t_method) multitouch_float);
+}