Merge pull request #1707 from acrisci/transparency

Implement opacity command
This commit is contained in:
emersion 2018-04-04 22:01:00 -04:00 committed by GitHub
commit 5a64622181
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 68 additions and 16 deletions

View file

@ -123,6 +123,7 @@ sway_cmd cmd_mark;
sway_cmd cmd_mode; sway_cmd cmd_mode;
sway_cmd cmd_mouse_warping; sway_cmd cmd_mouse_warping;
sway_cmd cmd_move; sway_cmd cmd_move;
sway_cmd cmd_opacity;
sway_cmd cmd_new_float; sway_cmd cmd_new_float;
sway_cmd cmd_new_window; sway_cmd cmd_new_window;
sway_cmd cmd_no_focus; sway_cmd cmd_no_focus;

View file

@ -83,6 +83,8 @@ struct sway_container {
list_t *marks; // list of char* list_t *marks; // list of char*
float alpha;
struct { struct {
struct wl_signal destroy; struct wl_signal destroy;
// Raised after the tree updates, but before arrange_windows // Raised after the tree updates, but before arrange_windows

View file

@ -163,6 +163,7 @@ static struct cmd_handler command_handlers[] = {
{ "kill", cmd_kill }, { "kill", cmd_kill },
{ "layout", cmd_layout }, { "layout", cmd_layout },
{ "move", cmd_move }, { "move", cmd_move },
{ "opacity", cmd_opacity },
{ "reload", cmd_reload }, { "reload", cmd_reload },
{ "split", cmd_split }, { "split", cmd_split },
{ "splith", cmd_splith }, { "splith", cmd_splith },

39
sway/commands/opacity.c Normal file
View file

@ -0,0 +1,39 @@
#include <assert.h>
#include <stdlib.h>
#include "sway/commands.h"
#include "sway/tree/view.h"
#include "log.h"
static bool parse_opacity(const char *opacity, float *val) {
char *err;
*val = strtof(opacity, &err);
if (*val < 0 || *val > 1 || *err) {
return false;
}
return true;
}
struct cmd_results *cmd_opacity(int argc, char **argv) {
struct cmd_results *error = NULL;
if ((error = checkarg(argc, "layout", EXPECTED_EQUAL_TO, 1))) {
return error;
}
struct sway_container *con =
config->handler_context.current_container;
float opacity = 0.0f;
if (!parse_opacity(argv[0], &opacity)) {
return cmd_results_new(CMD_INVALID, "opacity <value>",
"Invalid value (expected 0..1): %s", argv[0]);
}
con->alpha = opacity;
if (con->type == C_VIEW) {
view_damage_whole(con->sway_view);
}
return cmd_results_new(CMD_SUCCESS, NULL, NULL);
}

View file

@ -75,7 +75,7 @@ static bool surface_intersect_output(struct wlr_surface *surface,
static void render_surface(struct wlr_surface *surface, static void render_surface(struct wlr_surface *surface,
struct wlr_output *wlr_output, struct timespec *when, struct wlr_output *wlr_output, struct timespec *when,
double ox, double oy, float rotation) { double ox, double oy, float rotation, float alpha) {
struct wlr_renderer *renderer = struct wlr_renderer *renderer =
wlr_backend_get_renderer(wlr_output->backend); wlr_backend_get_renderer(wlr_output->backend);
@ -95,8 +95,8 @@ static void render_surface(struct wlr_surface *surface,
wlr_matrix_project_box(matrix, &box, transform, rotation, wlr_matrix_project_box(matrix, &box, transform, rotation,
wlr_output->transform_matrix); wlr_output->transform_matrix);
// TODO: configurable alpha wlr_render_texture_with_matrix(renderer, surface->texture,
wlr_render_texture_with_matrix(renderer, surface->texture, matrix, 1.0f); matrix, alpha);
wlr_surface_send_frame_done(surface, when); wlr_surface_send_frame_done(surface, when);
} }
@ -110,13 +110,13 @@ static void render_surface(struct wlr_surface *surface,
surface->current->width, surface->current->height, rotation); surface->current->width, surface->current->height, rotation);
render_surface(subsurface->surface, wlr_output, when, render_surface(subsurface->surface, wlr_output, when,
ox + sx, oy + sy, rotation); ox + sx, oy + sy, rotation, alpha);
} }
} }
static void render_xdg_v6_popups(struct wlr_xdg_surface_v6 *surface, static void render_xdg_v6_popups(struct wlr_xdg_surface_v6 *surface,
struct wlr_output *wlr_output, struct timespec *when, double base_x, struct wlr_output *wlr_output, struct timespec *when, double base_x,
double base_y, float rotation) { double base_y, float rotation, float alpha) {
double width = surface->surface->current->width; double width = surface->surface->current->width;
double height = surface->surface->current->height; double height = surface->surface->current->height;
@ -136,19 +136,19 @@ static void render_xdg_v6_popups(struct wlr_xdg_surface_v6 *surface,
width, height, rotation); width, height, rotation);
render_surface(popup->surface, wlr_output, when, render_surface(popup->surface, wlr_output, when,
base_x + popup_sx, base_y + popup_sy, rotation); base_x + popup_sx, base_y + popup_sy, rotation, alpha);
render_xdg_v6_popups(popup, wlr_output, when, render_xdg_v6_popups(popup, wlr_output, when,
base_x + popup_sx, base_y + popup_sy, rotation); base_x + popup_sx, base_y + popup_sy, rotation, alpha);
} }
} }
static void render_wl_shell_surface(struct wlr_wl_shell_surface *surface, static void render_wl_shell_surface(struct wlr_wl_shell_surface *surface,
struct wlr_output *wlr_output, struct timespec *when, struct wlr_output *wlr_output, struct timespec *when,
double lx, double ly, float rotation, double lx, double ly, float rotation, float alpha,
bool is_child) { bool is_child) {
if (is_child || surface->state != WLR_WL_SHELL_SURFACE_STATE_POPUP) { if (is_child || surface->state != WLR_WL_SHELL_SURFACE_STATE_POPUP) {
render_surface(surface->surface, wlr_output, when, render_surface(surface->surface, wlr_output, when,
lx, ly, rotation); lx, ly, rotation, alpha);
double width = surface->surface->current->width; double width = surface->surface->current->width;
double height = surface->surface->current->height; double height = surface->surface->current->height;
@ -164,7 +164,7 @@ static void render_wl_shell_surface(struct wlr_wl_shell_surface *surface,
width, height, rotation); width, height, rotation);
render_wl_shell_surface(popup, wlr_output, when, render_wl_shell_surface(popup, wlr_output, when,
lx + popup_x, ly + popup_y, rotation, true); lx + popup_x, ly + popup_y, rotation, alpha, true);
} }
} }
} }
@ -181,6 +181,7 @@ static void render_view(struct sway_container *view, void *data) {
struct wlr_output *wlr_output = output->wlr_output; struct wlr_output *wlr_output = output->wlr_output;
struct sway_view *sway_view = view->sway_view; struct sway_view *sway_view = view->sway_view;
struct wlr_surface *surface = sway_view->surface; struct wlr_surface *surface = sway_view->surface;
float alpha = sway_view->swayc->alpha;
if (!surface) { if (!surface) {
return; return;
@ -191,17 +192,18 @@ static void render_view(struct sway_container *view, void *data) {
int window_offset_x = view->sway_view->wlr_xdg_surface_v6->geometry.x; int window_offset_x = view->sway_view->wlr_xdg_surface_v6->geometry.x;
int window_offset_y = view->sway_view->wlr_xdg_surface_v6->geometry.y; int window_offset_y = view->sway_view->wlr_xdg_surface_v6->geometry.y;
render_surface(surface, wlr_output, when, render_surface(surface, wlr_output, when,
view->x - window_offset_x, view->y - window_offset_y, 0); view->x - window_offset_x, view->y - window_offset_y, 0, alpha);
render_xdg_v6_popups(sway_view->wlr_xdg_surface_v6, wlr_output, render_xdg_v6_popups(sway_view->wlr_xdg_surface_v6, wlr_output,
when, view->x - window_offset_x, view->y - window_offset_y, 0); when, view->x - window_offset_x, view->y - window_offset_y, 0, alpha);
break; break;
} }
case SWAY_WL_SHELL_VIEW: case SWAY_WL_SHELL_VIEW:
render_wl_shell_surface(sway_view->wlr_wl_shell_surface, wlr_output, render_wl_shell_surface(sway_view->wlr_wl_shell_surface, wlr_output,
when, view->x, view->y, 0, false); when, view->x, view->y, 0, alpha, false);
break; break;
case SWAY_XWAYLAND_VIEW: case SWAY_XWAYLAND_VIEW:
render_surface(surface, wlr_output, when, view->x, view->y, 0); render_surface(surface, wlr_output, when, view->x, view->y,
0, alpha);
break; break;
default: default:
break; break;
@ -214,7 +216,7 @@ static void render_layer(struct sway_output *output, struct timespec *when,
wl_list_for_each(sway_layer, layer, link) { wl_list_for_each(sway_layer, layer, link) {
struct wlr_layer_surface *layer = sway_layer->layer_surface; struct wlr_layer_surface *layer = sway_layer->layer_surface;
render_surface(layer->surface, output->wlr_output, when, render_surface(layer->surface, output->wlr_output, when,
sway_layer->geo.x, sway_layer->geo.y, 0); sway_layer->geo.x, sway_layer->geo.y, 0, 1.0f);
wlr_surface_send_frame_done(layer->surface, when); wlr_surface_send_frame_done(layer->surface, when);
} }
} }
@ -288,7 +290,7 @@ static void render_output(struct sway_output *output, struct timespec *when,
} }
render_surface(xsurface->surface, wlr_output, &output->last_frame, render_surface(xsurface->surface, wlr_output, &output->last_frame,
view_box.x - output_box->x, view_box.y - output_box->y, 0); view_box.x - output_box->x, view_box.y - output_box->y, 0, 1.0f);
} }
// TODO: Consider revising this when fullscreen windows are supported // TODO: Consider revising this when fullscreen windows are supported

View file

@ -15,6 +15,7 @@ sway_sources = files(
'commands/focus.c', 'commands/focus.c',
'commands/focus_follows_mouse.c', 'commands/focus_follows_mouse.c',
'commands/kill.c', 'commands/kill.c',
'commands/opacity.c',
'commands/include.c', 'commands/include.c',
'commands/input.c', 'commands/input.c',
'commands/layout.c', 'commands/layout.c',

View file

@ -413,6 +413,10 @@ The default colors are:
However, any mark that starts with an underscore will not be drawn even if the However, any mark that starts with an underscore will not be drawn even if the
option is on. The default option is _on_. option is on. The default option is _on_.
**opacity** <value>::
Set the opacity of the window between 0 (completely transparent) and 1
(completely opaque).
**unmark** <identifier>:: **unmark** <identifier>::
**Unmark** will remove _identifier_ from the list of current marks on a window. If **Unmark** will remove _identifier_ from the list of current marks on a window. If
no _identifier_ is specified, then **unmark** will remove all marks. no _identifier_ is specified, then **unmark** will remove all marks.

View file

@ -72,6 +72,8 @@ struct sway_container *container_create(enum sway_container_type type) {
c->layout = L_NONE; c->layout = L_NONE;
c->workspace_layout = L_NONE; c->workspace_layout = L_NONE;
c->type = type; c->type = type;
c->alpha = 1.0f;
if (type != C_VIEW) { if (type != C_VIEW) {
c->children = create_list(); c->children = create_list();
} }