aboutsummaryrefslogtreecommitdiff
path: root/js/helper-classes/RDGE/src/core/script/particle.js
diff options
context:
space:
mode:
Diffstat (limited to 'js/helper-classes/RDGE/src/core/script/particle.js')
-rw-r--r--js/helper-classes/RDGE/src/core/script/particle.js842
1 files changed, 842 insertions, 0 deletions
diff --git a/js/helper-classes/RDGE/src/core/script/particle.js b/js/helper-classes/RDGE/src/core/script/particle.js
new file mode 100644
index 00000000..dd83433e
--- /dev/null
+++ b/js/helper-classes/RDGE/src/core/script/particle.js
@@ -0,0 +1,842 @@
1/* <copyright>
2This file contains proprietary software owned by Motorola Mobility, Inc.<br/>
3No rights, expressed or implied, whatsoever to this software are provided by Motorola Mobility, Inc. hereunder.<br/>
4(c) Copyright 2011 Motorola Mobility, Inc. All Rights Reserved.
5</copyright> */
6
7particleStats = function() {
8 this.numParticles = new stat("particles", "numParticles", 0);
9 this.numDrawCalls = new stat("particles", "numDrawCalls", 0);
10 this.numVerts = new stat("particles", "numVerts", 0);
11 this.numTris = new stat("particles", "numTris", 0);
12
13 this.report = function(psys) {
14 for (em in psys.emitters) {
15 var pbuffer = psys.emitters[em].pbuffer;
16 var idxBuffer = pbuffer.indexBuffer.front();
17 var posBuffer = pbuffer.posBuffer.front();
18 this.numParticles.value += idxBuffer.numIndices / 6;
19 this.numTris.value += idxBuffer.numIndices / 3;
20 this.numVerts.value += this.numParticles.value * 4;
21 if(this.numParticles.value > 0) {
22 this.numDrawCalls.value++;
23 }
24 }
25 }
26};
27
28g_particleStats = null;
29//if( g_enableBenchmarks ) {
30// g_particleStats = new particleStats;
31//}
32
33particle = function(def, id) {
34 this.id = id;
35 this.def = def;
36 if( this.def.numFrames == undefined ) {
37 if( this.def.textureSize && this.def.frameSize ) {
38 this.def.numFrames = ( this.def.textureSize[0] / this.def.frameSize[0] ) * ( this.def.textureSize[1] / this.def.frameSize[1] );
39 } else {
40 this.def.numFrames = 0;
41 }
42 }
43
44 this.pos = vec3.zero();
45 this.delta = vec3.zero();
46 this.rotate = 0.0;
47 this.age = 0.0;
48 this.lifespan = 0.0;
49 this.velocity = vec3.zero();
50 this.gravity = vec3.zero();
51 this.frame = 0;
52 this.frameCount = 0;
53 this.lastPos = vec3.zero();
54 this.state = 0;
55 this.hide = false;
56 this.color = vec4.zero();
57
58 this.randomize = function(min, max) {
59 return min + (max - min) * Math.random();
60 }
61 this.rate = this.randomize( -1.0, 1.0 );
62
63 this.randomize3 = function(min, max) {
64 return [this.randomize(min[0], max[0]),
65 this.randomize(min[1], max[1]),
66 this.randomize(min[2], max[2])];
67 }
68
69 this.spawn = function(spawnMatrix) {
70 if( this.def.initialframe == undefined ) {
71 this.frame = this.id % this.def.numFrames;
72 } else {
73 this.frame = this.randomize( this.def.initialframe[0], this.def.initialframe[1] );
74 }
75 this.pos = this.randomize3(this.def.initialpos[0], this.def.initialpos[1]);
76 if (this.def.worldSpace) {
77 // calculate the initial position in world space.
78 this.pos = mat4.transformPoint( spawnMatrix, this.pos );
79 }
80 // all other values are assumed to be defined in local or world space depending on
81 // the particles worldSpace designation.
82 var toRadians = Math.PI/180.0;
83 if( this.def.initialsize ) {
84 this.size = this.randomize(this.def.initialsize[0], this.def.initialsize[1]);
85 } else {
86 this.size = 1.0;
87 }
88 this.velocity = this.randomize3(this.def.initialvel[0], this.def.initialvel[1]);
89 this.gravity = [this.def.gravity[0], this.def.gravity[1], this.def.gravity[2]];
90 this.rotate = this.randomize(this.def.initialrot[0] * toRadians, this.def.initialrot[1] * toRadians);
91 this.lifespan = this.randomize(this.def.lifespan[0], this.def.lifespan[1]);
92 this.age = 0.0;
93 this.delta = [0.0, 0.0, 0.0];
94 this.lastPos = vec3.add(this.pos, vec3.scale(this.velocity, -1.0 / 30.0));
95 this.color = [1,1,1,1];//vec4.random( [0.0, 0.0, 0.0, 1.0], [1.0, 1.0, 1.0, 1.0] );
96 }
97}
98
99// double buffered array utility class
100DoubleBuffer = function(arrType, size) {
101 this.buffer = {};
102 this.buffer[0] = new arrType(size);
103 this.buffer[1] = new arrType(size);
104 this.bufferIndex = 0;
105
106 this.flip = function() {
107 this.bufferIndex = 1 - this.bufferIndex;
108 }
109 this.front = function() {
110 return this.buffer[this.bufferIndex];
111 }
112 this.back = function() {
113 return this.buffer[1 - this.bufferIndex];
114 }
115}
116
117
118// cycling buffer
119particleBuffer = function(pdef, emitter, size)
120{
121 var renderer = g_Engine.getContext().renderer;
122 var ctx = renderer.ctx;
123
124 s_particleShader = new jshader();
125 s_particleShader.def = {
126 'shaders': {
127 'defaultVShader': "assets/shaders/particle_vshader.glsl",
128 'defaultFShader': "assets/shaders/particle_fshader.glsl"
129 },
130 'techniques': {
131 'defaultTechnique': [{
132 'vshader' : 'defaultVShader',
133 'fshader' : 'defaultFShader',
134 'attributes' : {
135 'a_pos' : { 'type' : 'vec4' },
136 'a_posId' : { 'type' : 'float' },
137 'a_rotation' : { 'type' : 'float' },
138 'a_size' : { 'type' : 'float' },
139 'a_color' : { 'type' : 'vec4' }
140 },
141 'params' : {
142 'u_projMatrix' : { 'type' : 'mat4' },
143 'u_viewMatrix' : { 'type' : 'mat4' },
144 'u_worldMatrix' : { 'type' : 'mat4' },
145 'u_particleSizeX' : { 'type' : 'vec4' },
146 'u_particleSizeY' : { 'type' : 'vec4' },
147 'u_particleRot' : { 'type' : 'vec4' },
148 'u_particleColors' : { 'type' : 'mat4' },
149 'u_textureSize' : { 'type' : 'vec2' },
150 'u_frameSize' : { 'type' : 'vec2' },
151 's_texture0' : { 'type' : 'tex2d' }
152// 's_texture1' : { 'type' : 'tex2d' }
153 }
154 }]
155 }
156 }
157 s_particleShader.init();
158 s_particleTextures = {};
159
160 this.shader = s_particleShader;
161 this.owner = emitter;
162 if( pdef.texture && s_particleTextures[pdef.texture] == undefined ) {
163 s_particleTextures[pdef.texture] = renderer.createTexture(pdef.texture);
164 if( !pdef.textureSize || !pdef.frameSize ) {
165 pdef.textureSize = [];
166 pdef.textureSize[0] = s_particleTextures[pdef.texture].image.width;
167 pdef.textureSize[1] = s_particleTextures[pdef.texture].image.height;
168
169 }
170
171 if( !pdef.frameSize ) {
172 pdef.frameSize = [];
173 pdef.frameSize[0] = s_particleTextures[pdef.texture].image.width;
174 pdef.frameSize[1] = s_particleTextures[pdef.texture].image.height;
175 }
176 }
177 if( pdef.texture2 && s_particleTextures[pdef.texture2] == undefined ) {
178 s_particleTextures[pdef.texture2] = renderer.createTexture(pdef.texture2);
179 }
180 this.texture = s_particleTextures[pdef.texture];
181 this.texture2 = s_particleTextures[pdef.texture2];
182 this.bounds = {};
183 this.bounds.min = vec3.zero();
184 this.bounds.max = vec3.zero();
185
186 this.srcBlend = pdef.srcBlend;
187 this.dstBlend = pdef.dstBlend;
188
189 this.particles = new Array();
190
191 this.posBuffer = new DoubleBuffer(Float32Array, 16 * size); // 4 positions per particle, 4 components per position (particle age in w)
192 this.posIdBuffer = new Float32Array(4 * size);
193 this.sizeBuffer = new DoubleBuffer(Float32Array, 4 * size);
194 this.rotBuffer = new DoubleBuffer(Float32Array, 4 * size);
195 this.colorBuffer = new DoubleBuffer(Float32Array, 16 * size);
196 this.indexBuffer = new DoubleBuffer(Uint16Array, 6 * size);
197 this.indexBuffer.front().numIndices = 0;
198 this.indexBuffer.back().numIndices = 0;
199
200 for ( i = 0; i < size; ++i ) {
201 this.particles.push(new particle(pdef, i));
202
203 // initialize double buffers.
204 // the first pass will init the front buffers.
205 // the second pass will init the back buffers.
206 for ( j = 0; j < 2; ++j ) {
207 // init position buffer
208 var pfb = this.posBuffer.front();
209 var i16 = i * 16;
210 for ( j = 0; j < 4; ++j ) {
211 var cmpBaseIndex = i16 + j * 4;