summaryrefslogtreecommitdiff
path: root/clutter/clutter/clutter-main.c
diff options
context:
space:
mode:
authorDaniel van Vugt <daniel.van.vugt@canonical.com>2018-08-02 19:03:30 +0800
committerJonas Ã…dahl <jadahl@gmail.com>2019-09-02 16:41:13 +0000
commit14c706e51b4d70ac4046ea3c8bacd7292681651c (patch)
tree19cfff38f726d8e6bbb6f67d71a1845b1a2d228a /clutter/clutter/clutter-main.c
parenta70823dd1ca3a0892f7b5fa9c7fe88d885d306eb (diff)
downloadmutter-14c706e51b4d70ac4046ea3c8bacd7292681651c.tar.gz
clutter: Introduce geometric picking
Currently, Clutter does picking by drawing with Cogl and reading the pixel that's beneath the given point. Since Cogl has a journal that records drawing operations, and has optimizations to read a single pixel from a list of rectangle, it would be expected that we would hit this fast path and not flush the journal while picking. However, that's not the case: dithering, clipping with scissors, etc, can all flush the journal, issuing commands to the GPU and making picking slow. On NVidia-based systems, this glReadPixels() call is extremely costly. Introduce geometric picking, and avoid using the Cogl journal entirely. Do this by introducing a stack of actors in ClutterStage. This stack is cached, but for now, don't use the cache as much as possible. The picking routines are still tied to painting. When projecting the actor vertexes, do it manually and take the modelview matrix of the framebuffer into account as well. CPU usage on an Intel i7-7700, tested with two different GPUs/drivers: | | Intel | Nvidia | | ------: | --------: | -----: | | Moving the mouse: | | Before | 10% | 10% | | After | 6% | 6% | | Moving a window: | | Before | 23% | 81% | | After | 19% | 40% | Closes: https://gitlab.gnome.org/GNOME/mutter/issues/154, https://gitlab.gnome.org/GNOME/mutter/issues/691 Helps significantly with: https://gitlab.gnome.org/GNOME/mutter/issues/283, https://gitlab.gnome.org/GNOME/mutter/issues/590, https://gitlab.gnome.org/GNOME/mutter/issues/700 v2: Fix code style issues Simplify quadrilateral checks Remove the 0.5f hack Differentiate axis-aligned rectangles https://gitlab.gnome.org/GNOME/mutter/merge_requests/189
Diffstat (limited to 'clutter/clutter/clutter-main.c')
-rw-r--r--clutter/clutter/clutter-main.c120
1 files changed, 0 insertions, 120 deletions
diff --git a/clutter/clutter/clutter-main.c b/clutter/clutter/clutter-main.c
index 171441577..2bb5bd2c8 100644
--- a/clutter/clutter/clutter-main.c
+++ b/clutter/clutter/clutter-main.c
@@ -129,7 +129,6 @@ static const GDebugKey clutter_debug_keys[] = {
static const GDebugKey clutter_pick_debug_keys[] = {
{ "nop-picking", CLUTTER_DEBUG_NOP_PICKING },
- { "dump-pick-buffers", CLUTTER_DEBUG_DUMP_PICK_BUFFERS },
};
static const GDebugKey clutter_paint_debug_keys[] = {
@@ -401,125 +400,6 @@ clutter_disable_accessibility (void)
clutter_enable_accessibility = FALSE;
}
-void
-_clutter_id_to_color (guint id_,
- ClutterColor *col)
-{
- ClutterMainContext *ctx;
- gint red, green, blue;
-
- ctx = _clutter_context_get_default ();
-
- if (ctx->fb_g_mask == 0)
- {
- /* Figure out framebuffer masks used for pick */
- cogl_get_bitmasks (&ctx->fb_r_mask,
- &ctx->fb_g_mask,
- &ctx->fb_b_mask, NULL);
-
- ctx->fb_r_mask_used = ctx->fb_r_mask;
- ctx->fb_g_mask_used = ctx->fb_g_mask;
- ctx->fb_b_mask_used = ctx->fb_b_mask;
-
- /* XXX - describe what "fuzzy picking" is */
- if (clutter_use_fuzzy_picking)
- {
- ctx->fb_r_mask_used--;
- ctx->fb_g_mask_used--;
- ctx->fb_b_mask_used--;
- }
- }
-
- /* compute the numbers we'll store in the components */
- red = (id_ >> (ctx->fb_g_mask_used+ctx->fb_b_mask_used))
- & (0xff >> (8-ctx->fb_r_mask_used));
- green = (id_ >> ctx->fb_b_mask_used)
- & (0xff >> (8-ctx->fb_g_mask_used));
- blue = (id_)
- & (0xff >> (8-ctx->fb_b_mask_used));
-
- /* shift left bits a bit and add one, this circumvents
- * at least some potential rounding errors in GL/GLES
- * driver / hw implementation.
- */
- if (ctx->fb_r_mask_used != ctx->fb_r_mask)
- red = red * 2;
- if (ctx->fb_g_mask_used != ctx->fb_g_mask)
- green = green * 2;
- if (ctx->fb_b_mask_used != ctx->fb_b_mask)
- blue = blue * 2;
-
- /* shift up to be full 8bit values */
- red = (red << (8 - ctx->fb_r_mask)) | (0x7f >> (ctx->fb_r_mask_used));
- green = (green << (8 - ctx->fb_g_mask)) | (0x7f >> (ctx->fb_g_mask_used));
- blue = (blue << (8 - ctx->fb_b_mask)) | (0x7f >> (ctx->fb_b_mask_used));
-
- col->red = red;
- col->green = green;
- col->blue = blue;
- col->alpha = 0xff;
-
- /* XXX: We rotate the nibbles of the colors here so that there is a
- * visible variation between colors of sequential actor identifiers;
- * otherwise pick buffers dumped to an image will pretty much just look
- * black.
- */
- if (G_UNLIKELY (clutter_pick_debug_flags & CLUTTER_DEBUG_DUMP_PICK_BUFFERS))
- {
- col->red = (col->red << 4) | (col->red >> 4);
- col->green = (col->green << 4) | (col->green >> 4);
- col->blue = (col->blue << 4) | (col->blue >> 4);
- }
-}
-
-guint
-_clutter_pixel_to_id (guchar pixel[4])
-{
- ClutterMainContext *ctx;
- gint red, green, blue;
- guint retval;
-
- ctx = _clutter_context_get_default ();
-
- /* reduce the pixel components to the number of bits actually used of the
- * 8bits.
- */
- if (G_UNLIKELY (clutter_pick_debug_flags & CLUTTER_DEBUG_DUMP_PICK_BUFFERS))
- {
- guchar tmp;
-
- /* XXX: In _clutter_id_to_color we rotated the nibbles of the colors so
- * that there is a visible variation between colors of sequential actor
- * identifiers (otherwise pick buffers dumped to an image will pretty
- * much just look black.) Here we reverse that rotation.
- */
- tmp = ((pixel[0] << 4) | (pixel[0] >> 4));
- red = tmp >> (8 - ctx->fb_r_mask);
- tmp = ((pixel[1] << 4) | (pixel[1] >> 4));
- green = tmp >> (8 - ctx->fb_g_mask);
- tmp = ((pixel[2] << 4) | (pixel[2] >> 4));
- blue = tmp >> (8 - ctx->fb_b_mask);
- }
- else
- {
- red = pixel[0] >> (8 - ctx->fb_r_mask);
- green = pixel[1] >> (8 - ctx->fb_g_mask);
- blue = pixel[2] >> (8 - ctx->fb_b_mask);
- }
-
- /* divide potentially by two if 'fuzzy' */
- red = red >> (ctx->fb_r_mask - ctx->fb_r_mask_used);
- green = green >> (ctx->fb_g_mask - ctx->fb_g_mask_used);
- blue = blue >> (ctx->fb_b_mask - ctx->fb_b_mask_used);
-
- /* combine the correct per component values into the final id */
- retval = blue
- + (green << ctx->fb_b_mask_used)
- + (red << (ctx->fb_b_mask_used + ctx->fb_g_mask_used));
-
- return retval;
-}
-
static CoglPangoFontMap *
clutter_context_get_pango_fontmap (void)
{