132 lines
5.1 KiB
JavaScript
132 lines
5.1 KiB
JavaScript
//
|
|
// boom.js
|
|
//
|
|
// An object with this entity script will blow up when clicked or grabbed,
|
|
// throwing nearby objects flying. After a time period, it will return all the objects to their original positions.
|
|
//
|
|
// Created by Philip Rosedale on March 7, 2016
|
|
// Copyright 2016 High Fidelity, Inc.
|
|
//
|
|
// Distributed under the Apache License, Version 2.0.
|
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
|
//
|
|
|
|
(function() {
|
|
var entityID,
|
|
wantDebug = true,
|
|
BLAST_FORCE = 10,
|
|
BLAST_RADIUS = 10,
|
|
BLAST_STEPDOWN = 10.0,
|
|
TIME_TILL_RESTORE = 10.0,
|
|
NETWORK_MAX_ROUNDRIP_MSECS = 1000,
|
|
COUNTDOWN_TIME_MSECS = 2000,
|
|
ZERO_GRAVITY = { x: 0, y: 0, z: 0 },
|
|
FALL_GRAVITY = { x: 0, y: -4.0, z: 0 },
|
|
SOUND_BOOM = SoundCache.getSound("http://hifi-content.s3.amazonaws.com/alan/dev/Audio/bigboom_converted.wav"),
|
|
SOUND_COUNTDOWN = SoundCache.getSound("https://s3.amazonaws.com/hifi-public/philip/countdown_converted.wav"),
|
|
RED = { red: 255, green: 0, blue: 0 },
|
|
affected = [],
|
|
state = "ready"
|
|
function printDebug(message) {
|
|
if (wantDebug) {
|
|
print(message);
|
|
}
|
|
}
|
|
|
|
function blowStuffUp(position, force, radius, stepdown, gravity) {
|
|
var stuff = Entities.findEntities(position, radius);
|
|
printDebug("Blowing " + stuff.length + " things up");
|
|
for (var i = 0; i < stuff.length; i++) {
|
|
var properties = Entities.getEntityProperties(stuff[i]);
|
|
if (!properties.locked && (stuff[i] != entityID)) {
|
|
// Store original position
|
|
affected.push({ entityID: stuff[i],
|
|
position: properties.position,
|
|
rotation: properties.rotation,
|
|
gravity: properties.gravity,
|
|
dynamic: properties.dynamic });
|
|
var diff = Vec3.subtract(Vec3.sum(properties.position, { x: 0, y: -stepdown, z: 0 }), position);
|
|
var distance = Vec3.length(diff);
|
|
var velocity = Vec3.sum(properties.velocity, Vec3.multiply(force, Vec3.normalize(diff)));
|
|
var angularVelocity = { x: Math.random() * force, y: Math.random() * force, z: Math.random() * force };
|
|
Entities.editEntity(stuff[i], { dynamic: true, gravity: gravity, velocity: velocity,
|
|
angularVelocity: angularVelocity });
|
|
}
|
|
}
|
|
}
|
|
|
|
function replaceStuff() {
|
|
if (state == "waitingToReplace") {
|
|
printDebug("replace phase 1");
|
|
for (var i = 0; i < affected.length; i++) {
|
|
// Set everything back the first time and non-dynamic, wait for a network RT
|
|
Entities.editEntity(affected[i].entityID, { position: affected[i].position,
|
|
rotation: affected[i].rotation,
|
|
gravity: ZERO_GRAVITY,
|
|
dynamic: false,
|
|
velocity: { x: 0, y: 0, z: 0 },
|
|
angularVelocity: { x: 0, y: 0, z: 0 } });
|
|
}
|
|
state = "replacePhase2";
|
|
Script.setTimeout(replaceStuff, NETWORK_MAX_ROUNDRIP_MSECS);
|
|
} else {
|
|
printDebug("replace phase 2");
|
|
for (var i = 0; i < affected.length; i++) {
|
|
// After network RT, do it again with original dynamic state
|
|
Entities.editEntity(affected[i].entityID, { position: affected[i].position,
|
|
rotation: affected[i].rotation,
|
|
gravity: affected[i].gravity,
|
|
dynamic: affected[i].dynamic,
|
|
velocity: { x: 0, y: 0, z: 0 },
|
|
angularVelocity: { x: 0, y: 0, z: 0 } });
|
|
}
|
|
state = "ready";
|
|
affected = [];
|
|
}
|
|
}
|
|
|
|
function maybeBlowUp() {
|
|
if (state == "ready") {
|
|
printDebug("start countdown");
|
|
var properties = Entities.getEntityProperties(entityID);
|
|
Audio.playSound(SOUND_COUNTDOWN, {
|
|
position: properties.position,
|
|
volume: 1.0,
|
|
loop: false
|
|
});
|
|
state = "countdown";
|
|
Script.setTimeout(maybeBlowUp, COUNTDOWN_TIME_MSECS);
|
|
}
|
|
else if (state == "countdown") {
|
|
// blow up
|
|
printDebug("Explode!");
|
|
var properties = Entities.getEntityProperties(entityID);
|
|
Entities.editEntity(entityID, { color: RED });
|
|
Audio.playSound(SOUND_BOOM, {
|
|
position: properties.position,
|
|
volume: 1.0,
|
|
loop: false
|
|
});
|
|
blowStuffUp(properties.position, BLAST_FORCE, BLAST_RADIUS, BLAST_STEPDOWN, FALL_GRAVITY);
|
|
Script.setTimeout(replaceStuff, TIME_TILL_RESTORE * 1000);
|
|
state = "waitingToReplace";
|
|
}
|
|
}
|
|
|
|
this.startNearGrab = function() {
|
|
maybeBlowUp();
|
|
}
|
|
this.mousePressOnEntity = function() {
|
|
maybeBlowUp();
|
|
}
|
|
|
|
this.preload = function(givenEntityID) {
|
|
printDebug("load boom...");
|
|
entityID = givenEntityID;
|
|
};
|
|
|
|
this.unload = function() {
|
|
printDebug("Unload boom...");
|
|
};
|
|
|
|
});
|