[sysprof/wip/chergert/mem-preload: 35/43] memprof: use pixbuf drawing
- From: Christian Hergert <chergert src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [sysprof/wip/chergert/mem-preload: 35/43] memprof: use pixbuf drawing
- Date: Sat, 8 Feb 2020 01:01:18 +0000 (UTC)
commit 6246d6d9f095d7f27265b816ae226b8eddf5ed3b
Author: Christian Hergert <chergert redhat com>
Date: Thu Feb 6 13:16:51 2020 -0800
memprof: use pixbuf drawing
We will have to draw a lot of these, so by reducing this to pixel drawing
we can save quite a bit of overhead and memory from storing paths for
eventual filling.
Also, we should have enough pixels to draw that you'll still get the idea
of allocations without having to draw lines.
src/libsysprof-ui/sysprof-memprof-visualizer.c | 81 +++++++++++++++++---------
1 file changed, 52 insertions(+), 29 deletions(-)
---
diff --git a/src/libsysprof-ui/sysprof-memprof-visualizer.c b/src/libsysprof-ui/sysprof-memprof-visualizer.c
index 1c2209d..9137d77 100644
--- a/src/libsysprof-ui/sysprof-memprof-visualizer.c
+++ b/src/libsysprof-ui/sysprof-memprof-visualizer.c
@@ -99,23 +99,6 @@ sysprof_memprof_visualizer_new (void)
return g_object_new (SYSPROF_TYPE_MEMPROF_VISUALIZER, NULL);
}
-static void
-draw_context_add (cairo_t *cr,
- DrawContext *draw,
- const SysprofCaptureAllocation *ev)
-{
- gint x;
- gint y;
-
- g_assert (draw != NULL);
- g_assert (ev != NULL);
-
- x = (ev->frame.time - draw->begin_time) / (gdouble)draw->duration * draw->alloc.width;
- y = 0;
-
- cairo_rectangle (cr, x, y, 1, 1);
-}
-
static void
sysprof_memprof_visualizer_draw_worker (GTask *task,
gpointer source_object,
@@ -125,7 +108,10 @@ sysprof_memprof_visualizer_draw_worker (GTask *task,
DrawContext *draw = task_data;
SysprofCaptureFrameType type;
cairo_t *cr;
+ guint8 *data;
guint counter = 0;
+ gint stride;
+ gint r, g, b;
g_assert (G_IS_TASK (task));
g_assert (draw != NULL);
@@ -133,26 +119,42 @@ sysprof_memprof_visualizer_draw_worker (GTask *task,
g_assert (draw->reader != NULL);
g_assert (!cancellable || G_IS_CANCELLABLE (cancellable));
- cr = cairo_create (draw->surface);
-
/* Fill background first */
+ cr = cairo_create (draw->surface);
gdk_cairo_rectangle (cr, &draw->alloc);
gdk_cairo_set_source_rgba (cr, &draw->bg);
cairo_fill (cr);
+ cairo_destroy (cr);
+
+ stride = cairo_image_surface_get_stride (draw->surface);
+ data = cairo_image_surface_get_data (draw->surface);
+
+ if (data == NULL)
+ {
+ g_task_return_new_error (task,
+ G_IO_ERROR,
+ G_IO_ERROR_INVALID_DATA,
+ "No data from image surface to access");
+ return;
+ }
+
+ r = draw->fg.red * 255;
+ g = draw->fg.green * 255;
+ b = draw->fg.blue * 255;
/* Now draw data points */
while (sysprof_capture_reader_peek_type (draw->reader, &type))
{
const SysprofCaptureAllocation *ev;
+ guint8 *pptr;
+ gint x;
+ gint y;
/* Cancellation check every 1000 frames */
if G_UNLIKELY (++counter == 1000)
{
if (g_task_return_error_if_cancelled (task))
- {
- cairo_destroy (cr);
- return;
- }
+ return;
counter = 0;
}
@@ -174,13 +176,14 @@ sysprof_memprof_visualizer_draw_worker (GTask *task,
if (ev == NULL)
break;
- draw_context_add (cr, draw, ev);
- }
+ x = (ev->frame.time - draw->begin_time) / (gdouble)draw->duration * draw->alloc.width;
+ y = 0;
- /* Now fill our draw paths */
- gdk_cairo_set_source_rgba (cr, &draw->fg);
- cairo_fill (cr);
- cairo_destroy (cr);
+ pptr = data + ((stride * y) + (x * 3));
+ pptr[0] = r;
+ pptr[1] = g;
+ pptr[2] = b;
+ }
g_task_return_boolean (task, TRUE);
}
@@ -363,7 +366,27 @@ sysprof_memprof_visualizer_class_init (SysprofMemprofVisualizerClass *klass)
visualizer_class->set_reader = sysprof_memprof_visualizer_set_reader;
}
+static void
+on_style_changed_cb (SysprofMemprofVisualizer *self,
+ GtkStyleContext *style_context)
+{
+ g_assert (SYSPROF_IS_MEMPROF_VISUALIZER (self));
+ g_assert (GTK_IS_STYLE_CONTEXT (style_context));
+
+ /* Style changing means we might look odd (dark on light, etc) so
+ * we just invalidate immediately instead of skewing the result
+ * until it has drawn.
+ */
+ g_clear_pointer (&self->surface, cairo_surface_destroy);
+ sysprof_memprof_visualizer_queue_redraw (self);
+}
+
static void
sysprof_memprof_visualizer_init (SysprofMemprofVisualizer *self)
{
+ g_signal_connect_object (gtk_widget_get_style_context (GTK_WIDGET (self)),
+ "changed",
+ G_CALLBACK (on_style_changed_cb),
+ self,
+ G_CONNECT_SWAPPED);
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]