/** * CAD-14 Phase 4a - Werkzeug-Optionen-Panel. * * Rendert das optionsSchema des aktiven V2-Werkzeugs und bindet * die Werte an den toolOptionsService (Quelle fuer den Dispatcher). */ import React, { useState, useEffect, useMemo } from 'react'; import { pluginRegistry } from '../plugins'; import { getToolOption, setToolOption, subscribeToolOptions } from '../services/toolOptionsService'; interface ToolOptionsPanelProps { activeToolId: string | null | undefined; } const ToolOptionsPanel: React.FC = ({ activeToolId }) => { const [, forceRender] = useState(0); // Store-Abonnement: Panel bei Optionsaenderung neu rendern React.useEffect(() => { return subscribeToolOptions(() => forceRender((n) => n + 1)); }, []); const tool = useMemo(() => { if (!activeToolId) return null; return pluginRegistry.getToolV2(activeToolId) ?? null; }, [activeToolId]); const schema = tool?.optionsSchema ?? []; if (!tool || schema.length === 0) return null; const renderField = (field: { key: string; label: string; type: string; min?: number; max?: number; options?: Array<{ value: string; label: string }> }) => { const value = getToolOption(tool.manifest.id, field.key); const onChange = (v: unknown) => setToolOption(tool.manifest.id, field.key, v); if (field.type === 'number') { return ( ); } if (field.type === 'color') { return ( ); } if (field.type === 'select' && field.options) { return ( ); } if (field.type === 'boolean') { return ( ); } return null; }; return (
Werkzeug-Optionen: {tool.manifest.label}
{schema.map((f) => renderField(f as never))}
); }; export default ToolOptionsPanel;