API

Component

Component API reference

Provides access to a component instance of a specified component type.

Example: This is how you implement extend this class to create your own custom component:

 1import { Component, Type } from '@wonderlandengine/api';
 2
 3export class MyComponent extends Component {
 4    static TypeName = 'my-component';
 5    static Properties = {
 6        myBoolean: { type: Type.Boolean, default: false },
 7    };
 8    start() {}
 9    onActivate() {}
10    onDeactivate() {}
11    update(dt) {}
12}

.InheritProperties: boolean 

When set to true, the child class inherits from the parent properties, as shown in the following example:

 1import {Component, Property} from '@wonderlandengine/api';
 2
 3class Parent extends Component {
 4    static TypeName = 'parent';
 5    static Properties = {parentName: Property.string('parent')}
 6}
 7
 8class Child extends Parent {
 9    static TypeName = 'child';
10    static Properties = {name: Property.string('child')}
11    static InheritProperties = true;
12
13    start() {
14        // Works because `InheritProperties` is `true`.
15        console.log(`${this.name} inherits from ${this.parentName}`);
16    }
17}

Note: Properties defined in descendant classes will override properties with the same name defined in ancestor classes.

Defaults to true.

.Properties: Record<string, ComponentProperty

Properties of this component class.

Properties are public attributes that can be configured via the Wonderland Editor.

Example:

1import { Component, Type } from '@wonderlandengine/api';
2class MyComponent extends Component {
3    static TypeName = 'my-component';
4    static Properties = {
5        myBoolean: { type: Type.Boolean, default: false },
6        myFloat: { type: Type.Float, default: false },
7        myTexture: { type: Type.Texture, default: null },
8    };
9}

Properties are automatically added to each component instance, and are accessible like any JS attribute:

 1// Creates a new component and set each properties value:
 2const myComponent = object.addComponent(MyComponent, {
 3    myBoolean: true,
 4    myFloat: 42.0,
 5    myTexture: null
 6});
 7
 8// You can also override the properties on the instance:
 9myComponent.myBoolean = false;
10myComponent.myFloat = -42.0;

References 

Reference types (i.e., mesh, object, etc…) can also be listed as required:

 1import {Component, Property} from '@wonderlandengine/api';
 2
 3class MyComponent extends Component {
 4    static Properties = {
 5        myObject: Property.object({required: true}),
 6        myAnimation: Property.animation({required: true}),
 7        myTexture: Property.texture({required: true}),
 8        myMesh: Property.mesh({required: true}),
 9    }
10}

Please note that references are validated once before the call to start only, via the validateProperties method.

.TypeName: string 

Unique identifier for this component class.

This is used to register, add, and retrieve components of a given type.

.onRegister: (engine: WonderlandEngine) ⇒ void 

Called when this component class is registered.

Example: This callback can be used to register dependencies of a component, e.g., component classes that need to be registered in order to add them at runtime with addComponent, independent of whether they are used in the editor.

1class Spawner extends Component {
2    static TypeName = 'spawner';
3
4    static onRegister(engine) {
5        engine.registerComponent(SpawnedComponent);
6    }
7
8    // You can now use addComponent with SpawnedComponent
9}

Example: This callback can be used to register different implementations of a component depending on client features or API versions.

 1// Properties need to be the same for all implementations!
 2const SharedProperties = {};
 3
 4class Anchor extends Component {
 5    static TypeName = 'spawner';
 6    static Properties = SharedProperties;
 7
 8    static onRegister(engine) {
 9        if(navigator.xr === undefined) {
10            /* WebXR unsupported, keep this dummy component */
11            return;
12        }
13        /* WebXR supported! Override already registered dummy implementation
14         * with one depending on hit-test API support */
15        engine.registerComponent(window.HitTestSource === undefined ?
16            AnchorWithoutHitTest : AnchorWithHitTest);
17    }
18
19    // This one implements no functions
20}

.active: boolean 

Whether this component is active

.active 

Set whether this component is active.

Activating/deactivating a component comes at a small cost of reordering components in the respective component manager. This function therefore is not a trivial assignment.

Does nothing if the component is already activated/deactivated.

.engine: WonderlandEngine 

Hosting engine instance.

.isDestroyed: boolean 

1.1.1+

true if the component is destroyed, false otherwise.

If erasePrototypeOnDestroy is true, reading a custom property will not work:

1engine.erasePrototypeOnDestroy = true;
2
3const comp = obj.addComponent('mesh');
4comp.customParam = 'Hello World!';
5
6console.log(comp.isDestroyed); // Prints `false`
7comp.destroy();
8console.log(comp.isDestroyed); // Prints `true`
9console.log(comp.customParam); // Throws an error

.object: Object3D 

The object this component is attached to.

.type: string 

The name of this component’s type

.copy(src: Record<string, any>) ⇒ Component 

Copy all the properties from src into this instance.

Note: Only properties are copied. If a component needs to copy extra data, it needs to override this method.

Example: ```js class MyComponent extends Component { nonPropertyData = ‘Hello World’;

copy(src) {
    super.copy(src);
    this.nonPropertyData = src.nonPropertyData;
    return this;
}

}

 1
 2***Note:*** This method is called by [clone](/jsapi/object3d/#clone). Do not attempt to:
 3    - Create new component
 4    - Read references to other objects
 5
 6When cloning via [clone](/jsapi/object3d/#clone), this method will be called before
 7[start](/jsapi/component/#start).
 8
 9***Note:*** JavaScript component properties aren't retargeted. Thus, references
10inside the source object will not be retargeted to the destination object,
11at the exception of the skin data on [MeshComponent](/jsapi/meshcomponent/) and [AnimationComponent](/jsapi/animationcomponent/).
12
13***Returns:*** Reference to self (for method chaining).
14
15| Param | Type | Description |
16| --- | --- | --- |
17| src | [Record](https://www.typescriptlang.org/docs/handbook/utility-types.html)<[string](https://developer.mozilla.org/en-US/docs/Glossary/string), [any](https://www.typescriptlang.org/docs/handbook/basic-types.html#any)> | The source component to copy from. |
18
19### .destroy() ⇒ [void](https://www.typescriptlang.org/docs/handbook/basic-types.html#void) {#destroy}
20
21
22
230.9.0+

24
25Remove this component from its objects and destroy it.
26
27It is best practice to set the component to `null` after,
28to ensure it does not get used later.
29
30```js
31   c.destroy();
32   c = null;

.equals(otherComponent: undefined | null | Component) ⇒ boolean 

Checks equality by comparing whether the wrapped native component ids and component manager types are equal.

Returns: Whether this component equals the given component.

ParamTypeDescription
otherComponentundefined | null | ComponentComponent to check equality with.

.init() ⇒ void 

Triggered when the component is initialized by the runtime. This method will only be triggered once after instantiation.

.onActivate() ⇒ void 

Triggered when the component goes from an inactive state to an active state.

Note: You can manually activate or deactivate a component using: active.

.onDeactivate() ⇒ void 

Triggered when the component goes from an activated state to an inactive state.

Note: You can manually activate or deactivate a component using: active.

.onDestroy() ⇒ void 

0.9.0+

Triggered when the component is removed from its object.

Note: You can remove a component using: destroy.

.reset() ⇒ Component 

Deprecated: Use resetProperties instead.

.resetProperties() ⇒ Component 

Reset the component properties to default.

Note: This is automatically called during the component instantiation.

Returns: Reference to self (for method chaining).

.start() ⇒ void 

Triggered when the component is started by the runtime, or activated.

You can use that to re-initialize the state of the component.

.update(delta: number) ⇒ void 

Triggered every frame by the runtime.

You should perform your business logic in this method. Example:

 1import { Component, Type } from '@wonderlandengine/api';
 2
 3class TranslateForwardComponent extends Component {
 4    static TypeName = 'translate-forward-component';
 5    static Properties = {
 6        speed: { type: Type.Float, default: 1.0 }
 7    };
 8    constructor() {
 9        this._forward = new Float32Array([0, 0, 0]);
10    }
11    update(dt) {
12        this.object.getForward(this._forward);
13        this._forward[0] *= this.speed;
14        this._forward[1] *= this.speed;
15        this._forward[2] *= this.speed;
16        this.object.translate(this._forward);
17    }
18}
ParamTypeDescription
deltanumberElapsed time between this frame and the previous one, in seconds.

.validateProperties() ⇒ void 

Validate the properties on this instance.

Throws: If any of the required properties isn’t initialized on this instance.