"use client"

import React from 'react'
import {
  useReactTable,
  getCoreRowModel,
  getFilteredRowModel,
  getPaginationRowModel,
  getSortedRowModel,
  ColumnDef,
  flexRender,
  SortingState,
  ColumnFiltersState,
  VisibilityState,
  OnChangeFn,
  Row,
} from '@tanstack/react-table'
import { Button } from '../ui/button'
import { Input } from '../ui/input'
import { Card, CardContent } from '../ui/card'
import { 
  ChevronLeft, 
  ChevronRight, 
  ChevronsLeft, 
  ChevronsRight,
  ChevronDown,
  ArrowUpDown,
  ArrowUp,
  ArrowDown,
  Search,
  Filter,
  Download,
  Settings,
  Lock,
  Sparkles,
  Loader2,
  FileDown,
  FileJson,
  FileSpreadsheet
} from 'lucide-react'
import { cn } from '../../lib/utils'
import { useSubscription } from '../../hooks/use-subscription'
import { motion, AnimatePresence } from 'framer-motion'
import { DataTableColumnToggle } from './data-table-column-toggle'
import { DataTableBulkActions, type BulkAction } from './data-table-bulk-actions'
import { exportData, type ExportFormat, getVisibleColumns } from './data-table-export'
import { DataTableFilterDrawer, type FilterCondition, type FilterOperator } from './data-table-filter-drawer'
import {
  DropdownMenu,
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuTrigger,
} from '../ui/dropdown-menu'

interface DataTableProps<TData, TValue> {
  columns: ColumnDef<TData, TValue>[]
  data: TData[]
  searchable?: boolean
  filterable?: boolean
  exportable?: boolean | {
    formats?: ExportFormat[]
    filename?: string
    onExport?: (data: TData[], format: ExportFormat) => void
  }
  selectable?: boolean
  pagination?: boolean
  pageSize?: number
  className?: string
  onRowSelect?: (rows: TData[]) => void
  onExport?: (data: TData[]) => void
  enableExpandable?: boolean
  renderSubComponent?: (props: { row: { original: TData; id: string } }) => React.ReactNode
  expandedRows?: Set<string>
  onRowExpandChange?: (expandedRows: Set<string>) => void
  bulkActions?: BulkAction<TData>[]
  // Additional props for compatibility
  enableSorting?: boolean
  enableFiltering?: boolean
  enablePagination?: boolean
  enableColumnVisibility?: boolean
  enableRowSelection?: boolean
  filterPlaceholder?: string
  defaultPageSize?: number
  manualPagination?: boolean
  pageCount?: number
  onPaginationChange?: (updater: any) => void
  onSortingChange?: OnChangeFn<SortingState>
  onColumnFiltersChange?: OnChangeFn<ColumnFiltersState>
  state?: any
  features?: {
    sorting?: boolean
    filtering?: boolean
    pagination?: boolean
    search?: boolean
    columnVisibility?: boolean
    rowSelection?: boolean
    export?: boolean | string[]
    density?: boolean
    fullscreen?: boolean
    print?: boolean
  }
  theme?: {
    headerBg?: string
    headerText?: string
    borderColor?: string
    rowHoverBg?: string
    selectedRowBg?: string
  }
  texts?: {
    searchPlaceholder?: string
    noResults?: string
    rowsPerPage?: string
    selectedRows?: string
    exportButton?: string
    columnsButton?: string
    densityButton?: string
    filterButton?: string
  }
}

export function DataTable<TData, TValue>({
  columns: originalColumns,
  data,
  searchable = true,
  filterable = true,
  exportable = true,
  selectable = false,
  pagination = true,
  pageSize = 10,
  className,
  onRowSelect,
  onExport,
  enableExpandable = false,
  renderSubComponent,
  expandedRows: controlledExpandedRows,
  onRowExpandChange,
  bulkActions = [],
  features = {},
  theme = {},
  texts = {},
  // Additional props
  enableSorting = true,
  enableFiltering = true,
  enablePagination = true,
  enableColumnVisibility = true,
  enableRowSelection,
  filterPlaceholder = "Search all columns...",
  defaultPageSize,
  manualPagination = false,
  pageCount,
  onPaginationChange,
  onSortingChange,
  onColumnFiltersChange,
  state: externalState,
}: DataTableProps<TData, TValue>) {
  // Process columns to ensure they can be hidden and use custom filter
  const columns = React.useMemo(() => {
    return originalColumns.map(col => {
      // Remove any enableHiding: false to avoid conflicts
      const { enableHiding, ...restCol } = col as any;
      return {
        ...restCol,
        enableHiding: true, // Force all columns to be hideable
        filterFn: 'custom', // Use our custom filter function
      }
    })
  }, [originalColumns])
  // Check if we're in docs mode or have pro access
  const { hasProAccess, isLoading } = useSubscription()
  
  // In docs mode, always show the component
  
  // If not in docs mode and no pro access, show upgrade prompt
  if (!isLoading && !hasProAccess) {
    return (
      <Card className={cn("w-full", className)}>
        <CardContent className="py-12 text-center">
          <div className="max-w-md mx-auto space-y-4">
            <div className="rounded-full bg-purple-100 dark:bg-purple-900/30 p-3 w-fit mx-auto">
              <Lock className="h-6 w-6 text-purple-600 dark:text-purple-400" />
            </div>
            <div>
              <h3 className="font-semibold text-lg mb-2">Pro Feature</h3>
              <p className="text-muted-foreground text-sm mb-4">
                Data Table is available exclusively to MoonUI Pro subscribers.
              </p>
              <div className="flex gap-3 justify-center">
                <a href="/pricing">
                  <Button size="sm">
                    <Sparkles className="mr-2 h-4 w-4" />
                    Upgrade to Pro
                  </Button>
                </a>
              </div>
            </div>
          </div>
        </CardContent>
      </Card>
    )
  }
  const [sorting, setSorting] = React.useState<SortingState>([])
  const [columnFilters, setColumnFilters] = React.useState<ColumnFiltersState>([])
  const [columnVisibility, setColumnVisibility] = React.useState<VisibilityState>({})
  const [rowSelection, setRowSelection] = React.useState({})
  const [globalFilter, setGlobalFilter] = React.useState('')
  const [isPaginationLoading, setIsPaginationLoading] = React.useState(false)
  const [internalExpandedRows, setInternalExpandedRows] = React.useState<Set<string>>(new Set())
  const [filterDrawerOpen, setFilterDrawerOpen] = React.useState(false)

  // Use controlled or internal expanded state
  const expandedRows = controlledExpandedRows || internalExpandedRows
  const setExpandedRows = onRowExpandChange ? 
    (newExpanded: Set<string>) => onRowExpandChange(newExpanded) :
    setInternalExpandedRows

  const actualPageSize = defaultPageSize || pageSize
  
  // Memoize data to prevent unnecessary re-renders
  const stableData = React.useMemo(() => data, [data])
  
  const table = useReactTable({
    data: stableData,
    columns,
    onSortingChange: onSortingChange !== undefined ? onSortingChange : setSorting,
    onColumnFiltersChange: onColumnFiltersChange !== undefined ? onColumnFiltersChange : setColumnFilters,
    getCoreRowModel: getCoreRowModel(),
    getPaginationRowModel: getPaginationRowModel(),
    getSortedRowModel: getSortedRowModel(),
    getFilteredRowModel: getFilteredRowModel(),
    onColumnVisibilityChange: setColumnVisibility,
    onRowSelectionChange: setRowSelection,
    onGlobalFilterChange: setGlobalFilter,
    globalFilterFn: 'includesString',
    filterFns: {
      custom: (row, columnId, filterValue) => {
        if (!filterValue?.custom || !filterValue?.filters) return true
        
        const filters = filterValue.filters as FilterCondition[]
        const matchAll = filterValue.matchAll !== undefined ? filterValue.matchAll : true
        
        // Get all filter conditions (not just for this column)
        const allFilterResults = filters.map(filterCondition => {
          const cellValue = row.getValue(filterCondition.column)
          const filterVal = filterCondition.value

          switch (filterCondition.operator) {
            case 'equals':
              return cellValue === filterVal
            case 'notEquals':
              return cellValue !== filterVal
            case 'contains':
              return String(cellValue).toLowerCase().includes(String(filterVal).toLowerCase())
            case 'notContains':
              return !String(cellValue).toLowerCase().includes(String(filterVal).toLowerCase())
            case 'startsWith':
              return String(cellValue).toLowerCase().startsWith(String(filterVal).toLowerCase())
            case 'endsWith':
              return String(cellValue).toLowerCase().endsWith(String(filterVal).toLowerCase())
            case 'greaterThan':
              return Number(cellValue) > Number(filterVal)
            case 'lessThan':
              return Number(cellValue) < Number(filterVal)
            case 'greaterThanOrEqual':
              return Number(cellValue) >= Number(filterVal)
            case 'lessThanOrEqual':
              return Number(cellValue) <= Number(filterVal)
            case 'isNull':
              return cellValue == null || cellValue === ''
            case 'isNotNull':
              return cellValue != null && cellValue !== ''
            default:
              return true
          }
        })
        
        // Apply match logic
        if (matchAll) {
          return allFilterResults.every(result => result)
        } else {
          return allFilterResults.some(result => result)
        }
      }
    },
    manualPagination,
    pageCount,
    state: {
      sorting: externalState?.sorting ?? sorting,
      columnFilters: externalState?.columnFilters ?? columnFilters,
      columnVisibility: externalState?.columnVisibility ?? columnVisibility,
      rowSelection: externalState?.rowSelection ?? rowSelection,
      globalFilter: externalState?.globalFilter ?? globalFilter,
      ...(externalState || {}),
    },
    initialState: {
      pagination: {
        pageSize: actualPageSize,
      },
    },
    // Prevent re-renders on state changes
    autoResetAll: false,
    autoResetPageIndex: false,
    autoResetExpanded: false,
    getRowId: (row: TData) => (row as any).id || (row as any).orderId || Math.random().toString(),
  })

  React.useEffect(() => {
    if (onRowSelect && selectable) {
      const selectedRows = table.getFilteredSelectedRowModel().rows.map(row => row.original)
      onRowSelect(selectedRows)
    }
  }, [rowSelection, onRowSelect, selectable, table])
  
  // Memoize row model to prevent unnecessary re-renders when only expanded state changes
  const tableState = table.getState()
  const rowModel = table.getRowModel()
  
  // Use a ref to track if rows actually changed
  const rowsRef = React.useRef(rowModel.rows)
  const rowsChanged = React.useMemo(() => {
    const changed = rowsRef.current !== rowModel.rows
    if (changed) {
      rowsRef.current = rowModel.rows
    }
    return changed
  }, [rowModel.rows])
  
  const rows = rowsRef.current

  // Merge features with defaults
  const enabledFeatures = {
    sorting: features.sorting !== false,
    filtering: features.filtering !== false || filterable,
    pagination: features.pagination !== false || pagination,
    search: features.search !== false || searchable,
    columnVisibility: features.columnVisibility !== false,
    rowSelection: features.rowSelection !== false || selectable,
    export: features.export !== false || exportable,
  }

  const handleExport = async (format: ExportFormat) => {
    const selectedRows = table.getFilteredSelectedRowModel().rows
    const dataToExport = selectedRows.length > 0 
      ? selectedRows.map(row => row.original)
      : table.getFilteredRowModel().rows.map(row => row.original)
    
    // Use custom export handler if provided
    if (typeof exportable === 'object' && exportable.onExport) {
      exportable.onExport(dataToExport, format)
      return
    }
    
    // Use legacy onExport if provided
    if (onExport) {
      onExport(dataToExport)
      return
    }
    
    // Default export behavior
    const filename = typeof exportable === 'object' && exportable.filename 
      ? exportable.filename 
      : 'data-export'
    
    const visibleColumns = getVisibleColumns(columns as any, columnVisibility)
    
    await exportData(dataToExport as Record<string, any>[], {
      format,
      filename,
      columns: visibleColumns,
      includeHeaders: true
    })
  }

  // Parse export options
  const exportFormats: ExportFormat[] = React.useMemo(() => {
    if (!exportable) return []
    if (exportable === true) return ['csv', 'json']
    if (typeof exportable === 'object' && exportable.formats) {
      return exportable.formats
    }
    return ['csv', 'json']
  }, [exportable])

  const clearRowSelection = () => {
    table.resetRowSelection()
  }

  return (
    <div className={cn("moonui-pro-datatable-container flex flex-col gap-4", className)}>
      {/* Toolbar */}
      <div className="moonui-pro-datatable-toolbar flex items-center justify-between">
        <div className="flex items-center space-x-2">
          {searchable && (
            <div className="relative">
              <span suppressHydrationWarning>
                <Search className="absolute left-2 top-2.5 h-4 w-4 text-muted-foreground" />
              </span>
              <Input
                placeholder={filterPlaceholder}
                value={globalFilter}
                onChange={(e) => setGlobalFilter(e.target.value)}
                className="pl-8 w-64"
              />
            </div>
          )}
          
          {filterable && (
            <Button 
              variant="outline" 
              size="sm"
              onClick={() => setFilterDrawerOpen(true)}
            >
              <span suppressHydrationWarning><Filter className="mr-2 h-4 w-4" /></span>
              Filters
              {columnFilters.length > 0 && (
                <span className="ml-2 rounded-full bg-primary px-2 py-0.5 text-xs text-primary-foreground">
                  {columnFilters.length}
                </span>
              )}
            </Button>
          )}
          
          {/* Bulk actions */}
          {selectable && bulkActions.length > 0 && (
            <DataTableBulkActions
              selectedRows={table.getFilteredSelectedRowModel().rows.map(row => row.original)}
              actions={bulkActions}
              onClearSelection={clearRowSelection}
            />
          )}
        </div>

        <div className="flex items-center space-x-2">
          {/* Export dropdown */}
          {exportable && exportFormats.length > 0 && (
            <DropdownMenu>
              <DropdownMenuTrigger asChild>
                <Button variant="outline" size="sm">
                  <span suppressHydrationWarning><Download className="mr-2 h-4 w-4" /></span>
                  Export
                </Button>
              </DropdownMenuTrigger>
              <DropdownMenuContent align="end">
                {exportFormats.includes('csv') && (
                  <DropdownMenuItem onClick={() => handleExport('csv')}>
                    <FileSpreadsheet className="mr-2 h-4 w-4" />
                    Export as CSV
                  </DropdownMenuItem>
                )}
                {exportFormats.includes('json') && (
                  <DropdownMenuItem onClick={() => handleExport('json')}>
                    <FileJson className="mr-2 h-4 w-4" />
                    Export as JSON
                  </DropdownMenuItem>
                )}
                {exportFormats.includes('xlsx') && (
                  <DropdownMenuItem onClick={() => handleExport('xlsx')}>
                    <FileDown className="mr-2 h-4 w-4" />
                    Export as Excel
                  </DropdownMenuItem>
                )}
              </DropdownMenuContent>
            </DropdownMenu>
          )}
          
          {/* Column visibility toggle */}
          <DataTableColumnToggle table={table} />
        </div>
      </div>

      {/* Table */}
      <div className="moonui-pro-datatable-wrapper rounded-md border overflow-hidden" style={{ contain: 'layout style' }}>
        <div style={{ overflowX: 'auto' }}>
          <table className="moonui-pro-datatable" style={{ width: '100%', tableLayout: 'auto' }}>
          <thead className="moonui-data-table-header">
            {table.getHeaderGroups().map((headerGroup) => (
              <tr key={headerGroup.id} className="moonui-data-table-row border-b">
                {headerGroup.headers
                  .filter((header) => header.column.getIsVisible())
                  .map((header) => (
                    <th
                      key={header.id}
                      className="moonui-data-table-th h-12 px-4 text-left align-middle font-medium text-muted-foreground"
                    >
                      {header.isPlaceholder ? null : (
                        <div
                          className={cn(
                            "flex items-center space-x-2",
                            header.column.getCanSort() && "cursor-pointer select-none"
                          )}
                          onClick={header.column.getToggleSortingHandler()}
                        >
                          {flexRender(header.column.columnDef.header, header.getContext())}
                          {header.column.getCanSort() && (
                            <div className="ml-2">
                              {header.column.getIsSorted() === 'asc' ? (
                                <span suppressHydrationWarning><ArrowUp className="h-4 w-4" /></span>
                              ) : header.column.getIsSorted() === 'desc' ? (
                                <span suppressHydrationWarning><ArrowDown className="h-4 w-4" /></span>
                              ) : (
                                <span suppressHydrationWarning><ArrowUpDown className="h-4 w-4" /></span>
                              )}
                            </div>
                          )}
                        </div>
                      )}
                    </th>
                  ))}
              </tr>
            ))}
          </thead>
          <tbody className="moonui-data-table-body">
            {isPaginationLoading ? (
              <motion.tr
                key="loading"
                initial={{ opacity: 0 }}
                animate={{ opacity: 1 }}
                exit={{ opacity: 0 }}
                transition={{ duration: 0.2 }}
              >
                <td colSpan={table.getAllLeafColumns().filter(col => col.getIsVisible()).length} className="h-24 text-center">
                  <div className="flex items-center justify-center space-x-2">
                    <span suppressHydrationWarning><Loader2 className="h-4 w-4 animate-spin" /></span>
                    <span className="text-sm text-muted-foreground">Loading...</span>
                  </div>
                </td>
              </motion.tr>
            ) : rows?.length ? (
              <>
                {rows.map((row, index) => {
                  const rowId = (row.original as any).id || row.id
                  const isExpanded = enableExpandable && expandedRows.has(rowId)
                  
                  return (
                    <TableRow
                      key={rowId}
                      row={row}
                      columns={columns}
                      isExpanded={isExpanded}
                      enableExpandable={enableExpandable}
                      renderSubComponent={renderSubComponent}
                      visibilityState={table.getState().columnVisibility}
                    />
                  );
                })}
              </>
            ) : (
              <motion.tr
                key="no-results"
                initial={{ opacity: 0 }}
                animate={{ opacity: 1 }}
                exit={{ opacity: 0 }}
                transition={{ duration: 0.2 }}
              >
                <td colSpan={table.getAllLeafColumns().filter(col => col.getIsVisible()).length} className="h-24 text-center">
                  No results found.
                </td>
              </motion.tr>
            )}
          </tbody>
        </table>
        </div>
      </div>

      {/* Pagination */}
      {pagination && (
        <div className="flex items-center justify-between px-2">
          <div className="flex-1 text-sm text-muted-foreground">
            {selectable && table.getFilteredSelectedRowModel().rows.length > 0 && (
              <span>
                {table.getFilteredSelectedRowModel().rows.length} of{" "}
                {table.getFilteredRowModel().rows.length} row(s) selected.
              </span>
            )}
          </div>
          <div className="flex items-center space-x-6 lg:space-x-8">
            <div className="flex items-center space-x-2">
              <p className="text-sm font-medium">Rows per page</p>
              <select
                value={table.getState().pagination.pageSize}
                onChange={async (e) => {
                  setIsPaginationLoading(true)
                  await new Promise(resolve => setTimeout(resolve, 300))
                  table.setPageSize(Number(e.target.value))
                  setIsPaginationLoading(false)
                }}
                className="h-8 w-[70px] rounded border border-input bg-background px-3 py-1 text-sm"
                disabled={isPaginationLoading}
              >
                {[10, 20, 30, 40, 50].map((pageSize) => (
                  <option key={pageSize} value={pageSize}>
                    {pageSize}
                  </option>
                ))}
              </select>
            </div>
            <div className="flex w-[100px] items-center justify-center text-sm font-medium">
              Page {table.getState().pagination.pageIndex + 1} of{" "}
              {table.getPageCount()}
            </div>
            <div className="flex items-center space-x-2">
              <Button
                variant="outline"
                className="hidden h-8 w-8 p-0 lg:flex"
                onClick={async () => {
                  if (onPaginationChange) {
                    onPaginationChange({ pageIndex: 0, pageSize: table.getState().pagination.pageSize })
                  } else {
                    setIsPaginationLoading(true)
                    await new Promise(resolve => setTimeout(resolve, 300))
                    table.setPageIndex(0)
                    setIsPaginationLoading(false)
                  }
                }}
                disabled={!table.getCanPreviousPage() || isPaginationLoading}
              >
                <span suppressHydrationWarning><ChevronsLeft className="h-4 w-4" /></span>
              </Button>
              <Button
                variant="outline"
                className="h-8 w-8 p-0"
                onClick={async () => {
                  if (onPaginationChange) {
                    const currentIndex = table.getState().pagination.pageIndex
                    onPaginationChange({ pageIndex: currentIndex - 1, pageSize: table.getState().pagination.pageSize })
                  } else {
                    setIsPaginationLoading(true)
                    await new Promise(resolve => setTimeout(resolve, 300))
                    table.previousPage()
                    setIsPaginationLoading(false)
                  }
                }}
                disabled={!table.getCanPreviousPage() || isPaginationLoading}
              >
                <span suppressHydrationWarning><ChevronLeft className="h-4 w-4" /></span>
              </Button>
              <Button
                variant="outline"
                className="h-8 w-8 p-0"
                onClick={async () => {
                  setIsPaginationLoading(true)
                  await new Promise(resolve => setTimeout(resolve, 300))
                  table.nextPage()
                  setIsPaginationLoading(false)
                }}
                disabled={!table.getCanNextPage() || isPaginationLoading}
              >
                <span suppressHydrationWarning><ChevronRight className="h-4 w-4" /></span>
              </Button>
              <Button
                variant="outline"
                className="hidden h-8 w-8 p-0 lg:flex"
                onClick={async () => {
                  setIsPaginationLoading(true)
                  await new Promise(resolve => setTimeout(resolve, 300))
                  table.setPageIndex(table.getPageCount() - 1)
                  setIsPaginationLoading(false)
                }}
                disabled={!table.getCanNextPage() || isPaginationLoading}
              >
                <span suppressHydrationWarning><ChevronsRight className="h-4 w-4" /></span>
              </Button>
            </div>
          </div>
        </div>
      )}

      {/* Filter Drawer */}
      {filterable && (
        <DataTableFilterDrawer
          table={table}
          open={filterDrawerOpen}
          onOpenChange={setFilterDrawerOpen}
        />
      )}
    </div>
  )
}

/**
 * Helper function to create an expandable column
 * @param expandedRows - Set of expanded row IDs
 * @param onToggle - Function to toggle row expansion
 * @returns ColumnDef for expandable rows
 */
export function getExpandableColumn<TData>(
  expandedRows: Set<string>,
  onToggle: (id: string) => void
): ColumnDef<TData, any> {
  return {
    id: "expander",
    header: () => null,
    size: 50,
    cell: ({ row }) => {
      const rowId = (row.original as any).id || row.id;
      const isExpanded = expandedRows.has(rowId);
      
      return (
        <button
          onClick={(e) => {
            e.stopPropagation();
            onToggle(rowId);
          }}
          className="p-2 hover:bg-muted rounded-md transition-colors"
          aria-label={isExpanded ? "Collapse row" : "Expand row"}
        >
          <span suppressHydrationWarning>
            {isExpanded ? (
              <ChevronDown className="h-4 w-4 text-muted-foreground" />
            ) : (
              <ChevronRight className="h-4 w-4 text-muted-foreground" />
            )}
          </span>
        </button>
      );
    },
  };
}

/**
 * Hook for managing expandable rows
 * @param initialExpanded - Initial set of expanded row IDs
 * @returns Object with expandedRows, toggleRow, and expandAll/collapseAll functions
 */
export function useExpandableRows(initialExpanded: Set<string> = new Set()) {
  const [expandedRows, setExpandedRows] = React.useState<Set<string>>(initialExpanded);

  const toggleRow = React.useCallback((id: string) => {
    setExpandedRows(prev => {
      const newExpanded = new Set(prev);
      if (newExpanded.has(id)) {
        newExpanded.delete(id);
      } else {
        newExpanded.add(id);
      }
      return newExpanded;
    });
  }, []);

  const expandAll = React.useCallback((rowIds: string[]) => {
    setExpandedRows(new Set(rowIds));
  }, []);

  const collapseAll = React.useCallback(() => {
    setExpandedRows(new Set());
  }, []);

  return {
    expandedRows,
    setExpandedRows,
    toggleRow,
    expandAll,
    collapseAll,
  };
}

// Memoized table row component
interface TableRowProps {
  row: Row<any>
  columns: ColumnDef<any, any>[]
  isExpanded: boolean
  enableExpandable: boolean
  renderSubComponent?: (props: { row: { original: any; id: string } }) => React.ReactNode
  visibilityState: Record<string, boolean>
}

const TableRow = React.memo(({ 
  row, 
  columns, 
  isExpanded, 
  enableExpandable,
  renderSubComponent,
  visibilityState 
}: TableRowProps) => {
  const rowId = (row.original as any).id || row.id
  
  return (
    <>
      <tr
        className={cn(
          "border-b transition-colors hover:bg-muted/50",
          row.getIsSelected() && "bg-muted",
          isExpanded && "border-b-0"
        )}
      >
        {row.getAllCells()
          .filter((cell) => {
            // Manual visibility check
            const isVisible = visibilityState[cell.column.id] !== false;
            return isVisible;
          })
          .map((cell) => {
            return (
              <td key={cell.id} className="moonui-data-table-td p-4 align-middle">
                {flexRender(cell.column.columnDef.cell, cell.getContext())}
              </td>
            );
          })}
      </tr>
      
      {isExpanded && renderSubComponent && (
        <tr className="border-b">
          <td colSpan={row.getAllCells().filter(cell => 
            visibilityState[cell.column.id] !== false
          ).length || 1} className="p-0 overflow-hidden">
            <div 
              className="transition-all duration-300 ease-out"
              style={{
                maxHeight: isExpanded ? '1000px' : '0',
                opacity: isExpanded ? 1 : 0,
              }}
            >
              <div className="border-t border-border/50">
                {renderSubComponent({ row: { original: row.original, id: rowId } })}
              </div>
            </div>
          </td>
        </tr>
      )}
    </>
  )
}, (prevProps, nextProps) => {
  // Custom comparison - only re-render if row data, expanded state, or visibility changed
  const prevRowId = (prevProps.row.original as any).id || prevProps.row.id
  const nextRowId = (nextProps.row.original as any).id || nextProps.row.id
  
  // Include visibility state in comparison
  const prevVisibilityKeys = Object.keys(prevProps.visibilityState).sort().join(',')
  const nextVisibilityKeys = Object.keys(nextProps.visibilityState).sort().join(',')
  const prevVisibilityValues = Object.values(prevProps.visibilityState).join(',')
  const nextVisibilityValues = Object.values(nextProps.visibilityState).join(',')
  
  return prevRowId === nextRowId && 
         prevProps.isExpanded === nextProps.isExpanded &&
         prevProps.row.getIsSelected() === nextProps.row.getIsSelected() &&
         prevVisibilityKeys === nextVisibilityKeys &&
         prevVisibilityValues === nextVisibilityValues
})

TableRow.displayName = 'TableRow'

// Re-export types for convenience
export { type ColumnDef } from "@tanstack/react-table";
export type { BulkAction } from './data-table-bulk-actions';
export type { ExportFormat } from './data-table-export';
export type { FilterCondition, FilterOperator } from './data-table-filter-drawer';
