UNPKG

bnk-components

Version:

Reusable React components for Issaglam UI - Modern, responsive UI components with TypeScript support

111 lines (110 loc) 6.02 kB
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime"; import { useState, useCallback, useContext } from 'react'; import { createFormField } from './ComponentFactory'; import { FormContext } from '../CrudGrid/CrudGrid'; import './AutoForm.css'; export function AutoForm({ metadata, data, onChange, onSubmit, onCancel, loading = false, readOnly = false, className = '' }) { const [errors, setErrors] = useState({}); const formContext = useContext(FormContext); // Field değişiklik handler'ı const handleFieldChange = useCallback((fieldName, value) => { // Validation const field = metadata.fields.find(f => f.name === fieldName); if (field) { const error = validateField(field, value); setErrors(prev => (Object.assign(Object.assign({}, prev), { [fieldName]: error || '' }))); } // FormContext aracılığıyla değişikliği ilet if (formContext && formContext.onFieldChange) { formContext.onFieldChange(fieldName, value); } // Parent onChange çağır onChange(fieldName, value); }, [metadata, onChange, formContext]); // Field validation const validateField = (field, value) => { const { validation } = field; if (!validation) return null; // Required validation if (validation.required && (!value || value === '')) { return `${field.label || field.name} zorunludur`; } // Min length validation if (validation.minLength && value && value.length < validation.minLength) { return `${field.label || field.name} en az ${validation.minLength} karakter olmalıdır`; } // Max length validation if (validation.maxLength && value && value.length > validation.maxLength) { return `${field.label || field.name} en fazla ${validation.maxLength} karakter olmalıdır`; } // Min value validation if (validation.min !== undefined && value !== undefined && Number(value) < validation.min) { return `${field.label || field.name} en az ${validation.min} olmalıdır`; } // Max value validation if (validation.max !== undefined && value !== undefined && Number(value) > validation.max) { return `${field.label || field.name} en fazla ${validation.max} olmalıdır`; } // Pattern validation if (validation.pattern && value && !new RegExp(validation.pattern).test(value)) { return `${field.label || field.name} geçerli formatta değil`; } // Custom validation if (validation.custom) { return validation.custom(value); } return null; }; // Form submit handler const handleSubmit = useCallback((e) => { e.preventDefault(); // Tüm field'ları validate et const newErrors = {}; metadata.fields.forEach(field => { const error = validateField(field, data[field.name]); if (error) { newErrors[field.name] = error; } }); setErrors(newErrors); // Eğer hata yoksa submit et if (Object.keys(newErrors).length === 0 && onSubmit) { onSubmit(data); } }, [metadata, data, onSubmit]); // Form cancel handler const handleCancel = useCallback(() => { if (onCancel) { onCancel(); } }, [onCancel]); // Field render function const renderField = (field) => { const FieldComponent = createFormField(field); const value = data[field.name]; const error = errors[field.name]; return (_jsx(FieldComponent, { field: field, value: value, onChange: (value) => handleFieldChange(field.name, value), error: error, disabled: loading, readOnly: readOnly }, field.name)); }; // Layout'a göre field'ları grupla const renderFields = () => { const { fields, layout = 'single', sections } = metadata; if (sections && sections.length > 0) { // Section'lı layout return sections.map((section, index) => (_jsxs("div", { className: "auto-form-section", children: [_jsx("h3", { className: "auto-form-section-title", children: section.title }), _jsx("div", { className: "auto-form-section-content", children: section.fields.map(fieldName => { const field = fields.find(f => f.name === fieldName); return field ? renderField(field) : null; }) })] }, index))); } // Layout'a göre field'ları grupla switch (layout) { case 'two-column': return (_jsx("div", { className: "auto-form-two-column", children: fields.map((field, index) => (_jsx("div", { className: "auto-form-field-wrapper", children: renderField(field) }, field.name))) })); case 'three-column': return (_jsx("div", { className: "auto-form-three-column", children: fields.map((field, index) => (_jsx("div", { className: "auto-form-field-wrapper", children: renderField(field) }, field.name))) })); default: // single column return (_jsx("div", { className: "auto-form-single-column", children: fields.map(field => (_jsx("div", { className: "auto-form-field-wrapper", children: renderField(field) }, field.name))) })); } }; return (_jsxs("form", { className: `auto-form ${className}`, onSubmit: handleSubmit, children: [_jsx("div", { className: "auto-form-content", children: renderFields() }), (onSubmit || onCancel) && (_jsxs("div", { className: "auto-form-actions", children: [onSubmit && (_jsx("button", { type: "submit", className: "auto-form-submit-btn", disabled: loading, children: loading ? 'Kaydediliyor...' : 'Kaydet' })), onCancel && (_jsx("button", { type: "button", className: "auto-form-cancel-btn", onClick: handleCancel, disabled: loading, children: "\u0130ptal" }))] }))] })); }