@caperjs/plugin-3d 0.0.0-stage → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +190 -2
- package/lib/Entity3D.d.ts +28 -0
- package/lib/Entity3D.d.ts.map +1 -0
- package/lib/Model.d.ts +13 -0
- package/lib/Model.d.ts.map +1 -0
- package/lib/Plugin3D.d.ts +20 -0
- package/lib/Plugin3D.d.ts.map +1 -0
- package/lib/View3D.d.ts +58 -0
- package/lib/View3D.d.ts.map +1 -0
- package/lib/caper-plugin-3d.mjs +396 -0
- package/lib/caper-plugin-3d.mjs.map +1 -0
- package/lib/factory3d.d.ts +34 -0
- package/lib/factory3d.d.ts.map +1 -0
- package/lib/fit.d.ts +7 -0
- package/lib/fit.d.ts.map +1 -0
- package/lib/index.d.ts +14 -0
- package/lib/index.d.ts.map +1 -0
- package/lib/owned.d.ts +22 -0
- package/lib/owned.d.ts.map +1 -0
- package/lib/props.d.ts +60 -0
- package/lib/props.d.ts.map +1 -0
- package/lib/quality.d.ts +9 -0
- package/lib/quality.d.ts.map +1 -0
- package/lib/renderer.d.ts +2 -0
- package/lib/renderer.d.ts.map +1 -0
- package/lib/version.d.ts +2 -0
- package/lib/version.d.ts.map +1 -0
- package/package.json +46 -3
- package/src/Entity3D.ts +72 -0
- package/src/Model.ts +73 -0
- package/src/Plugin3D.ts +35 -0
- package/src/View3D.ts +173 -0
- package/src/factory3d.ts +188 -0
- package/src/fit.ts +10 -0
- package/src/index.ts +13 -0
- package/src/owned.ts +42 -0
- package/src/props.ts +96 -0
- package/src/quality.ts +12 -0
- package/src/renderer.ts +22 -0
- package/src/version.ts +1 -0
package/README.md
CHANGED
|
@@ -1,3 +1,191 @@
|
|
|
1
|
-
#
|
|
1
|
+
# @caperjs/plugin-3d
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
**Experimental** — `@pixi/3d` is in open beta; this package pins an exact version and the API
|
|
4
|
+
we expose may change until upstream stabilizes.
|
|
5
|
+
|
|
6
|
+
Official 3D for [Caper](https://github.com/anthonysapp/caper) games, built on Pixi's
|
|
7
|
+
[`@pixi/3d`](https://pixijs.com/3d). A `View3D` is a normal node on the 2D stage; lights,
|
|
8
|
+
models, and meshes live in a separate tree inside it. Interactive 2D UI you add **after** the
|
|
9
|
+
view draws on top and receives taps first.
|
|
10
|
+
|
|
11
|
+
## Install
|
|
12
|
+
|
|
13
|
+
```bash
|
|
14
|
+
npx caper add 3d
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
Then `npx caper doctor`. The command:
|
|
18
|
+
|
|
19
|
+
- Installs `@caperjs/plugin-3d`, `@pixi/3d` at the pin this package expects, and `pixi.js` only if
|
|
20
|
+
yours is older than the version Caper pins; announces packages and the install command before running it.
|
|
21
|
+
- Adds `'3d'` to `plugins` in `caper.config.ts` (or prints the line if there is no `plugins` array).
|
|
22
|
+
- Creates `src/scenes/Sample3DScene.ts` when missing (never overwrites).
|
|
23
|
+
- On pnpm ≥ 10.16, may add `@pixi/3d` to `minimumReleaseAgeExclude` in `pnpm-workspace.yaml`.
|
|
24
|
+
|
|
25
|
+
### By hand
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
pnpm add @caperjs/plugin-3d @pixi/3d@0.1.0
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Peers: `@caperjs/core` (requires `pixi.js@8.23.0`), `pixi.js`, `@pixi/3d@0.1.0` (exact). Add `'3d'`
|
|
32
|
+
to `plugins` in `caper.config.ts`. On **pnpm 11**, you may need
|
|
33
|
+
`minimumReleaseAgeExclude: ['@pixi/3d@0.1.0']` in `pnpm-workspace.yaml`; `caper add 3d` adds it when
|
|
34
|
+
needed.
|
|
35
|
+
|
|
36
|
+
## Use
|
|
37
|
+
|
|
38
|
+
```ts
|
|
39
|
+
// caper.config.ts
|
|
40
|
+
export default defineConfig({
|
|
41
|
+
plugins: [
|
|
42
|
+
'3d',
|
|
43
|
+
// or, with options:
|
|
44
|
+
// ['3d', { options: { quality: 'low' } }],
|
|
45
|
+
],
|
|
46
|
+
});
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
```ts
|
|
50
|
+
// any Scene
|
|
51
|
+
const view = this.add.view3d({
|
|
52
|
+
camera: { position: [0, 1.5, 4], lookAt: [0, 0, 0] },
|
|
53
|
+
});
|
|
54
|
+
const hero = view.add.model({ asset: 'robot', y: 0 });
|
|
55
|
+
view.add.light({ type: 'directional', intensity: 2, castShadow: true });
|
|
56
|
+
const cube = view.add.mesh({ geometry: 'box', color: 0xe85d5d, x: -1 });
|
|
57
|
+
hero.play('Walking');
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
Put self-contained `.glb` files in your assets folder (AssetPack pass-through). v1 supports
|
|
61
|
+
**.glb only** — multi-file `.gltf` and `.hdr` are not tested.
|
|
62
|
+
|
|
63
|
+
## Animation
|
|
64
|
+
|
|
65
|
+
`model.play(name, options?)` replaces whatever is playing and restarts the clip from the start
|
|
66
|
+
(unlike 0.7, which layered by default). Use `layer: true` to blend on purpose. Options
|
|
67
|
+
(`loop`, `fade`, `onComplete`, …) do not carry over to the next call. A replaced clip does not run
|
|
68
|
+
its previous `onComplete`.
|
|
69
|
+
|
|
70
|
+
```ts
|
|
71
|
+
model.play('Walking');
|
|
72
|
+
model.play('Wave', { loop: false, fade: 0.2, onComplete: () => model.play('Walking') });
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
## Entities
|
|
76
|
+
|
|
77
|
+
Declare a 3D game object the way you declare any Caper entity, on the `Entity3D` base class.
|
|
78
|
+
Scaffold with `npx caper add entity <Name> --3d`.
|
|
79
|
+
|
|
80
|
+
```ts
|
|
81
|
+
// src/entities/Car.ts
|
|
82
|
+
import { defineEntity } from '@caperjs/core';
|
|
83
|
+
import { Entity3D } from '@caperjs/plugin-3d';
|
|
84
|
+
|
|
85
|
+
export const entity = defineEntity({ id: 'car' });
|
|
86
|
+
|
|
87
|
+
export default class Car extends Entity3D<{ color?: number }> {
|
|
88
|
+
added() {
|
|
89
|
+
// this.add / this.make are the 3D factory, parented to the entity
|
|
90
|
+
this.add.mesh({ geometry: 'box', color: this.props.color ?? 0xd9534f, scale: [2, 0.6, 1] });
|
|
91
|
+
}
|
|
92
|
+
update() {
|
|
93
|
+
this.rotation.y += 0.02 * this.app.ticker.deltaTime;
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
```ts
|
|
99
|
+
const car = view.add.entity('car', { color: 0x4a90d9, x: -2, y: 0.3 });
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
- `id`, props and the returned instance are typed from the class. Only ids whose class extends
|
|
103
|
+
`Container3D` are accepted; `this.add.entity('car')` on a 2D container is a type error.
|
|
104
|
+
- `view.add.entity` applies the placement props (`position`, `rotation`, `scale`, `x` / `y` / `z`,
|
|
105
|
+
`visible`, `lookAt`, `parent`); the rest are the entity's own, on `this.props`.
|
|
106
|
+
- Build parts in `added()`, not in the constructor: the entity's factory belongs to the view it is
|
|
107
|
+
in. What it creates is freed with that view, and its models' clips follow `app.ticker`.
|
|
108
|
+
- `update()` runs every frame while the entity is in the scene, and stops with `app.pause()`.
|
|
109
|
+
- `view.make.entity` builds without parenting; `this.add.entity(...)` inside an entity nests one.
|
|
110
|
+
- `entity.on('pointertap', …)` opts the entity into picking on itself and passive parts (set
|
|
111
|
+
`eventMode = 'static'` yourself for property handlers).
|
|
112
|
+
|
|
113
|
+
## Many meshes: share one material
|
|
114
|
+
|
|
115
|
+
`color` gives each mesh its own material for the life of the view; materials are never shared by
|
|
116
|
+
colour behind your back. For a spawner, make one material and pass it. The view frees it.
|
|
117
|
+
|
|
118
|
+
```ts
|
|
119
|
+
const red = view.make.material({ color: 0xd9534f, roughness: 0.6 });
|
|
120
|
+
for (let i = 0; i < 200; i++) view.add.mesh({ geometry: 'box', material: red, x: i });
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
`color` is shorthand for `baseColor`; every other key is a raw `Material3D` option. Writing to
|
|
124
|
+
`red` recolours every mesh that uses it. (`view.add.material` is the same function: a material has
|
|
125
|
+
no parent.) A `new Material3D(...)` you build yourself also works and stays yours to destroy.
|
|
126
|
+
|
|
127
|
+
## Portrait screens
|
|
128
|
+
|
|
129
|
+
Optional `camera.fitAspect` on props cameras (not a raw `Camera3D`) is the width/height ratio you
|
|
130
|
+
frame for (e.g. `16 / 9`). On a narrower view, vertical FOV grows so the same width stays in frame.
|
|
131
|
+
|
|
132
|
+
```ts
|
|
133
|
+
const view = this.add.view3d({
|
|
134
|
+
camera: { position: [0, 1.5, 4], lookAt: [0, 0, 0], fitAspect: 16 / 9 },
|
|
135
|
+
});
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
## Quality
|
|
139
|
+
|
|
140
|
+
Plugin option `quality: 'auto' | 'low' | 'high'` (default `'auto'`):
|
|
141
|
+
|
|
142
|
+
| Value | Shadows | Resolution cap |
|
|
143
|
+
| --- | --- | --- |
|
|
144
|
+
| `high` | high | inherit |
|
|
145
|
+
| `low` | low | capped at 1 |
|
|
146
|
+
| `auto` | low on mobile, medium otherwise | cap 2 on mobile, inherit on desktop |
|
|
147
|
+
|
|
148
|
+
Per-view `shadowQuality` and `resolution` props override the global default.
|
|
149
|
+
|
|
150
|
+
## Interaction
|
|
151
|
+
|
|
152
|
+
`interactive` on the view (default `true`):
|
|
153
|
+
|
|
154
|
+
- `true` → `eventMode: 'static'`: 3D picking on; the view's rectangle captures taps, so put
|
|
155
|
+
buttons and HUD **above** the view in the 2D tree.
|
|
156
|
+
- `false` → `eventMode: 'none'`: taps pass through to 2D behind the view; no 3D picking.
|
|
157
|
+
|
|
158
|
+
Do not use `'passive'` on the view: it disables picking and still blocks taps to 2D behind the view.
|
|
159
|
+
|
|
160
|
+
`view.pin(2dNode, target3d, { offset? })` keeps a 2D node over a 3D point (updates each frame;
|
|
161
|
+
the view owns `visible` while pinned).
|
|
162
|
+
|
|
163
|
+
## Boot cost
|
|
164
|
+
|
|
165
|
+
Opting in loads `@pixi/3d` in the **pre-renderer** phase, before the Pixi renderer is created.
|
|
166
|
+
That is required for 3D to work, but it means every app start pays roughly **~490 KB raw /
|
|
167
|
+
~155 KB gzip** even if no scene uses 3D. The import pulls both WebGL and WebGPU backend
|
|
168
|
+
chunks at boot. Apps without `'3d'` in `plugins` pay nothing.
|
|
169
|
+
|
|
170
|
+
## Teardown
|
|
171
|
+
|
|
172
|
+
Never destroy a loaded model or the view with `{ material: true }` (or blanket geometry flags
|
|
173
|
+
on glTF nodes): glTF materials are shared on the cached source and the next visit crashes every
|
|
174
|
+
frame. The plugin destroys only geometry and materials **it** created; models use
|
|
175
|
+
`{ children: true }` only.
|
|
176
|
+
|
|
177
|
+
Nodes made by a view's factory belong to that view: the built-in geometry, `color` materials and
|
|
178
|
+
`make.material` materials are freed when the view is destroyed, so do not keep such a node alive past its view. A raw
|
|
179
|
+
`geometry` or `material` you pass in stays yours to destroy.
|
|
180
|
+
|
|
181
|
+
## Types
|
|
182
|
+
|
|
183
|
+
No import needed in scenes: with `'3d'` in `plugins` and this package installed, regenerated
|
|
184
|
+
`src/types/caper-app.d.ts` includes `import type {} from '@caperjs/plugin-3d'` so
|
|
185
|
+
`this.add.view3d` typechecks. When AssetPack ships `.glb`/`.gltf` models, `caper-assets.d.ts`
|
|
186
|
+
defines `AssetModels`; `view.add.model({ asset: '…' })` only accepts known manifest names or a
|
|
187
|
+
loaded `Scene3DSource` (`asset: await Assets.load(url)`).
|
|
188
|
+
|
|
189
|
+
## License
|
|
190
|
+
|
|
191
|
+
MIT
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { Container3D } from '@pixi/3d';
|
|
2
|
+
import { Factory3D } from './factory3d';
|
|
3
|
+
type Listen<Self> = (event: string | symbol, fn: (...args: any[]) => void, context?: any) => Self;
|
|
4
|
+
declare const Entity3D_base: typeof Container3D & import('@caperjs/core').Constructor<import('@caperjs/core').ISignalContainer> & import('@caperjs/core').Constructor<import('@caperjs/core').ILifecycle>;
|
|
5
|
+
/**
|
|
6
|
+
* Base class for 3D entities: a `Container3D` with the Caper lifecycle (`added` / `removed` / `update`),
|
|
7
|
+
* signals, and its own 3D factory. Declare one like any entity (`defineEntity` + default export under
|
|
8
|
+
* `src/entities/`) and build it with `view.add.entity(id, props)`.
|
|
9
|
+
*
|
|
10
|
+
* Build parts in `added()`, not in the constructor: `this.add` / `this.make` belong to the view the entity is
|
|
11
|
+
* in, so they work once it has been added to one. Parts are parented to the entity; the resources they
|
|
12
|
+
* create are freed with the view, and model animations are driven by the view.
|
|
13
|
+
* Adding a pointer listener makes a passive entity interactive so it hears taps on its parts.
|
|
14
|
+
*/
|
|
15
|
+
export declare class Entity3D<Props = void> extends Entity3D_base {
|
|
16
|
+
readonly props: Props;
|
|
17
|
+
private factories?;
|
|
18
|
+
constructor(props?: Props);
|
|
19
|
+
on: Container3D['on'] & Listen<this>;
|
|
20
|
+
once: Container3D['once'] & Listen<this>;
|
|
21
|
+
/** Listening is the opt-in: a passive ancestor is skipped when a part's event bubbles. */
|
|
22
|
+
private enablePointerEvents;
|
|
23
|
+
get add(): Factory3D;
|
|
24
|
+
get make(): Factory3D;
|
|
25
|
+
private resolveFactories;
|
|
26
|
+
}
|
|
27
|
+
export {};
|
|
28
|
+
//# sourceMappingURL=Entity3D.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Entity3D.d.ts","sourceRoot":"","sources":["../src/Entity3D.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAGvC,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAK7C,KAAK,MAAM,CAAC,IAAI,IAAI,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,EAAE,EAAE,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,IAAI,EAAE,OAAO,CAAC,EAAE,GAAG,KAAK,IAAI,CAAC;;AAElG;;;;;;;;;GASG;AACH,qBAAa,QAAQ,CAAC,KAAK,GAAG,IAAI,CAAE,SAAQ,aAAuC;IACjF,QAAQ,CAAC,KAAK,EAAE,KAAK,CAAC;IACtB,OAAO,CAAC,SAAS,CAAC,CAAsD;gBAE5D,KAAK,CAAC,EAAE,KAAK;IAQhB,EAAE,EAAE,WAAW,CAAC,IAAI,CAAC,GAAG,MAAM,CAAC,IAAI,CAAC,CAGN;IAE9B,IAAI,EAAE,WAAW,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,CAAC,CAGR;IAEzC,0FAA0F;IAC1F,OAAO,CAAC,mBAAmB;IAM3B,IAAI,GAAG,IAAI,SAAS,CAEnB;IAED,IAAI,IAAI,IAAI,SAAS,CAEpB;IAED,OAAO,CAAC,gBAAgB;CAczB"}
|
package/lib/Model.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { Model3D, AnimationState } from '@pixi/3d';
|
|
2
|
+
import { Ticker } from 'pixi.js';
|
|
3
|
+
export type PlayOptions = Partial<Pick<AnimationState, 'loop' | 'animationSpeed' | 'weight' | 'onComplete' | 'onLoop'>> & {
|
|
4
|
+
fade?: number;
|
|
5
|
+
layer?: boolean;
|
|
6
|
+
};
|
|
7
|
+
export declare class Model extends Model3D {
|
|
8
|
+
private transition?;
|
|
9
|
+
play(name: string, options?: PlayOptions): AnimationState;
|
|
10
|
+
stop(): void;
|
|
11
|
+
update(ticker: Ticker): void;
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=Model.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Model.d.ts","sourceRoot":"","sources":["../src/Model.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,UAAU,CAAC;AACnC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,UAAU,CAAC;AAC/C,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AAEtC,MAAM,MAAM,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,cAAc,EAAE,MAAM,GAAG,gBAAgB,GAAG,QAAQ,GAAG,YAAY,GAAG,QAAQ,CAAC,CAAC,GAAG;IACxH,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB,CAAC;AAIF,qBAAa,KAAM,SAAQ,OAAO;IAChC,OAAO,CAAC,UAAU,CAAC,CAAO;IAE1B,IAAI,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,GAAE,WAAgB,GAAG,cAAc;IAuC7D,IAAI,IAAI,IAAI;IAKZ,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI;CAc7B"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { Plugin, IApplication, IPlugin } from '@caperjs/core';
|
|
2
|
+
import { View3D, View3DProps } from './View3D';
|
|
3
|
+
import { Quality3D } from './quality';
|
|
4
|
+
export interface Plugin3DOptions {
|
|
5
|
+
quality: Quality3D;
|
|
6
|
+
}
|
|
7
|
+
export interface IPlugin3D extends IPlugin<Plugin3DOptions> {
|
|
8
|
+
}
|
|
9
|
+
declare module '@caperjs/core' {
|
|
10
|
+
interface FactoryMethodOverrides {
|
|
11
|
+
view3d: (props?: View3DProps) => View3D;
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
export declare class Plugin3D extends Plugin<Plugin3DOptions> implements IPlugin3D {
|
|
15
|
+
id: string;
|
|
16
|
+
initialize(options?: Partial<Plugin3DOptions>): void;
|
|
17
|
+
postInitialize(app: IApplication): void;
|
|
18
|
+
}
|
|
19
|
+
export default Plugin3D;
|
|
20
|
+
//# sourceMappingURL=Plugin3D.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Plugin3D.d.ts","sourceRoot":"","sources":["../src/Plugin3D.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAA0B,MAAM,eAAe,CAAC;AAC/D,OAAO,KAAK,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AAC3D,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAClC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAC5C,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AAG3C,MAAM,WAAW,eAAe;IAC9B,OAAO,EAAE,SAAS,CAAC;CACpB;AACD,MAAM,WAAW,SAAU,SAAQ,OAAO,CAAC,eAAe,CAAC;CAAG;AAE9D,OAAO,QAAQ,eAAe,CAAC;IAC7B,UAAU,sBAAsB;QAC9B,MAAM,EAAE,CAAC,KAAK,CAAC,EAAE,WAAW,KAAK,MAAM,CAAC;KACzC;CACF;AAKD,qBAAa,QAAS,SAAQ,MAAM,CAAC,eAAe,CAAE,YAAW,SAAS;IACxE,EAAE,SAAQ;IAEV,UAAU,CAAC,OAAO,GAAE,OAAO,CAAC,eAAe,CAAM,GAAG,IAAI;IAKxD,cAAc,CAAC,GAAG,EAAE,YAAY,GAAG,IAAI;CAGxC;AAED,eAAe,QAAQ,CAAC"}
|
package/lib/View3D.d.ts
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import { Camera3D, Container3D, View3D as PixiView3D, View3DOptions } from '@pixi/3d';
|
|
2
|
+
import { Size } from '@caperjs/core';
|
|
3
|
+
import { Container, Ticker } from 'pixi.js';
|
|
4
|
+
import { Factory3D } from './factory3d';
|
|
5
|
+
import { Vec3 } from './props';
|
|
6
|
+
type CameraProps = {
|
|
7
|
+
position?: Vec3;
|
|
8
|
+
lookAt?: Vec3;
|
|
9
|
+
/** Vertical field of view in degrees. */
|
|
10
|
+
fov?: number;
|
|
11
|
+
near?: number;
|
|
12
|
+
far?: number;
|
|
13
|
+
/**
|
|
14
|
+
* The aspect ratio (width / height) the scene is framed for, e.g. `16 / 9`. On a narrower view (a phone
|
|
15
|
+
* held upright) the field of view grows so the sides stay in frame. Leave it out to keep `fov` fixed.
|
|
16
|
+
*/
|
|
17
|
+
fitAspect?: number;
|
|
18
|
+
};
|
|
19
|
+
export interface View3DProps extends Omit<View3DOptions, 'camera'> {
|
|
20
|
+
camera?: Camera3D | CameraProps;
|
|
21
|
+
interactive?: boolean;
|
|
22
|
+
}
|
|
23
|
+
/** Something an add-on attaches to a view. The view drives it; games never call these. */
|
|
24
|
+
export interface View3DPart {
|
|
25
|
+
/** Every frame the view updates (on app.ticker), after model clips. */
|
|
26
|
+
update?(ticker: Ticker): void;
|
|
27
|
+
/** Once when owned with the current size, then on every view resize. */
|
|
28
|
+
resize?(size: Size): void;
|
|
29
|
+
/** Before the view frees its nodes and resources, while the view is still usable. */
|
|
30
|
+
destroy(): void;
|
|
31
|
+
}
|
|
32
|
+
declare const View3D_base: (new (options?: View3DOptions<Container3D> | undefined) => PixiView3D<Container3D>) & import('@caperjs/core').Constructor<import('@caperjs/core').ISignalContainer> & import('@caperjs/core').Constructor<import('@caperjs/core').ILifecycle>;
|
|
33
|
+
export declare class View3D extends View3D_base {
|
|
34
|
+
readonly add: Factory3D;
|
|
35
|
+
readonly make: Factory3D;
|
|
36
|
+
private readonly owned;
|
|
37
|
+
private readonly parts;
|
|
38
|
+
private readonly pins;
|
|
39
|
+
private readonly fillsScreen;
|
|
40
|
+
private readonly fit?;
|
|
41
|
+
constructor(props?: View3DProps);
|
|
42
|
+
/** For add-ons: the view updates `part` every frame, tells it about resizes, and destroys it with itself. */
|
|
43
|
+
own<T extends View3DPart>(part: T): T;
|
|
44
|
+
/** Keeps a 2D node over a 3D point, hidden while the point is behind the camera. Returns the function that unpins it. */
|
|
45
|
+
pin(node: Container, target: Container3D | Vec3, options?: {
|
|
46
|
+
offset?: Vec3;
|
|
47
|
+
}): () => void;
|
|
48
|
+
added(): void;
|
|
49
|
+
resize(_size?: Size): void;
|
|
50
|
+
update(_ticker?: Ticker | number): void;
|
|
51
|
+
private placePins;
|
|
52
|
+
destroy(_options?: Parameters<PixiView3D['destroy']>[0] | boolean): void;
|
|
53
|
+
private fitCamera;
|
|
54
|
+
private get viewSize();
|
|
55
|
+
private placeFullScreen;
|
|
56
|
+
}
|
|
57
|
+
export {};
|
|
58
|
+
//# sourceMappingURL=View3D.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"View3D.d.ts","sourceRoot":"","sources":["../src/View3D.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAW,MAAM,IAAI,UAAU,EAAE,MAAM,UAAU,CAAC;AAChF,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAE9C,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAC1C,OAAO,EAAS,KAAK,SAAS,EAAE,KAAK,MAAM,EAAE,MAAM,SAAS,CAAC;AAG7D,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAE7C,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,SAAS,CAAC;AAMpC,KAAK,WAAW,GAAG;IACjB,QAAQ,CAAC,EAAE,IAAI,CAAC;IAChB,MAAM,CAAC,EAAE,IAAI,CAAC;IACd,yCAAyC;IACzC,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,GAAG,CAAC,EAAE,MAAM,CAAC;IACb;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,WAAW,WAAY,SAAQ,IAAI,CAAC,aAAa,EAAE,QAAQ,CAAC;IAChE,MAAM,CAAC,EAAE,QAAQ,GAAG,WAAW,CAAC;IAChC,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAED,0FAA0F;AAC1F,MAAM,WAAW,UAAU;IACzB,uEAAuE;IACvE,MAAM,CAAC,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IAC9B,wEAAwE;IACxE,MAAM,CAAC,CAAC,IAAI,EAAE,IAAI,GAAG,IAAI,CAAC;IAC1B,qFAAqF;IACrF,OAAO,IAAI,IAAI,CAAC;CACjB;;AAOD,qBAAa,MAAO,SAAQ,WAAsC;IAChE,QAAQ,CAAC,GAAG,EAAE,SAAS,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC;IACzB,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAiB;IACvC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAyB;IAC/C,OAAO,CAAC,QAAQ,CAAC,IAAI,CAA6B;IAClD,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAU;IACtC,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAkC;gBAE3C,KAAK,GAAE,WAAgB;IAqCnC,6GAA6G;IAC7G,GAAG,CAAC,CAAC,SAAS,UAAU,EAAE,IAAI,EAAE,CAAC,GAAG,CAAC;IAMrC,yHAAyH;IACzH,GAAG,CAAC,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,WAAW,GAAG,IAAI,EAAE,OAAO,GAAE;QAAE,MAAM,CAAC,EAAE,IAAI,CAAA;KAAO,GAAG,MAAM,IAAI;IAW7F,KAAK,IAAI,IAAI;IAIb,MAAM,CAAC,KAAK,CAAC,EAAE,IAAI,GAAG,IAAI;IAM1B,MAAM,CAAC,OAAO,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;IAMvC,OAAO,CAAC,SAAS;IAmBjB,OAAO,CAAC,QAAQ,CAAC,EAAE,UAAU,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,OAAO,GAAG,IAAI;IASxE,OAAO,CAAC,SAAS;IAMjB,OAAO,KAAK,QAAQ,GAGnB;IAED,OAAO,CAAC,eAAe;CAGxB"}
|