]> Dogcows Code - chaz/openbox/blob - openbox/actions.c
make mouse use the new action stuff
[chaz/openbox] / openbox / actions.c
1 /* -*- indent-tabs-mode: nil; tab-width: 4; c-basic-offset: 4; -*-
2
3 actions.h for the Openbox window manager
4 Copyright (c) 2007 Dana Jansens
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 See the COPYING file for a copy of the GNU General Public License.
17 */
18
19 #include "actions.h"
20 #include "gettext.h"
21
22 static void actions_definition_ref(ObActionsDefinition *def);
23 static void actions_definition_unref(ObActionsDefinition *def);
24
25 struct _ObActionsDefinition {
26 guint ref;
27
28 gchar *name;
29 ObActionsType type;
30
31 ObActionsDataSetupFunc setup;
32 ObActionsDataFreeFunc free;
33 ObActionsRunFunc run;
34 };
35
36 struct _ObActionsAct {
37 guint ref;
38
39 ObActionsDefinition *def;
40 gpointer options;
41 };
42
43 static GSList *registered = NULL;
44
45
46 void actions_startup(gboolean reconfig)
47 {
48 if (reconfig) return;
49
50
51 }
52
53 void actions_shutdown(gboolean reconfig)
54 {
55 if (reconfig) return;
56
57 /* free all the registered actions */
58 while (registered) {
59 actions_definition_unref(registered->data);
60 registered = g_slist_delete_link(registered, registered);
61 }
62 }
63
64 gboolean actions_register(const gchar *name,
65 ObActionsType type,
66 ObActionsDataSetupFunc setup,
67 ObActionsDataFreeFunc free,
68 ObActionsRunFunc run)
69 {
70 GSList *it;
71 ObActionsDefinition *def;
72
73 for (it = registered; it; it = g_slist_next(it)) {
74 def = it->data;
75 if (!g_ascii_strcasecmp(name, def->name)) /* already registered */
76 return FALSE;
77 }
78
79 def = g_new(ObActionsDefinition, 1);
80 def->ref = 1;
81 def->name = g_strdup(name);
82 def->type = type;
83 def->setup = setup;
84 def->free = free;
85 def->run = run;
86 return TRUE;
87 }
88
89 static void actions_definition_ref(ObActionsDefinition *def)
90 {
91 ++def->ref;
92 }
93
94 static void actions_definition_unref(ObActionsDefinition *def)
95 {
96 if (def && --def->ref == 0) {
97 g_free(def->name);
98 g_free(def);
99 }
100 }
101
102 ObActionsAct* actions_parse_string(const gchar *name)
103 {
104 GSList *it;
105 ObActionsDefinition *def;
106 ObActionsAct *act = NULL;
107
108 /* find the requested action */
109 for (it = registered; it; it = g_slist_next(it)) {
110 def = it->data;
111 if (!g_ascii_strcasecmp(name, def->name))
112 break;
113 def = NULL;
114 }
115
116 /* if we found the action */
117 if (def) {
118 act = g_new(ObActionsAct, 1);
119 act->ref = 1;
120 act->def = def;
121 actions_definition_ref(act->def);
122 act->options = NULL;
123 } else
124 g_message(_("Invalid action '%s' requested. No such action exists."),
125 name);
126
127 return act;
128 }
129
130 ObActionsAct* actions_parse(ObParseInst *i,
131 xmlDocPtr doc,
132 xmlNodePtr node)
133 {
134 gchar *name;
135 ObActionsAct *act = NULL;
136
137 if (parse_attr_string("name", node, &name)) {
138 if ((act = actions_parse_string(name)))
139 /* there is more stuff to parse here */
140 act->options = act->def->setup(i, doc, node->children);
141
142 g_free(name);
143 }
144
145 return act;
146 }
147
148 void actions_act_ref(ObActionsAct *act)
149 {
150 ++act->ref;
151 }
152
153 void actions_act_unref(ObActionsAct *act)
154 {
155 if (act && --act->ref == 0) {
156 /* free the action specific options */
157 act->def->free(act->options);
158 /* unref the definition */
159 actions_definition_unref(act->def);
160 g_free(act);
161 }
162 }
163
164 static void actions_setup_data(ObActionsData *data,
165 ObUserAction uact,
166 Time time,
167 guint state,
168 guint button,
169 gint x,
170 gint y)
171 {
172 data->any.uact = uact;
173 data->any.time = time;
174 data->any.state = state;
175 data->any.button = button;
176 data->any.x = x;
177 data->any.y = y;
178 }
179
180 void actions_run_acts(GSList *acts,
181 ObUserAction uact,
182 Time time,
183 guint state,
184 guint button,
185 gint x,
186 gint y,
187 ObFrameContext con,
188 struct _ObClient *client,
189 ObActionsInteractiveState interactive)
190 {
191 GSList *it;
192
193 for (it = acts; it; it = g_slist_next(it)) {
194 ObActionsData data;
195 ObActionsAct *act = it->data;
196
197 data.type = act->def->type;
198 actions_setup_data(&data, uact, time, state, button, x, y);
199 switch (data.type) {
200 case OB_ACTION_TYPE_GLOBAL:
201 break;
202 case OB_ACTION_TYPE_CLIENT:
203 data.client.context = con;
204 data.client.c = client;
205 break;
206 case OB_ACTION_TYPE_SELECTOR:
207 data.selector.interactive = interactive;
208 break;
209 default:
210 g_assert_not_reached();
211 }
212
213 /* fire the action's run function with this data */
214 act->def->run(&data, act->options);
215 }
216 }
This page took 0.042929 seconds and 5 git commands to generate.