output: add color transform to state

Color transforms are better suited than raw gamma tables, because:

- They don't need to get copied around: they are ref'counted.
- They can represent more color operations (will be useful for the
  upcoming KMS color pipeline API, and for the Wayland color
  management protocol).
This commit is contained in:
Simon Ser 2024-08-24 11:14:54 +02:00 committed by Kenny Levinsen
parent 74217a4d93
commit 97f6946c8d
3 changed files with 33 additions and 1 deletions

View file

@ -74,6 +74,7 @@ enum wlr_output_state_field {
WLR_OUTPUT_STATE_LAYERS = 1 << 10,
WLR_OUTPUT_STATE_WAIT_TIMELINE = 1 << 11,
WLR_OUTPUT_STATE_SIGNAL_TIMELINE = 1 << 12,
WLR_OUTPUT_STATE_COLOR_TRANSFORM = 1 << 13,
};
enum wlr_output_state_mode_type {
@ -132,6 +133,8 @@ struct wlr_output_state {
uint64_t wait_point;
struct wlr_drm_syncobj_timeline *signal_timeline;
uint64_t signal_point;
struct wlr_color_transform *color_transform;
};
struct wlr_output_impl;
@ -586,6 +589,13 @@ void wlr_output_state_set_wait_timeline(struct wlr_output_state *state,
*/
void wlr_output_state_set_signal_timeline(struct wlr_output_state *state,
struct wlr_drm_syncobj_timeline *timeline, uint64_t dst_point);
/**
* Set the color transform for an output.
*
* The color transform is applied after blending output layers.
*/
void wlr_output_state_set_color_transform(struct wlr_output_state *state,
struct wlr_color_transform *tr);
/**
* Copies the output state from src to dst. It is safe to then

View file

@ -651,6 +651,10 @@ static bool output_basic_test(struct wlr_output *output,
wlr_log(WLR_DEBUG, "Tried to set the subpixel layout on a disabled output");
return false;
}
if (!enabled && state->committed & WLR_OUTPUT_STATE_COLOR_TRANSFORM) {
wlr_log(WLR_DEBUG, "Tried to set a color transform on a disabled output");
return false;
}
if (state->committed & WLR_OUTPUT_STATE_LAYERS) {
if (state->layers_len != (size_t)wl_list_length(&output->layers)) {

View file

@ -1,6 +1,7 @@
#include <stdlib.h>
#include <string.h>
#include <wlr/render/drm_syncobj.h>
#include <wlr/render/color.h>
#include <wlr/util/log.h>
#include "types/wlr_output.h"
@ -133,6 +134,17 @@ void wlr_output_state_set_signal_timeline(struct wlr_output_state *state,
state->signal_point = dst_point;
}
void wlr_output_state_set_color_transform(struct wlr_output_state *state,
struct wlr_color_transform *tr) {
state->committed |= WLR_OUTPUT_STATE_COLOR_TRANSFORM;
wlr_color_transform_unref(state->color_transform);
if (tr) {
state->color_transform = wlr_color_transform_ref(tr);
} else {
state->color_transform = NULL;
}
}
bool wlr_output_state_copy(struct wlr_output_state *dst,
const struct wlr_output_state *src) {
struct wlr_output_state copy = *src;
@ -140,7 +152,8 @@ bool wlr_output_state_copy(struct wlr_output_state *dst,
WLR_OUTPUT_STATE_DAMAGE |
WLR_OUTPUT_STATE_GAMMA_LUT |
WLR_OUTPUT_STATE_WAIT_TIMELINE |
WLR_OUTPUT_STATE_SIGNAL_TIMELINE);
WLR_OUTPUT_STATE_SIGNAL_TIMELINE |
WLR_OUTPUT_STATE_COLOR_TRANSFORM);
copy.buffer = NULL;
copy.buffer_src_box = (struct wlr_fbox){0};
copy.buffer_dst_box = (struct wlr_box){0};
@ -149,6 +162,7 @@ bool wlr_output_state_copy(struct wlr_output_state *dst,
copy.gamma_lut_size = 0;
copy.wait_timeline = NULL;
copy.signal_timeline = NULL;
copy.color_transform = NULL;
if (src->committed & WLR_OUTPUT_STATE_BUFFER) {
wlr_output_state_set_buffer(&copy, src->buffer);
@ -178,6 +192,10 @@ bool wlr_output_state_copy(struct wlr_output_state *dst,
src->signal_point);
}
if (src->committed & WLR_OUTPUT_STATE_COLOR_TRANSFORM) {
wlr_output_state_set_color_transform(&copy, src->color_transform);
}
wlr_output_state_finish(dst);
*dst = copy;
return true;