r3-legacy/src/game-lib-d3-particle.js

371 lines
11 KiB
JavaScript
Raw Normal View History

/**
* Creates a Particle object
* @param graphics GameLib.GraphicsRuntime
* @param apiParticle GameLib.D3.API.Particle
* @constructor
*/
GameLib.D3.Particle = function(
graphics,
apiParticle
) {
this.graphics = graphics;
this.graphics.isNotThreeThrow();
if (GameLib.Utils.UndefinedOrNull(apiParticle)) {
apiParticle = {};
}
GameLib.D3.API.Particle.call(
this,
apiParticle.id,
apiParticle.name,
apiParticle.lifeTime,
apiParticle.elapsed,
apiParticle.mesh,
2017-11-13 15:22:08 +01:00
apiParticle.opacityType,
apiParticle.opacityFactor,
apiParticle.positionOffsetType,
apiParticle.positionOffset,
apiParticle.positionOffsetFn,
apiParticle.directionType,
apiParticle.direction,
apiParticle.directionFn,
2017-11-16 13:54:51 +01:00
apiParticle.speedType,
2017-11-13 08:39:07 +01:00
apiParticle.speed,
apiParticle.scaleType,
apiParticle.scale,
apiParticle.scaleFn,
apiParticle.rotationType,
apiParticle.rotation,
apiParticle.rotationFn,
2018-01-14 14:13:35 +01:00
apiParticle.parentParticleEngine,
apiParticle.parentEntity
);
if (this.mesh instanceof GameLib.D3.API.Mesh) {
this.mesh = new GameLib.D3.Mesh(
graphics,
this.mesh
)
}
2018-01-14 14:13:35 +01:00
this.positionOffset = new GameLib.Vector3(
graphics,
this.positionOffset,
this
);
2018-01-14 14:13:35 +01:00
this.direction = new GameLib.Vector3(
graphics,
this.direction,
this
);
2018-01-14 14:13:35 +01:00
this.scale = new GameLib.Vector3(
graphics,
this.scale,
this
);
2018-01-14 14:13:35 +01:00
this.rotation = new GameLib.Vector3(
graphics,
this.rotation,
this
);
GameLib.Component.call(
this,
{
mesh : GameLib.D3.Mesh,
2018-01-14 14:13:35 +01:00
parentParticleEngine : GameLib.D3.ParticleEngine
}
);
};
2018-01-07 12:40:16 +01:00
GameLib.D3.Particle.prototype = Object.create(GameLib.Component.prototype);
GameLib.D3.Particle.prototype.constructor = GameLib.D3.Particle;
2017-11-13 15:22:08 +01:00
GameLib.D3.Particle.OPACITY_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.OPACITY_TYPE_DECREASE_LINEAR = 0x2;
GameLib.D3.Particle.OPACITY_TYPE_INCREASE_LINEAR = 0x3;
GameLib.D3.Particle.POSITION_OFFSET_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.POSITION_OFFSET_TYPE_RANDOM = 0x2;
GameLib.D3.Particle.POSITION_OFFSET_TYPE_FUNCTION = 0x3;
GameLib.D3.Particle.DIRECTION_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.DIRECTION_TYPE_RANDOM = 0x2;
2017-11-16 13:54:51 +01:00
GameLib.D3.Particle.DIRECTION_TYPE_RANDOM_NORMALIZED = 0x3;
GameLib.D3.Particle.DIRECTION_TYPE_FUNCTION = 0x4;
GameLib.D3.Particle.SCALE_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.SCALE_TYPE_LINEAR = 0x2;
GameLib.D3.Particle.SCALE_TYPE_EXPONENTIAL = 0x3;
GameLib.D3.Particle.SCALE_TYPE_RANDOM = 0x4;
2017-11-13 15:06:59 +01:00
GameLib.D3.Particle.SCALE_TYPE_RANDOM_X_EQUALS_Y = 0x6;
GameLib.D3.Particle.SCALE_TYPE_FUNCTION = 0x7;
2017-11-16 13:54:51 +01:00
GameLib.D3.Particle.SPEED_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.SPEED_TYPE_LINEAR = 0x2;
GameLib.D3.Particle.SPEED_TYPE_EXPONENTIAL = 0x3;
GameLib.D3.Particle.SPEED_TYPE_LOGARITHMIC = 0x4;
GameLib.D3.Particle.SPEED_TYPE_ONE_OVER_LOG = 0x5;
GameLib.D3.Particle.SPEED_TYPE_EXP = 0x6;
GameLib.D3.Particle.SPEED_TYPE_ONE_OVER_EXP = 0x7;
GameLib.D3.Particle.ROTATION_TYPE_CONSTANT = 0x1;
GameLib.D3.Particle.ROTATION_TYPE_RANDOM = 0x2;
GameLib.D3.Particle.ROTATION_TYPE_FUNCTION = 0x3;
/**
* Particle create instance
*/
GameLib.D3.Particle.prototype.createInstance = function() {
if (!this.mesh) {
console.warn('no mesh to clone from - failed dependency check?');
return
}
2017-11-06 14:45:05 +01:00
this.instance = this.mesh.instance;
GameLib.Component.prototype.createInstance.call(this);
};
/**
* Updates the instance with the current state
*/
GameLib.D3.Particle.prototype.updateInstance = function(property) {
2017-11-13 15:06:59 +01:00
2017-11-15 11:43:46 +01:00
if (property === 'positionOffset') {
this.positionOffset.instance.x = this.positionOffset.x;
this.positionOffset.instance.y = this.positionOffset.y;
this.positionOffset.instance.z = this.positionOffset.z;
}
if (property === 'direction') {
this.direction.instance.x = this.direction.x;
this.direction.instance.y = this.direction.y;
this.direction.instance.z = this.direction.z;
}
if (property === 'scale') {
this.scale.instance.x = this.scale.x;
this.scale.instance.y = this.scale.y;
this.scale.instance.z = this.scale.z;
2017-11-13 15:06:59 +01:00
}
2017-11-15 11:43:46 +01:00
if (property === 'rotation') {
this.rotation.instance.x = this.rotation.x;
this.rotation.instance.y = this.rotation.y;
this.rotation.instance.z = this.rotation.z;
}
};
2017-11-06 14:45:05 +01:00
/**
* Clones a particle - this only clones 3rd party instances, so we have less overhead of creating these types of objects
*/
2017-11-15 11:43:46 +01:00
GameLib.D3.Particle.prototype.cloneInstance = function() {
this.updateInstance('positionOffset');
this.updateInstance('direction');
this.updateInstance('scale');
this.updateInstance('rotation');
var clone = GameLib.Component.prototype.cloneInstance.call(this);
2018-01-14 14:13:35 +01:00
clone.position = this.parentParticleEngine.position.instance.clone();
2017-11-15 11:43:46 +01:00
clone.material = this.mesh.materials[0].instance.clone();
clone.visible = true;
if (this.positionOffsetType === GameLib.D3.Particle.POSITION_OFFSET_TYPE_CONSTANT) {
clone.position.add(this.positionOffset.instance);
}
2017-11-15 14:25:37 +01:00
var addX = 1;
var addY = 1;
var addZ = 1;
2017-11-15 11:43:46 +01:00
if (this.positionOffsetType === GameLib.D3.Particle.POSITION_OFFSET_TYPE_RANDOM) {
2017-11-15 14:25:37 +01:00
addX = GameLib.Utils.GetRandomIntInclusive(1,2);
addY = GameLib.Utils.GetRandomIntInclusive(1,2);
addZ = GameLib.Utils.GetRandomIntInclusive(1,2);
2017-11-15 11:43:46 +01:00
2017-11-15 14:25:37 +01:00
if (addX === 1) {
2017-11-15 11:43:46 +01:00
clone.position.x += Math.random() * this.positionOffset.x;
} else {
clone.position.x -= Math.random() * this.positionOffset.x;
2017-11-15 14:25:37 +01:00
}
if (addY === 1) {
2017-11-15 11:43:46 +01:00
clone.position.y -= Math.random() * this.positionOffset.y;
2017-11-15 14:25:37 +01:00
} else {
clone.position.y += Math.random() * this.positionOffset.y;
}
if (addZ === 1) {
2017-11-15 11:43:46 +01:00
clone.position.z -= Math.random() * this.positionOffset.z;
2017-11-15 14:25:37 +01:00
} else {
clone.position.z += Math.random() * this.positionOffset.z;
2017-11-15 11:43:46 +01:00
}
}
2017-11-16 13:54:51 +01:00
clone.userData.direction = this.direction.clone();
if (this.directionType === GameLib.D3.Particle.DIRECTION_TYPE_CONSTANT) {
/**
* Nothing to do
*/
} else if (
this.directionType === GameLib.D3.Particle.DIRECTION_TYPE_RANDOM ||
this.directionType === GameLib.D3.Particle.DIRECTION_TYPE_RANDOM_NORMALIZED
) {
addX = GameLib.Utils.GetRandomIntInclusive(1,2);
addY = GameLib.Utils.GetRandomIntInclusive(1,2);
addZ = GameLib.Utils.GetRandomIntInclusive(1,2);
clone.userData.direction.x = 0;
clone.userData.direction.y = 0;
clone.userData.direction.z = 0;
if (addX === 1) {
clone.userData.direction.x += Math.random() * this.direction.x;
} else {
clone.userData.direction.x -= Math.random() * this.direction.x;
}
if (addY === 1) {
clone.userData.direction.y -= Math.random() * this.direction.y;
} else {
clone.userData.direction.y += Math.random() * this.direction.y;
}
if (addZ === 1) {
clone.userData.direction.z -= Math.random() * this.direction.z;
} else {
clone.userData.direction.z += Math.random() * this.direction.z;
}
if (this.directionType === GameLib.D3.Particle.DIRECTION_TYPE_RANDOM_NORMALIZED) {
clone.userData.direction.normalize();
}
} else {
throw new Error('not yet implemented')
}
2017-11-15 11:43:46 +01:00
if (this.scaleType === GameLib.D3.Particle.SCALE_TYPE_CONSTANT) {
clone.scale.x += this.scale.x;
clone.scale.y += this.scale.y;
clone.scale.z += this.scale.z;
}
if (this.scaleType === GameLib.D3.Particle.SCALE_TYPE_RANDOM) {
add = GameLib.Utils.GetRandomIntInclusive(1,2);
if (add === 1) {
clone.scale.x += Math.random() * this.scale.x;
clone.scale.y += Math.random() * this.scale.y;
clone.scale.z += Math.random() * this.scale.z;
} else {
clone.scale.x -= Math.random() * this.scale.x;
clone.scale.y -= Math.random() * this.scale.y;
clone.scale.z -= Math.random() * this.scale.z;
}
}
if (this.scaleType === GameLib.D3.Particle.SCALE_TYPE_RANDOM_X_EQUALS_Y) {
add = GameLib.Utils.GetRandomIntInclusive(1,2);
var factor = Math.random() * this.scale.x;
if (add === 1) {
clone.scale.x += factor;
clone.scale.y += factor;
clone.scale.z += Math.random() * this.scale.z;
} else {
clone.scale.x -= factor;
clone.scale.y -= factor;
clone.scale.z -= Math.random() * this.scale.z;
}
}
2017-11-16 13:54:51 +01:00
2017-11-15 11:43:46 +01:00
clone.userData.scale = this.scale.clone();
clone.userData.lifeTime = this.lifeTime;
2017-11-16 13:54:51 +01:00
clone.userData.speedType = this.speedType;
2017-11-15 11:43:46 +01:00
clone.userData.speed = this.speed;
clone.userData.scene = this.mesh.parentScene.instance;
clone.userData.elapsed = 0;
clone.userData.scene.add(clone);
return clone;
};
2017-11-06 14:45:05 +01:00
/**
* Converts a GameLib.D3.Particle to a new GameLib.D3.API.Particle
* @returns {GameLib.D3.API.Particle}
*/
GameLib.D3.Particle.prototype.toApiObject = function() {
return new GameLib.D3.API.Particle(
this.id,
this.name,
this.lifeTime,
this.elapsed,
GameLib.Utils.IdOrNull(this.mesh),
2017-11-13 15:22:08 +01:00
this.opacityType,
this.opacityFactor,
this.positionOffsetType,
this.positionOffset.toApiObject(),
this.positionOffsetFn,
this.directionType,
this.direction.toApiObject(),
this.directionFn,
2017-11-16 13:54:51 +01:00
this.speedType,
2017-11-13 08:39:07 +01:00
this.speed,
this.scaleType,
this.scale.toApiObject(),
this.scaleFn,
this.rotationType,
this.rotation.toApiObject(),
this.rotationFn,
2018-01-14 14:13:35 +01:00
GameLib.Utils.IdOrNull(this.parentParticleEngine),
GameLib.Utils.IdOrNull(this.parentEntity)
);
};
/**
* Converts from an Object Particle to a GameLib.D3.Particle
* @param graphics GameLib.GraphicsRuntime
* @param objectParticle Object
* @returns {GameLib.D3.Particle}
* @constructor
*/
GameLib.D3.Particle.FromObject = function(graphics, objectParticle) {
var apiParticle = GameLib.D3.API.Particle.FromObject(objectParticle);
return new GameLib.D3.Particle(
graphics,
apiParticle
);
};