summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLibravatar Ryan Dwyer <RyanDwyer@users.noreply.github.com>2018-05-13 11:52:51 +1000
committerLibravatar GitHub <noreply@github.com>2018-05-13 11:52:51 +1000
commit0c96d757d0d5d1762390dd119cbe344e8781c19f (patch)
tree34ca494ccdc42799010a00f495b1d19193f20fe7
parentMerge pull request #1967 from emersion/remove-xdg-popup-unmap (diff)
parentMerge branch 'master' into edge-borders (diff)
downloadsway-0c96d757d0d5d1762390dd119cbe344e8781c19f.tar.gz
sway-0c96d757d0d5d1762390dd119cbe344e8781c19f.tar.zst
sway-0c96d757d0d5d1762390dd119cbe344e8781c19f.zip
Merge pull request #1960 from RedSoxFan/edge-borders
Implement hide_edge_borders
-rw-r--r--include/sway/tree/container.h3
-rw-r--r--sway/commands.c1
-rw-r--r--sway/commands/hide_edge_borders.c37
-rw-r--r--sway/desktop/output.c256
-rw-r--r--sway/meson.build1
-rw-r--r--sway/tree/container.c15
-rw-r--r--sway/tree/view.c59
7 files changed, 251 insertions, 121 deletions
diff --git a/include/sway/tree/container.h b/include/sway/tree/container.h
index 61ab7ca1..ec9e2385 100644
--- a/include/sway/tree/container.h
+++ b/include/sway/tree/container.h
@@ -187,6 +187,9 @@ bool container_has_anscestor(struct sway_container *container,
187bool container_has_child(struct sway_container *con, 187bool container_has_child(struct sway_container *con,
188 struct sway_container *child); 188 struct sway_container *child);
189 189
190int container_count_descendants_of_type(struct sway_container *con,
191 enum sway_container_type type);
192
190void container_create_notify(struct sway_container *container); 193void container_create_notify(struct sway_container *container);
191 194
192void container_damage_whole(struct sway_container *container); 195void container_damage_whole(struct sway_container *container);
diff --git a/sway/commands.c b/sway/commands.c
index 2e1cdc2c..37ead367 100644
--- a/sway/commands.c
+++ b/sway/commands.c
@@ -108,6 +108,7 @@ static struct cmd_handler handlers[] = {
108 { "font", cmd_font }, 108 { "font", cmd_font },
109 { "for_window", cmd_for_window }, 109 { "for_window", cmd_for_window },
110 { "fullscreen", cmd_fullscreen }, 110 { "fullscreen", cmd_fullscreen },
111 { "hide_edge_borders", cmd_hide_edge_borders },
111 { "include", cmd_include }, 112 { "include", cmd_include },
112 { "input", cmd_input }, 113 { "input", cmd_input },
113 { "mode", cmd_mode }, 114 { "mode", cmd_mode },
diff --git a/sway/commands/hide_edge_borders.c b/sway/commands/hide_edge_borders.c
new file mode 100644
index 00000000..7d70055b
--- /dev/null
+++ b/sway/commands/hide_edge_borders.c
@@ -0,0 +1,37 @@
1#include "sway/commands.h"
2#include "sway/config.h"
3#include "sway/tree/container.h"
4#include "sway/tree/view.h"
5
6static void _configure_view(struct sway_container *con, void *data) {
7 if (con->type == C_VIEW) {
8 view_autoconfigure(con->sway_view);
9 }
10}
11
12struct cmd_results *cmd_hide_edge_borders(int argc, char **argv) {
13 struct cmd_results *error = NULL;
14 if ((error = checkarg(argc, "hide_edge_borders", EXPECTED_EQUAL_TO, 1))) {
15 return error;
16 }
17
18 if (strcmp(argv[0], "none") == 0) {
19 config->hide_edge_borders = E_NONE;
20 } else if (strcmp(argv[0], "vertical") == 0) {
21 config->hide_edge_borders = E_VERTICAL;
22 } else if (strcmp(argv[0], "horizontal") == 0) {
23 config->hide_edge_borders = E_HORIZONTAL;
24 } else if (strcmp(argv[0], "both") == 0) {
25 config->hide_edge_borders = E_BOTH;
26 } else if (strcmp(argv[0], "smart") == 0) {
27 config->hide_edge_borders = E_SMART;
28 } else {
29 return cmd_results_new(CMD_INVALID, "hide_edge_borders",
30 "Expected 'hide_edge_borders "
31 "<none|vertical|horizontal|both|smart>'");
32 }
33
34 container_for_each_descendant_dfs(&root_container, _configure_view, NULL);
35
36 return cmd_results_new(CMD_SUCCESS, NULL, NULL);
37}
diff --git a/sway/desktop/output.c b/sway/desktop/output.c
index a25139b4..974cd56c 100644
--- a/sway/desktop/output.c
+++ b/sway/desktop/output.c
@@ -14,6 +14,7 @@
14#include <wlr/types/wlr_wl_shell.h> 14#include <wlr/types/wlr_wl_shell.h>
15#include <wlr/util/region.h> 15#include <wlr/util/region.h>
16#include "log.h" 16#include "log.h"
17#include "sway/config.h"
17#include "sway/input/input-manager.h" 18#include "sway/input/input-manager.h"
18#include "sway/input/seat.h" 19#include "sway/input/seat.h"
19#include "sway/layers.h" 20#include "sway/layers.h"
@@ -321,82 +322,99 @@ static void render_container_simple_border_normal(struct sway_output *output,
321 struct wlr_box box; 322 struct wlr_box box;
322 float color[4]; 323 float color[4];
323 324
324 // Child border - left edge 325 int other_views = 1;
325 memcpy(&color, colors->child_border, sizeof(float) * 4); 326 if (config->hide_edge_borders == E_SMART) {
326 color[3] *= con->alpha; 327 struct sway_container *ws = container_parent(con, C_WORKSPACE);
327 box.x = con->x; 328 other_views = container_count_descendants_of_type(ws, C_VIEW) - 1;
328 box.y = con->y + 1;
329 box.width = con->sway_view->border_thickness;
330 box.height = con->height - 1;
331 render_rect(output->wlr_output, output_damage, &box, color);
332
333 // Child border - right edge
334 if (con->parent->children->length == 1 && con->parent->layout == L_HORIZ) {
335 memcpy(&color, colors->indicator, sizeof(float) * 4);
336 } else {
337 memcpy(&color, colors->child_border, sizeof(float) * 4);
338 } 329 }
339 color[3] *= con->alpha;
340 box.x = con->x + con->width - con->sway_view->border_thickness;
341 box.y = con->y + 1;
342 box.width = con->sway_view->border_thickness;
343 box.height = con->height - 1;
344 render_rect(output->wlr_output, output_damage, &box, color);
345 330
346 // Child border - bottom edge 331 if (config->hide_edge_borders != E_VERTICAL
347 if (con->parent->children->length == 1 && con->parent->layout == L_VERT) { 332 && config->hide_edge_borders != E_BOTH
348 memcpy(&color, colors->indicator, sizeof(float) * 4); 333 && (config->hide_edge_borders != E_SMART || other_views)) {
349 } else { 334 // Child border - left edge
350 memcpy(&color, colors->child_border, sizeof(float) * 4); 335 memcpy(&color, colors->child_border, sizeof(float) * 4);
351 } 336 color[3] *= con->alpha;
352 color[3] *= con->alpha; 337 box.x = con->x;
353 box.x = con->x; 338 box.y = con->y + 1;
354 box.y = con->y + con->height - con->sway_view->border_thickness; 339 box.width = con->sway_view->border_thickness;
355 box.width = con->width; 340 box.height = con->height - 1;
356 box.height = con->sway_view->border_thickness; 341 render_rect(output->wlr_output, output_damage, &box, color);
357 render_rect(output->wlr_output, output_damage, &box, color); 342
358 343 // Child border - right edge
359 // Single pixel bar above title 344 if (con->parent->children->length == 1
360 memcpy(&color, colors->border, sizeof(float) * 4); 345 && con->parent->layout == L_HORIZ) {
361 color[3] *= con->alpha; 346 memcpy(&color, colors->indicator, sizeof(float) * 4);
362 box.x = con->x; 347 } else {
363 box.y = con->y; 348 memcpy(&color, colors->child_border, sizeof(float) * 4);
364 box.width = con->width; 349 }
365 box.height = 1; 350 color[3] *= con->alpha;
366 render_rect(output->wlr_output, output_damage, &box, color); 351 box.x = con->x + con->width - con->sway_view->border_thickness;
367 352 box.y = con->y + 1;
368 // Single pixel bar below title 353 box.width = con->sway_view->border_thickness;
369 box.x = con->x + con->sway_view->border_thickness; 354 box.height = con->height - 1;
370 box.y = con->sway_view->y - 1; 355 render_rect(output->wlr_output, output_damage, &box, color);
371 box.width = con->width - con->sway_view->border_thickness * 2; 356 }
372 box.height = 1; 357
373 render_rect(output->wlr_output, output_damage, &box, color); 358 if (config->hide_edge_borders != E_HORIZONTAL
374 359 && config->hide_edge_borders != E_BOTH
375 // Title background 360 && (config->hide_edge_borders != E_SMART || other_views)) {
376 memcpy(&color, colors->background, sizeof(float) * 4); 361 // Child border - bottom edge
377 color[3] *= con->alpha; 362 if (con->parent->children->length == 1
378 box.x = con->x + con->sway_view->border_thickness; 363 && con->parent->layout == L_VERT) {
379 box.y = con->y + 1; 364 memcpy(&color, colors->indicator, sizeof(float) * 4);
380 box.width = con->width - con->sway_view->border_thickness * 2; 365 } else {
381 box.height = con->sway_view->y - con->y - 2; 366 memcpy(&color, colors->child_border, sizeof(float) * 4);
382 render_rect(output->wlr_output, output_damage, &box, color); 367 }
383 368 color[3] *= con->alpha;
384 // Title text 369 box.x = con->x;
385 if (title_texture) { 370 box.y = con->y + con->height - con->sway_view->border_thickness;
386 float output_scale = output->wlr_output->scale; 371 box.width = con->width;
387 struct wlr_box texture_box = { 372 box.height = con->sway_view->border_thickness;
388 .x = box.x * output_scale, 373 render_rect(output->wlr_output, output_damage, &box, color);
389 .y = box.y * output_scale, 374
390 }; 375 // Single pixel bar above title
391 wlr_texture_get_size(title_texture, 376 memcpy(&color, colors->border, sizeof(float) * 4);
392 &texture_box.width, &texture_box.height); 377 color[3] *= con->alpha;
393 378 box.x = con->x;
394 float matrix[9]; 379 box.y = con->y;
395 wlr_matrix_project_box(matrix, &texture_box, WL_OUTPUT_TRANSFORM_NORMAL, 380 box.width = con->width;
396 0.0, output->wlr_output->transform_matrix); 381 box.height = 1;
397 382 render_rect(output->wlr_output, output_damage, &box, color);
398 render_texture(output->wlr_output, output_damage, title_texture, 383
399 &texture_box, matrix, 1.0); 384 // Single pixel bar below title
385 box.x = con->x + con->sway_view->border_thickness;
386 box.y = con->sway_view->y - 1;
387 box.width = con->width - con->sway_view->border_thickness * 2;
388 box.height = 1;
389 render_rect(output->wlr_output, output_damage, &box, color);
390
391 // Title background
392 memcpy(&color, colors->background, sizeof(float) * 4);
393 color[3] *= con->alpha;
394 box.x = con->x + con->sway_view->border_thickness;
395 box.y = con->y + 1;
396 box.width = con->width - con->sway_view->border_thickness * 2;
397 box.height = con->sway_view->y - con->y - 2;
398 render_rect(output->wlr_output, output_damage, &box, color);
399
400 // Title text
401 if (title_texture) {
402 float output_scale = output->wlr_output->scale;
403 struct wlr_box texture_box = {
404 .x = box.x * output_scale,
405 .y = box.y * output_scale,
406 };
407 wlr_texture_get_size(title_texture,
408 &texture_box.width, &texture_box.height);
409
410 float matrix[9];
411 wlr_matrix_project_box(matrix, &texture_box,
412 WL_OUTPUT_TRANSFORM_NORMAL,
413 0.0, output->wlr_output->transform_matrix);
414
415 render_texture(output->wlr_output, output_damage, title_texture,
416 &texture_box, matrix, 1.0);
417 }
400 } 418 }
401} 419}
402 420
@@ -409,47 +427,63 @@ static void render_container_simple_border_pixel(struct sway_output *output,
409 struct wlr_box box; 427 struct wlr_box box;
410 float color[4]; 428 float color[4];
411 429
412 // Child border - left edge 430 int other_views = 1;
413 memcpy(&color, colors->child_border, sizeof(float) * 4); 431 if (config->hide_edge_borders == E_SMART) {
414 color[3] *= con->alpha; 432 struct sway_container *ws = container_parent(con, C_WORKSPACE);
415 box.x = con->x; 433 other_views = container_count_descendants_of_type(ws, C_VIEW) - 1;
416 box.y = con->y;
417 box.width = con->sway_view->border_thickness;
418 box.height = con->height;
419 render_rect(output->wlr_output, output_damage, &box, color);
420
421 // Child border - right edge
422 if (con->parent->children->length == 1 && con->parent->layout == L_HORIZ) {
423 memcpy(&color, colors->indicator, sizeof(float) * 4);
424 } else {
425 memcpy(&color, colors->child_border, sizeof(float) * 4);
426 } 434 }
427 color[3] *= con->alpha; 435
428 box.x = con->x + con->width - con->sway_view->border_thickness; 436 if (config->hide_edge_borders != E_VERTICAL
429 box.y = con->y; 437 && config->hide_edge_borders != E_BOTH
430 box.width = con->sway_view->border_thickness; 438 && (config->hide_edge_borders != E_SMART || other_views)) {
431 box.height = con->height; 439 // Child border - left edge
432 render_rect(output->wlr_output, output_damage, &box, color);
433
434 // Child border - top edge
435 box.x = con->x;
436 box.y = con->y;
437 box.width = con->width;
438 box.height = con->sway_view->border_thickness;
439 render_rect(output->wlr_output, output_damage, &box, color);
440
441 // Child border - bottom edge
442 if (con->parent->children->length == 1 && con->parent->layout == L_VERT) {
443 memcpy(&color, colors->indicator, sizeof(float) * 4);
444 } else {
445 memcpy(&color, colors->child_border, sizeof(float) * 4); 440 memcpy(&color, colors->child_border, sizeof(float) * 4);
441 color[3] *= con->alpha;
442 box.x = con->x;
443 box.y = con->y;
444 box.width = con->sway_view->border_thickness;
445 box.height = con->height;
446 render_rect(output->wlr_output, output_damage, &box, color);
447
448 // Child border - right edge
449 if (con->parent->children->length == 1
450 && con->parent->layout == L_HORIZ) {
451 memcpy(&color, colors->indicator, sizeof(float) * 4);
452 } else {
453 memcpy(&color, colors->child_border, sizeof(float) * 4);
454 }
455 color[3] *= con->alpha;
456 box.x = con->x + con->width - con->sway_view->border_thickness;
457 box.y = con->y;
458 box.width = con->sway_view->border_thickness;
459 box.height = con->height;
460 render_rect(output->wlr_output, output_damage, &box, color);
461 }
462
463 if (config->hide_edge_borders != E_HORIZONTAL
464 && config->hide_edge_borders != E_BOTH
465 && (config->hide_edge_borders != E_SMART || other_views)) {
466 // Child border - top edge
467 box.x = con->x;
468 box.y = con->y;
469 box.width = con->width;
470 box.height = con->sway_view->border_thickness;
471 render_rect(output->wlr_output, output_damage, &box, color);
472
473 // Child border - bottom edge
474 if (con->parent->children->length == 1
475 && con->parent->layout == L_VERT) {
476 memcpy(&color, colors->indicator, sizeof(float) * 4);
477 } else {
478 memcpy(&color, colors->child_border, sizeof(float) * 4);
479 }
480 color[3] *= con->alpha;
481 box.x = con->x;
482 box.y = con->y + con->height - con->sway_view->border_thickness;
483 box.width = con->width;
484 box.height = con->sway_view->border_thickness;
485 render_rect(output->wlr_output, output_damage, &box, color);
446 } 486 }
447 color[3] *= con->alpha;
448 box.x = con->x;
449 box.y = con->y + con->height - con->sway_view->border_thickness;
450 box.width = con->width;
451 box.height = con->sway_view->border_thickness;
452 render_rect(output->wlr_output, output_damage, &box, color);
453} 487}
454 488
455static void render_container(struct sway_output *output, 489static void render_container(struct sway_output *output,
diff --git a/sway/meson.build b/sway/meson.build
index f70a8e44..acf4a3e4 100644
--- a/sway/meson.build
+++ b/sway/meson.build
@@ -41,6 +41,7 @@ sway_sources = files(
41 'commands/font.c', 41 'commands/font.c',
42 'commands/for_window.c', 42 'commands/for_window.c',
43 'commands/fullscreen.c', 43 'commands/fullscreen.c',
44 'commands/hide_edge_borders.c',
44 'commands/kill.c', 45 'commands/kill.c',
45 'commands/opacity.c', 46 'commands/opacity.c',
46 'commands/include.c', 47 'commands/include.c',
diff --git a/sway/tree/container.c b/sway/tree/container.c
index db02c69c..fc35a81c 100644
--- a/sway/tree/container.c
+++ b/sway/tree/container.c
@@ -547,6 +547,21 @@ bool container_has_child(struct sway_container *con,
547 return container_find(con, find_child_func, child); 547 return container_find(con, find_child_func, child);
548} 548}
549 549
550int container_count_descendants_of_type(struct sway_container *con,
551 enum sway_container_type type) {
552 int children = 0;
553 if (con->type == type) {
554 children++;
555 }
556 if (con->children) {
557 for (int i = 0; i < con->children->length; i++) {
558 struct sway_container *child = con->children->items[i];
559 children += container_count_descendants_of_type(child, type);
560 }
561 }
562 return children;
563}
564
550void container_damage_whole(struct sway_container *container) { 565void container_damage_whole(struct sway_container *container) {
551 for (int i = 0; i < root_container.children->length; ++i) { 566 for (int i = 0; i < root_container.children->length; ++i) {
552 struct sway_container *cont = root_container.children->items[i]; 567 struct sway_container *cont = root_container.children->items[i];
diff --git a/sway/tree/view.c b/sway/tree/view.c
index 424c1084..e2cb8a7a 100644
--- a/sway/tree/view.c
+++ b/sway/tree/view.c
@@ -100,6 +100,12 @@ void view_autoconfigure(struct sway_view *view) {
100 return; 100 return;
101 } 101 }
102 102
103 int other_views = 1;
104 if (config->hide_edge_borders == E_SMART) {
105 struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE);
106 other_views = container_count_descendants_of_type(ws, C_VIEW) - 1;
107 }
108
103 double x, y, width, height; 109 double x, y, width, height;
104 x = y = width = height = 0; 110 x = y = width = height = 0;
105 switch (view->border) { 111 switch (view->border) {
@@ -110,18 +116,51 @@ void view_autoconfigure(struct sway_view *view) {
110 height = view->swayc->height; 116 height = view->swayc->height;
111 break; 117 break;
112 case B_PIXEL: 118 case B_PIXEL:
113 x = view->swayc->x + view->border_thickness; 119 if (view->swayc->layout > L_VERT
114 y = view->swayc->y + view->border_thickness; 120 || config->hide_edge_borders == E_NONE
115 width = view->swayc->width - view->border_thickness * 2; 121 || config->hide_edge_borders == E_HORIZONTAL
116 height = view->swayc->height - view->border_thickness * 2; 122 || (config->hide_edge_borders == E_SMART && other_views)) {
123 x = view->swayc->x + view->border_thickness;
124 width = view->swayc->width - view->border_thickness * 2;
125 } else {
126 x = view->swayc->x;
127 width = view->swayc->width;
128 }
129 if (view->swayc->layout > L_VERT
130 || config->hide_edge_borders == E_NONE
131 || config->hide_edge_borders == E_VERTICAL
132 || (config->hide_edge_borders == E_SMART && other_views)) {
133 y = view->swayc->y + view->border_thickness;
134 height = view->swayc->height - view->border_thickness * 2;
135 } else {
136 y = view->swayc->y;
137 height = view->swayc->height;
138 }
117 break; 139 break;
118 case B_NORMAL: 140 case B_NORMAL:
119 // Height is: border + title height + border + view height + border 141 if (view->swayc->layout > L_VERT
120 x = view->swayc->x + view->border_thickness; 142 || config->hide_edge_borders == E_NONE
121 y = view->swayc->y + config->font_height + view->border_thickness * 2; 143 || config->hide_edge_borders == E_HORIZONTAL
122 width = view->swayc->width - view->border_thickness * 2; 144 || (config->hide_edge_borders == E_SMART && other_views)) {
123 height = view->swayc->height - config->font_height 145 x = view->swayc->x + view->border_thickness;
124 - view->border_thickness * 3; 146 width = view->swayc->width - view->border_thickness * 2;
147 } else {
148 x = view->swayc->x;
149 width = view->swayc->width;
150 }
151 if (view->swayc->layout > L_VERT
152 || config->hide_edge_borders == E_NONE
153 || config->hide_edge_borders == E_VERTICAL
154 || (config->hide_edge_borders == E_SMART && other_views)) {
155 // Height is: border + title height + border + view height + border
156 y = view->swayc->y + config->font_height
157 + view->border_thickness * 2;
158 height = view->swayc->height - config->font_height
159 - view->border_thickness * 3;
160 } else {
161 y = view->swayc->y;
162 height = view->swayc->height;
163 }
125 break; 164 break;
126 } 165 }
127 166