]> icculus.org git repositories - mikachu/openbox.git/blob - plugins/mouse/mouseparse.c
move the move/resize functionality into moveresize.c, for use with the netwm atoms...
[mikachu/openbox.git] / plugins / mouse / mouseparse.c
1 #include "kernel/action.h"
2 #include "kernel/parse.h"
3 #include "kernel/prop.h"
4 #include "mouse.h"
5
6 void mouseparse(ParseToken *token)
7 {
8     static char *top = NULL;
9     static char *context = NULL, *button = NULL;
10     static char *arg_str = NULL;
11     static int arg_int = 0;
12     static MouseAction event = -1;
13     static Action *action = NULL;
14     static gboolean err = FALSE;
15
16     if (err) {
17         if (token->type == TOKEN_NEWLINE)
18             err = FALSE;
19         /* just fall through and free the token */
20     } else if (top == NULL) {
21         if (token->type == TOKEN_IDENTIFIER &&
22             !g_ascii_strcasecmp("mbind", token->data.identifier)) {
23             top = token->data.identifier;
24             return;
25         } else {
26             yyerror("syntax error (expected mbind)");
27             err = TRUE;
28         }
29     } else if (context == NULL) {
30         if (token->type == TOKEN_IDENTIFIER) {
31             context = token->data.identifier;
32             return;
33         } else {
34             yyerror("syntax error (expected Key)");
35             err = TRUE;
36         }
37     } else if (event == (unsigned) -1) {
38         if (token->type == TOKEN_IDENTIFIER) {
39             if (!g_ascii_strcasecmp("press", token->data.identifier))
40                 event = MouseAction_Press;
41             else if (!g_ascii_strcasecmp("release", token->data.identifier))
42                 event = MouseAction_Release;
43             else if (!g_ascii_strcasecmp("click", token->data.identifier))
44                 event = MouseAction_Click;
45             else if (!g_ascii_strcasecmp("doubleclick",token->data.identifier))
46                 event = MouseAction_DClick;
47             else if (!g_ascii_strcasecmp("drag", token->data.identifier))
48                 event = MouseAction_Motion;
49             if (event != (unsigned) -1)
50                 return;
51             else {
52                 yyerror("invalid event");
53                 err = TRUE;
54             }
55         } else {
56             yyerror("syntax error (expected event)");
57             err = TRUE;
58         }
59     } else if (button == NULL) {
60         if (token->type == TOKEN_IDENTIFIER) {
61             button = token->data.identifier;
62             return;
63         } else {
64             yyerror("syntax error (expected button)");
65             err = TRUE;
66         }
67     } else if (action == NULL) {
68         if (token->type == TOKEN_IDENTIFIER) {
69             action = action_from_string(token->data.identifier);
70
71             /* check for valid actions for motion events */
72             if (action->func == action_moveresize)
73                 g_message("%d", action->data.moveresize.corner);
74             if (event == MouseAction_Motion) {
75                 if (action && (action->func != action_moveresize ||
76                                action->data.moveresize.corner ==
77                                prop_atoms.net_wm_moveresize_move_keyboard ||
78                                action->data.moveresize.corner ==
79                                prop_atoms.net_wm_moveresize_size_keyboard)) {
80                     action_free(action);
81                     action = NULL;
82                 }
83             } else {
84                 if (action && action->func == action_moveresize &&
85                     action->data.moveresize.corner !=
86                     prop_atoms.net_wm_moveresize_move_keyboard &&
87                     action->data.moveresize.corner !=
88                     prop_atoms.net_wm_moveresize_size_keyboard) {
89                     action_free(action);
90                     action = NULL;
91                 }
92             }
93
94             if (action != NULL) {
95                 return;
96             } else {
97                 yyerror("invalid action");
98                 err = TRUE;
99             }
100         } else {
101             yyerror("syntax error (expected action)");
102             err = TRUE;
103         }
104     } else if (token->type == TOKEN_STRING) {
105         arg_str = token->data.string;
106         return;
107     } else if (token->type == TOKEN_INTEGER) {
108         arg_int = token->data.integer;
109         return;
110     } else if (token->type != TOKEN_NEWLINE) {
111         yyerror("syntax error (unexpected trailing token)");
112     } else {
113
114         /* these use the argument */
115         if (action->func == action_execute || action->func == action_restart)
116             action->data.execute.path = g_strdup(arg_str);
117         else if (action->func == action_showmenu)
118             action->data.showmenu.name = g_strdup(arg_str);
119         if ((action->func == action_desktop ||
120              action->func == action_send_to_desktop) &&
121             arg_int)
122             action->data.desktop.desk = (unsigned) arg_int - 1;
123         if (action->func == action_move_relative_horz ||
124             action->func == action_move_relative_vert ||
125             action->func == action_resize_relative_horz ||
126             action->func == action_resize_relative_vert)
127             action->data.relative.delta = arg_int;
128
129         if (mbind(button, context, event, action))
130             action = NULL; /* don't free this if mbind succeeds */
131         else
132             yyerror("failed to add mouse binding");
133     }
134
135     g_free(top); top = NULL;
136     g_free(context); context = NULL;
137     g_free(button); button = NULL;
138     g_free(arg_str); arg_str = NULL;
139     arg_int = 0;
140     event = -1;
141     action_free(action); action = NULL;
142     parse_free_token(token);
143 }