mirror of
https://github.com/hajimehoshi/ebiten.git
synced 2024-12-25 03:08:54 +01:00
internal/graphicsdriver/metal: reduce rendering paths for even-odd rendering
This commit is contained in:
parent
1839dd0b9b
commit
0afb6fd22a
@ -42,7 +42,7 @@ type Graphics struct {
|
|||||||
unusedBuffers map[mtl.Buffer]struct{}
|
unusedBuffers map[mtl.Buffer]struct{}
|
||||||
|
|
||||||
lastDst *Image
|
lastDst *Image
|
||||||
lastStencilMode stencilMode
|
lastEvenOdd bool
|
||||||
|
|
||||||
vb mtl.Buffer
|
vb mtl.Buffer
|
||||||
ib mtl.Buffer
|
ib mtl.Buffer
|
||||||
@ -421,15 +421,15 @@ func (g *Graphics) flushRenderCommandEncoderIfNeeded() {
|
|||||||
g.lastDst = nil
|
g.lastDst = nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (g *Graphics) draw(rps mtl.RenderPipelineState, dst *Image, dstRegion graphicsdriver.Region, srcs [graphics.ShaderImageCount]*Image, indexLen int, indexOffset int, uniforms [][]float32, stencilMode stencilMode) error {
|
func (g *Graphics) draw(dst *Image, dstRegion graphicsdriver.Region, srcs [graphics.ShaderImageCount]*Image, indexLen int, indexOffset int, shader *Shader, uniforms [][]float32, blend graphicsdriver.Blend, evenOdd bool) error {
|
||||||
// When prepareing a stencil buffer, flush the current render command encoder
|
// When prepareing a stencil buffer, flush the current render command encoder
|
||||||
// to make sure the stencil buffer is cleared when loading.
|
// to make sure the stencil buffer is cleared when loading.
|
||||||
// TODO: What about clearing the stencil buffer by vertices?
|
// TODO: What about clearing the stencil buffer by vertices?
|
||||||
if g.lastDst != dst || (g.lastStencilMode == noStencil) != (stencilMode == noStencil) || stencilMode == prepareStencil {
|
if g.lastDst != dst || g.lastEvenOdd != evenOdd || evenOdd {
|
||||||
g.flushRenderCommandEncoderIfNeeded()
|
g.flushRenderCommandEncoderIfNeeded()
|
||||||
}
|
}
|
||||||
g.lastDst = dst
|
g.lastDst = dst
|
||||||
g.lastStencilMode = stencilMode
|
g.lastEvenOdd = evenOdd
|
||||||
|
|
||||||
if g.rce == (mtl.RenderCommandEncoder{}) {
|
if g.rce == (mtl.RenderCommandEncoder{}) {
|
||||||
rpd := mtl.RenderPassDescriptor{}
|
rpd := mtl.RenderPassDescriptor{}
|
||||||
@ -451,7 +451,7 @@ func (g *Graphics) draw(rps mtl.RenderPipelineState, dst *Image, dstRegion graph
|
|||||||
rpd.ColorAttachments[0].Texture = t
|
rpd.ColorAttachments[0].Texture = t
|
||||||
rpd.ColorAttachments[0].ClearColor = mtl.ClearColor{}
|
rpd.ColorAttachments[0].ClearColor = mtl.ClearColor{}
|
||||||
|
|
||||||
if stencilMode == prepareStencil {
|
if evenOdd {
|
||||||
dst.ensureStencil()
|
dst.ensureStencil()
|
||||||
rpd.StencilAttachment.LoadAction = mtl.LoadActionClear
|
rpd.StencilAttachment.LoadAction = mtl.LoadActionClear
|
||||||
rpd.StencilAttachment.StoreAction = mtl.StoreActionDontCare
|
rpd.StencilAttachment.StoreAction = mtl.StoreActionDontCare
|
||||||
@ -464,8 +464,6 @@ func (g *Graphics) draw(rps mtl.RenderPipelineState, dst *Image, dstRegion graph
|
|||||||
g.rce = g.cb.MakeRenderCommandEncoder(rpd)
|
g.rce = g.cb.MakeRenderCommandEncoder(rpd)
|
||||||
}
|
}
|
||||||
|
|
||||||
g.rce.SetRenderPipelineState(rps)
|
|
||||||
|
|
||||||
w, h := dst.internalSize()
|
w, h := dst.internalSize()
|
||||||
g.rce.SetViewport(mtl.Viewport{
|
g.rce.SetViewport(mtl.Viewport{
|
||||||
OriginX: 0,
|
OriginX: 0,
|
||||||
@ -499,10 +497,34 @@ func (g *Graphics) draw(rps mtl.RenderPipelineState, dst *Image, dstRegion graph
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
g.rce.SetDepthStencilState(g.dsss[stencilMode])
|
if evenOdd {
|
||||||
|
prepareStencilRpss, err := shader.RenderPipelineState(&g.view, blend, prepareStencil, dst.screen)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
drawWithStencilRpss, err := shader.RenderPipelineState(&g.view, blend, drawWithStencil, dst.screen)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
g.rce.SetDepthStencilState(g.dsss[prepareStencil])
|
||||||
|
g.rce.SetRenderPipelineState(prepareStencilRpss)
|
||||||
g.rce.DrawIndexedPrimitives(mtl.PrimitiveTypeTriangle, indexLen, mtl.IndexTypeUInt16, g.ib, indexOffset*2)
|
g.rce.DrawIndexedPrimitives(mtl.PrimitiveTypeTriangle, indexLen, mtl.IndexTypeUInt16, g.ib, indexOffset*2)
|
||||||
|
|
||||||
|
g.rce.SetDepthStencilState(g.dsss[drawWithStencil])
|
||||||
|
g.rce.SetRenderPipelineState(drawWithStencilRpss)
|
||||||
|
g.rce.DrawIndexedPrimitives(mtl.PrimitiveTypeTriangle, indexLen, mtl.IndexTypeUInt16, g.ib, indexOffset*2)
|
||||||
|
} else {
|
||||||
|
rpss, err := shader.RenderPipelineState(&g.view, blend, noStencil, dst.screen)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
g.rce.SetDepthStencilState(g.dsss[noStencil])
|
||||||
|
g.rce.SetRenderPipelineState(rpss)
|
||||||
|
g.rce.DrawIndexedPrimitives(mtl.PrimitiveTypeTriangle, indexLen, mtl.IndexTypeUInt16, g.ib, indexOffset*2)
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -564,30 +586,9 @@ func (g *Graphics) DrawTriangles(dstID graphicsdriver.ImageID, srcIDs [graphics.
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if evenOdd {
|
if err := g.draw(dst, dstRegion, srcs, indexLen, indexOffset, g.shaders[shaderID], uniformVars, blend, evenOdd); err != nil {
|
||||||
prepareStencilRpss, err := g.shaders[shaderID].RenderPipelineState(&g.view, blend, prepareStencil, dst.screen)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if err := g.draw(prepareStencilRpss, dst, dstRegion, srcs, indexLen, indexOffset, uniformVars, prepareStencil); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
drawWithStencilRpss, err := g.shaders[shaderID].RenderPipelineState(&g.view, blend, drawWithStencil, dst.screen)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
if err := g.draw(drawWithStencilRpss, dst, dstRegion, srcs, indexLen, indexOffset, uniformVars, drawWithStencil); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
rpss, err := g.shaders[shaderID].RenderPipelineState(&g.view, blend, noStencil, dst.screen)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
if err := g.draw(rpss, dst, dstRegion, srcs, indexLen, indexOffset, uniformVars, noStencil); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user