Pārlūkot izejas kodu

changing uniform transfers...

leonsal 8 gadi atpakaļ
vecāks
revīzija
e61c851b55

+ 10 - 4
gls/gls.go

@@ -583,9 +583,9 @@ func (gs *GLS) Uniform1fv(location int32, count int32, v []float32) {
 	gs.stats.Unisets++
 }
 
-func (gs *GLS) Uniform2fv(location int32, count int32, v []float32) {
+func (gs *GLS) Uniform2fv(location int32, count int32, v *float32) {
 
-	C.glUniform2fv(C.GLint(location), C.GLsizei(count), (*C.GLfloat)(&v[0]))
+	C.glUniform2fv(C.GLint(location), C.GLsizei(count), (*C.GLfloat)(v))
 	gs.stats.Unisets++
 }
 
@@ -595,9 +595,9 @@ func (gs *GLS) Uniform2fvUP(location int32, count int32, v unsafe.Pointer) {
 	gs.stats.Unisets++
 }
 
-func (gs *GLS) Uniform3fv(location int32, count int32, v []float32) {
+func (gs *GLS) Uniform3fv(location int32, count int32, v *float32) {
 
-	C.glUniform3fv(C.GLint(location), C.GLsizei(count), (*C.GLfloat)(&v[0]))
+	C.glUniform3fv(C.GLint(location), C.GLsizei(count), (*C.GLfloat)(v))
 	gs.stats.Unisets++
 }
 
@@ -613,6 +613,12 @@ func (gs *GLS) Uniform4fv(location int32, count int32, v []float32) {
 	gs.stats.Unisets++
 }
 
+func (gs *GLS) Uniform4fvUP(location int32, count int32, v unsafe.Pointer) {
+
+	C.glUniform4fv(C.GLint(location), C.GLsizei(count), (*C.GLfloat)(v))
+	gs.stats.Unisets++
+}
+
 func (gs *GLS) VertexAttribPointer(index uint32, size int32, xtype uint32, normalized bool, stride int32, offset uint32) {
 
 	C.glVertexAttribPointer(C.GLuint(index), C.GLint(size), C.GLenum(xtype), bool2c(normalized), C.GLsizei(stride), unsafe.Pointer(uintptr(offset)))

+ 4 - 713
gls/uniform.go

@@ -6,7 +6,6 @@ package gls
 
 import (
 	"fmt"
-	"github.com/g3n/engine/math32"
 )
 
 type Uniform2 struct {
@@ -17,7 +16,7 @@ type Uniform2 struct {
 	lastIndex int32  // last index
 }
 
-// Init initializes this uniform and sets its name
+// Init initializes this uniform location cache and sets its name
 func (u *Uniform2) Init(name string) {
 
 	u.name = name
@@ -35,7 +34,7 @@ func (u *Uniform2) Location(gs *GLS) int32 {
 	if handle != u.handle {
 		u.location = gs.prog.GetUniformLocation(u.name)
 		u.handle = handle
-		log.Error("Uniform:%s location:%v", u.name, u.location)
+		//log.Error("Uniform:%s location:%v", u.name, u.location)
 	}
 	return u.location
 }
@@ -49,721 +48,13 @@ func (u *Uniform2) LocationIdx(gs *GLS, idx int32) int32 {
 		u.nameIdx = fmt.Sprintf("%s[%d]", u.name, idx)
 		u.lastIndex = idx
 		u.handle = 0
-		log.Error("Uniform:%s rebuild nameIdx", u.nameIdx)
+		//log.Error("Uniform:%s rebuild nameIdx", u.nameIdx)
 	}
 	handle := gs.prog.Handle()
 	if handle != u.handle {
 		u.location = gs.prog.GetUniformLocation(u.nameIdx)
 		u.handle = handle
-		log.Error("Uniform:%s location:%v", u.nameIdx, u.location)
+		//log.Error("Uniform:%s location:%v", u.nameIdx, u.location)
 	}
 	return u.location
 }
-
-// ----------------------------------------------------------------------
-
-//
-// Type Uniform is the type for all uniforms
-//
-type Uniform struct {
-	name    string // original name
-	nameidx string // cached indexed name
-	idx     int    // index value of indexed name
-}
-
-// Location returns the current location of the uniform
-// for the current active program
-func (uni *Uniform) Location(gs *GLS) int32 {
-
-	loc := gs.prog.GetUniformLocation(uni.name)
-	return loc
-}
-
-// Location returns the current location of the uniform
-// for the current active program and index
-func (uni *Uniform) LocationIdx(gs *GLS, idx int) int32 {
-
-	// Rebuilds uniform indexed name if necessary
-	if uni.nameidx == "" || uni.idx != idx {
-		uni.nameidx = fmt.Sprintf("%s[%d]", uni.name, idx)
-		uni.idx = idx
-	}
-	loc := gs.prog.GetUniformLocation(uni.nameidx)
-	return loc
-}
-
-//
-// Type Uniform1i is a Uniform containing one int value
-//
-type Uniform1i struct {
-	Uniform
-	v0 int32
-}
-
-func NewUniform1i(name string) *Uniform1i {
-
-	uni := new(Uniform1i)
-	uni.name = name
-	return uni
-}
-
-func (uni *Uniform1i) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *Uniform1i) Set(v int32) {
-
-	uni.v0 = v
-}
-
-func (uni *Uniform1i) Get() int32 {
-
-	return uni.v0
-}
-
-func (uni *Uniform1i) Transfer(gs *GLS) {
-
-	gs.Uniform1i(uni.Location(gs), uni.v0)
-}
-
-func (uni *Uniform1i) TransferIdx(gs *GLS, idx int) {
-
-	gs.Uniform1i(uni.LocationIdx(gs, idx), uni.v0)
-}
-
-//
-// Type Uniform1f is a Uniform containing one float32 value
-//
-type Uniform1f struct {
-	Uniform
-	v0 float32
-}
-
-func NewUniform1f(name string) *Uniform1f {
-
-	uni := new(Uniform1f)
-	uni.Init(name)
-	return uni
-}
-
-func (uni *Uniform1f) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *Uniform1f) Set(v float32) {
-
-	uni.v0 = v
-}
-
-func (uni *Uniform1f) Get() float32 {
-
-	return uni.v0
-}
-
-func (uni *Uniform1f) Transfer(gs *GLS) {
-
-	gs.Uniform1f(uni.Location(gs), uni.v0)
-}
-
-func (uni *Uniform1f) TransferIdx(gs *GLS, idx int) {
-
-	gs.Uniform1f(uni.LocationIdx(gs, idx), uni.v0)
-}
-
-//
-// Type Uniform2f is a Uniform containing two float32 values
-//
-type Uniform2f struct {
-	Uniform
-	v0 float32
-	v1 float32
-}
-
-func NewUniform2f(name string) *Uniform2f {
-
-	uni := new(Uniform2f)
-	uni.Init(name)
-	return uni
-}
-
-func (uni *Uniform2f) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *Uniform2f) Set(v0, v1 float32) {
-
-	uni.v0 = v0
-	uni.v1 = v1
-}
-
-func (uni *Uniform2f) Get() (float32, float32) {
-
-	return uni.v0, uni.v1
-}
-
-func (uni *Uniform2f) SetVector2(v *math32.Vector2) {
-
-	uni.v0 = v.X
-	uni.v1 = v.Y
-}
-
-func (uni *Uniform2f) GetVector2() math32.Vector2 {
-
-	return math32.Vector2{uni.v0, uni.v1}
-}
-
-func (uni *Uniform2f) Transfer(gs *GLS) {
-
-	gs.Uniform2f(uni.Location(gs), uni.v0, uni.v1)
-}
-
-func (uni *Uniform2f) TransferIdx(gs *GLS, idx int) {
-
-	gs.Uniform2f(uni.LocationIdx(gs, idx), uni.v0, uni.v1)
-}
-
-//
-// Type Uniform3f is a Uniform containing three float32 values
-//
-type Uniform3f struct {
-	Uniform
-	v0 float32
-	v1 float32
-	v2 float32
-}
-
-func NewUniform3f(name string) *Uniform3f {
-
-	uni := new(Uniform3f)
-	uni.Init(name)
-	return uni
-}
-
-func (uni *Uniform3f) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *Uniform3f) Set(v0, v1, v2 float32) {
-
-	uni.v0 = v0
-	uni.v1 = v1
-	uni.v2 = v2
-}
-
-func (uni *Uniform3f) Get() (float32, float32, float32) {
-
-	return uni.v0, uni.v1, uni.v2
-}
-
-func (uni *Uniform3f) SetVector3(v *math32.Vector3) {
-
-	uni.v0 = v.X
-	uni.v1 = v.Y
-	uni.v2 = v.Z
-}
-
-func (uni *Uniform3f) GetVector3() math32.Vector3 {
-
-	return math32.Vector3{uni.v0, uni.v1, uni.v2}
-}
-
-func (uni *Uniform3f) SetColor(color *math32.Color) {
-
-	uni.v0 = color.R
-	uni.v1 = color.G
-	uni.v2 = color.B
-}
-
-func (uni *Uniform3f) GetColor() math32.Color {
-
-	return math32.Color{uni.v0, uni.v1, uni.v2}
-}
-
-func (uni *Uniform3f) Transfer(gl *GLS) {
-
-	loc := uni.Location(gl)
-	gl.Uniform3f(loc, uni.v0, uni.v1, uni.v2)
-	//log.Debug("Uniform3f: %s (%v) -> %v,%v,%v", uni.name, loc, uni.v0, uni.v1, uni.v2)
-}
-
-func (uni *Uniform3f) TransferIdx(gl *GLS, idx int) {
-
-	loc := uni.LocationIdx(gl, idx)
-	gl.Uniform3f(loc, uni.v0, uni.v1, uni.v2)
-	//log.Debug("Uniform3f: %s -> %v,%v,%v", uni.nameidx, uni.v0, uni.v1, uni.v2)
-}
-
-//
-// Type Uniform4f is a Uniform containing four float32 values
-//
-type Uniform4f struct {
-	Uniform
-	v0 float32
-	v1 float32
-	v2 float32
-	v3 float32
-}
-
-func NewUniform4f(name string) *Uniform4f {
-
-	uni := new(Uniform4f)
-	uni.Init(name)
-	return uni
-}
-
-func (uni *Uniform4f) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *Uniform4f) Set(v0, v1, v2, v3 float32) {
-
-	uni.v0 = v0
-	uni.v1 = v1
-	uni.v2 = v2
-	uni.v3 = v3
-}
-
-func (uni *Uniform4f) Get() (float32, float32, float32, float32) {
-
-	return uni.v0, uni.v1, uni.v2, uni.v3
-}
-
-func (uni *Uniform4f) SetVector4(v *math32.Vector4) {
-
-	uni.v0 = v.X
-	uni.v1 = v.Y
-	uni.v2 = v.Z
-	uni.v3 = v.W
-}
-
-func (uni *Uniform4f) GetVector4() math32.Vector4 {
-
-	return math32.Vector4{uni.v0, uni.v1, uni.v2, uni.v3}
-}
-
-func (uni *Uniform4f) SetColor4(c *math32.Color4) {
-
-	uni.v0 = c.R
-	uni.v1 = c.G
-	uni.v2 = c.B
-	uni.v3 = c.A
-}
-
-func (uni *Uniform4f) GetColor4() math32.Color4 {
-
-	return math32.Color4{uni.v0, uni.v1, uni.v2, uni.v3}
-}
-
-func (uni *Uniform4f) Transfer(gl *GLS) {
-
-	//log.Debug("Uniform4f.Transfer: %s %d", uni.name, uni.Location(gl))
-	gl.Uniform4f(uni.Location(gl), uni.v0, uni.v1, uni.v2, uni.v3)
-}
-
-func (uni *Uniform4f) TransferIdx(gl *GLS, idx int) {
-
-	gl.Uniform4f(uni.LocationIdx(gl, idx), uni.v0, uni.v1, uni.v2, uni.v3)
-}
-
-//
-// Type UniformMatrix3f is a Uniform containing nine float32 values
-// organized as 3x3 matrix
-//
-type UniformMatrix3f struct {
-	Uniform
-	v [9]float32
-}
-
-// NewUniformMatrix3 creates and returns a pointer to a new UniformMatrix3f
-// with the specified name
-func NewUniformMatrix3f(name string) *UniformMatrix3f {
-
-	uni := new(UniformMatrix3f)
-	uni.Init(name)
-	return uni
-}
-
-// Init initializes this uniform the specified name
-// It is normally used when the uniform is embedded in another object.
-func (uni *UniformMatrix3f) Init(name string) {
-
-	uni.name = name
-}
-
-// SetMatrix3 sets the matrix stored by the uniform
-func (uni *UniformMatrix3f) SetMatrix3(m *math32.Matrix3) {
-
-	uni.v = *m
-}
-
-// GetMatrix3 gets the matrix stored by the uniform
-func (uni *UniformMatrix3f) GetMatrix3() math32.Matrix3 {
-
-	return uni.v
-}
-
-// SetElement sets the value of the matrix element at the specified column and row
-func (uni *UniformMatrix3f) SetElement(col, row int, v float32) {
-
-	uni.v[col*3+row] = v
-}
-
-// GetElement gets the value of the matrix element at the specified column and row
-func (uni *UniformMatrix3f) GetElement(col, row int, v float32) float32 {
-
-	return uni.v[col*3+row]
-}
-
-// Set sets the value of the matrix element by its position starting
-// from 0 for col0, row0 to 8 from col2, row2.
-// This way the matrix can be considered as a vector of 9 elements
-func (uni *UniformMatrix3f) Set(pos int, v float32) {
-
-	uni.v[pos] = v
-}
-
-// Get gets the value of the matrix element by its position starting
-// from 0 for col0, row0 to 8 from col2, row2.
-// This way the matrix can be considered as a vector of 9 elements
-func (uni *UniformMatrix3f) Get(pos int) float32 {
-
-	return uni.v[pos]
-}
-
-// Transfer transfer the uniform matrix data to the graphics library
-func (uni *UniformMatrix3f) Transfer(gl *GLS) {
-
-	gl.UniformMatrix3fv(uni.Location(gl), 1, false, &uni.v[0])
-}
-
-// TransferIdx transfer the uniform matrix data to a specified destination index
-// of an uniform array to the graphics library
-func (uni *UniformMatrix3f) TransferIdx(gl *GLS, idx int) {
-
-	gl.UniformMatrix3fv(uni.LocationIdx(gl, idx), 1, false, &uni.v[0])
-}
-
-//
-// Type UniformMatrix4f is a Uniform containing sixteen float32 values
-// organized as 4x4 matrix
-//
-type UniformMatrix4f struct {
-	Uniform
-	v [16]float32
-}
-
-func NewUniformMatrix4f(name string) *UniformMatrix4f {
-
-	uni := new(UniformMatrix4f)
-	uni.Init(name)
-	return uni
-}
-
-func (uni *UniformMatrix4f) Init(name string) {
-
-	uni.name = name
-}
-
-func (uni *UniformMatrix4f) SetMatrix4(m *math32.Matrix4) {
-
-	uni.v = *m
-}
-
-func (uni *UniformMatrix4f) GetMatrix4() math32.Matrix4 {
-
-	return uni.v
-}
-
-func (uni *UniformMatrix4f) Transfer(gl *GLS) {
-
-	gl.UniformMatrix4fv(uni.Location(gl), 1, false, &uni.v[0])
-}
-
-func (uni *UniformMatrix4f) TransferIdx(gl *GLS, idx int) {
-
-	gl.UniformMatrix4fv(uni.LocationIdx(gl, idx), 1, false, &uni.v[0])
-}
-
-//
-// Type Uniform1fv is a uniform containing an array of float32 values
-//
-type Uniform1fv struct {
-	Uniform           // embedded uniform
-	v       []float32 // array of values
-}
-
-// NewUniform1fv creates and returns an uniform with array of float32 values
-// with the specified size
-func NewUniform1fv(name string, count int) *Uniform1fv {
-
-	uni := new(Uniform1fv)
-	uni.Init(name, count)
-	return uni
-}
-
-// Init initializes an Uniform1fv object with the specified name and count of float32 values.
-// It is normally used when the uniform is embedded in another object.
-func (uni *Uniform1fv) Init(name string, count int) {
-
-	uni.name = name
-	uni.v = make([]float32, count)
-}
-
-// SetVector3 sets the value of the elements of uniform starting at pos
-// from the specified Vector3 object.
-func (uni *Uniform1fv) SetVector3(pos int, v *math32.Vector3) {
-
-	uni.v[pos] = v.X
-	uni.v[pos+1] = v.Y
-	uni.v[pos+2] = v.Z
-}
-
-// GetVector3 gets the value of the elements of the uniform starting at
-// pos as a Vector3 object.
-func (uni *Uniform1fv) GetVector3(pos int) math32.Vector3 {
-
-	return math32.Vector3{uni.v[pos], uni.v[pos+1], uni.v[pos+2]}
-}
-
-// SetColor sets the value of the elements of the uniform starting at pos
-// from the specified Color object.
-func (uni *Uniform1fv) SetColor(pos int, color *math32.Color) {
-
-	uni.v[pos] = color.R
-	uni.v[pos+1] = color.G
-	uni.v[pos+2] = color.B
-}
-
-// GetColor gets the value of the elements of the uniform starting at pos
-// as a Color object.
-func (uni *Uniform1fv) GetColor(pos int) math32.Color {
-
-	return math32.Color{uni.v[pos], uni.v[pos+1], uni.v[pos+2]}
-}
-
-// Set sets the value of the element at the specified position
-func (uni *Uniform1fv) Set(pos int, v float32) {
-
-	uni.v[pos] = v
-}
-
-// Get gets the value of the element at the specified position
-func (uni *Uniform1fv) Get(pos int, v float32) float32 {
-
-	return uni.v[pos]
-}
-
-// TransferIdx transfer a block of 'count' values of this uniform starting at 'pos'.
-func (uni *Uniform1fv) TransferIdx(gl *GLS, pos, count int) {
-
-	gl.Uniform1fv(uni.LocationIdx(gl, pos), 1, uni.v[pos:])
-}
-
-//
-// Type Uniform3fv is a uniform containing an array of three float32 values
-//
-type Uniform3fv struct {
-	Uniform           // embedded uniform
-	count   int       // number of groups of 3 float32 values
-	v       []float32 // array of values
-}
-
-// NewUniform3fv creates and returns an uniform array with the specified size
-// of 3 float values
-func NewUniform3fv(name string, count int) *Uniform3fv {
-
-	uni := new(Uniform3fv)
-	uni.Init(name, count)
-	return uni
-}
-
-// Init initializes an Uniform3fv object with the specified name and count of 3 float32 groups.
-// It is normally used when the uniform is embedded in another object.
-func (uni *Uniform3fv) Init(name string, count int) {
-
-	uni.name = name
-	uni.count = count
-	uni.v = make([]float32, count*3)
-}
-
-// Set sets the value of all elements of the specified group of 3 floats for this uniform array
-func (uni *Uniform3fv) Set(idx int, v0, v1, v2 float32) {
-
-	pos := idx * 3
-	uni.v[pos] = v0
-	uni.v[pos+1] = v1
-	uni.v[pos+2] = v2
-}
-
-// Get gets the value of all elements of the specified group of 3 floats for this uniform array
-func (uni *Uniform3fv) Get(idx int) (v0, v1, v2 float32) {
-
-	pos := idx * 3
-	return uni.v[pos], uni.v[pos+1], uni.v[pos+2]
-}
-
-// SetVector3 sets the value of all elements for the specified group of 3 float for this uniform array
-// from the specified Vector3 object.
-func (uni *Uniform3fv) SetVector3(idx int, v *math32.Vector3) {
-
-	pos := idx * 3
-	uni.v[pos] = v.X
-	uni.v[pos+1] = v.Y
-	uni.v[pos+2] = v.Z
-}
-
-// GetVector3 gets the value of all elements of the specified group of 3 float for this uniform array
-// as a Vector3 object.
-func (uni *Uniform3fv) GetVector3(idx int) math32.Vector3 {
-
-	pos := idx * 3
-	return math32.Vector3{uni.v[pos], uni.v[pos+1], uni.v[pos+2]}
-}
-
-// SetColor sets the value of all elements of the specified group of 3 floats for this uniform array
-// form the specified Color object.
-func (uni *Uniform3fv) SetColor(idx int, color *math32.Color) {
-
-	pos := idx * 3
-	uni.v[pos] = color.R
-	uni.v[pos+1] = color.G
-	uni.v[pos+2] = color.B
-}
-
-// GetColor gets the value of all elements of the specified group of 3 float for this uniform array
-// as a Color object.
-func (uni *Uniform3fv) GetColor(idx int) math32.Color {
-
-	pos := idx * 3
-	return math32.Color{uni.v[pos], uni.v[pos+1], uni.v[pos+2]}
-}
-
-// SetPos sets the value at the specified position in the uniform array.
-func (uni *Uniform3fv) SetPos(pos int, v float32) {
-
-	uni.v[pos] = v
-}
-
-// GetPos gets the value at the specified position in the uniform array.
-func (uni *Uniform3fv) GetPos(pos int) float32 {
-
-	return uni.v[pos]
-}
-
-// Transfer transfers the current values of this uniform to the current shader program
-func (uni *Uniform3fv) Transfer(gl *GLS) {
-
-	gl.Uniform3fv(uni.Location(gl), int32(uni.count), uni.v)
-}
-
-// Transfer transfers the current values of this uniform to a specified
-// start position in the target uniform array.
-func (uni *Uniform3fv) TransferIdx(gl *GLS, idx int) {
-
-	gl.Uniform3fv(uni.LocationIdx(gl, idx), int32(uni.count), uni.v)
-}
-
-//
-// Type Uniform4fv is a Uniform containing an array of four float32 values
-//
-type Uniform4fv struct {
-	Uniform           // embedded uniform
-	count   int       // number of group of 4 float32 values
-	v       []float32 // array of values
-}
-
-// NewUniform4fv creates and returns an uniform array with the specified size
-// of 4 float values
-func NewUniform4fv(name string, count int) *Uniform4fv {
-
-	uni := new(Uniform4fv)
-	uni.Init(name, count)
-	return uni
-}
-
-// Init initializes an Uniform4fv object with the specified name and count of 4 float32 groups.
-// It is normally used when the uniform is embedded in another object.
-func (uni *Uniform4fv) Init(name string, count int) {
-
-	uni.name = name
-	uni.count = count
-	uni.v = make([]float32, count*4)
-}
-
-// Set sets the value of all elements of the specified group of 4 floats for this uniform array
-func (uni *Uniform4fv) Set(idx int, v0, v1, v2, v3 float32) {
-
-	pos := idx * 4
-	uni.v[pos] = v0
-	uni.v[pos+1] = v1
-	uni.v[pos+2] = v2
-	uni.v[pos+3] = v3
-}
-
-// Get gets the value of all elements of the specified group of 4 floats for this uniform array
-func (uni *Uniform4fv) Get(idx int) (v0, v1, v2, v3 float32) {
-
-	pos := idx * 4
-	return uni.v[pos], uni.v[pos+1], uni.v[pos+2], uni.v[pos+3]
-}
-
-// SetVector4 sets the value of all elements for the specified group of 4 float for this uniform array
-// from the specified Vector4 object.
-func (uni *Uniform4fv) SetVector4(idx int, v *math32.Vector4) {
-
-	pos := idx * 4
-	uni.v[pos] = v.X
-	uni.v[pos+1] = v.Y
-	uni.v[pos+2] = v.Z
-	uni.v[pos+3] = v.W
-}
-
-// GetVector4 gets the value of all elements of the specified group of 4 float for this uniform array
-// as a Vector4 object.
-func (uni *Uniform4fv) GetVector4(idx int) math32.Vector4 {
-
-	pos := idx * 4
-	return math32.Vector4{uni.v[pos], uni.v[pos+1], uni.v[pos+2], uni.v[pos+3]}
-}
-
-// SetColor4 sets the value of all elements of the specified group of 4 floats for this uniform array
-// form the specified Color4 object.
-func (uni *Uniform4fv) SetColor4(idx int, color *math32.Color4) {
-
-	pos := idx * 4
-	uni.v[pos] = color.R
-	uni.v[pos+1] = color.G
-	uni.v[pos+2] = color.B
-	uni.v[pos+3] = color.A
-}
-
-// GetColor4 gets the value of all elements of the specified group of 4 float for this uniform array
-// as a Color4 object.
-func (uni *Uniform4fv) GetColor4(idx int) math32.Color4 {
-
-	pos := idx * 4
-	return math32.Color4{uni.v[pos], uni.v[pos+1], uni.v[pos+2], uni.v[pos+3]}
-}
-
-// SetPos sets the value at the specified position in the uniform array.
-func (uni *Uniform4fv) SetPos(pos int, v float32) {
-
-	uni.v[pos] = v
-}
-
-// GetPos gets the value at the specified position in the uniform array.
-func (uni *Uniform4fv) GetPos(pos int) float32 {
-
-	return uni.v[pos]
-}
-
-// Transfer transfers the current values of this uniform to the current shader program
-func (uni *Uniform4fv) Transfer(gl *GLS) {
-
-	gl.Uniform4fv(uni.Location(gl), int32(uni.count), uni.v)
-}

+ 7 - 5
graphic/line_strip.go

@@ -13,8 +13,8 @@ import (
 )
 
 type LineStrip struct {
-	Graphic
-	mvpm gls.UniformMatrix4f // Model view projection matrix uniform
+	Graphic              // Embedded graphic object
+	uniMVP  gls.Uniform2 // Model view projection matrix uniform location cache
 }
 
 // NewLineStrip creates and returns a pointer to a new LineStrip graphic
@@ -24,7 +24,7 @@ func NewLineStrip(igeom geometry.IGeometry, imat material.IMaterial) *LineStrip
 	l := new(LineStrip)
 	l.Graphic.Init(igeom, gls.LINE_STRIP)
 	l.AddMaterial(l, imat, 0, 0)
-	l.mvpm.Init("MVP")
+	l.uniMVP.Init("MVP")
 	return l
 }
 
@@ -36,8 +36,10 @@ func (l *LineStrip) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ViewMatrix, &mw)
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvpm)
-	l.mvpm.SetMatrix4(&mvpm)
-	l.mvpm.Transfer(gs)
+
+	// Transfer mvpm uniform
+	location := l.uniMVP.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 }
 
 // Raycast satisfies the INode interface and checks the intersections

+ 7 - 5
graphic/lines.go

@@ -14,15 +14,15 @@ import (
 
 // Lines is a Graphic which is rendered as a collection of independent lines
 type Lines struct {
-	Graphic
-	mvpm gls.UniformMatrix4f // Model view projection matrix uniform
+	Graphic              // Embedded graphic object
+	uniMVP  gls.Uniform2 // Model view projection matrix uniform location cache
 }
 
 func (l *Lines) Init(igeom geometry.IGeometry, imat material.IMaterial) {
 
 	l.Graphic.Init(igeom, gls.LINES)
 	l.AddMaterial(l, imat, 0, 0)
-	l.mvpm.Init("MVP")
+	l.uniMVP.Init("MVP")
 }
 
 func NewLines(igeom geometry.IGeometry, imat material.IMaterial) *Lines {
@@ -40,8 +40,10 @@ func (l *Lines) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ViewMatrix, &mw)
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvpm)
-	l.mvpm.SetMatrix4(&mvpm)
-	l.mvpm.Transfer(gs)
+
+	// Transfer mvpm uniform
+	location := l.uniMVP.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 }
 
 // Raycast satisfies the INode interface and checks the intersections

+ 14 - 14
graphic/mesh.go

@@ -13,10 +13,10 @@ import (
 )
 
 type Mesh struct {
-	Graphic                     // Embedded graphic
-	mvm     gls.UniformMatrix4f // Model view matrix uniform
-	mvpm    gls.UniformMatrix4f // Model view projection matrix uniform
-	nm      gls.UniformMatrix3f // Normal matrix uniform
+	Graphic              // Embedded graphic
+	uniMVM  gls.Uniform2 // Model view matrix uniform location cache
+	uniMVPM gls.Uniform2 // Model view projection matrix uniform cache
+	uniNM   gls.Uniform2 // Normal matrix uniform cache
 }
 
 // NewMesh creates and returns a pointer to a mesh with the specified geometry and material
@@ -34,9 +34,9 @@ func (m *Mesh) Init(igeom geometry.IGeometry, imat material.IMaterial) {
 	m.Graphic.Init(igeom, gls.TRIANGLES)
 
 	// Initialize uniforms
-	m.mvm.Init("ModelViewMatrix")
-	m.mvpm.Init("MVP")
-	m.nm.Init("NormalMatrix")
+	m.uniMVM.Init("ModelViewMatrix")
+	m.uniMVPM.Init("MVP")
+	m.uniNM.Init("NormalMatrix")
 
 	// Adds single material if not nil
 	if imat != nil {
@@ -60,24 +60,24 @@ func (m *Mesh) AddGroupMaterial(imat material.IMaterial, gindex int) {
 // the model matrices.
 func (m *Mesh) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 
-	// Calculates model view matrix and updates uniform
+	// Calculates model view matrix and transfer uniform
 	mw := m.MatrixWorld()
 	var mvm math32.Matrix4
 	mvm.MultiplyMatrices(&rinfo.ViewMatrix, &mw)
-	m.mvm.SetMatrix4(&mvm)
-	m.mvm.Transfer(gs)
+	location := m.uniMVM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvm[0])
 
 	// Calculates model view projection matrix and updates uniform
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvm)
-	m.mvpm.SetMatrix4(&mvpm)
-	m.mvpm.Transfer(gs)
+	location = m.uniMVPM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 
 	// Calculates normal matrix and updates uniform
 	var nm math32.Matrix3
 	nm.GetNormalMatrix(&mvm)
-	m.nm.SetMatrix3(&nm)
-	m.nm.Transfer(gs)
+	location = m.uniNM.Location(gs)
+	gs.UniformMatrix3fv(location, 1, false, &nm[0])
 }
 
 // Raycast checks intersections between this geometry and the specified raycaster

+ 8 - 6
graphic/points.go

@@ -13,8 +13,8 @@ import (
 )
 
 type Points struct {
-	Graphic                     // Embedded graphic
-	mvpm    gls.UniformMatrix4f // Model view projection matrix uniform
+	Graphic              // Embedded graphic
+	uniMVPM gls.Uniform2 // Model view projection matrix uniform location cache
 }
 
 // NewPoints creates and returns a graphic points object with the specified
@@ -26,20 +26,22 @@ func NewPoints(igeom geometry.IGeometry, imat material.IMaterial) *Points {
 	if imat != nil {
 		p.AddMaterial(p, imat, 0, 0)
 	}
-	p.mvpm.Init("MVP")
+	p.uniMVPM.Init("MVP")
 	return p
 }
 
 // RenderSetup is called by the engine before rendering this graphic
 func (p *Points) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 
-	// Calculates model view projection matrix and updates uniform
+	// Calculates model view projection matrix
 	mw := p.MatrixWorld()
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ViewMatrix, &mw)
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvpm)
-	p.mvpm.SetMatrix4(&mvpm)
-	p.mvpm.Transfer(gs)
+
+	// Transfer model view projection matrix uniform
+	location := p.uniMVPM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 }
 
 // Raycast satisfies the INode interface and checks the intersections

+ 15 - 14
graphic/skybox.go

@@ -20,10 +20,10 @@ type SkyboxData struct {
 }
 
 type Skybox struct {
-	Graphic                     // embedded graphic object
-	mvm     gls.UniformMatrix4f // model view matrix uniform
-	mvpm    gls.UniformMatrix4f // model view projection matrix uniform
-	nm      gls.UniformMatrix3f // normal matrix uniform
+	Graphic              // embedded graphic object
+	uniMVM  gls.Uniform2 // model view matrix uniform location cache
+	uniMVPM gls.Uniform2 // model view projection matrix uniform cache
+	uniNM   gls.Uniform2 // normal matrix uniform cache
 }
 
 // NewSkybox creates and returns a pointer to a skybox with the specified textures
@@ -47,9 +47,9 @@ func NewSkybox(data SkyboxData) (*Skybox, error) {
 	}
 
 	// Creates uniforms
-	skybox.mvm.Init("ModelViewMatrix")
-	skybox.mvpm.Init("MVP")
-	skybox.nm.Init("NormalMatrix")
+	skybox.uniMVM.Init("ModelViewMatrix")
+	skybox.uniMVPM.Init("MVP")
+	skybox.uniNM.Init("NormalMatrix")
 
 	return skybox, nil
 }
@@ -72,19 +72,20 @@ func (skybox *Skybox) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 	mvm[13] = 0
 	mvm[14] = 0
 	// mvm.ExtractRotation(&rinfo.ViewMatrix) // TODO <- ExtractRotation does not work as expected?
-	skybox.mvm.SetMatrix4(&mvm)
-	skybox.mvm.Transfer(gs)
+
+	// Transfer mvp uniform
+	location := skybox.uniMVM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvm[0])
 
 	// Calculates model view projection matrix and updates uniform
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvm)
-	skybox.mvpm.SetMatrix4(&mvpm)
-	skybox.mvpm.Transfer(gs)
+	location = skybox.uniMVPM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 
 	// Calculates normal matrix and updates uniform
 	var nm math32.Matrix3
 	nm.GetNormalMatrix(&mvm)
-	skybox.nm.SetMatrix3(&nm)
-	skybox.nm.Transfer(gs)
-
+	location = skybox.uniNM.Location(gs)
+	gs.UniformMatrix3fv(location, 1, false, &nm[0])
 }

+ 5 - 5
graphic/sprite.go

@@ -13,8 +13,8 @@ import (
 )
 
 type Sprite struct {
-	Graphic                     // Embedded graphic
-	mvpm    gls.UniformMatrix4f // Model view projection matrix uniform
+	Graphic              // Embedded graphic
+	uniMVPM gls.Uniform2 // Model view projection matrix uniform location cache
 }
 
 // NewSprite creates and returns a pointer to a sprite with the specified dimensions and material
@@ -51,7 +51,7 @@ func NewSprite(width, height float32, imat material.IMaterial) *Sprite {
 	s.Graphic.Init(geom, gls.TRIANGLES)
 	s.AddMaterial(s, imat, 0, 0)
 
-	s.mvpm.Init("MVP")
+	s.uniMVPM.Init("MVP")
 	return s
 }
 
@@ -79,8 +79,8 @@ func (s *Sprite) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 	// Calculates final MVP and updates uniform
 	var mvpm math32.Matrix4
 	mvpm.MultiplyMatrices(&rinfo.ProjMatrix, &mvm_new)
-	s.mvpm.SetMatrix4(&mvpm)
-	s.mvpm.Transfer(gs)
+	location := s.uniMVPM.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mvpm[0])
 }
 
 // Raycast checks intersections between this geometry and the specified raycaster

+ 42 - 39
gui/chart.go

@@ -434,11 +434,11 @@ func (ch *Chart) recalc() {
 // vertical lines and line labels.
 //
 type chartScaleX struct {
-	Panel                // Embedded panel
-	chart  *Chart        // Container chart
-	lines  int           // Number of vertical lines
-	bounds gls.Uniform4f // Bound uniform in OpenGL window coordinates
-	mat    chartMaterial // Chart material
+	Panel                   // Embedded panel
+	chart     *Chart        // Container chart
+	lines     int           // Number of vertical lines
+	mat       chartMaterial // Chart material
+	uniBounds gls.Uniform2  // Bounds uniform location cache
 }
 
 // newChartScaleX creates and returns a pointer to a new chartScaleX for the specified
@@ -448,7 +448,7 @@ func newChartScaleX(chart *Chart, lines int, color *math32.Color) *chartScaleX {
 	sx := new(chartScaleX)
 	sx.chart = chart
 	sx.lines = lines
-	sx.bounds.Init("Bounds")
+	sx.uniBounds.Init("Bounds")
 
 	// Appends bottom horizontal line
 	positions := math32.NewArrayF32(0, 0)
@@ -494,16 +494,18 @@ func (sx *chartScaleX) recalc() {
 // Calculates the model matrix and transfer to OpenGL.
 func (sx *chartScaleX) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 
-	// Sets model matrix and transfer to shader
+	// Sets model matrix
 	var mm math32.Matrix4
 	sx.SetModelMatrix(gs, &mm)
-	sx.modelMatrixUni.SetMatrix4(&mm)
-	sx.modelMatrixUni.Transfer(gs)
+
+	// Transfer model matrix uniform
+	location := sx.uniMatrix.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mm[0])
 
 	// Sets bounds in OpenGL window coordinates and transfer to shader
 	_, _, _, height := gs.GetViewport()
-	sx.bounds.Set(sx.pospix.X, float32(height)-sx.pospix.Y, sx.width, sx.height)
-	sx.bounds.Transfer(gs)
+	location = sx.uniBounds.Location(gs)
+	gs.Uniform4f(location, sx.pospix.X, float32(height)-sx.pospix.Y, sx.width, sx.height)
 }
 
 //
@@ -511,11 +513,11 @@ func (sx *chartScaleX) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 // horizontal and labels.
 //
 type chartScaleY struct {
-	Panel                // Embedded panel
-	chart  *Chart        // Container chart
-	lines  int           // Number of horizontal lines
-	bounds gls.Uniform4f // Bound uniform in OpenGL window coordinates
-	mat    chartMaterial // Chart material
+	Panel                   // Embedded panel
+	chart     *Chart        // Container chart
+	lines     int           // Number of horizontal lines
+	mat       chartMaterial // Chart material
+	uniBounds gls.Uniform2  // Bounds uniform location cache
 }
 
 // newChartScaleY creates and returns a pointer to a new chartScaleY for the specified
@@ -528,7 +530,7 @@ func newChartScaleY(chart *Chart, lines int, color *math32.Color) *chartScaleY {
 	sy := new(chartScaleY)
 	sy.chart = chart
 	sy.lines = lines
-	sy.bounds.Init("Bounds")
+	sy.uniBounds.Init("Bounds")
 
 	// Appends left vertical line
 	positions := math32.NewArrayF32(0, 0)
@@ -577,16 +579,18 @@ func (sy *chartScaleY) recalc() {
 // Calculates the model matrix and transfer to OpenGL.
 func (sy *chartScaleY) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 
-	// Sets model matrix and transfer to shader
+	// Sets model matrix
 	var mm math32.Matrix4
 	sy.SetModelMatrix(gs, &mm)
-	sy.modelMatrixUni.SetMatrix4(&mm)
-	sy.modelMatrixUni.Transfer(gs)
+
+	// Transfer model matrix uniform
+	location := sy.uniMatrix.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mm[0])
 
 	// Sets bounds in OpenGL window coordinates and transfer to shader
 	_, _, _, height := gs.GetViewport()
-	sy.bounds.Set(sy.pospix.X, float32(height)-sy.pospix.Y, sy.width, sy.height)
-	sy.bounds.Transfer(gs)
+	location = sy.uniBounds.Location(gs)
+	gs.Uniform4f(location, sy.pospix.X, float32(height)-sy.pospix.Y, sy.width, sy.height)
 }
 
 //
@@ -597,17 +601,17 @@ type Graph struct {
 	chart     *Chart        // Container chart
 	color     math32.Color  // Line color
 	data      []float32     // Data y
-	bounds    gls.Uniform4f // Bound uniform in OpenGL window coordinates
 	mat       chartMaterial // Chart material
 	vbo       *gls.VBO
 	positions math32.ArrayF32
+	uniBounds gls.Uniform2 // Bounds uniform location cache
 }
 
 // newGraph creates and returns a pointer to a new graph for the specified chart
 func newGraph(chart *Chart, color *math32.Color, data []float32) *Graph {
 
 	lg := new(Graph)
-	lg.bounds.Init("Bounds")
+	lg.uniBounds.Init("Bounds")
 	lg.chart = chart
 	lg.color = *color
 	lg.data = data
@@ -632,7 +636,7 @@ func newGraph(chart *Chart, color *math32.Color, data []float32) *Graph {
 // SetColor sets the color of the graph
 func (lg *Graph) SetColor(color *math32.Color) {
 
-	lg.mat.color.SetColor(color)
+	lg.color = *color
 }
 
 // SetData sets the graph data
@@ -687,24 +691,27 @@ func (lg *Graph) recalc() {
 // Calculates the model matrix and transfer to OpenGL.
 func (lg *Graph) RenderSetup(gs *gls.GLS, rinfo *core.RenderInfo) {
 
-	// Sets model matrix and transfer to shader
+	// Sets model matrix
 	var mm math32.Matrix4
 	lg.SetModelMatrix(gs, &mm)
-	lg.modelMatrixUni.SetMatrix4(&mm)
-	lg.modelMatrixUni.Transfer(gs)
+
+	// Transfer model matrix uniform
+	location := lg.uniMatrix.Location(gs)
+	gs.UniformMatrix4fv(location, 1, false, &mm[0])
 
 	// Sets bounds in OpenGL window coordinates and transfer to shader
 	_, _, _, height := gs.GetViewport()
-	lg.bounds.Set(lg.pospix.X, float32(height)-lg.pospix.Y, lg.width, lg.height)
-	lg.bounds.Transfer(gs)
+	location = lg.uniBounds.Location(gs)
+	gs.Uniform4f(location, lg.pospix.X, float32(height)-lg.pospix.Y, lg.width, lg.height)
 }
 
 //
 // Chart material
 //
 type chartMaterial struct {
-	material.Material                // Embedded material
-	color             *gls.Uniform3f // Emissive color uniform
+	material.Material              // Embedded material
+	color             math32.Color // emissive color
+	uniColor          gls.Uniform2 // color uniform location cache
 }
 
 func (cm *chartMaterial) Init(color *math32.Color) {
@@ -712,18 +719,14 @@ func (cm *chartMaterial) Init(color *math32.Color) {
 	cm.Material.Init()
 	cm.SetShader("shaderChart")
 	cm.SetShaderUnique(true)
-
-	// Creates uniforms and adds to material
-	cm.color = gls.NewUniform3f("MatColor")
-
-	// Set initial values
-	cm.color.SetColor(color)
+	cm.uniColor.Init("MatColor")
+	cm.color = *color
 }
 
 func (cm *chartMaterial) RenderSetup(gs *gls.GLS) {
 
 	cm.Material.RenderSetup(gs)
-	cm.color.Transfer(gs)
+	gs.Uniform3f(cm.uniColor.Location(gs), cm.color.R, cm.color.G, cm.color.B)
 }
 
 //

+ 87 - 82
gui/panel.go

@@ -5,13 +5,15 @@
 package gui
 
 import (
+	"math"
+	"unsafe"
+
 	"github.com/g3n/engine/core"
 	"github.com/g3n/engine/geometry"
 	"github.com/g3n/engine/gls"
 	"github.com/g3n/engine/graphic"
 	"github.com/g3n/engine/material"
 	"github.com/g3n/engine/math32"
-	"math"
 )
 
 /*********************************************
@@ -51,43 +53,46 @@ type IPanel interface {
 // and a content area. The content area can be associated wit a texture
 // It is the building block of most GUI widgets.
 type Panel struct {
-	*graphic.Graphic                     // Embedded graphic
-	root             *Root               // pointer to root container
-	width            float32             // external width in pixels
-	height           float32             // external height in pixels
-	mat              *material.Material  // panel material
-	marginSizes      BorderSizes         // external margin sizes in pixel coordinates
-	borderSizes      BorderSizes         // border sizes in pixel coordinates
-	paddingSizes     BorderSizes         // padding sizes in pixel coordinates
-	content          Rect                // current content rectangle in pixel coordinates
-	modelMatrixUni   gls.UniformMatrix4f // model matrix uniform
-	panUni           gls.Uniform4fv      // uniform array with all panel dimensions and colors
-	pospix           math32.Vector3      // absolute position in pixels
-	posclip          math32.Vector3      // position in clip (NDC) coordinates
-	wclip            float32             // width in clip coordinates
-	hclip            float32             // height in clip coordinates
-	xmin             float32             // minimum absolute x this panel can use
-	xmax             float32             // maximum absolute x this panel can use
-	ymin             float32             // minimum absolute y this panel can use
-	ymax             float32             // maximum absolute y this panel can use
-	bounded          bool                // panel is bounded by its parent
-	enabled          bool                // enable event processing
-	cursorEnter      bool                // mouse enter dispatched
-	layout           ILayout             // current layout for children
-	layoutParams     interface{}         // current layout parameters used by container panel
+	*graphic.Graphic                    // Embedded graphic
+	root             *Root              // pointer to root container
+	width            float32            // external width in pixels
+	height           float32            // external height in pixels
+	mat              *material.Material // panel material
+	marginSizes      BorderSizes        // external margin sizes in pixel coordinates
+	borderSizes      BorderSizes        // border sizes in pixel coordinates
+	paddingSizes     BorderSizes        // padding sizes in pixel coordinates
+	content          Rect               // current content rectangle in pixel coordinates
+	pospix           math32.Vector3     // absolute position in pixels
+	posclip          math32.Vector3     // position in clip (NDC) coordinates
+	wclip            float32            // width in clip coordinates
+	hclip            float32            // height in clip coordinates
+	xmin             float32            // minimum absolute x this panel can use
+	xmax             float32            // maximum absolute x this panel can use
+	ymin             float32            // minimum absolute y this panel can use
+	ymax             float32            // maximum absolute y this panel can use
+	bounded          bool               // panel is bounded by its parent
+	enabled          bool               // enable event processing
+	cursorEnter      bool               // mouse enter dispatched
+	layout           ILayout            // current layout for children
+	layoutParams     interface{}        // current layout parameters used by container panel
+	uniMatrix        gls.Uniform2       // model matrix uniform location cache
+	uniPanel         gls.Uniform2       // panel parameters uniform location cache
+	udata            struct {           // Combined uniform data 8 * vec4
+		bounds        math32.Vector4 // panel bounds in texture coordinates
+		borders       math32.Vector4 // panel borders in texture coordinates
+		paddings      math32.Vector4 // panel paddings in texture coordinates
+		content       math32.Vector4 // panel content area in texture coordinates
+		bordersColor  math32.Color4  // panel border color
+		paddingsColor math32.Color4  // panel padding color
+		contentColor  math32.Color4  // panel content color
+		textureValid  float32        // texture valid flag (bool)
+		dummy         [3]float32     // complete 8 * vec4
+	}
 }
 
 const (
-	deltaZ          = -0.000001      // delta Z for bounded panels
-	deltaZunb       = deltaZ * 10000 // delta Z for unbounded panels
-	idxBounds       = 0              // index of uniform array for bounds coordinates
-	idxBorder       = 1              // index of uniform array for border coordinates
-	idxPadding      = 2              // index of uniform array for padding coordinates
-	idxContent      = 3              // index of uniform array for content coordinates
-	idxBorderColor  = 4              // index of uniform array for border color
-	idxPaddingColor = 5              // index of uniform array for padding color
-	idxContentColor = 6              // index of uniform array for content color
-	posTextureValid = 7 * 4          // position of uniform array for texture valid
+	deltaZ    = -0.000001      // delta Z for bounded panels
+	deltaZunb = deltaZ * 10000 // delta Z for unbounded panels
 )
 
 // NewPanel creates and returns a pointer to a new panel with the
@@ -135,12 +140,12 @@ func (p *Panel) Initialize(width, height float32) {
 	p.Graphic = graphic.NewGraphic(geom, gls.TRIANGLES)
 	p.AddMaterial(p, p.mat, 0, 0)
 
-	// Initialize uniforms
-	p.modelMatrixUni.Init("ModelMatrix")
-	p.panUni.Init("Panel", 8)
+	// Initialize uniforms location caches
+	p.uniMatrix.Init("ModelMatrix")
+	p.uniPanel.Init("Panel")
 
 	// Set defaults
-	p.panUni.Set(idxBorderColor, 0, 0, 0, 1)
+	p.udata.bordersColor = math32.Color4{0, 0, 0, 1}
 	p.bounded = true
 	p.enabled = true
 	p.resize(width, height)
@@ -153,12 +158,12 @@ func (p *Panel) InitializeGraphic(width, height float32, gr *graphic.Graphic) {
 	p.width = width
 	p.height = height
 
-	// Initializes uniforms
-	p.modelMatrixUni.Init("ModelMatrix")
-	p.panUni.Init("Panel", 8)
+	// Initializes uniforms location caches
+	p.uniMatrix.Init("ModelMatrix")
+	p.uniPanel.Init("Panel")
 
 	// Set defaults
-	p.panUni.Set(idxBorderColor, 0, 0, 0, 1)
+	p.udata.bordersColor = math32.Color4{0, 0, 0, 1}
 	p.bounded = true
 	p.enabled = true
 	p.resize(width, height)
@@ -373,47 +378,47 @@ func (p *Panel) Paddings() BorderSizes {
 // The borders opacity is set to 1.0 (full opaque)
 func (p *Panel) SetBordersColor(color *math32.Color) {
 
-	p.panUni.Set(idxBorderColor, color.R, color.G, color.B, 1)
+	p.udata.bordersColor = math32.Color4{color.R, color.G, color.B, 1}
 }
 
 // SetBordersColor4 sets the color and opacity of this panel borders
 func (p *Panel) SetBordersColor4(color *math32.Color4) {
 
-	p.panUni.SetColor4(idxBorderColor, color)
+	p.udata.bordersColor = *color
 }
 
 // BorderColor4 returns current border color
 func (p *Panel) BordersColor4() math32.Color4 {
 
-	return p.panUni.GetColor4(idxBorderColor)
+	return p.udata.bordersColor
 }
 
 // SetPaddingsColor sets the color of this panel paddings.
 func (p *Panel) SetPaddingsColor(color *math32.Color) {
 
-	p.panUni.Set(idxPaddingColor, color.R, color.G, color.B, 1)
+	p.udata.paddingsColor = math32.Color4{color.R, color.G, color.B, 1}
 }
 
 // SetColor sets the color of the panel paddings and content area
 func (p *Panel) SetColor(color *math32.Color) *Panel {
 
-	p.panUni.Set(idxPaddingColor, color.R, color.G, color.B, 1)
-	p.panUni.Set(idxContentColor, color.R, color.G, color.B, 1)
+	p.udata.paddingsColor = math32.Color4{color.R, color.G, color.B, 1}
+	p.udata.contentColor = p.udata.paddingsColor
 	return p
 }
 
 // SetColor4 sets the color of the panel paddings and content area
 func (p *Panel) SetColor4(color *math32.Color4) *Panel {
 
-	p.panUni.SetColor4(idxPaddingColor, color)
-	p.panUni.SetColor4(idxContentColor, color)
+	p.udata.paddingsColor = *color
+	p.udata.contentColor = *color
 	return p
 }
 
 // Color4 returns the current color of the panel content area
 func (p *Panel) Color4() math32.Color4 {
 
-	return p.panUni.GetColor4(idxContentColor)
+	return p.udata.contentColor
 }
 
 // SetContentSize sets this panel content size to the specified dimensions.
@@ -668,7 +673,7 @@ func (p *Panel) updateBounds(par *Panel) {
 		p.ymin = -math.MaxFloat32
 		p.xmax = math.MaxFloat32
 		p.ymax = math.MaxFloat32
-		p.panUni.Set(idxBounds, 0, 0, 1, 1)
+		p.udata.bounds = math32.Vector4{0, 0, 1, 1}
 		return
 	}
 	// If this panel is bounded to its parent, its coordinates are relative
@@ -741,8 +746,7 @@ func (p *Panel) updateBounds(par *Panel) {
 		}
 	}
 	// Sets bounds uniform
-	//p.boundsUni.Set(xmintex, ymintex, xmaxtex, ymaxtex)
-	p.panUni.Set(idxBounds, xmintex, ymintex, xmaxtex, ymaxtex)
+	p.udata.bounds = math32.Vector4{xmintex, ymintex, xmaxtex, ymaxtex}
 }
 
 // calcWidth calculates the panel external width in pixels
@@ -812,29 +816,26 @@ func (p *Panel) resize(width, height float32) {
 	p.height = p.marginSizes.Top + border.Height + p.marginSizes.Bottom
 
 	// Updates border uniform in texture coordinates (0,0 -> 1,1)
-	//p.borderUni.Set(
-	p.panUni.Set(idxBorder,
-		float32(border.X)/float32(p.width),
-		float32(border.Y)/float32(p.height),
-		float32(border.Width)/float32(p.width),
-		float32(border.Height)/float32(p.height),
-	)
+	p.udata.borders = math32.Vector4{
+		float32(border.X) / float32(p.width),
+		float32(border.Y) / float32(p.height),
+		float32(border.Width) / float32(p.width),
+		float32(border.Height) / float32(p.height),
+	}
 	// Updates padding uniform in texture coordinates (0,0 -> 1,1)
-	//p.paddingUni.Set(
-	p.panUni.Set(idxPadding,
-		float32(padding.X)/float32(p.width),
-		float32(padding.Y)/float32(p.height),
-		float32(padding.Width)/float32(p.width),
-		float32(padding.Height)/float32(p.height),
-	)
+	p.udata.paddings = math32.Vector4{
+		float32(padding.X) / float32(p.width),
+		float32(padding.Y) / float32(p.height),
+		float32(padding.Width) / float32(p.width),
+		float32(padding.Height) / float32(p.height),
+	}
 	// Updates content uniform in texture coordinates (0,0 -> 1,1)
-	//p.contentUni.Set(
-	p.panUni.Set(idxContent,
-		float32(p.content.X)/float32(p.width),
-		float32(p.content.Y)/float32(p.height),
-		float32(p.content.Width)/float32(p.width),
-		float32(p.content.Height)/float32(p.height),
-	)
+	p.udata.content = math32.Vector4{
+		float32(p.content.X) / float32(p.width),
+		float32(p.content.Y) / float32(p.height),
+		float32(p.content.Width) / float32(p.width),
+		float32(p.content.Height) / float32(p.height),
+	}
 	// Update layout and dispatch event
 	if p.layout != nil {
 		p.layout.Recalc(p)
@@ -848,19 +849,23 @@ func (p *Panel) RenderSetup(gl *gls.GLS, rinfo *core.RenderInfo) {
 	// Sets texture valid flag in uniforms
 	// depending if the material has texture
 	if p.mat.TextureCount() > 0 {
-		p.panUni.SetPos(posTextureValid, 1)
+		p.udata.textureValid = 1
 	} else {
-		p.panUni.SetPos(posTextureValid, 0)
+		p.udata.textureValid = 0
 	}
 
 	// Sets model matrix
 	var mm math32.Matrix4
 	p.SetModelMatrix(gl, &mm)
-	p.modelMatrixUni.SetMatrix4(&mm)
 
-	// Transfer uniforms
-	p.panUni.Transfer(gl)
-	p.modelMatrixUni.Transfer(gl)
+	// Transfer model matrix uniform
+	location := p.uniMatrix.Location(gl)
+	gl.UniformMatrix4fv(location, 1, false, &mm[0])
+
+	// Transfer panel parameters combined uniform
+	location = p.uniPanel.Location(gl)
+	const vec4count = 8
+	gl.Uniform4fvUP(location, vec4count, unsafe.Pointer(&p.udata))
 }
 
 // SetModelMatrix calculates and sets the specified matrix with the model matrix for this panel

+ 9 - 9
renderer/shaders/panel_fragment.glsl

@@ -2,15 +2,15 @@
 // Fragment Shader template
 //
 
-// Textures uniforms
-uniform sampler2D	MatTexture[1];
-uniform mat3		MatTexinfo[1];
+// Texture uniforms
+uniform sampler2D	MatTexture;
+uniform vec2		MatTexinfo[3];
 
-// Macros to access elements inside MatTexinfo uniform
-#define MatTexOffset(a)		MatTexinfo[a][0].xy
-#define MatTexRepeat(a)		MatTexinfo[a][1].xy
-#define MatTexFlipY(a)		bool(MatTexinfo[a][2].x)
-#define MatTexVisible(a)	bool(MatTexinfo[a][2].y)
+// Macros to access elements inside the MatTexinfo array
+#define MatTexOffset		MatTexinfo[0]
+#define MatTexRepeat		MatTexinfo[1]
+#define MatTexFlipY	    	bool(MatTexinfo[2].x) // not used
+#define MatTexVisible	    bool(MatTexinfo[2].y) // not used
 
 // Inputs from vertex shader
 in vec2 FragTexcoord;
@@ -79,7 +79,7 @@ void main() {
             vec2 offset = vec2(-Content[0], -Content[1]);
             vec2 factor = vec2(1/Content[2], 1/Content[3]);
             vec2 texcoord = (FragTexcoord + offset) * factor;
-            vec4 texColor = texture(MatTexture[0], texcoord * MatTexRepeat(0) + MatTexOffset(0));
+            vec4 texColor = texture(MatTexture, texcoord * MatTexRepeat + MatTexOffset);
             // Mix content color with texture color ???
             //color = mix(color, texColor, texColor.a);
             color = texColor;

+ 9 - 9
renderer/shaders/sources.go

@@ -434,15 +434,15 @@ const panel_fragment_source = `//
 // Fragment Shader template
 //
 
-// Textures uniforms
-uniform sampler2D	MatTexture[1];
-uniform mat3		MatTexinfo[1];
+// Texture uniforms
+uniform sampler2D	MatTexture;
+uniform vec2		MatTexinfo[3];
 
-// Macros to access elements inside MatTexinfo uniform
-#define MatTexOffset(a)		MatTexinfo[a][0].xy
-#define MatTexRepeat(a)		MatTexinfo[a][1].xy
-#define MatTexFlipY(a)		bool(MatTexinfo[a][2].x)
-#define MatTexVisible(a)	bool(MatTexinfo[a][2].y)
+// Macros to access elements inside the MatTexinfo array
+#define MatTexOffset		MatTexinfo[0]
+#define MatTexRepeat		MatTexinfo[1]
+#define MatTexFlipY	    	bool(MatTexinfo[2].x) // not used
+#define MatTexVisible	    bool(MatTexinfo[2].y) // not used
 
 // Inputs from vertex shader
 in vec2 FragTexcoord;
@@ -511,7 +511,7 @@ void main() {
             vec2 offset = vec2(-Content[0], -Content[1]);
             vec2 factor = vec2(1/Content[2], 1/Content[3]);
             vec2 texcoord = (FragTexcoord + offset) * factor;
-            vec4 texColor = texture(MatTexture[0], texcoord * MatTexRepeat(0) + MatTexOffset(0));
+            vec4 texColor = texture(MatTexture, texcoord * MatTexRepeat + MatTexOffset);
             // Mix content color with texture color ???
             //color = mix(color, texColor, texColor.a);
             color = texColor;

+ 1 - 3
texture/texture2D.go

@@ -64,7 +64,7 @@ func newTexture2D() *Texture2D {
 	t.uniUnit.Init("MatTexture")
 	t.uniInfo.Init("MatTexinfo")
 	t.SetOffset(0, 0)
-	t.SetRepeat(0, 0)
+	t.SetRepeat(1, 1)
 	t.SetFlipY(true)
 	t.SetVisible(true)
 	return t
@@ -339,11 +339,9 @@ func (t *Texture2D) RenderSetup(gs *gls.GLS, idx int) {
 	// Transfer texture unit uniform
 	location := t.uniUnit.LocationIdx(gs, int32(idx))
 	gs.Uniform1i(location, int32(idx))
-	log.Error("unit location:%v", location)
 
 	// Transfer texture info combined uniform
 	const vec2count = 3
 	location = t.uniInfo.LocationIdx(gs, vec2count*int32(idx))
-	log.Error("info location:%v count:%v udata:%v", location, vec2count, t.udata)
 	gs.Uniform2fvUP(location, vec2count, unsafe.Pointer(&t.udata))
 }