コード例 #1
0
void WaveParticleManager::SpawnCircularWave(int numberOfParticles, glm::vec2 position, float amplitude, float speed, float radius)
{
    float dispersionAngle = 2.0f * 3.14159f / numberOfParticles;
    float initializationTime = (radius / speed);
	for (int i = 0; i < numberOfParticles; ++i)
	{
		WaveParticle* waveParticle = GetNextParticle();
        WaveParticle* waveParticle2 = GetNextParticle();
		float dispersionAngle = 2.0f * 3.14159f / numberOfParticles;
		waveParticle->Initialize(glm::rotate(glm::vec2(1.f, 0.f), i * dispersionAngle), position, amplitude, speed, initializationTime, radius, dispersionAngle);
        waveParticle2->Initialize(glm::rotate(glm::vec2(1.f, 0.f), i * dispersionAngle), position, -amplitude, speed, 0.f , radius, dispersionAngle);
    }
}
コード例 #2
0
ファイル: Scene.cpp プロジェクト: sunzhiyuan/opencl
//--------------------------------------------------------------------------------------
// Name: EmitParticles()
// Desc: 
//--------------------------------------------------------------------------------------
VOID CParticleEmitter::EmitParticles( PARTICLE* pParticles, FLOAT32 fElapsedTime,
                                      FLOAT32 fCurrentTime, FRMCOLOR Colors[NUM_COLORS],
                                      FLOAT32 fTimePerColor,
									  EmitParticleShader *epShader,
									  GLuint *srcBuffer, GLuint *pVAOs, GLuint *dstBuffer,
									  FRM_VERTEX_ELEMENT* pVertexLayout,
									  UINT32 nVertexSize, BOOL bUseTransformFeedback, GLuint Query )
{
    // Determine the color of the particles to be emitted
    FLOAT32  t = ( fCurrentTime / fTimePerColor ) - FrmFloor( fCurrentTime / fTimePerColor );
    UINT32   nColorIndex = (INT32)FrmFloor( fCurrentTime / fTimePerColor ) % NUM_COLORS;
    FRMCOLOR vColor1 = Colors[ nColorIndex ];
    FRMCOLOR vColor2 = Colors[(nColorIndex+1) % NUM_COLORS ];
    FRMCOLOR vColor  = FrmLerp( t, vColor1, vColor2 );

    m_fLeftOverParticles += m_fEmissionRate * fElapsedTime;

	if( !bUseTransformFeedback )
	{
		// Create the needed number of particles based upon our emission rate.
		for( INT32 i = 0; i < (INT32)NUM_PARTICLES; i++ )
		{
			// Get the next particle
			PARTICLE* pParticle = GetNextParticle( pParticles );

			if( FrmRand() < m_fLeftOverParticles / NUM_PARTICLES )
			{
				FLOAT32      fAngle            = m_fEmitterSpread * ( FrmRand() - 0.5f );
				FRMMATRIX4X4 matRotate         = FrmMatrixRotate( FrmRadians(fAngle), 0.0f, 0.0f, -1.0f );
				FRMVECTOR3   vVelocity         = FrmVector3TransformCoord( m_vVelocity, matRotate );

				pParticle->m_vPosition         = m_vPosition + FrmSphrand( m_fEmitterRadius );
				pParticle->m_vVelocity         = vVelocity * ApplyVariance( 1.0f, m_fSpeedVariance );
				pParticle->m_vColor            = FRMVECTOR4( vColor.r/255.0f, vColor.g/255.0f, vColor.b/255.0f, vColor.a/255.0f );
				pParticle->m_vColor.a          = ApplyVariance( m_fInitialOpacity, m_fOpacityVariance );
				pParticle->m_fStartTime        = fCurrentTime;
				pParticle->m_fLifeSpan         = ApplyVariance( m_fInitialLifeSpan, m_fLifeSpanVariance );
				pParticle->m_fInitialSize      = ApplyVariance( m_fInitialSize, m_fInitialSizeVariance );
				pParticle->m_fSizeIncreaseRate = ApplyVariance( m_fSizeIncreaseRate, m_fSizeIncreaseRateVarience );
			}
		}
	}
	else
	{
		// Using transform feedback to do particle emission

		// Set up the shader
		glUseProgram( epShader->ShaderID );
		glUniform3fv( epShader->slotvPosition, 1, (FLOAT32 *)&m_vPosition );
		glUniform3fv( epShader->slotvVelocity, 1, (FLOAT32 *)&m_vVelocity );
		glUniform1f( epShader->slotfEmitterSpread, m_fEmitterSpread );
		glUniform1f( epShader->slotfEmitterRadius, m_fEmitterRadius );
		glUniform1f( epShader->slotfSpeedVariance, m_fSpeedVariance );
		glUniform1f( epShader->slotfInitialOpacity, m_fInitialOpacity );
		glUniform1f( epShader->slotfOpacityVariance, m_fOpacityVariance );
		glUniform1f( epShader->slotfInitialLifeSpan, m_fInitialLifeSpan );
		glUniform1f( epShader->slotfLifeSpanVariance, m_fLifeSpanVariance );
		glUniform1f( epShader->slotfInitialSize, m_fInitialSize );
		glUniform1f( epShader->slotfInitialSizeVariance, m_fInitialSizeVariance );
		glUniform1f( epShader->slotfSizeIncreaseRate, m_fSizeIncreaseRate );
		glUniform1f( epShader->slotfSizeIncreaseRateVariance, m_fSizeIncreaseRateVarience );
		glUniform1f( epShader->slotfTime, fCurrentTime );
		glUniform4f( epShader->slotvColor, vColor.r/255.0f, vColor.g/255.0f, vColor.b/255.0f, vColor.a/255.0f );
		glUniform1f( epShader->slotfEmissionRate, m_fLeftOverParticles/NUM_PARTICLES );


		glEnable( GL_RASTERIZER_DISCARD );

		glBindVertexArray(pVAOs[0]);
		// set source buffer
		glBindBuffer( GL_ARRAY_BUFFER, *srcBuffer );		
		FrmSetVertexLayout( pVertexLayout, nVertexSize, 0 );
		glBindBuffer( GL_ARRAY_BUFFER, 0 );	
		glBindVertexArray(0);

		// set destination buffer
		glBindBufferBase( GL_TRANSFORM_FEEDBACK_BUFFER, 0, *dstBuffer );
		
		glBindVertexArray(pVAOs[0]);

		glBeginQuery(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, Query); 

		// Perfom transform feedback
		glBeginTransformFeedback( GL_POINTS );

		glDrawArrays( GL_POINTS, 0, NUM_PARTICLES );
		glEndTransformFeedback();

		glEndQuery(GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN); 

		glDisable( GL_RASTERIZER_DISCARD );

		glBindVertexArray(0);
		glBindBufferBase( GL_TRANSFORM_FEEDBACK_BUFFER, 0, 0 );
	}

	m_fLeftOverParticles -= FrmFloor( m_fLeftOverParticles );
}