Images, files, and mesh resources
Pass data to the interface through resource references rather than treating local paths as web URLs.
Pass references, then read content
Python disk paths are not directly readable page URLs. Publish resources, return references, then obtain display URLs or bytes. References have scope and expiry; do not save them as permanent source-file locations.
Choose publication by source
| Source | Method and notes |
|---|---|
| In-memory bytes | resource.bytes: provide data and MIME. |
| Disk file | resource.file: provide a valid path for the framework to publish. |
| Blender image | resource.image: bytes format accepts exactly one of data/path/image; rgba32f accepts image/source. |
| Blender mesh | resource.mesh: supply an object. Default maximum is 500000 triangles; simplify complex previews first. |
Publish through plugin.bridge().resource. Set ttl_seconds/window_key as needed; actions can pass context.window_key. Multiple active windows require an explicit target. Changing URLs cannot bypass window scope or access another add-on's resources.
Read the current render result
Using the starter template with bpy imported and _get_plugin bound, add this module function and register once. It reads an existing render result without rendering.
def _render_preview(payload, context):
image = bpy.data.images.get("Render Result")
if image is None or not image.has_data:
return {"ok": False, "message": "还没有可用的渲染结果。"}
ref = _get_plugin().bridge().resource.image(
"render-preview", image=image, window_key=context.window_key, ttl_seconds=300
)
return {"ok": True, "ref": ref}Register once after bind succeeds in _get_plugin:
_plugin.bridge().action("plugin.my_addon.render_preview", _render_preview)Add an img and status element, then pass both real elements to this function from a button handler.
async function refreshPreview(image, output) {
try {
const webui = window.acquireNexusWebUI();
const result = await webui.action.call("plugin.my_addon.render_preview");
if (!result.ok) { output.textContent = result.message; return; }
const { url } = await webui.resource.url(result.ref);
image.src = url;
output.textContent = "已取得预览地址,请检查图像是否显示。";
} catch (error) {
output.textContent = `预览读取失败:${error.message || String(error)}`;
}
}Obtaining a URL does not guarantee decoding. Update final display status in img load/error handlers. Use resource.arrayBuffer for binary data rather than decoding image bytes as text.
Return page content to Python
action.callWithResource sends Blob, ArrayBuffer, or typed views and adds resourceId to the payload. In the handler, context.resource.take(resourceId) yields a one-time temporary file. Explicitly declare both nexus_web.action.plugin.call and nexus_web.resource.write.
take succeeds once. The framework deletes the temporary file after the handler ends. Read or persist inside the callback, not by handing the path to later tasks. Purpose, format validation, and Blender writes remain application responsibilities.
Renew expired references
- Expired resource: republish or reread, not repeated loading of the old URL.
- Disposed client or closed owning window: verify references rather than reusing invalid data.
- Empty image source: check actual render/image data exists.
- Oversized mesh: simplify or adjust limits with understood cost. Do not hide failure as an empty model.
For imports, see Drop and pick; for exports, see Save files.