diff options
author | akokshar@redhat.com <akokshar@redhat.com> | 2017-08-29 11:19:43 +0200 |
---|---|---|
committer | akokshar@redhat.com <akokshar@redhat.com> | 2017-08-29 11:19:43 +0200 |
commit | 65022e1cbf0ccf8764dcef7e2a738feb3331deeb (patch) | |
tree | 2b08e4aa1a186ffe3cd990887ad18322756bbfc6 /swaybar/status_line.c | |
parent | Merge pull request #1247 from clarcharr/master (diff) | |
download | sway-65022e1cbf0ccf8764dcef7e2a738feb3331deeb.tar.gz sway-65022e1cbf0ccf8764dcef7e2a738feb3331deeb.tar.zst sway-65022e1cbf0ccf8764dcef7e2a738feb3331deeb.zip |
click_events as documented at https://i3wm.org/docs/i3bar-protocol.html
Diffstat (limited to 'swaybar/status_line.c')
-rw-r--r-- | swaybar/status_line.c | 82 |
1 files changed, 80 insertions, 2 deletions
diff --git a/swaybar/status_line.c b/swaybar/status_line.c index 83e8ce2c..f0888273 100644 --- a/swaybar/status_line.c +++ b/swaybar/status_line.c | |||
@@ -27,6 +27,8 @@ struct { | |||
27 | static char line[1024]; | 27 | static char line[1024]; |
28 | static char line_rest[1024]; | 28 | static char line_rest[1024]; |
29 | 29 | ||
30 | static char event_buff[1024]; | ||
31 | |||
30 | static void free_status_block(void *item) { | 32 | static void free_status_block(void *item) { |
31 | if (!item) { | 33 | if (!item) { |
32 | return; | 34 | return; |
@@ -391,6 +393,67 @@ static int i3json_handle_fd(struct bar *bar) { | |||
391 | return i3json_parse(bar); | 393 | return i3json_parse(bar); |
392 | } | 394 | } |
393 | 395 | ||
396 | bool status_line_mouse_event(struct bar *bar, int x, int y, uint32_t button) { | ||
397 | sway_log(L_DEBUG, "status_line_mouse_event."); | ||
398 | if (!bar->status->click_events) { | ||
399 | sway_log(L_DEBUG, "click_events are not enabled."); | ||
400 | return false; | ||
401 | } | ||
402 | |||
403 | if (bar->status->protocol == I3BAR) { | ||
404 | sway_log(L_DEBUG, "Sending click event."); | ||
405 | |||
406 | // find clicked block | ||
407 | struct status_block *clicked_block = NULL; | ||
408 | struct status_block *current_block = NULL; | ||
409 | int num_blocks = bar->status->block_line->length; | ||
410 | |||
411 | if (num_blocks == 0) { | ||
412 | return false; | ||
413 | } | ||
414 | else { | ||
415 | current_block = bar->status->block_line->items[0]; | ||
416 | if (x < current_block->x) { | ||
417 | return false; | ||
418 | } | ||
419 | } | ||
420 | |||
421 | for (int i = 0; i < num_blocks; i++) { | ||
422 | current_block = bar->status->block_line->items[i]; | ||
423 | if (x < (current_block->x + current_block->width)) { | ||
424 | clicked_block = current_block; | ||
425 | break; | ||
426 | } | ||
427 | } | ||
428 | |||
429 | if (!clicked_block || !clicked_block->name) { | ||
430 | return false; | ||
431 | } | ||
432 | |||
433 | // event example {"name":"capture","instance":"label","button":1,"x":3431,"y":18} | ||
434 | |||
435 | struct json_object *event_json = json_object_new_object(); | ||
436 | json_object_object_add(event_json, "name", json_object_new_string(clicked_block->name)); | ||
437 | if (clicked_block->instance) { | ||
438 | json_object_object_add(event_json, "instance", json_object_new_string(clicked_block->instance)); | ||
439 | } | ||
440 | json_object_object_add(event_json, "button", json_object_new_int(button)); | ||
441 | json_object_object_add(event_json, "x", json_object_new_int(x)); | ||
442 | json_object_object_add(event_json, "y", json_object_new_int(y)); | ||
443 | |||
444 | int len = snprintf(event_buff, sizeof(event_buff), "%s,\n", json_object_to_json_string(event_json)); | ||
445 | |||
446 | json_object_put(event_json); | ||
447 | |||
448 | if (len <= (int)sizeof(event_buff)) { // if not truncated | ||
449 | write(bar->status_write_fd, event_buff, len); | ||
450 | return true; | ||
451 | } | ||
452 | } | ||
453 | |||
454 | return false; | ||
455 | } | ||
456 | |||
394 | bool handle_status_line(struct bar *bar) { | 457 | bool handle_status_line(struct bar *bar) { |
395 | bool dirty = false; | 458 | bool dirty = false; |
396 | 459 | ||
@@ -418,15 +481,29 @@ bool handle_status_line(struct bar *bar) { | |||
418 | if (line[0] == '{') { | 481 | if (line[0] == '{') { |
419 | // detect i3bar json protocol | 482 | // detect i3bar json protocol |
420 | json_object *proto = json_tokener_parse(line); | 483 | json_object *proto = json_tokener_parse(line); |
421 | json_object *version; | ||
422 | if (proto) { | 484 | if (proto) { |
485 | |||
486 | json_object *version; | ||
423 | if (json_object_object_get_ex(proto, "version", &version) | 487 | if (json_object_object_get_ex(proto, "version", &version) |
424 | && json_object_get_int(version) == 1 | 488 | && json_object_get_int(version) == 1 |
425 | ) { | 489 | ) { |
426 | sway_log(L_DEBUG, "Switched to i3bar protocol."); | 490 | sway_log(L_DEBUG, "Switched to i3bar protocol."); |
427 | bar->status->protocol = I3BAR; | 491 | bar->status->protocol = I3BAR; |
428 | i3json_handle_data(bar, line_rest); | ||
429 | } | 492 | } |
493 | |||
494 | json_object *click_events; | ||
495 | if (json_object_object_get_ex(proto, "click_events", &click_events) | ||
496 | && json_object_get_boolean(click_events) | ||
497 | ) { | ||
498 | sway_log(L_DEBUG, "Enabling click events."); | ||
499 | bar->status->click_events = true; | ||
500 | |||
501 | const char *events_array = "[\n"; | ||
502 | write(bar->status_write_fd, events_array, strlen(events_array)); | ||
503 | } | ||
504 | |||
505 | i3json_handle_data(bar, line_rest); | ||
506 | |||
430 | json_object_put(proto); | 507 | json_object_put(proto); |
431 | } | 508 | } |
432 | } | 509 | } |
@@ -441,6 +518,7 @@ struct status_line *init_status_line() { | |||
441 | line->block_line = create_list(); | 518 | line->block_line = create_list(); |
442 | line->text_line = NULL; | 519 | line->text_line = NULL; |
443 | line->protocol = UNDEF; | 520 | line->protocol = UNDEF; |
521 | line->click_events = false; | ||
444 | 522 | ||
445 | return line; | 523 | return line; |
446 | } | 524 | } |