Compare commits

..

1 Commits

Author SHA1 Message Date
Nelson Benítez León bd206f3b7a Improve window size for long text tooltips
When a tooltip reaches the hardcoded limit of 50
chars it will wrap to a new line, but keeps the
window's width same as if it were just one line.

From GtkLabel docs:
"For wrapping labels, width-chars is used as the
minimum width, if specified, and max-width-chars
is used as the natural width."

So we detect for this case and set label's width-chars
property, so we set the minimum size to a lesser value.

Fixes #5521
2023-01-22 16:34:07 +00:00
198 changed files with 20320 additions and 21869 deletions
-1
View File
@@ -364,7 +364,6 @@ asan-build:
tags: [ asan ] tags: [ asan ]
stage: analysis stage: analysis
needs: [] needs: []
when: manual
variables: variables:
script: script:
- export PATH="$HOME/.local/bin:$PATH" - export PATH="$HOME/.local/bin:$PATH"
+1 -2
View File
@@ -21,7 +21,7 @@ many things that we value:
Please, do not use the issue tracker for support questions. If you have Please, do not use the issue tracker for support questions. If you have
questions on how to use GTK effectively, you can use: questions on how to use GTK effectively, you can use:
- the `gtk` [room on matrix](https://matrix.to/#/#gtk:gnome.org) - the `#gtk` IRC channel on irc.gnome.org
- the [gtk tag on the GNOME Discourse instance](https://discourse.gnome.org/tag/gtk) - the [gtk tag on the GNOME Discourse instance](https://discourse.gnome.org/tag/gtk)
You can also look at the GTK tag on [Stack You can also look at the GTK tag on [Stack
@@ -44,7 +44,6 @@ If you're reporting a bug make sure to list:
0. which version of GTK are you using? 0. which version of GTK are you using?
0. which operating system are you using? 0. which operating system are you using?
0. what display and graphics driver are you using?
0. the necessary steps to reproduce the issue 0. the necessary steps to reproduce the issue
0. the expected outcome 0. the expected outcome
0. a description of the behavior; screenshots are also welcome 0. a description of the behavior; screenshots are also welcome
+1 -96
View File
@@ -1,101 +1,6 @@
Overview of Changes in 4.9.4, xx-xx-xxxx Overview of Changes in 4.9.3, xx-xx-xxxx
======================================== ========================================
* Printing:
- Add a CPDB print backend
* GtkFileDialog:
- Robustness fixes
* GtkScaleButton:
- Add an 'active' property
* Fix conflicting type names between gtk and gio
* Gsk:
- Settable filtering for scaled textures
- Add mask nodes
* Wayland:
- Handle dispatch failing in more places
* Translation updates:
Belarusian
Chinese (Taiwan)
Georgian
Turkish
Overview of Changes in 4.9.3, 04-02-2023
========================================
* Add GtkUriLauncher, as replacement for gtk_show_uri
* Add GdkMonitor::description
* Fix problems with tooltip sizing
* Deprecations:
- GtkStatusbar
- GtkAssistant
- GtkLockButton
- gtk_gesture_set_sequence_state
* GtkColumnView:
- Only create widgets for visible columns
* GtkFileDialog:
- Drop shortcut folders API
* GtkCalendar:
- Make marked days work again
* GtkSwitch:
- Make state and active independently settable
* GtkFileChooser:
- Fix a crash with DND
- Fix excessively wide sidebar
- Make context menus work again
* Accessibility:
- Make GtkAccessible public, so it can be implemented outside GTK
- Support accessible implementation for editables
* CSS:
- Fix randomly stopping CSS animations
* GL:
- Fix synchronization with GStreamer
- Fix problems with 3rd party GL in the same thread
* Wayland:
- Fix startup notification with xdg_activation
* Broadway:
- Implement modal windows
* macOS:
- Make DND work
* Build:
- Require graphene 1.10
- Require gobject-introspection 1.72
* Translation updates
Catalan
Galician
German
Hebrew
Indonesian
Portuguese
Russian
Spanish
Swedish
Turkish
Ukrainian
Overview of Changes in 4.9.2, 26-12-2022 Overview of Changes in 4.9.2, 26-12-2022
======================================== ========================================
-2
View File
@@ -2,8 +2,6 @@
#include <gtk/gtk.h> #include <gtk/gtk.h>
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
typedef GtkApplication DemoApplication; typedef GtkApplication DemoApplication;
typedef GtkApplicationClass DemoApplicationClass; typedef GtkApplicationClass DemoApplicationClass;
-2
View File
@@ -7,8 +7,6 @@
#include <gtk/gtk.h> #include <gtk/gtk.h>
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
static GtkWidget *progress_bar = NULL; static GtkWidget *progress_bar = NULL;
static gboolean static gboolean
-4
View File
@@ -37,8 +37,6 @@ remove_timeout (gpointer data)
g_source_remove (id); g_source_remove (id);
} }
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
static gboolean static gboolean
pop_status (gpointer data) pop_status (gpointer data)
{ {
@@ -59,8 +57,6 @@ status_message (GtkStatusbar *status,
g_object_set_data_full (G_OBJECT (status), "timeout", GUINT_TO_POINTER (id), remove_timeout); g_object_set_data_full (G_OBJECT (status), "timeout", GUINT_TO_POINTER (id), remove_timeout);
} }
G_GNUC_END_IGNORE_DEPRECATIONS
static void static void
help_activate (GSimpleAction *action, help_activate (GSimpleAction *action,
GVariant *parameter, GVariant *parameter,
-7
View File
@@ -215,12 +215,6 @@
<file>demo3widget.h</file> <file>demo3widget.h</file>
<file>demo3widget.ui</file> <file>demo3widget.ui</file>
</gresource> </gresource>
<gresource prefix="/mask">
<file>demo4widget.c</file>
<file>demo4widget.h</file>
<file>hsla.h</file>
<file>hsla.c</file>
</gresource>
<gresource prefix="/paintable_svg"> <gresource prefix="/paintable_svg">
<file>svgpaintable.h</file> <file>svgpaintable.h</file>
<file>svgpaintable.c</file> <file>svgpaintable.c</file>
@@ -317,7 +311,6 @@
<file>list_store.c</file> <file>list_store.c</file>
<file>main.c</file> <file>main.c</file>
<file>markup.c</file> <file>markup.c</file>
<file>mask.c</file>
<file>menu.c</file> <file>menu.c</file>
<file>overlay.c</file> <file>overlay.c</file>
<file>overlay_decorative.c</file> <file>overlay_decorative.c</file>
+24 -43
View File
@@ -3,8 +3,7 @@
enum enum
{ {
PROP_TEXTURE = 1, PROP_PAINTABLE = 1,
PROP_FILTER,
PROP_SCALE PROP_SCALE
}; };
@@ -12,9 +11,8 @@ struct _Demo3Widget
{ {
GtkWidget parent_instance; GtkWidget parent_instance;
GdkTexture *texture; GdkPaintable *paintable;
float scale; float scale;
GskScalingFilter filter;
GtkWidget *menu; GtkWidget *menu;
}; };
@@ -30,7 +28,6 @@ static void
demo3_widget_init (Demo3Widget *self) demo3_widget_init (Demo3Widget *self)
{ {
self->scale = 1.f; self->scale = 1.f;
self->filter = GSK_SCALING_FILTER_LINEAR;
gtk_widget_init_template (GTK_WIDGET (self)); gtk_widget_init_template (GTK_WIDGET (self));
} }
@@ -39,7 +36,7 @@ demo3_widget_dispose (GObject *object)
{ {
Demo3Widget *self = DEMO3_WIDGET (object); Demo3Widget *self = DEMO3_WIDGET (object);
g_clear_object (&self->texture); g_clear_object (&self->paintable);
gtk_widget_dispose_template (GTK_WIDGET (self), DEMO3_TYPE_WIDGET); gtk_widget_dispose_template (GTK_WIDGET (self), DEMO3_TYPE_WIDGET);
@@ -53,13 +50,12 @@ demo3_widget_snapshot (GtkWidget *widget,
Demo3Widget *self = DEMO3_WIDGET (widget); Demo3Widget *self = DEMO3_WIDGET (widget);
int x, y, width, height; int x, y, width, height;
double w, h; double w, h;
GskRenderNode *node;
width = gtk_widget_get_width (widget); width = gtk_widget_get_width (widget);
height = gtk_widget_get_height (widget); height = gtk_widget_get_height (widget);
w = self->scale * gdk_texture_get_width (self->texture); w = self->scale * gdk_paintable_get_intrinsic_width (self->paintable);
h = self->scale * gdk_texture_get_height (self->texture); h = self->scale * gdk_paintable_get_intrinsic_height (self->paintable);
x = MAX (0, (width - ceil (w)) / 2); x = MAX (0, (width - ceil (w)) / 2);
y = MAX (0, (height - ceil (h)) / 2); y = MAX (0, (height - ceil (h)) / 2);
@@ -67,11 +63,7 @@ demo3_widget_snapshot (GtkWidget *widget,
gtk_snapshot_push_clip (snapshot, &GRAPHENE_RECT_INIT (0, 0, width, height)); gtk_snapshot_push_clip (snapshot, &GRAPHENE_RECT_INIT (0, 0, width, height));
gtk_snapshot_save (snapshot); gtk_snapshot_save (snapshot);
gtk_snapshot_translate (snapshot, &GRAPHENE_POINT_INIT (x, y)); gtk_snapshot_translate (snapshot, &GRAPHENE_POINT_INIT (x, y));
node = gsk_texture_scale_node_new (self->texture, gdk_paintable_snapshot (self->paintable, snapshot, w, h);
&GRAPHENE_RECT_INIT (0, 0, w, h),
self->filter);
gtk_snapshot_append_node (snapshot, node);
gsk_render_node_unref (node);
gtk_snapshot_restore (snapshot); gtk_snapshot_restore (snapshot);
gtk_snapshot_pop (snapshot); gtk_snapshot_pop (snapshot);
} }
@@ -89,9 +81,9 @@ demo3_widget_measure (GtkWidget *widget,
int size; int size;
if (orientation == GTK_ORIENTATION_HORIZONTAL) if (orientation == GTK_ORIENTATION_HORIZONTAL)
size = gdk_texture_get_width (self->texture); size = gdk_paintable_get_intrinsic_width (self->paintable);
else else
size = gdk_texture_get_height (self->texture); size = gdk_paintable_get_intrinsic_height (self->paintable);
*minimum = *natural = self->scale * size; *minimum = *natural = self->scale * size;
} }
@@ -121,9 +113,9 @@ demo3_widget_set_property (GObject *object,
switch (prop_id) switch (prop_id)
{ {
case PROP_TEXTURE: case PROP_PAINTABLE:
g_clear_object (&self->texture); g_clear_object (&self->paintable);
self->texture = g_value_dup_object (value); self->paintable = g_value_dup_object (value);
gtk_widget_queue_resize (GTK_WIDGET (object)); gtk_widget_queue_resize (GTK_WIDGET (object));
break; break;
@@ -132,11 +124,6 @@ demo3_widget_set_property (GObject *object,
gtk_widget_queue_resize (GTK_WIDGET (object)); gtk_widget_queue_resize (GTK_WIDGET (object));
break; break;
case PROP_FILTER:
self->filter = g_value_get_enum (value);
gtk_widget_queue_resize (GTK_WIDGET (object));
break;
default: default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break; break;
@@ -153,18 +140,14 @@ demo3_widget_get_property (GObject *object,
switch (prop_id) switch (prop_id)
{ {
case PROP_TEXTURE: case PROP_PAINTABLE:
g_value_set_object (value, self->texture); g_value_set_object (value, self->paintable);
break; break;
case PROP_SCALE: case PROP_SCALE:
g_value_set_float (value, self->scale); g_value_set_float (value, self->scale);
break; break;
case PROP_FILTER:
g_value_set_enum (value, self->filter);
break;
default: default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break; break;
@@ -222,21 +205,16 @@ demo3_widget_class_init (Demo3WidgetClass *class)
widget_class->measure = demo3_widget_measure; widget_class->measure = demo3_widget_measure;
widget_class->size_allocate = demo3_widget_size_allocate; widget_class->size_allocate = demo3_widget_size_allocate;
g_object_class_install_property (object_class, PROP_TEXTURE, g_object_class_install_property (object_class, PROP_PAINTABLE,
g_param_spec_object ("texture", NULL, NULL, g_param_spec_object ("paintable", "Paintable", "Paintable",
GDK_TYPE_TEXTURE, GDK_TYPE_PAINTABLE,
G_PARAM_READWRITE)); G_PARAM_READWRITE));
g_object_class_install_property (object_class, PROP_SCALE, g_object_class_install_property (object_class, PROP_SCALE,
g_param_spec_float ("scale", NULL, NULL, g_param_spec_float ("scale", "Scale", "Scale",
0.0, 10.0, 1.0, 0.0, 10.0, 1.0,
G_PARAM_READWRITE)); G_PARAM_READWRITE));
g_object_class_install_property (object_class, PROP_FILTER,
g_param_spec_enum ("filter", NULL, NULL,
GSK_TYPE_SCALING_FILTER, GSK_SCALING_FILTER_LINEAR,
G_PARAM_READWRITE));
/* These are the actions that we are using in the menu */ /* These are the actions that we are using in the menu */
gtk_widget_class_install_action (widget_class, "zoom.in", NULL, zoom_cb); gtk_widget_class_install_action (widget_class, "zoom.in", NULL, zoom_cb);
gtk_widget_class_install_action (widget_class, "zoom.out", NULL, zoom_cb); gtk_widget_class_install_action (widget_class, "zoom.out", NULL, zoom_cb);
@@ -251,13 +229,16 @@ GtkWidget *
demo3_widget_new (const char *resource) demo3_widget_new (const char *resource)
{ {
Demo3Widget *self; Demo3Widget *self;
GdkTexture *texture; GdkPixbuf *pixbuf;
GdkPaintable *paintable;
texture = gdk_texture_new_from_resource (resource); pixbuf = gdk_pixbuf_new_from_resource (resource, NULL);
paintable = GDK_PAINTABLE (gdk_texture_new_for_pixbuf (pixbuf));
self = g_object_new (DEMO3_TYPE_WIDGET, "texture", texture, NULL); self = g_object_new (DEMO3_TYPE_WIDGET, "paintable", paintable, NULL);
g_object_unref (texture); g_object_unref (pixbuf);
g_object_unref (paintable);
return GTK_WIDGET (self); return GTK_WIDGET (self);
} }
-123
View File
@@ -1,123 +0,0 @@
#include <math.h>
#include "demo4widget.h"
#include "hsla.h"
struct _Demo4Widget
{
GtkWidget parent_instance;
PangoLayout *layout;
GskColorStop stops[8];
gsize n_stops;
guint tick;
};
struct _Demo4WidgetClass
{
GtkWidgetClass parent_class;
};
G_DEFINE_TYPE (Demo4Widget, demo4_widget, GTK_TYPE_WIDGET)
static void
rotate_color (GdkRGBA *rgba)
{
GdkHSLA hsla;
_gdk_hsla_init_from_rgba (&hsla, rgba);
hsla.hue -= 1;
_gdk_rgba_init_from_hsla (rgba, &hsla);
}
static gboolean
rotate_colors (GtkWidget *widget,
GdkFrameClock *clock,
gpointer user_data)
{
Demo4Widget *self = DEMO4_WIDGET (widget);
for (unsigned int i = 0; i < self->n_stops; i++)
rotate_color (&self->stops[i].color);
gtk_widget_queue_draw (widget);
return G_SOURCE_CONTINUE;
}
static void
demo4_widget_init (Demo4Widget *self)
{
PangoFontDescription *desc;
self->n_stops = 8;
self->stops[0].offset = 0;
self->stops[0].color = (GdkRGBA) { 1, 0, 0, 1 };
for (unsigned int i = 1; i < self->n_stops; i++)
{
GdkHSLA hsla;
self->stops[i].offset = i / (double)(self->n_stops - 1);
_gdk_hsla_init_from_rgba (&hsla, &self->stops[i - 1].color);
hsla.hue += 360.0 / (double)(self->n_stops - 1);
_gdk_rgba_init_from_hsla (&self->stops[i].color, &hsla);
}
self->layout = gtk_widget_create_pango_layout (GTK_WIDGET (self), "123");
desc = pango_font_description_from_string ("Cantarell Bold 210");
pango_layout_set_font_description (self->layout, desc);
pango_font_description_free (desc);
self->tick = gtk_widget_add_tick_callback (GTK_WIDGET (self), rotate_colors, NULL, NULL);
}
static void
demo4_widget_dispose (GObject *object)
{
Demo4Widget *self = DEMO4_WIDGET (object);
g_clear_object (&self->layout);
gtk_widget_remove_tick_callback (GTK_WIDGET (self), self->tick);
G_OBJECT_CLASS (demo4_widget_parent_class)->dispose (object);
}
static void
demo4_widget_snapshot (GtkWidget *widget,
GtkSnapshot *snapshot)
{
Demo4Widget *self = DEMO4_WIDGET (widget);
int width, height;
width = gtk_widget_get_width (widget);
height = gtk_widget_get_height (widget);
gtk_snapshot_push_mask (snapshot);
gtk_snapshot_append_layout (snapshot, self->layout, &(GdkRGBA) { 0, 0, 0, 1 });
gtk_snapshot_pop (snapshot);
gtk_snapshot_append_linear_gradient (snapshot,
&GRAPHENE_RECT_INIT (0, 0, width, height),
&GRAPHENE_POINT_INIT (0, 0),
&GRAPHENE_POINT_INIT (width, height),
self->stops,
self->n_stops);
gtk_snapshot_pop (snapshot);
}
static void
demo4_widget_class_init (Demo4WidgetClass *class)
{
GObjectClass *object_class = G_OBJECT_CLASS (class);
GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (class);
object_class->dispose = demo4_widget_dispose;
widget_class->snapshot = demo4_widget_snapshot;
}
GtkWidget *
demo4_widget_new (void)
{
return g_object_new (DEMO4_TYPE_WIDGET, NULL);
}
-8
View File
@@ -1,8 +0,0 @@
#pragma once
#include <gtk/gtk.h>
#define DEMO4_TYPE_WIDGET (demo4_widget_get_type ())
G_DECLARE_FINAL_TYPE (Demo4Widget, demo4_widget, DEMO4, WIDGET, GtkWidget)
GtkWidget * demo4_widget_new (void);
+1 -1
View File
@@ -362,7 +362,7 @@ do_drawingarea (GtkWidget *do_widget)
G_CALLBACK (scribble_resize), NULL); G_CALLBACK (scribble_resize), NULL);
drag = gtk_gesture_drag_new (); drag = gtk_gesture_drag_new ();
gtk_gesture_single_set_button (GTK_GESTURE_SINGLE (drag), 0); gtk_gesture_single_set_button (GTK_GESTURE_SINGLE (drag), GDK_BUTTON_PRIMARY);
gtk_widget_add_controller (da, GTK_EVENT_CONTROLLER (drag)); gtk_widget_add_controller (da, GTK_EVENT_CONTROLLER (drag));
g_signal_connect (drag, "drag-begin", G_CALLBACK (drag_begin), da); g_signal_connect (drag, "drag-begin", G_CALLBACK (drag_begin), da);
-146
View File
@@ -1,146 +0,0 @@
#include <gdk/gdk.h>
#include "hsla.h"
void
_gdk_hsla_init_from_rgba (GdkHSLA *hsla,
const GdkRGBA *rgba)
{
float min;
float max;
float red;
float green;
float blue;
float delta;
g_return_if_fail (hsla != NULL);
g_return_if_fail (rgba != NULL);
red = rgba->red;
green = rgba->green;
blue = rgba->blue;
if (red > green)
{
if (red > blue)
max = red;
else
max = blue;
if (green < blue)
min = green;
else
min = blue;
}
else
{
if (green > blue)
max = green;
else
max = blue;
if (red < blue)
min = red;
else
min = blue;
}
hsla->lightness = (max + min) / 2;
hsla->saturation = 0;
hsla->hue = 0;
hsla->alpha = rgba->alpha;
if (max != min)
{
if (hsla->lightness <= 0.5)
hsla->saturation = (max - min) / (max + min);
else
hsla->saturation = (max - min) / (2 - max - min);
delta = max -min;
if (red == max)
hsla->hue = (green - blue) / delta;
else if (green == max)
hsla->hue = 2 + (blue - red) / delta;
else if (blue == max)
hsla->hue = 4 + (red - green) / delta;
hsla->hue *= 60;
if (hsla->hue < 0.0)
hsla->hue += 360;
}
}
void
_gdk_rgba_init_from_hsla (GdkRGBA *rgba,
const GdkHSLA *hsla)
{
float hue;
float lightness;
float saturation;
float m1, m2;
lightness = hsla->lightness;
saturation = hsla->saturation;
if (lightness <= 0.5)
m2 = lightness * (1 + saturation);
else
m2 = lightness + saturation - lightness * saturation;
m1 = 2 * lightness - m2;
rgba->alpha = hsla->alpha;
if (saturation == 0)
{
rgba->red = lightness;
rgba->green = lightness;
rgba->blue = lightness;
}
else
{
hue = hsla->hue + 120;
while (hue > 360)
hue -= 360;
while (hue < 0)
hue += 360;
if (hue < 60)
rgba->red = m1 + (m2 - m1) * hue / 60;
else if (hue < 180)
rgba->red = m2;
else if (hue < 240)
rgba->red = m1 + (m2 - m1) * (240 - hue) / 60;
else
rgba->red = m1;
hue = hsla->hue;
while (hue > 360)
hue -= 360;
while (hue < 0)
hue += 360;
if (hue < 60)
rgba->green = m1 + (m2 - m1) * hue / 60;
else if (hue < 180)
rgba->green = m2;
else if (hue < 240)
rgba->green = m1 + (m2 - m1) * (240 - hue) / 60;
else
rgba->green = m1;
hue = hsla->hue - 120;
while (hue > 360)
hue -= 360;
while (hue < 0)
hue += 360;
if (hue < 60)
rgba->blue = m1 + (m2 - m1) * hue / 60;
else if (hue < 180)
rgba->blue = m2;
else if (hue < 240)
rgba->blue = m1 + (m2 - m1) * (240 - hue) / 60;
else
rgba->blue = m1;
}
}
-15
View File
@@ -1,15 +0,0 @@
#pragma once
typedef struct _GdkHSLA GdkHSLA;
struct _GdkHSLA {
float hue;
float saturation;
float lightness;
float alpha;
};
void _gdk_hsla_init_from_rgba (GdkHSLA *hsla,
const GdkRGBA *rgba);
void _gdk_rgba_init_from_hsla (GdkRGBA *rgba,
const GdkHSLA *hsla);
-46
View File
@@ -1,46 +0,0 @@
/* Masking
*
* Demonstrates mask nodes.
*
* This demo uses a text node as mask for
* an animated linear gradient.
*/
#include <gtk/gtk.h>
#include "demo4widget.h"
GtkWidget *
do_mask (GtkWidget *do_widget)
{
static GtkWidget *window = NULL;
if (!window)
{
GtkWidget *box;
GtkWidget *widget;
window = gtk_window_new ();
gtk_window_set_title (GTK_WINDOW (window), "Mask Nodes");
gtk_window_set_default_size (GTK_WINDOW (window), 600, 400);
gtk_window_set_display (GTK_WINDOW (window),
gtk_widget_get_display (do_widget));
g_object_add_weak_pointer (G_OBJECT (window), (gpointer *)&window);
box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0);
gtk_window_set_child (GTK_WINDOW (window), box);
widget = demo4_widget_new ();
gtk_widget_set_hexpand (widget, TRUE);
gtk_widget_set_vexpand (widget, TRUE);
gtk_box_append (GTK_BOX (box), widget);
}
if (!gtk_widget_get_visible (window))
gtk_widget_set_visible (window, TRUE);
else
gtk_window_destroy (GTK_WINDOW (window));
return window;
}
+1 -12
View File
@@ -22,11 +22,9 @@ do_menu (GtkWidget *do_widget)
if (!window) if (!window)
{ {
GtkWidget *box; GtkWidget *box;
GtkWidget *box2;
GtkWidget *sw; GtkWidget *sw;
GtkWidget *widget; GtkWidget *widget;
GtkWidget *scale; GtkWidget *scale;
GtkWidget *dropdown;
window = gtk_window_new (); window = gtk_window_new ();
gtk_window_set_title (GTK_WINDOW (window), "Menu"); gtk_window_set_title (GTK_WINDOW (window), "Menu");
@@ -45,19 +43,10 @@ do_menu (GtkWidget *do_widget)
widget = demo3_widget_new ("/transparent/portland-rose.jpg"); widget = demo3_widget_new ("/transparent/portland-rose.jpg");
gtk_scrolled_window_set_child (GTK_SCROLLED_WINDOW (sw), widget); gtk_scrolled_window_set_child (GTK_SCROLLED_WINDOW (sw), widget);
box2 = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 0);
gtk_box_append (GTK_BOX (box), box2);
scale = gtk_scale_new_with_range (GTK_ORIENTATION_HORIZONTAL, 0.01, 10.0, 0.1); scale = gtk_scale_new_with_range (GTK_ORIENTATION_HORIZONTAL, 0.01, 10.0, 0.1);
gtk_range_set_value (GTK_RANGE (scale), 1.0); gtk_range_set_value (GTK_RANGE (scale), 1.0);
gtk_widget_set_hexpand (scale, TRUE); gtk_box_append (GTK_BOX (box), scale);
gtk_box_append (GTK_BOX (box2), scale);
dropdown = gtk_drop_down_new (G_LIST_MODEL (gtk_string_list_new ((const char *[]){ "Linear", "Nearest", "Trilinear", NULL })), NULL);
gtk_box_append (GTK_BOX (box2), dropdown);
g_object_bind_property (dropdown, "selected", widget, "filter", G_BINDING_DEFAULT);
g_object_bind_property (gtk_range_get_adjustment (GTK_RANGE (scale)), "value", g_object_bind_property (gtk_range_get_adjustment (GTK_RANGE (scale)), "value",
widget, "scale", widget, "scale",
G_BINDING_BIDIRECTIONAL); G_BINDING_BIDIRECTIONAL);
-3
View File
@@ -46,7 +46,6 @@ demos = files([
'links.c', 'links.c',
'listbox.c', 'listbox.c',
'listbox_controls.c', 'listbox_controls.c',
'mask.c',
'menu.c', 'menu.c',
'flowbox.c', 'flowbox.c',
'list_store.c', 'list_store.c',
@@ -115,7 +114,6 @@ extra_demo_sources = files([
'gtkshadertoy.c', 'gtkshadertoy.c',
'gtkshaderstack.c', 'gtkshaderstack.c',
'gskshaderpaintable.c', 'gskshaderpaintable.c',
'hsla.c',
'puzzlepiece.c', 'puzzlepiece.c',
'bluroverlay.c', 'bluroverlay.c',
'demoimage.c', 'demoimage.c',
@@ -128,7 +126,6 @@ extra_demo_sources = files([
'four_point_transform.c', 'four_point_transform.c',
'demo2widget.c', 'demo2widget.c',
'demo3widget.c', 'demo3widget.c',
'demo4widget.c',
'pixbufpaintable.c', 'pixbufpaintable.c',
'script-names.c', 'script-names.c',
'unicode-names.c', 'unicode-names.c',
-15
View File
@@ -297,21 +297,6 @@ The default texture is a 10x10 checkerboard with the top left and bottom right
representation for this texture is `url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABmJLR0QA/wD/AP+gvaeTAAAAKUlEQVQYlWP8z3DmPwMaYGQwYUQXY0IXwAUGUCGGoxkYGBiweXAoeAYAz44F3e3U1xUAAAAASUVORK5CYII=") representation for this texture is `url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAoAAAAKCAYAAACNMs+9AAAABmJLR0QA/wD/AP+gvaeTAAAAKUlEQVQYlWP8z3DmPwMaYGQwYUQXY0IXwAUGUCGGoxkYGBiweXAoeAYAz44F3e3U1xUAAAAASUVORK5CYII=")
`. `.
### texture-scale
| property | syntax | default | printed |
| -------- | ---------------- | ---------------------- | ----------- |
| bounds | `<rect>` | 50 | always |
| texture | `<url>` | *see below* | always |
| filter | `filter` | *see below* | non-default |
Creates a node like `gsk_texture_scale_node_new()` with the given properties.
The default texture is a 10x10 checkerboard, just like for texture.
The possible filter values are `linear`, `nearest` and `trilinear`, with
`linear` being the default.
### transform ### transform
| property | syntax | default | printed | | property | syntax | default | printed |
-2
View File
@@ -6,8 +6,6 @@
#include "demo_conf.h" #include "demo_conf.h"
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
static GtkWidget *main_window; static GtkWidget *main_window;
static GFile *filename = NULL; static GFile *filename = NULL;
static GtkPageSetup *page_setup = NULL; static GtkPageSetup *page_setup = NULL;
-4
View File
@@ -2252,13 +2252,11 @@ activate (GApplication *app)
for (i = 0; i < G_N_ELEMENTS (accels); i++) for (i = 0; i < G_N_ELEMENTS (accels); i++)
gtk_application_set_accels_for_action (GTK_APPLICATION (app), accels[i].action_and_target, accels[i].accelerators); gtk_application_set_accels_for_action (GTK_APPLICATION (app), accels[i].action_and_target, accels[i].accelerators);
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
widget = (GtkWidget *)gtk_builder_get_object (builder, "statusbar"); widget = (GtkWidget *)gtk_builder_get_object (builder, "statusbar");
gtk_statusbar_push (GTK_STATUSBAR (widget), 0, "All systems are operating normally."); gtk_statusbar_push (GTK_STATUSBAR (widget), 0, "All systems are operating normally.");
action = G_ACTION (g_property_action_new ("statusbar", widget, "visible")); action = G_ACTION (g_property_action_new ("statusbar", widget, "visible"));
g_action_map_add_action (G_ACTION_MAP (window), action); g_action_map_add_action (G_ACTION_MAP (window), action);
g_object_unref (G_OBJECT (action)); g_object_unref (G_OBJECT (action));
G_GNUC_END_IGNORE_DEPRECATIONS
widget = (GtkWidget *)gtk_builder_get_object (builder, "toolbar"); widget = (GtkWidget *)gtk_builder_get_object (builder, "toolbar");
action = G_ACTION (g_property_action_new ("toolbar", widget, "visible")); action = G_ACTION (g_property_action_new ("toolbar", widget, "visible"));
@@ -2432,7 +2430,6 @@ G_GNUC_END_IGNORE_DEPRECATIONS
widget = (GtkWidget *)gtk_builder_get_object (builder, "record_button"); widget = (GtkWidget *)gtk_builder_get_object (builder, "record_button");
g_object_set_data (G_OBJECT (window), "record_button", widget); g_object_set_data (G_OBJECT (window), "record_button", widget);
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
widget = (GtkWidget *)gtk_builder_get_object (builder, "lockbox"); widget = (GtkWidget *)gtk_builder_get_object (builder, "lockbox");
widget2 = (GtkWidget *)gtk_builder_get_object (builder, "lockbutton"); widget2 = (GtkWidget *)gtk_builder_get_object (builder, "lockbutton");
g_object_set_data (G_OBJECT (window), "lockbutton", widget2); g_object_set_data (G_OBJECT (window), "lockbutton", widget2);
@@ -2450,7 +2447,6 @@ G_GNUC_BEGIN_IGNORE_DEPRECATIONS
G_BINDING_SYNC_CREATE); G_BINDING_SYNC_CREATE);
gtk_lock_button_set_permission (GTK_LOCK_BUTTON (widget2), permission); gtk_lock_button_set_permission (GTK_LOCK_BUTTON (widget2), permission);
g_object_unref (permission); g_object_unref (permission);
G_GNUC_END_IGNORE_DEPRECATIONS
widget = (GtkWidget *)gtk_builder_get_object (builder, "iconview1"); widget = (GtkWidget *)gtk_builder_get_object (builder, "iconview1");
widget2 = (GtkWidget *)gtk_builder_get_object (builder, "increase_button"); widget2 = (GtkWidget *)gtk_builder_get_object (builder, "increase_button");
-10
View File
@@ -109,13 +109,3 @@ Other libraries, such as libadwaita, may provide replacements as well.
## gtk_show_uri is being replaced ## gtk_show_uri is being replaced
Instead of gtk_show_uri(), you should use GtkUriLauncher or GtkFileLauncher. Instead of gtk_show_uri(), you should use GtkUriLauncher or GtkFileLauncher.
## GtkStatusbar is going away
This is an oldfashioned widget that does not do all that much anymore, since
it no longer has a resize handle for the window.
## GtkLockButton and GtkVolumeButton are going away
These are very specialized widgets that should better live with the application
where they are used.
+1 -1
View File
@@ -37,7 +37,7 @@ main (int argc,
GtkApplication *app; GtkApplication *app;
int status; int status;
app = gtk_application_new ("org.gtk.example", G_APPLICATION_DEFAULT_FLAGS); app = gtk_application_new ("org.gtk.example", G_APPLICATION_FLAGS_NONE);
g_signal_connect (app, "activate", G_CALLBACK (activate), NULL); g_signal_connect (app, "activate", G_CALLBACK (activate), NULL);
status = g_application_run (G_APPLICATION (app), argc, argv); status = g_application_run (G_APPLICATION (app), argc, argv);
g_object_unref (app); g_object_unref (app);
-8
View File
@@ -213,7 +213,6 @@ typedef enum {
BROADWAY_REQUEST_RELEASE_TEXTURE, BROADWAY_REQUEST_RELEASE_TEXTURE,
BROADWAY_REQUEST_SET_NODES, BROADWAY_REQUEST_SET_NODES,
BROADWAY_REQUEST_ROUNDTRIP, BROADWAY_REQUEST_ROUNDTRIP,
BROADWAY_REQUEST_SET_MODAL_HINT,
} BroadwayRequestType; } BroadwayRequestType;
typedef struct { typedef struct {
@@ -294,12 +293,6 @@ typedef struct {
guint32 show_keyboard; guint32 show_keyboard;
} BroadwayRequestSetShowKeyboard; } BroadwayRequestSetShowKeyboard;
typedef struct {
BroadwayRequestBase base;
guint32 id;
gboolean modal_hint;
} BroadwayRequestSetModalHint;
typedef union { typedef union {
BroadwayRequestBase base; BroadwayRequestBase base;
BroadwayRequestNewSurface new_surface; BroadwayRequestNewSurface new_surface;
@@ -319,7 +312,6 @@ typedef union {
BroadwayRequestUploadTexture upload_texture; BroadwayRequestUploadTexture upload_texture;
BroadwayRequestReleaseTexture release_texture; BroadwayRequestReleaseTexture release_texture;
BroadwayRequestSetNodes set_nodes; BroadwayRequestSetNodes set_nodes;
BroadwayRequestSetModalHint set_modal_hint;
} BroadwayRequest; } BroadwayRequest;
typedef enum { typedef enum {
-36
View File
@@ -124,7 +124,6 @@ struct BroadwaySurface {
gboolean visible; gboolean visible;
gint32 transient_for; gint32 transient_for;
guint32 texture; guint32 texture;
gboolean modal_hint;
BroadwayNode *nodes; BroadwayNode *nodes;
GHashTable *node_lookup; GHashTable *node_lookup;
}; };
@@ -422,14 +421,6 @@ update_event_state (BroadwayServer *server,
{ {
surface->x = message->configure_notify.x; surface->x = message->configure_notify.x;
surface->y = message->configure_notify.y; surface->y = message->configure_notify.y;
if (server->focused_surface_id != message->configure_notify.id &&
server->pointer_grab_surface_id == -1 && surface->modal_hint)
{
broadway_server_surface_raise (server, message->configure_notify.id);
broadway_server_focus_surface (server, message->configure_notify.id);
broadway_server_flush (server);
}
} }
break; break;
case BROADWAY_EVENT_ROUNDTRIP_NOTIFY: case BROADWAY_EVENT_ROUNDTRIP_NOTIFY:
@@ -1577,7 +1568,6 @@ broadway_server_destroy_surface (BroadwayServer *server,
int id) int id)
{ {
BroadwaySurface *surface; BroadwaySurface *surface;
gint32 transient_for = -1;
if (server->mouse_in_surface_id == id) if (server->mouse_in_surface_id == id)
{ {
@@ -1595,24 +1585,11 @@ broadway_server_destroy_surface (BroadwayServer *server,
surface = broadway_server_lookup_surface (server, id); surface = broadway_server_lookup_surface (server, id);
if (surface != NULL) if (surface != NULL)
{ {
if (server->focused_surface_id == id)
transient_for = surface->transient_for;
server->surfaces = g_list_remove (server->surfaces, surface); server->surfaces = g_list_remove (server->surfaces, surface);
g_hash_table_remove (server->surface_id_hash, g_hash_table_remove (server->surface_id_hash,
GINT_TO_POINTER (id)); GINT_TO_POINTER (id));
broadway_surface_free (server, surface); broadway_surface_free (server, surface);
} }
if (transient_for != -1)
{
surface = broadway_server_lookup_surface (server, transient_for);
if (surface != NULL)
{
broadway_server_focus_surface (server, transient_for);
broadway_server_flush (server);
}
}
} }
gboolean gboolean
@@ -1733,19 +1710,6 @@ broadway_server_surface_set_transient_for (BroadwayServer *server,
} }
} }
void
broadway_server_surface_set_modal_hint (BroadwayServer *server,
int id, gboolean modal_hint)
{
BroadwaySurface *surface;
surface = broadway_server_lookup_surface (server, id);
if (surface == NULL)
return;
surface->modal_hint = modal_hint;
}
gboolean gboolean
broadway_server_has_client (BroadwayServer *server) broadway_server_has_client (BroadwayServer *server)
{ {
-3
View File
@@ -130,9 +130,6 @@ gboolean broadway_server_surface_move_resize (BroadwayServer *
int height); int height);
void broadway_server_focus_surface (BroadwayServer *server, void broadway_server_focus_surface (BroadwayServer *server,
int new_focused_surface); int new_focused_surface);
void broadway_server_surface_set_modal_hint (BroadwayServer *server,
int id,
gboolean modal_hint);
#endif /* __BROADWAY_SERVER__ */ #endif /* __BROADWAY_SERVER__ */
-5
View File
@@ -380,11 +380,6 @@ client_handle_request (BroadwayClient *client,
case BROADWAY_REQUEST_SET_SHOW_KEYBOARD: case BROADWAY_REQUEST_SET_SHOW_KEYBOARD:
broadway_server_set_show_keyboard (server, request->set_show_keyboard.show_keyboard); broadway_server_set_show_keyboard (server, request->set_show_keyboard.show_keyboard);
break; break;
case BROADWAY_REQUEST_SET_MODAL_HINT:
broadway_server_surface_set_modal_hint (server,
request->set_modal_hint.id,
request->set_modal_hint.modal_hint);
break;
default: default:
g_warning ("Unknown request of type %d", request->base.type); g_warning ("Unknown request of type %d", request->base.type);
} }
-12
View File
@@ -561,18 +561,6 @@ _gdk_broadway_server_surface_set_transient_for (GdkBroadwayServer *server,
BROADWAY_REQUEST_SET_TRANSIENT_FOR); BROADWAY_REQUEST_SET_TRANSIENT_FOR);
} }
void
_gdk_broadway_server_surface_set_modal_hint (GdkBroadwayServer *server,
int id, gboolean modal_hint)
{
BroadwayRequestSetModalHint msg;
msg.id = id;
msg.modal_hint = modal_hint;
gdk_broadway_server_send_message (server, msg,
BROADWAY_REQUEST_SET_MODAL_HINT);
}
static int static int
open_shared_memory (void) open_shared_memory (void)
{ {
-3
View File
@@ -78,8 +78,5 @@ gboolean _gdk_broadway_server_surface_move_resize (GdkBroadwaySe
int y, int y,
int width, int width,
int height); int height);
void _gdk_broadway_server_surface_set_modal_hint (GdkBroadwayServer *server,
int id,
gboolean modal_hint);
#endif /* __GDK_BROADWAY_SERVER__ */ #endif /* __GDK_BROADWAY_SERVER__ */
-25
View File
@@ -82,27 +82,6 @@ gdk_event_source_check (GSource *source)
return retval; return retval;
} }
static void
handle_focus_change (GdkEvent *event)
{
GdkEvent *focus_event;
gboolean focus_in = (gdk_event_get_event_type (event) == GDK_ENTER_NOTIFY);
if (gdk_crossing_event_get_detail (event) == GDK_NOTIFY_INFERIOR)
return;
if (!gdk_crossing_event_get_focus (event) )
return;
focus_event = gdk_focus_event_new (gdk_event_get_surface (event),
gdk_event_get_device (event),
focus_in);
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
gdk_display_put_event (gdk_event_get_display (event), focus_event);
G_GNUC_END_IGNORE_DEPRECATIONS
gdk_event_unref (focus_event);
}
void void
_gdk_broadway_events_got_input (GdkDisplay *display, _gdk_broadway_events_got_input (GdkDisplay *display,
BroadwayInputMsg *message) BroadwayInputMsg *message)
@@ -131,8 +110,6 @@ _gdk_broadway_events_got_input (GdkDisplay *display,
node = _gdk_event_queue_append (display, event); node = _gdk_event_queue_append (display, event);
_gdk_windowing_got_event (display, node, event, message->base.serial); _gdk_windowing_got_event (display, node, event, message->base.serial);
handle_focus_change (event);
} }
break; break;
case BROADWAY_EVENT_LEAVE: case BROADWAY_EVENT_LEAVE:
@@ -149,8 +126,6 @@ _gdk_broadway_events_got_input (GdkDisplay *display,
message->crossing.mode, message->crossing.mode,
GDK_NOTIFY_ANCESTOR); GDK_NOTIFY_ANCESTOR);
handle_focus_change (event);
node = _gdk_event_queue_append (display, event); node = _gdk_event_queue_append (display, event);
_gdk_windowing_got_event (display, node, event, message->base.serial); _gdk_windowing_got_event (display, node, event, message->base.serial);
} }
-21
View File
@@ -709,21 +709,6 @@ gdk_broadway_surface_set_transient_for (GdkSurface *surface,
_gdk_broadway_server_surface_set_transient_for (display->server, impl->id, impl->transient_for); _gdk_broadway_server_surface_set_transient_for (display->server, impl->id, impl->transient_for);
} }
static void
gdk_broadway_surface_set_modal_hint (GdkSurface *surface,
gboolean modal)
{
GdkBroadwayDisplay *display;
GdkBroadwaySurface *impl;
impl = GDK_BROADWAY_SURFACE (surface);
impl->modal_hint = modal;
display = GDK_BROADWAY_DISPLAY (gdk_surface_get_display (surface));
_gdk_broadway_server_surface_set_modal_hint (display->server, impl->id, impl->modal_hint);
}
static void static void
gdk_broadway_surface_get_geometry (GdkSurface *surface, gdk_broadway_surface_get_geometry (GdkSurface *surface,
int *x, int *x,
@@ -1448,8 +1433,6 @@ gdk_broadway_toplevel_set_property (GObject *object,
break; break;
case LAST_PROP + GDK_TOPLEVEL_PROP_MODAL: case LAST_PROP + GDK_TOPLEVEL_PROP_MODAL:
gdk_broadway_surface_set_modal_hint (surface, g_value_get_boolean (value));
g_object_notify_by_pspec (G_OBJECT (surface), pspec);
break; break;
case LAST_PROP + GDK_TOPLEVEL_PROP_ICON_LIST: case LAST_PROP + GDK_TOPLEVEL_PROP_ICON_LIST:
@@ -1496,10 +1479,6 @@ gdk_broadway_toplevel_get_property (GObject *object,
g_value_set_object (value, surface->transient_for); g_value_set_object (value, surface->transient_for);
break; break;
case LAST_PROP + GDK_TOPLEVEL_PROP_MODAL:
g_value_set_boolean (value, surface->modal_hint);
break;
case LAST_PROP + GDK_TOPLEVEL_PROP_ICON_LIST: case LAST_PROP + GDK_TOPLEVEL_PROP_ICON_LIST:
g_value_set_pointer (value, NULL); g_value_set_pointer (value, NULL);
break; break;
-1
View File
@@ -54,7 +54,6 @@ struct _GdkBroadwaySurface
gboolean dirty; gboolean dirty;
gboolean last_synced; gboolean last_synced;
gboolean modal_hint;
GdkGeometry geometry_hints; GdkGeometry geometry_hints;
GdkSurfaceHints geometry_hints_mask; GdkSurfaceHints geometry_hints_mask;
+5 -45
View File
@@ -26,7 +26,6 @@
#include "gdkcontentformats.h" #include "gdkcontentformats.h"
#include "gdkcontentserializer.h" #include "gdkcontentserializer.h"
#include "gdkcontentdeserializer.h" #include "gdkcontentdeserializer.h"
#include "gdkdebugprivate.h"
#include <gio/gio.h> #include <gio/gio.h>
@@ -214,8 +213,6 @@ file_transfer_portal_register_files (const char **files,
afd->len = g_strv_length ((char **)files); afd->len = g_strv_length ((char **)files);
afd->start = 0; afd->start = 0;
GDK_DEBUG (DND, "file transfer portal: registering %d files", afd->len);
g_variant_builder_init (&options, G_VARIANT_TYPE_VARDICT); g_variant_builder_init (&options, G_VARIANT_TYPE_VARDICT);
g_variant_builder_add (&options, "{sv}", "writable", g_variant_new_boolean (writable)); g_variant_builder_add (&options, "{sv}", "writable", g_variant_new_boolean (writable));
g_variant_builder_add (&options, "{sv}", "autostop", g_variant_new_boolean (TRUE)); g_variant_builder_add (&options, "{sv}", "autostop", g_variant_new_boolean (TRUE));
@@ -351,8 +348,9 @@ portal_ready (GObject *object,
static void static void
portal_file_serializer (GdkContentSerializer *serializer) portal_file_serializer (GdkContentSerializer *serializer)
{ {
GPtrArray *files; GFile *file;
const GValue *value; const GValue *value;
GPtrArray *files;
files = g_ptr_array_new_with_free_func (g_free); files = g_ptr_array_new_with_free_func (g_free);
@@ -360,24 +358,9 @@ portal_file_serializer (GdkContentSerializer *serializer)
if (G_VALUE_HOLDS (value, G_TYPE_FILE)) if (G_VALUE_HOLDS (value, G_TYPE_FILE))
{ {
GFile *file;
file = g_value_get_object (gdk_content_serializer_get_value (serializer)); file = g_value_get_object (gdk_content_serializer_get_value (serializer));
if (file)
if (file && g_file_peek_path (file)) g_ptr_array_add (files, g_file_get_path (file));
{
GDK_DEBUG (DND, "file transfer portal: Adding %s", g_file_peek_path (file));
g_ptr_array_add (files, g_file_get_path (file));
}
#ifdef G_ENABLE_DEBUG
else if (GDK_DEBUG_CHECK (DND))
{
char *uri = g_file_get_uri (file);
gdk_debug_message ("file transfer portal: %s has no path, dropping\n", uri);
g_free (uri);
}
#endif
g_ptr_array_add (files, NULL); g_ptr_array_add (files, NULL);
} }
else if (G_VALUE_HOLDS (value, GDK_TYPE_FILE_LIST)) else if (G_VALUE_HOLDS (value, GDK_TYPE_FILE_LIST))
@@ -385,21 +368,7 @@ portal_file_serializer (GdkContentSerializer *serializer)
GSList *l; GSList *l;
for (l = g_value_get_boxed (value); l; l = l->next) for (l = g_value_get_boxed (value); l; l = l->next)
{ g_ptr_array_add (files, g_file_get_path (l->data));
GFile *file = l->data;
if (file && g_file_peek_path (file))
{
GDK_DEBUG (DND, "file transfer portal: Adding %s", g_file_peek_path (file));
g_ptr_array_add (files, g_file_get_path (file));
}
else
{
char *uri = g_file_get_uri (file);
gdk_debug_message ("file transfer portal: %s has no path, dropping", uri);
g_free (uri);
}
}
g_ptr_array_add (files, NULL); g_ptr_array_add (files, NULL);
} }
@@ -426,15 +395,6 @@ portal_finish (GObject *object,
return; return;
} }
#ifdef G_ENABLE_DEBUG
if (GDK_DEBUG_CHECK (DND))
{
char *s = g_strjoinv (", ", files);
gdk_debug_message ("file transfer portal: Receiving files: %s", s);
g_free (s);
}
#endif
value = gdk_content_deserializer_get_value (deserializer); value = gdk_content_deserializer_get_value (deserializer);
if (G_VALUE_HOLDS (value, G_TYPE_FILE)) if (G_VALUE_HOLDS (value, G_TYPE_FILE))
{ {
+1 -3
View File
@@ -1149,7 +1149,7 @@ _gdk_display_get_next_serial (GdkDisplay *display)
* [method@Gtk.Window.set_auto_startup_notification] * [method@Gtk.Window.set_auto_startup_notification]
* is called to disable that feature. * is called to disable that feature.
* *
* Deprecated: 4.10: Using [method@Gdk.Toplevel.set_startup_id] is sufficient * Deprecated: 4.10. Using gdk_toplevel_set_startup_id() is sufficient.
*/ */
void void
gdk_display_notify_startup_complete (GdkDisplay *display, gdk_display_notify_startup_complete (GdkDisplay *display,
@@ -1168,8 +1168,6 @@ gdk_display_notify_startup_complete (GdkDisplay *display,
* if no ID has been defined. * if no ID has been defined.
* *
* Returns: (nullable): the startup notification ID for @display * Returns: (nullable): the startup notification ID for @display
*
* Deprecated: 4.10
*/ */
const char * const char *
gdk_display_get_startup_notification_id (GdkDisplay *display) gdk_display_get_startup_notification_id (GdkDisplay *display)
+1 -1
View File
@@ -86,7 +86,7 @@ GdkClipboard * gdk_display_get_primary_clipboard (GdkDisplay
GDK_DEPRECATED_IN_4_10_FOR(gdk_toplevel_set_startup_id) GDK_DEPRECATED_IN_4_10_FOR(gdk_toplevel_set_startup_id)
void gdk_display_notify_startup_complete (GdkDisplay *display, void gdk_display_notify_startup_complete (GdkDisplay *display,
const char *startup_id); const char *startup_id);
GDK_DEPRECATED_IN_4_10 GDK_AVAILABLE_IN_ALL
const char * gdk_display_get_startup_notification_id (GdkDisplay *display); const char * gdk_display_get_startup_notification_id (GdkDisplay *display);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
+12 -2
View File
@@ -1511,6 +1511,7 @@ gdk_button_event_get_button (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkKeyEvent */ /* {{{ GdkKeyEvent */
/** /**
@@ -1971,6 +1972,7 @@ gdk_key_event_get_match (GdkEvent *event,
} }
/* }}} */ /* }}} */
/* {{{ GdkTouchEvent */ /* {{{ GdkTouchEvent */
/** /**
@@ -2107,6 +2109,7 @@ gdk_touch_event_get_emulating_pointer (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkCrossingEvent */ /* {{{ GdkCrossingEvent */
/** /**
@@ -2250,6 +2253,7 @@ gdk_crossing_event_get_detail (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkDeleteEvent */ /* {{{ GdkDeleteEvent */
/** /**
@@ -2280,6 +2284,7 @@ gdk_delete_event_new (GdkSurface *surface)
} }
/* }}} */ /* }}} */
/* {{{ GdkFocusEvent */ /* {{{ GdkFocusEvent */
/** /**
@@ -2336,6 +2341,7 @@ gdk_focus_event_get_in (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkScrollEvent */ /* {{{ GdkScrollEvent */
/** /**
@@ -2594,6 +2600,7 @@ gdk_scroll_event_get_unit (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkTouchpadEvent */ /* {{{ GdkTouchpadEvent */
/** /**
@@ -2852,6 +2859,7 @@ gdk_touchpad_event_get_pinch_scale (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkPadEvent */ /* {{{ GdkPadEvent */
/** /**
@@ -3025,6 +3033,7 @@ gdk_pad_event_get_group_mode (GdkEvent *event,
} }
/* }}} */ /* }}} */
/* {{{ GdkMotionEvent */ /* {{{ GdkMotionEvent */
/** /**
@@ -3186,6 +3195,7 @@ gdk_event_get_history (GdkEvent *event,
} }
/* }}} */ /* }}} */
/* {{{ GdkProximityEvent */ /* {{{ GdkProximityEvent */
/** /**
@@ -3248,6 +3258,7 @@ gdk_proximity_event_new (GdkEventType type,
} }
/* }}} */ /* }}} */
/* {{{ GdkDNDEvent */ /* {{{ GdkDNDEvent */
/** /**
@@ -3353,6 +3364,7 @@ gdk_dnd_event_get_drop (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* {{{ GdkGrabBrokenEvent */ /* {{{ GdkGrabBrokenEvent */
/** /**
@@ -3430,5 +3442,3 @@ gdk_grab_broken_event_get_implicit (GdkEvent *event)
} }
/* }}} */ /* }}} */
/* vim:set foldmethod=marker expandtab: */
+2 -29
View File
@@ -501,18 +501,6 @@ gdk_gl_context_real_is_shared (GdkGLContext *self,
return TRUE; return TRUE;
} }
static gboolean
gdk_gl_context_real_is_current (GdkGLContext *self)
{
#ifdef HAVE_EGL
GdkGLContextPrivate *priv = gdk_gl_context_get_instance_private (self);
return priv->egl_context == eglGetCurrentContext ();
#else
return TRUE;
#endif
}
static gboolean static gboolean
gdk_gl_context_real_clear_current (GdkGLContext *context) gdk_gl_context_real_clear_current (GdkGLContext *context)
{ {
@@ -682,7 +670,6 @@ gdk_gl_context_class_init (GdkGLContextClass *klass)
klass->is_shared = gdk_gl_context_real_is_shared; klass->is_shared = gdk_gl_context_real_is_shared;
klass->make_current = gdk_gl_context_real_make_current; klass->make_current = gdk_gl_context_real_make_current;
klass->clear_current = gdk_gl_context_real_clear_current; klass->clear_current = gdk_gl_context_real_clear_current;
klass->is_current = gdk_gl_context_real_is_current;
klass->get_default_framebuffer = gdk_gl_context_real_get_default_framebuffer; klass->get_default_framebuffer = gdk_gl_context_real_get_default_framebuffer;
draw_context_class->begin_frame = gdk_gl_context_real_begin_frame; draw_context_class->begin_frame = gdk_gl_context_real_begin_frame;
@@ -1564,12 +1551,6 @@ gdk_gl_context_check_extensions (GdkGLContext *context)
priv->extensions_checked = TRUE; priv->extensions_checked = TRUE;
} }
static gboolean
gdk_gl_context_check_is_current (GdkGLContext *context)
{
return GDK_GL_CONTEXT_GET_CLASS (context)->is_current (context);
}
/** /**
* gdk_gl_context_make_current: * gdk_gl_context_make_current:
* @context: a `GdkGLContext` * @context: a `GdkGLContext`
@@ -1588,7 +1569,7 @@ gdk_gl_context_make_current (GdkGLContext *context)
masked_context = mask_context (context, surfaceless); masked_context = mask_context (context, surfaceless);
current = g_private_get (&thread_current_context); current = g_private_get (&thread_current_context);
if (current == masked_context && gdk_gl_context_check_is_current (context)) if (current == masked_context)
return; return;
/* we need to realize the GdkGLContext if it wasn't explicitly realized */ /* we need to realize the GdkGLContext if it wasn't explicitly realized */
@@ -1759,18 +1740,10 @@ GdkGLContext *
gdk_gl_context_get_current (void) gdk_gl_context_get_current (void)
{ {
MaskedContext *current; MaskedContext *current;
GdkGLContext *context;
current = g_private_get (&thread_current_context); current = g_private_get (&thread_current_context);
context = unmask_context (current);
if (context && !gdk_gl_context_check_is_current (context)) return unmask_context (current);
{
g_private_replace (&thread_current_context, NULL);
context = NULL;
}
return context;
} }
gboolean gboolean
-1
View File
@@ -83,7 +83,6 @@ struct _GdkGLContextClass
gboolean (* make_current) (GdkGLContext *context, gboolean (* make_current) (GdkGLContext *context,
gboolean surfaceless); gboolean surfaceless);
gboolean (* clear_current) (GdkGLContext *context); gboolean (* clear_current) (GdkGLContext *context);
gboolean (* is_current) (GdkGLContext *context);
cairo_region_t * (* get_damage) (GdkGLContext *context); cairo_region_t * (* get_damage) (GdkGLContext *context);
gboolean (* is_shared) (GdkGLContext *self, gboolean (* is_shared) (GdkGLContext *self,
+24 -78
View File
@@ -39,7 +39,6 @@ struct _GdkGLTexture {
GdkGLContext *context; GdkGLContext *context;
guint id; guint id;
GLsync sync;
GdkTexture *saved; GdkTexture *saved;
@@ -54,8 +53,10 @@ struct _GdkGLTextureClass {
G_DEFINE_TYPE (GdkGLTexture, gdk_gl_texture, GDK_TYPE_TEXTURE) G_DEFINE_TYPE (GdkGLTexture, gdk_gl_texture, GDK_TYPE_TEXTURE)
static void static void
drop_gl_resources (GdkGLTexture *self) gdk_gl_texture_dispose (GObject *object)
{ {
GdkGLTexture *self = GDK_GL_TEXTURE (object);
if (self->destroy) if (self->destroy)
{ {
self->destroy (self->data); self->destroy (self->data);
@@ -65,30 +66,17 @@ drop_gl_resources (GdkGLTexture *self)
g_clear_object (&self->context); g_clear_object (&self->context);
self->id = 0; self->id = 0;
self->sync = NULL;
}
static void
gdk_gl_texture_dispose (GObject *object)
{
GdkGLTexture *self = GDK_GL_TEXTURE (object);
drop_gl_resources (self);
g_clear_object (&self->saved); g_clear_object (&self->saved);
G_OBJECT_CLASS (gdk_gl_texture_parent_class)->dispose (object); G_OBJECT_CLASS (gdk_gl_texture_parent_class)->dispose (object);
} }
typedef void (* GLFunc) (GdkGLTexture *self,
GdkGLContext *context,
gpointer data);
typedef struct _InvokeData typedef struct _InvokeData
{ {
GdkGLTexture *self; GdkGLTexture *self;
volatile int spinlock; volatile int spinlock;
GLFunc func; GFunc func;
gpointer data; gpointer data;
} InvokeData; } InvokeData;
@@ -101,13 +89,9 @@ gdk_gl_texture_invoke_callback (gpointer data)
context = gdk_display_get_gl_context (gdk_gl_context_get_display (invoke->self->context)); context = gdk_display_get_gl_context (gdk_gl_context_get_display (invoke->self->context));
gdk_gl_context_make_current (context); gdk_gl_context_make_current (context);
if (invoke->self->sync && context != invoke->self->context)
glWaitSync (invoke->self->sync, 0, GL_TIMEOUT_IGNORED);
glBindTexture (GL_TEXTURE_2D, invoke->self->id); glBindTexture (GL_TEXTURE_2D, invoke->self->id);
invoke->func (invoke->self, context, invoke->data); invoke->func (invoke->self, invoke->data);
g_atomic_int_set (&invoke->spinlock, 1); g_atomic_int_set (&invoke->spinlock, 1);
@@ -116,7 +100,7 @@ gdk_gl_texture_invoke_callback (gpointer data)
static void static void
gdk_gl_texture_run (GdkGLTexture *self, gdk_gl_texture_run (GdkGLTexture *self,
GLFunc func, GFunc func,
gpointer data) gpointer data)
{ {
InvokeData invoke = { self, 0, func, data }; InvokeData invoke = { self, 0, func, data };
@@ -161,19 +145,19 @@ gdk_gl_texture_find_format (gboolean use_es,
} }
static inline void static inline void
gdk_gl_texture_do_download (GdkGLTexture *self, gdk_gl_texture_do_download (gpointer texture_,
GdkGLContext *context, gpointer download_)
gpointer download_)
{ {
GdkTexture *texture = GDK_TEXTURE (self);
gsize expected_stride; gsize expected_stride;
GdkGLTexture *self = texture_;
GdkTexture *texture = texture_;
Download *download = download_; Download *download = download_;
GLenum gl_internal_format, gl_format, gl_type; GLenum gl_internal_format, gl_format, gl_type;
expected_stride = texture->width * gdk_memory_format_bytes_per_pixel (download->format); expected_stride = texture->width * gdk_memory_format_bytes_per_pixel (download->format);
if (download->stride == expected_stride && if (download->stride == expected_stride &&
!gdk_gl_context_get_use_es (context) && !gdk_gl_context_get_use_es (self->context) &&
gdk_memory_format_gl_format (download->format, TRUE, &gl_internal_format, &gl_format, &gl_type)) gdk_memory_format_gl_format (download->format, TRUE, &gl_internal_format, &gl_format, &gl_type))
{ {
glGetTexImage (GL_TEXTURE_2D, glGetTexImage (GL_TEXTURE_2D,
@@ -191,11 +175,11 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
glGenFramebuffers (1, &fbo); glGenFramebuffers (1, &fbo);
glBindFramebuffer (GL_FRAMEBUFFER, fbo); glBindFramebuffer (GL_FRAMEBUFFER, fbo);
glFramebufferTexture2D (GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, self->id, 0); glFramebufferTexture2D (GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, self->id, 0);
if (gdk_gl_context_check_version (context, 4, 3, 3, 1)) if (gdk_gl_context_check_version (self->context, 4, 3, 3, 1))
{ {
glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_FORMAT, &gl_read_format); glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_FORMAT, &gl_read_format);
glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_TYPE, &gl_read_type); glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_TYPE, &gl_read_type);
if (!gdk_gl_texture_find_format (gdk_gl_context_get_use_es (context), gl_read_format, gl_read_type, &actual_format)) if (!gdk_gl_texture_find_format (gdk_gl_context_get_use_es (self->context), gl_read_format, gl_read_type, &actual_format))
actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED; /* pray */ actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED; /* pray */
} }
else else
@@ -209,7 +193,7 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
(download->stride == expected_stride)) (download->stride == expected_stride))
{ {
glReadPixels (0, 0, glReadPixels (0, 0,
texture->width, texture->height, texture->width, texture->height,
gl_read_format, gl_read_format,
gl_read_type, gl_read_type,
download->data); download->data);
@@ -220,7 +204,7 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
guchar *pixels = g_malloc_n (texture->width * actual_bpp, texture->height); guchar *pixels = g_malloc_n (texture->width * actual_bpp, texture->height);
glReadPixels (0, 0, glReadPixels (0, 0,
texture->width, texture->height, texture->width, texture->height,
gl_read_format, gl_read_format,
gl_read_type, gl_read_type,
pixels); pixels);
@@ -313,7 +297,15 @@ gdk_gl_texture_release (GdkGLTexture *self)
self->saved = GDK_TEXTURE (gdk_memory_texture_from_texture (texture, self->saved = GDK_TEXTURE (gdk_memory_texture_from_texture (texture,
gdk_texture_get_format (texture))); gdk_texture_get_format (texture)));
drop_gl_resources (self); if (self->destroy)
{
self->destroy (self->data);
self->destroy = NULL;
self->data = NULL;
}
g_clear_object (&self->context);
self->id = 0;
} }
static void static void
@@ -446,46 +438,6 @@ gdk_gl_texture_new (GdkGLContext *context,
int height, int height,
GDestroyNotify destroy, GDestroyNotify destroy,
gpointer data) gpointer data)
{
g_return_val_if_fail (GDK_IS_GL_CONTEXT (context), NULL);
g_return_val_if_fail (id != 0, NULL);
g_return_val_if_fail (width > 0, NULL);
g_return_val_if_fail (height > 0, NULL);
return gdk_gl_texture_new_with_sync (context, id, NULL, width, height, destroy, data);
}
/*< private >
* gdk_gl_texture_new_with_sync:
* @context: a `GdkGLContext`
* @id: the ID of a texture that was created with @context
* @sync: (nullable): an optional GLsync object
* @width: the nominal width of the texture
* @height: the nominal height of the texture
* @destroy: a destroy notify that will be called when the GL resources
* are released
* @data: data that gets passed to @destroy
*
* Creates a new texture for an existing GL texture.
*
* If @sync is given, consumers of the texture are required to wait on
* it before attempting to use the GL texture.
*
* The GL texture and the sync object must stay alive unmodified until
* @destroy is called, which will happen when the GdkTexture object is
* finalized, or due to an explicit call of [method@Gdk.GLTexture.release].
*
* Return value: (transfer full) (type GdkGLTexture): A newly-created
* `GdkTexture`
*/
GdkTexture *
gdk_gl_texture_new_with_sync (GdkGLContext *context,
guint id,
gpointer sync,
int width,
int height,
GDestroyNotify destroy,
gpointer data)
{ {
GdkGLTexture *self; GdkGLTexture *self;
@@ -501,7 +453,6 @@ gdk_gl_texture_new_with_sync (GdkGLContext *context,
self->context = g_object_ref (context); self->context = g_object_ref (context);
self->id = id; self->id = id;
self->sync = sync;
self->destroy = destroy; self->destroy = destroy;
self->data = data; self->data = data;
@@ -510,8 +461,3 @@ gdk_gl_texture_new_with_sync (GdkGLContext *context,
return GDK_TEXTURE (self); return GDK_TEXTURE (self);
} }
gpointer
gdk_gl_texture_get_sync (GdkGLTexture *self)
{
return self->sync;
}
-10
View File
@@ -9,16 +9,6 @@ G_BEGIN_DECLS
GdkGLContext * gdk_gl_texture_get_context (GdkGLTexture *self); GdkGLContext * gdk_gl_texture_get_context (GdkGLTexture *self);
guint gdk_gl_texture_get_id (GdkGLTexture *self); guint gdk_gl_texture_get_id (GdkGLTexture *self);
gpointer gdk_gl_texture_get_sync (GdkGLTexture *self);
GDK_AVAILABLE_IN_4_10
GdkTexture * gdk_gl_texture_new_with_sync (GdkGLContext *context,
guint id,
gpointer sync,
int width,
int height,
GDestroyNotify destroy,
gpointer data);
G_END_DECLS G_END_DECLS
-52
View File
@@ -39,7 +39,6 @@
enum { enum {
PROP_0, PROP_0,
PROP_DESCRIPTION,
PROP_DISPLAY, PROP_DISPLAY,
PROP_MANUFACTURER, PROP_MANUFACTURER,
PROP_MODEL, PROP_MODEL,
@@ -82,10 +81,6 @@ gdk_monitor_get_property (GObject *object,
switch (prop_id) switch (prop_id)
{ {
case PROP_DESCRIPTION:
g_value_set_string (value, monitor->description);
break;
case PROP_DISPLAY: case PROP_DISPLAY:
g_value_set_object (value, monitor->display); g_value_set_object (value, monitor->display);
break; break;
@@ -159,7 +154,6 @@ gdk_monitor_finalize (GObject *object)
{ {
GdkMonitor *monitor = GDK_MONITOR (object); GdkMonitor *monitor = GDK_MONITOR (object);
g_free (monitor->description);
g_free (monitor->connector); g_free (monitor->connector);
g_free (monitor->manufacturer); g_free (monitor->manufacturer);
g_free (monitor->model); g_free (monitor->model);
@@ -176,18 +170,6 @@ gdk_monitor_class_init (GdkMonitorClass *class)
object_class->get_property = gdk_monitor_get_property; object_class->get_property = gdk_monitor_get_property;
object_class->set_property = gdk_monitor_set_property; object_class->set_property = gdk_monitor_set_property;
/**
* GdkMonitor:description: (attributes org.gtk.Property.get=gdk_monitor_get_description)
*
* A short description of the monitor, meant for display to the user.
*
* Since: 4.10
*/
props[PROP_DESCRIPTION] =
g_param_spec_string ("description", NULL, NULL,
NULL,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
/** /**
* GdkMonitor:display: (attributes org.gtk.Property.get=gdk_monitor_get_display) * GdkMonitor:display: (attributes org.gtk.Property.get=gdk_monitor_get_display)
* *
@@ -395,10 +377,6 @@ gdk_monitor_get_height_mm (GdkMonitor *monitor)
* *
* Gets the name of the monitor's connector, if available. * Gets the name of the monitor's connector, if available.
* *
* These are strings such as "eDP-1", or "HDMI-2". They depend
* on software and hardware configuration, and should not be
* relied on as stable identifiers of a specific monitor.
*
* Returns: (transfer none) (nullable): the name of the connector * Returns: (transfer none) (nullable): the name of the connector
*/ */
const char * const char *
@@ -641,33 +619,3 @@ gdk_monitor_is_valid (GdkMonitor *monitor)
return monitor->valid; return monitor->valid;
} }
/**
* gdk_monitor_get_description: (attributes org.gtk.Method.get_property=description)
* @monitor: a `GdkMonitor`
*
* Gets a string describing the monitor, if available.
*
* This can be used to identify a monitor in the UI.
*
* Returns: (transfer none) (nullable): the monitor description
*
* Since: 4.10
*/
const char *
gdk_monitor_get_description (GdkMonitor *monitor)
{
g_return_val_if_fail (GDK_IS_MONITOR (monitor), NULL);
return monitor->description;
}
void
gdk_monitor_set_description (GdkMonitor *monitor,
const char *description)
{
g_free (monitor->description);
monitor->description = g_strdup (description);
g_object_notify_by_pspec (G_OBJECT (monitor), props[PROP_DESCRIPTION]);
}
-2
View File
@@ -86,8 +86,6 @@ GDK_AVAILABLE_IN_ALL
GdkSubpixelLayout gdk_monitor_get_subpixel_layout (GdkMonitor *monitor); GdkSubpixelLayout gdk_monitor_get_subpixel_layout (GdkMonitor *monitor);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
gboolean gdk_monitor_is_valid (GdkMonitor *monitor); gboolean gdk_monitor_is_valid (GdkMonitor *monitor);
GDK_AVAILABLE_IN_4_10
const char * gdk_monitor_get_description (GdkMonitor *monitor);
G_DEFINE_AUTOPTR_CLEANUP_FUNC(GdkMonitor, g_object_unref) G_DEFINE_AUTOPTR_CLEANUP_FUNC(GdkMonitor, g_object_unref)
-3
View File
@@ -37,7 +37,6 @@ struct _GdkMonitor {
char *manufacturer; char *manufacturer;
char *model; char *model;
char *connector; char *connector;
char *description;
GdkRectangle geometry; GdkRectangle geometry;
int width_mm; int width_mm;
int height_mm; int height_mm;
@@ -71,8 +70,6 @@ void gdk_monitor_set_refresh_rate (GdkMonitor *monitor,
void gdk_monitor_set_subpixel_layout (GdkMonitor *monitor, void gdk_monitor_set_subpixel_layout (GdkMonitor *monitor,
GdkSubpixelLayout subpixel); GdkSubpixelLayout subpixel);
void gdk_monitor_invalidate (GdkMonitor *monitor); void gdk_monitor_invalidate (GdkMonitor *monitor);
void gdk_monitor_set_description (GdkMonitor *monitor,
const char *description);
G_END_DECLS G_END_DECLS
+4 -60
View File
@@ -27,12 +27,10 @@
#import "GdkMacosView.h" #import "GdkMacosView.h"
#import "GdkMacosWindow.h" #import "GdkMacosWindow.h"
#include "gdkmacosclipboard-private.h"
#include "gdkmacosdisplay-private.h" #include "gdkmacosdisplay-private.h"
#include "gdkmacosdrag-private.h"
#include "gdkmacosdrop-private.h" #include "gdkmacosdrop-private.h"
#include "gdkmacoseventsource-private.h"
#include "gdkmacosmonitor-private.h" #include "gdkmacosmonitor-private.h"
#include "gdkmacospasteboard-private.h"
#include "gdkmacossurface-private.h" #include "gdkmacossurface-private.h"
#include "gdkmacospopupsurface-private.h" #include "gdkmacospopupsurface-private.h"
#include "gdkmacostoplevelsurface-private.h" #include "gdkmacostoplevelsurface-private.h"
@@ -146,7 +144,7 @@ typedef NSString *CALayerContentsGravity;
* *
* TODO: Can we improve grab breaking to fix this? * TODO: Can we improve grab breaking to fix this?
*/ */
_gdk_macos_display_send_event ([self gdkDisplay], event); _gdk_macos_display_send_button_event ([self gdkDisplay], event);
_gdk_macos_display_break_all_grabs (GDK_MACOS_DISPLAY (display), time); _gdk_macos_display_break_all_grabs (GDK_MACOS_DISPLAY (display), time);
@@ -248,7 +246,7 @@ typedef NSString *CALayerContentsGravity;
[view release]; [view release];
/* TODO: We might want to make this more extensible at some point */ /* TODO: We might want to make this more extensible at some point */
_gdk_macos_pasteboard_register_drag_types (self); _gdk_macos_clipboard_register_drag_types (self);
return self; return self;
} }
@@ -670,61 +668,7 @@ typedef NSString *CALayerContentsGravity;
} }
// NSDraggingSource protocol // NSDraggingSource protocol
// ...
- (NSDragOperation)draggingSession:(NSDraggingSession *)session sourceOperationMaskForDraggingContext:(NSDraggingContext)context
{
NSInteger sequence_number = [session draggingSequenceNumber];
GdkDisplay *display = gdk_surface_get_display (GDK_SURFACE (gdk_surface));
GdkDrag *drag = _gdk_macos_display_find_drag (GDK_MACOS_DISPLAY (display), sequence_number);
GdkModifierType state = _gdk_macos_display_get_current_keyboard_modifiers (GDK_MACOS_DISPLAY (display));
_gdk_macos_drag_set_actions (GDK_MACOS_DRAG (drag), state);
return _gdk_macos_drag_operation (GDK_MACOS_DRAG (drag));
}
- (void)draggingSession:(NSDraggingSession *)session willBeginAtPoint:(NSPoint)screenPoint
{
NSInteger sequence_number = [session draggingSequenceNumber];
GdkDisplay *display = gdk_surface_get_display (GDK_SURFACE (gdk_surface));
GdkDrag *drag = _gdk_macos_display_find_drag (GDK_MACOS_DISPLAY (display), sequence_number);
int x, y;
_gdk_macos_display_from_display_coords (GDK_MACOS_DISPLAY (display), screenPoint.x, screenPoint.y, &x, &y);
_gdk_macos_drag_set_start_position (GDK_MACOS_DRAG (drag), x, y);
_gdk_macos_drag_surface_move (GDK_MACOS_DRAG (drag), x, y);
}
- (void)draggingSession:(NSDraggingSession *)session movedToPoint:(NSPoint)screenPoint
{
NSInteger sequence_number = [session draggingSequenceNumber];
GdkMacosDisplay *display = GDK_MACOS_DISPLAY (gdk_surface_get_display (GDK_SURFACE (gdk_surface)));
GdkDrag *drag = _gdk_macos_display_find_drag (GDK_MACOS_DISPLAY (display), sequence_number);
int x, y;
_gdk_macos_display_send_event (display, [NSApp currentEvent]);
_gdk_macos_display_from_display_coords (display, screenPoint.x, screenPoint.y, &x, &y);
_gdk_macos_drag_surface_move (GDK_MACOS_DRAG (drag), x, y);
}
- (void)draggingSession:(NSDraggingSession *)session endedAtPoint:(NSPoint)screenPoint operation:(NSDragOperation)operation
{
NSInteger sequence_number = [session draggingSequenceNumber];
GdkMacosDisplay *display = GDK_MACOS_DISPLAY (gdk_surface_get_display (GDK_SURFACE (gdk_surface)));
GdkDrag *drag = _gdk_macos_display_find_drag (display, sequence_number);
_gdk_macos_display_send_event (display, [NSApp currentEvent]);
gdk_drag_set_selected_action (drag, _gdk_macos_drag_ns_operation_to_action (operation));
if (gdk_drag_get_selected_action (drag) != 0)
g_signal_emit_by_name (drag, "drop-performed");
else
gdk_drag_cancel (drag, GDK_DRAG_CANCEL_NO_TARGET);
_gdk_macos_display_set_drag (display, [session draggingSequenceNumber], NULL);
}
// end // end
-(void)setStyleMask:(NSWindowStyleMask)styleMask -(void)setStyleMask:(NSWindowStyleMask)styleMask
+1 -1
View File
@@ -32,7 +32,7 @@
#define GDK_IS_MACOS_WINDOW(obj) ([obj isKindOfClass:[GdkMacosWindow class]]) #define GDK_IS_MACOS_WINDOW(obj) ([obj isKindOfClass:[GdkMacosWindow class]])
@interface GdkMacosWindow : NSWindow <NSDraggingSource, NSDraggingDestination> { @interface GdkMacosWindow : NSWindow {
GdkMacosSurface *gdk_surface; GdkMacosSurface *gdk_surface;
BOOL inMove; BOOL inMove;
+24 -1
View File
@@ -24,7 +24,6 @@
#include "gdkclipboardprivate.h" #include "gdkclipboardprivate.h"
#include "gdkmacosdisplay-private.h" #include "gdkmacosdisplay-private.h"
#include "gdkmacospasteboard-private.h"
G_BEGIN_DECLS G_BEGIN_DECLS
@@ -42,6 +41,30 @@ NSPasteboardType _gdk_macos_clipboard_to_ns_type (const char
NSPasteboardType *alternate); NSPasteboardType *alternate);
const char *_gdk_macos_clipboard_from_ns_type (NSPasteboardType ns_type); const char *_gdk_macos_clipboard_from_ns_type (NSPasteboardType ns_type);
void _gdk_macos_clipboard_register_drag_types (NSWindow *window); void _gdk_macos_clipboard_register_drag_types (NSWindow *window);
GdkContentFormats *_gdk_macos_pasteboard_load_formats (NSPasteboard *pasteboard);
void _gdk_macos_pasteboard_read_async (GObject *object,
NSPasteboard *pasteboard,
GdkContentFormats *formats,
int io_priority,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
GInputStream *_gdk_macos_pasteboard_read_finish (GObject *object,
GAsyncResult *result,
const char **out_mime_type,
GError **error);
@interface GdkMacosClipboardDataProvider : NSObject <NSPasteboardItemDataProvider>
{
GCancellable *cancellable;
GdkClipboard *clipboard;
char **mimeTypes;
}
-(id)initClipboard:(GdkClipboard *)gdkClipboard mimetypes:(const char * const *)mime_types;
-(NSArray<NSPasteboardType> *)types;
@end
G_END_DECLS G_END_DECLS
+488 -15
View File
@@ -22,7 +22,6 @@
#include <glib/gi18n.h> #include <glib/gi18n.h>
#include "gdkmacosclipboard-private.h" #include "gdkmacosclipboard-private.h"
#include "gdkmacospasteboard-private.h"
#include "gdkmacosutils-private.h" #include "gdkmacosutils-private.h"
#include "gdkprivate.h" #include "gdkprivate.h"
@@ -33,8 +32,163 @@ struct _GdkMacosClipboard
NSInteger last_change_count; NSInteger last_change_count;
}; };
typedef struct
{
GMemoryOutputStream *stream;
NSPasteboardItem *item;
NSPasteboardType type;
GMainContext *main_context;
guint done : 1;
} WriteRequest;
enum {
TYPE_STRING,
TYPE_PBOARD,
TYPE_URL,
TYPE_FILE_URL,
TYPE_COLOR,
TYPE_TIFF,
TYPE_PNG,
TYPE_LAST
};
#define PTYPE(k) (get_pasteboard_type(TYPE_##k))
static NSPasteboardType pasteboard_types[TYPE_LAST];
G_DEFINE_TYPE (GdkMacosClipboard, _gdk_macos_clipboard, GDK_TYPE_CLIPBOARD) G_DEFINE_TYPE (GdkMacosClipboard, _gdk_macos_clipboard, GDK_TYPE_CLIPBOARD)
static NSPasteboardType
get_pasteboard_type (int type)
{
static gsize initialized = FALSE;
g_assert (type >= 0);
g_assert (type < TYPE_LAST);
if (g_once_init_enter (&initialized))
{
pasteboard_types[TYPE_PNG] = NSPasteboardTypePNG;
pasteboard_types[TYPE_STRING] = NSPasteboardTypeString;
pasteboard_types[TYPE_TIFF] = NSPasteboardTypeTIFF;
pasteboard_types[TYPE_COLOR] = NSPasteboardTypeColor;
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
pasteboard_types[TYPE_PBOARD] = NSStringPboardType;
G_GNUC_END_IGNORE_DEPRECATIONS
#ifdef AVAILABLE_MAC_OS_X_VERSION_10_13_AND_LATER
pasteboard_types[TYPE_URL] = NSPasteboardTypeURL;
pasteboard_types[TYPE_FILE_URL] = NSPasteboardTypeFileURL;
#else
pasteboard_types[TYPE_URL] = [[NSString alloc] initWithUTF8String:"public.url"];
pasteboard_types[TYPE_FILE_URL] = [[NSString alloc] initWithUTF8String:"public.file-url"];
#endif
g_once_init_leave (&initialized, TRUE);
}
return pasteboard_types[type];
}
static void
write_request_free (WriteRequest *wr)
{
g_clear_pointer (&wr->main_context, g_main_context_unref);
g_clear_object (&wr->stream);
[wr->item release];
g_slice_free (WriteRequest, wr);
}
const char *
_gdk_macos_clipboard_from_ns_type (NSPasteboardType type)
{
G_GNUC_BEGIN_IGNORE_DEPRECATIONS;
if ([type isEqualToString:PTYPE(STRING)] ||
[type isEqualToString:PTYPE(PBOARD)])
return g_intern_string ("text/plain;charset=utf-8");
else if ([type isEqualToString:PTYPE(URL)] ||
[type isEqualToString:PTYPE(FILE_URL)])
return g_intern_string ("text/uri-list");
else if ([type isEqualToString:PTYPE(COLOR)])
return g_intern_string ("application/x-color");
else if ([type isEqualToString:PTYPE(TIFF)])
return g_intern_string ("image/tiff");
else if ([type isEqualToString:PTYPE(PNG)])
return g_intern_string ("image/png");
G_GNUC_END_IGNORE_DEPRECATIONS;
return NULL;
}
NSPasteboardType
_gdk_macos_clipboard_to_ns_type (const char *mime_type,
NSPasteboardType *alternate)
{
if (alternate)
*alternate = NULL;
if (g_strcmp0 (mime_type, "text/plain;charset=utf-8") == 0)
{
return PTYPE(STRING);
}
else if (g_strcmp0 (mime_type, "text/uri-list") == 0)
{
if (alternate)
*alternate = PTYPE(URL);
return PTYPE(FILE_URL);
}
else if (g_strcmp0 (mime_type, "application/x-color") == 0)
{
return PTYPE(COLOR);
}
else if (g_strcmp0 (mime_type, "image/tiff") == 0)
{
return PTYPE(TIFF);
}
else if (g_strcmp0 (mime_type, "image/png") == 0)
{
return PTYPE(PNG);
}
return nil;
}
static void
populate_content_formats (GdkContentFormatsBuilder *builder,
NSPasteboardType type)
{
const char *mime_type;
g_return_if_fail (builder != NULL);
g_return_if_fail (type != NULL);
mime_type = _gdk_macos_clipboard_from_ns_type (type);
if (mime_type != NULL)
gdk_content_formats_builder_add_mime_type (builder, mime_type);
}
static GdkContentFormats *
load_offer_formats (NSPasteboard *pasteboard)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
GdkContentFormatsBuilder *builder;
GdkContentFormats *formats;
builder = gdk_content_formats_builder_new ();
for (NSPasteboardType type in [pasteboard types])
populate_content_formats (builder, type);
formats = gdk_content_formats_builder_free_to_formats (builder);
GDK_END_MACOS_ALLOC_POOL;
return g_steal_pointer (&formats);
}
static void static void
_gdk_macos_clipboard_load_contents (GdkMacosClipboard *self) _gdk_macos_clipboard_load_contents (GdkMacosClipboard *self)
{ {
@@ -45,13 +199,22 @@ _gdk_macos_clipboard_load_contents (GdkMacosClipboard *self)
change_count = [self->pasteboard changeCount]; change_count = [self->pasteboard changeCount];
formats = _gdk_macos_pasteboard_load_formats (self->pasteboard); formats = load_offer_formats (self->pasteboard);
gdk_clipboard_claim_remote (GDK_CLIPBOARD (self), formats); gdk_clipboard_claim_remote (GDK_CLIPBOARD (self), formats);
gdk_content_formats_unref (formats); gdk_content_formats_unref (formats);
self->last_change_count = change_count; self->last_change_count = change_count;
} }
static GInputStream *
create_stream_from_nsdata (NSData *data)
{
const guint8 *bytes = [data bytes];
gsize len = [data length];
return g_memory_input_stream_new_from_data (g_memdup2 (bytes, len), len, g_free);
}
static void static void
_gdk_macos_clipboard_read_async (GdkClipboard *clipboard, _gdk_macos_clipboard_read_async (GdkClipboard *clipboard,
GdkContentFormats *formats, GdkContentFormats *formats,
@@ -82,26 +245,34 @@ static void
_gdk_macos_clipboard_send_to_pasteboard (GdkMacosClipboard *self, _gdk_macos_clipboard_send_to_pasteboard (GdkMacosClipboard *self,
GdkContentProvider *content) GdkContentProvider *content)
{ {
GdkMacosPasteboardItem *item;
NSArray<NSPasteboardItem *> *items;
g_assert (GDK_IS_MACOS_CLIPBOARD (self));
g_assert (GDK_IS_CONTENT_PROVIDER (content));
if (self->pasteboard == NULL)
return;
GDK_BEGIN_MACOS_ALLOC_POOL; GDK_BEGIN_MACOS_ALLOC_POOL;
item = [[GdkMacosPasteboardItem alloc] initForClipboard:GDK_CLIPBOARD (self) withContentProvider:content]; GdkMacosClipboardDataProvider *dataProvider;
items = [NSArray arrayWithObject:item]; GdkContentFormats *serializable;
NSPasteboardItem *item;
const char * const *mime_types;
gsize n_mime_types;
g_return_if_fail (GDK_IS_MACOS_CLIPBOARD (self));
g_return_if_fail (GDK_IS_CONTENT_PROVIDER (content));
serializable = gdk_content_provider_ref_storable_formats (content);
serializable = gdk_content_formats_union_serialize_mime_types (serializable);
mime_types = gdk_content_formats_get_mime_types (serializable, &n_mime_types);
dataProvider = [[GdkMacosClipboardDataProvider alloc] initClipboard:GDK_CLIPBOARD (self)
mimetypes:mime_types];
item = [[NSPasteboardItem alloc] init];
[item setDataProvider:dataProvider forTypes:[dataProvider types]];
[self->pasteboard clearContents]; [self->pasteboard clearContents];
if ([self->pasteboard writeObjects:items] == NO) if ([self->pasteboard writeObjects:[NSArray arrayWithObject:item]] == NO)
g_warning ("Failed to send clipboard to pasteboard"); g_warning ("Failed to write object to pasteboard");
self->last_change_count = [self->pasteboard changeCount]; self->last_change_count = [self->pasteboard changeCount];
g_clear_pointer (&serializable, gdk_content_formats_unref);
GDK_END_MACOS_ALLOC_POOL; GDK_END_MACOS_ALLOC_POOL;
} }
@@ -194,3 +365,305 @@ _gdk_macos_clipboard_check_externally_modified (GdkMacosClipboard *self)
if ([self->pasteboard changeCount] != self->last_change_count) if ([self->pasteboard changeCount] != self->last_change_count)
_gdk_macos_clipboard_load_contents (self); _gdk_macos_clipboard_load_contents (self);
} }
@implementation GdkMacosClipboardDataProvider
-(id)initClipboard:(GdkClipboard *)gdkClipboard mimetypes:(const char * const *)mime_types;
{
[super init];
self->mimeTypes = g_strdupv ((char **)mime_types);
self->clipboard = g_object_ref (gdkClipboard);
return self;
}
-(void)dealloc
{
g_cancellable_cancel (self->cancellable);
g_clear_pointer (&self->mimeTypes, g_strfreev);
g_clear_object (&self->clipboard);
g_clear_object (&self->cancellable);
[super dealloc];
}
-(void)pasteboardFinishedWithDataProvider:(NSPasteboard *)pasteboard
{
g_clear_object (&self->clipboard);
}
-(NSArray<NSPasteboardType> *)types
{
NSMutableArray *ret = [[NSMutableArray alloc] init];
for (guint i = 0; self->mimeTypes[i]; i++)
{
const char *mime_type = self->mimeTypes[i];
NSPasteboardType type;
NSPasteboardType alternate = nil;
if ((type = _gdk_macos_clipboard_to_ns_type (mime_type, &alternate)))
{
[ret addObject:type];
if (alternate)
[ret addObject:alternate];
}
}
return g_steal_pointer (&ret);
}
static void
on_data_ready_cb (GObject *object,
GAsyncResult *result,
gpointer user_data)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
GdkClipboard *clipboard = (GdkClipboard *)object;
WriteRequest *wr = user_data;
GError *error = NULL;
NSData *data = nil;
g_assert (GDK_IS_CLIPBOARD (clipboard));
g_assert (G_IS_ASYNC_RESULT (result));
g_assert (wr != NULL);
g_assert (G_IS_MEMORY_OUTPUT_STREAM (wr->stream));
g_assert ([wr->item isKindOfClass:[NSPasteboardItem class]]);
if (gdk_clipboard_write_finish (clipboard, result, &error))
{
gsize size;
gpointer bytes;
g_output_stream_close (G_OUTPUT_STREAM (wr->stream), NULL, NULL);
size = g_memory_output_stream_get_data_size (wr->stream);
bytes = g_memory_output_stream_steal_data (wr->stream);
data = [[NSData alloc] initWithBytesNoCopy:bytes
length:size
deallocator:^(void *alloc, NSUInteger length) { g_free (alloc); }];
}
else
{
g_warning ("Failed to serialize clipboard contents: %s",
error->message);
g_clear_error (&error);
}
[wr->item setData:data forType:wr->type];
wr->done = TRUE;
GDK_END_MACOS_ALLOC_POOL;
}
-(void) pasteboard:(NSPasteboard *)pasteboard
item:(NSPasteboardItem *)item
provideDataForType:(NSPasteboardType)type
{
const char *mime_type = _gdk_macos_clipboard_from_ns_type (type);
GMainContext *main_context = g_main_context_default ();
WriteRequest *wr;
if (self->clipboard == NULL || mime_type == NULL)
{
[item setData:[NSData data] forType:type];
return;
}
wr = g_slice_new0 (WriteRequest);
wr->item = [item retain];
wr->stream = G_MEMORY_OUTPUT_STREAM (g_memory_output_stream_new_resizable ());
wr->type = type;
wr->main_context = g_main_context_ref (main_context);
wr->done = FALSE;
gdk_clipboard_write_async (self->clipboard,
mime_type,
G_OUTPUT_STREAM (wr->stream),
G_PRIORITY_DEFAULT,
self->cancellable,
on_data_ready_cb,
wr);
/* We're forced to provide data synchronously via this API
* so we must block on the main loop. Using another main loop
* than the default tends to get us locked up here, so that is
* what we'll do for now.
*/
while (!wr->done)
g_main_context_iteration (wr->main_context, TRUE);
write_request_free (wr);
}
void
_gdk_macos_clipboard_register_drag_types (NSWindow *window)
{
[window registerForDraggedTypes:[NSArray arrayWithObjects:PTYPE(STRING),
PTYPE(PBOARD),
PTYPE(URL),
PTYPE(FILE_URL),
PTYPE(COLOR),
PTYPE(TIFF),
PTYPE(PNG),
nil]];
}
@end
GdkContentFormats *
_gdk_macos_pasteboard_load_formats (NSPasteboard *pasteboard)
{
return load_offer_formats (pasteboard);
}
void
_gdk_macos_pasteboard_read_async (GObject *object,
NSPasteboard *pasteboard,
GdkContentFormats *formats,
int io_priority,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
GdkContentFormats *offer_formats = NULL;
const char *mime_type;
GInputStream *stream = NULL;
GTask *task = NULL;
g_assert (G_IS_OBJECT (object));
g_assert (pasteboard != NULL);
g_assert (formats != NULL);
task = g_task_new (object, cancellable, callback, user_data);
g_task_set_source_tag (task, _gdk_macos_pasteboard_read_async);
g_task_set_priority (task, io_priority);
offer_formats = load_offer_formats (pasteboard);
mime_type = gdk_content_formats_match_mime_type (formats, offer_formats);
if (mime_type == NULL)
{
g_task_return_new_error (task,
G_IO_ERROR,
G_IO_ERROR_NOT_SUPPORTED,
"%s",
_("No compatible transfer format found"));
goto cleanup;
}
if (strcmp (mime_type, "text/plain;charset=utf-8") == 0)
{
NSString *nsstr = [pasteboard stringForType:NSPasteboardTypeString];
if (nsstr != NULL)
{
const char *str = [nsstr UTF8String];
stream = g_memory_input_stream_new_from_data (g_strdup (str),
strlen (str) + 1,
g_free);
}
}
else if (strcmp (mime_type, "text/uri-list") == 0)
{
G_GNUC_BEGIN_IGNORE_DEPRECATIONS;
if ([[pasteboard types] containsObject:PTYPE(FILE_URL)])
{
GString *str = g_string_new (NULL);
NSArray *files = [pasteboard propertyListForType:NSFilenamesPboardType];
gsize n_files = [files count];
char *data;
guint len;
for (gsize i = 0; i < n_files; ++i)
{
NSString* uriString = [files objectAtIndex:i];
uriString = [@"file://" stringByAppendingString:uriString];
uriString = [uriString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
g_string_append_printf (str,
"%s\r\n",
[uriString cStringUsingEncoding:NSUTF8StringEncoding]);
}
len = str->len;
data = g_string_free (str, FALSE);
stream = g_memory_input_stream_new_from_data (data, len, g_free);
}
G_GNUC_END_IGNORE_DEPRECATIONS;
}
else if (strcmp (mime_type, "application/x-color") == 0)
{
NSColorSpace *colorspace;
NSColor *nscolor;
guint16 color[4];
colorspace = [NSColorSpace genericRGBColorSpace];
nscolor = [[NSColor colorFromPasteboard:pasteboard]
colorUsingColorSpace:colorspace];
color[0] = 0xffff * [nscolor redComponent];
color[1] = 0xffff * [nscolor greenComponent];
color[2] = 0xffff * [nscolor blueComponent];
color[3] = 0xffff * [nscolor alphaComponent];
stream = g_memory_input_stream_new_from_data (g_memdup2 (&color, sizeof color),
sizeof color,
g_free);
}
else if (strcmp (mime_type, "image/tiff") == 0)
{
NSData *data = [pasteboard dataForType:PTYPE(TIFF)];
stream = create_stream_from_nsdata (data);
}
else if (strcmp (mime_type, "image/png") == 0)
{
NSData *data = [pasteboard dataForType:PTYPE(PNG)];
stream = create_stream_from_nsdata (data);
}
if (stream != NULL)
{
g_task_set_task_data (task, g_strdup (mime_type), g_free);
g_task_return_pointer (task, g_steal_pointer (&stream), g_object_unref);
}
else
{
g_task_return_new_error (task,
G_IO_ERROR,
G_IO_ERROR_FAILED,
_("Failed to decode contents with mime-type of '%s'"),
mime_type);
}
cleanup:
g_clear_object (&task);
g_clear_pointer (&offer_formats, gdk_content_formats_unref);
GDK_END_MACOS_ALLOC_POOL;
}
GInputStream *
_gdk_macos_pasteboard_read_finish (GObject *object,
GAsyncResult *result,
const char **out_mime_type,
GError **error)
{
GTask *task = (GTask *)result;
g_assert (G_IS_OBJECT (object));
g_assert (G_IS_TASK (task));
if (out_mime_type != NULL)
*out_mime_type = g_strdup (g_task_get_task_data (task));
return g_task_propagate_pointer (task, error);
}
+1 -2
View File
@@ -155,13 +155,12 @@ void _gdk_macos_display_surface_became_key (GdkMacosDisp
GdkMacosSurface *surface); GdkMacosSurface *surface);
void _gdk_macos_display_clear_sorting (GdkMacosDisplay *self); void _gdk_macos_display_clear_sorting (GdkMacosDisplay *self);
const GList *_gdk_macos_display_get_surfaces (GdkMacosDisplay *self); const GList *_gdk_macos_display_get_surfaces (GdkMacosDisplay *self);
void _gdk_macos_display_send_event (GdkMacosDisplay *self, void _gdk_macos_display_send_button_event (GdkMacosDisplay *self,
NSEvent *nsevent); NSEvent *nsevent);
void _gdk_macos_display_warp_pointer (GdkMacosDisplay *self, void _gdk_macos_display_warp_pointer (GdkMacosDisplay *self,
int x, int x,
int y); int y);
NSEvent *_gdk_macos_display_get_nsevent (GdkEvent *event); NSEvent *_gdk_macos_display_get_nsevent (GdkEvent *event);
NSEvent *_gdk_macos_display_get_last_nsevent (void);
GdkDrag *_gdk_macos_display_find_drag (GdkMacosDisplay *self, GdkDrag *_gdk_macos_display_find_drag (GdkMacosDisplay *self,
NSInteger sequence_number); NSInteger sequence_number);
GdkDrop *_gdk_macos_display_find_drop (GdkMacosDisplay *self, GdkDrop *_gdk_macos_display_find_drop (GdkMacosDisplay *self,
+74 -85
View File
@@ -723,85 +723,6 @@ fill_scroll_event (GdkMacosDisplay *self,
return g_steal_pointer (&ret); return g_steal_pointer (&ret);
} }
static GdkEvent *
fill_event (GdkMacosDisplay *self,
GdkMacosWindow *window,
NSEvent *nsevent,
int x,
int y)
{
GdkMacosSurface *surface = [window gdkSurface];
NSEventType event_type = [nsevent type];
GdkEvent *ret = NULL;
switch ((int)event_type)
{
case NSEventTypeLeftMouseDown:
case NSEventTypeRightMouseDown:
case NSEventTypeOtherMouseDown:
case NSEventTypeLeftMouseUp:
case NSEventTypeRightMouseUp:
case NSEventTypeOtherMouseUp:
ret = fill_button_event (self, surface, nsevent, x, y);
break;
case NSEventTypeLeftMouseDragged:
case NSEventTypeRightMouseDragged:
case NSEventTypeOtherMouseDragged:
case NSEventTypeMouseMoved:
ret = fill_motion_event (self, surface, nsevent, x, y);
break;
case NSEventTypeMagnify:
case NSEventTypeRotate:
ret = fill_pinch_event (self, surface, nsevent, x, y);
break;
case NSEventTypeMouseExited:
case NSEventTypeMouseEntered:
{
GdkSeat *seat = gdk_display_get_default_seat (GDK_DISPLAY (self));
GdkDevice *pointer = gdk_seat_get_pointer (seat);
GdkDeviceGrabInfo *grab = _gdk_display_get_last_device_grab (GDK_DISPLAY (self), pointer);
if ([(GdkMacosWindow *)window isInManualResizeOrMove])
{
ret = GDK_MACOS_EVENT_DROP;
}
else if (grab == NULL || grab->owner_events)
{
if (event_type == NSEventTypeMouseExited)
[[NSCursor arrowCursor] set];
ret = synthesize_crossing_event (self, surface, nsevent, x, y);
}
}
break;
case NSEventTypeKeyDown:
case NSEventTypeKeyUp:
case NSEventTypeFlagsChanged: {
GdkEventType type = _gdk_macos_keymap_get_event_type (nsevent);
if (type)
ret = fill_key_event (self, surface, nsevent, type);
break;
}
case NSEventTypeScrollWheel:
ret = fill_scroll_event (self, surface, nsevent, x, y);
break;
default:
break;
}
return ret;
}
static gboolean static gboolean
is_mouse_button_press_event (NSEventType type) is_mouse_button_press_event (NSEventType type)
{ {
@@ -1104,12 +1025,16 @@ find_surface_for_ns_event (GdkMacosDisplay *self,
GdkMacosBaseView *view; GdkMacosBaseView *view;
GdkSurface *surface; GdkSurface *surface;
NSPoint point; NSPoint point;
int x_tmp;
int y_tmp;
g_assert (GDK_IS_MACOS_DISPLAY (self)); g_assert (GDK_IS_MACOS_DISPLAY (self));
g_assert (nsevent != NULL); g_assert (nsevent != NULL);
g_assert (x != NULL); g_assert (x != NULL);
g_assert (y != NULL); g_assert (y != NULL);
_gdk_macos_display_from_display_coords (self, point.x, point.y, &x_tmp, &y_tmp);
switch ((int)[nsevent type]) switch ((int)[nsevent type])
{ {
case NSEventTypeLeftMouseDown: case NSEventTypeLeftMouseDown:
@@ -1158,6 +1083,7 @@ _gdk_macos_display_translate (GdkMacosDisplay *self,
GdkMacosWindow *window; GdkMacosWindow *window;
NSEventType event_type; NSEventType event_type;
NSWindow *event_window; NSWindow *event_window;
GdkEvent *ret = NULL;
int x; int x;
int y; int y;
@@ -1265,15 +1191,79 @@ _gdk_macos_display_translate (GdkMacosDisplay *self,
_gdk_macos_display_clear_sorting (self); _gdk_macos_display_clear_sorting (self);
} }
} }
return fill_event (self, window, nsevent, x, y);
switch ((int)event_type)
{
case NSEventTypeLeftMouseDown:
case NSEventTypeRightMouseDown:
case NSEventTypeOtherMouseDown:
case NSEventTypeLeftMouseUp:
case NSEventTypeRightMouseUp:
case NSEventTypeOtherMouseUp:
ret = fill_button_event (self, surface, nsevent, x, y);
break;
case NSEventTypeLeftMouseDragged:
case NSEventTypeRightMouseDragged:
case NSEventTypeOtherMouseDragged:
case NSEventTypeMouseMoved:
ret = fill_motion_event (self, surface, nsevent, x, y);
break;
case NSEventTypeMagnify:
case NSEventTypeRotate:
ret = fill_pinch_event (self, surface, nsevent, x, y);
break;
case NSEventTypeMouseExited:
case NSEventTypeMouseEntered:
{
GdkSeat *seat = gdk_display_get_default_seat (GDK_DISPLAY (self));
GdkDevice *pointer = gdk_seat_get_pointer (seat);
GdkDeviceGrabInfo *grab = _gdk_display_get_last_device_grab (GDK_DISPLAY (self), pointer);
if ([(GdkMacosWindow *)window isInManualResizeOrMove])
{
ret = GDK_MACOS_EVENT_DROP;
}
else if (grab == NULL)
{
if (event_type == NSEventTypeMouseExited)
[[NSCursor arrowCursor] set];
ret = synthesize_crossing_event (self, surface, nsevent, x, y);
}
}
break;
case NSEventTypeKeyDown:
case NSEventTypeKeyUp:
case NSEventTypeFlagsChanged: {
GdkEventType type = _gdk_macos_keymap_get_event_type (nsevent);
if (type)
ret = fill_key_event (self, surface, nsevent, type);
break;
}
case NSEventTypeScrollWheel:
ret = fill_scroll_event (self, surface, nsevent, x, y);
break;
default:
break;
}
return ret;
} }
void void
_gdk_macos_display_send_event (GdkMacosDisplay *self, _gdk_macos_display_send_button_event (GdkMacosDisplay *self,
NSEvent *nsevent) NSEvent *nsevent)
{ {
GdkMacosSurface *surface; GdkMacosSurface *surface;
GdkMacosWindow *window;
GdkEvent *event; GdkEvent *event;
int x; int x;
int y; int y;
@@ -1282,8 +1272,7 @@ _gdk_macos_display_send_event (GdkMacosDisplay *self,
g_return_if_fail (nsevent != NULL); g_return_if_fail (nsevent != NULL);
if ((surface = find_surface_for_ns_event (self, nsevent, &x, &y)) && if ((surface = find_surface_for_ns_event (self, nsevent, &x, &y)) &&
(window = (GdkMacosWindow *)_gdk_macos_surface_get_native (surface)) && (event = fill_button_event (self, surface, nsevent, x, y)))
(event = fill_event (self, window, nsevent, x, y)))
_gdk_windowing_got_event (GDK_DISPLAY (self), _gdk_windowing_got_event (GDK_DISPLAY (self),
_gdk_event_queue_append (GDK_DISPLAY (self), event), _gdk_event_queue_append (GDK_DISPLAY (self), event),
event, event,
-10
View File
@@ -1024,16 +1024,6 @@ _gdk_macos_display_get_nsevent (GdkEvent *event)
return NULL; return NULL;
} }
NSEvent *
_gdk_macos_display_get_last_nsevent ()
{
const GdkToNSEventMap *map = g_queue_peek_tail (&event_map);
if (map)
return map->nsevent;
return NULL;
}
GdkDrag * GdkDrag *
_gdk_macos_display_find_drag (GdkMacosDisplay *self, _gdk_macos_display_find_drag (GdkMacosDisplay *self,
NSInteger sequence_number) NSInteger sequence_number)
+3 -16
View File
@@ -41,6 +41,7 @@ struct _GdkMacosDrag
GdkDrag parent_instance; GdkDrag parent_instance;
GdkMacosDragSurface *drag_surface; GdkMacosDragSurface *drag_surface;
GdkSeat *drag_seat;
GdkCursor *cursor; GdkCursor *cursor;
int hot_x; int hot_x;
@@ -61,22 +62,8 @@ struct _GdkMacosDragClass
GdkDragClass parent_class; GdkDragClass parent_class;
}; };
GType gdk_macos_drag_get_type (void) G_GNUC_CONST; GType gdk_macos_drag_get_type (void) G_GNUC_CONST;
gboolean _gdk_macos_drag_begin (GdkMacosDrag *self, gboolean _gdk_macos_drag_begin (GdkMacosDrag *self);
GdkContentProvider *content,
GdkMacosWindow *window);
NSDragOperation _gdk_macos_drag_operation (GdkMacosDrag *self);
GdkDragAction _gdk_macos_drag_ns_operation_to_action
(NSDragOperation operation);
void _gdk_macos_drag_surface_move (GdkMacosDrag *self,
int x_root,
int y_root);
void _gdk_macos_drag_set_start_position (GdkMacosDrag *self,
int start_x,
int start_y);
void _gdk_macos_drag_set_actions (GdkMacosDrag *self,
GdkModifierType mods);
G_END_DECLS G_END_DECLS
+271 -106
View File
@@ -25,7 +25,6 @@
#include "gdkmacoscursor-private.h" #include "gdkmacoscursor-private.h"
#include "gdkmacosdisplay-private.h" #include "gdkmacosdisplay-private.h"
#include "gdkmacosdragsurface-private.h" #include "gdkmacosdragsurface-private.h"
#include "gdkmacospasteboard-private.h"
#include "gdk/gdkdeviceprivate.h" #include "gdk/gdkdeviceprivate.h"
#include "gdk/gdkeventsprivate.h" #include "gdk/gdkeventsprivate.h"
@@ -188,6 +187,47 @@ gdk_macos_drag_set_cursor (GdkDrag *drag,
[nscursor set]; [nscursor set];
} }
static gboolean
drag_grab (GdkMacosDrag *self)
{
GdkSeat *seat;
g_assert (GDK_IS_MACOS_DRAG (self));
seat = gdk_device_get_seat (gdk_drag_get_device (GDK_DRAG (self)));
if (gdk_seat_grab (seat,
GDK_SURFACE (self->drag_surface),
GDK_SEAT_CAPABILITY_ALL_POINTING,
FALSE,
self->cursor,
NULL,
NULL,
NULL) != GDK_GRAB_SUCCESS)
return FALSE;
g_set_object (&self->drag_seat, seat);
return TRUE;
}
static void
drag_ungrab (GdkMacosDrag *self)
{
GdkDisplay *display;
g_assert (GDK_IS_MACOS_DRAG (self));
if (self->drag_seat)
{
gdk_seat_ungrab (self->drag_seat);
g_clear_object (&self->drag_seat);
}
display = gdk_drag_get_display (GDK_DRAG (self));
_gdk_macos_display_break_all_grabs (GDK_MACOS_DISPLAY (display), GDK_CURRENT_TIME);
}
static void static void
gdk_macos_drag_cancel (GdkDrag *drag, gdk_macos_drag_cancel (GdkDrag *drag,
GdkDragCancelReason reason) GdkDragCancelReason reason)
@@ -200,6 +240,7 @@ gdk_macos_drag_cancel (GdkDrag *drag,
return; return;
self->cancelled = TRUE; self->cancelled = TRUE;
drag_ungrab (self);
gdk_drag_drop_done (drag, FALSE); gdk_drag_drop_done (drag, FALSE);
} }
@@ -212,6 +253,7 @@ gdk_macos_drag_drop_performed (GdkDrag *drag,
g_assert (GDK_IS_MACOS_DRAG (self)); g_assert (GDK_IS_MACOS_DRAG (self));
g_object_ref (self); g_object_ref (self);
drag_ungrab (self);
g_signal_emit_by_name (drag, "dnd-finished"); g_signal_emit_by_name (drag, "dnd-finished");
gdk_drag_drop_done (drag, TRUE); gdk_drag_drop_done (drag, TRUE);
g_object_unref (self); g_object_unref (self);
@@ -274,6 +316,225 @@ gdk_drag_get_current_actions (GdkModifierType state,
} }
} }
static void
gdk_drag_update (GdkDrag *drag,
double x_root,
double y_root,
GdkModifierType mods,
guint32 evtime)
{
GdkMacosDrag *self = (GdkMacosDrag *)drag;
GdkDragAction suggested_action;
GdkDragAction possible_actions;
g_assert (GDK_IS_MACOS_DRAG (self));
self->last_x = x_root;
self->last_y = y_root;
gdk_drag_get_current_actions (mods,
GDK_BUTTON_PRIMARY,
gdk_drag_get_actions (drag),
&suggested_action,
&possible_actions);
if (GDK_IS_MACOS_SURFACE (self->drag_surface))
_gdk_macos_surface_move (GDK_MACOS_SURFACE (self->drag_surface),
x_root - self->hot_x,
y_root - self->hot_y);
if (!self->did_update)
{
self->start_x = self->last_x;
self->start_y = self->last_y;
self->did_update = TRUE;
}
gdk_drag_set_actions (drag, possible_actions);
}
static gboolean
gdk_dnd_handle_motion_event (GdkDrag *drag,
GdkEvent *event)
{
double x, y;
int x_root, y_root;
g_assert (GDK_IS_MACOS_DRAG (drag));
g_assert (event != NULL);
/* Ignore motion while doing zoomback */
if (GDK_MACOS_DRAG (drag)->cancelled)
return FALSE;
gdk_event_get_position (event, &x, &y);
x_root = event->surface->x + x;
y_root = event->surface->y + y;
gdk_drag_update (drag, x_root, y_root,
gdk_event_get_modifier_state (event),
gdk_event_get_time (event));
return TRUE;
}
static gboolean
gdk_dnd_handle_grab_broken_event (GdkDrag *drag,
GdkEvent *event)
{
GdkMacosDrag *self = GDK_MACOS_DRAG (drag);
gboolean is_implicit = gdk_grab_broken_event_get_implicit (event);
GdkSurface *grab_surface = gdk_grab_broken_event_get_grab_surface (event);
/* Don't cancel if we break the implicit grab from the initial button_press. */
if (is_implicit || grab_surface == (GdkSurface *)self->drag_surface)
return FALSE;
if (gdk_event_get_device (event) != gdk_drag_get_device (drag))
return FALSE;
gdk_drag_cancel (drag, GDK_DRAG_CANCEL_ERROR);
return TRUE;
}
static gboolean
gdk_dnd_handle_button_event (GdkDrag *drag,
GdkEvent *event)
{
GdkMacosDrag *self = GDK_MACOS_DRAG (drag);
g_assert (GDK_IS_MACOS_DRAG (self));
g_assert (event != NULL);
#if 0
/* FIXME: Check the button matches */
if (event->button != self->button)
return FALSE;
#endif
if (gdk_drag_get_selected_action (drag) != 0)
g_signal_emit_by_name (drag, "drop-performed");
else
gdk_drag_cancel (drag, GDK_DRAG_CANCEL_NO_TARGET);
return TRUE;
}
static gboolean
gdk_dnd_handle_key_event (GdkDrag *drag,
GdkEvent *event)
{
GdkMacosDrag *self = GDK_MACOS_DRAG (drag);
GdkModifierType state;
GdkDevice *pointer;
GdkSeat *seat;
int dx, dy;
dx = dy = 0;
state = gdk_event_get_modifier_state (event);
seat = gdk_event_get_seat (event);
pointer = gdk_seat_get_pointer (seat);
if (event->event_type == GDK_KEY_PRESS)
{
guint keyval = gdk_key_event_get_keyval (event);
switch (keyval)
{
case GDK_KEY_Escape:
gdk_drag_cancel (drag, GDK_DRAG_CANCEL_USER_CANCELLED);
return TRUE;
case GDK_KEY_space:
case GDK_KEY_Return:
case GDK_KEY_ISO_Enter:
case GDK_KEY_KP_Enter:
case GDK_KEY_KP_Space:
if (gdk_drag_get_selected_action (drag) != 0)
g_signal_emit_by_name (drag, "drop-performed");
else
gdk_drag_cancel (drag, GDK_DRAG_CANCEL_NO_TARGET);
return TRUE;
case GDK_KEY_Up:
case GDK_KEY_KP_Up:
dy = (state & GDK_ALT_MASK) ? -BIG_STEP : -SMALL_STEP;
break;
case GDK_KEY_Down:
case GDK_KEY_KP_Down:
dy = (state & GDK_ALT_MASK) ? BIG_STEP : SMALL_STEP;
break;
case GDK_KEY_Left:
case GDK_KEY_KP_Left:
dx = (state & GDK_ALT_MASK) ? -BIG_STEP : -SMALL_STEP;
break;
case GDK_KEY_Right:
case GDK_KEY_KP_Right:
dx = (state & GDK_ALT_MASK) ? BIG_STEP : SMALL_STEP;
break;
default:
break;
}
}
/* The state is not yet updated in the event, so we need
* to query it here. We could use XGetModifierMapping, but
* that would be overkill.
*/
gdk_macos_device_query_state (pointer, NULL, NULL, NULL, NULL, &state);
if (dx != 0 || dy != 0)
{
GdkDisplay *display = gdk_event_get_display ((GdkEvent *)event);
self->last_x += dx;
self->last_y += dy;
_gdk_macos_display_warp_pointer (GDK_MACOS_DISPLAY (display),
self->last_x,
self->last_y);
}
gdk_drag_update (drag,
self->last_x, self->last_y,
state,
gdk_event_get_time (event));
return TRUE;
}
static gboolean
gdk_macos_drag_handle_event (GdkDrag *drag,
GdkEvent *event)
{
g_assert (GDK_IS_MACOS_DRAG (drag));
g_assert (event != NULL);
switch ((guint) event->event_type)
{
case GDK_MOTION_NOTIFY:
return gdk_dnd_handle_motion_event (drag, event);
case GDK_BUTTON_RELEASE:
return gdk_dnd_handle_button_event (drag, event);
case GDK_KEY_PRESS:
case GDK_KEY_RELEASE:
return gdk_dnd_handle_key_event (drag, event);
case GDK_GRAB_BROKEN:
return gdk_dnd_handle_grab_broken_event (drag, event);
default:
return FALSE;
}
}
static void static void
gdk_macos_drag_finalize (GObject *object) gdk_macos_drag_finalize (GObject *object)
{ {
@@ -281,6 +542,11 @@ gdk_macos_drag_finalize (GObject *object)
GdkMacosDragSurface *drag_surface = g_steal_pointer (&self->drag_surface); GdkMacosDragSurface *drag_surface = g_steal_pointer (&self->drag_surface);
g_clear_object (&self->cursor); g_clear_object (&self->cursor);
if (self->drag_seat)
{
gdk_seat_ungrab (self->drag_seat);
g_clear_object (&self->drag_seat);
}
G_OBJECT_CLASS (gdk_macos_drag_parent_class)->finalize (object); G_OBJECT_CLASS (gdk_macos_drag_parent_class)->finalize (object);
@@ -342,6 +608,7 @@ gdk_macos_drag_class_init (GdkMacosDragClass *klass)
drag_class->set_cursor = gdk_macos_drag_set_cursor; drag_class->set_cursor = gdk_macos_drag_set_cursor;
drag_class->cancel = gdk_macos_drag_cancel; drag_class->cancel = gdk_macos_drag_cancel;
drag_class->drop_performed = gdk_macos_drag_drop_performed; drag_class->drop_performed = gdk_macos_drag_drop_performed;
drag_class->handle_event = gdk_macos_drag_handle_event;
properties [PROP_DRAG_SURFACE] = properties [PROP_DRAG_SURFACE] =
g_param_spec_object ("drag-surface", NULL, NULL, g_param_spec_object ("drag-surface", NULL, NULL,
@@ -357,113 +624,11 @@ gdk_macos_drag_init (GdkMacosDrag *self)
} }
gboolean gboolean
_gdk_macos_drag_begin (GdkMacosDrag *self, _gdk_macos_drag_begin (GdkMacosDrag *self)
GdkContentProvider *content,
GdkMacosWindow *window)
{ {
NSArray<NSDraggingItem *> *items;
NSDraggingSession *session;
NSPasteboardItem *item;
NSEvent *nsevent;
g_return_val_if_fail (GDK_IS_MACOS_DRAG (self), FALSE); g_return_val_if_fail (GDK_IS_MACOS_DRAG (self), FALSE);
g_return_val_if_fail (GDK_IS_MACOS_WINDOW (window), FALSE);
GDK_BEGIN_MACOS_ALLOC_POOL; _gdk_macos_surface_show (GDK_MACOS_SURFACE (self->drag_surface));
item = [[GdkMacosPasteboardItem alloc] initForDrag:GDK_DRAG (self) withContentProvider:content]; return drag_grab (self);
items = [NSArray arrayWithObject:item];
nsevent = _gdk_macos_display_get_last_nsevent ();
session = [[window contentView] beginDraggingSessionWithItems:items
event:nsevent
source:window];
GDK_END_MACOS_ALLOC_POOL;
_gdk_macos_display_set_drag (GDK_MACOS_DISPLAY (gdk_drag_get_display (GDK_DRAG (self))),
[session draggingSequenceNumber],
GDK_DRAG (self));
return TRUE;
}
NSDragOperation
_gdk_macos_drag_operation (GdkMacosDrag *self)
{
NSDragOperation operation = NSDragOperationNone;
GdkDragAction actions;
g_return_val_if_fail (GDK_IS_MACOS_DRAG (self), NSDragOperationNone);
actions = gdk_drag_get_actions (GDK_DRAG (self));
if (actions & GDK_ACTION_LINK)
operation |= NSDragOperationLink;
if (actions & GDK_ACTION_MOVE)
operation |= NSDragOperationMove;
if (actions & GDK_ACTION_COPY)
operation |= NSDragOperationCopy;
return operation;
}
GdkDragAction
_gdk_macos_drag_ns_operation_to_action (NSDragOperation operation)
{
if (operation & NSDragOperationCopy)
return GDK_ACTION_COPY;
if (operation & NSDragOperationMove)
return GDK_ACTION_MOVE;
if (operation & NSDragOperationLink)
return GDK_ACTION_LINK;
return 0;
}
void
_gdk_macos_drag_surface_move (GdkMacosDrag *self,
int x_root,
int y_root)
{
g_return_if_fail (GDK_IS_MACOS_DRAG (self));
self->last_x = x_root;
self->last_y = y_root;
if (GDK_IS_MACOS_SURFACE (self->drag_surface))
_gdk_macos_surface_move (GDK_MACOS_SURFACE (self->drag_surface),
x_root - self->hot_x,
y_root - self->hot_y);
}
void
_gdk_macos_drag_set_start_position (GdkMacosDrag *self,
int start_x,
int start_y)
{
g_return_if_fail (GDK_IS_MACOS_DRAG (self));
self->start_x = start_x;
self->start_y = start_y;
}
void
_gdk_macos_drag_set_actions (GdkMacosDrag *self,
GdkModifierType mods)
{
GdkDragAction suggested_action;
GdkDragAction possible_actions;
g_assert (GDK_IS_MACOS_DRAG (self));
gdk_drag_get_current_actions (mods,
GDK_BUTTON_PRIMARY,
gdk_drag_get_actions (GDK_DRAG (self)),
&suggested_action,
&possible_actions);
gdk_drag_set_selected_action (GDK_DRAG (self), suggested_action);
gdk_drag_set_actions (GDK_DRAG (self), possible_actions);
} }
+26 -42
View File
@@ -37,15 +37,11 @@
/* /*
* This file implementations integration between the GLib main loop and * This file implementations integration between the GLib main loop and
* the native system of the Core Foundation run loop and Cocoa event * the native system of the Core Foundation run loop and Cocoa event
* handling. There are basically three different cases that we need to * handling. There are basically two different cases that we need to
* handle: * handle: either the GLib main loop is in control (the application
* * has called gtk_main(), or is otherwise iterating the main loop), or
* - the GLib main loop is in control. The application has called * CFRunLoop is in control (we are in a modal operation such as window
* gtk_main(), or is otherwise iterating the main loop. * resizing or drag-and-drop.)
* - CFRunLoop is in control. We are in a modal operation such as window
* resizing.
* - CFRunLoop is running a nested loop. This happens when a drag-and-drop
* operation has been initiated.
* *
* When the GLib main loop is in control we integrate in native event * When the GLib main loop is in control we integrate in native event
* handling in two ways: first we add a GSource that handles checking * handling in two ways: first we add a GSource that handles checking
@@ -61,23 +57,14 @@
* stages of the GLib main loop (prepare, check, dispatch), and make the * stages of the GLib main loop (prepare, check, dispatch), and make the
* appropriate calls into GLib. * appropriate calls into GLib.
* *
* When initiating a drag operation, a nested CFRunLoop is executed. * Both cases share a single problem: the OS X APIs dont allow us to
* The nested run loop is started when fetching a native event in our GLib
* main loop. The application does not receive any events until the nested loop
* is finished. We work around this by forwarding the
* events that trigger the callbacks of the NSDraggingSource protocol.
* The "run loop observer" is executing the GLib main loop stages as long as we're
* in the nested run loop, as if CFRunLoop were in control.
* See also GdkMacosWindow.
*
* All cases share a single problem: the macOS APIs dont allow us to
* wait simultaneously for file descriptors and for events. So when we * wait simultaneously for file descriptors and for events. So when we
* need to do a blocking wait that includes file descriptor activity, we * need to do a blocking wait that includes file descriptor activity, we
* push the actual work of calling select() to a helper thread (the * push the actual work of calling select() to a helper thread (the
* "select thread") and wait for native events in the main thread. * "select thread") and wait for native events in the main thread.
* *
* The main known limitation of this code is that if a callback is triggered * The main known limitation of this code is that if a callback is triggered
* via the macOS run loop while we are "polling" (in either case described * via the OS X run loop while we are "polling" (in either case described
* above), iteration of the GLib main loop is not possible from within * above), iteration of the GLib main loop is not possible from within
* that callback. If the programmer tries to do so explicitly, then they * that callback. If the programmer tries to do so explicitly, then they
* will get a warning from GLib "main loop already active in another thread". * will get a warning from GLib "main loop already active in another thread".
@@ -653,23 +640,6 @@ _gdk_macos_event_source_get_pending (void)
return event; return event;
} }
static void
_gdk_macos_event_source_queue_event (NSEvent *event)
{
/* Just used to wake us up; if an event and a FD arrived at the same
* time; could have come from a previous iteration in some cases,
* but the spurious wake up is harmless if a little inefficient.
*/
if (!event ||
([event type] == NSEventTypeApplicationDefined &&
[event subtype] == GDK_MACOS_EVENT_SUBTYPE_EVENTLOOP))
return;
if (!current_events)
current_events = g_queue_new ();
g_queue_push_head (current_events, [event retain]);
}
static gboolean static gboolean
gdk_macos_event_source_prepare (GSource *source, gdk_macos_event_source_prepare (GSource *source,
int *timeout) int *timeout)
@@ -812,7 +782,23 @@ poll_func (GPollFD *ufds,
if (last_ufds == ufds && n_ready < 0) if (last_ufds == ufds && n_ready < 0)
n_ready = select_thread_collect_poll (ufds, nfds); n_ready = select_thread_collect_poll (ufds, nfds);
_gdk_macos_event_source_queue_event (event); if (event &&
[event type] == NSEventTypeApplicationDefined &&
[event subtype] == GDK_MACOS_EVENT_SUBTYPE_EVENTLOOP)
{
/* Just used to wake us up; if an event and a FD arrived at the same
* time; could have come from a previous iteration in some cases,
* but the spurious wake up is harmless if a little inefficient.
*/
event = NULL;
}
if (event)
{
if (!current_events)
current_events = g_queue_new ();
g_queue_push_head (current_events, [event retain]);
}
return n_ready; return n_ready;
} }
@@ -1032,10 +1018,7 @@ run_loop_observer_callback (CFRunLoopObserverRef observer,
break; break;
} }
/* DnD starts a nested runloop, or so it seems. if (getting_events > 0) /* Activity we triggered */
If we have such a loop, we still want to run
our idle handlers. */
if (getting_events > 0 && current_loop_level < 2)
return; return;
switch (activity) switch (activity)
@@ -1059,6 +1042,7 @@ run_loop_observer_callback (CFRunLoopObserverRef observer,
run_loop_exit (); run_loop_exit ();
break; break;
case kCFRunLoopAllActivities: case kCFRunLoopAllActivities:
/* TODO: Do most of the above? */
default: default:
break; break;
} }
-9
View File
@@ -548,14 +548,6 @@ gdk_macos_gl_context_clear_current (GdkGLContext *context)
return TRUE; return TRUE;
} }
static gboolean
gdk_macos_gl_context_is_current (GdkGLContext *context)
{
GdkMacosGLContext *self = GDK_MACOS_GL_CONTEXT (context);
return self->cgl_context == CGLGetCurrentContext ();
}
static gboolean static gboolean
gdk_macos_gl_context_make_current (GdkGLContext *context, gdk_macos_gl_context_make_current (GdkGLContext *context,
gboolean surfaceless) gboolean surfaceless)
@@ -647,7 +639,6 @@ gdk_macos_gl_context_class_init (GdkMacosGLContextClass *klass)
gl_class->get_damage = gdk_macos_gl_context_get_damage; gl_class->get_damage = gdk_macos_gl_context_get_damage;
gl_class->clear_current = gdk_macos_gl_context_clear_current; gl_class->clear_current = gdk_macos_gl_context_clear_current;
gl_class->is_current = gdk_macos_gl_context_is_current;
gl_class->make_current = gdk_macos_gl_context_make_current; gl_class->make_current = gdk_macos_gl_context_make_current;
gl_class->realize = gdk_macos_gl_context_real_realize; gl_class->realize = gdk_macos_gl_context_real_realize;
gl_class->get_default_framebuffer = gdk_macos_gl_context_get_default_framebuffer; gl_class->get_default_framebuffer = gdk_macos_gl_context_get_default_framebuffer;
-74
View File
@@ -1,74 +0,0 @@
/*
* Copyright © 2021 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.1 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/>.
*
* SPDX-License-Identifier: LGPL-2.1-or-later
*/
#ifndef __GDK_MACOS_PASTEBOARD_PRIVATE_H__
#define __GDK_MACOS_PASTEBOARD_PRIVATE_H__
#include <AppKit/AppKit.h>
#include <gio/gio.h>
#include "gdkclipboardprivate.h"
G_BEGIN_DECLS
@interface GdkMacosPasteboardItemDataProvider : NSObject <NSPasteboardItemDataProvider>
{
GdkContentProvider *_contentProvider;
GdkClipboard *_clipboard;
GdkDrag *_drag;
}
-(id)initForClipboard:(GdkClipboard *)clipboard withContentProvider:(GdkContentProvider *)contentProvider;
-(id)initForDrag:(GdkDrag *)drag withContentProvider:(GdkContentProvider *)contentProvider;
@end
@interface GdkMacosPasteboardItem : NSPasteboardItem
{
GdkContentProvider *_contentProvider;
GdkClipboard *_clipboard;
GdkDrag *_drag;
NSRect _draggingFrame;
}
-(id)initForClipboard:(GdkClipboard *)clipboard withContentProvider:(GdkContentProvider *)contentProvider;
-(id)initForDrag:(GdkDrag *)drag withContentProvider:(GdkContentProvider *)contentProvider;
@end
NSPasteboardType _gdk_macos_pasteboard_to_ns_type (const char *mime_type,
NSPasteboardType *alternate);
const char *_gdk_macos_pasteboard_from_ns_type (NSPasteboardType type);
GdkContentFormats *_gdk_macos_pasteboard_load_formats (NSPasteboard *pasteboard);
void _gdk_macos_pasteboard_register_drag_types (NSWindow *window);
void _gdk_macos_pasteboard_read_async (GObject *object,
NSPasteboard *pasteboard,
GdkContentFormats *formats,
int io_priority,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
GInputStream *_gdk_macos_pasteboard_read_finish (GObject *object,
GAsyncResult *result,
const char **out_mime_type,
GError **error);
G_END_DECLS
#endif /* __GDK_MACOS_PASTEBOARD_PRIVATE_H__ */
-602
View File
@@ -1,602 +0,0 @@
/*
* Copyright © 2021 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.1 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/>.
*
* SPDX-License-Identifier: LGPL-2.1-or-later
*/
#include "config.h"
#include <glib/gi18n.h>
#include "gdkdragprivate.h"
#include "gdkmacospasteboard-private.h"
#include "gdkmacosutils-private.h"
enum {
TYPE_STRING,
TYPE_PBOARD,
TYPE_URL,
TYPE_FILE_URL,
TYPE_COLOR,
TYPE_TIFF,
TYPE_PNG,
TYPE_LAST
};
#define PTYPE(k) (get_pasteboard_type(TYPE_##k))
static NSPasteboardType pasteboard_types[TYPE_LAST];
static NSPasteboardType
get_pasteboard_type (int type)
{
static gsize initialized = FALSE;
g_assert (type >= 0);
g_assert (type < TYPE_LAST);
if (g_once_init_enter (&initialized))
{
pasteboard_types[TYPE_PNG] = NSPasteboardTypePNG;
pasteboard_types[TYPE_STRING] = NSPasteboardTypeString;
pasteboard_types[TYPE_TIFF] = NSPasteboardTypeTIFF;
pasteboard_types[TYPE_COLOR] = NSPasteboardTypeColor;
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
pasteboard_types[TYPE_PBOARD] = NSStringPboardType;
G_GNUC_END_IGNORE_DEPRECATIONS
#ifdef AVAILABLE_MAC_OS_X_VERSION_10_13_AND_LATER
pasteboard_types[TYPE_URL] = NSPasteboardTypeURL;
pasteboard_types[TYPE_FILE_URL] = NSPasteboardTypeFileURL;
#else
pasteboard_types[TYPE_URL] = [[NSString alloc] initWithUTF8String:"public.url"];
pasteboard_types[TYPE_FILE_URL] = [[NSString alloc] initWithUTF8String:"public.file-url"];
#endif
g_once_init_leave (&initialized, TRUE);
}
return pasteboard_types[type];
}
const char *
_gdk_macos_pasteboard_from_ns_type (NSPasteboardType type)
{
G_GNUC_BEGIN_IGNORE_DEPRECATIONS;
if ([type isEqualToString:PTYPE(STRING)] ||
[type isEqualToString:PTYPE(PBOARD)])
return g_intern_string ("text/plain;charset=utf-8");
else if ([type isEqualToString:PTYPE(URL)] ||
[type isEqualToString:PTYPE(FILE_URL)])
return g_intern_string ("text/uri-list");
else if ([type isEqualToString:PTYPE(COLOR)])
return g_intern_string ("application/x-color");
else if ([type isEqualToString:PTYPE(TIFF)])
return g_intern_string ("image/tiff");
else if ([type isEqualToString:PTYPE(PNG)])
return g_intern_string ("image/png");
G_GNUC_END_IGNORE_DEPRECATIONS;
return NULL;
}
NSPasteboardType
_gdk_macos_pasteboard_to_ns_type (const char *mime_type,
NSPasteboardType *alternate)
{
if (alternate)
*alternate = NULL;
if (g_strcmp0 (mime_type, "text/plain;charset=utf-8") == 0)
{
return PTYPE(STRING);
}
else if (g_strcmp0 (mime_type, "text/uri-list") == 0)
{
if (alternate)
*alternate = PTYPE(URL);
return PTYPE(FILE_URL);
}
else if (g_strcmp0 (mime_type, "application/x-color") == 0)
{
return PTYPE(COLOR);
}
else if (g_strcmp0 (mime_type, "image/tiff") == 0)
{
return PTYPE(TIFF);
}
else if (g_strcmp0 (mime_type, "image/png") == 0)
{
return PTYPE(PNG);
}
return nil;
}
static void
populate_content_formats (GdkContentFormatsBuilder *builder,
NSPasteboardType type)
{
const char *mime_type;
g_assert (builder != NULL);
g_assert (type != NULL);
if ((mime_type = _gdk_macos_pasteboard_from_ns_type (type)))
gdk_content_formats_builder_add_mime_type (builder, mime_type);
}
static GdkContentFormats *
load_offer_formats (NSPasteboard *pasteboard)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
GdkContentFormatsBuilder *builder;
GdkContentFormats *formats;
builder = gdk_content_formats_builder_new ();
for (NSPasteboardType type in [pasteboard types])
populate_content_formats (builder, type);
formats = gdk_content_formats_builder_free_to_formats (builder);
GDK_END_MACOS_ALLOC_POOL;
return g_steal_pointer (&formats);
}
GdkContentFormats *
_gdk_macos_pasteboard_load_formats (NSPasteboard *pasteboard)
{
return load_offer_formats (pasteboard);
}
static GInputStream *
create_stream_from_nsdata (NSData *data)
{
const guint8 *bytes = [data bytes];
gsize len = [data length];
return g_memory_input_stream_new_from_data (g_memdup2 (bytes, len), len, g_free);
}
void
_gdk_macos_pasteboard_read_async (GObject *object,
NSPasteboard *pasteboard,
GdkContentFormats *formats,
int io_priority,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
GdkContentFormats *offer_formats = NULL;
const char *mime_type;
GInputStream *stream = NULL;
GTask *task = NULL;
g_assert (G_IS_OBJECT (object));
g_assert (pasteboard != NULL);
g_assert (formats != NULL);
task = g_task_new (object, cancellable, callback, user_data);
g_task_set_source_tag (task, _gdk_macos_pasteboard_read_async);
g_task_set_priority (task, io_priority);
offer_formats = load_offer_formats (pasteboard);
mime_type = gdk_content_formats_match_mime_type (formats, offer_formats);
if (mime_type == NULL)
{
g_task_return_new_error (task,
G_IO_ERROR,
G_IO_ERROR_NOT_SUPPORTED,
"%s",
_("No compatible transfer format found"));
goto cleanup;
}
if (strcmp (mime_type, "text/plain;charset=utf-8") == 0)
{
NSString *nsstr = [pasteboard stringForType:NSPasteboardTypeString];
if (nsstr != NULL)
{
const char *str = [nsstr UTF8String];
stream = g_memory_input_stream_new_from_data (g_strdup (str),
strlen (str) + 1,
g_free);
}
}
else if (strcmp (mime_type, "text/uri-list") == 0)
{
G_GNUC_BEGIN_IGNORE_DEPRECATIONS;
if ([[pasteboard types] containsObject:PTYPE(FILE_URL)])
{
GString *str = g_string_new (NULL);
NSArray *files = [pasteboard propertyListForType:NSFilenamesPboardType];
gsize n_files = [files count];
char *data;
guint len;
for (gsize i = 0; i < n_files; ++i)
{
NSString* uriString = [files objectAtIndex:i];
uriString = [@"file://" stringByAppendingString:uriString];
uriString = [uriString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
g_string_append_printf (str,
"%s\r\n",
[uriString cStringUsingEncoding:NSUTF8StringEncoding]);
}
len = str->len;
data = g_string_free (str, FALSE);
stream = g_memory_input_stream_new_from_data (data, len, g_free);
}
G_GNUC_END_IGNORE_DEPRECATIONS;
}
else if (strcmp (mime_type, "application/x-color") == 0)
{
NSColorSpace *colorspace;
NSColor *nscolor;
guint16 color[4];
colorspace = [NSColorSpace genericRGBColorSpace];
nscolor = [[NSColor colorFromPasteboard:pasteboard]
colorUsingColorSpace:colorspace];
color[0] = 0xffff * [nscolor redComponent];
color[1] = 0xffff * [nscolor greenComponent];
color[2] = 0xffff * [nscolor blueComponent];
color[3] = 0xffff * [nscolor alphaComponent];
stream = g_memory_input_stream_new_from_data (g_memdup2 (&color, sizeof color),
sizeof color,
g_free);
}
else if (strcmp (mime_type, "image/tiff") == 0)
{
NSData *data = [pasteboard dataForType:PTYPE(TIFF)];
stream = create_stream_from_nsdata (data);
}
else if (strcmp (mime_type, "image/png") == 0)
{
NSData *data = [pasteboard dataForType:PTYPE(PNG)];
stream = create_stream_from_nsdata (data);
}
if (stream != NULL)
{
g_task_set_task_data (task, g_strdup (mime_type), g_free);
g_task_return_pointer (task, g_steal_pointer (&stream), g_object_unref);
}
else
{
g_task_return_new_error (task,
G_IO_ERROR,
G_IO_ERROR_FAILED,
_("Failed to decode contents with mime-type of '%s'"),
mime_type);
}
cleanup:
g_clear_object (&task);
g_clear_pointer (&offer_formats, gdk_content_formats_unref);
GDK_END_MACOS_ALLOC_POOL;
}
GInputStream *
_gdk_macos_pasteboard_read_finish (GObject *object,
GAsyncResult *result,
const char **out_mime_type,
GError **error)
{
GTask *task = (GTask *)result;
g_assert (G_IS_OBJECT (object));
g_assert (G_IS_TASK (task));
if (out_mime_type != NULL)
*out_mime_type = g_strdup (g_task_get_task_data (task));
return g_task_propagate_pointer (task, error);
}
void
_gdk_macos_pasteboard_register_drag_types (NSWindow *window)
{
[window registerForDraggedTypes:[NSArray arrayWithObjects:PTYPE(STRING),
PTYPE(PBOARD),
PTYPE(URL),
PTYPE(FILE_URL),
PTYPE(COLOR),
PTYPE(TIFF),
PTYPE(PNG),
nil]];
}
@implementation GdkMacosPasteboardItemDataProvider
-(id)initForClipboard:(GdkClipboard*)clipboard withContentProvider:(GdkContentProvider*)contentProvider
{
[super init];
g_set_object (&self->_clipboard, clipboard);
g_set_object (&self->_contentProvider, contentProvider);
return self;
}
-(id)initForDrag:(GdkDrag*)drag withContentProvider:(GdkContentProvider*)contentProvider
{
[super init];
g_set_object (&self->_drag, drag);
g_set_object (&self->_contentProvider, contentProvider);
return self;
}
-(void)dealloc
{
g_clear_object (&self->_contentProvider);
g_clear_object (&self->_clipboard);
g_clear_object (&self->_drag);
[super dealloc];
}
-(NSArray<NSPasteboardType> *)types
{
NSMutableArray *ret = [[NSMutableArray alloc] init];
GdkContentFormats *serializable;
const char * const *mime_types;
gsize n_mime_types;
serializable = gdk_content_provider_ref_storable_formats (self->_contentProvider);
serializable = gdk_content_formats_union_serialize_mime_types (serializable);
mime_types = gdk_content_formats_get_mime_types (serializable, &n_mime_types);
for (gsize i = 0; i < n_mime_types; i++)
{
const char *mime_type = mime_types[i];
NSPasteboardType type;
NSPasteboardType alternate = nil;
if ((type = _gdk_macos_pasteboard_to_ns_type (mime_type, &alternate)))
{
[ret addObject:type];
if (alternate)
[ret addObject:alternate];
}
}
gdk_content_formats_unref (serializable);
/* Default to an url type (think gobject://internal)
* to support internal, GType-based DnD.
*/
if (n_mime_types == 0)
{
GdkContentFormats *formats;
gsize n_gtypes;
formats = gdk_content_provider_ref_formats (self->_contentProvider);
gdk_content_formats_get_gtypes (formats, &n_gtypes);
if (n_gtypes)
[ret addObject:NSPasteboardTypeURL];
gdk_content_formats_unref (formats);
}
return g_steal_pointer (&ret);
}
typedef struct
{
GMemoryOutputStream *stream;
NSPasteboardItem *item;
NSPasteboardType type;
GMainContext *main_context;
guint done : 1;
} WriteRequest;
static void
write_request_free (WriteRequest *wr)
{
g_clear_pointer (&wr->main_context, g_main_context_unref);
g_clear_object (&wr->stream);
[wr->item release];
g_slice_free (WriteRequest, wr);
}
static void
on_data_ready_cb (GObject *object,
GAsyncResult *result,
gpointer user_data)
{
GDK_BEGIN_MACOS_ALLOC_POOL;
WriteRequest *wr = user_data;
GError *error = NULL;
NSData *data = nil;
gboolean ret;
g_assert (G_IS_OBJECT (object));
g_assert (GDK_IS_CLIPBOARD (object) || GDK_IS_DRAG (object));
g_assert (G_IS_ASYNC_RESULT (result));
g_assert (wr != NULL);
g_assert (G_IS_MEMORY_OUTPUT_STREAM (wr->stream));
g_assert ([wr->item isKindOfClass:[NSPasteboardItem class]]);
if (GDK_IS_CLIPBOARD (object))
ret = gdk_clipboard_write_finish (GDK_CLIPBOARD (object), result, &error);
else if (GDK_IS_DRAG (object))
ret = gdk_drag_write_finish (GDK_DRAG (object), result, &error);
else
g_return_if_reached ();
if (ret)
{
gsize size;
gpointer bytes;
g_output_stream_close (G_OUTPUT_STREAM (wr->stream), NULL, NULL);
size = g_memory_output_stream_get_data_size (wr->stream);
bytes = g_memory_output_stream_steal_data (wr->stream);
data = [[NSData alloc] initWithBytesNoCopy:bytes
length:size
deallocator:^(void *alloc, NSUInteger length) { g_free (alloc); }];
}
else
{
g_warning ("Failed to serialize pasteboard contents: %s",
error->message);
g_clear_error (&error);
}
[wr->item setData:data forType:wr->type];
wr->done = TRUE;
GDK_END_MACOS_ALLOC_POOL;
}
-(void)pasteboard:(NSPasteboard *)pasteboard item:(NSPasteboardItem *)item provideDataForType:(NSPasteboardType)type
{
const char *mime_type = _gdk_macos_pasteboard_from_ns_type (type);
GMainContext *main_context = g_main_context_default ();
WriteRequest *wr;
if (self->_contentProvider == NULL || mime_type == NULL)
{
[item setData:[NSData data] forType:type];
return;
}
wr = g_slice_new0 (WriteRequest);
wr->item = [item retain];
wr->stream = G_MEMORY_OUTPUT_STREAM (g_memory_output_stream_new_resizable ());
wr->type = type;
wr->main_context = g_main_context_ref (main_context);
wr->done = FALSE;
if (GDK_IS_CLIPBOARD (self->_clipboard))
gdk_clipboard_write_async (self->_clipboard,
mime_type,
G_OUTPUT_STREAM (wr->stream),
G_PRIORITY_DEFAULT,
NULL,
on_data_ready_cb,
wr);
else if (GDK_IS_DRAG (self->_drag))
gdk_drag_write_async (self->_drag,
mime_type,
G_OUTPUT_STREAM (wr->stream),
G_PRIORITY_DEFAULT,
NULL,
on_data_ready_cb,
wr);
else
g_return_if_reached ();
/* We're forced to provide data synchronously via this API
* so we must block on the main loop. Using another main loop
* than the default tends to get us locked up here, so that is
* what we'll do for now.
*/
while (!wr->done)
g_main_context_iteration (wr->main_context, TRUE);
write_request_free (wr);
}
-(void)pasteboardFinishedWithDataProvider:(NSPasteboard *)pasteboard
{
g_clear_object (&self->_clipboard);
g_clear_object (&self->_drag);
g_clear_object (&self->_contentProvider);
}
@end
@implementation GdkMacosPasteboardItem
-(id)initForClipboard:(GdkClipboard*)clipboard withContentProvider:(GdkContentProvider*)contentProvider
{
GdkMacosPasteboardItemDataProvider *dataProvider;
dataProvider = [[GdkMacosPasteboardItemDataProvider alloc] initForClipboard:clipboard withContentProvider:contentProvider];
[super init];
g_set_object (&self->_clipboard, clipboard);
g_set_object (&self->_contentProvider, contentProvider);
[self setDataProvider:dataProvider forTypes:[dataProvider types]];
[dataProvider release];
return self;
}
-(id)initForDrag:(GdkDrag*)drag withContentProvider:(GdkContentProvider*)contentProvider
{
GdkMacosPasteboardItemDataProvider *dataProvider;
dataProvider = [[GdkMacosPasteboardItemDataProvider alloc] initForDrag:drag withContentProvider:contentProvider];
[super init];
g_set_object (&self->_drag, drag);
g_set_object (&self->_contentProvider, contentProvider);
[self setDataProvider:dataProvider forTypes:[dataProvider types]];
[dataProvider release];
return self;
}
-(void)dealloc
{
g_clear_object (&self->_contentProvider);
g_clear_object (&self->_clipboard);
g_clear_object (&self->_drag);
[super dealloc];
}
-(NSRect)draggingFrame
{
return self->_draggingFrame;
}
-(void)setDraggingFrame:(NSRect)draggingFrame;
{
self->_draggingFrame = draggingFrame;
}
-(id)item
{
return self;
}
-(NSArray* (^) (void))imageComponentsProvider
{
return nil;
}
@end
+1 -1
View File
@@ -446,7 +446,7 @@ gdk_macos_surface_drag_begin (GdkSurface *surface,
gdk_drag_get_selected_action (GDK_DRAG (drag))); gdk_drag_get_selected_action (GDK_DRAG (drag)));
gdk_drag_set_cursor (GDK_DRAG (drag), cursor); gdk_drag_set_cursor (GDK_DRAG (drag), cursor);
if (!_gdk_macos_drag_begin (drag, content, self->window)) if (!_gdk_macos_drag_begin (drag))
{ {
g_object_unref (drag); g_object_unref (drag);
return NULL; return NULL;
-1
View File
@@ -19,7 +19,6 @@ gdk_macos_sources = files([
'gdkmacoseventsource.c', 'gdkmacoseventsource.c',
'gdkmacoskeymap.c', 'gdkmacoskeymap.c',
'gdkmacosmonitor.c', 'gdkmacosmonitor.c',
'gdkmacospasteboard.c',
'gdkmacospopupsurface.c', 'gdkmacospopupsurface.c',
'gdkmacosseat.c', 'gdkmacosseat.c',
'gdkmacossurface.c', 'gdkmacossurface.c',
+1 -1
View File
@@ -87,7 +87,7 @@ gdk_wayland_app_launch_context_get_startup_notify_id (GAppLaunchContext *context
xdg_activation_token_v1_commit (token); xdg_activation_token_v1_commit (token);
while (app_launch_data.token == NULL) while (app_launch_data.token == NULL)
gdk_wayland_display_dispatch_queue (GDK_DISPLAY (display), event_queue); wl_display_dispatch_queue (display->wl_display, event_queue);
xdg_activation_token_v1_destroy (token); xdg_activation_token_v1_destroy (token);
id = app_launch_data.token; id = app_launch_data.token;
-250
View File
@@ -2,236 +2,6 @@
#define __GDK_DEVICE_WAYLAND_PRIVATE_H__ #define __GDK_DEVICE_WAYLAND_PRIVATE_H__
#include "gdkwaylanddevice.h" #include "gdkwaylanddevice.h"
#include "gdkwaylandseat.h"
#include <gdk/gdkdeviceprivate.h>
#include <gdk/gdkkeysprivate.h>
#include <xkbcommon/xkbcommon.h>
struct _GdkWaylandDevice
{
GdkDevice parent_instance;
};
struct _GdkWaylandDeviceClass
{
GdkDeviceClass parent_class;
};
typedef struct _GdkWaylandTouchData GdkWaylandTouchData;
typedef struct _GdkWaylandPointerFrameData GdkWaylandPointerFrameData;
typedef struct _GdkWaylandPointerData GdkWaylandPointerData;
typedef struct _GdkWaylandTabletPadGroupData GdkWaylandTabletPadGroupData;
typedef struct _GdkWaylandTabletPadData GdkWaylandTabletPadData;
typedef struct _GdkWaylandTabletData GdkWaylandTabletData;
typedef struct _GdkWaylandTabletToolData GdkWaylandTabletToolData;
struct _GdkWaylandTouchData
{
uint32_t id;
double x;
double y;
GdkSurface *surface;
uint32_t touch_down_serial;
guint initial_touch : 1;
};
struct _GdkWaylandPointerFrameData
{
GdkEvent *event;
/* Specific to the scroll event */
double delta_x, delta_y;
int32_t value120_x, value120_y;
gint8 is_scroll_stop;
enum wl_pointer_axis_source source;
};
struct _GdkWaylandPointerData {
GdkSurface *focus;
double surface_x, surface_y;
GdkModifierType button_modifiers;
uint32_t time;
uint32_t enter_serial;
uint32_t press_serial;
GdkSurface *grab_surface;
uint32_t grab_time;
struct wl_surface *pointer_surface;
guint cursor_is_default: 1;
GdkCursor *cursor;
guint cursor_timeout_id;
guint cursor_image_index;
guint cursor_image_delay;
guint touchpad_event_sequence;
guint current_output_scale;
GSList *pointer_surface_outputs;
/* Accumulated event data for a pointer frame */
GdkWaylandPointerFrameData frame;
};
struct _GdkWaylandTabletPadGroupData
{
GdkWaylandTabletPadData *pad;
struct zwp_tablet_pad_group_v2 *wp_tablet_pad_group;
GList *rings;
GList *strips;
GList *buttons;
guint mode_switch_serial;
guint n_modes;
guint current_mode;
struct {
guint source;
gboolean is_stop;
double value;
} axis_tmp_info;
};
struct _GdkWaylandTabletPadData
{
GdkSeat *seat;
struct zwp_tablet_pad_v2 *wp_tablet_pad;
GdkDevice *device;
GdkWaylandTabletData *current_tablet;
guint enter_serial;
uint32_t n_buttons;
char *path;
GList *rings;
GList *strips;
GList *mode_groups;
};
struct _GdkWaylandTabletToolData
{
GdkSeat *seat;
struct zwp_tablet_tool_v2 *wp_tablet_tool;
GdkAxisFlags axes;
GdkDeviceToolType type;
guint64 hardware_serial;
guint64 hardware_id_wacom;
GdkDeviceTool *tool;
GdkWaylandTabletData *current_tablet;
};
struct _GdkWaylandTabletData
{
struct zwp_tablet_v2 *wp_tablet;
char *name;
char *path;
uint32_t vid;
uint32_t pid;
GdkDevice *logical_device;
GdkDevice *stylus_device;
GdkSeat *seat;
GdkWaylandPointerData pointer_info;
GList *pads;
GdkWaylandTabletToolData *current_tool;
int axis_indices[GDK_AXIS_LAST];
double axes[GDK_AXIS_LAST];
};
struct _GdkWaylandSeat
{
GdkSeat parent_instance;
guint32 id;
struct wl_seat *wl_seat;
struct wl_pointer *wl_pointer;
struct wl_keyboard *wl_keyboard;
struct wl_touch *wl_touch;
struct zwp_pointer_gesture_swipe_v1 *wp_pointer_gesture_swipe;
struct zwp_pointer_gesture_pinch_v1 *wp_pointer_gesture_pinch;
struct zwp_pointer_gesture_hold_v1 *wp_pointer_gesture_hold;
struct zwp_tablet_seat_v2 *wp_tablet_seat;
GdkDisplay *display;
GdkDevice *logical_pointer;
GdkDevice *logical_keyboard;
GdkDevice *pointer;
GdkDevice *wheel_scrolling;
GdkDevice *finger_scrolling;
GdkDevice *continuous_scrolling;
GdkDevice *keyboard;
GdkDevice *logical_touch;
GdkDevice *touch;
GdkCursor *cursor;
GdkKeymap *keymap;
GHashTable *touches;
GList *tablets;
GList *tablet_tools;
GList *tablet_pads;
GdkWaylandPointerData pointer_info;
GdkWaylandPointerData touch_info;
GdkModifierType key_modifiers;
GdkSurface *keyboard_focus;
GdkSurface *grab_surface;
uint32_t grab_time;
gboolean have_server_repeat;
uint32_t server_repeat_rate;
uint32_t server_repeat_delay;
struct wl_data_offer *pending_offer;
GdkContentFormatsBuilder *pending_builder;
GdkDragAction pending_source_actions;
GdkDragAction pending_action;
struct wl_callback *repeat_callback;
guint32 repeat_timer;
guint32 repeat_key;
guint32 repeat_count;
gint64 repeat_deadline;
uint32_t keyboard_time;
uint32_t keyboard_key_serial;
GdkClipboard *clipboard;
GdkClipboard *primary_clipboard;
struct wl_data_device *data_device;
GdkDrag *drag;
GdkDrop *drop;
/* Some tracking on gesture events */
guint gesture_n_fingers;
double gesture_scale;
GdkCursor *grab_cursor;
};
#define GDK_TYPE_WAYLAND_DEVICE_PAD (gdk_wayland_device_pad_get_type ())
GType gdk_wayland_device_pad_get_type (void);
void gdk_wayland_seat_stop_cursor_animation (GdkWaylandSeat *seat,
GdkWaylandPointerData *pointer);
GdkWaylandPointerData * gdk_wayland_device_get_pointer (GdkWaylandDevice *wayland_device);
void gdk_wayland_device_set_pointer (GdkWaylandDevice *wayland_device,
GdkWaylandPointerData *pointer);
GdkWaylandTouchData * gdk_wayland_device_get_emulating_touch (GdkWaylandDevice *wayland_device);
void gdk_wayland_device_set_emulating_touch (GdkWaylandDevice *wayland_device,
GdkWaylandTouchData *touch);
void gdk_wayland_device_query_state (GdkDevice *device, void gdk_wayland_device_query_state (GdkDevice *device,
GdkSurface *surface, GdkSurface *surface,
@@ -244,24 +14,4 @@ void gdk_wayland_device_pad_set_feedback (GdkDevice *device,
guint feature_idx, guint feature_idx,
const char *label); const char *label);
GdkWaylandTabletPadData * gdk_wayland_seat_find_pad (GdkWaylandSeat *seat,
GdkDevice *device);
GdkWaylandTabletData * gdk_wayland_seat_find_tablet (GdkWaylandSeat *seat,
GdkDevice *device);
GdkWaylandTouchData * gdk_wayland_seat_get_touch (GdkWaylandSeat *seat,
uint32_t id);
void gdk_wayland_device_maybe_emit_grab_crossing (GdkDevice *device,
GdkSurface *window,
guint32 time);
GdkSurface * gdk_wayland_device_maybe_emit_ungrab_crossing (GdkDevice *device,
guint32 time_);
gboolean gdk_wayland_device_update_surface_cursor (GdkDevice *device);
GdkModifierType gdk_wayland_device_get_modifiers (GdkDevice *device);
#endif #endif
File diff suppressed because it is too large Load Diff
-266
View File
@@ -1,266 +0,0 @@
/* GDK - The GIMP Drawing Kit
* Copyright (C) 2009 Carlos Garnacho <carlosg@gnome.org>
*
* 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 "config.h"
#include "gdkwaylanddevice.h"
#include "gdkdevice-wayland-private.h"
#include "tablet-unstable-v2-client-protocol.h"
#include <gdk/gdkdevicepadprivate.h>
typedef struct _GdkWaylandDevicePad GdkWaylandDevicePad;
typedef struct _GdkWaylandDevicePadClass GdkWaylandDevicePadClass;
struct _GdkWaylandDevicePad
{
GdkWaylandDevice parent_instance;
};
struct _GdkWaylandDevicePadClass
{
GdkWaylandDeviceClass parent_class;
};
static void gdk_wayland_device_pad_iface_init (GdkDevicePadInterface *iface);
G_DEFINE_TYPE_WITH_CODE (GdkWaylandDevicePad, gdk_wayland_device_pad,
GDK_TYPE_WAYLAND_DEVICE,
G_IMPLEMENT_INTERFACE (GDK_TYPE_DEVICE_PAD,
gdk_wayland_device_pad_iface_init))
static int
gdk_wayland_device_pad_get_n_groups (GdkDevicePad *pad)
{
GdkSeat *seat = gdk_device_get_seat (GDK_DEVICE (pad));
GdkWaylandTabletPadData *data;
data = gdk_wayland_seat_find_pad (GDK_WAYLAND_SEAT (seat),
GDK_DEVICE (pad));
#ifdef G_DISABLE_ASSERT
if (data == NULL)
return 0;
#else
g_assert (data != NULL);
#endif
return g_list_length (data->mode_groups);
}
static int
gdk_wayland_device_pad_get_group_n_modes (GdkDevicePad *pad,
int n_group)
{
GdkSeat *seat = gdk_device_get_seat (GDK_DEVICE (pad));
GdkWaylandTabletPadGroupData *group;
GdkWaylandTabletPadData *data;
data = gdk_wayland_seat_find_pad (GDK_WAYLAND_SEAT (seat),
GDK_DEVICE (pad));
#ifdef G_DISABLE_ASSERT
if (data == NULL)
return 0;
#else
g_assert (data != NULL);
#endif
group = g_list_nth_data (data->mode_groups, n_group);
if (!group)
return -1;
return group->n_modes;
}
static int
gdk_wayland_device_pad_get_n_features (GdkDevicePad *pad,
GdkDevicePadFeature feature)
{
GdkSeat *seat = gdk_device_get_seat (GDK_DEVICE (pad));
GdkWaylandTabletPadData *data;
data = gdk_wayland_seat_find_pad (GDK_WAYLAND_SEAT (seat),
GDK_DEVICE (pad));
g_assert (data != NULL);
switch (feature)
{
case GDK_DEVICE_PAD_FEATURE_BUTTON:
return data->n_buttons;
case GDK_DEVICE_PAD_FEATURE_RING:
return g_list_length (data->rings);
case GDK_DEVICE_PAD_FEATURE_STRIP:
return g_list_length (data->strips);
default:
return -1;
}
}
static int
gdk_wayland_device_pad_get_feature_group (GdkDevicePad *pad,
GdkDevicePadFeature feature,
int idx)
{
GdkSeat *seat = gdk_device_get_seat (GDK_DEVICE (pad));
GdkWaylandTabletPadGroupData *group;
GdkWaylandTabletPadData *data;
GList *l;
int i;
data = gdk_wayland_seat_find_pad (GDK_WAYLAND_SEAT (seat),
GDK_DEVICE (pad));
#ifdef G_DISABLE_ASSERT
if (data == NULL)
return -1;
#else
g_assert (data != NULL);
#endif
for (l = data->mode_groups, i = 0; l; l = l->next, i++)
{
group = l->data;
switch (feature)
{
case GDK_DEVICE_PAD_FEATURE_BUTTON:
if (g_list_find (group->buttons, GINT_TO_POINTER (idx)))
return i;
break;
case GDK_DEVICE_PAD_FEATURE_RING:
{
gpointer ring;
ring = g_list_nth_data (data->rings, idx);
if (ring && g_list_find (group->rings, ring))
return i;
break;
}
case GDK_DEVICE_PAD_FEATURE_STRIP:
{
gpointer strip;
strip = g_list_nth_data (data->strips, idx);
if (strip && g_list_find (group->strips, strip))
return i;
break;
}
default:
break;
}
}
return -1;
}
static void
gdk_wayland_device_pad_iface_init (GdkDevicePadInterface *iface)
{
iface->get_n_groups = gdk_wayland_device_pad_get_n_groups;
iface->get_group_n_modes = gdk_wayland_device_pad_get_group_n_modes;
iface->get_n_features = gdk_wayland_device_pad_get_n_features;
iface->get_feature_group = gdk_wayland_device_pad_get_feature_group;
}
static void
gdk_wayland_device_pad_class_init (GdkWaylandDevicePadClass *klass)
{
}
static void
gdk_wayland_device_pad_init (GdkWaylandDevicePad *pad)
{
}
static GdkWaylandTabletPadGroupData *
tablet_pad_lookup_button_group (GdkWaylandTabletPadData *pad,
uint32_t button)
{
GdkWaylandTabletPadGroupData *group;
GList *l;
for (l = pad->mode_groups; l; l = l->next)
{
group = l->data;
if (g_list_find (group->buttons, GUINT_TO_POINTER (button)))
return group;
}
return NULL;
}
/*<private>
* gdk_wayland_device_pad_set_feedback:
* @device: (type GdkWaylandDevice): a %GDK_SOURCE_TABLET_PAD device
* @feature: Feature to set the feedback label for
* @feature_idx: 0-indexed index of the feature to set the feedback label for
* @label: Feedback label
*
* Sets the feedback label for the given feature/index.
*
* This may be used by the compositor to provide user feedback
* of the actions available/performed.
*/
void
gdk_wayland_device_pad_set_feedback (GdkDevice *device,
GdkDevicePadFeature feature,
guint feature_idx,
const char *label)
{
GdkWaylandTabletPadData *pad;
GdkWaylandTabletPadGroupData *group;
GdkSeat *seat;
seat = gdk_device_get_seat (device);
pad = gdk_wayland_seat_find_pad (GDK_WAYLAND_SEAT (seat), device);
if (!pad)
return;
if (feature == GDK_DEVICE_PAD_FEATURE_BUTTON)
{
group = tablet_pad_lookup_button_group (pad, feature_idx);
if (!group)
return;
zwp_tablet_pad_v2_set_feedback (pad->wp_tablet_pad, feature_idx, label,
group->mode_switch_serial);
}
else if (feature == GDK_DEVICE_PAD_FEATURE_RING)
{
struct zwp_tablet_pad_ring_v2 *wp_pad_ring;
wp_pad_ring = g_list_nth_data (pad->rings, feature_idx);
if (!wp_pad_ring)
return;
group = zwp_tablet_pad_ring_v2_get_user_data (wp_pad_ring);
zwp_tablet_pad_ring_v2_set_feedback (wp_pad_ring, label,
group->mode_switch_serial);
}
else if (feature == GDK_DEVICE_PAD_FEATURE_STRIP)
{
struct zwp_tablet_pad_strip_v2 *wp_pad_strip;
wp_pad_strip = g_list_nth_data (pad->strips, feature_idx);
if (!wp_pad_strip)
return;
group = zwp_tablet_pad_strip_v2_get_user_data (wp_pad_strip);
zwp_tablet_pad_strip_v2_set_feedback (wp_pad_strip, label,
group->mode_switch_serial);
}
}
+3 -27
View File
@@ -832,8 +832,6 @@ gdk_wayland_display_get_next_serial (GdkDisplay *display)
* if no ID has been defined. * if no ID has been defined.
* *
* Returns: (nullable): the startup notification ID for @display * Returns: (nullable): the startup notification ID for @display
*
* Deprecated: 4.10.
*/ */
const char * const char *
gdk_wayland_display_get_startup_notification_id (GdkDisplay *display) gdk_wayland_display_get_startup_notification_id (GdkDisplay *display)
@@ -855,8 +853,6 @@ gdk_wayland_display_get_startup_notification_id (GdkDisplay *display)
* The startup ID is also what is used to signal that the startup is * The startup ID is also what is used to signal that the startup is
* complete (for example, when opening a window or when calling * complete (for example, when opening a window or when calling
* [method@Gdk.Display.notify_startup_complete]). * [method@Gdk.Display.notify_startup_complete]).
*
* Deprecated: 4.10. Use [method@Gdk.Toplevel.set_startup_id]
*/ */
void void
gdk_wayland_display_set_startup_notification_id (GdkDisplay *display, gdk_wayland_display_set_startup_notification_id (GdkDisplay *display,
@@ -985,9 +981,7 @@ gdk_wayland_display_class_init (GdkWaylandDisplayClass *class)
display_class->queue_events = _gdk_wayland_display_queue_events; display_class->queue_events = _gdk_wayland_display_queue_events;
display_class->get_app_launch_context = _gdk_wayland_display_get_app_launch_context; display_class->get_app_launch_context = _gdk_wayland_display_get_app_launch_context;
display_class->get_next_serial = gdk_wayland_display_get_next_serial; display_class->get_next_serial = gdk_wayland_display_get_next_serial;
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
display_class->get_startup_notification_id = gdk_wayland_display_get_startup_notification_id; display_class->get_startup_notification_id = gdk_wayland_display_get_startup_notification_id;
G_GNUC_END_IGNORE_DEPRECATIONS
display_class->notify_startup_complete = gdk_wayland_display_notify_startup_complete; display_class->notify_startup_complete = gdk_wayland_display_notify_startup_complete;
display_class->create_surface = _gdk_wayland_display_create_surface; display_class->create_surface = _gdk_wayland_display_create_surface;
display_class->get_keymap = _gdk_wayland_display_get_keymap; display_class->get_keymap = _gdk_wayland_display_get_keymap;
@@ -2332,7 +2326,6 @@ apply_monitor_change (GdkWaylandMonitor *monitor)
monitor->x, monitor->y, monitor->x, monitor->y,
monitor->width, monitor->height }); monitor->width, monitor->height });
gdk_monitor_set_connector (GDK_MONITOR (monitor), monitor->name); gdk_monitor_set_connector (GDK_MONITOR (monitor), monitor->name);
gdk_monitor_set_description (GDK_MONITOR (monitor), monitor->description);
monitor->wl_output_done = FALSE; monitor->wl_output_done = FALSE;
monitor->xdg_output_done = FALSE; monitor->xdg_output_done = FALSE;
@@ -2389,7 +2382,7 @@ xdg_output_handle_name (void *data,
{ {
GdkWaylandMonitor *monitor = (GdkWaylandMonitor *) data; GdkWaylandMonitor *monitor = (GdkWaylandMonitor *) data;
GDK_DEBUG (MISC, "handle name xdg-output %d: %s", monitor->id, name); GDK_DEBUG (MISC, "handle name xdg-output %d", monitor->id);
monitor->name = g_strdup (name); monitor->name = g_strdup (name);
} }
@@ -2399,11 +2392,8 @@ xdg_output_handle_description (void *data,
struct zxdg_output_v1 *xdg_output, struct zxdg_output_v1 *xdg_output,
const char *description) const char *description)
{ {
GdkWaylandMonitor *monitor = (GdkWaylandMonitor *) data; GDK_DEBUG (MISC, "handle description xdg-output %d",
((GdkWaylandMonitor *)data)->id);
GDK_DEBUG (MISC, "handle description xdg-output %d: %s", monitor->id, description);
monitor->description = g_strdup (description);
} }
static const struct zxdg_output_v1_listener xdg_output_listener = { static const struct zxdg_output_v1_listener xdg_output_listener = {
@@ -2694,17 +2684,3 @@ gdk_wayland_display_query_registry (GdkDisplay *display,
return FALSE; return FALSE;
} }
void
gdk_wayland_display_dispatch_queue (GdkDisplay *display,
struct wl_event_queue *event_queue)
{
GdkWaylandDisplay *display_wayland = GDK_WAYLAND_DISPLAY (display);
if (wl_display_dispatch_queue (display_wayland->wl_display, event_queue) == -1)
{
g_message ("Error %d (%s) dispatching to Wayland display.",
errno, g_strerror (errno));
_exit (1);
}
}
-3
View File
@@ -158,9 +158,6 @@ struct _GdkWaylandDisplayClass
gboolean gdk_wayland_display_prefers_ssd (GdkDisplay *display); gboolean gdk_wayland_display_prefers_ssd (GdkDisplay *display);
void gdk_wayland_display_dispatch_queue (GdkDisplay *display,
struct wl_event_queue *event_queue);
G_END_DECLS G_END_DECLS
#endif /* __GDK_WAYLAND_DISPLAY__ */ #endif /* __GDK_WAYLAND_DISPLAY__ */
-1
View File
@@ -46,7 +46,6 @@ gdk_wayland_monitor_finalize (GObject *object)
GdkWaylandMonitor *monitor = (GdkWaylandMonitor *)object; GdkWaylandMonitor *monitor = (GdkWaylandMonitor *)object;
g_free (monitor->name); g_free (monitor->name);
g_free (monitor->description);
g_clear_pointer (&monitor->xdg_output, zxdg_output_v1_destroy); g_clear_pointer (&monitor->xdg_output, zxdg_output_v1_destroy);
-1
View File
@@ -38,7 +38,6 @@ struct _GdkWaylandMonitor {
int32_t width; int32_t width;
int32_t height; int32_t height;
char *name; char *name;
char *description;
gboolean wl_output_done; gboolean wl_output_done;
gboolean xdg_output_done; gboolean xdg_output_done;
}; };
+3 -4
View File
@@ -1334,6 +1334,8 @@ gdk_wayland_surface_present_popup (GdkWaylandPopup *wayland_popup,
GdkPopupLayout *layout) GdkPopupLayout *layout)
{ {
GdkSurface *surface = GDK_SURFACE (wayland_popup); GdkSurface *surface = GDK_SURFACE (wayland_popup);
GdkWaylandDisplay *display_wayland =
GDK_WAYLAND_DISPLAY (gdk_surface_get_display (surface));
GdkWaylandSurface *wayland_surface = GDK_WAYLAND_SURFACE (wayland_popup); GdkWaylandSurface *wayland_surface = GDK_WAYLAND_SURFACE (wayland_popup);
if (!wayland_surface->mapped) if (!wayland_surface->mapped)
@@ -1386,10 +1388,7 @@ gdk_wayland_surface_present_popup (GdkWaylandPopup *wayland_popup,
} }
while (wayland_popup->display_server.xdg_popup && !is_relayout_finished (surface)) while (wayland_popup->display_server.xdg_popup && !is_relayout_finished (surface))
{ wl_display_dispatch_queue (display_wayland->wl_display, wayland_surface->event_queue);
gdk_wayland_display_dispatch_queue (surface->display,
wayland_surface->event_queue);
}
if (wayland_popup->display_server.xdg_popup) if (wayland_popup->display_server.xdg_popup)
{ {
File diff suppressed because it is too large Load Diff
+1 -4
View File
@@ -2119,10 +2119,7 @@ gdk_wayland_toplevel_focus (GdkToplevel *toplevel,
xdg_activation_token_v1_commit (token); xdg_activation_token_v1_commit (token);
while (startup_id == NULL) while (startup_id == NULL)
{ wl_display_dispatch_queue (display_wayland->wl_display, event_queue);
gdk_wayland_display_dispatch_queue (GDK_DISPLAY (display_wayland),
event_queue);
}
xdg_activation_token_v1_destroy (token); xdg_activation_token_v1_destroy (token);
wl_event_queue_destroy (event_queue); wl_event_queue_destroy (event_queue);
+2 -2
View File
@@ -53,9 +53,9 @@ GDK_AVAILABLE_IN_ALL
void gdk_wayland_display_set_cursor_theme (GdkDisplay *display, void gdk_wayland_display_set_cursor_theme (GdkDisplay *display,
const char *name, const char *name,
int size); int size);
GDK_DEPRECATED_IN_4_10 GDK_AVAILABLE_IN_ALL
const char * gdk_wayland_display_get_startup_notification_id (GdkDisplay *display); const char * gdk_wayland_display_get_startup_notification_id (GdkDisplay *display);
GDK_DEPRECATED_IN_4_10_FOR(gdk_toplevel_set_startup_id) GDK_AVAILABLE_IN_ALL
void gdk_wayland_display_set_startup_notification_id (GdkDisplay *display, void gdk_wayland_display_set_startup_notification_id (GdkDisplay *display,
const char *startup_id); const char *startup_id);
+1 -3
View File
@@ -6,17 +6,15 @@ gdk_wayland_sources = files([
'gdkclipboard-wayland.c', 'gdkclipboard-wayland.c',
'gdkcursor-wayland.c', 'gdkcursor-wayland.c',
'gdkdevice-wayland.c', 'gdkdevice-wayland.c',
'gdkdevicepad-wayland.c',
'gdkdisplay-wayland.c', 'gdkdisplay-wayland.c',
'gdkdrag-wayland.c', 'gdkdrag-wayland.c',
'gdkdragsurface-wayland.c', 'gdkdragsurface-wayland.c',
'gdkdrop-wayland.c', 'gdkdrop-wayland.c',
'gdkeventsource.c', 'gdkeventsource.c',
'gdkglcontext-wayland.c', 'gdkglcontext-wayland.c',
'gdkkeymap-wayland.c', 'gdkkeys-wayland.c',
'gdkmonitor-wayland.c', 'gdkmonitor-wayland.c',
'gdkprimary-wayland.c', 'gdkprimary-wayland.c',
'gdkseat-wayland.c',
'gdksurface-wayland.c', 'gdksurface-wayland.c',
'gdktoplevel-wayland.c', 'gdktoplevel-wayland.c',
'gdkpopup-wayland.c', 'gdkpopup-wayland.c',
-9
View File
@@ -631,14 +631,6 @@ gdk_win32_gl_context_wgl_clear_current (GdkGLContext *context)
return wglMakeCurrent (NULL, NULL); return wglMakeCurrent (NULL, NULL);
} }
static gboolean
gdk_win32_gl_context_wgl_is_current (GdkGLContext *context)
{
GdkWin32GLContextWGL *self = GDK_WIN32_GL_CONTEXT_WGL (context);
return self->wgl_context == wglGetCurrentContext ();
}
static gboolean static gboolean
gdk_win32_gl_context_wgl_make_current (GdkGLContext *context, gdk_win32_gl_context_wgl_make_current (GdkGLContext *context,
gboolean surfaceless) gboolean surfaceless)
@@ -690,7 +682,6 @@ gdk_win32_gl_context_wgl_class_init (GdkWin32GLContextWGLClass *klass)
context_class->realize = gdk_win32_gl_context_wgl_realize; context_class->realize = gdk_win32_gl_context_wgl_realize;
context_class->make_current = gdk_win32_gl_context_wgl_make_current; context_class->make_current = gdk_win32_gl_context_wgl_make_current;
context_class->clear_current = gdk_win32_gl_context_wgl_clear_current; context_class->clear_current = gdk_win32_gl_context_wgl_clear_current;
context_class->is_current = gdk_win32_gl_context_wgl_is_current;
draw_context_class->begin_frame = gdk_win32_gl_context_wgl_begin_frame; draw_context_class->begin_frame = gdk_win32_gl_context_wgl_begin_frame;
draw_context_class->end_frame = gdk_win32_gl_context_wgl_end_frame; draw_context_class->end_frame = gdk_win32_gl_context_wgl_end_frame;
+1
View File
@@ -740,6 +740,7 @@ GPtrArray *
_gdk_win32_display_get_monitor_list (GdkWin32Display *win32_display) _gdk_win32_display_get_monitor_list (GdkWin32Display *win32_display)
{ {
EnumMonitorData data; EnumMonitorData data;
int i;
data.display = win32_display; data.display = win32_display;
data.monitors = get_monitor_devices (win32_display); data.monitors = get_monitor_devices (win32_display);
+12 -3
View File
@@ -2066,10 +2066,19 @@ gdk_x11_device_manager_xi2_translate_event (GdkEventTranslator *translator,
xev->detail != XINotifyInferior && xev->mode != XINotifyPassiveUngrab && xev->detail != XINotifyInferior && xev->mode != XINotifyPassiveUngrab &&
GDK_IS_TOPLEVEL (surface)) GDK_IS_TOPLEVEL (surface))
{ {
GList *l; if (gdk_x11_device_xi2_get_device_type ((GdkX11DeviceXI2 *) device) != GDK_X11_DEVICE_TYPE_LOGICAL)
_gdk_device_xi2_reset_scroll_valuators (GDK_X11_DEVICE_XI2 (source_device));
else
{
GList *physical_devices, *l;
for (l = device_manager->devices; l; l = l->next) physical_devices = gdk_device_list_physical_devices (source_device);
_gdk_device_xi2_reset_scroll_valuators (GDK_X11_DEVICE_XI2 (l->data));
for (l = physical_devices; l; l = l->next)
_gdk_device_xi2_reset_scroll_valuators (GDK_X11_DEVICE_XI2 (l->data));
g_list_free (physical_devices);
}
} }
event = gdk_crossing_event_new (ev->evtype == XI_Enter event = gdk_crossing_event_new (ev->evtype == XI_Enter
+1 -9
View File
@@ -2074,10 +2074,8 @@ gdk_x11_display_make_default (GdkDisplay *display)
display_x11->startup_notification_id = NULL; display_x11->startup_notification_id = NULL;
startup_id = gdk_get_startup_notification_id (); startup_id = gdk_get_startup_notification_id ();
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
if (startup_id) if (startup_id)
gdk_x11_display_set_startup_notification_id (display, startup_id); gdk_x11_display_set_startup_notification_id (display, startup_id);
G_GNUC_END_IGNORE_DEPRECATIONS
} }
static void static void
@@ -2305,8 +2303,6 @@ gdk_x11_display_get_user_time (GdkDisplay *display)
* Gets the startup notification ID for a display. * Gets the startup notification ID for a display.
* *
* Returns: the startup notification ID for @display * Returns: the startup notification ID for @display
*
* Deprecated: 4.10
*/ */
const char * const char *
gdk_x11_display_get_startup_notification_id (GdkDisplay *display) gdk_x11_display_get_startup_notification_id (GdkDisplay *display)
@@ -2333,9 +2329,7 @@ gdk_x11_display_get_startup_notification_id (GdkDisplay *display)
* The startup ID is also what is used to signal that the startup is * The startup ID is also what is used to signal that the startup is
* complete (for example, when opening a window or when calling * complete (for example, when opening a window or when calling
* gdk_display_notify_startup_complete()). * gdk_display_notify_startup_complete()).
* **/
* Deprecated: 4.10: Using [method@Gdk.Toplevel.set_startup_id] is sufficient
*/
void void
gdk_x11_display_set_startup_notification_id (GdkDisplay *display, gdk_x11_display_set_startup_notification_id (GdkDisplay *display,
const char *startup_id) const char *startup_id)
@@ -3048,9 +3042,7 @@ gdk_x11_display_class_init (GdkX11DisplayClass * class)
display_class->get_app_launch_context = _gdk_x11_display_get_app_launch_context; display_class->get_app_launch_context = _gdk_x11_display_get_app_launch_context;
display_class->get_next_serial = gdk_x11_display_get_next_serial; display_class->get_next_serial = gdk_x11_display_get_next_serial;
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
display_class->get_startup_notification_id = gdk_x11_display_get_startup_notification_id; display_class->get_startup_notification_id = gdk_x11_display_get_startup_notification_id;
G_GNUC_END_IGNORE_DEPRECATIONS
display_class->notify_startup_complete = gdk_x11_display_notify_startup_complete; display_class->notify_startup_complete = gdk_x11_display_notify_startup_complete;
display_class->create_surface = _gdk_x11_display_create_surface; display_class->create_surface = _gdk_x11_display_create_surface;
display_class->get_keymap = gdk_x11_display_get_keymap; display_class->get_keymap = gdk_x11_display_get_keymap;
-9
View File
@@ -210,14 +210,6 @@ gdk_x11_gl_context_glx_clear_current (GdkGLContext *context)
return TRUE; return TRUE;
} }
static gboolean
gdk_x11_gl_context_glx_is_current (GdkGLContext *context)
{
GdkX11GLContextGLX *self = GDK_X11_GL_CONTEXT_GLX (context);
return self->glx_context == glXGetCurrentContext ();
}
static gboolean static gboolean
gdk_x11_gl_context_glx_make_current (GdkGLContext *context, gdk_x11_gl_context_glx_make_current (GdkGLContext *context,
gboolean surfaceless) gboolean surfaceless)
@@ -693,7 +685,6 @@ gdk_x11_gl_context_glx_class_init (GdkX11GLContextGLXClass *klass)
context_class->realize = gdk_x11_gl_context_glx_realize; context_class->realize = gdk_x11_gl_context_glx_realize;
context_class->make_current = gdk_x11_gl_context_glx_make_current; context_class->make_current = gdk_x11_gl_context_glx_make_current;
context_class->clear_current = gdk_x11_gl_context_glx_clear_current; context_class->clear_current = gdk_x11_gl_context_glx_clear_current;
context_class->is_current = gdk_x11_gl_context_glx_is_current;
context_class->get_damage = gdk_x11_gl_context_glx_get_damage; context_class->get_damage = gdk_x11_gl_context_glx_get_damage;
draw_context_class->end_frame = gdk_x11_gl_context_glx_end_frame; draw_context_class->end_frame = gdk_x11_gl_context_glx_end_frame;
+2 -2
View File
@@ -80,9 +80,9 @@ Cursor gdk_x11_display_get_xcursor (GdkDisplay *display,
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
guint32 gdk_x11_display_get_user_time (GdkDisplay *display); guint32 gdk_x11_display_get_user_time (GdkDisplay *display);
GDK_DEPRECATED_IN_4_10 GDK_AVAILABLE_IN_ALL
const char * gdk_x11_display_get_startup_notification_id (GdkDisplay *display); const char * gdk_x11_display_get_startup_notification_id (GdkDisplay *display);
GDK_DEPRECATED_IN_4_10 GDK_AVAILABLE_IN_ALL
void gdk_x11_display_set_startup_notification_id (GdkDisplay *display, void gdk_x11_display_set_startup_notification_id (GdkDisplay *display,
const char *startup_id); const char *startup_id);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
-4
View File
@@ -250,7 +250,6 @@ collect_reused_child_nodes (GskRenderer *renderer,
/* Leaf nodes */ /* Leaf nodes */
case GSK_TEXTURE_NODE: case GSK_TEXTURE_NODE:
case GSK_TEXTURE_SCALE_NODE:
case GSK_CAIRO_NODE: case GSK_CAIRO_NODE:
case GSK_COLOR_NODE: case GSK_COLOR_NODE:
case GSK_BORDER_NODE: case GSK_BORDER_NODE:
@@ -270,7 +269,6 @@ collect_reused_child_nodes (GskRenderer *renderer,
case GSK_BLEND_NODE: case GSK_BLEND_NODE:
case GSK_CROSS_FADE_NODE: case GSK_CROSS_FADE_NODE:
case GSK_BLUR_NODE: case GSK_BLUR_NODE:
case GSK_MASK_NODE:
default: default:
@@ -847,8 +845,6 @@ gsk_broadway_renderer_add_node (GskRenderer *renderer,
} }
break; /* Fallback */ break; /* Fallback */
case GSK_MASK_NODE:
case GSK_TEXTURE_SCALE_NODE:
case GSK_TEXT_NODE: case GSK_TEXT_NODE:
case GSK_RADIAL_GRADIENT_NODE: case GSK_RADIAL_GRADIENT_NODE:
case GSK_REPEATING_LINEAR_GRADIENT_NODE: case GSK_REPEATING_LINEAR_GRADIENT_NODE:
+5 -21
View File
@@ -403,7 +403,6 @@ gsk_gl_command_queue_dispose (GObject *object)
gsk_gl_command_batches_clear (&self->batches); gsk_gl_command_batches_clear (&self->batches);
gsk_gl_command_binds_clear (&self->batch_binds); gsk_gl_command_binds_clear (&self->batch_binds);
gsk_gl_command_uniforms_clear (&self->batch_uniforms); gsk_gl_command_uniforms_clear (&self->batch_uniforms);
gsk_gl_syncs_clear (&self->syncs);
gsk_gl_buffer_destroy (&self->vertices); gsk_gl_buffer_destroy (&self->vertices);
@@ -426,7 +425,6 @@ gsk_gl_command_queue_init (GskGLCommandQueue *self)
gsk_gl_command_batches_init (&self->batches, 128); gsk_gl_command_batches_init (&self->batches, 128);
gsk_gl_command_binds_init (&self->batch_binds, 1024); gsk_gl_command_binds_init (&self->batch_binds, 1024);
gsk_gl_command_uniforms_init (&self->batch_uniforms, 2048); gsk_gl_command_uniforms_init (&self->batch_uniforms, 2048);
gsk_gl_syncs_init (&self->syncs, 10);
gsk_gl_buffer_init (&self->vertices, GL_ARRAY_BUFFER, sizeof (GskGLDrawVertex)); gsk_gl_buffer_init (&self->vertices, GL_ARRAY_BUFFER, sizeof (GskGLDrawVertex));
} }
@@ -572,10 +570,7 @@ gsk_gl_command_queue_end_draw (GskGLCommandQueue *self)
g_assert (self->batches.len > 0); g_assert (self->batches.len > 0);
if (will_ignore_batch (self)) if (will_ignore_batch (self))
{ return;
self->in_draw = FALSE;
return;
}
batch = gsk_gl_command_batches_tail (&self->batches); batch = gsk_gl_command_batches_tail (&self->batches);
@@ -961,7 +956,7 @@ gsk_gl_command_queue_execute (GskGLCommandQueue *self,
guint default_framebuffer) guint default_framebuffer)
{ {
G_GNUC_UNUSED guint count = 0; G_GNUC_UNUSED guint count = 0;
graphene_rect_t scissor_test = GRAPHENE_RECT_INIT (0, 0, 0, 0); graphene_rect_t scissor_test;
gboolean has_scissor = scissor != NULL; gboolean has_scissor = scissor != NULL;
gboolean scissor_state = -1; gboolean scissor_state = -1;
guint program = 0; guint program = 0;
@@ -1100,25 +1095,17 @@ gsk_gl_command_queue_execute (GskGLCommandQueue *self,
if G_UNLIKELY (batch->draw.bind_count > 0) if G_UNLIKELY (batch->draw.bind_count > 0)
{ {
const GskGLCommandBind *bind = &self->batch_binds.items[batch->draw.bind_offset]; const GskGLCommandBind *bind = &self->batch_binds.items[batch->draw.bind_offset];
for (guint i = 0; i < batch->draw.bind_count; i++) for (guint i = 0; i < batch->draw.bind_count; i++)
{ {
if (textures[bind->texture] != bind->id) if (textures[bind->texture] != bind->id)
{ {
GskGLSync *s;
if (active != bind->texture) if (active != bind->texture)
{ {
active = bind->texture; active = bind->texture;
glActiveTexture (GL_TEXTURE0 + bind->texture); glActiveTexture (GL_TEXTURE0 + bind->texture);
} }
s = gsk_gl_syncs_get_sync (&self->syncs, bind->id);
if (s && s->sync)
{
glWaitSync ((GLsync) s->sync, 0, GL_TIMEOUT_IGNORED);
s->sync = NULL;
}
glBindTexture (GL_TEXTURE_2D, bind->id); glBindTexture (GL_TEXTURE_2D, bind->id);
textures[bind->texture] = bind->id; textures[bind->texture] = bind->id;
} }
@@ -1246,7 +1233,6 @@ gsk_gl_command_queue_end_frame (GskGLCommandQueue *self)
self->batches.len = 0; self->batches.len = 0;
self->batch_binds.len = 0; self->batch_binds.len = 0;
self->batch_uniforms.len = 0; self->batch_uniforms.len = 0;
self->syncs.len = 0;
self->n_uploads = 0; self->n_uploads = 0;
self->tail_batch_index = -1; self->tail_batch_index = -1;
self->in_frame = FALSE; self->in_frame = FALSE;
@@ -1453,7 +1439,8 @@ gsk_gl_command_queue_upload_texture (GskGLCommandQueue *self,
g_assert (GSK_IS_GL_COMMAND_QUEUE (self)); g_assert (GSK_IS_GL_COMMAND_QUEUE (self));
g_assert (!GDK_IS_GL_TEXTURE (texture)); g_assert (!GDK_IS_GL_TEXTURE (texture));
g_assert (mag_filter == GL_LINEAR || mag_filter == GL_NEAREST); g_assert (min_filter == GL_LINEAR || min_filter == GL_NEAREST);
g_assert (mag_filter == GL_LINEAR || min_filter == GL_NEAREST);
width = gdk_texture_get_width (texture); width = gdk_texture_get_width (texture);
height = gdk_texture_get_height (texture); height = gdk_texture_get_height (texture);
@@ -1477,9 +1464,6 @@ gsk_gl_command_queue_upload_texture (GskGLCommandQueue *self,
gsk_gl_command_queue_do_upload_texture (self, texture); gsk_gl_command_queue_do_upload_texture (self, texture);
if (min_filter == GL_LINEAR_MIPMAP_LINEAR)
glGenerateMipmap (GL_TEXTURE_2D);
/* Restore previous texture state if any */ /* Restore previous texture state if any */
if (self->attachments->textures[0].id > 0) if (self->attachments->textures[0].id > 0)
glBindTexture (self->attachments->textures[0].target, glBindTexture (self->attachments->textures[0].target,
-39
View File
@@ -167,15 +167,9 @@ typedef union _GskGLCommandBatch
G_STATIC_ASSERT (sizeof (GskGLCommandBatch) == 32); G_STATIC_ASSERT (sizeof (GskGLCommandBatch) == 32);
typedef struct _GskGLSync {
guint id;
gpointer sync;
} GskGLSync;
DEFINE_INLINE_ARRAY (GskGLCommandBatches, gsk_gl_command_batches, GskGLCommandBatch) DEFINE_INLINE_ARRAY (GskGLCommandBatches, gsk_gl_command_batches, GskGLCommandBatch)
DEFINE_INLINE_ARRAY (GskGLCommandBinds, gsk_gl_command_binds, GskGLCommandBind) DEFINE_INLINE_ARRAY (GskGLCommandBinds, gsk_gl_command_binds, GskGLCommandBind)
DEFINE_INLINE_ARRAY (GskGLCommandUniforms, gsk_gl_command_uniforms, GskGLCommandUniform) DEFINE_INLINE_ARRAY (GskGLCommandUniforms, gsk_gl_command_uniforms, GskGLCommandUniform)
DEFINE_INLINE_ARRAY (GskGLSyncs, gsk_gl_syncs, GskGLSync)
struct _GskGLCommandQueue struct _GskGLCommandQueue
{ {
@@ -231,8 +225,6 @@ struct _GskGLCommandQueue
*/ */
GskGLCommandUniforms batch_uniforms; GskGLCommandUniforms batch_uniforms;
GskGLSyncs syncs;
/* Discovered max texture size when loading the command queue so that we /* Discovered max texture size when loading the command queue so that we
* can either scale down or slice textures to fit within this size. Assumed * can either scale down or slice textures to fit within this size. Assumed
* to be both height and width. * to be both height and width.
@@ -362,37 +354,6 @@ gsk_gl_command_queue_bind_framebuffer (GskGLCommandQueue *self,
return ret; return ret;
} }
static inline GskGLSync *
gsk_gl_syncs_get_sync (GskGLSyncs *syncs,
guint id)
{
for (unsigned int i = 0; i < syncs->len; i++)
{
GskGLSync *sync = &syncs->items[i];
if (sync->id == id)
return sync;
}
return NULL;
}
static inline void
gsk_gl_syncs_add_sync (GskGLSyncs *syncs,
guint id,
gpointer sync)
{
GskGLSync *s;
s = gsk_gl_syncs_get_sync (syncs, id);
if (s)
g_assert (s->sync == sync);
else
{
s = gsk_gl_syncs_append (syncs);
s->id = id;
s->sync = sync;
}
}
G_END_DECLS G_END_DECLS
#endif /* __GSK_GL_COMMAND_QUEUE_PRIVATE_H__ */ #endif /* __GSK_GL_COMMAND_QUEUE_PRIVATE_H__ */
+19 -34
View File
@@ -753,7 +753,7 @@ gsk_gl_driver_load_texture (GskGLDriver *self,
{ {
if ((t = gdk_texture_get_render_data (texture, self))) if ((t = gdk_texture_get_render_data (texture, self)))
{ {
if (t->min_filter == min_filter && t->mag_filter == mag_filter && t->texture_id) if (t->min_filter == min_filter && t->mag_filter == mag_filter)
return t->texture_id; return t->texture_id;
} }
@@ -1195,10 +1195,6 @@ gsk_gl_driver_create_command_queue (GskGLDriver *self,
void void
gsk_gl_driver_add_texture_slices (GskGLDriver *self, gsk_gl_driver_add_texture_slices (GskGLDriver *self,
GdkTexture *texture, GdkTexture *texture,
int min_filter,
int mag_filter,
guint min_cols,
guint min_rows,
GskGLTextureSlice **out_slices, GskGLTextureSlice **out_slices,
guint *out_n_slices) guint *out_n_slices)
{ {
@@ -1220,37 +1216,31 @@ gsk_gl_driver_add_texture_slices (GskGLDriver *self,
/* XXX: Too much? */ /* XXX: Too much? */
max_texture_size = self->command_queue->max_texture_size / 4; max_texture_size = self->command_queue->max_texture_size / 4;
tex_width = texture->width; tex_width = texture->width;
tex_height = texture->height; tex_height = texture->height;
cols = (texture->width / max_texture_size) + 1;
cols = MAX ((texture->width / max_texture_size) + 1, min_cols); rows = (texture->height / max_texture_size) + 1;
rows = MAX ((texture->height / max_texture_size) + 1, min_rows);
n_slices = cols * rows;
if ((t = gdk_texture_get_render_data (texture, self))) if ((t = gdk_texture_get_render_data (texture, self)))
{ {
if (t->n_slices == n_slices) *out_slices = t->slices;
{ *out_n_slices = t->n_slices;
*out_slices = t->slices; return;
*out_n_slices = t->n_slices;
return;
}
gdk_texture_clear_render_data (texture);
} }
n_slices = cols * rows;
slices = g_new0 (GskGLTextureSlice, n_slices); slices = g_new0 (GskGLTextureSlice, n_slices);
memtex = gdk_memory_texture_from_texture (texture, memtex = gdk_memory_texture_from_texture (texture,
gdk_texture_get_format (texture)); gdk_texture_get_format (texture));
for (guint col = 0; col < cols; col++) for (guint col = 0; col < cols; col ++)
{ {
int slice_width = col + 1 < cols ? tex_width / cols : tex_width - x; int slice_width = MIN (max_texture_size, texture->width - x);
for (guint row = 0; row < rows; row++) for (guint row = 0; row < rows; row ++)
{ {
int slice_height = row + 1 < rows ? tex_height / rows : tex_height - y; int slice_height = MIN (max_texture_size, texture->height - y);
int slice_index = (col * rows) + row; int slice_index = (col * rows) + row;
GdkTexture *subtex; GdkTexture *subtex;
guint texture_id; guint texture_id;
@@ -1260,7 +1250,7 @@ gsk_gl_driver_add_texture_slices (GskGLDriver *self,
slice_width, slice_height); slice_width, slice_height);
texture_id = gsk_gl_command_queue_upload_texture (self->command_queue, texture_id = gsk_gl_command_queue_upload_texture (self->command_queue,
subtex, subtex,
min_filter, mag_filter); GL_NEAREST, GL_NEAREST);
g_object_unref (subtex); g_object_unref (subtex);
slices[slice_index].rect.x = x; slices[slice_index].rect.x = x;
@@ -1329,7 +1319,6 @@ typedef struct _GskGLTextureState
{ {
GdkGLContext *context; GdkGLContext *context;
GLuint texture_id; GLuint texture_id;
GLsync sync;
} GskGLTextureState; } GskGLTextureState;
static void static void
@@ -1342,7 +1331,6 @@ create_texture_from_texture_destroy (gpointer data)
gdk_gl_context_make_current (state->context); gdk_gl_context_make_current (state->context);
glDeleteTextures (1, &state->texture_id); glDeleteTextures (1, &state->texture_id);
glDeleteSync (state->sync);
g_clear_object (&state->context); g_clear_object (&state->context);
g_slice_free (GskGLTextureState, state); g_slice_free (GskGLTextureState, state);
} }
@@ -1377,13 +1365,10 @@ gsk_gl_driver_create_gdk_texture (GskGLDriver *self,
texture->texture_id = 0; texture->texture_id = 0;
gsk_gl_texture_free (texture); gsk_gl_texture_free (texture);
state->sync = glFenceSync (GL_SYNC_GPU_COMMANDS_COMPLETE, 0); return gdk_gl_texture_new (self->command_queue->context,
texture_id,
return gdk_gl_texture_new_with_sync (self->command_queue->context, width,
texture_id, height,
state->sync, create_texture_from_texture_destroy,
width, state);
height,
create_texture_from_texture_destroy,
state);
} }
+4 -15
View File
@@ -177,10 +177,6 @@ GskGLTexture * gsk_gl_driver_mark_texture_permanent (GskGLDriver *s
guint texture_id); guint texture_id);
void gsk_gl_driver_add_texture_slices (GskGLDriver *self, void gsk_gl_driver_add_texture_slices (GskGLDriver *self,
GdkTexture *texture, GdkTexture *texture,
int min_filter,
int mag_filter,
guint min_cols,
guint min_rows,
GskGLTextureSlice **out_slices, GskGLTextureSlice **out_slices,
guint *out_n_slices); guint *out_n_slices);
GskGLProgram * gsk_gl_driver_lookup_shader (GskGLDriver *self, GskGLProgram * gsk_gl_driver_lookup_shader (GskGLDriver *self,
@@ -232,10 +228,6 @@ gsk_gl_driver_lookup_texture (GskGLDriver *self,
static inline void static inline void
gsk_gl_driver_slice_texture (GskGLDriver *self, gsk_gl_driver_slice_texture (GskGLDriver *self,
GdkTexture *texture, GdkTexture *texture,
int min_filter,
int mag_filter,
guint min_cols,
guint min_rows,
GskGLTextureSlice **out_slices, GskGLTextureSlice **out_slices,
guint *out_n_slices) guint *out_n_slices)
{ {
@@ -243,15 +235,12 @@ gsk_gl_driver_slice_texture (GskGLDriver *self,
if ((t = gdk_texture_get_render_data (texture, self))) if ((t = gdk_texture_get_render_data (texture, self)))
{ {
if (min_cols == 0 && min_rows == 0) *out_slices = t->slices;
{ *out_n_slices = t->n_slices;
*out_slices = t->slices; return;
*out_n_slices = t->n_slices;
return;
}
} }
gsk_gl_driver_add_texture_slices (self, texture, min_filter, mag_filter, min_cols, min_rows, out_slices, out_n_slices); gsk_gl_driver_add_texture_slices (self, texture, out_slices, out_n_slices);
} }
G_END_DECLS G_END_DECLS
-21
View File
@@ -264,27 +264,6 @@ gsk_gl_program_set_uniform_texture (GskGLProgram *self,
texture_slot); texture_slot);
} }
static inline void
gsk_gl_program_set_uniform_texture_with_sync (GskGLProgram *self,
guint key,
guint stamp,
GLenum texture_target,
GLenum texture_slot,
guint texture_id,
gpointer sync)
{
gsk_gl_attachment_state_bind_texture (self->driver->command_queue->attachments,
texture_target,
texture_slot,
texture_id);
gsk_gl_uniform_state_set_texture (self->uniforms,
self->program_info,
key,
stamp,
texture_slot);
gsk_gl_syncs_add_sync (&self->driver->command_queue->syncs, texture_id, sync);
}
static inline void static inline void
gsk_gl_program_set_uniform_matrix (GskGLProgram *self, gsk_gl_program_set_uniform_matrix (GskGLProgram *self,
guint key, guint key,
-4
View File
@@ -60,10 +60,6 @@ GSK_GL_DEFINE_PROGRAM (linear_gradient,
GSK_GL_ADD_UNIFORM (3, LINEAR_GRADIENT_POINTS, u_points) GSK_GL_ADD_UNIFORM (3, LINEAR_GRADIENT_POINTS, u_points)
GSK_GL_ADD_UNIFORM (4, LINEAR_GRADIENT_REPEAT, u_repeat)) GSK_GL_ADD_UNIFORM (4, LINEAR_GRADIENT_REPEAT, u_repeat))
GSK_GL_DEFINE_PROGRAM (mask,
GSK_GL_SHADER_SINGLE (GSK_GL_SHADER_RESOURCE ("mask.glsl")),
GSK_GL_ADD_UNIFORM (1, MASK_SOURCE, u_mask))
GSK_GL_DEFINE_PROGRAM (outset_shadow, GSK_GL_DEFINE_PROGRAM (outset_shadow,
GSK_GL_SHADER_SINGLE (GSK_GL_SHADER_RESOURCE ("outset_shadow.glsl")), GSK_GL_SHADER_SINGLE (GSK_GL_SHADER_RESOURCE ("outset_shadow.glsl")),
GSK_GL_ADD_UNIFORM (1, OUTSET_SHADOW_OUTLINE_RECT, u_outline_rect)) GSK_GL_ADD_UNIFORM (1, OUTSET_SHADOW_OUTLINE_RECT, u_outline_rect))
+19 -236
View File
@@ -190,7 +190,6 @@ typedef struct _GskGLRenderOffscreen
/* Return location for texture ID */ /* Return location for texture ID */
guint texture_id; guint texture_id;
gpointer sync;
/* Whether to force creating a new texture, even if the /* Whether to force creating a new texture, even if the
* input already is a texture * input already is a texture
@@ -3278,56 +3277,6 @@ gsk_gl_render_job_visit_blend_node (GskGLRenderJob *job,
gsk_gl_render_job_end_draw (job); gsk_gl_render_job_end_draw (job);
} }
static inline void
gsk_gl_render_job_visit_mask_node (GskGLRenderJob *job,
const GskRenderNode *node)
{
const GskRenderNode *source = gsk_mask_node_get_source (node);
const GskRenderNode *mask = gsk_mask_node_get_mask (node);
GskGLRenderOffscreen source_offscreen = {0};
GskGLRenderOffscreen mask_offscreen = {0};
source_offscreen.bounds = &node->bounds;
source_offscreen.force_offscreen = TRUE;
source_offscreen.reset_clip = TRUE;
mask_offscreen.bounds = &node->bounds;
mask_offscreen.force_offscreen = TRUE;
mask_offscreen.reset_clip = TRUE;
/* TODO: We create 2 textures here as big as the mask node, but both
* nodes might be a lot smaller than that.
*/
if (!gsk_gl_render_job_visit_node_with_offscreen (job, source, &source_offscreen))
{
gsk_gl_render_job_visit_node (job, source);
return;
}
g_assert (source_offscreen.was_offscreen);
if (!gsk_gl_render_job_visit_node_with_offscreen (job, mask, &mask_offscreen))
{
return;
}
g_assert (mask_offscreen.was_offscreen);
gsk_gl_render_job_begin_draw (job, CHOOSE_PROGRAM (job, mask));
gsk_gl_program_set_uniform_texture (job->current_program,
UNIFORM_SHARED_SOURCE, 0,
GL_TEXTURE_2D,
GL_TEXTURE0,
source_offscreen.texture_id);
gsk_gl_program_set_uniform_texture (job->current_program,
UNIFORM_MASK_SOURCE, 0,
GL_TEXTURE_2D,
GL_TEXTURE1,
mask_offscreen.texture_id);
gsk_gl_render_job_draw_offscreen_rect (job, &node->bounds);
gsk_gl_render_job_end_draw (job);
}
static inline void static inline void
gsk_gl_render_job_visit_color_matrix_node (GskGLRenderJob *job, gsk_gl_render_job_visit_color_matrix_node (GskGLRenderJob *job,
const GskRenderNode *node) const GskRenderNode *node)
@@ -3494,21 +3443,12 @@ gsk_gl_render_job_visit_gl_shader_node (GskGLRenderJob *job,
static void static void
gsk_gl_render_job_upload_texture (GskGLRenderJob *job, gsk_gl_render_job_upload_texture (GskGLRenderJob *job,
GdkTexture *texture, GdkTexture *texture,
int min_filter,
int mag_filter,
GskGLRenderOffscreen *offscreen) GskGLRenderOffscreen *offscreen)
{ {
GdkGLTexture *gl_texture = NULL; if (gsk_gl_texture_library_can_cache ((GskGLTextureLibrary *)job->driver->icons_library,
if (GDK_IS_GL_TEXTURE (texture))
gl_texture = (GdkGLTexture *) texture;
if (min_filter == GL_LINEAR &&
mag_filter == GL_LINEAR &&
gsk_gl_texture_library_can_cache ((GskGLTextureLibrary *)job->driver->icons_library,
texture->width, texture->width,
texture->height) && texture->height) &&
!gl_texture) !GDK_IS_GL_TEXTURE (texture))
{ {
const GskGLIconData *icon_data; const GskGLIconData *icon_data;
@@ -3518,19 +3458,16 @@ gsk_gl_render_job_upload_texture (GskGLRenderJob *job,
} }
else else
{ {
offscreen->texture_id = gsk_gl_driver_load_texture (job->driver, texture, min_filter, mag_filter); offscreen->texture_id = gsk_gl_driver_load_texture (job->driver, texture, GL_LINEAR, GL_LINEAR);
init_full_texture_region (offscreen); init_full_texture_region (offscreen);
if (gl_texture && offscreen->texture_id == gdk_gl_texture_get_id (gl_texture) &&
gdk_gl_texture_get_context (gl_texture) != gsk_gl_command_queue_get_context (job->command_queue))
offscreen->sync = gdk_gl_texture_get_sync (gl_texture);
} }
} }
static inline void static inline void
gsk_gl_render_job_visit_texture (GskGLRenderJob *job, gsk_gl_render_job_visit_texture_node (GskGLRenderJob *job,
GdkTexture *texture, const GskRenderNode *node)
const graphene_rect_t *bounds)
{ {
GdkTexture *texture = gsk_texture_node_get_texture (node);
int max_texture_size = job->command_queue->max_texture_size; int max_texture_size = job->command_queue->max_texture_size;
if G_LIKELY (texture->width <= max_texture_size && if G_LIKELY (texture->width <= max_texture_size &&
@@ -3538,33 +3475,32 @@ gsk_gl_render_job_visit_texture (GskGLRenderJob *job,
{ {
GskGLRenderOffscreen offscreen = {0}; GskGLRenderOffscreen offscreen = {0};
gsk_gl_render_job_upload_texture (job, texture, GL_LINEAR, GL_LINEAR, &offscreen); gsk_gl_render_job_upload_texture (job, texture, &offscreen);
g_assert (offscreen.texture_id); g_assert (offscreen.texture_id);
g_assert (offscreen.was_offscreen == FALSE); g_assert (offscreen.was_offscreen == FALSE);
gsk_gl_render_job_begin_draw (job, CHOOSE_PROGRAM (job, blit)); gsk_gl_render_job_begin_draw (job, CHOOSE_PROGRAM (job, blit));
gsk_gl_program_set_uniform_texture_with_sync (job->current_program, gsk_gl_program_set_uniform_texture (job->current_program,
UNIFORM_SHARED_SOURCE, 0, UNIFORM_SHARED_SOURCE, 0,
GL_TEXTURE_2D, GL_TEXTURE_2D,
GL_TEXTURE0, GL_TEXTURE0,
offscreen.texture_id, offscreen.texture_id);
offscreen.sync); gsk_gl_render_job_draw_offscreen (job, &node->bounds, &offscreen);
gsk_gl_render_job_draw_offscreen (job, bounds, &offscreen);
gsk_gl_render_job_end_draw (job); gsk_gl_render_job_end_draw (job);
} }
else else
{ {
float min_x = job->offset_x + bounds->origin.x; float min_x = job->offset_x + node->bounds.origin.x;
float min_y = job->offset_y + bounds->origin.y; float min_y = job->offset_y + node->bounds.origin.y;
float max_x = min_x + bounds->size.width; float max_x = min_x + node->bounds.size.width;
float max_y = min_y + bounds->size.height; float max_y = min_y + node->bounds.size.height;
float scale_x = (max_x - min_x) / texture->width; float scale_x = (max_x - min_x) / texture->width;
float scale_y = (max_y - min_y) / texture->height; float scale_y = (max_y - min_y) / texture->height;
GskGLTextureSlice *slices = NULL; GskGLTextureSlice *slices = NULL;
guint n_slices = 0; guint n_slices = 0;
gsk_gl_driver_slice_texture (job->driver, texture, GL_NEAREST, GL_NEAREST, 0, 0, &slices, &n_slices); gsk_gl_driver_slice_texture (job->driver, texture, &slices, &n_slices);
g_assert (slices != NULL); g_assert (slices != NULL);
g_assert (n_slices > 0); g_assert (n_slices > 0);
@@ -3599,151 +3535,6 @@ gsk_gl_render_job_visit_texture (GskGLRenderJob *job,
} }
} }
static inline void
gsk_gl_render_job_visit_texture_node (GskGLRenderJob *job,
const GskRenderNode *node)
{
GdkTexture *texture = gsk_texture_node_get_texture (node);
const graphene_rect_t *bounds = &node->bounds;
gsk_gl_render_job_visit_texture (job, texture, bounds);
}
static inline void
gsk_gl_render_job_visit_texture_scale_node (GskGLRenderJob *job,
const GskRenderNode *node)
{
GdkTexture *texture = gsk_texture_scale_node_get_texture (node);
const graphene_rect_t *bounds = &node->bounds;
GskScalingFilter scaling_filter = gsk_texture_scale_node_get_filter (node);
int min_filters[] = { GL_LINEAR, GL_NEAREST, GL_LINEAR_MIPMAP_LINEAR };
int mag_filters[] = { GL_LINEAR, GL_NEAREST, GL_LINEAR };
int min_filter = min_filters[scaling_filter];
int mag_filter = mag_filters[scaling_filter];
int max_texture_size = job->command_queue->max_texture_size;
if (scaling_filter == GSK_SCALING_FILTER_LINEAR)
{
gsk_gl_render_job_visit_texture (job, texture, bounds);
return;
}
if G_LIKELY (texture->width <= max_texture_size &&
texture->height <= max_texture_size)
{
GskGLRenderTarget *render_target;
GskGLRenderOffscreen offscreen = {0};
graphene_rect_t viewport;
graphene_rect_t prev_viewport;
graphene_matrix_t prev_projection;
float prev_alpha;
guint prev_fbo;
guint texture_id;
viewport = GRAPHENE_RECT_INIT (0, 0,
bounds->size.width,
bounds->size.height);
if (!gsk_gl_driver_create_render_target (job->driver,
(int) ceilf (viewport.size.width),
(int) ceilf (viewport.size.height),
get_target_format (job, node),
GL_LINEAR, GL_LINEAR,
&render_target))
{
/* viewport is too big, slice the texture and try again */
goto slice;
}
gsk_gl_render_job_upload_texture (job, texture, min_filter, mag_filter, &offscreen);
g_assert (offscreen.texture_id);
g_assert (offscreen.was_offscreen == FALSE);
gsk_gl_render_job_set_viewport (job, &viewport, &prev_viewport);
gsk_gl_render_job_set_projection_from_rect (job, &viewport, &prev_projection);
gsk_gl_render_job_set_modelview (job, NULL);
prev_alpha = gsk_gl_render_job_set_alpha (job, 1.0f);
gsk_gl_render_job_push_clip (job, &GSK_ROUNDED_RECT_INIT_FROM_RECT (viewport));
prev_fbo = gsk_gl_command_queue_bind_framebuffer (job->command_queue, render_target->framebuffer_id);
gsk_gl_command_queue_clear (job->command_queue, 0, &viewport);
gsk_gl_render_job_begin_draw (job, CHOOSE_PROGRAM (job, blit));
gsk_gl_program_set_uniform_texture (job->current_program,
UNIFORM_SHARED_SOURCE, 0,
GL_TEXTURE_2D,
GL_TEXTURE0,
offscreen.texture_id);
gsk_gl_render_job_draw_offscreen (job, &viewport, &offscreen);
gsk_gl_render_job_end_draw (job);
gsk_gl_render_job_pop_clip (job);
gsk_gl_render_job_pop_modelview (job);
gsk_gl_render_job_set_viewport (job, &prev_viewport, NULL);
gsk_gl_render_job_set_projection (job, &prev_projection);
gsk_gl_render_job_set_alpha (job, prev_alpha);
gsk_gl_command_queue_bind_framebuffer (job->command_queue, prev_fbo);
texture_id = gsk_gl_driver_release_render_target (job->driver, render_target, FALSE);
gsk_gl_render_job_begin_draw (job, CHOOSE_PROGRAM (job, blit));
gsk_gl_program_set_uniform_texture (job->current_program,
UNIFORM_SHARED_SOURCE, 0,
GL_TEXTURE_2D,
GL_TEXTURE0,
texture_id);
gsk_gl_render_job_draw_offscreen_rect (job, bounds);
gsk_gl_render_job_end_draw (job);
}
else
{
slice:
float min_x = bounds->origin.x;
float min_y = bounds->origin.y;
float max_x = min_x + bounds->size.width;
float max_y = min_y + bounds->size.height;
float scale_x = (max_x - min_x) / texture->width;
float scale_y = (max_y - min_y) / texture->height;
GskGLTextureSlice *slices = NULL;
guint n_slices = 0;
GdkGLContext *context = gsk_gl_driver_get_context (job->driver);
guint rows, cols;
/* Slice enough that neither the original texture nor the scaled texture
* exceed the texture size limit
*/
cols = (int)(MAX (bounds->size.width, texture->width) / (max_texture_size / 4)) + 1;
rows = (int)(MAX (bounds->size.height, texture->height) / (max_texture_size / 4)) + 1;
gsk_gl_driver_slice_texture (job->driver, texture, GL_NEAREST, GL_NEAREST, cols, rows, &slices, &n_slices);
g_assert (slices != NULL);
g_assert (n_slices > 0);
for (guint i = 0; i < n_slices; i ++)
{
const GskGLTextureSlice *slice = &slices[i];
float x1, x2, y1, y2;
GdkTexture *sub_texture;
GskRenderNode *sub_node;
x1 = min_x + (scale_x * slice->rect.x);
x2 = x1 + (slice->rect.width * scale_x);
y1 = min_y + (scale_y * slice->rect.y);
y2 = y1 + (slice->rect.height * scale_y);
sub_texture = gdk_gl_texture_new (context, slice->texture_id, slice->rect.width, slice->rect.height, NULL, NULL);
sub_node = gsk_texture_scale_node_new (sub_texture, &GRAPHENE_RECT_INIT (x1, y1, x2 - x1, y2 - y1), scaling_filter);
gsk_gl_render_job_visit_node (job, sub_node);
gsk_render_node_unref (sub_node);
g_object_unref (sub_texture);
}
}
}
static inline void static inline void
gsk_gl_render_job_visit_repeat_node (GskGLRenderJob *job, gsk_gl_render_job_visit_repeat_node (GskGLRenderJob *job,
const GskRenderNode *node) const GskRenderNode *node)
@@ -3929,10 +3720,6 @@ gsk_gl_render_job_visit_node (GskGLRenderJob *job,
gsk_gl_render_job_visit_as_fallback (job, node); gsk_gl_render_job_visit_as_fallback (job, node);
break; break;
case GSK_MASK_NODE:
gsk_gl_render_job_visit_mask_node (job, node);
break;
case GSK_OPACITY_NODE: case GSK_OPACITY_NODE:
gsk_gl_render_job_visit_opacity_node (job, node); gsk_gl_render_job_visit_opacity_node (job, node);
break; break;
@@ -3975,10 +3762,6 @@ gsk_gl_render_job_visit_node (GskGLRenderJob *job,
gsk_gl_render_job_visit_texture_node (job, node); gsk_gl_render_job_visit_texture_node (job, node);
break; break;
case GSK_TEXTURE_SCALE_NODE:
gsk_gl_render_job_visit_texture_scale_node (job, node);
break;
case GSK_TRANSFORM_NODE: case GSK_TRANSFORM_NODE:
gsk_gl_render_job_visit_transform_node (job, node); gsk_gl_render_job_visit_transform_node (job, node);
break; break;
@@ -4025,7 +3808,7 @@ gsk_gl_render_job_visit_node_with_offscreen (GskGLRenderJob *job,
offscreen->force_offscreen == FALSE) offscreen->force_offscreen == FALSE)
{ {
GdkTexture *texture = gsk_texture_node_get_texture (node); GdkTexture *texture = gsk_texture_node_get_texture (node);
gsk_gl_render_job_upload_texture (job, texture, GL_LINEAR, GL_LINEAR, offscreen); gsk_gl_render_job_upload_texture (job, texture, offscreen);
g_assert (offscreen->was_offscreen == FALSE); g_assert (offscreen->was_offscreen == FALSE);
return TRUE; return TRUE;
} }
+1 -2
View File
@@ -112,8 +112,7 @@ gsk_gl_texture_library_real_compact (GskGLTextureLibrary *self,
{ {
if (!entry->accessed) if (!entry->accessed)
{ {
if (entry->texture) gsk_gl_driver_release_texture (self->driver, entry->texture);
gsk_gl_driver_release_texture (self->driver, entry->texture);
g_hash_table_iter_remove (&iter); g_hash_table_iter_remove (&iter);
dropped++; dropped++;
} }
-19
View File
@@ -1,19 +0,0 @@
// VERTEX_SHADER:
// mask.glsl
void main() {
gl_Position = u_projection * u_modelview * vec4(aPosition, 0.0, 1.0);
vUv = vec2(aUv.x, aUv.y);
}
// FRAGMENT_SHADER:
// mask.glsl
uniform sampler2D u_mask;
void main() {
vec4 source = GskTexture(u_source, vUv);
vec4 mask = GskTexture(u_mask, vUv);
gskSetOutputColor(vec4 (source * mask.a));
}
-4
View File
@@ -35,7 +35,6 @@
* @GSK_CONIC_GRADIENT_NODE: A node drawing a conic gradient * @GSK_CONIC_GRADIENT_NODE: A node drawing a conic gradient
* @GSK_BORDER_NODE: A node stroking a border around an area * @GSK_BORDER_NODE: A node stroking a border around an area
* @GSK_TEXTURE_NODE: A node drawing a `GdkTexture` * @GSK_TEXTURE_NODE: A node drawing a `GdkTexture`
* @GSK_TEXTURE_SCALE_NODE: A node drawing a `GdkTexture` scaled and filtered
* @GSK_INSET_SHADOW_NODE: A node drawing an inset shadow * @GSK_INSET_SHADOW_NODE: A node drawing an inset shadow
* @GSK_OUTSET_SHADOW_NODE: A node drawing an outset shadow * @GSK_OUTSET_SHADOW_NODE: A node drawing an outset shadow
* @GSK_TRANSFORM_NODE: A node that renders its child after applying a matrix transform * @GSK_TRANSFORM_NODE: A node that renders its child after applying a matrix transform
@@ -46,7 +45,6 @@
* @GSK_ROUNDED_CLIP_NODE: A node that clips its child to a rounded rectangle * @GSK_ROUNDED_CLIP_NODE: A node that clips its child to a rounded rectangle
* @GSK_SHADOW_NODE: A node that draws a shadow below its child * @GSK_SHADOW_NODE: A node that draws a shadow below its child
* @GSK_BLEND_NODE: A node that blends two children together * @GSK_BLEND_NODE: A node that blends two children together
* @GSK_MASK_NODE: A node that masks one child with another
* @GSK_CROSS_FADE_NODE: A node that cross-fades between two children * @GSK_CROSS_FADE_NODE: A node that cross-fades between two children
* @GSK_TEXT_NODE: A node containing a glyph string * @GSK_TEXT_NODE: A node containing a glyph string
* @GSK_BLUR_NODE: A node that applies a blur * @GSK_BLUR_NODE: A node that applies a blur
@@ -67,7 +65,6 @@ typedef enum {
GSK_CONIC_GRADIENT_NODE, GSK_CONIC_GRADIENT_NODE,
GSK_BORDER_NODE, GSK_BORDER_NODE,
GSK_TEXTURE_NODE, GSK_TEXTURE_NODE,
GSK_TEXTURE_SCALE_NODE,
GSK_INSET_SHADOW_NODE, GSK_INSET_SHADOW_NODE,
GSK_OUTSET_SHADOW_NODE, GSK_OUTSET_SHADOW_NODE,
GSK_TRANSFORM_NODE, GSK_TRANSFORM_NODE,
@@ -78,7 +75,6 @@ typedef enum {
GSK_ROUNDED_CLIP_NODE, GSK_ROUNDED_CLIP_NODE,
GSK_SHADOW_NODE, GSK_SHADOW_NODE,
GSK_BLEND_NODE, GSK_BLEND_NODE,
GSK_MASK_NODE,
GSK_CROSS_FADE_NODE, GSK_CROSS_FADE_NODE,
GSK_TEXT_NODE, GSK_TEXT_NODE,
GSK_BLUR_NODE, GSK_BLUR_NODE,
+1 -26
View File
@@ -142,7 +142,6 @@ GskRenderNode * gsk_render_node_deserialize (GBytes
#define GSK_TYPE_DEBUG_NODE (gsk_debug_node_get_type()) #define GSK_TYPE_DEBUG_NODE (gsk_debug_node_get_type())
#define GSK_TYPE_COLOR_NODE (gsk_color_node_get_type()) #define GSK_TYPE_COLOR_NODE (gsk_color_node_get_type())
#define GSK_TYPE_TEXTURE_NODE (gsk_texture_node_get_type()) #define GSK_TYPE_TEXTURE_NODE (gsk_texture_node_get_type())
#define GSK_TYPE_TEXTURE_SCALE_NODE (gsk_texture_scale_node_get_type())
#define GSK_TYPE_LINEAR_GRADIENT_NODE (gsk_linear_gradient_node_get_type()) #define GSK_TYPE_LINEAR_GRADIENT_NODE (gsk_linear_gradient_node_get_type())
#define GSK_TYPE_REPEATING_LINEAR_GRADIENT_NODE (gsk_repeating_linear_gradient_node_get_type()) #define GSK_TYPE_REPEATING_LINEAR_GRADIENT_NODE (gsk_repeating_linear_gradient_node_get_type())
#define GSK_TYPE_RADIAL_GRADIENT_NODE (gsk_radial_gradient_node_get_type()) #define GSK_TYPE_RADIAL_GRADIENT_NODE (gsk_radial_gradient_node_get_type())
@@ -164,13 +163,11 @@ GskRenderNode * gsk_render_node_deserialize (GBytes
#define GSK_TYPE_CROSS_FADE_NODE (gsk_cross_fade_node_get_type()) #define GSK_TYPE_CROSS_FADE_NODE (gsk_cross_fade_node_get_type())
#define GSK_TYPE_TEXT_NODE (gsk_text_node_get_type()) #define GSK_TYPE_TEXT_NODE (gsk_text_node_get_type())
#define GSK_TYPE_BLUR_NODE (gsk_blur_node_get_type()) #define GSK_TYPE_BLUR_NODE (gsk_blur_node_get_type())
#define GSK_TYPE_MASK_NODE (gsk_mask_node_get_type())
#define GSK_TYPE_GL_SHADER_NODE (gsk_gl_shader_node_get_type()) #define GSK_TYPE_GL_SHADER_NODE (gsk_gl_shader_node_get_type())
typedef struct _GskDebugNode GskDebugNode; typedef struct _GskDebugNode GskDebugNode;
typedef struct _GskColorNode GskColorNode; typedef struct _GskColorNode GskColorNode;
typedef struct _GskTextureNode GskTextureNode; typedef struct _GskTextureNode GskTextureNode;
typedef struct _GskTextureScaleNode GskTextureScaleNode;
typedef struct _GskLinearGradientNode GskLinearGradientNode; typedef struct _GskLinearGradientNode GskLinearGradientNode;
typedef struct _GskRepeatingLinearGradientNode GskRepeatingLinearGradientNode; typedef struct _GskRepeatingLinearGradientNode GskRepeatingLinearGradientNode;
typedef struct _GskRadialGradientNode GskRadialGradientNode; typedef struct _GskRadialGradientNode GskRadialGradientNode;
@@ -192,7 +189,6 @@ typedef struct _GskBlendNode GskBlendNode;
typedef struct _GskCrossFadeNode GskCrossFadeNode; typedef struct _GskCrossFadeNode GskCrossFadeNode;
typedef struct _GskTextNode GskTextNode; typedef struct _GskTextNode GskTextNode;
typedef struct _GskBlurNode GskBlurNode; typedef struct _GskBlurNode GskBlurNode;
typedef struct _GskMaskNode GskMaskNode;
typedef struct _GskGLShaderNode GskGLShaderNode; typedef struct _GskGLShaderNode GskGLShaderNode;
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
@@ -221,17 +217,6 @@ GskRenderNode * gsk_texture_node_new (GdkTexture
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GdkTexture * gsk_texture_node_get_texture (const GskRenderNode *node) G_GNUC_PURE; GdkTexture * gsk_texture_node_get_texture (const GskRenderNode *node) G_GNUC_PURE;
GDK_AVAILABLE_IN_4_10
GType gsk_texture_scale_node_get_type (void) G_GNUC_CONST;
GDK_AVAILABLE_IN_4_10
GskRenderNode * gsk_texture_scale_node_new (GdkTexture *texture,
const graphene_rect_t *bounds,
GskScalingFilter filter);
GDK_AVAILABLE_IN_4_10
GdkTexture * gsk_texture_scale_node_get_texture (const GskRenderNode *node) G_GNUC_PURE;
GDK_AVAILABLE_IN_4_10
GskScalingFilter gsk_texture_scale_node_get_filter (const GskRenderNode *node) G_GNUC_PURE;
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GType gsk_linear_gradient_node_get_type (void) G_GNUC_CONST; GType gsk_linear_gradient_node_get_type (void) G_GNUC_CONST;
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
@@ -531,18 +516,8 @@ GskRenderNode * gsk_blur_node_get_child (const GskRender
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
float gsk_blur_node_get_radius (const GskRenderNode *node) G_GNUC_PURE; float gsk_blur_node_get_radius (const GskRenderNode *node) G_GNUC_PURE;
GDK_AVAILABLE_IN_4_10
GType gsk_mask_node_get_type (void) G_GNUC_CONST;
GDK_AVAILABLE_IN_4_10
GskRenderNode * gsk_mask_node_new (GskRenderNode *source,
GskRenderNode *mask);
GDK_AVAILABLE_IN_4_10
GskRenderNode * gsk_mask_node_get_source (const GskRenderNode *node);
GDK_AVAILABLE_IN_4_10
GskRenderNode * gsk_mask_node_get_mask (const GskRenderNode *node);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GType gsk_gl_shader_node_get_type (void) G_GNUC_CONST; GType gsk_gl_shader_node_get_type (void) G_GNUC_CONST;
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GskRenderNode * gsk_gl_shader_node_new (GskGLShader *shader, GskRenderNode * gsk_gl_shader_node_new (GskGLShader *shader,
const graphene_rect_t *bounds, const graphene_rect_t *bounds,
+23 -397
View File
@@ -58,7 +58,7 @@ rectangle_init_from_graphene (cairo_rectangle_int_t *cairo,
cairo->height = ceilf (graphene->origin.y + graphene->size.height) - cairo->y; cairo->height = ceilf (graphene->origin.y + graphene->size.height) - cairo->y;
} }
/* {{{ GSK_COLOR_NODE */ /*** GSK_COLOR_NODE ***/
/** /**
* GskColorNode: * GskColorNode:
@@ -147,8 +147,7 @@ gsk_color_node_new (const GdkRGBA *rgba,
return node; return node;
} }
/* }}} */ /*** GSK_LINEAR_GRADIENT_NODE ***/
/* {{{ GSK_LINEAR_GRADIENT_NODE */
/** /**
* GskRepeatingLinearGradientNode: * GskRepeatingLinearGradientNode:
@@ -421,8 +420,7 @@ gsk_linear_gradient_node_get_color_stops (const GskRenderNode *node,
return self->stops; return self->stops;
} }
/* }}} */ /*** GSK_RADIAL_GRADIENT_NODE ***/
/* {{{ GSK_RADIAL_GRADIENT_NODE */
/** /**
* GskRepeatingRadialGradientNode: * GskRepeatingRadialGradientNode:
@@ -792,8 +790,7 @@ gsk_radial_gradient_node_get_end (const GskRenderNode *node)
return self->end; return self->end;
} }
/* }}} */ /*** GSK_CONIC_GRADIENT_NODE ***/
/* {{{ GSK_CONIC_GRADIENT_NODE */
/** /**
* GskConicGradientNode: * GskConicGradientNode:
@@ -1150,8 +1147,7 @@ gsk_conic_gradient_node_get_angle (const GskRenderNode *node)
return self->angle; return self->angle;
} }
/* }}} */ /*** GSK_BORDER_NODE ***/
/* {{{ GSK_BORDER_NODE */
/** /**
* GskBorderNode: * GskBorderNode:
@@ -1463,8 +1459,7 @@ gsk_border_node_get_uniform_color (const GskRenderNode *self)
return node->uniform_color; return node->uniform_color;
} }
/* }}} */ /*** GSK_TEXTURE_NODE ***/
/* {{{ GSK_TEXTURE_NODE */
/** /**
* GskTextureNode: * GskTextureNode:
@@ -1581,193 +1576,7 @@ gsk_texture_node_new (GdkTexture *texture,
return node; return node;
} }
/* }}} */ /*** GSK_INSET_SHADOW_NODE ***/
/* {{{ GSK_TEXTURE_SCALE_NODE */
/**
* GskTextureScaleNode:
*
* A render node for a `GdkTexture`.
*/
struct _GskTextureScaleNode
{
GskRenderNode render_node;
GdkTexture *texture;
GskScalingFilter filter;
};
static void
gsk_texture_scale_node_finalize (GskRenderNode *node)
{
GskTextureScaleNode *self = (GskTextureScaleNode *) node;
GskRenderNodeClass *parent_class = g_type_class_peek (g_type_parent (GSK_TYPE_TEXTURE_SCALE_NODE));
g_clear_object (&self->texture);
parent_class->finalize (node);
}
static void
gsk_texture_scale_node_draw (GskRenderNode *node,
cairo_t *cr)
{
GskTextureScaleNode *self = (GskTextureScaleNode *) node;
cairo_surface_t *surface;
cairo_pattern_t *pattern;
cairo_matrix_t matrix;
cairo_filter_t filters[] = {
CAIRO_FILTER_BILINEAR,
CAIRO_FILTER_NEAREST,
CAIRO_FILTER_GOOD,
};
cairo_t *cr2;
cairo_surface_t *surface2;
surface2 = cairo_image_surface_create (CAIRO_FORMAT_ARGB32,
(int) ceilf (node->bounds.size.width),
(int) ceilf (node->bounds.size.height));
cr2 = cairo_create (surface2);
cairo_set_source_rgba (cr2, 0, 0, 0, 0);
cairo_paint (cr2);
surface = gdk_texture_download_surface (self->texture);
pattern = cairo_pattern_create_for_surface (surface);
cairo_pattern_set_extend (pattern, CAIRO_EXTEND_PAD);
cairo_matrix_init_scale (&matrix,
gdk_texture_get_width (self->texture) / node->bounds.size.width,
gdk_texture_get_height (self->texture) / node->bounds.size.height);
cairo_pattern_set_matrix (pattern, &matrix);
cairo_pattern_set_filter (pattern, filters[self->filter]);
cairo_set_source (cr2, pattern);
cairo_pattern_destroy (pattern);
cairo_surface_destroy (surface);
cairo_rectangle (cr2, 0, 0, node->bounds.size.width, node->bounds.size.height);
cairo_fill (cr2);
cairo_destroy (cr2);
cairo_save (cr);
pattern = cairo_pattern_create_for_surface (surface2);
cairo_pattern_set_extend (pattern, CAIRO_EXTEND_PAD);
cairo_matrix_init_identity (&matrix);
cairo_matrix_translate (&matrix,
-node->bounds.origin.x,
-node->bounds.origin.y);
cairo_pattern_set_matrix (pattern, &matrix);
cairo_set_source (cr, pattern);
cairo_pattern_destroy (pattern);
cairo_surface_destroy (surface2);
gsk_cairo_rectangle (cr, &node->bounds);
cairo_fill (cr);
cairo_restore (cr);
}
static void
gsk_texture_scale_node_diff (GskRenderNode *node1,
GskRenderNode *node2,
cairo_region_t *region)
{
GskTextureScaleNode *self1 = (GskTextureScaleNode *) node1;
GskTextureScaleNode *self2 = (GskTextureScaleNode *) node2;
if (graphene_rect_equal (&node1->bounds, &node2->bounds) &&
self1->texture == self2->texture &&
self1->filter == self2->filter)
return;
gsk_render_node_diff_impossible (node1, node2, region);
}
/**
* gsk_texture_scale_node_get_texture:
* @node: (type GskTextureNode): a `GskRenderNode` of type %GSK_TEXTURE_SCALE_NODE
*
* Retrieves the `GdkTexture` used when creating this `GskRenderNode`.
*
* Returns: (transfer none): the `GdkTexture`
*
* Since: 4.10
*/
GdkTexture *
gsk_texture_scale_node_get_texture (const GskRenderNode *node)
{
const GskTextureScaleNode *self = (const GskTextureScaleNode *) node;
return self->texture;
}
/**
* gsk_texture_scale_node_get_filter:
* @node: (type GskTextureNode): a `GskRenderNode` of type %GSK_TEXTURE_SCALE_NODE
*
* Retrieves the `GskScalingFilter` used when creating this `GskRenderNode`.
*
* Returns: (transfer none): the `GskScalingFilter`
*
* Since: 4.10
*/
GskScalingFilter
gsk_texture_scale_node_get_filter (const GskRenderNode *node)
{
const GskTextureScaleNode *self = (const GskTextureScaleNode *) node;
return self->filter;
}
/**
* gsk_texture_scale_node_new:
* @texture: the texture to scale
* @bounds: the size of the texture to scale to
* @filter: how to scale the texture
*
* Creates a node that scales the texture to the size given by the
* bounds and the filter and then places it at the bounds' position.
*
* This node is intended for tight control over scaling applied
* to a texture, such as in image editors and requires the
* application to be aware of the whole render tree as further
* transforms may be applied that conflict with the desired effect
* of this node.
*
* Returns: (transfer full) (type GskTextureScaleNode): A new `GskRenderNode`
*
* Since: 4.10
*/
GskRenderNode *
gsk_texture_scale_node_new (GdkTexture *texture,
const graphene_rect_t *bounds,
GskScalingFilter filter)
{
GskTextureScaleNode *self;
GskRenderNode *node;
g_return_val_if_fail (GDK_IS_TEXTURE (texture), NULL);
g_return_val_if_fail (bounds != NULL, NULL);
self = gsk_render_node_alloc (GSK_TEXTURE_SCALE_NODE);
node = (GskRenderNode *) self;
node->offscreen_for_opacity = FALSE;
self->texture = g_object_ref (texture);
graphene_rect_init_from_rect (&node->bounds, bounds);
self->filter = filter;
node->prefers_high_depth = gdk_memory_format_prefers_high_depth (gdk_texture_get_format (texture));
return node;
}
/* }}} */
/* {{{ GSK_INSET_SHADOW_NODE */
/** /**
* GskInsetShadowNode: * GskInsetShadowNode:
@@ -2323,8 +2132,7 @@ gsk_inset_shadow_node_get_blur_radius (const GskRenderNode *node)
return self->blur_radius; return self->blur_radius;
} }
/* }}} */ /*** GSK_OUTSET_SHADOW_NODE ***/
/* {{{ GSK_OUTSET_SHADOW_NODE */
/** /**
* GskOutsetShadowNode: * GskOutsetShadowNode:
@@ -2630,8 +2438,7 @@ gsk_outset_shadow_node_get_blur_radius (const GskRenderNode *node)
return self->blur_radius; return self->blur_radius;
} }
/* }}} */ /*** GSK_CAIRO_NODE ***/
/* {{{ GSK_CAIRO_NODE */
/** /**
* GskCairoNode: * GskCairoNode:
@@ -2769,8 +2576,7 @@ gsk_cairo_node_get_draw_context (GskRenderNode *node)
return res; return res;
} }
/* }}} */ /**** GSK_CONTAINER_NODE ***/
/* {{{ GSK_CONTAINER_NODE */
/** /**
* GskContainerNode: * GskContainerNode:
@@ -3029,8 +2835,7 @@ gsk_container_node_is_disjoint (const GskRenderNode *node)
return self->disjoint; return self->disjoint;
} }
/* }}} */ /*** GSK_TRANSFORM_NODE ***/
/* {{{ GSK_TRANSFORM_NODE */
/** /**
* GskTransformNode: * GskTransformNode:
@@ -3253,8 +3058,7 @@ gsk_transform_node_get_translate (const GskRenderNode *node,
*dy = self->dy; *dy = self->dy;
} }
/* }}} */ /*** GSK_OPACITY_NODE ***/
/* {{{ GSK_OPACITY_NODE */
/** /**
* GskOpacityNode: * GskOpacityNode:
@@ -3381,8 +3185,7 @@ gsk_opacity_node_get_opacity (const GskRenderNode *node)
return self->opacity; return self->opacity;
} }
/* }}} */ /*** GSK_COLOR_MATRIX_NODE ***/
/* {{{ GSK_COLOR_MATRIX_NODE */
/** /**
* GskColorMatrixNode: * GskColorMatrixNode:
@@ -3603,8 +3406,7 @@ gsk_color_matrix_node_get_color_offset (const GskRenderNode *node)
return &self->color_offset; return &self->color_offset;
} }
/* }}} */ /*** GSK_REPEAT_NODE ***/
/* {{{ GSK_REPEAT_NODE */
/** /**
* GskRepeatNode: * GskRepeatNode:
@@ -3740,8 +3542,7 @@ gsk_repeat_node_get_child_bounds (const GskRenderNode *node)
return &self->child_bounds; return &self->child_bounds;
} }
/* }}} */ /*** GSK_CLIP_NODE ***/
/* {{{ GSK_CLIP_NODE */
/** /**
* GskClipNode: * GskClipNode:
@@ -3875,8 +3676,7 @@ gsk_clip_node_get_clip (const GskRenderNode *node)
return &self->clip; return &self->clip;
} }
/* }}} */ /*** GSK_ROUNDED_CLIP_NODE ***/
/* {{{ GSK_ROUNDED_CLIP_NODE */
/** /**
* GskRoundedClipNode: * GskRoundedClipNode:
@@ -4010,8 +3810,7 @@ gsk_rounded_clip_node_get_clip (const GskRenderNode *node)
return &self->clip; return &self->clip;
} }
/* }}} */ /*** GSK_SHADOW_NODE ***/
/* {{{ GSK_SHADOW_NODE */
/** /**
* GskShadowNode: * GskShadowNode:
@@ -4251,8 +4050,7 @@ gsk_shadow_node_get_n_shadows (const GskRenderNode *node)
return self->n_shadows; return self->n_shadows;
} }
/* }}} */ /*** GSK_BLEND_NODE ***/
/* {{{ GSK_BLEND_NODE */
/** /**
* GskBlendNode: * GskBlendNode:
@@ -4446,8 +4244,7 @@ gsk_blend_node_get_blend_mode (const GskRenderNode *node)
return self->blend_mode; return self->blend_mode;
} }
/* }}} */ /*** GSK_CROSS_FADE_NODE ***/
/* {{{ GSK_CROSS_FADE_NODE */
/** /**
* GskCrossFadeNode: * GskCrossFadeNode:
@@ -4598,8 +4395,7 @@ gsk_cross_fade_node_get_progress (const GskRenderNode *node)
return self->progress; return self->progress;
} }
/* }}} */ /*** GSK_TEXT_NODE ***/
/* {{{ GSK_TEXT_NODE */
/** /**
* GskTextNode: * GskTextNode:
@@ -4864,8 +4660,7 @@ gsk_text_node_get_offset (const GskRenderNode *node)
return &self->offset; return &self->offset;
} }
/* }}} */ /*** GSK_BLUR_NODE ***/
/* {{{ GSK_BLUR_NODE */
/** /**
* GskBlurNode: * GskBlurNode:
@@ -5184,137 +4979,7 @@ gsk_blur_node_get_radius (const GskRenderNode *node)
return self->radius; return self->radius;
} }
/* }}} */ /*** GSK_DEBUG_NODE ***/
/* {{{ GSK_MASK_NODE */
/**
* GskMaskNode:
*
* A render node masking one child node with another.
*
* Since: 4.10
*/
typedef struct _GskMaskNode GskMaskNode;
struct _GskMaskNode
{
GskRenderNode render_node;
GskRenderNode *mask;
GskRenderNode *source;
};
static void
gsk_mask_node_finalize (GskRenderNode *node)
{
GskMaskNode *self = (GskMaskNode *) node;
gsk_render_node_unref (self->source);
gsk_render_node_unref (self->mask);
}
static void
gsk_mask_node_draw (GskRenderNode *node,
cairo_t *cr)
{
GskMaskNode *self = (GskMaskNode *) node;
cairo_pattern_t *mask_pattern;
cairo_push_group (cr);
gsk_render_node_draw (self->source, cr);
cairo_pop_group_to_source (cr);
cairo_push_group (cr);
gsk_render_node_draw (self->mask, cr);
mask_pattern = cairo_pop_group (cr);
cairo_mask (cr, mask_pattern);
}
static void
gsk_mask_node_diff (GskRenderNode *node1,
GskRenderNode *node2,
cairo_region_t *region)
{
GskMaskNode *self1 = (GskMaskNode *) node1;
GskMaskNode *self2 = (GskMaskNode *) node2;
gsk_render_node_diff (self1->source, self2->source, region);
gsk_render_node_diff (self1->mask, self2->mask, region);
}
/**
* gsk_mask_node_new:
* @source: The bottom node to be drawn
* @mask: The node to be blended onto the @bottom node
*
* Creates a `GskRenderNode` that will use @blend_mode to blend the @top
* node onto the @bottom node.
*
* Returns: (transfer full) (type GskMaskNode): A new `GskRenderNode`
*
* Since: 4.10
*/
GskRenderNode *
gsk_mask_node_new (GskRenderNode *source,
GskRenderNode *mask)
{
GskMaskNode *self;
g_return_val_if_fail (GSK_IS_RENDER_NODE (source), NULL);
g_return_val_if_fail (GSK_IS_RENDER_NODE (mask), NULL);
self = gsk_render_node_alloc (GSK_MASK_NODE);
self->source = gsk_render_node_ref (source);
self->mask = gsk_render_node_ref (mask);
graphene_rect_union (&source->bounds, &mask->bounds, &self->render_node.bounds);
return &self->render_node;
}
/**
* gsk_mask_node_get_source:
* @node: (type GskBlendNode): a mask `GskRenderNode`
*
* Retrieves the source `GskRenderNode` child of the @node.
*
* Returns: (transfer none): the source child node
*
* Since: 4.10
*/
GskRenderNode *
gsk_mask_node_get_source (const GskRenderNode *node)
{
const GskMaskNode *self = (const GskMaskNode *) node;
g_return_val_if_fail (GSK_IS_RENDER_NODE_TYPE (node, GSK_MASK_NODE), NULL);
return self->source;
}
/**
* gsk_mask_node_get_mask:
* @node: (type GskBlendNode): a mask `GskRenderNode`
*
* Retrieves the mask `GskRenderNode` child of the @node.
*
* Returns: (transfer none): the mask child node
*
* Since: 4.10
*/
GskRenderNode *
gsk_mask_node_get_mask (const GskRenderNode *node)
{
const GskMaskNode *self = (const GskMaskNode *) node;
g_return_val_if_fail (GSK_IS_RENDER_NODE_TYPE (node, GSK_MASK_NODE), NULL);
return self->mask;
}
/* }}} */
/* {{{ GSK_DEBUG_NODE */
/** /**
* GskDebugNode: * GskDebugNode:
@@ -5439,8 +5104,7 @@ gsk_debug_node_get_message (const GskRenderNode *node)
return self->message; return self->message;
} }
/* }}} */ /*** GSK_GL_SHADER_NODE ***/
/* {{{ GSK_GL_SHADER_NODE */
/** /**
* GskGLShaderNode: * GskGLShaderNode:
@@ -5645,8 +5309,6 @@ gsk_gl_shader_node_get_args (const GskRenderNode *node)
return self->args; return self->args;
} }
/* }}} */
GType gsk_render_node_types[GSK_RENDER_NODE_TYPE_N_TYPES]; GType gsk_render_node_types[GSK_RENDER_NODE_TYPE_N_TYPES];
#ifndef I_ #ifndef I_
@@ -5671,7 +5333,6 @@ GSK_DEFINE_RENDER_NODE_TYPE (gsk_repeating_radial_gradient_node, GSK_REPEATING_R
GSK_DEFINE_RENDER_NODE_TYPE (gsk_conic_gradient_node, GSK_CONIC_GRADIENT_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_conic_gradient_node, GSK_CONIC_GRADIENT_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_border_node, GSK_BORDER_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_border_node, GSK_BORDER_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_texture_node, GSK_TEXTURE_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_texture_node, GSK_TEXTURE_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_texture_scale_node, GSK_TEXTURE_SCALE_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_inset_shadow_node, GSK_INSET_SHADOW_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_inset_shadow_node, GSK_INSET_SHADOW_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_outset_shadow_node, GSK_OUTSET_SHADOW_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_outset_shadow_node, GSK_OUTSET_SHADOW_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_transform_node, GSK_TRANSFORM_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_transform_node, GSK_TRANSFORM_NODE)
@@ -5685,7 +5346,6 @@ GSK_DEFINE_RENDER_NODE_TYPE (gsk_blend_node, GSK_BLEND_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_cross_fade_node, GSK_CROSS_FADE_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_cross_fade_node, GSK_CROSS_FADE_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_text_node, GSK_TEXT_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_text_node, GSK_TEXT_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_blur_node, GSK_BLUR_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_blur_node, GSK_BLUR_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_mask_node, GSK_MASK_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_gl_shader_node, GSK_GL_SHADER_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_gl_shader_node, GSK_GL_SHADER_NODE)
GSK_DEFINE_RENDER_NODE_TYPE (gsk_debug_node, GSK_DEBUG_NODE) GSK_DEFINE_RENDER_NODE_TYPE (gsk_debug_node, GSK_DEBUG_NODE)
@@ -5852,22 +5512,6 @@ gsk_render_node_init_types_once (void)
gsk_render_node_types[GSK_TEXTURE_NODE] = node_type; gsk_render_node_types[GSK_TEXTURE_NODE] = node_type;
} }
{
const GskRenderNodeTypeInfo node_info =
{
GSK_TEXTURE_SCALE_NODE,
sizeof (GskTextureScaleNode),
NULL,
gsk_texture_scale_node_finalize,
gsk_texture_scale_node_draw,
NULL,
gsk_texture_scale_node_diff,
};
GType node_type = gsk_render_node_type_register_static (I_("GskTextureScaleNode"), &node_info);
gsk_render_node_types[GSK_TEXTURE_SCALE_NODE] = node_type;
}
{ {
const GskRenderNodeTypeInfo node_info = const GskRenderNodeTypeInfo node_info =
{ {
@@ -6076,22 +5720,6 @@ gsk_render_node_init_types_once (void)
gsk_render_node_types[GSK_BLUR_NODE] = node_type; gsk_render_node_types[GSK_BLUR_NODE] = node_type;
} }
{
const GskRenderNodeTypeInfo node_info =
{
GSK_MASK_NODE,
sizeof (GskMaskNode),
NULL,
gsk_mask_node_finalize,
gsk_mask_node_draw,
NULL,
gsk_mask_node_diff,
};
GType node_type = gsk_render_node_type_register_static (I_("GskMaskNode"), &node_info);
gsk_render_node_types[GSK_MASK_NODE] = node_type;
}
{ {
const GskRenderNodeTypeInfo node_info = const GskRenderNodeTypeInfo node_info =
{ {
@@ -6256,5 +5884,3 @@ gsk_render_node_init_types (void)
g_once_init_leave (&register_types__volatile, initialized); g_once_init_leave (&register_types__volatile, initialized);
} }
} }
/* vim:set foldmethod=marker expandtab: */
-155
View File
@@ -600,32 +600,6 @@ clear_shadows (gpointer inout_shadows)
g_array_set_size (*(GArray **) inout_shadows, 0); g_array_set_size (*(GArray **) inout_shadows, 0);
} }
static const struct
{
GskScalingFilter filter;
const char *name;
} scaling_filters[] = {
{ GSK_SCALING_FILTER_LINEAR, "linear" },
{ GSK_SCALING_FILTER_NEAREST, "nearest" },
{ GSK_SCALING_FILTER_TRILINEAR, "trilinear" },
};
static gboolean
parse_scaling_filter (GtkCssParser *parser,
gpointer out_filter)
{
for (unsigned int i = 0; i < G_N_ELEMENTS (scaling_filters); i++)
{
if (gtk_css_parser_try_ident (parser, scaling_filters[i].name))
{
*(GskScalingFilter *) out_filter = scaling_filters[i].filter;
return TRUE;
}
}
return FALSE;
}
static const struct static const struct
{ {
GskBlendMode mode; GskBlendMode mode;
@@ -1376,31 +1350,6 @@ parse_glshader_node (GtkCssParser *parser)
return node; return node;
} }
static GskRenderNode *
parse_mask_node (GtkCssParser *parser)
{
GskRenderNode *source = NULL;
GskRenderNode *mask = NULL;
const Declaration declarations[] = {
{ "source", parse_node, clear_node, &source },
{ "mask", parse_node, clear_node, &mask },
};
GskRenderNode *result;
parse_declarations (parser, declarations, G_N_ELEMENTS(declarations));
if (source == NULL)
source = create_default_render_node ();
if (mask == NULL)
mask = gsk_color_node_new (&GDK_RGBA("AAFF00"), &GRAPHENE_RECT_INIT (0, 0, 50, 50));
result = gsk_mask_node_new (source, mask);
gsk_render_node_unref (source);
gsk_render_node_unref (mask);
return result;
}
static GskRenderNode * static GskRenderNode *
parse_border_node (GtkCssParser *parser) parse_border_node (GtkCssParser *parser)
{ {
@@ -1440,30 +1389,6 @@ parse_texture_node (GtkCssParser *parser)
return node; return node;
} }
static GskRenderNode *
parse_texture_scale_node (GtkCssParser *parser)
{
graphene_rect_t bounds = GRAPHENE_RECT_INIT (0, 0, 50, 50);
GdkTexture *texture = NULL;
GskScalingFilter filter = GSK_SCALING_FILTER_LINEAR;
const Declaration declarations[] = {
{ "bounds", parse_rect, NULL, &bounds },
{ "texture", parse_texture, clear_texture, &texture },
{ "filter", parse_scaling_filter, NULL, &filter }
};
GskRenderNode *node;
parse_declarations (parser, declarations, G_N_ELEMENTS (declarations));
if (texture == NULL)
texture = create_default_texture ();
node = gsk_texture_scale_node_new (texture, &bounds, filter);
g_object_unref (texture);
return node;
}
static GskRenderNode * static GskRenderNode *
parse_cairo_node (GtkCssParser *parser) parse_cairo_node (GtkCssParser *parser)
{ {
@@ -1936,10 +1861,8 @@ parse_node (GtkCssParser *parser,
{ "shadow", parse_shadow_node }, { "shadow", parse_shadow_node },
{ "text", parse_text_node }, { "text", parse_text_node },
{ "texture", parse_texture_node }, { "texture", parse_texture_node },
{ "texture-scale", parse_texture_scale_node },
{ "transform", parse_transform_node }, { "transform", parse_transform_node },
{ "glshader", parse_glshader_node }, { "glshader", parse_glshader_node },
{ "mask", parse_mask_node },
}; };
GskRenderNode **node_p = out_node; GskRenderNode **node_p = out_node;
guint i; guint i;
@@ -2834,73 +2757,6 @@ render_node_print (Printer *p,
} }
break; break;
case GSK_TEXTURE_SCALE_NODE:
{
GdkTexture *texture = gsk_texture_scale_node_get_texture (node);
GskScalingFilter filter = gsk_texture_scale_node_get_filter (node);
GBytes *bytes;
start_node (p, "texture-scale");
append_rect_param (p, "bounds", &node->bounds);
if (filter != GSK_SCALING_FILTER_LINEAR)
{
_indent (p);
for (unsigned int i = 0; i < G_N_ELEMENTS (scaling_filters); i++)
{
if (scaling_filters[i].filter == filter)
{
g_string_append_printf (p->str, "filter: %s;\n", scaling_filters[i].name);
break;
}
}
}
_indent (p);
switch (gdk_texture_get_format (texture))
{
case GDK_MEMORY_B8G8R8A8_PREMULTIPLIED:
case GDK_MEMORY_A8R8G8B8_PREMULTIPLIED:
case GDK_MEMORY_R8G8B8A8_PREMULTIPLIED:
case GDK_MEMORY_B8G8R8A8:
case GDK_MEMORY_A8R8G8B8:
case GDK_MEMORY_R8G8B8A8:
case GDK_MEMORY_A8B8G8R8:
case GDK_MEMORY_R8G8B8:
case GDK_MEMORY_B8G8R8:
case GDK_MEMORY_R16G16B16:
case GDK_MEMORY_R16G16B16A16_PREMULTIPLIED:
case GDK_MEMORY_R16G16B16A16:
bytes = gdk_texture_save_to_png_bytes (texture);
g_string_append (p->str, "texture: url(\"data:image/png;base64,");
break;
case GDK_MEMORY_R16G16B16_FLOAT:
case GDK_MEMORY_R16G16B16A16_FLOAT_PREMULTIPLIED:
case GDK_MEMORY_R16G16B16A16_FLOAT:
case GDK_MEMORY_R32G32B32_FLOAT:
case GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED:
case GDK_MEMORY_R32G32B32A32_FLOAT:
bytes = gdk_texture_save_to_tiff_bytes (texture);
g_string_append (p->str, "texture: url(\"data:image/tiff;base64,");
break;
case GDK_MEMORY_N_FORMATS:
default:
g_assert_not_reached ();
}
b64 = base64_encode_with_linebreaks (g_bytes_get_data (bytes, NULL),
g_bytes_get_size (bytes));
append_escaping_newlines (p->str, b64);
g_free (b64);
g_string_append (p->str, "\");\n");
end_node (p);
g_bytes_unref (bytes);
}
break;
case GSK_TEXT_NODE: case GSK_TEXT_NODE:
{ {
const graphene_point_t *offset = gsk_text_node_get_offset (node); const graphene_point_t *offset = gsk_text_node_get_offset (node);
@@ -3126,17 +2982,6 @@ render_node_print (Printer *p,
} }
break; break;
case GSK_MASK_NODE:
{
start_node (p, "mask");
append_node_param (p, "source", gsk_mask_node_get_source (node));
append_node_param (p, "mask", gsk_mask_node_get_mask (node));
end_node (p);
}
break;
case GSK_NOT_A_RENDER_NODE: case GSK_NOT_A_RENDER_NODE:
g_assert_not_reached (); g_assert_not_reached ();
break; break;
-1
View File
@@ -19,7 +19,6 @@ gsk_private_gl_shaders = [
'gl/resources/repeat.glsl', 'gl/resources/repeat.glsl',
'gl/resources/custom.glsl', 'gl/resources/custom.glsl',
'gl/resources/filled_border.glsl', 'gl/resources/filled_border.glsl',
'gl/resources/mask.glsl',
] ]
gsk_public_sources = files([ gsk_public_sources = files([
-6
View File
@@ -440,9 +440,6 @@ gsk_vulkan_render_pass_add_node (GskVulkanRenderPass *self,
g_array_append_val (self->render_ops, op); g_array_append_val (self->render_ops, op);
return; return;
case GSK_TEXTURE_SCALE_NODE:
goto fallback;
case GSK_COLOR_NODE: case GSK_COLOR_NODE:
if (gsk_vulkan_clip_contains_rect (&constants->clip, &node->bounds)) if (gsk_vulkan_clip_contains_rect (&constants->clip, &node->bounds))
pipeline_type = GSK_VULKAN_PIPELINE_COLOR; pipeline_type = GSK_VULKAN_PIPELINE_COLOR;
@@ -504,9 +501,6 @@ gsk_vulkan_render_pass_add_node (GskVulkanRenderPass *self,
g_array_append_val (self->render_ops, op); g_array_append_val (self->render_ops, op);
return; return;
case GSK_MASK_NODE:
goto fallback;
case GSK_COLOR_MATRIX_NODE: case GSK_COLOR_MATRIX_NODE:
if (gsk_vulkan_clip_contains_rect (&constants->clip, &node->bounds)) if (gsk_vulkan_clip_contains_rect (&constants->clip, &node->bounds))
pipeline_type = GSK_VULKAN_PIPELINE_COLOR_MATRIX; pipeline_type = GSK_VULKAN_PIPELINE_COLOR_MATRIX;
+271 -87
View File
@@ -82,10 +82,6 @@
* hold the TAB_PANEL role and be the target of the CONTROLS * hold the TAB_PANEL role and be the target of the CONTROLS
* relation with their corresponding tabs (in the stack * relation with their corresponding tabs (in the stack
* switcher or notebook). * switcher or notebook).
*
* These are the exceptions implemented by GTK itself, but note that application
* developers can customize the accessibility tree by implementing the
* [iface@Gtk.Accessible] interface in any way they choose.
*/ */
struct _GtkAtSpiContext struct _GtkAtSpiContext
@@ -333,43 +329,32 @@ collect_relations (GtkAtSpiContext *self,
/* }}} */ /* }}} */
/* {{{ Accessible implementation */ /* {{{ Accessible implementation */
static int static int
get_index_in (GtkAccessible *parent, get_index_in_parent (GtkWidget *widget)
GtkAccessible *child)
{ {
GtkAccessible *candidate; GtkWidget *parent = gtk_widget_get_parent (widget);
guint res; GtkWidget *child;
int idx;
if (parent == NULL) if (parent == NULL)
return -1; return -1;
res = 0; idx = 0;
for (candidate = gtk_accessible_get_first_accessible_child (parent); for (child = gtk_widget_get_first_child (parent);
candidate != NULL; child;
candidate = gtk_accessible_get_next_accessible_sibling (candidate)) child = gtk_widget_get_next_sibling (child))
{ {
if (candidate == child) if (child == widget)
return res; return idx;
if (!gtk_accessible_should_present (candidate)) if (!gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
continue; continue;
res++; idx++;
} }
return -1; return -1;
} }
static int
get_index_in_parent (GtkAccessible *accessible)
{
GtkAccessible *parent = gtk_accessible_get_accessible_parent (accessible);
if (parent != NULL)
return get_index_in (parent, accessible);
return -1;
}
static int static int
get_index_in_toplevels (GtkWidget *widget) get_index_in_toplevels (GtkWidget *widget)
{ {
@@ -402,21 +387,61 @@ get_parent_context_ref (GtkAccessible *accessible)
{ {
GVariant *res = NULL; GVariant *res = NULL;
GtkAccessible *parent = gtk_accessible_get_accessible_parent (accessible); if (GTK_IS_WIDGET (accessible))
if (parent == NULL)
{ {
GtkATContext *context = gtk_accessible_get_at_context (accessible); GtkWidget *widget = GTK_WIDGET (accessible);
GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (context); GtkWidget *parent = gtk_widget_get_parent (widget);
res = gtk_at_spi_root_to_ref (self->root); if (parent == NULL)
{
GtkATContext *context = gtk_accessible_get_at_context (accessible);
GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (context);
res = gtk_at_spi_root_to_ref (self->root);
}
else if (GTK_IS_STACK (parent))
{
GtkStackPage *page =
gtk_stack_get_page (GTK_STACK (parent), widget);
GtkATContext *parent_context =
gtk_accessible_get_at_context (GTK_ACCESSIBLE (page));
if (parent_context != NULL)
{
gtk_at_context_realize (parent_context);
res = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (parent_context));
}
}
else
{
GtkATContext *parent_context =
gtk_accessible_get_at_context (GTK_ACCESSIBLE (parent));
if (parent_context != NULL)
{
/* XXX: This realize() is needed otherwise opening a GtkPopover will
* emit a warning when getting the context's reference
*/
gtk_at_context_realize (parent_context);
res = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (parent_context));
}
}
} }
else else if (GTK_IS_STACK_PAGE (accessible))
{ {
GtkATContext *parent_context = gtk_accessible_get_at_context (parent); GtkWidget *parent =
gtk_at_context_realize (parent_context); gtk_widget_get_parent (gtk_stack_page_get_child (GTK_STACK_PAGE (accessible)));
GtkATContext *parent_context =
gtk_accessible_get_at_context (GTK_ACCESSIBLE (parent));
res = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (parent_context)); if (parent_context != NULL)
{
gtk_at_context_realize (parent_context);
res = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (parent_context));
}
} }
if (res == NULL) if (res == NULL)
@@ -497,30 +522,49 @@ handle_accessible_method (GDBusConnection *connection,
{ {
GtkATContext *context = NULL; GtkATContext *context = NULL;
GtkAccessible *accessible; GtkAccessible *accessible;
int idx, presentable_idx; int idx, real_idx = 0;
g_variant_get (parameters, "(i)", &idx); g_variant_get (parameters, "(i)", &idx);
accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self)); accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self));
GtkAccessible *child; if (GTK_IS_STACK_PAGE (accessible))
presentable_idx = 0;
for (child = gtk_accessible_get_first_accessible_child (accessible);
child != NULL;
child = gtk_accessible_get_next_accessible_sibling (child))
{ {
if (!gtk_accessible_should_present (child)) if (idx == 0)
continue; {
GtkWidget *child;
if (presentable_idx == idx)
break;
presentable_idx++;
child = gtk_stack_page_get_child (GTK_STACK_PAGE (accessible));
if (gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (child));
}
} }
if (child) else if (GTK_IS_WIDGET (accessible))
{ {
context = gtk_accessible_get_at_context (child); GtkWidget *widget = GTK_WIDGET (accessible);
GtkWidget *child;
real_idx = 0;
for (child = gtk_widget_get_first_child (widget);
child;
child = gtk_widget_get_next_sibling (child))
{
if (!gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
continue;
if (real_idx == idx)
break;
real_idx += 1;
}
if (child)
{
if (GTK_IS_STACK (accessible))
context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (gtk_stack_get_page (GTK_STACK (accessible), child)));
else
context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (child));
}
} }
if (context == NULL) if (context == NULL)
@@ -544,24 +588,45 @@ handle_accessible_method (GDBusConnection *connection,
GVariantBuilder builder = G_VARIANT_BUILDER_INIT (G_VARIANT_TYPE ("a(so)")); GVariantBuilder builder = G_VARIANT_BUILDER_INIT (G_VARIANT_TYPE ("a(so)"));
GtkAccessible *accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self)); GtkAccessible *accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self));
if (GTK_IS_WIDGET (accessible))
{
GtkWidget *widget = GTK_WIDGET (accessible);
GtkWidget *child;
GtkAccessible *child; for (child = gtk_widget_get_first_child (widget);
for (child = gtk_accessible_get_first_accessible_child (accessible); child;
child != NULL; child = gtk_widget_get_next_sibling (child))
child = gtk_accessible_get_next_accessible_sibling (child)) {
{ if (!gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
if (!gtk_accessible_should_present (child)) continue;
continue;
GtkATContext *context = gtk_accessible_get_at_context (child); GtkATContext *context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (child));
/* Realize the child ATContext in order to get its ref */ /* Realize the child ATContext in order to get its ref */
gtk_at_context_realize (context); gtk_at_context_realize (context);
GVariant *ref = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (context)); GVariant *ref = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (context));
if (ref != NULL) if (ref != NULL)
g_variant_builder_add (&builder, "@(so)", ref); g_variant_builder_add (&builder, "@(so)", ref);
}
}
else if (GTK_IS_STACK_PAGE (accessible))
{
GtkWidget *child = gtk_stack_page_get_child (GTK_STACK_PAGE (accessible));
if (gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
{
GtkATContext *context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (child));
/* Realize the child ATContext in order to get its ref */
gtk_at_context_realize (context);
GVariant *ref = gtk_at_spi_context_to_ref (GTK_AT_SPI_CONTEXT (context));
if (ref != NULL)
g_variant_builder_add (&builder, "@(so)", ref);
}
} }
g_dbus_method_invocation_return_value (invocation, g_variant_new ("(a(so))", &builder)); g_dbus_method_invocation_return_value (invocation, g_variant_new ("(a(so))", &builder));
@@ -850,7 +915,7 @@ gtk_at_spi_context_state_change (GtkATContext *ctx,
if (changed_states & GTK_ACCESSIBLE_STATE_CHANGE_HIDDEN) if (changed_states & GTK_ACCESSIBLE_STATE_CHANGE_HIDDEN)
{ {
GtkAccessible *parent; GtkWidget *parent;
GtkATContext *context; GtkATContext *context;
GtkAccessibleChildChange change; GtkAccessibleChildChange change;
@@ -867,9 +932,14 @@ gtk_at_spi_context_state_change (GtkATContext *ctx,
} }
else else
{ {
parent = gtk_accessible_get_accessible_parent (accessible); if (GTK_IS_WIDGET (accessible))
parent = gtk_widget_get_parent (GTK_WIDGET (accessible));
else if (GTK_IS_STACK_PAGE (accessible))
parent = gtk_widget_get_parent (gtk_stack_page_get_child (GTK_STACK_PAGE (accessible)));
else
g_assert_not_reached ();
context = gtk_accessible_get_at_context (parent); context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (parent));
gtk_at_context_child_changed (context, change, accessible); gtk_at_context_child_changed (context, change, accessible);
} }
} }
@@ -1098,9 +1168,29 @@ gtk_at_spi_context_bounds_change (GtkATContext *ctx)
{ {
GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (ctx); GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (ctx);
GtkAccessible *accessible = gtk_at_context_get_accessible (ctx); GtkAccessible *accessible = gtk_at_context_get_accessible (ctx);
int x, y, width, height; GtkWidget *widget;
if (gtk_accessible_get_bounds (accessible, &x, &y, &width, &height)) GtkWidget *parent;
emit_bounds_changed (self, x, y, width, height); double x, y;
int width, height;
if (!GTK_IS_WIDGET (accessible))
return;
widget = GTK_WIDGET (accessible);
if (!gtk_widget_get_realized (widget))
return;
parent = gtk_widget_get_parent (widget);
if (parent)
gtk_widget_translate_coordinates (widget, parent, 0., 0., &x, &y);
else
x = y = 0.;
width = gtk_widget_get_width (widget);
height = gtk_widget_get_height (widget);
emit_bounds_changed (self, (int)x, (int)y, width, height);
} }
static void static void
@@ -1111,17 +1201,99 @@ gtk_at_spi_context_child_change (GtkATContext *ctx,
GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (ctx); GtkAtSpiContext *self = GTK_AT_SPI_CONTEXT (ctx);
GtkAccessible *accessible = gtk_at_context_get_accessible (ctx); GtkAccessible *accessible = gtk_at_context_get_accessible (ctx);
GtkATContext *child_context = gtk_accessible_get_at_context (child); GtkATContext *child_context = gtk_accessible_get_at_context (child);
GtkWidget *parent_widget;
GtkWidget *child_widget;
int idx = 0;
if (!GTK_IS_WIDGET (accessible))
return;
if (child_context == NULL) if (child_context == NULL)
return; return;
GtkAccessible *parent = gtk_accessible_get_accessible_parent (child); /* handle the stack page special case */
int idx = 0; if (GTK_IS_WIDGET (child) &&
GTK_IS_STACK (gtk_widget_get_parent (GTK_WIDGET (child))))
{
GtkWidget *stack;
GtkStackPage *page;
GListModel *pages;
if (parent == NULL) stack = gtk_widget_get_parent (GTK_WIDGET (child));
idx = -1; page = gtk_stack_get_page (GTK_STACK (stack), GTK_WIDGET (child));
else if (parent == accessible) pages = G_LIST_MODEL (gtk_stack_get_pages (GTK_STACK (stack)));
idx = get_index_in (accessible, child); idx = 0;
for (guint i = 0; i < g_list_model_get_n_items (pages); i++)
{
GtkStackPage *item = g_list_model_get_item (pages, i);
g_object_unref (item);
if (!gtk_accessible_should_present (GTK_ACCESSIBLE (item)))
continue;
if (item == page)
break;
idx++;
}
g_object_unref (pages);
if (change & GTK_ACCESSIBLE_CHILD_CHANGE_ADDED)
{
emit_children_changed (GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (stack))),
GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (page))),
idx,
GTK_ACCESSIBLE_CHILD_STATE_ADDED);
emit_children_changed (GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (page))),
GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (child)),
0,
GTK_ACCESSIBLE_CHILD_STATE_ADDED);
}
if (change & GTK_ACCESSIBLE_CHILD_CHANGE_REMOVED)
{
emit_children_changed (GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (page))),
GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (child)),
0,
GTK_ACCESSIBLE_CHILD_STATE_REMOVED);
emit_children_changed (GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (stack))),
GTK_AT_SPI_CONTEXT (gtk_accessible_get_at_context (GTK_ACCESSIBLE (page))),
idx,
GTK_ACCESSIBLE_CHILD_STATE_REMOVED);
}
return;
}
parent_widget = GTK_WIDGET (accessible);
if (GTK_IS_STACK_PAGE (child))
child_widget = gtk_stack_page_get_child (GTK_STACK_PAGE (child));
else
child_widget = GTK_WIDGET (child);
if (gtk_widget_get_parent (child_widget) != parent_widget)
{
idx = 0;
}
else
{
for (GtkWidget *iter = gtk_widget_get_first_child (parent_widget);
iter != NULL;
iter = gtk_widget_get_next_sibling (iter))
{
if (!gtk_accessible_should_present (GTK_ACCESSIBLE (iter)))
continue;
if (iter == child_widget)
break;
idx += 1;
}
}
if (change & GTK_ACCESSIBLE_CHILD_CHANGE_ADDED) if (change & GTK_ACCESSIBLE_CHILD_CHANGE_ADDED)
emit_children_changed (self, emit_children_changed (self,
@@ -1686,8 +1858,12 @@ gtk_at_spi_context_get_index_in_parent (GtkAtSpiContext *self)
if (GTK_IS_ROOT (accessible)) if (GTK_IS_ROOT (accessible))
idx = get_index_in_toplevels (GTK_WIDGET (accessible)); idx = get_index_in_toplevels (GTK_WIDGET (accessible));
else if (GTK_IS_STACK_PAGE (accessible))
idx = get_index_in_parent (gtk_stack_page_get_child (GTK_STACK_PAGE (accessible)));
else if (GTK_IS_STACK (gtk_widget_get_parent (GTK_WIDGET (accessible))))
idx = 1;
else else
idx = get_index_in_parent (accessible); idx = get_index_in_parent (GTK_WIDGET (accessible));
return idx; return idx;
} }
@@ -1698,18 +1874,26 @@ gtk_at_spi_context_get_child_count (GtkAtSpiContext *self)
g_return_val_if_fail (GTK_IS_AT_SPI_CONTEXT (self), -1); g_return_val_if_fail (GTK_IS_AT_SPI_CONTEXT (self), -1);
GtkAccessible *accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self)); GtkAccessible *accessible = gtk_at_context_get_accessible (GTK_AT_CONTEXT (self));
int n_children = 0; int n_children = -1;
GtkAccessible *child = NULL; if (GTK_IS_WIDGET (accessible))
for (child = gtk_accessible_get_first_accessible_child (accessible);
child != NULL;
child = gtk_accessible_get_next_accessible_sibling (child))
{ {
if (!gtk_accessible_should_present (child)) GtkWidget *child;
continue;
n_children++; n_children = 0;
for (child = gtk_widget_get_first_child (GTK_WIDGET (accessible));
child;
child = gtk_widget_get_next_sibling (child))
{
if (!gtk_accessible_should_present (GTK_ACCESSIBLE (child)))
continue;
n_children++;
}
}
else if (GTK_IS_STACK_PAGE (accessible))
{
n_children = 1;
} }
return n_children; return n_children;
-8
View File
@@ -3,7 +3,6 @@ gtk_deprecated_sources = [
'deprecated/gtkappchooserbutton.c', 'deprecated/gtkappchooserbutton.c',
'deprecated/gtkappchooserdialog.c', 'deprecated/gtkappchooserdialog.c',
'deprecated/gtkappchooserwidget.c', 'deprecated/gtkappchooserwidget.c',
'deprecated/gtkassistant.c',
'deprecated/gtkcellarea.c', 'deprecated/gtkcellarea.c',
'deprecated/gtkcellareabox.c', 'deprecated/gtkcellareabox.c',
'deprecated/gtkcellareacontext.c', 'deprecated/gtkcellareacontext.c',
@@ -32,10 +31,8 @@ gtk_deprecated_sources = [
'deprecated/gtkiconview.c', 'deprecated/gtkiconview.c',
'deprecated/gtkinfobar.c', 'deprecated/gtkinfobar.c',
'deprecated/gtkliststore.c', 'deprecated/gtkliststore.c',
'deprecated/gtklockbutton.c',
'deprecated/gtkrender.c', 'deprecated/gtkrender.c',
'deprecated/gtkshow.c', 'deprecated/gtkshow.c',
'deprecated/gtkstatusbar.c',
'deprecated/gtkstylecontext.c', 'deprecated/gtkstylecontext.c',
'deprecated/gtktreedatalist.c', 'deprecated/gtktreedatalist.c',
'deprecated/gtktreednd.c', 'deprecated/gtktreednd.c',
@@ -49,7 +46,6 @@ gtk_deprecated_sources = [
'deprecated/gtktreepopover.c', 'deprecated/gtktreepopover.c',
'deprecated/gtktreeview.c', 'deprecated/gtktreeview.c',
'deprecated/gtktreeviewcolumn.c', 'deprecated/gtktreeviewcolumn.c',
'deprecated/gtkvolumebutton.c',
] ]
gtk_deprecated_headers = [ gtk_deprecated_headers = [
@@ -57,7 +53,6 @@ gtk_deprecated_headers = [
'deprecated/gtkappchooserbutton.h', 'deprecated/gtkappchooserbutton.h',
'deprecated/gtkappchooserdialog.h', 'deprecated/gtkappchooserdialog.h',
'deprecated/gtkappchooserwidget.h', 'deprecated/gtkappchooserwidget.h',
'deprecated/gtkassistant.h',
'deprecated/gtkcellarea.h', 'deprecated/gtkcellarea.h',
'deprecated/gtkcellareabox.h', 'deprecated/gtkcellareabox.h',
'deprecated/gtkcellareacontext.h', 'deprecated/gtkcellareacontext.h',
@@ -92,11 +87,9 @@ gtk_deprecated_headers = [
'deprecated/gtkiconview.h', 'deprecated/gtkiconview.h',
'deprecated/gtkinfobar.h', 'deprecated/gtkinfobar.h',
'deprecated/gtkliststore.h', 'deprecated/gtkliststore.h',
'deprecated/gtklockbutton.h',
'deprecated/gtkmessagedialog.h', 'deprecated/gtkmessagedialog.h',
'deprecated/gtkrender.h', 'deprecated/gtkrender.h',
'deprecated/gtkshow.h', 'deprecated/gtkshow.h',
'deprecated/gtkstatusbar.h',
'deprecated/gtkstylecontext.h', 'deprecated/gtkstylecontext.h',
'deprecated/gtktreednd.h', 'deprecated/gtktreednd.h',
'deprecated/gtktreemodel.h', 'deprecated/gtktreemodel.h',
@@ -107,5 +100,4 @@ gtk_deprecated_headers = [
'deprecated/gtktreestore.h', 'deprecated/gtktreestore.h',
'deprecated/gtktreeview.h', 'deprecated/gtktreeview.h',
'deprecated/gtktreeviewcolumn.h', 'deprecated/gtktreeviewcolumn.h',
'deprecated/gtkvolumebutton.h',
] ]
+33 -33
View File
@@ -26,7 +26,7 @@
#include <string.h> #include <string.h>
#include <glib/gstdio.h> #include <glib/gstdio.h>
#include "gtkopenuriportal.h" #include "gopenuriportal.h"
#include "xdp-dbus.h" #include "xdp-dbus.h"
#include "gtkwindowprivate.h" #include "gtkwindowprivate.h"
#include "gtkprivate.h" #include "gtkprivate.h"
@@ -43,7 +43,7 @@
#endif #endif
static GtkXdpOpenURI *openuri; static GXdpOpenURI *openuri;
static gboolean static gboolean
init_openuri_portal (void) init_openuri_portal (void)
@@ -57,10 +57,10 @@ init_openuri_portal (void)
if (connection != NULL) if (connection != NULL)
{ {
openuri = gtk_xdp_open_uri_proxy_new_sync (connection, 0, openuri = gxdp_open_uri_proxy_new_sync (connection, 0,
PORTAL_BUS_NAME, PORTAL_BUS_NAME,
PORTAL_OBJECT_PATH, PORTAL_OBJECT_PATH,
NULL, &error); NULL, &error);
if (openuri == NULL) if (openuri == NULL)
{ {
g_warning ("Cannot create OpenURI portal proxy: %s", error->message); g_warning ("Cannot create OpenURI portal proxy: %s", error->message);
@@ -83,7 +83,7 @@ init_openuri_portal (void)
} }
gboolean gboolean
gtk_openuri_portal_is_available (void) g_openuri_portal_is_available (void)
{ {
return init_openuri_portal (); return init_openuri_portal ();
} }
@@ -169,7 +169,7 @@ open_call_done (GObject *source,
GAsyncResult *result, GAsyncResult *result,
gpointer user_data) gpointer user_data)
{ {
GtkXdpOpenURI *portal = GTK_XDP_OPEN_URI (source); GXdpOpenURI *portal = GXDP_OPEN_URI (source);
GTask *task = user_data; GTask *task = user_data;
OpenUriData *data = g_task_get_task_data (task); OpenUriData *data = g_task_get_task_data (task);
GError *error = NULL; GError *error = NULL;
@@ -179,13 +179,13 @@ open_call_done (GObject *source,
switch (data->call) switch (data->call)
{ {
case OPEN_FILE: case OPEN_FILE:
res = gtk_xdp_open_uri_call_open_file_finish (portal, &path, NULL, result, &error); res = gxdp_open_uri_call_open_file_finish (portal, &path, NULL, result, &error);
break; break;
case OPEN_FOLDER: case OPEN_FOLDER:
res = gtk_xdp_open_uri_call_open_directory_finish (portal, &path, NULL, result, &error); res = gxdp_open_uri_call_open_directory_finish (portal, &path, NULL, result, &error);
break; break;
case OPEN_URI: case OPEN_URI:
res = gtk_xdp_open_uri_call_open_uri_finish (portal, &path, result, &error); res = gxdp_open_uri_call_open_uri_finish (portal, &path, result, &error);
break; break;
default: default:
g_assert_not_reached (); g_assert_not_reached ();
@@ -341,7 +341,7 @@ open_uri (OpenUriData *data,
if (open_folder) if (open_folder)
{ {
data->call = OPEN_FOLDER; data->call = OPEN_FOLDER;
gtk_xdp_open_uri_call_open_directory (openuri, gxdp_open_uri_call_open_directory (openuri,
parent_window ? parent_window : "", parent_window ? parent_window : "",
g_variant_new ("h", fd_id), g_variant_new ("h", fd_id),
opts, opts,
@@ -353,7 +353,7 @@ open_uri (OpenUriData *data,
else else
{ {
data->call = OPEN_FILE; data->call = OPEN_FILE;
gtk_xdp_open_uri_call_open_file (openuri, gxdp_open_uri_call_open_file (openuri,
parent_window ? parent_window : "", parent_window ? parent_window : "",
g_variant_new ("h", fd_id), g_variant_new ("h", fd_id),
opts, opts,
@@ -373,7 +373,7 @@ open_uri (OpenUriData *data,
uri = g_file_get_uri (file); uri = g_file_get_uri (file);
data->call = OPEN_URI; data->call = OPEN_URI;
gtk_xdp_open_uri_call_open_uri (openuri, gxdp_open_uri_call_open_uri (openuri,
parent_window ? parent_window : "", parent_window ? parent_window : "",
uri ? uri : data->uri, uri ? uri : data->uri,
opts, opts,
@@ -441,12 +441,12 @@ window_handle_exported (GtkWindow *window,
} }
void void
gtk_openuri_portal_open_async (GFile *file, g_openuri_portal_open_async (GFile *file,
gboolean open_folder, gboolean open_folder,
GtkWindow *parent, GtkWindow *parent,
GCancellable *cancellable, GCancellable *cancellable,
GAsyncReadyCallback callback, GAsyncReadyCallback callback,
gpointer user_data) gpointer user_data)
{ {
OpenUriData *data; OpenUriData *data;
@@ -465,27 +465,27 @@ gtk_openuri_portal_open_async (GFile *file,
data->cancellable = cancellable ? g_object_ref (cancellable) : NULL; data->cancellable = cancellable ? g_object_ref (cancellable) : NULL;
data->task = g_task_new (parent, cancellable, callback, user_data); data->task = g_task_new (parent, cancellable, callback, user_data);
g_task_set_check_cancellable (data->task, FALSE); g_task_set_check_cancellable (data->task, FALSE);
g_task_set_source_tag (data->task, gtk_openuri_portal_open_async); g_task_set_source_tag (data->task, g_openuri_portal_open_async);
if (!parent || !gtk_window_export_handle (parent, window_handle_exported, data)) if (!parent || !gtk_window_export_handle (parent, window_handle_exported, data))
window_handle_exported (parent, NULL, data); window_handle_exported (parent, NULL, data);
} }
gboolean gboolean
gtk_openuri_portal_open_finish (GAsyncResult *result, g_openuri_portal_open_finish (GAsyncResult *result,
GError **error) GError **error)
{ {
g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == gtk_openuri_portal_open_async, FALSE); g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == g_openuri_portal_open_async, FALSE);
return g_task_propagate_boolean (G_TASK (result), error); return g_task_propagate_boolean (G_TASK (result), error);
} }
void void
gtk_openuri_portal_open_uri_async (const char *uri, g_openuri_portal_open_uri_async (const char *uri,
GtkWindow *parent, GtkWindow *parent,
GCancellable *cancellable, GCancellable *cancellable,
GAsyncReadyCallback callback, GAsyncReadyCallback callback,
gpointer user_data) gpointer user_data)
{ {
OpenUriData *data; OpenUriData *data;
@@ -503,17 +503,17 @@ gtk_openuri_portal_open_uri_async (const char *uri,
data->cancellable = cancellable ? g_object_ref (cancellable) : NULL; data->cancellable = cancellable ? g_object_ref (cancellable) : NULL;
data->task = g_task_new (parent, cancellable, callback, user_data); data->task = g_task_new (parent, cancellable, callback, user_data);
g_task_set_check_cancellable (data->task, FALSE); g_task_set_check_cancellable (data->task, FALSE);
g_task_set_source_tag (data->task, gtk_openuri_portal_open_uri_async); g_task_set_source_tag (data->task, g_openuri_portal_open_uri_async);
if (!parent || !gtk_window_export_handle (parent, window_handle_exported, data)) if (!parent || !gtk_window_export_handle (parent, window_handle_exported, data))
window_handle_exported (parent, NULL, data); window_handle_exported (parent, NULL, data);
} }
gboolean gboolean
gtk_openuri_portal_open_uri_finish (GAsyncResult *result, g_openuri_portal_open_uri_finish (GAsyncResult *result,
GError **error) GError **error)
{ {
g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == gtk_openuri_portal_open_uri_async, FALSE); g_return_val_if_fail (g_task_get_source_tag (G_TASK (result)) == g_openuri_portal_open_uri_async, FALSE);
return g_task_propagate_boolean (G_TASK (result), error); return g_task_propagate_boolean (G_TASK (result), error);
} }
+52
View File
@@ -0,0 +1,52 @@
/* GIO - GLib Input, Output and Streaming Library
*
* Copyright 2017 Red Hat, Inc.
*
* SPDX-License-Identifier: LGPL-2.1-or-later
*
* 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.1 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 __G_OPEN_URI_PORTAL_H__
#include "gtkwindow.h"
#include <glib.h>
#include <gio/gio.h>
G_BEGIN_DECLS
gboolean g_openuri_portal_is_available (void);
void g_openuri_portal_open_async (GFile *file,
gboolean open_folder,
GtkWindow *window,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
gboolean g_openuri_portal_open_finish (GAsyncResult *result,
GError **error);
void g_openuri_portal_open_uri_async (const char *uri,
GtkWindow *window,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
gboolean g_openuri_portal_open_uri_finish (GAsyncResult *result,
GError **error);
G_END_DECLS
#endif
+4 -4
View File
@@ -46,7 +46,7 @@
#include <gtk/gtkapplication.h> #include <gtk/gtkapplication.h>
#include <gtk/gtkapplicationwindow.h> #include <gtk/gtkapplicationwindow.h>
#include <gtk/gtkaspectframe.h> #include <gtk/gtkaspectframe.h>
#include <gtk/deprecated/gtkassistant.h> #include <gtk/gtkassistant.h>
#include <gtk/gtkatcontext.h> #include <gtk/gtkatcontext.h>
#include <gtk/gtkbinlayout.h> #include <gtk/gtkbinlayout.h>
#include <gtk/gtkbitset.h> #include <gtk/gtkbitset.h>
@@ -177,7 +177,7 @@
#include <gtk/gtklistitemfactory.h> #include <gtk/gtklistitemfactory.h>
#include <gtk/deprecated/gtkliststore.h> #include <gtk/deprecated/gtkliststore.h>
#include <gtk/gtklistview.h> #include <gtk/gtklistview.h>
#include <gtk/deprecated/gtklockbutton.h> #include <gtk/gtklockbutton.h>
#include <gtk/gtkmain.h> #include <gtk/gtkmain.h>
#include <gtk/gtkmaplistmodel.h> #include <gtk/gtkmaplistmodel.h>
#include <gtk/gtkmediacontrols.h> #include <gtk/gtkmediacontrols.h>
@@ -252,7 +252,7 @@
#include <gtk/gtkspinner.h> #include <gtk/gtkspinner.h>
#include <gtk/gtkstack.h> #include <gtk/gtkstack.h>
#include <gtk/gtkstackswitcher.h> #include <gtk/gtkstackswitcher.h>
#include <gtk/deprecated/gtkstatusbar.h> #include <gtk/gtkstatusbar.h>
#include <gtk/gtkstringfilter.h> #include <gtk/gtkstringfilter.h>
#include <gtk/gtkstringlist.h> #include <gtk/gtkstringlist.h>
#include <gtk/gtkstringsorter.h> #include <gtk/gtkstringsorter.h>
@@ -290,7 +290,7 @@
#include <gtk/gtkversion.h> #include <gtk/gtkversion.h>
#include <gtk/gtkvideo.h> #include <gtk/gtkvideo.h>
#include <gtk/gtkviewport.h> #include <gtk/gtkviewport.h>
#include <gtk/deprecated/gtkvolumebutton.h> #include <gtk/gtkvolumebutton.h>
#include <gtk/gtkwidget.h> #include <gtk/gtkwidget.h>
#include <gtk/gtkwidgetpaintable.h> #include <gtk/gtkwidgetpaintable.h>
#include <gtk/gtkwindow.h> #include <gtk/gtkwindow.h>
+13 -114
View File
@@ -37,14 +37,6 @@
* a way that should be reflected by assistive technologies. For instance, * a way that should be reflected by assistive technologies. For instance,
* if a `GtkWidget` visibility changes, the %GTK_ACCESSIBLE_STATE_HIDDEN * if a `GtkWidget` visibility changes, the %GTK_ACCESSIBLE_STATE_HIDDEN
* state will also change to reflect the [property@Gtk.Widget:visible] property. * state will also change to reflect the [property@Gtk.Widget:visible] property.
*
* Every accessible implementation is part of a tree of accessible objects.
* Normally, this tree corresponds to the widget tree, but can be customized
* by reimplementing the [vfunc@Gtk.Accessible.get_accessible_parent],
* [vfunc@Gtk.Accessible.get_first_accessible_child] and
* [vfunc@Gtk.Accessible.get_next_accessible_sibling] virtual functions.
* Note that you can not create a top-level accessible object as of now,
* which means that you must always have a parent accessible object.
*/ */
#include "config.h" #include "config.h"
@@ -82,7 +74,7 @@ gtk_accessible_default_init (GtkAccessibleInterface *iface)
g_object_interface_install_property (iface, pspec); g_object_interface_install_property (iface, pspec);
} }
/** /*< private >
* gtk_accessible_get_at_context: * gtk_accessible_get_at_context:
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* *
@@ -99,68 +91,12 @@ gtk_accessible_get_at_context (GtkAccessible *self)
} }
/** /**
* gtk_accessible_get_accessible_parent: * gtk_accessible_get_accessible_role: (attributes org.gtk.Method.get_property=accessible-role)
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* *
* Retrieves the accessible accessible for an accessible object * Retrieves the `GtkAccessibleRole` for the given `GtkAccessible`.
* *
* This function returns `NULL` for top level widgets * Returns: a `GtkAccessibleRole`
*
* Returns: (transfer none) (nullable): the accessible parent
*
* Since: 4.10
*/
GtkAccessible *
gtk_accessible_get_accessible_parent (GtkAccessible *self)
{
g_return_val_if_fail (GTK_IS_ACCESSIBLE (self), NULL);
return GTK_ACCESSIBLE_GET_IFACE (self)->get_accessible_parent (self);
}
/**
* gtk_accessible_get_first_accessible_child:
* @self: an accessible object
*
* Retrieves the first accessible child of an accessible object.
*
* Returns: (transfer none) (nullable): the first accessible child
*
* since: 4.10
*/
GtkAccessible *
gtk_accessible_get_first_accessible_child (GtkAccessible *self)
{
g_return_val_if_fail (GTK_IS_ACCESSIBLE (self), NULL);
return GTK_ACCESSIBLE_GET_IFACE (self)->get_first_accessible_child (self);
}
/**
* gtk_accessible_get_next_accessible_sibling:
* @self: an accessible object
*
* Retrieves the next accessible sibling of an accessible object
*
* Returns: (transfer none) (nullable): the next accessible sibling
*
* since: 4.10
*/
GtkAccessible *
gtk_accessible_get_next_accessible_sibling (GtkAccessible *self)
{
g_return_val_if_fail (GTK_IS_ACCESSIBLE (self), NULL);
return GTK_ACCESSIBLE_GET_IFACE (self)->get_next_accessible_sibling (self);
}
/**
* gtk_accessible_get_accessible_role:
* @self: an accessible object
*
* Retrieves the accessible role of an accessible object.
*
* Returns: the accessible role
*/ */
GtkAccessibleRole GtkAccessibleRole
gtk_accessible_get_accessible_role (GtkAccessible *self) gtk_accessible_get_accessible_role (GtkAccessible *self)
@@ -191,7 +127,6 @@ gtk_accessible_get_accessible_role (GtkAccessible *self)
* state change must be communicated to assistive technologies. * state change must be communicated to assistive technologies.
* *
* Example: * Example:
*
* ```c * ```c
* value = GTK_ACCESSIBLE_TRISTATE_MIXED; * value = GTK_ACCESSIBLE_TRISTATE_MIXED;
* gtk_accessible_update_state (GTK_ACCESSIBLE (check_button), * gtk_accessible_update_state (GTK_ACCESSIBLE (check_button),
@@ -724,10 +659,10 @@ gtk_accessible_role_to_name (GtkAccessibleRole role,
/*< private > /*< private >
* gtk_accessible_role_is_range_subclass: * gtk_accessible_role_is_range_subclass:
* @role: a `GtkAccessibleRole` * @role: a `GtkAccessibleRole`
* *
* Checks if @role is considered to be a subclass of %GTK_ACCESSIBLE_ROLE_RANGE * Checks if @role is considered to be a subclass of %GTK_ACCESSIBLE_ROLE_RANGE
* according to the WAI-ARIA specification. * according to the WAI-ARIA specification.
* *
* Returns: whether the @role is range-like * Returns: whether the @role is range-like
*/ */
gboolean gboolean
@@ -748,7 +683,7 @@ gtk_accessible_role_is_range_subclass (GtkAccessibleRole role)
return FALSE; return FALSE;
} }
/*< private > /*<private>
* gtk_accessible_platform_changed: * gtk_accessible_platform_changed:
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* @change: the platform state change to report * @change: the platform state change to report
@@ -777,7 +712,7 @@ gtk_accessible_platform_changed (GtkAccessible *self,
/* propagate changes up from ignored widgets */ /* propagate changes up from ignored widgets */
if (gtk_accessible_get_accessible_role (self) == GTK_ACCESSIBLE_ROLE_NONE) if (gtk_accessible_get_accessible_role (self) == GTK_ACCESSIBLE_ROLE_NONE)
context = gtk_accessible_get_at_context (gtk_accessible_get_accessible_parent (self)); context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (gtk_widget_get_parent (GTK_WIDGET (self))));
if (context == NULL) if (context == NULL)
return; return;
@@ -786,7 +721,7 @@ gtk_accessible_platform_changed (GtkAccessible *self,
gtk_at_context_update (context); gtk_at_context_update (context);
} }
/** /*<private>
* gtk_accessible_get_platform_state: * gtk_accessible_get_platform_state:
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* @state: platform state to query * @state: platform state to query
@@ -800,19 +735,15 @@ gtk_accessible_platform_changed (GtkAccessible *self,
* child widget, as is the case for `GtkText` wrappers. * child widget, as is the case for `GtkText` wrappers.
* *
* Returns: the value of @state for the accessible * Returns: the value of @state for the accessible
*
* Since: 4.10
*/ */
gboolean gboolean
gtk_accessible_get_platform_state (GtkAccessible *self, gtk_accessible_get_platform_state (GtkAccessible *self,
GtkAccessiblePlatformState state) GtkAccessiblePlatformState state)
{ {
g_return_val_if_fail (GTK_IS_ACCESSIBLE (self), FALSE);
return GTK_ACCESSIBLE_GET_IFACE (self)->get_platform_state (self, state); return GTK_ACCESSIBLE_GET_IFACE (self)->get_platform_state (self, state);
} }
/*< private > /*<private>
* gtk_accessible_bounds_changed: * gtk_accessible_bounds_changed:
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* *
@@ -821,7 +752,7 @@ gtk_accessible_get_platform_state (GtkAccessible *self,
* changed. * changed.
* *
* Note that the bounds are not included in this API. * Note that the bounds are not included in this API.
* AT backends should use [method@Gtk.Accessible.get_bounds] to get them. * AT backends should use widget API to obtain them.
*/ */
void void
gtk_accessible_bounds_changed (GtkAccessible *self) gtk_accessible_bounds_changed (GtkAccessible *self)
@@ -839,39 +770,7 @@ gtk_accessible_bounds_changed (GtkAccessible *self)
gtk_at_context_bounds_changed (context); gtk_at_context_bounds_changed (context);
} }
/** /*<private>
* gtk_accessible_get_bounds:
* @self: a `GtkAccessible`
* @x: (out): the x coordinate of the top left corner of the accessible
* @y: (out): the y coordinate of the top left corner of the widget
* @width: (out): the width of the accessible object
* @height: (out): the height of the accessible object
*
* Queries the coordinates and dimensions of this accessible
*
* This functionality can be overridden by `GtkAccessible`
* implementations, e.g. to get the bounds from an ignored
* child widget.
*
* Returns: true if the bounds are valid, and false otherwise
*
* Since: 4.10
*/
gboolean
gtk_accessible_get_bounds (GtkAccessible *self,
int *x,
int *y,
int *width,
int *height)
{
g_return_val_if_fail (GTK_IS_ACCESSIBLE (self), FALSE);
g_return_val_if_fail (x != NULL && y != NULL, FALSE);
g_return_val_if_fail (width != NULL && height != NULL, FALSE);
return GTK_ACCESSIBLE_GET_IFACE (self)->get_bounds (self, x, y, width, height);
}
/*< private >
* gtk_accessible_should_present: * gtk_accessible_should_present:
* @self: a `GtkAccessible` * @self: a `GtkAccessible`
* *
@@ -930,7 +829,7 @@ gtk_accessible_update_children (GtkAccessible *self,
/* propagate changes up from ignored widgets */ /* propagate changes up from ignored widgets */
if (gtk_accessible_get_accessible_role (self) == GTK_ACCESSIBLE_ROLE_NONE) if (gtk_accessible_get_accessible_role (self) == GTK_ACCESSIBLE_ROLE_NONE)
context = gtk_accessible_get_at_context (gtk_accessible_get_accessible_parent (self)); context = gtk_accessible_get_at_context (GTK_ACCESSIBLE (gtk_widget_get_parent (GTK_WIDGET (self))));
if (context == NULL) if (context == NULL)
return; return;
+43 -184
View File
@@ -32,199 +32,58 @@ G_BEGIN_DECLS
#define GTK_TYPE_ACCESSIBLE (gtk_accessible_get_type()) #define GTK_TYPE_ACCESSIBLE (gtk_accessible_get_type())
GDK_AVAILABLE_IN_4_10 GDK_AVAILABLE_IN_ALL
G_DECLARE_INTERFACE (GtkAccessible, gtk_accessible, GTK, ACCESSIBLE, GObject) G_DECLARE_INTERFACE (GtkAccessible, gtk_accessible, GTK, ACCESSIBLE, GObject)
/** GDK_AVAILABLE_IN_ALL
* GtkAccessiblePlatformState: GtkAccessibleRole gtk_accessible_get_accessible_role (GtkAccessible *self);
* @GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSABLE: whether the accessible can be focused
* @GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSED: whether the accessible has focus
* @GTK_ACCESSIBLE_PLATFORM_STATE_ACTIVE: whether the accessible is active
*
* The various platform states which can be queried
* using [method@Gtk.Accessible.get_platform_state].
*
* Since: 4.10
*/
typedef enum {
GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSABLE,
GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSED,
GTK_ACCESSIBLE_PLATFORM_STATE_ACTIVE
} GtkAccessiblePlatformState;
/**
* GtkAccessibleInterface:
* @get_at_context: retrieve the platform-specific accessibility context
* for the accessible implementation
* @get_platform_state: retrieve the accessible state
*
* The common interface for accessible objects.
*
* Since: 4.10
*/
struct _GtkAccessibleInterface
{
GTypeInterface g_iface;
/**
* GtkAccessibleInterface::get_at_context:
* @self: an accessible object
*
* Retrieves the platform-specific accessibility context for the
* accessible implementation.
*
* Returns: (transfer none) (nullable): the accessibility context
*
* Since: 4.10
*/
GtkATContext * (* get_at_context) (GtkAccessible *self);
/**
* GtkAccessibleInterface::get_platform_state:
* @self: an accessible object
* @state: the state to query
*
* Checks if the given @state applies to the accessible object.
*
* Returns: true if the @state is set, and false otherwise
*
* Since: 4.10
*/
gboolean (* get_platform_state) (GtkAccessible *self,
GtkAccessiblePlatformState state);
/**
* GtkAccessibleInterface::get_accessible_parent:
* @self: an accessible object
*
* Retrieves the accessible parent of an accessible object.
*
* This virtual function should return `NULL` for top level objects.
*
* Returns: (nullable) (transfer none): the accessible parent
*
* Since: 4.10
*/
GtkAccessible * (* get_accessible_parent) (GtkAccessible *self);
/**
* GtkaccessibleInterface::get_first_accessible_child:
* @self: an accessible object
*
* Retrieves the first accessible child of an accessible object.
*
* Returns: (transfer none) (nullable): an accessible object
*
* Since: 4.10
*/
GtkAccessible * (* get_first_accessible_child) (GtkAccessible *self);
/**
* GtkaccessibleInterface::get_next_accessible_sibling:
* @self: an accessible object
*
* Retrieves the next accessible sibling of an accessible object.
*
* Returns: (transfer none) (nullable): an accessible object
*
* Since: 4.10
*/
GtkAccessible * (* get_next_accessible_sibling) (GtkAccessible *self);
/**
* GtkAccessibleInterface::get_bounds:
* @self: an accessible object
* @x: (out): the horizontal coordinate of a rectangle
* @y: (out): the vertical coordinate of a rectangle
* @width: (out): the width of a rectangle
* @height: (out): the height of a rectangle
*
* Retrieves the dimensions and position of an accessible object in its
* parent's coordinate space, if those values can be determined.
*
* For top level accessible objects, the X and Y coordinates are always
* going to be set to zero.
*
* Returns: true if the values are value, and false otherwise
*/
gboolean (* get_bounds) (GtkAccessible *self,
int *x,
int *y,
int *width,
int *height);
};
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GtkATContext * gtk_accessible_get_at_context (GtkAccessible *self); void gtk_accessible_update_state (GtkAccessible *self,
GtkAccessibleState first_state,
GDK_AVAILABLE_IN_4_10 ...);
gboolean gtk_accessible_get_platform_state (GtkAccessible *self, GDK_AVAILABLE_IN_ALL
GtkAccessiblePlatformState state); void gtk_accessible_update_property (GtkAccessible *self,
GtkAccessibleProperty first_property,
GDK_AVAILABLE_IN_4_10 ...);
GtkAccessible * gtk_accessible_get_accessible_parent (GtkAccessible *self); GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_relation (GtkAccessible *self,
GDK_AVAILABLE_IN_4_10 GtkAccessibleRelation first_relation,
GtkAccessible * gtk_accessible_get_first_accessible_child (GtkAccessible *self); ...);
GDK_AVAILABLE_IN_ALL
GDK_AVAILABLE_IN_4_10 void gtk_accessible_update_state_value (GtkAccessible *self,
GtkAccessible * gtk_accessible_get_next_accessible_sibling (GtkAccessible *self); int n_states,
GtkAccessibleState states[],
GDK_AVAILABLE_IN_4_10 const GValue values[]);
gboolean gtk_accessible_get_bounds (GtkAccessible *self, GDK_AVAILABLE_IN_ALL
int *x, void gtk_accessible_update_property_value (GtkAccessible *self,
int *y, int n_properties,
int *width, GtkAccessibleProperty properties[],
int *height); const GValue values[]);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_relation_value (GtkAccessible *self,
int n_relations,
GtkAccessibleRelation relations[],
const GValue values[]);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
GtkAccessibleRole gtk_accessible_get_accessible_role (GtkAccessible *self); void gtk_accessible_reset_state (GtkAccessible *self,
GtkAccessibleState state);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_reset_property (GtkAccessible *self,
GtkAccessibleProperty property);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_reset_relation (GtkAccessible *self,
GtkAccessibleRelation relation);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_state (GtkAccessible *self, void gtk_accessible_state_init_value (GtkAccessibleState state,
GtkAccessibleState first_state, GValue *value);
...);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_property (GtkAccessible *self, void gtk_accessible_property_init_value (GtkAccessibleProperty property,
GtkAccessibleProperty first_property, GValue *value);
...);
GDK_AVAILABLE_IN_ALL GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_relation (GtkAccessible *self, void gtk_accessible_relation_init_value (GtkAccessibleRelation relation,
GtkAccessibleRelation first_relation, GValue *value);
...);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_state_value (GtkAccessible *self,
int n_states,
GtkAccessibleState states[],
const GValue values[]);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_property_value (GtkAccessible *self,
int n_properties,
GtkAccessibleProperty properties[],
const GValue values[]);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_update_relation_value (GtkAccessible *self,
int n_relations,
GtkAccessibleRelation relations[],
const GValue values[]);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_reset_state (GtkAccessible *self,
GtkAccessibleState state);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_reset_property (GtkAccessible *self,
GtkAccessibleProperty property);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_reset_relation (GtkAccessible *self,
GtkAccessibleRelation relation);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_state_init_value (GtkAccessibleState state,
GValue *value);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_property_init_value (GtkAccessibleProperty property,
GValue *value);
GDK_AVAILABLE_IN_ALL
void gtk_accessible_relation_init_value (GtkAccessibleRelation relation,
GValue *value);
G_END_DECLS G_END_DECLS
+17 -30
View File
@@ -21,36 +21,21 @@
#pragma once #pragma once
#include "gtkaccessible.h" #include "gtkaccessible.h"
#include "gtkatcontextprivate.h"
G_BEGIN_DECLS G_BEGIN_DECLS
/* < private > struct _GtkAccessibleInterface
* GtkAccessiblePlatformChange: {
* @GTK_ACCESSIBLE_PLATFORM_CHANGE_FOCUSABLE: whether the accessible has changed GTypeInterface g_iface;
* its focusable state
* @GTK_ACCESSIBLE_PLATFORM_CHANGE_FOCUSED: whether the accessible has changed its
* focused state
* @GTK_ACCESSIBLE_PLATFORM_CHANGE_ACTIVE: whether the accessible has changed its
* active state
*
* Represents the various platform changes which can occur and are communicated
* using [method@Gtk.Accessible.platform_changed].
*/
typedef enum {
GTK_ACCESSIBLE_PLATFORM_CHANGE_FOCUSABLE = 1 << GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSABLE,
GTK_ACCESSIBLE_PLATFORM_CHANGE_FOCUSED = 1 << GTK_ACCESSIBLE_PLATFORM_STATE_FOCUSED,
GTK_ACCESSIBLE_PLATFORM_CHANGE_ACTIVE = 1 << GTK_ACCESSIBLE_PLATFORM_STATE_ACTIVE,
} GtkAccessiblePlatformChange;
typedef enum { GtkATContext * (* get_at_context) (GtkAccessible *self);
GTK_ACCESSIBLE_CHILD_STATE_ADDED,
GTK_ACCESSIBLE_CHILD_STATE_REMOVED
} GtkAccessibleChildState;
typedef enum { gboolean (* get_platform_state) (GtkAccessible *self,
GTK_ACCESSIBLE_CHILD_CHANGE_ADDED = 1 << GTK_ACCESSIBLE_CHILD_STATE_ADDED, GtkAccessiblePlatformState state);
GTK_ACCESSIBLE_CHILD_CHANGE_REMOVED = 1 << GTK_ACCESSIBLE_CHILD_STATE_REMOVED };
} GtkAccessibleChildChange;
GtkATContext * gtk_accessible_get_at_context (GtkAccessible *self);
const char * gtk_accessible_role_to_name (GtkAccessibleRole role, const char * gtk_accessible_role_to_name (GtkAccessibleRole role,
const char *domain); const char *domain);
@@ -59,13 +44,15 @@ gboolean gtk_accessible_role_is_range_subclass (GtkAccessibleRole role);
gboolean gtk_accessible_should_present (GtkAccessible *self); gboolean gtk_accessible_should_present (GtkAccessible *self);
void gtk_accessible_platform_changed (GtkAccessible *self,
GtkAccessiblePlatformChange change);
gboolean gtk_accessible_get_platform_state (GtkAccessible *self,
GtkAccessiblePlatformState state);
void gtk_accessible_bounds_changed (GtkAccessible *self);
void gtk_accessible_update_children (GtkAccessible *self, void gtk_accessible_update_children (GtkAccessible *self,
GtkAccessible *child, GtkAccessible *child,
GtkAccessibleChildState state); GtkAccessibleChildState state);
void gtk_accessible_bounds_changed (GtkAccessible *self);
void gtk_accessible_platform_changed (GtkAccessible *self,
GtkAccessiblePlatformChange change);
G_END_DECLS G_END_DECLS

Some files were not shown because too many files have changed in this diff Show More