home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
PC World 2006 July & August
/
PCWorld_2006-07-08_cd.bin
/
temacd
/
planearcade
/
planearcade.exe
/
Tank3.bmp
/
particlesystem.cpp
< prev
next >
Wrap
C/C++ Source or Header
|
2004-05-29
|
9KB
|
333 lines
#include "main.h"
//------------------------------------------------------------------
// Name: PARTICLESYSTEM()
// Desc: deÜtruktor
//------------------------------------------------------------------
PARTICLESYSTEM::PARTICLESYSTEM()
{
Point = NULL;
Particle = NULL;
NumParticles = 0;
ActParticle = 0;
//
//vÜetko nastavi na default
//
//--------------
//CycleMode
//--------------
CycleLeght = 10000.0f;
SpawnFreqency = 20.0f;
ActTime = 0.0f;
//-----------------
//Kolizie
//-----------------
Oct = NULL;
OctreeCollision = false;
//---------------
//Vlastnosti
//---------------
Emitter.Position = Get3D(0.0f,0.0f,0.0f);
Emitter.Radius = 10.0f;
Emitter.SizeX = 10.0f;
Emitter.SizeY = 10.0f;
Emitter.SizeZ = 10.0f;
Emitter.Type = EMITTER_POINT;
Direction = Get3D(0.0f,5.0f,0.0f);
Gravity = Get3D(0.0f,-2.0f,0.0f);
DirectionPower = 0.1f;
GravityPower = 0.2f;
SpawnPower = 10.0f;
MirrorFactor = 0.6f;
DirRandFactor = 1.0f;
Rotation = true;
RotationSpeed = 0.1f;
//SRC vlastnosti pociatocne
SRCSize = 0.7f;
SRCFrame = 0.0f;
SRCColor = GetColor(1.0f,1.0f,1.0f,0.0f);
//DST vlastnosti koneΦne
DSTSize = 0.7f;
DSTFrame = 0.0f;
DSTColor = GetColor(0.0f,1.0f,0.0f,0.0f);
}
//------------------------------------------------------------------
// Name: ~PARTICLESYSTEM()
// Desc: konÜtruktor
//------------------------------------------------------------------
PARTICLESYSTEM::~PARTICLESYSTEM()
{
if (Point != NULL)
delete[]Point;
Point = NULL;
}
//------------------------------------------------------------------
// Name: Initialize()
// Desc: inicializuje system
//------------------------------------------------------------------
void PARTICLESYSTEM::Initialize(PARTICLE *P,int NParticles)
{
//nastavi pointer
Particle = P;
Point = new PARTICLEPOINT [NParticles];
NumParticles = NParticles;
//nastavi vsetky particli na neaktivne
for (int i=0 ;i<NumParticles;i++)
{
Point[i].Active = false;
}
}
//------------------------------------------------------------------
// Name:
// Desc: Vyrenderuje aktivne particli
//------------------------------------------------------------------
void PARTICLESYSTEM::Render()
{
//vysledne
COLOR Color;
float Frame;
float Size;
//rozdiely
COLOR DColor;
float DFrame;
float DSize;
//rozdiely vypocita skor pre urychlenie
DColor.A = DSTColor.A - SRCColor.A;
DColor.R = DSTColor.R - SRCColor.R;
DColor.G = DSTColor.G - SRCColor.G;
DColor.B = DSTColor.B - SRCColor.B;
DFrame = DSTFrame - SRCFrame;
DSize = DSTSize - SRCSize;
//interpolant Φasu
float Int;
//pre vÜetky particles
for (int i=0;i<NumParticles;i++)
{
//ak je aktviny
if (Point[i].Active == true)
{
//vypocet Interpolatu
Int = Point[i].Time / CycleLeght ;
//interpoluj vlastnosti
Color.A = SRCColor.A + (Int * DColor.A);
Color.R = SRCColor.R + (Int * DColor.R);
Color.G = SRCColor.G + (Int * DColor.G);
Color.B = SRCColor.B + (Int * DColor.B);
Frame = SRCFrame + (Int*DFrame);
Size = SRCSize + (Int*DSize);
Particle->RenderParticle(Point[i].Position,Color,Size,Point[i].Rotation,Frame);
// DebugDrawLine(Point[i].Position,Get3D(Point[i].Position.X + Point[i].Direction.X,Point[i].Position.Y + Point[i].Direction.Y,Point[i].Position.Z+ Point[i].Direction.Z));
}
}
Engine.SetZwrite(false);
Particle->Render();
Engine.SetZwrite(true);
}
//------------------------------------------------------------------
// Name: ProcessParticles()
// Desc: VypoΦita poziciu particlov
//------------------------------------------------------------------
void PARTICLESYSTEM::ProcessParticles()
{
//pocitadlo
if(ActTime > SpawnFreqency)
{
ActTime = 0.0f;
}
ActTime += PowerTime(1.0f);
for (int i=0;i<NumParticles;i++)
{
if (Point[i].Active == true)
{
//casovac
Point[i].Time += PowerTime(1.0f);
//zastavi particle ak uz dlho zije
if (Point[i].Time > CycleLeght)
{
Point[i].Active = false;
continue;
}
//vypocita smerovy vektor
Point[i].Direction.X += Gravity.X*Power(GravityPower);
Point[i].Direction.Y += Gravity.Y*Power(GravityPower);
Point[i].Direction.Z += Gravity.Z*Power(GravityPower);
//kolizia
if (OctreeCollision == true)
{
if(Oct->ColliseDistance(Point[i].Position,Get3D(Point[i].Position.X + Power(DirectionPower) *Point[i].Direction.X,
Point[i].Position.Y + Power(DirectionPower) *Point[i].Direction.Y,
Point[i].Position.Z + Power(DirectionPower) *Point[i].Direction.Z)))
{
float DirSize = CalcDistance(Point[i].Direction,Get3D(0.0f,0.0f,0.0f));
//upravi kolizny normalovy vektor na velkost direction vektoru
VECTOR3D Pom;
Pom = Oct->IntNormal;
Pom.X = Pom.X * -DirSize;
Pom.Y = Pom.Y * -DirSize;
Pom.Z = Pom.Z * -DirSize;
//sub
Pom.X = Pom.X + Point[i].Direction.X;
Pom.Y = Pom.Y + Point[i].Direction.Y;
Pom.Z = Pom.Z + Point[i].Direction.Z;
//normalize
Normalize(&Pom);
Point[i].Direction.X = -Pom.X * DirSize * MirrorFactor;
Point[i].Direction.Y = -Pom.Y * DirSize * MirrorFactor;
Point[i].Direction.Z = -Pom.Z * DirSize * MirrorFactor;
}
}
//vypocita poziciu
Point[i].Position.X += Power(DirectionPower) * Point[i].Direction.X;
Point[i].Position.Y += Power(DirectionPower) * Point[i].Direction.Y;
Point[i].Position.Z += Power(DirectionPower) * Point[i].Direction.Z;
Point[i].Rotation += Power(RotationSpeed);
}
}
}
//------------------------------------------------------------------
// Name: SpawnParticles()
// Desc: Vypusti naraz particli
//------------------------------------------------------------------
void PARTICLESYSTEM::SpawnParticles(int NParticles)
{
for (int i=0;i<NParticles;i++)
Spawn();
}
//------------------------------------------------------------------
// Name: SpawnParticlesTime()
// Desc: Vypusta particli neustale podla frekvencie
//------------------------------------------------------------------
void PARTICLESYSTEM::SpawnParticlesTime(int NParticles)
{
if(ActTime > SpawnFreqency)
{
SpawnParticles(NParticles);
}
}
//------------------------------------------------------------------
// Name: Spawn()
// Desc: Vypusti jeden particle
//------------------------------------------------------------------
void PARTICLESYSTEM::Spawn()
{
//vektor vygenerovany
VECTOR3D RnDir;
//ak je eÜte stale aktviny nerenderuj
if (Point[ActParticle].Active == true)
return;
//////////
//Random
RnDir = RandomVector();
RnDir.X = (RnDir.X*DirRandFactor) + Direction.X;
RnDir.Y = (RnDir.Y*DirRandFactor) + Direction.Y;
RnDir.Z = (RnDir.Z*DirRandFactor) + Direction.Z;
Normalize(&RnDir);
/////////
//Point
if (Emitter.Type == EMITTER_POINT)
{
Point[ActParticle].Position = Emitter.Position;
}
/////////
//Box
if (Emitter.Type == EMITTER_BOX)
{
Point[ActParticle].Position.X = Emitter.Position.X + RandomMinMax(-Emitter.SizeX,Emitter.SizeX);
Point[ActParticle].Position.Y = Emitter.Position.Y + RandomMinMax(-Emitter.SizeY,Emitter.SizeY);
Point[ActParticle].Position.Z = Emitter.Position.Z + RandomMinMax(-Emitter.SizeZ,Emitter.SizeZ);
}
/////////
//Sphere
if (Emitter.Type == EMITTER_SPHERE)
{
Point[ActParticle].Position.X = Emitter.Position.X + RandomMinMax(-Emitter.Radius,Emitter.Radius);
Point[ActParticle].Position.Y = Emitter.Position.Y + RandomMinMax(-Emitter.Radius,Emitter.Radius);
Point[ActParticle].Position.Z = Emitter.Position.Z + RandomMinMax(-Emitter.Radius,Emitter.Radius);
}
Point[ActParticle].Active = true;
Point[ActParticle].Direction.X = RnDir.X * SpawnPower;
Point[ActParticle].Direction.Y = RnDir.Y * SpawnPower;
Point[ActParticle].Direction.Z = RnDir.Z * SpawnPower;
Point[ActParticle].Time = 0.0f;
Point[ActParticle].Rotation = RandomMinMax(-D3DX_PI,D3DX_PI);
ActParticle++;
if (ActParticle == NumParticles)
ActParticle = 0;
}
//------------------------------------------------------------------
// Name: SetOctreeCollision()
// Desc: nastavi koliziu particlov zo octree
//------------------------------------------------------------------
void PARTICLESYSTEM::SetOctreeCollision(OCTREE *O)
{
Oct = O;
OctreeCollision = true;
}