mirror of
https://github.com/hajimehoshi/ebiten.git
synced 2024-12-24 02:38:53 +01:00
internal/graphicsdriver/directx, internal/graphicsdriver/metal: bug fix: uniform matrix variables were passed wrongly
Updates #2036
This commit is contained in:
parent
e1a3f12e68
commit
f6d87f6ee8
@ -1637,21 +1637,23 @@ func (s *Shader) uniformsToFloat32s(uniforms [][]float32) []float32 {
|
||||
case shaderir.Float, shaderir.Vec2, shaderir.Vec3, shaderir.Vec4:
|
||||
fs = append(fs, u...)
|
||||
case shaderir.Mat2:
|
||||
for j := 0; j < 2; j++ {
|
||||
fs = append(fs, u[2*j:2*(j+1)]...)
|
||||
if j < 1 {
|
||||
fs = append(fs, 0, 0)
|
||||
}
|
||||
}
|
||||
fs = append(fs,
|
||||
u[0], u[2], 0, 0,
|
||||
u[1], u[3],
|
||||
)
|
||||
case shaderir.Mat3:
|
||||
for j := 0; j < 3; j++ {
|
||||
fs = append(fs, u[3*j:3*(j+1)]...)
|
||||
if j < 2 {
|
||||
fs = append(fs, 0)
|
||||
}
|
||||
}
|
||||
fs = append(fs,
|
||||
u[0], u[3], u[6], 0,
|
||||
u[1], u[4], u[7], 0,
|
||||
u[2], u[5], u[8],
|
||||
)
|
||||
case shaderir.Mat4:
|
||||
fs = append(fs, u...)
|
||||
fs = append(fs,
|
||||
u[0], u[4], u[8], u[12],
|
||||
u[1], u[5], u[9], u[13],
|
||||
u[2], u[6], u[10], u[14],
|
||||
u[3], u[7], u[11], u[15],
|
||||
)
|
||||
case shaderir.Array:
|
||||
// Each element is aligned to the boundary.
|
||||
switch t.Sub[0].Main {
|
||||
|
@ -998,7 +998,18 @@ func (g *Graphics) DrawTriangles(dstID graphicsdriver.ImageID, srcIDs [graphics.
|
||||
// Set the additional uniform variables.
|
||||
for i, v := range uniforms {
|
||||
const offset = graphics.PreservedUniformVariablesNum
|
||||
uniformVars[offset+i] = v
|
||||
switch g.shaders[shaderID].ir.Uniforms[offset+i].Main {
|
||||
case shaderir.Mat3:
|
||||
println("yo")
|
||||
// float3x3 requires 16-byte alignment (#2036).
|
||||
newV := make([]float32, 12)
|
||||
copy(newV[0:3], v[0:3])
|
||||
copy(newV[4:7], v[3:6])
|
||||
copy(newV[8:11], v[6:9])
|
||||
uniformVars[offset+i] = newV
|
||||
default:
|
||||
uniformVars[offset+i] = v
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
111
shader_test.go
111
shader_test.go
@ -726,3 +726,114 @@ func Fragment(position vec4, texCoord vec2, color vec4) vec4 {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestShaderUniformMatrix2(t *testing.T) {
|
||||
const w, h = 16, 16
|
||||
|
||||
dst := ebiten.NewImage(w, h)
|
||||
s, err := ebiten.NewShader([]byte(`package main
|
||||
|
||||
var Mat2 mat2
|
||||
|
||||
func Fragment(position vec4, texCoord vec2, color vec4) vec4 {
|
||||
return vec4(Mat2 * vec2(1), 1, 1)
|
||||
}
|
||||
`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
op := &ebiten.DrawRectShaderOptions{}
|
||||
op.Uniforms = map[string]interface{}{
|
||||
"Mat2": []float32{
|
||||
1.0 / 256.0, 2.0 / 256.0,
|
||||
3.0 / 256.0, 4.0 / 256.0,
|
||||
},
|
||||
}
|
||||
dst.DrawRectShader(w, h, s, op)
|
||||
|
||||
for j := 0; j < h; j++ {
|
||||
for i := 0; i < w; i++ {
|
||||
got := dst.At(i, j).(color.RGBA)
|
||||
want := color.RGBA{4, 6, 0xff, 0xff}
|
||||
if !sameColors(got, want, 2) {
|
||||
t.Errorf("dst.At(%d, %d): got: %v, want: %v", i, j, got, want)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestShaderUniformMatrix3(t *testing.T) {
|
||||
const w, h = 16, 16
|
||||
|
||||
dst := ebiten.NewImage(w, h)
|
||||
s, err := ebiten.NewShader([]byte(`package main
|
||||
|
||||
var Mat3 mat3
|
||||
|
||||
func Fragment(position vec4, texCoord vec2, color vec4) vec4 {
|
||||
return vec4(Mat3 * vec3(1), 1)
|
||||
}
|
||||
`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
op := &ebiten.DrawRectShaderOptions{}
|
||||
op.Uniforms = map[string]interface{}{
|
||||
"Mat3": []float32{
|
||||
1.0 / 256.0, 2.0 / 256.0, 3.0 / 256.0,
|
||||
4.0 / 256.0, 5.0 / 256.0, 6.0 / 256.0,
|
||||
7.0 / 256.0, 8.0 / 256.0, 9.0 / 256.0,
|
||||
},
|
||||
}
|
||||
dst.DrawRectShader(w, h, s, op)
|
||||
|
||||
for j := 0; j < h; j++ {
|
||||
for i := 0; i < w; i++ {
|
||||
got := dst.At(i, j).(color.RGBA)
|
||||
want := color.RGBA{12, 15, 18, 0xff}
|
||||
if !sameColors(got, want, 2) {
|
||||
t.Errorf("dst.At(%d, %d): got: %v, want: %v", i, j, got, want)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestShaderUniformMatrix4(t *testing.T) {
|
||||
const w, h = 16, 16
|
||||
|
||||
dst := ebiten.NewImage(w, h)
|
||||
s, err := ebiten.NewShader([]byte(`package main
|
||||
|
||||
var Mat4 mat4
|
||||
|
||||
func Fragment(position vec4, texCoord vec2, color vec4) vec4 {
|
||||
return Mat4 * vec4(1)
|
||||
}
|
||||
`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
op := &ebiten.DrawRectShaderOptions{}
|
||||
op.Uniforms = map[string]interface{}{
|
||||
"Mat4": []float32{
|
||||
1.0 / 256.0, 2.0 / 256.0, 3.0 / 256.0, 4.0 / 256.0,
|
||||
5.0 / 256.0, 6.0 / 256.0, 7.0 / 256.0, 8.0 / 256.0,
|
||||
9.0 / 256.0, 10.0 / 256.0, 11.0 / 256.0, 12.0 / 256.0,
|
||||
13.0 / 256.0, 14.0 / 256.0, 15.0 / 256.0, 16.0 / 256.0,
|
||||
},
|
||||
}
|
||||
dst.DrawRectShader(w, h, s, op)
|
||||
|
||||
for j := 0; j < h; j++ {
|
||||
for i := 0; i < w; i++ {
|
||||
got := dst.At(i, j).(color.RGBA)
|
||||
want := color.RGBA{28, 32, 36, 40}
|
||||
if !sameColors(got, want, 2) {
|
||||
t.Errorf("dst.At(%d, %d): got: %v, want: %v", i, j, got, want)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user