mirror of
https://github.com/brl/mutter.git
synced 2024-11-21 23:50:41 -05:00
clutter: Introduce pick contexts
Just as with painting, add a pick context that carries pick related temporary state when doing actor picking. It is currently unused, and will at least at first still carry around a framebuffer to deal track view transforms etc. https://gitlab.gnome.org/GNOME/mutter/merge_requests/935
This commit is contained in:
parent
e8e5ccf82d
commit
cb9d6b79ef
@ -1330,6 +1330,7 @@ _clutter_actor_transform_local_box_to_stage (ClutterActor *self,
|
||||
/**
|
||||
* clutter_actor_pick_box:
|
||||
* @self: The #ClutterActor being "pick" painted.
|
||||
* @pick_context: The #ClutterPickContext
|
||||
* @box: A rectangle in the actor's own local coordinates.
|
||||
*
|
||||
* Logs (does a virtual paint of) a rectangle for picking. Note that @box is
|
||||
@ -1340,6 +1341,7 @@ _clutter_actor_transform_local_box_to_stage (ClutterActor *self,
|
||||
*/
|
||||
void
|
||||
clutter_actor_pick_box (ClutterActor *self,
|
||||
ClutterPickContext *pick_context,
|
||||
const ClutterActorBox *box)
|
||||
{
|
||||
ClutterStage *stage;
|
||||
@ -2321,7 +2323,8 @@ _clutter_actor_rerealize (ClutterActor *self,
|
||||
}
|
||||
|
||||
static void
|
||||
clutter_actor_real_pick (ClutterActor *self)
|
||||
clutter_actor_real_pick (ClutterActor *self,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
if (clutter_actor_should_pick_paint (self))
|
||||
{
|
||||
@ -2332,7 +2335,7 @@ clutter_actor_real_pick (ClutterActor *self)
|
||||
.y2 = clutter_actor_get_height (self),
|
||||
};
|
||||
|
||||
clutter_actor_pick_box (self, &box);
|
||||
clutter_actor_pick_box (self, pick_context, &box);
|
||||
}
|
||||
|
||||
/* XXX - this thoroughly sucks, but we need to maintain compatibility
|
||||
@ -2349,7 +2352,7 @@ clutter_actor_real_pick (ClutterActor *self)
|
||||
for (iter = self->priv->first_child;
|
||||
iter != NULL;
|
||||
iter = iter->priv->next_sibling)
|
||||
clutter_actor_pick (iter);
|
||||
clutter_actor_pick (iter, pick_context);
|
||||
}
|
||||
}
|
||||
|
||||
@ -4174,7 +4177,8 @@ clutter_actor_continue_paint (ClutterActor *self,
|
||||
* Asks @actor to perform a pick.
|
||||
*/
|
||||
void
|
||||
clutter_actor_pick (ClutterActor *actor)
|
||||
clutter_actor_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
ClutterActorPrivate *priv;
|
||||
ClutterActorBox clip;
|
||||
@ -4234,7 +4238,7 @@ clutter_actor_pick (ClutterActor *actor)
|
||||
_clutter_meta_group_peek_metas (priv->effects);
|
||||
}
|
||||
|
||||
clutter_actor_continue_pick (actor);
|
||||
clutter_actor_continue_pick (actor, pick_context);
|
||||
|
||||
if (clip_set)
|
||||
_clutter_actor_pop_pick_clip (actor);
|
||||
@ -4256,7 +4260,8 @@ clutter_actor_pick (ClutterActor *actor)
|
||||
* is the last effect in the chain.
|
||||
*/
|
||||
void
|
||||
clutter_actor_continue_pick (ClutterActor *actor)
|
||||
clutter_actor_continue_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
ClutterActorPrivate *priv;
|
||||
|
||||
@ -4282,9 +4287,9 @@ clutter_actor_continue_pick (ClutterActor *actor)
|
||||
*/
|
||||
if (g_signal_has_handler_pending (actor, actor_signals[PICK],
|
||||
0, TRUE))
|
||||
g_signal_emit (actor, actor_signals[PICK], 0);
|
||||
g_signal_emit (actor, actor_signals[PICK], 0, pick_context);
|
||||
else
|
||||
CLUTTER_ACTOR_GET_CLASS (actor)->pick (actor);
|
||||
CLUTTER_ACTOR_GET_CLASS (actor)->pick (actor, pick_context);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -4298,7 +4303,7 @@ clutter_actor_continue_pick (ClutterActor *actor)
|
||||
priv->current_effect = priv->next_effect_to_paint->data;
|
||||
priv->next_effect_to_paint = priv->next_effect_to_paint->next;
|
||||
|
||||
_clutter_effect_pick (priv->current_effect);
|
||||
_clutter_effect_pick (priv->current_effect, pick_context);
|
||||
|
||||
priv->current_effect = old_current_effect;
|
||||
}
|
||||
@ -8610,6 +8615,7 @@ clutter_actor_class_init (ClutterActorClass *klass)
|
||||
/**
|
||||
* ClutterActor::pick:
|
||||
* @actor: the #ClutterActor that received the signal
|
||||
* @pick_context: a #ClutterPickContext
|
||||
*
|
||||
* The ::pick signal is emitted each time an actor is being painted
|
||||
* in "pick mode". The pick mode is used to identify the actor during
|
||||
@ -8631,7 +8637,8 @@ clutter_actor_class_init (ClutterActorClass *klass)
|
||||
G_SIGNAL_RUN_LAST | G_SIGNAL_DEPRECATED,
|
||||
G_STRUCT_OFFSET (ClutterActorClass, pick),
|
||||
NULL, NULL, NULL,
|
||||
G_TYPE_NONE, 0);
|
||||
G_TYPE_NONE, 1,
|
||||
CLUTTER_TYPE_PICK_CONTEXT);
|
||||
|
||||
/**
|
||||
* ClutterActor::allocation-changed:
|
||||
|
@ -40,6 +40,7 @@
|
||||
#include <clutter/clutter-types.h>
|
||||
#include <clutter/clutter-event.h>
|
||||
#include <clutter/clutter-paint-context.h>
|
||||
#include <clutter/clutter-pick-context.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@ -235,7 +236,8 @@ struct _ClutterActorClass
|
||||
ClutterActor *old_parent);
|
||||
|
||||
void (* destroy) (ClutterActor *self);
|
||||
void (* pick) (ClutterActor *actor);
|
||||
void (* pick) (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context);
|
||||
|
||||
gboolean (* queue_redraw) (ClutterActor *actor,
|
||||
ClutterActor *leaf_that_queued,
|
||||
@ -357,9 +359,11 @@ CLUTTER_EXPORT
|
||||
void clutter_actor_continue_paint (ClutterActor *self,
|
||||
ClutterPaintContext *paint_context);
|
||||
CLUTTER_EXPORT
|
||||
void clutter_actor_pick (ClutterActor *actor);
|
||||
void clutter_actor_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context);
|
||||
CLUTTER_EXPORT
|
||||
void clutter_actor_continue_pick (ClutterActor *actor);
|
||||
void clutter_actor_continue_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context);
|
||||
CLUTTER_EXPORT
|
||||
void clutter_actor_queue_redraw (ClutterActor *self);
|
||||
CLUTTER_EXPORT
|
||||
@ -911,6 +915,7 @@ void clutter_actor_bind_model_with_properties
|
||||
|
||||
CLUTTER_EXPORT
|
||||
void clutter_actor_pick_box (ClutterActor *self,
|
||||
ClutterPickContext *pick_context,
|
||||
const ClutterActorBox *box);
|
||||
|
||||
G_END_DECLS
|
||||
|
@ -15,7 +15,8 @@ gboolean _clutter_effect_has_custom_paint_volume (ClutterEffect
|
||||
void _clutter_effect_paint (ClutterEffect *effect,
|
||||
ClutterPaintContext *paint_context,
|
||||
ClutterEffectPaintFlags flags);
|
||||
void _clutter_effect_pick (ClutterEffect *effect);
|
||||
void _clutter_effect_pick (ClutterEffect *effect,
|
||||
ClutterPickContext *pick_context);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
@ -219,13 +219,14 @@ clutter_effect_real_paint (ClutterEffect *effect,
|
||||
}
|
||||
|
||||
static void
|
||||
clutter_effect_real_pick (ClutterEffect *effect)
|
||||
clutter_effect_real_pick (ClutterEffect *effect,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
ClutterActorMeta *actor_meta = CLUTTER_ACTOR_META (effect);
|
||||
ClutterActor *actor;
|
||||
|
||||
actor = clutter_actor_meta_get_actor (actor_meta);
|
||||
clutter_actor_continue_pick (actor);
|
||||
clutter_actor_continue_pick (actor, pick_context);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -293,11 +294,12 @@ _clutter_effect_paint (ClutterEffect *effect,
|
||||
}
|
||||
|
||||
void
|
||||
_clutter_effect_pick (ClutterEffect *effect)
|
||||
_clutter_effect_pick (ClutterEffect *effect,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
g_return_if_fail (CLUTTER_IS_EFFECT (effect));
|
||||
|
||||
CLUTTER_EFFECT_GET_CLASS (effect)->pick (effect);
|
||||
CLUTTER_EFFECT_GET_CLASS (effect)->pick (effect, pick_context);
|
||||
}
|
||||
|
||||
gboolean
|
||||
|
@ -31,6 +31,7 @@
|
||||
|
||||
#include <clutter/clutter-actor-meta.h>
|
||||
#include <clutter/clutter-paint-context.h>
|
||||
#include <clutter/clutter-pick-context.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@ -86,7 +87,8 @@ struct _ClutterEffectClass
|
||||
void (* paint) (ClutterEffect *effect,
|
||||
ClutterPaintContext *paint_context,
|
||||
ClutterEffectPaintFlags flags);
|
||||
void (* pick) (ClutterEffect *effect);
|
||||
void (* pick) (ClutterEffect *effect,
|
||||
ClutterPickContext *pick_context);
|
||||
|
||||
/*< private >*/
|
||||
void (* _clutter_effect4) (void);
|
||||
|
25
clutter/clutter/clutter-pick-context-private.h
Normal file
25
clutter/clutter/clutter-pick-context-private.h
Normal file
@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Red Hat Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef CLUTTER_PICK_CONTEXT_PRIVATE_H
|
||||
#define CLUTTER_PICK_CONTEXT_PRIVATE_H
|
||||
|
||||
#include "clutter-pick-context.h"
|
||||
|
||||
ClutterPickContext * clutter_pick_context_new_for_view (ClutterStageView *view);
|
||||
|
||||
#endif /* CLUTTER_PICK_CONTEXT_PRIVATE_H */
|
83
clutter/clutter/clutter-pick-context.c
Normal file
83
clutter/clutter/clutter-pick-context.c
Normal file
@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Red Hat Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "clutter-build-config.h"
|
||||
|
||||
#include "clutter-pick-context-private.h"
|
||||
|
||||
struct _ClutterPickContext
|
||||
{
|
||||
grefcount ref_count;
|
||||
|
||||
CoglFramebuffer *framebuffer;
|
||||
};
|
||||
|
||||
G_DEFINE_BOXED_TYPE (ClutterPickContext, clutter_pick_context,
|
||||
clutter_pick_context_ref,
|
||||
clutter_pick_context_unref)
|
||||
|
||||
ClutterPickContext *
|
||||
clutter_pick_context_new_for_view (ClutterStageView *view)
|
||||
{
|
||||
ClutterPickContext *pick_context;
|
||||
|
||||
pick_context = g_new0 (ClutterPickContext, 1);
|
||||
g_ref_count_init (&pick_context->ref_count);
|
||||
pick_context->framebuffer =
|
||||
cogl_object_ref (clutter_stage_view_get_framebuffer (view));
|
||||
|
||||
return pick_context;
|
||||
}
|
||||
|
||||
ClutterPickContext *
|
||||
clutter_pick_context_ref (ClutterPickContext *pick_context)
|
||||
{
|
||||
g_ref_count_inc (&pick_context->ref_count);
|
||||
return pick_context;
|
||||
}
|
||||
|
||||
static void
|
||||
clutter_pick_context_dispose (ClutterPickContext *pick_context)
|
||||
{
|
||||
g_clear_pointer (&pick_context->framebuffer, cogl_object_unref);
|
||||
}
|
||||
|
||||
void
|
||||
clutter_pick_context_unref (ClutterPickContext *pick_context)
|
||||
{
|
||||
if (g_ref_count_dec (&pick_context->ref_count))
|
||||
{
|
||||
clutter_pick_context_dispose (pick_context);
|
||||
g_free (pick_context);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
clutter_pick_context_destroy (ClutterPickContext *pick_context)
|
||||
{
|
||||
clutter_pick_context_dispose (pick_context);
|
||||
clutter_pick_context_unref (pick_context);
|
||||
}
|
||||
|
||||
/**
|
||||
* clutter_pick_context_get_framebuffer: (skip)
|
||||
*/
|
||||
CoglFramebuffer *
|
||||
clutter_pick_context_get_framebuffer (ClutterPickContext *pick_context)
|
||||
{
|
||||
return pick_context->framebuffer;
|
||||
}
|
49
clutter/clutter/clutter-pick-context.h
Normal file
49
clutter/clutter/clutter-pick-context.h
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (C) 2019 Red Hat Inc.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef CLUTTER_PICK_CONTEXT_H
|
||||
#define CLUTTER_PICK_CONTEXT_H
|
||||
|
||||
#if !defined(__CLUTTER_H_INSIDE__) && !defined(CLUTTER_COMPILATION)
|
||||
#error "Only <clutter/clutter.h> can be included directly."
|
||||
#endif
|
||||
|
||||
#include <glib-object.h>
|
||||
|
||||
#include "clutter-macros.h"
|
||||
#include "clutter-stage-view.h"
|
||||
|
||||
typedef struct _ClutterPickContext ClutterPickContext;
|
||||
|
||||
#define CLUTTER_TYPE_PICK_CONTEXT (clutter_pick_context_get_type ())
|
||||
|
||||
CLUTTER_EXPORT
|
||||
GType clutter_pick_context_get_type (void);
|
||||
|
||||
CLUTTER_EXPORT
|
||||
ClutterPickContext * clutter_pick_context_ref (ClutterPickContext *pick_context);
|
||||
|
||||
CLUTTER_EXPORT
|
||||
void clutter_pick_context_unref (ClutterPickContext *pick_context);
|
||||
|
||||
CLUTTER_EXPORT
|
||||
void clutter_pick_context_destroy (ClutterPickContext *pick_context);
|
||||
|
||||
CLUTTER_EXPORT
|
||||
CoglFramebuffer * clutter_pick_context_get_framebuffer (ClutterPickContext *pick_context);
|
||||
|
||||
#endif /* CLUTTER_PICK_CONTEXT_H */
|
@ -70,6 +70,7 @@
|
||||
#include "clutter-mutter.h"
|
||||
#include "clutter-paint-context-private.h"
|
||||
#include "clutter-paint-volume-private.h"
|
||||
#include "clutter-pick-context-private.h"
|
||||
#include "clutter-private.h"
|
||||
#include "clutter-stage-manager-private.h"
|
||||
#include "clutter-stage-private.h"
|
||||
@ -981,7 +982,8 @@ clutter_stage_paint (ClutterActor *self,
|
||||
}
|
||||
|
||||
static void
|
||||
clutter_stage_pick (ClutterActor *self)
|
||||
clutter_stage_pick (ClutterActor *self,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
ClutterActorIter iter;
|
||||
ClutterActor *child;
|
||||
@ -992,7 +994,7 @@ clutter_stage_pick (ClutterActor *self)
|
||||
*/
|
||||
clutter_actor_iter_init (&iter, self);
|
||||
while (clutter_actor_iter_next (&iter, &child))
|
||||
clutter_actor_pick (child);
|
||||
clutter_actor_pick (child, pick_context);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
@ -1652,17 +1654,21 @@ _clutter_stage_do_pick_on_view (ClutterStage *stage,
|
||||
|
||||
if (mode != priv->cached_pick_mode)
|
||||
{
|
||||
ClutterPickContext *pick_context;
|
||||
|
||||
_clutter_stage_clear_pick_stack (stage);
|
||||
|
||||
pick_context = clutter_pick_context_new_for_view (view);
|
||||
cogl_push_framebuffer (fb);
|
||||
|
||||
context->pick_mode = mode;
|
||||
setup_view_for_pick_or_paint (stage, view, NULL);
|
||||
clutter_actor_pick (CLUTTER_ACTOR (stage));
|
||||
clutter_actor_pick (CLUTTER_ACTOR (stage), pick_context);
|
||||
context->pick_mode = CLUTTER_PICK_NONE;
|
||||
priv->cached_pick_mode = mode;
|
||||
|
||||
cogl_pop_framebuffer ();
|
||||
clutter_pick_context_destroy (pick_context);
|
||||
|
||||
add_pick_stack_weak_refs (stage);
|
||||
}
|
||||
|
@ -292,14 +292,15 @@ clutter_group_real_paint (ClutterActor *actor,
|
||||
}
|
||||
|
||||
static void
|
||||
clutter_group_real_pick (ClutterActor *actor)
|
||||
clutter_group_real_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
ClutterGroupPrivate *priv = CLUTTER_GROUP (actor)->priv;
|
||||
|
||||
/* Chain up so we get a bounding box pained (if we are reactive) */
|
||||
CLUTTER_ACTOR_CLASS (clutter_group_parent_class)->pick (actor);
|
||||
CLUTTER_ACTOR_CLASS (clutter_group_parent_class)->pick (actor, pick_context);
|
||||
|
||||
g_list_foreach (priv->children, (GFunc) clutter_actor_pick, NULL);
|
||||
g_list_foreach (priv->children, (GFunc) clutter_actor_pick, pick_context);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -64,6 +64,7 @@ clutter_headers = [
|
||||
'clutter-pan-action.h',
|
||||
'clutter-path-constraint.h',
|
||||
'clutter-path.h',
|
||||
'clutter-pick-context.h',
|
||||
'clutter-property-transition.h',
|
||||
'clutter-rotate-action.h',
|
||||
'clutter-script.h',
|
||||
@ -153,6 +154,7 @@ clutter_sources = [
|
||||
'clutter-pan-action.c',
|
||||
'clutter-path-constraint.c',
|
||||
'clutter-path.c',
|
||||
'clutter-pick-context.c',
|
||||
'clutter-property-transition.c',
|
||||
'clutter-rotate-action.c',
|
||||
'clutter-script.c',
|
||||
|
@ -131,7 +131,8 @@ meta_surface_actor_paint (ClutterActor *actor,
|
||||
}
|
||||
|
||||
static void
|
||||
meta_surface_actor_pick (ClutterActor *actor)
|
||||
meta_surface_actor_pick (ClutterActor *actor,
|
||||
ClutterPickContext *pick_context)
|
||||
{
|
||||
MetaSurfaceActor *self = META_SURFACE_ACTOR (actor);
|
||||
MetaSurfaceActorPrivate *priv =
|
||||
@ -144,7 +145,12 @@ meta_surface_actor_pick (ClutterActor *actor)
|
||||
|
||||
/* If there is no region then use the regular pick */
|
||||
if (priv->input_region == NULL)
|
||||
CLUTTER_ACTOR_CLASS (meta_surface_actor_parent_class)->pick (actor);
|
||||
{
|
||||
ClutterActorClass *actor_class =
|
||||
CLUTTER_ACTOR_CLASS (meta_surface_actor_parent_class);
|
||||
|
||||
actor_class->pick (actor, pick_context);
|
||||
}
|
||||
else
|
||||
{
|
||||
int n_rects;
|
||||
@ -163,14 +169,14 @@ meta_surface_actor_pick (ClutterActor *actor)
|
||||
box.y1 = rect.y;
|
||||
box.x2 = rect.x + rect.width;
|
||||
box.y2 = rect.y + rect.height;
|
||||
clutter_actor_pick_box (actor, &box);
|
||||
clutter_actor_pick_box (actor, pick_context, &box);
|
||||
}
|
||||
}
|
||||
|
||||
clutter_actor_iter_init (&iter, actor);
|
||||
|
||||
while (clutter_actor_iter_next (&iter, &child))
|
||||
clutter_actor_pick (child);
|
||||
clutter_actor_pick (child, pick_context);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
Loading…
Reference in New Issue
Block a user