コンテンツにスキップ

Plugin

プラグインを実装するための API について説明します。プラグインシステムの概念については About Plugin を参照してください。

すべてのプラグインは Plugin 抽象クラスを継承して実装します。

import { Plugin } from "@navaramap/three";
abstract class Plugin<TView = unknown, TCtx = unknown> {
abstract init(view: TView, ctx: TCtx): Promise<void>;
}

Plugin クラスは意図的に最小限のインターフェースとして設計されており、init() メソッドのみを持ちます。

メソッド説明
init(view, ctx)プラグインの初期化処理。view.init() の中で自動的に呼び出される
パラメータ説明
TViewinit() に渡される view の型。通常は ThreeView または ThreeView<MyDescriptions> を指定します。
TCtxinit() に渡されるコンテキストの型。ViewContext を指定すると、レンダラー、バッファ、パス管理 API にアクセスできます。

プラグインは以下のタイミングで動作します:

  1. view.addPlugin(plugin): プラグインを登録(view.init()に呼び出す必要あり)
  2. view.init(): 登録済みのすべてのプラグインの init()並列に実行される
view.addPlugin(pluginA)
view.addPlugin(pluginB)
await view.init()
├── レンダーパス初期化
├── Promise.all([pluginA.init(view, ctx), pluginB.init(view, ctx)]) ← 並列実行
└── メインループ開始

Descriptor の登録をカプセル化する基本的なプラグインの例です。

import ThreeView, { Plugin, type ViewContext } from "@navaramap/three";
import {
BoxMeshDesc,
SphereMeshDesc,
SunLightDesc,
AmbientLightDesc,
FXAAEffectDesc,
} from "@navaramap/three-default-descs";
class MyScenePlugin extends Plugin<ThreeView, ViewContext> {
async init(view: ThreeView, _ctx: ViewContext) {
// メッシュ Descriptor の登録
view.registerMesh("box", BoxMeshDesc);
view.registerMesh("sphere", SphereMeshDesc);
// ライト Descriptor の登録
view.registerLight("sun", SunLightDesc);
view.registerLight("ambient", AmbientLightDesc);
// エフェクト Descriptor の登録
view.registerEffect("fxaa", FXAAEffectDesc);
}
}
// 使用例
const plugin = new MyScenePlugin();
const view = new ThreeView({});
view.addPlugin(plugin);
await view.init();
// プラグインで登録した Descriptor が利用可能
view.addMesh({ box: { width: 100, height: 100, depth: 100 } });
view.addLight({ sun: { intensity: 1.0 } });

高レベル API を提供するプラグイン

Section titled “高レベル API を提供するプラグイン”

init() 内で Descriptor を登録するだけでなく、初期化後に呼び出すメソッドを提供することもできます。

import ThreeView, { Plugin, type ViewContext, type BaseHandle } from "@navaramap/three";
import {
SkyMeshDesc,
SunLightDesc,
AmbientLightDesc,
ToneMappingEffectDesc,
FXAAEffectDesc,
} from "@navaramap/three-default-descs";
class MyScenePlugin extends Plugin<ThreeView, ViewContext> {
private view?: ThreeView;
async init(view: ThreeView, _ctx: ViewContext) {
this.view = view;
view.registerMesh("sky", SkyMeshDesc);
view.registerLight("sun", SunLightDesc);
view.registerLight("ambient", AmbientLightDesc);
view.registerEffect("toneMapping", ToneMappingEffectDesc);
view.registerEffect("fxaa", FXAAEffectDesc);
}
/** シーンに基本的な照明とエフェクトを追加する */
setupScene(): {
sky: BaseHandle<SkyMeshDesc>;
sun: BaseHandle<SunLightDesc>;
} {
if (!this.view) throw new Error("Plugin is not initialized");
const sky = this.view.addMesh<SkyMeshDesc>({ sky: {} });
const sun = this.view.addLight<SunLightDesc>({
sun: { intensity: 1.0, castShadow: true },
});
this.view.addLight({ ambient: { intensity: 0.3 } });
this.view.addEffect({ toneMapping: {} });
this.view.addEffect({ fxaa: {} });
return { sky, sun };
}
}
const plugin = new MyScenePlugin();
const view = new ThreeView({});
view.addPlugin(plugin);
await view.init();
// 初期化後にプラグインのメソッドを呼び出す
const { sky, sun } = plugin.setupScene();

カスタム Descriptor を含むプラグイン

Section titled “カスタム Descriptor を含むプラグイン”

独自に実装したカスタム Descriptor(Custom Descriptor を参照)を登録するプラグインも作成できます。

import ThreeView, { Plugin, type ViewContext } from "@navaramap/three";
import { MyCustomMeshDesc } from "./layers/MyCustomMeshDesc";
import { MyCustomEffectDesc } from "./layers/MyCustomEffectDesc";
class MyCustomPlugin extends Plugin<ThreeView, ViewContext> {
async init(view: ThreeView, _ctx: ViewContext) {
view.registerMesh("myCustomMesh", MyCustomMeshDesc);
view.registerEffect("myCustomEffect", MyCustomEffectDesc);
}
}