Skip to main content
Glama

Spline MCP Server

by aydinfer
material-tools.js7.91 kB
import { z } from 'zod'; import apiClient from '../utils/api-client.js'; /** * Material management tools for Spline.design * @param {object} server - MCP server instance */ export const registerMaterialTools = (server) => { // Get all materials in a scene server.tool( 'getMaterials', { sceneId: z.string().min(1).describe('Scene ID'), }, async ({ sceneId }) => { try { const materials = await apiClient.getMaterials(sceneId); return { content: [ { type: 'text', text: JSON.stringify(materials, null, 2) } ] }; } catch (error) { return { content: [ { type: 'text', text: `Error retrieving materials: ${error.message}` } ], isError: true }; } } ); // Get details of a specific material server.tool( 'getMaterialDetails', { sceneId: z.string().min(1).describe('Scene ID'), materialId: z.string().min(1).describe('Material ID'), }, async ({ sceneId, materialId }) => { try { const material = await apiClient.getMaterial(sceneId, materialId); return { content: [ { type: 'text', text: JSON.stringify(material, null, 2) } ] }; } catch (error) { return { content: [ { type: 'text', text: `Error retrieving material details: ${error.message}` } ], isError: true }; } } ); // Create a new material server.tool( 'createMaterial', { sceneId: z.string().min(1).describe('Scene ID'), name: z.string().min(1).describe('Material name'), type: z.enum([ 'standard', 'physical', 'basic', 'lambert', 'phong', 'toon', 'matcap', 'normal' ]).describe('Material type'), color: z.string().optional().describe('Base color (hex)'), roughness: z.number().min(0).max(1).optional().describe('Surface roughness (0-1)'), metalness: z.number().min(0).max(1).optional().describe('Metalness factor (0-1)'), opacity: z.number().min(0).max(1).optional().describe('Opacity (0-1)'), transparent: z.boolean().optional().describe('Whether the material is transparent'), wireframe: z.boolean().optional().describe('Whether to render as wireframe'), emissive: z.string().optional().describe('Emissive color (hex)'), emissiveIntensity: z.number().min(0).optional().describe('Intensity of emission'), side: z.enum(['front', 'back', 'double']).optional().describe('Which side to render'), flatShading: z.boolean().optional().describe('Use flat shading'), properties: z.record(z.any()).optional().describe('Additional properties'), }, async ({ sceneId, name, type, color, roughness, metalness, opacity, transparent, wireframe, emissive, emissiveIntensity, side, flatShading, properties }) => { try { const materialData = { name, type, ...(color && { color }), ...(roughness !== undefined && { roughness }), ...(metalness !== undefined && { metalness }), ...(opacity !== undefined && { opacity }), ...(transparent !== undefined && { transparent }), ...(wireframe !== undefined && { wireframe }), ...(emissive && { emissive }), ...(emissiveIntensity !== undefined && { emissiveIntensity }), ...(side && { side }), ...(flatShading !== undefined && { flatShading }), ...(properties && { properties }), }; const result = await apiClient.request('POST', `/scenes/${sceneId}/materials`, materialData); return { content: [ { type: 'text', text: `Material created successfully with ID: ${result.id}` } ] }; } catch (error) { return { content: [ { type: 'text', text: `Error creating material: ${error.message}` } ], isError: true }; } } ); // Update an existing material server.tool( 'updateMaterial', { sceneId: z.string().min(1).describe('Scene ID'), materialId: z.string().min(1).describe('Material ID'), color: z.string().optional().describe('Base color (hex)'), roughness: z.number().min(0).max(1).optional().describe('Surface roughness (0-1)'), metalness: z.number().min(0).max(1).optional().describe('Metalness factor (0-1)'), opacity: z.number().min(0).max(1).optional().describe('Opacity (0-1)'), transparent: z.boolean().optional().describe('Whether the material is transparent'), wireframe: z.boolean().optional().describe('Whether to render as wireframe'), emissive: z.string().optional().describe('Emissive color (hex)'), emissiveIntensity: z.number().min(0).optional().describe('Intensity of emission'), side: z.enum(['front', 'back', 'double']).optional().describe('Which side to render'), flatShading: z.boolean().optional().describe('Use flat shading'), properties: z.record(z.any()).optional().describe('Additional properties'), }, async ({ sceneId, materialId, color, roughness, metalness, opacity, transparent, wireframe, emissive, emissiveIntensity, side, flatShading, properties }) => { try { const updateData = { ...(color && { color }), ...(roughness !== undefined && { roughness }), ...(metalness !== undefined && { metalness }), ...(opacity !== undefined && { opacity }), ...(transparent !== undefined && { transparent }), ...(wireframe !== undefined && { wireframe }), ...(emissive && { emissive }), ...(emissiveIntensity !== undefined && { emissiveIntensity }), ...(side && { side }), ...(flatShading !== undefined && { flatShading }), ...(properties && { properties }), }; await apiClient.updateMaterial(sceneId, materialId, updateData); return { content: [ { type: 'text', text: `Material ${materialId} updated successfully` } ] }; } catch (error) { return { content: [ { type: 'text', text: `Error updating material: ${error.message}` } ], isError: true }; } } ); // Apply a material to an object server.tool( 'applyMaterial', { sceneId: z.string().min(1).describe('Scene ID'), objectId: z.string().min(1).describe('Object ID'), materialId: z.string().min(1).describe('Material ID'), }, async ({ sceneId, objectId, materialId }) => { try { await apiClient.request('POST', `/scenes/${sceneId}/objects/${objectId}/material`, { materialId }); return { content: [ { type: 'text', text: `Material ${materialId} applied to object ${objectId} successfully` } ] }; } catch (error) { return { content: [ { type: 'text', text: `Error applying material: ${error.message}` } ], isError: true }; } } ); };

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/aydinfer/spline-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server