/* GSK - The GTK Scene Kit * * Copyright 2016 Endless * * 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 . */ /** * SECTION:GskRenderer * @title: GskRenderer * @Short_desc: Renders a scene with a simplified graph * * TODO */ #include "config.h" #include "gskrendererprivate.h" #include "gskdebugprivate.h" #include "gskglrendererprivate.h" #include "gskrendernodeprivate.h" #include "gskenumtypes.h" #include #include #include #ifdef GDK_WINDOWING_X11 #include #endif #ifdef GDK_WINDOWING_WAYLAND #include #endif typedef struct { GObject parent_instance; graphene_rect_t viewport; graphene_matrix_t modelview; graphene_matrix_t projection; GskScalingFilter min_filter; GskScalingFilter mag_filter; GdkWindow *window; GdkDrawingContext *drawing_context; GskRenderNode *root_node; GdkDisplay *display; int scale_factor; gboolean is_realized : 1; gboolean auto_clear : 1; gboolean use_alpha : 1; } GskRendererPrivate; G_DEFINE_ABSTRACT_TYPE_WITH_PRIVATE (GskRenderer, gsk_renderer, G_TYPE_OBJECT) enum { PROP_VIEWPORT = 1, PROP_MODELVIEW, PROP_PROJECTION, PROP_MINIFICATION_FILTER, PROP_MAGNIFICATION_FILTER, PROP_AUTO_CLEAR, PROP_USE_ALPHA, PROP_SCALE_FACTOR, PROP_WINDOW, PROP_DISPLAY, PROP_DRAWING_CONTEXT, N_PROPS }; static GParamSpec *gsk_renderer_properties[N_PROPS]; #define GSK_RENDERER_WARN_NOT_IMPLEMENTED_METHOD(obj,method) \ g_critical ("Renderer of type '%s' does not implement GskRenderer::" # method, G_OBJECT_TYPE_NAME (obj)) static gboolean gsk_renderer_real_realize (GskRenderer *self) { GSK_RENDERER_WARN_NOT_IMPLEMENTED_METHOD (self, realize); return FALSE; } static void gsk_renderer_real_unrealize (GskRenderer *self) { GSK_RENDERER_WARN_NOT_IMPLEMENTED_METHOD (self, unrealize); } static void gsk_renderer_real_render (GskRenderer *self, GskRenderNode *root, GdkDrawingContext *context) { GSK_RENDERER_WARN_NOT_IMPLEMENTED_METHOD (self, render); } static void gsk_renderer_dispose (GObject *gobject) { GskRenderer *self = GSK_RENDERER (gobject); GskRendererPrivate *priv = gsk_renderer_get_instance_private (self); gsk_renderer_unrealize (self); g_clear_object (&priv->window); g_clear_object (&priv->display); G_OBJECT_CLASS (gsk_renderer_parent_class)->dispose (gobject); } static void gsk_renderer_set_property (GObject *gobject, guint prop_id, const GValue *value, GParamSpec *pspec) { GskRenderer *self = GSK_RENDERER (gobject); GskRendererPrivate *priv = gsk_renderer_get_instance_private (self); switch (prop_id) { case PROP_VIEWPORT: gsk_renderer_set_viewport (self, g_value_get_boxed (value)); break; case PROP_MODELVIEW: gsk_renderer_set_modelview (self, g_value_get_boxed (value)); break; case PROP_PROJECTION: gsk_renderer_set_projection (self, g_value_get_boxed (value)); break; case PROP_MINIFICATION_FILTER: gsk_renderer_set_scaling_filters (self, g_value_get_enum (value), priv->mag_filter); break; case PROP_MAGNIFICATION_FILTER: gsk_renderer_set_scaling_filters (self, priv->min_filter, g_value_get_enum (value)); break; case PROP_AUTO_CLEAR: gsk_renderer_set_auto_clear (self, g_value_get_boolean (value)); break; case PROP_USE_ALPHA: gsk_renderer_set_use_alpha (self, g_value_get_boolean (value)); break; case PROP_SCALE_FACTOR: gsk_renderer_set_scale_factor (self, g_value_get_int (value)); break; case PROP_WINDOW: gsk_renderer_set_window (self, g_value_get_object (value)); break; case PROP_DISPLAY: /* Construct-only */ priv->display = g_value_dup_object (value); break; } } static void gsk_renderer_get_property (GObject *gobject, guint prop_id, GValue *value, GParamSpec *pspec) { GskRenderer *self = GSK_RENDERER (gobject); GskRendererPrivate *priv = gsk_renderer_get_instance_private (self); switch (prop_id) { case PROP_VIEWPORT: g_value_set_boxed (value, &priv->viewport); break; case PROP_MODELVIEW: g_value_set_boxed (value, &priv->modelview); break; case PROP_PROJECTION: g_value_set_boxed (value, &priv->projection); break; case PROP_MINIFICATION_FILTER: g_value_set_enum (value, priv->min_filter); break; case PROP_MAGNIFICATION_FILTER: g_value_set_enum (value, priv->mag_filter); break; case PROP_AUTO_CLEAR: g_value_set_boolean (value, priv->auto_clear); break; case PROP_USE_ALPHA: g_value_set_boolean (value, priv->use_alpha); break; case PROP_SCALE_FACTOR: g_value_set_int (value, priv->scale_factor); break; case PROP_WINDOW: g_value_set_object (value, priv->window); break; case PROP_DRAWING_CONTEXT: g_value_set_object (value, priv->drawing_context); break; case PROP_DISPLAY: g_value_set_object (value, priv->display); break; } } static void gsk_renderer_constructed (GObject *gobject) { GskRenderer *self = GSK_RENDERER (gobject); GskRendererPrivate *priv = gsk_renderer_get_instance_private (self); if (priv->display == NULL) { GdkDisplayManager *manager = gdk_display_manager_get (); priv->display = gdk_display_manager_get_default_display (manager); g_assert (priv->display != NULL); } G_OBJECT_CLASS (gsk_renderer_parent_class)->constructed (gobject); } static void gsk_renderer_class_init (GskRendererClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); klass->realize = gsk_renderer_real_realize; klass->unrealize = gsk_renderer_real_unrealize; klass->render = gsk_renderer_real_render; gobject_class->constructed = gsk_renderer_constructed; gobject_class->set_property = gsk_renderer_set_property; gobject_class->get_property = gsk_renderer_get_property; gobject_class->dispose = gsk_renderer_dispose; /** * GskRenderer:viewport: * * The visible area used by the #GskRenderer to render its contents. * * Since: 3.22 */ gsk_renderer_properties[PROP_VIEWPORT] = g_param_spec_boxed ("viewport", "Viewport", "The visible area used by the renderer", GRAPHENE_TYPE_RECT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS | G_PARAM_EXPLICIT_NOTIFY); /** * GskRenderer:modelview: * * The initial modelview matrix used by the #GskRenderer. * * If set to %NULL, the identity matrix: * * |[