mirror of
https://github.com/hajimehoshi/ebiten.git
synced 2024-12-26 03:38:55 +01:00
internal/graphicscommand: Merge even-odd draw-triangles commands when possible
Closes #1685
This commit is contained in:
parent
63a00f6171
commit
5e1d6c06f1
@ -163,8 +163,8 @@ func (q *commandQueue) EnqueueDrawTrianglesCommand(dst *Image, srcs [graphics.Sh
|
|||||||
if !split && 0 < len(q.commands) {
|
if !split && 0 < len(q.commands) {
|
||||||
// TODO: Pass offsets and uniforms when merging considers the shader.
|
// TODO: Pass offsets and uniforms when merging considers the shader.
|
||||||
if last, ok := q.commands[len(q.commands)-1].(*drawTrianglesCommand); ok {
|
if last, ok := q.commands[len(q.commands)-1].(*drawTrianglesCommand); ok {
|
||||||
if last.CanMergeWithDrawTrianglesCommand(dst, srcs, color, mode, filter, address, dstRegion, srcRegion, shader, evenOdd) {
|
if last.CanMergeWithDrawTrianglesCommand(dst, srcs, vertices, color, mode, filter, address, dstRegion, srcRegion, shader, evenOdd) {
|
||||||
last.addNumVertices(len(vertices))
|
last.setVertices(q.lastVertices(len(vertices) + last.numVertices()))
|
||||||
last.addNumIndices(len(indices))
|
last.addNumIndices(len(indices))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -175,7 +175,7 @@ func (q *commandQueue) EnqueueDrawTrianglesCommand(dst *Image, srcs [graphics.Sh
|
|||||||
dst: dst,
|
dst: dst,
|
||||||
srcs: srcs,
|
srcs: srcs,
|
||||||
offsets: offsets,
|
offsets: offsets,
|
||||||
nvertices: len(vertices),
|
vertices: q.lastVertices(len(vertices)),
|
||||||
nindices: len(indices),
|
nindices: len(indices),
|
||||||
color: color,
|
color: color,
|
||||||
mode: mode,
|
mode: mode,
|
||||||
@ -190,6 +190,10 @@ func (q *commandQueue) EnqueueDrawTrianglesCommand(dst *Image, srcs [graphics.Sh
|
|||||||
q.commands = append(q.commands, c)
|
q.commands = append(q.commands, c)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (q *commandQueue) lastVertices(n int) []float32 {
|
||||||
|
return q.vertices[q.nvertices-n : q.nvertices]
|
||||||
|
}
|
||||||
|
|
||||||
// Enqueue enqueues a drawing command other than a draw-triangles command.
|
// Enqueue enqueues a drawing command other than a draw-triangles command.
|
||||||
//
|
//
|
||||||
// For a draw-triangles command, use EnqueueDrawTrianglesCommand.
|
// For a draw-triangles command, use EnqueueDrawTrianglesCommand.
|
||||||
@ -311,7 +315,7 @@ type drawTrianglesCommand struct {
|
|||||||
dst *Image
|
dst *Image
|
||||||
srcs [graphics.ShaderImageNum]*Image
|
srcs [graphics.ShaderImageNum]*Image
|
||||||
offsets [graphics.ShaderImageNum - 1][2]float32
|
offsets [graphics.ShaderImageNum - 1][2]float32
|
||||||
nvertices int
|
vertices []float32
|
||||||
nindices int
|
nindices int
|
||||||
color *affine.ColorM
|
color *affine.ColorM
|
||||||
mode driver.CompositeMode
|
mode driver.CompositeMode
|
||||||
@ -435,15 +439,15 @@ func (c *drawTrianglesCommand) Exec(indexOffset int) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *drawTrianglesCommand) numVertices() int {
|
func (c *drawTrianglesCommand) numVertices() int {
|
||||||
return c.nvertices
|
return len(c.vertices)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *drawTrianglesCommand) numIndices() int {
|
func (c *drawTrianglesCommand) numIndices() int {
|
||||||
return c.nindices
|
return c.nindices
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *drawTrianglesCommand) addNumVertices(n int) {
|
func (c *drawTrianglesCommand) setVertices(vertices []float32) {
|
||||||
c.nvertices += n
|
c.vertices = vertices
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *drawTrianglesCommand) addNumIndices(n int) {
|
func (c *drawTrianglesCommand) addNumIndices(n int) {
|
||||||
@ -452,7 +456,7 @@ func (c *drawTrianglesCommand) addNumIndices(n int) {
|
|||||||
|
|
||||||
// CanMergeWithDrawTrianglesCommand returns a boolean value indicating whether the other drawTrianglesCommand can be merged
|
// CanMergeWithDrawTrianglesCommand returns a boolean value indicating whether the other drawTrianglesCommand can be merged
|
||||||
// with the drawTrianglesCommand c.
|
// with the drawTrianglesCommand c.
|
||||||
func (c *drawTrianglesCommand) CanMergeWithDrawTrianglesCommand(dst *Image, srcs [graphics.ShaderImageNum]*Image, color *affine.ColorM, mode driver.CompositeMode, filter driver.Filter, address driver.Address, dstRegion, srcRegion driver.Region, shader *Shader, evenOdd bool) bool {
|
func (c *drawTrianglesCommand) CanMergeWithDrawTrianglesCommand(dst *Image, srcs [graphics.ShaderImageNum]*Image, vertices []float32, color *affine.ColorM, mode driver.CompositeMode, filter driver.Filter, address driver.Address, dstRegion, srcRegion driver.Region, shader *Shader, evenOdd bool) bool {
|
||||||
// If a shader is used, commands are not merged.
|
// If a shader is used, commands are not merged.
|
||||||
//
|
//
|
||||||
// TODO: Merge shader commands considering uniform variables.
|
// TODO: Merge shader commands considering uniform variables.
|
||||||
@ -484,11 +488,51 @@ func (c *drawTrianglesCommand) CanMergeWithDrawTrianglesCommand(dst *Image, srcs
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
if c.evenOdd || evenOdd {
|
if c.evenOdd || evenOdd {
|
||||||
|
if c.evenOdd && evenOdd {
|
||||||
|
return !mightOverlapsDstRegions(c.vertices, vertices)
|
||||||
|
}
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
posInf32 = float32(math.Inf(1))
|
||||||
|
negInf32 = float32(math.Inf(-1))
|
||||||
|
)
|
||||||
|
|
||||||
|
func dstRegionFromVertices(vertices []float32) (minX, minY, maxX, maxY float32) {
|
||||||
|
minX = posInf32
|
||||||
|
minY = posInf32
|
||||||
|
maxX = negInf32
|
||||||
|
maxY = negInf32
|
||||||
|
|
||||||
|
for i := 0; i < len(vertices)/graphics.VertexFloatNum; i++ {
|
||||||
|
x := vertices[graphics.VertexFloatNum*i]
|
||||||
|
y := vertices[graphics.VertexFloatNum*i+1]
|
||||||
|
if x < minX {
|
||||||
|
minX = x
|
||||||
|
}
|
||||||
|
if y < minY {
|
||||||
|
minY = y
|
||||||
|
}
|
||||||
|
if maxX < x {
|
||||||
|
maxX = x
|
||||||
|
}
|
||||||
|
if maxY < y {
|
||||||
|
maxY = y
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func mightOverlapsDstRegions(vertices1, vertices2 []float32) bool {
|
||||||
|
minX1, minY1, maxX1, maxY1 := dstRegionFromVertices(vertices1)
|
||||||
|
minX2, minY2, maxX2, maxY2 := dstRegionFromVertices(vertices2)
|
||||||
|
const mergin = 1
|
||||||
|
return minX1 < maxX2+mergin && minX2 < maxX1+mergin && minY1 < maxY2+mergin && minY2 < maxY1+mergin
|
||||||
|
}
|
||||||
|
|
||||||
// replacePixelsCommand represents a command to replace pixels of an image.
|
// replacePixelsCommand represents a command to replace pixels of an image.
|
||||||
type replacePixelsCommand struct {
|
type replacePixelsCommand struct {
|
||||||
dst *Image
|
dst *Image
|
||||||
|
Loading…
Reference in New Issue
Block a user