chore: checkpoint web Blender migration source, tools and docs
Some checks failed
M6 deployable RC / quick (push) Has been cancelled
M6 deployable RC / chromium (push) Has been cancelled
M6 deployable RC / release (push) Has been cancelled

Accumulated uncommitted work: GHOST Web backend, WebGL/GPU web layer,
web workflow engine and protocol, tooling, docs and task records.
Large generated evidence, user-testing archives, build snapshots and
imported test assets remain untracked.

Co-Authored-By: Claude Code <noreply@anthropic.com>
This commit is contained in:
mes123456
2026-11-10 11:18:01 +08:00
parent 122142c26c
commit f3e21c6b98
6887 changed files with 257154 additions and 12294 deletions

View File

@@ -167,6 +167,7 @@ function canonicalGraph(material: MaterialIR): string {
imageId: node.imageId ?? null,
defaultValue: node.defaultValue ?? null,
properties: node.properties ?? null,
...(node.sockets?{inputs:node.sockets.filter(socket=>socket.direction==='INPUT').map(socket=>({id:socket.id,value:socket.value??null}))}:{}),
})),
links: (material.links ?? []).map((link) => ({
fromNodeId: link.fromNodeId,
@@ -393,8 +394,12 @@ export function compileMaterialGraph(material: MaterialIR, context: ShaderCompil
else if (node.type === "MATH") {
const first = sourceLink(incoming, node.id, "Value") ?? sourceLink(incoming, node.id, "A");
const second = sourceLink(incoming, node.id, "Value_001") ?? sourceLink(incoming, node.id, "B");
const left = first ? evalScalar(first.fromNodeId, depth + 1) : undefined;
const right = second ? evalScalar(second.fromNodeId, depth + 1) : undefined;
const socketDefault=(id:string):number|undefined=>{
const value=node.sockets?.find(socket=>socket.direction==='INPUT'&&normalizeSocket(socket.id)===normalizeSocket(id))?.value;
return finite(value)?value:undefined;
};
const left = first ? evalScalar(first.fromNodeId, depth + 1) : socketDefault('Value');
const right = second ? evalScalar(second.fromNodeId, depth + 1) : socketDefault('Value_001');
if (left !== undefined && right !== undefined) {
switch (node.properties?.operation) {
case "ADD": value = left + right; break;
@@ -490,7 +495,8 @@ export function compileMaterialGraph(material: MaterialIR, context: ShaderCompil
colorSpace: identity?.colorSpace ?? (binding.usage === "BASE_COLOR" ? "SRGB" : "NON_COLOR"),
};
});
base.compileKey = createShaderCompileKey({ graphHash, rendererBackend, textures: textureKeys });
const parameterHash=nodes.some(node=>node.sockets)?fallbackGraphHash(JSON.stringify({graphHash,parameters:canonicalGraph(material)})):graphHash;
base.compileKey = createShaderCompileKey({ graphHash:parameterHash, rendererBackend, textures: textureKeys });
if (base.textureBindings.length > SHADER_COMPILE_BUDGET.maxTextures) base.issues.push(issue("SHADER_NODE_UNSUPPORTED", "Shader graph exceeds the bounded texture binding budget", "nodes"));
base.compiledNodeTypes = [...new Set(nodes.map((node) => node.type).filter((type): type is CompileNodeType => (SHADER_COMPILE_ALLOWLIST as readonly string[]).includes(type)))];
base.instructions = base.nodeOrder.map((nodeId) => {