libsysprof-gtk: allow filling a line chart

This commit is contained in:
Christian Hergert
2023-06-20 16:55:34 -07:00
parent 122c4906b8
commit f71fbd9a31
3 changed files with 70 additions and 2 deletions

View File

@ -30,6 +30,7 @@ struct _SysprofLineLayer
GdkRGBA color;
guint use_curves : 1;
guint flip_y : 1;
guint fill : 1;
};
G_DEFINE_FINAL_TYPE (SysprofLineLayer, sysprof_line_layer, SYSPROF_TYPE_CHART_LAYER)
@ -37,6 +38,7 @@ G_DEFINE_FINAL_TYPE (SysprofLineLayer, sysprof_line_layer, SYSPROF_TYPE_CHART_LA
enum {
PROP_0,
PROP_COLOR,
PROP_FILL,
PROP_FLIP_Y,
PROP_SERIES,
PROP_USE_CURVES,
@ -78,7 +80,6 @@ sysprof_line_layer_snapshot (GtkWidget *widget,
cr = gtk_snapshot_append_cairo (snapshot, &GRAPHENE_RECT_INIT (0, 0, width, height));
gdk_cairo_set_source_rgba (cr, &self->color);
cairo_set_line_width (cr, 1./width);
if (!self->flip_y)
@ -89,7 +90,16 @@ sysprof_line_layer_snapshot (GtkWidget *widget,
last_x = values->x;
last_y = values->y;
cairo_move_to (cr, last_x, last_y);
if (self->fill)
{
cairo_move_to (cr, last_x, 0);
cairo_line_to (cr, last_x, last_y);
}
else
{
cairo_move_to (cr, last_x, last_y);
}
if (self->use_curves)
{
@ -118,10 +128,25 @@ sysprof_line_layer_snapshot (GtkWidget *widget,
const SysprofXYSeriesValue *v = &values[i];
cairo_line_to (cr, v->x, v->y);
last_x = v->x;
last_y = v->y;
}
}
if (self->fill)
{
GdkRGBA fill_color = self->color;
cairo_line_to (cr, last_x, 0);
fill_color.alpha *= .5;
cairo_fill_preserve (cr);
}
gdk_cairo_set_source_rgba (cr, &self->color);
cairo_stroke (cr);
cairo_destroy (cr);
}
@ -149,6 +174,10 @@ sysprof_line_layer_get_property (GObject *object,
g_value_set_boxed (value, sysprof_line_layer_get_color (self));
break;
case PROP_FILL:
g_value_set_boolean (value, sysprof_line_layer_get_fill (self));
break;
case PROP_FLIP_Y:
g_value_set_boolean (value, sysprof_line_layer_get_flip_y (self));
break;
@ -180,6 +209,10 @@ sysprof_line_layer_set_property (GObject *object,
sysprof_line_layer_set_color (self, g_value_get_boxed (value));
break;
case PROP_FILL:
sysprof_line_layer_set_fill (self, g_value_get_boolean (value));
break;
case PROP_FLIP_Y:
sysprof_line_layer_set_flip_y (self, g_value_get_boolean (value));
break;
@ -214,6 +247,11 @@ sysprof_line_layer_class_init (SysprofLineLayerClass *klass)
GDK_TYPE_RGBA,
(G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS));
properties [PROP_FILL] =
g_param_spec_boolean ("fill", NULL, NULL,
FALSE,
(G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS));
properties [PROP_FLIP_Y] =
g_param_spec_boolean ("flip-y", NULL, NULL,
FALSE,
@ -297,6 +335,30 @@ sysprof_line_layer_set_series (SysprofLineLayer *self,
gtk_widget_queue_draw (GTK_WIDGET (self));
}
gboolean
sysprof_line_layer_get_fill (SysprofLineLayer *self)
{
g_return_val_if_fail (SYSPROF_IS_LINE_LAYER (self), FALSE);
return self->fill;
}
void
sysprof_line_layer_set_fill (SysprofLineLayer *self,
gboolean fill)
{
g_return_if_fail (SYSPROF_IS_LINE_LAYER (self));
fill = !!fill;
if (fill != self->fill)
{
self->fill = fill;
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_FILL]);
gtk_widget_queue_draw (GTK_WIDGET (self));
}
}
gboolean
sysprof_line_layer_get_flip_y (SysprofLineLayer *self)
{

View File

@ -45,6 +45,11 @@ SYSPROF_AVAILABLE_IN_ALL
void sysprof_line_layer_set_series (SysprofLineLayer *self,
SysprofXYSeries *series);
SYSPROF_AVAILABLE_IN_ALL
gboolean sysprof_line_layer_get_fill (SysprofLineLayer *self);
SYSPROF_AVAILABLE_IN_ALL
void sysprof_line_layer_set_fill (SysprofLineLayer *self,
gboolean fill);
SYSPROF_AVAILABLE_IN_ALL
gboolean sysprof_line_layer_get_flip_y (SysprofLineLayer *self);
SYSPROF_AVAILABLE_IN_ALL
void sysprof_line_layer_set_flip_y (SysprofLineLayer *self,

View File

@ -185,6 +185,7 @@ main (int argc,
"top", g_object_new (SYSPROF_TYPE_LINE_LAYER,
"series", samples_series,
"title", "Stack Depth as Line",
"fill", TRUE,
NULL),
"bottom", g_object_new (SYSPROF_TYPE_LINE_LAYER,
"series", samples_series,