graphicscommand: Move pixel->texel conversion to graphicscommand

This commit is contained in:
Hajime Hoshi 2019-09-20 23:59:04 +09:00
parent 915ed91f25
commit 70a38dc09a
3 changed files with 36 additions and 42 deletions

View File

@ -195,6 +195,14 @@ func (q *commandQueue) Flush() {
for i := 0; i < q.nvertices/graphics.VertexFloatNum; i++ {
s := q.srcSizes[i]
// Convert pixels to texels.
vs[i*graphics.VertexFloatNum+2] /= s.width
vs[i*graphics.VertexFloatNum+3] /= s.height
vs[i*graphics.VertexFloatNum+4] /= s.width
vs[i*graphics.VertexFloatNum+5] /= s.height
vs[i*graphics.VertexFloatNum+6] /= s.width
vs[i*graphics.VertexFloatNum+7] /= s.height
// Adjust the destination position to avoid jaggy (#929).
// This is not a perfect solution since texels on a texture can take a position on borders
// which can cause jaggy. But adjusting only edges should work in most cases.

View File

@ -37,13 +37,11 @@ const (
// Image represents an image that is implemented with OpenGL.
type Image struct {
image driver.Image
width int
height int
internalWidth int
internalHeight int
screen bool
id int
image driver.Image
width int
height int
screen bool
id int
lastCommand lastCommand
}
@ -61,11 +59,9 @@ func genNextID() int {
// Note that the image is not initialized yet.
func NewImage(width, height int) *Image {
i := &Image{
width: width,
height: height,
internalWidth: graphics.InternalImageSize(width),
internalHeight: graphics.InternalImageSize(height),
id: genNextID(),
width: width,
height: height,
id: genNextID(),
}
c := &newImageCommand{
result: i,
@ -78,12 +74,10 @@ func NewImage(width, height int) *Image {
func NewScreenFramebufferImage(width, height int) *Image {
i := &Image{
width: width,
height: height,
internalWidth: graphics.InternalImageSize(width),
internalHeight: graphics.InternalImageSize(height),
screen: true,
id: genNextID(),
width: width,
height: height,
screen: true,
id: genNextID(),
}
c := &newScreenFramebufferImageCommand{
result: i,
@ -102,7 +96,7 @@ func (i *Image) Dispose() {
}
func (i *Image) InternalSize() (int, int) {
return i.internalWidth, i.internalHeight
return graphics.InternalImageSize(i.width), graphics.InternalImageSize(i.height)
}
// DrawTriangles draws triangles with the given image.
@ -111,12 +105,12 @@ func (i *Image) InternalSize() (int, int) {
//
// 0: Destination X in pixels
// 1: Destination Y in pixels
// 2: Source X in texels
// 3: Source Y in texels
// 4: Bounds of the source min X in texels
// 5: Bounds of the source min Y in texels
// 6: Bounds of the source max X in texels
// 7: Bounds of the source max Y in texels
// 2: Source X in pixels (not texels!)
// 3: Source Y in pixels
// 4: Bounds of the source min X in pixels
// 5: Bounds of the source min Y in pixels
// 6: Bounds of the source max X in pixels
// 7: Bounds of the source max Y in pixels
// 8: Color R [0.0-1.0]
// 9: Color G
// 10: Color B

View File

@ -206,12 +206,12 @@ func (i *Image) Clear() {
}
// quadVertices returns vertices to render a quad. These values are passed to graphicscommand.Image.
func quadVertices(dx0, dy0, dx1, dy1, u0, v0, u1, v1, cr, cg, cb, ca float32) []float32 {
func quadVertices(dx0, dy0, dx1, dy1, sx0, sy0, sx1, sy1, cr, cg, cb, ca float32) []float32 {
return []float32{
dx0, dy0, u0, v0, u0, v0, u1, v1, cr, cg, cb, ca,
dx1, dy0, u1, v0, u0, v0, u1, v1, cr, cg, cb, ca,
dx0, dy1, u0, v1, u0, v0, u1, v1, cr, cg, cb, ca,
dx1, dy1, u1, v1, u0, v0, u1, v1, cr, cg, cb, ca,
dx0, dy0, sx0, sy0, sx0, sy0, sx1, sy1, cr, cg, cb, ca,
dx1, dy0, sx1, sy0, sx0, sy0, sx1, sy1, cr, cg, cb, ca,
dx0, dy1, sx0, sy1, sx0, sy0, sx1, sy1, cr, cg, cb, ca,
dx1, dy1, sx1, sy1, sx0, sy0, sx1, sy1, cr, cg, cb, ca,
}
}
@ -228,7 +228,8 @@ func clearImage(img *graphicscommand.Image) {
// The rendering target size needs to be its 'internal' size instead of the exposed size to avoid glitches on
// mobile platforms (See the change 1e1f309a).
dw, dh := img.InternalSize()
vs := quadVertices(0, 0, float32(dw), float32(dh), 0, 0, 1, 1, 0, 0, 0, 0)
sw, sh := emptyImage.image.InternalSize()
vs := quadVertices(0, 0, float32(dw), float32(dh), 0, 0, float32(sw), float32(sh), 0, 0, 0, 0)
is := graphics.QuadIndices()
// The first DrawTriangles must be clear mode for initialization.
// TODO: Can the graphicscommand package hide this knowledge?
@ -281,7 +282,8 @@ func fillImage(i *graphicscommand.Image, clr color.RGBA) {
// TODO: Integrate with clearColor
dw, dh := i.InternalSize()
vs := quadVertices(0, 0, float32(dw), float32(dh), 0, 0, 1, 1, rf, gf, bf, af)
sw, sh := emptyImage.image.InternalSize()
vs := quadVertices(0, 0, float32(dw), float32(dh), 0, 0, float32(sw), float32(sh), rf, gf, bf, af)
is := graphics.QuadIndices()
i.DrawTriangles(emptyImage.image, vs, is, nil, compositemode, driver.FilterNearest, driver.AddressClampToZero)
@ -399,16 +401,6 @@ func (i *Image) DrawTriangles(img *Image, vertices []float32, indices []uint16,
}
theImages.makeStaleIfDependingOn(i)
w, h := img.image.InternalSize()
for i := 0; i < len(vertices)/graphics.VertexFloatNum; i++ {
vertices[i*graphics.VertexFloatNum+2] /= float32(w)
vertices[i*graphics.VertexFloatNum+3] /= float32(h)
vertices[i*graphics.VertexFloatNum+4] /= float32(w)
vertices[i*graphics.VertexFloatNum+5] /= float32(h)
vertices[i*graphics.VertexFloatNum+6] /= float32(w)
vertices[i*graphics.VertexFloatNum+7] /= float32(h)
}
if img.stale || img.volatile || i.screen || !needsRestoring() || i.volatile {
i.makeStale()
} else {