Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for incremental transfer of selections #275

Open
ghost opened this issue Apr 15, 2014 · 5 comments
Open

Add support for incremental transfer of selections #275

ghost opened this issue Apr 15, 2014 · 5 comments
Labels
bug Bug reports and bugfix pull requests verified Reproduced or otherwise verified bugs X11

Comments

@ghost
Copy link

ghost commented Apr 15, 2014

You can repro this with clipboard app from tests folder, here's a junk file of 262146 bytes, copy all of it and paste into window, you'll get:

Error: X11: Failed to convert selection to string
Clipboard does not contain a string
@elmindreda elmindreda added this to the 3.2 milestone Apr 16, 2014
@elmindreda elmindreda self-assigned this Apr 16, 2014
@elmindreda elmindreda changed the title Clipboard fails to get more than 262145 bytes of text (Arch Linux) Clipboard fails to get more than 262145 bytes of text Apr 16, 2014
@elmindreda
Copy link
Member

GLFW doesn't support incremental clipboard data transfer yet.

@elmindreda elmindreda changed the title Clipboard fails to get more than 262145 bytes of text Add support for incremental transfer of selections Jun 20, 2014
@elmindreda elmindreda modified the milestones: 3.2, 3.3 Feb 16, 2016
@elmindreda elmindreda added bug Bug reports and bugfix pull requests verified Reproduced or otherwise verified bugs and removed enhancement Feature suggestions and PRs labels Aug 7, 2017
@elmindreda
Copy link
Member

Note to self: UTF8_STRING

@CaffeineViking
Copy link

CaffeineViking commented Aug 9, 2017

I've been looking into this myself but I haven't been able to complete the implementation of it. Hopefully some of the experience in trying to implement it might be of use to someone else trying to do the same. In a nutshell, here is what happens and what ICCCM expects us to do to handle this INCR atom:

Below, when calling _glfwPlatformGetClipboardString is where X11 becomes very sad:

if (_glfwGetWindowPropertyX11(event.xselection.requestor,
                              event.xselection.property,
                              event.xselection.target,
                              (unsigned char**) &data))
    _glfw.x11.clipboardString = strdup(data);

And the reason is because we are requesting event.xselection.target of type UTF8_STRING, which will work most of the time, except when we have passed the selection owner's maximum allowed single-batch transfer size (262146 bytes in this case). The selection owner will instead give us an actualType of INCR which is not the same as the requested type UTF8_STRING. The owner wants to send data incrementally, i.e. in chunks of several XGetWindowPropertys containing UTF8_STRINGs.

To solve this we need to follow the ICCCM recommendation "INCR Properties". But in a nutshell:

  1. Get a handle to the INCR-atom with XInternAtom e.g. with the name INCR_STRING.
  2. See in _glfwGetWindowPropertyX11 if we received actualType of INCR_STRING, if so:
    a) Fetch INCR_STRING using XGetWindowProperty, it contains a lower transfer bound.
    b) Delete this INCR_STRING property so the owner can start sending us the good stuff.
    c) Wait for a PropertyNotify event, signaling arrival of a chunk of the full data.
    d) Retrieve chunk data using XGetWindowProperty, append it to a buffer.
    e) Delete the property, signaling owner to send additional chunks.
    f) Check if the size of the data is zero, if not loop back to c.
    g) Transfer complete, you now have the entire data!

If you are interested, here is a half-done implementation gist of incremental selections that I wrote.
Here are a couple of links that I found useful when looking into the issue:

Hopefully this is to some use to somebody, I wasn't able to figure it out myself unfortunately.

@elmindreda
Copy link
Member

elmindreda commented Aug 9, 2017

Thank you, that's an an excellent description! It's a little absurd what clients need to do to accomplish things that are a couple of function calls on other platforms.

I started implementing INCR two days ago. I have reading working, as well as conversion from STRING / Latin-1, but had a brief moment of despair when I realized that INCR, MULTIPLE and STRING can combine for writing. Some restructuring is in order before that can be implemented cleanly.

Pushed it just now to the selection-fixes branch if anyone wants a peek.

@elmindreda
Copy link
Member

elmindreda commented Aug 9, 2017

I need to focus on pull request reviews for a while. I've kept a lot of fine code waiting for a shameful a amount of time. If anyone wants to continue working on this in the meantime, based on code above or not, please do.

@elmindreda elmindreda removed their assignment Sep 1, 2017
elmindreda added a commit that referenced this issue Sep 17, 2017
This allows glfwGetClipboardString to retrieve clipboard contents larger
than (typically) 2^18 bytes.

Related to #275.
@elmindreda elmindreda modified the milestones: 3.3, 3.4 Oct 2, 2017
@elmindreda elmindreda removed this from the 3.4 milestone Dec 14, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Bug reports and bugfix pull requests verified Reproduced or otherwise verified bugs X11
Projects
None yet
Development

No branches or pull requests

2 participants