mirror of
				https://github.com/cage-kiosk/cage.git
				synced 2025-11-03 09:01:43 -05:00 
			
		
		
		
	output: use backend commits
Pass the whole new desired state to the backend, so that the backend can leverage KMS atomic commits.
This commit is contained in:
		
							parent
							
								
									e8eec54129
								
							
						
					
					
						commit
						76e7a1872a
					
				
					 1 changed files with 54 additions and 31 deletions
				
			
		
							
								
								
									
										81
									
								
								output.c
									
										
									
									
									
								
							
							
						
						
									
										81
									
								
								output.c
									
										
									
									
									
								
							| 
						 | 
					@ -21,12 +21,14 @@
 | 
				
			||||||
#if WLR_HAS_X11_BACKEND
 | 
					#if WLR_HAS_X11_BACKEND
 | 
				
			||||||
#include <wlr/backend/x11.h>
 | 
					#include <wlr/backend/x11.h>
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
 | 
					#include <wlr/render/swapchain.h>
 | 
				
			||||||
#include <wlr/render/wlr_renderer.h>
 | 
					#include <wlr/render/wlr_renderer.h>
 | 
				
			||||||
#include <wlr/types/wlr_compositor.h>
 | 
					#include <wlr/types/wlr_compositor.h>
 | 
				
			||||||
#include <wlr/types/wlr_data_device.h>
 | 
					#include <wlr/types/wlr_data_device.h>
 | 
				
			||||||
#include <wlr/types/wlr_output.h>
 | 
					#include <wlr/types/wlr_output.h>
 | 
				
			||||||
#include <wlr/types/wlr_output_layout.h>
 | 
					#include <wlr/types/wlr_output_layout.h>
 | 
				
			||||||
#include <wlr/types/wlr_output_management_v1.h>
 | 
					#include <wlr/types/wlr_output_management_v1.h>
 | 
				
			||||||
 | 
					#include <wlr/types/wlr_output_swapchain_manager.h>
 | 
				
			||||||
#include <wlr/types/wlr_scene.h>
 | 
					#include <wlr/types/wlr_scene.h>
 | 
				
			||||||
#include <wlr/types/wlr_xdg_shell.h>
 | 
					#include <wlr/types/wlr_xdg_shell.h>
 | 
				
			||||||
#include <wlr/util/log.h>
 | 
					#include <wlr/util/log.h>
 | 
				
			||||||
| 
						 | 
					@ -130,31 +132,6 @@ output_disable(struct cg_output *output)
 | 
				
			||||||
	output_layout_remove(output);
 | 
						output_layout_remove(output);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static bool
 | 
					 | 
				
			||||||
output_apply_config(struct cg_output *output, struct wlr_output_configuration_head_v1 *head, bool test_only)
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
	struct wlr_output_state state = {0};
 | 
					 | 
				
			||||||
	wlr_output_head_v1_state_apply(&head->state, &state);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if (test_only) {
 | 
					 | 
				
			||||||
		bool ret = wlr_output_test_state(output->wlr_output, &state);
 | 
					 | 
				
			||||||
		return ret;
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	/* Apply output configuration */
 | 
					 | 
				
			||||||
	if (!wlr_output_commit_state(output->wlr_output, &state)) {
 | 
					 | 
				
			||||||
		return false;
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if (head->state.enabled) {
 | 
					 | 
				
			||||||
		output_layout_add(output, head->state.x, head->state.y);
 | 
					 | 
				
			||||||
	} else {
 | 
					 | 
				
			||||||
		output_layout_remove(output);
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return true;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
static void
 | 
					static void
 | 
				
			||||||
handle_output_frame(struct wl_listener *listener, void *data)
 | 
					handle_output_frame(struct wl_listener *listener, void *data)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
| 
						 | 
					@ -355,17 +332,63 @@ output_set_window_title(struct cg_output *output, const char *title)
 | 
				
			||||||
static bool
 | 
					static bool
 | 
				
			||||||
output_config_apply(struct cg_server *server, struct wlr_output_configuration_v1 *config, bool test_only)
 | 
					output_config_apply(struct cg_server *server, struct wlr_output_configuration_v1 *config, bool test_only)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct wlr_output_configuration_head_v1 *head;
 | 
						bool ok = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						size_t states_len;
 | 
				
			||||||
 | 
						struct wlr_backend_output_state *states = wlr_output_configuration_v1_build_state(config, &states_len);
 | 
				
			||||||
 | 
						if (states == NULL) {
 | 
				
			||||||
 | 
							return false;
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						struct wlr_output_swapchain_manager swapchain_manager;
 | 
				
			||||||
 | 
						wlr_output_swapchain_manager_init(&swapchain_manager, server->backend);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ok = wlr_output_swapchain_manager_prepare(&swapchain_manager, states, states_len);
 | 
				
			||||||
 | 
						if (!ok || test_only) {
 | 
				
			||||||
 | 
							goto out;
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for (size_t i = 0; i < states_len; i++) {
 | 
				
			||||||
 | 
							struct wlr_backend_output_state *backend_state = &states[i];
 | 
				
			||||||
 | 
							struct cg_output *output = backend_state->output->data;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							struct wlr_swapchain *swapchain =
 | 
				
			||||||
 | 
								wlr_output_swapchain_manager_get_swapchain(&swapchain_manager, backend_state->output);
 | 
				
			||||||
 | 
							struct wlr_scene_output_state_options options = {
 | 
				
			||||||
 | 
								.swapchain = swapchain,
 | 
				
			||||||
 | 
							};
 | 
				
			||||||
 | 
							struct wlr_output_state *state = &backend_state->base;
 | 
				
			||||||
 | 
							if (!wlr_scene_output_build_state(output->scene_output, state, &options)) {
 | 
				
			||||||
 | 
								ok = false;
 | 
				
			||||||
 | 
								goto out;
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ok = wlr_backend_commit(server->backend, states, states_len);
 | 
				
			||||||
 | 
						if (!ok) {
 | 
				
			||||||
 | 
							goto out;
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						wlr_output_swapchain_manager_apply(&swapchain_manager);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						struct wlr_output_configuration_head_v1 *head;
 | 
				
			||||||
	wl_list_for_each (head, &config->heads, link) {
 | 
						wl_list_for_each (head, &config->heads, link) {
 | 
				
			||||||
		struct cg_output *output = head->state.output->data;
 | 
							struct cg_output *output = head->state.output->data;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		if (!output_apply_config(output, head, test_only)) {
 | 
							if (head->state.enabled) {
 | 
				
			||||||
			return false;
 | 
								output_layout_add(output, head->state.x, head->state.y);
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								output_layout_remove(output);
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return true;
 | 
					out:
 | 
				
			||||||
 | 
						wlr_output_swapchain_manager_finish(&swapchain_manager);
 | 
				
			||||||
 | 
						for (size_t i = 0; i < states_len; i++) {
 | 
				
			||||||
 | 
							wlr_output_state_finish(&states[i].base);
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						free(states);
 | 
				
			||||||
 | 
						return ok;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void
 | 
					void
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue