UNPKG

@vladkrutenyuk/three-kvy-core

Version:

Everything you need to create any-complexity 3D apps with Three.js. Empower Three.js with a modular, lifecycle-managed context that seamlessly propagates through objects via reusable features providing structured logic.

126 lines (125 loc) 6.58 kB
import { EventEmitter } from "eventemitter3"; import type * as THREE from "three"; import { CoreContextModule } from "./CoreContextModule"; import { IFeaturable } from "./Object3DFeaturablity"; import { ThreeContext, ThreeContextParams } from "./ThreeContext"; export type ModulesRecord = Record<string, CoreContextModule>; export type ModulesRecordDefault = Record<string, CoreContextModule & Record<string, any>>; /** * The primary central entity, acting as a main hub, that orchestrates the Three.js environment, animation loop, and module system.\ * Propagates through features `Object3DFeature` which are added to Three.js `Object3D`.\ * Provides an elegant lifecycle management system and handles fundametal initializations. * @see {@link https://three-kvy-core.vladkrutenyuk.ru/docs/api/core-context | Official Documentation} * @see {@link https://github.com/vladkrutenyuk/three-kvy-core/blob/main/src/core/CoreContext.ts | Source} */ export declare class CoreContext<TModules extends ModulesRecord = ModulesRecordDefault> extends EventEmitter<{ destroy: []; looprun: []; loopstop: []; }> { /** * Initialization shortcut. Creates and returns a new {@link CoreContext} instance. * @param {typeof import("three")} Three - Object containing Three.js class constructors `WebGLRenderer`, `Scene`, `PerspectiveCamera`, `Clock`, `Raycaster`. In short, just use imported [`THREE`](https://threejs.org/docs/manual/en/introduction/Installation.html) Three.js module. * @param {TModules} modules - (optional) Custom dictionary of any your modules {@link CoreContextModules}. * @param {ThreeContextParams} params - (optional) Object paramateres * @example * ```js * import * as THREE from "three"; * import * as KVY from "@vladkrutenyuk/three-kvy-core"; * * const modules = { * moduleA: new MyModuleA(), * moduleB: new MyModuleB(), * }; * const ctx = KVY.CoreContext.create(THREE, modules, { renderer: { antialias: true } }); * ``` * @returns {CoreContext} */ static create<TModules extends ModulesRecord = ModulesRecordDefault>(Three: { Scene: typeof THREE.Scene; WebGLRenderer: typeof THREE.WebGLRenderer; PerspectiveCamera: typeof THREE.PerspectiveCamera; Raycaster: typeof THREE.Raycaster; Clock: typeof THREE.Clock; }, modules?: Partial<TModules>, params?: ThreeContextParams): CoreContext<TModules>; /** (readonly) Flag to mark that it is an instance of {@link CoreContext}. */ readonly isCoreContext: true; /** (readonly) Instance of {@link ThreeContext}. Utility to manage Three.js setup. */ readonly three: ThreeContext; /** (readonly) Dictionary of assinged modules. * @type { { [key:string]: CoreContextModule } } */ readonly modules: TModules; /** * (readonly) Instance of Three.js `Object3D` that plays the role of entry point for a given context propagation.\ * By default, it's Three.js `Scene` instance given in `ThreeContext` of this (`this.root === this.three.scene`).\ * You can specify any other `root` if you initialize the context through constructor. * @type {THREE.Object3D} * */ get root(): IFeaturableRoot<TModules>; /** (readonly) The seconds passed since the last frame. */ get deltaTime(): number; /** (readonly) The seconds passed since the context loop started - by {@link run run()}. */ get time(): number; /** (readonly) Flag to check if this instance is destroyed. */ get isDestroyed(): boolean; /** (readonly) Flag to check if this instance loop is running. */ get isRunning(): boolean; private readonly _root; private readonly _clock; private _time; private _deltaTime; private _isDestroyed; private _isRunning; /** * This creates a new {@link CoreContext} instance. * @param three - An instance of {@link ThreeContext}. Utility to manage Three.js setup. * @param {THREE.Object3D} root - (optional) An instance of Three.js `Object3D`. The entry point for context propagation. If root is not providen then Three.js `Scene` from the given {@link ThreeContext} will be taken as root. * @param {TModules} modules - (optional) Custom dictionary of any your modules {@link CoreContextModules}. */ constructor(three: ThreeContext, root?: THREE.Object3D, modules?: Partial<TModules>); /** Run animation loop and Three.js rendering. Stoppable as many times as you need by `stop()`. */ run(): void; /** Stop animation loop and Three.js rendering. Resumable as many times as you need by `run()`. */ stop(): void; private _cleanups; /** * Assigns the given dictionary of modules to this instance. * It will be merged with the existing dictionary of modules. * * @remarks Note that if the given dictionary contains a key for which a module is already assigned, * it will be skipped, and a warning message will be fired. * * @param {{ [key: string]: CoreContextModule }} modules - Dictionary of module instances to assign to this context. */ assignModules(modules: Partial<TModules>): this; /** * Assign module by key to this instance. * It will be added to the existing dictionary of modules by the given key. * * @remarks Note that if the given key is already assigned, it will be skipped, and a warning message will be fired. * @param {string} key - The key by which to assign the module to the context in the dictionary. * @param {CoreContextModule} module - An instance of `CoreContextModule` implementation. * @returns */ assignModule<TKey extends keyof TModules>(key: TKey, module: TModules[TKey]): void; /** * Remove a module by key that was specified when it was assigned. * @param {string} key - key by which a module was assigned. */ removeModule(key: keyof TModules): void; /** * Destroy this instance. * - Sets {@link isDestroyed} to `true` permanently. * - Stops its animation loop permanently. * - Destroys its {@link three three}: {@link ThreeContext} permanently. * - Fires the `"destroy"` event. * - Cleans up {@link root} from the assigned logic when it was designated as `root` in the given CoreContext. * - Removes all assigned {@link modules}. * - Removes all listeners from its events. */ destroy(): this; } export interface IFeaturableRoot<TModules extends ModulesRecord = any> extends IFeaturable<TModules> { isRoot: true; }