]> Pileus Git - ~andy/gtk/blob - gdk/linux-fb/gdkinput.c
applied patch from Andreas Persenius <ndap@swipnet.se> that updates the
[~andy/gtk] / gdk / linux-fb / gdkinput.c
1 /* GDK - The GIMP Drawing Kit
2  * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the
16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17  * Boston, MA 02111-1307, USA.
18  */
19
20 /*
21  * Modified by the GTK+ Team and others 1997-2000.  See the AUTHORS
22  * file for a list of people on the GTK+ Team.  See the ChangeLog
23  * files for a list of changes.  These files are distributed with
24  * GTK+ at ftp://ftp.gtk.org/pub/gtk/. 
25  */
26
27 #include <stdlib.h>
28 #include "config.h"
29
30 #include "gdkprivate-fb.h"
31 #include "gdkinput.h"
32 #include "gdkprivate.h"
33 #include "gdkinputprivate.h"
34
35 static const GdkDeviceAxis gdk_input_core_axes[] = {
36   { GDK_AXIS_X, 0, 0 },
37   { GDK_AXIS_Y, 0, 0 }
38 };
39
40 static GdkDevice gdk_input_core_info =
41 {
42   "Core Pointer",
43   GDK_SOURCE_MOUSE,
44   GDK_MODE_SCREEN,
45   TRUE,
46   2,
47   (GdkDeviceAxis *)gdk_input_core_axes,
48   0,
49   NULL
50 };
51
52 GdkDevice *gdk_core_pointer = (GdkDevice *)&gdk_input_core_info;
53
54 /* Global variables  */
55
56 gchar            *gdk_input_gxid_host;
57 gint              gdk_input_gxid_port;
58 gint              gdk_input_ignore_core;
59 GList            *gdk_input_windows;
60 GList            *gdk_input_devices;
61
62 GList *
63 gdk_devices_list (void)
64 {
65   return gdk_input_devices;
66 }
67
68 void
69 gdk_device_set_source (GdkDevice *device, GdkInputSource source)
70 {
71   device->source = source;
72 }
73
74
75 void
76 gdk_device_set_key (GdkDevice      *device,
77                     guint           index,
78                     guint           keyval,
79                     GdkModifierType modifiers)
80 {
81   g_return_if_fail (device != NULL);
82   g_return_if_fail (index < device->num_keys);
83
84   device->keys[index].keyval = keyval;
85   device->keys[index].modifiers = modifiers;
86 }
87
88 void
89 gdk_device_set_axis_use (GdkDevice   *device,
90                          guint        index,
91                          GdkAxisUse   use)
92 {
93   g_return_if_fail (device != NULL);
94   g_return_if_fail (index < device->num_axes);
95
96   device->axes[index].use = use;
97
98   switch (use)
99     {
100     case GDK_AXIS_X:
101     case GDK_AXIS_Y:
102       device->axes[index].min = 0.;
103       device->axes[index].max = 0.;
104       break;
105     case GDK_AXIS_XTILT:
106     case GDK_AXIS_YTILT:
107       device->axes[index].min = -1.;
108       device->axes[index].max = 1;
109       break;
110     default:
111       device->axes[index].min = 0.;
112       device->axes[index].max = 1;
113       break;
114     }
115 }
116
117 void 
118 gdk_device_get_state (GdkDevice       *device,
119                       GdkWindow       *window,
120                       gdouble         *axes,
121                       GdkModifierType *mask)
122 {
123   gint x_int, y_int;
124
125   g_assert(device == gdk_core_pointer);
126       
127   gdk_window_get_pointer (window, &x_int, &y_int, mask);
128
129   if (axes)
130     {
131       axes[0] = x_int;
132       axes[1] = y_int;
133     }
134 }
135
136 void 
137 gdk_device_free_history (GdkTimeCoord **events,
138                          gint           n_events)
139 {
140   gint i;
141   
142   for (i=0; i<n_events; i++)
143     g_free (events[i]);
144
145   g_free (events);
146 }
147
148 gboolean
149 gdk_device_get_history  (GdkDevice         *device,
150                          GdkWindow         *window,
151                          guint32            start,
152                          guint32            stop,
153                          GdkTimeCoord    ***events,
154                          gint              *n_events)
155 {
156   g_return_val_if_fail (window != NULL, FALSE);
157   g_return_val_if_fail (GDK_IS_WINDOW (window), FALSE);
158   g_return_val_if_fail (events != NULL, FALSE);
159   g_return_val_if_fail (n_events != NULL, FALSE);
160
161   *n_events = 0;
162   *events = NULL;
163   return FALSE;
164 }
165
166 gboolean
167 gdk_device_set_mode (GdkDevice   *device,
168                      GdkInputMode mode)
169 {
170   return FALSE;
171 }
172
173 gint
174 gdk_input_enable_window (GdkWindow *window, GdkDevicePrivate *gdkdev)
175 {
176   return TRUE;
177 }
178
179 gint
180 gdk_input_disable_window (GdkWindow *window, GdkDevicePrivate *gdkdev)
181 {
182   return TRUE;
183 }
184
185
186 GdkInputWindow *
187 gdk_input_window_find(GdkWindow *window)
188 {
189   GList *tmp_list;
190
191   for (tmp_list=gdk_input_windows; tmp_list; tmp_list=tmp_list->next)
192     if (((GdkInputWindow *)(tmp_list->data))->window == window)
193       return (GdkInputWindow *)(tmp_list->data);
194
195   return NULL;      /* Not found */
196 }
197
198 /* FIXME: this routine currently needs to be called between creation
199    and the corresponding configure event (because it doesn't get the
200    root_relative_geometry).  This should work with
201    gtk_window_set_extension_events, but will likely fail in other
202    cases */
203
204 void
205 gdk_input_set_extension_events (GdkWindow *window, gint mask,
206                                 GdkExtensionMode mode)
207 {
208   GdkWindowPrivate *window_private;
209   GList *tmp_list;
210   GdkInputWindow *iw;
211
212   g_return_if_fail (window != NULL);
213   g_return_if_fail (GDK_IS_WINDOW (window));
214
215   window_private = (GdkWindowPrivate*) window;
216
217   if (mode == GDK_EXTENSION_EVENTS_NONE)
218     mask = 0;
219
220   if (mask != 0)
221     {
222       iw = g_new(GdkInputWindow,1);
223
224       iw->window = window;
225       iw->mode = mode;
226
227       iw->obscuring = NULL;
228       iw->num_obscuring = 0;
229       iw->grabbed = FALSE;
230
231       gdk_input_windows = g_list_append(gdk_input_windows,iw);
232       window_private->extension_events = mask;
233
234       /* Add enter window events to the event mask */
235       /* FIXME, this is not needed for XINPUT_NONE */
236       gdk_window_set_events (window,
237                              gdk_window_get_events (window) | 
238                              GDK_ENTER_NOTIFY_MASK);
239     }
240   else
241     {
242       iw = gdk_input_window_find (window);
243       if (iw)
244         {
245           gdk_input_windows = g_list_remove(gdk_input_windows,iw);
246           g_free(iw);
247         }
248
249       window_private->extension_events = 0;
250     }
251
252   for (tmp_list = gdk_input_devices; tmp_list; tmp_list = tmp_list->next)
253     {
254       GdkDevicePrivate *gdkdev = (GdkDevicePrivate *)(tmp_list->data);
255
256       if (gdkdev != (GdkDevicePrivate *)gdk_core_pointer)
257         {
258           if (mask != 0 && gdkdev->info.mode != GDK_MODE_DISABLED
259               && (gdkdev->info.has_cursor || mode == GDK_EXTENSION_EVENTS_ALL))
260             gdk_input_enable_window(window,gdkdev);
261           else
262             gdk_input_disable_window(window,gdkdev);
263         }
264     }
265 }
266
267 void
268 gdk_input_window_destroy (GdkWindow *window)
269 {
270   GdkInputWindow *input_window;
271
272   input_window = gdk_input_window_find (window);
273   g_return_if_fail (input_window != NULL);
274
275   gdk_input_windows = g_list_remove (gdk_input_windows,input_window);
276   g_free(input_window);
277 }
278
279 void
280 gdk_input_exit (void)
281 {
282   GList *tmp_list;
283   GdkDevicePrivate *gdkdev;
284
285   for (tmp_list = gdk_input_devices; tmp_list; tmp_list = tmp_list->next)
286     {
287       gdkdev = (GdkDevicePrivate *)(tmp_list->data);
288       if (gdkdev != (GdkDevicePrivate *)gdk_core_pointer)
289         {
290           gdk_device_set_mode((GdkDevice *)gdkdev, GDK_MODE_DISABLED);
291
292           g_free(gdkdev->info.name);
293           g_free(gdkdev->info.axes);
294           g_free(gdkdev->info.keys);
295           g_free(gdkdev);
296         }
297     }
298
299   g_list_free(gdk_input_devices);
300
301   for (tmp_list = gdk_input_windows; tmp_list; tmp_list = tmp_list->next)
302     {
303       g_free(tmp_list->data);
304     }
305   g_list_free(gdk_input_windows);
306 }
307
308 /**
309  * gdk_device_get_axis:
310  * @axis: a #GdkDevice
311  * @axes: pointer to an array of axes
312  * @use: the use to look for
313  * @value: location to store the found value.
314  * 
315  * Interprets an array of double as axis values for a given device,
316  * and locates the value in the array for a given axis use.
317  * 
318  * Return value: %TRUE if the given axis use was found, otherwies %FALSE
319  **/
320 gboolean
321 gdk_device_get_axis (GdkDevice *device, gdouble *axes, GdkAxisUse use, gdouble *value)
322 {
323   gint i;
324   
325   g_return_val_if_fail (device != NULL, FALSE);
326
327   if (axes == NULL)
328     return FALSE;
329   
330   for (i=0; i<device->num_axes; i++)
331     if (device->axes[i].use == use)
332       {
333         if (value)
334           *value = axes[i];
335         return TRUE;
336       }
337   
338   return FALSE;
339 }