Skip to content

[gpu] Refactor and fix OpenGL backend using Skia - #193

Merged
dacap merged 9 commits into
aseprite:betafrom
dacap:gpu
Aug 13, 2026
Merged

[gpu] Refactor and fix OpenGL backend using Skia#193
dacap merged 9 commits into
aseprite:betafrom
dacap:gpu

Conversation

@dacap

@dacap dacap commented Aug 4, 2026

Copy link
Copy Markdown
Member
  • New os::GpuContext class to wrap native OpenGL context
  • New os::SkiaGpuContext class to wrap Skia GrDirectContext
  • Added os::System::makePlatformGpuContext()
  • Added os::Window::clientSize()
  • Fixed makeCurrent/swapBuffers logic
  • Fixed support for multiple windows
  • Fixed macOS support

Related to aseprite/aseprite#960

@dacap dacap self-assigned this Aug 4, 2026

@aseprite-bot aseprite-bot left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

Comment thread examples/toggle_gpu.h

inline bool handle_toggle_gpu_key(const os::Event& ev)
{
os::WindowRef w = ev.window();

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: the variable 'w' is copy-constructed from a const reference but is only used as const reference; consider making it a const reference [performance-unnecessary-copy-initialization]

Suggested change
os::WindowRef w = ev.window();
const os::WindowRef& w = ev.window();

Comment thread examples/toggle_gpu.h

inline bool handle_toggle_gpu_key(const os::Event& ev)
{
os::WindowRef w = ev.window();

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: variable 'w' of type 'os::WindowRef' (aka 'Refos::Window') can be declared 'const' [misc-const-correctness]

Suggested change
os::WindowRef w = ev.window();
os::WindowRef const w = ev.window();

Comment thread os/gl/gl_context_glx.h
GLContextGLX(::Display* display) : m_display(display) {}

~GLContextGLX() { destroyGLContext(); }
~GLContextGLX() { destroyContext(); }

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: Call to virtual method 'GLContextGLX::destroyContext' during destruction bypasses virtual dispatch [clang-analyzer-optin.cplusplus.VirtualCall]

  ~GLContextGLX() { destroyContext(); }
                    ^
Additional context

os/gl/gl_context_glx.h:23: Call to virtual method 'GLContextGLX::destroyContext' during destruction bypasses virtual dispatch

  ~GLContextGLX() { destroyContext(); }
                    ^

Comment thread os/gl/gl_context_glx.h
bool createGLContext() override
bool makeContext(Window* window, GpuContext* shared) override
{
auto sharedGpuContext = (shared ? (GLXContext)shared->nativeHandle() : nullptr);

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: 'auto sharedGpuContext' can be declared as 'auto *sharedGpuContext' [readability-qualified-auto]

Suggested change
auto sharedGpuContext = (shared ? (GLXContext)shared->nativeHandle() : nullptr);
auto *sharedGpuContext = (shared ? (GLXContext)shared->nativeHandle() : nullptr);

Comment thread os/gl/gl_context_nsgl.h
GLContextNSGL();
~GLContextNSGL();

void setView(id view);

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: unknown type name 'id' [clang-diagnostic-error]

  void setView(id view);
               ^

Comment thread os/gpu_context.h
virtual ~GpuContext() {}
virtual bool isValid() { return false; }

virtual bool makeContext(Window* window, GpuContext* shared) { return false; }

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'window' is unused [misc-unused-parameters]

Suggested change
virtual bool makeContext(Window* window, GpuContext* shared) { return false; }
virtual bool makeContext(Window* /*window*/, GpuContext* shared) { return false; }

Comment thread os/gpu_context.h Outdated
virtual void makeCurrent(Window* window) {}
virtual void swapBuffers(Window* window) {}
virtual void flush() {}
virtual RenderTarget makeRenderTarget(const gfx::Size& size,

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'size' is unused [misc-unused-parameters]

Suggested change
virtual RenderTarget makeRenderTarget(const gfx::Size& size,
virtual RenderTarget makeRenderTarget(const gfx::Size& /*size*/,

Comment thread os/gpu_context.h Outdated
virtual void swapBuffers(Window* window) {}
virtual void flush() {}
virtual RenderTarget makeRenderTarget(const gfx::Size& size,
const int scale,

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'scale' is unused [misc-unused-parameters]

Suggested change
const int scale,
const int /*scale*/,

Comment thread os/gpu_context.h Outdated
virtual void flush() {}
virtual RenderTarget makeRenderTarget(const gfx::Size& size,
const int scale,
const os::ColorSpaceRef& cs)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'cs' is unused [misc-unused-parameters]

Suggested change
const os::ColorSpaceRef& cs)
const os::ColorSpaceRef& /*cs*/)

Comment thread os/win/system.cpp
m_screenMousePos = ev.window()->pointToScreen(ev.position());
}

std::unique_ptr<GpuContext> SystemWin::makePlatformGpuContext()

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: method 'makePlatformGpuContext' can be made static [readability-convert-member-functions-to-static]

Suggested change
std::unique_ptr<GpuContext> SystemWin::makePlatformGpuContext()
static std::unique_ptr<GpuContext> SystemWin::makePlatformGpuContext()

dacap added 3 commits August 11, 2026 08:50
* New os::GpuContext class to wrap native OpenGL context
* New os::SkiaGpuContext class to wrap Skia GrDirectContext
* Added os::System::makePlatformGpuContext()
* Added os::Window::clientSize()
* Fixed makeCurrent/swapBuffers logic
* Fixed support for multiple windows
* macOS support doesn't work

Related to aseprite/aseprite#960

@aseprite-bot aseprite-bot left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

Comment thread examples/allevents.cpp
p.color(gfx::rgba(0, 0, 0));
surface->drawRect(gfx::Rect(rc.x, rc.y + rc.h - h, rc.w, h), p);
if (m_textLog.size() >= m_maxlines) {
int h = m_lineHeight * newlines;

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: variable 'h' of type 'int' can be declared 'const' [misc-const-correctness]

Suggested change
int h = m_lineHeight * newlines;
int const h = m_lineHeight * newlines;

Comment thread os/gl/gl_context_wgl.h
#define WGL_CONTEXT_CORE_PROFILE_BIT_ARB 0x00000001
#define WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB 0x00000002

using PFNWGLCREATECONTEXTATTRIBSARBPROC = HGLRC(WINAPI*)(HDC, HGLRC, const int*);

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'window' is unused [misc-unused-parameters]

Suggested change
using PFNWGLCREATECONTEXTATTRIBSARBPROC = HGLRC(WINAPI*)(HDC, HGLRC, const int*);
bool makeContext(Window* /*window*/, GpuContext* shared) override

Comment thread os/gl/gl_context_wgl.h
@@ -81,22 +103,27 @@ class GLContextWGL : public GLContext {
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'window' is unused [misc-unused-parameters]

Suggested change
}
void swapBuffers(Window* /*window*/) override

@aseprite-bot aseprite-bot left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-tidy made some suggestions

Comment thread os/gpu_context.h
virtual void swapBuffers(Window* window) {}
virtual void flush() {}

virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'cs' is unused [misc-unused-parameters]

Suggested change
virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)
virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& /*cs*/)

Comment thread os/gpu_context.h
virtual void swapBuffers(Window* window) {}
virtual void flush() {}

virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'size' is unused [misc-unused-parameters]

Suggested change
virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)
virtual SurfaceRef makeOnscreenRenderTarget(const gfx::Size& /*size*/, const os::ColorSpaceRef& cs)

Comment thread os/gpu_context.h
return {};
}

virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'cs' is unused [misc-unused-parameters]

Suggested change
virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)
virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& /*cs*/)

Comment thread os/gpu_context.h
return {};
}

virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: parameter 'size' is unused [misc-unused-parameters]

Suggested change
virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& size, const os::ColorSpaceRef& cs)
virtual SurfaceRef makeOffscreenRenderTarget(const gfx::Size& /*size*/, const os::ColorSpaceRef& cs)

@dacap
dacap marked this pull request as ready for review August 12, 2026 22:56
* Fixed using shared OpenGL contexts with [NSOpenGLContext initWithFormat...]
* NSView requires an wantsUpdateLayer/updateLayer when using GPU
  acceleration to call [NSOpenGLContext update].

There is still a bug/crash when we go back to CPU/raster backend after
enabling the GPU acceleration.
@dacap
dacap merged commit 5d107ba into aseprite:beta Aug 13, 2026
12 checks passed
@dacap
dacap deleted the gpu branch August 13, 2026 12:47
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