Compare commits

..

169 Commits

Author SHA1 Message Date
Matthias Clasen 0f2bce941a fontchooser: Flip models around
Make the fontchooser use a GtkFilterListModel
wrapping a GtkSingleSelection, instead of the
other way around. This exercises the new
selection model support in GtkFilterListModel.
2023-06-04 20:35:50 -04:00
Matthias Clasen 0a7fb26909 filterlistmodel: Implement GtkSelectionModel
Pass through selections from an underlying selection
model.

Tests included.
2023-06-04 20:35:50 -04:00
Matthias Clasen 444d5fa500 Merge branch 'drop-x11-dnd-keynav' into 'main'
x11: Stop using passive grabs

See merge request GNOME/gtk!6055
2023-06-03 19:38:24 +00:00
Matthias Clasen c380d17621 Revert "gdk/x11: Also grab keyboard during XDnD grabs"
This reverts commit ae94417f80.
2023-06-03 12:25:25 -04:00
Matthias Clasen 686d18dfc2 x11: Stop using passive grabs
The keynav that this implements is half-broken under
xwayland anyway, and it confused and complicates things
on the compositor side.
2023-06-03 12:25:25 -04:00
Benjamin Otte 0a1702ae99 Merge branch 'wip/otte/fix-glx' into 'main'
glx: Trap errors inside loop

Closes #5857

See merge request GNOME/gtk!6056
2023-06-03 16:19:09 +00:00
Benjamin Otte 0016fea36b glx: Trap errors inside loop
Instead of trapping errors for the whole loop trying to create GL
contexts, trap them once per GL context.

Apparently GLX does throw an error when a too high version is requested
and doesn't just return NULL and then that error lingers when we try
lower versions.

Fixes #5857
2023-06-03 18:03:56 +02:00
Matthias Clasen 7ef46293aa Merge branch 'wip/antoniof/boxlayout-baseline-optional' into 'main'
boxlayout: Don't always reserve height for baseline alignment

Closes #5863

See merge request GNOME/gtk!6053
2023-06-03 11:01:40 +00:00
António Fernandes 6b59c138b2 boxlayout: Don't always reserve height for baseline alignment
Otherwise an horizontal box may have a larger minumum height than
any of its children even though non of them is baseline-aligned.

Fixes https://gitlab.gnome.org/GNOME/gtk/-/issues/5863
2023-06-02 20:18:56 +01:00
Matthias Clasen c8c895d160 Merge branch 'trap-bad-rr-errors' into 'main'
x11: Trap XRandr errors when getting outputs during init and update

See merge request GNOME/gtk!6046
2023-06-02 11:31:45 +00:00
Luca Bacci acbd7f212e Merge branch 'for-main' into 'main'
GdkWin32 Cleanup

See merge request GNOME/gtk!5714
2023-06-02 09:34:48 +00:00
Marco Trevisan (Treviño) f2a2889153 x11: Trap XRandr errors when getting outputs during init and update
We may try to update the XRR outputs and Crtcs when they're changing in
the server, and so we may get BadRROutput that we're currently not
handling properly.

As per this, use traps and check whether we got errors, and if we did
let's ignore the current output.

It's not required to call init_randr13() again because if we got errors
it's very likely that there's a change coming that will be notified at
next iteration during which we'll repeat the init actions.
2023-06-02 00:30:14 +02:00
Matthias Clasen a4ae215309 Merge branch 'sumibi-yakitori/fix-glcontext-macos' into 'main'
macOS: Fix problems with OpenGL context creation on macOS

Closes #5811

See merge request GNOME/gtk!6044
2023-06-01 20:58:22 +00:00
Daniel Boles fa16ba12cf Window: Copy caveats from :*visible to the setters 2023-06-01 20:31:22 +01:00
Daniel Boles ec2421b187 Window: Fix wrong case in property attribute which
rendered the literal text `org.gtk.MEthod.set_property	focus-visible`.
2023-06-01 20:26:57 +01:00
sumibi-yakitori 1fce2b1e06 Fix an issue where min_version was not being used as the minimum version required by GTK 2023-06-01 23:05:44 +09:00
Matthias Clasen 38bf843de8 Merge branch 'wip/alice/muxer-fix' into 'main'
actionmuxer: Correctly notify actions after reparenting

Closes #5861

See merge request GNOME/gtk!6043
2023-06-01 10:54:33 +00:00
sumibi-yakitori 7b8a5235d4 Fix a bug in error checking conditions. This avoids unintentional Legacy of the created OpenGL context 2023-06-01 16:46:24 +09:00
sumibi-yakitori 3c9b3ead6f The GL version reported by epoxy seems to depend on the current GL context, so the GL context to create should be the one determined by gdk_gl_context_get_matching_version 2023-06-01 16:43:57 +09:00
Alice Mikhaylenko 1549ec5f9b actionmuxer: Correctly notify actions after reparenting
When registering an observer, we send a notification and for that we need
to query the action's state and param type. When setting up a muxer parent,
same thing happens, except the action is queried on the parent instead.

This means that the muxer will notify observers about the parent's actions,
but not about its own.

Add a test to verify it works.

Fixes https://gitlab.gnome.org/GNOME/gtk/-/issues/5861
2023-06-01 06:39:44 +04:00
Matthias Clasen 4339e8e464 Merge branch 'matthiasc/for-main' into 'main'
gsk: Support straight alpha textures

See merge request GNOME/gtk!6041
2023-05-31 19:14:07 +00:00
Matthias Clasen 39f4d5ccf7 gltexturebuilder: Update the docs
We do handle unpremultiplied alpha correctly (albeit
non-optimally) now.
2023-05-31 14:39:07 -04:00
Matthias Clasen 957fa87fce gsk: Support straight alpha textures
This is not the optimal way of doing it: we're
reuploading the texture with client-side conversion.
But it fits nicely into our current handling of mipmaps.

We can do better once we use shaders for colorspace
conversions.
2023-05-31 14:37:33 -04:00
Matthias Clasen e8bdd46d8d Merge branch 'a11y-crash' into 'main'
label: Fix crashes when executing a11y actions

See merge request GNOME/gtk!6034
2023-05-31 12:27:49 +00:00
Erik Schilling d03b27b441 label: Fix crashes when executing a11y actions 2023-05-31 12:27:48 +00:00
Matthias Clasen f4cbe26af3 Merge branch 'more-texture-tests' into 'main'
testsuite: Add more download tests

See merge request GNOME/gtk!6038
2023-05-31 12:01:31 +00:00
Luca Bacci 24af4b48cc GdkWin32: Remove unused functions 2023-05-31 12:15:57 +02:00
Luca Bacci 1c8caf745f GdkWin32: Remove declarations of unused types from gdkprivate-win32.h 2023-05-31 12:15:57 +02:00
Luca Bacci 395d80f131 GdkWin32: Remove declarations of unexisting functions from gdkprivate-win32.h 2023-05-31 12:15:57 +02:00
Luca Bacci 74229572e7 GdkWin32: Remove defines for old MinGW headers 2023-05-31 12:15:57 +02:00
Luca Bacci cbb3d3f177 GdkWin32: Remove _gdk_display_hdc global variable 2023-05-31 12:15:57 +02:00
Luca Bacci 8861d0eb53 GdkWin32: Turn a few functions to static
When used only in the source file they're defined in.
Also remove the corresponding declarations from
gdkrivate-win32.h.
2023-05-31 12:15:57 +02:00
Luca Bacci a23bc894e9 GdkWin32: Remove unused debug functions
* _gdk_win32_print_paletteentries
 * _gdk_win32_print_system_palette
 * _gdk_win32_print_hpalette
 * _gdk_win32_drag_protocol_to_string
 * _gdk_win32_data_to_string
 * _gdk_win32_gdkrectangle_to_string
 * _gdk_win32_cairo_region_to_string
 * _gdk_win32_surface_description
2023-05-31 12:15:57 +02:00
Luca Bacci 156e25b6aa Update manifest XML for the GTK DLL 2023-05-31 12:15:49 +02:00
Matthias Clasen 96f6787a3e testsuite: Add more download tests
Add some odd-sized texture sizes to the
download tests, to trigger alignment issues
in the various upload code paths. And add
a size that is bigger than the max-texture-size
we force in one of our test setups.

To compensate, reduce the number of
runs per size from 20 to 10.
2023-05-30 23:01:20 -04:00
Matthias Clasen cc665f29ea testsuite: Plug a memory leak 2023-05-30 22:37:03 -04:00
Matthias Clasen 8d2047c824 testsuite: Use proper alignment when uploading to GL 2023-05-30 22:36:41 -04:00
Matthias Clasen a79da8b655 Improve test coverage for GdkGLTexture 2023-05-30 22:36:10 -04:00
Matthias Clasen f29c7e76f5 gltexture: Use proper alignment for downloads 2023-05-30 22:35:45 -04:00
Matthias Clasen 29867e7ae1 NEWS: Updates 2023-05-30 20:21:13 -04:00
Matthias Clasen 876b439d4a Merge branch 'matthiasc/conversion-tests' into 'main'
Texture format work

See merge request GNOME/gtk!6035
2023-05-31 00:13:51 +00:00
Matthias Clasen 4f6d7c69a1 gltexturebuilder: Document format expectations
Provide some details about storage and alpha handling.
2023-05-30 19:46:13 -04:00
Matthias Clasen 2bf2635635 testsuite: Exclude some formats on GLES
GLES < 3.2 has some problems with 16-bit formats,
so exclude these from our download tests.
2023-05-30 19:46:13 -04:00
Matthias Clasen 67ed09f5ae testsuite: Add tests for native GL textures
Create GL textures in gray and GA formats
and check that we can download from them
successfully.
2023-05-30 19:46:13 -04:00
Matthias Clasen 1c72f46eed gltexture: Rewrite downloading code
For non-gles, make it handle unpremultiplied formats,
and everything else, by downloading the texture in its
preferred format and, in most cases, doing a
gdk_memory_convert afterwards.

For gles, keep using glReadPixels, but handle cases
where the gl read format doesn't match the texture
format by doing the necessary swizzling before calling
gdk_memory_convert.
2023-05-30 15:57:18 -04:00
Matthias Clasen f5e7a1d4cc Merge branch 'fix-selection-input-stream-leak' into 'main'
gtkselectioninputstream-x11: Do not leak the stream and double-free the EOF bytes marker

Closes #4892

See merge request GNOME/gtk!6037
2023-05-30 19:10:49 +00:00
Matthias Clasen 0f61c52593 gdk: Simplify gdk_memory_format_gl_format
Make the callers of this function check for
straight alpha themselves, and only do the
version compatibility check here. This makes
the function usable in contexts where straight
alpha is acceptable.
2023-05-30 14:49:45 -04:00
Matthias Clasen a4bae6a62d gsk: Use matching memory format
memory_format_gl_format returns the new memory
format if it made a change, we should not drop
that on the floor.
2023-05-30 14:41:01 -04:00
Sophie Herold d141ac5adf gdk: Add gray/alpha memory formats to testsuite 2023-05-30 14:41:01 -04:00
Sophie Herold 894a4bda85 gdk: Support gray/alpha in PNG loader 2023-05-30 14:41:01 -04:00
Sophie Herold 2b88505ca4 gdk: Support gray/alpha in TIFF loader
Use PHOTOMETRIC_MINISBLACK for grayscale image
2023-05-30 14:41:01 -04:00
Sophie Herold ef8c835762 gsk: Support swizzle for gray and alpha formats
Swizzling is needed to display one channel memory formats
as gray etc.
2023-05-30 14:41:01 -04:00
Sophie Herold 50115d70c6 gdk: Add grayscale and alpha memory formats 2023-05-30 14:41:01 -04:00
Luca Bacci 1a058a41c9 Do not keep HINSTANCE variables around
Use &__ImageBase for the GTK DLL and GetModuleHandle (NULL)
for the application module. Then remove DllMain as it's not
necessary anymore.

References:

 [1] Accessing the current module's HINSTANCE from a static library:
     https://devblogs.microsoft.com/oldnewthing/20041025-00/?p=37483
2023-05-30 19:31:54 +02:00
Marco Trevisan (Treviño) be4f6ff3da gdkselectioninputstream-x11: Explicitly handle stream ownership in signal
The display xevent signal connection takes the ownership of the stream
until we get a valid event, so it should manage the stream lifetime.

So make this clearer, by automatically removing the stream reference
when we disconnect from the xevent signal handler.
2023-05-30 17:59:19 +02:00
Marco Trevisan (Treviño) 4fcf899852 gdkselectioninputstream-x11: Make it clearer how we manage the stream ownership
It gets unreffed during gdk_x11_selection_input_stream_complete, so use
APIs that make this clearer.
2023-05-30 17:54:29 +02:00
Marco Trevisan (Treviño) 371e860184 gtkselectioninputstream-x11: Do not add an extra reference to the returned stream
We create a new stream during gdk_x11_selection_input_stream_new_async()
then such stream is referenced when passed to the task via
g_task_return_pointer(), so there's no need to reference it again before
returning it, or we'd end up leaking.

Fixes: https://gitlab.gnome.org/GNOME/gtk/-/issues/4892
2023-05-30 17:50:56 +02:00
Marco Trevisan (Treviño) bce1e0bfdd gtkselectioninputstream-x11: Do not add unreffed bytes to the chunks queue
This should never happen, but we may exit the loop because of count value
with an unreffed bytes pointer being added back to the chunks queue.
2023-05-30 17:43:57 +02:00
Marco Trevisan (Treviño) 468d2cb7f2 gtkselectioninputstream-x11: Do not add EOF marker twice to the chunks queue
We were adding the same EOF marker two times back to the chunks queue,
one implicitly, and the other time could happen when exiting the loop.
2023-05-30 17:42:59 +02:00
Jordi Mas b520a5ceda Update Catalan translation 2023-05-30 06:41:10 +02:00
Matthias Clasen e6bc82cff5 Merge branch 'fix_gtkstack_crash' into 'main'
GtkStack: Fix a potential crash in gtk_stack_get_first_accessible_child

See merge request GNOME/gtk!6031
2023-05-29 23:38:05 +00:00
Matthias Clasen d021aa7bd2 Merge branch 'macos-fixes' into 'main'
For main

See merge request GNOME/gtk!6032
2023-05-29 23:37:22 +00:00
Benjamin Otte 3dc3d03a08 testsuite: Add conversion tests
Ensure we can convert from any format to any other format.
2023-05-30 00:42:10 +02:00
Benjamin Otte 788bd575d6 testsuite: Disable certain texture download tests
The GL renderers like to premultiply content that isn't, and due to the
data loss with alpha == 0 (transparent white, transparent black and
transparent anything are all represented by (0, 0, 0, 0) when
premultiplied) these values cannot be converted back.
2023-05-30 00:42:10 +02:00
Benjamin Otte 94a2dc4c47 testsuite: Update memorytexture test for TextureDownloader
There is no longer a need to use gdk_texture_download() and force
conversion to ARGB8 format. We can download the pixels in the original
format again.

That way we avoid testing the conversion code and avoid having to deal
with differences in representable colors.

However, some formats do do conversions, so we allow pixel comparisons
to be accurate (requires 16bit comparison accuracy) or inaccurate (we
only care about 8bit).
Note that for the default RGBA formats, this is identical and means they
need to be bit-exact the same, no matter what.
But the higher bit depth formats may be more different - floating point
can even have different values with high accuracy (the float mantissa is
23 bit, we only care about 16).
2023-05-30 00:42:10 +02:00
Benjamin Otte 169a7f83e6 testsuite: Imitate gdk_memory_convert() correctly
The formula use to compute pixel values from GdkRGBA floats was slightly
adapted some time ago, copy that adaptation
2023-05-30 00:39:46 +02:00
Luca Bacci 703494c7fa testsuite: rename 'wait' function to 'timed_loop'
When compiling for macOS, CLang errors out because a non-static
wait function is declared in sys/wait.h.
2023-05-29 16:43:28 +02:00
Luca Bacci d642072603 Check for NULL groups in gtk_action_muxer_get_group ()
The groups hash table is initialized lazily when inserting
the first GActionGroup (gtk_action_muxer_insert ()). Do as
all surrounding code does and check for NULL before using
groups.

This avoids triggering a warning
2023-05-29 16:43:28 +02:00
Lukáš Tyrychtr ab7a4f64cb GtkStack: Fix a potential crash in gtk_stack_get_first_accessible_child
This one can occur when the stack has no pages.
2023-05-29 15:14:51 +02:00
Luca Bacci 21c53a1969 Merge branch 'win32-monitors' into 'main'
GdkWin32Monitor fixes

See merge request GNOME/gtk!6015
2023-05-29 09:50:30 +00:00
Matthias Clasen ae2dd1d907 Merge branch 'matthiasc/for-main' into 'main'
css: Add a test for non-ASCII font family

See merge request GNOME/gtk!6028
2023-05-28 17:58:38 +00:00
Matthias Clasen f10c234361 css: Add a test for non-ASCII font family
This came up in #5852, so make sure that it works.
2023-05-28 07:57:40 -04:00
Matthias Clasen 3a650bff66 Merge branch 'matthiasc/for-main' into 'main'
Annotate more enum additions

See merge request GNOME/gtk!6027
2023-05-28 11:41:48 +00:00
Matthias Clasen e9f622b81f listitemmanager: Small docs clarifications
If we write docs for private functions,
lets make them relevant.
2023-05-28 07:19:02 -04:00
Matthias Clasen a85ad2ce67 Annotate more enum additions
We have the technology now, lets use it.
2023-05-28 07:19:02 -04:00
Daniel Boles 2af7e45860 MenuButton: Always mention child@always-show-arrow
get_always_show_arrow() did not mention at all that the custom child is
relevant. set_always_show_arrow() only did in the blurb, not for the arg
2023-05-28 11:35:44 +01:00
Matthias Clasen 2741e00210 Merge branch 'test-sections' into 'main'
testsections: A testbed for sections

See merge request GNOME/gtk!6025
2023-05-28 01:54:06 +00:00
Matthias Clasen 495411e16d testsections: A testbed for sections
Add a simple test client that lets us compare
and explore the section handling in listview
and gridview.
2023-05-27 21:30:14 -04:00
Matthias Clasen 9880f9d16a Merge branch 'slice-sections' into 'main'
Beef up our section models

Closes #5854

See merge request GNOME/gtk!6009
2023-05-28 01:00:04 +00:00
Matthias Clasen 5c1c22156c sortlistmodel: Optimize signals
When we emit items-changed due to a section
sorter change, don't also emit sections-changed.
Instead make the items-changed signal cover the
whole range.

Tests included.
2023-05-27 20:37:28 -04:00
Matthias Clasen d7e8c52d37 Merge branch 'fix-section-sorter-keys' into 'main'
sortlistmodel: Fix handling of section sort keys

Closes #5854

See merge request GNOME/gtk!6024
2023-05-27 23:37:35 +00:00
Matthias Clasen c3d3e2d47b sortlistmodel: Fix handling of section sort keys
When the section sorter changes, we need to update
the keys, otherwise the sorter will continue to report
the old sections.

This code is currently a bit suboptimal, since the
creation of sort keys and section sort keys are
muddled together.

Fixes: #5854
2023-05-27 19:09:05 -04:00
Matthias Clasen 9c1049e710 multiselection: Pass through sections-changed
If our underlying model emits sections-changed,
we need to pass it on.

Add a test for this too.
2023-05-27 17:27:19 -04:00
Matthias Clasen a1352a88ff singleselection: Pass through sections-changed
If our underlying model emits sections-changed,
we need to pass it on.

Add a test for this too.
2023-05-27 17:27:19 -04:00
Matthias Clasen 8825917140 noselection: Pass through sections-changed
If our underlying model emits sections-changed,
we need to pass it on.

Add a test for this too.
2023-05-27 17:27:19 -04:00
Matthias Clasen ba8d4902b5 filterlistmodel: Pass through sections-changed
If our underlying model emits sections-changed,
we need to pass it on.

Add a test for this too.
2023-05-27 17:27:19 -04:00
Matthias Clasen 8f3d3ca587 slicelistmodel: Pass through sections
Implement GtkSectionModel in the obvious way.

Tests included.
2023-05-27 17:27:19 -04:00
Matthias Clasen aeba1e08e8 sortlistmodel: Emit sections-changed
When a new section sorter is set, potentially
all sections have changed. So emit sections-changed
for all items.

Tests included.
2023-05-27 17:27:19 -04:00
Matthias Clasen 9f47bfe193 sortlistmodel: Fix handling of section sort keys
When the section sorter changes, we need to update
    the keys, otherwise the sorter will continue to report
    the old sections.

    This code is currently a bit suboptimal, since the
    creation of sort keys and section sort keys are
    muddled together.

    Fixes: #5854
2023-05-27 17:27:19 -04:00
Benjamin Otte 43417e9e55 Merge branch 'columnview-sections' into 'main'
Columnview sections

See merge request GNOME/gtk!6006
2023-05-27 18:51:12 +00:00
Matthias Clasen bbb7446e93 Merge branch 'matthiasc/for-main' into 'main'
docs: Cosmetics

See merge request GNOME/gtk!6023
2023-05-27 18:42:34 +00:00
Matthias Clasen 6623baeb52 docs: Cosmetics 2023-05-27 14:40:49 -04:00
Matthias Clasen d90b09f8c3 Merge branch 'matthiasc/for-main' into 'main'
sortlistmodel: Cosmetics

See merge request GNOME/gtk!6022
2023-05-27 18:30:37 +00:00
Matthias Clasen bcae6271df Merge branch 'handle-sections-changed' into 'main'
wip: list widgets: handle sections-changed

See merge request GNOME/gtk!6011
2023-05-27 17:55:00 +00:00
Matthias Clasen fc524ed346 Cosmetics
Fix copy-paste errors in line 1.
2023-05-27 13:51:39 -04:00
Matthias Clasen c80a0c0e85 sortlistmodel: Cosmetics
Make the set_[section]_sorter functions a bit more symmetric.
2023-05-27 13:47:46 -04:00
Matthias Clasen 7572f2ed87 columnview: Add section plumbing
Add a header-factory property, and pass it through
to the listview.
2023-05-27 13:39:55 -04:00
Matthias Clasen 54ec750238 Merge branch 'matthiasc/for-main' into 'main'
gtk: Annotate new enum values

See merge request GNOME/gtk!6021
2023-05-27 13:35:27 +00:00
Matthias Clasen 5d78cf6546 Merge branch 'wip/kabus/popover-direction' into 'main'
gtk/popover: Flip anchoring direction in RTL

Closes #5847

See merge request GNOME/gtk!6020
2023-05-27 13:19:28 +00:00
Khalid Abu Shawarib d329b00bda gtk/popover: Flip anchoring direction in RTL 2023-05-27 13:19:28 +00:00
Matthias Clasen ddf1ea9917 gtk: Annotate new enum values
We have decorators now to tell compilers when
enum values were added, so lets use them for the
new GtkAlign values.
2023-05-27 08:02:15 -04:00
Matthias Clasen 215f60e450 listitemmanager: Listen to sections-changed
And recreate header and footer tiles as needed.

This commit was tested using a sortlistmodel, changing
the section sorter from sorting only by first char
to sorting by the first two chars, which changes
the number of sections, but leaves the alphabetic
order of items unchanged.
2023-05-27 06:33:50 -04:00
Sabri Ünal 87070e0bdd Update Turkish translation 2023-05-26 22:48:53 +00:00
Matthias Clasen 19f51b5de2 Merge branch 'docs/gdk-RGBA-parse' into 'main'
docs: add HSL to Gdk.RGBA.parse

See merge request GNOME/gtk!6017
2023-05-25 17:40:08 +00:00
FineFindus 2d8c112f08 docs: add HSL to Gdk.RGBA.parse
Update the Gdk.RGBA.parse docs to reflect the ability to parse HSL, which has been added in 4.5.0.
2023-05-25 17:16:55 +02:00
Matthias Clasen f1901081a6 NEWS: Updates 2023-05-24 22:03:48 -04:00
Jason Francis cf79ad4433 win32: implement fullscreen_on_monitor
Track the HMONITOR so it can be used by the toplevel layout.
2023-05-24 18:48:37 -04:00
Benjamin Otte d912628583 Merge branch 'wip/otte/for-main' into 'main'
2 GDK GL XWayland improvements

See merge request GNOME/gtk!6014
2023-05-24 22:22:48 +00:00
Jason Francis f254ab700c win32: Invalidate inactive monitors
Without this, there are still GdkMonitors present for displays that are
present but disconnected (such as when a laptop disables the internal
display to connect to an external monitor).
2023-05-24 17:34:34 -04:00
Benjamin Otte c7b62d89e3 glx: Implement support for EXT_swap_control
XWayland (at least on gnome-shell) does not support SGI_swap_control,
which we were using to unset the swap interval.

It does support EXT_swap_control though, which is the more modern
version of the same thing, so this commit adds support for that.

And now GDK_DEBUG=no-vsync gives me >1000fps instead of just 60fps,
2023-05-24 21:44:43 +02:00
Benjamin Otte 46e3454eb7 gl: Update tracked buffers from 2 to 4
With XWayland and direct scanout it is possible that some apps get into
a situation where more than 2 buffers are in flight and in that case we
want to be able to still track the change regions for those buffers.

Usually 3 buffers are in use, so we go one higher, just to be safe.
2023-05-24 21:44:43 +02:00
Benjamin Otte 7573a9d2a7 gl: Rewrite update area tracking code
Make it more generic. That way we could dynamically change the number of
buffers we track.

We don't do that yet though.
2023-05-24 21:44:29 +02:00
Carlos Garnacho d24d193301 Merge branch 'lores-scroll-mid-detent' into 'main'
Send low-res scroll event in the middle of the wheel detent

See merge request GNOME/gtk!5128
2023-05-24 14:23:47 +00:00
José Expósito e61938793a gtkeventcontrollerscroll: Send lores scroll in the middle of the detent
Some mice send a value slightly lower than 120 for some detents. The
current approach waits until a value of 120 is reached before sending a
low-resolution scroll event.

For example, the MX Master 3 sends a value of 112 in some detents:

              detent                   detent
    |                        |                       |
                        ^    ^                    ^
                        112  REL_WHEEL            224

As illustrated, only one event was sent but two were expected. However,
sending the low-resolution scroll event in the middle plus the existing
heuristics to reset the accumulator solve this issue:

              detent                   detent
    |                        |                       |
                ^          ^             ^          ^
                REL_WHEEL  112           REL_WHEEL  224

Send low-resolution scroll events in the middle of the detent to solve
this problem.

Related to https://gitlab.gnome.org/GNOME/mutter/-/issues/2469
2023-05-24 13:42:49 +00:00
Matthias Clasen 2f584c16f0 Merge branch 'reomveunused' into 'main'
widget: Don't include gtkpopover.h

See merge request GNOME/gtk!6012
2023-05-23 23:49:25 +00:00
Maximiliano Sandoval R 2565a28e59 widget: Don't include gtkpopover.h
It is not used.
2023-05-23 23:43:15 +02:00
Emmanuele Bassi 793a2b2a70 Merge branch 'zbrown/marshallers' into 'main'
marshallers: fix up some mistypes in drags

See merge request GNOME/gtk!6010
2023-05-23 13:50:26 +00:00
Matthias Clasen 146223cd74 Merge branch 'fix-menu-padding' into 'main'
menus: Avoid unnecessary right padding

Closes #5839

See merge request GNOME/gtk!6008
2023-05-22 20:50:56 +00:00
Daniel Boles d8e7f0a8a9 MenuButton: Fix small grammar-o/match related syms 2023-05-22 21:39:36 +01:00
Matthias Clasen a9adf7163f menus: Avoid unnecessary right padding
We are using placeholders in the 'check' column
that are put in a size group, so that they all
take the same space once a check or radio is shown.

Unfortunately, for the inline-buttons option, we
were using a GtkBuiltinIcon as placeholder, and those
respect the -gtk-icon-size CSS property and take
a minimum size of 16px. Use a GtkGizmo instead to
get the expected result of no extra padding unless
there's a check or radio.

Fixes: #5839
2023-05-22 16:16:45 -04:00
Matthias Clasen 10825cdc72 Merge branch 'matthiasc/for-main' into 'main'
widget-factory: Align some widgets better

See merge request GNOME/gtk!6007
2023-05-22 13:17:58 +00:00
Matthias Clasen 3b105a637c widget-factory: Align some widgets better 2023-05-22 08:36:13 -04:00
Matthias Clasen fdbc203690 Merge branch 'wip/kabus/date-leak' into 'main'
gtk/recentmanager: Fix date leak

Closes #5842

See merge request GNOME/gtk!6005
2023-05-22 12:25:24 +00:00
Khalid Abu Shawarib 26c583227e gtk/recentmanager: Fix date leak 2023-05-22 12:25:24 +00:00
Арсений Засыпкин 1ea0bebf15 Update Russian translation 2023-05-22 12:18:13 +00:00
Matthias Clasen ca0e27ec9d Merge branch 'matthiasc/for-main' into 'main'
Improve section model docs

See merge request GNOME/gtk!6003
2023-05-21 23:57:48 +00:00
Matthias Clasen 5edf9fc449 Merge branch 'fm-showitems' into 'main'
filelauncher: Use ShowItems to show in File Manager

Closes #5842

See merge request GNOME/gtk!5997
2023-05-21 23:22:57 +00:00
Matthias Clasen 534f11e317 Improve section model docs
Mention sections in the list widget overview,
and document the list models that support sections.
2023-05-21 19:20:08 -04:00
Zander Brown d8cffa9350 marshallers: fix up some mistypes in drags
Fix: ff330668cf
2023-05-21 19:14:45 +01:00
Matthias Clasen 60dfa777f0 Merge branch 'gdk-introspection-fix' into 'main'
introspection: Include deprecated gdk api in gir

See merge request GNOME/gtk!5999
2023-05-21 14:25:59 +00:00
Matthias Clasen d6fc0d6c94 gdk: Fix up introspection build
Referring to files across directories is not
easy, we need to use files() in just the right
way to make this work.
2023-05-21 09:46:49 -04:00
Matthias Clasen 4e71bd92aa introspection: Include deprecated gdk api in gir
This was overlooked in when the headers were moved
in ed265f6a7e.
2023-05-21 09:39:13 -04:00
Matthias Clasen 8aec42244e Merge branch 'ebassi/build-introspection' into 'main'
ci: Add introspection to the feature flags

See merge request GNOME/gtk!6000
2023-05-21 12:20:12 +00:00
Emmanuele Bassi 6ff36977f4 ci: Add introspection to the feature flags
It should be enabled by default, if we ever want to catch issues.
2023-05-21 12:22:50 +01:00
Matthias Clasen ed84ccdaca Merge branch 'docs-css-fix' into 'main'
Fix typo in CSS docs

See merge request GNOME/gtk!5998
2023-05-21 11:02:45 +00:00
Arjan Molenaar d9ec27ab29 Fix typo in CSS docs 2023-05-21 12:11:19 +02:00
Matthias Clasen ca744b925e Merge branch 'list-tile-gc' into 'main'
Add gtk_list_item_manager_gc_tiles

See merge request GNOME/gtk!5995
2023-05-21 00:51:00 +00:00
Matthias Clasen 53c63673e4 gridview: Use gtk_list_item_manager_gc_tiles
This simplifies the code a bit.
2023-05-20 19:50:11 -04:00
Matthias Clasen 431458ed78 listview: Use gtk_list_item_manager_gc_tiles
This simplifies the code a bit.
2023-05-20 19:50:11 -04:00
Matthias Clasen 56cfef3544 testsuite: Use gtk_list_item_manager_gc_tiles
Use this  new api instead of open-coding it.

Also, assert that it merges consecutive
multi-item tiles.
2023-05-20 19:50:11 -04:00
Calvin Walton be897646b1 filelauncher: Use ShowItems to show in File Manager
The non-portal fallback method for launching a file manager to show the
file in its parent directory was incorrectly using the `ShowFolders`
method (open a folder) instead of `ShowItems` (open the parent directory
and show the file).

The `show_item` function (previously `show_folder`) had an unused
`callback` parameter; it has been removed and the type of the parameter
containing the GTask has been renamed and now uses the correct type
instead of gpointer to reduce the amount of casting required.

Fixes GNOME/gtk#5842
2023-05-20 19:40:09 -04:00
Matthias Clasen e23358e09f Merge branch 'matthiasc/for-main' into 'main'
Cosmetics

See merge request GNOME/gtk!5996
2023-05-20 23:22:56 +00:00
Matthias Clasen 833e1bdcf6 Cosmetics
Fix some typos.
2023-05-20 19:03:41 -04:00
Matthias Clasen 0091425729 listitemmanager: Stop exporting tile_gc
This function is now just used internally,
so make it static.
2023-05-20 18:59:16 -04:00
Matthias Clasen b1c2a1c015 listitemmanager: Use gc_tiles
Replace an open-coded version of this function
with a call to gtk_list_item_manager_gc_tiles.
2023-05-20 18:59:16 -04:00
Matthias Clasen 31d03f9f26 Add gtk_list_item_manager_gc_tiles
This will allow us to simplify size allocation
code in listview and gridview.
2023-05-20 16:17:11 -04:00
Benjamin Otte 3beaf0962c Merge branch 'drop-filler-tiles' into 'main'
Drop the FILLER tile type

See merge request GNOME/gtk!5993
2023-05-20 17:18:53 +00:00
Matthias Clasen 48e49b4c50 gridview: Update factories in set_factory
Call update_factories() so the children get their
factories properly updated.

This matches what GtkListView does.
2023-05-20 12:53:39 -04:00
Matthias Clasen 1d4f383ba5 Drop the FILLER tile type
It is not used anymore.
2023-05-20 12:28:19 -04:00
Matthias Clasen 8cb3e01eef gridview: Stop using a filler tile
We can just use the footer to fill that space.
2023-05-20 12:28:19 -04:00
Matthias Clasen 42a0dcc7e4 gridview: Add an assertion
The want to use the footer tile at the end
to fill leftover space at the bottome right.

So lets assert that we actually dealing with
a footer tile, just in case something changes
in the future that might have us end up with
some other kind of tile.
2023-05-20 12:26:51 -04:00
Matthias Clasen e9731fc99b Add some tile helpers 2023-05-20 12:26:39 -04:00
Matthias Clasen 2890557236 Revert "gridview: GC tiles first"
This reverts commit e121a5ca6f.

The tile that was causing the critical in #5836
(what that commit was about) was a FILLER, and we
are getting rid of FILLER tiles here. Which will
avoid the issue in a more elegant way.
2023-05-20 12:25:33 -04:00
Matthias Clasen 43a22bb350 Cosmetics
Use the proper g_assert variant.
2023-05-20 07:39:21 -04:00
Matthias Clasen cd9c277820 Merge branch 'ci-clang-build' into 'main'
ci: Add a clang build

See merge request GNOME/gtk!5987
2023-05-18 19:10:52 +00:00
Matthias Clasen 42a12f1788 ci: Add a clang build
This is meant to catch build errors with clang.
2023-05-18 14:39:46 -04:00
Matthias Clasen 5f39820729 cups: Silence a compiler warning
Bitfields should be unsigned int.
2023-05-18 14:39:46 -04:00
Matthias Clasen c2a8620660 gsk: Mark some variables as unused
Hopefully that shuts up clang.
2023-05-18 13:29:28 -04:00
Asier Sarasua Garmendia 647d5e17c1 Update Basque translation
(cherry picked from commit a6931a66c5)
2023-05-18 16:31:00 +00:00
Matthias Clasen d87b9ee4c5 Merge branch 'matthiasc/for-main' into 'main'
roaring: Mark a variable as unused

See merge request GNOME/gtk!5990
2023-05-18 13:35:17 +00:00
Matthias Clasen 70ba00ae53 testsuite: Make this test compile
clang did not like this creative use of
strings at all. Rightfully so.
2023-05-18 08:40:50 -04:00
Matthias Clasen c4fb473d4b roaring: Mark a variable as unused
Otherwise clang complains.
2023-05-18 08:34:48 -04:00
Matthias Clasen b4fbd74f98 Merge branch 'fina/scrolled-window-measure' into 'main'
scrolledwindow: Propagate child measure size whenever possible

Closes #5838

See merge request GNOME/gtk!5986
2023-05-18 12:26:05 +00:00
Fina Wilke 7fae0bc0de scrolledwindow: Propagate child measure size whenever possible
In height-for-width and hscrollbar-policy = never, we can provide
the child with a proper for_size when measuring it. The same is true for
width-for-height and vscrollbar-policy = never.

This allows for accurately measuring the size of eg. wrapping labels.
2023-05-18 13:25:20 +02:00
Benjamin Otte 89b61eeec4 Merge branch 'listview-factory-leak' into 'main'
listview: Don't leak the factories

See merge request GNOME/gtk!5989
2023-05-17 18:57:28 +00:00
Matthias Clasen e2492dd568 gridview: Don't leak the factory 2023-05-17 14:32:55 -04:00
Matthias Clasen ca000287fc listview: Don't leak the factories 2023-05-17 14:17:47 -04:00
Benjamin Otte ff14fea672 Merge branch 'fix-gridview-critical' into 'main'
gridview: GC tiles first

Closes #5836

See merge request GNOME/gtk!5988
2023-05-17 17:04:43 +00:00
Matthias Clasen e121a5ca6f gridview: GC tiles first
Before checking that there are no tiles,
we need to gc any possibly leftover filler
tiles.

Fixes: #5836
2023-05-17 12:31:16 -04:00
110 changed files with 4654 additions and 2083 deletions
+21 -1
View File
@@ -24,7 +24,7 @@ stages:
variables:
COMMON_MESON_FLAGS: "-Dwerror=true -Dcairo:werror=false -Dgi-docgen:werror=false -Dgraphene:werror=false -Dlibepoxy:werror=false -Dlibsass:werror=false -Dpango:werror=false -Dsassc:werror=false -Dgdk-pixbuf:werror=false -Dglib:werror=false -Dlibcloudproviders:werror=false -Dlibpng:werror=false -Dlibtiff:werror=false -Dsysprof:werror=false -Dwayland-protocols:werror=false -Dharfbuzz:werror=false -Dfreetype2:werror=false -Dfontconfig:werror=false -Dfribidi:werror=false -Dlibffi:werror=false -Dlibjpeg-turbo:werror=false -Dmutest:werror=false -Dpixman:werror=false -Dproxy-libintl:werror=false"
BACKEND_FLAGS: "-Dx11-backend=true -Dwayland-backend=true -Dbroadway-backend=true"
FEATURE_FLAGS: "-Dvulkan=enabled -Dcloudproviders=enabled -Dbuild-testsuite=true"
FEATURE_FLAGS: "-Dvulkan=enabled -Dcloudproviders=enabled -Dbuild-testsuite=true -Dintrospection=enabled"
MESON_TEST_TIMEOUT_MULTIPLIER: 3
FEDORA_IMAGE: "registry.gitlab.gnome.org/gnome/gtk/fedora:v46"
@@ -123,6 +123,26 @@ release-build:
- LD_LIBRARY_PATH=${CI_PROJECT_DIR}/_install/lib64 meson compile -C _build_hello
- .gitlab-ci/run-tests.sh _build x11
fedora-clang:
extends: .build-fedora-default
stage: build
needs: []
variables:
EXTRA_MESON_FLAGS: "--buildtype=release"
script:
- .gitlab-ci/show-info-linux.sh
- export PATH="$HOME/.local/bin:$PATH"
- export CC=clang
- meson subprojects download
- meson subprojects update --reset
- meson setup
${COMMON_MESON_FLAGS}
${EXTRA_MESON_FLAGS}
${BACKEND_FLAGS}
${FEATURE_FLAGS}
_build
- meson compile -C _build
fedora-mingw64:
extends: .build-fedora-default
stage: build
+58
View File
@@ -1,6 +1,64 @@
Overview of Changes in 4.11.3, xx-xx-xxxx
=========================================
* GtkGridView:
- Respect css border-spacing
- Don't leak the factories
* GtkListView:
- Don't leak the factories
* GtkColumnView:
- Support displaying sections
* GtkNotebook:
- Make the pages model implement GtkSelectionModel
* GtkScrolledWindow:
- Propagate child measure size whenever possible
* GtkPopoverMenu:
- Avoid unnecessary left padding
* Css:
- Add new binding-friendly css provider apis
* GDK:
- Support grayscale texture and alpha texture formats
for loading and saving to png and tiff, and in GL
* Theme:
- Show focus in the shortcuts window
* Tests:
- Improve test coverage
* Wayland:
- Make exporting surface handles more flexible
* Build:
- Some build options have been renamed:
demos -> build-demos
profile -> demo-profile
The old names still work
* Deprecations:
- gtk_css_provider_load_from_data
- gdk_wayland_toplevel_unexport_handle
- gdk_pixbuf_get_from_surface
- gdk_pixbuf_get_from_texture
- gtk_image_new_from_pixbuf
- gtk_image_set_from_pixbuf
- gtk_picture_new_for_pixbuf
- gtk_picture_set_pixbuf
* Translation updates:
Basque
Catalan
Russian
Turkish
Overview of Changes in 4.11.2, 09-05-2023
=========================================
+15 -1
View File
@@ -2244,20 +2244,24 @@ microphone-sensitivity-medium-symbolic</property>
<child>
<object class="GtkBox">
<property name="spacing">6</property>
<property name="valign">center</property>
<child>
<object class="GtkBox" id="lockbox">
<property name="hexpand">1</property>
<property name="spacing">6</property>
<property name="valign">center</property>
<child>
<object class="GtkMenuButton" id="open_menubutton">
<property name="halign">3</property>
<property name="popover">open_popover</property>
<property name="label">Open</property>
<property name="valign">center</property>
</object>
</child>
<child>
<object class="GtkToggleButton" id="record_button">
<property name="halign">3</property>
<property name="valign">center</property>
<signal name="toggled" handler="on_record_button_toggled"/>
<style>
<class name="text-button"/>
@@ -2267,16 +2271,19 @@ microphone-sensitivity-medium-symbolic</property>
<child>
<object class="GtkBox">
<property name="spacing">6</property>
<property name="valign">center</property>
<child>
<object class="GtkImage">
<property name="valign">4</property>
<property name="icon-name">media-record-symbolic</property>
<property name="valign">center</property>
</object>
</child>
<child>
<object class="GtkLabel">
<property name="valign">4</property>
<property name="label">Record</property>
<property name="valign">center</property>
</object>
</child>
</object>
@@ -2285,6 +2292,7 @@ microphone-sensitivity-medium-symbolic</property>
</child>
<child>
<object class="GtkBox">
<property name="valign">center</property>
<style>
<class name="linked"/>
</style>
@@ -2292,12 +2300,14 @@ microphone-sensitivity-medium-symbolic</property>
<object class="GtkToggleButton" id="grid_button">
<property name="active">1</property>
<property name="icon-name">view-grid-symbolic</property>
<property name="valign">center</property>
</object>
</child>
<child>
<object class="GtkToggleButton" id="list_button">
<property name="group">grid_button</property>
<property name="icon-name">view-list-symbolic</property>
<property name="valign">center</property>
</object>
</child>
</object>
@@ -2305,6 +2315,7 @@ microphone-sensitivity-medium-symbolic</property>
<child>
<object class="GtkButton" id="circular_button">
<property name="icon-name">emblem-system-symbolic</property>
<property name="valign">center</property>
<style>
<class name="circular"/>
</style>
@@ -2313,12 +2324,15 @@ microphone-sensitivity-medium-symbolic</property>
</object>
</child>
<child>
<object class="GtkLockButton" id="lockbutton"/>
<object class="GtkLockButton" id="lockbutton">
<property name="valign">center</property>
</object>
</child>
<child>
<object class="GtkMenuButton">
<property name="icon-name">view-more-symbolic</property>
<property name="menu-model">new_style_menu_model</property>
<property name="valign">center</property>
</object>
</child>
</object>
+1 -1
View File
@@ -68,7 +68,7 @@ in a selector, widget names must be prefixed with a &num; character.
| E:focus-within | [CSS Selector Level 4](https://drafts.csswg.org/selectors/#focus-within-pseudo) | Set on all ancestors of the focus widget, unlike CSS |
| E:focus-visible | [CSS Selector Level 4](https://drafts.csswg.org/selectors/#focus-within-pseudo) | Set on focus widget and all ancestors, unlike CSS |
| E:disabled | [CSS Selector Level 3](https://www.w3.org/TR/css3-selectors/#UIstates) | Corresponds to GTK_STATE_FLAG_INSENSITIVE |
| E:disabled | [CSS Selector Level 3](https://www.w3.org/TR/css3-selectors/#UIstates) | Corresponds to GTK_STATE_FLAG_CHECKED |
| E:checked | [CSS Selector Level 3](https://www.w3.org/TR/css3-selectors/#UIstates) | Corresponds to GTK_STATE_FLAG_CHECKED |
| E:indeterminate | [CSS Selector Level 3](https://www.w3.org/TR/css3-selectors/#indeterminate) | Corresponds to GTK_STATE_FLAG_INCONSISTENT |
| E:backdrop, E:selected | | Corresponds to GTK_STATE_FLAG_BACKDROP, GTK_STATE_FLAG_SELECTED |
| E:not(selector) | [CSS Selector Level 3](https://www.w3.org/TR/css3-selectors/#negation) | |
@@ -196,6 +196,15 @@ The _data table_ style of list is a high density table, similar in style to a
traditional treeview. Individual cells can be selectable and editable. Use
the `.data-table` style class.
## Sections
List models can optionally group their items into **_sections_**, by implementing
the `GtkSectionModel` interface. Both `GtkListView` and `GtkGridView` can
display headers for sections, by installing a separate **_header factory_**.
Many GTK list models support section inherently, or they pass through the
section of a model they are wrapping.
## Comparison to GtkTreeView
Developers familiar with `GtkTreeView` may wonder how this way of doing lists
+6 -6
View File
@@ -1,7 +1,7 @@
gdk_deprecated_sources = [
'deprecated/gdkpixbuf.c',
]
gdk_deprecated_sources = files([
'gdkpixbuf.c',
])
gdk_deprecated_headers = [
'deprecated/gdkpixbuf.h',
]
gdk_deprecated_headers = files([
'gdkpixbuf.h',
])
+24
View File
@@ -30,6 +30,8 @@
#include <glib.h>
#include <gdk/version/gdkversionmacros.h>
G_BEGIN_DECLS
/**
@@ -306,6 +308,20 @@ typedef enum
* the alpha value. Since: 4.6
* @GDK_MEMORY_R32G32B32A32_FLOAT: 4 float values; for red, green, blue and
* alpha. Since: 4.6
* @GDK_MEMORY_G8A8_PREMULTIPLIED: 2 bytes; for grayscale, alpha. The color
* values are premultiplied with the alpha value. Since: 4.12
* @GDK_MEMORY_G8A8: 2 bytes; for grayscale, alpha. Since: 4.12
* @GDK_MEMORY_G8: One byte; for grayscale. The data is opaque.
* Since: 4.12
* @GDK_MEMORY_G16A16_PREMULTIPLIED: 2 guint16 values; for grayscale, alpha.
* The color values are premultiplied with the alpha value. Since: 4.12
* @GDK_MEMORY_G16A16: 2 guint16 values; for grayscale, alpha. Since: 4.12
* @GDK_MEMORY_G16: One guint16 value; for grayscale. The data is opaque.
* Since: 4.12
* @GDK_MEMORY_A8: One byte; for alpha.
* Since: 4.12
* @GDK_MEMORY_A16: One guint16 value; for alpha.
* Since: 4.12
* @GDK_MEMORY_N_FORMATS: The number of formats. This value will change as
* more formats get added, so do not rely on its concrete integer.
*
@@ -340,6 +356,14 @@ typedef enum {
GDK_MEMORY_R32G32B32_FLOAT,
GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED,
GDK_MEMORY_R32G32B32A32_FLOAT,
GDK_MEMORY_G8A8_PREMULTIPLIED GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_G8A8 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_G8 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_G16A16_PREMULTIPLIED GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_G16A16 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_G16 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_A8 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_A16 GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GDK_MEMORY_N_FORMATS
} GdkMemoryFormat;
+23 -23
View File
@@ -466,29 +466,26 @@ gdk_gl_context_real_get_damage (GdkGLContext *context)
eglQuerySurface (gdk_display_get_egl_display (display), egl_surface,
EGL_BUFFER_AGE_EXT, &buffer_age);
switch (buffer_age)
if (buffer_age > 0 && buffer_age <= GDK_GL_MAX_TRACKED_BUFFERS)
{
case 1:
return cairo_region_create ();
break;
cairo_region_t *damage = cairo_region_create ();
int i;
case 2:
if (context->old_updated_area[0])
return cairo_region_copy (context->old_updated_area[0]);
break;
for (i = 0; i < buffer_age - 1; i++)
{
if (context->old_updated_area[i] == NULL)
{
cairo_region_create_rectangle (&(GdkRectangle) {
0, 0,
gdk_surface_get_width (surface),
gdk_surface_get_height (surface)
});
break;
}
cairo_region_union (damage, context->old_updated_area[i]);
}
case 3:
if (context->old_updated_area[0] &&
context->old_updated_area[1])
{
cairo_region_t *damage = cairo_region_copy (context->old_updated_area[0]);
cairo_region_union (damage, context->old_updated_area[1]);
return damage;
}
break;
default:
;
return damage;
}
}
#endif
@@ -597,6 +594,7 @@ gdk_gl_context_real_begin_frame (GdkDrawContext *draw_context,
cairo_region_t *damage;
double scale;
int ww, wh;
int i;
surface = gdk_draw_context_get_surface (draw_context);
scale = gdk_gl_context_get_scale (context);
@@ -608,9 +606,11 @@ gdk_gl_context_real_begin_frame (GdkDrawContext *draw_context,
damage = GDK_GL_CONTEXT_GET_CLASS (context)->get_damage (context);
if (context->old_updated_area[1])
cairo_region_destroy (context->old_updated_area[1]);
context->old_updated_area[1] = context->old_updated_area[0];
g_clear_pointer (&context->old_updated_area[GDK_GL_MAX_TRACKED_BUFFERS - 1], cairo_region_destroy);
for (i = GDK_GL_MAX_TRACKED_BUFFERS - 1; i > 0; i--)
{
context->old_updated_area[i] = context->old_updated_area[i - 1];
}
context->old_updated_area[0] = cairo_region_copy (region);
cairo_region_union (region, damage);
+6 -1
View File
@@ -34,6 +34,11 @@ typedef enum {
GDK_GL_CGL
} GdkGLBackend;
/* The maximum amount of buffers we track update regions for.
* Note that this is equal to the max buffer age value we
* can provide a damage region for */
#define GDK_GL_MAX_TRACKED_BUFFERS 4
#define GDK_GL_CONTEXT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GDK_TYPE_GL_CONTEXT, GdkGLContextClass))
#define GDK_IS_GL_CONTEXT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GDK_TYPE_GL_CONTEXT))
#define GDK_GL_CONTEXT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GDK_TYPE_GL_CONTEXT, GdkGLContextClass))
@@ -45,7 +50,7 @@ struct _GdkGLContext
GdkDrawContext parent_instance;
/* We store the old drawn areas to support buffer-age optimizations */
cairo_region_t *old_updated_area[2];
cairo_region_t *old_updated_area[GDK_GL_MAX_TRACKED_BUFFERS];
};
struct _GdkGLContextClass
+139 -15
View File
@@ -138,6 +138,7 @@ static gboolean
gdk_gl_texture_find_format (gboolean use_es,
guint gl_major,
guint gl_minor,
GdkMemoryAlpha alpha,
GLint gl_format,
GLint gl_type,
GdkMemoryFormat *out_format)
@@ -147,8 +148,12 @@ gdk_gl_texture_find_format (gboolean use_es,
for (format = 0; format < GDK_MEMORY_N_FORMATS; format++)
{
GLenum q_internal_format, q_format, q_type;
GLint q_swizzle[4];
if (!gdk_memory_format_gl_format (format, use_es, gl_major, gl_minor, &q_internal_format, &q_format, &q_type))
if (gdk_memory_format_alpha (format) != alpha)
continue;
if (!gdk_memory_format_gl_format (format, use_es, gl_major, gl_minor, &q_internal_format, &q_format, &q_type, &q_swizzle))
continue;
if (q_format != gl_format || q_type != gl_type)
@@ -167,23 +172,57 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
gpointer download_)
{
GdkTexture *texture = GDK_TEXTURE (self);
GdkMemoryFormat format;
gsize expected_stride;
Download *download = download_;
GLenum gl_internal_format, gl_format, gl_type;
GLint gl_swizzle[4];
int major, minor;
format = gdk_texture_get_format (texture),
expected_stride = texture->width * gdk_memory_format_bytes_per_pixel (download->format);
gdk_gl_context_get_version (context, &major, &minor);
if (download->stride == expected_stride &&
!gdk_gl_context_get_use_es (context) &&
gdk_memory_format_gl_format (download->format, TRUE, major, minor, &gl_internal_format, &gl_format, &gl_type))
if (!gdk_gl_context_get_use_es (context) &&
gdk_memory_format_gl_format (format,
FALSE,
major, minor,
&gl_internal_format,
&gl_format, &gl_type, &gl_swizzle))
{
glGetTexImage (GL_TEXTURE_2D,
0,
gl_format,
gl_type,
download->data);
if (download->stride == expected_stride &&
download->format == format)
{
glGetTexImage (GL_TEXTURE_2D,
0,
gl_format,
gl_type,
download->data);
}
else
{
gsize stride = texture->width * gdk_memory_format_bytes_per_pixel (format);
guchar *pixels = g_malloc_n (stride, texture->height);
glPixelStorei (GL_PACK_ALIGNMENT, 1);
glGetTexImage (GL_TEXTURE_2D,
0,
gl_format,
gl_type,
pixels);
gdk_memory_convert (download->data,
download->stride,
download->format,
pixels,
stride,
format,
texture->width,
texture->height);
g_free (pixels);
}
}
else
{
@@ -196,17 +235,26 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
glFramebufferTexture2D (GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, self->id, 0);
if (gdk_gl_context_check_version (context, "4.3", "3.1"))
{
gdk_gl_context_get_version (context, &major, &minor);
glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_FORMAT, &gl_read_format);
glGetFramebufferParameteriv (GL_FRAMEBUFFER, GL_IMPLEMENTATION_COLOR_READ_TYPE, &gl_read_type);
if (!gdk_gl_texture_find_format (gdk_gl_context_get_use_es (context), major, minor, gl_read_format, gl_read_type, &actual_format))
actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED; /* pray */
if (!gdk_gl_texture_find_format (TRUE, major, minor, gdk_memory_format_alpha (format), gl_read_format, gl_read_type, &actual_format))
{
gl_read_format = GL_RGBA;
gl_read_type = GL_UNSIGNED_BYTE;
if (gdk_memory_format_alpha (format) == GDK_MEMORY_ALPHA_PREMULTIPLIED)
actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED; /* pray */
else
actual_format = GDK_MEMORY_R8G8B8A8;
}
}
else
{
gl_read_format = GL_RGBA;
gl_read_type = GL_UNSIGNED_BYTE;
actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED;
if (gdk_memory_format_alpha (format) == GDK_MEMORY_ALPHA_PREMULTIPLIED)
actual_format = GDK_MEMORY_R8G8B8A8_PREMULTIPLIED; /* pray */
else
actual_format = GDK_MEMORY_R8G8B8A8;
}
if (download->format == actual_format &&
@@ -221,19 +269,95 @@ gdk_gl_texture_do_download (GdkGLTexture *self,
else
{
gsize actual_bpp = gdk_memory_format_bytes_per_pixel (actual_format);
guchar *pixels = g_malloc_n (texture->width * actual_bpp, texture->height);
gsize stride = actual_bpp * texture->width;
guchar *pixels = g_malloc_n (stride, texture->height);
glPixelStorei (GL_PACK_ALIGNMENT, 1);
glReadPixels (0, 0,
texture->width, texture->height,
gl_read_format,
gl_read_type,
pixels);
/* Fix up gles inadequacies */
if (gl_read_format == GL_RGBA &&
gl_read_type == GL_UNSIGNED_BYTE &&
(format == GDK_MEMORY_G8A8 ||
format == GDK_MEMORY_G8A8_PREMULTIPLIED ||
format == GDK_MEMORY_G8 ||
format == GDK_MEMORY_A8))
{
for (unsigned int y = 0; y < texture->height; y++)
{
for (unsigned int x = 0; x < texture->width; x++)
{
guchar *data = &pixels[y * stride + x * actual_bpp];
if (format == GDK_MEMORY_G8A8 ||
format == GDK_MEMORY_G8A8_PREMULTIPLIED)
{
data[3] = data[1];
data[1] = data[0];
data[2] = data[0];
}
else if (format == GDK_MEMORY_G8)
{
data[1] = data[0];
data[2] = data[0];
data[3] = 0xff;
}
else if (format == GDK_MEMORY_A8)
{
data[3] = data[0];
data[0] = 0;
data[1] = 0;
data[2] = 0;
}
}
}
}
if (gl_read_format == GL_RGBA &&
gl_read_type == GL_UNSIGNED_SHORT &&
(format == GDK_MEMORY_G16A16 ||
format == GDK_MEMORY_G16A16_PREMULTIPLIED ||
format == GDK_MEMORY_G16 ||
format == GDK_MEMORY_A16))
{
for (unsigned int y = 0; y < texture->height; y++)
{
for (unsigned int x = 0; x < texture->width; x++)
{
guint16 *data = (guint16 *) &pixels[y * stride + x * actual_bpp];
if (format == GDK_MEMORY_G16A16 ||
format == GDK_MEMORY_G16A16_PREMULTIPLIED)
{
data[3] = data[1];
data[1] = data[0];
data[2] = data[0];
}
else if (format == GDK_MEMORY_G16)
{
data[1] = data[0];
data[2] = data[0];
data[3] = 0xffff;
}
else if (format == GDK_MEMORY_A16)
{
data[3] = data[0];
data[0] = 0;
data[1] = 0;
data[2] = 0;
}
}
}
}
gdk_memory_convert (download->data,
download->stride,
download->format,
pixels,
texture->width * actual_bpp,
stride,
actual_format,
texture->width,
texture->height);
+8
View File
@@ -644,10 +644,18 @@ gdk_gl_texture_builder_get_format (GdkGLTextureBuilder *self)
* The format is the preferred format the texture data should be downloaded to. The
* format must be supported by the GL version of [property@Gdk.GLTextureBuilder:context].
*
* GDK's texture download code assumes that the format corresponds to the storage
* parameters of the GL texture in an obvious way. For example, a format of
* `GDK_MEMORY_R16G16B16A16_PREMULTIPLIED` is expected to be stored as `GL_RGBA16`
* texture, and `GDK_MEMORY_G8A8` is expected to be stored as `GL_RG8` texture.
*
* Setting the right format is particularly useful when using high bit depth textures
* to preserve the bit depth, to set the correct value for unpremultiplied textures
* and to make sure opaque textures are treated as such.
*
* Non-RGBA textures need to have swizzling parameters set up properly to be usable
* in GSK's shaders.
*
* Since: 4.12
*/
void
+141 -22
View File
@@ -60,6 +60,36 @@ name ## _from_float (guchar *dest_data, \
} \
}
#define TYPED_GRAY_FUNCS(name, T, G, A, bpp, scale) \
static void \
name ## _to_float (float *dest, \
const guchar *src_data, \
gsize n) \
{ \
for (gsize i = 0; i < n; i++) \
{ \
T *src = (T *) (src_data + i * bpp); \
if (G >= 0) dest[0] = (float) src[G] / scale; else dest[0] = 1.0; \
dest[1] = dest[2] = dest[0]; \
if (A >= 0) dest[3] = (float) src[A] / scale; else dest[3] = 1.0; \
dest += 4; \
} \
} \
\
static void \
name ## _from_float (guchar *dest_data, \
const float *src, \
gsize n) \
{ \
for (gsize i = 0; i < n; i++) \
{ \
T *dest = (T *) (dest_data + i * bpp); \
if (G >= 0) dest[G] = CLAMP ((src[0] + src[1] + src[2]) * scale / 3.f + 0.5, 0, scale); \
if (A >= 0) dest[A] = CLAMP (src[3] * scale + 0.5, 0, scale); \
src += 4; \
} \
}
TYPED_FUNCS (b8g8r8a8_premultiplied, guchar, 2, 1, 0, 3, 4, 255)
TYPED_FUNCS (a8r8g8b8_premultiplied, guchar, 1, 2, 3, 0, 4, 255)
TYPED_FUNCS (r8g8b8a8_premultiplied, guchar, 0, 1, 2, 3, 4, 255)
@@ -72,6 +102,15 @@ TYPED_FUNCS (b8g8r8, guchar, 2, 1, 0, -1, 3, 255)
TYPED_FUNCS (r16g16b16, guint16, 0, 1, 2, -1, 6, 65535)
TYPED_FUNCS (r16g16b16a16, guint16, 0, 1, 2, 3, 8, 65535)
TYPED_GRAY_FUNCS (g8a8_premultiplied, guchar, 0, 1, 2, 255)
TYPED_GRAY_FUNCS (g8a8, guchar, 0, 1, 2, 255)
TYPED_GRAY_FUNCS (g8, guchar, 0, -1, 1, 255)
TYPED_GRAY_FUNCS (a8, guchar, -1, 0, 1, 255)
TYPED_GRAY_FUNCS (g16a16_premultiplied, guint16, 0, 1, 4, 65535)
TYPED_GRAY_FUNCS (g16a16, guint16, 0, 1, 4, 65535)
TYPED_GRAY_FUNCS (g16, guint16, 0, -1, 2, 65535)
TYPED_GRAY_FUNCS (a16, guint16, -1, 0, 2, 65535)
static void
r16g16b16_float_to_float (float *dest,
const guchar *src_data,
@@ -230,6 +269,7 @@ struct _GdkMemoryFormatDescription
guint internal_format;
guint format;
guint type;
GLint swizzle[4];
} gl;
/* no premultiplication going on here */
void (* to_float) (float *, const guchar*, gsize);
@@ -251,7 +291,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE },
{ GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
b8g8r8a8_premultiplied_to_float,
b8g8r8a8_premultiplied_from_float,
},
@@ -261,7 +301,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGBA8, GL_BGRA, GDK_GL_UNSIGNED_BYTE_FLIPPED },
{ GL_RGBA8, GL_BGRA, GDK_GL_UNSIGNED_BYTE_FLIPPED, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
a8r8g8b8_premultiplied_to_float,
a8r8g8b8_premultiplied_from_float,
},
@@ -271,7 +311,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 0, 0 },
{ GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE },
{ GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r8g8b8a8_premultiplied_to_float,
r8g8b8a8_premultiplied_from_float,
},
@@ -281,7 +321,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE },
{ GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
b8g8r8a8_to_float,
b8g8r8a8_from_float,
},
@@ -291,7 +331,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGBA8, GL_RGBA, GDK_GL_UNSIGNED_BYTE_FLIPPED },
{ GL_RGBA8, GL_RGBA, GDK_GL_UNSIGNED_BYTE_FLIPPED, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
a8r8g8b8_to_float,
a8r8g8b8_from_float,
},
@@ -301,7 +341,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 0, 0 },
{ GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE },
{ GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r8g8b8a8_to_float,
r8g8b8a8_from_float,
},
@@ -311,7 +351,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGBA8, GL_BGRA, GDK_GL_UNSIGNED_BYTE_FLIPPED },
{ GL_RGBA8, GL_BGRA, GDK_GL_UNSIGNED_BYTE_FLIPPED, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
a8b8g8r8_to_float,
a8b8g8r8_from_float,
},
@@ -321,7 +361,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 0, 0 },
{ GL_RGB8, GL_RGB, GL_UNSIGNED_BYTE },
{ GL_RGB8, GL_RGB, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ONE } },
r8g8b8_to_float,
r8g8b8_from_float,
},
@@ -331,7 +371,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, G_MAXUINT, G_MAXUINT },
{ GL_RGB8, GL_BGR, GL_UNSIGNED_BYTE },
{ GL_RGB8, GL_BGR, GL_UNSIGNED_BYTE, { GL_RED, GL_GREEN, GL_BLUE, GL_ONE } },
b8g8r8_to_float,
b8g8r8_from_float,
},
@@ -341,7 +381,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGB16, GL_RGB, GL_UNSIGNED_SHORT },
{ GL_RGB16, GL_RGB, GL_UNSIGNED_SHORT, { GL_RED, GL_GREEN, GL_BLUE, GL_ONE } },
r16g16b16_to_float,
r16g16b16_from_float,
},
@@ -351,7 +391,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT },
{ GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r16g16b16a16_to_float,
r16g16b16a16_from_float,
},
@@ -361,7 +401,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT },
{ GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r16g16b16a16_to_float,
r16g16b16a16_from_float,
},
@@ -371,7 +411,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGB16F, GL_RGB, GL_HALF_FLOAT },
{ GL_RGB16F, GL_RGB, GL_HALF_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ONE } },
r16g16b16_float_to_float,
r16g16b16_float_from_float,
},
@@ -381,7 +421,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT },
{ GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r16g16b16a16_float_to_float,
r16g16b16a16_float_from_float,
},
@@ -391,7 +431,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT },
{ GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r16g16b16a16_float_to_float,
r16g16b16a16_float_from_float,
},
@@ -401,7 +441,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (float),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGB32F, GL_RGB, GL_FLOAT },
{ GL_RGB32F, GL_RGB, GL_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ONE } },
r32g32b32_float_to_float,
r32g32b32_float_from_float,
},
@@ -411,7 +451,7 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (float),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA32F, GL_RGBA, GL_FLOAT },
{ GL_RGBA32F, GL_RGBA, GL_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r32g32b32a32_float_to_float,
r32g32b32a32_float_from_float,
},
@@ -421,9 +461,89 @@ static const GdkMemoryFormatDescription memory_formats[GDK_MEMORY_N_FORMATS] = {
G_ALIGNOF (float),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RGBA32F, GL_RGBA, GL_FLOAT },
{ GL_RGBA32F, GL_RGBA, GL_FLOAT, { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA } },
r32g32b32a32_float_to_float,
r32g32b32a32_float_from_float,
},
[GDK_MEMORY_G8A8_PREMULTIPLIED] = {
GDK_MEMORY_ALPHA_PREMULTIPLIED,
2,
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 3, 0 },
{ GL_RG8, GL_RG, GL_UNSIGNED_BYTE, { GL_RED, GL_RED, GL_RED, GL_GREEN } },
g8a8_premultiplied_to_float,
g8a8_premultiplied_from_float,
},
[GDK_MEMORY_G8A8] = {
GDK_MEMORY_ALPHA_STRAIGHT,
2,
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 3, 0 },
{ GL_RG8, GL_RG, GL_UNSIGNED_BYTE, { GL_RED, GL_RED, GL_RED, GL_GREEN } },
g8a8_to_float,
g8a8_from_float,
},
[GDK_MEMORY_G8] = {
GDK_MEMORY_ALPHA_OPAQUE,
1,
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 3, 0 },
{ GL_R8, GL_RED, GL_UNSIGNED_BYTE, { GL_RED, GL_RED, GL_RED, GL_ONE } },
g8_to_float,
g8_from_float,
},
[GDK_MEMORY_G16A16_PREMULTIPLIED] = {
GDK_MEMORY_ALPHA_PREMULTIPLIED,
4,
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RG16, GL_RG, GL_UNSIGNED_SHORT, { GL_RED, GL_RED, GL_RED, GL_GREEN } },
g16a16_premultiplied_to_float,
g16a16_premultiplied_from_float,
},
[GDK_MEMORY_G16A16] = {
GDK_MEMORY_ALPHA_STRAIGHT,
4,
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_RG16, GL_RG, GL_UNSIGNED_SHORT, { GL_RED, GL_RED, GL_RED, GL_GREEN } },
g16a16_to_float,
g16a16_from_float,
},
[GDK_MEMORY_G16] = {
GDK_MEMORY_ALPHA_OPAQUE,
2,
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_R16, GL_RED, GL_UNSIGNED_SHORT, { GL_RED, GL_RED, GL_RED, GL_ONE } },
g16_to_float,
g16_from_float,
},
[GDK_MEMORY_A8] = {
GDK_MEMORY_ALPHA_STRAIGHT,
1,
G_ALIGNOF (guchar),
FALSE,
{ 0, 0, 3, 0 },
{ GL_R8, GL_RED, GL_UNSIGNED_BYTE, { GL_ONE, GL_ONE, GL_ONE, GL_RED } },
a8_to_float,
a8_from_float,
},
[GDK_MEMORY_A16] = {
GDK_MEMORY_ALPHA_STRAIGHT,
2,
G_ALIGNOF (guint16),
TRUE,
{ 0, 0, 3, 0 },
{ GL_R16, GL_RED, GL_UNSIGNED_SHORT, { GL_ONE, GL_ONE, GL_ONE, GL_RED } },
a16_to_float,
a16_from_float,
}
};
@@ -472,14 +592,13 @@ gdk_memory_format_gl_format (GdkMemoryFormat format,
guint gl_minor,
guint *out_internal_format,
guint *out_format,
guint *out_type)
guint *out_type,
GLint (*out_swizzle)[4])
{
*out_internal_format = memory_formats[format].gl.internal_format;
*out_format = memory_formats[format].gl.format;
*out_type = memory_formats[format].gl.type;
if (memory_formats[format].alpha == GDK_MEMORY_ALPHA_STRAIGHT)
return FALSE;
memcpy (out_swizzle, &memory_formats[format].gl.swizzle, sizeof(GLint) * 4);
if (gles)
{
+4 -1
View File
@@ -21,6 +21,8 @@
#include "gdkenums.h"
#include <epoxy/gl.h>
G_BEGIN_DECLS
typedef enum {
@@ -39,7 +41,8 @@ gboolean gdk_memory_format_gl_format (GdkMemoryFormat
guint gl_minor,
guint *out_internal_format,
guint *out_format,
guint *out_type);
guint *out_type,
GLint (*out_gizzle)[4]);
void gdk_memory_convert (guchar *dest_data,
gsize dest_stride,
+3 -1
View File
@@ -170,7 +170,7 @@ parse_rgb_value (const char *str,
*
* The string can be either one of:
*
* - A standard name (Taken from the Css specification).
* - A standard name (Taken from the CSS specification).
* - A hexadecimal value in the form “\#rgb”, “\#rrggbb”,
* “\#rrrgggbbb” or ”\#rrrrggggbbbb”
* - A hexadecimal value in the form “\#rgba”, “\#rrggbbaa”,
@@ -178,6 +178,8 @@ parse_rgb_value (const char *str,
* - A RGB color in the form “rgb(r,g,b)” (In this case the color
* will have full opacity)
* - A RGBA color in the form “rgba(r,g,b,a)”
* - A HSL color in the form "hsl(hue, saturation, lightness)"
* - A HSLA color in the form "hsla(hue, saturation, lightness, alpha)"
*
* Where “r”, “g”, “b” and “a” are respectively the red, green,
* blue and alpha color values. In the last two cases, “r”, “g”,
+49 -6
View File
@@ -183,8 +183,7 @@ gdk_load_png (GBytes *bytes,
if (color_type == PNG_COLOR_TYPE_PALETTE)
png_set_palette_to_rgb (png);
if (color_type == PNG_COLOR_TYPE_GRAY ||
color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
if (color_type == PNG_COLOR_TYPE_GRAY)
png_set_expand_gray_1_2_4_to_8 (png);
if (png_get_valid (png, info, PNG_INFO_tRNS))
@@ -193,10 +192,6 @@ gdk_load_png (GBytes *bytes,
if (depth < 8)
png_set_packing (png);
if (color_type == PNG_COLOR_TYPE_GRAY ||
color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
png_set_gray_to_rgb (png);
if (interlace != PNG_INTERLACE_NONE)
png_set_interlace_handling (png);
@@ -239,6 +234,26 @@ gdk_load_png (GBytes *bytes,
format = GDK_MEMORY_R16G16B16;
}
break;
case PNG_COLOR_TYPE_GRAY:
if (depth == 8)
{
format = GDK_MEMORY_G8;
}
else if (depth == 16)
{
format = GDK_MEMORY_G16;
}
break;
case PNG_COLOR_TYPE_GRAY_ALPHA:
if (depth == 8)
{
format = GDK_MEMORY_G8A8;
}
else if (depth == 16)
{
format = GDK_MEMORY_G16A16;
}
break;
default:
png_destroy_read_struct (&png, &info, NULL);
g_set_error (error,
@@ -349,6 +364,34 @@ gdk_save_png (GdkTexture *texture)
depth = 16;
break;
case GDK_MEMORY_G8:
format = GDK_MEMORY_G8;
png_format = PNG_COLOR_TYPE_GRAY;
depth = 8;
break;
case GDK_MEMORY_G8A8_PREMULTIPLIED:
case GDK_MEMORY_G8A8:
case GDK_MEMORY_A8:
format = GDK_MEMORY_G8A8;
png_format = PNG_COLOR_TYPE_GRAY_ALPHA;
depth = 8;
break;
case GDK_MEMORY_G16:
format = GDK_MEMORY_G16;
png_format = PNG_COLOR_TYPE_GRAY;
depth = 16;
break;
case GDK_MEMORY_G16A16_PREMULTIPLIED:
case GDK_MEMORY_G16A16:
case GDK_MEMORY_A16:
format = GDK_MEMORY_G16A16;
png_format = PNG_COLOR_TYPE_GRAY_ALPHA;
depth = 16;
break;
case GDK_MEMORY_N_FORMATS:
default:
g_assert_not_reached ();
+32 -22
View File
@@ -229,27 +229,36 @@ struct _FormatData {
guint16 samples_per_pixel;
guint16 sample_format;
guint16 alpha_samples;
guint16 photometric;
};
static const FormatData format_data[] = {
[GDK_MEMORY_B8G8R8A8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_A8R8G8B8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_R8G8B8A8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_B8G8R8A8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_A8R8G8B8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_R8G8B8A8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_A8B8G8R8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_R8G8B8] = { GDK_MEMORY_R8G8B8, 8, 3, SAMPLEFORMAT_UINT, 0 },
[GDK_MEMORY_B8G8R8] = { GDK_MEMORY_R8G8B8, 8, 3, SAMPLEFORMAT_UINT, 0 },
[GDK_MEMORY_R16G16B16] = { GDK_MEMORY_R16G16B16, 16, 3, SAMPLEFORMAT_UINT, 0 },
[GDK_MEMORY_R16G16B16A16_PREMULTIPLIED] = { GDK_MEMORY_R16G16B16A16_PREMULTIPLIED, 16, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_R16G16B16A16] = { GDK_MEMORY_R16G16B16A16, 16, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_R16G16B16_FLOAT] = { GDK_MEMORY_R16G16B16_FLOAT, 16, 3, SAMPLEFORMAT_IEEEFP, 0 },
[GDK_MEMORY_R16G16B16A16_FLOAT_PREMULTIPLIED] = { GDK_MEMORY_R16G16B16A16_FLOAT_PREMULTIPLIED, 16, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_R16G16B16A16_FLOAT] = { GDK_MEMORY_R16G16B16A16_FLOAT, 16, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_R32G32B32_FLOAT] = { GDK_MEMORY_R32G32B32_FLOAT, 32, 3, SAMPLEFORMAT_IEEEFP, 0 },
[GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED] = { GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED, 32, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_ASSOCALPHA },
[GDK_MEMORY_R32G32B32A32_FLOAT] = { GDK_MEMORY_R32G32B32A32_FLOAT, 32, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_UNASSALPHA },
[GDK_MEMORY_B8G8R8A8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_A8R8G8B8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R8G8B8A8_PREMULTIPLIED] = { GDK_MEMORY_R8G8B8A8_PREMULTIPLIED, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_B8G8R8A8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_A8R8G8B8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R8G8B8A8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_A8B8G8R8] = { GDK_MEMORY_R8G8B8A8, 8, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R8G8B8] = { GDK_MEMORY_R8G8B8, 8, 3, SAMPLEFORMAT_UINT, 0, PHOTOMETRIC_RGB },
[GDK_MEMORY_B8G8R8] = { GDK_MEMORY_R8G8B8, 8, 3, SAMPLEFORMAT_UINT, 0, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16] = { GDK_MEMORY_R16G16B16, 16, 3, SAMPLEFORMAT_UINT, 0, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16A16_PREMULTIPLIED] = { GDK_MEMORY_R16G16B16A16_PREMULTIPLIED, 16, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16A16] = { GDK_MEMORY_R16G16B16A16, 16, 4, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16_FLOAT] = { GDK_MEMORY_R16G16B16_FLOAT, 16, 3, SAMPLEFORMAT_IEEEFP, 0, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16A16_FLOAT_PREMULTIPLIED] = { GDK_MEMORY_R16G16B16A16_FLOAT_PREMULTIPLIED, 16, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R16G16B16A16_FLOAT] = { GDK_MEMORY_R16G16B16A16_FLOAT, 16, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R32G32B32_FLOAT] = { GDK_MEMORY_R32G32B32_FLOAT, 32, 3, SAMPLEFORMAT_IEEEFP, 0, PHOTOMETRIC_RGB },
[GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED] = { GDK_MEMORY_R32G32B32A32_FLOAT_PREMULTIPLIED, 32, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_R32G32B32A32_FLOAT] = { GDK_MEMORY_R32G32B32A32_FLOAT, 32, 4, SAMPLEFORMAT_IEEEFP, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_RGB },
[GDK_MEMORY_G8A8_PREMULTIPLIED] = { GDK_MEMORY_G8A8_PREMULTIPLIED, 8, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_G8A8] = { GDK_MEMORY_G8A8, 8, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_G8] = { GDK_MEMORY_G8, 8, 1, SAMPLEFORMAT_UINT, 0, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_G16A16_PREMULTIPLIED] = { GDK_MEMORY_G16A16_PREMULTIPLIED, 16, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_ASSOCALPHA, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_G16A16] = { GDK_MEMORY_G16A16, 16, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_G16] = { GDK_MEMORY_G16, 16, 1, SAMPLEFORMAT_UINT, 0, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_A8] = { GDK_MEMORY_G8A8, 8, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_MINISBLACK },
[GDK_MEMORY_A16] = { GDK_MEMORY_G16A16, 16, 2, SAMPLEFORMAT_UINT, EXTRASAMPLE_UNASSALPHA, PHOTOMETRIC_MINISBLACK },
};
/* if this fails, somebody forgot to add formats above */
@@ -289,7 +298,7 @@ gdk_save_tiff (GdkTexture *texture)
if (fdata->alpha_samples)
TIFFSetField (tif, TIFFTAG_EXTRASAMPLES, 1, &fdata->alpha_samples);
TIFFSetField (tif, TIFFTAG_PHOTOMETRIC, PHOTOMETRIC_RGB);
TIFFSetField (tif, TIFFTAG_PHOTOMETRIC, fdata->photometric);
TIFFSetField (tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG);
gdk_texture_downloader_init (&downloader, texture);
@@ -397,7 +406,7 @@ gdk_load_tiff (GBytes *input_bytes,
TIFFGetFieldDefaulted (tif, TIFFTAG_IMAGEWIDTH, &width);
TIFFGetFieldDefaulted (tif, TIFFTAG_IMAGELENGTH, &height);
if (samples_per_pixel == 4)
if (samples_per_pixel == 2 || samples_per_pixel == 4)
{
guint16 extra;
guint16 *extra_types;
@@ -426,14 +435,15 @@ gdk_load_tiff (GBytes *input_bytes,
if (format_data[format].sample_format == sample_format &&
format_data[format].bits_per_sample == bits_per_sample &&
format_data[format].samples_per_pixel == samples_per_pixel &&
format_data[format].alpha_samples == alpha_samples)
format_data[format].alpha_samples == alpha_samples &&
format_data[format].photometric == photometric)
{
break;
}
}
if (format == G_N_ELEMENTS(format_data) ||
photometric != PHOTOMETRIC_RGB ||
(photometric != PHOTOMETRIC_RGB && photometric != PHOTOMETRIC_MINISBLACK) ||
planarconfig != PLANARCONFIG_CONTIG ||
TIFFIsTiled (tif) ||
orientation != ORIENTATION_TOPLEFT)
+3 -3
View File
@@ -344,14 +344,14 @@ create_pixel_format (GdkGLVersion *version,
if (gdk_gl_version_get_major (version) >= 4)
{
attrs[1] = (CGLPixelFormatAttribute)kCGLOGLPVersion_GL4_Core;
if (CGLChoosePixelFormat (attrs, &format, &n_format))
if (CHECK (error, CGLChoosePixelFormat (attrs, &format, &n_format)))
return g_steal_pointer (&format);
}
if (gdk_gl_version_greater_equal (version, &GDK_GL_MIN_GL_VERSION))
{
attrs[1] = (CGLPixelFormatAttribute)kCGLOGLPVersion_GL3_Core;
if (CGLChoosePixelFormat (attrs, &format, &n_format))
if (CHECK (error, CGLChoosePixelFormat (attrs, &format, &n_format)))
return g_steal_pointer (&format);
}
@@ -396,7 +396,7 @@ gdk_macos_gl_context_real_realize (GdkGLContext *context,
gdk_gl_context_get_matching_version (context,
GDK_GL_API_GL,
FALSE,
&version);
&min_version);
display = gdk_gl_context_get_display (context);
shared = gdk_display_get_gl_context (display);
+3 -3
View File
@@ -1436,7 +1436,7 @@ register_clipboard_notification ()
wclass.lpszClassName = "GdkClipboardNotification";
wclass.lpfnWndProc = _clipboard_window_procedure;
wclass.hInstance = _gdk_dll_hinstance;
wclass.hInstance = this_module ();
wclass.cbWndExtra = sizeof (GdkWin32ClipboardThread *);
klass = RegisterClass (&wclass);
@@ -1446,7 +1446,7 @@ register_clipboard_notification ()
clipboard_thread_data->clipboard_window = CreateWindow (MAKEINTRESOURCE (klass),
NULL, WS_POPUP,
0, 0, 0, 0, NULL, NULL,
_gdk_dll_hinstance, NULL);
this_module (), NULL);
if (clipboard_thread_data->clipboard_window == NULL)
goto failed;
@@ -1471,7 +1471,7 @@ register_clipboard_notification ()
failed:
g_critical ("Failed to install clipboard viewer");
UnregisterClass (MAKEINTRESOURCE (klass), _gdk_dll_hinstance);
UnregisterClass (MAKEINTRESOURCE (klass), this_module ());
return FALSE;
}
+7 -30
View File
@@ -417,13 +417,12 @@ hcursor_from_x_cursor (int i,
#undef SET_BIT
#undef RESET_BIT
rv = CreateCursor (_gdk_app_hmodule, cursors[i].hotx, cursors[i].hoty,
rv = CreateCursor (NULL, cursors[i].hotx, cursors[i].hoty,
w, h, and_plane, xor_plane);
}
else
{
rv = CreateCursor (_gdk_app_hmodule, 0, 0,
w, h, and_plane, xor_plane);
rv = CreateCursor (NULL, 0, 0, w, h, and_plane, xor_plane);
}
if (rv == NULL)
@@ -466,7 +465,7 @@ win32_cursor_create_win32hcursor (GdkWin32Display *display,
break;
case GDK_WIN32_CURSOR_LOAD_FROM_RESOURCE_THIS:
result = gdk_win32_hcursor_new (display,
LoadImageA (_gdk_app_hmodule,
LoadImageA (GetModuleHandle (NULL),
(const char *) cursor->resource_name,
IMAGE_CURSOR,
cursor->width,
@@ -476,7 +475,7 @@ win32_cursor_create_win32hcursor (GdkWin32Display *display,
break;
case GDK_WIN32_CURSOR_LOAD_FROM_RESOURCE_GTK:
result = gdk_win32_hcursor_new (display,
LoadImageA (_gdk_dll_hinstance,
LoadImageA (this_module (),
(const char *) cursor->resource_name,
IMAGE_CURSOR,
cursor->width,
@@ -858,9 +857,7 @@ create_blank_win32hcursor (GdkWin32Display *display)
xor_plane = g_malloc ((w/8) * h);
memset (xor_plane, 0, (w/8) * h);
rv = CreateCursor (_gdk_app_hmodule, 0, 0,
w, h, and_plane, xor_plane);
rv = CreateCursor (NULL, 0, 0, w, h, and_plane, xor_plane);
if (rv == NULL)
WIN32_API_FAILED ("CreateCursor");
@@ -871,6 +868,7 @@ static GdkWin32HCursor *
gdk_win32hcursor_create_for_name (GdkWin32Display *display,
const char *name)
{
const HINSTANCE hinstance = GetModuleHandle (NULL);
GdkWin32HCursor *win32hcursor = NULL;
/* Blank cursor case */
@@ -885,7 +883,7 @@ gdk_win32hcursor_create_for_name (GdkWin32Display *display,
/* Allow to load named cursor resources linked into the executable.
* Cursors obtained with LoadCursor() cannot be destroyed.
*/
return gdk_win32_hcursor_new (display, LoadCursor (_gdk_app_hmodule, name), FALSE);
return gdk_win32_hcursor_new (display, LoadCursor (hinstance, name), FALSE);
}
static HICON
@@ -1452,27 +1450,6 @@ pixbuf_to_hicon (GdkPixbuf *pixbuf,
return icon;
}
HICON
_gdk_win32_texture_to_hicon (GdkTexture *texture)
{
cairo_surface_t *surface;
GdkPixbuf *pixbuf;
int width, height;
HICON icon;
surface = gdk_texture_download_surface (texture);
width = cairo_image_surface_get_width (surface);
height = cairo_image_surface_get_height (surface);
pixbuf = gdk_pixbuf_get_from_surface (surface, 0, 0, width, height);
icon = pixbuf_to_hicon (pixbuf, TRUE, 0, 0);
g_object_unref (pixbuf);
return icon;
}
/**
* gdk_win32_display_get_win32hcursor:
* @display: (type GdkWin32Display): a `GdkDisplay`
+4 -3
View File
@@ -292,6 +292,7 @@ _gdk_win32_display_init_monitors (GdkWin32Display *win32_display)
if (!w32_ex_monitor->remove)
continue;
w32_ex_monitor->hmonitor = NULL;
g_list_store_remove (G_LIST_STORE (win32_display->monitors), i);
gdk_monitor_invalidate (ex_monitor);
}
@@ -480,7 +481,7 @@ register_display_change_notification (GdkDisplay *display)
wclass.lpszClassName = "GdkDisplayChange";
wclass.lpfnWndProc = display_change_window_procedure;
wclass.hInstance = _gdk_app_hmodule;
wclass.hInstance = this_module ();
wclass.style = CS_OWNDC;
klass = RegisterClass (&wclass);
@@ -489,10 +490,10 @@ register_display_change_notification (GdkDisplay *display)
display_win32->hwnd = CreateWindow (MAKEINTRESOURCE (klass),
NULL, WS_POPUP,
0, 0, 0, 0, NULL, NULL,
_gdk_app_hmodule, NULL);
this_module (), NULL);
if (!display_win32->hwnd)
{
UnregisterClass (MAKEINTRESOURCE (klass), _gdk_app_hmodule);
UnregisterClass (MAKEINTRESOURCE (klass), this_module ());
}
}
}
+1 -2
View File
@@ -413,8 +413,7 @@ set_up_low_level_keyboard_hook (void)
hook_handle = SetWindowsHookEx (WH_KEYBOARD_LL,
(HOOKPROC) low_level_keyboard_proc,
_gdk_dll_hinstance,
0);
this_module (), 0);
if (hook_handle != NULL)
keyboard_hook = hook_handle;
+3 -3
View File
@@ -261,7 +261,7 @@ create_dummy_gl_window (void)
wclass.lpszClassName = "GdkGLDummyWindow";
wclass.lpfnWndProc = DefWindowProc;
wclass.hInstance = _gdk_app_hmodule;
wclass.hInstance = this_module ();
wclass.style = CS_OWNDC;
klass = RegisterClass (&wclass);
@@ -270,10 +270,10 @@ create_dummy_gl_window (void)
hwnd = CreateWindow (MAKEINTRESOURCE (klass),
NULL, WS_POPUP,
0, 0, 0, 0, NULL, NULL,
_gdk_app_hmodule, NULL);
this_module (), NULL);
if (!hwnd)
{
UnregisterClass (MAKEINTRESOURCE (klass), _gdk_app_hmodule);
UnregisterClass (MAKEINTRESOURCE (klass), this_module ());
}
}
-4
View File
@@ -30,10 +30,6 @@
GdkDisplay *_gdk_display = NULL;
GdkDeviceManagerWin32 *_gdk_device_manager = NULL;
HDC _gdk_display_hdc;
HINSTANCE _gdk_dll_hinstance;
HINSTANCE _gdk_app_hmodule;
int _gdk_input_ignore_core;
HKL _gdk_input_locale;
+2 -2
View File
@@ -1003,7 +1003,7 @@ winpointer_notif_window_create (void)
wndclassex.cbSize = sizeof (wndclassex);
wndclassex.lpszClassName = L"GdkWin32WinpointerNotificationsWindowClass";
wndclassex.lpfnWndProc = winpointer_notifications_window_procedure;
wndclassex.hInstance = _gdk_dll_hinstance;
wndclassex.hInstance = this_module ();
if ((notifications_window_class = RegisterClassExW (&wndclassex)) == 0)
{
@@ -1018,7 +1018,7 @@ winpointer_notif_window_create (void)
0, 0, 0, 0,
HWND_MESSAGE,
NULL,
_gdk_dll_hinstance,
this_module (),
NULL)))
{
WIN32_API_FAILED ("CreateWindowExW");
-13
View File
@@ -576,19 +576,6 @@ gdk_mod_mask_to_mod_bits (GdkModifierType mod_mask)
return result;
}
/* keypad decimal mark depends on active keyboard layout
* return current decimal mark as unicode character
*/
guint32
_gdk_win32_keymap_get_decimal_mark (GdkWin32Keymap *keymap)
{
guint32 c = MapVirtualKeyW (VK_DECIMAL, MAPVK_VK_TO_CHAR);
if (!c)
c = (guint32) '.';
return c;
}
static void
update_keymap (GdkWin32Keymap *keymap)
{
+56 -190
View File
@@ -45,9 +45,6 @@
#include <wintab.h>
#include <imm.h>
/* for CFSTR_SHELLIDLIST */
#include <shlobj.h>
static gboolean gdk_synchronize = FALSE;
/* Whether GDK initialized COM */
@@ -66,8 +63,6 @@ _gdk_win32_surfaceing_init (void)
if (gdk_synchronize)
GdiSetBatchLimit (1);
_gdk_app_hmodule = GetModuleHandle (NULL);
_gdk_display_hdc = CreateDC ("DISPLAY", NULL, NULL, NULL);
_gdk_input_locale = GetKeyboardLayout (0);
_gdk_win32_keymap_set_active_layout (win32_keymap, _gdk_input_locale);
@@ -187,135 +182,6 @@ static_printf (const char *format,
return retval;
}
void
_gdk_win32_print_paletteentries (const PALETTEENTRY *pep,
const int nentries)
{
char buf[20];
int i;
for (i = 0; i < nentries; i++)
g_print (" %3d %02x: %02x %02x %02x%s\n",
i, i,
pep[i].peRed, pep[i].peGreen, pep[i].peBlue,
(pep[i].peFlags == 0 ? "" :
(pep[i].peFlags == PC_EXPLICIT ? " PC_EXPLICIT" :
(pep[i].peFlags == PC_NOCOLLAPSE ? " PC_NOCOLLAPSE" :
(pep[i].peFlags == PC_RESERVED ? " PC_RESERVED" :
(g_sprintf (buf, " %d", pep[i].peFlags), buf))))));
}
void
_gdk_win32_print_system_palette (void)
{
PALETTEENTRY *pe;
int k;
k = GetSystemPaletteEntries (_gdk_display_hdc, 0, 0, NULL);
pe = g_new (PALETTEENTRY, k);
k = GetSystemPaletteEntries (_gdk_display_hdc, 0, k, pe);
if (!k)
g_print ("GetSystemPaletteEntries failed: %s\n",
g_win32_error_message (GetLastError ()));
else
{
g_print ("System palette: %d entries\n", k);
_gdk_win32_print_paletteentries (pe, k);
}
g_free (pe);
}
static int
palette_size (HPALETTE hpal)
{
WORD npal = 0;
if (!GetObject (hpal, sizeof (npal), &npal))
WIN32_GDI_FAILED ("GetObject (HPALETTE)");
return npal;
}
void
_gdk_win32_print_hpalette (HPALETTE hpal)
{
PALETTEENTRY *pe;
int n, npal;
npal = palette_size (hpal);
pe = g_new (PALETTEENTRY, npal);
n = GetPaletteEntries (hpal, 0, npal, pe);
if (!n)
g_print ("HPALETTE %p: GetPaletteEntries failed: %s\n",
hpal, g_win32_error_message (GetLastError ()));
else
{
g_print ("HPALETTE %p: %d (%d) entries\n", hpal, n, npal);
_gdk_win32_print_paletteentries (pe, n);
}
g_free (pe);
}
void
_gdk_win32_print_dc (HDC hdc)
{
HGDIOBJ obj;
LOGBRUSH logbrush;
EXTLOGPEN extlogpen;
HRGN hrgn;
RECT rect;
int flag;
g_print ("%p:\n", hdc);
obj = GetCurrentObject (hdc, OBJ_BRUSH);
GetObject (obj, sizeof (LOGBRUSH), &logbrush);
g_print ("brush: %s color=%06lx hatch=%p\n",
_gdk_win32_lbstyle_to_string (logbrush.lbStyle),
logbrush.lbColor, (gpointer) logbrush.lbHatch);
obj = GetCurrentObject (hdc, OBJ_PEN);
GetObject (obj, sizeof (EXTLOGPEN), &extlogpen);
g_print ("pen: %s %s %s %s w=%d %s\n",
_gdk_win32_pstype_to_string (extlogpen.elpPenStyle),
_gdk_win32_psstyle_to_string (extlogpen.elpPenStyle),
_gdk_win32_psendcap_to_string (extlogpen.elpPenStyle),
_gdk_win32_psjoin_to_string (extlogpen.elpPenStyle),
(int) extlogpen.elpWidth,
_gdk_win32_lbstyle_to_string (extlogpen.elpBrushStyle));
g_print ("rop2: %s textcolor=%06lx\n",
_gdk_win32_rop2_to_string (GetROP2 (hdc)),
GetTextColor (hdc));
hrgn = CreateRectRgn (0, 0, 0, 0);
if ((flag = GetClipRgn (hdc, hrgn)) == -1)
WIN32_API_FAILED ("GetClipRgn");
else if (flag == 0)
g_print ("no clip region\n");
else if (flag == 1)
{
GetRgnBox (hrgn, &rect);
g_print ("clip region: %p bbox: %s\n",
hrgn, _gdk_win32_rect_to_string (&rect));
}
DeleteObject (hrgn);
}
char *
_gdk_win32_drag_protocol_to_string (GdkDragProtocol protocol)
{
switch (protocol)
{
#define CASE(x) case GDK_DRAG_PROTO_##x: return #x
CASE (NONE);
CASE (WIN32_DROPFILES);
CASE (OLE2);
#undef CASE
default: return static_printf ("illegal_%d", protocol);
}
/* NOTREACHED */
return NULL;
}
char *
_gdk_win32_surface_state_to_string (GdkToplevelState state)
{
@@ -478,7 +344,7 @@ _gdk_win32_drag_action_to_string (GdkDragAction actions)
return static_printf ("%s", buf);
}
char *
static char *
_gdk_win32_rop2_to_string (int rop2)
{
switch (rop2)
@@ -507,7 +373,7 @@ _gdk_win32_rop2_to_string (int rop2)
return NULL;
}
char *
static char *
_gdk_win32_lbstyle_to_string (UINT brush_style)
{
switch (brush_style)
@@ -526,7 +392,7 @@ _gdk_win32_lbstyle_to_string (UINT brush_style)
return NULL;
}
char *
static char *
_gdk_win32_pstype_to_string (DWORD pen_style)
{
switch (pen_style & PS_TYPE_MASK)
@@ -539,7 +405,7 @@ _gdk_win32_pstype_to_string (DWORD pen_style)
return NULL;
}
char *
static char *
_gdk_win32_psstyle_to_string (DWORD pen_style)
{
switch (pen_style & PS_STYLE_MASK)
@@ -561,7 +427,7 @@ _gdk_win32_psstyle_to_string (DWORD pen_style)
return NULL;
}
char *
static char *
_gdk_win32_psendcap_to_string (DWORD pen_style)
{
switch (pen_style & PS_ENDCAP_MASK)
@@ -577,7 +443,7 @@ _gdk_win32_psendcap_to_string (DWORD pen_style)
return NULL;
}
char *
static char *
_gdk_win32_psjoin_to_string (DWORD pen_style)
{
switch (pen_style & PS_JOIN_MASK)
@@ -593,6 +459,56 @@ _gdk_win32_psjoin_to_string (DWORD pen_style)
return NULL;
}
void
_gdk_win32_print_dc (HDC hdc)
{
HGDIOBJ obj;
LOGBRUSH logbrush;
EXTLOGPEN extlogpen;
HRGN hrgn;
RECT rect;
int flag;
g_print ("%p:\n", hdc);
obj = GetCurrentObject (hdc, OBJ_BRUSH);
GetObject (obj, sizeof (LOGBRUSH), &logbrush);
g_print ("brush: %s color=%06lx hatch=%p\n",
_gdk_win32_lbstyle_to_string (logbrush.lbStyle),
logbrush.lbColor, (gpointer) logbrush.lbHatch);
obj = GetCurrentObject (hdc, OBJ_PEN);
GetObject (obj, sizeof (EXTLOGPEN), &extlogpen);
g_print ("pen: %s %s %s %s w=%d %s\n",
_gdk_win32_pstype_to_string (extlogpen.elpPenStyle),
_gdk_win32_psstyle_to_string (extlogpen.elpPenStyle),
_gdk_win32_psendcap_to_string (extlogpen.elpPenStyle),
_gdk_win32_psjoin_to_string (extlogpen.elpPenStyle),
(int) extlogpen.elpWidth,
_gdk_win32_lbstyle_to_string (extlogpen.elpBrushStyle));
g_print ("rop2: %s textcolor=%06lx\n",
_gdk_win32_rop2_to_string (GetROP2 (hdc)),
GetTextColor (hdc));
hrgn = CreateRectRgn (0, 0, 0, 0);
if ((flag = GetClipRgn (hdc, hrgn)) == -1)
WIN32_API_FAILED ("GetClipRgn");
else if (flag == 0)
g_print ("no clip region\n");
else if (flag == 1)
{
GetRgnBox (hrgn, &rect);
g_print ("clip region: %p bbox: %s\n",
hrgn, _gdk_win32_rect_to_string (&rect));
}
DeleteObject (hrgn);
}
char *
_gdk_win32_message_to_string (UINT msg)
{
@@ -893,26 +809,6 @@ _gdk_win32_cf_to_string (UINT format)
}
}
char *
_gdk_win32_data_to_string (const guchar *data,
int nbytes)
{
GString *s = g_string_new ("");
int i;
char *retval;
for (i = 0; i < nbytes; i++)
if (data[i] >=' ' && data[i] <= '~')
g_string_append_printf (s, "%c ", data[i]);
else
g_string_append_printf (s, "%02X ", data[i]);
retval = static_printf ("%s", s->str);
g_string_free (s, TRUE);
return retval;
}
char *
_gdk_win32_rect_to_string (const RECT *rect)
{
@@ -921,34 +817,4 @@ _gdk_win32_rect_to_string (const RECT *rect)
rect->left, rect->top);
}
char *
_gdk_win32_gdkrectangle_to_string (const GdkRectangle *rect)
{
return static_printf ("%dx%d@%+d%+d",
rect->width, rect->height,
rect->x, rect->y);
}
char *
_gdk_win32_cairo_region_to_string (const cairo_region_t *rgn)
{
cairo_rectangle_int_t extents;
cairo_region_get_extents (rgn, &extents);
return static_printf ("%dx%d@%+d%+d",
extents.width, extents.height,
extents.x, extents.y);
}
char *
_gdk_win32_surface_description (GdkSurface *d)
{
g_return_val_if_fail (GDK_IS_SURFACE (d), NULL);
return static_printf ("%s:%p:%dx%d",
G_OBJECT_TYPE_NAME (d),
GDK_SURFACE_HWND (d),
gdk_surface_get_width (GDK_SURFACE (d)),
gdk_surface_get_height (GDK_SURFACE (d)));
}
#endif /* G_ENABLE_DEBUG */
+8 -3
View File
@@ -443,9 +443,6 @@ populate_monitor_devices_from_display_config (GPtrArray *monitors)
char *path, *path_lower;
DISPLAYCONFIG_RATIONAL *refresh;
if ((dispconf_paths[path_index].flags & DISPLAYCONFIG_PATH_ACTIVE) == 0)
continue;
tdn.header.type = DISPLAYCONFIG_DEVICE_INFO_GET_TARGET_NAME;
tdn.header.size = sizeof (tdn);
tdn.header.adapterId = dispconf_paths[path_index].targetInfo.adapterId;
@@ -481,6 +478,12 @@ populate_monitor_devices_from_display_config (GPtrArray *monitors)
if (w32mon == NULL)
continue;
if ((dispconf_paths[path_index].flags & DISPLAYCONFIG_PATH_ACTIVE) == 0)
{
w32mon->remove = TRUE;
continue;
}
mon = GDK_MONITOR (w32mon);
if (!tdn.flags.friendlyNameForced)
@@ -598,6 +601,8 @@ enum_monitor (HMONITOR hmonitor,
if (w32mon == NULL)
continue;
w32mon->hmonitor = hmonitor;
}
else
{
+3
View File
@@ -35,6 +35,9 @@ struct _GdkWin32Monitor
/* Device instance path (used to match GdkWin32Monitor to monitor device) */
char *instance_path;
/* MOnitor handle (used to fullscreen windows on monitors) */
HMONITOR hmonitor;
/* TRUE if monitor is made up by us
* (this happens when system has logical monitors, but no physical ones).
*/
+10 -157
View File
@@ -15,15 +15,10 @@
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
/*
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
* file for a list of people on the GTK+ Team. See the ChangeLog
* files for a list of changes. These files are distributed with
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
*/
#pragma once
#include "config.h"
#include <gdk/gdkcursorprivate.h>
#include <gdk/gdkdebugprivate.h>
#include <gdk/win32/gdksurface-win32.h>
@@ -32,10 +27,6 @@
#include <gdk/win32/gdkwin32keys.h>
#include <gdk/win32/gdkdevicemanager-win32.h>
#include <gdk/win32/gdkclipdrop-win32.h>
//#include <gdk/win32/gdkselection-win32.h>
#include "config.h"
/* Old debug macros */
@@ -54,62 +45,6 @@
#endif
/* Make up for some minor w32api or MSVC6 header lossage */
#ifndef PS_JOIN_MASK
#define PS_JOIN_MASK (PS_JOIN_BEVEL|PS_JOIN_MITER|PS_JOIN_ROUND)
#endif
#ifndef FS_VIETNAMESE
#define FS_VIETNAMESE 0x100
#endif
#ifndef WM_GETOBJECT
#define WM_GETOBJECT 0x3D
#endif
#ifndef WM_NCXBUTTONDOWN
#define WM_NCXBUTTONDOWN 0xAB
#endif
#ifndef WM_NCXBUTTONUP
#define WM_NCXBUTTONUP 0xAC
#endif
#ifndef WM_NCXBUTTONDBLCLK
#define WM_NCXBUTTONDBLCLK 0xAD
#endif
#ifndef WM_CHANGEUISTATE
#define WM_CHANGEUISTATE 0x127
#endif
#ifndef WM_UPDATEUISTATE
#define WM_UPDATEUISTATE 0x128
#endif
#ifndef WM_QUERYUISTATE
#define WM_QUERYUISTATE 0x129
#endif
#ifndef WM_XBUTTONDOWN
#define WM_XBUTTONDOWN 0x20B
#endif
#ifndef WM_XBUTTONUP
#define WM_XBUTTONUP 0x20C
#endif
#ifndef WM_XBUTTONDBLCLK
#define WM_XBUTTONDBLCLK 0x20D
#endif
#ifndef WM_NCMOUSEHOVER
#define WM_NCMOUSEHOVER 0x2A0
#endif
#ifndef WM_NCMOUSELEAVE
#define WM_NCMOUSELEAVE 0x2A2
#endif
#ifndef WM_APPCOMMAND
#define WM_APPCOMMAND 0x319
#endif
#ifndef WM_MOUSEHWHEEL
#define WM_MOUSEHWHEEL 0x20E
#endif
#ifndef WM_DPICHANGED
#define WM_DPICHANGED 0x02E0
#endif
/* According to
* http://blog.airesoft.co.uk/2009/11/wm_messages/
* this is the actual internal name MS uses for this undocumented message.
@@ -122,11 +57,6 @@
#define WM_SYSMENU 0x313
#endif
#ifndef CF_DIBV5
#define CF_DIBV5 17
#endif
/* Define some combinations of GdkDebugFlags */
#define GDK_DEBUG_EVENTS_OR_INPUT (GDK_DEBUG_EVENTS|GDK_DEBUG_INPUT)
#define GDK_DEBUG_MISC_OR_EVENTS (GDK_DEBUG_MISC|GDK_DEBUG_EVENTS)
@@ -140,22 +70,6 @@ GdkWin32Screen *GDK_SURFACE_SCREEN(GObject *win);
*/
#define SWP_NOZORDER_SPECIFIED HWND_TOP
typedef struct _GdkWin32SingleFont GdkWin32SingleFont;
struct _GdkWin32SingleFont
{
HFONT hfont;
UINT charset;
UINT codepage;
FONTSIGNATURE fs;
};
typedef enum {
GDK_WIN32_PE_STATIC,
GDK_WIN32_PE_AVAILABLE,
GDK_WIN32_PE_INUSE
} GdkWin32PalEntryState;
typedef enum
{
GDK_DRAG_PROTO_NONE = 0,
@@ -163,51 +77,23 @@ typedef enum
GDK_DRAG_PROTO_OLE2,
} GdkDragProtocol;
GType _gdk_gc_win32_get_type (void);
gulong _gdk_win32_get_next_tick (gulong suggested_tick);
BOOL _gdk_win32_get_cursor_pos (LPPOINT lpPoint);
void _gdk_surface_init_position (GdkSurface *window);
void _gdk_surface_move_resize_child (GdkSurface *window,
int x,
int y,
int width,
int height);
gboolean _gdk_win32_surface_enable_transparency (GdkSurface *window);
/* GdkSurfaceImpl methods */
void _gdk_win32_surface_scroll (GdkSurface *window,
int dx,
int dy);
void _gdk_win32_surface_move_region (GdkSurface *window,
const cairo_region_t *region,
int dx,
int dy);
void _gdk_win32_selection_init (void);
void _gdk_win32_dnd_exit (void);
void gdk_win32_handle_table_insert (HANDLE *handle,
gpointer data);
void gdk_win32_handle_table_remove (HANDLE handle);
HRGN _gdk_win32_cairo_region_to_hrgn (const cairo_region_t *region,
int x_origin,
int y_origin);
cairo_region_t *_gdk_win32_hrgn_to_region (HRGN hrgn,
guint scale);
void _gdk_win32_adjust_client_rect (GdkSurface *window,
RECT *RECT);
void _gdk_selection_property_delete (GdkSurface *);
void _gdk_push_modal_window (GdkSurface *window);
void _gdk_remove_modal_window (GdkSurface *window);
GdkSurface *_gdk_modal_current (void);
@@ -217,41 +103,22 @@ gboolean gdk_win32_ensure_com (void);
gboolean gdk_win32_ensure_ole (void);
#ifdef G_ENABLE_DEBUG
void _gdk_win32_print_paletteentries (const PALETTEENTRY *pep,
const int nentries);
void _gdk_win32_print_system_palette (void);
void _gdk_win32_print_hpalette (HPALETTE hpal);
void _gdk_win32_print_dc (HDC hdc);
char *_gdk_win32_drag_protocol_to_string (GdkDragProtocol protocol);
char *_gdk_win32_surface_state_to_string (GdkToplevelState state);
char *_gdk_win32_surface_style_to_string (LONG style);
char *_gdk_win32_surface_exstyle_to_string (LONG style);
char *_gdk_win32_surface_pos_bits_to_string (UINT flags);
char *_gdk_win32_drag_action_to_string (GdkDragAction actions);
char *_gdk_win32_surface_description (GdkSurface *d);
char *_gdk_win32_rop2_to_string (int rop2);
char *_gdk_win32_lbstyle_to_string (UINT brush_style);
char *_gdk_win32_pstype_to_string (DWORD pen_style);
char *_gdk_win32_psstyle_to_string (DWORD pen_style);
char *_gdk_win32_psendcap_to_string (DWORD pen_style);
char *_gdk_win32_psjoin_to_string (DWORD pen_style);
char *_gdk_win32_message_to_string (UINT msg);
char *_gdk_win32_key_to_string (LONG lParam);
char *_gdk_win32_cf_to_string (UINT format);
char *_gdk_win32_data_to_string (const guchar*data,
int nbytes);
char *_gdk_win32_rect_to_string (const RECT *rect);
char *_gdk_win32_gdkrectangle_to_string (const GdkRectangle *rect);
char *_gdk_win32_cairo_region_to_string (const cairo_region_t *box);
void _gdk_win32_print_event (GdkEvent *event);
#endif
char *_gdk_win32_last_error_string (void);
void _gdk_win32_api_failed (const char *where,
const char *api);
void _gdk_other_api_failed (const char *where,
@@ -284,10 +151,6 @@ extern GdkDisplay *_gdk_display;
extern GdkDeviceManagerWin32 *_gdk_device_manager;
extern HDC _gdk_display_hdc;
extern HINSTANCE _gdk_dll_hinstance;
extern HINSTANCE _gdk_app_hmodule;
extern int _gdk_input_ignore_core;
/* These are thread specific, but GDK/win32 works OK only when invoked
@@ -304,8 +167,6 @@ extern GdkWin32Clipdrop *_win32_clipdrop;
/* Used to identify the main thread */
extern GThread *_win32_main_thread;
void _gdk_win32_dnd_do_dragdrop (void);
typedef enum {
GDK_WIN32_MODAL_OP_NONE = 0x0,
GDK_WIN32_MODAL_OP_SIZE = 0x1 << 0,
@@ -324,16 +185,9 @@ extern HWND _modal_move_resize_window;
void _gdk_win32_begin_modal_call (GdkWin32ModalOpKind kind);
void _gdk_win32_end_modal_call (GdkWin32ModalOpKind kind);
/* Convert a pixbuf to an HICON (or HCURSOR). Supports alpha under
* Windows XP, thresholds alpha otherwise.
*/
HICON _gdk_win32_texture_to_hicon (GdkTexture *texture);
void _gdk_win32_display_init_cursors (GdkWin32Display *display);
void _gdk_win32_display_finalize_cursors (GdkWin32Display *display);
void _gdk_win32_display_update_cursors (GdkWin32Display *display);
GdkCursor *_gdk_win32_display_get_cursor_for_name (GdkDisplay *display, const char * cursor_name);
GdkCursor *gdk_win32_display_cursor_from_hcursor (GdkDisplay *display, HCURSOR hcursor);
typedef struct _Win32CursorTheme Win32CursorTheme;
@@ -367,9 +221,6 @@ Win32Cursor * win32_cursor_theme_get_cursor (Win32CursorTheme *theme,
void win32_cursor_theme_destroy (Win32CursorTheme *theme);
Win32CursorTheme *_gdk_win32_display_get_cursor_theme (GdkWin32Display *win32_display);
/* GdkDisplay member functions */
GList *_gdk_win32_display_list_devices (GdkDisplay *dpy);
gboolean _gdk_win32_display_has_pending (GdkDisplay *display);
void _gdk_win32_display_queue_events (GdkDisplay *display);
@@ -395,16 +246,11 @@ GdkDrag *_gdk_win32_surface_drag_begin (GdkSurface *window,
/* Stray GdkWin32Screen members */
gboolean _gdk_win32_get_setting (const char *name, GValue *value);
void _gdk_win32_screen_on_displaychange_event (GdkWin32Screen *screen);
GdkSurface *gdk_win32_screen_get_root_window (GdkWin32Screen *screen);
GdkSurface *gdk_win32_display_get_root_window (GdkDisplay *display);
/* Distributed display manager implementation */
GdkDisplay *_gdk_win32_display_open (const char *display_name);
void _gdk_win32_append_event (GdkEvent *event);
guint32 _gdk_win32_keymap_get_decimal_mark (GdkWin32Keymap *keymap);
void _gdk_win32_surface_handle_aerosnap (GdkSurface *window,
GdkWin32AeroSnapCombo combo);
@@ -449,8 +295,15 @@ gboolean _gdk_win32_check_processor (GdkWin32ProcessorCheckType check_type);
GdkPixbuf *gdk_win32_icon_to_pixbuf_libgtk_only (HICON hicon,
double *x_hot,
double *y_hot);
HICON gdk_win32_pixbuf_to_hicon_libgtk_only (GdkPixbuf *pixbuf);
void gdk_win32_set_modal_dialog_libgtk_only (HWND window);
gpointer gdk_win32_handle_table_lookup_ (HWND handle);
extern IMAGE_DOS_HEADER __ImageBase;
static inline HMODULE
this_module (void)
{
return (HMODULE) &__ImageBase;
}
+9 -1
View File
@@ -113,7 +113,15 @@ _gdk_win32_get_setting (const char *name,
}
else if (strcmp ("gtk-font-name", name) == 0)
{
char *font_name = _get_system_font_name (_gdk_display_hdc);
char *font_name = NULL;
HDC hdc = NULL;
if ((hdc = GetDC (HWND_DESKTOP)) != NULL)
{
font_name = _get_system_font_name (hdc);
ReleaseDC (HWND_DESKTOP, hdc);
hdc = NULL;
}
if (font_name)
{
+28 -17
View File
@@ -50,6 +50,7 @@
#include "gdkdisplay-win32.h"
#include "gdkdevice-win32.h"
#include "gdkcairocontext-win32.h"
#include "gdkmonitor-win32.h"
#include <cairo-win32.h>
#include <dwmapi.h>
@@ -338,7 +339,7 @@ RegisterGdkClass (GType wtype)
wcl.lpfnWndProc = _gdk_win32_surface_procedure;
wcl.cbClsExtra = 0;
wcl.cbWndExtra = 0;
wcl.hInstance = _gdk_dll_hinstance;
wcl.hInstance = this_module ();
wcl.hIcon = 0;
wcl.hIconSm = 0;
@@ -355,7 +356,7 @@ RegisterGdkClass (GType wtype)
if (0 == hAppIcon && 0 == hAppIconSm)
{
// fallback : load icon from GTK DLL
if (0 != GetModuleFileName (_gdk_dll_hinstance, sLoc, MAX_PATH))
if (0 != GetModuleFileName (this_module (), sLoc, MAX_PATH))
{
ExtractIconEx (sLoc, 0, &hAppIcon, &hAppIconSm, 1);
}
@@ -492,7 +493,7 @@ gdk_win32_surface_constructed (GObject *object)
CW_USEDEFAULT, CW_USEDEFAULT,
owner,
NULL,
_gdk_dll_hinstance,
this_module (),
surface);
if (impl->handle == NULL)
{
@@ -625,7 +626,8 @@ get_outer_rect (GdkSurface *window,
}
static void
gdk_win32_surface_fullscreen (GdkSurface *window);
gdk_win32_surface_fullscreen (GdkSurface *window,
GdkMonitor *monitor);
static void
show_window_internal (GdkSurface *window,
@@ -789,11 +791,7 @@ show_window_internal (GdkSurface *window,
}
if (window->state & GDK_TOPLEVEL_STATE_FULLSCREEN)
{
gdk_win32_surface_fullscreen (window);
}
else if (window->state & GDK_TOPLEVEL_STATE_MAXIMIZED)
if (window->state & GDK_TOPLEVEL_STATE_MAXIMIZED)
{
GtkShowWindow (window, SW_MAXIMIZE);
}
@@ -2406,7 +2404,7 @@ RegisterGdkDumbClass ()
wcl.lpfnWndProc = DefWindowProcW;
wcl.cbClsExtra = 0;
wcl.cbWndExtra = 0;
wcl.hInstance = _gdk_dll_hinstance;
wcl.hInstance = this_module ();
wcl.hIcon = 0;
wcl.hIconSm = 0;
wcl.lpszMenuName = NULL;
@@ -2447,7 +2445,7 @@ ensure_snap_indicator_exists (GdkW32DragMoveResizeContext *context)
0, 0,
NULL,
NULL,
_gdk_dll_hinstance,
this_module (),
NULL);
context->shape_indicator = handle;
@@ -4008,11 +4006,12 @@ gdk_win32_surface_unmaximize (GdkSurface *surface)
}
static void
gdk_win32_surface_fullscreen (GdkSurface *window)
gdk_win32_surface_fullscreen (GdkSurface *window,
GdkMonitor *monitor)
{
int x, y, width, height;
FullscreenInfo *fi;
HMONITOR monitor;
HMONITOR hmonitor = NULL;
MONITORINFO mi;
g_return_if_fail (GDK_IS_SURFACE (window));
@@ -4025,9 +4024,14 @@ gdk_win32_surface_fullscreen (GdkSurface *window)
{
GdkWin32Surface *impl = GDK_WIN32_SURFACE (window);
monitor = MonitorFromWindow (GDK_SURFACE_HWND (window), MONITOR_DEFAULTTONEAREST);
if (monitor && GDK_IS_WIN32_MONITOR (monitor))
hmonitor = GDK_WIN32_MONITOR (monitor)->hmonitor;
if (!hmonitor)
hmonitor = MonitorFromWindow (GDK_SURFACE_HWND (window), MONITOR_DEFAULTTONEAREST);
mi.cbSize = sizeof (mi);
if (monitor && GetMonitorInfo (monitor, &mi))
if (hmonitor && GetMonitorInfo (hmonitor, &mi))
{
x = mi.rcMonitor.left;
y = mi.rcMonitor.top;
@@ -4869,9 +4873,16 @@ gdk_win32_toplevel_present (GdkToplevel *toplevel,
if (gdk_toplevel_layout_get_fullscreen (layout, &fullscreen))
{
if (fullscreen)
gdk_win32_surface_fullscreen (surface);
{
GdkMonitor *monitor;
monitor = gdk_toplevel_layout_get_fullscreen_monitor (layout);
gdk_win32_surface_fullscreen (surface, monitor);
}
else
gdk_win32_surface_unfullscreen (surface);
{
gdk_win32_surface_unfullscreen (surface);
}
}
gdk_win32_surface_show (surface, FALSE);
+1 -3
View File
@@ -30,8 +30,6 @@
#include "gdkprivate-win32.h"
#include "gdkwin32misc.h"
extern HINSTANCE _gdk_dll_hinstance;
G_DEFINE_TYPE (GdkWin32VulkanContext, gdk_win32_vulkan_context, GDK_TYPE_VULKAN_CONTEXT)
static VkResult
@@ -47,7 +45,7 @@ gdk_win32_vulkan_context_create_surface (GdkVulkanContext *context,
info.sType = VK_STRUCTURE_TYPE_WIN32_SURFACE_CREATE_INFO_KHR;
info.pNext = NULL;
info.flags = 0;
info.hinstance = _gdk_dll_hinstance;
info.hinstance = this_module ();
info.hwnd = GDK_SURFACE_HWND (window);
/* This is necessary so that Vulkan sees the Window.
+2 -1
View File
@@ -144,7 +144,8 @@ struct _GdkX11Display
guint server_time_is_monotonic_time : 1;
/* GLX extensions we check */
guint has_glx_swap_interval : 1;
guint has_glx_sgi_swap_control : 1;
guint has_glx_swap_control : 1;
guint has_glx_create_context : 1;
guint has_glx_texture_from_pixmap : 1;
guint has_glx_video_sync : 1;
+1 -204
View File
@@ -134,35 +134,6 @@ struct _GdkX11DragClass
GdkDragClass parent_class;
};
typedef struct {
int keysym;
int modifiers;
} GrabKey;
static GrabKey grab_keys[] = {
{ XK_Escape, 0 },
{ XK_space, 0 },
{ XK_KP_Space, 0 },
{ XK_Return, 0 },
{ XK_KP_Enter, 0 },
{ XK_Up, 0 },
{ XK_Up, Mod1Mask },
{ XK_Down, 0 },
{ XK_Down, Mod1Mask },
{ XK_Left, 0 },
{ XK_Left, Mod1Mask },
{ XK_Right, 0 },
{ XK_Right, Mod1Mask },
{ XK_KP_Up, 0 },
{ XK_KP_Up, Mod1Mask },
{ XK_KP_Down, 0 },
{ XK_KP_Down, Mod1Mask },
{ XK_KP_Left, 0 },
{ XK_KP_Left, Mod1Mask },
{ XK_KP_Right, 0 },
{ XK_KP_Right, Mod1Mask }
};
/* Forward declarations */
static GdkSurfaceCache *gdk_surface_cache_ref (GdkSurfaceCache *cache);
@@ -1861,20 +1832,15 @@ drag_grab (GdkDrag *drag)
{
GdkX11Drag *x11_drag = GDK_X11_DRAG (drag);
GdkSeatCapabilities capabilities;
GdkDisplay *display;
Window root;
GdkSeat *seat;
int keycode, i;
GdkCursor *cursor;
if (!x11_drag->ipc_surface)
return FALSE;
display = gdk_drag_get_display (drag);
root = GDK_DISPLAY_XROOTWIN (display);
seat = gdk_device_get_seat (gdk_drag_get_device (drag));
capabilities = GDK_SEAT_CAPABILITY_ALL_POINTING | GDK_SEAT_CAPABILITY_KEYBOARD;
capabilities = GDK_SEAT_CAPABILITY_ALL_POINTING;
cursor = gdk_drag_get_cursor (drag, x11_drag->current_action);
g_set_object (&x11_drag->cursor, cursor);
@@ -1886,46 +1852,6 @@ drag_grab (GdkDrag *drag)
g_set_object (&x11_drag->grab_seat, seat);
gdk_x11_display_error_trap_push (display);
for (i = 0; i < G_N_ELEMENTS (grab_keys); ++i)
{
int deviceid = gdk_x11_device_get_id (gdk_seat_get_keyboard (seat));
unsigned char mask[XIMaskLen(XI_LASTEVENT)];
XIGrabModifiers mods;
XIEventMask evmask;
int num_mods;
keycode = XKeysymToKeycode (GDK_DISPLAY_XDISPLAY (display),
grab_keys[i].keysym);
if (keycode == NoSymbol)
continue;
memset (mask, 0, sizeof (mask));
XISetMask (mask, XI_KeyPress);
XISetMask (mask, XI_KeyRelease);
evmask.deviceid = deviceid;
evmask.mask_len = sizeof (mask);
evmask.mask = mask;
num_mods = 1;
mods.modifiers = grab_keys[i].modifiers;
XIGrabKeycode (GDK_DISPLAY_XDISPLAY (display),
deviceid,
keycode,
root,
GrabModeAsync,
GrabModeAsync,
False,
&evmask,
num_mods,
&mods);
}
gdk_x11_display_error_trap_pop_ignored (display);
return TRUE;
}
@@ -1933,41 +1859,13 @@ static void
drag_ungrab (GdkDrag *drag)
{
GdkX11Drag *x11_drag = GDK_X11_DRAG (drag);
GdkDisplay *display;
GdkDevice *keyboard;
Window root;
int keycode, i;
if (!x11_drag->grab_seat)
return;
gdk_seat_ungrab (x11_drag->grab_seat);
display = gdk_drag_get_display (drag);
keyboard = gdk_seat_get_keyboard (x11_drag->grab_seat);
root = GDK_DISPLAY_XROOTWIN (display);
g_clear_object (&x11_drag->grab_seat);
for (i = 0; i < G_N_ELEMENTS (grab_keys); ++i)
{
XIGrabModifiers mods;
int num_mods;
keycode = XKeysymToKeycode (GDK_DISPLAY_XDISPLAY (display),
grab_keys[i].keysym);
if (keycode == NoSymbol)
continue;
num_mods = 1;
mods.modifiers = grab_keys[i].modifiers;
XIUngrabKeycode (GDK_DISPLAY_XDISPLAY (display),
gdk_x11_device_get_id (keyboard),
keycode,
root,
num_mods,
&mods);
}
}
GdkDrag *
@@ -2191,103 +2089,6 @@ gdk_dnd_handle_motion_event (GdkDrag *drag,
return TRUE;
}
static gboolean
gdk_dnd_handle_key_event (GdkDrag *drag,
GdkEvent *event)
{
GdkX11Drag *x11_drag = GDK_X11_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) &&
(x11_drag->proxy_xid != None))
{
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_x11_device_xi2_query_state (pointer, NULL, NULL, NULL, &state);
if (dx != 0 || dy != 0)
{
GdkDisplay *display;
Display *xdisplay;
GdkX11Screen *screen;
Window dest;
x11_drag->last_x += dx;
x11_drag->last_y += dy;
display = gdk_event_get_display ((GdkEvent *)event);
xdisplay = GDK_DISPLAY_XDISPLAY (display);
screen = GDK_X11_DISPLAY (display)->screen;
dest = GDK_SCREEN_XROOTWIN (screen);
XWarpPointer (xdisplay, None, dest, 0, 0, 0, 0,
round (x11_drag->last_x * screen->surface_scale),
round (x11_drag->last_y * screen->surface_scale));
}
gdk_drag_update (drag, x11_drag->last_x, x11_drag->last_y, state,
gdk_event_get_time (event));
return TRUE;
}
static gboolean
gdk_dnd_handle_grab_broken_event (GdkDrag *drag,
GdkEvent *event)
@@ -2354,10 +2155,6 @@ gdk_x11_drag_handle_event (GdkDrag *drag,
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);
+57 -44
View File
@@ -162,7 +162,7 @@ gdk_x11_gl_context_glx_end_frame (GdkDrawContext *draw_context,
if (display_x11->has_glx_video_sync)
glXGetVideoSyncSGI (&end_frame_counter);
if (self->do_frame_sync && !display_x11->has_glx_swap_interval)
if (self->do_frame_sync && !display_x11->has_glx_sgi_swap_control && !display_x11->has_glx_swap_control)
{
glFinish ();
@@ -249,7 +249,7 @@ gdk_x11_gl_context_glx_make_current (GdkGLContext *context,
if (!glXMakeContextCurrent (dpy, drawable, drawable, self->glx_context))
return FALSE;
if (!surfaceless && GDK_X11_DISPLAY (display)->has_glx_swap_interval)
if (!surfaceless)
{
/* If the WM is compositing there is no particular need to delay
* the swap when drawing on the offscreen, rendering to the screen
@@ -257,14 +257,35 @@ gdk_x11_gl_context_glx_make_current (GdkGLContext *context,
* to the vblank. */
do_frame_sync = ! gdk_display_is_composited (display);
if (do_frame_sync != self->do_frame_sync)
if (GDK_X11_DISPLAY (display)->has_glx_swap_control)
{
self->do_frame_sync = do_frame_sync;
if (do_frame_sync != self->do_frame_sync)
{
self->do_frame_sync = do_frame_sync;
if (do_frame_sync)
glXSwapIntervalSGI (1);
else
glXSwapIntervalSGI (0);
if (do_frame_sync)
glXSwapIntervalEXT (dpy, drawable, 1);
else
glXSwapIntervalEXT (dpy, drawable, 0);
}
}
else if (GDK_X11_DISPLAY (display)->has_glx_sgi_swap_control)
{
/* If the WM is compositing there is no particular need to delay
* the swap when drawing on the offscreen, rendering to the screen
* happens later anyway, and its up to the compositor to sync that
* to the vblank. */
do_frame_sync = ! gdk_display_is_composited (display);
if (do_frame_sync != self->do_frame_sync)
{
self->do_frame_sync = do_frame_sync;
if (do_frame_sync)
glXSwapIntervalSGI (1);
else
glXSwapIntervalSGI (0);
}
}
}
@@ -287,29 +308,20 @@ gdk_x11_gl_context_glx_get_damage (GdkGLContext *context)
glXQueryDrawable (dpy, gdk_x11_gl_context_glx_get_drawable (self),
GLX_BACK_BUFFER_AGE_EXT, &buffer_age);
switch (buffer_age)
if (buffer_age > 0 && buffer_age <= GDK_GL_MAX_TRACKED_BUFFERS)
{
case 1:
return cairo_region_create ();
break;
cairo_region_t *damage = cairo_region_create ();
int i;
case 2:
if (context->old_updated_area[0])
return cairo_region_copy (context->old_updated_area[0]);
break;
for (i = 0; i < buffer_age - 1; i++)
{
if (context->old_updated_area[i] == NULL)
return GDK_GL_CONTEXT_CLASS (gdk_x11_gl_context_glx_parent_class)->get_damage (context);
case 3:
if (context->old_updated_area[0] &&
context->old_updated_area[1])
{
cairo_region_t *damage = cairo_region_copy (context->old_updated_area[0]);
cairo_region_union (damage, context->old_updated_area[1]);
return damage;
}
break;
cairo_region_union (damage, context->old_updated_area[i]);
}
default:
;
return damage;
}
}
@@ -531,14 +543,14 @@ gdk_x11_context_create_glx_context (GdkGLContext *context,
if (share != NULL)
share_glx = GDK_X11_GL_CONTEXT_GLX (share);
gdk_x11_display_error_trap_push (display);
supported_versions = gdk_gl_versions_get_for_api (api);
for (j = 0; gdk_gl_version_greater_equal (&supported_versions[j], &version); j++)
{
context_attribs [major_idx] = gdk_gl_version_get_major (&supported_versions[j]);
context_attribs [minor_idx] = gdk_gl_version_get_minor (&supported_versions[j]);
gdk_x11_display_error_trap_push (display);
/* If we don't have access to GLX_ARB_create_context_profile, then
* we have to fall back to the old GLX 1.3 API.
*/
@@ -556,22 +568,19 @@ gdk_x11_context_create_glx_context (GdkGLContext *context,
True,
context_attribs);
if (ctx)
if (ctx == NULL)
{
gdk_x11_display_error_trap_pop_ignored (display);
}
else if (gdk_x11_display_error_trap_pop (display))
{
glXDestroyContext (dpy, ctx);
ctx = NULL;
}
else
break;
}
if (ctx == NULL)
{
gdk_x11_display_error_trap_pop_ignored (display);
return 0;
}
if (gdk_x11_display_error_trap_pop (display))
{
glXDestroyContext (dpy, ctx);
return 0;
}
GDK_DISPLAY_DEBUG (display, OPENGL,
"Realized GLX context[%p], %s, version: %d.%d",
context_glx->glx_context,
@@ -945,8 +954,10 @@ gdk_x11_display_init_glx (GdkX11Display *display_x11,
epoxy_has_glx_extension (dpy, screen_num, "GLX_ARB_create_context_profile");
display_x11->has_glx_create_es2_context =
epoxy_has_glx_extension (dpy, screen_num, "GLX_EXT_create_context_es2_profile");
display_x11->has_glx_swap_interval =
display_x11->has_glx_sgi_swap_control =
epoxy_has_glx_extension (dpy, screen_num, "GLX_SGI_swap_control");
display_x11->has_glx_swap_control =
epoxy_has_glx_extension (dpy, screen_num, "GLX_EXT_swap_control");
display_x11->has_glx_texture_from_pixmap =
epoxy_has_glx_extension (dpy, screen_num, "GLX_EXT_texture_from_pixmap");
display_x11->has_glx_video_sync =
@@ -1007,6 +1018,7 @@ gdk_x11_display_init_glx (GdkX11Display *display_x11,
"\t* GLX_ARB_create_context_profile: %s\n"
"\t* GLX_EXT_create_context_es2_profile: %s\n"
"\t* GLX_SGI_swap_control: %s\n"
"\t* GLX_EXT_swap_control: %s\n"
"\t* GLX_EXT_texture_from_pixmap: %s\n"
"\t* GLX_SGI_video_sync: %s\n"
"\t* GLX_EXT_buffer_age: %s\n"
@@ -1018,7 +1030,8 @@ gdk_x11_display_init_glx (GdkX11Display *display_x11,
glXGetClientString (dpy, GLX_VENDOR),
display_x11->has_glx_create_context ? "yes" : "no",
display_x11->has_glx_create_es2_context ? "yes" : "no",
display_x11->has_glx_swap_interval ? "yes" : "no",
display_x11->has_glx_sgi_swap_control ? "yes" : "no",
display_x11->has_glx_swap_control ? "yes" : "no",
display_x11->has_glx_texture_from_pixmap ? "yes" : "no",
display_x11->has_glx_video_sync ? "yes" : "no",
display_x11->has_glx_buffer_age ? "yes" : "no",
+19 -3
View File
@@ -685,8 +685,13 @@ init_randr13 (GdkX11Screen *x11_screen)
for (i = 0; i < resources->noutput; ++i)
{
RROutput output = resources->outputs[i];
XRROutputInfo *output_info =
XRRGetOutputInfo (x11_screen->xdisplay, resources, output);
XRROutputInfo *output_info;
gdk_x11_display_error_trap_push (display);
output_info = XRRGetOutputInfo (x11_screen->xdisplay, resources, output);
if (gdk_x11_display_error_trap_pop (display))
continue;
if (output_info->connection == RR_Disconnected)
{
@@ -697,13 +702,22 @@ init_randr13 (GdkX11Screen *x11_screen)
if (output_info->crtc)
{
GdkX11Monitor *monitor;
XRRCrtcInfo *crtc = XRRGetCrtcInfo (x11_screen->xdisplay, resources, output_info->crtc);
XRRCrtcInfo *crtc;
char *name;
GdkRectangle geometry;
GdkRectangle newgeo;
int j;
int refresh_rate = 0;
gdk_x11_display_error_trap_push (display);
crtc = XRRGetCrtcInfo (x11_screen->xdisplay, resources, output_info->crtc);
if (gdk_x11_display_error_trap_pop (display))
{
XRRFreeOutputInfo (output_info);
continue;
}
for (j = 0; j < resources->nmode; j++)
{
XRRModeInfo *xmode = &resources->modes[j];
@@ -775,8 +789,10 @@ init_randr13 (GdkX11Screen *x11_screen)
}
x11_display->primary_monitor = 0;
gdk_x11_display_error_trap_push (display);
primary_output = XRRGetOutputPrimary (x11_screen->xdisplay,
x11_screen->xroot_window);
gdk_x11_display_error_trap_pop_ignored (display);
for (i = 0; i < g_list_model_get_n_items (G_LIST_MODEL (x11_display->monitors)); i++)
{
+12 -12
View File
@@ -89,7 +89,7 @@ gdk_x11_selection_input_stream_fill_buffer (GdkX11SelectionInputStream *stream,
if (size == 0)
{
/* EOF marker, put it back */
g_async_queue_push_front_unlocked (priv->chunks, bytes);
g_async_queue_push_front_unlocked (priv->chunks, g_steal_pointer (&bytes));
break;
}
else if (size > count)
@@ -107,7 +107,7 @@ gdk_x11_selection_input_stream_fill_buffer (GdkX11SelectionInputStream *stream,
memcpy (buffer, g_bytes_get_data (bytes, NULL), size);
}
g_bytes_unref (bytes);
g_bytes_unref (g_steal_pointer (&bytes));
result += size;
if (buffer)
buffer += size;
@@ -165,9 +165,7 @@ gdk_x11_selection_input_stream_complete (GdkX11SelectionInputStream *stream)
GDK_X11_DISPLAY (priv->display)->streams = g_slist_remove (GDK_X11_DISPLAY (priv->display)->streams, stream);
g_signal_handlers_disconnect_by_func (priv->display,
gdk_x11_selection_input_stream_xevent,
stream);
g_object_unref (stream);
g_steal_pointer (&stream));
}
static gssize
@@ -416,7 +414,7 @@ gdk_x11_selection_input_stream_xevent (GdkDisplay *display,
"%s:%s: got PropertyNotify erroring out of INCR",
priv->selection, priv->target);
/* error, should we signal one? */
gdk_x11_selection_input_stream_complete (stream);
g_clear_pointer (&stream, gdk_x11_selection_input_stream_complete);
}
else if (g_bytes_get_size (bytes) == 0 || type == None)
{
@@ -424,7 +422,7 @@ gdk_x11_selection_input_stream_xevent (GdkDisplay *display,
"%s:%s: got PropertyNotify ending INCR",
priv->selection, priv->target);
g_bytes_unref (bytes);
gdk_x11_selection_input_stream_complete (stream);
g_clear_pointer (&stream, gdk_x11_selection_input_stream_complete);
}
else
{
@@ -467,7 +465,7 @@ gdk_x11_selection_input_stream_xevent (GdkDisplay *display,
G_IO_ERROR,
G_IO_ERROR_NOT_FOUND,
_("Format %s not supported"), priv->target);
gdk_x11_selection_input_stream_complete (stream);
g_clear_pointer (&stream, gdk_x11_selection_input_stream_complete);
}
else
{
@@ -478,7 +476,7 @@ gdk_x11_selection_input_stream_xevent (GdkDisplay *display,
if (bytes == NULL)
{
gdk_x11_selection_input_stream_complete (stream);
g_clear_pointer (&stream, gdk_x11_selection_input_stream_complete);
}
else
{
@@ -500,7 +498,7 @@ gdk_x11_selection_input_stream_xevent (GdkDisplay *display,
g_bytes_get_size (bytes));
g_async_queue_push (priv->chunks, bytes);
gdk_x11_selection_input_stream_complete (stream);
g_clear_pointer (&stream, gdk_x11_selection_input_stream_complete);
}
}
@@ -541,7 +539,10 @@ gdk_x11_selection_input_stream_new_async (GdkDisplay *display,
priv->property = g_strdup_printf ("GDK_SELECTION_%p", stream);
priv->xproperty = gdk_x11_get_xatom_by_name_for_display (display, priv->property);
g_signal_connect (display, "xevent", G_CALLBACK (gdk_x11_selection_input_stream_xevent), stream);
g_signal_connect_data (display, "xevent",
G_CALLBACK (gdk_x11_selection_input_stream_xevent),
g_steal_pointer (&stream),
(GClosureNotify) g_object_unref, 0);
XConvertSelection (GDK_DISPLAY_XDISPLAY (display),
priv->xselection,
@@ -577,7 +578,6 @@ gdk_x11_selection_input_stream_new_finish (GAsyncResult *result,
*type = priv->type;
if (format)
*format = priv->format;
g_object_ref (stream);
}
return G_INPUT_STREAM (stream);
+34 -12
View File
@@ -1447,6 +1447,7 @@ gsk_gl_command_queue_create_framebuffer (GskGLCommandQueue *self)
return fbo_id;
}
static GdkMemoryFormat
memory_format_gl_format (GdkMemoryFormat data_format,
gboolean use_es,
@@ -1454,7 +1455,8 @@ memory_format_gl_format (GdkMemoryFormat data_format,
guint minor,
guint *gl_internalformat,
guint *gl_format,
guint *gl_type)
guint *gl_type,
GLint (*gl_swizzle)[4])
{
if (gdk_memory_format_gl_format (data_format,
use_es,
@@ -1462,7 +1464,9 @@ memory_format_gl_format (GdkMemoryFormat data_format,
minor,
gl_internalformat,
gl_format,
gl_type))
gl_type,
gl_swizzle) &&
gdk_memory_format_alpha (data_format) != GDK_MEMORY_ALPHA_STRAIGHT)
return data_format;
if (gdk_memory_format_prefers_high_depth (data_format))
@@ -1474,7 +1478,8 @@ memory_format_gl_format (GdkMemoryFormat data_format,
minor,
gl_internalformat,
gl_format,
gl_type))
gl_type,
gl_swizzle))
return data_format;
}
@@ -1485,7 +1490,8 @@ memory_format_gl_format (GdkMemoryFormat data_format,
minor,
gl_internalformat,
gl_format,
gl_type))
gl_type,
gl_swizzle))
{
g_assert_not_reached ();
}
@@ -1508,6 +1514,7 @@ gsk_gl_command_queue_do_upload_texture_chunk (GskGLCommandQueue *self,
GLenum gl_internalformat;
GLenum gl_format;
GLenum gl_type;
GLint gl_swizzle[4];
gsize bpp;
gboolean use_es;
int major, minor;
@@ -1524,7 +1531,8 @@ gsk_gl_command_queue_do_upload_texture_chunk (GskGLCommandQueue *self,
minor,
&gl_internalformat,
&gl_format,
&gl_type);
&gl_type,
&gl_swizzle);
gdk_texture_downloader_init (&downloader, texture);
gdk_texture_downloader_set_format (&downloader, data_format);
@@ -1559,6 +1567,18 @@ gsk_gl_command_queue_do_upload_texture_chunk (GskGLCommandQueue *self,
glPixelStorei (GL_UNPACK_ALIGNMENT, 4);
/* Only apply swizzle if really needed, might not even be
* supported if default values are set
*/
if (gl_swizzle[0] != GL_RED || gl_swizzle[1] != GL_GREEN || gl_swizzle[2] != GL_BLUE)
{
/* Set each channel independently since GLES 3.0 doesn't support the iv method */
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_R, gl_swizzle[0]);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_G, gl_swizzle[1]);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_B, gl_swizzle[2]);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_A, gl_swizzle[3]);
}
g_bytes_unref (bytes);
}
@@ -1573,6 +1593,7 @@ gsk_gl_command_queue_upload_texture_chunks (GskGLCommandQueue *self,
GLenum gl_internalformat;
GLenum gl_format;
GLenum gl_type;
GLint gl_swizzle[4];
gboolean use_es;
int texture_id;
int major, minor;
@@ -1611,13 +1632,14 @@ gsk_gl_command_queue_upload_texture_chunks (GskGLCommandQueue *self,
use_es = gdk_gl_context_get_use_es (self->context);
gdk_gl_context_get_version (self->context, &major, &minor);
data_format = gdk_texture_get_format (chunks[0].texture);
memory_format_gl_format (data_format,
use_es,
major,
minor,
&gl_internalformat,
&gl_format,
&gl_type);
data_format = memory_format_gl_format (data_format,
use_es,
major,
minor,
&gl_internalformat,
&gl_format,
&gl_type,
&gl_swizzle);
glTexImage2D (GL_TEXTURE_2D, 0, gl_internalformat, width, height, 0, gl_format, gl_type, NULL);
+2 -1
View File
@@ -761,7 +761,8 @@ gsk_gl_driver_load_texture (GskGLDriver *self,
GdkGLContext *texture_context = gdk_gl_texture_get_context (gl_texture);
if (gdk_gl_context_is_shared (context, texture_context) &&
(!ensure_mipmap || gdk_gl_texture_has_mipmap (gl_texture)))
(!ensure_mipmap || gdk_gl_texture_has_mipmap (gl_texture)) &&
gdk_memory_format_alpha (gdk_texture_get_format (texture)) != GDK_MEMORY_ALPHA_STRAIGHT)
{
/* A GL texture from the same GL context is a simple task... */
return gdk_gl_texture_get_id (gl_texture);
+1 -1
View File
@@ -88,7 +88,7 @@ gsk_gl_texture_library_real_compact (GskGLTextureLibrary *self,
GskGLTextureAtlasEntry *entry;
GHashTableIter iter;
guint dropped = 0;
guint atlased = 0;
G_GNUC_UNUSED guint atlased = 0;
g_hash_table_iter_init (&iter, self->hash_table);
while (g_hash_table_iter_next (&iter, NULL, (gpointer *)&entry))
+8
View File
@@ -2892,6 +2892,14 @@ append_texture_param (Printer *p,
case GDK_MEMORY_R16G16B16:
case GDK_MEMORY_R16G16B16A16_PREMULTIPLIED:
case GDK_MEMORY_R16G16B16A16:
case GDK_MEMORY_G8A8_PREMULTIPLIED:
case GDK_MEMORY_G8A8:
case GDK_MEMORY_G8:
case GDK_MEMORY_G16A16_PREMULTIPLIED:
case GDK_MEMORY_G16A16:
case GDK_MEMORY_G16:
case GDK_MEMORY_A8:
case GDK_MEMORY_A16:
bytes = gdk_texture_save_to_png_bytes (texture);
g_string_append (p->str, "url(\"data:image/png;base64,");
break;
+1 -1
View File
@@ -450,7 +450,7 @@ gsk_vulkan_glyph_cache_begin_frame (GskVulkanGlyphCache *cache)
GHashTableIter iter;
GlyphCacheKey *key;
GskVulkanCachedGlyph *value;
guint dropped = 0;
G_GNUC_UNUSED guint dropped = 0;
cache->timestamp++;
+1 -1
View File
@@ -32,4 +32,4 @@ VS_VERSION_INFO VERSIONINFO
END
END
ISOLATIONAWARE_MANIFEST_RESOURCE_ID RT_MANIFEST libgtk4.manifest
ISOLATIONAWARE_MANIFEST_RESOURCE_ID RT_MANIFEST libgtk.manifest
+4 -1
View File
@@ -325,6 +325,9 @@ gtk_action_muxer_get_group (GtkActionMuxer *muxer,
{
Group *group;
if (!muxer->groups)
return NULL;
group = g_hash_table_lookup (muxer->groups, group_name);
if (group)
return group->group;
@@ -452,7 +455,7 @@ notify_observers_added (GtkActionMuxer *muxer,
gtk_action_observable_register_observer (GTK_ACTION_OBSERVABLE (parent), action_name, GTK_ACTION_OBSERVER (muxer));
if (!action_muxer_query_action (parent, action_name,
if (!action_muxer_query_action (muxer, action_name,
&enabled, &parameter_type,
NULL, NULL, &state,
TRUE))
+6 -1
View File
@@ -323,6 +323,7 @@ gtk_box_layout_compute_opposite_size (GtkBoxLayout *self,
int largest_min_above = -1, largest_min_below = -1;
int largest_nat_above = -1, largest_nat_below = -1;
gboolean have_baseline = FALSE;
gboolean align_baseline = FALSE;
for (child = gtk_widget_get_first_child (widget);
child != NULL;
@@ -350,6 +351,10 @@ gtk_box_layout_compute_opposite_size (GtkBoxLayout *self,
if (child_min_baseline > -1)
{
have_baseline = TRUE;
if (gtk_widget_get_valign (child) == GTK_ALIGN_BASELINE_FILL ||
gtk_widget_get_valign (child) == GTK_ALIGN_BASELINE_CENTER)
align_baseline = TRUE;
largest_min_above = MAX (largest_min_above, child_min_baseline);
largest_min_below = MAX (largest_min_below, child_min - child_min_baseline);
largest_nat_above = MAX (largest_nat_above, child_nat_baseline);
@@ -358,7 +363,7 @@ gtk_box_layout_compute_opposite_size (GtkBoxLayout *self,
}
}
if (self->orientation == GTK_ORIENTATION_HORIZONTAL)
if (self->orientation == GTK_ORIENTATION_HORIZONTAL && align_baseline)
{
largest_min = MAX (largest_min, largest_min_above + largest_min_below);
largest_nat = MAX (largest_nat, largest_nat_above + largest_nat_below);
+67
View File
@@ -220,6 +220,7 @@ enum
PROP_COLUMNS,
PROP_ENABLE_RUBBERBAND,
PROP_HADJUSTMENT,
PROP_HEADER_FACTORY,
PROP_HSCROLL_POLICY,
PROP_MODEL,
PROP_REORDERABLE,
@@ -629,6 +630,10 @@ gtk_column_view_get_property (GObject *object,
g_value_set_object (value, self->hadjustment);
break;
case PROP_HEADER_FACTORY:
g_value_set_object (value, gtk_column_view_get_header_factory (self));
break;
case PROP_HSCROLL_POLICY:
g_value_set_enum (value, gtk_scrollable_get_hscroll_policy (GTK_SCROLLABLE (self->listview)));
break;
@@ -712,6 +717,10 @@ gtk_column_view_set_property (GObject *object,
}
break;
case PROP_HEADER_FACTORY:
gtk_column_view_set_header_factory (self, g_value_get_object (value));
break;
case PROP_HSCROLL_POLICY:
if (gtk_scrollable_get_hscroll_policy (GTK_SCROLLABLE (self->listview)) != g_value_get_enum (value))
{
@@ -911,6 +920,18 @@ gtk_column_view_class_init (GtkColumnViewClass *klass)
GTK_LIST_TAB_ALL,
G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY);
/**
* GtkColumnView:header-factory: (attributes org.gtk.Property.get=gtk_column_view_get_header_factory org.gtk.Property.set=gtk_column_view_set_header_factory)
*
* Factory for creating header widgets.
*
* Since: 4.12
*/
properties[PROP_HEADER_FACTORY] =
g_param_spec_object ("header-factory", NULL, NULL,
GTK_TYPE_LIST_ITEM_FACTORY,
G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS);
g_object_class_install_properties (gobject_class, N_PROPS, properties);
/**
@@ -2107,3 +2128,49 @@ gtk_column_view_get_tab_behavior (GtkColumnView *self)
return gtk_list_view_get_tab_behavior (self->listview);
}
/**
* gtk_column_view_get_header_factory: (attributes org.gtk.Method.get_property=header-factory)
* @self: a `GtkColumnView`
*
* Gets the factory that's currently used to populate section headers.
*
* Returns: (nullable) (transfer none): The factory in use
*
* Since: 4.12
*/
GtkListItemFactory *
gtk_column_view_get_header_factory (GtkColumnView *self)
{
g_return_val_if_fail (GTK_IS_COLUMN_VIEW (self), NULL);
return gtk_list_view_get_header_factory (self->listview);
}
/**
* gtk_column_view_set_header_factory: (attributes org.gtk.Method.set_property=header-factory)
* @self: a `GtkColumnView`
* @factory: (nullable) (transfer none): the factory to use
*
* Sets the `GtkListItemFactory` to use for populating the
* [class@Gtk.ListHeader] objects used in section headers.
*
* If this factory is set to %NULL, the list will not show
* section headers.
*
* Since: 4.12
*/
void
gtk_column_view_set_header_factory (GtkColumnView *self,
GtkListItemFactory *factory)
{
g_return_if_fail (GTK_IS_COLUMN_VIEW (self));
g_return_if_fail (factory == NULL || GTK_IS_LIST_ITEM_FACTORY (factory));
if (factory == gtk_list_view_get_header_factory (self->listview))
return;
gtk_list_view_set_header_factory (self->listview, factory);
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_HEADER_FACTORY]);
}
+8
View File
@@ -122,5 +122,13 @@ GDK_AVAILABLE_IN_4_12
GtkListItemFactory *
gtk_column_view_get_row_factory (GtkColumnView *self);
GDK_AVAILABLE_IN_4_12
void gtk_column_view_set_header_factory (GtkColumnView *self,
GtkListItemFactory *factory);
GDK_AVAILABLE_IN_4_12
GtkListItemFactory *
gtk_column_view_get_header_factory (GtkColumnView *self);
G_END_DECLS
+4 -4
View File
@@ -19,7 +19,7 @@
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
* file for a list of people on the GTK+ Team. See the ChangeLog
* files for a list of changes. These files are distributed with
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
*/
#include "config.h"
@@ -207,7 +207,7 @@ gtk_drag_source_set_property (GObject *object,
GParamSpec *pspec)
{
GtkDragSource *source = GTK_DRAG_SOURCE (object);
switch (prop_id)
{
case PROP_CONTENT:
@@ -424,13 +424,13 @@ gtk_drag_source_class_init (GtkDragSourceClass *class)
G_SIGNAL_RUN_LAST,
0,
NULL, NULL,
_gtk_marshal_OBJECT__BOOLEAN,
_gtk_marshal_VOID__OBJECT_BOOLEAN,
G_TYPE_NONE, 2,
GDK_TYPE_DRAG,
G_TYPE_BOOLEAN);
g_signal_set_va_marshaller (signals[DRAG_END],
GTK_TYPE_DRAG_SOURCE,
_gtk_marshal_OBJECT__BOOLEANv);
_gtk_marshal_VOID__OBJECT_BOOLEANv);
/**
* GtkDragSource::drag-cancel:
+9 -9
View File
@@ -150,13 +150,13 @@ make_action_unique (GdkDragAction actions)
if (actions & GDK_ACTION_MOVE)
return GDK_ACTION_MOVE;
if (actions & GDK_ACTION_LINK)
return GDK_ACTION_LINK;
return 0;
}
static GdkDragAction
gtk_drop_target_async_drag_enter (GtkDropTargetAsync *self,
GdkDrop *drop,
@@ -166,7 +166,7 @@ gtk_drop_target_async_drag_enter (GtkDropTargetAsync *self,
return make_action_unique (self->actions & gdk_drop_get_actions (drop));
}
static GdkDragAction
static GdkDragAction
gtk_drop_target_async_drag_motion (GtkDropTargetAsync *self,
GdkDrop *drop,
double x,
@@ -457,12 +457,12 @@ gtk_drop_target_async_class_init (GtkDropTargetAsyncClass *class)
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GtkDropTargetAsyncClass, drag_enter),
g_signal_accumulator_first_wins, NULL,
_gtk_marshal_ENUM__OBJECT_DOUBLE_DOUBLE,
_gtk_marshal_FLAGS__OBJECT_DOUBLE_DOUBLE,
GDK_TYPE_DRAG_ACTION, 3,
GDK_TYPE_DROP, G_TYPE_DOUBLE, G_TYPE_DOUBLE);
g_signal_set_va_marshaller (signals[DRAG_ENTER],
GTK_TYPE_DROP_TARGET_ASYNC,
_gtk_marshal_ENUM__OBJECT_DOUBLE_DOUBLEv);
_gtk_marshal_FLAGS__OBJECT_DOUBLE_DOUBLEv);
/**
* GtkDropTargetAsync::drag-motion:
@@ -481,12 +481,12 @@ gtk_drop_target_async_class_init (GtkDropTargetAsyncClass *class)
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GtkDropTargetAsyncClass, drag_motion),
g_signal_accumulator_first_wins, NULL,
_gtk_marshal_ENUM__OBJECT_DOUBLE_DOUBLE,
_gtk_marshal_FLAGS__OBJECT_DOUBLE_DOUBLE,
GDK_TYPE_DRAG_ACTION, 3,
GDK_TYPE_DROP, G_TYPE_DOUBLE, G_TYPE_DOUBLE);
g_signal_set_va_marshaller (signals[DRAG_MOTION],
GTK_TYPE_DROP_TARGET_ASYNC,
_gtk_marshal_ENUM__OBJECT_DOUBLE_DOUBLEv);
_gtk_marshal_FLAGS__OBJECT_DOUBLE_DOUBLEv);
/**
* GtkDropTargetAsync::drag-leave:
@@ -617,7 +617,7 @@ GdkContentFormats *
gtk_drop_target_async_get_formats (GtkDropTargetAsync *self)
{
g_return_val_if_fail (GTK_IS_DROP_TARGET_ASYNC (self), NULL);
return self->formats;
}
@@ -633,7 +633,7 @@ gtk_drop_target_async_set_actions (GtkDropTargetAsync *self,
GdkDragAction actions)
{
g_return_if_fail (GTK_IS_DROP_TARGET_ASYNC (self));
if (self->actions == actions)
return;
+6 -5
View File
@@ -69,9 +69,9 @@ typedef enum
GTK_ALIGN_START,
GTK_ALIGN_END,
GTK_ALIGN_CENTER,
GTK_ALIGN_BASELINE_FILL,
GTK_ALIGN_BASELINE_FILL GDK_AVAILABLE_ENUMERATOR_IN_4_12,
GTK_ALIGN_BASELINE GDK_DEPRECATED_ENUMERATOR_IN_4_12_FOR(GTK_ALIGN_BASELINE_FILL) = GTK_ALIGN_BASELINE_FILL,
GTK_ALIGN_BASELINE_CENTER,
GTK_ALIGN_BASELINE_CENTER GDK_AVAILABLE_ENUMERATOR_IN_4_12,
} GtkAlign;
/**
@@ -1422,7 +1422,7 @@ typedef enum {
GTK_ACCESSIBLE_ROLE_TREE_ITEM,
GTK_ACCESSIBLE_ROLE_WIDGET,
GTK_ACCESSIBLE_ROLE_WINDOW,
GTK_ACCESSIBLE_ROLE_TOGGLE_BUTTON
GTK_ACCESSIBLE_ROLE_TOGGLE_BUTTON GDK_AVAILABLE_ENUMERATOR_IN_4_10
} GtkAccessibleRole;
/**
@@ -1449,7 +1449,8 @@ typedef enum {
* @GTK_ACCESSIBLE_STATE_SELECTED: A selected state; set when a widget
* is selected. Value type: boolean or undefined
* @GTK_ACCESSIBLE_STATE_VISITED: Indicates that a widget with the
* GTK_ACCESSIBLE_ROLE_LINK has been visited. Value type: boolean. Since: 4.12
* GTK_ACCESSIBLE_ROLE_LINK has been visited. Value type: boolean.
* Since: 4.12
*
* The possible accessible states of a [iface@Accessible].
*/
@@ -1462,7 +1463,7 @@ typedef enum {
GTK_ACCESSIBLE_STATE_INVALID,
GTK_ACCESSIBLE_STATE_PRESSED,
GTK_ACCESSIBLE_STATE_SELECTED,
GTK_ACCESSIBLE_STATE_VISITED
GTK_ACCESSIBLE_STATE_VISITED GDK_AVAILABLE_ENUMERATOR_IN_4_12
} GtkAccessibleState;
/**
+16 -4
View File
@@ -410,16 +410,22 @@ gtk_event_controller_scroll_handle_event (GtkEventController *controller,
}
else
{
if (ABS (scroll->cur_dx) >= 1)
if (ABS (scroll->cur_dx) >= 0.5)
{
steps = trunc (scroll->cur_dx);
if (steps == 0)
steps = (scroll->cur_dx > 0) ? 1 : -1;
scroll->cur_dx -= steps;
dx = steps;
}
if (ABS (scroll->cur_dy) >= 1)
if (ABS (scroll->cur_dy) >= 0.5)
{
steps = trunc (scroll->cur_dy);
if (steps == 0)
steps = (scroll->cur_dy > 0) ? 1 : -1;
scroll->cur_dy -= steps;
dy = steps;
}
@@ -459,16 +465,22 @@ gtk_event_controller_scroll_handle_event (GtkEventController *controller,
scroll->cur_dy += dy;
dx = dy = 0;
if (ABS (scroll->cur_dx) >= 1)
if (ABS (scroll->cur_dx) >= 0.5)
{
steps = trunc (scroll->cur_dx);
if (steps == 0)
steps = (scroll->cur_dx > 0) ? 1 : -1;
scroll->cur_dx -= steps;
dx = steps;
}
if (ABS (scroll->cur_dy) >= 1)
if (ABS (scroll->cur_dy) >= 0.5)
{
steps = trunc (scroll->cur_dy);
if (steps == 0)
steps = (scroll->cur_dy > 0) ? 1 : -1;
scroll->cur_dy -= steps;
dy = steps;
}
+1 -1
View File
@@ -40,7 +40,7 @@
* expanded widget yourself, such as when you want to actually create
* the widget at expansion time. In this case, create a `GtkExpander`
* but do not add a child to it. The expander widget has an
* [property@Gtk.Expander:expanded[ property which can be used to
* [property@Gtk.Expander:expanded] property which can be used to
* monitor its expansion state. You should watch this property with
* a signal connection as follows:
*
+13 -14
View File
@@ -229,9 +229,9 @@ open_done (GObject *source,
#endif
static void
show_folder_done (GObject *source,
GAsyncResult *result,
gpointer data)
show_item_done (GObject *source,
GAsyncResult *result,
gpointer data)
{
GDBusConnection *bus = G_DBUS_CONNECTION (source);
GTask *task = G_TASK (data);
@@ -261,11 +261,10 @@ show_folder_done (GObject *source,
#define FILE_MANAGER_DBUS_PATH "/org/freedesktop/FileManager1"
static void
show_folder (GtkWindow *parent,
const char *uri,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data)
show_item (GtkWindow *parent,
const char *uri,
GCancellable *cancellable,
GTask *task)
{
GDBusConnection *bus;
GVariantBuilder uris_builder = G_VARIANT_BUILDER_INIT (G_VARIANT_TYPE_STRING_ARRAY);
@@ -274,10 +273,10 @@ show_folder (GtkWindow *parent,
if (!bus)
{
g_task_return_new_error (G_TASK (user_data),
g_task_return_new_error (task,
GTK_DIALOG_ERROR, GTK_DIALOG_ERROR_FAILED,
"Session bus not available");
g_object_unref (G_TASK (user_data));
g_object_unref (task);
return;
}
@@ -287,14 +286,14 @@ show_folder (GtkWindow *parent,
FILE_MANAGER_DBUS_NAME,
FILE_MANAGER_DBUS_PATH,
FILE_MANAGER_DBUS_IFACE,
"ShowFolders",
"ShowItems",
g_variant_new ("(ass)", &uris_builder, ""),
NULL, /* ignore returned type */
G_DBUS_CALL_FLAGS_NONE,
-1,
cancellable,
show_folder_done,
user_data);
show_item_done,
task);
}
G_GNUC_BEGIN_IGNORE_DEPRECATIONS
@@ -470,7 +469,7 @@ gtk_file_launcher_open_containing_folder (GtkFileLauncher *self,
{
char *uri = g_file_get_uri (self->file);
show_folder (parent, uri, cancellable, show_folder_done, task);
show_item (parent, uri, cancellable, task);
g_free (uri);
}
+316 -2
View File
@@ -23,6 +23,7 @@
#include "gtkbitset.h"
#include "gtkprivate.h"
#include "gtkselectionmodel.h"
#include "gtksectionmodelprivate.h"
/**
@@ -34,11 +35,17 @@
* It hides some elements from the other model according to
* criteria given by a `GtkFilter`.
*
* The model can be set up to do incremental searching, so that
* The model can be set up to do incremental filtering, so that
* filtering long lists doesn't block the UI. See
* [method@Gtk.FilterListModel.set_incremental] for details.
*
* `GtkFilterListModel` passes through sections from the underlying model.
*
* Since 4.12, `GtkFilterListModel` also implements `GtkSelectionModel`
* and passes through selections from the underlying model. Any changes
* to the selection that are done through the filter model will cause
* filtered-out items to be unselected.
*/
enum {
PROP_0,
PROP_FILTER,
@@ -136,6 +143,240 @@ gtk_filter_list_model_model_init (GListModelInterface *iface)
iface->get_item = gtk_filter_list_model_get_item;
}
static gboolean
gtk_filter_list_model_is_selected (GtkSelectionModel *model,
guint position)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (model);
guint unfiltered;
if (!GTK_IS_SELECTION_MODEL (self->model))
return FALSE;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return FALSE;
case GTK_FILTER_MATCH_ALL:
unfiltered = position;
break;
case GTK_FILTER_MATCH_SOME:
unfiltered = gtk_bitset_get_nth (self->matches, position);
if (unfiltered == 0 && position >= gtk_bitset_get_size (self->matches))
return FALSE;
break;
default:
g_assert_not_reached ();
}
return gtk_selection_model_is_selected (GTK_SELECTION_MODEL (self->model), unfiltered);
}
static GtkBitset *
gtk_filter_list_model_get_selection_in_range (GtkSelectionModel *model,
guint pos,
guint n_items)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (model);
if (!GTK_IS_SELECTION_MODEL (self->model))
return gtk_bitset_new_empty ();
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return gtk_bitset_new_empty ();
case GTK_FILTER_MATCH_ALL:
return gtk_selection_model_get_selection_in_range (GTK_SELECTION_MODEL (self->model),
pos,
n_items);
case GTK_FILTER_MATCH_SOME:
{
GtkBitset *result;
GtkBitset *selected;
unsigned int last;
unsigned int start, end;
if (pos >= gtk_bitset_get_size (self->matches))
return gtk_bitset_new_empty ();
last = MIN (pos + n_items, gtk_bitset_get_size (self->matches));
start = gtk_bitset_get_nth (self->matches, pos);
end = gtk_bitset_get_nth (self->matches, last - 1);
selected = gtk_selection_model_get_selection_in_range (GTK_SELECTION_MODEL (self->model),
start, end - start + 1);
result = gtk_bitset_new_empty ();
for (unsigned int i = pos; i < last; i++)
{
if (gtk_bitset_contains (selected, gtk_bitset_get_nth (self->matches, i)))
gtk_bitset_add (result, i);
}
gtk_bitset_unref (selected);
return result;
}
default:
g_assert_not_reached ();
}
}
static gboolean
gtk_filter_list_model_select_item (GtkSelectionModel *model,
guint position,
gboolean unselect_rest)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (model);
unsigned int unfiltered;
if (!GTK_IS_SELECTION_MODEL (self->model))
return TRUE;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return TRUE;
case GTK_FILTER_MATCH_ALL:
unfiltered = position;
break;
case GTK_FILTER_MATCH_SOME:
unfiltered = gtk_bitset_get_nth (self->matches, position);
if (unfiltered == 0 && position >= gtk_bitset_get_size (self->matches))
return TRUE;
break;
default:
g_assert_not_reached ();
}
return gtk_selection_model_select_item (GTK_SELECTION_MODEL (self->model),
unfiltered,
unselect_rest);
}
static gboolean
gtk_filter_list_model_unselect_item (GtkSelectionModel *model,
guint position)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (model);
unsigned int unfiltered;
if (!GTK_IS_SELECTION_MODEL (self->model))
return TRUE;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return TRUE;
case GTK_FILTER_MATCH_ALL:
unfiltered = position;
break;
case GTK_FILTER_MATCH_SOME:
unfiltered = gtk_bitset_get_nth (self->matches, position);
if (unfiltered == 0 && position >= gtk_bitset_get_size (self->matches))
return TRUE;
break;
default:
g_assert_not_reached ();
}
return gtk_selection_model_unselect_item (GTK_SELECTION_MODEL (self->model),
unfiltered);
}
static gboolean
gtk_filter_list_model_set_selection (GtkSelectionModel *model,
GtkBitset *selected,
GtkBitset *mask)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (model);
if (!GTK_IS_SELECTION_MODEL (self->model))
return TRUE;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return TRUE;
case GTK_FILTER_MATCH_ALL:
return gtk_selection_model_set_selection (GTK_SELECTION_MODEL (self->model),
selected,
mask);
case GTK_FILTER_MATCH_SOME:
{
GtkBitset *selected2;
GtkBitset *mask2;
GtkBitset *unmatched;
GtkBitsetIter iter;
unsigned int unfiltered;
gboolean ret;
selected2 = gtk_bitset_new_empty ();
mask2 = gtk_bitset_new_empty ();
if (gtk_bitset_iter_init_first (&iter, self->matches, &unfiltered))
{
unsigned int i = 0;
do
{
if (gtk_bitset_contains (selected, i))
gtk_bitset_add (selected2, unfiltered);
if (gtk_bitset_contains (mask, i))
gtk_bitset_add (mask2, unfiltered);
i++;
}
while (gtk_bitset_iter_next (&iter, &unfiltered));
}
unmatched = gtk_bitset_new_range (0, g_list_model_get_n_items (self->model));
gtk_bitset_subtract (unmatched, self->matches);
gtk_bitset_union (mask2, unmatched);
ret = gtk_selection_model_set_selection (GTK_SELECTION_MODEL (self->model),
selected2,
mask2);
gtk_bitset_unref (unmatched);
gtk_bitset_unref (selected2);
gtk_bitset_unref (mask2);
return ret;
}
default:
g_assert_not_reached ();
}
}
static void
gtk_filter_list_model_selection_model_init (GtkSelectionModelInterface *iface)
{
iface->is_selected = gtk_filter_list_model_is_selected;
iface->select_item = gtk_filter_list_model_select_item;
iface->unselect_item = gtk_filter_list_model_unselect_item;
iface->get_selection_in_range = gtk_filter_list_model_get_selection_in_range;
iface->set_selection = gtk_filter_list_model_set_selection;
}
static void
gtk_filter_list_model_get_section (GtkSectionModel *model,
guint position,
@@ -188,6 +429,72 @@ gtk_filter_list_model_get_section (GtkSectionModel *model,
*out_end = *out_start + gtk_bitset_get_size_in_range (self->matches, start, end - 1);
}
static void
gtk_filter_list_model_selection_changed_cb (GtkSelectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (user_data);
unsigned int start, end;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return;
case GTK_FILTER_MATCH_ALL:
gtk_selection_model_selection_changed (GTK_SELECTION_MODEL (self), position, n_items);
break;
case GTK_FILTER_MATCH_SOME:
if (position > 0)
start = gtk_bitset_get_size_in_range (self->matches, 0, position - 1);
else
start = 0;
end = gtk_bitset_get_size_in_range (self->matches, 0, position + n_items - 1);
if (end - start > 0)
gtk_selection_model_selection_changed (GTK_SELECTION_MODEL (self), start, end - start);
break;
default:
g_assert_not_reached ();
}
}
static void
gtk_filter_list_model_sections_changed_cb (GtkSectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkFilterListModel *self = GTK_FILTER_LIST_MODEL (user_data);
unsigned int start, end;
switch (self->strictness)
{
case GTK_FILTER_MATCH_NONE:
return;
case GTK_FILTER_MATCH_ALL:
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), position, n_items);
break;
case GTK_FILTER_MATCH_SOME:
if (position > 0)
start = gtk_bitset_get_size_in_range (self->matches, 0, position - 1);
else
start = 0;
end = gtk_bitset_get_size_in_range (self->matches, 0, position + n_items - 1);
if (end - start > 0)
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), start, end - start);
break;
default:
g_assert_not_reached ();
}
}
static void
gtk_filter_list_model_section_model_init (GtkSectionModelInterface *iface)
{
@@ -196,6 +503,7 @@ gtk_filter_list_model_section_model_init (GtkSectionModelInterface *iface)
G_DEFINE_TYPE_WITH_CODE (GtkFilterListModel, gtk_filter_list_model, G_TYPE_OBJECT,
G_IMPLEMENT_INTERFACE (G_TYPE_LIST_MODEL, gtk_filter_list_model_model_init)
G_IMPLEMENT_INTERFACE (GTK_TYPE_SELECTION_MODEL, gtk_filter_list_model_selection_model_init)
G_IMPLEMENT_INTERFACE (GTK_TYPE_SECTION_MODEL, gtk_filter_list_model_section_model_init))
static gboolean
@@ -463,6 +771,8 @@ gtk_filter_list_model_clear_model (GtkFilterListModel *self)
gtk_filter_list_model_stop_filtering (self);
g_signal_handlers_disconnect_by_func (self->model, gtk_filter_list_model_items_changed_cb, self);
g_signal_handlers_disconnect_by_func (self->model, gtk_filter_list_model_selection_changed_cb, self);
g_signal_handlers_disconnect_by_func (self->model, gtk_filter_list_model_sections_changed_cb, self);
g_clear_object (&self->model);
if (self->matches)
gtk_bitset_remove_all (self->matches);
@@ -827,6 +1137,10 @@ gtk_filter_list_model_set_model (GtkFilterListModel *self,
{
self->model = g_object_ref (model);
g_signal_connect (model, "items-changed", G_CALLBACK (gtk_filter_list_model_items_changed_cb), self);
if (GTK_IS_SELECTION_MODEL (model))
g_signal_connect (model, "selection-changed", G_CALLBACK (gtk_filter_list_model_selection_changed_cb), self);
if (GTK_IS_SECTION_MODEL (model))
g_signal_connect (model, "sections-changed", G_CALLBACK (gtk_filter_list_model_sections_changed_cb), self);
if (removed == 0)
{
self->strictness = GTK_FILTER_MATCH_NONE;
+2 -2
View File
@@ -29,8 +29,8 @@
*
* `GtkFlattenListModel` is a list model that concatenates other list models.
*
* `GtkFlattenListModel` takes a list model containing list models,
* and flattens it into a single model.
* `GtkFlattenListModel` takes a list model containing list models, and flattens
* it into a single model. Each list model becomes a section in the single model.
*/
enum {
+1 -1
View File
@@ -1162,7 +1162,7 @@ update_fontlist (GtkFontChooserWidget *self)
model = G_LIST_MODEL (gtk_slice_list_model_new (model, 0, 20));
gtk_widget_add_tick_callback (GTK_WIDGET (self), add_to_fontlist, g_object_ref (model), g_object_unref);
gtk_filter_list_model_set_model (self->filter_model, model);
gtk_single_selection_set_model (self->selection, model);
g_object_unref (model);
}
+16 -13
View File
@@ -553,8 +553,7 @@ static int
gtk_grid_view_get_unknown_row_size (GtkGridView *self,
GArray *heights)
{
if (heights->len == 0)
return 0;
g_return_val_if_fail (heights->len > 0, 0);
/* return the median and hope rows are generally uniform with few outliers */
g_array_sort (heights, compare_ints);
@@ -757,8 +756,10 @@ gtk_grid_view_size_allocate (GtkWidget *widget,
min_row_height = ceil ((double) height / GTK_GRID_VIEW_MAX_VISIBLE_ROWS);
gtk_list_base_get_border_spacing (GTK_LIST_BASE (self), &xspacing, &yspacing);
gtk_list_item_manager_gc_tiles (self->item_manager);
/* step 0: exit early if list is empty */
tile = gtk_list_tile_gc (self->item_manager, gtk_list_item_manager_get_first (self->item_manager));
tile = gtk_list_item_manager_get_first (self->item_manager);
if (tile == NULL)
{
gtk_list_base_allocate (GTK_LIST_BASE (self));
@@ -777,9 +778,7 @@ gtk_grid_view_size_allocate (GtkWidget *widget,
/* step 2: determine height of known rows */
heights = g_array_new (FALSE, FALSE, sizeof (int));
for (;
tile != NULL;
tile = gtk_list_tile_gc (self->item_manager, tile))
while (tile != NULL)
{
/* if it's a multirow tile, handle it here */
if (tile->n_items > 1 && tile->n_items >= self->n_columns)
@@ -796,7 +795,7 @@ gtk_grid_view_size_allocate (GtkWidget *widget,
for (i = 0, start = tile;
i < self->n_columns && tile != NULL;
tile = gtk_list_tile_gc (self->item_manager, gtk_rb_tree_node_get_next (tile)))
tile = gtk_rb_tree_node_get_next (tile))
{
if (tile->widget)
{
@@ -884,16 +883,16 @@ gtk_grid_view_size_allocate (GtkWidget *widget,
/* Add a filler tile for empty space in the bottom right */
if (i > 0)
{
GtkListTile *filler;
tile = gtk_list_item_manager_get_last (self->item_manager);
filler = gtk_list_tile_append_filler (self->item_manager, tile);
GtkListTile *footer = gtk_list_item_manager_get_last (self->item_manager);
g_assert (gtk_list_tile_is_footer (footer));
tile = gtk_rb_tree_node_get_previous (footer);
gtk_list_tile_set_area_position (self->item_manager,
filler,
footer,
column_start (self, xspacing, i),
y);
gtk_list_tile_set_area_size (self->item_manager,
filler,
column_end (self, xspacing, self->n_columns - 1) - filler->area.x,
footer,
column_end (self, xspacing, self->n_columns - 1) - footer->area.x,
tile->area.height);
}
@@ -952,6 +951,8 @@ gtk_grid_view_dispose (GObject *object)
self->item_manager = NULL;
g_clear_object (&self->factory);
G_OBJECT_CLASS (gtk_grid_view_parent_class)->dispose (object);
}
@@ -1336,6 +1337,8 @@ gtk_grid_view_set_factory (GtkGridView *self,
if (!g_set_object (&self->factory, factory))
return;
gtk_grid_view_update_factories (self);
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_FACTORY]);
}
+15 -11
View File
@@ -1970,10 +1970,13 @@ gtk_label_activate_link_open (GtkWidget *widget,
GVariant *parameter)
{
GtkLabel *self = GTK_LABEL (widget);
GtkLabelLink *link = self->select_info->context_link;
if (self->select_info)
{
GtkLabelLink *link = self->select_info->context_link;
if (link)
emit_activate_link (self, link);
if (link)
emit_activate_link (self, link);
}
}
static void
@@ -1982,17 +1985,18 @@ gtk_label_activate_link_copy (GtkWidget *widget,
GVariant *parameter)
{
GtkLabel *self = GTK_LABEL (widget);
GtkLabelLink *link = self->select_info->context_link;
if (link)
if (self->select_info)
{
GdkClipboard *clipboard;
GtkLabelLink *link = self->select_info->context_link;
clipboard = gtk_widget_get_clipboard (widget);
gdk_clipboard_set_text (clipboard, link->uri);
if (link)
{
GdkClipboard *clipboard;
clipboard = gtk_widget_get_clipboard (widget);
gdk_clipboard_set_text (clipboard, link->uri);
}
}
else
g_print ("no link ?!\n");
}
static void
+100 -60
View File
@@ -198,7 +198,6 @@ gtk_list_item_manager_augment_node (GtkRbTree *tree,
aug->has_footer = TRUE;
break;
case GTK_LIST_TILE_ITEM:
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
aug->has_header = FALSE;
aug->has_footer = FALSE;
@@ -569,8 +568,7 @@ gtk_list_tile_get_tile_at (GtkListItemManager *self,
* If multiple tiles have the same distance, the one closest to the start
* will be returned.
*
* Returns: (nullable): The tile nearest to (x, y) or NULL if there are no
* tile
* Returns: (nullable): The tile nearest to (x, y) or NULL if there are no tiles
**/
GtkListTile *
gtk_list_item_manager_get_nearest_tile (GtkListItemManager *self,
@@ -633,7 +631,7 @@ static GtkListTile *
gtk_list_tile_get_next_skip (GtkListTile *tile)
{
for (tile = gtk_rb_tree_node_get_next (tile);
tile && (tile->type == GTK_LIST_TILE_FILLER || tile->type == GTK_LIST_TILE_REMOVED);
tile && tile->type == GTK_LIST_TILE_REMOVED;
tile = gtk_rb_tree_node_get_next (tile))
{ }
@@ -644,7 +642,7 @@ static GtkListTile *
gtk_list_tile_get_previous_skip (GtkListTile *tile)
{
for (tile = gtk_rb_tree_node_get_previous (tile);
tile && (tile->type == GTK_LIST_TILE_FILLER || tile->type == GTK_LIST_TILE_REMOVED);
tile && tile->type == GTK_LIST_TILE_REMOVED;
tile = gtk_rb_tree_node_get_previous (tile))
{ }
@@ -885,7 +883,6 @@ gtk_list_item_manager_remove_items (GtkListItemManager *self,
gtk_list_tile_set_type (tile, GTK_LIST_TILE_REMOVED);
break;
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
default:
g_assert_not_reached ();
@@ -928,7 +925,7 @@ gtk_list_item_manager_add_items (GtkListItemManager *self,
{
/* at end of list, pick the footer */
for (tile = gtk_rb_tree_get_last (self->items);
tile && (tile->type == GTK_LIST_TILE_REMOVED || tile->type == GTK_LIST_TILE_FILLER);
tile && tile->type == GTK_LIST_TILE_REMOVED;
tile = gtk_rb_tree_node_get_previous (tile))
{ }
@@ -1002,11 +999,13 @@ gtk_list_item_manager_merge_list_items (GtkListItemManager *self,
* Splits the given tile into two tiles. The original
* tile will remain with @n_items items, the remaining
* items will be given to the new tile, which will be
* nserted after the tile.
* inserted after the tile.
*
* It is not valid for either tile to have 0 items after
* the split.
*
* This function does not update the tiles' areas.
*
* Returns: The new tile
**/
GtkListTile *
@@ -1029,34 +1028,6 @@ gtk_list_tile_split (GtkListItemManager *self,
return result;
}
/*
* gtk_list_tile_append_filler:
* @self: the listitemmanager
* @previous: tile to append to
*
* Appends a filler tile.
*
* Filler tiles don't refer to any items or header and exist
* just to take up space, so that finding items by position gets
* easier.
*
* They ave a special garbage-collection behavior, see
* gtk_list_tile_gc().
*
* Returns: The new filler tile
**/
GtkListTile *
gtk_list_tile_append_filler (GtkListItemManager *self,
GtkListTile *previous)
{
GtkListTile *result;
result = gtk_rb_tree_insert_after (self->items, previous);
result->type = GTK_LIST_TILE_FILLER;
return result;
}
/*
* gtk_list_tile_gc:
* @self: the listitemmanager
@@ -1068,13 +1039,9 @@ gtk_list_tile_append_filler (GtkListItemManager *self,
*
* Note that this only looks forward, but never backward.
*
* A special case here are filler tiles. They only get
* collected, when they are explicitly passed in, but never
* otherwise.
*
* Returns: The next tile or NULL if everything was gc'ed
**/
GtkListTile *
static GtkListTile *
gtk_list_tile_gc (GtkListItemManager *self,
GtkListTile *tile)
{
@@ -1083,13 +1050,6 @@ gtk_list_tile_gc (GtkListItemManager *self,
if (tile == NULL)
return NULL;
if (tile->type == GTK_LIST_TILE_FILLER)
{
next = gtk_rb_tree_node_get_next (tile);
gtk_rb_tree_remove (self->items, tile);
tile = next;
}
while (tile)
{
next = gtk_rb_tree_node_get_next (tile);
@@ -1113,7 +1073,6 @@ gtk_list_tile_gc (GtkListItemManager *self,
case GTK_LIST_TILE_FOOTER:
case GTK_LIST_TILE_UNMATCHED_HEADER:
case GTK_LIST_TILE_UNMATCHED_FOOTER:
case GTK_LIST_TILE_FILLER:
break;
case GTK_LIST_TILE_REMOVED:
@@ -1132,6 +1091,27 @@ gtk_list_tile_gc (GtkListItemManager *self,
return tile;
}
/*
* gtk_list_item_manager_gc_tiles:
* @self: the listitemmanager
*
* Removes all tiles of type GTK_LIST_TILE_REMOVED
* and merges item tiles as much as possible.
*
* This function does not update the tiles' areas.
*/
void
gtk_list_item_manager_gc_tiles (GtkListItemManager *self)
{
GtkListTile *tile;
for (tile = gtk_list_tile_gc (self, gtk_list_item_manager_get_first (self));
tile != NULL;
tile = gtk_list_tile_gc (self, gtk_rb_tree_node_get_next (tile)))
{
}
}
static void
gtk_list_item_manager_release_items (GtkListItemManager *self,
GtkListItemChange *change)
@@ -1180,7 +1160,6 @@ gtk_list_item_manager_release_items (GtkListItemManager *self,
deleted_section = TRUE;
break;
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
default:
g_assert_not_reached ();
@@ -1414,7 +1393,6 @@ gtk_list_item_manager_ensure_items (GtkListItemManager *self,
break;
case GTK_LIST_TILE_UNMATCHED_FOOTER:
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
default:
g_assert_not_reached ();
@@ -1594,6 +1572,67 @@ gtk_list_item_manager_model_items_changed_cb (GListModel *model,
gtk_widget_queue_resize (self->widget);
}
static void
gtk_list_item_manager_model_sections_changed_cb (GListModel *model,
guint position,
guint n_items,
GtkListItemManager *self)
{
GtkListItemChange change;
GtkListTile *tile, *header;
guint offset;
if (!gtk_list_item_manager_has_sections (self))
return;
gtk_list_item_change_init (&change);
tile = gtk_list_item_manager_get_nth (self, position, &offset);
header = gtk_list_tile_get_header (self, tile);
gtk_list_item_change_clear_header (&change, &header->widget);
gtk_list_tile_set_type (header, GTK_LIST_TILE_UNMATCHED_HEADER);
n_items -= MIN (n_items, position - offset);
while (n_items > 0)
{
switch (tile->type)
{
case GTK_LIST_TILE_HEADER:
case GTK_LIST_TILE_UNMATCHED_HEADER:
gtk_list_item_change_clear_header (&change, &tile->widget);
gtk_list_tile_set_type (tile, GTK_LIST_TILE_REMOVED);
break;
case GTK_LIST_TILE_FOOTER:
case GTK_LIST_TILE_UNMATCHED_FOOTER:
gtk_list_tile_set_type (tile, GTK_LIST_TILE_REMOVED);
break;
case GTK_LIST_TILE_ITEM:
n_items -= MIN (n_items, tile->n_items);
break;
case GTK_LIST_TILE_REMOVED:
default:
g_assert_not_reached ();
break;
}
tile = gtk_list_tile_get_next_skip (tile);
}
if (!gtk_list_tile_is_footer (tile))
tile = gtk_list_tile_get_footer (self, tile);
gtk_list_tile_set_type (tile, GTK_LIST_TILE_UNMATCHED_FOOTER);
gtk_list_item_manager_ensure_items (self, &change, G_MAXUINT, 0);
gtk_list_item_change_finish (&change);
gtk_widget_queue_resize (GTK_WIDGET (self->widget));
}
static void
gtk_list_item_manager_model_selection_changed_cb (GListModel *model,
guint position,
@@ -1634,7 +1673,6 @@ static void
gtk_list_item_manager_clear_model (GtkListItemManager *self)
{
GtkListItemChange change;
GtkListTile *tile;
GSList *l;
if (self->model == NULL)
@@ -1654,15 +1692,13 @@ gtk_list_item_manager_clear_model (GtkListItemManager *self)
g_signal_handlers_disconnect_by_func (self->model,
gtk_list_item_manager_model_items_changed_cb,
self);
g_signal_handlers_disconnect_by_func (self->model,
gtk_list_item_manager_model_sections_changed_cb,
self);
g_clear_object (&self->model);
/* really empty the tiles */
for (tile = gtk_list_tile_gc (self, gtk_list_item_manager_get_first (self));
tile;
tile = gtk_list_tile_gc (self, tile))
{
g_assert (tile->type == GTK_LIST_TILE_FILLER);
}
gtk_list_item_manager_gc_tiles (self);
g_assert (gtk_rb_tree_get_root (self->items) == NULL);
}
@@ -1717,6 +1753,11 @@ gtk_list_item_manager_set_model (GtkListItemManager *self,
"selection-changed",
G_CALLBACK (gtk_list_item_manager_model_selection_changed_cb),
self);
if (GTK_IS_SECTION_MODEL (model))
g_signal_connect (model,
"sections-changed",
G_CALLBACK (gtk_list_item_manager_model_sections_changed_cb),
self);
gtk_list_item_change_init (&change);
gtk_list_item_manager_add_items (self, &change, 0, g_list_model_get_n_items (G_LIST_MODEL (model)));
@@ -1775,7 +1816,6 @@ gtk_list_item_manager_set_has_sections (GtkListItemManager *self,
footer = tile;
break;
case GTK_LIST_TILE_ITEM:
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
break;
default:
+13 -6
View File
@@ -51,7 +51,6 @@ typedef enum
GTK_LIST_TILE_FOOTER,
GTK_LIST_TILE_UNMATCHED_HEADER,
GTK_LIST_TILE_UNMATCHED_FOOTER,
GTK_LIST_TILE_FILLER,
GTK_LIST_TILE_REMOVED,
} GtkListTileType;
@@ -60,7 +59,7 @@ struct _GtkListTile
GtkListTileType type;
GtkWidget *widget;
guint n_items;
/* area occupied by tile. May be empty if tile has no allcoation */
/* area occupied by tile. May be empty if tile has no allocation */
cairo_rectangle_int_t area;
};
@@ -95,7 +94,19 @@ gpointer gtk_list_item_manager_get_nth (GtkListItemMana
GtkListTile * gtk_list_item_manager_get_nearest_tile (GtkListItemManager *self,
int x,
int y);
void gtk_list_item_manager_gc_tiles (GtkListItemManager *self);
static inline gboolean
gtk_list_tile_is_header (GtkListTile *tile)
{
return tile->type == GTK_LIST_TILE_HEADER || tile->type == GTK_LIST_TILE_UNMATCHED_HEADER;
}
static inline gboolean
gtk_list_tile_is_footer (GtkListTile *tile)
{
return tile->type == GTK_LIST_TILE_FOOTER || tile->type == GTK_LIST_TILE_UNMATCHED_FOOTER;
}
guint gtk_list_tile_get_position (GtkListItemManager *self,
GtkListTile *tile);
@@ -116,10 +127,6 @@ void gtk_list_tile_set_area_size (GtkListItemMana
GtkListTile * gtk_list_tile_split (GtkListItemManager *self,
GtkListTile *tile,
guint n_items);
GtkListTile * gtk_list_tile_append_filler (GtkListItemManager *self,
GtkListTile *previous);
GtkListTile * gtk_list_tile_gc (GtkListItemManager *self,
GtkListTile *tile);
void gtk_list_item_manager_set_model (GtkListItemManager *self,
GtkSelectionModel *model);
+7 -3
View File
@@ -235,7 +235,6 @@ gtk_list_view_update_factories_with (GtkListView *self,
case GTK_LIST_TILE_UNMATCHED_HEADER:
case GTK_LIST_TILE_FOOTER:
case GTK_LIST_TILE_UNMATCHED_FOOTER:
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
g_assert (tile->widget == NULL);
break;
@@ -609,8 +608,10 @@ gtk_list_view_size_allocate (GtkWidget *widget,
opposite_scroll_policy = gtk_list_base_get_scroll_policy (GTK_LIST_BASE (self), opposite_orientation);
gtk_list_base_get_border_spacing (GTK_LIST_BASE (self), NULL, &spacing);
gtk_list_item_manager_gc_tiles (self->item_manager);
/* step 0: exit early if list is empty */
tile = gtk_list_tile_gc (self->item_manager, gtk_list_item_manager_get_first (self->item_manager));
tile = gtk_list_item_manager_get_first (self->item_manager);
if (tile == NULL)
{
gtk_list_base_allocate (GTK_LIST_BASE (self));
@@ -632,7 +633,7 @@ gtk_list_view_size_allocate (GtkWidget *widget,
for (;
tile != NULL;
tile = gtk_list_tile_gc (self->item_manager, gtk_rb_tree_node_get_next (tile)))
tile = gtk_rb_tree_node_get_next (tile))
{
if (tile->widget == NULL)
continue;
@@ -726,6 +727,9 @@ gtk_list_view_dispose (GObject *object)
self->item_manager = NULL;
g_clear_object (&self->factory);
g_clear_object (&self->header_factory);
G_OBJECT_CLASS (gtk_list_view_parent_class)->dispose (object);
}
+1 -2
View File
@@ -42,12 +42,11 @@ BOOLEAN:OBJECT,OBJECT,OBJECT
BOOLEAN:STRING
BOOLEAN:UINT,UINT,FLAGS
BOOLEAN:VOID
ENUM:OBJECT,DOUBLE,DOUBLE
FLAGS:OBJECT,DOUBLE,DOUBLE
FLAGS:DOUBLE,DOUBLE
INT:INT
INT:OBJECT,OBJECT,POINTER
INT:POINTER
OBJECT:BOOLEAN
OBJECT:DOUBLE,DOUBLE
OBJECT:OBJECT
OBJECT:VOID
+6 -3
View File
@@ -1094,6 +1094,7 @@ gtk_menu_button_get_icon_name (GtkMenuButton *menu_button)
* gtk_menu_button_set_always_show_arrow: (attributes org.gtk.Method.set_property=always-show-arrow)
* @menu_button: a `GtkMenuButton`
* @always_show_arrow: whether to show a dropdown arrow even when using an icon
* or a custom child
*
* Sets whether to show a dropdown arrow even when using an icon or a custom
* child.
@@ -1122,9 +1123,11 @@ gtk_menu_button_set_always_show_arrow (GtkMenuButton *menu_button,
* gtk_menu_button_get_always_show_arrow: (attributes org.gtk.Method.get_property=always-show-arrow)
* @menu_button: a `GtkMenuButton`
*
* Gets whether to show a dropdown arrow even when using an icon.
* Gets whether to show a dropdown arrow even when using an icon or a custom
* child.
*
* Returns: whether to show a dropdown arrow even when using an icon
* Returns: whether to show a dropdown arrow even when using an icon or a custom
* child.
*
* Since: 4.4
*/
@@ -1554,7 +1557,7 @@ gtk_menu_button_get_child (GtkMenuButton *menu_button)
* @menu_button: a `GtkMenuButton`
* @active: whether the menu button is active
*
* Sets whether menu button acts is active.
* Sets whether the menu button is active.
*
* Since: 4.10
*/
+1 -1
View File
@@ -664,7 +664,7 @@ gtk_menu_section_box_new_section (GtkMenuTrackerItem *item,
gtk_orientable_set_orientation (GTK_ORIENTABLE (box->item_box), GTK_ORIENTATION_HORIZONTAL);
gtk_widget_add_css_class (GTK_WIDGET (box->item_box), "inline-buttons");
spacer = gtk_builtin_icon_new ("none");
spacer = gtk_gizmo_new ("none", NULL, NULL, NULL,NULL, NULL, NULL);
gtk_box_append (GTK_BOX (box->item_box), spacer);
gtk_size_group_add_widget (box->indicators, spacer);
+17
View File
@@ -291,6 +291,17 @@ gtk_multi_selection_items_changed_cb (GListModel *model,
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_N_ITEMS]);
}
static void
gtk_multi_selection_sections_changed_cb (GtkSectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkMultiSelection *self = GTK_MULTI_SELECTION (user_data);
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), position, n_items);
}
static void
gtk_multi_selection_clear_model (GtkMultiSelection *self)
{
@@ -300,6 +311,9 @@ gtk_multi_selection_clear_model (GtkMultiSelection *self)
g_signal_handlers_disconnect_by_func (self->model,
gtk_multi_selection_items_changed_cb,
self);
g_signal_handlers_disconnect_by_func (self->model,
gtk_multi_selection_sections_changed_cb,
self);
g_clear_object (&self->model);
}
@@ -490,6 +504,9 @@ gtk_multi_selection_set_model (GtkMultiSelection *self,
"items-changed",
G_CALLBACK (gtk_multi_selection_items_changed_cb),
self);
if (GTK_IS_SECTION_MODEL (self->model))
g_signal_connect (self->model, "sections-changed",
G_CALLBACK (gtk_multi_selection_sections_changed_cb), self);
gtk_multi_selection_items_changed_cb (self->model,
0,
n_items_before,
+20 -1
View File
@@ -33,6 +33,8 @@
*
* This model is meant to be used as a simple wrapper around a `GListModel`
* when a `GtkSelectionModel` is required.
*
* `GtkNoSelection` passes through sections from the underlying model.
*/
struct _GtkNoSelection
{
@@ -152,15 +154,29 @@ gtk_no_selection_items_changed_cb (GListModel *model,
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_N_ITEMS]);
}
static void
gtk_no_selection_sections_changed_cb (GtkSectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkNoSelection *self = GTK_NO_SELECTION (user_data);
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), position, n_items);
}
static void
gtk_no_selection_clear_model (GtkNoSelection *self)
{
if (self->model == NULL)
return;
g_signal_handlers_disconnect_by_func (self->model,
g_signal_handlers_disconnect_by_func (self->model,
gtk_no_selection_items_changed_cb,
self);
g_signal_handlers_disconnect_by_func (self->model,
gtk_no_selection_sections_changed_cb,
self);
g_clear_object (&self->model);
}
@@ -345,6 +361,9 @@ gtk_no_selection_set_model (GtkNoSelection *self,
self->model = g_object_ref (model);
g_signal_connect (self->model, "items-changed",
G_CALLBACK (gtk_no_selection_items_changed_cb), self);
if (GTK_IS_SECTION_MODEL (self->model))
g_signal_connect (self->model, "sections-changed",
G_CALLBACK (gtk_no_selection_sections_changed_cb), self);
n_items_after = g_list_model_get_n_items (self->model);
}
else
+9 -8
View File
@@ -483,6 +483,7 @@ create_popup_layout (GtkPopover *popover)
GdkPopupLayout *layout;
GtkCssStyle *style;
GtkBorder shadow_width;
gboolean ltr = gtk_widget_get_direction (GTK_WIDGET (popover)) != GTK_TEXT_DIR_RTL;
compute_surface_pointing_to (popover, &rect);
@@ -545,13 +546,13 @@ create_popup_layout (GtkPopover *popover)
switch (gtk_widget_get_halign (GTK_WIDGET (popover)))
{
case GTK_ALIGN_START:
parent_anchor = GDK_GRAVITY_NORTH_WEST;
surface_anchor = GDK_GRAVITY_SOUTH_WEST;
parent_anchor = ltr ? GDK_GRAVITY_NORTH_WEST : GDK_GRAVITY_NORTH_EAST;
surface_anchor = ltr ? GDK_GRAVITY_SOUTH_WEST : GDK_GRAVITY_SOUTH_EAST;
break;
case GTK_ALIGN_END:
parent_anchor = GDK_GRAVITY_NORTH_EAST;
surface_anchor = GDK_GRAVITY_SOUTH_EAST;
parent_anchor = ltr ? GDK_GRAVITY_NORTH_EAST : GDK_GRAVITY_NORTH_WEST;
surface_anchor = ltr ? GDK_GRAVITY_SOUTH_EAST : GDK_GRAVITY_SOUTH_WEST;
break;
case GTK_ALIGN_FILL:
@@ -570,13 +571,13 @@ create_popup_layout (GtkPopover *popover)
switch (gtk_widget_get_halign (GTK_WIDGET (popover)))
{
case GTK_ALIGN_START:
parent_anchor = GDK_GRAVITY_SOUTH_WEST;
surface_anchor = GDK_GRAVITY_NORTH_WEST;
parent_anchor = ltr ? GDK_GRAVITY_SOUTH_WEST : GDK_GRAVITY_SOUTH_EAST;
surface_anchor = ltr ? GDK_GRAVITY_NORTH_WEST : GDK_GRAVITY_NORTH_EAST;
break;
case GTK_ALIGN_END:
parent_anchor = GDK_GRAVITY_SOUTH_EAST;
surface_anchor = GDK_GRAVITY_NORTH_EAST;
parent_anchor = ltr ? GDK_GRAVITY_SOUTH_EAST : GDK_GRAVITY_SOUTH_WEST;
surface_anchor = ltr ? GDK_GRAVITY_NORTH_EAST : GDK_GRAVITY_NORTH_WEST;
break;
case GTK_ALIGN_FILL:
+1 -1
View File
@@ -1494,7 +1494,7 @@ create_application_page (GtkPrintOperation *op)
memset (&page, 0, sizeof (page));
page.dwSize = sizeof (page);
page.dwFlags = PSP_DLGINDIRECT | PSP_USETITLE | PSP_PREMATURE;
page.hInstance = GetModuleHandle (NULL);
page.hInstance = NULL;
page.pResource = template;
tab_label = op->priv->custom_tab_label;
+5 -1
View File
@@ -1431,6 +1431,7 @@ gtk_recent_manager_clamp_to_age (GtkRecentManager *manager,
}
g_strfreev (uris);
g_date_time_unref (now);
}
static void
@@ -2180,13 +2181,16 @@ gtk_recent_info_get_uri_display (GtkRecentInfo *info)
int
gtk_recent_info_get_age (GtkRecentInfo *info)
{
int diff;
GDateTime *now;
g_return_val_if_fail (info != NULL, -1);
now = g_date_time_new_now_utc ();
diff = (int) (g_date_time_difference (now, info->modified) / (double)G_TIME_SPAN_DAY);
return (int) (g_date_time_difference (now, info->modified) / (double)G_TIME_SPAN_DAY);
g_date_time_unref (now);
return diff;
}
/**
+31 -1
View File
@@ -1750,8 +1750,38 @@ gtk_scrolled_window_measure (GtkWidget *widget,
if (priv->child && gtk_widget_get_visible (priv->child))
{
int min_child_size, nat_child_size;
int child_for_size = -1;
gtk_widget_measure (priv->child, orientation, -1,
/* We can pass on the requested size if we have a scrollbar policy that prevents scrolling in that direction */
if ((orientation == GTK_ORIENTATION_VERTICAL && priv->hscrollbar_policy == GTK_POLICY_NEVER)
|| (orientation == GTK_ORIENTATION_HORIZONTAL && priv->vscrollbar_policy == GTK_POLICY_NEVER))
{
child_for_size = for_size;
/* If the other scrollbar is always visible and not an overlay scrollbar we must subtract it from the measure */
if (orientation == GTK_ORIENTATION_VERTICAL && !priv->use_indicators && priv->vscrollbar_policy == GTK_POLICY_ALWAYS)
{
int min_scrollbar_width;
gtk_widget_measure (priv->vscrollbar, GTK_ORIENTATION_HORIZONTAL, -1,
&min_scrollbar_width, NULL,
NULL, NULL);
child_for_size = MAX (0, child_for_size - min_scrollbar_width);
}
if (orientation == GTK_ORIENTATION_HORIZONTAL && !priv->use_indicators && priv->hscrollbar_policy == GTK_POLICY_ALWAYS)
{
int min_scrollbar_height;
gtk_widget_measure (priv->hscrollbar, GTK_ORIENTATION_VERTICAL, -1,
&min_scrollbar_height, NULL,
NULL, NULL);
child_for_size = MAX (0, child_for_size - min_scrollbar_height);
}
}
gtk_widget_measure (priv->child, orientation, child_for_size,
&min_child_size, &nat_child_size,
NULL, NULL);
+11 -12
View File
@@ -26,21 +26,19 @@
/**
* GtkSectionModel:
*
* `GtkSectionModel` is an interface that adds support for section to list models.
* `GtkSectionModel` is an interface that adds support for sections to list models.
*
* This support is then used by widgets using list models to be able to group their
* items into sections.
* A `GtkSectionModel` groups successive items into so-called sections. List widgets
* like `GtkListView` and `GtkGridView` then allow displaying section headers for
* these sections by installing a header factory.
*
* Many GTK list models support sections inherently, or they pass through the sections
* of a model they are wrapping.
*
* A `GtkSectionModel` groups successive items into so-called sections. List widgets
* like `GtkListView` then allow displaying section headers for these sections.
*
* When the section groupings of a model changes, the model will emit the
* When the section groupings of a model change, the model will emit the
* [signal@Gtk.SectionModel::sections-changed] signal by calling the
* [method@Gtk.SectionModel.sections_changed] function. All sections in the given range
* now need to be queried again.
* then need to be queried again.
* The [signal@Gio.ListModel::items-changed] signal has the same effect, all sections in
* that range are invalidated, too.
*
@@ -196,10 +194,11 @@ gtk_list_model_get_section (GListModel *self,
* @n_items: the number of changed items
*
* This function emits the [signal@Gtk.SectionModel::section-changed]
* signal to notify about changes to sections. It must cover all
* positions that used to be a section start or that are now a section
* start. It does not have to cover all positions for which the section
* has changed.
* signal to notify about changes to sections.
*
* It must cover all positions that used to be a section start or that
* are now a section start. It does not have to cover all positions for
* which the section has changed.
*
* The [signal@Gio.ListModel::items-changed] implies the effect of the
* [signal@Gtk.SectionModel::section-changed] signal for all the items
+19 -2
View File
@@ -300,15 +300,29 @@ gtk_single_selection_items_changed_cb (GListModel *model,
g_object_thaw_notify (G_OBJECT (self));
}
static void
gtk_single_selection_sections_changed_cb (GtkSectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkSingleSelection *self = GTK_SINGLE_SELECTION (user_data);
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), position, n_items);
}
static void
gtk_single_selection_clear_model (GtkSingleSelection *self)
{
if (self->model == NULL)
return;
g_signal_handlers_disconnect_by_func (self->model,
g_signal_handlers_disconnect_by_func (self->model,
gtk_single_selection_items_changed_cb,
self);
g_signal_handlers_disconnect_by_func (self->model,
gtk_single_selection_sections_changed_cb,
self);
g_clear_object (&self->model);
}
@@ -558,7 +572,7 @@ gtk_single_selection_set_model (GtkSingleSelection *self,
return;
g_object_freeze_notify (G_OBJECT (self));
n_items_before = self->model ? g_list_model_get_n_items (self->model) : 0;
gtk_single_selection_clear_model (self);
@@ -567,6 +581,9 @@ gtk_single_selection_set_model (GtkSingleSelection *self,
self->model = g_object_ref (model);
g_signal_connect (self->model, "items-changed",
G_CALLBACK (gtk_single_selection_items_changed_cb), self);
if (GTK_IS_SECTION_MODEL (self->model))
g_signal_connect (self->model, "sections-changed",
G_CALLBACK (gtk_single_selection_sections_changed_cb), self);
gtk_single_selection_items_changed_cb (self->model,
0,
n_items_before,
+69 -3
View File
@@ -20,6 +20,7 @@
#include "config.h"
#include "gtkslicelistmodel.h"
#include "gtksectionmodelprivate.h"
#include "gtkprivate.h"
@@ -31,6 +32,8 @@
* This is useful when implementing paging by setting the size to the number
* of elements per page and updating the offset whenever a different page is
* opened.
*
* `GtkSliceListModel` passes through sections from the underlying model.
*/
#define DEFAULT_SIZE 10
@@ -52,8 +55,6 @@ struct _GtkSliceListModel
GListModel *model;
guint offset;
guint size;
guint n_items;
};
struct _GtkSliceListModelClass
@@ -111,8 +112,69 @@ gtk_slice_list_model_model_init (GListModelInterface *iface)
iface->get_item = gtk_slice_list_model_get_item;
}
static void
gtk_slice_list_model_get_section (GtkSectionModel *model,
guint position,
guint *start,
guint *end)
{
GtkSliceListModel *self = GTK_SLICE_LIST_MODEL (model);
unsigned int n_items;
n_items = g_list_model_get_n_items (G_LIST_MODEL (self));
if (position >= n_items)
{
*start = n_items;
*end = G_MAXUINT;
}
else
{
gtk_list_model_get_section (self->model, position + self->offset, start, end);
*start = MAX (*start, self->offset) - self->offset;
*end = MIN (*end - self->offset, n_items);
}
}
static void
gtk_slice_list_model_sections_changed_cb (GtkSectionModel *model,
unsigned int position,
unsigned int n_items,
gpointer user_data)
{
GtkSliceListModel *self = GTK_SLICE_LIST_MODEL (user_data);
unsigned int start = position;
unsigned int end = position + n_items;
unsigned int size;
if (end <= self->offset)
return;
size = g_list_model_get_n_items (G_LIST_MODEL (self));
end = MIN (end - self->offset, size);
if (start <= self->offset)
start = 0;
else
start = start - self->offset;
if (start >= size)
return;
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), start, end - start);
}
static void
gtk_slice_list_model_section_model_init (GtkSectionModelInterface *iface)
{
iface->get_section = gtk_slice_list_model_get_section;
}
G_DEFINE_TYPE_WITH_CODE (GtkSliceListModel, gtk_slice_list_model, G_TYPE_OBJECT,
G_IMPLEMENT_INTERFACE (G_TYPE_LIST_MODEL, gtk_slice_list_model_model_init))
G_IMPLEMENT_INTERFACE (G_TYPE_LIST_MODEL, gtk_slice_list_model_model_init)
G_IMPLEMENT_INTERFACE (GTK_TYPE_SECTION_MODEL, gtk_slice_list_model_section_model_init))
static void
gtk_slice_list_model_items_changed_cb (GListModel *model,
@@ -238,6 +300,7 @@ gtk_slice_list_model_clear_model (GtkSliceListModel *self)
if (self->model == NULL)
return;
g_signal_handlers_disconnect_by_func (self->model, gtk_slice_list_model_sections_changed_cb, self);
g_signal_handlers_disconnect_by_func (self->model, gtk_slice_list_model_items_changed_cb, self);
g_clear_object (&self->model);
}
@@ -387,6 +450,9 @@ gtk_slice_list_model_set_model (GtkSliceListModel *self,
self->model = g_object_ref (model);
g_signal_connect (model, "items-changed", G_CALLBACK (gtk_slice_list_model_items_changed_cb), self);
added = g_list_model_get_n_items (G_LIST_MODEL (self));
if (GTK_IS_SECTION_MODEL (model))
g_signal_connect (model, "sections-changed", G_CALLBACK (gtk_slice_list_model_sections_changed_cb), self);
}
else
{
+36 -19
View File
@@ -873,9 +873,10 @@ gtk_sort_list_model_get_property (GObject *object,
}
static void
gtk_sort_list_model_sorter_changed_cb (GtkSorter *sorter,
int change,
GtkSortListModel *self)
gtk_sort_list_model_sorter_changed (GtkSorter *sorter,
int change,
GtkSortListModel *self,
gboolean sections_changed)
{
guint pos, n_items;
@@ -912,6 +913,12 @@ gtk_sort_list_model_sorter_changed_cb (GtkSorter *sorter,
}
}
if (self->section_sorter)
{
gtk_sort_keys_unref (self->section_sort_keys);
self->section_sort_keys = gtk_sorter_get_keys (self->section_sorter);
}
if (gtk_sort_list_model_start_sorting (self, NULL))
pos = n_items = 0;
else
@@ -922,8 +929,25 @@ gtk_sort_list_model_sorter_changed_cb (GtkSorter *sorter,
gtk_sort_list_model_clear_items (self, &pos, &n_items);
}
if (n_items > 0)
g_list_model_items_changed (G_LIST_MODEL (self), pos, n_items, n_items);
if (sections_changed && self->n_items > 0)
{
if (n_items > 0)
g_list_model_items_changed (G_LIST_MODEL (self), 0, self->n_items, self->n_items);
else
gtk_section_model_sections_changed (GTK_SECTION_MODEL (self), 0, self->n_items);
}
else if (n_items > 0)
{
g_list_model_items_changed (G_LIST_MODEL (self), pos, n_items, n_items);
}
}
static void
gtk_sort_list_model_sorter_changed_cb (GtkSorter *sorter,
int change,
GtkSortListModel *self)
{
gtk_sort_list_model_sorter_changed (sorter, change, self, FALSE);
}
static void
@@ -949,7 +973,8 @@ gtk_sort_list_model_clear_real_sorter (GtkSortListModel *self)
}
static void
gtk_sort_list_model_ensure_real_sorter (GtkSortListModel *self)
gtk_sort_list_model_ensure_real_sorter (GtkSortListModel *self,
gboolean sections_changed)
{
if (self->sorter)
{
@@ -974,7 +999,7 @@ gtk_sort_list_model_ensure_real_sorter (GtkSortListModel *self)
if (self->real_sorter)
g_signal_connect (self->real_sorter, "changed", G_CALLBACK (gtk_sort_list_model_sorter_changed_cb), self);
gtk_sort_list_model_sorter_changed_cb (self->real_sorter, GTK_SORTER_CHANGE_DIFFERENT, self);
gtk_sort_list_model_sorter_changed (self->real_sorter, GTK_SORTER_CHANGE_DIFFERENT, self, sections_changed);
}
static void
@@ -1195,12 +1220,8 @@ gtk_sort_list_model_set_sorter (GtkSortListModel *self,
return;
gtk_sort_list_model_clear_real_sorter (self);
g_clear_object (&self->sorter);
if (sorter)
self->sorter = g_object_ref (sorter);
gtk_sort_list_model_ensure_real_sorter (self);
g_set_object (&self->sorter, sorter);
gtk_sort_list_model_ensure_real_sorter (self, FALSE);
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_SORTER]);
}
@@ -1241,12 +1262,8 @@ gtk_sort_list_model_set_section_sorter (GtkSortListModel *self,
return;
gtk_sort_list_model_clear_real_sorter (self);
g_clear_object (&self->section_sorter);
if (sorter)
self->section_sorter = g_object_ref (sorter);
gtk_sort_list_model_ensure_real_sorter (self);
g_set_object (&self->section_sorter, sorter);
gtk_sort_list_model_ensure_real_sorter (self, TRUE);
g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_SECTION_SORTER]);
}
+5 -2
View File
@@ -809,9 +809,12 @@ gtk_stack_accessible_get_first_accessible_child (GtkAccessible *accessible)
{
GtkStack *stack = GTK_STACK (accessible);
GtkStackPrivate *priv = gtk_stack_get_instance_private (stack);
GtkStackPage *page = g_ptr_array_index (priv->children, 0);
GtkAccessible *page_accessible = NULL;
return GTK_ACCESSIBLE (g_object_ref (page));
if (priv->children->len > 0)
page_accessible = GTK_ACCESSIBLE (g_object_ref (g_ptr_array_index (priv->children, 0)));
return page_accessible;
}
static void
-1
View File
@@ -47,7 +47,6 @@
#include "gtkmain.h"
#include "gtkmarshalers.h"
#include "gtknative.h"
#include "gtkpopover.h"
#include "gtkprivate.h"
#include "gtkrenderbackgroundprivate.h"
#include "gtkrenderborderprivate.h"
+16 -35
View File
@@ -33,38 +33,19 @@
#include <commctrl.h>
#undef STRICT
extern IMAGE_DOS_HEADER __ImageBase;
static inline HMODULE
this_module ()
{
return (HMODULE) &__ImageBase;
}
/* In practice, resulting DLL will have manifest resource under index 2.
* Fall back to that value if we can't find resource index programmatically.
*/
#define EMPIRIC_MANIFEST_RESOURCE_INDEX 2
static HMODULE gtk_dll;
extern HINSTANCE _gdk_dll_hinstance;
BOOL WINAPI
DllMain (HINSTANCE hinstDLL,
DWORD fdwReason,
LPVOID lpvReserved);
BOOL WINAPI
DllMain (HINSTANCE hinstDLL,
DWORD fdwReason,
LPVOID lpvReserved)
{
switch (fdwReason)
{
case DLL_PROCESS_ATTACH:
gtk_dll = (HMODULE) hinstDLL;
_gdk_dll_hinstance = hinstDLL;
break;
default:
break;
}
return TRUE;
}
static BOOL CALLBACK
find_first_manifest (HMODULE module_handle,
LPCSTR resource_type,
@@ -111,7 +92,7 @@ _gtk_load_dll_with_libgtk3_manifest (const char *dll_name)
DWORD error_code;
resource_name = NULL;
EnumResourceNames (gtk_dll, RT_MANIFEST, find_first_manifest,
EnumResourceNames (this_module (), RT_MANIFEST, find_first_manifest,
(LONG_PTR) &resource_name);
if (resource_name == NULL)
@@ -122,7 +103,7 @@ _gtk_load_dll_with_libgtk3_manifest (const char *dll_name)
activation_ctx_descriptor.dwFlags = ACTCTX_FLAG_RESOURCE_NAME_VALID |
ACTCTX_FLAG_HMODULE_VALID |
ACTCTX_FLAG_SET_PROCESS_DEFAULT;
activation_ctx_descriptor.hModule = gtk_dll;
activation_ctx_descriptor.hModule = this_module ();
activation_ctx_descriptor.lpResourceName = resource_name;
activation_ctx_handle = CreateActCtx (&activation_ctx_descriptor);
error_code = GetLastError ();
@@ -130,7 +111,7 @@ _gtk_load_dll_with_libgtk3_manifest (const char *dll_name)
if (activation_ctx_handle == INVALID_HANDLE_VALUE &&
error_code != ERROR_SXS_PROCESS_DEFAULT_ALREADY_SET)
g_warning ("Failed to CreateActCtx for module %p, resource %p: %lu",
gtk_dll, resource_name, GetLastError ());
this_module (), resource_name, GetLastError ());
else if (error_code != ERROR_SXS_PROCESS_DEFAULT_ALREADY_SET)
{
activation_cookie = 0;
@@ -157,7 +138,7 @@ _gtk_get_libdir (void)
static char *gtk_libdir = NULL;
if (gtk_libdir == NULL)
{
char *root = g_win32_get_package_installation_directory_of_module (gtk_dll);
char *root = g_win32_get_package_installation_directory_of_module (this_module ());
char *slash = strrchr (root, '\\');
if (slash != NULL &&
g_ascii_strcasecmp (slash + 1, ".libs") == 0)
@@ -188,7 +169,7 @@ _gtk_get_localedir (void)
while (*--p != '/')
;
root = g_win32_get_package_installation_directory_of_module (gtk_dll);
root = g_win32_get_package_installation_directory_of_module (this_module ());
temp = g_build_filename (root, p, NULL);
g_free (root);
@@ -207,7 +188,7 @@ _gtk_get_datadir (void)
static char *gtk_datadir = NULL;
if (gtk_datadir == NULL)
{
char *root = g_win32_get_package_installation_directory_of_module (gtk_dll);
char *root = g_win32_get_package_installation_directory_of_module (this_module ());
gtk_datadir = g_build_filename (root, "share", NULL);
g_free (root);
}
@@ -221,7 +202,7 @@ _gtk_get_sysconfdir (void)
static char *gtk_sysconfdir = NULL;
if (gtk_sysconfdir == NULL)
{
char *root = g_win32_get_package_installation_directory_of_module (gtk_dll);
char *root = g_win32_get_package_installation_directory_of_module (this_module ());
gtk_sysconfdir = g_build_filename (root, "etc", NULL);
g_free (root);
}
@@ -234,7 +215,7 @@ _gtk_get_data_prefix (void)
{
static char *gtk_data_prefix = NULL;
if (gtk_data_prefix == NULL)
gtk_data_prefix = g_win32_get_package_installation_directory_of_module (gtk_dll);
gtk_data_prefix = g_win32_get_package_installation_directory_of_module (this_module ());
return gtk_data_prefix;
}
+7 -1
View File
@@ -5947,6 +5947,9 @@ gtk_window_get_mnemonics_visible (GtkWindow *window)
* @setting: the new value
*
* Sets whether mnemonics are supposed to be visible.
*
* This property is maintained by GTK based on user input,
* and should not be set by applications.
*/
void
gtk_window_set_mnemonics_visible (GtkWindow *window,
@@ -6032,11 +6035,14 @@ unset_focus_visible (gpointer data)
}
/**
* gtk_window_set_focus_visible: (attributes org.gtk.MEthod.set_property=focus-visible)
* gtk_window_set_focus_visible: (attributes org.gtk.Method.set_property=focus-visible)
* @window: a `GtkWindow`
* @setting: the new value
*
* Sets whether focus rectangles are supposed to be visible.
*
* This property is maintained by GTK based on user input,
* and should not be set by applications.
*/
void
gtk_window_set_focus_visible (GtkWindow *window,
@@ -1,18 +1,19 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<assemblyIdentity
version="1.0.0.0"
processorArchitecture="@EXE_MANIFEST_ARCHITECTURE@"
name="libgtk3"
version="@GTK_MANIFEST_VERSION@"
processorArchitecture="*"
name="org.gnome.GTK"
type="win32"
/>
<description>GTK is a multi-platform GUI toolkit based on GObject</description>
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
processorArchitecture="@EXE_MANIFEST_ARCHITECTURE@"
processorArchitecture="*"
publicKeyToken="6595b64144ccf1df"
language="*"
/>
+6 -4
View File
@@ -1014,7 +1014,9 @@ gtkversion_cdata.set('GTK_VERSION', gtk_version)
gtkversion_cdata.set('GTK_API_VERSION', gtk_api_version)
if host_machine.system() == 'windows'
gtkversion_cdata.set('EXE_MANIFEST_ARCHITECTURE', '*')
v = gtk_binary_version.split('.')
gtk_manifest_version = '.'.join(v.get(0, '0'), v.get(1, '0'), v.get(2, '0'), v.get(3, '0'))
gtkversion_cdata.set('GTK_MANIFEST_VERSION', gtk_manifest_version)
endif
gtkversion = configure_file(input: 'gtkversion.h.in',
@@ -1097,8 +1099,8 @@ if win32_enabled
configuration: gtkversion_cdata,
)
win32_manifest = configure_file(input: 'libgtk4.manifest.in',
output: 'libgtk4.manifest',
win32_manifest = configure_file(input: 'libgtk.manifest.in',
output: 'libgtk.manifest',
configuration: gtkversion_cdata,
)
@@ -1195,7 +1197,7 @@ if build_gir
gdk_gir_inc = [ 'cairo-1.0', 'Gio-2.0', 'GdkPixbuf-2.0', 'Pango-1.0', 'PangoCairo-1.0' ]
gdk_gir = gnome.generate_gir(libgtk,
sources: gdk_public_headers + gdk_public_sources + [ gdkenum_h ],
sources: gdk_public_headers + gdk_deprecated_headers + gdk_public_sources + gdk_deprecated_sources + [ gdkenum_h ],
namespace: 'Gdk',
nsversion: gtk_api_version,
identifier_prefix: 'Gdk',
+1 -1
View File
@@ -4543,7 +4543,7 @@ void *convert_run_optimize(void *c, uint8_t typecode_original,
int long_ctr = 0;
uint64_t cur_word = c_qua_bitset->array[0];
int run_count = 0;
G_GNUC_UNUSED int run_count = 0;
while (true) {
while (cur_word == UINT64_C(0) &&
long_ctr < BITSET_CONTAINER_SIZE_IN_WORDS - 1)
+27 -27
View File
@@ -1,32 +1,32 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface domain="gtk40">
<object class="GtkSingleSelection" id="selection">
<signal name="notify::selected-item" handler="selection_changed_cb" object="GtkFontChooserWidget" swapped="0"/>
<signal name="items-changed" handler="rows_changed_cb" object="GtkFontChooserWidget" swapped="1"/>
<property name="model">
<object class="GtkFilterListModel" id="filter_model">
<signal name="notify::pending" handler="rows_changed_cb" object="GtkFontChooserWidget" swapped="1"/>
<property name="incremental">1</property>
<property name="filter">
<object class="GtkEveryFilter" id="multi_filter">
<child>
<object class="GtkStringFilter">
<binding name="search">
<lookup name="text">search_entry</lookup>
</binding>
<property name="expression">
<closure type="gchararray" swapped="1" function="get_font_name"/>
</property>
</object>
</child>
<child>
<object class="GtkCustomFilter" id="custom_filter"/>
</child>
<child>
<object class="GtkCustomFilter" id="user_filter"/>
</child>
<object class="GtkFilterListModel" id="filter_model">
<signal name="notify::pending" handler="rows_changed_cb" object="GtkFontChooserWidget" swapped="1"/>
<property name="incremental">1</property>
<property name="filter">
<object class="GtkEveryFilter" id="multi_filter">
<child>
<object class="GtkStringFilter">
<binding name="search">
<lookup name="text">search_entry</lookup>
</binding>
<property name="expression">
<closure type="gchararray" swapped="1" function="get_font_name"/>
</property>
</object>
</property>
</child>
<child>
<object class="GtkCustomFilter" id="custom_filter"/>
</child>
<child>
<object class="GtkCustomFilter" id="user_filter"/>
</child>
</object>
</property>
<property name="model">
<object class="GtkSingleSelection" id="selection">
<signal name="notify::selected-item" handler="selection_changed_cb" object="GtkFontChooserWidget" swapped="0"/>
<signal name="items-changed" handler="rows_changed_cb" object="GtkFontChooserWidget" swapped="1"/>
</object>
</property>
</object>
@@ -141,7 +141,7 @@
<property name="has-frame">1</property>
<child>
<object class="GtkListView" id="family_face_list">
<property name="model">selection</property>
<property name="model">filter_model</property>
<signal name="activate" handler="row_activated_cb" swapped="no"/>
<property name="factory">
<object class="GtkBuilderListItemFactory">
+3 -3
View File
@@ -96,9 +96,9 @@ struct _GtkCupsRequest
char *password;
char *username;
int own_http : 1;
int need_password : 1;
int need_auth_info : 1;
unsigned int own_http : 1;
unsigned int need_password : 1;
unsigned int need_auth_info : 1;
char **auth_info_required;
char **auth_info;
GtkCupsPasswordState password_state;
+18 -22
View File
@@ -35,7 +35,7 @@ msgstr ""
"Project-Id-Version: gtk+ 2.8.2\n"
"Report-Msgid-Bugs-To: https://gitlab.gnome.org/GNOME/gtk/-/issues/\n"
"POT-Creation-Date: 2023-05-12 13:13+0000\n"
"PO-Revision-Date: 2023-05-12 11:18+0100\n"
"PO-Revision-Date: 2023-05-30 11:18+0100\n"
"Last-Translator: Jordi Mas i Hernàndez <jmas@softcatala.org>\n"
"Language-Team: Catalan <tradgnome@softcatala.org>\n"
"Language: ca\n"
@@ -3275,44 +3275,52 @@ msgid "Initial state"
msgstr "Estat inicial"
#: gtk/gtkprintoperation.c:1684
# N.T.: Usat com a nom de pestanya
msgctxt "print operation status"
msgid "Preparing to print"
msgstr "S'està preparant per a imprimir"
msgstr "Preparant-se per a imprimir"
#: gtk/gtkprintoperation.c:1685
# N.T.: Usat com a nom de pestanya
msgctxt "print operation status"
msgid "Generating data"
msgstr "S'estan generant les dades"
msgstr "Generant les dades"
#: gtk/gtkprintoperation.c:1686
# N.T.: Usat com a nom de pestanya
msgctxt "print operation status"
msgid "Sending data"
msgstr "S'estan enviant les dades"
msgstr "Enviant les dades"
#: gtk/gtkprintoperation.c:1687
# N.T.: Usat com a nom de pestanya
msgctxt "print operation status"
msgid "Waiting"
msgstr "S'està esperant"
msgstr "Esperant"
# N.T.: Usat com a nom de pestanya
#: gtk/gtkprintoperation.c:1688
msgctxt "print operation status"
msgid "Blocking on issue"
msgstr "Bloquejat a causa d'un problema"
msgstr "Bloquejat per un problema"
# N.T.: Usat com a nom de pestanya
#: gtk/gtkprintoperation.c:1689
msgctxt "print operation status"
msgid "Printing"
msgstr "S'està imprimint"
msgstr "Imprimint"
# N.T.: Usat com a nom de pestanya
#: gtk/gtkprintoperation.c:1690
msgctxt "print operation status"
msgid "Finished"
msgstr "S'ha finalitzat"
msgstr "Finalitzat"
# N.T.: Usat com a nom de pestanya
#: gtk/gtkprintoperation.c:1691
msgctxt "print operation status"
msgid "Finished with error"
msgstr "S'ha finalitzat amb error"
msgstr "Finalitzat amb error"
#: gtk/gtkprintoperation.c:2234
#, c-format
@@ -6350,7 +6358,7 @@ msgstr "_Ordenació de les pàgines:"
#: gtk/ui/gtkprintunixdialog.ui:474
msgid "_Only print:"
msgstr "_Només imprimeix:"
msgstr "_Imprimeix només:"
#: gtk/ui/gtkprintunixdialog.ui:490
msgid "All sheets"
@@ -7431,15 +7439,3 @@ msgstr ""
"No hi ha el fitxer índex de tema a «%s».\n"
"Si realment voleu crear una memòria cau d'icones aquí, utilitzeu --ignore-theme-index.\n"
#~ msgid "Tab"
#~ msgstr "Pestanya"
# FIXME
#~ msgid "Print to LPR"
#~ msgstr "Imprimeix a LPR"
#~ msgid "Pages Per Sheet"
#~ msgstr "Pàgines per full"
#~ msgid "Command Line"
#~ msgstr "Línia d'ordres"
+330 -315
View File
File diff suppressed because it is too large Load Diff
+251 -237
View File
File diff suppressed because it is too large Load Diff
+231 -209
View File
File diff suppressed because it is too large Load Diff
+1
View File
@@ -1,5 +1,6 @@
gtk_tests = [
# testname, optional extra sources
['testsections'],
['testfilelauncher'],
['input'],
['testpopup'],
+389
View File
@@ -0,0 +1,389 @@
#include <gtk/gtk.h>
static void
setup_item (GtkSignalListItemFactory *self,
GObject *object)
{
GtkListItem *list_item = GTK_LIST_ITEM (object);
GtkWidget *child = gtk_label_new ("");
gtk_label_set_xalign (GTK_LABEL (child), 0);
gtk_list_item_set_child (list_item, child);
}
static void
bind_item (GtkSignalListItemFactory *self,
GObject *object)
{
GtkListItem *list_item = GTK_LIST_ITEM (object);
GObject *item = gtk_list_item_get_item (list_item);
GtkWidget *child = gtk_list_item_get_child (list_item);
gtk_label_set_label (GTK_LABEL (child),
gtk_string_object_get_string (GTK_STRING_OBJECT (item)));
}
static char *
reverse_word (const char *word)
{
GString *s = g_string_new ("");
const char *p;
gunichar c;
gboolean capitalize;
capitalize = g_unichar_isupper (g_utf8_get_char (word));
p = word + strlen (word);
while ((p = g_utf8_find_prev_char (word, p)) != NULL)
{
c = g_utf8_get_char (p);
if (s->len == 0 && capitalize)
c = g_unichar_toupper (c);
else
c = g_unichar_tolower (c);
g_string_append_unichar (s, c);
}
return g_string_free (s, FALSE);
}
static void
bind_item_reverse (GtkSignalListItemFactory *self,
GObject *object)
{
GtkListItem *list_item = GTK_LIST_ITEM (object);
GObject *item = gtk_list_item_get_item (list_item);
GtkWidget *child = gtk_list_item_get_child (list_item);
char *word;
word = reverse_word (gtk_string_object_get_string (GTK_STRING_OBJECT (item)));
gtk_label_set_label (GTK_LABEL (child), word);
g_free (word);
}
static void
setup_header (GtkSignalListItemFactory *self,
GObject *object)
{
GtkListHeader *header = GTK_LIST_HEADER (object);
GtkWidget *child = gtk_label_new ("");
gtk_label_set_xalign (GTK_LABEL (child), 0);
gtk_list_header_set_child (header, child);
}
static char *
get_first (GObject *this)
{
const char *s = gtk_string_object_get_string (GTK_STRING_OBJECT (this));
char buffer[6] = { 0, };
g_unichar_to_utf8 (g_unichar_toupper (g_utf8_get_char (s)), buffer);
return g_strdup (buffer);
}
static void
bind_header (GtkSignalListItemFactory *self,
GObject *object)
{
GtkListHeader *header = GTK_LIST_HEADER (object);
GObject *item = gtk_list_header_get_item (header);
GtkWidget *child = gtk_list_header_get_child (header);
PangoAttrList *attrs;
char *string;
string = get_first (item);
gtk_label_set_label (GTK_LABEL (child), string);
attrs = pango_attr_list_new ();
pango_attr_list_insert (attrs, pango_attr_scale_new (PANGO_SCALE_X_LARGE));
pango_attr_list_insert (attrs, pango_attr_weight_new (PANGO_WEIGHT_BOLD));
gtk_label_set_attributes (GTK_LABEL (child), attrs);
pango_attr_list_unref (attrs);
g_free (string);
}
static const char *strings[] = {
"Alpha", "Andromeda", "Anaphylaxis", "Anaheim", "Beer", "Branch", "Botulism", "Banana",
"Bee", "Crane", "Caldera", "Copper", "Crowd", "Dora", "Dolphin", "Dam", "Ding",
NULL,
};
gboolean done_reading = FALSE;
static gboolean
dump_sections (gpointer data)
{
GtkSectionModel *model = data;
if (!done_reading)
return G_SOURCE_CONTINUE;
for (unsigned int i = 0; i < g_list_model_get_n_items (G_LIST_MODEL (model)); i++)
{
unsigned int s, e;
gtk_section_model_get_section (model, i, &s, &e);
g_print ("(%u %u)\n", s, e - 1);
i = e;
}
return G_SOURCE_REMOVE;
}
static void
read_lines_cb (GObject *object,
GAsyncResult *result,
gpointer data)
{
GBufferedInputStream *stream = G_BUFFERED_INPUT_STREAM (object);
GtkStringList *stringlist = data;
GError *error = NULL;
gsize size;
GPtrArray *lines;
gssize n_filled;
const char *buffer, *newline;
n_filled = g_buffered_input_stream_fill_finish (stream, result, &error);
if (n_filled < 0)
{
g_print ("Could not read data: %s\n", error->message);
g_clear_error (&error);
g_object_unref (stringlist);
return;
}
buffer = g_buffered_input_stream_peek_buffer (stream, &size);
if (n_filled == 0)
{
if (size)
gtk_string_list_take (stringlist, g_utf8_make_valid (buffer, size));
g_object_unref (stringlist);
done_reading = TRUE;
return;
}
lines = NULL;
while ((newline = memchr (buffer, '\n', size)))
{
if (newline > buffer)
{
if (lines == NULL)
lines = g_ptr_array_new_with_free_func (g_free);
g_ptr_array_add (lines, g_utf8_make_valid (buffer, newline - buffer));
}
if (g_input_stream_skip (G_INPUT_STREAM (stream), newline - buffer + 1, NULL, &error) < 0)
{
g_clear_error (&error);
break;
}
buffer = g_buffered_input_stream_peek_buffer (stream, &size);
}
if (lines == NULL)
{
g_buffered_input_stream_set_buffer_size (stream, g_buffered_input_stream_get_buffer_size (stream) + 4096);
}
else
{
g_ptr_array_add (lines, NULL);
gtk_string_list_splice (stringlist, g_list_model_get_n_items (G_LIST_MODEL (stringlist)), 0, (const char **) lines->pdata);
g_ptr_array_free (lines, TRUE);
}
g_buffered_input_stream_fill_async (stream, -1, G_PRIORITY_HIGH_IDLE, NULL, read_lines_cb, data);
}
static void
file_is_open_cb (GObject *file,
GAsyncResult *result,
gpointer data)
{
GError *error = NULL;
GFileInputStream *file_stream;
GBufferedInputStream *stream;
file_stream = g_file_read_finish (G_FILE (file), result, &error);
if (file_stream == NULL)
{
g_print ("Could not open file: %s\n", error->message);
g_error_free (error);
g_object_unref (data);
return;
}
stream = G_BUFFERED_INPUT_STREAM (g_buffered_input_stream_new (G_INPUT_STREAM (file_stream)));
g_buffered_input_stream_fill_async (stream, -1, G_PRIORITY_HIGH_IDLE, NULL, read_lines_cb, data);
g_object_unref (stream);
}
static void
load_file (GtkStringList *list,
GFile *file)
{
gtk_string_list_splice (list, 0, g_list_model_get_n_items (G_LIST_MODEL (list)), NULL);
g_file_read_async (file, G_PRIORITY_HIGH_IDLE, NULL, file_is_open_cb, g_object_ref (list));
}
static void
toggle_cb (GtkCheckButton *check, GtkWidget *list)
{
GtkListItemFactory *header_factory = NULL;
if (gtk_check_button_get_active (check))
{
header_factory = gtk_signal_list_item_factory_new ();
g_signal_connect (header_factory, "setup", G_CALLBACK (setup_header), NULL);
g_signal_connect (header_factory, "bind", G_CALLBACK (bind_header), NULL);
}
g_object_set (list, "header-factory", header_factory, NULL);
g_clear_object (&header_factory);
}
static void
value_changed_cb (GtkAdjustment *adj, gpointer data)
{
g_print ("horizontal adjustment changed to %f\n", gtk_adjustment_get_value (adj));
}
int
main (int argc, char *argv[])
{
GtkWidget *window;
GtkWidget *sw;
GtkWidget *lv;
GtkWidget *gv;
GtkWidget *cv;
GtkWidget *header;
GtkWidget *toggle;
GtkWidget *switcher;
GtkWidget *stack;
GtkListItemFactory *factory;
GtkExpression *expression;
GtkSortListModel *sortmodel;
GtkSelectionModel *selection;
GtkStringList *stringlist;
GtkAdjustment *adj;
GtkColumnViewColumn *column;
stringlist = gtk_string_list_new (NULL);
if (argc > 1)
{
GFile *file = g_file_new_for_commandline_arg (argv[1]);
load_file (stringlist, file);
g_object_unref (file);
}
else
{
for (int i = 0; strings[i]; i++)
gtk_string_list_append (stringlist, strings[i]);
done_reading = TRUE;
}
gtk_init ();
window = gtk_window_new ();
gtk_window_set_default_size (GTK_WINDOW (window), 800, 600);
header = gtk_header_bar_new ();
gtk_window_set_titlebar (GTK_WINDOW (window), header);
toggle = gtk_check_button_new ();
gtk_widget_set_valign (toggle, GTK_ALIGN_CENTER);
gtk_header_bar_pack_start (GTK_HEADER_BAR (header), toggle);
stack = gtk_stack_new ();
gtk_window_set_child (GTK_WINDOW (window), stack);
switcher = gtk_stack_switcher_new ();
gtk_header_bar_set_title_widget (GTK_HEADER_BAR (header), switcher);
gtk_stack_switcher_set_stack (GTK_STACK_SWITCHER (switcher), GTK_STACK (stack));
expression = gtk_property_expression_new (GTK_TYPE_STRING_OBJECT, NULL, "string");
sortmodel = gtk_sort_list_model_new (G_LIST_MODEL (stringlist),
GTK_SORTER (gtk_string_sorter_new (expression)));
expression = gtk_cclosure_expression_new (G_TYPE_STRING, NULL, 0, NULL, (GCallback) get_first, NULL, NULL);
gtk_sort_list_model_set_section_sorter (sortmodel, GTK_SORTER (gtk_string_sorter_new (expression)));
selection = GTK_SELECTION_MODEL (gtk_no_selection_new (G_LIST_MODEL (sortmodel)));
/* list */
sw = gtk_scrolled_window_new ();
gtk_stack_add_titled (GTK_STACK (stack), sw, "list", "List");
factory = gtk_signal_list_item_factory_new ();
g_signal_connect (factory, "setup", G_CALLBACK (setup_item), NULL);
g_signal_connect (factory, "bind", G_CALLBACK (bind_item), NULL);
lv = gtk_list_view_new (g_object_ref (selection), factory);
gtk_scrolled_window_set_child (GTK_SCROLLED_WINDOW (sw), lv);
g_signal_connect (toggle, "toggled", G_CALLBACK (toggle_cb), lv);
/* grid */
sw = gtk_scrolled_window_new ();
gtk_stack_add_titled (GTK_STACK (stack), sw, "grid", "Grid");
factory = gtk_signal_list_item_factory_new ();
g_signal_connect (factory, "setup", G_CALLBACK (setup_item), NULL);
g_signal_connect (factory, "bind", G_CALLBACK (bind_item), NULL);
gv = gtk_grid_view_new (g_object_ref (selection), factory);
gtk_scrolled_window_set_child (GTK_SCROLLED_WINDOW (sw), gv);
g_signal_connect (toggle, "toggled", G_CALLBACK (toggle_cb), gv);
gtk_grid_view_set_min_columns (GTK_GRID_VIEW (gv), 5);
adj = gtk_scrolled_window_get_hadjustment (GTK_SCROLLED_WINDOW (sw));
g_signal_connect (adj, "value-changed", G_CALLBACK (value_changed_cb), NULL);
/* columns */
sw = gtk_scrolled_window_new ();
gtk_stack_add_titled (GTK_STACK (stack), sw, "columns", "Columns");
cv = gtk_column_view_new (g_object_ref (selection));
gtk_scrolled_window_set_child (GTK_SCROLLED_WINDOW (sw), cv);
factory = gtk_signal_list_item_factory_new ();
g_signal_connect (factory, "setup", G_CALLBACK (setup_item), NULL);
g_signal_connect (factory, "bind", G_CALLBACK (bind_item), NULL);
column = gtk_column_view_column_new ("Word", factory);
gtk_column_view_append_column (GTK_COLUMN_VIEW (cv), column);
gtk_column_view_column_set_expand (column, TRUE);
gtk_column_view_column_set_resizable (column, TRUE);
g_object_unref (column);
factory = gtk_signal_list_item_factory_new ();
g_signal_connect (factory, "setup", G_CALLBACK (setup_item), NULL);
g_signal_connect (factory, "bind", G_CALLBACK (bind_item_reverse), NULL);
column = gtk_column_view_column_new ("Reverse", factory);
gtk_column_view_append_column (GTK_COLUMN_VIEW (cv), column);
gtk_column_view_column_set_expand (column, TRUE);
gtk_column_view_column_set_resizable (column, TRUE);
g_object_unref (column);
g_signal_connect (toggle, "toggled", G_CALLBACK (toggle_cb), cv);
gtk_window_present (GTK_WINDOW (window));
g_timeout_add (500, dump_sections, selection);
while (g_list_model_get_n_items (gtk_window_get_toplevels ()) > 0)
g_main_context_iteration (NULL, FALSE);
g_object_unref (selection);
return 0;
}
+4
View File
@@ -25,3 +25,7 @@ f {
g {
font-family: Macaroni al dente, Tomato sauce;
}
h {
font-family: 楷体;
}
+4
View File
@@ -25,3 +25,7 @@ f {
g {
font-family: "Macaroni al dente", "Tomato sauce";
}
h {
font-family: "楷体";
}
+6
View File
@@ -2,6 +2,7 @@
#include <epoxy/gl.h>
#include "gdk/gdktextureprivate.h"
#include "gdk/gdkglcontextprivate.h"
#include "gdk/gdkgltextureprivate.h"
static cairo_surface_t *
make_surface (void)
@@ -202,6 +203,11 @@ G_GNUC_END_IGNORE_DEPRECATIONS
texture = gdk_gl_texture_builder_build (builder, NULL, NULL);
g_assert_true (gdk_gl_texture_get_context (GDK_GL_TEXTURE (texture)) == context);
g_assert_true (gdk_gl_texture_get_id (GDK_GL_TEXTURE (texture)) == id);
g_assert_false (gdk_gl_texture_has_mipmap (GDK_GL_TEXTURE (texture)));
g_assert_true (gdk_gl_texture_get_sync (GDK_GL_TEXTURE (texture)) == sync);
data = g_malloc0 (64 * 64 * 4);
gdk_texture_download (texture, data, 64 * 4);
File diff suppressed because it is too large Load Diff
+55
View File
@@ -717,6 +717,60 @@ test_enabled (void)
g_object_unref (g_object_ref_sink (text));
}
#define MY_TYPE_GTK_ACTIONABLE (my_gtk_actionable_get_type ())
G_DECLARE_FINAL_TYPE (MyGtkActionable, my_gtk_actionable, MY, GTK_ACTIONABLE, GtkButton)
struct _MyGtkActionable
{
GtkButton parent_instance;
};
G_DEFINE_FINAL_TYPE (MyGtkActionable, my_gtk_actionable, GTK_TYPE_BUTTON);
static void
test_cb (GtkWidget *sender,
const char *name,
GVariant *param)
{
}
static void
my_gtk_actionable_init (MyGtkActionable *actionable)
{
gtk_actionable_set_action_name (GTK_ACTIONABLE (actionable), "test.test");
}
static void
my_gtk_actionable_class_init (MyGtkActionableClass *klass)
{
GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass);
gtk_widget_class_install_action (widget_class, "test.test", NULL, test_cb);
}
/* Test that actions are correctly notified after reparenting */
static void
test_reparenting (void)
{
GtkWidget *window, *actionable;
window = gtk_window_new ();
actionable = g_object_new (MY_TYPE_GTK_ACTIONABLE, NULL);
gtk_window_set_child (GTK_WINDOW (window), actionable);
g_assert_true (gtk_widget_get_sensitive (actionable));
g_object_ref (actionable);
gtk_window_set_child (GTK_WINDOW (window), NULL);
g_assert_false (gtk_widget_get_sensitive (actionable));
gtk_window_set_child (GTK_WINDOW (window), actionable);
g_object_unref (actionable);
g_assert_true (gtk_widget_get_sensitive (actionable));
g_object_unref (window);
}
int
main (int argc,
char *argv[])
@@ -732,6 +786,7 @@ main (int argc,
g_test_add_func ("/action/overlap2", test_overlap2);
g_test_add_func ("/action/introspection", test_introspection);
g_test_add_func ("/action/enabled", test_enabled);
g_test_add_func ("/action/reparenting", test_reparenting);
return g_test_run();
}
+1 -1
View File
@@ -1,4 +1,4 @@
/* GtkRBTree tests.
/* Bitmask tests.
*
* Copyright (C) 2011, Red Hat, Inc.
* Authors: Benjamin Otte <otte@gnome.org>
+1 -1
View File
@@ -1,4 +1,4 @@
/* GtkRBTree tests.
/* Bitset tests.
*
* Copyright (C) 2011, Red Hat, Inc.
* Authors: Benjamin Otte <otte@gnome.org>
+1 -1
View File
@@ -1,4 +1,4 @@
/* GtkRBTree tests.
/* Filter tests.
*
* Copyright (C) 2011, Red Hat, Inc.
* Authors: Benjamin Otte <otte@gnome.org>
+131 -1
View File
@@ -1,4 +1,4 @@
/* GtkRBTree tests.
/* Filterlistmodel tests.
*
* Copyright (C) 2011, Red Hat, Inc.
* Authors: Benjamin Otte <otte@gnome.org>
@@ -23,6 +23,7 @@
static GQuark number_quark;
static GQuark changes_quark;
static GQuark selection_quark;
static guint
get (GListModel *model,
@@ -52,6 +53,25 @@ model_to_string (GListModel *model)
return g_string_free (string, FALSE);
}
static char *
selection_to_string (GListModel *model)
{
GString *string = g_string_new (NULL);
guint i;
for (i = 0; i < g_list_model_get_n_items (model); i++)
{
if (!gtk_selection_model_is_selected (GTK_SELECTION_MODEL (model), i))
continue;
if (string->len > 0)
g_string_append (string, " ");
g_string_append_printf (string, "%u", get (model, i));
}
return g_string_free (string, FALSE);
}
static GListStore *
new_store (guint start,
guint end,
@@ -93,6 +113,14 @@ add (GListStore *store,
g_string_set_size (changes, 0); \
}G_STMT_END
#define assert_selection(model, expected) G_STMT_START{ \
char *s = selection_to_string (G_LIST_MODEL (model)); \
if (!g_str_equal (s, expected)) \
g_assertion_message_cmpstr (G_LOG_DOMAIN, __FILE__, __LINE__, G_STRFUNC, \
#model " == " #expected, s, "==", expected); \
g_free (s); \
}G_STMT_END
static GListStore *
new_empty_store (void)
{
@@ -478,6 +506,17 @@ filter_func (gpointer item,
return s[0] == s[1];
}
static void
sections_changed (GtkSectionModel *model,
unsigned int start,
unsigned int end,
gpointer user_data)
{
gboolean *got_it = user_data;
*got_it = TRUE;
}
static void
test_sections (void)
{
@@ -499,6 +538,7 @@ test_sections (void)
guint s, e;
GtkFilterListModel *filtered;
GtkFilter *filter;
gboolean got_it = FALSE;
list = gtk_string_list_new (strings);
sorter = GTK_SORTER (gtk_string_sorter_new (gtk_property_expression_new (GTK_TYPE_STRING_OBJECT, NULL, "string")));
@@ -541,10 +581,98 @@ test_sections (void)
g_assert_cmpint (s, ==, 3);
g_assert_cmpint (e, ==, 4);
g_signal_connect (filtered, "sections-changed", G_CALLBACK (sections_changed), &got_it);
gtk_sort_list_model_set_section_sorter (GTK_SORT_LIST_MODEL (sorted), NULL);
g_assert_true (got_it);
g_object_unref (filtered);
g_object_unref (sorted);
}
static void
selection_changed (GListModel *model,
guint position,
guint n_items,
GString *changes)
{
if (changes->len)
g_string_append (changes, ", ");
g_string_append_printf (changes, "%u:%u", position, n_items);
}
#define assert_selection_changes(model, expected) G_STMT_START{ \
GString *chchanges = g_object_get_qdata (G_OBJECT (model), selection_quark); \
if (!g_str_equal (chchanges->str, expected)) \
g_assertion_message_cmpstr (G_LOG_DOMAIN, __FILE__, __LINE__, G_STRFUNC, \
#model " == " #expected, changes->str, "==", expected); \
g_string_set_size (chchanges, 0); \
}G_STMT_END
static void
test_selections (void)
{
GListStore *store;
GtkSelectionModel *selection;
GtkFilter *filter;
GtkFilterListModel *filtermodel;
GString *changes;
store = new_store (1, 10, 1);
selection = GTK_SELECTION_MODEL (gtk_multi_selection_new (G_LIST_MODEL (store)));
filter = GTK_FILTER (gtk_custom_filter_new (is_larger_than, GUINT_TO_POINTER (5), NULL));
filtermodel = gtk_filter_list_model_new (G_LIST_MODEL (selection), filter);
changes = g_string_new ("");
g_object_set_qdata_full (G_OBJECT (filtermodel), selection_quark, changes, free_changes);
g_signal_connect (filtermodel, "selection-changed", G_CALLBACK (selection_changed), changes);
assert_selection (filtermodel, "");
g_assert_false (gtk_selection_model_is_selected (GTK_SELECTION_MODEL (filtermodel), 3));
gtk_selection_model_select_item (selection, 3, FALSE);
assert_selection (selection, "4");
assert_selection (filtermodel, "");
g_assert_false (gtk_selection_model_is_selected (GTK_SELECTION_MODEL (filtermodel), 3));
assert_selection_changes (filtermodel, "");
gtk_selection_model_select_item (selection, 8, FALSE);
assert_selection (selection, "4 9");
assert_selection (filtermodel, "9");
g_assert_true (gtk_selection_model_is_selected (GTK_SELECTION_MODEL (filtermodel), 3));
assert_selection_changes (filtermodel, "3:1");
gtk_selection_model_select_item (GTK_SELECTION_MODEL (filtermodel), 0, FALSE);
assert_selection (selection, "6 9");
assert_selection (filtermodel, "6 9");
assert_selection_changes (filtermodel, "0:1");
gtk_selection_model_select_item (GTK_SELECTION_MODEL (filtermodel), 1, TRUE);
assert_selection (selection, "7");
assert_selection (filtermodel, "7");
assert_selection_changes (filtermodel, "0:4");
gtk_selection_model_select_all (GTK_SELECTION_MODEL (filtermodel));
assert_selection (selection, "6 7 8 9 10");
assert_selection (filtermodel, "6 7 8 9 10");
assert_selection_changes (filtermodel, "0:5");
gtk_selection_model_unselect_range (GTK_SELECTION_MODEL (filtermodel), 1, 3);
assert_selection (selection, "6 10");
assert_selection (filtermodel, "6 10");
assert_selection_changes (filtermodel, "1:3");
gtk_selection_model_select_range (GTK_SELECTION_MODEL (filtermodel), 0, 3, TRUE);
assert_selection (selection, "6 7 8");
assert_selection (filtermodel, "6 7 8");
assert_selection_changes (filtermodel, "1:4");
g_object_unref (filtermodel);
}
int
main (int argc, char *argv[])
{
@@ -553,6 +681,7 @@ main (int argc, char *argv[])
number_quark = g_quark_from_static_string ("Hell and fire was spawned to be released.");
changes_quark = g_quark_from_static_string ("What did I see? Can I believe what I saw?");
selection_quark = g_quark_from_static_string ("Mana mana, badibidibi");
g_test_add_func ("/filterlistmodel/create", test_create);
g_test_add_func ("/filterlistmodel/empty_set_filter", test_empty_set_filter);
@@ -561,6 +690,7 @@ main (int argc, char *argv[])
g_test_add_func ("/filterlistmodel/empty", test_empty);
g_test_add_func ("/filterlistmodel/add_remove_item", test_add_remove_item);
g_test_add_func ("/filterlistmodel/sections", test_sections);
g_test_add_func ("/filterlistmodel/selections", test_selections);
return g_test_run ();
}
+1 -1
View File
@@ -1,4 +1,4 @@
/* GtkRBTree tests.
/* Flattenlistmodel tests.
*
* Copyright (C) 2011, Red Hat, Inc.
* Authors: Benjamin Otte <otte@gnome.org>
+25 -17
View File
@@ -71,9 +71,6 @@ print_list_item_manager_tiles (GtkListItemManager *items)
g_string_append_c (string, ')');
break;
case GTK_LIST_TILE_FILLER:
g_string_append_c (string, '_');
break;
case GTK_LIST_TILE_REMOVED:
g_string_append_c (string, '.');
break;
@@ -103,6 +100,7 @@ check_list_item_manager (GtkListItemManager *items,
MATCHED_SECTION,
UNMATCHED_SECTION
} section_state = NO_SECTION;
gboolean after_items = FALSE;
has_sections = gtk_list_item_manager_get_has_sections (items);
@@ -118,28 +116,32 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_true (has_sections);
g_assert_true (tile->widget);
section_state = MATCHED_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_UNMATCHED_HEADER:
g_assert_cmpint (section_state, ==, NO_SECTION);
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_false (tile->widget);
g_assert_null (tile->widget);
section_state = UNMATCHED_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_FOOTER:
g_assert_cmpint (section_state, ==, MATCHED_SECTION);
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_true (has_sections);
g_assert_false (tile->widget);
g_assert_null (tile->widget);
section_state = NO_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_UNMATCHED_FOOTER:
g_assert_cmpint (section_state, ==, UNMATCHED_SECTION);
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_false (tile->widget);
g_assert_null (tile->widget);
section_state = NO_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_ITEM:
@@ -155,19 +157,19 @@ check_list_item_manager (GtkListItemManager *items,
g_object_unref (item);
g_assert_cmpint (n_items, ==, gtk_list_item_base_get_position (GTK_LIST_ITEM_BASE (tile->widget)));
g_assert_cmpint (tile->n_items, ==, 1);
after_items = FALSE;
}
else
{
after_items = TRUE;
}
if (tile->n_items)
n_items += tile->n_items;
break;
case GTK_LIST_TILE_FILLER:
/* We don't add fillers */
g_assert_not_reached ();
break;
case GTK_LIST_TILE_REMOVED:
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_false (tile->widget);
g_assert_null (tile->widget);
break;
default:
@@ -192,10 +194,7 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_true (tile->widget);
}
for (tile = gtk_list_tile_gc (items, gtk_list_item_manager_get_first (items));
tile != NULL;
tile = gtk_list_tile_gc (items, gtk_rb_tree_node_get_next (tile)))
;
gtk_list_item_manager_gc_tiles (items);
n_items = 0;
@@ -211,6 +210,7 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_true (has_sections);
g_assert_true (tile->widget);
section_state = MATCHED_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_UNMATCHED_HEADER:
@@ -218,6 +218,7 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_false (tile->widget);
section_state = UNMATCHED_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_FOOTER:
@@ -226,6 +227,7 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_true (has_sections);
g_assert_false (tile->widget);
section_state = NO_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_UNMATCHED_FOOTER:
@@ -233,6 +235,7 @@ check_list_item_manager (GtkListItemManager *items,
g_assert_cmpint (tile->n_items, ==, 0);
g_assert_false (tile->widget);
section_state = NO_SECTION;
after_items = FALSE;
break;
case GTK_LIST_TILE_ITEM:
@@ -240,12 +243,17 @@ check_list_item_manager (GtkListItemManager *items,
if (tile->widget)
{
g_assert_cmpint (tile->n_items, ==, 1);
after_items = FALSE;
}
else
{
g_assert_false (after_items);
after_items = TRUE;
}
if (tile->n_items)
n_items += tile->n_items;
break;
case GTK_LIST_TILE_FILLER:
case GTK_LIST_TILE_REMOVED:
default:
g_assert_not_reached ();

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