#pragma kernel CSMain ${VFXGlobalInclude} ${VFXGlobalDeclaration} #define USE_DEAD_LIST (VFX_USE_ALIVE_CURRENT && !HAS_STRIPS) RWByteAddressBuffer attributeBuffer; #if USE_DEAD_LIST RWStructuredBuffer deadListOut; #endif #if VFX_HAS_INDIRECT_DRAW RWStructuredBuffer indirectBuffer; #endif #if HAS_STRIPS RWStructuredBuffer stripDataBuffer; #endif #if VFX_USE_STRIPALIVE_CURRENT Buffer attachedStripDataBuffer; #endif CBUFFER_START(updateParams) uint nbMax; uint dispatchWidth; uint systemSeed; CBUFFER_END ${VFXPerPassInclude} ${VFXGeneratedBlockFunction} [numthreads(NB_THREADS_PER_GROUP,1,1)] void CSMain(uint3 groupId : SV_GroupID, uint3 groupThreadId : SV_GroupThreadID) { uint id = groupThreadId.x + groupId.x * NB_THREADS_PER_GROUP + groupId.y * dispatchWidth * NB_THREADS_PER_GROUP; uint index = id; if (id < nbMax) { Attributes attributes = (Attributes)0; SourceAttributes sourceAttributes = (SourceAttributes)0; #if VFX_USE_ALIVE_CURRENT ${VFXLoadAttributes:{alive|stripAlive}} if (attributes.alive) { ${VFXLoadAttributes:{(?!(alive|stripAlive))(\b\w)}} #if HAS_STRIPS const StripData stripData = GetStripDataFromParticleIndex(index, PARTICLE_PER_STRIP_COUNT); InitStripAttributes(index, attributes, stripData); #endif #if VFX_UPDATE_SKIP_ZERO_DELTA_TIME ${VFXLoadParameter:{deltaTime}} if (deltaTime != 0.0f) #endif { ${VFXProcessBlocks} } if (attributes.alive) { ${VFXStoreAttributes:{(?!(alive))(\b\w)}} #if VFX_HAS_INDIRECT_DRAW uint indirectIndex = indirectBuffer.IncrementCounter(); indirectBuffer[indirectIndex] = index; #endif #if HAS_STRIPS uint relativeIndexInStrip = GetRelativeIndex(index, stripData); InterlockedMin(STRIP_DATA(STRIP_MIN_ALIVE, stripData.stripIndex), relativeIndexInStrip); InterlockedMax(STRIP_DATA(STRIP_MAX_ALIVE, stripData.stripIndex), relativeIndexInStrip); #endif } else { ${VFXStoreAttributes:{alive|eventCount}} #if USE_DEAD_LIST && !VFX_USE_STRIPALIVE_CURRENT uint deadIndex = deadListOut.IncrementCounter(); deadListOut[deadIndex] = index; #endif } } #if USE_DEAD_LIST && VFX_USE_STRIPALIVE_CURRENT else if (attributes.stripAlive) { if (STRIP_DATA_X(attachedStripDataBuffer, STRIP_MIN_ALIVE, index) == ~1) // Attached strip is no longer alive, recycle the particle { uint deadIndex = deadListOut.IncrementCounter(); deadListOut[deadIndex] = index; attributes.stripAlive = false; ${VFXStoreAttributes:{stripAlive}} } } #endif #else ${VFXLoadAttributes} #if HAS_STRIPS const StripData stripData = GetStripDataFromParticleIndex(index, PARTICLE_PER_STRIP_COUNT); InitStripAttributes(index, attributes, stripData); #endif #if VFX_UPDATE_SKIP_ZERO_DELTA_TIME ${VFXLoadParameter:{deltaTime}} if (deltaTime != 0.0f) #endif { ${VFXProcessBlocks} } ${VFXStoreAttributes} #if VFX_HAS_INDIRECT_DRAW uint indirectIndex = indirectBuffer.IncrementCounter(); indirectBuffer[indirectIndex] = index; #endif #endif } }