Merge branch 'main' of https://codeberg.org/dwl/dwl
This commit is contained in:
		
							
								
								
									
										2
									
								
								.mailmap
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								.mailmap
									
									
									
									
									
								
							| @@ -1 +1,3 @@ | ||||
| Lennart Jablonka <humm@ljabl.com> <hummsmith42@gmail.com> | ||||
| Leonardo Hernández Hernández <leohdz172@proton.me> <leohdz172@outlook.com> | ||||
| Leonardo Hernández Hernández <leohdz172@proton.me> <leohdz172@protonmail.com> | ||||
|   | ||||
							
								
								
									
										12
									
								
								CHANGELOG.md
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								CHANGELOG.md
									
									
									
									
									
								
							| @@ -8,10 +8,22 @@ | ||||
|  | ||||
| ## Unreleased | ||||
| ### Added | ||||
|  | ||||
| * Support for the linux-drm-syncobj-v1 protocol ([wlroots!4715][wlroots!4715], [#685][685]) | ||||
| * Allow the use of non-system wlroots library ([#646][646]) | ||||
|  | ||||
| [wlroots!4715]: https://gitlab.freedesktop.org/wlroots/wlroots/-/merge_requests/4715 | ||||
| [685]: https://codeberg.org/dwl/dwl/pulls/685 | ||||
| [646]: https://codeberg.org/dwl/dwl/pulls/646 | ||||
|  | ||||
|  | ||||
| ### Changed | ||||
| ### Deprecated | ||||
| ### Removed | ||||
| ### Fixed | ||||
|  | ||||
| * Crash when a client is created while all outputs are disabled. | ||||
|  | ||||
| ### Security | ||||
| ### Contributors | ||||
|  | ||||
|   | ||||
							
								
								
									
										9
									
								
								Makefile
									
									
									
									
									
								
							
							
						
						
									
										9
									
								
								Makefile
									
									
									
									
									
								
							| @@ -6,15 +6,15 @@ include config.mk | ||||
| # flags for compiling | ||||
| DWLCPPFLAGS = -I. -DWLR_USE_UNSTABLE -D_POSIX_C_SOURCE=200809L \ | ||||
| 	-DVERSION=\"$(VERSION)\" $(XWAYLAND) | ||||
| DWLDEVCFLAGS = -g -pedantic -Wall -Wextra -Wdeclaration-after-statement \ | ||||
| DWLDEVCFLAGS = -g -Wpedantic -Wall -Wextra -Wdeclaration-after-statement \ | ||||
| 	-Wno-unused-parameter -Wshadow -Wunused-macros -Werror=strict-prototypes \ | ||||
| 	-Werror=implicit -Werror=return-type -Werror=incompatible-pointer-types \ | ||||
| 	-Wfloat-conversion | ||||
|  | ||||
| # CFLAGS / LDFLAGS | ||||
| PKGS      = wlroots-0.18 wayland-server xkbcommon libinput $(XLIBS) | ||||
| DWLCFLAGS = `$(PKG_CONFIG) --cflags $(PKGS)` $(DWLCPPFLAGS) $(DWLDEVCFLAGS) $(CFLAGS) | ||||
| LDLIBS    = `$(PKG_CONFIG) --libs $(PKGS)` -lm $(LIBS) | ||||
| PKGS      = wayland-server xkbcommon libinput $(XLIBS) | ||||
| DWLCFLAGS = `$(PKG_CONFIG) --cflags $(PKGS)` $(WLR_INCS) $(DWLCPPFLAGS) $(DWLDEVCFLAGS) $(CFLAGS) | ||||
| LDLIBS    = `$(PKG_CONFIG) --libs $(PKGS)` $(WLR_LIBS) -lm $(LIBS) | ||||
|  | ||||
| all: dwl | ||||
| dwl: dwl.o util.o dwl-ipc-unstable-v2-protocol.o | ||||
| @@ -68,6 +68,7 @@ dist: clean | ||||
|  | ||||
| install: dwl | ||||
| 	mkdir -p $(DESTDIR)$(PREFIX)/bin | ||||
| 	rm -f $(DESTDIR)$(PREFIX)/bin/dwl | ||||
| 	cp -f dwl $(DESTDIR)$(PREFIX)/bin | ||||
| 	chmod 755 $(DESTDIR)$(PREFIX)/bin/dwl | ||||
| 	mkdir -p $(DESTDIR)$(MANDIR)/man1 | ||||
|   | ||||
| @@ -1,7 +1,7 @@ | ||||
| # dwl - dwm for Wayland | ||||
|  | ||||
| Join us on our IRC channel: [#dwl on Libera Chat]   | ||||
| Or on our [Discord server]. | ||||
| Or on the community-maintained [Discord server]. | ||||
|  | ||||
| dwl is a compact, hackable compositor for [Wayland] based on [wlroots]. It is | ||||
| intended to fill the same space in the Wayland world that dwm does in X11, | ||||
|   | ||||
							
								
								
									
										39
									
								
								client.h
									
									
									
									
									
								
							
							
						
						
									
										39
									
								
								client.h
									
									
									
									
									
								
							| @@ -126,15 +126,14 @@ client_get_appid(Client *c) | ||||
| { | ||||
| #ifdef XWAYLAND | ||||
| 	if (client_is_x11(c)) | ||||
| 		return c->surface.xwayland->class; | ||||
| 		return c->surface.xwayland->class ? c->surface.xwayland->class : "broken"; | ||||
| #endif | ||||
| 	return c->surface.xdg->toplevel->app_id; | ||||
| 	return c->surface.xdg->toplevel->app_id ? c->surface.xdg->toplevel->app_id : "broken"; | ||||
| } | ||||
|  | ||||
| static inline void | ||||
| client_get_clip(Client *c, struct wlr_box *clip) | ||||
| { | ||||
| 	struct wlr_box xdg_geom = {0}; | ||||
| 	*clip = (struct wlr_box){ | ||||
| 		.x = 0, | ||||
| 		.y = 0, | ||||
| @@ -147,9 +146,8 @@ client_get_clip(Client *c, struct wlr_box *clip) | ||||
| 		return; | ||||
| #endif | ||||
|  | ||||
| 	wlr_xdg_surface_get_geometry(c->surface.xdg, &xdg_geom); | ||||
| 	clip->x = xdg_geom.x; | ||||
| 	clip->y = xdg_geom.y; | ||||
| 	clip->x = c->surface.xdg->geometry.x; | ||||
| 	clip->y = c->surface.xdg->geometry.y; | ||||
| } | ||||
|  | ||||
| static inline void | ||||
| @@ -164,7 +162,7 @@ client_get_geometry(Client *c, struct wlr_box *geom) | ||||
| 		return; | ||||
| 	} | ||||
| #endif | ||||
| 	wlr_xdg_surface_get_geometry(c->surface.xdg, geom); | ||||
| 	*geom = c->surface.xdg->geometry; | ||||
| } | ||||
|  | ||||
| static inline Client * | ||||
| @@ -200,9 +198,9 @@ client_get_title(Client *c) | ||||
| { | ||||
| #ifdef XWAYLAND | ||||
| 	if (client_is_x11(c)) | ||||
| 		return c->surface.xwayland->title; | ||||
| 		return c->surface.xwayland->title ? c->surface.xwayland->title : "broken"; | ||||
| #endif | ||||
| 	return c->surface.xdg->toplevel->title; | ||||
| 	return c->surface.xdg->toplevel->title ? c->surface.xdg->toplevel->title : "broken"; | ||||
| } | ||||
|  | ||||
| static inline int | ||||
| @@ -301,17 +299,6 @@ client_notify_enter(struct wlr_surface *s, struct wlr_keyboard *kb) | ||||
| 		wlr_seat_keyboard_notify_enter(seat, s, NULL, 0, NULL); | ||||
| } | ||||
|  | ||||
| static inline void | ||||
| client_restack_surface(Client *c) | ||||
| { | ||||
| #ifdef XWAYLAND | ||||
| 	if (client_is_x11(c)) | ||||
| 		wlr_xwayland_surface_restack(c->surface.xwayland, NULL, | ||||
| 				XCB_STACK_MODE_ABOVE); | ||||
| #endif | ||||
| 	return; | ||||
| } | ||||
|  | ||||
| static inline void | ||||
| client_send_close(Client *c) | ||||
| { | ||||
| @@ -344,6 +331,13 @@ client_set_fullscreen(Client *c, int fullscreen) | ||||
| 	wlr_xdg_toplevel_set_fullscreen(c->surface.xdg->toplevel, fullscreen); | ||||
| } | ||||
|  | ||||
| static inline void | ||||
| client_set_scale(struct wlr_surface *s, float scale) | ||||
| { | ||||
| 	wlr_fractional_scale_v1_notify_scale(s, scale); | ||||
| 	wlr_surface_set_preferred_buffer_scale(s, (int32_t)ceilf(scale)); | ||||
| } | ||||
|  | ||||
| static inline uint32_t | ||||
| client_set_size(Client *c, uint32_t width, uint32_t height) | ||||
| { | ||||
| @@ -364,8 +358,11 @@ static inline void | ||||
| client_set_tiled(Client *c, uint32_t edges) | ||||
| { | ||||
| #ifdef XWAYLAND | ||||
| 	if (client_is_x11(c)) | ||||
| 	if (client_is_x11(c)) { | ||||
| 		wlr_xwayland_surface_set_maximized(c->surface.xwayland, | ||||
| 				edges != WLR_EDGE_NONE, edges != WLR_EDGE_NONE); | ||||
| 		return; | ||||
|   } | ||||
| #endif | ||||
| 	if (wl_resource_get_version(c->surface.xdg->toplevel->resource) | ||||
| 			>= XDG_TOPLEVEL_STATE_TILED_RIGHT_SINCE_VERSION) { | ||||
|   | ||||
							
								
								
									
										21
									
								
								config.mk
									
									
									
									
									
								
							
							
						
						
									
										21
									
								
								config.mk
									
									
									
									
									
								
							| @@ -8,10 +8,29 @@ PREFIX = /usr/local | ||||
| MANDIR = $(PREFIX)/share/man | ||||
| DATADIR = $(PREFIX)/share | ||||
|  | ||||
| WLR_INCS = `$(PKG_CONFIG) --cflags wlroots-0.19` | ||||
| WLR_LIBS = `$(PKG_CONFIG) --libs wlroots-0.19` | ||||
|  | ||||
| # Allow using an alternative wlroots installations | ||||
| # This has to have all the includes required by wlroots, e.g: | ||||
| # Assuming wlroots git repo is "${PWD}/wlroots" and you only ran "meson setup build && ninja -C build" | ||||
| #WLR_INCS = -I/usr/include/pixman-1 -I/usr/include/elogind -I/usr/include/libdrm \ | ||||
| #	-I$(PWD)/wlroots/include | ||||
| # Set -rpath to avoid using the wrong library. | ||||
| #WLR_LIBS = -Wl,-rpath,$(PWD)/wlroots/build -L$(PWD)/wlroots/build -lwlroots-0.19 | ||||
|  | ||||
| # Assuming you ran "meson setup --prefix ${PWD}/0.19 build && ninja -C build install" | ||||
| #WLR_INCS = -I/usr/include/pixman-1 -I/usr/include/elogind -I/usr/include/libdrm \ | ||||
| #	-I$(PWD)/wlroots/0.19/include/wlroots-0.19 | ||||
| #WLR_LIBS = -Wl,-rpath,$(PWD)/wlroots/0.19/lib64 -L$(PWD)/wlroots/0.19/lib64 -lwlroots-0.19 | ||||
|  | ||||
| XWAYLAND = | ||||
| XLIBS = | ||||
| # Uncomment to build XWayland support | ||||
| #XWAYLAND = -DXWAYLAND | ||||
| #XLIBS = xcb xcb-icccm | ||||
|  | ||||
| CC = gcc | ||||
| # dwl itself only uses C99 features, but wlroots' headers use anonymous unions (C11). | ||||
| # To avoid warnings about them, we do not use -std=c99 and instead of using the | ||||
| # gmake default 'CC=c99', we use cc. | ||||
| CC = cc | ||||
|   | ||||
							
								
								
									
										149
									
								
								dwl.c
									
									
									
									
									
								
							
							
						
						
									
										149
									
								
								dwl.c
									
									
									
									
									
								
							| @@ -33,6 +33,7 @@ | ||||
| #include <wlr/types/wlr_keyboard_group.h> | ||||
| #include <wlr/types/wlr_layer_shell_v1.h> | ||||
| #include <wlr/types/wlr_linux_dmabuf_v1.h> | ||||
| #include <wlr/types/wlr_linux_drm_syncobj_v1.h> | ||||
| #include <wlr/types/wlr_output.h> | ||||
| #include <wlr/types/wlr_output_layout.h> | ||||
| #include <wlr/types/wlr_output_management_v1.h> | ||||
| @@ -106,15 +107,18 @@ typedef struct { | ||||
|  | ||||
| typedef struct Monitor Monitor; | ||||
| typedef struct { | ||||
| 	/* Must keep these three elements in this order */ | ||||
| 	/* Must keep this field first */ | ||||
| 	unsigned int type; /* XDGShell or X11* */ | ||||
| 	struct wlr_box geom; /* layout-relative, includes border */ | ||||
|  | ||||
| 	Monitor *mon; | ||||
| 	struct wlr_scene_tree *scene; | ||||
| 	struct wlr_scene_rect *border[4]; /* top, bottom, left, right */ | ||||
| 	struct wlr_scene_tree *scene_surface; | ||||
| 	struct wl_list link; | ||||
| 	struct wl_list flink; | ||||
| 	struct wlr_box geom; /* layout-relative, includes border */ | ||||
| 	struct wlr_box prev; /* layout-relative, includes border */ | ||||
| 	struct wlr_box bounds; /* only width and height are used */ | ||||
| 	union { | ||||
| 		struct wlr_xdg_surface *xdg; | ||||
| 		struct wlr_xwayland_surface *xwayland; | ||||
| @@ -129,8 +133,6 @@ typedef struct { | ||||
| 	struct wl_listener fullscreen; | ||||
| 	struct wl_listener set_decoration_mode; | ||||
| 	struct wl_listener destroy_decoration; | ||||
| 	struct wlr_box prev; /* layout-relative, includes border */ | ||||
| 	struct wlr_box bounds; | ||||
| #ifdef XWAYLAND | ||||
| 	struct wl_listener activate; | ||||
| 	struct wl_listener associate; | ||||
| @@ -158,7 +160,6 @@ typedef struct { | ||||
| } Key; | ||||
|  | ||||
| typedef struct { | ||||
| 	struct wl_list link; | ||||
| 	struct wlr_keyboard_group *wlr_group; | ||||
|  | ||||
| 	int nsyms; | ||||
| @@ -172,9 +173,9 @@ typedef struct { | ||||
| } KeyboardGroup; | ||||
|  | ||||
| typedef struct { | ||||
| 	/* Must keep these three elements in this order */ | ||||
| 	/* Must keep this field first */ | ||||
| 	unsigned int type; /* LayerShell */ | ||||
| 	struct wlr_box geom; | ||||
|  | ||||
| 	Monitor *mon; | ||||
| 	struct wlr_scene_tree *scene; | ||||
| 	struct wlr_scene_tree *popups; | ||||
| @@ -347,7 +348,6 @@ static void setcursor(struct wl_listener *listener, void *data); | ||||
| static void setcursorshape(struct wl_listener *listener, void *data); | ||||
| static void setfloating(Client *c, int floating); | ||||
| static void setfullscreen(Client *c, int fullscreen); | ||||
| static void setgamma(struct wl_listener *listener, void *data); | ||||
| static void setlayout(const Arg *arg); | ||||
| static void setmfact(const Arg *arg); | ||||
| static void setmon(Client *c, Monitor *m, uint32_t newtags); | ||||
| @@ -382,7 +382,6 @@ static void xytonode(double x, double y, struct wlr_surface **psurface, | ||||
| static void zoom(const Arg *arg); | ||||
|  | ||||
| /* variables */ | ||||
| static const char broken[] = "broken"; | ||||
| static pid_t child_pid = -1; | ||||
| static int locked; | ||||
| static void *exclusive_focus; | ||||
| @@ -410,7 +409,6 @@ static struct zdwl_ipc_output_v2_interface dwl_output_implementation = {.release | ||||
| static struct wlr_idle_inhibit_manager_v1 *idle_inhibit_mgr; | ||||
| static struct wlr_layer_shell_v1 *layer_shell; | ||||
| static struct wlr_output_manager_v1 *output_mgr; | ||||
| static struct wlr_gamma_control_manager_v1 *gamma_control_mgr; | ||||
| static struct wlr_virtual_keyboard_manager_v1 *virtual_keyboard_mgr; | ||||
| static struct wlr_virtual_pointer_manager_v1 *virtual_pointer_mgr; | ||||
| static struct wlr_cursor_shape_manager_v1 *cursor_shape_mgr; | ||||
| @@ -488,10 +486,8 @@ applyrules(Client *c) | ||||
| 	Monitor *mon = selmon, *m; | ||||
|  | ||||
| 	c->isfloating = client_is_float_type(c); | ||||
| 	if (!(appid = client_get_appid(c))) | ||||
| 		appid = broken; | ||||
| 	if (!(title = client_get_title(c))) | ||||
| 		title = broken; | ||||
| 	appid = client_get_appid(c); | ||||
| 	title = client_get_title(c); | ||||
|  | ||||
| 	for (r = rules; r < END(rules); r++) { | ||||
| 		if ((!r->title || strstr(title, r->title)) | ||||
| @@ -562,8 +558,6 @@ arrangelayer(Monitor *m, struct wl_list *list, struct wlr_box *usable_area, int | ||||
|  | ||||
| 		wlr_scene_layer_surface_v1_configure(l->scene_layer, &full_area, usable_area); | ||||
| 		wlr_scene_node_set_position(&l->popups->node, l->scene->node.x, l->scene->node.y); | ||||
| 		l->geom.x = l->scene->node.x; | ||||
| 		l->geom.y = l->scene->node.y; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| @@ -657,17 +651,17 @@ buttonpress(struct wl_listener *listener, void *data) | ||||
| 		break; | ||||
| 	case WL_POINTER_BUTTON_STATE_RELEASED: | ||||
| 		/* If you released any buttons, we exit interactive move/resize mode. */ | ||||
| 		/* TODO should reset to the pointer focus's current setcursor */ | ||||
| 		/* TODO: should reset to the pointer focus's current setcursor */ | ||||
| 		if (!locked && cursor_mode != CurNormal && cursor_mode != CurPressed) { | ||||
| 			wlr_cursor_set_xcursor(cursor, cursor_mgr, "default"); | ||||
| 			cursor_mode = CurNormal; | ||||
| 			/* Drop the window off on its new monitor */ | ||||
| 			selmon = xytomon(cursor->x, cursor->y); | ||||
| 			setmon(grabc, selmon, 0); | ||||
| 			grabc = NULL; | ||||
| 			return; | ||||
| 		} else { | ||||
| 			cursor_mode = CurNormal; | ||||
| 		} | ||||
| 		cursor_mode = CurNormal; | ||||
| 		break; | ||||
| 	} | ||||
| 	/* If the event wasn't handled by the compositor, notify the client with | ||||
| @@ -793,8 +787,7 @@ commitlayersurfacenotify(struct wl_listener *listener, void *data) | ||||
| 	struct wlr_layer_surface_v1_state old_state; | ||||
|  | ||||
| 	if (l->layer_surface->initial_commit) { | ||||
| 		wlr_fractional_scale_v1_notify_scale(layer_surface->surface, l->mon->wlr_output->scale); | ||||
| 		wlr_surface_set_preferred_buffer_scale(layer_surface->surface, (int32_t)ceilf(l->mon->wlr_output->scale)); | ||||
| 		client_set_scale(layer_surface->surface, l->mon->wlr_output->scale); | ||||
|  | ||||
| 		/* Temporarily set the layer's current state to pending | ||||
| 		 * so that we can easily arrange it */ | ||||
| @@ -833,19 +826,20 @@ commitnotify(struct wl_listener *listener, void *data) | ||||
| 		 * a wrong monitor. | ||||
| 		 */ | ||||
| 		applyrules(c); | ||||
| 		wlr_surface_set_preferred_buffer_scale(client_surface(c), (int)ceilf(c->mon->wlr_output->scale)); | ||||
| 		wlr_fractional_scale_v1_notify_scale(client_surface(c), c->mon->wlr_output->scale); | ||||
| 		if (c->mon) { | ||||
| 			client_set_scale(client_surface(c), c->mon->wlr_output->scale); | ||||
| 		} | ||||
| 		setmon(c, NULL, 0); /* Make sure to reapply rules in mapnotify() */ | ||||
|  | ||||
| 		wlr_xdg_toplevel_set_wm_capabilities(c->surface.xdg->toplevel, WLR_XDG_TOPLEVEL_WM_CAPABILITIES_FULLSCREEN); | ||||
| 		wlr_xdg_toplevel_set_size(c->surface.xdg->toplevel, 0, 0); | ||||
| 		wlr_xdg_toplevel_set_wm_capabilities(c->surface.xdg->toplevel, | ||||
| 				WLR_XDG_TOPLEVEL_WM_CAPABILITIES_FULLSCREEN); | ||||
| 		if (c->decoration) | ||||
| 			requestdecorationmode(&c->set_decoration_mode, c->decoration); | ||||
| 		wlr_xdg_toplevel_set_size(c->surface.xdg->toplevel, 0, 0); | ||||
| 		return; | ||||
| 	} | ||||
|  | ||||
| 	if (client_surface(c)->mapped && c->mon) | ||||
| 		resize(c, c->geom, (c->isfloating && !c->isfullscreen)); | ||||
| 	resize(c, c->geom, (c->isfloating && !c->isfullscreen)); | ||||
|  | ||||
| 	/* mark a pending resize as completed */ | ||||
| 	if (c->resize && c->resize <= c->surface.xdg->current.configure_serial) | ||||
| @@ -870,11 +864,13 @@ commitpopup(struct wl_listener *listener, void *data) | ||||
| 		return; | ||||
| 	popup->base->surface->data = wlr_scene_xdg_surface_create( | ||||
| 			popup->parent->data, popup->base); | ||||
| 	if ((l && !l->mon) || (c && !c->mon)) | ||||
| 	if ((l && !l->mon) || (c && !c->mon)) { | ||||
| 		wlr_xdg_popup_destroy(popup); | ||||
| 		return; | ||||
| 	} | ||||
| 	box = type == LayerShell ? l->mon->m : c->mon->w; | ||||
| 	box.x -= (type == LayerShell ? l->geom.x : c->geom.x); | ||||
| 	box.y -= (type == LayerShell ? l->geom.y : c->geom.y); | ||||
| 	box.x -= (type == LayerShell ? l->scene->node.x : c->geom.x); | ||||
| 	box.y -= (type == LayerShell ? l->scene->node.y : c->geom.y); | ||||
| 	wlr_xdg_popup_unconstrain_from_box(popup, &box); | ||||
| 	wl_list_remove(&listener->link); | ||||
| } | ||||
| @@ -1130,10 +1126,10 @@ createpointer(struct wlr_pointer *pointer) | ||||
| 			libinput_device_config_middle_emulation_set_enabled(device, middle_button_emulation); | ||||
|  | ||||
| 		if (libinput_device_config_scroll_get_methods(device) != LIBINPUT_CONFIG_SCROLL_NO_SCROLL) | ||||
| 			libinput_device_config_scroll_set_method (device, scroll_method); | ||||
| 			libinput_device_config_scroll_set_method(device, scroll_method); | ||||
|  | ||||
| 		if (libinput_device_config_click_get_methods(device) != LIBINPUT_CONFIG_CLICK_METHOD_NONE) | ||||
| 			libinput_device_config_click_set_method (device, click_method); | ||||
| 			libinput_device_config_click_set_method(device, click_method); | ||||
|  | ||||
| 		if (libinput_device_config_send_events_get_modes(device)) { | ||||
| 			const char *dev_name = libinput_device_get_name(device); | ||||
| @@ -1222,7 +1218,6 @@ void | ||||
| destroydecoration(struct wl_listener *listener, void *data) | ||||
| { | ||||
| 	Client *c = wl_container_of(listener, c, destroy_decoration); | ||||
| 	c->decoration = NULL; | ||||
|  | ||||
| 	wl_list_remove(&c->destroy_decoration.link); | ||||
| 	wl_list_remove(&c->set_decoration_mode.link); | ||||
| @@ -1323,6 +1318,7 @@ destroynotify(struct wl_listener *listener, void *data) | ||||
| 		wl_list_remove(&c->commit.link); | ||||
| 		wl_list_remove(&c->map.link); | ||||
| 		wl_list_remove(&c->unmap.link); | ||||
| 		wl_list_remove(&c->maximize.link); | ||||
| 	} | ||||
| 	free(c); | ||||
| } | ||||
| @@ -1620,7 +1616,6 @@ focusclient(Client *c, int lift) | ||||
| 		wl_list_insert(&fstack, &c->flink); | ||||
| 		selmon = c->mon; | ||||
| 		c->isurgent = 0; | ||||
| 		client_restack_surface(c); | ||||
|  | ||||
| 		/* Don't change border color if there is an exclusive focus or we are | ||||
| 		 * handling a drag operation */ | ||||
| @@ -1948,7 +1943,8 @@ mapnotify(struct wl_listener *listener, void *data) | ||||
|  | ||||
| 	/* Create scene tree for this client and its border */ | ||||
| 	c->scene = client_surface(c)->data = wlr_scene_tree_create(layers[LyrTile]); | ||||
| 	wlr_scene_node_set_enabled(&c->scene->node, c->type != XDGShell); | ||||
| 	/* Enabled later by a call to arrange() */ | ||||
| 	wlr_scene_node_set_enabled(&c->scene->node, client_is_unmanaged(c)); | ||||
| 	c->scene_surface = c->type == XDGShell | ||||
| 			? wlr_scene_xdg_surface_create(c->scene, c->surface.xdg) | ||||
| 			: wlr_scene_subsurface_tree_create(c->scene, client_surface(c)); | ||||
| @@ -1961,6 +1957,7 @@ mapnotify(struct wl_listener *listener, void *data) | ||||
| 		/* Unmanaged clients always are floating */ | ||||
| 		wlr_scene_node_reparent(&c->scene->node, layers[LyrFloat]); | ||||
| 		wlr_scene_node_set_position(&c->scene->node, c->geom.x, c->geom.y); | ||||
| 		client_set_size(c, c->geom.width, c->geom.height); | ||||
| 		if (client_wants_focus(c)) { | ||||
| 			focusclient(c, 1); | ||||
| 			exclusive_focus = c; | ||||
| @@ -2078,8 +2075,8 @@ motionnotify(uint32_t time, struct wlr_input_device *device, double dx, double d | ||||
| 			&& toplevel_from_wlr_surface(seat->pointer_state.focused_surface, &w, &l) >= 0) { | ||||
| 		c = w; | ||||
| 		surface = seat->pointer_state.focused_surface; | ||||
| 		sx = cursor->x - (l ? l->geom.x : w->geom.x); | ||||
| 		sy = cursor->y - (l ? l->geom.y : w->geom.y); | ||||
| 		sx = cursor->x - (l ? l->scene->node.x : w->geom.x); | ||||
| 		sy = cursor->y - (l ? l->scene->node.y : w->geom.y); | ||||
| 	} | ||||
|  | ||||
| 	/* time is 0 in internal calls meant to restore pointer focus. */ | ||||
| @@ -2343,6 +2340,7 @@ powermgrsetmode(struct wl_listener *listener, void *data) | ||||
| 	wlr_output_commit_state(m->wlr_output, &state); | ||||
|  | ||||
| 	m->asleep = !event->mode; | ||||
| 	updatemons(NULL, NULL); | ||||
| } | ||||
|  | ||||
| void | ||||
| @@ -2359,7 +2357,6 @@ rendermon(struct wl_listener *listener, void *data) | ||||
| 	Monitor *m = wl_container_of(listener, m, frame); | ||||
| 	Client *c; | ||||
| 	struct wlr_output_state pending = {0}; | ||||
| 	struct wlr_gamma_control_v1 *gamma_control; | ||||
| 	struct timespec now; | ||||
|  | ||||
| 	/* Render if no XDG clients have an outstanding resize and are visible on | ||||
| @@ -2369,32 +2366,7 @@ rendermon(struct wl_listener *listener, void *data) | ||||
| 			goto skip; | ||||
| 	} | ||||
|  | ||||
| 	/* | ||||
| 	 * HACK: The "correct" way to set the gamma is to commit it together with | ||||
| 	 * the rest of the state in one go, but to do that we would need to rewrite | ||||
| 	 * wlr_scene_output_commit() in order to add the gamma to the pending | ||||
| 	 * state before committing, instead try to commit the gamma in one frame, | ||||
| 	 * and commit the rest of the state in the next one (or in the same frame if | ||||
| 	 * the gamma can not be committed). | ||||
| 	 */ | ||||
| 	if (m->gamma_lut_changed) { | ||||
| 		gamma_control | ||||
| 				= wlr_gamma_control_manager_v1_get_control(gamma_control_mgr, m->wlr_output); | ||||
| 		m->gamma_lut_changed = 0; | ||||
|  | ||||
| 		if (!wlr_gamma_control_v1_apply(gamma_control, &pending)) | ||||
| 			goto commit; | ||||
|  | ||||
| 		if (!wlr_output_test_state(m->wlr_output, &pending)) { | ||||
| 			wlr_gamma_control_v1_send_failed_and_destroy(gamma_control); | ||||
| 			goto commit; | ||||
| 		} | ||||
| 		wlr_output_commit_state(m->wlr_output, &pending); | ||||
| 		wlr_output_schedule_frame(m->wlr_output); | ||||
| 	} else { | ||||
| commit: | ||||
| 		wlr_scene_output_commit(m->scene_output, NULL); | ||||
| 	} | ||||
| 	wlr_scene_output_commit(m->scene_output, NULL); | ||||
|  | ||||
| skip: | ||||
| 	/* Let clients know a frame has been rendered */ | ||||
| @@ -2438,7 +2410,7 @@ resize(Client *c, struct wlr_box geo, int interact) | ||||
| 	struct wlr_box *bbox; | ||||
| 	struct wlr_box clip; | ||||
|  | ||||
| 	if (!c->mon || !c->scene) | ||||
| 	if (!c->mon || !client_surface(c)->mapped) | ||||
| 		return; | ||||
|  | ||||
| 	bbox = interact ? &sgeom : &c->mon->w; | ||||
| @@ -2596,17 +2568,6 @@ setfullscreen(Client *c, int fullscreen) | ||||
| 	printstatus(); | ||||
| } | ||||
|  | ||||
| void | ||||
| setgamma(struct wl_listener *listener, void *data) | ||||
| { | ||||
| 	struct wlr_gamma_control_manager_v1_set_gamma_event *event = data; | ||||
| 	Monitor *m = event->output->data; | ||||
| 	if (!m) | ||||
| 		return; | ||||
| 	m->gamma_lut_changed = 1; | ||||
| 	wlr_output_schedule_frame(m->wlr_output); | ||||
| } | ||||
|  | ||||
| void | ||||
| setlayout(const Arg *arg) | ||||
| { | ||||
| @@ -2684,7 +2645,7 @@ setsel(struct wl_listener *listener, void *data) | ||||
| void | ||||
| setup(void) | ||||
| { | ||||
| 	int i, sig[] = {SIGCHLD, SIGINT, SIGTERM, SIGPIPE}; | ||||
| 	int drm_fd, i, sig[] = {SIGCHLD, SIGINT, SIGTERM, SIGPIPE}; | ||||
| 	struct sigaction sa = {.sa_flags = SA_RESTART, .sa_handler = handlesig}; | ||||
| 	sigemptyset(&sa.sa_mask); | ||||
|  | ||||
| @@ -2734,6 +2695,10 @@ setup(void) | ||||
| 				wlr_linux_dmabuf_v1_create_with_renderer(dpy, 5, drw)); | ||||
| 	} | ||||
|  | ||||
| 	if ((drm_fd = wlr_renderer_get_drm_fd(drw)) >= 0 && drw->features.timeline | ||||
| 			&& backend->features.timeline) | ||||
| 		wlr_linux_drm_syncobj_manager_v1_create(dpy, 1, drm_fd); | ||||
|  | ||||
| 	/* Autocreates an allocator for us. | ||||
| 	 * The allocator is the bridge between the renderer and the backend. It | ||||
| 	 * handles the buffer creation, allowing wlroots to render onto the | ||||
| @@ -2757,15 +2722,14 @@ setup(void) | ||||
| 	wlr_viewporter_create(dpy); | ||||
| 	wlr_single_pixel_buffer_manager_v1_create(dpy); | ||||
| 	wlr_fractional_scale_manager_v1_create(dpy, 1); | ||||
| 	wlr_presentation_create(dpy, backend); | ||||
| 	wlr_presentation_create(dpy, backend, 2); | ||||
| 	wlr_alpha_modifier_v1_create(dpy); | ||||
|  | ||||
| 	/* Initializes the interface used to implement urgency hints */ | ||||
| 	activation = wlr_xdg_activation_v1_create(dpy); | ||||
| 	LISTEN_STATIC(&activation->events.request_activate, urgent); | ||||
|  | ||||
| 	gamma_control_mgr = wlr_gamma_control_manager_v1_create(dpy); | ||||
| 	LISTEN_STATIC(&gamma_control_mgr->events.set_gamma, setgamma); | ||||
| 	wlr_scene_set_gamma_control_manager_v1(scene, wlr_gamma_control_manager_v1_create(dpy)); | ||||
|  | ||||
| 	power_mgr = wlr_output_power_manager_v1_create(dpy); | ||||
| 	LISTEN_STATIC(&power_mgr->events.set_mode, powermgrsetmode); | ||||
| @@ -3260,11 +3224,11 @@ void | ||||
| virtualpointer(struct wl_listener *listener, void *data) | ||||
| { | ||||
| 	struct wlr_virtual_pointer_v1_new_pointer_event *event = data; | ||||
| 	struct wlr_pointer pointer = event->new_pointer->pointer; | ||||
| 	struct wlr_input_device *device = &event->new_pointer->pointer.base; | ||||
|  | ||||
| 	wlr_cursor_attach_input_device(cursor, &pointer.base); | ||||
| 	wlr_cursor_attach_input_device(cursor, device); | ||||
| 	if (event->suggested_output) | ||||
| 		wlr_cursor_map_input_to_output(cursor, &pointer.base, event->suggested_output); | ||||
| 		wlr_cursor_map_input_to_output(cursor, device, event->suggested_output); | ||||
| } | ||||
|  | ||||
| Monitor * | ||||
| @@ -3363,17 +3327,24 @@ configurex11(struct wl_listener *listener, void *data) | ||||
| { | ||||
| 	Client *c = wl_container_of(listener, c, configure); | ||||
| 	struct wlr_xwayland_surface_configure_event *event = data; | ||||
| 	/* TODO: figure out if there is another way to do this */ | ||||
| 	if (!c->mon) { | ||||
| 	if (!client_surface(c) || !client_surface(c)->mapped) { | ||||
| 		wlr_xwayland_surface_configure(c->surface.xwayland, | ||||
| 				event->x, event->y, event->width, event->height); | ||||
| 		return; | ||||
| 	} | ||||
| 	if (c->isfloating || client_is_unmanaged(c)) | ||||
| 		resize(c, (struct wlr_box){.x = event->x, .y = event->y, | ||||
| 				.width = event->width + c->bw * 2, .height = event->height + c->bw * 2}, 0); | ||||
| 	else | ||||
| 	if (client_is_unmanaged(c)) { | ||||
| 		wlr_scene_node_set_position(&c->scene->node, event->x, event->y); | ||||
| 		wlr_xwayland_surface_configure(c->surface.xwayland, | ||||
| 				event->x, event->y, event->width, event->height); | ||||
| 		return; | ||||
| 	} | ||||
| 	if ((c->isfloating && c != grabc) || !c->mon->lt[c->mon->sellt]->arrange) { | ||||
| 		resize(c, (struct wlr_box){.x = event->x - c->bw, | ||||
| 				.y = event->y - c->bw, .width = event->width + c->bw * 2, | ||||
| 				.height = event->height + c->bw * 2}, 0); | ||||
| 	} else { | ||||
| 		arrange(c->mon); | ||||
| 	} | ||||
| } | ||||
|  | ||||
| void | ||||
|   | ||||
							
								
								
									
										10
									
								
								util.c
									
									
									
									
									
								
							
							
						
						
									
										10
									
								
								util.c
									
									
									
									
									
								
							| @@ -38,14 +38,14 @@ ecalloc(size_t nmemb, size_t size) | ||||
| int | ||||
| fd_set_nonblock(int fd) { | ||||
| 	int flags = fcntl(fd, F_GETFL); | ||||
|     if (flags < 0) { | ||||
| 	if (flags < 0) { | ||||
| 		perror("fcntl(F_GETFL):"); | ||||
|         return -1; | ||||
|     } | ||||
|     if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) < 0) { | ||||
| 		return -1; | ||||
| 	} | ||||
| 	if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) < 0) { | ||||
| 		perror("fcntl(F_SETFL):"); | ||||
| 		return -1; | ||||
|     } | ||||
| 	} | ||||
|  | ||||
| 	return 0; | ||||
| } | ||||
|   | ||||
		Reference in New Issue
	
	Block a user