Home > Mobile >  How to register components in Aframe using Nextjs?
How to register components in Aframe using Nextjs?

Time:12-06

I'm trying to create a VR scene using Aframe, and I want to register a custom Aframe component, with click events, as in the example.

I tried this:

import type { NextPage } from 'next';

import React, { useEffect, useState } from 'react';
import {
  Scene,
  Box,
  Sky,
  Entity,
  Assets
} from '@belivvr/aframe-react';

const Home: NextPage = () => {
  const [rendered, setRendered] = useState<boolean>(false);


  function register() {
    AFRAME.registerComponent('foo', {
      events: {
        click: function (evt: any) {
          console.log('This entity was clicked!');
        }
      }
    });
  }


  useEffect(() => {
    setRendered(true);
    if (typeof window !== 'undefined') {
      require('aframe');
      register();
    }
  }, [setRendered]);

  if (!rendered) {
    return <>loading</>;
  }

  return (
    <Scene>
      <Assets>
        <img id="sky" src="https://cdn.glitch.com/c52283d6-3489-44e4-b56b-43550d1bc76c/1.jpg?v=1564408735128" alt="sky" />
        <img id="hotspot" src="https://cdn.glitch.com/c52283d6-3489-44e4-b56b-43550d1bc76c/hotspot.png?v=1564471993959" />
      </Assets>
      <Box
        foo
        position={{ x: -1, y: 0.5, z: -3 }}
        rotation={{ x: 0, y: 45, z: 0 }}
        color="#4CC3D9"
      />
      <Entity>
        <Sky className="sky" src="#sky" rotation={{ x: 0, y: 0, z: 0 }} />
      </Entity>

    </Scene>
  );
};

export default Home;

But I receive the following error:

Unhandled Runtime Error
Error: The component `foo` has been already registered. Check that you are not loading two versions of the same component or two different components of the same name.

Does anyone have any idea how to work properly with Aframe and NextJs?

CodePudding user response:

You can check if component exists

function register() {
    if (AFRAME.components['foo']) return;

    AFRAME.registerComponent('foo', {
      events: {
        click: function (evt: any) {
          console.log('This entity was clicked!');
        }
      }
    });
  }

If you are using nextjs you can move this function to another file and import it using next/dynamic

CodePudding user response:

You can create a new module with your component defined within:

// foo.js
AFRAME.registerComponent('foo', {
  init: function() {
    console.log("FOO INIT!");
  }
});

And import it after a-frame:

useEffect(() => {
  setRendered(true);
  if (typeof window !== 'undefined') {
    require('aframe');
    require('foo');
  }
}, [setRendered]);

Keep in mind, that the component has to be registered before the scene is attached to the DOM (docs), but after requiring a-frame

  • Related