mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2025-07-31 21:29:06 +00:00
LibCore+LibWeb: Use Metal backend for Skia painter on macOS
If Metal context and IOSurface are available, Skia painter will use Ganesh GPU backend on macOS, which is noticeably faster than the default CPU backend. Painting pipeline: 1. (WebContent) Allocate IOSurface for backing store 2. (WebContent) Allocate MTLTexture that wraps IOSurface 3. (WebContent) Paint into MTLTexture using Skia 4. (Browser) Wrap IOSurface into Gfx::Painter and use QPainter/CoreGraphics to blit backing store into viewport. Things we should improve in the future: 1. Upload textures for images in advance instead of doing that before every repaint. 2. Teach AppKit client to read directly from IOSurface instead of copying.
This commit is contained in:
parent
8de9516272
commit
79acb998e1
Notes:
sideshowbarker
2024-07-16 20:05:14 +09:00
Author: https://github.com/kalenikaliaksandr
Commit: 79acb998e1
Pull-request: https://github.com/LadybirdBrowser/ladybird/pull/294
10 changed files with 288 additions and 21 deletions
|
@ -18,7 +18,6 @@
|
|||
#include <LibWeb/HTML/Window.h>
|
||||
#include <LibWeb/Page/Page.h>
|
||||
#include <LibWeb/Painting/DisplayListPlayerCPU.h>
|
||||
#include <LibWeb/Painting/DisplayListPlayerSkia.h>
|
||||
#include <LibWeb/Platform/EventLoopPlugin.h>
|
||||
|
||||
#ifdef HAS_ACCELERATED_GRAPHICS
|
||||
|
@ -33,6 +32,10 @@ TraversableNavigable::TraversableNavigable(JS::NonnullGCPtr<Page> page)
|
|||
: Navigable(page)
|
||||
, m_session_history_traversal_queue(vm().heap().allocate_without_realm<SessionHistoryTraversalQueue>())
|
||||
{
|
||||
#ifdef AK_OS_MACOS
|
||||
m_metal_context = Core::get_metal_context();
|
||||
m_skia_backend_context = Web::Painting::DisplayListPlayerSkia::create_metal_context(*m_metal_context);
|
||||
#endif
|
||||
}
|
||||
|
||||
TraversableNavigable::~TraversableNavigable() = default;
|
||||
|
@ -1174,10 +1177,8 @@ JS::GCPtr<DOM::Node> TraversableNavigable::currently_focused_area()
|
|||
return candidate;
|
||||
}
|
||||
|
||||
void TraversableNavigable::paint(Web::DevicePixelRect const& content_rect, Painting::BackingStore& backing_store, Web::PaintOptions paint_options)
|
||||
void TraversableNavigable::paint(Web::DevicePixelRect const& content_rect, Painting::BackingStore& target, Web::PaintOptions paint_options)
|
||||
{
|
||||
auto& target = backing_store.bitmap();
|
||||
|
||||
Painting::DisplayList display_list;
|
||||
Painting::DisplayListRecorder display_list_recorder(display_list);
|
||||
|
||||
|
@ -1193,7 +1194,7 @@ void TraversableNavigable::paint(Web::DevicePixelRect const& content_rect, Paint
|
|||
auto display_list_player_type = page().client().display_list_player_type();
|
||||
if (display_list_player_type == DisplayListPlayerType::GPU) {
|
||||
#ifdef HAS_ACCELERATED_GRAPHICS
|
||||
Web::Painting::DisplayListPlayerGPU player(*paint_options.accelerated_graphics_context, target);
|
||||
Web::Painting::DisplayListPlayerGPU player(*paint_options.accelerated_graphics_context, target.bitmap());
|
||||
display_list.execute(player);
|
||||
#else
|
||||
static bool has_warned_about_configuration = false;
|
||||
|
@ -1204,10 +1205,19 @@ void TraversableNavigable::paint(Web::DevicePixelRect const& content_rect, Paint
|
|||
}
|
||||
#endif
|
||||
} else if (display_list_player_type == DisplayListPlayerType::Skia) {
|
||||
Painting::DisplayListPlayerSkia player(target);
|
||||
#ifdef AK_OS_MACOS
|
||||
if (m_metal_context && m_skia_backend_context && is<Painting::IOSurfaceBackingStore>(target)) {
|
||||
auto& iosurface_backing_store = static_cast<Painting::IOSurfaceBackingStore&>(target);
|
||||
auto texture = m_metal_context->create_texture_from_iosurface(iosurface_backing_store.iosurface_handle());
|
||||
Painting::DisplayListPlayerSkia player(*m_skia_backend_context, *texture);
|
||||
display_list.execute(player);
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
Web::Painting::DisplayListPlayerSkia player(target.bitmap());
|
||||
display_list.execute(player);
|
||||
} else {
|
||||
Web::Painting::DisplayListPlayerCPU player(target);
|
||||
Web::Painting::DisplayListPlayerCPU player(target.bitmap());
|
||||
display_list.execute(player);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue