Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Angular 13 compatibility #150

Closed
demisquare opened this issue Mar 30, 2022 · 8 comments
Closed

Angular 13 compatibility #150

demisquare opened this issue Mar 30, 2022 · 8 comments

Comments

@demisquare
Copy link

Hi, I'm trying to write an Angular 13 module using your React example at https://github.com/hiukim/mind-ar-js-react. While the A-Frame module works well, my camera is on but no image is shown.
I already tried with Safari and Chrome.

@krsbx
Copy link

krsbx commented Mar 31, 2022

@demisquare can you share your code, maybe i could help you that one
If you need a reference, maybe this wrapper in react could help you out Mind AR React

@demisquare
Copy link
Author

demisquare commented Mar 31, 2022

@krsbx As I read in #66 I noticed if I disable all UI features, the AR engine won't autostart. In addition, if I leave them enabled the camera won't show.

I installed libraries with npm, then I imported in the app.module.ts in this way:

import {CUSTOM_ELEMENTS_SCHEMA, NgModule} from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';

import { AppComponent } from './app.component';
import { MindarViewerComponent } from './mindar-viewer/mindar-viewer.component';

import 'mind-ar/dist/mindar-image.prod.js';
import 'aframe';
import 'mind-ar/dist/mindar-image-aframe.prod.js';

@NgModule({
  declarations: [
    AppComponent,
    MindarViewerComponent
  ],
  imports: [
    BrowserModule
  ],
  providers: [],
  bootstrap: [AppComponent],
  schemas: [CUSTOM_ELEMENTS_SCHEMA]
})
export class AppModule { }

Then, I created a MindAR viewer:

mindar-viewer.component.html

<button id="start-button">Start</button>
<a-scene #scene mindar-image="imageTargetSrc: https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.0.0/examples/image-tracking/assets/card-example/card.mind; uiLoading: no; uiError: no; uiScanning: no;" color-space="sRGB" embedded renderer="colorManagement: true, physicallyCorrectLights" vr-mode-ui="enabled: false" device-orientation-permission-ui="enabled: false">
  <a-assets>
    <img id="card" alt="card" crossorigin="anonymous" src="https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.0.0/examples/image-tracking/assets/card-example/card.png" />
    <a-asset-item id="avatarModel" src="https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.0.0/examples/image-tracking/assets/card-example/softmind/scene.gltf"></a-asset-item>
  </a-assets>

  <a-camera position="0 0 0" look-controls="enabled: false"></a-camera>

  <a-entity mindar-image-target="targetIndex: 0">
    <a-plane src="#card" position="0 0 0" height="0.552" width="1" rotation="0 0 0"></a-plane>
    <a-gltf-model rotation="0 0 0 " position="0 0 0.1" scale="0.005 0.005 0.005" src="#avatarModel" animation="property: position; to: 0 0.1 0.1; dur: 1000; easing: easeInOutQuad; loop: true; dir: alternate"></a-gltf-model>
  </a-entity>
</a-scene>

mindar-viewer.component.ts

import {AfterViewInit, Component, ElementRef, ViewChild} from '@angular/core';

@Component({
  selector: 'app-mindar-viewer',
  templateUrl: './mindar-viewer.component.html',
  styleUrls: ['./mindar-viewer.component.css']
})
export class MindarViewerComponent implements AfterViewInit {
  @ViewChild('scene', { read: ElementRef }) sceneRef!: ElementRef;

  ngAfterViewInit(): void {
    const sceneEl = this.sceneRef.nativeElement;
    const arSystem = sceneEl.systems["mindar-image-system"];
    
    const startButton = document.querySelector("#start-button");
    startButton?.addEventListener('click', () => {
      arSystem.start(); // start AR
      console.log("start");
    });
  }
}

Some screenshots:
MindAR viewer

Console output if I click on the start button:
MindAR console output

I also printed the output of arSystem and it returns undefined. I can't understand if I mistake something or that's a bug.

@krsbx
Copy link

krsbx commented Mar 31, 2022

I never use angular, but from what I see, probably you are referring to the wrong elements

I think you can start by checking does the element that you are trying to reference to is the correct one

make sure the sceneRef is referencing to the scene element in the template html file, if it's the correct one then you can check the arSystem does it has the systems attributes or not

@demisquare
Copy link
Author

I tried to print the output of sceneEl and it's okay, there's also a systems attribute. I also tried to print the other attributes and some of them return undefined even if are not empty. I think it's a problem of importing libraries in Angular, I don't know.

@krsbx
Copy link

krsbx commented Mar 31, 2022

I'll try to look at it tomorrow, let's see if it possible to make a wrapper for the angular as well

@krsbx
Copy link

krsbx commented Apr 1, 2022

@demisquare do you have a repo for this problem? If you do, can you share it in here so we could look into the problem much easier

@demisquare
Copy link
Author

@krsbx yes, but it's private at this moment. I'll share it in the next days.

@demisquare
Copy link
Author

demisquare commented Apr 8, 2022

UPDATE: I managed to run MindAR in Angular 13, even with UI widgets and autostart!

The start function of mindar-image-aframe.prod.js says:

start: function() {
        this.container = this.el.sceneEl.parentNode,
        this.showStats && (this.mainStats = new Stats,
          this.mainStats.showPanel(0),
          this.mainStats.domElement.style.cssText = "position:absolute;top:0px;left:0px;z-index:999",
          this.container.appendChild(this.mainStats.domElement)),
          this.ui.showLoading(),
          this._startVideo()
      }

If you call the parentNode method in an Angular component without any container wrapped into <a-scene>, it'll return the component itself, not the <div class='container'> outside like in the React example.

So, in the _resize function we have that clientWidth and clientHeight always return 0 cause there's not any style assigned in the container. And video doesn't appears.

_resize: function() {
        const t = this.video
          , e = this.container;
        let i, s;
        const a = t.videoWidth / t.videoHeight;
        a > e.clientWidth / e.clientHeight ? (s = e.clientHeight,
          i = s * a) : (i = e.clientWidth,
          s = i / a);
...
}

SOLUTION

You must wrap your <a-scene> into a <div> inside the component and then define a class which you have to define your width and height. In this way the parent of <a-scene> will be <div> and not <app-mindar-viewer>.

Example

app.component.html

<div class="app">
  <h1>Example Angular component</h1>
  <app-mindar-viewer></app-mindar-viewer>
</div>

mindar-viewer.component.html

<div class="container">
  <a-scene #scene mindar-image="imageTargetSrc: https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.1.4/examples/image-tracking/assets/card-example/card.mind; autoStart: false; uiError: no; uiScanning: no;" color-space="sRGB" embedded renderer="colorManagement: true, physicallyCorrectLights" vr-mode-ui="enabled: false" device-orientation-permission-ui="enabled: false">
    <a-assets>
      <img id="card" alt="card" crossorigin="anonymous" src="https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.1.4/examples/image-tracking/assets/card-example/card.png" />
      <a-asset-item id="avatarModel" src="https://cdn.jsdelivr.net/gh/hiukim/mind-ar-js@1.1.4/examples/image-tracking/assets/card-example/softmind/scene.gltf"></a-asset-item>
    </a-assets>

    <a-camera position="0 0 0" look-controls="enabled: false"></a-camera>

    <a-entity #target mindar-image-target="targetIndex: 0">
      <a-plane src="#card" position="0 0 0" height="0.552" width="1" rotation="0 0 0"></a-plane>
      <a-gltf-model rotation="0 0 0 " position="0 0 0.1" scale="0.005 0.005 0.005" src="#avatarModel"
                    animation="property: position; to: 0 0.1 0.1; dur: 1000; easing: easeInOutQuad; loop: true; dir: alternate"></a-gltf-model>
    </a-entity>
  </a-scene>
</div>

mindar-viewer.component.css

.container {
  display: block;
  margin: 20px auto;
  position: relative;
  height: 300px;
  width: 600px;
  max-width: 100%;
  overflow: hidden;
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants