mirror of
https://github.com/bloeys/nmage.git
synced 2025-12-29 13:28:20 +00:00
Compare commits
7 Commits
v0.23.1
...
8c6b1d5821
| Author | SHA1 | Date | |
|---|---|---|---|
| 8c6b1d5821 | |||
| dfd1fe9c5e | |||
| 24613823a7 | |||
| 0386f441d6 | |||
| 57ab851534 | |||
| d523c0951b | |||
| abd7079e61 |
5
.gitignore
vendored
5
.gitignore
vendored
@ -15,4 +15,7 @@
|
||||
vendor/
|
||||
.vscode/
|
||||
imgui.ini
|
||||
*~
|
||||
*~
|
||||
|
||||
# Custom
|
||||
*.pprof
|
||||
@ -41,7 +41,7 @@ func (c *Camera) Update() {
|
||||
c.ViewMat = gglm.LookAtRH(&c.Pos, c.Pos.Clone().Add(&c.Forward), &c.WorldUp).Mat4
|
||||
|
||||
if c.Type == Type_Perspective {
|
||||
c.ProjMat = *gglm.Perspective(c.Fov, c.AspectRatio, c.NearClip, c.FarClip)
|
||||
c.ProjMat = gglm.Perspective(c.Fov, c.AspectRatio, c.NearClip, c.FarClip)
|
||||
} else {
|
||||
c.ProjMat = gglm.Ortho(c.Left, c.Right, c.Top, c.Bottom, c.NearClip, c.FarClip).Mat4
|
||||
}
|
||||
@ -59,9 +59,9 @@ func (c *Camera) UpdateRotation(pitch, yaw float32) {
|
||||
c.Update()
|
||||
}
|
||||
|
||||
func NewPerspective(pos, forward, worldUp *gglm.Vec3, nearClip, farClip, fovRadians, aspectRatio float32) *Camera {
|
||||
func NewPerspective(pos, forward, worldUp *gglm.Vec3, nearClip, farClip, fovRadians, aspectRatio float32) Camera {
|
||||
|
||||
cam := &Camera{
|
||||
cam := Camera{
|
||||
Type: Type_Perspective,
|
||||
Pos: *pos,
|
||||
Forward: *forward,
|
||||
@ -78,9 +78,9 @@ func NewPerspective(pos, forward, worldUp *gglm.Vec3, nearClip, farClip, fovRadi
|
||||
return cam
|
||||
}
|
||||
|
||||
func NewOrthographic(pos, forward, worldUp *gglm.Vec3, nearClip, farClip, left, right, top, bottom float32) *Camera {
|
||||
func NewOrthographic(pos, forward, worldUp *gglm.Vec3, nearClip, farClip, left, right, top, bottom float32) Camera {
|
||||
|
||||
cam := &Camera{
|
||||
cam := Camera{
|
||||
Type: Type_Orthographic,
|
||||
Pos: *pos,
|
||||
Forward: *forward,
|
||||
|
||||
@ -58,25 +58,15 @@ func (w *Window) handleInputs() {
|
||||
case *sdl.KeyboardEvent:
|
||||
|
||||
input.HandleKeyboardEvent(e)
|
||||
|
||||
// Send modifier key updates to imgui (based on the imgui SDL backend)
|
||||
imIo.AddKeyEvent(imgui.ModCtrl, e.Keysym.Mod&sdl.KMOD_CTRL != 0)
|
||||
imIo.AddKeyEvent(imgui.ModShift, e.Keysym.Mod&sdl.KMOD_SHIFT != 0)
|
||||
imIo.AddKeyEvent(imgui.ModAlt, e.Keysym.Mod&sdl.KMOD_ALT != 0)
|
||||
imIo.AddKeyEvent(imgui.ModSuper, e.Keysym.Mod&sdl.KMOD_GUI != 0)
|
||||
|
||||
imIo.AddKeyEvent(nmageimgui.SdlScancodeToImGuiKey(e.Keysym.Scancode), e.Type == sdl.KEYDOWN)
|
||||
|
||||
// Send modifier key updates to imgui
|
||||
if e.Keysym.Sym == sdl.K_LCTRL || e.Keysym.Sym == sdl.K_RCTRL {
|
||||
imIo.SetKeyCtrl(e.Type == sdl.KEYDOWN)
|
||||
}
|
||||
|
||||
if e.Keysym.Sym == sdl.K_LSHIFT || e.Keysym.Sym == sdl.K_RSHIFT {
|
||||
imIo.SetKeyShift(e.Type == sdl.KEYDOWN)
|
||||
}
|
||||
|
||||
if e.Keysym.Sym == sdl.K_LALT || e.Keysym.Sym == sdl.K_RALT {
|
||||
imIo.SetKeyAlt(e.Type == sdl.KEYDOWN)
|
||||
}
|
||||
|
||||
if e.Keysym.Sym == sdl.K_LGUI || e.Keysym.Sym == sdl.K_RGUI {
|
||||
imIo.SetKeySuper(e.Type == sdl.KEYDOWN)
|
||||
}
|
||||
|
||||
case *sdl.TextInputEvent:
|
||||
imIo.AddInputCharactersUTF8(e.GetText())
|
||||
|
||||
@ -177,42 +167,44 @@ func initSDL() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func CreateOpenGLWindow(title string, x, y, width, height int32, flags WindowFlags, rend renderer.Render) (*Window, error) {
|
||||
func CreateOpenGLWindow(title string, x, y, width, height int32, flags WindowFlags, rend renderer.Render) (Window, error) {
|
||||
return createWindow(title, x, y, width, height, WindowFlags_OPENGL|flags, rend)
|
||||
}
|
||||
|
||||
func CreateOpenGLWindowCentered(title string, width, height int32, flags WindowFlags, rend renderer.Render) (*Window, error) {
|
||||
func CreateOpenGLWindowCentered(title string, width, height int32, flags WindowFlags, rend renderer.Render) (Window, error) {
|
||||
return createWindow(title, sdl.WINDOWPOS_CENTERED, sdl.WINDOWPOS_CENTERED, width, height, WindowFlags_OPENGL|flags, rend)
|
||||
}
|
||||
|
||||
func createWindow(title string, x, y, width, height int32, flags WindowFlags, rend renderer.Render) (*Window, error) {
|
||||
func createWindow(title string, x, y, width, height int32, flags WindowFlags, rend renderer.Render) (Window, error) {
|
||||
|
||||
assert.T(isInited, "engine.Init() was not called!")
|
||||
|
||||
sdlWin, err := sdl.CreateWindow(title, x, y, width, height, uint32(flags))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
win := &Window{
|
||||
SDLWin: sdlWin,
|
||||
win := Window{
|
||||
SDLWin: nil,
|
||||
EventCallbacks: make([]func(sdl.Event), 0),
|
||||
Rend: rend,
|
||||
}
|
||||
|
||||
win.GlCtx, err = sdlWin.GLCreateContext()
|
||||
var err error
|
||||
|
||||
win.SDLWin, err = sdl.CreateWindow(title, x, y, width, height, uint32(flags))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return win, err
|
||||
}
|
||||
|
||||
win.GlCtx, err = win.SDLWin.GLCreateContext()
|
||||
if err != nil {
|
||||
return win, err
|
||||
}
|
||||
|
||||
err = initOpenGL()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return win, err
|
||||
}
|
||||
|
||||
// Get rid of the blinding white startup screen (unfortunately there is still one frame of white)
|
||||
gl.Clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT | gl.STENCIL_BUFFER_BIT)
|
||||
sdlWin.GLSwap()
|
||||
win.SDLWin.GLSwap()
|
||||
|
||||
return win, err
|
||||
}
|
||||
|
||||
2
go.mod
2
go.mod
@ -8,7 +8,7 @@ require github.com/go-gl/gl v0.0.0-20211210172815-726fda9656d6
|
||||
|
||||
require (
|
||||
github.com/bloeys/assimp-go v0.4.4
|
||||
github.com/bloeys/gglm v0.43.0
|
||||
github.com/bloeys/gglm v0.49.0
|
||||
)
|
||||
|
||||
require (
|
||||
|
||||
4
go.sum
4
go.sum
@ -2,8 +2,8 @@ github.com/AllenDang/cimgui-go v0.0.0-20230720025235-f2ff398a66b2 h1:3HA/5qD8Rim
|
||||
github.com/AllenDang/cimgui-go v0.0.0-20230720025235-f2ff398a66b2/go.mod h1:iNfbIyOBN8k3XScMxULbrwYbPsXEAUD0Jb6UwrspQb8=
|
||||
github.com/bloeys/assimp-go v0.4.4 h1:Yn5e/RpE0Oes0YMBy8O7KkwAO4R/RpgrZPJCt08dVIU=
|
||||
github.com/bloeys/assimp-go v0.4.4/go.mod h1:my3yRxT7CfOztmvi+0svmwbaqw0KFrxaHxncoyaEIP0=
|
||||
github.com/bloeys/gglm v0.43.0 h1:ZpOghR3PHfpkigTDh+FqxLsF0gN8CD6s/bWoei6LyxI=
|
||||
github.com/bloeys/gglm v0.43.0/go.mod h1:qwJQ0WzV191wAMwlGicbfbChbKoSedMk7gFFX6GnyOk=
|
||||
github.com/bloeys/gglm v0.49.0 h1:YtbyHpszYhjnxw7KVV0LaCdBktRMqfGx/i37EMomxsE=
|
||||
github.com/bloeys/gglm v0.49.0/go.mod h1:qwJQ0WzV191wAMwlGicbfbChbKoSedMk7gFFX6GnyOk=
|
||||
github.com/go-gl/gl v0.0.0-20211210172815-726fda9656d6 h1:zDw5v7qm4yH7N8C8uWd+8Ii9rROdgWxQuGoJ9WDXxfk=
|
||||
github.com/go-gl/gl v0.0.0-20211210172815-726fda9656d6/go.mod h1:9YTyiznxEY1fVinfM7RvRcjRHbw2xLBJ3AAGIT0I4Nw=
|
||||
github.com/mandykoh/go-parallel v0.1.0 h1:7vJMNMC4dsbgZdkAb2A8tV5ENY1v7VxIO1wzQWZoT8k=
|
||||
|
||||
284
main.go
284
main.go
@ -2,7 +2,9 @@ package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"runtime"
|
||||
"runtime/pprof"
|
||||
"strconv"
|
||||
|
||||
imgui "github.com/AllenDang/cimgui-go"
|
||||
@ -33,19 +35,19 @@ import (
|
||||
- Directional light shadows ✅
|
||||
- Point light shadows ✅
|
||||
- Spotlight shadows ✅
|
||||
- Create VAO struct independent from VBO to support multi-VBO use cases (e.g. instancing) ✅
|
||||
- UBO support
|
||||
- HDR
|
||||
- Cascaded shadow mapping
|
||||
- Skeletal animations
|
||||
- In some cases we DO want input even when captured by UI. We need two systems within input package, one filtered and one not
|
||||
- In some cases we DO want input even when captured by UI. We need two systems within input package, one filtered and one not✅
|
||||
- Proper model loading (i.e. load model by reading all its meshes, textures, and so on together)
|
||||
- Create VAO struct independent from VBO to support multi-VBO use cases (e.g. instancing) ✅
|
||||
- Renderer batching
|
||||
- Scene graph
|
||||
- Separate engine loop from rendering loop? or leave it to the user?
|
||||
- Abstract keys enum away from sdl
|
||||
- Proper Asset loading
|
||||
- Abstract keys enum away from sdl?
|
||||
- Frustum culling
|
||||
- Proper Asset loading system
|
||||
- Material system editor with fields automatically extracted from the shader
|
||||
*/
|
||||
|
||||
@ -71,8 +73,9 @@ func (d *DirLight) GetProjViewMat() gglm.Mat4 {
|
||||
nearClip := dirLightNear
|
||||
farClip := dirLightFar
|
||||
|
||||
up := gglm.NewVec3(0, 1, 0)
|
||||
projMat := gglm.Ortho(-size, size, -size, size, nearClip, farClip).Mat4
|
||||
viewMat := gglm.LookAtRH(pos, pos.Clone().Add(&d.Dir), gglm.NewVec3(0, 1, 0)).Mat4
|
||||
viewMat := gglm.LookAtRH(&pos, pos.Clone().Add(&d.Dir), &up).Mat4
|
||||
|
||||
return *projMat.Mul(&viewMat)
|
||||
}
|
||||
@ -109,13 +112,34 @@ func (p *PointLight) GetProjViewMats(shadowMapWidth, shadowMapHeight float32) [6
|
||||
aspect := float32(shadowMapWidth) / float32(shadowMapHeight)
|
||||
projMat := gglm.Perspective(90*gglm.Deg2Rad, aspect, pointLightNear, p.FarPlane)
|
||||
|
||||
targetPos0 := gglm.NewVec3(1+p.Pos.X(), p.Pos.Y(), p.Pos.Z())
|
||||
targetPos1 := gglm.NewVec3(-1+p.Pos.X(), p.Pos.Y(), p.Pos.Z())
|
||||
targetPos2 := gglm.NewVec3(p.Pos.X(), 1+p.Pos.Y(), p.Pos.Z())
|
||||
targetPos3 := gglm.NewVec3(p.Pos.X(), -1+p.Pos.Y(), p.Pos.Z())
|
||||
targetPos4 := gglm.NewVec3(p.Pos.X(), p.Pos.Y(), 1+p.Pos.Z())
|
||||
targetPos5 := gglm.NewVec3(p.Pos.X(), p.Pos.Y(), -1+p.Pos.Z())
|
||||
|
||||
worldUp0 := gglm.NewVec3(0, -1, 0)
|
||||
worldUp1 := gglm.NewVec3(0, -1, 0)
|
||||
worldUp2 := gglm.NewVec3(0, 0, 1)
|
||||
worldUp3 := gglm.NewVec3(0, 0, -1)
|
||||
worldUp4 := gglm.NewVec3(0, -1, 0)
|
||||
worldUp5 := gglm.NewVec3(0, -1, 0)
|
||||
|
||||
lookAt0 := gglm.LookAtRH(&p.Pos, &targetPos0, &worldUp0)
|
||||
lookAt1 := gglm.LookAtRH(&p.Pos, &targetPos1, &worldUp1)
|
||||
lookAt2 := gglm.LookAtRH(&p.Pos, &targetPos2, &worldUp2)
|
||||
lookAt3 := gglm.LookAtRH(&p.Pos, &targetPos3, &worldUp3)
|
||||
lookAt4 := gglm.LookAtRH(&p.Pos, &targetPos4, &worldUp4)
|
||||
lookAt5 := gglm.LookAtRH(&p.Pos, &targetPos5, &worldUp5)
|
||||
|
||||
projViewMats := [6]gglm.Mat4{
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(1, 0, 0).Add(&p.Pos), gglm.NewVec3(0, -1, 0)).Mat4),
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(-1, 0, 0).Add(&p.Pos), gglm.NewVec3(0, -1, 0)).Mat4),
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(0, 1, 0).Add(&p.Pos), gglm.NewVec3(0, 0, 1)).Mat4),
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(0, -1, 0).Add(&p.Pos), gglm.NewVec3(0, 0, -1)).Mat4),
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(0, 0, 1).Add(&p.Pos), gglm.NewVec3(0, -1, 0)).Mat4),
|
||||
*projMat.Clone().Mul(&gglm.LookAtRH(&p.Pos, gglm.NewVec3(0, 0, -1).Add(&p.Pos), gglm.NewVec3(0, -1, 0)).Mat4),
|
||||
*projMat.Clone().Mul(&lookAt0.Mat4),
|
||||
*projMat.Clone().Mul(&lookAt1.Mat4),
|
||||
*projMat.Clone().Mul(&lookAt2.Mat4),
|
||||
*projMat.Clone().Mul(&lookAt3.Mat4),
|
||||
*projMat.Clone().Mul(&lookAt4.Mat4),
|
||||
*projMat.Clone().Mul(&lookAt5.Mat4),
|
||||
}
|
||||
|
||||
return projViewMats
|
||||
@ -143,11 +167,11 @@ func (s *SpotLight) GetProjViewMat() gglm.Mat4 {
|
||||
// Adjust up vector if lightDir is parallel or nearly parallel to upVector
|
||||
// as lookat view matrix breaks if up and look at are parallel
|
||||
up := gglm.NewVec3(0, 1, 0)
|
||||
if gglm.Abs32(gglm.DotVec3(&s.Dir, up)) > 0.99 {
|
||||
if gglm.Abs32(gglm.DotVec3(&s.Dir, &up)) > 0.99 {
|
||||
up.SetXY(1, 0)
|
||||
}
|
||||
|
||||
viewMat := gglm.LookAtRH(&s.Pos, s.Pos.Clone().Add(&s.Dir), up).Mat4
|
||||
viewMat := gglm.LookAtRH(&s.Pos, s.Pos.Clone().Add(&s.Dir), &up).Mat4
|
||||
|
||||
return *projMat.Mul(&viewMat)
|
||||
}
|
||||
@ -166,14 +190,16 @@ const (
|
||||
|
||||
unscaledWindowWidth = 1280
|
||||
unscaledWindowHeight = 720
|
||||
|
||||
PROFILE_CPU = true
|
||||
)
|
||||
|
||||
var (
|
||||
window *engine.Window
|
||||
window engine.Window
|
||||
|
||||
pitch float32 = 0
|
||||
yaw float32 = -1.5
|
||||
cam *camera.Camera
|
||||
cam camera.Camera
|
||||
|
||||
// Demo fbo
|
||||
renderToDemoFbo = false
|
||||
@ -195,22 +221,22 @@ var (
|
||||
spotLightDepthMapFbo buffers.Framebuffer
|
||||
|
||||
screenQuadVao buffers.VertexArray
|
||||
screenQuadMat *materials.Material
|
||||
screenQuadMat materials.Material
|
||||
|
||||
unlitMat *materials.Material
|
||||
whiteMat *materials.Material
|
||||
containerMat *materials.Material
|
||||
palleteMat *materials.Material
|
||||
skyboxMat *materials.Material
|
||||
depthMapMat *materials.Material
|
||||
arrayDepthMapMat *materials.Material
|
||||
omnidirDepthMapMat *materials.Material
|
||||
debugDepthMat *materials.Material
|
||||
unlitMat materials.Material
|
||||
whiteMat materials.Material
|
||||
containerMat materials.Material
|
||||
palleteMat materials.Material
|
||||
skyboxMat materials.Material
|
||||
depthMapMat materials.Material
|
||||
arrayDepthMapMat materials.Material
|
||||
omnidirDepthMapMat materials.Material
|
||||
debugDepthMat materials.Material
|
||||
|
||||
cubeMesh *meshes.Mesh
|
||||
sphereMesh *meshes.Mesh
|
||||
chairMesh *meshes.Mesh
|
||||
skyboxMesh *meshes.Mesh
|
||||
cubeMesh meshes.Mesh
|
||||
sphereMesh meshes.Mesh
|
||||
chairMesh meshes.Mesh
|
||||
skyboxMesh meshes.Mesh
|
||||
|
||||
cubeModelMat = gglm.NewTrMatId()
|
||||
|
||||
@ -224,17 +250,18 @@ var (
|
||||
// Light settings
|
||||
ambientColor = gglm.NewVec3(0, 0, 0)
|
||||
|
||||
dirLightDir = gglm.NewVec3(0, -0.5, -0.8)
|
||||
// Lights
|
||||
dirLight = DirLight{
|
||||
Dir: *gglm.NewVec3(0, -0.5, -0.8).Normalize(),
|
||||
DiffuseColor: *gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Dir: *dirLightDir.Normalize(),
|
||||
DiffuseColor: gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
}
|
||||
pointLights = [...]PointLight{
|
||||
{
|
||||
Pos: *gglm.NewVec3(0, 2, -2),
|
||||
DiffuseColor: *gglm.NewVec3(1, 0, 0),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Pos: gglm.NewVec3(0, 2, -2),
|
||||
DiffuseColor: gglm.NewVec3(1, 0, 0),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
// These values are for 50m range
|
||||
Constant: 1.0,
|
||||
Linear: 0.09,
|
||||
@ -243,39 +270,41 @@ var (
|
||||
FarPlane: 25,
|
||||
},
|
||||
{
|
||||
Pos: *gglm.NewVec3(0, -5, 0),
|
||||
DiffuseColor: *gglm.NewVec3(0, 1, 0),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Pos: gglm.NewVec3(0, -5, 0),
|
||||
DiffuseColor: gglm.NewVec3(0, 1, 0),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
Constant: 1.0,
|
||||
Linear: 0.09,
|
||||
Quadratic: 0.032,
|
||||
FarPlane: 25,
|
||||
},
|
||||
{
|
||||
Pos: *gglm.NewVec3(5, 0, 0),
|
||||
DiffuseColor: *gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Pos: gglm.NewVec3(5, 0, 0),
|
||||
DiffuseColor: gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
Constant: 1.0,
|
||||
Linear: 0.09,
|
||||
Quadratic: 0.032,
|
||||
FarPlane: 25,
|
||||
},
|
||||
{
|
||||
Pos: *gglm.NewVec3(-3, 4, 3),
|
||||
DiffuseColor: *gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Pos: gglm.NewVec3(-3, 4, 3),
|
||||
DiffuseColor: gglm.NewVec3(1, 1, 1),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
Constant: 1.0,
|
||||
Linear: 0.09,
|
||||
Quadratic: 0.032,
|
||||
FarPlane: 25,
|
||||
},
|
||||
}
|
||||
spotLights = [...]SpotLight{
|
||||
|
||||
spotLightDir0 = gglm.NewVec3(1.5, -0.9, 0)
|
||||
spotLights = [...]SpotLight{
|
||||
{
|
||||
Pos: *gglm.NewVec3(-4, 7, 5),
|
||||
Dir: *gglm.NewVec3(1.5, -0.9, 0).Normalize(),
|
||||
DiffuseColor: *gglm.NewVec3(1, 0, 1),
|
||||
SpecularColor: *gglm.NewVec3(1, 1, 1),
|
||||
Pos: gglm.NewVec3(-4, 7, 5),
|
||||
Dir: *spotLightDir0.Normalize(),
|
||||
DiffuseColor: gglm.NewVec3(1, 0, 1),
|
||||
SpecularColor: gglm.NewVec3(1, 1, 1),
|
||||
// These must be cosine values
|
||||
InnerCutoffRad: 15 * gglm.Deg2Rad,
|
||||
OuterCutoffRad: 20 * gglm.Deg2Rad,
|
||||
@ -314,14 +343,43 @@ func main() {
|
||||
engine.SetSrgbFramebuffer(true)
|
||||
|
||||
game := &Game{
|
||||
Win: window,
|
||||
Win: &window,
|
||||
WinWidth: int32(unscaledWindowWidth * dpiScaling),
|
||||
WinHeight: int32(unscaledWindowHeight * dpiScaling),
|
||||
ImGUIInfo: nmageimgui.NewImGui("./res/shaders/imgui.glsl"),
|
||||
}
|
||||
window.EventCallbacks = append(window.EventCallbacks, game.handleWindowEvents)
|
||||
|
||||
engine.Run(game, window, game.ImGUIInfo)
|
||||
if PROFILE_CPU {
|
||||
|
||||
pf, err := os.Create("cpu.pprof")
|
||||
if err == nil {
|
||||
defer pf.Close()
|
||||
pprof.StartCPUProfile(pf)
|
||||
} else {
|
||||
logging.ErrLog.Printf("Creating cpu.pprof file failed. CPU profiling will not run. Err=%v\n", err)
|
||||
}
|
||||
}
|
||||
|
||||
engine.Run(game, &window, game.ImGUIInfo)
|
||||
|
||||
if PROFILE_CPU {
|
||||
pprof.StopCPUProfile()
|
||||
|
||||
heapProfile, err := os.Create("heap.pprof")
|
||||
if err == nil {
|
||||
|
||||
err = pprof.WriteHeapProfile(heapProfile)
|
||||
if err != nil {
|
||||
logging.ErrLog.Printf("Writing heap profile to heap.pprof failed. Err=%v\n", err)
|
||||
}
|
||||
|
||||
heapProfile.Close()
|
||||
|
||||
} else {
|
||||
logging.ErrLog.Printf("Creating heap.pprof file failed. Err=%v\n", err)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (g *Game) handleWindowEvents(e sdl.Event) {
|
||||
@ -380,10 +438,14 @@ func (g *Game) Init() {
|
||||
|
||||
// Camera
|
||||
winWidth, winHeight := g.Win.SDLWin.GetSize()
|
||||
|
||||
camPos := gglm.NewVec3(0, 0, 10)
|
||||
camForward := gglm.NewVec3(0, 0, -1)
|
||||
camWorldUp := gglm.NewVec3(0, 1, 0)
|
||||
cam = camera.NewPerspective(
|
||||
gglm.NewVec3(0, 0, 10),
|
||||
gglm.NewVec3(0, 0, -1),
|
||||
gglm.NewVec3(0, 1, 0),
|
||||
&camPos,
|
||||
&camForward,
|
||||
&camWorldUp,
|
||||
0.1, 200,
|
||||
45*gglm.Deg2Rad,
|
||||
float32(winWidth)/float32(winHeight),
|
||||
@ -450,14 +512,16 @@ func (g *Game) Init() {
|
||||
// Create materials and assign any unused texture slots to black
|
||||
//
|
||||
screenQuadMat = materials.NewMaterial("Screen Quad Mat", "./res/shaders/screen-quad.glsl")
|
||||
screenQuadMat.SetUnifVec2("scale", demoFboScale)
|
||||
screenQuadMat.SetUnifVec2("offset", demoFboOffset)
|
||||
screenQuadMat.SetUnifVec2("scale", &demoFboScale)
|
||||
screenQuadMat.SetUnifVec2("offset", &demoFboOffset)
|
||||
screenQuadMat.SetUnifInt32("material.diffuse", int32(materials.TextureSlot_Diffuse))
|
||||
|
||||
unlitMat = materials.NewMaterial("Unlit mat", "./res/shaders/simple-unlit.glsl")
|
||||
unlitMat.Settings.Set(materials.MaterialSettings_HasModelMat)
|
||||
unlitMat.SetUnifInt32("material.diffuse", int32(materials.TextureSlot_Diffuse))
|
||||
|
||||
whiteMat = materials.NewMaterial("White mat", "./res/shaders/simple.glsl")
|
||||
whiteMat.Settings.Set(materials.MaterialSettings_HasModelMat | materials.MaterialSettings_HasNormalMat)
|
||||
whiteMat.Shininess = 64
|
||||
whiteMat.DiffuseTex = whiteTex.TexID
|
||||
whiteMat.SpecularTex = blackTex.TexID
|
||||
@ -467,7 +531,7 @@ func (g *Game) Init() {
|
||||
whiteMat.SetUnifInt32("material.specular", int32(materials.TextureSlot_Specular))
|
||||
// whiteMat.SetUnifInt32("material.normal", int32(materials.TextureSlot_Normal))
|
||||
whiteMat.SetUnifInt32("material.emission", int32(materials.TextureSlot_Emission))
|
||||
whiteMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
whiteMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
whiteMat.SetUnifFloat32("material.shininess", whiteMat.Shininess)
|
||||
whiteMat.SetUnifVec3("dirLight.dir", &dirLight.Dir)
|
||||
whiteMat.SetUnifVec3("dirLight.diffuseColor", &dirLight.DiffuseColor)
|
||||
@ -477,6 +541,7 @@ func (g *Game) Init() {
|
||||
whiteMat.SetUnifInt32("spotLightShadowMaps", int32(materials.TextureSlot_ShadowMap_Array1))
|
||||
|
||||
containerMat = materials.NewMaterial("Container mat", "./res/shaders/simple.glsl")
|
||||
containerMat.Settings.Set(materials.MaterialSettings_HasModelMat | materials.MaterialSettings_HasNormalMat)
|
||||
containerMat.Shininess = 64
|
||||
containerMat.DiffuseTex = containerDiffuseTex.TexID
|
||||
containerMat.SpecularTex = containerSpecularTex.TexID
|
||||
@ -486,7 +551,7 @@ func (g *Game) Init() {
|
||||
containerMat.SetUnifInt32("material.specular", int32(materials.TextureSlot_Specular))
|
||||
// containerMat.SetUnifInt32("material.normal", int32(materials.TextureSlot_Normal))
|
||||
containerMat.SetUnifInt32("material.emission", int32(materials.TextureSlot_Emission))
|
||||
containerMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
containerMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
containerMat.SetUnifFloat32("material.shininess", containerMat.Shininess)
|
||||
containerMat.SetUnifVec3("dirLight.dir", &dirLight.Dir)
|
||||
containerMat.SetUnifVec3("dirLight.diffuseColor", &dirLight.DiffuseColor)
|
||||
@ -496,6 +561,7 @@ func (g *Game) Init() {
|
||||
containerMat.SetUnifInt32("spotLightShadowMaps", int32(materials.TextureSlot_ShadowMap_Array1))
|
||||
|
||||
palleteMat = materials.NewMaterial("Pallete mat", "./res/shaders/simple.glsl")
|
||||
palleteMat.Settings.Set(materials.MaterialSettings_HasModelMat | materials.MaterialSettings_HasNormalMat)
|
||||
palleteMat.Shininess = 64
|
||||
palleteMat.DiffuseTex = palleteTex.TexID
|
||||
palleteMat.SpecularTex = blackTex.TexID
|
||||
@ -505,7 +571,7 @@ func (g *Game) Init() {
|
||||
palleteMat.SetUnifInt32("material.specular", int32(materials.TextureSlot_Specular))
|
||||
// palleteMat.SetUnifInt32("material.normal", int32(materials.TextureSlot_Normal))
|
||||
palleteMat.SetUnifInt32("material.emission", int32(materials.TextureSlot_Emission))
|
||||
palleteMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
palleteMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
palleteMat.SetUnifFloat32("material.shininess", palleteMat.Shininess)
|
||||
palleteMat.SetUnifVec3("dirLight.diffuseColor", &dirLight.DiffuseColor)
|
||||
palleteMat.SetUnifVec3("dirLight.specularColor", &dirLight.SpecularColor)
|
||||
@ -514,22 +580,29 @@ func (g *Game) Init() {
|
||||
palleteMat.SetUnifInt32("spotLightShadowMaps", int32(materials.TextureSlot_ShadowMap_Array1))
|
||||
|
||||
debugDepthMat = materials.NewMaterial("Debug depth mat", "./res/shaders/debug-depth.glsl")
|
||||
debugDepthMat.Settings.Set(materials.MaterialSettings_HasModelMat)
|
||||
|
||||
depthMapMat = materials.NewMaterial("Depth Map mat", "./res/shaders/depth-map.glsl")
|
||||
depthMapMat.Settings.Set(materials.MaterialSettings_HasModelMat)
|
||||
|
||||
arrayDepthMapMat = materials.NewMaterial("Array Depth Map mat", "./res/shaders/array-depth-map.glsl")
|
||||
arrayDepthMapMat.Settings.Set(materials.MaterialSettings_HasModelMat)
|
||||
|
||||
omnidirDepthMapMat = materials.NewMaterial("Omnidirectional Depth Map mat", "./res/shaders/omnidirectional-depth-map.glsl")
|
||||
omnidirDepthMapMat.Settings.Set(materials.MaterialSettings_HasModelMat)
|
||||
|
||||
skyboxMat = materials.NewMaterial("Skybox mat", "./res/shaders/skybox.glsl")
|
||||
skyboxMat.CubemapTex = skyboxCmap.TexID
|
||||
skyboxMat.SetUnifInt32("skybox", int32(materials.TextureSlot_Cubemap))
|
||||
|
||||
// Cube model mat
|
||||
translationMat := gglm.NewTranslationMat(gglm.NewVec3(0, 0, 0))
|
||||
scaleMat := gglm.NewScaleMat(gglm.NewVec3(1, 1, 1))
|
||||
rotMat := gglm.NewRotMat(gglm.NewQuatEuler(gglm.NewVec3(-90, -90, 0).AsRad()))
|
||||
cubeModelMat.Mul(translationMat.Mul(rotMat.Mul(scaleMat)))
|
||||
translationMat := gglm.NewTranslationMat(0, 0, 0)
|
||||
|
||||
scaleMat := gglm.NewScaleMat(1, 1, 1)
|
||||
|
||||
rotMatRot := gglm.NewQuatEuler(-90*gglm.Deg2Rad, -90*gglm.Deg2Rad, 0)
|
||||
rotMat := gglm.NewRotMatQuat(&rotMatRot)
|
||||
cubeModelMat.Mul(translationMat.Mul(rotMat.Mul(&scaleMat)))
|
||||
|
||||
// Screen quad vao setup.
|
||||
// We don't actually care about the values here because the quad is hardcoded in the shader,
|
||||
@ -566,7 +639,7 @@ func (g *Game) initFbos() {
|
||||
assert.T(demoFbo.IsComplete(), "Demo fbo is not complete after init")
|
||||
|
||||
// Depth map fbo
|
||||
dirLightDepthMapFbo = buffers.NewFramebuffer(1024, 1024)
|
||||
dirLightDepthMapFbo = buffers.NewFramebuffer(2048, 2048)
|
||||
dirLightDepthMapFbo.SetNoColorBuffer()
|
||||
dirLightDepthMapFbo.NewDepthAttachment(
|
||||
buffers.FramebufferAttachmentType_Texture,
|
||||
@ -576,7 +649,7 @@ func (g *Game) initFbos() {
|
||||
assert.T(dirLightDepthMapFbo.IsComplete(), "Depth map fbo is not complete after init")
|
||||
|
||||
// Point light depth map fbo
|
||||
pointLightDepthMapFbo = buffers.NewFramebuffer(1024, 1024)
|
||||
pointLightDepthMapFbo = buffers.NewFramebuffer(512, 512)
|
||||
pointLightDepthMapFbo.SetNoColorBuffer()
|
||||
pointLightDepthMapFbo.NewDepthCubemapArrayAttachment(
|
||||
buffers.FramebufferAttachmentDataFormat_DepthF32,
|
||||
@ -586,7 +659,7 @@ func (g *Game) initFbos() {
|
||||
assert.T(pointLightDepthMapFbo.IsComplete(), "Point light depth map fbo is not complete after init")
|
||||
|
||||
// Spot light depth map fbo
|
||||
spotLightDepthMapFbo = buffers.NewFramebuffer(1024, 1024)
|
||||
spotLightDepthMapFbo = buffers.NewFramebuffer(512, 512)
|
||||
spotLightDepthMapFbo.SetNoColorBuffer()
|
||||
spotLightDepthMapFbo.NewDepthTextureArrayAttachment(
|
||||
buffers.FramebufferAttachmentDataFormat_DepthF32,
|
||||
@ -722,9 +795,9 @@ func (g *Game) showDebugWindow() {
|
||||
imgui.Text("Ambient Light")
|
||||
|
||||
if imgui.DragFloat3("Ambient Color", &ambientColor.Data) {
|
||||
whiteMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
containerMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
palleteMat.SetUnifVec3("ambientColor", ambientColor)
|
||||
whiteMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
containerMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
palleteMat.SetUnifVec3("ambientColor", &ambientColor)
|
||||
}
|
||||
|
||||
imgui.Spacing()
|
||||
@ -944,10 +1017,12 @@ func (g *Game) updateCameraPos() {
|
||||
|
||||
// Left and right
|
||||
if input.KeyDown(sdl.K_d) {
|
||||
cam.Pos.Add(gglm.Cross(&cam.Forward, &cam.WorldUp).Normalize().Scale(camSpeed * camSpeedScale * timing.DT()))
|
||||
cross := gglm.Cross(&cam.Forward, &cam.WorldUp)
|
||||
cam.Pos.Add(cross.Normalize().Scale(camSpeed * camSpeedScale * timing.DT()))
|
||||
update = true
|
||||
} else if input.KeyDown(sdl.K_a) {
|
||||
cam.Pos.Add(gglm.Cross(&cam.Forward, &cam.WorldUp).Normalize().Scale(-camSpeed * camSpeedScale * timing.DT()))
|
||||
cross := gglm.Cross(&cam.Forward, &cam.WorldUp)
|
||||
cam.Pos.Add(cross.Normalize().Scale(-camSpeed * camSpeedScale * timing.DT()))
|
||||
update = true
|
||||
}
|
||||
|
||||
@ -965,9 +1040,9 @@ var (
|
||||
rotatingCubeSpeedDeg1 float32 = 45
|
||||
rotatingCubeSpeedDeg2 float32 = 120
|
||||
rotatingCubeSpeedDeg3 float32 = 120
|
||||
rotatingCubeTrMat1 = *gglm.NewTrMatId().Translate(gglm.NewVec3(-4, -1, 4))
|
||||
rotatingCubeTrMat2 = *gglm.NewTrMatId().Translate(gglm.NewVec3(-1, 0.5, 4))
|
||||
rotatingCubeTrMat3 = *gglm.NewTrMatId().Translate(gglm.NewVec3(5, 0.5, 4))
|
||||
rotatingCubeTrMat1 = gglm.NewTrMatWithPos(-4, -1, 4)
|
||||
rotatingCubeTrMat2 = gglm.NewTrMatWithPos(-1, 0.5, 4)
|
||||
rotatingCubeTrMat3 = gglm.NewTrMatWithPos(5, 0.5, 4)
|
||||
)
|
||||
|
||||
func (g *Game) Render() {
|
||||
@ -976,9 +1051,9 @@ func (g *Game) Render() {
|
||||
containerMat.SetUnifVec3("camPos", &cam.Pos)
|
||||
palleteMat.SetUnifVec3("camPos", &cam.Pos)
|
||||
|
||||
rotatingCubeTrMat1.Rotate(rotatingCubeSpeedDeg1*gglm.Deg2Rad*timing.DT(), gglm.NewVec3(0, 1, 0))
|
||||
rotatingCubeTrMat2.Rotate(rotatingCubeSpeedDeg2*gglm.Deg2Rad*timing.DT(), gglm.NewVec3(1, 1, 0))
|
||||
rotatingCubeTrMat3.Rotate(rotatingCubeSpeedDeg3*gglm.Deg2Rad*timing.DT(), gglm.NewVec3(1, 1, 1))
|
||||
rotatingCubeTrMat1.Rotate(rotatingCubeSpeedDeg1*gglm.Deg2Rad*timing.DT(), 0, 1, 0)
|
||||
rotatingCubeTrMat2.Rotate(rotatingCubeSpeedDeg2*gglm.Deg2Rad*timing.DT(), 1, 1, 0)
|
||||
rotatingCubeTrMat3.Rotate(rotatingCubeSpeedDeg3*gglm.Deg2Rad*timing.DT(), 1, 1, 1)
|
||||
|
||||
if renderDirLightShadows {
|
||||
g.renderDirectionalLightShadowmap()
|
||||
@ -995,7 +1070,7 @@ func (g *Game) Render() {
|
||||
if renderToBackBuffer {
|
||||
|
||||
if renderDepthBuffer {
|
||||
g.RenderScene(debugDepthMat)
|
||||
g.RenderScene(&debugDepthMat)
|
||||
} else {
|
||||
g.RenderScene(nil)
|
||||
}
|
||||
@ -1031,17 +1106,17 @@ func (g *Game) renderDirectionalLightShadowmap() {
|
||||
//
|
||||
// Some note that this is too troublesome and fails in many cases. Might be better to remove.
|
||||
gl.CullFace(gl.FRONT)
|
||||
g.RenderScene(depthMapMat)
|
||||
g.RenderScene(&depthMapMat)
|
||||
gl.CullFace(gl.BACK)
|
||||
|
||||
dirLightDepthMapFbo.UnBindWithViewport(uint32(g.WinWidth), uint32(g.WinHeight))
|
||||
|
||||
if showDirLightDepthMapFbo {
|
||||
screenQuadMat.DiffuseTex = dirLightDepthMapFbo.Attachments[0].Id
|
||||
screenQuadMat.SetUnifVec2("offset", dirLightDepthMapFboOffset)
|
||||
screenQuadMat.SetUnifVec2("scale", dirLightDepthMapFboScale)
|
||||
screenQuadMat.SetUnifVec2("offset", &dirLightDepthMapFboOffset)
|
||||
screenQuadMat.SetUnifVec2("scale", &dirLightDepthMapFboScale)
|
||||
screenQuadMat.Bind()
|
||||
window.Rend.DrawVertexArray(screenQuadMat, &screenQuadVao, 0, 6)
|
||||
window.Rend.DrawVertexArray(&screenQuadMat, &screenQuadVao, 0, 6)
|
||||
}
|
||||
}
|
||||
|
||||
@ -1070,7 +1145,7 @@ func (g *Game) renderSpotLightShadowmaps() {
|
||||
|
||||
// Front culling created issues
|
||||
// gl.CullFace(gl.FRONT)
|
||||
g.RenderScene(arrayDepthMapMat)
|
||||
g.RenderScene(&arrayDepthMapMat)
|
||||
// gl.CullFace(gl.BACK)
|
||||
|
||||
spotLightDepthMapFbo.UnBindWithViewport(uint32(g.WinWidth), uint32(g.WinHeight))
|
||||
@ -1096,7 +1171,7 @@ func (g *Game) renderPointLightShadowmaps() {
|
||||
omnidirDepthMapMat.SetUnifMat4("cubemapProjViewMats["+strconv.Itoa(j)+"]", &projViewMats[j])
|
||||
}
|
||||
|
||||
g.RenderScene(omnidirDepthMapMat)
|
||||
g.RenderScene(&omnidirDepthMapMat)
|
||||
}
|
||||
|
||||
pointLightDepthMapFbo.UnBindWithViewport(uint32(g.WinWidth), uint32(g.WinHeight))
|
||||
@ -1108,7 +1183,7 @@ func (g *Game) renderDemoFob() {
|
||||
demoFbo.Clear()
|
||||
|
||||
if renderDepthBuffer {
|
||||
g.RenderScene(debugDepthMat)
|
||||
g.RenderScene(&debugDepthMat)
|
||||
} else {
|
||||
g.RenderScene(nil)
|
||||
}
|
||||
@ -1120,10 +1195,10 @@ func (g *Game) renderDemoFob() {
|
||||
demoFbo.UnBind()
|
||||
|
||||
screenQuadMat.DiffuseTex = demoFbo.Attachments[0].Id
|
||||
screenQuadMat.SetUnifVec2("offset", demoFboOffset)
|
||||
screenQuadMat.SetUnifVec2("scale", demoFboScale)
|
||||
screenQuadMat.SetUnifVec2("offset", &demoFboOffset)
|
||||
screenQuadMat.SetUnifVec2("scale", &demoFboScale)
|
||||
|
||||
window.Rend.DrawVertexArray(screenQuadMat, &screenQuadVao, 0, 6)
|
||||
window.Rend.DrawVertexArray(&screenQuadMat, &screenQuadVao, 0, 6)
|
||||
}
|
||||
|
||||
func (g *Game) RenderScene(overrideMat *materials.Material) {
|
||||
@ -1131,9 +1206,9 @@ func (g *Game) RenderScene(overrideMat *materials.Material) {
|
||||
tempModelMatrix := cubeModelMat.Clone()
|
||||
|
||||
// See if we need overrides
|
||||
sunMat := palleteMat
|
||||
chairMat := palleteMat
|
||||
cubeMat := containerMat
|
||||
sunMat := &palleteMat
|
||||
chairMat := &palleteMat
|
||||
cubeMat := &containerMat
|
||||
|
||||
if overrideMat != nil {
|
||||
sunMat = overrideMat
|
||||
@ -1142,32 +1217,35 @@ func (g *Game) RenderScene(overrideMat *materials.Material) {
|
||||
}
|
||||
|
||||
// Draw dir light
|
||||
window.Rend.DrawMesh(sphereMesh, gglm.NewTrMatId().Translate(gglm.NewVec3(0, 10, 0)).Scale(gglm.NewVec3(0.1, 0.1, 0.1)), sunMat)
|
||||
dirLightTrMat := gglm.NewTrMatId()
|
||||
window.Rend.DrawMesh(&sphereMesh, dirLightTrMat.Translate(0, 10, 0).Scale(0.1, 0.1, 0.1), sunMat)
|
||||
|
||||
// Draw point lights
|
||||
for i := 0; i < len(pointLights); i++ {
|
||||
|
||||
pl := &pointLights[i]
|
||||
window.Rend.DrawMesh(cubeMesh, gglm.NewTrMatId().Translate(&pl.Pos).Scale(gglm.NewVec3(0.1, 0.1, 0.1)), sunMat)
|
||||
plTrMat := gglm.NewTrMatId()
|
||||
window.Rend.DrawMesh(&cubeMesh, plTrMat.TranslateVec(&pl.Pos).Scale(0.1, 0.1, 0.1), sunMat)
|
||||
}
|
||||
|
||||
// Chair
|
||||
window.Rend.DrawMesh(chairMesh, tempModelMatrix, chairMat)
|
||||
window.Rend.DrawMesh(&chairMesh, tempModelMatrix, chairMat)
|
||||
|
||||
// Ground
|
||||
window.Rend.DrawMesh(cubeMesh, gglm.NewTrMatId().Translate(gglm.NewVec3(0, -3, 0)).Scale(gglm.NewVec3(20, 1, 20)), cubeMat)
|
||||
groundTrMat := gglm.NewTrMatId()
|
||||
window.Rend.DrawMesh(&cubeMesh, groundTrMat.Translate(0, -3, 0).Scale(20, 1, 20), cubeMat)
|
||||
|
||||
// Cubes
|
||||
tempModelMatrix.Translate(gglm.NewVec3(-6, 0, 0))
|
||||
window.Rend.DrawMesh(cubeMesh, tempModelMatrix, cubeMat)
|
||||
tempModelMatrix.Translate(-6, 0, 0)
|
||||
window.Rend.DrawMesh(&cubeMesh, tempModelMatrix, cubeMat)
|
||||
|
||||
tempModelMatrix.Translate(gglm.NewVec3(0, -1, -4))
|
||||
window.Rend.DrawMesh(cubeMesh, tempModelMatrix, cubeMat)
|
||||
tempModelMatrix.Translate(0, -1, -4)
|
||||
window.Rend.DrawMesh(&cubeMesh, tempModelMatrix, cubeMat)
|
||||
|
||||
// Rotating cubes
|
||||
window.Rend.DrawMesh(cubeMesh, &rotatingCubeTrMat1, cubeMat)
|
||||
window.Rend.DrawMesh(cubeMesh, &rotatingCubeTrMat2, cubeMat)
|
||||
window.Rend.DrawMesh(cubeMesh, &rotatingCubeTrMat3, cubeMat)
|
||||
window.Rend.DrawMesh(&cubeMesh, &rotatingCubeTrMat1, cubeMat)
|
||||
window.Rend.DrawMesh(&cubeMesh, &rotatingCubeTrMat2, cubeMat)
|
||||
window.Rend.DrawMesh(&cubeMesh, &rotatingCubeTrMat3, cubeMat)
|
||||
|
||||
// Cubes generator
|
||||
// rowSize := 1
|
||||
@ -1185,7 +1263,7 @@ func (g *Game) DrawSkybox() {
|
||||
gl.Disable(gl.CULL_FACE)
|
||||
gl.DepthFunc(gl.LEQUAL)
|
||||
|
||||
window.Rend.DrawCubemap(skyboxMesh, skyboxMat)
|
||||
window.Rend.DrawCubemap(&skyboxMesh, &skyboxMat)
|
||||
|
||||
gl.DepthFunc(gl.LESS)
|
||||
gl.Enable(gl.CULL_FACE)
|
||||
|
||||
@ -21,9 +21,30 @@ const (
|
||||
TextureSlot_ShadowMap_Array1 TextureSlot = 13
|
||||
)
|
||||
|
||||
type MaterialSettings uint64
|
||||
|
||||
const (
|
||||
MaterialSettings_None MaterialSettings = iota
|
||||
MaterialSettings_HasModelMat MaterialSettings = 1 << (iota - 1)
|
||||
MaterialSettings_HasNormalMat
|
||||
)
|
||||
|
||||
func (ms *MaterialSettings) Set(flags MaterialSettings) {
|
||||
*ms |= flags
|
||||
}
|
||||
|
||||
func (ms *MaterialSettings) Remove(flags MaterialSettings) {
|
||||
*ms &= ^flags
|
||||
}
|
||||
|
||||
func (ms *MaterialSettings) Has(flags MaterialSettings) bool {
|
||||
return *ms&flags == flags
|
||||
}
|
||||
|
||||
type Material struct {
|
||||
Name string
|
||||
ShaderProg shaders.ShaderProgram
|
||||
Settings MaterialSettings
|
||||
|
||||
UnifLocs map[string]int32
|
||||
AttribLocs map[string]int32
|
||||
@ -166,22 +187,22 @@ func (m *Material) Delete() {
|
||||
gl.DeleteProgram(m.ShaderProg.Id)
|
||||
}
|
||||
|
||||
func NewMaterial(matName, shaderPath string) *Material {
|
||||
func NewMaterial(matName, shaderPath string) Material {
|
||||
|
||||
shdrProg, err := shaders.LoadAndCompileCombinedShader(shaderPath)
|
||||
if err != nil {
|
||||
logging.ErrLog.Fatalf("Failed to create new material '%s'. Err: %s\n", matName, err.Error())
|
||||
}
|
||||
|
||||
return &Material{Name: matName, ShaderProg: shdrProg, UnifLocs: make(map[string]int32), AttribLocs: make(map[string]int32)}
|
||||
return Material{Name: matName, ShaderProg: shdrProg, UnifLocs: make(map[string]int32), AttribLocs: make(map[string]int32)}
|
||||
}
|
||||
|
||||
func NewMaterialSrc(matName string, shaderSrc []byte) *Material {
|
||||
func NewMaterialSrc(matName string, shaderSrc []byte) Material {
|
||||
|
||||
shdrProg, err := shaders.LoadAndCompileCombinedShaderSrc(shaderSrc)
|
||||
if err != nil {
|
||||
logging.ErrLog.Fatalf("Failed to create new material '%s'. Err: %s\n", matName, err.Error())
|
||||
}
|
||||
|
||||
return &Material{Name: matName, ShaderProg: shdrProg, UnifLocs: make(map[string]int32), AttribLocs: make(map[string]int32)}
|
||||
return Material{Name: matName, ShaderProg: shdrProg, UnifLocs: make(map[string]int32), AttribLocs: make(map[string]int32)}
|
||||
}
|
||||
|
||||
@ -21,19 +21,19 @@ type Mesh struct {
|
||||
SubMeshes []SubMesh
|
||||
}
|
||||
|
||||
func NewMesh(name, modelPath string, postProcessFlags asig.PostProcess) (*Mesh, error) {
|
||||
func NewMesh(name, modelPath string, postProcessFlags asig.PostProcess) (Mesh, error) {
|
||||
|
||||
scene, release, err := asig.ImportFile(modelPath, asig.PostProcessTriangulate|postProcessFlags)
|
||||
if err != nil {
|
||||
return nil, errors.New("Failed to load model. Err: " + err.Error())
|
||||
return Mesh{}, errors.New("Failed to load model. Err: " + err.Error())
|
||||
}
|
||||
defer release()
|
||||
|
||||
if len(scene.Meshes) == 0 {
|
||||
return nil, errors.New("No meshes found in file: " + modelPath)
|
||||
return Mesh{}, errors.New("No meshes found in file: " + modelPath)
|
||||
}
|
||||
|
||||
mesh := &Mesh{
|
||||
mesh := Mesh{
|
||||
Name: name,
|
||||
Vao: buffers.NewVertexArray(),
|
||||
SubMeshes: make([]SubMesh, 0, 1),
|
||||
|
||||
@ -29,7 +29,14 @@ func (r *Rend3DGL) DrawMesh(mesh *meshes.Mesh, modelMat *gglm.TrMat, mat *materi
|
||||
r.BoundMat = mat
|
||||
}
|
||||
|
||||
mat.SetUnifMat4("modelMat", &modelMat.Mat4)
|
||||
if mat.Settings.Has(materials.MaterialSettings_HasModelMat) {
|
||||
mat.SetUnifMat4("modelMat", &modelMat.Mat4)
|
||||
}
|
||||
|
||||
if mat.Settings.Has(materials.MaterialSettings_HasNormalMat) {
|
||||
normalMat := modelMat.Clone().InvertAndTranspose().ToMat3()
|
||||
mat.SetUnifMat3("normalMat", &normalMat)
|
||||
}
|
||||
|
||||
for i := 0; i < len(mesh.SubMeshes); i++ {
|
||||
gl.DrawElementsBaseVertexWithOffset(gl.TRIANGLES, mesh.SubMeshes[i].IndexCount, gl.UNSIGNED_INT, uintptr(mesh.SubMeshes[i].BaseIndex), mesh.SubMeshes[i].BaseVertex)
|
||||
|
||||
@ -2,22 +2,18 @@
|
||||
#version 410
|
||||
|
||||
layout(location=0) in vec3 vertPosIn;
|
||||
layout(location=1) in vec3 vertNormalIn;
|
||||
layout(location=2) in vec2 vertUV0In;
|
||||
layout(location=3) in vec3 vertColorIn;
|
||||
|
||||
out vec3 vertNormal;
|
||||
out vec2 vertUV0;
|
||||
out vec3 vertColor;
|
||||
out vec3 fragPos;
|
||||
|
||||
//MVP = Model View Projection
|
||||
uniform mat4 modelMat;
|
||||
uniform mat4 projViewMat;
|
||||
|
||||
void main()
|
||||
{
|
||||
vertNormal = mat3(transpose(inverse(modelMat))) * vertNormalIn;
|
||||
vertUV0 = vertUV0In;
|
||||
vertColor = vertColorIn;
|
||||
|
||||
@ -31,7 +27,6 @@ void main()
|
||||
#version 410
|
||||
|
||||
in vec3 vertColor;
|
||||
in vec3 vertNormal;
|
||||
in vec2 vertUV0;
|
||||
in vec3 fragPos;
|
||||
|
||||
|
||||
@ -6,23 +6,15 @@ layout(location=1) in vec3 vertNormalIn;
|
||||
layout(location=2) in vec2 vertUV0In;
|
||||
layout(location=3) in vec3 vertColorIn;
|
||||
|
||||
out vec3 vertNormal;
|
||||
out vec2 vertUV0;
|
||||
out vec3 vertColor;
|
||||
out vec3 fragPos;
|
||||
|
||||
//MVP = Model View Projection
|
||||
uniform mat4 modelMat;
|
||||
uniform mat4 projViewMat;
|
||||
|
||||
void main()
|
||||
{
|
||||
// @TODO: Calculate this on the CPU and send it as a uniform
|
||||
//
|
||||
// This produces the normal matrix that multiplies with the model normal to produce the
|
||||
// world space normal. Based on 'One last thing' section from: https://learnopengl.com/Lighting/Basic-Lighting
|
||||
vertNormal = mat3(transpose(inverse(modelMat))) * vertNormalIn;
|
||||
|
||||
vertUV0 = vertUV0In;
|
||||
vertColor = vertColorIn;
|
||||
|
||||
@ -41,7 +33,6 @@ struct Material {
|
||||
uniform Material material;
|
||||
|
||||
in vec3 vertColor;
|
||||
in vec3 vertNormal;
|
||||
in vec2 vertUV0;
|
||||
in vec3 fragPos;
|
||||
|
||||
|
||||
@ -7,6 +7,7 @@ layout(location=2) in vec2 vertUV0In;
|
||||
layout(location=3) in vec3 vertColorIn;
|
||||
|
||||
uniform mat4 modelMat;
|
||||
uniform mat3 normalMat;
|
||||
uniform mat4 projViewMat;
|
||||
uniform mat4 dirLightProjViewMat;
|
||||
|
||||
@ -22,11 +23,7 @@ out vec4 fragPosSpotLight[NUM_SPOT_LIGHTS];
|
||||
|
||||
void main()
|
||||
{
|
||||
// @TODO: Calculate this on the CPU and send it as a uniform
|
||||
//
|
||||
// This produces the normal matrix that multiplies with the model normal to produce the
|
||||
// world space normal. Based on 'One last thing' section from: https://learnopengl.com/Lighting/Basic-Lighting
|
||||
vertNormal = mat3(transpose(inverse(modelMat))) * vertNormalIn;
|
||||
vertNormal = normalMat * vertNormalIn;
|
||||
|
||||
vertUV0 = vertUV0In;
|
||||
vertColor = vertColorIn;
|
||||
|
||||
@ -12,7 +12,7 @@ import (
|
||||
type ImguiInfo struct {
|
||||
ImCtx imgui.Context
|
||||
|
||||
Mat *materials.Material
|
||||
Mat materials.Material
|
||||
VaoID uint32
|
||||
VboID uint32
|
||||
IndexBufID uint32
|
||||
@ -204,7 +204,7 @@ void main()
|
||||
// If the path is empty a default nMage shader is used
|
||||
func NewImGui(shaderPath string) ImguiInfo {
|
||||
|
||||
var imguiMat *materials.Material
|
||||
var imguiMat materials.Material
|
||||
if shaderPath == "" {
|
||||
imguiMat = materials.NewMaterialSrc("ImGUI Mat", []byte(DefaultImguiShader))
|
||||
} else {
|
||||
|
||||
Reference in New Issue
Block a user