@epicgames-ps/lib-pixelstreamingfrontend-ue5.5 0.3.0 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (169) hide show
  1. package/dist/commonjs/AFK/AFKController.js +109 -109
  2. package/dist/commonjs/Config/Config.js +559 -559
  3. package/dist/commonjs/Config/SettingBase.js +98 -98
  4. package/dist/commonjs/Config/SettingFlag.js +49 -49
  5. package/dist/commonjs/Config/SettingNumber.js +83 -83
  6. package/dist/commonjs/Config/SettingOption.js +84 -84
  7. package/dist/commonjs/Config/SettingText.js +42 -42
  8. package/dist/commonjs/DataChannel/DataChannelController.js +106 -106
  9. package/dist/commonjs/DataChannel/DataChannelLatencyTestController.js +94 -94
  10. package/dist/commonjs/DataChannel/DataChannelLatencyTestResults.js +18 -18
  11. package/dist/commonjs/DataChannel/DataChannelSender.js +43 -43
  12. package/dist/commonjs/DataChannel/InitialSettings.js +41 -41
  13. package/dist/commonjs/DataChannel/LatencyTestResults.js +60 -60
  14. package/dist/commonjs/FreezeFrame/FreezeFrame.js +93 -93
  15. package/dist/commonjs/FreezeFrame/FreezeFrameController.js +95 -95
  16. package/dist/commonjs/Inputs/GamepadController.js +188 -188
  17. package/dist/commonjs/Inputs/GamepadTypes.js +21 -21
  18. package/dist/commonjs/Inputs/IInputController.js +2 -2
  19. package/dist/commonjs/Inputs/InputClassesFactory.js +96 -96
  20. package/dist/commonjs/Inputs/KeyCodes.js +112 -112
  21. package/dist/commonjs/Inputs/KeyboardController.js +137 -137
  22. package/dist/commonjs/Inputs/MouseButtons.js +28 -28
  23. package/dist/commonjs/Inputs/MouseController.js +97 -97
  24. package/dist/commonjs/Inputs/MouseControllerHovering.js +93 -93
  25. package/dist/commonjs/Inputs/MouseControllerLocked.js +153 -153
  26. package/dist/commonjs/Inputs/SpecialKeyCodes.js +19 -19
  27. package/dist/commonjs/Inputs/TouchController.js +123 -123
  28. package/dist/commonjs/Inputs/TouchControllerFake.js +91 -91
  29. package/dist/commonjs/Inputs/XRGamepadController.js +124 -124
  30. package/dist/commonjs/PeerConnectionController/AggregatedStats.js +252 -252
  31. package/dist/commonjs/PeerConnectionController/CandidatePairStats.js +10 -10
  32. package/dist/commonjs/PeerConnectionController/CandidateStat.js +10 -10
  33. package/dist/commonjs/PeerConnectionController/CodecStats.js +10 -10
  34. package/dist/commonjs/PeerConnectionController/DataChannelStats.js +10 -10
  35. package/dist/commonjs/PeerConnectionController/InboundRTPStats.js +22 -22
  36. package/dist/commonjs/PeerConnectionController/InboundTrackStats.js +10 -10
  37. package/dist/commonjs/PeerConnectionController/OutBoundRTPStats.js +16 -16
  38. package/dist/commonjs/PeerConnectionController/PeerConnectionController.js +584 -584
  39. package/dist/commonjs/PeerConnectionController/SessionStats.js +10 -10
  40. package/dist/commonjs/PeerConnectionController/StreamStats.js +10 -10
  41. package/dist/commonjs/PixelStreaming/PixelStreaming.js +607 -607
  42. package/dist/commonjs/UI/OnScreenKeyboard.js +82 -82
  43. package/dist/commonjs/UeInstanceMessage/ResponseController.js +38 -38
  44. package/dist/commonjs/UeInstanceMessage/SendMessageController.js +120 -120
  45. package/dist/commonjs/UeInstanceMessage/StreamMessageController.js +210 -210
  46. package/dist/commonjs/UeInstanceMessage/ToStreamerMessagesController.js +49 -49
  47. package/dist/commonjs/Util/EventEmitter.js +386 -386
  48. package/dist/commonjs/Util/FileUtil.js +108 -108
  49. package/dist/commonjs/Util/IURLSearchParams.js +25 -25
  50. package/dist/commonjs/Util/InputCoordTranslator.js +49 -49
  51. package/dist/commonjs/Util/RTCUtils.js +40 -40
  52. package/dist/commonjs/VideoPlayer/StreamController.js +67 -67
  53. package/dist/commonjs/VideoPlayer/VideoPlayer.js +177 -177
  54. package/dist/commonjs/WebRtcPlayer/WebRtcPlayerController.js +1221 -1221
  55. package/dist/commonjs/WebXR/WebXRController.js +335 -335
  56. package/dist/commonjs/pixelstreamingfrontend.js +70 -70
  57. package/dist/esm/AFK/AFKController.js +105 -105
  58. package/dist/esm/Config/Config.js +551 -551
  59. package/dist/esm/Config/SettingBase.js +94 -94
  60. package/dist/esm/Config/SettingFlag.js +45 -45
  61. package/dist/esm/Config/SettingNumber.js +79 -79
  62. package/dist/esm/Config/SettingOption.js +80 -80
  63. package/dist/esm/Config/SettingText.js +38 -38
  64. package/dist/esm/DataChannel/DataChannelController.js +102 -102
  65. package/dist/esm/DataChannel/DataChannelLatencyTestController.js +90 -90
  66. package/dist/esm/DataChannel/DataChannelLatencyTestResults.js +14 -14
  67. package/dist/esm/DataChannel/DataChannelSender.js +39 -39
  68. package/dist/esm/DataChannel/InitialSettings.js +34 -34
  69. package/dist/esm/DataChannel/LatencyTestResults.js +56 -56
  70. package/dist/esm/FreezeFrame/FreezeFrame.js +89 -89
  71. package/dist/esm/FreezeFrame/FreezeFrameController.js +91 -91
  72. package/dist/esm/Inputs/GamepadController.js +184 -184
  73. package/dist/esm/Inputs/GamepadTypes.js +17 -17
  74. package/dist/esm/Inputs/IInputController.js +1 -1
  75. package/dist/esm/Inputs/InputClassesFactory.js +91 -91
  76. package/dist/esm/Inputs/KeyCodes.js +109 -109
  77. package/dist/esm/Inputs/KeyboardController.js +133 -133
  78. package/dist/esm/Inputs/MouseButtons.js +23 -23
  79. package/dist/esm/Inputs/MouseController.js +93 -93
  80. package/dist/esm/Inputs/MouseControllerHovering.js +89 -89
  81. package/dist/esm/Inputs/MouseControllerLocked.js +149 -149
  82. package/dist/esm/Inputs/SpecialKeyCodes.js +15 -15
  83. package/dist/esm/Inputs/TouchController.js +119 -119
  84. package/dist/esm/Inputs/TouchControllerFake.js +87 -87
  85. package/dist/esm/Inputs/XRGamepadController.js +120 -120
  86. package/dist/esm/PeerConnectionController/AggregatedStats.js +248 -248
  87. package/dist/esm/PeerConnectionController/CandidatePairStats.js +6 -6
  88. package/dist/esm/PeerConnectionController/CandidateStat.js +6 -6
  89. package/dist/esm/PeerConnectionController/CodecStats.js +6 -6
  90. package/dist/esm/PeerConnectionController/DataChannelStats.js +6 -6
  91. package/dist/esm/PeerConnectionController/InboundRTPStats.js +16 -16
  92. package/dist/esm/PeerConnectionController/InboundTrackStats.js +6 -6
  93. package/dist/esm/PeerConnectionController/OutBoundRTPStats.js +11 -11
  94. package/dist/esm/PeerConnectionController/PeerConnectionController.js +580 -580
  95. package/dist/esm/PeerConnectionController/SessionStats.js +6 -6
  96. package/dist/esm/PeerConnectionController/StreamStats.js +6 -6
  97. package/dist/esm/PixelStreaming/PixelStreaming.js +603 -603
  98. package/dist/esm/UI/OnScreenKeyboard.js +78 -78
  99. package/dist/esm/UeInstanceMessage/ResponseController.js +34 -34
  100. package/dist/esm/UeInstanceMessage/SendMessageController.js +116 -116
  101. package/dist/esm/UeInstanceMessage/StreamMessageController.js +205 -205
  102. package/dist/esm/UeInstanceMessage/ToStreamerMessagesController.js +45 -45
  103. package/dist/esm/Util/EventEmitter.js +345 -345
  104. package/dist/esm/Util/FileUtil.js +103 -103
  105. package/dist/esm/Util/IURLSearchParams.js +21 -21
  106. package/dist/esm/Util/InputCoordTranslator.js +45 -45
  107. package/dist/esm/Util/RTCUtils.js +36 -36
  108. package/dist/esm/VideoPlayer/StreamController.js +63 -63
  109. package/dist/esm/VideoPlayer/VideoPlayer.js +173 -173
  110. package/dist/esm/WebRtcPlayer/WebRtcPlayerController.js +1217 -1217
  111. package/dist/esm/WebXR/WebXRController.js +331 -331
  112. package/dist/esm/pixelstreamingfrontend.js +24 -24
  113. package/dist/types/AFK/AFKController.d.ts +38 -38
  114. package/dist/types/Config/Config.d.ts +220 -220
  115. package/dist/types/Config/SettingBase.d.ts +43 -43
  116. package/dist/types/Config/SettingFlag.d.ts +24 -24
  117. package/dist/types/Config/SettingNumber.d.ts +41 -41
  118. package/dist/types/Config/SettingOption.d.ts +41 -41
  119. package/dist/types/Config/SettingText.d.ts +21 -21
  120. package/dist/types/DataChannel/DataChannelController.d.ts +59 -59
  121. package/dist/types/DataChannel/DataChannelLatencyTestController.d.ts +25 -25
  122. package/dist/types/DataChannel/DataChannelLatencyTestResults.d.ts +46 -46
  123. package/dist/types/DataChannel/DataChannelSender.d.ts +21 -21
  124. package/dist/types/DataChannel/InitialSettings.d.ts +44 -44
  125. package/dist/types/DataChannel/LatencyTestResults.d.ts +31 -31
  126. package/dist/types/FreezeFrame/FreezeFrame.d.ts +36 -36
  127. package/dist/types/FreezeFrame/FreezeFrameController.d.ts +37 -37
  128. package/dist/types/Inputs/GamepadController.d.ts +61 -61
  129. package/dist/types/Inputs/GamepadTypes.d.ts +15 -15
  130. package/dist/types/Inputs/IInputController.d.ts +16 -16
  131. package/dist/types/Inputs/InputClassesFactory.d.ts +53 -53
  132. package/dist/types/Inputs/KeyCodes.d.ts +5 -5
  133. package/dist/types/Inputs/KeyboardController.d.ts +34 -34
  134. package/dist/types/Inputs/MouseButtons.d.ts +22 -22
  135. package/dist/types/Inputs/MouseController.d.ts +40 -40
  136. package/dist/types/Inputs/MouseControllerHovering.d.ts +26 -26
  137. package/dist/types/Inputs/MouseControllerLocked.d.ts +31 -31
  138. package/dist/types/Inputs/SpecialKeyCodes.d.ts +14 -14
  139. package/dist/types/Inputs/TouchController.d.ts +28 -28
  140. package/dist/types/Inputs/TouchControllerFake.d.ts +29 -29
  141. package/dist/types/Inputs/XRGamepadController.d.ts +15 -15
  142. package/dist/types/PeerConnectionController/AggregatedStats.d.ts +82 -82
  143. package/dist/types/PeerConnectionController/CandidatePairStats.d.ts +22 -22
  144. package/dist/types/PeerConnectionController/CandidateStat.d.ts +13 -13
  145. package/dist/types/PeerConnectionController/CodecStats.d.ts +14 -14
  146. package/dist/types/PeerConnectionController/DataChannelStats.d.ts +15 -15
  147. package/dist/types/PeerConnectionController/InboundRTPStats.d.ts +141 -141
  148. package/dist/types/PeerConnectionController/InboundTrackStats.d.ts +32 -32
  149. package/dist/types/PeerConnectionController/OutBoundRTPStats.d.ts +23 -23
  150. package/dist/types/PeerConnectionController/PeerConnectionController.d.ts +143 -143
  151. package/dist/types/PeerConnectionController/SessionStats.d.ts +8 -8
  152. package/dist/types/PeerConnectionController/StreamStats.d.ts +9 -9
  153. package/dist/types/PixelStreaming/PixelStreaming.d.ts +271 -271
  154. package/dist/types/UI/OnScreenKeyboard.d.ts +30 -30
  155. package/dist/types/UeInstanceMessage/ResponseController.d.ts +19 -19
  156. package/dist/types/UeInstanceMessage/SendMessageController.d.ts +18 -18
  157. package/dist/types/UeInstanceMessage/StreamMessageController.d.ts +29 -29
  158. package/dist/types/UeInstanceMessage/ToStreamerMessagesController.d.ts +32 -32
  159. package/dist/types/Util/EventEmitter.d.ts +429 -429
  160. package/dist/types/Util/FileUtil.d.ts +32 -32
  161. package/dist/types/Util/IURLSearchParams.d.ts +9 -9
  162. package/dist/types/Util/InputCoordTranslator.d.ts +29 -29
  163. package/dist/types/Util/RTCUtils.d.ts +8 -8
  164. package/dist/types/VideoPlayer/StreamController.d.ts +22 -22
  165. package/dist/types/VideoPlayer/VideoPlayer.d.ts +78 -78
  166. package/dist/types/WebRtcPlayer/WebRtcPlayerController.d.ts +379 -379
  167. package/dist/types/WebXR/WebXRController.d.ts +42 -42
  168. package/dist/types/pixelstreamingfrontend.d.ts +23 -23
  169. package/package.json +45 -45
@@ -1,68 +1,68 @@
1
- "use strict";
2
- // Copyright Epic Games, Inc. All Rights Reserved.
3
- Object.defineProperty(exports, "__esModule", { value: true });
4
- exports.WebXRController = void 0;
5
- const lib_pixelstreamingcommon_ue5_5_1 = require("@epicgames-ps/lib-pixelstreamingcommon-ue5.5");
6
- const XRGamepadController_1 = require("../Inputs/XRGamepadController");
7
- const EventEmitter_1 = require("../Util/EventEmitter");
8
- const pixelstreamingfrontend_1 = require("../pixelstreamingfrontend");
9
- class WebXRController {
10
- constructor(webRtcPlayerController) {
11
- this.xrViewerPose = null;
12
- // Used for comparisons to ensure two numbers are close enough.
13
- this.EPSILON = 0.0000001;
14
- this.videoTexture = null;
15
- this.prevVideoWidth = 0;
16
- this.prevVideoHeight = 0;
17
- this.leftView = null;
18
- this.rightView = null;
19
- // Store the HMD data we have last sent (not all of it is needed every frame unless it changes)
20
- this.lastSentLeftEyeProj = null;
21
- this.lastSentRightEyeProj = null;
22
- this.lastSentRelativeLeftEyePos = null;
23
- this.lastSentRelativeRightEyePos = null;
24
- this.xrSession = null;
25
- this.webRtcController = webRtcPlayerController;
26
- this.xrGamepadController = new XRGamepadController_1.XRGamepadController(this.webRtcController.streamMessageController);
27
- this.onSessionEnded = new EventTarget();
28
- this.onSessionStarted = new EventTarget();
29
- this.onFrame = new EventTarget();
30
- }
31
- xrClicked() {
32
- if (!this.xrSession) {
33
- if (!navigator.xr) {
34
- lib_pixelstreamingcommon_ue5_5_1.Logger.Error('This browser does not support XR.');
35
- return;
36
- }
37
- navigator.xr
38
- /* Request immersive-vr session without any optional features. */
39
- .requestSession('immersive-vr', { optionalFeatures: [] })
40
- .then((session) => {
41
- this.onXrSessionStarted(session);
42
- });
43
- }
44
- else {
45
- this.xrSession.end();
46
- }
47
- }
48
- onXrSessionEnded() {
49
- lib_pixelstreamingcommon_ue5_5_1.Logger.Info('XR Session ended');
50
- this.xrSession = null;
51
- this.onSessionEnded.dispatchEvent(new Event('xrSessionEnded'));
52
- }
53
- initGL() {
54
- if (this.gl) {
55
- return;
56
- }
57
- const canvas = document.createElement('canvas');
58
- this.gl = canvas.getContext('webgl2', {
59
- xrCompatible: true
60
- });
61
- // Set our clear color
62
- this.gl.clearColor(0.0, 0.0, 0.0, 1);
63
- }
64
- initShaders() {
65
- // shader source code
1
+ "use strict";
2
+ // Copyright Epic Games, Inc. All Rights Reserved.
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.WebXRController = void 0;
5
+ const lib_pixelstreamingcommon_ue5_5_1 = require("@epicgames-ps/lib-pixelstreamingcommon-ue5.5");
6
+ const XRGamepadController_1 = require("../Inputs/XRGamepadController");
7
+ const EventEmitter_1 = require("../Util/EventEmitter");
8
+ const pixelstreamingfrontend_1 = require("../pixelstreamingfrontend");
9
+ class WebXRController {
10
+ constructor(webRtcPlayerController) {
11
+ this.xrViewerPose = null;
12
+ // Used for comparisons to ensure two numbers are close enough.
13
+ this.EPSILON = 0.0000001;
14
+ this.videoTexture = null;
15
+ this.prevVideoWidth = 0;
16
+ this.prevVideoHeight = 0;
17
+ this.leftView = null;
18
+ this.rightView = null;
19
+ // Store the HMD data we have last sent (not all of it is needed every frame unless it changes)
20
+ this.lastSentLeftEyeProj = null;
21
+ this.lastSentRightEyeProj = null;
22
+ this.lastSentRelativeLeftEyePos = null;
23
+ this.lastSentRelativeRightEyePos = null;
24
+ this.xrSession = null;
25
+ this.webRtcController = webRtcPlayerController;
26
+ this.xrGamepadController = new XRGamepadController_1.XRGamepadController(this.webRtcController.streamMessageController);
27
+ this.onSessionEnded = new EventTarget();
28
+ this.onSessionStarted = new EventTarget();
29
+ this.onFrame = new EventTarget();
30
+ }
31
+ xrClicked() {
32
+ if (!this.xrSession) {
33
+ if (!navigator.xr) {
34
+ lib_pixelstreamingcommon_ue5_5_1.Logger.Error('This browser does not support XR.');
35
+ return;
36
+ }
37
+ navigator.xr
38
+ /* Request immersive-vr session without any optional features. */
39
+ .requestSession('immersive-vr', { optionalFeatures: [] })
40
+ .then((session) => {
41
+ this.onXrSessionStarted(session);
42
+ });
43
+ }
44
+ else {
45
+ this.xrSession.end();
46
+ }
47
+ }
48
+ onXrSessionEnded() {
49
+ lib_pixelstreamingcommon_ue5_5_1.Logger.Info('XR Session ended');
50
+ this.xrSession = null;
51
+ this.onSessionEnded.dispatchEvent(new Event('xrSessionEnded'));
52
+ }
53
+ initGL() {
54
+ if (this.gl) {
55
+ return;
56
+ }
57
+ const canvas = document.createElement('canvas');
58
+ this.gl = canvas.getContext('webgl2', {
59
+ xrCompatible: true
60
+ });
61
+ // Set our clear color
62
+ this.gl.clearColor(0.0, 0.0, 0.0, 1);
63
+ }
64
+ initShaders() {
65
+ // shader source code
66
66
  const vertexShaderSource = `
67
67
  attribute vec2 a_position;
68
68
  attribute vec2 a_texCoord;
@@ -76,7 +76,7 @@ class WebXRController {
76
76
  // The GPU will interpolate this value between points.
77
77
  v_texCoord = a_texCoord;
78
78
  }
79
- `;
79
+ `;
80
80
  const fragmentShaderSource = `
81
81
  precision mediump float;
82
82
 
@@ -89,273 +89,273 @@ class WebXRController {
89
89
  void main() {
90
90
  gl_FragColor = texture2D(u_image, v_texCoord);
91
91
  }
92
- `;
93
- // setup vertex shader
94
- const vertexShader = this.gl.createShader(this.gl.VERTEX_SHADER);
95
- this.gl.shaderSource(vertexShader, vertexShaderSource);
96
- this.gl.compileShader(vertexShader);
97
- // setup fragment shader
98
- const fragmentShader = this.gl.createShader(this.gl.FRAGMENT_SHADER);
99
- this.gl.shaderSource(fragmentShader, fragmentShaderSource);
100
- this.gl.compileShader(fragmentShader);
101
- // setup GLSL program
102
- const shaderProgram = this.gl.createProgram();
103
- this.gl.attachShader(shaderProgram, vertexShader);
104
- this.gl.attachShader(shaderProgram, fragmentShader);
105
- this.gl.linkProgram(shaderProgram);
106
- this.gl.useProgram(shaderProgram);
107
- // look up where vertex data needs to go
108
- this.positionLocation = this.gl.getAttribLocation(shaderProgram, 'a_position');
109
- this.texcoordLocation = this.gl.getAttribLocation(shaderProgram, 'a_texCoord');
110
- }
111
- updateVideoTexture() {
112
- if (!this.videoTexture) {
113
- // Create our texture that we use in our shader
114
- // and bind it once because we never use any other texture.
115
- this.videoTexture = this.gl.createTexture();
116
- this.gl.bindTexture(this.gl.TEXTURE_2D, this.videoTexture);
117
- // Set the parameters so we can render any size image.
118
- this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_S, this.gl.CLAMP_TO_EDGE);
119
- this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_T, this.gl.CLAMP_TO_EDGE);
120
- this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MIN_FILTER, this.gl.LINEAR);
121
- this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MAG_FILTER, this.gl.LINEAR);
122
- }
123
- const videoHeight = this.webRtcController.videoPlayer.getVideoElement().videoHeight;
124
- const videoWidth = this.webRtcController.videoPlayer.getVideoElement().videoWidth;
125
- if (this.prevVideoHeight != videoHeight || this.prevVideoWidth != videoWidth) {
126
- // Do full update of texture if dimensions do not match
127
- this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.RGBA, videoWidth, videoHeight, 0, this.gl.RGBA, this.gl.UNSIGNED_BYTE, this.webRtcController.videoPlayer.getVideoElement());
128
- }
129
- else {
130
- // If dimensions match just update the sub region
131
- this.gl.texSubImage2D(this.gl.TEXTURE_2D, 0, 0, 0, videoWidth, videoHeight, this.gl.RGBA, this.gl.UNSIGNED_BYTE, this.webRtcController.videoPlayer.getVideoElement());
132
- }
133
- // Update prev video width/height
134
- this.prevVideoHeight = videoHeight;
135
- this.prevVideoWidth = videoWidth;
136
- }
137
- initBuffers() {
138
- // Create out position buffer and its vertex shader attribute
139
- {
140
- // Create a buffer to put the the vertices of the plane we will draw the video stream onto
141
- this.positionBuffer = this.gl.createBuffer();
142
- // Bind the position buffer
143
- this.gl.bindBuffer(this.gl.ARRAY_BUFFER, this.positionBuffer);
144
- // Enable `positionLocation` to be used as vertex shader attribute
145
- this.gl.enableVertexAttribArray(this.positionLocation);
146
- // Note: positions are passed in clip-space coordinates [-1..1] so no need to convert in-shader
147
- // prettier-ignore
148
- this.gl.bufferData(this.gl.ARRAY_BUFFER, new Float32Array([
149
- -1.0, 1.0,
150
- 1.0, 1.0,
151
- -1.0, -1.0,
152
- -1.0, -1.0,
153
- 1.0, 1.0,
154
- 1.0, -1.0
155
- ]), this.gl.STATIC_DRAW);
156
- // Tell position attribute of the vertex shader how to get data out of the bound buffer (the positionBuffer)
157
- this.gl.vertexAttribPointer(this.positionLocation, 2 /*size*/, this.gl.FLOAT /*type*/, false /*normalize*/, 0 /*stride*/, 0 /*offset*/);
158
- }
159
- // Create our texture coordinate buffers for accessing our texture
160
- {
161
- this.texcoordBuffer = this.gl.createBuffer();
162
- // Bind the texture coordinate buffer
163
- this.gl.bindBuffer(this.gl.ARRAY_BUFFER, this.texcoordBuffer);
164
- // Enable `texcoordLocation` to be used as a vertex shader attribute
165
- this.gl.enableVertexAttribArray(this.texcoordLocation);
166
- // The texture coordinates to apply for rectangle we are drawing
167
- this.gl.bufferData(this.gl.ARRAY_BUFFER, new Float32Array([0.0, 0.0, 1.0, 0.0, 0.0, 1.0, 0.0, 1.0, 1.0, 0.0, 1.0, 1.0]), this.gl.STATIC_DRAW);
168
- // Tell texture coordinate attribute of the vertex shader how to get data out of the bound buffer (the texcoordBuffer)
169
- this.gl.vertexAttribPointer(this.texcoordLocation, 2 /*size*/, this.gl.FLOAT /*type*/, false /*normalize*/, 0 /*stride*/, 0 /*offset*/);
170
- }
171
- }
172
- onXrSessionStarted(session) {
173
- lib_pixelstreamingcommon_ue5_5_1.Logger.Info('XR Session started');
174
- this.xrSession = session;
175
- this.xrSession.addEventListener('end', () => {
176
- this.onXrSessionEnded();
177
- });
178
- // Initialization
179
- this.initGL();
180
- this.initShaders();
181
- this.initBuffers();
182
- session.requestReferenceSpace('local').then((refSpace) => {
183
- this.xrRefSpace = refSpace;
184
- // Set up our base layer (i.e. a projection layer that fills the entire XR viewport).
185
- this.xrSession.updateRenderState({
186
- baseLayer: new XRWebGLLayer(this.xrSession, this.gl)
187
- });
188
- // Update target framerate to 90 fps if 90 fps is supported in this XR device
189
- if (this.xrSession.supportedFrameRates) {
190
- for (const frameRate of this.xrSession.supportedFrameRates) {
191
- if (frameRate == 90) {
192
- session.updateTargetFrameRate(90);
193
- }
194
- }
195
- }
196
- // Binding to each new frame to get latest XR updates
197
- this.xrSession.requestAnimationFrame(this.onXrFrame.bind(this));
198
- });
199
- this.onSessionStarted.dispatchEvent(new Event('xrSessionStarted'));
200
- }
201
- areArraysEqual(a, b) {
202
- return (a.length === b.length && a.every((element, index) => Math.abs(element - b[index]) <= this.EPSILON));
203
- }
204
- arePointsEqual(a, b) {
205
- return (Math.abs(a.x - b.x) >= this.EPSILON &&
206
- Math.abs(a.y - b.y) >= this.EPSILON &&
207
- Math.abs(a.z - b.z) >= this.EPSILON);
208
- }
209
- sendXRDataToUE() {
210
- if (this.leftView == null || this.rightView == null) {
211
- return;
212
- }
213
- // We selectively send either the `XREyeViews` or `XRHMDTransform`
214
- // messages over the datachannel. The reason for this selective sending is that
215
- // the `XREyeViews` is a much larger message and changes infrequently (e.g. only when user changes headset IPD).
216
- // Therefore, we only need to send it once on startup and then any time it changes.
217
- // The rest of the time we can send the `XRHMDTransform` message.
218
- let shouldSendEyeViews = this.lastSentLeftEyeProj == null ||
219
- this.lastSentRightEyeProj == null ||
220
- this.lastSentRelativeLeftEyePos == null ||
221
- this.lastSentRelativeRightEyePos == null;
222
- const leftEyeTrans = this.leftView.transform.matrix;
223
- const leftEyeProj = this.leftView.projectionMatrix;
224
- const rightEyeTrans = this.rightView.transform.matrix;
225
- const rightEyeProj = this.rightView.projectionMatrix;
226
- const hmdTrans = this.xrViewerPose.transform.matrix;
227
- // Check if projection matrices have changed
228
- if (!shouldSendEyeViews && this.lastSentLeftEyeProj != null && this.lastSentRightEyeProj != null) {
229
- const leftEyeProjUnchanged = this.areArraysEqual(leftEyeProj, this.lastSentLeftEyeProj);
230
- const rightEyeProjUnchanged = this.areArraysEqual(rightEyeProj, this.lastSentRightEyeProj);
231
- shouldSendEyeViews = leftEyeProjUnchanged == false || rightEyeProjUnchanged == false;
232
- }
233
- const leftEyeRelativePos = new DOMPointReadOnly(this.leftView.transform.position.x - this.xrViewerPose.transform.position.x, this.leftView.transform.position.y - this.xrViewerPose.transform.position.y, this.leftView.transform.position.z - this.xrViewerPose.transform.position.z, 1.0);
234
- const rightEyeRelativePos = new DOMPointReadOnly(this.leftView.transform.position.x - this.xrViewerPose.transform.position.x, this.leftView.transform.position.y - this.xrViewerPose.transform.position.y, this.leftView.transform.position.z - this.xrViewerPose.transform.position.z, 1.0);
235
- // Check if relative eye pos has changed (e.g IPD changed)
236
- if (!shouldSendEyeViews &&
237
- this.lastSentRelativeLeftEyePos != null &&
238
- this.lastSentRelativeRightEyePos != null) {
239
- const leftEyePosUnchanged = this.arePointsEqual(leftEyeRelativePos, this.lastSentRelativeLeftEyePos);
240
- const rightEyePosUnchanged = this.arePointsEqual(rightEyeRelativePos, this.lastSentRelativeRightEyePos);
241
- shouldSendEyeViews = leftEyePosUnchanged == false || rightEyePosUnchanged == false;
242
- // Note: We are not checking if EyeView rotation changes (as far as I know no HMD supports changing this value at runtime).
243
- }
244
- if (shouldSendEyeViews) {
245
- // send transform (4x4) and projection matrix (4x4) data for each eye (left first, then right)
246
- // prettier-ignore
247
- this.webRtcController.streamMessageController.toStreamerHandlers.get('XREyeViews')([
248
- // Left eye 4x4 transform matrix
249
- leftEyeTrans[0], leftEyeTrans[4], leftEyeTrans[8], leftEyeTrans[12],
250
- leftEyeTrans[1], leftEyeTrans[5], leftEyeTrans[9], leftEyeTrans[13],
251
- leftEyeTrans[2], leftEyeTrans[6], leftEyeTrans[10], leftEyeTrans[14],
252
- leftEyeTrans[3], leftEyeTrans[7], leftEyeTrans[11], leftEyeTrans[15],
253
- // Left eye 4x4 projection matrix
254
- leftEyeProj[0], leftEyeProj[4], leftEyeProj[8], leftEyeProj[12],
255
- leftEyeProj[1], leftEyeProj[5], leftEyeProj[9], leftEyeProj[13],
256
- leftEyeProj[2], leftEyeProj[6], leftEyeProj[10], leftEyeProj[14],
257
- leftEyeProj[3], leftEyeProj[7], leftEyeProj[11], leftEyeProj[15],
258
- // Right eye 4x4 transform matrix
259
- rightEyeTrans[0], rightEyeTrans[4], rightEyeTrans[8], rightEyeTrans[12],
260
- rightEyeTrans[1], rightEyeTrans[5], rightEyeTrans[9], rightEyeTrans[13],
261
- rightEyeTrans[2], rightEyeTrans[6], rightEyeTrans[10], rightEyeTrans[14],
262
- rightEyeTrans[3], rightEyeTrans[7], rightEyeTrans[11], rightEyeTrans[15],
263
- // right eye 4x4 projection matrix
264
- rightEyeProj[0], rightEyeProj[4], rightEyeProj[8], rightEyeProj[12],
265
- rightEyeProj[1], rightEyeProj[5], rightEyeProj[9], rightEyeProj[13],
266
- rightEyeProj[2], rightEyeProj[6], rightEyeProj[10], rightEyeProj[14],
267
- rightEyeProj[3], rightEyeProj[7], rightEyeProj[11], rightEyeProj[15],
268
- // HMD 4x4 transform
269
- hmdTrans[0], hmdTrans[4], hmdTrans[8], hmdTrans[12],
270
- hmdTrans[1], hmdTrans[5], hmdTrans[9], hmdTrans[13],
271
- hmdTrans[2], hmdTrans[6], hmdTrans[10], hmdTrans[14],
272
- hmdTrans[3], hmdTrans[7], hmdTrans[11], hmdTrans[15],
273
- ]);
274
- this.lastSentLeftEyeProj = leftEyeProj;
275
- this.lastSentRightEyeProj = rightEyeProj;
276
- this.lastSentRelativeLeftEyePos = leftEyeRelativePos;
277
- this.lastSentRelativeRightEyePos = rightEyeRelativePos;
278
- }
279
- else {
280
- // If we don't need to the entire eye views being sent just send the HMD transform
281
- this.webRtcController.streamMessageController.toStreamerHandlers.get('XRHMDTransform')([
282
- // HMD 4x4 transform
283
- hmdTrans[0],
284
- hmdTrans[4],
285
- hmdTrans[8],
286
- hmdTrans[12],
287
- hmdTrans[1],
288
- hmdTrans[5],
289
- hmdTrans[9],
290
- hmdTrans[13],
291
- hmdTrans[2],
292
- hmdTrans[6],
293
- hmdTrans[10],
294
- hmdTrans[14],
295
- hmdTrans[3],
296
- hmdTrans[7],
297
- hmdTrans[11],
298
- hmdTrans[15]
299
- ]);
300
- }
301
- }
302
- onXrFrame(time, frame) {
303
- this.xrViewerPose = frame.getViewerPose(this.xrRefSpace);
304
- if (this.xrViewerPose) {
305
- this.updateViews();
306
- if (this.leftView == null || this.rightView == null) {
307
- return;
308
- }
309
- this.sendXRDataToUE();
310
- this.updateVideoTexture();
311
- this.render();
312
- }
313
- if (this.webRtcController.config.isFlagEnabled(pixelstreamingfrontend_1.Flags.XRControllerInput)) {
314
- this.xrSession.inputSources.forEach((source, _index, _array) => {
315
- this.xrGamepadController.updateStatus(source, frame, this.xrRefSpace);
316
- }, this);
317
- }
318
- this.xrSession.requestAnimationFrame((time, frame) => this.onXrFrame(time, frame));
319
- this.onFrame.dispatchEvent(new EventEmitter_1.XrFrameEvent({ time, frame }));
320
- }
321
- updateViews() {
322
- if (!this.xrViewerPose) {
323
- return;
324
- }
325
- for (const view of this.xrViewerPose.views) {
326
- if (view.eye === 'left') {
327
- this.leftView = view;
328
- }
329
- else if (view.eye === 'right') {
330
- this.rightView = view;
331
- }
332
- }
333
- }
334
- render() {
335
- if (!this.gl) {
336
- return;
337
- }
338
- // Bind the framebuffer to the base layer's framebuffer
339
- const glLayer = this.xrSession.renderState.baseLayer;
340
- this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, glLayer.framebuffer);
341
- // Set the relevant portion of clip space
342
- this.gl.viewport(0, 0, glLayer.framebufferWidth, glLayer.framebufferHeight);
343
- // Draw the rectangle we will show the video stream texture on
344
- this.gl.drawArrays(this.gl.TRIANGLES /*primitiveType*/, 0 /*offset*/, 6 /*count*/);
345
- }
346
- static isSessionSupported(mode) {
347
- if (location.protocol !== 'https:') {
348
- lib_pixelstreamingcommon_ue5_5_1.Logger.Info('WebXR requires https, if you want WebXR use https.');
349
- }
350
- if (navigator.xr) {
351
- return navigator.xr.isSessionSupported(mode);
352
- }
353
- else {
354
- return new Promise(() => {
355
- return false;
356
- });
357
- }
358
- }
359
- }
360
- exports.WebXRController = WebXRController;
92
+ `;
93
+ // setup vertex shader
94
+ const vertexShader = this.gl.createShader(this.gl.VERTEX_SHADER);
95
+ this.gl.shaderSource(vertexShader, vertexShaderSource);
96
+ this.gl.compileShader(vertexShader);
97
+ // setup fragment shader
98
+ const fragmentShader = this.gl.createShader(this.gl.FRAGMENT_SHADER);
99
+ this.gl.shaderSource(fragmentShader, fragmentShaderSource);
100
+ this.gl.compileShader(fragmentShader);
101
+ // setup GLSL program
102
+ const shaderProgram = this.gl.createProgram();
103
+ this.gl.attachShader(shaderProgram, vertexShader);
104
+ this.gl.attachShader(shaderProgram, fragmentShader);
105
+ this.gl.linkProgram(shaderProgram);
106
+ this.gl.useProgram(shaderProgram);
107
+ // look up where vertex data needs to go
108
+ this.positionLocation = this.gl.getAttribLocation(shaderProgram, 'a_position');
109
+ this.texcoordLocation = this.gl.getAttribLocation(shaderProgram, 'a_texCoord');
110
+ }
111
+ updateVideoTexture() {
112
+ if (!this.videoTexture) {
113
+ // Create our texture that we use in our shader
114
+ // and bind it once because we never use any other texture.
115
+ this.videoTexture = this.gl.createTexture();
116
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.videoTexture);
117
+ // Set the parameters so we can render any size image.
118
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_S, this.gl.CLAMP_TO_EDGE);
119
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_T, this.gl.CLAMP_TO_EDGE);
120
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MIN_FILTER, this.gl.LINEAR);
121
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MAG_FILTER, this.gl.LINEAR);
122
+ }
123
+ const videoHeight = this.webRtcController.videoPlayer.getVideoElement().videoHeight;
124
+ const videoWidth = this.webRtcController.videoPlayer.getVideoElement().videoWidth;
125
+ if (this.prevVideoHeight != videoHeight || this.prevVideoWidth != videoWidth) {
126
+ // Do full update of texture if dimensions do not match
127
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.RGBA, videoWidth, videoHeight, 0, this.gl.RGBA, this.gl.UNSIGNED_BYTE, this.webRtcController.videoPlayer.getVideoElement());
128
+ }
129
+ else {
130
+ // If dimensions match just update the sub region
131
+ this.gl.texSubImage2D(this.gl.TEXTURE_2D, 0, 0, 0, videoWidth, videoHeight, this.gl.RGBA, this.gl.UNSIGNED_BYTE, this.webRtcController.videoPlayer.getVideoElement());
132
+ }
133
+ // Update prev video width/height
134
+ this.prevVideoHeight = videoHeight;
135
+ this.prevVideoWidth = videoWidth;
136
+ }
137
+ initBuffers() {
138
+ // Create out position buffer and its vertex shader attribute
139
+ {
140
+ // Create a buffer to put the the vertices of the plane we will draw the video stream onto
141
+ this.positionBuffer = this.gl.createBuffer();
142
+ // Bind the position buffer
143
+ this.gl.bindBuffer(this.gl.ARRAY_BUFFER, this.positionBuffer);
144
+ // Enable `positionLocation` to be used as vertex shader attribute
145
+ this.gl.enableVertexAttribArray(this.positionLocation);
146
+ // Note: positions are passed in clip-space coordinates [-1..1] so no need to convert in-shader
147
+ // prettier-ignore
148
+ this.gl.bufferData(this.gl.ARRAY_BUFFER, new Float32Array([
149
+ -1.0, 1.0,
150
+ 1.0, 1.0,
151
+ -1.0, -1.0,
152
+ -1.0, -1.0,
153
+ 1.0, 1.0,
154
+ 1.0, -1.0
155
+ ]), this.gl.STATIC_DRAW);
156
+ // Tell position attribute of the vertex shader how to get data out of the bound buffer (the positionBuffer)
157
+ this.gl.vertexAttribPointer(this.positionLocation, 2 /*size*/, this.gl.FLOAT /*type*/, false /*normalize*/, 0 /*stride*/, 0 /*offset*/);
158
+ }
159
+ // Create our texture coordinate buffers for accessing our texture
160
+ {
161
+ this.texcoordBuffer = this.gl.createBuffer();
162
+ // Bind the texture coordinate buffer
163
+ this.gl.bindBuffer(this.gl.ARRAY_BUFFER, this.texcoordBuffer);
164
+ // Enable `texcoordLocation` to be used as a vertex shader attribute
165
+ this.gl.enableVertexAttribArray(this.texcoordLocation);
166
+ // The texture coordinates to apply for rectangle we are drawing
167
+ this.gl.bufferData(this.gl.ARRAY_BUFFER, new Float32Array([0.0, 0.0, 1.0, 0.0, 0.0, 1.0, 0.0, 1.0, 1.0, 0.0, 1.0, 1.0]), this.gl.STATIC_DRAW);
168
+ // Tell texture coordinate attribute of the vertex shader how to get data out of the bound buffer (the texcoordBuffer)
169
+ this.gl.vertexAttribPointer(this.texcoordLocation, 2 /*size*/, this.gl.FLOAT /*type*/, false /*normalize*/, 0 /*stride*/, 0 /*offset*/);
170
+ }
171
+ }
172
+ onXrSessionStarted(session) {
173
+ lib_pixelstreamingcommon_ue5_5_1.Logger.Info('XR Session started');
174
+ this.xrSession = session;
175
+ this.xrSession.addEventListener('end', () => {
176
+ this.onXrSessionEnded();
177
+ });
178
+ // Initialization
179
+ this.initGL();
180
+ this.initShaders();
181
+ this.initBuffers();
182
+ session.requestReferenceSpace('local').then((refSpace) => {
183
+ this.xrRefSpace = refSpace;
184
+ // Set up our base layer (i.e. a projection layer that fills the entire XR viewport).
185
+ this.xrSession.updateRenderState({
186
+ baseLayer: new XRWebGLLayer(this.xrSession, this.gl)
187
+ });
188
+ // Update target framerate to 90 fps if 90 fps is supported in this XR device
189
+ if (this.xrSession.supportedFrameRates) {
190
+ for (const frameRate of this.xrSession.supportedFrameRates) {
191
+ if (frameRate == 90) {
192
+ session.updateTargetFrameRate(90);
193
+ }
194
+ }
195
+ }
196
+ // Binding to each new frame to get latest XR updates
197
+ this.xrSession.requestAnimationFrame(this.onXrFrame.bind(this));
198
+ });
199
+ this.onSessionStarted.dispatchEvent(new Event('xrSessionStarted'));
200
+ }
201
+ areArraysEqual(a, b) {
202
+ return (a.length === b.length && a.every((element, index) => Math.abs(element - b[index]) <= this.EPSILON));
203
+ }
204
+ arePointsEqual(a, b) {
205
+ return (Math.abs(a.x - b.x) >= this.EPSILON &&
206
+ Math.abs(a.y - b.y) >= this.EPSILON &&
207
+ Math.abs(a.z - b.z) >= this.EPSILON);
208
+ }
209
+ sendXRDataToUE() {
210
+ if (this.leftView == null || this.rightView == null) {
211
+ return;
212
+ }
213
+ // We selectively send either the `XREyeViews` or `XRHMDTransform`
214
+ // messages over the datachannel. The reason for this selective sending is that
215
+ // the `XREyeViews` is a much larger message and changes infrequently (e.g. only when user changes headset IPD).
216
+ // Therefore, we only need to send it once on startup and then any time it changes.
217
+ // The rest of the time we can send the `XRHMDTransform` message.
218
+ let shouldSendEyeViews = this.lastSentLeftEyeProj == null ||
219
+ this.lastSentRightEyeProj == null ||
220
+ this.lastSentRelativeLeftEyePos == null ||
221
+ this.lastSentRelativeRightEyePos == null;
222
+ const leftEyeTrans = this.leftView.transform.matrix;
223
+ const leftEyeProj = this.leftView.projectionMatrix;
224
+ const rightEyeTrans = this.rightView.transform.matrix;
225
+ const rightEyeProj = this.rightView.projectionMatrix;
226
+ const hmdTrans = this.xrViewerPose.transform.matrix;
227
+ // Check if projection matrices have changed
228
+ if (!shouldSendEyeViews && this.lastSentLeftEyeProj != null && this.lastSentRightEyeProj != null) {
229
+ const leftEyeProjUnchanged = this.areArraysEqual(leftEyeProj, this.lastSentLeftEyeProj);
230
+ const rightEyeProjUnchanged = this.areArraysEqual(rightEyeProj, this.lastSentRightEyeProj);
231
+ shouldSendEyeViews = leftEyeProjUnchanged == false || rightEyeProjUnchanged == false;
232
+ }
233
+ const leftEyeRelativePos = new DOMPointReadOnly(this.leftView.transform.position.x - this.xrViewerPose.transform.position.x, this.leftView.transform.position.y - this.xrViewerPose.transform.position.y, this.leftView.transform.position.z - this.xrViewerPose.transform.position.z, 1.0);
234
+ const rightEyeRelativePos = new DOMPointReadOnly(this.leftView.transform.position.x - this.xrViewerPose.transform.position.x, this.leftView.transform.position.y - this.xrViewerPose.transform.position.y, this.leftView.transform.position.z - this.xrViewerPose.transform.position.z, 1.0);
235
+ // Check if relative eye pos has changed (e.g IPD changed)
236
+ if (!shouldSendEyeViews &&
237
+ this.lastSentRelativeLeftEyePos != null &&
238
+ this.lastSentRelativeRightEyePos != null) {
239
+ const leftEyePosUnchanged = this.arePointsEqual(leftEyeRelativePos, this.lastSentRelativeLeftEyePos);
240
+ const rightEyePosUnchanged = this.arePointsEqual(rightEyeRelativePos, this.lastSentRelativeRightEyePos);
241
+ shouldSendEyeViews = leftEyePosUnchanged == false || rightEyePosUnchanged == false;
242
+ // Note: We are not checking if EyeView rotation changes (as far as I know no HMD supports changing this value at runtime).
243
+ }
244
+ if (shouldSendEyeViews) {
245
+ // send transform (4x4) and projection matrix (4x4) data for each eye (left first, then right)
246
+ // prettier-ignore
247
+ this.webRtcController.streamMessageController.toStreamerHandlers.get('XREyeViews')([
248
+ // Left eye 4x4 transform matrix
249
+ leftEyeTrans[0], leftEyeTrans[4], leftEyeTrans[8], leftEyeTrans[12],
250
+ leftEyeTrans[1], leftEyeTrans[5], leftEyeTrans[9], leftEyeTrans[13],
251
+ leftEyeTrans[2], leftEyeTrans[6], leftEyeTrans[10], leftEyeTrans[14],
252
+ leftEyeTrans[3], leftEyeTrans[7], leftEyeTrans[11], leftEyeTrans[15],
253
+ // Left eye 4x4 projection matrix
254
+ leftEyeProj[0], leftEyeProj[4], leftEyeProj[8], leftEyeProj[12],
255
+ leftEyeProj[1], leftEyeProj[5], leftEyeProj[9], leftEyeProj[13],
256
+ leftEyeProj[2], leftEyeProj[6], leftEyeProj[10], leftEyeProj[14],
257
+ leftEyeProj[3], leftEyeProj[7], leftEyeProj[11], leftEyeProj[15],
258
+ // Right eye 4x4 transform matrix
259
+ rightEyeTrans[0], rightEyeTrans[4], rightEyeTrans[8], rightEyeTrans[12],
260
+ rightEyeTrans[1], rightEyeTrans[5], rightEyeTrans[9], rightEyeTrans[13],
261
+ rightEyeTrans[2], rightEyeTrans[6], rightEyeTrans[10], rightEyeTrans[14],
262
+ rightEyeTrans[3], rightEyeTrans[7], rightEyeTrans[11], rightEyeTrans[15],
263
+ // right eye 4x4 projection matrix
264
+ rightEyeProj[0], rightEyeProj[4], rightEyeProj[8], rightEyeProj[12],
265
+ rightEyeProj[1], rightEyeProj[5], rightEyeProj[9], rightEyeProj[13],
266
+ rightEyeProj[2], rightEyeProj[6], rightEyeProj[10], rightEyeProj[14],
267
+ rightEyeProj[3], rightEyeProj[7], rightEyeProj[11], rightEyeProj[15],
268
+ // HMD 4x4 transform
269
+ hmdTrans[0], hmdTrans[4], hmdTrans[8], hmdTrans[12],
270
+ hmdTrans[1], hmdTrans[5], hmdTrans[9], hmdTrans[13],
271
+ hmdTrans[2], hmdTrans[6], hmdTrans[10], hmdTrans[14],
272
+ hmdTrans[3], hmdTrans[7], hmdTrans[11], hmdTrans[15],
273
+ ]);
274
+ this.lastSentLeftEyeProj = leftEyeProj;
275
+ this.lastSentRightEyeProj = rightEyeProj;
276
+ this.lastSentRelativeLeftEyePos = leftEyeRelativePos;
277
+ this.lastSentRelativeRightEyePos = rightEyeRelativePos;
278
+ }
279
+ else {
280
+ // If we don't need to the entire eye views being sent just send the HMD transform
281
+ this.webRtcController.streamMessageController.toStreamerHandlers.get('XRHMDTransform')([
282
+ // HMD 4x4 transform
283
+ hmdTrans[0],
284
+ hmdTrans[4],
285
+ hmdTrans[8],
286
+ hmdTrans[12],
287
+ hmdTrans[1],
288
+ hmdTrans[5],
289
+ hmdTrans[9],
290
+ hmdTrans[13],
291
+ hmdTrans[2],
292
+ hmdTrans[6],
293
+ hmdTrans[10],
294
+ hmdTrans[14],
295
+ hmdTrans[3],
296
+ hmdTrans[7],
297
+ hmdTrans[11],
298
+ hmdTrans[15]
299
+ ]);
300
+ }
301
+ }
302
+ onXrFrame(time, frame) {
303
+ this.xrViewerPose = frame.getViewerPose(this.xrRefSpace);
304
+ if (this.xrViewerPose) {
305
+ this.updateViews();
306
+ if (this.leftView == null || this.rightView == null) {
307
+ return;
308
+ }
309
+ this.sendXRDataToUE();
310
+ this.updateVideoTexture();
311
+ this.render();
312
+ }
313
+ if (this.webRtcController.config.isFlagEnabled(pixelstreamingfrontend_1.Flags.XRControllerInput)) {
314
+ this.xrSession.inputSources.forEach((source, _index, _array) => {
315
+ this.xrGamepadController.updateStatus(source, frame, this.xrRefSpace);
316
+ }, this);
317
+ }
318
+ this.xrSession.requestAnimationFrame((time, frame) => this.onXrFrame(time, frame));
319
+ this.onFrame.dispatchEvent(new EventEmitter_1.XrFrameEvent({ time, frame }));
320
+ }
321
+ updateViews() {
322
+ if (!this.xrViewerPose) {
323
+ return;
324
+ }
325
+ for (const view of this.xrViewerPose.views) {
326
+ if (view.eye === 'left') {
327
+ this.leftView = view;
328
+ }
329
+ else if (view.eye === 'right') {
330
+ this.rightView = view;
331
+ }
332
+ }
333
+ }
334
+ render() {
335
+ if (!this.gl) {
336
+ return;
337
+ }
338
+ // Bind the framebuffer to the base layer's framebuffer
339
+ const glLayer = this.xrSession.renderState.baseLayer;
340
+ this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, glLayer.framebuffer);
341
+ // Set the relevant portion of clip space
342
+ this.gl.viewport(0, 0, glLayer.framebufferWidth, glLayer.framebufferHeight);
343
+ // Draw the rectangle we will show the video stream texture on
344
+ this.gl.drawArrays(this.gl.TRIANGLES /*primitiveType*/, 0 /*offset*/, 6 /*count*/);
345
+ }
346
+ static isSessionSupported(mode) {
347
+ if (location.protocol !== 'https:') {
348
+ lib_pixelstreamingcommon_ue5_5_1.Logger.Info('WebXR requires https, if you want WebXR use https.');
349
+ }
350
+ if (navigator.xr) {
351
+ return navigator.xr.isSessionSupported(mode);
352
+ }
353
+ else {
354
+ return new Promise(() => {
355
+ return false;
356
+ });
357
+ }
358
+ }
359
+ }
360
+ exports.WebXRController = WebXRController;
361
361
  //# sourceMappingURL=WebXRController.js.map