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

feat: Add screenshot functionality #1258

Draft
wants to merge 8 commits into
base: dev
Choose a base branch
from

Conversation

atlanticaccent
Copy link
Contributor

Based on work in PR #226 - adds screenshot functionality to macOS, linux and Windows. Android is unsupported.

Compared to 226, this PR does not include the region selection functionality. This comment in the Webview2 repo indicates that it may now be possible to have parity across all three platforms in selecting regions, and so make it worthwhile to re-add.

This PR does not (yet) improve on the API presented in 226.

@andrewjanssen
Copy link

andrewjanssen commented Oct 24, 2024

I'm getting an EXC_BAD_ACCESS error when I call screenshot, on the following line. MacOS 15.0.1.

let image: id = msg_send![ns_image, CGImageForProposedRect:nil context:nil hints:nil];

This is crashing on A::invoke in:

pub unsafe fn send_unverified<T, A, R>(obj: *const T, sel: Sel, args: A) -> Result<R, MessageError>
where T: Message, A: MessageArguments, R: Any {
    let receiver = obj as *mut T as *mut Object;
    let msg_send_fn = msg_send_fn::<R>();
    objc_try!({
        A::invoke(msg_send_fn, receiver, sel, args)
    })
}

deprecated_screenshot runs successfully for me but the WebView doesn't appear in the screenshot: the image contains every window except the WebView. This is fixed by using only the kCGWindowListOptionIncludingWindow option and removing kCGWindowListOptionOnScreenAboveWindow and kCGWindowListExcludeDesktopElements. (It does capture the correct region, even after the WebView window is moved.)

Thanks for your work here!

@atlanticaccent
Copy link
Contributor Author

I'm getting an EXC_BAD_ACCESS error when I call screenshot, on the following line. MacOS 15.0.1.

let image: id = msg_send![ns_image, CGImageForProposedRect:nil context:nil hints:nil];

This is crashing on A::invoke in:

pub unsafe fn send_unverified<T, A, R>(obj: *const T, sel: Sel, args: A) -> Result<R, MessageError>
where T: Message, A: MessageArguments, R: Any {
    let receiver = obj as *mut T as *mut Object;
    let msg_send_fn = msg_send_fn::<R>();
    objc_try!({
        A::invoke(msg_send_fn, receiver, sel, args)
    })
}

deprecated_screenshot runs successfully for me but the WebView doesn't appear in the screenshot: the image contains every window except the WebView. This is fixed by using only the kCGWindowListOptionIncludingWindow option and removing kCGWindowListOptionOnScreenAboveWindow and kCGWindowListExcludeDesktopElements. (It does capture the correct region, even after the WebView window is moved.)

Thanks for your work here!

Hi! Yes, I pretty much gave up on the macOS implementation and in my own project currently have it disabled entirely. I believe I did have the "newer" version working at some point and lost it, or it might actually work right now but require granting the running application an Accessibility permission so it can capture properly - possibly both.

Either way, the performance is also catastrophic using either method, which further contributed to me abandoning the work.

I've since had some ideas about alternatives (grabbing the window handle and using something like wgpu to render the window texture to a usable image format), so I may come back to this PR if they work out/people are still interested in this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants