-
-
Notifications
You must be signed in to change notification settings - Fork 4k
/
Copy pathvr-mode-ui.js
152 lines (126 loc) · 4.48 KB
/
vr-mode-ui.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
var registerComponent = require('../../core/component').registerComponent;
var constants = require('../../constants/');
var utils = require('../../utils/');
var bind = utils.bind;
var ENTER_VR_CLASS = 'a-enter-vr';
var ENTER_VR_BTN_CLASS = 'a-enter-vr-button';
var HIDDEN_CLASS = 'a-hidden';
var ORIENTATION_MODAL_CLASS = 'a-orientation-modal';
/**
* UI for entering VR mode.
*/
module.exports.Component = registerComponent('vr-mode-ui', {
dependencies: ['canvas'],
schema: {
enabled: {default: true}
},
init: function () {
var self = this;
var sceneEl = this.el;
if (utils.getUrlParameter('ui') === 'false') { return; }
this.enterVR = bind(sceneEl.enterVR, sceneEl);
this.exitVR = bind(sceneEl.exitVR, sceneEl);
this.insideLoader = false;
this.enterVREl = null;
this.orientationModalEl = null;
// Hide/show VR UI when entering/exiting VR mode.
sceneEl.addEventListener('enter-vr', bind(this.updateEnterVRInterface, this));
sceneEl.addEventListener('exit-vr', bind(this.updateEnterVRInterface, this));
window.addEventListener('message', function (event) {
if (event.data.type === 'loaderReady') {
self.insideLoader = true;
self.remove();
}
});
// Modal that tells the user to change orientation if in portrait.
window.addEventListener('orientationchange',
bind(this.toggleOrientationModalIfNeeded, this));
},
update: function () {
var sceneEl = this.el;
if (!this.data.enabled || this.insideLoader || utils.getUrlParameter('ui') === 'false') {
return this.remove();
}
if (this.enterVREl || this.orientationModalEl) { return; }
// Add UI if enabled and not already present.
this.enterVREl = createEnterVRButton(this.enterVR);
sceneEl.appendChild(this.enterVREl);
this.orientationModalEl = createOrientationModal(this.exitVR);
sceneEl.appendChild(this.orientationModalEl);
this.updateEnterVRInterface();
},
remove: function () {
[this.enterVREl, this.orientationModalEl].forEach(function (uiElement) {
if (uiElement) {
uiElement.parentNode.removeChild(uiElement);
}
});
},
updateEnterVRInterface: function () {
this.toggleEnterVRButtonIfNeeded();
this.toggleOrientationModalIfNeeded();
},
toggleEnterVRButtonIfNeeded: function () {
var sceneEl = this.el;
if (!this.enterVREl) { return; }
if (sceneEl.is('vr-mode')) {
this.enterVREl.classList.add(HIDDEN_CLASS);
} else {
this.enterVREl.classList.remove(HIDDEN_CLASS);
}
},
toggleOrientationModalIfNeeded: function () {
var sceneEl = this.el;
var orientationModalEl = this.orientationModalEl;
if (!orientationModalEl || !sceneEl.isMobile) { return; }
if (!utils.device.isLandscape() && sceneEl.is('vr-mode')) {
// Show if in VR mode on portrait.
orientationModalEl.classList.remove(HIDDEN_CLASS);
} else {
orientationModalEl.classList.add(HIDDEN_CLASS);
}
}
});
/**
* Creates a button that when clicked will enter into stereo-rendering mode for VR.
*
* Structure: <div><button></div>
*
* @param {function} enterVRHandler
* @returns {Element} Wrapper <div>.
*/
function createEnterVRButton (enterVRHandler) {
var vrButton;
var wrapper;
// Create elements.
wrapper = document.createElement('div');
wrapper.classList.add(ENTER_VR_CLASS);
wrapper.setAttribute(constants.AFRAME_INJECTED, '');
vrButton = document.createElement('button');
vrButton.className = ENTER_VR_BTN_CLASS;
vrButton.setAttribute('title', 'Enter VR mode with a headset or fullscreen mode on a desktop. Visit https://webvr.rocks or https://webvr.info for more information.');
vrButton.setAttribute(constants.AFRAME_INJECTED, '');
// Insert elements.
wrapper.appendChild(vrButton);
vrButton.addEventListener('click', function (evt) {
enterVRHandler();
});
return wrapper;
}
/**
* Create a modal that tells mobile users to orient the phone to landscape.
* Add a close button that if clicked, exits VR and closes the modal.
*/
function createOrientationModal (exitVRHandler) {
var modal = document.createElement('div');
modal.className = ORIENTATION_MODAL_CLASS;
modal.classList.add(HIDDEN_CLASS);
modal.setAttribute(constants.AFRAME_INJECTED, '');
var exit = document.createElement('button');
exit.setAttribute(constants.AFRAME_INJECTED, '');
exit.innerHTML = 'Exit VR';
// Exit VR on close.
exit.addEventListener('click', exitVRHandler);
modal.appendChild(exit);
return modal;
}