Fix config view
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
import React, { useEffect, useRef } from 'react';
|
||||
import React, { useEffect } from 'react';
|
||||
import { AppConfig, PerforationPattern } from '../types';
|
||||
import { Settings2, Grid, Circle, Triangle, Hexagon, LayoutGrid } from 'lucide-react';
|
||||
import { Settings2, Box, Ruler, LayoutGrid, Circle, Hexagon, Triangle, Scan } from 'lucide-react';
|
||||
|
||||
interface Props {
|
||||
config: AppConfig;
|
||||
@@ -9,17 +9,17 @@ interface Props {
|
||||
|
||||
export const ConfigStep: React.FC<Props> = ({ config, onChange }) => {
|
||||
|
||||
// Инициализация дефолтных значений, если их нет
|
||||
// Инициализация дефолтных значений перфорации
|
||||
useEffect(() => {
|
||||
if (!config.perforation) {
|
||||
onChange({
|
||||
...config,
|
||||
perforation: { enabled: false, pattern: 'hexagon', diameter: 8, spacing: 4 }
|
||||
perforation: { enabled: false, pattern: 'hexagon', diameter: 8, spacing: 2 }
|
||||
});
|
||||
}
|
||||
}, []);
|
||||
|
||||
const perf = config.perforation || { enabled: false, pattern: 'hexagon', diameter: 8, spacing: 4 };
|
||||
const perf = config.perforation || { enabled: false, pattern: 'hexagon', diameter: 8, spacing: 2 };
|
||||
|
||||
const updatePerf = (updates: Partial<typeof perf>) => {
|
||||
onChange({ ...config, perforation: { ...perf, ...updates } });
|
||||
@@ -29,41 +29,46 @@ export const ConfigStep: React.FC<Props> = ({ config, onChange }) => {
|
||||
onChange({ ...config, drawer: { ...config.drawer, [key]: value } });
|
||||
};
|
||||
|
||||
// --- RENDER PREVIEW (SVG) ---
|
||||
// --- RENDER PREVIEW ---
|
||||
const renderPreview = () => {
|
||||
if (!perf.enabled) return <div className="text-gray-500 text-xs flex items-center justify-center h-full">Перфорация выключена</div>;
|
||||
|
||||
const size = perf.diameter;
|
||||
const gap = Math.max(2, perf.spacing); // Минимальный зазор 2мм
|
||||
const gap = Math.max(2, perf.spacing);
|
||||
const step = size + gap;
|
||||
const W = 140;
|
||||
const H = 100;
|
||||
const W = 200;
|
||||
const H = 120;
|
||||
|
||||
const elements = [];
|
||||
const rows = Math.floor(H / (step * 0.866)); // 0.866 для сот (sin 60)
|
||||
// Приблизительный расчет для превью
|
||||
const rows = Math.floor(H / (step * 0.866));
|
||||
const cols = Math.floor(W / step);
|
||||
|
||||
const startX = (W - (cols * step)) / 2;
|
||||
const startY = (H - (rows * step * 0.866)) / 2;
|
||||
|
||||
for(let j=0; j<rows; j++) {
|
||||
const isOdd = j % 2 !== 0;
|
||||
const y = 10 + j * (perf.pattern === 'circle' ? step : step * 0.866);
|
||||
const y = startY + j * (perf.pattern === 'circle' ? step : step * 0.866);
|
||||
|
||||
for(let i=0; i<cols; i++) {
|
||||
let x = 10 + i * step;
|
||||
let x = startX + i * step;
|
||||
if ((perf.pattern === 'hexagon' || perf.pattern === 'triangle') && isOdd) x += step / 2;
|
||||
|
||||
if (x > W - 10 || y > H - 10) continue;
|
||||
if (x > W - size || y > H - size) continue;
|
||||
|
||||
const color = "#3b82f6";
|
||||
|
||||
if (perf.pattern === 'circle') {
|
||||
elements.push(<circle key={`${i}-${j}`} cx={x} cy={y} r={size/2} fill="#3b82f6" />);
|
||||
elements.push(<circle key={`${i}-${j}`} cx={x} cy={y} r={size/2} fill={color} />);
|
||||
} else if (perf.pattern === 'hexagon') {
|
||||
// Рисуем шестиугольник
|
||||
const r = size / 2;
|
||||
const points = [];
|
||||
for (let k = 0; k < 6; k++) {
|
||||
const angle = (k * 60 + 30) * Math.PI / 180;
|
||||
points.push(`${x + r * Math.cos(angle)},${y + r * Math.sin(angle)}`);
|
||||
}
|
||||
elements.push(<polygon key={`${i}-${j}`} points={points.join(' ')} fill="#3b82f6" />);
|
||||
elements.push(<polygon key={`${i}-${j}`} points={points.join(' ')} fill={color} />);
|
||||
} else if (perf.pattern === 'triangle') {
|
||||
const r = size / 2;
|
||||
const angleOffset = isOdd ? 180 : 0;
|
||||
@@ -72,100 +77,208 @@ export const ConfigStep: React.FC<Props> = ({ config, onChange }) => {
|
||||
const angle = (k * 120 - 90 + angleOffset) * Math.PI / 180;
|
||||
points.push(`${x + r * Math.cos(angle)},${y + r * Math.sin(angle)}`);
|
||||
}
|
||||
elements.push(<polygon key={`${i}-${j}`} points={points.join(' ')} fill="#3b82f6" />);
|
||||
elements.push(<polygon key={`${i}-${j}`} points={points.join(' ')} fill={color} />);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<svg viewBox={`0 0 ${W} ${H}`} className="w-full h-full bg-slate-900 border border-slate-700 rounded">
|
||||
<svg viewBox={`0 0 ${W} ${H}`} className="w-full h-full bg-slate-950/50 border border-slate-700/50 rounded">
|
||||
{elements}
|
||||
</svg>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="space-y-6 pb-20">
|
||||
{/* 1. ГАБАРИТЫ */}
|
||||
<section className="bg-slate-900 p-5 rounded-xl border border-slate-800 shadow-lg">
|
||||
<h2 className="text-lg font-bold mb-4 flex items-center gap-2 text-primary"><Settings2 size={20}/> 1. Размеры ящика</h2>
|
||||
<div className="grid grid-cols-3 gap-4">
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1">Ширина (X)</label>
|
||||
<input type="number" value={config.drawer.width} onChange={(e) => updateDrawer('width', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg px-3 py-2 text-white focus:ring-2 focus:ring-primary outline-none mt-1"/>
|
||||
</div>
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1">Глубина (Y)</label>
|
||||
<input type="number" value={config.drawer.depth} onChange={(e) => updateDrawer('depth', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg px-3 py-2 text-white focus:ring-2 focus:ring-primary outline-none mt-1"/>
|
||||
</div>
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1">Высота (Z)</label>
|
||||
<input type="number" value={config.drawer.height} onChange={(e) => updateDrawer('height', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg px-3 py-2 text-white focus:ring-2 focus:ring-primary outline-none mt-1"/>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
<div className="max-w-5xl mx-auto space-y-6 pb-24">
|
||||
|
||||
{/* ВЕРХНИЙ БЛОК: Размеры и Параметры печати */}
|
||||
<div className="grid grid-cols-1 lg:grid-cols-2 gap-6">
|
||||
|
||||
{/* 1. РАЗМЕРЫ */}
|
||||
<section className="bg-slate-900 p-6 rounded-xl border border-slate-800 shadow-xl">
|
||||
<h2 className="text-lg font-bold mb-6 flex items-center gap-2 text-blue-400">
|
||||
<Box size={20}/> 1. Размеры
|
||||
</h2>
|
||||
|
||||
<div className="space-y-5">
|
||||
<div className="bg-slate-950/50 p-4 rounded-lg border border-slate-800/50">
|
||||
<h3 className="text-xs font-bold text-gray-400 uppercase mb-3 flex items-center gap-2"><Ruler size={14}/> Внутренние размеры ящика</h3>
|
||||
<div className="space-y-4">
|
||||
<div>
|
||||
<label className="text-xs text-gray-500 mb-1.5 block ml-1">Ширина (X)</label>
|
||||
<div className="relative">
|
||||
<input type="number" value={config.drawer.width} onChange={(e) => updateDrawer('width', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg pl-4 pr-12 py-2.5 text-white focus:ring-2 focus:ring-blue-500/50 outline-none transition-all font-mono"/>
|
||||
<span className="absolute right-4 top-1/2 -translate-y-1/2 text-xs text-gray-500 font-bold">MM</span>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<label className="text-xs text-gray-500 mb-1.5 block ml-1">Глубина (Y)</label>
|
||||
<div className="relative">
|
||||
<input type="number" value={config.drawer.depth} onChange={(e) => updateDrawer('depth', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg pl-4 pr-12 py-2.5 text-white focus:ring-2 focus:ring-blue-500/50 outline-none transition-all font-mono"/>
|
||||
<span className="absolute right-4 top-1/2 -translate-y-1/2 text-xs text-gray-500 font-bold">MM</span>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<label className="text-xs text-gray-500 mb-1.5 block ml-1">Высота (Z)</label>
|
||||
<div className="relative">
|
||||
<input type="number" value={config.drawer.height} onChange={(e) => updateDrawer('height', parseFloat(e.target.value))} className="w-full bg-slate-800 border border-slate-700 rounded-lg pl-4 pr-12 py-2.5 text-white focus:ring-2 focus:ring-blue-500/50 outline-none transition-all font-mono"/>
|
||||
<span className="absolute right-4 top-1/2 -translate-y-1/2 text-xs text-gray-500 font-bold">MM</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
{/* 2. ПЕРФОРАЦИЯ */}
|
||||
<section className="bg-slate-900 p-5 rounded-xl border border-slate-800 shadow-lg">
|
||||
<div className="flex justify-between items-center mb-4">
|
||||
<h2 className="text-lg font-bold flex items-center gap-2 text-primary"><LayoutGrid size={20}/> 2. Перфорация (узоры)</h2>
|
||||
<div className="flex items-center gap-2">
|
||||
<span className="text-sm text-gray-400">{perf.enabled ? 'Включено' : 'Выключено'}</span>
|
||||
{/* 2. ПАРАМЕТРЫ ПЕЧАТИ */}
|
||||
<section className="bg-slate-900 p-6 rounded-xl border border-slate-800 shadow-xl">
|
||||
<h2 className="text-lg font-bold mb-6 flex items-center gap-2 text-yellow-500">
|
||||
<Settings2 size={20}/> Параметры печати
|
||||
</h2>
|
||||
|
||||
<div className="bg-slate-950/50 p-4 rounded-lg border border-slate-800/50 space-y-6">
|
||||
|
||||
{/* Wall Thickness */}
|
||||
<div>
|
||||
<div className="flex justify-between text-xs font-medium text-gray-400 mb-2">
|
||||
<span>Толщина стенок</span>
|
||||
<span className="text-blue-400 bg-blue-400/10 px-2 py-0.5 rounded">{config.wallThickness} мм</span>
|
||||
</div>
|
||||
<input type="range" min="0.8" max="4.0" step="0.4"
|
||||
value={config.wallThickness}
|
||||
onChange={(e) => onChange({...config, wallThickness: parseFloat(e.target.value)})}
|
||||
className="w-full h-1.5 bg-slate-700 rounded-lg appearance-none cursor-pointer accent-blue-500"
|
||||
/>
|
||||
<div className="flex justify-between text-[10px] text-gray-600 mt-1 px-1">
|
||||
<span>0.8</span><span>4.0</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Corner Radius */}
|
||||
<div>
|
||||
<div className="flex justify-between text-xs font-medium text-gray-400 mb-2">
|
||||
<span>Радиус скругления</span>
|
||||
<span className="text-purple-400 bg-purple-400/10 px-2 py-0.5 rounded">{config.cornerRadius} мм</span>
|
||||
</div>
|
||||
<input type="range" min="0" max="20" step="1"
|
||||
value={config.cornerRadius}
|
||||
onChange={(e) => onChange({...config, cornerRadius: parseFloat(e.target.value)})}
|
||||
className="w-full h-1.5 bg-slate-700 rounded-lg appearance-none cursor-pointer accent-purple-500"
|
||||
/>
|
||||
<div className="flex justify-between text-[10px] text-gray-600 mt-1 px-1">
|
||||
<span>0</span><span>20</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Tolerance */}
|
||||
<div>
|
||||
<div className="flex justify-between text-xs font-medium text-gray-400 mb-2">
|
||||
<span>Зазор (Tolerance)</span>
|
||||
<span className="text-yellow-400 bg-yellow-400/10 px-2 py-0.5 rounded">{config.printerTolerance} мм</span>
|
||||
</div>
|
||||
<input type="range" min="0" max="1.0" step="0.05"
|
||||
value={config.printerTolerance}
|
||||
onChange={(e) => onChange({...config, printerTolerance: parseFloat(e.target.value)})}
|
||||
className="w-full h-1.5 bg-slate-700 rounded-lg appearance-none cursor-pointer accent-yellow-500"
|
||||
/>
|
||||
<div className="flex justify-between text-[10px] text-gray-600 mt-1 px-1">
|
||||
<span>0.0</span><span>1.0</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
{/* НИЖНИЙ БЛОК: ПЕРФОРАЦИЯ */}
|
||||
<section className={`bg-slate-900 p-6 rounded-xl border border-slate-800 shadow-xl transition-all ${perf.enabled ? 'border-blue-500/30' : ''}`}>
|
||||
<div className="flex justify-between items-center mb-6">
|
||||
<h2 className={`text-lg font-bold flex items-center gap-2 ${perf.enabled ? 'text-blue-400' : 'text-gray-500'}`}>
|
||||
<LayoutGrid size={20}/> 2. Перфорация (узоры)
|
||||
</h2>
|
||||
<div className="flex items-center gap-3">
|
||||
<span className="text-xs font-bold text-gray-500 uppercase tracking-wider">{perf.enabled ? 'Включено' : 'Выключено'}</span>
|
||||
<button
|
||||
onClick={() => updatePerf({ enabled: !perf.enabled })}
|
||||
className={`w-12 h-6 rounded-full p-1 transition-colors ${perf.enabled ? 'bg-primary' : 'bg-slate-700'}`}
|
||||
className={`w-14 h-7 rounded-full p-1 transition-all duration-300 ${perf.enabled ? 'bg-blue-600 shadow-lg shadow-blue-900/50' : 'bg-slate-700'}`}
|
||||
>
|
||||
<div className={`w-4 h-4 bg-white rounded-full shadow-md transform transition-transform ${perf.enabled ? 'translate-x-6' : 'translate-x-0'}`}/>
|
||||
<div className={`w-5 h-5 bg-white rounded-full shadow-sm transform transition-transform duration-300 ${perf.enabled ? 'translate-x-7' : 'translate-x-0'}`}/>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className={`grid grid-cols-1 md:grid-cols-2 gap-6 transition-opacity ${perf.enabled ? 'opacity-100' : 'opacity-50 pointer-events-none'}`}>
|
||||
{/* Controls */}
|
||||
<div className="space-y-4">
|
||||
<div className={`grid grid-cols-1 md:grid-cols-2 gap-8 transition-all duration-500 ${perf.enabled ? 'opacity-100 max-h-[500px]' : 'opacity-40 pointer-events-none grayscale max-h-[100px] overflow-hidden'}`}>
|
||||
{/* Настройки */}
|
||||
<div className="space-y-6">
|
||||
|
||||
{/* Тип узора */}
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1 mb-2 block">Тип узора</label>
|
||||
<div className="flex gap-2">
|
||||
<button onClick={() => updatePerf({ pattern: 'circle' })} className={`flex-1 py-2 rounded border flex items-center justify-center gap-2 ${perf.pattern === 'circle' ? 'bg-primary/20 border-primary text-primary' : 'bg-slate-800 border-slate-700 text-gray-400'}`}><Circle size={16}/> Круг</button>
|
||||
<button onClick={() => updatePerf({ pattern: 'hexagon' })} className={`flex-1 py-2 rounded border flex items-center justify-center gap-2 ${perf.pattern === 'hexagon' ? 'bg-primary/20 border-primary text-primary' : 'bg-slate-800 border-slate-700 text-gray-400'}`}><Hexagon size={16}/> Соты</button>
|
||||
<button onClick={() => updatePerf({ pattern: 'triangle' })} className={`flex-1 py-2 rounded border flex items-center justify-center gap-2 ${perf.pattern === 'triangle' ? 'bg-primary/20 border-primary text-primary' : 'bg-slate-800 border-slate-700 text-gray-400'}`}><Triangle size={16}/> Треуг.</button>
|
||||
<label className="text-xs font-bold text-gray-400 uppercase mb-3 block">Тип узора</label>
|
||||
<div className="grid grid-cols-3 gap-3">
|
||||
<button onClick={() => updatePerf({ pattern: 'circle' })} className={`py-3 rounded-lg border flex flex-col items-center justify-center gap-2 transition-all ${perf.pattern === 'circle' ? 'bg-blue-500/10 border-blue-500 text-blue-400 shadow-lg shadow-blue-900/20' : 'bg-slate-800 border-slate-700 text-gray-500 hover:bg-slate-700 hover:text-gray-300'}`}>
|
||||
<Circle size={20}/> <span className="text-xs font-medium">Круг</span>
|
||||
</button>
|
||||
<button onClick={() => updatePerf({ pattern: 'hexagon' })} className={`py-3 rounded-lg border flex flex-col items-center justify-center gap-2 transition-all ${perf.pattern === 'hexagon' ? 'bg-blue-500/10 border-blue-500 text-blue-400 shadow-lg shadow-blue-900/20' : 'bg-slate-800 border-slate-700 text-gray-500 hover:bg-slate-700 hover:text-gray-300'}`}>
|
||||
<Hexagon size={20}/> <span className="text-xs font-medium">Соты</span>
|
||||
</button>
|
||||
<button onClick={() => updatePerf({ pattern: 'triangle' })} className={`py-3 rounded-lg border flex flex-col items-center justify-center gap-2 transition-all ${perf.pattern === 'triangle' ? 'bg-blue-500/10 border-blue-500 text-blue-400 shadow-lg shadow-blue-900/20' : 'bg-slate-800 border-slate-700 text-gray-500 hover:bg-slate-700 hover:text-gray-300'}`}>
|
||||
<Triangle size={20}/> <span className="text-xs font-medium">Треуг.</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="grid grid-cols-2 gap-4">
|
||||
{/* Ползунки параметров */}
|
||||
<div className="bg-slate-950/50 p-4 rounded-lg border border-slate-800/50 space-y-6">
|
||||
{/* Diameter */}
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1">Диаметр (мм)</label>
|
||||
<input type="number" min="2" max="12" step="0.5" value={perf.diameter} onChange={(e) => updatePerf({ diameter: Math.min(12, parseFloat(e.target.value)) })} className="w-full bg-slate-800 border border-slate-700 rounded-lg px-3 py-2 text-white mt-1"/>
|
||||
<div className="flex justify-between text-xs font-medium text-gray-400 mb-2">
|
||||
<span>Диаметр отверстий</span>
|
||||
<span className="text-blue-400 bg-blue-400/10 px-2 py-0.5 rounded font-mono">{perf.diameter} мм</span>
|
||||
</div>
|
||||
<input type="range" min="2" max="12" step="0.5"
|
||||
value={perf.diameter}
|
||||
onChange={(e) => updatePerf({ diameter: parseFloat(e.target.value) })}
|
||||
className="w-full h-1.5 bg-slate-700 rounded-lg appearance-none cursor-pointer accent-blue-500"
|
||||
/>
|
||||
<div className="flex justify-between text-[10px] text-gray-600 mt-1 px-1">
|
||||
<span>2 мм</span><span>12 мм</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Spacing */}
|
||||
<div>
|
||||
<label className="text-xs text-gray-400 font-bold ml-1">Зазор (мм)</label>
|
||||
<input type="number" min="2" value={perf.spacing} onChange={(e) => updatePerf({ spacing: Math.max(2, parseFloat(e.target.value)) })} className="w-full bg-slate-800 border border-slate-700 rounded-lg px-3 py-2 text-white mt-1"/>
|
||||
<div className="flex justify-between text-xs font-medium text-gray-400 mb-2">
|
||||
<span>Зазор (между отверстиями)</span>
|
||||
<span className="text-blue-400 bg-blue-400/10 px-2 py-0.5 rounded font-mono">{perf.spacing} мм</span>
|
||||
</div>
|
||||
<input type="range" min="2" max="10" step="0.5"
|
||||
value={perf.spacing}
|
||||
onChange={(e) => updatePerf({ spacing: parseFloat(e.target.value) })}
|
||||
className="w-full h-1.5 bg-slate-700 rounded-lg appearance-none cursor-pointer accent-blue-500"
|
||||
/>
|
||||
<div className="flex justify-between text-[10px] text-gray-600 mt-1 px-1">
|
||||
<span>2 мм</span><span>10 мм</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Preview */}
|
||||
<div className="h-32 md:h-auto flex flex-col">
|
||||
<span className="text-xs text-gray-400 mb-2 font-bold ml-1">Предпросмотр</span>
|
||||
{renderPreview()}
|
||||
<div className="flex flex-col">
|
||||
<div className="flex justify-between items-end mb-2">
|
||||
<label className="text-xs font-bold text-gray-400 uppercase">Предпросмотр</label>
|
||||
<span className="text-[10px] text-gray-600 flex items-center gap-1"><Scan size={10}/> Масштаб условен</span>
|
||||
</div>
|
||||
<div className="flex-1 min-h-[200px] bg-slate-950 rounded-lg border border-slate-800 relative overflow-hidden flex items-center justify-center p-4">
|
||||
<div className="w-full h-full max-w-[300px] max-h-[180px] shadow-2xl">
|
||||
{renderPreview()}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
{/* 3. ПРОЧЕЕ */}
|
||||
<section className="bg-slate-900 p-5 rounded-xl border border-slate-800 shadow-lg opacity-80 hover:opacity-100 transition-opacity">
|
||||
<h2 className="text-sm font-bold mb-4 text-gray-400">Дополнительно</h2>
|
||||
<div className="flex gap-4">
|
||||
<div>
|
||||
<label className="text-xs text-gray-500 block">Толщина стенок</label>
|
||||
<input type="number" step="0.1" value={config.wallThickness} onChange={(e) => onChange({...config, wallThickness: parseFloat(e.target.value)})} className="bg-slate-800 border border-slate-700 rounded px-2 py-1 text-sm w-20 text-gray-300"/>
|
||||
</div>
|
||||
<div>
|
||||
<label className="text-xs text-gray-500 block">Скругление углов</label>
|
||||
<input type="number" value={config.cornerRadius} onChange={(e) => onChange({...config, cornerRadius: parseFloat(e.target.value)})} className="bg-slate-800 border border-slate-700 rounded px-2 py-1 text-sm w-20 text-gray-300"/>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
Reference in New Issue
Block a user