sceneview-mcp 4.0.0 → 4.0.2
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 +29 -7
- package/dist/analyze-project.js +1 -1
- package/dist/debug-issue.js +2 -2
- package/dist/extra-guides.js +1 -1
- package/dist/generate-scene.js +2 -2
- package/dist/generated/llms-txt.js +1 -1
- package/dist/guides.js +8 -8
- package/dist/index.js +3 -3
- package/dist/migration.js +2 -2
- package/dist/platform-setup.js +11 -11
- package/dist/samples.js +64 -64
- package/dist/telemetry.js +1 -1
- package/dist/tiers.js +1 -0
- package/dist/tools/definitions.js +27 -0
- package/dist/tools/handler.js +114 -28
- package/llms.txt +85 -8
- package/package.json +1 -1
package/dist/tools/handler.js
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
* 1. The stdio MCP server in `../index.ts` (legacy npm package path).
|
|
10
10
|
* 2. The HTTP gateway in `mcp-gateway/src/mcp/registry.ts` (hosted path).
|
|
11
11
|
*
|
|
12
|
-
* Zero runtime behaviour change from 4.0.0
|
|
12
|
+
* Zero runtime behaviour change from 4.0.0: every tool returns exactly the
|
|
13
13
|
* same content it did when the logic lived inside the stdio server's
|
|
14
14
|
* `CallToolRequestSchema` handler.
|
|
15
15
|
*
|
|
@@ -35,32 +35,69 @@ import { MATERIAL_GUIDE, COLLISION_GUIDE, MODEL_OPTIMIZATION_GUIDE, WEB_RENDERIN
|
|
|
35
35
|
import { searchModels, formatSearchResults } from "../search-models.js";
|
|
36
36
|
import { analyzeProject, formatAnalysisReport } from "../analyze-project.js";
|
|
37
37
|
import { LLMS_TXT } from "../generated/llms-txt.js";
|
|
38
|
-
// ─── Legal disclaimer (identical to index.ts 4.0.0
|
|
38
|
+
// ─── Legal disclaimer (identical to index.ts 4.0.0) ─────────────────────
|
|
39
39
|
const DISCLAIMER = "\n\n---\n*Generated code suggestion. Review before use in production. See [TERMS.md](https://github.com/sceneview/sceneview/blob/main/mcp/TERMS.md).*";
|
|
40
|
-
// ───
|
|
40
|
+
// ─── Tiered Pro CTA ─────────────────────────────────────────────────────────
|
|
41
41
|
//
|
|
42
|
-
//
|
|
43
|
-
//
|
|
44
|
-
//
|
|
45
|
-
//
|
|
46
|
-
|
|
47
|
-
|
|
42
|
+
// Empirical motivation (30-day telemetry, April 2026):
|
|
43
|
+
// - 0 paying customers despite 140 inits / 77 tool calls
|
|
44
|
+
// - The previous CTA (every 10 calls, dual sponsor + upgrade link) was seen
|
|
45
|
+
// ~2× by the heaviest user and 0× by everyone else (most users never hit
|
|
46
|
+
// 10 calls). The dual link also split attention: a free sponsor link
|
|
47
|
+
// always wins against a paid upgrade link.
|
|
48
|
+
//
|
|
49
|
+
// New strategy:
|
|
50
|
+
// - Fire EARLIER (call #3 — first nudge) so users actually see the pitch
|
|
51
|
+
// - Single CTA (no sponsor competition) pointing to /pricing
|
|
52
|
+
// - Tiered wording: tease → ask → final push, each more specific than the last
|
|
53
|
+
// - Same opt-out env var (`SCENEVIEW_SPONSOR_CTA=0`) for backwards compat,
|
|
54
|
+
// plus a new `SCENEVIEW_CTA=0` alias for clarity going forward
|
|
55
|
+
//
|
|
56
|
+
// The counter is module-scoped (per MCP process lifetime), not persisted.
|
|
57
|
+
const PRICING_URL = "https://sceneview-mcp.mcp-tools-lab.workers.dev/pricing";
|
|
58
|
+
const CTA_STAGES = [
|
|
59
|
+
{
|
|
60
|
+
at: 3,
|
|
61
|
+
message: `\n\n💎 *Tip: SceneView Pro unlocks \`generate_scene\` — describe an AR app in plain English, get working Kotlin/Swift in one shot. [Try it free for 7 days](${PRICING_URL}).*`,
|
|
62
|
+
},
|
|
63
|
+
{
|
|
64
|
+
at: 10,
|
|
65
|
+
message: `\n\n🚀 *You've used 10 free SceneView tools. Ready to GENERATE a full AR app in one call? Pro unlocks 35+ tools (scene gen, multi-platform, vertical packages) for €19/mo — [start your free trial](${PRICING_URL}).*`,
|
|
66
|
+
},
|
|
67
|
+
{
|
|
68
|
+
at: 25,
|
|
69
|
+
message: `\n\n⭐ *Heavy SceneView user — save €38 / year with the annual plan (€190/yr instead of €19×12). [Lock it in](${PRICING_URL}).*`,
|
|
70
|
+
},
|
|
71
|
+
];
|
|
72
|
+
/** After all explicit stages, recurring nudge cadence (call #25, #35, #45…). */
|
|
73
|
+
const POST_STAGE_INTERVAL = 10;
|
|
48
74
|
let toolCallCount = 0;
|
|
49
75
|
/** Test-only: reset the module-scoped counter between test cases. */
|
|
50
76
|
export function __resetSponsorCounter() {
|
|
51
77
|
toolCallCount = 0;
|
|
52
78
|
}
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
79
|
+
/** Returns the CTA suffix to append on this call, or `""` if none. */
|
|
80
|
+
function nextCtaSuffix() {
|
|
81
|
+
// Two opt-out env vars: keep the legacy name for backwards compatibility.
|
|
82
|
+
if (process.env.SCENEVIEW_SPONSOR_CTA === "0" ||
|
|
83
|
+
process.env.SCENEVIEW_CTA === "0") {
|
|
84
|
+
return "";
|
|
85
|
+
}
|
|
56
86
|
toolCallCount += 1;
|
|
57
|
-
|
|
87
|
+
const stage = CTA_STAGES.find((s) => s.at === toolCallCount);
|
|
88
|
+
if (stage)
|
|
89
|
+
return stage.message;
|
|
90
|
+
const last = CTA_STAGES[CTA_STAGES.length - 1];
|
|
91
|
+
if (toolCallCount > last.at && (toolCallCount - last.at) % POST_STAGE_INTERVAL === 0) {
|
|
92
|
+
return last.message;
|
|
93
|
+
}
|
|
94
|
+
return "";
|
|
58
95
|
}
|
|
59
96
|
function withDisclaimer(content) {
|
|
60
97
|
if (content.length === 0)
|
|
61
98
|
return content;
|
|
62
99
|
const last = content[content.length - 1];
|
|
63
|
-
const suffix = DISCLAIMER + (
|
|
100
|
+
const suffix = DISCLAIMER + nextCtaSuffix();
|
|
64
101
|
return [
|
|
65
102
|
...content.slice(0, -1),
|
|
66
103
|
{ ...last, text: last.text + suffix },
|
|
@@ -91,6 +128,55 @@ const NODE_SECTIONS = parseNodeSections(API_DOCS);
|
|
|
91
128
|
*/
|
|
92
129
|
export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
93
130
|
switch (toolName) {
|
|
131
|
+
// ── get_started ───────────────────────────────────────────────────────────
|
|
132
|
+
// Activation entry point — see definition in `definitions.ts` for context.
|
|
133
|
+
// Pure markdown response, no I/O, deliberately concise so the host AI can
|
|
134
|
+
// forward the bullets straight into chat without summarising.
|
|
135
|
+
case "get_started": {
|
|
136
|
+
const platformArg = args?.platform ?? "any";
|
|
137
|
+
const platform = platformArg === "android" || platformArg === "ios" || platformArg === "web"
|
|
138
|
+
? platformArg
|
|
139
|
+
: "any";
|
|
140
|
+
const installSnippets = {
|
|
141
|
+
android: "**Android (Jetpack Compose + Filament):**\n```kotlin\n// app/build.gradle.kts\nimplementation(\"io.github.sceneview:sceneview:4.0.1\") // 3D only\nimplementation(\"io.github.sceneview:arsceneview:4.0.1\") // AR\n```",
|
|
142
|
+
ios: "**iOS / macOS / visionOS (SwiftUI + RealityKit):**\n```swift\n// Package.swift\n.package(url: \"https://github.com/sceneview/SceneViewSwift\", from: \"4.0.1\")\n```",
|
|
143
|
+
web: "**Web (Filament.js + WebXR):**\n```bash\nnpm install sceneview-web@4.0.1\n```",
|
|
144
|
+
any: "**Pick your platform** (call `get_started` again with `platform`):\n- `android` — Jetpack Compose + Filament\n- `ios` — SwiftUI + RealityKit (iOS / macOS / visionOS)\n- `web` — Filament.js + WebXR",
|
|
145
|
+
};
|
|
146
|
+
const promptIdeas = [
|
|
147
|
+
"💬 *\"Show me a working AR sample I can run today.\"* → I'll call `get_sample` with an AR scenario.",
|
|
148
|
+
"💬 *\"Generate a 3D scene with a rotating model and ambient light.\"* → triggers `generate_scene` (Pro).",
|
|
149
|
+
"💬 *\"Validate this Kotlin SceneView snippet.\"* → triggers `validate_code`.",
|
|
150
|
+
];
|
|
151
|
+
const text = [
|
|
152
|
+
"# 🎬 SceneView MCP — quick start",
|
|
153
|
+
"",
|
|
154
|
+
"**SceneView** = native 3D & AR for **Android** (Compose + Filament), **iOS / macOS / visionOS** (SwiftUI + RealityKit) and **Web** (Filament.js + WebXR).",
|
|
155
|
+
"",
|
|
156
|
+
"## Try one of these prompts now",
|
|
157
|
+
...promptIdeas.map((p) => `- ${p}`),
|
|
158
|
+
"",
|
|
159
|
+
"## Install snippet",
|
|
160
|
+
installSnippets[platform],
|
|
161
|
+
"",
|
|
162
|
+
"## Useful next tools",
|
|
163
|
+
"- `list_samples` — see all 33 ready-to-paste examples",
|
|
164
|
+
"- `get_node_reference` — full API for a specific composable / node",
|
|
165
|
+
"- `validate_code` — catch threading / API mistakes before you ship",
|
|
166
|
+
"- `analyze_project` — inspect an existing project for SceneView readiness",
|
|
167
|
+
"",
|
|
168
|
+
"## Pro tools (€19/mo · [free trial](https://sceneview-mcp.mcp-tools-lab.workers.dev/pricing))",
|
|
169
|
+
"Unlocks `generate_scene`, `create_3d_artifact`, `render_3d_preview`, multi-platform setup, and the four vertical packages (Automotive · Gaming · Healthcare · Interior).",
|
|
170
|
+
"",
|
|
171
|
+
"## Resources",
|
|
172
|
+
"- 🌐 Playground: <https://sceneview.github.io>",
|
|
173
|
+
"- 📚 Full API: read the `sceneview://api` MCP resource",
|
|
174
|
+
"- 🐛 Issues: <https://github.com/sceneview/sceneview/issues>",
|
|
175
|
+
].join("\n");
|
|
176
|
+
return {
|
|
177
|
+
content: [{ type: "text", text }],
|
|
178
|
+
};
|
|
179
|
+
}
|
|
94
180
|
// ── get_sample ────────────────────────────────────────────────────────────
|
|
95
181
|
case "get_sample": {
|
|
96
182
|
const scenario = args?.scenario;
|
|
@@ -111,7 +197,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
111
197
|
? [
|
|
112
198
|
`**SPM dependency:**`,
|
|
113
199
|
`\`\`\`swift`,
|
|
114
|
-
`.package(url: "${sample.spmDependency ?? sample.dependency}", from: "4.0.0
|
|
200
|
+
`.package(url: "${sample.spmDependency ?? sample.dependency}", from: "4.0.0")`,
|
|
115
201
|
`\`\`\``,
|
|
116
202
|
]
|
|
117
203
|
: [
|
|
@@ -184,7 +270,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
184
270
|
`### build.gradle.kts`,
|
|
185
271
|
`\`\`\`kotlin`,
|
|
186
272
|
`dependencies {`,
|
|
187
|
-
` implementation("io.github.sceneview:sceneview:4.0.0
|
|
273
|
+
` implementation("io.github.sceneview:sceneview:4.0.0")`,
|
|
188
274
|
`}`,
|
|
189
275
|
`\`\`\``,
|
|
190
276
|
``,
|
|
@@ -205,7 +291,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
205
291
|
`### build.gradle.kts`,
|
|
206
292
|
`\`\`\`kotlin`,
|
|
207
293
|
`dependencies {`,
|
|
208
|
-
` implementation("io.github.sceneview:arsceneview:4.0.0
|
|
294
|
+
` implementation("io.github.sceneview:arsceneview:4.0.0")`,
|
|
209
295
|
`}`,
|
|
210
296
|
`\`\`\``,
|
|
211
297
|
``,
|
|
@@ -318,7 +404,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
318
404
|
`\`\`\``,
|
|
319
405
|
`https://github.com/sceneview/sceneview`,
|
|
320
406
|
`\`\`\``,
|
|
321
|
-
`Set version rule to **"from: 4.0.0
|
|
407
|
+
`Set version rule to **"from: 4.0.0"**.`,
|
|
322
408
|
``,
|
|
323
409
|
`Or in Package.swift:`,
|
|
324
410
|
`\`\`\`swift`,
|
|
@@ -329,7 +415,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
329
415
|
` name: "MyApp",`,
|
|
330
416
|
` platforms: [.iOS(.v17), .macOS(.v14), .visionOS(.v1)],`,
|
|
331
417
|
` dependencies: [`,
|
|
332
|
-
` .package(url: "https://github.com/sceneview/sceneview", from: "4.0.0
|
|
418
|
+
` .package(url: "https://github.com/sceneview/sceneview", from: "4.0.0")`,
|
|
333
419
|
` ],`,
|
|
334
420
|
` targets: [`,
|
|
335
421
|
` .executableTarget(`,
|
|
@@ -400,7 +486,7 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
400
486
|
`### 1. Add SPM Dependency`,
|
|
401
487
|
``,
|
|
402
488
|
`\`\`\`swift`,
|
|
403
|
-
`.package(url: "https://github.com/sceneview/sceneview", from: "4.0.0
|
|
489
|
+
`.package(url: "https://github.com/sceneview/sceneview", from: "4.0.0")`,
|
|
404
490
|
`\`\`\``,
|
|
405
491
|
``,
|
|
406
492
|
`### 2. Minimum Platform`,
|
|
@@ -680,15 +766,15 @@ export async function dispatchTool(toolName, args, _ctx = {}) {
|
|
|
680
766
|
// ── list_platforms ────────────────────────────────────────────────────────
|
|
681
767
|
case "list_platforms": {
|
|
682
768
|
const platforms = [
|
|
683
|
-
{ platform: "Android", renderer: "Filament", framework: "Jetpack Compose", status: "Stable", version: "4.0.0
|
|
684
|
-
{ platform: "Android TV", renderer: "Filament", framework: "Compose TV", status: "Alpha", version: "4.0.0
|
|
769
|
+
{ platform: "Android", renderer: "Filament", framework: "Jetpack Compose", status: "Stable", version: "4.0.0", dependency: "io.github.sceneview:sceneview:4.0.0", features: ["3D", "AR (ARCore)", "Model loading (GLB/glTF)", "Geometry nodes", "Physics", "Gestures"] },
|
|
770
|
+
{ platform: "Android TV", renderer: "Filament", framework: "Compose TV", status: "Alpha", version: "4.0.0", dependency: "io.github.sceneview:sceneview:4.0.0", features: ["3D", "D-pad controls", "Auto-rotation", "Model loading"] },
|
|
685
771
|
{ platform: "Android XR", renderer: "Jetpack XR SceneCore", framework: "Compose XR", status: "Planned", version: "-", dependency: "-", features: ["Spatial computing", "Hand tracking", "Passthrough"] },
|
|
686
|
-
{ platform: "iOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0
|
|
687
|
-
{ platform: "macOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0
|
|
688
|
-
{ platform: "visionOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0
|
|
689
|
-
{ platform: "Web", renderer: "Filament.js (WASM)", framework: "Kotlin/JS", status: "Alpha", version: "4.0.0
|
|
690
|
-
{ platform: "Desktop", renderer: "Software / Filament JNI", framework: "Compose Desktop", status: "Alpha", version: "4.0.0
|
|
691
|
-
{ platform: "Flutter", renderer: "Filament / RealityKit", framework: "PlatformView", status: "Alpha", version: "4.0.0
|
|
772
|
+
{ platform: "iOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0", dependency: "SceneViewSwift (SPM)", features: ["3D", "AR (ARKit)", "16 node types", "USDZ models"] },
|
|
773
|
+
{ platform: "macOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0", dependency: "SceneViewSwift (SPM)", features: ["3D", "Orbit camera", "USDZ models"] },
|
|
774
|
+
{ platform: "visionOS", renderer: "RealityKit", framework: "SwiftUI", status: "Alpha", version: "4.0.0", dependency: "SceneViewSwift (SPM)", features: ["3D", "Immersive spaces", "Hand tracking (planned)"] },
|
|
775
|
+
{ platform: "Web", renderer: "Filament.js (WASM)", framework: "Kotlin/JS", status: "Alpha", version: "4.0.0", dependency: "@sceneview/sceneview-web", features: ["3D", "WebXR AR/VR", "GLB models", "WebGL2"] },
|
|
776
|
+
{ platform: "Desktop", renderer: "Software / Filament JNI", framework: "Compose Desktop", status: "Alpha", version: "4.0.0", dependency: "sceneview-desktop (local)", features: ["3D", "Software renderer", "Wireframe"] },
|
|
777
|
+
{ platform: "Flutter", renderer: "Filament / RealityKit", framework: "PlatformView", status: "Alpha", version: "4.0.0", dependency: "flutter pub: sceneview", features: ["3D", "AR", "Android + iOS bridge"] },
|
|
692
778
|
];
|
|
693
779
|
const lines = [
|
|
694
780
|
"## SceneView Supported Platforms\n",
|
package/llms.txt
CHANGED
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
|
|
3
3
|
SceneView is a declarative 3D and AR SDK for Android (Jetpack Compose, Filament, ARCore) and Apple platforms — iOS, macOS, visionOS (SwiftUI, RealityKit, ARKit) — with shared core logic via Kotlin Multiplatform. Each platform uses its native renderer: Filament on Android, RealityKit on Apple.
|
|
4
4
|
|
|
5
|
-
**Android — Maven artifacts (version 4.0.
|
|
6
|
-
- 3D only: `io.github.sceneview:sceneview:4.0.
|
|
7
|
-
- AR + 3D: `io.github.sceneview:arsceneview:4.0.
|
|
5
|
+
**Android — Maven artifacts (version 4.0.1):**
|
|
6
|
+
- 3D only: `io.github.sceneview:sceneview:4.0.1`
|
|
7
|
+
- AR + 3D: `io.github.sceneview:arsceneview:4.0.1`
|
|
8
8
|
|
|
9
9
|
**Apple (iOS 17+ / macOS 14+ / visionOS 1+) — Swift Package:**
|
|
10
|
-
- `https://github.com/sceneview/sceneview-swift.git` (from: "
|
|
10
|
+
- `https://github.com/sceneview/sceneview-swift.git` (from: "4.0.0")
|
|
11
11
|
|
|
12
12
|
**Min SDK:** 24 | **Target SDK:** 36 | **Kotlin:** 2.3.20 | **Compose BOM compatible**
|
|
13
13
|
|
|
@@ -18,8 +18,8 @@ SceneView is a declarative 3D and AR SDK for Android (Jetpack Compose, Filament,
|
|
|
18
18
|
### build.gradle (app module)
|
|
19
19
|
```kotlin
|
|
20
20
|
dependencies {
|
|
21
|
-
implementation("io.github.sceneview:sceneview:4.0.
|
|
22
|
-
implementation("io.github.sceneview:arsceneview:4.0.
|
|
21
|
+
implementation("io.github.sceneview:sceneview:4.0.1") // 3D only
|
|
22
|
+
implementation("io.github.sceneview:arsceneview:4.0.1") // AR (includes sceneview)
|
|
23
23
|
}
|
|
24
24
|
```
|
|
25
25
|
|
|
@@ -338,6 +338,56 @@ SceneView(...) {
|
|
|
338
338
|
)
|
|
339
339
|
```
|
|
340
340
|
|
|
341
|
+
### ConeNode — cone geometry
|
|
342
|
+
```kotlin
|
|
343
|
+
@Composable fun ConeNode(
|
|
344
|
+
radius: Float = Cone.DEFAULT_RADIUS, // 1.0f
|
|
345
|
+
height: Float = Cone.DEFAULT_HEIGHT, // 2.0f
|
|
346
|
+
center: Position = Cone.DEFAULT_CENTER,
|
|
347
|
+
sideCount: Int = Cone.DEFAULT_SIDE_COUNT, // 24
|
|
348
|
+
materialInstance: MaterialInstance? = null,
|
|
349
|
+
position: Position = Position(x = 0f),
|
|
350
|
+
rotation: Rotation = Rotation(x = 0f),
|
|
351
|
+
scale: Scale = Scale(1f),
|
|
352
|
+
apply: ConeNode.() -> Unit = {},
|
|
353
|
+
content: (@Composable NodeScope.() -> Unit)? = null
|
|
354
|
+
)
|
|
355
|
+
```
|
|
356
|
+
|
|
357
|
+
### TorusNode — torus (donut) geometry
|
|
358
|
+
```kotlin
|
|
359
|
+
@Composable fun TorusNode(
|
|
360
|
+
majorRadius: Float = Torus.DEFAULT_MAJOR_RADIUS, // 1.0f (ring centre)
|
|
361
|
+
minorRadius: Float = Torus.DEFAULT_MINOR_RADIUS, // 0.3f (tube thickness)
|
|
362
|
+
center: Position = Torus.DEFAULT_CENTER,
|
|
363
|
+
majorSegments: Int = Torus.DEFAULT_MAJOR_SEGMENTS, // 32
|
|
364
|
+
minorSegments: Int = Torus.DEFAULT_MINOR_SEGMENTS, // 16
|
|
365
|
+
materialInstance: MaterialInstance? = null,
|
|
366
|
+
position: Position = Position(x = 0f),
|
|
367
|
+
rotation: Rotation = Rotation(x = 0f),
|
|
368
|
+
scale: Scale = Scale(1f),
|
|
369
|
+
apply: TorusNode.() -> Unit = {},
|
|
370
|
+
content: (@Composable NodeScope.() -> Unit)? = null
|
|
371
|
+
)
|
|
372
|
+
```
|
|
373
|
+
|
|
374
|
+
### CapsuleNode — capsule (cylinder + hemisphere caps)
|
|
375
|
+
```kotlin
|
|
376
|
+
@Composable fun CapsuleNode(
|
|
377
|
+
radius: Float = Capsule.DEFAULT_RADIUS, // 0.5f
|
|
378
|
+
height: Float = Capsule.DEFAULT_HEIGHT, // 2.0f (cylinder section; total = h + 2r)
|
|
379
|
+
center: Position = Capsule.DEFAULT_CENTER,
|
|
380
|
+
capStacks: Int = Capsule.DEFAULT_CAP_STACKS, // 8
|
|
381
|
+
sideSlices: Int = Capsule.DEFAULT_SIDE_SLICES, // 24
|
|
382
|
+
materialInstance: MaterialInstance? = null,
|
|
383
|
+
position: Position = Position(x = 0f),
|
|
384
|
+
rotation: Rotation = Rotation(x = 0f),
|
|
385
|
+
scale: Scale = Scale(1f),
|
|
386
|
+
apply: CapsuleNode.() -> Unit = {},
|
|
387
|
+
content: (@Composable NodeScope.() -> Unit)? = null
|
|
388
|
+
)
|
|
389
|
+
```
|
|
390
|
+
|
|
341
391
|
### PlaneNode — flat quad
|
|
342
392
|
```kotlin
|
|
343
393
|
@Composable fun PlaneNode(
|
|
@@ -364,6 +414,9 @@ SceneView(...) {
|
|
|
364
414
|
CubeNode(size = Size(0.5f), center = Position(0f, 0.25f, 0f), materialInstance = redMaterial)
|
|
365
415
|
SphereNode(radius = 0.3f, materialInstance = blueMaterial)
|
|
366
416
|
CylinderNode(radius = 0.2f, height = 1.0f, materialInstance = greenMaterial)
|
|
417
|
+
ConeNode(radius = 0.3f, height = 0.8f, materialInstance = yellowMaterial)
|
|
418
|
+
TorusNode(majorRadius = 0.5f, minorRadius = 0.15f, materialInstance = purpleMaterial)
|
|
419
|
+
CapsuleNode(radius = 0.2f, height = 0.6f, materialInstance = orangeMaterial)
|
|
367
420
|
PlaneNode(size = Size(5f, 5f), materialInstance = greyMaterial)
|
|
368
421
|
}
|
|
369
422
|
```
|
|
@@ -1069,6 +1122,25 @@ SceneView(surfaceType = SurfaceType.TextureSurface, isOpaque = false) // Textur
|
|
|
1069
1122
|
|
|
1070
1123
|
---
|
|
1071
1124
|
|
|
1125
|
+
## Performance
|
|
1126
|
+
|
|
1127
|
+
- **Frame budget**: 16.6ms at 60fps. Target 12ms for headroom.
|
|
1128
|
+
- **Cold start**: ~120ms (3D), ~350ms (AR, ARCore init dominates).
|
|
1129
|
+
- **APK size**: +3.2MB (sceneview), +5.1MB (sceneview + arsceneview).
|
|
1130
|
+
- **Memory**: ~25MB empty 3D scene, ~45MB empty AR scene.
|
|
1131
|
+
- **Triangle budget**: <100K per model, <200K total scene (mid-tier devices).
|
|
1132
|
+
- **Textures**: use KTX2 with Basis Universal, max 2048x2048 on mobile.
|
|
1133
|
+
- **Draw calls**: aim for <100 per frame. Merge static geometry in Blender before export.
|
|
1134
|
+
- **Lights**: 1 directional + IBL covers most cases. Max 2-3 additional point/spot lights.
|
|
1135
|
+
- **Post-processing**: Bloom ~1ms, SSAO ~2-3ms. Disable SSAO on low-end devices.
|
|
1136
|
+
- **Compose**: use `remember` for Position/Rotation/Scale — no allocations in composition body.
|
|
1137
|
+
- **Engine**: create one `rememberEngine()` at app level, share across all scenes.
|
|
1138
|
+
- **AR**: disable `planeRenderer` after object placement to reduce overdraw.
|
|
1139
|
+
- **Rerun bridge**: adds ~0.5ms when active. Gate with `BuildConfig.DEBUG`.
|
|
1140
|
+
- See full guide: docs/docs/performance.md
|
|
1141
|
+
|
|
1142
|
+
---
|
|
1143
|
+
|
|
1072
1144
|
## Error Handling
|
|
1073
1145
|
|
|
1074
1146
|
| Problem | Cause | Fix |
|
|
@@ -1788,7 +1860,7 @@ React Native (Turbo Module / Fabric), KMP Compose iOS (UIKitView).
|
|
|
1788
1860
|
```swift
|
|
1789
1861
|
// Package.swift
|
|
1790
1862
|
dependencies: [
|
|
1791
|
-
.package(url: "https://github.com/sceneview/sceneview-swift.git", from: "
|
|
1863
|
+
.package(url: "https://github.com/sceneview/sceneview-swift.git", from: "4.0.1")
|
|
1792
1864
|
]
|
|
1793
1865
|
```
|
|
1794
1866
|
|
|
@@ -2041,6 +2113,11 @@ let data = SceneSnapshot.pngData(image) // or jpegData(image, quality: 0.9)
|
|
|
2041
2113
|
| Environment | `rememberEnvironment(loader) { }` | `.environment(.studio)` |
|
|
2042
2114
|
| Cube | `CubeNode(size)` | `GeometryNode.cube(size:color:)` |
|
|
2043
2115
|
| Sphere | `SphereNode(radius)` | `GeometryNode.sphere(radius:)` |
|
|
2116
|
+
| Cylinder | `CylinderNode(radius, height)` | `GeometryNode.cylinder(radius:height:)` |
|
|
2117
|
+
| Plane | `PlaneNode(size)` | `GeometryNode.plane(width:height:)` |
|
|
2118
|
+
| Cone | `ConeNode(radius, height)` | `GeometryNode.cone(radius:height:)` |
|
|
2119
|
+
| Torus | `TorusNode(majorRadius, minorRadius)` | `GeometryNode.torus(majorRadius:minorRadius:)` |
|
|
2120
|
+
| Capsule | `CapsuleNode(radius, height)` | `GeometryNode.capsule(radius:height:)` |
|
|
2044
2121
|
| Light | `LightNode(type, apply = { })` | `LightNode.directional(color:intensity:)` |
|
|
2045
2122
|
| Text | `TextNode(text = "...")` | `TextNode(text:fontSize:color:depth:)` |
|
|
2046
2123
|
| Line | `LineNode(start, end, materialInstance)` | `LineNode(from:to:color:)` |
|
|
@@ -2462,7 +2539,7 @@ Renderer: **RealityKit**. Requires iOS 17+ / macOS 14+ / visionOS 1+.
|
|
|
2462
2539
|
|
|
2463
2540
|
SPM dependency (Package.swift or Xcode):
|
|
2464
2541
|
```swift
|
|
2465
|
-
.package(url: "https://github.com/sceneview/sceneview-swift.git", from: "
|
|
2542
|
+
.package(url: "https://github.com/sceneview/sceneview-swift.git", from: "4.0.1")
|
|
2466
2543
|
```
|
|
2467
2544
|
|
|
2468
2545
|
Import: `import SceneViewSwift`
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "sceneview-mcp",
|
|
3
|
-
"version": "4.0.
|
|
3
|
+
"version": "4.0.2",
|
|
4
4
|
"mcpName": "io.github.sceneview/mcp",
|
|
5
5
|
"description": "MCP server for SceneView — cross-platform 3D & AR SDK for Android and iOS. Give Claude the full SceneView SDK so it writes correct, compilable code.",
|
|
6
6
|
"keywords": [
|