mirror of
https://github.com/overte-org/overte.git
synced 2025-08-09 16:41:02 +02:00
Merge pull request #6003 from imgntn/basketball_rack
[Scripts] Basketball rack
This commit is contained in:
commit
f01d4dde42
4 changed files with 332 additions and 29 deletions
|
@ -1,12 +1,10 @@
|
||||||
//
|
//
|
||||||
// createHoop.js
|
// createHoop.js
|
||||||
// examples/entityScripts
|
|
||||||
//
|
//
|
||||||
// Created by James B. Pollack on 9/29/2015
|
// Created by James B. Pollack on 9/29/2015
|
||||||
// Copyright 2015 High Fidelity, Inc.
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
//
|
//
|
||||||
// This is a script that creates a persistent basketball hoop with a working collision hull. Feel free to move it.
|
// This is a script that creates a persistent basketball hoop with a working collision hull. Feel free to move it.
|
||||||
// Run basketball.js to make a basketball.
|
|
||||||
//
|
//
|
||||||
// Distributed under the Apache License, Version 2.0.
|
// Distributed under the Apache License, Version 2.0.
|
||||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
152
examples/toys/basketball/createRack.js
Normal file
152
examples/toys/basketball/createRack.js
Normal file
|
@ -0,0 +1,152 @@
|
||||||
|
//
|
||||||
|
// createRack.js
|
||||||
|
//
|
||||||
|
// Created by James B. Pollack @imgntn on 10/5/2015
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// This is a script that creates a persistent basketball rack.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
/*global print, MyAvatar, Entities, AnimationCache, SoundCache, Scene, Camera, Overlays, HMD, AvatarList, AvatarManager, Controller, UndoStack, Window, Account, GlobalServices, Script, ScriptDiscoveryService, LODManager, Menu, Vec3, Quat, AudioDevice, Paths, Clipboard, Settings, XMLHttpRequest, randFloat, randInt */
|
||||||
|
Script.include("../../libraries/utils.js");
|
||||||
|
|
||||||
|
var HIFI_PUBLIC_BUCKET = "http://s3.amazonaws.com/hifi-public/";
|
||||||
|
|
||||||
|
var basketballURL = HIFI_PUBLIC_BUCKET + "models/content/basketball2.fbx";
|
||||||
|
var collisionSoundURL = HIFI_PUBLIC_BUCKET + "sounds/basketball/basketball.wav";
|
||||||
|
var rackURL = HIFI_PUBLIC_BUCKET + "models/basketball_hoop/basketball_rack.fbx";
|
||||||
|
var rackCollisionHullURL = HIFI_PUBLIC_BUCKET + "models/basketball_hoop/rack_collision_hull.obj";
|
||||||
|
var NUMBER_OF_BALLS = 4;
|
||||||
|
var DIAMETER = 0.30;
|
||||||
|
var RESET_DISTANCE = 1;
|
||||||
|
var MINIMUM_MOVE_LENGTH = 0.05;
|
||||||
|
|
||||||
|
var GRABBABLE_DATA_KEY = "grabbableKey";
|
||||||
|
|
||||||
|
var rackStartPosition =
|
||||||
|
Vec3.sum(MyAvatar.position,
|
||||||
|
Vec3.multiplyQbyV(MyAvatar.orientation, {
|
||||||
|
x: 0,
|
||||||
|
y: 0.0,
|
||||||
|
z: -2
|
||||||
|
}));
|
||||||
|
|
||||||
|
var rack = Entities.addEntity({
|
||||||
|
name: 'Basketball Rack',
|
||||||
|
type: "Model",
|
||||||
|
modelURL: rackURL,
|
||||||
|
position: rackStartPosition,
|
||||||
|
shapeType: 'compound',
|
||||||
|
gravity: {
|
||||||
|
x: 0,
|
||||||
|
y: -9.8,
|
||||||
|
z: 0
|
||||||
|
},
|
||||||
|
linearDamping: 1,
|
||||||
|
dimensions: {
|
||||||
|
x: 0.4,
|
||||||
|
y: 1.37,
|
||||||
|
z: 1.73
|
||||||
|
},
|
||||||
|
collisionsWillMove: true,
|
||||||
|
ignoreForCollisions: false,
|
||||||
|
collisionSoundURL: collisionSoundURL,
|
||||||
|
compoundShapeURL: rackCollisionHullURL,
|
||||||
|
// scriptURL: rackScriptURL
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
setEntityCustomData(GRABBABLE_DATA_KEY, rack, {
|
||||||
|
grabbable: false
|
||||||
|
});
|
||||||
|
|
||||||
|
var nonCollidingBalls = [];
|
||||||
|
var collidingBalls = [];
|
||||||
|
var originalBallPositions = [];
|
||||||
|
|
||||||
|
function createCollidingBalls() {
|
||||||
|
var position = rackStartPosition;
|
||||||
|
|
||||||
|
var i;
|
||||||
|
for (i = 0; i < NUMBER_OF_BALLS; i++) {
|
||||||
|
var ballPosition = {
|
||||||
|
x: position.x,
|
||||||
|
y: position.y + DIAMETER * 2,
|
||||||
|
z: position.z + (DIAMETER) - (DIAMETER * i)
|
||||||
|
};
|
||||||
|
|
||||||
|
var collidingBall = Entities.addEntity({
|
||||||
|
type: "Model",
|
||||||
|
name: 'Colliding Basketball',
|
||||||
|
shapeType: 'Sphere',
|
||||||
|
position: ballPosition,
|
||||||
|
dimensions: {
|
||||||
|
x: DIAMETER,
|
||||||
|
y: DIAMETER,
|
||||||
|
z: DIAMETER
|
||||||
|
},
|
||||||
|
restitution: 1.0,
|
||||||
|
linearDamping: 0.00001,
|
||||||
|
gravity: {
|
||||||
|
x: 0,
|
||||||
|
y: -9.8,
|
||||||
|
z: 0
|
||||||
|
},
|
||||||
|
collisionsWillMove: true,
|
||||||
|
ignoreForCollisions: false,
|
||||||
|
modelURL: basketballURL,
|
||||||
|
});
|
||||||
|
|
||||||
|
collidingBalls.push(collidingBall);
|
||||||
|
originalBallPositions.push(position);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function testBallDistanceFromStart() {
|
||||||
|
var resetCount = 0;
|
||||||
|
collidingBalls.forEach(function(ball, index) {
|
||||||
|
var currentPosition = Entities.getEntityProperties(ball, "position").position;
|
||||||
|
var originalPosition = originalBallPositions[index];
|
||||||
|
var distance = Vec3.subtract(originalPosition, currentPosition);
|
||||||
|
var length = Vec3.length(distance);
|
||||||
|
if (length > RESET_DISTANCE) {
|
||||||
|
Script.setTimeout(function() {
|
||||||
|
var newPosition = Entities.getEntityProperties(ball, "position").position;
|
||||||
|
var moving = Vec3.length(Vec3.subtract(currentPosition, newPosition));
|
||||||
|
if (moving < MINIMUM_MOVE_LENGTH) {
|
||||||
|
resetCount++;
|
||||||
|
if (resetCount === NUMBER_OF_BALLS) {
|
||||||
|
deleteCollidingBalls();
|
||||||
|
createCollidingBalls();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, 200)
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteEntity(entityID) {
|
||||||
|
if (entityID === rack) {
|
||||||
|
deleteCollidingBalls();
|
||||||
|
Script.clearInterval(distanceCheckInterval);
|
||||||
|
Entities.deletingEntity.disconnect(deleteEntity);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteCollidingBalls() {
|
||||||
|
while (collidingBalls.length > 0) {
|
||||||
|
Entities.deleteEntity(collidingBalls.pop());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
createCollidingBalls();
|
||||||
|
Entities.deletingEntity.connect(deleteEntity);
|
||||||
|
|
||||||
|
var distanceCheckInterval = Script.setInterval(testBallDistanceFromStart, 1000);
|
||||||
|
|
||||||
|
function atEnd() {
|
||||||
|
Script.clearInterval(distanceCheckInterval);
|
||||||
|
}
|
||||||
|
|
||||||
|
Script.scriptEnding.connect(atEnd);
|
|
@ -1,5 +1,5 @@
|
||||||
//
|
//
|
||||||
// basketball.js
|
// createSingleBasketball.js
|
||||||
// examples
|
// examples
|
||||||
//
|
//
|
||||||
// Created by Philip Rosedale on August 20, 2015
|
// Created by Philip Rosedale on August 20, 2015
|
||||||
|
@ -17,34 +17,39 @@ var collisionSoundURL = HIFI_PUBLIC_BUCKET + "sounds/basketball/basketball.wav";
|
||||||
|
|
||||||
var basketball = null;
|
var basketball = null;
|
||||||
var originalPosition = null;
|
var originalPosition = null;
|
||||||
var hasMoved = false;
|
var hasMoved = false;
|
||||||
|
|
||||||
var GRAVITY = -9.8;
|
var GRAVITY = -9.8;
|
||||||
var DISTANCE_IN_FRONT_OF_ME = 1.0;
|
var DISTANCE_IN_FRONT_OF_ME = 1.0;
|
||||||
var START_MOVE = 0.01;
|
var START_MOVE = 0.01;
|
||||||
var DIAMETER = 0.30;
|
var DIAMETER = 0.30;
|
||||||
|
|
||||||
function makeBasketball() {
|
function makeBasketball() {
|
||||||
var position = Vec3.sum(MyAvatar.position,
|
var position = Vec3.sum(MyAvatar.position,
|
||||||
Vec3.multiplyQbyV(MyAvatar.orientation,
|
Vec3.multiplyQbyV(MyAvatar.orientation, {
|
||||||
{ x: 0, y: 0.0, z: -DISTANCE_IN_FRONT_OF_ME }));
|
x: 0,
|
||||||
|
y: 0.0,
|
||||||
|
z: -DISTANCE_IN_FRONT_OF_ME
|
||||||
|
}));
|
||||||
var rotation = Quat.multiply(MyAvatar.orientation,
|
var rotation = Quat.multiply(MyAvatar.orientation,
|
||||||
Quat.fromPitchYawRollDegrees(0, -90, 0));
|
Quat.fromPitchYawRollDegrees(0, -90, 0));
|
||||||
basketball = Entities.addEntity({
|
basketball = Entities.addEntity({
|
||||||
type: "Model",
|
type: "Model",
|
||||||
position: position,
|
position: position,
|
||||||
rotation: rotation,
|
rotation: rotation,
|
||||||
dimensions: { x: DIAMETER,
|
dimensions: {
|
||||||
y: DIAMETER,
|
x: DIAMETER,
|
||||||
z: DIAMETER },
|
y: DIAMETER,
|
||||||
collisionsWillMove: true,
|
z: DIAMETER
|
||||||
collisionSoundURL: collisionSoundURL,
|
},
|
||||||
modelURL: basketballURL,
|
collisionsWillMove: true,
|
||||||
restitution: 1.0,
|
collisionSoundURL: collisionSoundURL,
|
||||||
linearDamping: 0.00001,
|
modelURL: basketballURL,
|
||||||
shapeType: "sphere"
|
restitution: 1.0,
|
||||||
});
|
linearDamping: 0.00001,
|
||||||
originalPosition = position;
|
shapeType: "sphere"
|
||||||
|
});
|
||||||
|
originalPosition = position;
|
||||||
}
|
}
|
||||||
|
|
||||||
function update() {
|
function update() {
|
||||||
|
@ -55,28 +60,33 @@ function update() {
|
||||||
var moved = Vec3.length(Vec3.subtract(originalPosition, newProperties.position));
|
var moved = Vec3.length(Vec3.subtract(originalPosition, newProperties.position));
|
||||||
if (!hasMoved && (moved > START_MOVE)) {
|
if (!hasMoved && (moved > START_MOVE)) {
|
||||||
hasMoved = true;
|
hasMoved = true;
|
||||||
Entities.editEntity(basketball, { gravity: {x: 0, y: GRAVITY, z: 0 }});
|
Entities.editEntity(basketball, {
|
||||||
|
gravity: {
|
||||||
|
x: 0,
|
||||||
|
y: GRAVITY,
|
||||||
|
z: 0
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
var MAX_DISTANCE = 10.0;
|
var MAX_DISTANCE = 10.0;
|
||||||
var distance = Vec3.length(Vec3.subtract(MyAvatar.position, newProperties.position));
|
var distance = Vec3.length(Vec3.subtract(MyAvatar.position, newProperties.position));
|
||||||
if (distance > MAX_DISTANCE) {
|
if (distance > MAX_DISTANCE) {
|
||||||
deleteStuff();
|
deleteStuff();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function scriptEnding() {
|
function scriptEnding() {
|
||||||
deleteStuff();
|
deleteStuff();
|
||||||
}
|
}
|
||||||
|
|
||||||
function deleteStuff() {
|
function deleteStuff() {
|
||||||
if (basketball != null) {
|
if (basketball != null) {
|
||||||
Entities.deleteEntity(basketball);
|
Entities.deleteEntity(basketball);
|
||||||
basketball = null;
|
basketball = null;
|
||||||
hasMoved = false;
|
hasMoved = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Script.update.connect(update);
|
Script.update.connect(update);
|
||||||
Script.scriptEnding.connect(scriptEnding);
|
Script.scriptEnding.connect(scriptEnding);
|
||||||
|
|
|
@ -86,6 +86,8 @@ function createAllToys() {
|
||||||
|
|
||||||
createBasketballHoop();
|
createBasketballHoop();
|
||||||
|
|
||||||
|
createBasketballRack();
|
||||||
|
|
||||||
createGates();
|
createGates();
|
||||||
|
|
||||||
createFire();
|
createFire();
|
||||||
|
@ -673,6 +675,147 @@ function createBasketballHoop() {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function createBasketballRack() {
|
||||||
|
var NUMBER_OF_BALLS = 4;
|
||||||
|
var DIAMETER = 0.30;
|
||||||
|
var RESET_DISTANCE = 1;
|
||||||
|
var MINIMUM_MOVE_LENGTH = 0.05;
|
||||||
|
var basketballURL = HIFI_PUBLIC_BUCKET + "models/content/basketball2.fbx";
|
||||||
|
var basketballCollisionSoundURL = HIFI_PUBLIC_BUCKET + "sounds/basketball/basketball.wav";
|
||||||
|
var rackURL = HIFI_PUBLIC_BUCKET + "models/basketball_hoop/basketball_rack.fbx";
|
||||||
|
var rackCollisionHullURL = HIFI_PUBLIC_BUCKET + "models/basketball_hoop/rack_collision_hull.obj";
|
||||||
|
|
||||||
|
var rackRotation = Quat.fromPitchYawRollDegrees(0, -90, 0);
|
||||||
|
|
||||||
|
var rackStartPosition = {
|
||||||
|
x: 542.86,
|
||||||
|
y: 494.84,
|
||||||
|
z: 475.06
|
||||||
|
};
|
||||||
|
var rack = Entities.addEntity({
|
||||||
|
name: 'Basketball Rack',
|
||||||
|
type: "Model",
|
||||||
|
modelURL: rackURL,
|
||||||
|
position: rackStartPosition,
|
||||||
|
rotation: rackRotation,
|
||||||
|
shapeType: 'compound',
|
||||||
|
gravity: {
|
||||||
|
x: 0,
|
||||||
|
y: -9.8,
|
||||||
|
z: 0
|
||||||
|
},
|
||||||
|
linearDamping: 1,
|
||||||
|
dimensions: {
|
||||||
|
x: 0.4,
|
||||||
|
y: 1.37,
|
||||||
|
z: 1.73
|
||||||
|
},
|
||||||
|
collisionsWillMove: true,
|
||||||
|
ignoreForCollisions: false,
|
||||||
|
compoundShapeURL: rackCollisionHullURL
|
||||||
|
});
|
||||||
|
|
||||||
|
setEntityCustomData(resetKey, rack, {
|
||||||
|
resetMe: true
|
||||||
|
});
|
||||||
|
|
||||||
|
setEntityCustomData(GRABBABLE_DATA_KEY, rack, {
|
||||||
|
grabbable: false
|
||||||
|
});
|
||||||
|
|
||||||
|
var collidingBalls = [];
|
||||||
|
var originalBallPositions = [];
|
||||||
|
|
||||||
|
function createCollidingBalls() {
|
||||||
|
var position = rackStartPosition;
|
||||||
|
|
||||||
|
var i;
|
||||||
|
for (i = 0; i < NUMBER_OF_BALLS; i++) {
|
||||||
|
var ballPosition = {
|
||||||
|
x: position.x,
|
||||||
|
y: position.y + DIAMETER * 2,
|
||||||
|
z: position.z + (DIAMETER) - (DIAMETER * i)
|
||||||
|
};
|
||||||
|
|
||||||
|
var collidingBall = Entities.addEntity({
|
||||||
|
type: "Model",
|
||||||
|
name: 'Colliding Basketball',
|
||||||
|
shapeType: 'Sphere',
|
||||||
|
position: {
|
||||||
|
x: position.x + (DIAMETER * 2) - (DIAMETER * i),
|
||||||
|
y: position.y + DIAMETER * 2,
|
||||||
|
z: position.z
|
||||||
|
},
|
||||||
|
dimensions: {
|
||||||
|
x: DIAMETER,
|
||||||
|
y: DIAMETER,
|
||||||
|
z: DIAMETER
|
||||||
|
},
|
||||||
|
restitution: 1.0,
|
||||||
|
linearDamping: 0.00001,
|
||||||
|
gravity: {
|
||||||
|
x: 0,
|
||||||
|
y: -9.8,
|
||||||
|
z: 0
|
||||||
|
},
|
||||||
|
collisionsWillMove: true,
|
||||||
|
ignoreForCollisions: false,
|
||||||
|
modelURL: basketballURL,
|
||||||
|
});
|
||||||
|
|
||||||
|
collidingBalls.push(collidingBall);
|
||||||
|
originalBallPositions.push(position);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function testBallDistanceFromStart() {
|
||||||
|
var resetCount = 0;
|
||||||
|
|
||||||
|
collidingBalls.forEach(function(ball, index) {
|
||||||
|
var currentPosition = Entities.getEntityProperties(ball, "position").position;
|
||||||
|
var originalPosition = originalBallPositions[index];
|
||||||
|
var distance = Vec3.subtract(originalPosition, currentPosition);
|
||||||
|
var length = Vec3.length(distance);
|
||||||
|
|
||||||
|
if (length > RESET_DISTANCE) {
|
||||||
|
Script.setTimeout(function() {
|
||||||
|
var newPosition = Entities.getEntityProperties(ball, "position").position;
|
||||||
|
var moving = Vec3.length(Vec3.subtract(currentPosition, newPosition));
|
||||||
|
if (moving < MINIMUM_MOVE_LENGTH) {
|
||||||
|
resetCount++;
|
||||||
|
if (resetCount === NUMBER_OF_BALLS) {
|
||||||
|
deleteCollidingBalls();
|
||||||
|
createCollidingBalls();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, 200);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteEntity(entityID) {
|
||||||
|
if (entityID === rack) {
|
||||||
|
deleteCollidingBalls();
|
||||||
|
Script.clearInterval(distanceCheckInterval);
|
||||||
|
Entities.deletingEntity.disconnect(deleteEntity);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteCollidingBalls() {
|
||||||
|
while (collidingBalls.length > 0) {
|
||||||
|
Entities.deleteEntity(collidingBalls.pop());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
createCollidingBalls();
|
||||||
|
Entities.deletingEntity.connect(deleteEntity);
|
||||||
|
|
||||||
|
var distanceCheckInterval = Script.setInterval(testBallDistanceFromStart, 1000);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
function createWand(position) {
|
function createWand(position) {
|
||||||
var WAND_MODEL = 'http://hifi-public.s3.amazonaws.com/james/bubblewand/models/wand/wand.fbx';
|
var WAND_MODEL = 'http://hifi-public.s3.amazonaws.com/james/bubblewand/models/wand/wand.fbx';
|
||||||
var WAND_COLLISION_SHAPE = 'http://hifi-public.s3.amazonaws.com/james/bubblewand/models/wand/actual_no_top_collision_hull.obj';
|
var WAND_COLLISION_SHAPE = 'http://hifi-public.s3.amazonaws.com/james/bubblewand/models/wand/actual_no_top_collision_hull.obj';
|
||||||
|
|
Loading…
Reference in a new issue