/// <reference path="../../lynx.d.ts" />
/**
 * FormControlLabel Component - Lynx 版 MUI FormControlLabel
 * 100% 一比一复刻 MUI FormControlLabel
 * 
 * 将表单控件（Checkbox、Radio、Switch）与标签组合在一起
 * 
 * 对应 MUI: packages/mui-material/src/FormControlLabel/FormControlLabel.js
 */
import './FormControlLabel.css'
import formControlLabelClasses, { getFormControlLabelUtilityClass } from './formControlLabelClasses'
import { useFormControl, formControlState } from '../FormControl'
export { formControlLabelClasses, getFormControlLabelUtilityClass }

// =============================================
// 类型定义
// =============================================

export type FormControlLabelLabelPlacement = 'end' | 'start' | 'top' | 'bottom'

export interface FormControlLabelProps {
  /** 表单控件 */
  control: any
  /** 标签文本 */
  label: any
  /** 自定义类名 */
  className?: string
  /** 样式类覆盖 */
  classes?: Partial<typeof formControlLabelClasses>
  /** 是否选中 - 传递给 control */
  checked?: boolean
  /** 是否禁用 */
  disabled?: boolean
  /** 是否禁用排版 */
  disableTypography?: boolean
  /** input 元素的 ref */
  inputRef?: any
  /** 标签位置 */
  labelPlacement?: FormControlLabelLabelPlacement
  /** name 属性 */
  name?: string
  /** 变化回调 */
  onChange?: (event: any, checked: boolean) => void
  /** 是否必填 */
  required?: boolean
  /** 内联样式 */
  style?: Record<string, any>
  /** sx 属性 */
  sx?: Record<string, any>
  /** 值 */
  value?: string
}

// =============================================
// 辅助函数
// =============================================

function composeClasses(
  slots: Record<string, (string | boolean | null | undefined)[]>,
  getUtilityClass: (slot: string) => string,
  classes?: Record<string, string>
): Record<string, string> {
  const output: Record<string, string> = {}
  
  Object.keys(slots).forEach((slot) => {
    output[slot] = slots[slot]
      .filter(Boolean)
      .map((key) => {
        if (classes && classes[key as string]) {
          return `${getUtilityClass(key as string)} ${classes[key as string]}`
        }
        return getUtilityClass(key as string)
      })
      .join(' ')
  })
  
  return output
}

// =============================================
// useUtilityClasses
// =============================================

interface OwnerState extends FormControlLabelProps {}

function useUtilityClasses(ownerState: OwnerState & { error?: boolean }) {
  const { 
    classes, 
    disabled, 
    error,
    required,
    labelPlacement = 'end' 
  } = ownerState

  const slots = {
    root: [
      'root',
      disabled && 'disabled',
      error && 'error',
      required && 'required',
      labelPlacement !== 'end' && `labelPlacement${labelPlacement.charAt(0).toUpperCase() + labelPlacement.slice(1)}`,
    ],
    label: ['label', disabled && 'disabled'],
    asterisk: ['asterisk', error && 'error'],
  }

  return composeClasses(slots, getFormControlLabelUtilityClass, classes)
}

// =============================================
// FormControlLabel 组件
// =============================================

export function FormControlLabel(props: FormControlLabelProps) {
  const {
    control,
    label,
    className,
    classes: classesProp,
    checked,
    disabled: disabledProp,
    disableTypography = false,
    inputRef,
    labelPlacement = 'end',
    name,
    onChange,
    required: requiredProp,
    style,
    sx,
    value,
    ...other
  } = props

  const muiFormControl = useFormControl()

  const fcs = formControlState({
    props,
    muiFormControl,
    states: ['disabled', 'error', 'required'],
  })

  const disabled = disabledProp ?? control?.props?.disabled ?? fcs.disabled
  const required = requiredProp ?? control?.props?.required ?? fcs.required

  const ownerState: OwnerState & { error?: boolean } = {
    ...props,
    disabled,
    labelPlacement,
    required,
    error: fcs.error,
  }

  const classes = useUtilityClasses(ownerState)

  // 增强控件，注入必要的 props
  const controlProps: Record<string, any> = {
    disabled,
    required,
  }

  // 传递可选 props
  if (checked !== undefined && control?.props?.checked === undefined) {
    controlProps.checked = checked
  }
  if (name !== undefined && control?.props?.name === undefined) {
    controlProps.name = name
  }
  if (onChange !== undefined && control?.props?.onChange === undefined) {
    controlProps.onChange = onChange
  }
  if (value !== undefined && control?.props?.value === undefined) {
    controlProps.value = value
  }
  if (inputRef !== undefined && control?.props?.inputRef === undefined) {
    controlProps.inputRef = inputRef
  }

  const enhancedControl = control ? {
    ...control,
    props: {
      ...control.props,
      ...controlProps,
    }
  } : null

  // 构建类名
  const rootClasses = [
    classes.root,
    formControlLabelClasses.root,
    className,
    disabled && formControlLabelClasses.disabled,
    fcs.error && formControlLabelClasses.error,
    labelPlacement !== 'end' && formControlLabelClasses[`labelPlacement${labelPlacement.charAt(0).toUpperCase() + labelPlacement.slice(1)}` as keyof typeof formControlLabelClasses],
  ].filter(Boolean).join(' ')

  const labelClasses = [
    classes.label,
    formControlLabelClasses.label,
    disabled && formControlLabelClasses.disabled,
  ].filter(Boolean).join(' ')

  // 根据标签位置渲染不同布局
  const renderContent = () => {
    switch (labelPlacement) {
      case 'start':
        return (
          <>
            <text className={labelClasses}>{label}</text>
            {enhancedControl}
          </>
        )
      case 'top':
        return (
          <view className="MuiFormControlLabel-vertical">
            <text className={labelClasses}>{label}</text>
            {enhancedControl}
          </view>
        )
      case 'bottom':
        return (
          <view className="MuiFormControlLabel-vertical">
            {enhancedControl}
            <text className={labelClasses}>{label}</text>
          </view>
        )
      case 'end':
      default:
        return (
          <>
            {enhancedControl}
            <text className={labelClasses}>{label}</text>
          </>
        )
    }
  }

  return (
    <view
      className={rootClasses}
      style={sx ? { ...sx, ...style } : style}
      {...other}
    >
      {renderContent()}
    </view>
  )
}

export default FormControlLabel
