diff options
| author | Leonardo Hernández Hernández <leohdz172@protonmail.com> | 2022-11-11 00:22:36 -0600 | 
|---|---|---|
| committer | Leonardo Hernández Hernández <leohdz172@protonmail.com> | 2022-11-21 20:50:26 -0600 | 
| commit | caec566286b1bbef1758bcf0599677650017c5b9 (patch) | |
| tree | 1eb4ed679b6e6b2c9cf300f8f74238db94128872 | |
| parent | 05eca0e2d95a44a2d33959b8362a21a0f974e17a (diff) | |
create a dedicated layer for fullscreen clients
Bug: https://github.com/djpohly/dwl/issues/327
Diffstat (limited to '')
| -rw-r--r-- | dwl.c | 48 | 
1 files changed, 25 insertions, 23 deletions
| @@ -73,7 +73,7 @@  /* enums */  enum { CurNormal, CurPressed, CurMove, CurResize }; /* cursor */  enum { XDGShell, LayerShell, X11Managed, X11Unmanaged }; /* client types */ -enum { LyrBg, LyrBottom, LyrTop, LyrOverlay, LyrTile, LyrFloat, LyrDragIcon, NUM_LAYERS }; /* scene layers */ +enum { LyrBg, LyrBottom, LyrTop, LyrOverlay, LyrTile, LyrFloat, LyrFS, LyrDragIcon, NUM_LAYERS }; /* scene layers */  #ifdef XWAYLAND  enum { NetWMWindowTypeDialog, NetWMWindowTypeSplash, NetWMWindowTypeToolbar,  	NetWMWindowTypeUtility, NetLast }; /* EWMH atoms */ @@ -102,7 +102,6 @@ typedef struct {  	struct wlr_scene_tree *scene;  	struct wlr_scene_rect *border[4]; /* top, bottom, left, right */  	struct wlr_scene_tree *scene_surface; -	struct wlr_scene_rect *fullscreen_bg; /* See setfullscreen() for info */  	struct wl_list link;  	struct wl_list flink;  	union { @@ -171,6 +170,7 @@ struct Monitor {  	struct wl_list link;  	struct wlr_output *wlr_output;  	struct wlr_scene_output *scene_output; +	struct wlr_scene_rect *fullscreen_bg; /* See createmon() for info */  	struct wl_listener frame;  	struct wl_listener destroy;  	struct wlr_box m;      /* monitor area, layout-relative */ @@ -445,6 +445,9 @@ arrange(Monitor *m)  		if (c->mon == m)  			wlr_scene_node_set_enabled(&c->scene->node, VISIBLEON(c, m)); +	wlr_scene_node_set_enabled(&m->fullscreen_bg->node, +			(c = focustop(m)) && c->isfullscreen); +  	if (m && m->lt[m->sellt]->arrange)  		m->lt[m->sellt]->arrange(m);  	motionnotify(0); @@ -655,6 +658,7 @@ cleanupmon(struct wl_listener *listener, void *data)  	m->wlr_output->data = NULL;  	wlr_output_layout_remove(output_layout, m->wlr_output);  	wlr_scene_output_destroy(m->scene_output); +	wlr_scene_node_destroy(&m->fullscreen_bg->node);  	closemon(m);  	free(m); @@ -874,6 +878,18 @@ createmon(struct wl_listener *listener, void *data)  	wl_list_insert(&mons, &m->link);  	printstatus(); +	/* The xdg-protocol specifies: +	 * +	 * If the fullscreened surface is not opaque, the compositor must make +	 * sure that other screen content not part of the same surface tree (made +	 * up of subsurfaces, popups or similarly coupled surfaces) are not +	 * visible below the fullscreened surface. +	 * +	 */ +	/* updatemons() will resize and set correct position */ +	m->fullscreen_bg = wlr_scene_rect_create(layers[LyrFS], 0, 0, fullscreen_bg); +	wlr_scene_node_set_enabled(&m->fullscreen_bg->node, 0); +  	/* Adds this to the output layout in the order it was configured in.  	 *  	 * The output layout utility automatically adds a wl_output global to the @@ -1724,8 +1740,6 @@ resize(Client *c, struct wlr_box geo, int interact)  	wlr_scene_node_set_position(&c->border[1]->node, 0, c->geom.height - c->bw);  	wlr_scene_node_set_position(&c->border[2]->node, 0, c->bw);  	wlr_scene_node_set_position(&c->border[3]->node, c->geom.width - c->bw, c->bw); -	if (c->fullscreen_bg) -		wlr_scene_rect_set_size(c->fullscreen_bg, c->geom.width, c->geom.height);  	/* wlroots makes this a no-op if size hasn't changed */  	c->resize = client_set_size(c, c->geom.width - 2 * c->bw, @@ -1833,32 +1847,16 @@ setfullscreen(Client *c, int fullscreen)  		return;  	c->bw = fullscreen ? 0 : borderpx;  	client_set_fullscreen(c, fullscreen); +	wlr_scene_node_reparent(&c->scene->node, layers[fullscreen +			? LyrFS : c->isfloating ? LyrFloat : LyrTile]);  	if (fullscreen) {  		c->prev = c->geom;  		resize(c, c->mon->m, 0); -		/* The xdg-protocol specifies: -		 * -		 * If the fullscreened surface is not opaque, the compositor must make -		 * sure that other screen content not part of the same surface tree (made -		 * up of subsurfaces, popups or similarly coupled surfaces) are not -		 * visible below the fullscreened surface. -		 * -		 * For brevity we set a black background for all clients -		 */ -		if (!c->fullscreen_bg) { -			c->fullscreen_bg = wlr_scene_rect_create(c->scene, -				c->geom.width, c->geom.height, fullscreen_bg); -			wlr_scene_node_lower_to_bottom(&c->fullscreen_bg->node); -		}  	} else {  		/* restore previous size instead of arrange for floating windows since  		 * client positions are set by the user and cannot be recalculated */  		resize(c, c->prev, 0); -		if (c->fullscreen_bg) { -			wlr_scene_node_destroy(&c->fullscreen_bg->node); -			c->fullscreen_bg = NULL; -		}  	}  	arrange(c->mon);  	printstatus(); @@ -1976,6 +1974,7 @@ setup(void)  	layers[LyrBottom] = wlr_scene_tree_create(&scene->tree);  	layers[LyrTile] = wlr_scene_tree_create(&scene->tree);  	layers[LyrFloat] = wlr_scene_tree_create(&scene->tree); +	layers[LyrFS] = wlr_scene_tree_create(&scene->tree);  	layers[LyrTop] = wlr_scene_tree_create(&scene->tree);  	layers[LyrOverlay] = wlr_scene_tree_create(&scene->tree);  	layers[LyrDragIcon] = wlr_scene_tree_create(&scene->tree); @@ -2342,6 +2341,9 @@ updatemons(struct wl_listener *listener, void *data)  		/* Don't move clients to the left output when plugging monitors */  		arrange(m); +		wlr_scene_node_set_position(&m->fullscreen_bg->node, m->m.x, m->m.y); +		wlr_scene_rect_set_size(m->fullscreen_bg, m->m.width, m->m.height); +  		config_head->state.enabled = 1;  		config_head->state.mode = m->wlr_output->current_mode;  		config_head->state.x = m->m.x; @@ -2411,7 +2413,7 @@ xytonode(double x, double y, struct wlr_surface **psurface,  	Client *c = NULL;  	LayerSurface *l = NULL;  	const int *layer; -	int focus_order[] = { LyrOverlay, LyrTop, LyrFloat, LyrTile, LyrBottom, LyrBg }; +	int focus_order[] = { LyrOverlay, LyrTop, LyrFS, LyrFloat, LyrTile, LyrBottom, LyrBg };  	for (layer = focus_order; layer < END(focus_order); layer++) {  		if ((node = wlr_scene_node_at(&layers[*layer]->node, x, y, nx, ny))) { | 
