
Cafe with terrace
Cafe on a 4 m lot with an awning and an optional terrace.
What you can change
- Size (W × H × D)
- 3.85 × 5.53 × 7.63 m
- Triangles
- 6,020
- GLB
- 373 KB
Part of the Stylized Town kit
npx agent-ready-assets add stylized-town/cafe-01@0.1.0 --to public/assetsRenders from 6 views






Customize without Blender
Each change applies to one instance in the browser through the SDK; other instances and the file itself stay unchanged. Anything not listed here is refused with an explanation.
Front doorPart swap
AwningVisibility toggle
Shown by default; can be hiddenTerraceVisibility toggle
Shown by default; can be hiddenWall colorRecolour
Details
Specifications6,020 triangles · 373 KB
- Dimensions (W × H × D)
- 3.85 × 5.53 × 7.63 m
- Triangles
- 6,020
- Materials / textures
- 8 / 1
- GLB file
- 373 KB
- Package download
- 143 KB
- Animation clips
- None
- Engines
- Three.js, React Three Fiber
- Tested with
- three 0.186.1; no decoders
- In the tested scenes
- Explorable town (1×)
- Parts it mounts
- Door part: panelled door, Door part: glazed door
Connectors3 connectors
In a scene, a connector of this asset snaps to a compatible connector of another piece, so pieces are placed without coordinates.
| Connector | Type | Snaps to |
|---|---|---|
anchor-lot-front | lot-front | road-side |
anchor-door-main (part slot) | door-socket | door-plug |
anchor-awning | awning-socket | awning-plug |
Compatibility5 of 10 supported
| Feature | Status | Detail |
|---|---|---|
| Material recolor (runtime, Blender-free) | Supported | wall-color -> mat-wall (palette swatches: paving #E3C2AC, ivory #EDE3CF, lantern-glow #F3C374) (per-instance, host and mounted parts; base color factor of untextured materials, not baked texture… Show allwall-color -> mat-wall (palette swatches: paving #E3C2AC, ivory #EDE3CF, lantern-glow #F3C374) (per-instance, host and mounted parts; base color factor of untextured materials, not baked texture pixels) |
| Placement (position / rotation in a scene) | Supported | scene.json position_m (meters) and rotation_euler_rad (XYZ radians); free scene scaling is not supported |
| Connector snapping (scene 1.1.0 attach_to) | Supported | typed connectors: anchor-lot-front (lot-front -> road-side), anchor-door-main (door-socket -> door-plug), anchor-awning (awning-socket -> awning-plug); mates within 1 mm, opposed outward, aligned up |
| Node visibility toggles | Supported | awning: false hides awning; terrace: false hides terrace (declared optional parts only; anchors, markers and slot parts never disappear) |
| Modular part swap | Supported | front-door at anchor-door-main: door-01 -> stylized-town/door-01@0.1.0, door-02 (default) -> stylized-town/door-02@0.1.0 (allowlisted parts of the same kit with a compatible plug; mounted per… Show allfront-door at anchor-door-main: door-01 -> stylized-town/door-01@0.1.0, door-02 (default) -> stylized-town/door-02@0.1.0 (allowlisted parts of the same kit with a compatible plug; mounted per instance) |
| Uniform scale (runtime, Blender-free) | Not supported | no uniform-scale capability; scene uniform_scale must stay 1 |
| Animations | Not supported | static asset: no animation clips |
| Custom mesh editing / parametric geometry (e.g. slat count) | Advanced only | L4 authoring in Blender or another DCC; not possible with the SDK. declared.recipe_parameters are publisher-only knobs. |
| Baked texture recolor | Not supported | texture pixels are never edited by the SDK |
| GLB re-export of a customized asset | Not supported | customization is a declarative JSON config applied at runtime; no modified GLB is written |
Integration codeThree.js and React Three Fiber
The entry file your agent writes, generated from the catalog. Run the commands inside your project, where the SDK is installed.
Three.js
// stylized-town/cafe-01@0.1.0 in a plain Three.js scene
// Generated by the Agent-Ready Assets integration guide (target: plain Three.js, SDK 0.5.1, tested with three 0.186.1).
// The files are served from this project's own public/ folder (installed with `npx agent-ready-assets ...`):
// no CDN at runtime, no decoders, no Blender.
import * as THREE from 'three';
import { AssetLibrary, isCustomizationError } from '@agent-ready-assets/runtime-three';
const KIT_URL = '/assets/stylized-town/kit.json';
const ASSET = 'stylized-town/cafe-01@0.1.0';
const renderer = new THREE.WebGLRenderer({ antialias: true, preserveDrawingBuffer: true });
renderer.setPixelRatio(Math.min(window.devicePixelRatio, 2));
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.outputColorSpace = THREE.SRGBColorSpace;
document.body.style.margin = '0';
document.body.appendChild(renderer.domElement);
const scene = new THREE.Scene();
scene.background = new THREE.Color('#e9e4da');
scene.add(new THREE.HemisphereLight(0xffffff, 0x8d7c64, 1.4));
const sun = new THREE.DirectionalLight(0xffffff, 2.0);
sun.position.set(4, 8, 5);
scene.add(sun);
const camera = new THREE.PerspectiveCamera(40, window.innerWidth / window.innerHeight, 0.05, 400);
/** Points the camera at everything that was loaded (3/4 view). */
function frame(target: THREE.Object3D): void {
const box = new THREE.Box3().setFromObject(target);
const center = box.getCenter(new THREE.Vector3());
const radius = Math.max(box.getSize(new THREE.Vector3()).length() / 2, 0.5);
const dist = radius / Math.sin(THREE.MathUtils.degToRad(camera.fov / 2));
camera.position.copy(center).add(new THREE.Vector3(0.55, 0.5, 1).normalize().multiplyScalar(dist * 0.95));
camera.lookAt(center);
camera.updateProjectionMatrix();
}
window.addEventListener('resize', () => {
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.render(scene, camera);
});
async function main(): Promise<void> {
const library = await AssetLibrary.fromKit(KIT_URL); // verifies every file against the sha256 pins first
const original = await library.loadAsset(ASSET);
scene.add(original.object);
// Only the capabilities returned by get_customization_capabilities exist (here: front-door, awning, terrace, wall-color).
// Each customized instance gets its own material copies and mounted parts; the original and the cached GLB stay unchanged.
const customized = await library.instantiate(ASSET, {"front-door":"door-01","awning":false,"terrace":false,"wall-color":"ivory"});
customized.object.position.x = 4.85;
scene.add(customized.object);
frame(scene);
renderer.render(scene, camera);
renderer.domElement.dataset.ready = 'true'; // handy for tests: the scene finished loading
}
main().catch((error: unknown) => {
// Unsupported or invalid customizations are refused with a structured error instead of being approximated.
const message = isCustomizationError(error) ? `${error.code}: ${error.message}` : String(error);
renderer.domElement.dataset.error = message;
console.error(message);
});
React Three Fiber
// stylized-town/cafe-01@0.1.0 with React Three Fiber
// Generated by the Agent-Ready Assets integration guide (target: React Three Fiber, SDK 0.5.1, tested with three 0.186.1).
// Assets are served from this project's own public/ folder; no CDN, no Blender.
import { StrictMode, useEffect, useState } from 'react';
import { createRoot } from 'react-dom/client';
import { Canvas } from '@react-three/fiber';
import { Asset, AssetLibraryProvider } from '@agent-ready-assets/runtime-r3f';
import { AssetLibrary } from '@agent-ready-assets/runtime-three';
const KIT_URL = '/assets/stylized-town/kit.json';
const ASSET = 'stylized-town/cafe-01@0.1.0';
/** Marks the canvas once every <Asset> reported onReady (handy for tests). */
function useReadyFlag(expected: number): () => void {
const [count, setCount] = useState(0);
useEffect(() => {
if (count >= expected) document.querySelector('canvas')?.setAttribute('data-ready', 'true');
}, [count, expected]);
return () => setCount((n) => n + 1);
}
function App({ library }: { library: AssetLibrary }) {
const onReady = useReadyFlag(2);
return (
<Canvas camera={{ position: [9.91, 6.86, 14.49], fov: 40 }} gl={{ preserveDrawingBuffer: true }}>
<color attach="background" args={['#e9e4da']} />
<hemisphereLight args={[0xffffff, 0x8d7c64, 1.4]} />
<directionalLight position={[4, 8, 5]} intensity={2} />
<AssetLibraryProvider library={library}>
<Asset assetId={ASSET} position={[-2.425, 0, 0]} onReady={onReady} onError={(e) => console.error(e)} />
{/* customize accepts only declared capabilities; anything else calls onError with UNSUPPORTED_OPERATION */}
<Asset assetId={ASSET} customize={{"front-door":"door-01","awning":false,"terrace":false,"wall-color":"ivory"}} position={[2.425, 0, 0]} onReady={onReady} onError={(e) => console.error(e)} />
</AssetLibraryProvider>
</Canvas>
);
}
AssetLibrary.fromKit(KIT_URL).then(
(library) => createRoot(document.getElementById('root')!).render(<StrictMode><App library={library} /></StrictMode>),
(error: unknown) => console.error(error),
);
{
"schema_version": "1.0.0",
"asset": "stylized-town/cafe-01@0.1.0",
"values": {
"front-door": "door-01",
"awning": false,
"terrace": false,
"wall-color": "ivory"
}
}Quality reportAutomated checks passed
Every automated check that applies passed on this exact file, including glTF validity, scale and pivots, materials and a Three.js render in Chromium. The asset was released after review.
These are the publisher's own automated checks, not an independent certification.
Read the full report