@@ -15,14 +15,14 @@ import {
1515
1616import { Configuration , Role } from './common'
1717import { DefaultUIService } from './ui'
18- import { Event } from './utils'
18+ import { Event , isIOS , getEventSynthesizier , createEventForwarder , hasNativeWebVRImplementation } from './utils'
1919
2020import { EntityService , EntityServiceProvider } from './entity'
2121import { ContextService , ContextServiceProvider } from './context'
2222import { FocusService , FocusServiceProvider } from './focus'
2323import { DeviceService , DeviceServiceProvider } from './device'
2424import { RealityService , RealityServiceProvider } from './reality'
25- import { ViewService , ViewServiceProvider , ViewElement } from './view'
25+ import { ViewService , ViewServiceProvider , ViewItems , ViewportMode } from './view'
2626import { VisibilityService , VisibilityServiceProvider } from './visibility'
2727import { VuforiaService , VuforiaServiceProvider } from './vuforia'
2828import { PermissionService , PermissionServiceProvider } from './permission'
@@ -101,10 +101,102 @@ export class ArgonSystem {
101101
102102 if ( this . container . hasResolver ( ArgonSystemProvider ) )
103103 this . _provider = this . container . get ( ArgonSystemProvider ) ;
104+
105+ this . _setupDOM ( ) ;
104106
105107 this . session . connect ( ) ;
106108 }
107109
110+ private _setupDOM ( ) {
111+ const viewItems :ViewItems = this . container . get ( ViewItems ) ;
112+ const element = viewItems . element ;
113+
114+ if ( element && typeof document !== 'undefined' && document . createElement ) {
115+
116+ element . classList . add ( 'argon-view' ) ;
117+
118+ // prevent pinch-zoom of the page in ios 10.
119+ if ( isIOS ) {
120+ const touchMoveListener = ( event ) => {
121+ if ( event . touches . length > 1 )
122+ event . preventDefault ( ) ;
123+ }
124+ element . addEventListener ( 'touchmove' , touchMoveListener , true ) ;
125+ this . session . manager . closeEvent . addEventListener ( ( ) => {
126+ element . removeEventListener ( 'touchmove' , touchMoveListener )
127+ } ) ;
128+ }
129+
130+ // add/remove document-level css classes
131+ this . focus . focusEvent . addEventListener ( ( ) => {
132+ document . documentElement . classList . remove ( 'argon-no-focus' ) ;
133+ document . documentElement . classList . remove ( 'argon-blur' ) ;
134+ document . documentElement . classList . add ( 'argon-focus' ) ;
135+ } ) ;
136+
137+ this . focus . blurEvent . addEventListener ( ( ) => {
138+ document . documentElement . classList . remove ( 'argon-focus' ) ;
139+ document . documentElement . classList . add ( 'argon-blur' ) ;
140+ document . documentElement . classList . add ( 'argon-no-focus' ) ;
141+ } ) ;
142+
143+ this . view . viewportModeChangeEvent . addEventListener ( ( mode ) => {
144+ switch ( mode ) {
145+ case ViewportMode . EMBEDDED :
146+ document . documentElement . classList . remove ( 'argon-immersive' ) ;
147+ break ;
148+ case ViewportMode . IMMERSIVE :
149+ document . documentElement . classList . add ( 'argon-immersive' ) ;
150+ break ;
151+ }
152+ } ) ;
153+
154+ // Setup event forwarding / synthesizing
155+ if ( this . session . isRealityViewer ) {
156+ this . session . manager . on [ 'ar.view.uievent' ] = getEventSynthesizier ( ) ! ;
157+ } else {
158+ createEventForwarder ( this . view , ( event ) => {
159+ if ( this . session . manager . isConnected && this . session . manager . version [ 0 ] >= 1 )
160+ this . session . manager . send ( 'ar.view.forwardUIEvent' , event ) ;
161+ } ) ;
162+ this . view . _watchEmbeddedViewport ( ) ;
163+ }
164+
165+ this . context . renderEvent . addEventListener ( ( ) => {
166+ if ( this . view . autoStyleLayerElements ) {
167+ const layers = this . view . layers ;
168+ if ( ! layers ) return ;
169+
170+ const viewport = this . view . viewport ;
171+ let zIndex = - layers . length ;
172+ for ( const layer of layers ) {
173+ const layerStyle = layer . source . style ;
174+ layerStyle . position = 'absolute' ;
175+ layerStyle . left = viewport . x + 'px' ;
176+ layerStyle . bottom = viewport . y + 'px' ;
177+ layerStyle . width = viewport . width + 'px' ;
178+ layerStyle . height = viewport . height + 'px' ;
179+ layerStyle . zIndex = '' + zIndex ;
180+ zIndex ++ ;
181+ }
182+ }
183+ } ) ;
184+
185+ if ( ! this . session . isRealityAugmenter ) {
186+ this . view . viewportChangeEvent . addEventListener ( ( viewport ) => {
187+ if ( this . view . element && this . view . autoLayoutImmersiveMode &&
188+ this . view . viewportMode === ViewportMode . IMMERSIVE ) {
189+ const elementStyle = this . view . element . style ;
190+ elementStyle . position = 'fixed' ;
191+ elementStyle . left = viewport . x + 'px' ;
192+ elementStyle . bottom = viewport . y + 'px' ;
193+ elementStyle . width = viewport . width + 'px' ;
194+ elementStyle . height = viewport . height + 'px' ;
195+ }
196+ } )
197+ }
198+ }
199+ }
108200 public _provider :ArgonSystemProvider ;
109201 public get provider ( ) {
110202 this . session . ensureIsRealityManager ( ) ;
@@ -145,13 +237,39 @@ export class ArgonConfigurationManager {
145237
146238 constructor (
147239 public configuration :Configuration ,
148- public container :DI . Container = new DI . Container
240+ public container :DI . Container = new DI . Container ,
241+ public elementOrSelector ?:HTMLElement | string | null ,
149242 ) {
150243 container . registerInstance ( Configuration , configuration ) ;
151244
152245 if ( Role . isRealityManager ( configuration . role ) )
153246 container . registerSingleton ( ArgonSystemProvider ) ;
154247
248+ let element = elementOrSelector ;
249+ if ( ! element || typeof element === 'string' ) {
250+ if ( typeof document !== 'undefined' ) {
251+ const selector = element ;
252+ element = selector ? < HTMLElement > document . querySelector ( selector ) : undefined ;
253+ if ( ! element && ! selector ) {
254+ element = document . querySelector ( '#argon' ) as HTMLElement ;
255+ if ( ! element ) {
256+ element = document . createElement ( 'div' ) ;
257+ element . id = 'argon' ;
258+ document . body . appendChild ( element ) ;
259+ }
260+ } else if ( ! element ) {
261+ throw new Error ( 'Unable to find element with selector: ' + selector ) ;
262+ }
263+ } else {
264+ console . warn ( 'No DOM environment is available' ) ;
265+ element = undefined ;
266+ }
267+ }
268+
269+ const viewItems = new ViewItems ( ) ;
270+ viewItems . element = element ;
271+ container . registerInstance ( ViewItems , viewItems ) ;
272+
155273 ArgonConfigurationManager . configure ( this ) ;
156274 }
157275
@@ -254,7 +372,6 @@ export function init(
254372 }
255373
256374 if ( ! dependencyInjectionContainer ) dependencyInjectionContainer = new DI . Container ( ) ;
257- dependencyInjectionContainer . registerInstance ( ViewElement , element || null ) ;
258375
259376 return new ArgonConfigurationManager ( configuration , dependencyInjectionContainer ) . container . get ( ArgonSystem ) ;
260377}
0 commit comments