Skip to content

Commit

Permalink
instancing
Browse files Browse the repository at this point in the history
  • Loading branch information
OVOAOVO committed Nov 1, 2023
1 parent 43de71b commit b8854c4
Show file tree
Hide file tree
Showing 11 changed files with 113 additions and 29 deletions.
8 changes: 7 additions & 1 deletion Engine/BuiltInShaders/shaders/varying.def.sc
Original file line number Diff line number Diff line change
Expand Up @@ -18,4 +18,10 @@ vec2 a_texcoord0 : TEXCOORD0;
vec4 a_color0 : COLOR0;
vec4 a_color1 : COLOR1;
ivec4 a_indices : BLENDINDICES;
vec4 a_weight : BLENDWEIGHT;
vec4 a_weight : BLENDWEIGHT;

vec4 i_data0 : TEXCOORD7;
vec4 i_data1 : TEXCOORD6;
vec4 i_data2 : TEXCOORD5;
vec4 i_data3 : TEXCOORD4;
vec4 i_data4 : TEXCOORD3;
9 changes: 6 additions & 3 deletions Engine/BuiltInShaders/shaders/vs_particle.sc
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
$input a_position, a_color0, a_texcoord0
$input a_position, a_color0, a_texcoord0, i_data0, i_data1 ,i_data2 ,i_data3 ,i_data4
$output v_color0, v_texcoord0

#include "../common/common.sh"

void main()
{
gl_Position = mul(u_modelViewProj, vec4(a_position, 1.0) );
v_color0 = a_color0;
mat4 model = mtxFromCols(i_data0, i_data1, i_data2, i_data3);

vec4 worldPos = mul(model,vec4(a_position,1.0));
gl_Position = mul(u_viewProj, worldPos);
v_color0 = a_color0*i_data4;
v_texcoord0 = a_texcoord0;
}
31 changes: 30 additions & 1 deletion Engine/Source/Editor/ECWorld/ECWorldConsumer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,11 @@ void ECWorldConsumer::Execute(const cd::SceneDatabase* pSceneDatabase)
CD_WARN("[ECWorldConsumer] No valid meshes in the consumed SceneDatabase.");
}

if (0U != pSceneDatabase->GetParticleEmitterCount())
{
CD_INFO("[ECWorldConsumer] Have ParticleEmitter");
}

auto ParseMesh = [&](cd::MeshID meshID, const cd::Transform& tranform)
{
engine::Entity meshEntity = m_pSceneWorld->GetWorld()->CreateEntity();
Expand Down Expand Up @@ -139,7 +144,7 @@ void ECWorldConsumer::Execute(const cd::SceneDatabase* pSceneDatabase)
}

for (const auto& node : pSceneDatabase->GetNodes())
{
{
if (m_nodeMinID > node.GetID().Data())
{
continue;
Expand Down Expand Up @@ -167,6 +172,12 @@ void ECWorldConsumer::Execute(const cd::SceneDatabase* pSceneDatabase)
engine::Entity lightEntity = m_pSceneWorld->GetWorld()->CreateEntity();
AddLight(lightEntity, light);
}

for (const auto& particle : pSceneDatabase->GetParticleEmitters())
{
engine::Entity particleEntity = m_pSceneWorld->GetWorld()->CreateEntity();
AddParticleEmitter(particleEntity, particle);
}
}

void ECWorldConsumer::AddCamera(engine::Entity entity, const cd::Camera& camera)
Expand Down Expand Up @@ -371,4 +382,22 @@ void ECWorldConsumer::AddMorphs(engine::Entity entity, const std::vector<cd::Mor
blendShapeComponent.Build();
}

void ECWorldConsumer::AddParticleEmitter(engine::Entity entity, const cd::ParticleEmitter& particle)
{
engine::World* pWorld = m_pSceneWorld->GetWorld();
engine::NameComponent& nameComponent = pWorld->CreateComponent<engine::NameComponent>(entity);
nameComponent.SetName(particle.GetName());
auto& particleEmitterComponent = pWorld->CreateComponent<engine::ParticleEmitterComponent>(entity);
// TODO : Some initialization here.
auto& transformComponent = pWorld->CreateComponent<engine::TransformComponent>(entity);
cd::Vec3f pos = particle.GetPosition();
transformComponent.SetTransform(cd::Transform::Identity());
transformComponent.GetTransform().SetTranslation(pos);
transformComponent.Build();

particleEmitterComponent.GetParticleSystem().Init();
particleEmitterComponent.SetFVelocity(particle.GetVelocity());
particleEmitterComponent.Build();
}

}
2 changes: 2 additions & 0 deletions Engine/Source/Editor/ECWorld/ECWorldConsumer.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ class Node;
class SceneDatabase;
class Texture;
class VertexFormat;
class ParticleEmitter;

}

Expand Down Expand Up @@ -67,6 +68,7 @@ class ECWorldConsumer final : public cdtools::IConsumer
void AddAnimation(engine::Entity entity, const cd::Animation& animation, const cd::SceneDatabase* pSceneDatabase);
void AddMaterial(engine::Entity entity, const cd::Material* pMaterial, engine::MaterialType* pMaterialType, const cd::SceneDatabase* pSceneDatabase);
void AddMorphs(engine::Entity entity, const std::vector<cd::Morph>& morphs, const cd::Mesh* pMesh);
void AddParticleEmitter(engine::Entity entity, const cd::ParticleEmitter& particle);

private:
engine::MaterialType* m_pDefaultMaterialType = nullptr;
Expand Down
2 changes: 1 addition & 1 deletion Engine/Source/Editor/UILayers/AssetBrowser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ bool IsLightInputFile(const char* pFileExtension)

bool IsParticleInputFile(const char* pFileExtension)
{
constexpr const char* pFileExtensions[] = { ".efkefc" };
constexpr const char* pFileExtensions[] = { ".efkefc"};
constexpr const int fileExtensionsSize = sizeof(pFileExtensions) / sizeof(pFileExtensions[0]);
for (int extensionIndex = 0; extensionIndex < fileExtensionsSize; ++extensionIndex)
{
Expand Down
2 changes: 1 addition & 1 deletion Engine/Source/Editor/UILayers/Inspector.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -630,7 +630,7 @@ void UpdateComponentWidget<engine::ParticleEmitterComponent>(engine::SceneWorld*

if (isOpen)
{
ImGuiUtils::ImGuiVectorProperty("Velocity",pParticleEmitterComponent->GetParticleSystem().GetVelocity());
ImGuiUtils::ImGuiVectorProperty("Velocity",pParticleEmitterComponent->GetFVelocity());
}

ImGui::Separator();
Expand Down
28 changes: 14 additions & 14 deletions Engine/Source/Runtime/ECWorld/ParticleEmitterComponent.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,19 +14,19 @@ void engine::ParticleEmitterComponent::Build()
PaddingVertexBuffer();
PaddingIndexBuffer();

m_particleVBH = bgfx::createDynamicVertexBuffer(bgfx::makeRef(m_particleVertexBuffer.data(), static_cast<uint32_t>(m_particleVertexBuffer.size())), vertexLayout).idx;
m_particleIBH = bgfx::createDynamicIndexBuffer(bgfx::makeRef(m_particleIndexBuffer.data(), static_cast<uint32_t>(m_particleIndexBuffer.size())), 0U).idx;
m_particleVBH = bgfx::createVertexBuffer(bgfx::makeRef(m_particleVertexBuffer.data(), static_cast<uint32_t>(m_particleVertexBuffer.size())), vertexLayout).idx;
m_particleIBH = bgfx::createIndexBuffer(bgfx::makeRef(m_particleIndexBuffer.data(), static_cast<uint32_t>(m_particleIndexBuffer.size())), 0U).idx;
}

void engine::ParticleEmitterComponent::UpdateBuffer()
{
//bgfx::update(vbh, 0, bgfx::makeRef(vertexBuffer.data(), vertexBuffer.size()));
PaddingVertexBuffer();
PaddingIndexBuffer();

bgfx::update(bgfx::DynamicVertexBufferHandle{ GetParticleVBH() }, 0 , bgfx::makeRef(m_particleVertexBuffer.data(), static_cast<uint32_t>(m_particleVertexBuffer.size())));
bgfx::update(bgfx::DynamicIndexBufferHandle{GetParticleIBH()}, 0, bgfx::makeRef(m_particleIndexBuffer.data(), static_cast<uint32_t>(m_particleIndexBuffer.size())));
}
//void engine::ParticleEmitterComponent::UpdateBuffer()
//{
// //bgfx::update(vbh, 0, bgfx::makeRef(vertexBuffer.data(), vertexBuffer.size()));
// PaddingVertexBuffer();
// PaddingIndexBuffer();
//
// bgfx::update(bgfx::DynamicVertexBufferHandle{ GetParticleVBH() }, 0 , bgfx::makeRef(m_particleVertexBuffer.data(), static_cast<uint32_t>(m_particleVertexBuffer.size())));
// bgfx::update(bgfx::DynamicIndexBufferHandle{GetParticleIBH()}, 0, bgfx::makeRef(m_particleIndexBuffer.data(), static_cast<uint32_t>(m_particleIndexBuffer.size())));
//}

void engine::ParticleEmitterComponent::PaddingVertexBuffer()
{
Expand Down Expand Up @@ -63,7 +63,7 @@ void engine::ParticleEmitterComponent::PaddingIndexBuffer()
* indexBuffer
*/
size_t indexTypeSize = sizeof(uint16_t);
m_particleIndexBuffer.resize(m_particleSystem.GetMaxCount()/4*7 * indexTypeSize);
m_particleIndexBuffer.resize(m_particleSystem.GetMaxCount()/4* 6 * indexTypeSize);
uint32_t currentDataSize = 0U;
auto currentDataPtr = m_particleIndexBuffer.data();

Expand All @@ -77,12 +77,12 @@ void engine::ParticleEmitterComponent::PaddingIndexBuffer()
indexes.push_back(vertexIndex);
indexes.push_back(vertexIndex+2);
indexes.push_back(vertexIndex+3);
indexes.push_back(static_cast<uint16_t>(65535));

}

for (const auto& index : indexes)
{
std::memcpy(&currentDataPtr[currentDataSize], &index, indexTypeSize);
currentDataSize += static_cast<uint32_t>(indexTypeSize);
}
}
}
8 changes: 7 additions & 1 deletion Engine/Source/Runtime/ECWorld/ParticleEmitterComponent.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ class ParticleEmitterComponent final

engine::ParticleSystem &GetParticleSystem() { return m_particleSystem; }

cd::Vec3f& GetFVelocity() { return m_fill_velocity; }
void SetFVelocity(cd::Vec3f fillnum) { m_fill_velocity = fillnum; }

uint16_t& GetParticleVBH(){ return m_particleVBH; }
uint16_t& GetParticleIBH() { return m_particleIBH; }

Expand All @@ -35,14 +38,17 @@ class ParticleEmitterComponent final

void Build();

void UpdateBuffer();
//void UpdateBuffer();

void PaddingVertexBuffer();

void PaddingIndexBuffer();

private:
ParticleSystem m_particleSystem;

cd::Vec3f m_fill_velocity
;
std::vector<std::byte> m_particleVertexBuffer;
std::vector<std::byte> m_particleIndexBuffer;
uint16_t m_particleVBH = UINT16_MAX;
Expand Down
4 changes: 4 additions & 0 deletions Engine/Source/Runtime/ParticleSystem/ParticleSystem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@ void engine::ParticleSystem::Reset(int index)
{

m_pos[index] = cd::Vec3f(0.0f, 0.0f, 0.0f);
m_rotation[index] = cd::Vec3f(0.0f, 0.0f, 0.0f);
m_scale[index] = cd::Vec3f(0.0f, 0.0f, 0.0f);
m_velocity[index] = cd::Vec3f(0.0f, 0.0f, 0.0f);
m_acceleration[index] = cd::Vec3f(0.0f, 0.0f, 0.0f);

Expand Down Expand Up @@ -116,6 +118,8 @@ bool engine::ParticleSystem::UpdateActive(float deltaTime,int i)
void engine::ParticleSystem::Init()
{
m_pos.resize(m_particleMaxCount);
m_rotation.resize(m_particleMaxCount);
m_scale.resize(m_particleMaxCount);
m_velocity.resize(m_particleMaxCount);
m_acceleration.resize(m_particleMaxCount);
m_color.resize(m_particleMaxCount);
Expand Down
9 changes: 9 additions & 0 deletions Engine/Source/Runtime/ParticleSystem/ParticleSystem.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,12 @@ class ParticleSystem final
cd::Vec3f& GetPos(int index) { return m_pos[index]; }
void SetPos(cd::Vec3f pos) { m_pos[m_particleIndex] = pos; }

cd::Vec3f& GetRotation(int index) { return m_rotation[index]; }
void SetRotation(cd::Vec3f rotate) { m_rotation[m_particleIndex] = rotate; }

cd::Vec3f& GetScale(int index) { return m_scale[index]; }
void SetScale(cd::Vec3f scale) { m_scale[m_particleIndex] = scale; }

cd::Vec3f& GetVelocity() { return m_velocity[m_particleIndex]; }
void SetVelocity(cd::Vec3f velocity) { m_velocity[m_particleIndex] = velocity; }

Expand Down Expand Up @@ -70,6 +76,9 @@ class ParticleSystem final

std::vector<int> m_FreeParticleIndex;
std::vector<cd::Vec3f> m_pos;
std::vector<cd::Vec3f>m_rotation;
std::vector<cd::Vec3f>m_scale;

std::vector<cd::Vec3f> m_velocity;
//std::vector<cd::Quaternion> m_emiterDirection;
std::vector<cd::Vec3f> m_acceleration;
Expand Down
39 changes: 32 additions & 7 deletions Engine/Source/Runtime/Rendering/ParticleRenderer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,7 @@ namespace engine {
void ParticleRenderer::Init()
{
constexpr StringCrc ParticleProgram = StringCrc{ "ParticleProgram" };
GetRenderContext()->RegisterShaderProgram(ParticleProgram, { "vs_PBR", "fs_PBR" });
//GetRenderContext()->CreateProgram("ParticleProgram", "vs_particle.bin", "fs_particle.bin");
GetRenderContext()->RegisterShaderProgram(ParticleProgram, { "vs_particle", "fs_particle" });
bgfx::setViewName(GetViewID(), "ParticleRenderer");
}

Expand Down Expand Up @@ -45,6 +44,8 @@ void ParticleRenderer::Render(float deltaTime)
{
pEmitterComponent->GetParticleSystem().AllocateParticleIndex();
pEmitterComponent->GetParticleSystem().SetPos(particleTransform.GetTranslation());
//pEmitterComponent->GetParticleSystem().SetVelocity(cd::Vec3f(0.7f,0.7f,0.0f));
pEmitterComponent->GetParticleSystem().SetVelocity(pEmitterComponent->GetFVelocity());
}

for (int i = 0; i < particleMaxCount; ++i)
Expand All @@ -56,17 +57,41 @@ void ParticleRenderer::Render(float deltaTime)
}
}

if (m_bufferChange)
pEmitterComponent->PaddingVertexBuffer();
pEmitterComponent->PaddingIndexBuffer();

const uint16_t instanceStride = 80;
// to total number of instances to draw
uint32_t totalSprites = pEmitterComponent->GetParticleSystem().GetMaxCount();
uint32_t drawnSprites = bgfx::getAvailInstanceDataBuffer(totalSprites, instanceStride);

bgfx::InstanceDataBuffer idb;
bgfx::allocInstanceDataBuffer(&idb, drawnSprites, instanceStride);

uint8_t* data = idb.data;

for (uint32_t ii = 0; ii < drawnSprites; ++ii)
{
pEmitterComponent->UpdateBuffer();
float* mtx = (float*)data;
bx::mtxRotateXY(mtx,0.0f, 0.0f);
mtx[12] = pEmitterComponent->GetParticleSystem().GetPos(ii).x();
mtx[13] = pEmitterComponent->GetParticleSystem().GetPos(ii).y();
mtx[14] = pEmitterComponent->GetParticleSystem().GetPos(ii).z();
float* color = (float*)&data[64];
color[0] = 1.0f;
color[1] = 1.0f;
color[2] = 1.0f;
color[3] = 1.0f;

data += instanceStride;
}

constexpr StringCrc ParticleSampler("s_texColor");
bgfx::setTexture(0, GetRenderContext()->GetUniform(ParticleSampler), m_particleTextureHandle);
bgfx::setVertexBuffer(0, bgfx::VertexBufferHandle{ pEmitterComponent->GetParticleVBH() });
bgfx::setIndexBuffer(bgfx::IndexBufferHandle{ pEmitterComponent->GetParticleIBH() });

bgfx::setVertexBuffer(0, bgfx::DynamicVertexBufferHandle{ pEmitterComponent->GetParticleVBH() });
bgfx::setIndexBuffer(bgfx::DynamicIndexBufferHandle{ pEmitterComponent->GetParticleIBH() });

bgfx::setInstanceDataBuffer(&idb);

constexpr uint64_t state = BGFX_STATE_WRITE_MASK | BGFX_STATE_MSAA | BGFX_STATE_DEPTH_TEST_LESS |
BGFX_STATE_BLEND_FUNC(BGFX_STATE_BLEND_SRC_ALPHA, BGFX_STATE_BLEND_INV_SRC_ALPHA) | BGFX_STATE_PT_TRISTRIP;
Expand Down

0 comments on commit b8854c4

Please sign in to comment.