rotation scale for particle engines

beta.r3js.org
-=yb4f310 2017-11-05 15:53:23 +01:00
parent 61d191456d
commit 87051a584d
8 changed files with 243 additions and 69 deletions

View File

@ -2,10 +2,15 @@
* Raw ParticleEngine API object - should always correspond with the ParticleEngine Schema * Raw ParticleEngine API object - should always correspond with the ParticleEngine Schema
* @param id * @param id
* @param name * @param name
* @param meshes
* @param materials * @param materials
* @param position * @param position
* @param rotation
* @param direction * @param direction
* @param lookAt
* @param particlesPerSecond * @param particlesPerSecond
* @param frequency
* @param elapsed
* @param distanceType * @param distanceType
* @param minDistance * @param minDistance
* @param maxDistance * @param maxDistance
@ -24,6 +29,8 @@ GameLib.D3.API.ParticleEngine = function(
meshes, meshes,
materials, materials,
position, position,
rotation,
scale,
direction, direction,
lookAt, lookAt,
particlesPerSecond, particlesPerSecond,
@ -66,6 +73,16 @@ GameLib.D3.API.ParticleEngine = function(
} }
this.position = position; this.position = position;
if (GameLib.Utils.UndefinedOrNull(rotation)) {
rotation = new GameLib.API.Vector3(0, 0, 0);
}
this.rotation = rotation;
if (GameLib.Utils.UndefinedOrNull(scale)) {
scale = new GameLib.API.Vector3(1, 1, 1);
}
this.scale = scale;
if (GameLib.Utils.UndefinedOrNull(direction)) { if (GameLib.Utils.UndefinedOrNull(direction)) {
direction = new GameLib.API.Vector3(0, 0, 1); direction = new GameLib.API.Vector3(0, 0, 1);
} }
@ -185,6 +202,8 @@ GameLib.D3.API.ParticleEngine.FromObject = function(objectParticleEngine) {
apiMeshes, apiMeshes,
apiMaterials, apiMaterials,
GameLib.API.Vector3.FromObject(objectParticleEngine.position), GameLib.API.Vector3.FromObject(objectParticleEngine.position),
GameLib.API.Vector3.FromObject(objectParticleEngine.rotation),
GameLib.API.Vector3.FromObject(objectParticleEngine.scale),
GameLib.API.Vector3.FromObject(objectParticleEngine.direction), GameLib.API.Vector3.FromObject(objectParticleEngine.direction),
GameLib.API.Vector3.FromObject(objectParticleEngine.lookAt), GameLib.API.Vector3.FromObject(objectParticleEngine.lookAt),
objectParticleEngine.particlesPerSecond, objectParticleEngine.particlesPerSecond,

View File

@ -1175,8 +1175,6 @@ GameLib.D3.Mesh.prototype.applyPositionRotationScale = function() {
this.scale.z = 1; this.scale.z = 1;
this.instance.scale.set(1,1,1); this.instance.scale.set(1,1,1);
if (this.useQuaternion) {
/** /**
* Reset rotation * Reset rotation
* @type {number} * @type {number}
@ -1189,13 +1187,12 @@ GameLib.D3.Mesh.prototype.applyPositionRotationScale = function() {
this.quaternion.axis.y = 0; this.quaternion.axis.y = 0;
this.quaternion.axis.z = 0; this.quaternion.axis.z = 0;
this.quaternion.angle = 0; this.quaternion.angle = 0;
this.updateInstanceRotationFromAxisAngle();
} else {
this.rotation.x = 0; this.rotation.x = 0;
this.rotation.y = 0; this.rotation.y = 0;
this.rotation.z = 0; this.rotation.z = 0;
this.instance.rotation.set(0,0,0);
} this.updateInstanceRotation();
/** /**
* Update our instance matrix * Update our instance matrix
@ -1231,13 +1228,24 @@ GameLib.D3.Mesh.prototype.updateInstanceRotationFromAxisAngle = function(axis, a
GameLib.D3.Mesh.prototype.updateInstanceRotation = function() { GameLib.D3.Mesh.prototype.updateInstanceRotation = function() {
if (this.useQuaternion) {
this.updateInstanceRotationFromAxisAngle();
} else {
this.rotation.instance.set( this.rotation.instance.set(
this.rotation.x, this.rotation.x,
this.rotation.y, this.rotation.y,
this.rotation.z this.rotation.z
); );
this.instance.rotation.copy(this.rotation.instance); this.instance.rotation.set(
this.rotation.x,
this.rotation.y,
this.rotation.z
);
}
if (this.helper) { if (this.helper) {
this.helper.updateInstance(); this.helper.updateInstance();

View File

@ -27,6 +27,8 @@ GameLib.D3.ParticleEngine = function(
apiParticleEngine.meshes, apiParticleEngine.meshes,
apiParticleEngine.materials, apiParticleEngine.materials,
apiParticleEngine.position, apiParticleEngine.position,
apiParticleEngine.rotation,
apiParticleEngine.scale,
apiParticleEngine.direction, apiParticleEngine.direction,
apiParticleEngine.lookAt, apiParticleEngine.lookAt,
apiParticleEngine.particlesPerSecond, apiParticleEngine.particlesPerSecond,
@ -77,6 +79,30 @@ GameLib.D3.ParticleEngine = function(
throw new Error('position not instance of API.Vector3'); throw new Error('position not instance of API.Vector3');
} }
if (this.rotation instanceof GameLib.API.Vector3) {
this.rotation = new GameLib.Vector3(
graphics,
this.rotation,
this
);
} else {
console.warn('rotation not instance of API.Vector3');
throw new Error('rotation not instance of API.Vector3');
}
if (this.scale instanceof GameLib.API.Vector3) {
this.scale = new GameLib.Vector3(
graphics,
this.scale,
this
);
} else {
console.warn('scale not instance of API.Vector3');
throw new Error('scale not instance of API.Vector3');
}
if (this.direction instanceof GameLib.API.Vector3) { if (this.direction instanceof GameLib.API.Vector3) {
this.direction = new GameLib.Vector3( this.direction = new GameLib.Vector3(
graphics, graphics,
@ -99,10 +125,17 @@ GameLib.D3.ParticleEngine = function(
throw new Error('lookAt not instance of API.Vector3'); throw new Error('lookAt not instance of API.Vector3');
} }
/**
* This is just a reference to the first mesh in the array
* @type {null}
*/
this.parentMesh = null;
GameLib.Component.call( GameLib.Component.call(
this, this,
GameLib.Component.COMPONENT_PARTICLE_ENGINE, GameLib.Component.COMPONENT_PARTICLE_ENGINE,
{ {
parentMesh : GameLib.D3.Mesh,
meshes : [GameLib.D3.Mesh], meshes : [GameLib.D3.Mesh],
materials : [GameLib.D3.Material] materials : [GameLib.D3.Material]
} }
@ -125,13 +158,11 @@ GameLib.D3.ParticleEngine.prototype.createInstance = function() {
this.frequency = Number(1 / this.particlesPerSecond); this.frequency = Number(1 / this.particlesPerSecond);
for (var i = 0; i < this.frequency; i++) { this.parentMesh = null;
var parentMesh = null; for (var i = 0; i < this.particlesPerSecond; i++) {
if (i !== 0) { if (i === 0) {
parentMesh = this.meshes[0];
}
var apiMesh = new GameLib.D3.API.Mesh( var apiMesh = new GameLib.D3.API.Mesh(
null, null,
@ -140,10 +171,10 @@ GameLib.D3.ParticleEngine.prototype.createInstance = function() {
null, null,
null, null,
this.materials, this.materials,
parentMesh null
); );
var mesh = new GameLib.D3.Mesh.Plane( this.parentMesh = new GameLib.D3.Mesh.Plane(
this.graphics, this.graphics,
apiMesh, apiMesh,
1, 1,
@ -152,10 +183,31 @@ GameLib.D3.ParticleEngine.prototype.createInstance = function() {
1 1
); );
this.parentMesh.useQuaternion = false;
this.parentMesh.position.setFrom(this.position);
this.parentMesh.rotation.setFrom(this.rotation);
this.parentMesh.scale.setFrom(this.scale);
this.meshes.push(this.parentMesh);
} else {
var mesh = this.parentMesh.clone();
mesh.parentMesh = this.parentMesh;
mesh.updateInstance();
this.meshes.push(mesh); this.meshes.push(mesh);
} }
this.instance = { }
this.updateDistances();
this.instance = true;/* {
parentMesh : this.parentMesh.instance,
position : this.position.instance, position : this.position.instance,
direction : this.direction.instance, direction : this.direction.instance,
lookAt : this.lookAt.instance, lookAt : this.lookAt.instance,
@ -169,16 +221,94 @@ GameLib.D3.ParticleEngine.prototype.createInstance = function() {
return material.instance return material.instance
} }
) )
}; };*/
GameLib.Component.prototype.createInstance.call(this); GameLib.Component.prototype.createInstance.call(this);
}; };
GameLib.D3.ParticleEngine.prototype.updateDistances = function() {
var distanceGrain = 1;
if (this.particlesPerSecond > 1) {
distanceGrain = Number(1 / (this.particlesPerSecond - 1));
}
var minDistance = this.direction.clone().multiply(this.minDistance, true);
minDistance.parentObject = null;
minDistance.updateInstance();
var maxDistance = this.direction.clone().multiply(this.maxDistance, true);
maxDistance.parentObject = null;
maxDistance.updateInstance();
this.meshes.map(
function(mesh, index) {
if (index === 0) {
return;
}
var distance = minDistance.instance.lerp(maxDistance.instance, (index * distanceGrain));
mesh.position.x = this.direction.x * (distance.x);
mesh.position.y = this.direction.y * (distance.y);
mesh.position.z = this.direction.z * (distance.z);
mesh.updateInstancePosition();
}.bind(this)
);
};
/** /**
* Updates the instance with the current state * Updates the instance with the current state
*/ */
GameLib.D3.ParticleEngine.prototype.updateInstance = function() { GameLib.D3.ParticleEngine.prototype.updateInstance = function(property) {
GameLib.Event.Emit(GameLib.Event.PARTICLE_INSTANCE_UPDATED, {component:this});
console.log('property : ' + property);
if (property === 'position') {
this.parentMesh.position.setFrom(this.position);
this.parentMesh.updateInstancePosition();
}
if (property === 'rotation') {
this.parentMesh.rotation.setFrom(this.rotation);
this.parentMesh.updateInstanceRotation();
}
if (property === 'scale') {
this.parentMesh.scale.setFrom(this.scale);
this.parentMesh.updateInstanceScale();
}
if (property === 'particlesPerSecond') {
console.log('particles per second or max distance');
this.meshes.map(
function(mesh) {
GameLib.Event.Emit(
GameLib.Event.REMOVE_COMPONENT,
{
component : mesh
}
)
}
);
this.meshes = [];
this.createInstance();
}
if (property === 'minDistance' || property === 'maxDistance') {
this.updateDistances();
}
//GameLib.Event.Emit(GameLib.Event.PARTICLE_INSTANCE_UPDATED, {component:this});
}; };
/** /**
@ -202,6 +332,8 @@ GameLib.D3.ParticleEngine.prototype.toApiObject = function() {
} }
), ),
this.position.toApiObject(), this.position.toApiObject(),
this.rotation.toApiObject(),
this.scale.toApiObject(),
this.direction.toApiObject(), this.direction.toApiObject(),
this.lookAt.toApiObject(), this.lookAt.toApiObject(),
this.particlesPerSecond, this.particlesPerSecond,

View File

@ -101,7 +101,7 @@ GameLib.Quaternion.prototype.createInstance = function() {
/** /**
* Updates the instance vector, calls updateInstance on the parent object * Updates the instance vector, calls updateInstance on the parent object
*/ */
GameLib.Quaternion.prototype.updateInstance = function() { GameLib.Quaternion.prototype.updateInstance = function(property) {
this.instance.x = this.x; this.instance.x = this.x;
this.instance.y = this.y; this.instance.y = this.y;
@ -110,7 +110,7 @@ GameLib.Quaternion.prototype.updateInstance = function() {
if (this.parentObject && if (this.parentObject &&
this.parentObject.updateInstance) { this.parentObject.updateInstance) {
this.parentObject.updateInstance(); this.parentObject.updateInstance(property);
} }
}; };

View File

@ -202,11 +202,11 @@ GameLib.System.GUI.prototype.onChange = function(property, subProperty, affected
} }
if (typeof component[property].updateInstance === 'function') { if (typeof component[property].updateInstance === 'function') {
component[property].updateInstance(); component[property].updateInstance(property);
} else if (typeof component[property][subProperty].updateInstance === 'function') { } else if (typeof component[property][subProperty].updateInstance === 'function') {
component[property][subProperty].updateInstance(); component[property][subProperty].updateInstance(subProperty);
} else { } else {
component.updateInstance(); component.updateInstance(property);
} }
}); });
@ -1118,7 +1118,8 @@ GameLib.System.GUI.prototype.buildControl = function(folder, componentTemplate,
} else if ( } else if (
property === 'widthSegments' || property === 'widthSegments' ||
property === 'radiusSegments' || property === 'radiusSegments' ||
property === 'heightSegments' property === 'heightSegments' ||
property === 'particlesPerSecond'
) { ) {
controllers.push(folder.add(object, property, 1, 1000, 1)); controllers.push(folder.add(object, property, 1, 1000, 1));
} else if ( } else if (
@ -1166,7 +1167,7 @@ GameLib.System.GUI.prototype.buildControl = function(folder, componentTemplate,
) { ) {
controllers.push(folder.add(object, property, -Math.PI * 2, Math.PI * 2, 0.01)); controllers.push(folder.add(object, property, -Math.PI * 2, Math.PI * 2, 0.01));
} else { } else {
controllers.push(folder.add(object, property, -10000, 10000, grain)); controllers.push(folder.add(object, property, -1000, 1000, 0.1));
} }
} }
} }
@ -1182,7 +1183,7 @@ GameLib.System.GUI.prototype.buildControl = function(folder, componentTemplate,
componentTemplate.affected.map( componentTemplate.affected.map(
function(component){ function(component){
component[property] = value; component[property] = value;
component.updateInstance(); component.updateInstance(property);
} }
); );
@ -1202,7 +1203,7 @@ GameLib.System.GUI.prototype.buildControl = function(folder, componentTemplate,
componentTemplate.affected.map( componentTemplate.affected.map(
function(component){ function(component){
component[property] = value; component[property] = value;
component.updateInstance(); component.updateInstance(property);
} }
); );
} }

View File

@ -17,6 +17,7 @@ GameLib.Vector2 = function (
if (GameLib.Utils.UndefinedOrNull(apiVector2)) { if (GameLib.Utils.UndefinedOrNull(apiVector2)) {
apiVector2 = {}; apiVector2 = {};
apiVector2 = {};
} }
if (apiVector2 instanceof GameLib.Vector2) { if (apiVector2 instanceof GameLib.Vector2) {
@ -57,14 +58,14 @@ GameLib.Vector2.prototype.createInstance = function() {
/** /**
* Updates the instance vector, calls updateInstance on the parent object * Updates the instance vector, calls updateInstance on the parent object
*/ */
GameLib.Vector2.prototype.updateInstance = function() { GameLib.Vector2.prototype.updateInstance = function(property) {
this.instance.x = this.x; this.instance.x = this.x;
this.instance.y = this.y; this.instance.y = this.y;
if (this.parentObject && if (this.parentObject &&
this.parentObject.updateInstance) { this.parentObject.updateInstance) {
this.parentObject.updateInstance(); this.parentObject.updateInstance(property);
} }
}; };

View File

@ -83,7 +83,7 @@ GameLib.Vector3.prototype.createInstance = function() {
/** /**
* Updates the instance vector, calls updateInstance on the parent object * Updates the instance vector, calls updateInstance on the parent object
*/ */
GameLib.Vector3.prototype.updateInstance = function() { GameLib.Vector3.prototype.updateInstance = function(property) {
this.instance.x = this.x; this.instance.x = this.x;
this.instance.y = this.y; this.instance.y = this.y;
@ -92,7 +92,7 @@ GameLib.Vector3.prototype.updateInstance = function() {
if (this.parentObject && if (this.parentObject &&
this.parentObject !== this && this.parentObject !== this &&
this.parentObject.updateInstance) { this.parentObject.updateInstance) {
this.parentObject.updateInstance(); this.parentObject.updateInstance(property);
} }
}; };
@ -123,6 +123,19 @@ GameLib.Vector3.prototype.copy = function() {
) )
}; };
GameLib.Vector3.prototype.clone = function() {
return new GameLib.Vector3(
this.implementation,
new GameLib.API.Vector3(
this.x,
this.y,
this.z
),
this.parentObject,
this.grain
)
};
/** /**
* Create a negative version of this vector * Create a negative version of this vector
* @returns {GameLib.Vector3} * @returns {GameLib.Vector3}

View File

@ -64,7 +64,7 @@ GameLib.Vector4.prototype.createInstance = function() {
/** /**
* Updates the instance vector, calls updateInstance on the parent object * Updates the instance vector, calls updateInstance on the parent object
*/ */
GameLib.Vector4.prototype.updateInstance = function() { GameLib.Vector4.prototype.updateInstance = function(property) {
this.instance.x = this.x; this.instance.x = this.x;
this.instance.y = this.y; this.instance.y = this.y;
@ -73,7 +73,7 @@ GameLib.Vector4.prototype.updateInstance = function() {
if (this.parentObject && if (this.parentObject &&
this.parentObject.updateInstance) { this.parentObject.updateInstance) {
this.parentObject.updateInstance(); this.parentObject.updateInstance(property);
} }
}; };