From 46fbf38b5d38e7e7a1a9447d1e9e805fdc477ea7 Mon Sep 17 00:00:00 2001 From: "James B. Pollack" Date: Wed, 24 Feb 2016 12:36:18 -0800 Subject: [PATCH] ac movers --- .../CellScience/Scripts/colorRandomly.js | 104 ----- .../CellScience/Scripts/moveRandomly2.js | 91 ----- .../Scripts/showButtonToPlaySound.js | 4 - .../CellScience/Scripts/virtualBaton.js | 381 ------------------ .../Scripts/zoomAndMoveRandomly.js | 164 -------- .../CellScience/importCellScience.js | 43 +- .../DomainContent/CellScience/moveCellsAC.js | 96 +++++ .../CellScience/moveVesiclesAC.js | 106 +++++ 8 files changed, 212 insertions(+), 777 deletions(-) delete mode 100644 unpublishedScripts/DomainContent/CellScience/Scripts/colorRandomly.js delete mode 100644 unpublishedScripts/DomainContent/CellScience/Scripts/moveRandomly2.js delete mode 100644 unpublishedScripts/DomainContent/CellScience/Scripts/virtualBaton.js delete mode 100644 unpublishedScripts/DomainContent/CellScience/Scripts/zoomAndMoveRandomly.js create mode 100644 unpublishedScripts/DomainContent/CellScience/moveCellsAC.js create mode 100644 unpublishedScripts/DomainContent/CellScience/moveVesiclesAC.js diff --git a/unpublishedScripts/DomainContent/CellScience/Scripts/colorRandomly.js b/unpublishedScripts/DomainContent/CellScience/Scripts/colorRandomly.js deleted file mode 100644 index cf4ee810e7..0000000000 --- a/unpublishedScripts/DomainContent/CellScience/Scripts/colorRandomly.js +++ /dev/null @@ -1,104 +0,0 @@ -// 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() { - - Script.include(Script.resolvePath('virtualBaton.js')); - - var self = this; - - var baton; - var iOwn = false; - var currentInterval; - var _entityId; - - function startUpdate() { - iOwn = true; - print('i am the owner ' + _entityId) - } - - function stopUpdateAndReclaim() { - print('i released the object ' + _entityId) - iOwn = false; - baton.claim(startUpdate, stopUpdateAndReclaim); - } - - this.preload = function(entityId) { - this.isConnected = false; - this.entityId = entityId; - _entityId = entityId; - this.minVelocity = 1; - this.maxVelocity = 5; - this.minAngularVelocity = 0.01; - this.maxAngularVelocity = 0.03; - baton = virtualBaton({ - batonName: 'io.highfidelity.vesicles:' + entityId, // One winner for each entity - }); - stopUpdateAndReclaim(); - currentInterval = Script.setInterval(self.move, self.getTotalWait()) - } - - - this.getTotalWait = function() { - return (Math.random() * 5000) * 2; - // var avatars = AvatarList.getAvatarIdentifiers(); - // var avatarCount = avatars.length; - // var random = Math.random() * 5000; - // var totalWait = random * (avatarCount * 2); - // print('cellscience color avatarcount, totalwait: ', avatarCount, totalWait) - // return totalWait - } - - - this.move = function() { - if (!iOwn) { - return; - } - - var properties = Entities.getEntityProperties(self.entityId); - var color = properties.color; - - var newColor; - var red = { - red: 255, - green: 0, - blue: 0 - } - var green = { - red: 0, - green: 255, - blue: 0 - } - var blue = { - red: 0, - green: 0, - blue: 255 - } - if (color.red > 0) { - newColor = green; - } - if (color.green > 0) { - newColor = blue; - } - if (color.blue > 0) { - newColor = red - } - Entities.editEntity(self.entityId, { - color: newColor - }); - - - } - - - this.unload = function() { - baton.release(function() {}); - Script.clearTimeout(currentInterval); - } - - - -}) \ No newline at end of file diff --git a/unpublishedScripts/DomainContent/CellScience/Scripts/moveRandomly2.js b/unpublishedScripts/DomainContent/CellScience/Scripts/moveRandomly2.js deleted file mode 100644 index ec7b249db0..0000000000 --- a/unpublishedScripts/DomainContent/CellScience/Scripts/moveRandomly2.js +++ /dev/null @@ -1,91 +0,0 @@ -// 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() { - - Script.include('virtualBaton.js'); - - var self = this; - - var baton; - var iOwn = false; - var currentInterval; - var _entityId; - - function startUpdate() { - iOwn = true; - print('i am the owner ' + _entityId) - } - - function stopUpdateAndReclaim() { - print('i released the object ' + _entityId) - iOwn = false; - baton.claim(startUpdate, stopUpdateAndReclaim); - } - - this.preload = function(entityId) { - this.isConnected = false; - this.entityId = entityId; - _entityId = entityId; - this.minVelocity = 1; - this.maxVelocity = 5; - this.minAngularVelocity = 0.01; - this.maxAngularVelocity = 0.03; - baton = virtualBaton({ - batonName: 'io.highfidelity.vesicles:' + entityId, // One winner for each entity - }); - stopUpdateAndReclaim(); - currentInterval = Script.setInterval(self.move, self.getTotalWait()) - } - - - this.getTotalWait = function() { - return (Math.random() * 5000) * 2; - } - - - this.move = function() { - if (!iOwn) { - return; - } - - var magnitudeV = self.maxVelocity; - var directionV = { - x: Math.random() - 0.5, - y: Math.random() - 0.5, - z: Math.random() - 0.5 - }; - - //print("POS magnitude is " + magnitudeV + " and direction is " + directionV.x); - - var magnitudeAV = self.maxAngularVelocity; - - var directionAV = { - x: Math.random() - 0.5, - y: Math.random() - 0.5, - z: Math.random() - 0.5 - }; - //print("ROT magnitude is " + magnitudeAV + " and direction is " + directionAV.x); - Entities.editEntity(self.entityId, { - velocity: Vec3.multiply(magnitudeV, Vec3.normalize(directionV)), - angularVelocity: Vec3.multiply(magnitudeAV, Vec3.normalize(directionAV)) - - }); - - - } - - - this.unload = function() { - if (baton) { - baton.release(function() {}); - } - Script.clearInterval(currentInterval); - } - - - -}) \ No newline at end of file diff --git a/unpublishedScripts/DomainContent/CellScience/Scripts/showButtonToPlaySound.js b/unpublishedScripts/DomainContent/CellScience/Scripts/showButtonToPlaySound.js index 6651e435b4..8ee5e0092e 100644 --- a/unpublishedScripts/DomainContent/CellScience/Scripts/showButtonToPlaySound.js +++ b/unpublishedScripts/DomainContent/CellScience/Scripts/showButtonToPlaySound.js @@ -36,8 +36,6 @@ return; } - - self.addButton(); self.buttonShowing = false; self.showDistance = self.userData.showDistance; @@ -51,8 +49,6 @@ }; self.sound = SoundCache.getSound(this.soundURL); - - } this.addButton = function() { diff --git a/unpublishedScripts/DomainContent/CellScience/Scripts/virtualBaton.js b/unpublishedScripts/DomainContent/CellScience/Scripts/virtualBaton.js deleted file mode 100644 index 63f96a5c1e..0000000000 --- a/unpublishedScripts/DomainContent/CellScience/Scripts/virtualBaton.js +++ /dev/null @@ -1,381 +0,0 @@ -"use strict"; -/*jslint nomen: true, plusplus: true, vars: true */ -/*global Messages, Script, MyAvatar, AvatarList, Entities, print */ - -// Created by Howard Stearns -// 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 -// -// Allows cooperating scripts to pass a "virtual baton" between them, -// which is useful when part of a script should only be executed by -// the one participant that is holding this particular baton. -// -// A virtual baton is simply any string agreed upon by the scripts -// that use it. Only one script at a time can hold the baton, and it -// holds it until that script releases it, or the other scripts -// determine that the holding script is not responding. The script -// automatically determines who among claimants has the baton, if anyone, -// and holds an "election" if necessary. -// -// See entityScript/tribble.js as an example, and the functions -// virtualBaton(), claim(), release(). -// - -// Answers a new virtualBaton for the given parameters, of which 'key' -// is required. -function virtualBatonf(options) { - // Answer averages (number +/- variability). Avoids having everyone act in lockstep. - function randomize(number, variability) { - var allowedDeviation = number * variability; // one side of the deviation range - var allowedDeviationRange = allowedDeviation * 2; // total range for +/- deviation - var randomDeviation = Math.random() * allowedDeviationRange; - var result = number - allowedDeviation + randomDeviation; - return result; - } - // Allow testing outside in a harness outside of High Fidelity. - // See sourceCodeSandbox/tests/mocha/test/testVirtualBaton.js - var globals = options.globals || {}, - messages = globals.Messages || Messages, - myAvatar = globals.MyAvatar || MyAvatar, - avatarList = globals.AvatarList || AvatarList, - entities = globals.Entities || Entities, - timers = globals.Script || Script, - log = globals.print || print; - - var batonName = options.batonName, // The identify of the baton. - // instanceId is the identify of this particular copy of the script among all copies using the same batonName - // in the domain. For example, if you wanted only one entity among multiple entity scripts to hold the baton, - // you could specify virtualBaton({batonName: 'someBatonName', instanceId: MyAvatar.sessionUUID + entityID}). - instanceId = options.instanceId || myAvatar.sessionUUID, - // virtualBaton() returns the exports object with properties. You can pass in an object to be side-effected. - exports = options.exports || {}, - // Handy to set false if we believe the optimizations are wrong, or to use both values in a test harness. - useOptimizations = (options.useOptimizations === undefined) ? true : options.useOptimizations, - electionTimeout = options.electionTimeout || randomize(500, 0.2), // ms. If no winner in this time, hold a new election. - recheckInterval = options.recheckInterval || randomize(500, 0.2), // ms. Check that winners remain connected. - // If you supply your own instanceId, you might also supply a connectionTest that answers - // truthy iff the given id is still valid and connected, and is run at recheckInterval. You - // can use exports.validId (see below), and the default answers truthy if id is valid or a - // concatenation of two valid ids. (This handles the most common cases of instanceId being - // either (the default) MyAvatar.sessionUUID, an entityID, or the concatenation (in either - // order) of both.) - connectionTest = options.connectionTest || function connectionTest(id) { - var idLength = 38; - if (id.length === idLength) { - return exports.validId(id); - } - return (id.length === 2 * idLength) && exports.validId(id.slice(0, idLength)) && exports.validId(id.slice(idLength)); - }; - - if (!batonName) { - throw new Error("A virtualBaton must specify a batonName."); - } - // Truthy if id exists as either a connected avatar or valid entity. - exports.validId = function validId(id) { - var avatar = avatarList.getAvatar(id); - if (avatar && (avatar.sessionUUID === id)) { - return true; - } - var properties = entities.getEntityProperties(id, ['type']); - return properties && properties.type; - }; - - // Various logging, controllable through options. - function debug() { // Display the arguments not just [Object object]. - log.apply(null, [].map.call(arguments, JSON.stringify)); - } - function debugFlow() { - if (options.debugFlow) { - debug.apply(null, arguments); - } - } - function debugSend(destination, operation, data) { - if (options.debugSend) { - debug('baton:', batonName, instanceId, 's=>', destination, operation, data); - } - } - function debugReceive(senderID, operation, data) { // senderID is client sessionUUID -- not necessarily instanceID! - if (options.debugReceive) { - debug('baton:', batonName, senderID, '=>r', instanceId, operation, data); - } - } - - // Messages: Just synactic sugar for hooking things up to Messages system. - // We create separate subchannel strings for each operation within our general channelKey, instead of using - // a switch in the receiver. - var channelKey = "io.highfidelity.virtualBaton:" + batonName, - subchannelHandlers = {}, // Message channel string => {receiver, op} - subchannelKeys = {}; // operation => Message channel string - function subchannelKey(operation) { - return channelKey + ':' + operation; - } - function receive(operation, handler) { // Record a handler for an operation on our channelKey - var subKey = subchannelKey(operation); - subchannelHandlers[subKey] = {receiver: handler, op: operation}; - subchannelKeys[operation] = subKey; - messages.subscribe(subKey); - } - function sendHelper(subchannel, data) { - var message = JSON.stringify(data); - messages.sendMessage(subchannel, message); - } - function send1(operation, destination, data) { // Send data for an operation to just one destination on our channelKey. - debugSend(destination, operation, data); - sendHelper(subchannelKey(operation) + destination, data); - } - function send(operation, data) { // Send data for an operation on our channelKey. - debugSend('-', operation, data); - sendHelper(subchannelKeys[operation], data); - } - function messageHandler(channel, messageString, senderID) { - var handler = subchannelHandlers[channel]; - if (!handler) { - return; - } - var data = JSON.parse(messageString); - debugReceive(senderID, handler.op, data); - handler.receiver(data); - } - messages.messageReceived.connect(messageHandler); - - var nPromises = 0, nAccepted = 0, electionWatchdog; - - // It would be great if we had a way to know how many subscribers our channel has. Failing that... - var nNack = 0, previousNSubscribers = 0, lastGathering = 0, thisTimeout = electionTimeout; - function nSubscribers() { // Answer the number of subscribers. - // To find nQuorum, we need to know how many scripts are being run using this batonName, which isn't - // the same as the number of clients! - // - // If we overestimate by too much, we may fail to reach consensus, which triggers a new - // election proposal, so we take the number of acceptors to be the max(nPromises, nAccepted) - // + nNack reported in the previous round. - // - // If we understimate by too much, there can be different pockets on the Internet that each - // believe they have agreement on different holders of the baton, which is precisely what - // the virtualBaton is supposed to avoid. Therefore we need to allow 'nack' to gather stragglers. - - var now = Date.now(), elapsed = now - lastGathering; - if (elapsed >= thisTimeout) { - previousNSubscribers = Math.max(nPromises, nAccepted) + nNack; - lastGathering = now; - } // ...otherwise we use the previous value unchanged. - - // On startup, we do one proposal that we cannot possibly close, so that we'll - // lock things up for the full electionTimeout to gather responses. - if (!previousNSubscribers) { - var LARGE_INTEGER = Number.MAX_SAFE_INTEGER || (-1 >>> 1); // QT doesn't define the ECMA constant. Max int will do for our purposes. - previousNSubscribers = LARGE_INTEGER; - } - return previousNSubscribers; - } - - // MAIN ALGORITHM - // - // Internally, this uses the Paxos algorith to hold elections. - // Alternatively, we could have the message server pick and maintain a winner, but it would - // still have to deal with the same issues of verification in the presence of lost/delayed/reordered messages. - // Paxos is known to be optimal under these circumstances, except that its best to have a dedicated proposer - // (such as the server). - function betterNumber(number, best) { - return (number.number || 0) > best.number; - } - // Paxos Proposer behavior - var proposalNumber = 0, - nQuorum = 0, - bestPromise = {number: 0}, - claimCallback, - releaseCallback; - function propose() { // Make a new proposal, so that we learn/update the proposalNumber and winner. - // Even though we send back a 'nack' if the proposal is obsolete, with network errors - // there's no way to know for certain that we've failed. The electionWatchdog will try a new - // proposal if we have not been accepted by a quorum after election Timeout. - if (electionWatchdog) { - // If we had a means of determining nSubscribers other than by counting, we could just - // timers.clearTimeout(electionWatchdog) and not return. - return; - } - thisTimeout = randomize(electionTimeout, 0.5); // Note use in nSubcribers. - electionWatchdog = timers.setTimeout(function () { - electionWatchdog = null; - propose(); - }, thisTimeout); - var nAcceptors = nSubscribers(); - nQuorum = Math.floor(nAcceptors / 2) + 1; - - proposalNumber = Math.max(proposalNumber, bestPromise.number) + 1; - debugFlow('baton:', batonName, instanceId, 'propose', proposalNumber, - 'claim:', !!claimCallback, 'nAcceptors:', nAcceptors, nPromises, nAccepted, nNack); - nPromises = nAccepted = nNack = 0; - send('prepare!', {number: proposalNumber, proposerId: instanceId}); - } - // We create a distinguished promise subchannel for our id, because promises need only be sent to the proposer. - receive('promise' + instanceId, function (data) { - if (betterNumber(data, bestPromise)) { - bestPromise = data; - } - if ((data.proposalNumber === proposalNumber) && (++nPromises >= nQuorum)) { // Note check for not being a previous round - var answer = {number: data.proposalNumber, proposerId: data.proposerId, winner: bestPromise.winner}; // Not data.number. - if (!answer.winner || (answer.winner === instanceId)) { // We get to pick. - answer.winner = claimCallback ? instanceId : null; - } - send('accept!', answer); - } - }); - receive('nack' + instanceId, function (data) { // An acceptor reports more recent data... - if (data.proposalNumber === proposalNumber) { - nNack++; // For updating nQuorum. - // IWBNI if we started our next proposal right now/here, but we need a decent nNack count. - // Lets save that optimization for another day... - } - }); - // Paxos Acceptor behavior - var bestProposal = {number: 0}, accepted = {}; - function acceptedId() { - return accepted && accepted.winner; - } - receive('prepare!', function (data) { - var response = {proposalNumber: data.number, proposerId: data.proposerId}; - if (betterNumber(data, bestProposal)) { - bestProposal = data; - if (accepted.winner && connectionTest(accepted.winner)) { - response.number = accepted.number; - response.winner = accepted.winner; - } - send1('promise', data.proposerId, response); - } else { - send1('nack', data.proposerId, response); - } - }); - receive('accept!', function (data) { - if (!betterNumber(bestProposal, data)) { - bestProposal = accepted = data; // Update both with current data. Might have missed the proposal earlier. - if (useOptimizations) { - // The Paxos literature describes every acceptor sending 'accepted' to - // every proposer and learner. In our case, these are the same nodes that received - // the 'accept!' message, so we can send to just the originating proposer and invoke - // our own accepted handler directly. - // Note that this optimization cannot be used with Byzantine Paxos (which needs another - // multi-broadcast to detect lying and collusion). - debugSend('/', 'accepted', data); - debugReceive(instanceId, 'accepted', data); // direct on next line, which doesn't get logging. - subchannelHandlers[subchannelKey('accepted') + instanceId].receiver(data); - if (data.proposerId !== instanceId) { // i.e., we didn't already do it directly on the line above. - send1('accepted', data.proposerId, data); - } - } else { - send('accepted', data); - } - } else { - send1('nack', data.proposerId, {proposalNumber: data.number}); - } - }); - // Paxos Learner behavior. - function localRelease() { - var callback = releaseCallback; - debugFlow('baton:', batonName, 'localRelease', 'callback:', !!releaseCallback); - if (!releaseCallback) { - return; - } // Already released, but we might still receive a stale message. That's ok. - releaseCallback = undefined; - callback(batonName); // Pass batonName so that clients may use the same handler for different batons. - } - receive('accepted' + (useOptimizations ? instanceId : ''), function (data) { // See note in 'accept!' regarding use of instanceId here. - if (betterNumber(accepted, data)) { // Especially when !useOptimizations, we can receive other acceptances late. - return; - } - var oldAccepted = accepted; - debugFlow('baton:', batonName, instanceId, 'accepted', data.number, data.winner); - accepted = data; - // If we are proposer, make sure we get a quorum of acceptances. - if ((data.proposerId === instanceId) && (data.number === proposalNumber) && (++nAccepted >= nQuorum)) { - if (electionWatchdog) { - timers.clearTimeout(electionWatchdog); - electionWatchdog = null; - } - } - // If we are the winner -- regardless of whether we were the proposer. - if (acceptedId() === instanceId) { - if (claimCallback) { - var callback = claimCallback; - claimCallback = undefined; - callback(batonName); - } else if (!releaseCallback) { // We won, but have been released and are no longer interested. - // Propose that someone else take the job. - timers.setTimeout(propose, 0); // Asynchronous to queue message handling if some are synchronous and others not. - } - } else if (releaseCallback && (oldAccepted.winner === instanceId)) { // We've been released by someone else! - localRelease(); // This can happen if enough people thought we'd disconnected. - } - }); - - // Public Interface - // - // Registers an intent to hold the baton: - // Calls onElection(batonName) once, if you are elected by the scripts - // to be the unique holder of the baton, which may be never. - // Calls onRelease(batonName) once, if the baton held by you is released, - // whether this is by you calling release(), or by losing - // an election when you become disconnected. - // You may claim again at any time after the start of onRelease - // being called. - exports.claim = function claim(onElection, onRelease) { - debugFlow('baton:', batonName, instanceId, 'claim'); - if (claimCallback) { - log("Ignoring attempt to claim virtualBaton " + batonName + ", which is already waiting for claim."); - return; - } - if (releaseCallback) { - log("Ignoring attempt to claim virtualBaton " + batonName + ", which is somehow incorrect released, and that should not happen."); - return; - } - claimCallback = onElection; - releaseCallback = onRelease; - propose(); - return exports; // Allows chaining. e.g., var baton = virtualBaton({batonName: 'foo'}.claim(onClaim, onRelease); - }; - // Release the baton you hold, or just log that you are not holding it. - exports.release = function release(optionalReplacementOnRelease) { - debugFlow('baton:', batonName, instanceId, 'release'); - if (optionalReplacementOnRelease) { // If you want to change. - releaseCallback = optionalReplacementOnRelease; - } - if (acceptedId() !== instanceId) { - log("Ignoring attempt to release virtualBaton " + batonName + ", which is not being held."); - return; - } - localRelease(); - if (!claimCallback) { // No claim set in release callback. - propose(); - } - return exports; - }; - exports.recheckWatchdog = timers.setInterval(function recheck() { - var holder = acceptedId(); // If we're waiting and we notice the holder is gone, ... - if (holder && claimCallback && !electionWatchdog && !connectionTest(holder)) { - bestPromise.winner = null; // used if the quorum agrees that old winner is not there - propose(); // ... propose an election. - } - }, recheckInterval); - exports.unload = function unload() { // Disconnect from everything. - messages.messageReceived.disconnect(messageHandler); - timers.clearInterval(exports.recheckWatchdog); - if (electionWatchdog) { - timers.clearTimeout(electionWatchdog); - } - electionWatchdog = claimCallback = releaseCallback = null; - Object.keys(subchannelHandlers).forEach(messages.unsubscribe); - debugFlow('baton:', batonName, instanceId, 'unload'); - return exports; - }; - - // Gather nAcceptors by making two proposals with some gathering time, even without a claim. - propose(); - return exports; -} -if (typeof module !== 'undefined') { // Allow testing in nodejs. - module.exports = virtualBatonf; -} else { - virtualBaton = virtualBatonf; -} diff --git a/unpublishedScripts/DomainContent/CellScience/Scripts/zoomAndMoveRandomly.js b/unpublishedScripts/DomainContent/CellScience/Scripts/zoomAndMoveRandomly.js deleted file mode 100644 index dd6a48c617..0000000000 --- a/unpublishedScripts/DomainContent/CellScience/Scripts/zoomAndMoveRandomly.js +++ /dev/null @@ -1,164 +0,0 @@ -// 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 teleport; - var portalDestination; - var animationURL; - - this.entered = true; - Script.include('virtualBaton.js'); - - var self = this; - var baton; - - this.iOwn = false; - var currentInterval; - var _entityId; - - function startUpdate() { - self.iOwn = true; - print('i am the owner ' + _entityId) - } - - function stopUpdateAndReclaim() { - print('i released the object ' + _entityId) - self.iOwn = false; - baton.claim(startUpdate, stopUpdateAndReclaim); - } - - this.preload = function(entityID) { - this.entityId = entityID; - _entityId = entityID; - this.initialize(entityID); - this.initTimeout = null; - this.minVelocity = 1; - this.maxVelocity = 5; - this.minAngularVelocity = 0.03; - this.maxAngularVelocity = 0.10; - baton = virtualBaton({ - batonName: 'io.highfidelity.cells:' + entityID, // One winner for each entity - }); - stopUpdateAndReclaim(); - currentInterval = Script.setInterval(self.move, self.getTotalWait()) - - } - - this.initialize = function(entityID) { - // print(' should initialize') - var properties = Entities.getEntityProperties(entityID); - if (properties.userData.length === 0 || properties.hasOwnProperty('userData') === false) { - self.initTimeout = Script.setTimeout(function() { - // print(' no user data yet, try again in one second') - self.initialize(entityID); - }, 1000) - } else { - // print(' has userData') - self.portalDestination = properties.userData; - animationURL = properties.modelURL; - self.soundOptions = { - stereo: true, - loop: false, - localOnly: false, - position: properties.position, - volume: 0.5 - }; - - self.teleportSound = SoundCache.getSound("https://hifi-content.s3.amazonaws.com/DomainContent/CellScience/Audio/whoosh.wav"); - - } - } - - this.enterEntity = function(entityID) { - //print('ENTERED A BOUNDARY ENTITY, SHOULD ZOOM', entityID) - var data = JSON.parse(Entities.getEntityProperties(this.entityId).userData); - //print('DATA IS::' + data) - if (data != null) { - print("Teleporting to (" + data.location.x + ", " + data.location.y + ", " + data.location.z + ")"); - - MyAvatar.position = data.location; - } - - } - - this.lookAtTarget = function(entryPoint, target) { - //print('SHOULD LOOK AT TARGET') - var direction = Vec3.normalize(Vec3.subtract(entryPoint, target)); - var pitch = Quat.angleAxis(Math.asin(-direction.y) * 180.0 / Math.PI, { - x: 1, - y: 0, - z: 0 - }); - var yaw = Quat.angleAxis(Math.atan2(direction.x, direction.z) * 180.0 / Math.PI, { - x: 0, - y: 1, - z: 0 - }); - - MyAvatar.goToLocation(entryPoint, true, yaw); - - MyAvatar.headYaw = 0; - - } - - this.leaveEntity = function(entityID) { - Entities.editEntity(entityID, { - animationURL: animationURL, - animationSettings: '{ "frameIndex": 1, "running": false }' - }); - this.entered = false; - if (this.initTimeout !== null) { - Script.clearTimeout(this.initTimeout); - } - //playSound(); - } - - this.unload = function() { - if (this.initTimeout !== null) { - Script.clearTimeout(this.initTimeout); - } - if (baton) { - baton.release(function() {}); - } - - Script.clearInterval(currentInterval); - } - - this.hoverEnterEntity = function(entityID) { - Entities.editEntity(entityID, { - animationURL: animationURL, - animationSettings: '{ "fps": 24, "firstFrame": 1, "lastFrame": 25, "frameIndex": 1, "running": true, "hold": true }' - }); - } - - this.getTotalWait = function() { - return (Math.random() * 5000) * 3; - } - - this.move = function() { - if (self.iOwn === false) { - print('cell is not owned by me...') - return; - } - - var magnitudeAV = self.maxAngularVelocity; - - var directionAV = { - x: Math.random() - 0.5, - y: Math.random() - 0.5, - z: Math.random() - 0.5 - }; - // print("ROT magnitude is " + magnitudeAV + " and direction is " + directionAV.x); - Entities.editEntity(self.entityId, { - angularVelocity: Vec3.multiply(magnitudeAV, Vec3.normalize(directionAV)) - - }); - - - } - -}) \ No newline at end of file diff --git a/unpublishedScripts/DomainContent/CellScience/importCellScience.js b/unpublishedScripts/DomainContent/CellScience/importCellScience.js index 25323495d1..55b09cd4a7 100644 --- a/unpublishedScripts/DomainContent/CellScience/importCellScience.js +++ b/unpublishedScripts/DomainContent/CellScience/importCellScience.js @@ -120,7 +120,7 @@ var scenes = [{ location: locations.cellLayout[1], baseURL: baseLocation }), - script: "zoomAndMoveRandomly.js?" + version, + script: "zoom.js?" + version, visible: true }], boundary: { @@ -194,7 +194,6 @@ var scenes = [{ grabbable: false } }), - script: "moveRandomly2.js?" + version, visible: true }, { //golgi vesicles model: "vesicle", @@ -238,7 +237,6 @@ var scenes = [{ grabbable: false } }), - script: "moveRandomly2.js?" + version, visible: true }, { model: "vesicle", @@ -304,7 +302,6 @@ var scenes = [{ grabbable: false } }), - script: "moveRandomly2.js?" + version, visible: true }, { //outer vesicles model: "vesicle", @@ -326,32 +323,8 @@ var scenes = [{ grabbable: false } }), - script: "moveRandomly2.js?" + version, visible: true - }, - // {//wigglies - // model:"wiggly", - // dimensions:{x:320,y:40,z:160}, - // randomSize: 10, - // offset:{x:0,y:0,z:0}, - // radius:1800, - // number:50, - // userData:"", - // script:"moveRandomly", - // visible:true - // }, - //// {//wigglies - // model:"wiggly", - // dimensions:{x:640,y:80,z:320}, - // randomSize: 10, - // offset:{x:0,y:0,z:0}, - // radius:2100, - // number:50, - // userData:"", - // script:"moveRandomly", - // visible:true - // }, - { + }, { model: "hexokinase", dimensions: { x: 3, @@ -813,7 +786,7 @@ function CreateInstances(scene) { x: 0, y: 0, z: 0 - }, idBounds, 150); + }, idBounds, 150, scene.instances[i]); } //print('SCRIPT AT CREATE ENTITY: ' + script) @@ -824,8 +797,11 @@ function CreateInstances(scene) { -function CreateIdentification(name, position, rotation, dimensions, showDistance) { +function CreateIdentification(name, position, rotation, dimensions, showDistance, parentID) { //print ("creating ID for " + name); + if (parentID === undefined) { + parentID = "{00000000-0000-0000-0000-000000000000}"; + } Entities.addEntity({ type: "Sphere", name: "ID for " + name, @@ -834,6 +810,7 @@ function CreateIdentification(name, position, rotation, dimensions, showDistance green: 0, blue: 0 }, + parentID: parentID, dimensions: dimensions, position: position, rotation: rotation, @@ -9042,7 +9019,7 @@ Script.scriptEnding.connect(function() { Entities.addingEntity.disconnect(makeUngrabbable); }); -Script.setTimeout(function(){ +Script.setTimeout(function() { print('JBP stopping cell science import'); Script.stop(); -},30000) \ No newline at end of file +}, 30000) \ No newline at end of file diff --git a/unpublishedScripts/DomainContent/CellScience/moveCellsAC.js b/unpublishedScripts/DomainContent/CellScience/moveCellsAC.js new file mode 100644 index 0000000000..30e83108d6 --- /dev/null +++ b/unpublishedScripts/DomainContent/CellScience/moveCellsAC.js @@ -0,0 +1,96 @@ +var basePosition = { + x: 3000, + y: 13500, + z: 3000 +}; + +var initialized = false; + +EntityViewer.setPosition(basePosition); +EntityViewer.setKeyholeRadius(60000); +var octreeQueryInterval = Script.setInterval(function() { + EntityViewer.queryOctree(); +}, 200); + +var THROTTLE = true; +var THROTTLE_RATE = 5000; + +var sinceLastUpdate = 0; + +print('cells script') + +function findCells() { + var results = Entities.findEntities(basePosition, 60000); + + if (results.length === 0) { + print('no entities found') + return; + } + + results.forEach(function(v) { + var name = Entities.getEntityProperties(v, 'name').name; + print('name is:: ' + name) + if (name === 'Cell') { + print('found a cell!!' + v) + Script.setTimeout(function() { + moveCell(v); + }, Math.random() * THROTTLE_RATE) + } + }); +} + + +var minAngularVelocity = 0.01; +var maxAngularVelocity = 0.03; + +function moveCell(entityId) { + print('moving a cell! ' + entityId) + + var magnitudeAV = maxAngularVelocity; + + var directionAV = { + x: Math.random() - 0.5, + y: Math.random() - 0.5, + z: Math.random() - 0.5 + }; + print("ROT magnitude is " + magnitudeAV + " and direction is " + directionAV.x); + Entities.editEntity(entityId, { + angularVelocity: Vec3.multiply(magnitudeAV, Vec3.normalize(directionAV)) + }); + +} + +function update(deltaTime) { + + // print('deltaTime',deltaTime) + if (!initialized) { + print("checking for servers..."); + if (Entities.serversExist() && Entities.canRez()) { + print("servers exist -- makeAll..."); + Entities.setPacketsPerSecond(6000); + print("PPS:" + Entities.getPacketsPerSecond()); + initialized = true; + } + return; + } + + if (THROTTLE === true) { + sinceLastUpdate = sinceLastUpdate + deltaTime * 1000; + if (sinceLastUpdate > THROTTLE_RATE) { + print('SHOULD FIND CELLS!!!') + sinceLastUpdate = 0; + findCells(); + } else { + // print('returning in update ' + sinceLastUpdate) + return; + } + } + +} + +function unload() { + Script.update.disconnect(update); +} + +Script.update.connect(update); +Script.scriptEnding.connect(unload); \ No newline at end of file diff --git a/unpublishedScripts/DomainContent/CellScience/moveVesiclesAC.js b/unpublishedScripts/DomainContent/CellScience/moveVesiclesAC.js new file mode 100644 index 0000000000..ce8da54eb2 --- /dev/null +++ b/unpublishedScripts/DomainContent/CellScience/moveVesiclesAC.js @@ -0,0 +1,106 @@ +var basePosition = { + x: 3000, + y: 13500, + z: 3000 +}; + +var initialized = false; + +EntityViewer.setPosition(basePosition); +EntityViewer.setKeyholeRadius(60000); +var octreeQueryInterval = Script.setInterval(function() { + EntityViewer.queryOctree(); +}, 200); + +var THROTTLE = true; +var THROTTLE_RATE = 5000; + +var sinceLastUpdate = 0; + +print('vesicle script') + +function findVesicles() { + var results = Entities.findEntities(basePosition, 60000); + + if (results.length === 0) { + print('no entities found') + return; + } + + results.forEach(function(v) { + var name = Entities.getEntityProperties(v, 'name').name; + print('name is:: ' + name) + if (name === 'vesicle') { + print('found a vesicle!!' + v) + Script.setTimeout(function() { + moveVesicle(v); + }, Math.random() * THROTTLE_RATE) + } + }); +} + +var minVelocity = 1; +var maxVelocity = 5; +var minAngularVelocity = 0.01; +var maxAngularVelocity = 0.03; + +function moveVesicle(entityId) { + print('moving a vesicle! ' + entityId) + var magnitudeV = maxVelocity; + var directionV = { + x: Math.random() - 0.5, + y: Math.random() - 0.5, + z: Math.random() - 0.5 + }; + + print("POS magnitude is " + magnitudeV + " and direction is " + directionV.x); + + var magnitudeAV = maxAngularVelocity; + + var directionAV = { + x: Math.random() - 0.5, + y: Math.random() - 0.5, + z: Math.random() - 0.5 + }; + print("ROT magnitude is " + magnitudeAV + " and direction is " + directionAV.x); + Entities.editEntity(entityId, { + velocity: Vec3.multiply(magnitudeV, Vec3.normalize(directionV)), + angularVelocity: Vec3.multiply(magnitudeAV, Vec3.normalize(directionAV)) + }); + +} + +function update(deltaTime) { + + // print('deltaTime',deltaTime) + if (!initialized) { + print("checking for servers..."); + if (Entities.serversExist() && Entities.canRez()) { + print("servers exist -- makeAll..."); + Entities.setPacketsPerSecond(6000); + print("PPS:" + Entities.getPacketsPerSecond()); + initialized = true; + } + return; + } + + if (THROTTLE === true) { + sinceLastUpdate = sinceLastUpdate + deltaTime * 1000; + if (sinceLastUpdate > THROTTLE_RATE) { + print('SHOULD FIND VESICLES!!!') + sinceLastUpdate = 0; + findVesicles(); + } else { + // print('returning in update ' + sinceLastUpdate) + return; + } + } + +} + +function unload() { + Script.update.disconnect(update); +} + +Script.update.connect(update); +Script.scriptEnding.connect(unload); \ No newline at end of file