86 lines
2.0 KiB
Go
86 lines
2.0 KiB
Go
package pass
|
|
|
|
import (
|
|
"zworld/engine/object/light"
|
|
"zworld/engine/object/mesh"
|
|
"zworld/engine/render/uniform"
|
|
"zworld/engine/renderapi/cache"
|
|
"zworld/engine/renderapi/command"
|
|
"zworld/engine/renderapi/descriptor"
|
|
"zworld/engine/renderapi/material"
|
|
)
|
|
|
|
type ForwardDescriptors struct {
|
|
descriptor.Set
|
|
Camera *descriptor.Uniform[uniform.Camera]
|
|
Objects *descriptor.Storage[uniform.Object]
|
|
Lights *descriptor.Storage[uniform.Light]
|
|
Textures *descriptor.SamplerArray
|
|
}
|
|
|
|
type ForwardMaterial struct {
|
|
Instance *material.Instance[*ForwardDescriptors]
|
|
Objects *ObjectBuffer
|
|
Lights *LightBuffer
|
|
Shadows *ShadowCache
|
|
Textures cache.SamplerCache
|
|
Meshes cache.MeshCache
|
|
|
|
id material.ID
|
|
}
|
|
|
|
func (m *ForwardMaterial) ID() material.ID {
|
|
return m.id
|
|
}
|
|
|
|
func (m *ForwardMaterial) Begin(camera uniform.Camera, lights []light.T) {
|
|
m.Instance.Descriptors().Camera.Set(camera)
|
|
|
|
// multiple calls to this reset in a single frame will cause weird behaviour
|
|
// we need to split this function somehow in order to be able to do depth sorting etc
|
|
m.Objects.Reset()
|
|
|
|
if len(lights) > 0 {
|
|
// how to get ambient light info?
|
|
m.Lights.Reset()
|
|
for _, lit := range lights {
|
|
m.Lights.Store(lit.LightData(m.Shadows))
|
|
}
|
|
m.Lights.Flush(m.Instance.Descriptors().Lights)
|
|
}
|
|
}
|
|
|
|
func (m *ForwardMaterial) Bind(cmds command.Recorder) {
|
|
cmds.Record(func(cmd command.Buffer) {
|
|
m.Instance.Bind(cmd)
|
|
})
|
|
}
|
|
|
|
func (m *ForwardMaterial) End() {
|
|
m.Objects.Flush(m.Instance.Descriptors().Objects)
|
|
m.Textures.Flush()
|
|
}
|
|
|
|
func (m *ForwardMaterial) Draw(cmds command.Recorder, msh mesh.Mesh) {
|
|
vkmesh, meshReady := m.Meshes.TryFetch(msh.Mesh().Get())
|
|
if !meshReady {
|
|
return
|
|
}
|
|
|
|
textures := m.Instance.Material().TextureSlots()
|
|
textureIds := AssignMeshTextures(m.Textures, msh, textures)
|
|
|
|
index := m.Objects.Store(uniform.Object{
|
|
Model: msh.Transform().Matrix(),
|
|
Textures: textureIds,
|
|
})
|
|
|
|
cmds.Record(func(cmd command.Buffer) {
|
|
vkmesh.Draw(cmd, index)
|
|
})
|
|
}
|
|
|
|
func (m *ForwardMaterial) Destroy() {
|
|
m.Instance.Material().Destroy()
|
|
}
|