Add gtk_snapshot_push_mask

This commit is contained in:
Matthias Clasen
2023-02-11 10:06:54 -05:00
parent a9f50f1f7a
commit 8f47e885f0
2 changed files with 79 additions and 0 deletions

View File

@@ -121,6 +121,9 @@ struct _GtkSnapshotState {
struct {
char *message;
} debug;
struct {
GskRenderNode *mask_node;
} mask;
} data;
};
@@ -1241,6 +1244,79 @@ gtk_snapshot_push_blend (GtkSnapshot *snapshot,
NULL);
}
static GskRenderNode *
gtk_snapshot_collect_mask_source (GtkSnapshot *snapshot,
GtkSnapshotState *state,
GskRenderNode **nodes,
guint n_nodes)
{
GskRenderNode *source_child, *mask_child, *mask_node;
mask_child = gsk_render_node_ref (state->data.mask.mask_node);
source_child = gtk_snapshot_collect_default (snapshot, state, nodes, n_nodes);
if (source_child == NULL || mask_child == NULL)
return NULL;
mask_node = gsk_mask_node_new (source_child, mask_child);
gsk_render_node_unref (source_child);
gsk_render_node_unref (mask_child);
return mask_node;
}
static void
gtk_snapshot_clear_mask_source (GtkSnapshotState *state)
{
g_clear_pointer (&(state->data.mask.mask_node), gsk_render_node_unref);
}
static GskRenderNode *
gtk_snapshot_collect_mask_mask (GtkSnapshot *snapshot,
GtkSnapshotState *state,
GskRenderNode **nodes,
guint n_nodes)
{
GtkSnapshotState *prev_state = gtk_snapshot_get_previous_state (snapshot);
g_assert (prev_state->collect_func == gtk_snapshot_collect_mask_source);
prev_state->data.mask.mask_node = gtk_snapshot_collect_default (snapshot, state, nodes, n_nodes);
return NULL;
}
/**
* gtk_snapshot_push_mask:
* @snapshot: a #GtkSnapshot
*
* Until the first call to [method@Gtk.Snapshot.pop], the
* mask image for the mask operation will be recorded.
* After that call, the source image will be recorded until
* the second call to [method@Gtk.Snapshot.pop].
*
* Calling this function requires 2 subsequent calls to gtk_snapshot_pop().
*
* Since: 4.10
*/
void
gtk_snapshot_push_mask (GtkSnapshot *snapshot)
{
GtkSnapshotState *current_state = gtk_snapshot_get_current_state (snapshot);
GtkSnapshotState *source_state;
source_state = gtk_snapshot_push_state (snapshot,
current_state->transform,
gtk_snapshot_collect_mask_source,
gtk_snapshot_clear_mask_source);
gtk_snapshot_push_state (snapshot,
source_state->transform,
gtk_snapshot_collect_mask_mask,
NULL);
}
static GskRenderNode *
gtk_snapshot_collect_cross_fade_end (GtkSnapshot *snapshot,
GtkSnapshotState *state,

View File

@@ -95,6 +95,9 @@ void gtk_snapshot_push_shadow (GtkSnapshot
GDK_AVAILABLE_IN_ALL
void gtk_snapshot_push_blend (GtkSnapshot *snapshot,
GskBlendMode blend_mode);
GDK_AVAILABLE_IN_4_10
void gtk_snapshot_push_mask (GtkSnapshot *snapshot);
GDK_AVAILABLE_IN_ALL
void gtk_snapshot_push_cross_fade (GtkSnapshot *snapshot,
double progress);