wip: added menu
This commit is contained in:
parent
41a365200d
commit
f1254d7fed
|
@ -5,6 +5,7 @@ AFRAME.registerComponent('helloworld-html', {
|
||||||
|
|
||||||
init: function () {
|
init: function () {
|
||||||
|
|
||||||
|
this.el.addEventListener('ready', () => this.el.dom.style.display = 'none' )
|
||||||
},
|
},
|
||||||
|
|
||||||
requires:{
|
requires:{
|
||||||
|
@ -19,17 +20,12 @@ AFRAME.registerComponent('helloworld-html', {
|
||||||
</div>`,
|
</div>`,
|
||||||
|
|
||||||
css: `.helloworld-html {
|
css: `.helloworld-html {
|
||||||
color: var(--xrsh-dark-gray); /* see index.css */
|
color: var(--xrsh-light-gray); /* see index.css */
|
||||||
}
|
}`,
|
||||||
`,
|
|
||||||
},
|
},
|
||||||
|
|
||||||
events:{
|
events:{
|
||||||
|
|
||||||
// component events
|
|
||||||
html: function( ){ console.log("html-mesh requirement mounted") },
|
|
||||||
ready: function(e){ console.log("requires are loaded") },
|
|
||||||
|
|
||||||
// combined AFRAME+DOM reactive events
|
// combined AFRAME+DOM reactive events
|
||||||
keydown: function(e){ }, //
|
keydown: function(e){ }, //
|
||||||
click: function(e){
|
click: function(e){
|
||||||
|
@ -40,12 +36,18 @@ AFRAME.registerComponent('helloworld-html', {
|
||||||
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
||||||
|
|
||||||
|
|
||||||
DOMready: function( ){
|
ready: function( ){
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
console.log("this.el.dom has been added to DOM")
|
console.log("this.el.dom has been added to DOM")
|
||||||
this.el.dom.children[0].id = this.el.uid // important hint for html-mesh
|
this.el.dom.children[0].id = this.el.uid // important hint for html-mesh
|
||||||
this.data.myvalue = 1
|
this.data.myvalue = 1
|
||||||
setInterval( () => this.data.myvalue++, 100 )
|
setInterval( () => this.data.myvalue++, 100 )
|
||||||
}
|
},
|
||||||
|
|
||||||
|
launcher: function(){
|
||||||
|
this.el.dom.style.display = ''
|
||||||
|
console.log("launcher")
|
||||||
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -54,7 +56,7 @@ AFRAME.registerComponent('helloworld-html', {
|
||||||
"name": "Hello world",
|
"name": "Hello world",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/images/icons-vector.svg",
|
"src": "https://css.gg/browser.svg",
|
||||||
"type": "image/svg+xml",
|
"type": "image/svg+xml",
|
||||||
"sizes": "512x512"
|
"sizes": "512x512"
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,15 +3,12 @@ AFRAME.registerComponent('helloworld-htmlform', {
|
||||||
foo: { type:"string"}
|
foo: { type:"string"}
|
||||||
},
|
},
|
||||||
|
|
||||||
init: function () {
|
init: function () {},
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
requires:{
|
requires:{
|
||||||
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
||||||
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
stylis: "https://unpkg.com/stylis@4.3.1/dist/umd/stylis.js", // modern CSS (https://stylis.js.org)
|
|
||||||
},
|
},
|
||||||
|
|
||||||
dom: {
|
dom: {
|
||||||
|
@ -33,19 +30,15 @@ AFRAME.registerComponent('helloworld-htmlform', {
|
||||||
</fieldset>
|
</fieldset>
|
||||||
<button>hello</button>
|
<button>hello</button>
|
||||||
</div>`,
|
</div>`,
|
||||||
css: `.helloworld-htmlform {
|
|
||||||
div {
|
css: `.helloworld-htmlform > div { padding:11px; }`
|
||||||
padding:11px;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
`,
|
|
||||||
},
|
},
|
||||||
|
|
||||||
events:{
|
events:{
|
||||||
|
|
||||||
// component events
|
// component events
|
||||||
html: function( ){ console.log("html-mesh requirement mounted") },
|
html: function( ){ console.log("html-mesh requirement mounted") },
|
||||||
stylis: function( ){ console.log("stylis requirement mounted") },
|
|
||||||
|
|
||||||
// combined AFRAME+DOM reactive events
|
// combined AFRAME+DOM reactive events
|
||||||
click: function(e){ }, //
|
click: function(e){ }, //
|
||||||
|
@ -57,27 +50,26 @@ AFRAME.registerComponent('helloworld-htmlform', {
|
||||||
// reactive events for this.data updates
|
// reactive events for this.data updates
|
||||||
myvalue: function(e){ this.el.dom.querySelector('#myvalue').innerText = this.data.myvalue },
|
myvalue: function(e){ this.el.dom.querySelector('#myvalue').innerText = this.data.myvalue },
|
||||||
|
|
||||||
// requires are loaded
|
launcher: function(){
|
||||||
ready: function(e){
|
this.el.dom.style.display = ''
|
||||||
setTimeout( () => {
|
new WinBox("Hello World",{
|
||||||
new WinBox("Hello World",{
|
width: 250,
|
||||||
width: 250,
|
height: 315,
|
||||||
height: 315,
|
minwidth:250,
|
||||||
minwidth:250,
|
maxwidth:250,
|
||||||
maxwidth:250,
|
maxheight:315,
|
||||||
maxheight:315,
|
minheight:315,
|
||||||
minheight:315,
|
x: 100,
|
||||||
x: 100,
|
y: 100,
|
||||||
y: 100,
|
id: this.el.uid, // important hint for html-mesh
|
||||||
id: this.el.uid, // important hint for html-mesh
|
root: document.querySelector("#overlay"),
|
||||||
root: document.querySelector("#overlay"),
|
mount: this.el.dom,
|
||||||
mount: this.el.dom
|
onclose: () => { this.el.dom.style.display = 'none'; return false; }
|
||||||
});
|
});
|
||||||
},500) /*FIXME*/
|
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
DOMready: function( ){
|
ready: function( ){
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
console.log("this.el.dom has been added to DOM")
|
console.log("this.el.dom has been added to DOM")
|
||||||
this.data.myvalue = 1
|
this.data.myvalue = 1
|
||||||
}
|
}
|
||||||
|
@ -89,7 +81,7 @@ AFRAME.registerComponent('helloworld-htmlform', {
|
||||||
"name": "Hello world",
|
"name": "Hello world",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/images/icons-vector.svg",
|
"src": "https://css.gg/browser.svg",
|
||||||
"type": "image/svg+xml",
|
"type": "image/svg+xml",
|
||||||
"sizes": "512x512"
|
"sizes": "512x512"
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,15 +3,12 @@ AFRAME.registerComponent('helloworld-window', {
|
||||||
foo: { type:"string"}
|
foo: { type:"string"}
|
||||||
},
|
},
|
||||||
|
|
||||||
init: function () {
|
init: function(){},
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
requires:{
|
requires:{
|
||||||
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
||||||
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", //
|
||||||
stylis: "https://unpkg.com/stylis@4.3.1/dist/umd/stylis.js", // modern CSS (https://stylis.js.org)
|
|
||||||
},
|
},
|
||||||
|
|
||||||
dom: {
|
dom: {
|
||||||
|
@ -20,12 +17,8 @@ AFRAME.registerComponent('helloworld-window', {
|
||||||
html: (me) => `<div>
|
html: (me) => `<div>
|
||||||
<div class="pad"> ${me.data.foo} <b>${me.data.myvalue}</b></span>
|
<div class="pad"> ${me.data.foo} <b>${me.data.myvalue}</b></span>
|
||||||
</div>`,
|
</div>`,
|
||||||
css: `.helloworld-window {
|
|
||||||
div {
|
css: `.helloworld-window div.pad { padding:11px; }`
|
||||||
.pad { padding:11px; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
`,
|
|
||||||
},
|
},
|
||||||
|
|
||||||
events:{
|
events:{
|
||||||
|
@ -41,28 +34,27 @@ AFRAME.registerComponent('helloworld-window', {
|
||||||
// reactive events for this.data updates
|
// reactive events for this.data updates
|
||||||
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
||||||
|
|
||||||
// requires are loaded
|
ready: function( ){
|
||||||
ready: function(e){
|
this.el.dom.style.display = 'none'
|
||||||
|
|
||||||
setTimeout( () => {
|
|
||||||
new WinBox("Hello World",{
|
|
||||||
width: 250,
|
|
||||||
height: 150,
|
|
||||||
x:"center",
|
|
||||||
y:"center",
|
|
||||||
id: this.el.uid, // important hint for html-mesh
|
|
||||||
root: document.querySelector("#overlay"),
|
|
||||||
mount: this.el.dom
|
|
||||||
});
|
|
||||||
}, 500 )
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
DOMready: function( ){
|
|
||||||
console.log("this.el.dom has been added to DOM")
|
console.log("this.el.dom has been added to DOM")
|
||||||
this.data.myvalue = 1
|
this.data.myvalue = 1
|
||||||
setInterval( () => this.data.myvalue++, 100 )
|
setInterval( () => this.data.myvalue++, 100 )
|
||||||
}
|
},
|
||||||
|
|
||||||
|
launcher: function(){
|
||||||
|
console.log("this.el.dom has been added to DOM")
|
||||||
|
new WinBox("Hello World",{
|
||||||
|
width: 250,
|
||||||
|
height: 150,
|
||||||
|
x:"center",
|
||||||
|
y:"center",
|
||||||
|
id: this.el.uid, // important hint for html-mesh
|
||||||
|
root: document.querySelector("#overlay"),
|
||||||
|
mount: this.el.dom,
|
||||||
|
onclose: () => { this.el.dom.style.display = 'none'; return false; }
|
||||||
|
});
|
||||||
|
this.el.dom.style.display = ''
|
||||||
|
},
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -71,7 +63,7 @@ AFRAME.registerComponent('helloworld-window', {
|
||||||
"name": "Hello world",
|
"name": "Hello world",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/images/icons-vector.svg",
|
"src": "https://css.gg/browser.svg",
|
||||||
"type": "image/svg+xml",
|
"type": "image/svg+xml",
|
||||||
"sizes": "512x512"
|
"sizes": "512x512"
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,8 +3,12 @@ AFRAME.registerComponent('helloworld', {
|
||||||
foo: { type:"string"}
|
foo: { type:"string"}
|
||||||
},
|
},
|
||||||
|
|
||||||
init: function () {
|
init: function () {
|
||||||
|
this.el.object3D.visible = false
|
||||||
this.el.setAttribute("geometry","primitive: octahedron")
|
this.el.setAttribute("geometry","primitive: octahedron")
|
||||||
|
this.interval = setInterval( () => {
|
||||||
|
this.data.myvalue = ((this.data.myvalue||1.0) + 0.25) % 1
|
||||||
|
}, 400 )
|
||||||
},
|
},
|
||||||
|
|
||||||
requires:{
|
requires:{
|
||||||
|
@ -17,6 +21,13 @@ AFRAME.registerComponent('helloworld', {
|
||||||
somecomponent: function( ){ console.log("component requirement mounted") },
|
somecomponent: function( ){ console.log("component requirement mounted") },
|
||||||
ready: function(e){ console.log("requires are loaded") },
|
ready: function(e){ console.log("requires are loaded") },
|
||||||
|
|
||||||
|
launcher: function(e){
|
||||||
|
this.el.object3D.visible = !this.el.object3D.visible
|
||||||
|
},
|
||||||
|
|
||||||
|
// reactive this.data value demo
|
||||||
|
myvalue:function( ){ this.el.object3D.children[0].scale.y = this.data.myvalue }
|
||||||
|
|
||||||
},
|
},
|
||||||
|
|
||||||
manifest: { // HTML5 manifest to identify app to xrsh
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
@ -24,7 +35,7 @@ AFRAME.registerComponent('helloworld', {
|
||||||
"name": "Hello world",
|
"name": "Hello world",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/images/icons-vector.svg",
|
"src": "https://css.gg/shape-hexagon.svg",
|
||||||
"type": "image/svg+xml",
|
"type": "image/svg+xml",
|
||||||
"sizes": "512x512"
|
"sizes": "512x512"
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,110 @@
|
||||||
|
AFRAME.registerComponent('isoterminal', {
|
||||||
|
schema: {
|
||||||
|
foo: { type:"string"}
|
||||||
|
},
|
||||||
|
|
||||||
|
init: function(){},
|
||||||
|
|
||||||
|
requires:{
|
||||||
|
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
||||||
|
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
|
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", //
|
||||||
|
},
|
||||||
|
|
||||||
|
dom: {
|
||||||
|
scale: 3,
|
||||||
|
events: ['click','keydown'],
|
||||||
|
html: (me) => `<div>
|
||||||
|
<div class="pad">to be implemented</span>
|
||||||
|
</div>`,
|
||||||
|
|
||||||
|
css: `.helloworld-window div.pad { padding:11px; }`
|
||||||
|
},
|
||||||
|
|
||||||
|
events:{
|
||||||
|
|
||||||
|
// combined AFRAME+DOM reactive events
|
||||||
|
click: function(e){ }, //
|
||||||
|
keydown: function(e){ }, //
|
||||||
|
|
||||||
|
// reactive events for this.data updates
|
||||||
|
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
||||||
|
|
||||||
|
ready: function( ){
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
|
},
|
||||||
|
|
||||||
|
launcher: function(){
|
||||||
|
new WinBox( this.manifest.iso + ' ' + this.manifest.name, {
|
||||||
|
width: '70%',
|
||||||
|
height: '80%',
|
||||||
|
x:"center",
|
||||||
|
y:"center",
|
||||||
|
id: this.el.uid, // important hint for html-mesh
|
||||||
|
root: document.querySelector("#overlay"),
|
||||||
|
mount: this.el.dom,
|
||||||
|
onclose: () => {
|
||||||
|
if( !confirm('do you want to kill this virtual machine and all its processes?') ) return true
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
});
|
||||||
|
this.el.dom.style.display = ''
|
||||||
|
},
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
"iso": "linux-x64-4.15.iso",
|
||||||
|
"short_name": "ISOTerm",
|
||||||
|
"name": "terminal",
|
||||||
|
"icons": [
|
||||||
|
{
|
||||||
|
"src": "https://css.gg/terminal.svg",
|
||||||
|
"type": "image/svg+xml",
|
||||||
|
"sizes": "512x512"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"id": "/?source=pwa",
|
||||||
|
"start_url": "/?source=pwa",
|
||||||
|
"background_color": "#3367D6",
|
||||||
|
"display": "standalone",
|
||||||
|
"scope": "/",
|
||||||
|
"theme_color": "#3367D6",
|
||||||
|
"shortcuts": [
|
||||||
|
{
|
||||||
|
"name": "What is the latest news?",
|
||||||
|
"cli":{
|
||||||
|
"usage": "helloworld <type> [options]",
|
||||||
|
"example": "helloworld news",
|
||||||
|
"args":{
|
||||||
|
"--latest": {type:"string"}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"short_name": "Today",
|
||||||
|
"description": "View weather information for today",
|
||||||
|
"url": "/today?source=pwa",
|
||||||
|
"icons": [{ "src": "/images/today.png", "sizes": "192x192" }]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Hello world information",
|
||||||
|
"screenshots": [
|
||||||
|
{
|
||||||
|
"src": "/images/screenshot1.png",
|
||||||
|
"type": "image/png",
|
||||||
|
"sizes": "540x720",
|
||||||
|
"form_factor": "narrow"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"help":`
|
||||||
|
Helloworld application
|
||||||
|
|
||||||
|
This is a help file which describes the application.
|
||||||
|
It will be rendered thru troika text, and will contain
|
||||||
|
headers based on non-punctualized lines separated by linebreaks,
|
||||||
|
in above's case "\nHelloworld application\n" will qualify as header.
|
||||||
|
`
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
|
|
@ -0,0 +1,185 @@
|
||||||
|
/*
|
||||||
|
* ## launcher
|
||||||
|
*
|
||||||
|
* displays app (icons) for enduser to launch
|
||||||
|
*
|
||||||
|
* ```javascript
|
||||||
|
* <a-entity app="app/launcher.js"/>
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* | property | type | example |
|
||||||
|
* |--------------|--------------------|----------------------------------------------------------------------------------------|
|
||||||
|
* | `registries` | `array` of strings | <a-entity app="app/launcher.js; registers: https://foo.com/index.json, ./index.json"/> |
|
||||||
|
*
|
||||||
|
* | event | target | info |
|
||||||
|
* |--------------|-------------------------------------------------------------------------------------------------------------|
|
||||||
|
* | `launcher` | an app | when pressing an app icon, `launcher` event will be send to the respective app |
|
||||||
|
*/
|
||||||
|
|
||||||
|
AFRAME.registerComponent('launcher', {
|
||||||
|
schema: {
|
||||||
|
foo: { type:"string"}
|
||||||
|
},
|
||||||
|
|
||||||
|
init: function () {
|
||||||
|
this.data.apps = []
|
||||||
|
|
||||||
|
AFRAME.scenes.map( (scene) => {
|
||||||
|
scene.addEventListener('app:ready', (e) => this.render(e.detail) )
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
requires:{
|
||||||
|
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
||||||
|
},
|
||||||
|
|
||||||
|
dom: {
|
||||||
|
scale: 3,
|
||||||
|
events: ['click'],
|
||||||
|
html: (me) => `<div>
|
||||||
|
<div class="iconmenu"></div>
|
||||||
|
</div>`,
|
||||||
|
|
||||||
|
css: `#iconmenu {
|
||||||
|
z-index: 1000;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column-reverse;
|
||||||
|
align-items: flex-end;
|
||||||
|
height: 100%;
|
||||||
|
position: fixed;
|
||||||
|
top: 0px;
|
||||||
|
right: 20px;
|
||||||
|
bottom: 0;
|
||||||
|
padding-bottom: 72px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
#iconmenu > button {
|
||||||
|
pointer-events:all;
|
||||||
|
width: 58px;
|
||||||
|
height: 39px;
|
||||||
|
padding: 12px 0px 20px 0px;
|
||||||
|
border-radius: 0px;
|
||||||
|
color: var(--xrsh-primary);
|
||||||
|
background: #FFF;
|
||||||
|
border-left: 5px solid var(--xrsh-primary);
|
||||||
|
border-right: 5px solid var(--xrsh-primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
#iconmenu > button:first-child {
|
||||||
|
border-radius:0px 0px 30px 30px;
|
||||||
|
border-bottom: 5px solid var(--xrsh-primary);
|
||||||
|
padding-bottom:35px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#iconmenu > button:last-child {
|
||||||
|
border-radius:30px 30px 0px 0px;
|
||||||
|
border-top: 5px solid var(--xrsh-primary);
|
||||||
|
padding-top:13px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#iconmenu > button > img {
|
||||||
|
transform: translate(0px,-5px);
|
||||||
|
opacity:0.5;
|
||||||
|
padding: 5px;
|
||||||
|
border-radius: 0px;
|
||||||
|
}
|
||||||
|
#iconmenu > button > img:hover,
|
||||||
|
#iconmenu > button.enable > img {
|
||||||
|
border:2px solid #444;
|
||||||
|
transition:0.gg3s;
|
||||||
|
border-radius: 50%;
|
||||||
|
}`
|
||||||
|
},
|
||||||
|
|
||||||
|
events:{
|
||||||
|
|
||||||
|
// combined AFRAME+DOM reactive events
|
||||||
|
click: function(e){
|
||||||
|
console.dir(e)
|
||||||
|
}, //
|
||||||
|
|
||||||
|
|
||||||
|
ready: function( ){
|
||||||
|
this.el.dom.children[0].id = this.el.uid // important hint for html-mesh
|
||||||
|
},
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
render: function(app){
|
||||||
|
clearTimeout(this.timeout)
|
||||||
|
this.timeout = setTimeout( () => {
|
||||||
|
AFRAME.app.foreach( (app) => {
|
||||||
|
console.dir(app)
|
||||||
|
if( !app.manifest ) return
|
||||||
|
|
||||||
|
console.log("--rendering button")
|
||||||
|
return
|
||||||
|
let btn = app.btn = document.createElement('button')
|
||||||
|
if( app.manifest.icons?.length > 0){
|
||||||
|
let img = document.createElement('img')
|
||||||
|
img.src = app.manifest.icons[0].src
|
||||||
|
img.alt = app.manifest.name
|
||||||
|
btn.appendChild(img)
|
||||||
|
}else btn.innerText = app.manifest.short_name
|
||||||
|
btn.addEventListener('click', () => {
|
||||||
|
app.el.emit('launcher',app)
|
||||||
|
})
|
||||||
|
this.el.dom.querySelector('#iconmenu').appendChild(btn)
|
||||||
|
})
|
||||||
|
},200)
|
||||||
|
},
|
||||||
|
|
||||||
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
"short_name": "Hello world",
|
||||||
|
"name": "Hello world",
|
||||||
|
"icons": [
|
||||||
|
{
|
||||||
|
"src": "https://css.gg/browser.svg",
|
||||||
|
"type": "image/svg+xml",
|
||||||
|
"sizes": "512x512"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"id": "/?source=pwa",
|
||||||
|
"start_url": "/?source=pwa",
|
||||||
|
"background_color": "#3367D6",
|
||||||
|
"display": "standalone",
|
||||||
|
"scope": "/",
|
||||||
|
"theme_color": "#3367D6",
|
||||||
|
"shortcuts": [
|
||||||
|
{
|
||||||
|
"name": "What is the latest news?",
|
||||||
|
"cli":{
|
||||||
|
"usage": "helloworld <type> [options]",
|
||||||
|
"example": "helloworld news",
|
||||||
|
"args":{
|
||||||
|
"--latest": {type:"string"}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"short_name": "Today",
|
||||||
|
"description": "View weather information for today",
|
||||||
|
"url": "/today?source=pwa",
|
||||||
|
"icons": [{ "src": "/images/today.png", "sizes": "192x192" }]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Hello world information",
|
||||||
|
"screenshots": [
|
||||||
|
{
|
||||||
|
"src": "/images/screenshot1.png",
|
||||||
|
"type": "image/png",
|
||||||
|
"sizes": "540x720",
|
||||||
|
"form_factor": "narrow"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"help":`
|
||||||
|
Helloworld application
|
||||||
|
|
||||||
|
This is a help file which describes the application.
|
||||||
|
It will be rendered thru troika text, and will contain
|
||||||
|
headers based on non-punctualized lines separated by linebreaks,
|
||||||
|
in above's case "\nHelloworld application\n" will qualify as header.
|
||||||
|
`
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
|
|
@ -4,14 +4,14 @@ AFRAME.registerComponent('manual', {
|
||||||
},
|
},
|
||||||
|
|
||||||
init: function () {
|
init: function () {
|
||||||
//AFRAME.XRF.navigator.to("https://coderofsalvation.github.io/xrsh-media/assets/background.glb")
|
// requires are loaded
|
||||||
|
this.el.addEventListener('ready', () => this.el.dom.style.display = 'none' )
|
||||||
},
|
},
|
||||||
|
|
||||||
requires:{
|
requires:{
|
||||||
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
html: "https://unpkg.com/aframe-htmlmesh@2.1.0/build/aframe-html.js", // html to AFRAME
|
||||||
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxjs: "https://unpkg.com/winbox@0.2.82/dist/winbox.bundle.min.js", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", // deadsimple windows: https://nextapps-de.github.io/winbox
|
winboxcss: "https://unpkg.com/winbox@0.2.82/dist/css/winbox.min.css", // deadsimple windows: https://nextapps-de.github.io/winbox
|
||||||
xrfragments: "https://xrfragment.org/dist/xrfragment.aframe.js",
|
|
||||||
},
|
},
|
||||||
|
|
||||||
dom: {
|
dom: {
|
||||||
|
@ -35,19 +35,13 @@ AFRAME.registerComponent('manual', {
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
</div>`,
|
</div>`,
|
||||||
css: `.manual {
|
css: `.manual > div { padding:11px }`
|
||||||
div {
|
|
||||||
padding:11px;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
`,
|
|
||||||
},
|
},
|
||||||
|
|
||||||
events:{
|
events:{
|
||||||
|
|
||||||
// component events
|
// component events
|
||||||
html: function( ){ console.log("html-mesh requirement mounted") },
|
html: function( ){ console.log("html-mesh requirement mounted") },
|
||||||
stylis: function( ){ console.log("stylis requirement mounted") },
|
|
||||||
|
|
||||||
// combined AFRAME+DOM reactive events
|
// combined AFRAME+DOM reactive events
|
||||||
click: function(e){ }, //
|
click: function(e){ }, //
|
||||||
|
@ -56,26 +50,24 @@ AFRAME.registerComponent('manual', {
|
||||||
// reactive events for this.data updates
|
// reactive events for this.data updates
|
||||||
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
myvalue: function(e){ this.el.dom.querySelector('b').innerText = this.data.myvalue },
|
||||||
|
|
||||||
// requires are loaded
|
launcher: function(){
|
||||||
ready: function(e){
|
new WinBox( this.manifest.name, {
|
||||||
|
width: '70%',
|
||||||
setTimeout( () => {
|
height: '70%',
|
||||||
new WinBox("XRSH manual",{
|
x:"center",
|
||||||
width:300,
|
y:"center",
|
||||||
height:300,
|
id: this.el.uid, // important hint for html-mesh
|
||||||
x:"center",
|
root: document.querySelector("#overlay"),
|
||||||
y:"center",
|
mount: this.el.dom,
|
||||||
id: this.el.uid, // important hint for html-mesh
|
onclose: () => { this.el.dom.style.display = 'none'; return false; }
|
||||||
root: document.querySelector("#overlay"),
|
});
|
||||||
mount: this.el.dom
|
this.el.dom.style.display = ''
|
||||||
});
|
this.el.setAttribute("xrf", document.location.search || "https://coderofsalvation.github.io/xrsh-media/assets/background.glb")
|
||||||
}, 500 )
|
|
||||||
|
|
||||||
this.el.setAttribute("xrf","https://coderofsalvation.github.io/xrsh-media/assets/background.glb")
|
|
||||||
// navigate with: AFRAME.XRF.navigator.to("https://xrfragment.org/index.glb")
|
// navigate with: AFRAME.XRF.navigator.to("https://xrfragment.org/index.glb")
|
||||||
},
|
},
|
||||||
|
|
||||||
DOMready: function( ){
|
DOMready: function( ){
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
console.log("this.el.dom has been added to DOM")
|
console.log("this.el.dom has been added to DOM")
|
||||||
this.data.myvalue = 1
|
this.data.myvalue = 1
|
||||||
setInterval( () => this.data.myvalue++, 100 )
|
setInterval( () => this.data.myvalue++, 100 )
|
||||||
|
@ -84,11 +76,11 @@ AFRAME.registerComponent('manual', {
|
||||||
},
|
},
|
||||||
|
|
||||||
manifest: { // HTML5 manifest to identify app to xrsh
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
"short_name": "Hello world",
|
"short_name": "XRSH Manual",
|
||||||
"name": "Hello world",
|
"name": "XRSH Manual",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/images/icons-vector.svg",
|
"src": "https://css.gg/coffee.svg",
|
||||||
"type": "image/svg+xml",
|
"type": "image/svg+xml",
|
||||||
"sizes": "512x512"
|
"sizes": "512x512"
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,89 @@
|
||||||
|
AFRAME.registerComponent('spatialize', {
|
||||||
|
schema: {
|
||||||
|
foo: { type:"string"}
|
||||||
|
},
|
||||||
|
|
||||||
|
init: function () {
|
||||||
|
|
||||||
|
document.querySelector('a-scene').addEventListener('enter-vr',() => this.toggle(true) )
|
||||||
|
document.querySelector('a-scene').addEventListener('exit-vr', () => this.toggle(false) )
|
||||||
|
// toggle immersive with ESCAPE
|
||||||
|
document.body.addEventListener('keydown', (e) => e.key == 'Escape' && this.toggle() )
|
||||||
|
},
|
||||||
|
|
||||||
|
requires:{
|
||||||
|
// somecomponent: "https://unpkg.com/some-aframe-component/mycom.min.js"
|
||||||
|
},
|
||||||
|
|
||||||
|
events:{
|
||||||
|
|
||||||
|
// component events
|
||||||
|
ready: function(e){
|
||||||
|
this.btn.style.background = 'var(--xrsh-primary)'
|
||||||
|
},
|
||||||
|
|
||||||
|
launcher: function(e){ this.toggle() },
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
// draw a button so we can toggle apps between 2D / XR
|
||||||
|
toggle: function(state){
|
||||||
|
state = state || !document.body.className.match(/XR/)
|
||||||
|
document.body.classList[ state ? 'add' : 'remove'](['XR'])
|
||||||
|
AFRAME.scenes[0].emit( state ? 'apps:XR' : 'apps:2D')
|
||||||
|
this.btn.classList.toggle('enable')
|
||||||
|
},
|
||||||
|
|
||||||
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
"short_name": "spatialize",
|
||||||
|
"name": "spatialize",
|
||||||
|
"icons": [
|
||||||
|
{
|
||||||
|
"src": "https://css.gg/stack.svg",
|
||||||
|
"type": "image/svg+xml",
|
||||||
|
"sizes": "512x512"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"id": "/?source=pwa",
|
||||||
|
"start_url": "/?source=pwa",
|
||||||
|
"background_color": "#3367D6",
|
||||||
|
"display": "standalone",
|
||||||
|
"scope": "/",
|
||||||
|
"theme_color": "#3367D6",
|
||||||
|
"shortcuts": [
|
||||||
|
{
|
||||||
|
"name": "What is the latest news?",
|
||||||
|
"cli":{
|
||||||
|
"usage": "helloworld <type> [options]",
|
||||||
|
"example": "helloworld news",
|
||||||
|
"args":{
|
||||||
|
"--latest": {type:"string"}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"short_name": "Today",
|
||||||
|
"description": "View weather information for today",
|
||||||
|
"url": "/today?source=pwa",
|
||||||
|
"icons": [{ "src": "/images/today.png", "sizes": "192x192" }]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Hello world information",
|
||||||
|
"screenshots": [
|
||||||
|
{
|
||||||
|
"src": "/images/screenshot1.png",
|
||||||
|
"type": "image/png",
|
||||||
|
"sizes": "540x720",
|
||||||
|
"form_factor": "narrow"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"help":`
|
||||||
|
Helloworld application
|
||||||
|
|
||||||
|
This is a help file which describes the application.
|
||||||
|
It will be rendered thru troika text, and will contain
|
||||||
|
headers based on non-punctualized lines separated by linebreaks,
|
||||||
|
in above's case "\nHelloworld application\n" will qualify as header.
|
||||||
|
`
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
|
|
@ -0,0 +1,94 @@
|
||||||
|
AFRAME.registerComponent('vconsole', {
|
||||||
|
schema: {
|
||||||
|
foo: { type:"string"}
|
||||||
|
},
|
||||||
|
|
||||||
|
init: function () {
|
||||||
|
//AFRAME.XRF.navigator.to("https://coderofsalvation.github.io/xrsh-media/assets/background.glb")
|
||||||
|
document.head.innerHTML += `
|
||||||
|
<style type="text/css">
|
||||||
|
.vc-mask { display: none !important }
|
||||||
|
.vc-switch { display: none !important }
|
||||||
|
.vc-panel {
|
||||||
|
right:unset !important;
|
||||||
|
width:100%;
|
||||||
|
max-width:600px;
|
||||||
|
z-index:100 !important;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
`
|
||||||
|
},
|
||||||
|
|
||||||
|
requires:{
|
||||||
|
vconsole: "https://unpkg.com/vconsole@latest/dist/vconsole.min.js"
|
||||||
|
},
|
||||||
|
|
||||||
|
events:{
|
||||||
|
|
||||||
|
// requires are loaded
|
||||||
|
ready: function(e){
|
||||||
|
this.vConsole = new window.VConsole()
|
||||||
|
document.querySelector('.vc-mask').remove()
|
||||||
|
document.querySelector('.vc-switch').remove()
|
||||||
|
},
|
||||||
|
|
||||||
|
launcher: function(){
|
||||||
|
let panel = document.querySelector('.vc-panel')
|
||||||
|
if( panel.style.display == 'none' ) this.vConsole.show()
|
||||||
|
else this.vConsole.hide()
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
"short_name": "Hello world",
|
||||||
|
"name": "Hello world",
|
||||||
|
"icons": [
|
||||||
|
{
|
||||||
|
"src": "https://css.gg/border-bottom.svg",
|
||||||
|
"type": "image/svg+xml",
|
||||||
|
"sizes": "512x512"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"id": "/?source=pwa",
|
||||||
|
"start_url": "/?source=pwa",
|
||||||
|
"background_color": "#3367D6",
|
||||||
|
"display": "standalone",
|
||||||
|
"scope": "/",
|
||||||
|
"theme_color": "#3367D6",
|
||||||
|
"shortcuts": [
|
||||||
|
{
|
||||||
|
"name": "What is the latest news?",
|
||||||
|
"cli":{
|
||||||
|
"usage": "helloworld <type> [options]",
|
||||||
|
"example": "helloworld news",
|
||||||
|
"args":{
|
||||||
|
"--latest": {type:"string"}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"short_name": "Today",
|
||||||
|
"description": "View weather information for today",
|
||||||
|
"url": "/today?source=pwa",
|
||||||
|
"icons": [{ "src": "/images/today.png", "sizes": "192x192" }]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Hello world information",
|
||||||
|
"screenshots": [
|
||||||
|
{
|
||||||
|
"src": "/images/screenshot1.png",
|
||||||
|
"type": "image/png",
|
||||||
|
"sizes": "540x720",
|
||||||
|
"form_factor": "narrow"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"help":`
|
||||||
|
Helloworld application
|
||||||
|
|
||||||
|
This is a help file which describes the application.
|
||||||
|
It will be rendered thru troika text, and will contain
|
||||||
|
headers based on non-punctualized lines separated by linebreaks,
|
||||||
|
in above's case "\nHelloworld application\n" will qualify as header.
|
||||||
|
`
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
|
|
@ -0,0 +1,73 @@
|
||||||
|
AFRAME.registerComponent('xrfragments', {
|
||||||
|
schema: {
|
||||||
|
url: { type:"string"}
|
||||||
|
},
|
||||||
|
|
||||||
|
init: function () {
|
||||||
|
},
|
||||||
|
|
||||||
|
requires:{
|
||||||
|
xrfragments: "https://xrfragment.org/dist/xrfragment.aframe.js",
|
||||||
|
},
|
||||||
|
|
||||||
|
events:{
|
||||||
|
|
||||||
|
// requires are loaded
|
||||||
|
ready: function(e){
|
||||||
|
this.el.setAttribute("xrf","https://coderofsalvation.github.io/xrsh-media/assets/background.glb")
|
||||||
|
},
|
||||||
|
|
||||||
|
launcher: function(){
|
||||||
|
let url = prompt('enter URL to glb/fbx/json/obj/usdz asset', 'https://xrfragment.org/index.glb')
|
||||||
|
if( url ) AFRAME.XRF.navigator.to(url)
|
||||||
|
}
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
manifest: { // HTML5 manifest to identify app to xrsh
|
||||||
|
"short_name": "XRF",
|
||||||
|
"name": "XR Fragment URL",
|
||||||
|
"icons": [ ],
|
||||||
|
"id": "/?source=pwa",
|
||||||
|
"start_url": "/?source=pwa",
|
||||||
|
"background_color": "#3367D6",
|
||||||
|
"display": "standalone",
|
||||||
|
"scope": "/",
|
||||||
|
"theme_color": "#3367D6",
|
||||||
|
"shortcuts": [
|
||||||
|
{
|
||||||
|
"name": "What is the latest news?",
|
||||||
|
"cli":{
|
||||||
|
"usage": "helloworld <type> [options]",
|
||||||
|
"example": "helloworld news",
|
||||||
|
"args":{
|
||||||
|
"--latest": {type:"string"}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"short_name": "Today",
|
||||||
|
"description": "View weather information for today",
|
||||||
|
"url": "/today?source=pwa",
|
||||||
|
"icons": [{ "src": "/images/today.png", "sizes": "192x192" }]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Hello world information",
|
||||||
|
"screenshots": [
|
||||||
|
{
|
||||||
|
"src": "/images/screenshot1.png",
|
||||||
|
"type": "image/png",
|
||||||
|
"sizes": "540x720",
|
||||||
|
"form_factor": "narrow"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"help":`
|
||||||
|
Helloworld application
|
||||||
|
|
||||||
|
This is a help file which describes the application.
|
||||||
|
It will be rendered thru troika text, and will contain
|
||||||
|
headers based on non-punctualized lines separated by linebreaks,
|
||||||
|
in above's case "\nHelloworld application\n" will qualify as header.
|
||||||
|
`
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
|
98
com/app.js
98
com/app.js
|
@ -28,7 +28,18 @@ AFRAME.registerComponent('app', {
|
||||||
AFRAME.app[component].map( (app) => {
|
AFRAME.app[component].map( (app) => {
|
||||||
if( !app.el.getAttribute(component) ) app.el.setAttribute(component,app.data)
|
if( !app.el.getAttribute(component) ) app.el.setAttribute(component,app.data)
|
||||||
})
|
})
|
||||||
}
|
},
|
||||||
|
"requires:ready": function(){
|
||||||
|
let {id,component,type} = this.parseAppURI(this.data.uri)
|
||||||
|
AFRAME.app[component].map( (app) => {
|
||||||
|
if( app.readyFired ) return
|
||||||
|
setTimeout( () => {
|
||||||
|
if( this.el.dom ) this.el.dom.style.display = '' // finally show dom elements
|
||||||
|
app.el.emit('ready')
|
||||||
|
app.readyFired = true
|
||||||
|
},400) // big js scripts need some parsing time
|
||||||
|
})
|
||||||
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
init: function() {
|
init: function() {
|
||||||
|
@ -83,7 +94,9 @@ AFRAME.registerComponent('app', {
|
||||||
}
|
}
|
||||||
}catch(e){ console.error(`package ${package} could not be retrieved..aborting :(`); throw e; }
|
}catch(e){ console.error(`package ${package} could not be retrieved..aborting :(`); throw e; }
|
||||||
})
|
})
|
||||||
Promise.all(deps).then( () => this.el.emit( readyEvent||'ready', packages) )
|
Promise.all(deps).then( () => {
|
||||||
|
this.el.emit( readyEvent || 'requireReady', packages)
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
})
|
})
|
||||||
|
@ -109,39 +122,50 @@ AFRAME.AComponent.prototype.updateProperties = function(updateProperties){
|
||||||
return function(){
|
return function(){
|
||||||
updateProperties.apply(this,arguments)
|
updateProperties.apply(this,arguments)
|
||||||
|
|
||||||
|
if( !this.data || !this.data.uri ) return // only deal with apps
|
||||||
|
|
||||||
const reactify = (el,aframe) => new Proxy(this.data,{
|
// ensure overlay
|
||||||
get(me,k,v) { return me[k]
|
let overlay = document.querySelector('#overlay')
|
||||||
},
|
if( !overlay ){
|
||||||
set(me,k,v){
|
overlay = document.createElement('div')
|
||||||
me[k] = v
|
overlay.id = "overlay"
|
||||||
aframe.emit(k,{el,k,v})
|
document.body.appendChild(overlay)
|
||||||
}
|
document.querySelector("a-scene").setAttribute("webxr","overlayElement:#overlay")
|
||||||
})
|
let menu = document.createElement('div')
|
||||||
|
menu.id = 'iconmenu'
|
||||||
|
document.body.appendChild(menu)
|
||||||
|
}
|
||||||
|
|
||||||
if( !this.data ) return
|
// add menu button
|
||||||
|
if( this.manifest && this.manifest.icons ){
|
||||||
|
let btn = document.createElement('button')
|
||||||
|
btn.app = this
|
||||||
|
if( this.manifest.icons.length ){
|
||||||
|
btn.innerHTML = `<img src="${this.manifest.icons[0].src}"/>`
|
||||||
|
}else btn.innerText = this.manifest.short_name
|
||||||
|
btn.setAttribute("alt", this.manifest.name )
|
||||||
|
btn.addEventListener('click', (e) => this.el.emit('launcher',{}) )
|
||||||
|
document.querySelector("#iconmenu").appendChild(btn)
|
||||||
|
}
|
||||||
|
|
||||||
// reactify components with dom-definition
|
// reactify components with dom-definition
|
||||||
if( this.data.uri && this.dom && !this.el.dom ){
|
if( this.data.uri && this.dom && !this.el.dom ){
|
||||||
|
|
||||||
tasks = {
|
tasks = {
|
||||||
|
|
||||||
ensureOverlay: () => {
|
|
||||||
let overlay = document.querySelector('#overlay')
|
|
||||||
if( !overlay ){
|
|
||||||
overlay = document.createElement('div')
|
|
||||||
overlay.id = "overlay"
|
|
||||||
document.body.appendChild(overlay)
|
|
||||||
document.querySelector("a-scene").setAttribute("webxr","overlayElement:#overlay")
|
|
||||||
}
|
|
||||||
tasks.overlay = overlay
|
|
||||||
return tasks
|
|
||||||
},
|
|
||||||
|
|
||||||
createReactiveDOMElement: () => {
|
createReactiveDOMElement: () => {
|
||||||
|
const reactify = (el,aframe) => new Proxy(this.data,{
|
||||||
|
get(me,k,v) { return me[k]
|
||||||
|
},
|
||||||
|
set(me,k,v){
|
||||||
|
me[k] = v
|
||||||
|
aframe.emit(k,{el,k,v})
|
||||||
|
}
|
||||||
|
})
|
||||||
this.el.dom = document.createElement('div')
|
this.el.dom = document.createElement('div')
|
||||||
this.el.dom.className = this.parseAppURI(this.data.uri).component
|
this.el.dom.className = this.parseAppURI(this.data.uri).component
|
||||||
this.el.dom.innerHTML = this.dom.html(this)
|
this.el.dom.innerHTML = this.dom.html(this)
|
||||||
|
this.el.dom.style.display = 'none'
|
||||||
this.data = reactify( this.dom.el, this.el )
|
this.data = reactify( this.dom.el, this.el )
|
||||||
this.dom.events.map( (e) => this.el.dom.addEventListener(e, (ev) => this.el.emit(e,ev) ) )
|
this.dom.events.map( (e) => this.el.dom.addEventListener(e, (ev) => this.el.emit(e,ev) ) )
|
||||||
return tasks
|
return tasks
|
||||||
|
@ -159,37 +183,46 @@ AFRAME.AComponent.prototype.updateProperties = function(updateProperties){
|
||||||
return tasks
|
return tasks
|
||||||
},
|
},
|
||||||
|
|
||||||
requireDependencies: () => {
|
|
||||||
this.require( this.requires )
|
|
||||||
return tasks
|
|
||||||
},
|
|
||||||
|
|
||||||
setupListeners: () => {
|
setupListeners: () => {
|
||||||
this.scene.addEventListener('apps:2D', () => this.el.setAttribute('visible', false) )
|
this.scene.addEventListener('apps:2D', () => this.el.setAttribute('visible', false) )
|
||||||
this.scene.addEventListener('apps:XR', () => {
|
this.scene.addEventListener('apps:XR', () => {
|
||||||
console.log("JAXR")
|
|
||||||
this.el.setAttribute('visible', true)
|
this.el.setAttribute('visible', true)
|
||||||
this.el.setAttribute("html",`html:#${this.el.uid}; cursor:#cursor`)
|
this.el.setAttribute("html",`html:#${this.el.uid}; cursor:#cursor`)
|
||||||
})
|
})
|
||||||
return tasks
|
return tasks
|
||||||
|
},
|
||||||
|
|
||||||
|
triggerKeyboardForInputs: () => {
|
||||||
|
// https://developer.oculus.com/documentation/web/webxr-keyboard ;
|
||||||
|
[...this.el.dom.querySelectorAll('[type=text]')].map( (input) => {
|
||||||
|
let triggerKeyboard = function(){
|
||||||
|
this.focus()
|
||||||
|
console.log("focus")
|
||||||
|
}
|
||||||
|
input.addEventListener('click', triggerKeyboard )
|
||||||
|
})
|
||||||
|
return tasks
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
tasks
|
tasks
|
||||||
.ensureOverlay()
|
|
||||||
.addCSS()
|
.addCSS()
|
||||||
.createReactiveDOMElement()
|
.createReactiveDOMElement()
|
||||||
.scaleDOMvsXR()
|
.scaleDOMvsXR()
|
||||||
.requireDependencies()
|
.triggerKeyboardForInputs()
|
||||||
.setupListeners()
|
.setupListeners()
|
||||||
|
|
||||||
tasks.overlay.appendChild(this.el.dom)
|
document.querySelector('#overlay').appendChild(this.el.dom)
|
||||||
this.el.emit('DOMready',{el: this.el.dom})
|
this.el.emit('DOMready',{el: this.el.dom})
|
||||||
|
|
||||||
}
|
}
|
||||||
// assign unique app id
|
// assign unique app id
|
||||||
if( !this.el.uid ) this.el.uid = '_'+String(Math.random()).substr(10)
|
if( !this.el.uid ) this.el.uid = '_'+String(Math.random()).substr(10)
|
||||||
|
|
||||||
|
// fetch requires
|
||||||
|
if( this.requires ) this.require( this.requires, 'requires:ready' )
|
||||||
|
else this.el.emit('requires:ready')
|
||||||
}
|
}
|
||||||
}( AFRAME.AComponent.prototype.updateProperties)
|
}( AFRAME.AComponent.prototype.updateProperties)
|
||||||
|
|
||||||
|
@ -218,6 +251,7 @@ document.head.innerHTML += `
|
||||||
}
|
}
|
||||||
|
|
||||||
#toggle_overlay{
|
#toggle_overlay{
|
||||||
|
display:none;
|
||||||
position: fixed;
|
position: fixed;
|
||||||
right: 20px;
|
right: 20px;
|
||||||
bottom: 73px;
|
bottom: 73px;
|
||||||
|
|
Loading…
Reference in New Issue