Merge pull request #1142 from SilverfishVR/serverlessV3

Load serverless tutorial from local disk
This commit is contained in:
Kalila 2021-04-15 19:10:52 -04:00 committed by GitHub
commit 0150c46836
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
23 changed files with 4607 additions and 1696 deletions

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View file

@ -0,0 +1,59 @@
// Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
// 2020 Silverfish.
//material sequencer, put on a material entity (server script) to make it iterate through discrete steps of X UV offset.
/*UserData:
{
"verticalOffset": 0,
"segments": 16,
"updateInterval": 250
}
*/
(function() {
var DEFAULT_VERTICAL_OFFSET = 0.0;
var DEFAULT_HORIZONTAL_SPEED = 1;
var DEFAULT_UPDATE_INTERVAL = 1000;
var DEFAULT_SEGMENTS = 16;
var self = this;
var _entityID;
this.preload = function(entityID) {
_entityID = entityID;
var verticalOffset = DEFAULT_VERTICAL_OFFSET;
var updateInterval = DEFAULT_UPDATE_INTERVAL;
var moveDistance = 1 / DEFAULT_SEGMENTS;
var verticalOffset = DEFAULT_VERTICAL_OFFSET;
var oldPosition = 0;
var currentPosition = 0;
var userData = JSON.parse(Entities.getEntityProperties(_entityID, ["userData"]).userData);
if (userData !== undefined) {
if (userData.segments !== undefined) {
moveDistance = 1 / userData.segments;
}
if (userData.verticalOffset !== undefined) {
verticalOffset = userData.verticalOffset;
}
if (userData.updateInterval !== undefined) {
updateInterval = userData.updateInterval;
}
}
self.intervalID = Script.setInterval(function() {
if(currentPosition >= 1){
currentPosition = 0;
oldPosition = 0;
}
Entities.editEntity(_entityID, { materialMappingPos: { x: currentPosition, y: verticalOffset}});
// print("current Pos: " + currentPosition);
currentPosition = oldPosition + moveDistance;
oldPosition = currentPosition;
}, updateInterval);
};
this.unload = function() {
Script.clearInterval(self.intervalID);
}
});

View file

@ -0,0 +1,182 @@
//
// mirrorClient.js
//
// Created by Patrick Manalich
// Edited by Rebecca Stankus on 8/30/17.
// Edited by David Back on 11/17/17.
// Edited by Anna Brewer on 7/12/19.
// Copyright 2017 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
//
// Attach `mirrorClient.js` to a box entity whose z dimension is very small,
// and whose x and y dimensions are up to you. See comments in `mirrorReflection.js`
// for more information about the mirror on/off zone.
"use strict";
(function () { // BEGIN LOCAL SCOPE
// VARIABLES
/* globals utils, Render */
var _this = this;
var MAX_MIRROR_RESOLUTION_SIDE_PX = 960; // The max pixel resolution of the long side of the mirror
var ZERO_ROT = { w: 1, x: 0, y: 0, z: 0 }; // Constant quaternion for a rotation of 0
var FAR_CLIP_DISTANCE = 16; // The far clip distance for the spectator camera when the mirror is on
var mirrorLocalEntityID = false; // The entity ID of the local entity that displays the mirror reflection
var mirrorLocalEntityRunning; // True if mirror local entity is reflecting, false otherwise
var mirrorLocalEntityOffset = 0.01; // The distance between the center of the mirror and the mirror local entity
var spectatorCameraConfig = Render.getConfig("SecondaryCamera"); // Render configuration for the spectator camera
var lastDimensions = { x: 0, y: 0 }; // The previous dimensions of the mirror
var previousFarClipDistance; // Store the specator camera's previous far clip distance that we override for the mirror
// LOCAL FUNCTIONS
function isPositionInsideBox(position, boxProperties) {
var localPosition = Vec3.multiplyQbyV(Quat.inverse(boxProperties.rotation),
Vec3.subtract(MyAvatar.position, boxProperties.position));
var halfDimensions = Vec3.multiply(boxProperties.dimensions, 0.5);
return -halfDimensions.x <= localPosition.x &&
halfDimensions.x >= localPosition.x &&
-halfDimensions.y <= localPosition.y &&
halfDimensions.y >= localPosition.y &&
-halfDimensions.z <= localPosition.z &&
halfDimensions.z >= localPosition.z;
}
// When x or y dimensions of the mirror change - reset the resolution of the
// spectator camera and edit the mirror local entity to adjust for the new dimensions
function updateMirrorDimensions(forceUpdate) {
if (!mirrorLocalEntityID) {
return;
}
if (mirrorLocalEntityRunning) {
var newDimensions = Entities.getEntityProperties(_this.entityID, 'dimensions').dimensions;
if (forceUpdate === true || (newDimensions.x != lastDimensions.x || newDimensions.y != lastDimensions.y)) {
var mirrorResolution = _this.calculateMirrorResolution(newDimensions);
spectatorCameraConfig.resetSizeSpectatorCamera(mirrorResolution.x, mirrorResolution.y);
Entities.editEntity(mirrorLocalEntityID, {
dimensions: {
x: (Math.max(newDimensions.x, newDimensions.y)),
y: (Math.max(newDimensions.x, newDimensions.y)),
z: 0
}
});
}
lastDimensions = newDimensions;
}
}
// Takes in an mirror scalar number which is used for the index of "halfDimSigns" that is needed to adjust the mirror
// local entity's position. Deletes and re-adds the mirror local entity so the url and position are updated.
function createMirrorLocalEntity() {
if (mirrorLocalEntityID) {
Entities.deleteEntity(mirrorLocalEntityID);
mirrorLocalEntityID = false;
}
if (mirrorLocalEntityRunning) {
mirrorLocalEntityID = Entities.addEntity({
type: "Image",
name: "mirrorLocalEntity",
imageURL: "resource://spectatorCameraFrame",
emissive: true,
parentID: _this.entityID,
alpha: 1,
localPosition: {
x: 0,
y: 0,
z: mirrorLocalEntityOffset
},
localRotation: Quat.fromPitchYawRollDegrees(0, 0, 180),
isVisibleInSecondaryCamera: false
}, "local");
updateMirrorDimensions(true);
}
}
_this.calculateMirrorResolution = function(entityDimensions) {
var mirrorResolutionX, mirrorResolutionY;
if (entityDimensions.x > entityDimensions.y) {
mirrorResolutionX = MAX_MIRROR_RESOLUTION_SIDE_PX;
mirrorResolutionY = Math.round(mirrorResolutionX * entityDimensions.y / entityDimensions.x);
} else {
mirrorResolutionY = MAX_MIRROR_RESOLUTION_SIDE_PX;
mirrorResolutionX = Math.round(mirrorResolutionY * entityDimensions.x / entityDimensions.y);
}
var resolution = {
"x": mirrorResolutionX,
"y": mirrorResolutionY
};
return resolution;
};
// Sets up spectator camera to render the mirror, calls 'createMirrorLocalEntity' once to set up
// mirror local entity, then connects 'updateMirrorDimensions' to update dimension changes
_this.mirrorLocalEntityOn = function(onPreload) {
if (!mirrorLocalEntityRunning) {
if (!spectatorCameraConfig.attachedEntityId) {
mirrorLocalEntityRunning = true;
spectatorCameraConfig.mirrorProjection = true;
spectatorCameraConfig.attachedEntityId = _this.entityID;
previousFarClipDistance = spectatorCameraConfig.farClipPlaneDistance;
spectatorCameraConfig.farClipPlaneDistance = FAR_CLIP_DISTANCE;
var entityProperties = Entities.getEntityProperties(_this.entityID, ['dimensions']);
var mirrorEntityDimensions = entityProperties.dimensions;
var initialResolution = _this.calculateMirrorResolution(mirrorEntityDimensions);
spectatorCameraConfig.resetSizeSpectatorCamera(initialResolution.x, initialResolution.y);
spectatorCameraConfig.enableSecondaryCameraRenderConfigs(true);
createMirrorLocalEntity();
Script.update.connect(updateMirrorDimensions);
} else {
print("Cannot turn on mirror if spectator camera is already in use");
}
}
};
// Resets spectator camera, deletes the mirror local entity, and disconnects 'updateMirrorDimensions'
_this.mirrorLocalEntityOff = function() {
if (mirrorLocalEntityRunning) {
spectatorCameraConfig.enableSecondaryCameraRenderConfigs(false);
spectatorCameraConfig.mirrorProjection = false;
spectatorCameraConfig.attachedEntityId = null;
spectatorCameraConfig.farClipPlaneDistance = previousFarClipDistance;
if (mirrorLocalEntityID) {
Entities.deleteEntity(mirrorLocalEntityID);
mirrorLocalEntityID = false;
}
Script.update.disconnect(updateMirrorDimensions);
mirrorLocalEntityRunning = false;
}
};
// ENTITY FUNCTIONS
_this.preload = function(entityID) {
_this.entityID = entityID;
mirrorlocalEntityRunning = false;
// If avatar is already inside the mirror zone at the time preload is called then turn on the mirror
var children = Entities.getChildrenIDs(_this.entityID);
var childZero = Entities.getEntityProperties(children[0]);
if (isPositionInsideBox(MyAvatar.position, {
position: childZero.position,
rotation: childZero.rotation,
dimensions: childZero.dimensions
})) {
_this.mirrorLocalEntityOn(true);
}
};
// Turn off mirror on unload
_this.unload = function(entityID) {
_this.mirrorLocalEntityOff();
};
});

View file

@ -0,0 +1,32 @@
//
// mirrorReflection.js
//
// Created by Rebecca Stankus on 8/30/17.
// Copyright 2017 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
//
// Attach `mirrorReflection.js` to a zone entity that is parented to
// the box entity whose Script is `mirrorClient.js`.
// When a user enters this zone, the mirror will turn on.
// When a user leaves this zone, the mirror will turn off.
(function () {
var mirrorID, reflectionAreaID;
// get id of reflection area and mirror
this.preload = function(entityID) {
reflectionAreaID = entityID;
mirrorID = Entities.getEntityProperties(reflectionAreaID, 'parentID').parentID;
};
// when avatar enters reflection area, begin reflecting
this.enterEntity = function(entityID){
Entities.callEntityMethod(mirrorID, 'mirrorLocalEntityOn');
};
// when avatar leaves reflection area, stop reflecting
this.leaveEntity = function (entityID) {
Entities.callEntityMethod(mirrorID, 'mirrorLocalEntityOff');
};
});

View file

@ -0,0 +1,47 @@
//
// portal.js
// Created by Zach Fox on 2019-05-23
// Copyright 2019 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 Portal = function() {};
Portal.prototype = {
enterEntity: function (id) {
var properties = Entities.getEntityProperties(id, ["userData"]);
var userData;
try {
userData = JSON.parse(properties.userData);
} catch (e) {
console.error("Error parsing userData: ", e);
}
if (userData) {
if (userData.destination) {
var destination = userData.destination;
if (userData.destination.indexOf("bookmark:") > -1) {
var bookmarkName = userData.destination.replace("bookmark:", "");
destination = LocationBookmarks.getAddress(bookmarkName);
}
Window.location = destination;
} else {
console.log("Please specify `destination` inside this entity's `userData`!");
return;
}
} else {
console.log("Please specify this entity's `userData`! See README.md for instructions.");
return;
}
}
};
return new Portal();
});

View file

@ -0,0 +1,202 @@
/* eslint-disable no-magic-numbers */
//
// soundEmitter.js
//
// Created by Zach Fox on 2019-07-05
// Copyright High Fidelity 2019
//
// Licensed under the Apache 2.0 License
// See accompanying license file or http://apache.org/
//
(function() {
var that;
var SOUND_EMITTER_UPDATE_INTERVAL_MS = 500;
var DEFAULT_AUDIO_INJECTOR_OPTIONS = {
"position": {
"x": 0,
"y": 0,
"z": 0
},
"volume": 0.5,
"loop": false,
"localOnly": false
};
var SoundEmitter = function() {
that = this;
that.entityID = false;
that.soundObjectURL = false;
that.soundObject = false;
that.audioInjector = false;
that.audioInjectorOptions = DEFAULT_AUDIO_INJECTOR_OPTIONS;
that.signalsConnected = {};
that.soundEmitterUpdateInterval = false;
};
SoundEmitter.prototype = {
preload: function(entityID) {
that.entityID = entityID;
var properties = Entities.getEntityProperties(that.entityID, ["userData"]);
var userData;
try {
userData = JSON.parse(properties.userData);
} catch (e) {
console.error("Error parsing userData: ", e);
}
if (userData) {
if (userData.soundURL && userData.soundURL.length > 0) {
that.handleNewSoundURL(userData.soundURL);
} else {
console.log("Please specify this entity's `userData`! See README.md for instructions.");
return;
}
} else {
console.log("Please specify this entity's `userData`! See README.md for instructions.");
return;
}
},
clearCurrentSoundData: function() {
that.soundObjectURL = false;
if (that.signalsConnected["soundObjectReady"]) {
that.soundObject.ready.disconnect(that.updateSoundEmitter);
that.signalsConnected["soundObjectReady"] = false;
}
that.soundObject = false;
if (that.audioInjector) {
if (that.audioInjector.playing) {
that.audioInjector.stop();
}
that.audioInjector = false;
}
that.audioInjectorOptions = DEFAULT_AUDIO_INJECTOR_OPTIONS;
if (that.soundEmitterUpdateInterval) {
Script.clearInterval(that.soundEmitterUpdateInterval);
that.soundEmitterUpdateInterval = false;
}
},
unload: function() {
that.clearCurrentSoundData();
},
handleNewSoundURL: function(newSoundURL) {
that.clearCurrentSoundData();
that.soundObjectURL = newSoundURL;
that.soundObject = SoundCache.getSound(that.soundObjectURL);
if (that.soundObject.downloaded) {
that.updateSoundEmitter();
} else {
that.soundObject.ready.connect(that.updateSoundEmitter);
that.signalsConnected["soundObjectReady"] = true;
}
},
positionChanged: function(newPos) {
return (newPos.x !== that.audioInjectorOptions.position.x ||
newPos.y !== that.audioInjectorOptions.position.y ||
newPos.z !== that.audioInjectorOptions.position.z);
},
updateSoundEmitter: function() {
var properties = Entities.getEntityProperties(that.entityID, ["userData", "position", "script", "serverScripts"]);
var userData;
try {
userData = JSON.parse(properties.userData);
} catch (e) {
console.error("Error parsing userData: ", e);
}
var optionsChanged = false;
var shouldRestartPlayback = false;
var newPosition = properties.position;
if (userData) {
if (userData.soundURL && userData.soundURL.length > 0 && userData.soundURL !== that.soundObjectURL) {
console.log("Sound Emitter: User put a new sound URL into `userData`! Resetting...");
that.handleNewSoundURL(userData.soundURL);
return;
}
if (typeof(userData.volume) !== "undefined" && !isNaN(userData.volume) && userData.volume !== that.audioInjectorOptions.volume) {
optionsChanged = true;
that.audioInjectorOptions.volume = userData.volume;
}
if (typeof(userData.shouldLoop) !== "undefined" && userData.shouldLoop !== that.audioInjectorOptions.shouldLoop) {
optionsChanged = true;
if (!that.audioInjectorOptions.loop && userData.shouldLoop && that.audioInjector && !that.audioInjector.playing) {
shouldRestartPlayback = true;
}
that.audioInjectorOptions.loop = userData.shouldLoop;
}
if (typeof(userData.positionOverride) !== "undefined" && !isNaN(userData.positionOverride.x) &&
!isNaN(userData.positionOverride.y) && !isNaN(userData.positionOverride.z)) {
newPosition = userData.positionOverride;
}
} else {
console.log("Please specify this entity's `userData`! See README.md for instructions.");
that.clearCurrentSoundData();
return;
}
var localOnly = that.audioInjectorOptions.localOnly;
// If this script is attached as a client entity script...
if (properties.script.indexOf("soundEmitter.js") > -1) {
// ... Make sure that the audio injector IS local only.
localOnly = true;
// Else if this script is attached as a client server script...
} else if (properties.serverScripts.indexOf("soundEmitter.js") > -1) {
// ... Make sure that the audio injector IS NOT local only.
localOnly = false;
}
if (localOnly !== that.audioInjectorOptions.localOnly) {
optionsChanged = true;
that.audioInjectorOptions.localOnly = localOnly;
}
if (that.positionChanged(newPosition)) {
optionsChanged = true;
that.audioInjectorOptions["position"] = newPosition;
}
if (!that.audioInjector || shouldRestartPlayback) {
that.audioInjector = Audio.playSound(that.soundObject, that.audioInjectorOptions);
} else if (optionsChanged) {
that.audioInjector.setOptions(that.audioInjectorOptions);
}
if (!that.soundEmitterUpdateInterval) {
that.soundEmitterUpdateInterval = Script.setInterval(that.updateSoundEmitter, SOUND_EMITTER_UPDATE_INTERVAL_MS);
}
}
};
return new SoundEmitter();
});

View file

@ -0,0 +1,77 @@
'use strict';
//
// wizardLoader.js
//
// Created by Kalila L. on Feb 19 2021.
// Copyright 2021 Vircadia contributors.
//
// This script is used to load the onboarding wizard at the location of the entity it's on.
//
// 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 CONFIG_WIZARD_WEB_URL = 'https://cdn-1.vircadia.com/us-e-1/DomainContent/Tutorial/Apps/configWizard/dist/index.html';
var loaderEntityID;
var configWizardEntityID;
function onWebAppEventReceived(sendingEntityID, event) {
if (sendingEntityID === configWizardEntityID) {
var eventJSON = JSON.parse(event);
if (eventJSON.command === 'first-run-wizard-ready') {
var objectToSend = {
command: 'script-to-web-initialize',
data: {
performancePreset: Performance.getPerformancePreset(),
refreshRateProfile: Performance.getRefreshRateProfile(),
displayName: MyAvatar.displayName
}
};
Entities.emitScriptEvent(configWizardEntityID, JSON.stringify(objectToSend));
}
if (eventJSON.command === 'complete-wizard') {
Performance.setPerformancePreset(eventJSON.data.performancePreset);
Performance.setRefreshRateProfile(eventJSON.data.refreshRateProfile);
MyAvatar.displayName = eventJSON.data.displayName;
Entities.deleteEntity(configWizardEntityID);
Entities.webEventReceived.disconnect(onWebAppEventReceived);
}
}
}
this.preload = function (entityID) {
loaderEntityID = entityID;
var loaderEntityProps = Entities.getEntityProperties(loaderEntityID, ['position', 'rotation']);
configWizardEntityID = Entities.addEntity({
type: 'Web',
sourceUrl: CONFIG_WIZARD_WEB_URL,
maxFPS: 60,
dpi: 20,
useBackground: false,
grab: {
grabbable: false
},
position: loaderEntityProps.position,
rotation: loaderEntityProps.rotation,
dimensions: { x: 1.4, y: 0.75, z: 0 }
}, 'local');
Entities.webEventReceived.connect(onWebAppEventReceived);
}
this.unload = function () {
if (configWizardEntityID) {
Entities.deleteEntity(configWizardEntityID);
Entities.webEventReceived.disconnect(onWebAppEventReceived);
}
}
})

Binary file not shown.

After

Width:  |  Height:  |  Size: 78 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 870 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff