yari-garan/src/core/components/base/input.tsx
MehrdadAdabi f9ced9349b feat: enhance dashboard layout with user profile header and mobile navbar
feat: update campaign types to include user_id_nickname and add comments and signature item interfaces

feat: improve campaign detail page with comments functionality and remove comment feature

feat: refactor campaigns page to use new campaign service and update tab labels to Persian

feat: enhance user profile page with image upload functionality and improved form handling

fix: update router paths for campaign detail page

feat: implement user authentication context and protected route handling

feat: add global types for token management

feat: create utility functions for image handling and uploading
2025-11-24 16:58:35 +03:30

71 lines
2.1 KiB
TypeScript

import { cn } from "@core/lib/utils";
import * as React from "react";
export interface CustomInputProps
extends React.InputHTMLAttributes<HTMLInputElement> {
variant?: "primary" | "info" | "error";
error?: string;
label?: string;
required?: boolean;
}
const CustomInput = React.forwardRef<HTMLInputElement, CustomInputProps>(
(
{
className,
variant = "primary",
error,
label,
disabled,
required,
...props
},
ref
) => {
const finalVariant = error ? "error" : variant;
return (
<div className="w-full">
{label && (
<label className="mb-2 block text-sm font-medium text-foreground text-right">
{label} {required && <span className="text-red-500">*</span>}
</label>
)}
<input
className={cn(
"flex h-12 w-full rounded-lg border-2 bg-background px-4 py-2 text-sm transition-all duration-200 placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-offset-1 disabled:cursor-not-allowed disabled:opacity-50",
{
// Primary variant
"border-gray-300 focus-visible:border-blue-600 focus-visible:ring-blue-600":
finalVariant === "primary" && !disabled,
// Info variant
"border-cyan-300 focus-visible:border-cyan-600 focus-visible:ring-cyan-600":
finalVariant === "info" && !disabled,
// Error variant
"border-red-500 focus-visible:border-red-600 focus-visible:ring-red-600":
finalVariant === "error" && !disabled,
// Disabled state
"border-gray-200 bg-gray-100 text-gray-400": disabled,
},
className
)}
disabled={disabled}
ref={ref}
{...props}
/>
{error && (
<p className="text-end mt-2 text-sm text-red-600 flex items-center gap-1">
{error}
</p>
)}
</div>
);
}
);
CustomInput.displayName = "CustomInput";
export { CustomInput };