-
Notifications
You must be signed in to change notification settings - Fork 15k
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
Implementing offscreen rendering into External Textures #16961
Comments
👋 Thanks for opening your first issue here! If you're reporting a 🐞 bug, please make sure you include steps to reproduce it. We get a lot of issues on this repo, so please be patient and we will get back to you as soon as we can. To help make it easier for us to investigate your issue, please follow the contributing guidelines. |
Given that that this isn't currently on our roadmap, and in the interest of our issue tracker more closely reflecting our workstreams, i'm going to go ahead and label this a |
Allowing OSR with zero-copy texture sharing would open up at least two possibilities:
https://github.com/daktronics/cef-mixer
@ronhab Is there any chance we can start working on this? For realistic usage, feeding back into other-window within same electron app should be straight forward, In main process let hndl = offscreenBrowser.getTextureHandle(); //hndl works like nativeImage In other render process //hndl is sent via ipc
let texture = channel.getTextureFromHandle(hndl);
texture.asImg(); |
Any news on this one? |
It is hard, because all electron views are rendered by CPU (like popups) when offscreen mode is on. |
If anyone has any interest in opening a PR to address this, the rendering library used to manage the GPU buffer is Skia, and a good place to start would be here:
That's the line of code where the copy is done (hi @brenca). Perhaps a good design would be to add V8 native language bindings to toggle a boolean disabling that copy. Additionally, V8 API should be added that can help copy out the buffer's GPU info (get it from the Once the GPU buffer info is out, that can be passed to whatever rendering code via a NAPI/v8 bridge (which must be implemented by the user). Assuming the user uses something like D3D or Vulkan, some compatibility glue could be used to access the external OpenGL buffer, resulting in 0-copy buffer access to the rendered frames. I'd do this myself, but my company won't let me. I hope someone else can. This would really enable a lot of great applications that use a 3D-engine based frontend, but need the excellent framework the Electron folks here have made for authoring beautiful GUIs. @codebytere Given that I've presented a solution here, would it be possible to at least have an Electron dev validate this would work/provide additional guidance to anyone who endeavors to build it? I spitballed this after 30min of browsing a bit of code, but I'm not familiar with this codebase at all. |
any news here? |
Yes, indeed. In fact I just finished the feature at CEF side few hours ago, see: https://chromium-review.googlesource.com/c/chromium/src/+/5265077 (Probably OBS, CEF, Electron can unite to pressure Google merging this LOL) https://www.magpcss.org/ceforum/viewtopic.php?f=6&t=19404&start=20 Last time I check the electron is similar to CEF (Both use FrameSinkVideoCapturer), so I think it is definitely portable to electron. I'm going to create a PR if possible. |
Currently FrameSinkVideoCapturer only supports NV12 with NativeTexture, I added format support for related codes and make it also possible for RGBA. Firstly, it is reasonable RenderableGpuMemoryBufferVideoFramePool supports different formats, currently it is nailed to NV12 and cannot be easily ported to other formats in future. Also, with this change, the CEF OSR function can use shared GPU textures to accelerate the paint. This function means greatly to CEF developers, and I think it is better to make it goes into upstream Chromium instead of a big patch. The Electron also wanted this for a long time. The OBS also wanted this feature and they are stuck on M103 for a long time, which might introduce possible security concerns. https://bitbucket.org/chromiumembedded/cef/pull-requests/285 https://magpcss.org/ceforum/viewtopic.php?t=19404 electron/electron#16961 Changes: 1. RenderableGpuMemoryBufferVideoFramePool supports multiple formats, FrameSinkVideoCaptureImpl supports capturing RGBA use GMB mode, VideoFramePool supports format-aware (GMB) and format-unaware (SharedMemory) mode. 2. RenderableGpuMemoryBufferVideoFramePool use NV12 as default pixel format to provide compability 3. DXGI GMB Factory supports BGRA_8888 texture 4. FrameSinkVideoCapturerImpl::DidCopyFrame supports GMB RGBA 5. Respect buffer_format_preference_ to recreate frame_pool_ when FrameSinkVideoCapturerImpl::Start 6. FrameSinkVideoCaptureImpl use new GpuMemoryBufferVideoFramePool 7. Add test to `mojom::BufferFormatPreference::kPreferGpuMemoryBuffer + media::PIXEL_FORMAT_ARGB` Change-Id: Ie562f1ff69d8043ec1264ef6df7f9d50f60d9555 Bug: 324934085 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5265077 Reviewed-by: Kyle Charbonneau <kylechar@chromium.org> Reviewed-by: Mark Foltz <mfoltz@chromium.org> Commit-Queue: Kyle Charbonneau <kylechar@chromium.org> Cr-Commit-Position: refs/heads/main@{#1268507}
Good news: All the patches are merged in M124(6367), so implementing it on electron should be easy. |
Started working on this. See #41972 |
Current offscreen rendering approach requires to choose between two non-optimal options:
Would it be possible to implement a 3rd approach in Electron, which will allow to use hardware acceleration for rendering the frames, but instead of returning them as memory buffers (thus requiring a copy from GPU to system RAM) return a handle for the GPU texture (or render directly to a texture supplied externally by the user)?
This is similar to a recent change done in CEF:
see here for the PR, and here for the long discussion.
Thanks!
The text was updated successfully, but these errors were encountered: