mirror of
https://codeberg.org/vlw/still-alive.git
synced 2025-09-14 00:13:41 +02:00
Added functional code before manifest and CSS
The JS-part of this demo is now functional to the point where a Monkeydo manifest can be played on the different windows. CSS styling and an actual manifest will still have to be created.
This commit is contained in:
parent
cad5e2fb27
commit
3ef9e82d79
5 changed files with 90 additions and 72 deletions
93
assets/js/modules/WindowManager.mjs → assets/js/modules/PlayerManager.mjs
Executable file → Normal file
93
assets/js/modules/WindowManager.mjs → assets/js/modules/PlayerManager.mjs
Executable file → Normal file
|
@ -1,87 +1,36 @@
|
||||||
|
import { default as PlayerWindow } from "./PlayerWindow.mjs";
|
||||||
import { default as Monkeydo } from "./monkeydo/Monkeydo.mjs";
|
import { default as Monkeydo } from "./monkeydo/Monkeydo.mjs";
|
||||||
|
|
||||||
const windowPositions = {
|
|
||||||
"#lyrics": {
|
|
||||||
width: window.innerWidth / 2,
|
|
||||||
height: window.innerHeight,
|
|
||||||
top: 0,
|
|
||||||
left: 0
|
|
||||||
},
|
|
||||||
"#credits": {
|
|
||||||
width: window.innerWidth / 2,
|
|
||||||
height: window.innerHeight / 2,
|
|
||||||
top: 0,
|
|
||||||
left: window.innerWidth / 2
|
|
||||||
},
|
|
||||||
"#art": {
|
|
||||||
width: window.innerWidth / 2,
|
|
||||||
height: window.innerHeight / 2,
|
|
||||||
top: window.innerHeight / 2,
|
|
||||||
left: window.innerWidth / 2
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class PlayerWindow {
|
|
||||||
constructor(name) {
|
|
||||||
this.features = {
|
|
||||||
menubar: false,
|
|
||||||
location: false,
|
|
||||||
resizable: false,
|
|
||||||
scrollbar: false,
|
|
||||||
status: false
|
|
||||||
}
|
|
||||||
|
|
||||||
this.url = new URL(window.location.href + "player");
|
|
||||||
this.url.hash = name;
|
|
||||||
|
|
||||||
Object.assign(this.features,windowPositions[this.url.hash]);
|
|
||||||
}
|
|
||||||
|
|
||||||
windowFeatures() {
|
|
||||||
let output = [];
|
|
||||||
for(let [key,value] of Object.entries(this.features)) {
|
|
||||||
if(typeof key === "boolean") {
|
|
||||||
value = value ? "yes" : "no";
|
|
||||||
}
|
|
||||||
output.push(`${key}=${value}`);
|
|
||||||
}
|
|
||||||
return output.join(",");
|
|
||||||
}
|
|
||||||
|
|
||||||
open() {
|
|
||||||
const features = this.windowFeatures();
|
|
||||||
const open = window.open(this.url.toString(),this.url.hash,features);
|
|
||||||
|
|
||||||
if(!open) {
|
|
||||||
const channel = new BroadcastChannel(this.url.hash);
|
|
||||||
channel.postMessage(["WINDOW_ERROR",[this.url.hash,"BLOCKED"]]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export default class WindowManager {
|
export default class WindowManager {
|
||||||
constructor() {
|
constructor() {
|
||||||
const self = this;
|
const self = this;
|
||||||
|
|
||||||
// Bi-directional communcation to player windows
|
// Bi-directional communcation to player windows
|
||||||
this.channels = {
|
this.channels = {
|
||||||
lyrics: new BroadcastChannel("#lyrics"),
|
"#lyrics": new BroadcastChannel("#lyrics"),
|
||||||
credits: new BroadcastChannel("#credits"),
|
"#credits": new BroadcastChannel("#credits"),
|
||||||
art: new BroadcastChannel("#art")
|
"#art": new BroadcastChannel("#art")
|
||||||
};
|
};
|
||||||
|
|
||||||
// Monkeydo methods
|
// Monkeydo methods
|
||||||
const methods = {
|
const methods = {
|
||||||
self: self,
|
self: self,
|
||||||
pushText: (target,text) => {
|
blank: (target) => {
|
||||||
const channels = self.channels[target];
|
self.channels[target].postMessage(["BLANK",target]);
|
||||||
for(const channel of channels) {
|
},
|
||||||
channel.postMessage(["PUSH_TEXT",text]);
|
lineFeed: (target) => {
|
||||||
}
|
self.channels[target].postMessage(["LINE_FEED"]);
|
||||||
|
},
|
||||||
|
textFeed: (text,target = "#lyrics") => {
|
||||||
|
self.channels[target].postMessage(["TEXT_FEED",text]);
|
||||||
|
},
|
||||||
|
drawArt: (index,target = "#art") => {
|
||||||
|
self.channels[target].postMessage(["DRAW_ART",index]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
this.player = new Monkeydo(methods);
|
this.player = new Monkeydo(methods);
|
||||||
|
this.player.loop(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
playbackFailed(promiseObject = false) {
|
playbackFailed(promiseObject = false) {
|
||||||
|
@ -115,9 +64,9 @@ export default class WindowManager {
|
||||||
|
|
||||||
// Open player windows and start playback
|
// Open player windows and start playback
|
||||||
async play() {
|
async play() {
|
||||||
const art = this.spawnPlayer("art");
|
const art = this.spawnPlayer("#art");
|
||||||
const credits = this.spawnPlayer("credits");
|
const credits = this.spawnPlayer("#credits");
|
||||||
const lyrics = this.spawnPlayer("lyrics");
|
const lyrics = this.spawnPlayer("#lyrics");
|
||||||
|
|
||||||
const timeout = new Promise(resolve => setTimeout(() => resolve("TIMEOUT")),3000);
|
const timeout = new Promise(resolve => setTimeout(() => resolve("TIMEOUT")),3000);
|
||||||
const windows = await Promise.allSettled([lyrics,credits,art]);
|
const windows = await Promise.allSettled([lyrics,credits,art]);
|
||||||
|
@ -130,6 +79,10 @@ export default class WindowManager {
|
||||||
this.playbackFailed(promiseObject);
|
this.playbackFailed(promiseObject);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Load Monkeydo manifest and start playback
|
||||||
|
const manifest = new URL(window.location.href + "monkeydo.json");
|
||||||
|
this.player.load(manifest.toString()).then(() => this.player.do());
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
61
assets/js/modules/PlayerWindow.mjs
Normal file
61
assets/js/modules/PlayerWindow.mjs
Normal file
|
@ -0,0 +1,61 @@
|
||||||
|
const windowPositions = {
|
||||||
|
"#lyrics": {
|
||||||
|
width: window.innerWidth / 2,
|
||||||
|
height: window.innerHeight,
|
||||||
|
top: 0,
|
||||||
|
left: 0
|
||||||
|
},
|
||||||
|
"#credits": {
|
||||||
|
width: window.innerWidth / 2,
|
||||||
|
height: window.innerHeight / 2,
|
||||||
|
top: 0,
|
||||||
|
left: window.innerWidth / 2
|
||||||
|
},
|
||||||
|
"#art": {
|
||||||
|
width: window.innerWidth / 2,
|
||||||
|
height: window.innerHeight / 2,
|
||||||
|
top: window.innerHeight / 2,
|
||||||
|
left: window.innerWidth / 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export default class PlayerWindow {
|
||||||
|
constructor(name) {
|
||||||
|
this.features = {
|
||||||
|
menubar: false,
|
||||||
|
location: false,
|
||||||
|
resizable: false,
|
||||||
|
scrollbar: false,
|
||||||
|
status: false
|
||||||
|
}
|
||||||
|
|
||||||
|
this.url = new URL(window.location.href + "player");
|
||||||
|
this.url.hash = name;
|
||||||
|
|
||||||
|
// Copy window size rect into windowFeatures
|
||||||
|
Object.assign(this.features,windowPositions[this.url.hash]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Convert windowFeatures object into a CSV DOMString
|
||||||
|
windowFeatures() {
|
||||||
|
let output = [];
|
||||||
|
for(let [key,value] of Object.entries(this.features)) {
|
||||||
|
if(typeof key === "boolean") {
|
||||||
|
value = value ? "yes" : "no";
|
||||||
|
}
|
||||||
|
output.push(`${key}=${value}`);
|
||||||
|
}
|
||||||
|
return output.join(",");
|
||||||
|
}
|
||||||
|
|
||||||
|
open() {
|
||||||
|
const features = this.windowFeatures();
|
||||||
|
const open = window.open(this.url.toString(),this.url.hash,features);
|
||||||
|
|
||||||
|
// Window failed to open (usually due to pop-up blocking), tell the WindowManager about this
|
||||||
|
if(!open) {
|
||||||
|
const channel = new BroadcastChannel(this.url.hash);
|
||||||
|
channel.postMessage(["WINDOW_ERROR",[this.url.hash,"BLOCKED"]]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -51,10 +51,11 @@ class StillAlivePlayer {
|
||||||
message(event) {
|
message(event) {
|
||||||
const type = event.data[0];
|
const type = event.data[0];
|
||||||
const data = event.data[1];
|
const data = event.data[1];
|
||||||
|
console.log(event);
|
||||||
|
|
||||||
switch(type) {
|
switch(type) {
|
||||||
case "LINE_FEED": this.lineFeed(); break;
|
case "LINE_FEED": this.lineFeed(); break;
|
||||||
case "CHAR_FEED": this.textFeed(data); break;
|
case "TEXT_FEED": this.textFeed(data); break;
|
||||||
case "DRAW_ART": this.drawArt(data); break;
|
case "DRAW_ART": this.drawArt(data); break;
|
||||||
case "BLANK": this.blank(); break;
|
case "BLANK": this.blank(); break;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import { default as Player } from "./modules/WindowManager.mjs";
|
import { default as Player } from "./modules/PlayerManager.mjs";
|
||||||
|
|
||||||
const play = document.getElementById("play");
|
const play = document.getElementById("play");
|
||||||
const message = document.getElementById("message");
|
const message = document.getElementById("message");
|
||||||
|
|
3
monkeydo.json
Normal file
3
monkeydo.json
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
{
|
||||||
|
"tasks": []
|
||||||
|
}
|
Loading…
Add table
Reference in a new issue