]> Dogcows Code - chaz/openbox/blob - openbox/action.c
remove plugins from the menu parsing
[chaz/openbox] / openbox / action.c
1 #include "debug.h"
2 #include "client.h"
3 #include "focus.h"
4 #include "moveresize.h"
5 #include "menu.h"
6 #include "prop.h"
7 #include "stacking.h"
8 #include "frame.h"
9 #include "screen.h"
10 #include "action.h"
11 #include "openbox.h"
12
13 #include <glib.h>
14
15 typedef struct ActionString {
16 char *name;
17 void (*func)(union ActionData *);
18 void (*setup)(ObAction *);
19 } ActionString;
20
21 ObAction *action_new(void (*func)(union ActionData *data))
22 {
23 ObAction *a = g_new0(ObAction, 1);
24 a->func = func;
25
26 return a;
27 }
28
29 void action_free(ObAction *a)
30 {
31 if (a == NULL) return;
32
33 /* deal with pointers */
34 if (a->func == action_execute || a->func == action_restart)
35 g_free(a->data.execute.path);
36 else if (a->func == action_showmenu)
37 g_free(a->data.showmenu.name);
38
39 g_free(a);
40 }
41
42 void setup_action_directional_focus_north(ObAction *a)
43 {
44 a->data.diraction.direction = OB_DIRECTION_NORTH;
45 }
46
47 void setup_action_directional_focus_east(ObAction *a)
48 {
49 a->data.diraction.direction = OB_DIRECTION_EAST;
50 }
51
52 void setup_action_directional_focus_south(ObAction *a)
53 {
54 a->data.diraction.direction = OB_DIRECTION_SOUTH;
55 }
56
57 void setup_action_directional_focus_west(ObAction *a)
58 {
59 a->data.diraction.direction = OB_DIRECTION_WEST;
60 }
61
62 void setup_action_directional_focus_northeast(ObAction *a)
63 {
64 a->data.diraction.direction = OB_DIRECTION_NORTHEAST;
65 }
66
67 void setup_action_directional_focus_southeast(ObAction *a)
68 {
69 a->data.diraction.direction = OB_DIRECTION_SOUTHEAST;
70 }
71
72 void setup_action_directional_focus_southwest(ObAction *a)
73 {
74 a->data.diraction.direction = OB_DIRECTION_SOUTHWEST;
75 }
76
77 void setup_action_directional_focus_northwest(ObAction *a)
78 {
79 a->data.diraction.direction = OB_DIRECTION_NORTHWEST;
80 }
81
82 void setup_action_send_to_desktop(ObAction *a)
83 {
84 a->data.sendto.follow = TRUE;
85 }
86
87 void setup_action_send_to_desktop_prev(ObAction *a)
88 {
89 a->data.sendtodir.dir = OB_DIRECTION_WEST;
90 a->data.sendtodir.linear = TRUE;
91 a->data.sendtodir.wrap = TRUE;
92 a->data.sendtodir.follow = TRUE;
93 }
94
95 void setup_action_send_to_desktop_next(ObAction *a)
96 {
97 a->data.sendtodir.dir = OB_DIRECTION_EAST;
98 a->data.sendtodir.linear = TRUE;
99 a->data.sendtodir.wrap = TRUE;
100 a->data.sendtodir.follow = TRUE;
101 }
102
103 void setup_action_send_to_desktop_left(ObAction *a)
104 {
105 a->data.sendtodir.dir = OB_DIRECTION_WEST;
106 a->data.sendtodir.linear = FALSE;
107 a->data.sendtodir.wrap = TRUE;
108 a->data.sendtodir.follow = TRUE;
109 }
110
111 void setup_action_send_to_desktop_right(ObAction *a)
112 {
113 a->data.sendtodir.dir = OB_DIRECTION_EAST;
114 a->data.sendtodir.linear = FALSE;
115 a->data.sendtodir.wrap = TRUE;
116 a->data.sendtodir.follow = TRUE;
117 }
118
119 void setup_action_send_to_desktop_up(ObAction *a)
120 {
121 a->data.sendtodir.dir = OB_DIRECTION_NORTH;
122 a->data.sendtodir.linear = FALSE;
123 a->data.sendtodir.wrap = TRUE;
124 a->data.sendtodir.follow = TRUE;
125 }
126
127 void setup_action_send_to_desktop_down(ObAction *a)
128 {
129 a->data.sendtodir.dir = OB_DIRECTION_SOUTH;
130 a->data.sendtodir.linear = FALSE;
131 a->data.sendtodir.wrap = TRUE;
132 a->data.sendtodir.follow = TRUE;
133 }
134
135 void setup_action_desktop_prev(ObAction *a)
136 {
137 a->data.desktopdir.dir = OB_DIRECTION_WEST;
138 a->data.desktopdir.linear = TRUE;
139 a->data.desktopdir.wrap = TRUE;
140 }
141
142 void setup_action_desktop_next(ObAction *a)
143 {
144 a->data.desktopdir.dir = OB_DIRECTION_EAST;
145 a->data.desktopdir.linear = TRUE;
146 a->data.desktopdir.wrap = TRUE;
147 }
148
149 void setup_action_desktop_left(ObAction *a)
150 {
151 a->data.desktopdir.dir = OB_DIRECTION_WEST;
152 a->data.desktopdir.linear = FALSE;
153 a->data.desktopdir.wrap = TRUE;
154 }
155
156 void setup_action_desktop_right(ObAction *a)
157 {
158 a->data.desktopdir.dir = OB_DIRECTION_EAST;
159 a->data.desktopdir.linear = FALSE;
160 a->data.desktopdir.wrap = TRUE;
161 }
162
163 void setup_action_desktop_up(ObAction *a)
164 {
165 a->data.desktopdir.dir = OB_DIRECTION_NORTH;
166 a->data.desktopdir.linear = FALSE;
167 a->data.desktopdir.wrap = TRUE;
168 }
169
170 void setup_action_desktop_down(ObAction *a)
171 {
172 a->data.desktopdir.dir = OB_DIRECTION_SOUTH;
173 a->data.desktopdir.linear = FALSE;
174 a->data.desktopdir.wrap = TRUE;
175 }
176
177 void setup_action_move_keyboard(ObAction *a)
178 {
179 a->data.moveresize.corner = prop_atoms.net_wm_moveresize_move_keyboard;
180 }
181
182 void setup_action_move(ObAction *a)
183 {
184 a->data.moveresize.corner = prop_atoms.net_wm_moveresize_move;
185 }
186
187 void setup_action_resize(ObAction *a)
188 {
189 a->data.moveresize.corner = prop_atoms.net_wm_moveresize_size_topleft;
190 }
191
192 void setup_action_resize_keyboard(ObAction *a)
193 {
194 a->data.moveresize.corner = prop_atoms.net_wm_moveresize_size_keyboard;
195 }
196
197 void setup_action_cycle_windows_linear_next(ObAction *a)
198 {
199 a->data.cycle.linear = TRUE;
200 a->data.cycle.forward = TRUE;
201 }
202
203 void setup_action_cycle_windows_linear_previous(ObAction *a)
204 {
205 a->data.cycle.linear = TRUE;
206 a->data.cycle.forward = FALSE;
207 }
208
209 void setup_action_cycle_windows_next(ObAction *a)
210 {
211 a->data.cycle.linear = FALSE;
212 a->data.cycle.forward = TRUE;
213 }
214
215 void setup_action_cycle_windows_previous(ObAction *a)
216 {
217 a->data.cycle.linear = FALSE;
218 a->data.cycle.forward = FALSE;
219 }
220
221 void setup_action_movetoedge_north(ObAction *a)
222 {
223 a->data.diraction.direction = OB_DIRECTION_NORTH;
224 }
225
226 void setup_action_movetoedge_south(ObAction *a)
227 {
228 a->data.diraction.direction = OB_DIRECTION_SOUTH;
229 }
230
231 void setup_action_movetoedge_east(ObAction *a)
232 {
233 a->data.diraction.direction = OB_DIRECTION_EAST;
234 }
235
236 void setup_action_movetoedge_west(ObAction *a)
237 {
238 a->data.diraction.direction = OB_DIRECTION_WEST;
239 }
240
241 void setup_action_growtoedge_north(ObAction *a)
242 {
243 a->data.diraction.direction = OB_DIRECTION_NORTH;
244 }
245
246 void setup_action_growtoedge_south(ObAction *a)
247 {
248 a->data.diraction.direction = OB_DIRECTION_SOUTH;
249 }
250
251 void setup_action_growtoedge_east(ObAction *a)
252 {
253 a->data.diraction.direction = OB_DIRECTION_EAST;
254 }
255
256 void setup_action_growtoedge_west(ObAction *a)
257 {
258 a->data.diraction.direction = OB_DIRECTION_WEST;
259 }
260
261 void setup_action_top_layer(ObAction *a)
262 {
263 a->data.layer.layer = 1;
264 }
265
266 void setup_action_normal_layer(ObAction *a)
267 {
268 a->data.layer.layer = 0;
269 }
270
271 void setup_action_bottom_layer(ObAction *a)
272 {
273 a->data.layer.layer = -1;
274 }
275
276 ActionString actionstrings[] =
277 {
278 {
279 "execute",
280 action_execute,
281 NULL
282 },
283 {
284 "directionalfocusnorth",
285 action_directional_focus,
286 setup_action_directional_focus_north
287 },
288 {
289 "directionalfocuseast",
290 action_directional_focus,
291 setup_action_directional_focus_east
292 },
293 {
294 "directionalfocussouth",
295 action_directional_focus,
296 setup_action_directional_focus_south
297 },
298 {
299 "directionalfocuswest",
300 action_directional_focus,
301 setup_action_directional_focus_west
302 },
303 {
304 "directionalfocusnortheast",
305 action_directional_focus,
306 setup_action_directional_focus_northeast
307 },
308 {
309 "directionalfocussoutheast",
310 action_directional_focus,
311 setup_action_directional_focus_southeast
312 },
313 {
314 "directionalfocussouthwest",
315 action_directional_focus,
316 setup_action_directional_focus_southwest
317 },
318 {
319 "directionalfocusnorthwest",
320 action_directional_focus,
321 setup_action_directional_focus_northwest
322 },
323 {
324 "activate",
325 action_activate,
326 NULL,
327 },
328 {
329 "focus",
330 action_focus,
331 NULL,
332 },
333 {
334 "unfocus",
335 action_unfocus,
336 NULL
337 },
338 {
339 "iconify",
340 action_iconify,
341 NULL
342 },
343 {
344 "raiselower",
345 action_raiselower,
346 NULL
347 },
348 {
349 "raise",
350 action_raise,
351 NULL
352 },
353 {
354 "lower",
355 action_lower,
356 NULL
357 },
358 {
359 "close",
360 action_close,
361 NULL
362 },
363 {
364 "kill",
365 action_kill,
366 NULL
367 },
368 {
369 "shadelower",
370 action_shadelower,
371 NULL
372 },
373 {
374 "unshaderaise",
375 action_unshaderaise,
376 NULL
377 },
378 {
379 "shade",
380 action_shade,
381 NULL
382 },
383 {
384 "unshade",
385 action_unshade,
386 NULL
387 },
388 {
389 "toggleshade",
390 action_toggle_shade,
391 NULL
392 },
393 {
394 "toggleomnipresent",
395 action_toggle_omnipresent,
396 NULL
397 },
398 {
399 "moverelativehorz",
400 action_move_relative_horz,
401 NULL
402 },
403 {
404 "moverelativevert",
405 action_move_relative_vert,
406 NULL
407 },
408 {
409 "resizerelativehorz",
410 action_resize_relative_horz,
411 NULL
412 },
413 {
414 "resizerelativevert",
415 action_resize_relative_vert,
416 NULL
417 },
418 {
419 "maximizefull",
420 action_maximize_full,
421 NULL
422 },
423 {
424 "unmaximizefull",
425 action_unmaximize_full,
426 NULL
427 },
428 {
429 "togglemaximizefull",
430 action_toggle_maximize_full,
431 NULL
432 },
433 {
434 "maximizehorz",
435 action_maximize_horz,
436 NULL
437 },
438 {
439 "unmaximizehorz",
440 action_unmaximize_horz,
441 NULL
442 },
443 {
444 "togglemaximizehorz",
445 action_toggle_maximize_horz,
446 NULL
447 },
448 {
449 "maximizevert",
450 action_maximize_vert,
451 NULL
452 },
453 {
454 "unmaximizevert",
455 action_unmaximize_vert,
456 NULL
457 },
458 {
459 "togglemaximizevert",
460 action_toggle_maximize_vert,
461 NULL
462 },
463 {
464 "sendtodesktop",
465 action_send_to_desktop,
466 setup_action_send_to_desktop
467 },
468 {
469 "sendtodesktopnext",
470 action_send_to_desktop_dir,
471 setup_action_send_to_desktop_next
472 },
473 {
474 "sendtodesktopprevious",
475 action_send_to_desktop_dir,
476 setup_action_send_to_desktop_prev
477 },
478 {
479 "sendtodesktopright",
480 action_send_to_desktop_dir,
481 setup_action_send_to_desktop_right
482 },
483 {
484 "sendtodesktopleft",
485 action_send_to_desktop_dir,
486 setup_action_send_to_desktop_left
487 },
488 {
489 "sendtodesktopup",
490 action_send_to_desktop_dir,
491 setup_action_send_to_desktop_up
492 },
493 {
494 "sendtodesktopdown",
495 action_send_to_desktop_dir,
496 setup_action_send_to_desktop_down
497 },
498 {
499 "desktop",
500 action_desktop,
501 NULL
502 },
503 {
504 "desktopnext",
505 action_desktop_dir,
506 setup_action_desktop_next
507 },
508 {
509 "desktopprevious",
510 action_desktop_dir,
511 setup_action_desktop_prev
512 },
513 {
514 "desktopright",
515 action_desktop_dir,
516 setup_action_desktop_right
517 },
518 {
519 "desktopleft",
520 action_desktop_dir,
521 setup_action_desktop_left
522 },
523 {
524 "desktopup",
525 action_desktop_dir,
526 setup_action_desktop_up
527 },
528 {
529 "desktopdown",
530 action_desktop_dir,
531 setup_action_desktop_down
532 },
533 {
534 "toggledecorations",
535 action_toggle_decorations,
536 NULL
537 },
538 {
539 "keyboardmove",
540 action_moveresize,
541 setup_action_move_keyboard
542 },
543 {
544 "move",
545 action_moveresize,
546 setup_action_move
547 },
548 {
549 "resize",
550 action_moveresize,
551 setup_action_resize
552 },
553 {
554 "keyboardresize",
555 action_moveresize,
556 setup_action_resize_keyboard
557 },
558 {
559 "toggleshowdesktop",
560 action_toggle_show_desktop,
561 NULL
562 },
563 {
564 "showdesktop",
565 action_show_desktop,
566 NULL
567 },
568 {
569 "unshowdesktop",
570 action_unshow_desktop,
571 NULL
572 },
573 {
574 "restart",
575 action_restart,
576 NULL
577 },
578 {
579 "exit",
580 action_exit,
581 NULL
582 },
583 {
584 "showmenu",
585 action_showmenu,
586 NULL
587 },
588 {
589 "sendtotoplayer",
590 action_send_to_layer,
591 setup_action_top_layer
592 },
593 {
594 "togglealwaysontop",
595 action_toggle_layer,
596 setup_action_top_layer
597 },
598 {
599 "sendtonormallayer",
600 action_send_to_layer,
601 setup_action_normal_layer
602 },
603 {
604 "sendtobottomlayer",
605 action_send_to_layer,
606 setup_action_bottom_layer
607 },
608 {
609 "togglealwaysonbottom",
610 action_toggle_layer,
611 setup_action_bottom_layer
612 },
613 {
614 "nextwindowlinear",
615 action_cycle_windows,
616 setup_action_cycle_windows_linear_next
617 },
618 {
619 "previouswindowlinear",
620 action_cycle_windows,
621 setup_action_cycle_windows_linear_previous
622 },
623 {
624 "nextwindow",
625 action_cycle_windows,
626 setup_action_cycle_windows_next
627 },
628 {
629 "previouswindow",
630 action_cycle_windows,
631 setup_action_cycle_windows_previous
632 },
633 {
634 "movetoedgenorth",
635 action_movetoedge,
636 setup_action_movetoedge_north
637 },
638 {
639 "movetoedgesouth",
640 action_movetoedge,
641 setup_action_movetoedge_south
642 },
643 {
644 "movetoedgewest",
645 action_movetoedge,
646 setup_action_movetoedge_west
647 },
648 {
649 "movetoedgeeast",
650 action_movetoedge,
651 setup_action_movetoedge_east
652 },
653 {
654 "growtoedgenorth",
655 action_growtoedge,
656 setup_action_growtoedge_north
657 },
658 {
659 "growtoedgesouth",
660 action_growtoedge,
661 setup_action_growtoedge_south
662 },
663 {
664 "growtoedgewest",
665 action_growtoedge,
666 setup_action_growtoedge_west
667 },
668 {
669 "growtoedgeeast",
670 action_growtoedge,
671 setup_action_growtoedge_east
672 },
673 {
674 NULL,
675 NULL,
676 NULL
677 }
678 };
679
680 ObAction *action_from_string(char *name)
681 {
682 ObAction *a = NULL;
683 int i;
684
685 for (i = 0; actionstrings[i].name; i++)
686 if (!g_ascii_strcasecmp(name, actionstrings[i].name)) {
687 a = action_new(actionstrings[i].func);
688 if (actionstrings[i].setup)
689 actionstrings[i].setup(a);
690 break;
691 }
692 return a;
693 }
694
695 ObAction *action_parse(ObParseInst *i, xmlDocPtr doc, xmlNodePtr node)
696 {
697 char *actname;
698 ObAction *act = NULL;
699 xmlNodePtr n;
700
701 if (parse_attr_string("name", node, &actname)) {
702 if ((act = action_from_string(actname))) {
703 if (act->func == action_execute || act->func == action_restart) {
704 if ((n = parse_find_node("execute", node->xmlChildrenNode)))
705 act->data.execute.path = parse_string(doc, n);
706 } else if (act->func == action_showmenu) {
707 if ((n = parse_find_node("menu", node->xmlChildrenNode)))
708 act->data.showmenu.name = parse_string(doc, n);
709 } else if (act->func == action_desktop) {
710 if ((n = parse_find_node("desktop", node->xmlChildrenNode)))
711 act->data.desktop.desk = parse_int(doc, n);
712 if (act->data.desktop.desk > 0) act->data.desktop.desk--;
713 } else if (act->func == action_send_to_desktop) {
714 if ((n = parse_find_node("desktop", node->xmlChildrenNode)))
715 act->data.sendto.desk = parse_int(doc, n);
716 if (act->data.sendto.desk > 0) act->data.sendto.desk--;
717 } else if (act->func == action_move_relative_horz ||
718 act->func == action_move_relative_vert ||
719 act->func == action_resize_relative_horz ||
720 act->func == action_resize_relative_vert) {
721 if ((n = parse_find_node("delta", node->xmlChildrenNode)))
722 act->data.relative.delta = parse_int(doc, n);
723 } else if (act->func == action_desktop_dir) {
724 if ((n = parse_find_node("wrap", node->xmlChildrenNode))) {
725 act->data.desktopdir.wrap = parse_bool(doc, n);
726 }
727 } else if (act->func == action_send_to_desktop) {
728 if ((n = parse_find_node("follow", node->xmlChildrenNode)))
729 act->data.sendto.follow = parse_bool(doc, n);
730 } else if (act->func == action_send_to_desktop_dir) {
731 if ((n = parse_find_node("wrap", node->xmlChildrenNode)))
732 act->data.sendtodir.wrap = parse_bool(doc, n);
733 if ((n = parse_find_node("follow", node->xmlChildrenNode)))
734 act->data.sendtodir.follow = parse_bool(doc, n);
735 } else if (act->func == action_activate) {
736 if ((n = parse_find_node("here", node->xmlChildrenNode)))
737 act->data.activate.here = parse_bool(doc, n);
738 }
739 }
740 g_free(actname);
741 }
742 return act;
743 }
744
745 void action_execute(union ActionData *data)
746 {
747 GError *e = NULL;
748 char *cmd;
749 if (data->execute.path) {
750 cmd = g_filename_from_utf8(data->execute.path, -1, NULL, NULL, NULL);
751 if (cmd) {
752 if (!g_spawn_command_line_async(cmd, &e)) {
753 g_warning("failed to execute '%s': %s",
754 cmd, e->message);
755 }
756 } else {
757 g_warning("failed to convert '%s' from utf8", data->execute.path);
758 }
759 }
760 }
761
762 void action_activate(union ActionData *data)
763 {
764 if (data->activate.c)
765 client_activate(data->activate.c, data->activate.here);
766 }
767
768 void action_focus(union ActionData *data)
769 {
770 if (data->client.c)
771 client_focus(data->client.c);
772 }
773
774 void action_unfocus (union ActionData *data)
775 {
776 if (data->client.c)
777 client_unfocus(data->client.c);
778 }
779
780 void action_iconify(union ActionData *data)
781 {
782 if (data->client.c)
783 client_iconify(data->client.c, TRUE, TRUE);
784 }
785
786 void action_raiselower(union ActionData *data)
787 {
788 ObClient *c = data->client.c;
789 GList *it;
790 gboolean raise = FALSE;
791
792 if (!c) return;
793
794 for (it = stacking_list; it; it = g_list_next(it)) {
795 ObClient *cit = it->data;
796
797 if (cit == c) break;
798 if (client_normal(cit) == client_normal(c) &&
799 cit->layer == c->layer &&
800 cit->frame->visible)
801 {
802 if (RECT_INTERSECTS_RECT(cit->frame->area, c->frame->area)) {
803 raise = TRUE;
804 break;
805 }
806 }
807 }
808
809 if (raise)
810 stacking_raise(CLIENT_AS_WINDOW(c));
811 else
812 stacking_lower(CLIENT_AS_WINDOW(c));
813 }
814
815 void action_raise(union ActionData *data)
816 {
817 if (data->client.c)
818 stacking_raise(CLIENT_AS_WINDOW(data->client.c));
819 }
820
821 void action_unshaderaise(union ActionData *data)
822 {
823 if (data->client.c) {
824 if (data->client.c->shaded)
825 client_shade(data->client.c, FALSE);
826 else
827 stacking_raise(CLIENT_AS_WINDOW(data->client.c));
828 }
829 }
830
831 void action_shadelower(union ActionData *data)
832 {
833 if (data->client.c) {
834 if (data->client.c->shaded)
835 stacking_lower(CLIENT_AS_WINDOW(data->client.c));
836 else
837 client_shade(data->client.c, TRUE);
838 }
839 }
840
841 void action_lower(union ActionData *data)
842 {
843 if (data->client.c)
844 stacking_lower(CLIENT_AS_WINDOW(data->client.c));
845 }
846
847 void action_close(union ActionData *data)
848 {
849 if (data->client.c)
850 client_close(data->client.c);
851 }
852
853 void action_kill(union ActionData *data)
854 {
855 if (data->client.c)
856 client_kill(data->client.c);
857 }
858
859 void action_shade(union ActionData *data)
860 {
861 if (data->client.c)
862 client_shade(data->client.c, TRUE);
863 }
864
865 void action_unshade(union ActionData *data)
866 {
867 if (data->client.c)
868 client_shade(data->client.c, FALSE);
869 }
870
871 void action_toggle_shade(union ActionData *data)
872 {
873 if (data->client.c)
874 client_shade(data->client.c, !data->client.c->shaded);
875 }
876
877 void action_toggle_omnipresent(union ActionData *data)
878 {
879 if (data->client.c)
880 client_set_desktop(data->client.c,
881 data->client.c->desktop == DESKTOP_ALL ?
882 screen_desktop : DESKTOP_ALL, FALSE);
883 }
884
885 void action_move_relative_horz(union ActionData *data)
886 {
887 ObClient *c = data->relative.c;
888 if (c)
889 client_configure(c, OB_CORNER_TOPLEFT,
890 c->area.x + data->relative.delta, c->area.y,
891 c->area.width, c->area.height, TRUE, TRUE);
892 }
893
894 void action_move_relative_vert(union ActionData *data)
895 {
896 ObClient *c = data->relative.c;
897 if (c)
898 client_configure(c, OB_CORNER_TOPLEFT,
899 c->area.x, c->area.y + data->relative.delta,
900 c->area.width, c->area.height, TRUE, TRUE);
901 }
902
903 void action_resize_relative_horz(union ActionData *data)
904 {
905 ObClient *c = data->relative.c;
906 if (c)
907 client_configure(c, OB_CORNER_TOPLEFT, c->area.x, c->area.y,
908 c->area.width +
909 data->relative.delta * c->size_inc.width,
910 c->area.height, TRUE, TRUE);
911 }
912
913 void action_resize_relative_vert(union ActionData *data)
914 {
915 ObClient *c = data->relative.c;
916 if (c && !c->shaded)
917 client_configure(c, OB_CORNER_TOPLEFT, c->area.x, c->area.y,
918 c->area.width, c->area.height +
919 data->relative.delta * c->size_inc.height,
920 TRUE, TRUE);
921 }
922
923 void action_maximize_full(union ActionData *data)
924 {
925 if (data->client.c)
926 client_maximize(data->client.c, TRUE, 0, TRUE);
927 }
928
929 void action_unmaximize_full(union ActionData *data)
930 {
931 if (data->client.c)
932 client_maximize(data->client.c, FALSE, 0, TRUE);
933 }
934
935 void action_toggle_maximize_full(union ActionData *data)
936 {
937 if (data->client.c)
938 client_maximize(data->client.c,
939 !(data->client.c->max_horz ||
940 data->client.c->max_vert),
941 0, TRUE);
942 }
943
944 void action_maximize_horz(union ActionData *data)
945 {
946 if (data->client.c)
947 client_maximize(data->client.c, TRUE, 1, TRUE);
948 }
949
950 void action_unmaximize_horz(union ActionData *data)
951 {
952 if (data->client.c)
953 client_maximize(data->client.c, FALSE, 1, TRUE);
954 }
955
956 void action_toggle_maximize_horz(union ActionData *data)
957 {
958 if (data->client.c)
959 client_maximize(data->client.c, !data->client.c->max_horz, 1, TRUE);
960 }
961
962 void action_maximize_vert(union ActionData *data)
963 {
964 if (data->client.c)
965 client_maximize(data->client.c, TRUE, 2, TRUE);
966 }
967
968 void action_unmaximize_vert(union ActionData *data)
969 {
970 if (data->client.c)
971 client_maximize(data->client.c, FALSE, 2, TRUE);
972 }
973
974 void action_toggle_maximize_vert(union ActionData *data)
975 {
976 if (data->client.c)
977 client_maximize(data->client.c, !data->client.c->max_vert, 2, TRUE);
978 }
979
980 void action_send_to_desktop(union ActionData *data)
981 {
982 ObClient *c = data->sendto.c;
983
984 if (!c || !client_normal(c)) return;
985
986 if (data->sendto.desk < screen_num_desktops ||
987 data->sendto.desk == DESKTOP_ALL) {
988 client_set_desktop(c, data->sendto.desk, data->sendto.follow);
989 if (data->sendto.follow)
990 screen_set_desktop(data->sendto.desk);
991 }
992 }
993
994 void action_desktop(union ActionData *data)
995 {
996 if (data->desktop.desk < screen_num_desktops ||
997 data->desktop.desk == DESKTOP_ALL)
998 screen_set_desktop(data->desktop.desk);
999 }
1000
1001 void action_desktop_dir(union ActionData *data)
1002 {
1003 guint d;
1004
1005 d = screen_cycle_desktop(data->desktopdir.dir, data->desktopdir.wrap,
1006 data->sendtodir.linear,
1007 data->desktopdir.final, data->desktopdir.cancel);
1008 screen_set_desktop(d);
1009 }
1010
1011 void action_send_to_desktop_dir(union ActionData *data)
1012 {
1013 ObClient *c = data->sendtodir.c;
1014 guint d;
1015
1016 if (!c || !client_normal(c)) return;
1017
1018 d = screen_cycle_desktop(data->sendtodir.dir, data->sendtodir.wrap,
1019 data->sendtodir.linear,
1020 data->sendtodir.final, data->sendtodir.cancel);
1021 client_set_desktop(c, d, data->sendtodir.follow);
1022 if (data->sendtodir.follow)
1023 screen_set_desktop(d);
1024 }
1025
1026 #if 0
1027 void action_desktop_right(union ActionData *data)
1028 {
1029 guint r, c, d;
1030
1031 cur_row_col(&r, &c);
1032 ++c;
1033 if (c >= screen_desktop_layout.columns) {
1034 if (!data->desktopdir.wrap) return;
1035 c = 0;
1036 }
1037 d = translate_row_col(r, c);
1038 if (d >= screen_num_desktops) {
1039 if (!data->desktopdir.wrap) return;
1040 ++c;
1041 }
1042 d = translate_row_col(r, c);
1043 if (d < screen_num_desktops)
1044 screen_cycle_desktop(d, data->desktopdir.final,
1045 data->desktopdir.cancel);
1046 }
1047
1048 void action_send_to_desktop_right(union ActionData *data)
1049 {
1050 ObClient *cl = data->sendto.c;
1051 guint r, c, d;
1052
1053 if (!cl || !client_normal(cl)) return;
1054
1055 cur_row_col(&r, &c);
1056 ++c;
1057 if (c >= screen_desktop_layout.columns) {
1058 if (!data->sendtodir.wrap) return;
1059 c = 0;
1060 }
1061 d = translate_row_col(r, c);
1062 if (d >= screen_num_desktops) {
1063 if (!data->sendtodir.wrap) return;
1064 ++c;
1065 }
1066 d = translate_row_col(r, c);
1067 if (d < screen_num_desktops) {
1068 client_set_desktop(cl, d, data->sendtodir.follow);
1069 if (data->sendtodir.follow)
1070 screen_cycle_desktop(d, data->desktopdir.final,
1071 data->desktopdir.cancel);
1072 }
1073 }
1074
1075 void action_desktop_left(union ActionData *data)
1076 {
1077 guint r, c, d;
1078
1079 cur_row_col(&r, &c);
1080 --c;
1081 if (c >= screen_desktop_layout.columns) {
1082 if (!data->desktopdir.wrap) return;
1083 c = screen_desktop_layout.columns - 1;
1084 }
1085 d = translate_row_col(r, c);
1086 if (d >= screen_num_desktops) {
1087 if (!data->desktopdir.wrap) return;
1088 --c;
1089 }
1090 d = translate_row_col(r, c);
1091 if (d < screen_num_desktops)
1092 screen_cycle_desktop(d, data->desktopdir.final,
1093 data->desktopdir.cancel);
1094 }
1095
1096 void action_send_to_desktop_left(union ActionData *data)
1097 {
1098 ObClient *cl = data->sendto.c;
1099 guint r, c, d;
1100
1101 if (!cl || !client_normal(cl)) return;
1102
1103 cur_row_col(&r, &c);
1104 --c;
1105 if (c >= screen_desktop_layout.columns) {
1106 if (!data->sendtodir.wrap) return;
1107 c = screen_desktop_layout.columns - 1;
1108 }
1109 d = translate_row_col(r, c);
1110 if (d >= screen_num_desktops) {
1111 if (!data->sendtodir.wrap) return;
1112 --c;
1113 }
1114 d = translate_row_col(r, c);
1115 if (d < screen_num_desktops) {
1116 client_set_desktop(cl, d, data->sendtodir.follow);
1117 if (data->sendtodir.follow)
1118 screen_cycle_desktop(d, data->desktopdir.final,
1119 data->desktopdir.cancel);
1120 }
1121 }
1122
1123 void action_desktop_down(union ActionData *data)
1124 {
1125 guint r, c, d;
1126
1127 cur_row_col(&r, &c);
1128 ++r;
1129 if (r >= screen_desktop_layout.rows) {
1130 if (!data->desktopdir.wrap) return;
1131 r = 0;
1132 }
1133 d = translate_row_col(r, c);
1134 if (d >= screen_num_desktops) {
1135 if (!data->desktopdir.wrap) return;
1136 ++r;
1137 }
1138 d = translate_row_col(r, c);
1139 if (d < screen_num_desktops)
1140 screen_cycle_desktop(d, data->desktopdir.final,
1141 data->desktopdir.cancel);
1142 }
1143
1144 void action_send_to_desktop_down(union ActionData *data)
1145 {
1146 guint r, c, d;
1147
1148 if (data->sendtodir.c) {
1149 cur_row_col(&r, &c);
1150 ++r;
1151 if (r >= screen_desktop_layout.rows) {
1152 if (!data->sendtodir.wrap) return;
1153 r = 0;
1154 }
1155 d = translate_row_col(r, c);
1156 if (d >= screen_num_desktops) {
1157 if (!data->sendtodir.wrap) return;
1158 ++r;
1159 }
1160 d = translate_row_col(r, c);
1161 if (d < screen_num_desktops) {
1162 client_set_desktop(data->sendtodir.c, d, data->sendtodir.follow);
1163 if (data->sendtodir.follow)
1164 screen_cycle_desktop(d, data->desktopdir.final,
1165 data->desktopdir.cancel);
1166 }
1167 }
1168 }
1169
1170 void action_desktop_up(union ActionData *data)
1171 {
1172 guint r, c, d;
1173
1174 cur_row_col(&r, &c);
1175 --r;
1176 if (r >= screen_desktop_layout.rows) {
1177 if (!data->desktopdir.wrap) return;
1178 r = screen_desktop_layout.rows - 1;
1179 }
1180 d = translate_row_col(r, c);
1181 if (d >= screen_num_desktops) {
1182 if (!data->desktopdir.wrap) return;
1183 --r;
1184 }
1185 d = translate_row_col(r, c);
1186 if (d < screen_num_desktops)
1187 screen_cycle_desktop(d, data->desktopdir.final,
1188 data->desktopdir.cancel);
1189 }
1190
1191 void action_send_to_desktop_up(union ActionData *data)
1192 {
1193 guint r, c, d;
1194
1195 if (data->sendtodir.c) {
1196 cur_row_col(&r, &c);
1197 --r;
1198 if (r >= screen_desktop_layout.rows) {
1199 if (!data->sendtodir.wrap) return;
1200 r = screen_desktop_layout.rows - 1;
1201 }
1202 d = translate_row_col(r, c);
1203 if (d >= screen_num_desktops) {
1204 if (!data->sendtodir.wrap) return;
1205 --r;
1206 }
1207 d = translate_row_col(r, c);
1208 if (d < screen_num_desktops) {
1209 client_set_desktop(data->sendtodir.c, d, data->sendtodir.follow);
1210 if (data->sendtodir.follow)
1211 screen_cycle_desktop(d, data->desktopdir.final,
1212 data->desktopdir.cancel);
1213 }
1214 }
1215 }
1216 #endif
1217
1218 void action_toggle_decorations(union ActionData *data)
1219 {
1220 ObClient *c = data->client.c;
1221
1222 if (!c) return;
1223
1224 c->decorate = !c->decorate;
1225 client_setup_decor_and_functions(c);
1226 }
1227
1228 void action_moveresize(union ActionData *data)
1229 {
1230 ObClient *c = data->moveresize.c;
1231
1232 if (!c || !client_normal(c)) return;
1233
1234 moveresize_start(c, data->moveresize.x, data->moveresize.y,
1235 data->moveresize.button, data->moveresize.corner);
1236 }
1237
1238 void action_restart(union ActionData *data)
1239 {
1240 ob_restart_other(data->execute.path);
1241 }
1242
1243 void action_exit(union ActionData *data)
1244 {
1245 ob_exit();
1246 }
1247
1248 void action_showmenu(union ActionData *data)
1249 {
1250 if (data->showmenu.name) {
1251 menu_show(data->showmenu.name, data->showmenu.x, data->showmenu.y,
1252 data->showmenu.c);
1253 }
1254 }
1255
1256 void action_cycle_windows(union ActionData *data)
1257 {
1258 ObClient *c;
1259
1260 c = focus_cycle(data->cycle.forward, data->cycle.linear, data->cycle.final,
1261 data->cycle.cancel);
1262 }
1263
1264 void action_directional_focus(union ActionData *data)
1265 {
1266 ObClient *nf;
1267
1268 if (!data->diraction.c)
1269 return;
1270 if ((nf = client_find_directional(data->diraction.c,
1271 data->diraction.direction)))
1272 client_activate(nf, FALSE);
1273 }
1274
1275 void action_movetoedge(union ActionData *data)
1276 {
1277 int x, y;
1278 ObClient *c = data->diraction.c;
1279
1280 if (!c)
1281 return;
1282 x = c->frame->area.x;
1283 y = c->frame->area.y;
1284
1285 switch(data->diraction.direction) {
1286 case OB_DIRECTION_NORTH:
1287 y = client_directional_edge_search(c, OB_DIRECTION_NORTH);
1288 break;
1289 case OB_DIRECTION_WEST:
1290 x = client_directional_edge_search(c, OB_DIRECTION_WEST);
1291 break;
1292 case OB_DIRECTION_SOUTH:
1293 y = client_directional_edge_search(c, OB_DIRECTION_SOUTH) -
1294 c->frame->area.height;
1295 break;
1296 case OB_DIRECTION_EAST:
1297 x = client_directional_edge_search(c, OB_DIRECTION_EAST) -
1298 c->frame->area.width;
1299 break;
1300 default:
1301 g_assert_not_reached();
1302 }
1303 frame_frame_gravity(c->frame, &x, &y);
1304 client_configure(c, OB_CORNER_TOPLEFT,
1305 x, y, c->area.width, c->area.height, TRUE, TRUE);
1306
1307 }
1308
1309 void action_growtoedge(union ActionData *data)
1310 {
1311 int x, y, width, height, dest;
1312 ObClient *c = data->diraction.c;
1313 Rect *a = screen_area(c->desktop);
1314
1315 if (!c)
1316 return;
1317
1318 x = c->frame->area.x;
1319 y = c->frame->area.y;
1320 width = c->frame->area.width;
1321 height = c->frame->area.height;
1322
1323 switch(data->diraction.direction) {
1324 case OB_DIRECTION_NORTH:
1325 dest = client_directional_edge_search(c, OB_DIRECTION_NORTH);
1326 if (a->y == y)
1327 height = c->frame->area.height / 2;
1328 else {
1329 height = c->frame->area.y + c->frame->area.height - dest;
1330 y = dest;
1331 }
1332 break;
1333 case OB_DIRECTION_WEST:
1334 dest = client_directional_edge_search(c, OB_DIRECTION_WEST);
1335 if (a->x == x)
1336 width = c->frame->area.width / 2;
1337 else {
1338 width = c->frame->area.x + c->frame->area.width - dest;
1339 x = dest;
1340 }
1341 break;
1342 case OB_DIRECTION_SOUTH:
1343 dest = client_directional_edge_search(c, OB_DIRECTION_SOUTH);
1344 if (a->y + a->height == y + c->frame->area.height) {
1345 height = c->frame->area.height / 2;
1346 y = a->y + a->height - height;
1347 } else
1348 height = dest - c->frame->area.y;
1349 y += (height - c->frame->area.height) % c->size_inc.height;
1350 height -= (height - c->frame->area.height) % c->size_inc.height;
1351 break;
1352 case OB_DIRECTION_EAST:
1353 dest = client_directional_edge_search(c, OB_DIRECTION_EAST);
1354 if (a->x + a->width == x + c->frame->area.width) {
1355 width = c->frame->area.width / 2;
1356 x = a->x + a->width - width;
1357 } else
1358 width = dest - c->frame->area.x;
1359 x += (width - c->frame->area.width) % c->size_inc.width;
1360 width -= (width - c->frame->area.width) % c->size_inc.width;
1361 break;
1362 default:
1363 g_assert_not_reached();
1364 }
1365 frame_frame_gravity(c->frame, &x, &y);
1366 width -= c->frame->size.left + c->frame->size.right;
1367 height -= c->frame->size.top + c->frame->size.bottom;
1368 client_configure(c, OB_CORNER_TOPLEFT, x, y, width, height, TRUE, TRUE);
1369 }
1370
1371 void action_send_to_layer(union ActionData *data)
1372 {
1373 if (data->layer.c)
1374 client_set_layer(data->layer.c, data->layer.layer);
1375 }
1376
1377 void action_toggle_layer(union ActionData *data)
1378 {
1379 ObClient *c = data->layer.c;
1380
1381 if (c) {
1382 if (data->layer.layer < 0)
1383 client_set_layer(c, c->below ? 0 : -1);
1384 else if (data->layer.layer > 0)
1385 client_set_layer(c, c->above ? 0 : 1);
1386 }
1387 }
1388
1389 void action_toggle_show_desktop(union ActionData *data)
1390 {
1391 screen_show_desktop(!screen_showing_desktop);
1392 }
1393
1394 void action_show_desktop(union ActionData *data)
1395 {
1396 screen_show_desktop(TRUE);
1397 }
1398
1399 void action_unshow_desktop(union ActionData *data)
1400 {
1401 screen_show_desktop(FALSE);
1402 }
This page took 0.095866 seconds and 4 git commands to generate.