From a7e4665f716fc1ffb457db0d35416fae2355e91b Mon Sep 17 00:00:00 2001 From: Hajime Hoshi Date: Sun, 30 Jul 2023 18:47:45 +0900 Subject: [PATCH] internal/graphicscommand: use multiple command queues This is a preparation for asynchronous rendering. Updates #2664 --- internal/graphicscommand/command.go | 25 ++++++++++++++++++++++--- internal/graphicscommand/image.go | 16 ++++++++-------- internal/graphicscommand/shader.go | 4 ++-- 3 files changed, 32 insertions(+), 13 deletions(-) diff --git a/internal/graphicscommand/command.go b/internal/graphicscommand/command.go index c15c2202c..8440b2650 100644 --- a/internal/graphicscommand/command.go +++ b/internal/graphicscommand/command.go @@ -74,8 +74,23 @@ type commandQueue struct { uint32sBuffer uint32sBuffer } -// theCommandQueue is the command queue for the current process. -var theCommandQueue = &commandQueue{} +// theCommandQueues is the set of command queues for the current process. +var ( + theCommandQueues = [...]*commandQueue{ + {}, + {}, + } + commandQueueIndex int +) + +func currentCommandQueue() *commandQueue { + return theCommandQueues[commandQueueIndex] +} + +func switchCommandQueue() { + commandQueueIndex++ + commandQueueIndex = commandQueueIndex % len(theCommandQueues) +} func (q *commandQueue) appendIndices(indices []uint16, offset uint16) { n := len(q.indices) @@ -263,7 +278,11 @@ func (q *commandQueue) flush(graphicsDriver graphicsdriver.Graphics, endFrame bo // If endFrame is true, the current screen might be used to present. func FlushCommands(graphicsDriver graphicsdriver.Graphics, endFrame bool, swapBuffersForGL func()) error { flushImageBuffers() - return theCommandQueue.Flush(graphicsDriver, endFrame, swapBuffersForGL) + if err := currentCommandQueue().Flush(graphicsDriver, endFrame, swapBuffersForGL); err != nil { + return err + } + switchCommandQueue() + return nil } // drawTrianglesCommand represents a drawing command to draw an image on another image. diff --git a/internal/graphicscommand/image.go b/internal/graphicscommand/image.go index 28d35d8ce..942413fae 100644 --- a/internal/graphicscommand/image.go +++ b/internal/graphicscommand/image.go @@ -88,7 +88,7 @@ func NewImage(width, height int, screenFramebuffer bool) *Image { height: height, screen: screenFramebuffer, } - theCommandQueue.Enqueue(c) + currentCommandQueue().Enqueue(c) return i } @@ -100,7 +100,7 @@ func (i *Image) flushBufferedWritePixels() { dst: i, args: i.bufferedWP, } - theCommandQueue.Enqueue(c) + currentCommandQueue().Enqueue(c) i.bufferedWP = nil } @@ -109,7 +109,7 @@ func (i *Image) Dispose() { c := &disposeImageCommand{ target: i, } - theCommandQueue.Enqueue(c) + currentCommandQueue().Enqueue(c) } func (i *Image) InternalSize() (int, int) { @@ -158,7 +158,7 @@ func (i *Image) DrawTriangles(srcs [graphics.ShaderImageCount]*Image, offsets [g } i.flushBufferedWritePixels() - theCommandQueue.EnqueueDrawTrianglesCommand(i, srcs, offsets, vertices, indices, blend, dstRegion, srcRegion, shader, uniforms, evenOdd) + currentCommandQueue().EnqueueDrawTrianglesCommand(i, srcs, offsets, vertices, indices, blend, dstRegion, srcRegion, shader, uniforms, evenOdd) } // ReadPixels reads the image's pixels. @@ -170,8 +170,8 @@ func (i *Image) ReadPixels(graphicsDriver graphicsdriver.Graphics, buf []byte, r region: region, result: buf, } - theCommandQueue.Enqueue(c) - if err := theCommandQueue.Flush(graphicsDriver, false, nil); err != nil { + currentCommandQueue().Enqueue(c) + if err := currentCommandQueue().Flush(graphicsDriver, false, nil); err != nil { return err } return nil @@ -200,8 +200,8 @@ func (i *Image) IsInvalidated(graphicsDriver graphicsdriver.Graphics) (bool, err c := &isInvalidatedCommand{ image: i, } - theCommandQueue.Enqueue(c) - if err := theCommandQueue.Flush(graphicsDriver, false, nil); err != nil { + currentCommandQueue().Enqueue(c) + if err := currentCommandQueue().Flush(graphicsDriver, false, nil); err != nil { return false, err } return c.result, nil diff --git a/internal/graphicscommand/shader.go b/internal/graphicscommand/shader.go index 21625f3b2..071dbf50e 100644 --- a/internal/graphicscommand/shader.go +++ b/internal/graphicscommand/shader.go @@ -32,7 +32,7 @@ func NewShader(ir *shaderir.Program) *Shader { result: s, ir: ir, } - theCommandQueue.Enqueue(c) + currentCommandQueue().Enqueue(c) return s } @@ -40,7 +40,7 @@ func (s *Shader) Dispose() { c := &disposeShaderCommand{ target: s, } - theCommandQueue.Enqueue(c) + currentCommandQueue().Enqueue(c) } func (s *Shader) unit() shaderir.Unit {