diff --git a/buffers/buffers.go b/buffers/buffers.go index 2927e96..414434e 100755 --- a/buffers/buffers.go +++ b/buffers/buffers.go @@ -2,39 +2,58 @@ package buffers import ( "github.com/bloeys/go-sdl-engine/logging" - "github.com/go-gl/gl/v4.6-compatibility/gl" + "github.com/go-gl/gl/v4.6-core/gl" ) -type BufferType int +type BufGLType int const ( - BufTypeUnknown BufferType = iota + BufGLTypeUnknown BufGLType = 0 + //Generic array of data. Should be used for most data like vertex positions, vertex colors etc. + BufGLTypeArray BufGLType = gl.ARRAY_BUFFER + BufGLTypeIndices BufGLType = gl.ELEMENT_ARRAY_BUFFER +) + +type BufType int + +const ( + BufTypeUnknown BufType = iota BufTypeVertPos BufTypeColor + BufTypeIndex ) -type BufferGLType int +func (bt BufType) GetBufferGLType() BufGLType { + switch bt { -const ( - //Generic array of data. Should be used for most data like vertex positions, vertex colors etc. - BufGLTypeArrayBuffer BufferGLType = gl.ARRAY_BUFFER -) + case BufTypeColor: + fallthrough + case BufTypeVertPos: + return BufGLTypeArray -type BufferUsage int + case BufTypeIndex: + return BufGLTypeIndices + default: + logging.WarnLog.Println("Unknown BufferType. BufferType: ", bt) + return BufGLTypeUnknown + } +} + +type BufUsage int const ( //Buffer is set only once and used many times - BufUsageStatic BufferUsage = gl.STATIC_DRAW + BufUsageStatic BufUsage = gl.STATIC_DRAW //Buffer is changed a lot and used many times - BufUsageDynamic BufferUsage = gl.DYNAMIC_DRAW + BufUsageDynamic BufUsage = gl.DYNAMIC_DRAW //Buffer is set only once and used by the GPU at most a few times - BufUsageStream BufferUsage = gl.STREAM_DRAW + BufUsageStream BufUsage = gl.STREAM_DRAW ) type Buffer struct { ID uint32 - Type BufferType - GLType BufferGLType + Type BufType + GLType BufGLType DataTypeInfo } @@ -50,9 +69,10 @@ type BufferObject struct { VAOID uint32 VertPosBuf *Buffer ColorBuf *Buffer + IndexBuf *Buffer } -func (bo *BufferObject) GenBuffer(data []float32, bufUsage BufferUsage, bufType BufferType, bufDataType DataType) { +func (bo *BufferObject) GenBuffer(data []float32, bufUsage BufUsage, bufType BufType, bufDataType DataType) { gl.BindVertexArray(bo.VAOID) @@ -66,7 +86,35 @@ func (bo *BufferObject) GenBuffer(data []float32, bufUsage BufferUsage, bufType buf := &Buffer{ ID: vboID, Type: bufType, - GLType: BufGLTypeArrayBuffer, + GLType: bufType.GetBufferGLType(), + DataTypeInfo: GetDataTypeInfo(bufDataType), + } + bo.SetBuffer(buf) + + //Fill buffer with data + gl.BindBuffer(uint32(buf.GLType), buf.ID) + gl.BufferData(uint32(buf.GLType), int(buf.DataTypeInfo.ElementSize)*len(data), gl.Ptr(data), uint32(bufUsage)) + + //Unbind everything + gl.BindVertexArray(0) + gl.BindBuffer(uint32(buf.GLType), 0) +} + +func (bo *BufferObject) GenBufferUint32(data []uint32, bufUsage BufUsage, bufType BufType, bufDataType DataType) { + + gl.BindVertexArray(bo.VAOID) + + //Create vertex buffer object + var vboID uint32 + gl.CreateBuffers(1, &vboID) + if vboID == 0 { + logging.ErrLog.Println("Failed to create openGL buffer") + } + + buf := &Buffer{ + ID: vboID, + Type: bufType, + GLType: bufType.GetBufferGLType(), DataTypeInfo: GetDataTypeInfo(bufDataType), } bo.SetBuffer(buf) @@ -87,6 +135,8 @@ func (bo *BufferObject) SetBuffer(buf *Buffer) { bo.VertPosBuf = buf case BufTypeColor: bo.ColorBuf = buf + case BufTypeIndex: + bo.IndexBuf = buf default: logging.WarnLog.Println("Unknown buffer type in SetBuffer. Type:", buf.Type) } diff --git a/buffers/dataType.go b/buffers/dataType.go index 6c9841f..b82de21 100755 --- a/buffers/dataType.go +++ b/buffers/dataType.go @@ -2,13 +2,14 @@ package buffers import ( "github.com/bloeys/go-sdl-engine/logging" - "github.com/go-gl/gl/v4.6-compatibility/gl" + "github.com/go-gl/gl/v4.6-core/gl" ) type DataType int const ( - DataTypeUnknown = iota + DataTypeUnknown DataType = iota + DataTypeUint32 DataTypeInt32 DataTypeFloat32 DataTypeFloat64 @@ -37,6 +38,8 @@ func (dti *DataTypeInfo) GetSize() int32 { func GetDataTypeInfo(dt DataType) DataTypeInfo { switch dt { + case DataTypeUint32: + fallthrough case DataTypeInt32: return DataTypeInfo{ ElementSize: 4, diff --git a/go.mod b/go.mod index e51a9b8..21522f5 100755 --- a/go.mod +++ b/go.mod @@ -5,3 +5,5 @@ go 1.17 require github.com/veandco/go-sdl2 v0.4.10 require github.com/go-gl/gl v0.0.0-20210905235341-f7a045908259 + +require github.com/bloeys/gglm v0.1.1 // indirect diff --git a/go.sum b/go.sum index b7c9fd6..d14eb5a 100755 --- a/go.sum +++ b/go.sum @@ -1,3 +1,5 @@ +github.com/bloeys/gglm v0.1.1 h1:juLE2OqobKKamMq7IKkplOJcZaM45CAcmbS0rCND3Hc= +github.com/bloeys/gglm v0.1.1/go.mod h1:qwJQ0WzV191wAMwlGicbfbChbKoSedMk7gFFX6GnyOk= github.com/go-gl/gl v0.0.0-20210905235341-f7a045908259 h1:8q7+xl2D2qHPLTII1t4vSMNP2VKwDcn+Avf2WXvdB1A= github.com/go-gl/gl v0.0.0-20210905235341-f7a045908259/go.mod h1:wjpnOv6ONl2SuJSxqCPVaPZibGFdSci9HFocT9qtVYM= github.com/veandco/go-sdl2 v0.4.10 h1:8QoD2bhWl7SbQDflIAUYWfl9Vq+mT8/boJFAUzAScgY= diff --git a/main.go b/main.go index 87a93fd..62f4927 100755 --- a/main.go +++ b/main.go @@ -1,11 +1,13 @@ package main import ( + "github.com/bloeys/gglm/gglm" "github.com/bloeys/go-sdl-engine/buffers" "github.com/bloeys/go-sdl-engine/input" "github.com/bloeys/go-sdl-engine/logging" + "github.com/bloeys/go-sdl-engine/res/models" "github.com/bloeys/go-sdl-engine/shaders" - "github.com/go-gl/gl/v4.6-compatibility/gl" + "github.com/go-gl/gl/v4.6-core/gl" "github.com/veandco/go-sdl2/sdl" ) @@ -48,8 +50,16 @@ func main() { simpleShader.SetAttribute("vertPos", bo, bo.VertPosBuf) simpleShader.EnableAttribute("vertPos") - simpleShader.SetAttribute("vertColor", bo, bo.ColorBuf) - simpleShader.EnableAttribute("vertColor") + // simpleShader.SetAttribute("vertColor", bo, bo.ColorBuf) + // simpleShader.EnableAttribute("vertColor") + + modelMat := gglm.NewTrMatId() + translationMat := gglm.NewTranslationMat(gglm.NewVec3(-0.5, 0, 0)) + scaleMat := gglm.NewScaleMat(gglm.NewVec3(0.25, 0.25, 0.25)) + rotMat := gglm.NewRotMat(gglm.NewQuatEuler(gglm.NewVec3(0, 0, 0).AsRad())) + + modelMat.Mul(translationMat.Mul(rotMat.Mul(scaleMat))) + simpleShader.SetUnifMat4("modelMat", &modelMat.Mat4) //Game loop for isRunning { @@ -109,27 +119,32 @@ func loadBuffers() { vertices := []float32{ -0.5, 0.5, 0, - 0.5, 0.5, 0, - -0.5, -0.5, 0, - 0.5, 0.5, 0, 0.5, -0.5, 0, -0.5, -0.5, 0, } + // colors := []float32{ + // 1, 0, 0, + // 0, 0, 1, + // 0, 0, 1, + // 0, 0, 1, + // } + indices := []uint32{0, 1, 3, 1, 2, 3} - colors := []float32{ - 1, 0, 0, - 0, 0, 1, - 0, 0, 1, - - 0, 0, 1, - 0, 0, 1, - 0, 0, 1, + //Load obj + objInfo, err := models.LoadObj("./res/models/obj.obj") + if err != nil { + panic(err) } + logging.InfoLog.Printf("%v", objInfo.TriIndices) + + vertices = objInfo.VertPos + indices = objInfo.TriIndices bo = buffers.NewBufferObject() bo.GenBuffer(vertices, buffers.BufUsageStatic, buffers.BufTypeVertPos, buffers.DataTypeVec3) - bo.GenBuffer(colors, buffers.BufUsageStatic, buffers.BufTypeColor, buffers.DataTypeVec3) + // bo.GenBuffer(colors, buffers.BufUsageStatic, buffers.BufTypeColor, buffers.DataTypeVec3) + bo.GenBufferUint32(indices, buffers.BufUsageStatic, buffers.BufTypeIndex, buffers.DataTypeUint32) } func handleInputs() { @@ -162,7 +177,7 @@ func draw() { //DRAW bo.Activate() - gl.DrawArrays(gl.TRIANGLES, 0, 6) + gl.DrawElements(gl.TRIANGLES, 36, gl.UNSIGNED_INT, gl.PtrOffset(0)) bo.Deactivate() window.GLSwap() diff --git a/res/models/loader.go b/res/models/loader.go new file mode 100755 index 0000000..b32c291 --- /dev/null +++ b/res/models/loader.go @@ -0,0 +1,73 @@ +package models + +import ( + "os" + "strconv" + "strings" + + "github.com/bloeys/go-sdl-engine/logging" +) + +type ObjInfo struct { + VertPos []float32 + TriIndices []uint32 +} + +func LoadObj(file string) (objInfo ObjInfo, err error) { + + b, err := os.ReadFile(file) + if err != nil { + return objInfo, err + } + + lines := strings.Split(string(b), "\n") + for i := 0; i < len(lines); i++ { + + s := strings.SplitN(lines[i], " ", 2) + switch s[0] { + case "v": + + vertPosStrings := strings.Split(s[1], " ") + + f, err := strconv.ParseFloat(vertPosStrings[0], 32) + if err != nil { + return objInfo, err + } + objInfo.VertPos = append(objInfo.VertPos, float32(f)) + + f, err = strconv.ParseFloat(vertPosStrings[1], 32) + if err != nil { + return objInfo, err + } + objInfo.VertPos = append(objInfo.VertPos, float32(f)) + + f, err = strconv.ParseFloat(vertPosStrings[2], 32) + if err != nil { + return objInfo, err + } + objInfo.VertPos = append(objInfo.VertPos, float32(f)) + + case "f": + + facesStrings := strings.Split(s[1], " ") + objInfo.TriIndices = append(objInfo.TriIndices, getVertIndexFromFace(facesStrings[0])) + objInfo.TriIndices = append(objInfo.TriIndices, getVertIndexFromFace(facesStrings[1])) + objInfo.TriIndices = append(objInfo.TriIndices, getVertIndexFromFace(facesStrings[2])) + + default: + } + } + + return objInfo, nil +} + +func getVertIndexFromFace(f string) uint32 { + + indxStr := strings.SplitN(f, "/", 2)[0] + index, err := strconv.Atoi(indxStr) + if err != nil { + logging.ErrLog.Printf("Invalid face index '%v'. Err: %v", indxStr, err) + return 0 + } + return uint32(index) - 1 +} diff --git a/res/models/obj.obj b/res/models/obj.obj new file mode 100755 index 0000000..120d61f --- /dev/null +++ b/res/models/obj.obj @@ -0,0 +1,46 @@ +# Blender v2.92.0 OBJ File: '' +# www.blender.org +mtllib obj.mtl +o Cube +v 2.275618 1.000000 0.349413 +v 3.520138 -1.000000 0.102233 +v 2.275618 1.000000 0.752820 +v 3.520138 -1.000000 1.000000 +v 0.244520 1.000000 0.349413 +v -1.000000 -1.000000 0.102233 +v 0.244520 1.000000 0.752820 +v -1.000000 -1.000000 1.000000 +vt 0.806168 0.568832 +vt 0.693832 0.681168 +vt 0.693832 0.568832 +vt 0.375000 1.000000 +vt 0.375000 0.750000 +vt 0.375000 0.000000 +vt 0.625000 0.250000 +vt 0.375000 0.250000 +vt 0.375000 0.500000 +vt 0.125000 0.750000 +vt 0.125000 0.500000 +vt 0.806168 0.681168 +vt 0.625000 0.931168 +vt 0.625000 0.068832 +vn 0.0000 1.0000 0.0000 +vn 0.0000 0.1227 0.9924 +vn -0.8490 0.5283 0.0000 +vn 0.0000 -1.0000 0.0000 +vn 0.8490 0.5283 0.0000 +vn 0.0000 0.1227 -0.9924 +usemtl Material +s off +f 5/1/1 3/2/1 1/3/1 +f 3/2/2 8/4/2 4/5/2 +f 8/6/3 5/7/3 6/8/3 +f 2/9/4 8/10/4 6/11/4 +f 1/3/5 4/5/5 2/9/5 +f 5/7/6 2/9/6 6/8/6 +f 5/1/1 7/12/1 3/2/1 +f 3/2/2 7/13/2 8/4/2 +f 8/6/3 7/14/3 5/7/3 +f 2/9/4 4/5/4 8/10/4 +f 1/3/5 3/2/5 4/5/5 +f 5/7/6 1/3/6 2/9/6 diff --git a/res/shaders/simple.frag.glsl b/res/shaders/simple.frag.glsl index 5853b71..3604487 100755 --- a/res/shaders/simple.frag.glsl +++ b/res/shaders/simple.frag.glsl @@ -6,5 +6,6 @@ out vec4 fragColor; void main() { - fragColor = vec4(outColor, 1.0); + fragColor = vec4(1,1,1, 1.0); + // fragColor = vec4(outColor, 1.0); } diff --git a/res/shaders/simple.vert.glsl b/res/shaders/simple.vert.glsl index d8154e4..aab2d12 100755 --- a/res/shaders/simple.vert.glsl +++ b/res/shaders/simple.vert.glsl @@ -5,8 +5,10 @@ in vec3 vertColor; out vec3 outColor; +uniform mat4 modelMat; + void main() { outColor = vertColor; - gl_Position = vec4(vertPos, 1.0); // vec4(vertPos.x, vertPos.y, vertPos.z, 1.0) + gl_Position = modelMat * (vec4(vertPos, 1.0)); // vec4(vertPos.x, vertPos.y, vertPos.z, 1.0) } \ No newline at end of file diff --git a/shaders/shader_program.go b/shaders/shader_program.go index 2632e6e..4daa1ed 100755 --- a/shaders/shader_program.go +++ b/shaders/shader_program.go @@ -1,9 +1,10 @@ package shaders import ( + "github.com/bloeys/gglm/gglm" "github.com/bloeys/go-sdl-engine/buffers" "github.com/bloeys/go-sdl-engine/logging" - "github.com/go-gl/gl/v4.6-compatibility/gl" + "github.com/go-gl/gl/v4.6-core/gl" ) type ShaderProgram struct { @@ -69,6 +70,36 @@ func (sp *ShaderProgram) DisableAttribute(attribName string) { gl.DisableVertexAttribArray(uint32(sp.GetAttribLoc(attribName))) } +func (sp *ShaderProgram) SetUnifVec2(uniformName string, vec2 *gglm.Vec2) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniform2fv(sp.ID, loc, 1, &vec2.Data[0]) +} + +func (sp *ShaderProgram) SetUnifVec3(uniformName string, vec3 *gglm.Vec3) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniform3fv(sp.ID, loc, 1, &vec3.Data[0]) +} + +func (sp *ShaderProgram) SetUnifVec4(uniformName string, vec4 *gglm.Vec4) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniform4fv(sp.ID, loc, 1, &vec4.Data[0]) +} + +func (sp *ShaderProgram) SetUnifMat2(uniformName string, mat2 *gglm.Mat2) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniformMatrix2fv(sp.ID, loc, 1, true, &mat2.Data[0]) +} + +func (sp *ShaderProgram) SetUnifMat3(uniformName string, mat3 *gglm.Mat3) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniformMatrix3fv(sp.ID, loc, 1, true, &mat3.Data[0]) +} + +func (sp *ShaderProgram) SetUnifMat4(uniformName string, mat4 *gglm.Mat4) { + loc := gl.GetUniformLocation(sp.ID, gl.Str(uniformName+"\x00")) + gl.ProgramUniformMatrix4fv(sp.ID, loc, 1, true, &mat4.Data[0]) +} + func (sp *ShaderProgram) Delete() { gl.DeleteProgram(sp.ID) } diff --git a/shaders/shader_types.go b/shaders/shader_types.go index f462404..26dfe2a 100755 --- a/shaders/shader_types.go +++ b/shaders/shader_types.go @@ -1,6 +1,6 @@ package shaders -import "github.com/go-gl/gl/v4.6-compatibility/gl" +import "github.com/go-gl/gl/v4.6-core/gl" type ShaderType int diff --git a/shaders/shaders.go b/shaders/shaders.go index a78406b..2178816 100755 --- a/shaders/shaders.go +++ b/shaders/shaders.go @@ -6,7 +6,7 @@ import ( "strings" "github.com/bloeys/go-sdl-engine/logging" - "github.com/go-gl/gl/v4.6-compatibility/gl" + "github.com/go-gl/gl/v4.6-core/gl" ) type Shader struct {