You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
166 lines
6.1 KiB
166 lines
6.1 KiB
// Defined in order to enable writing to solver buffers |
|
#define FLUVIO_SOLVER |
|
|
|
#include "../Includes/FluvioLanguageSupport.cginc" // For FLUVIO_INITIALIZE |
|
|
|
// --------------------------------------------------------------------------------------- |
|
// Main include |
|
// --------------------------------------------------------------------------------------- |
|
|
|
// If the location of this shader or FluvioCompute.cginc is changed, |
|
// change this to the RELATIVE path to the new include. |
|
#include "../Includes/FluvioCompute.cginc" |
|
|
|
// Special kernel function |
|
#ifdef FLUVIO_API_OPENCL |
|
#define FLUVIO_KERNEL_PARTICLES(kernelName) \ |
|
__kernel \ |
|
void kernelName( \ |
|
int4 fluvio_Count, \ |
|
int fluvio_Stride, \ |
|
float4 fluvio_KernelSize, \ |
|
float4 fluvio_KernelFactors, \ |
|
float4 fluvio_Time, \ |
|
FLUVIO_BUFFER_RW(FluidParticle) fluvio_Particle, \ |
|
FLUVIO_BUFFER_SOLVER_RW(int) fluvio_Neighbors, \ |
|
FLUVIO_BUFFER(FluidData) fluvio_Fluid, \ |
|
int fluvio_ParticleSystem_FluidID, \ |
|
int fluvio_ParticleSystem_ParticleCount, \ |
|
float4 fluvio_ParticleSystem_Dimensions, \ |
|
mat4x4 fluvio_ParticleSystem_ParticleToWorldMatrix, \ |
|
mat4x4 fluvio_ParticleSystem_WorldToParticleMatrix) |
|
#else |
|
int fluvio_ParticleSystem_FluidID; |
|
int fluvio_ParticleSystem_ParticleCount; |
|
float4 fluvio_ParticleSystem_Dimensions; |
|
mat4x4 fluvio_ParticleSystem_ParticleToWorldMatrix; |
|
mat4x4 fluvio_ParticleSystem_WorldToParticleMatrix; |
|
#define FLUVIO_KERNEL_PARTICLES(kernelName) FLUVIO_KERNEL(kernelName) |
|
#endif |
|
|
|
// --------------------------------------------------------------------------------------- |
|
// Main plugin |
|
// --------------------------------------------------------------------------------------- |
|
|
|
FLUVIO_KERNEL_PARTICLES(ParticleSystemToFluid) |
|
{ |
|
int particleIndex = get_global_id(0); |
|
if (particleIndex >= fluvio_Count.y || fluvio_Particle[particleIndex].lifetime.x <= 0) return; |
|
|
|
if (fluvio_Particle[particleIndex].id.x != fluvio_ParticleSystem_FluidID) |
|
return; |
|
|
|
// Get particle ID |
|
int id = fluvio_Particle[particleIndex].id.y; |
|
|
|
// Skip despawned particles |
|
if (id >= fluvio_ParticleSystem_ParticleCount) |
|
return; |
|
|
|
// Get local position and velocity |
|
float4 position = fluvio_Particle[particleIndex].position; |
|
float4 velocity = fluvio_Particle[particleIndex].velocity; |
|
float size = velocity.w; |
|
|
|
// Apply transformation matrix |
|
float4 worldPosition = mul3x4(fluvio_ParticleSystem_ParticleToWorldMatrix, position); |
|
float4 worldVelocity = mulv(fluvio_ParticleSystem_ParticleToWorldMatrix, velocity); |
|
|
|
// Assign transformed position and velocity |
|
fluvio_Particle[particleIndex].position = worldPosition; |
|
worldVelocity.w = size; |
|
fluvio_Particle[particleIndex].velocity = worldVelocity; |
|
} |
|
|
|
#define INTEGRATE_PARTICLES \ |
|
if (particleIndex < fluvio_Count.z) \ |
|
{ \ |
|
float4 worldForce = fluvio_Particle[particleIndex].force; \ |
|
worldForce.z *= fluvio_ParticleSystem_Dimensions.x; \ |
|
float invMass = 1.0f/fluvio_Fluid[fluvio_Particle[particleIndex].id.x].particleMass; \ |
|
float4 acceleration = worldForce*invMass; \ |
|
int solverIterations = (int) fluvio_Time.w; \ |
|
float dtIter = fluvio_Time.y; \ |
|
for (int iter = 0; iter < solverIterations; ++iter) \ |
|
{ \ |
|
float4 t = dtIter*acceleration; \ |
|
if (dot(t, t) > (FLUVIO_MAX_SQR_VELOCITY_CHANGE*fluvio_KernelSize.w*fluvio_KernelSize.w)) \ |
|
{ \ |
|
t *= 0; \ |
|
} \ |
|
worldVelocity += t; \ |
|
} \ |
|
} |
|
|
|
FLUVIO_KERNEL_PARTICLES(FluidToParticleSystem) |
|
{ |
|
int particleIndex = get_global_id(0); |
|
if (particleIndex >= fluvio_Count.y || fluvio_Particle[particleIndex].lifetime.x <= 0) return; |
|
|
|
if (fluvio_Particle[particleIndex].id.x != fluvio_ParticleSystem_FluidID) |
|
return; |
|
|
|
// Get particle ID |
|
int id = fluvio_Particle[particleIndex].id.y; |
|
|
|
// Skip despawned particles |
|
if (id >= fluvio_ParticleSystem_ParticleCount) |
|
return; |
|
|
|
// Get world position, velocity, and normal |
|
float4 worldPosition = fluvio_Particle[particleIndex].position; |
|
float4 worldVelocity = fluvio_Particle[particleIndex].velocity; |
|
float4 worldNormal = fluvio_Particle[particleIndex].normal; |
|
|
|
// Axis constraint |
|
worldPosition.z *= fluvio_ParticleSystem_Dimensions.x; |
|
worldPosition.z += fluvio_ParticleSystem_Dimensions.y; |
|
worldVelocity.z *= fluvio_ParticleSystem_Dimensions.x; |
|
|
|
// Force integration: dynamic particles only |
|
INTEGRATE_PARTICLES; |
|
|
|
// Apply transformation matrix |
|
float4 position = mul3x4(fluvio_ParticleSystem_WorldToParticleMatrix, worldPosition); |
|
float4 velocity = mulv(fluvio_ParticleSystem_WorldToParticleMatrix, worldVelocity); |
|
float4 normal = mulv(fluvio_ParticleSystem_WorldToParticleMatrix, worldNormal); |
|
|
|
// Assign transformed position, velocity and normal |
|
fluvio_Particle[particleIndex].position = position; |
|
fluvio_Particle[particleIndex].velocity = velocity; |
|
fluvio_Particle[particleIndex].normal = normal; |
|
} |
|
|
|
FLUVIO_KERNEL_PARTICLES(FluidToParticleSystemFast) |
|
{ |
|
int particleIndex = get_global_id(0); |
|
if (particleIndex >= fluvio_Count.y || fluvio_Particle[particleIndex].lifetime.x <= 0) return; |
|
|
|
if (fluvio_Particle[particleIndex].id.x != fluvio_ParticleSystem_FluidID) |
|
return; |
|
|
|
// Get particle ID |
|
int id = fluvio_Particle[particleIndex].id.y; |
|
|
|
// Skip despawned particles |
|
if (id >= fluvio_ParticleSystem_ParticleCount) |
|
return; |
|
|
|
// Get world position, velocity, and normal |
|
float4 worldPosition = fluvio_Particle[particleIndex].position; |
|
float4 worldVelocity = fluvio_Particle[particleIndex].velocity; |
|
float4 worldNormal = fluvio_Particle[particleIndex].normal; |
|
|
|
// Axis constraint |
|
worldPosition.z *= fluvio_ParticleSystem_Dimensions.x; |
|
worldPosition.z += fluvio_ParticleSystem_Dimensions.y; |
|
worldVelocity.z *= fluvio_ParticleSystem_Dimensions.x; |
|
|
|
// Force integration: dynamic particles only |
|
INTEGRATE_PARTICLES; |
|
|
|
// Assign world position, velocity and normal |
|
fluvio_Particle[particleIndex].position = worldPosition; |
|
fluvio_Particle[particleIndex].velocity = worldVelocity; |
|
fluvio_Particle[particleIndex].normal = worldNormal; |
|
}
|
|
|