Overte-community-apps-Alezi.../applications/survivalKit/app-survivalKit.js
2023-05-30 21:50:22 -04:00

216 lines
7.1 KiB
JavaScript

"use strict";
//
// app-survivalKit.js
//
// Created by Alezia Kurdis, December 29th 2022.
// Copyright 2022, Overte e.V.
//
// Survival kit for virtual worlds exploration in Overte.
//
// 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 jsMainFileName = "app-survivalKit.js";
var ROOT = Script.resolvePath('').split(jsMainFileName)[0];
var APP_NAME = "SURVIVAL";
var APP_URL = ROOT + "survivalKit.html";
var APP_ICON_INACTIVE = ROOT + "icon_inactive.png";
var APP_ICON_ACTIVE = ROOT + "icon_active.png";
var appStatus = false;
var channel = "org.overte.app.survivalKit";
var tablet = Tablet.getTablet("com.highfidelity.interface.tablet.system");
var UPDATE_TIMER_INTERVAL = 100; // 0.1 sec
var processTimer = 0;
var flashLightID = Uuid.NULL;
var flashLightLightID = Uuid.NULL;
var filter = "WHITE";
var timestamp = 0;
var INTERCALL_DELAY = 200; //0.3 sec
var FLASHLIGHT_NAME = "%%!!Survival.Kit.vr.flashlight!!%%";
tablet.screenChanged.connect(onScreenChanged);
var button = tablet.addButton({
text: APP_NAME,
icon: APP_ICON_INACTIVE,
activeIcon: APP_ICON_ACTIVE
});
var lightColor = {
"WHITE": {"red": 255, "green": 250, "blue": 230},
"AMBER": {"red": 255, "green": 145, "blue": 0},
"RED": {"red": 255, "green": 0, "blue": 0},
"BLUE": {"red": 0, "green": 119, "blue": 255}
};
function clicked(){
if (appStatus === true) {
tablet.webEventReceived.disconnect(onMoreAppWebEventReceived);
tablet.gotoHomeScreen();
Script.update.disconnect(myTimer);
appStatus = false;
}else{
Script.update.connect(myTimer);
var isFlashlightActive = "OFF";
if (flashLightID !== Uuid.NULL) {
isFlashlightActive = "ON";
}
var url = APP_URL + "?flashlight=" + isFlashlightActive + "&filter=" + filter;
tablet.gotoWebScreen(url);
tablet.webEventReceived.connect(onMoreAppWebEventReceived);
appStatus = true;
}
if (flashLightID === Uuid.NULL) {
button.editProperties({
isActive: appStatus
});
} else {
button.editProperties({
isActive: true
});
}
}
button.clicked.connect(clicked);
function onMoreAppWebEventReceived(message) {
var d = new Date();
var n = d.getTime();
if (typeof message === "string") {
var eventObj = JSON.parse(message);
if (eventObj.channel === channel) {
if (eventObj.action === "UPDATE_FLASHLIGHT_ACTIVATION" && (n - timestamp) > INTERCALL_DELAY) {
d = new Date();
timestamp = d.getTime();
if (eventObj.isActive === true) {
createFlashLight();
} else {
clearFlashLight();
}
} else if (eventObj.action === "UPDATE_FLASHLIGHT_FILTER" && (n - timestamp) > INTERCALL_DELAY) {
d = new Date();
timestamp = d.getTime();
filter = eventObj.filter;
updateFlashLightFilter();
}
}
}
}
function onScreenChanged(type, url) {
if (type === "Web" && url.indexOf(APP_URL) !== -1) {
appStatus = true;
Script.update.connect(myTimer);
} else {
appStatus = false;
if (url.indexOf(APP_URL) !== -1) {
Script.update.disconnect(myTimer);
}
}
if (flashLightID === Uuid.NULL) {
button.editProperties({
isActive: appStatus
});
} else {
button.editProperties({
isActive: true
});
}
}
function myTimer(deltaTime) {
var today = new Date();
if ((today.getTime() - processTimer) > UPDATE_TIMER_INTERVAL ) {
var azimuth = "" + (2000 - Math.floor(2000 * ((Quat.safeEulerAngles(MyAvatar.orientation).y + 180) / 360)));
var dataToUi = {
"channel": channel,
"action": "UPDATE_AZIMUTH",
"azimuth": azimuth
};
tablet.emitScriptEvent(JSON.stringify(dataToUi));
today = new Date();
processTimer = today.getTime();
}
}
function createFlashLight() {
var entityIDs = Entities.findEntitiesByName(FLASHLIGHT_NAME, MyAvatar.position, 100, false);
entityIDs.forEach(function (currentEntityID) {
var currentEntityOwner = Entities.getEntityProperties(currentEntityID, ['owningAvatarID']).owningAvatarID;
if (currentEntityOwner === MyAvatar.sessionUUID && currentEntityID !== flashLightID) {
Entities.deleteEntity(currentEntityID);
}
});
if (flashLightID === Uuid.NULL) {
flashLightID = Entities.addEntity({
"type": "Model",
"modelURL": ROOT + "vrFlashLight_" + filter + ".fst",
"name": FLASHLIGHT_NAME,
"lifetime": 28800,
"position": Vec3.sum(MyAvatar.position, Vec3.multiplyQbyV(MyAvatar.orientation, { x: 0, y: 0, z: -1 })),
"shapeType": "cylinder-z",
"grab": {
"grabbable": true
},
"rotation": MyAvatar.orientation
}, "avatar");
flashLightLightID = Entities.addEntity({
"parentID": flashLightID,
"type": "Light",
"name": "Flashlight-Light",
"dimensions": {"x": 192.8363, "y": 192.8363, "z": 300},
"color": lightColor[filter],
"intensity": 15,
"falloffRadius": 1,
"isSpotlight": true,
"exponent": 1,
"cutoff": 40,
"localPosition": {"x": 0, "y": 0, "z": -0.18}
}, "avatar");
}
}
function updateFlashLightFilter() {
if (flashLightID !== Uuid.NULL) {
Entities.editEntity(flashLightID, {"modelURL": ROOT + "vrFlashLight_" + filter + ".fst"});
Entities.editEntity(flashLightLightID, {"color": lightColor[filter]});
}
}
function clearFlashLight() {
if (flashLightID !== Uuid.NULL) {
Entities.deleteEntity(flashLightID);
flashLightID = Uuid.NULL;
flashLightLightID = Uuid.NULL;
}
}
function cleanup() {
if (appStatus) {
tablet.gotoHomeScreen();
tablet.webEventReceived.disconnect(onMoreAppWebEventReceived);
}
clearFlashLight();
tablet.screenChanged.disconnect(onScreenChanged);
tablet.removeButton(button);
Script.update.disconnect(myTimer);
}
Script.scriptEnding.connect(cleanup);
}());