@php
    use Filament\Actions\Action;
    use Filament\Actions\ActionGroup;
    use Filament\Support\Enums\Alignment;
    use Illuminate\View\ComponentAttributeBag;
    use Webkul\Support\Filament\Forms\Components\Repeater\TableColumn;

    $items = $getItems();

    $addAction = $getAction($getAddActionName());
    $addActionAlignment = $getAddActionAlignment();
    $cloneAction = $getAction($getCloneActionName());
    $deleteAction = $getAction($getDeleteActionName());
    $moveDownAction = $getAction($getMoveDownActionName());
    $moveUpAction = $getAction($getMoveUpActionName());
    $reorderAction = $getAction($getReorderActionName());
    $extraItemActions = $getExtraItemActions();
    $footerActions = $getFooterActions();

    $isAddable = $isAddable();
    $isCloneable = $isCloneable();
    $isDeletable = $isDeletable();
    $isReorderableWithButtons = $isReorderableWithButtons();
    $isReorderableWithDragAndDrop = $isReorderableWithDragAndDrop();

    $key = $getKey();
    $statePath = $getStatePath();

    $tableColumns = $getTableColumns();
    $isCompact = $isCompact();

    $hasColumnManagerDropdown = $hasColumnManager();
    $columnManagerApplyAction = $getColumnManagerApplyAction();
    $columnManagerTriggerAction = $getColumnManagerTriggerAction();
    $hasSummary = $hasAnySummarizers();

    $hasResizableColumns = collect($tableColumns)->contains(fn (TableColumn $col) => $col->isResizable());

    $resizableColumnConfig = collect($tableColumns)->mapWithKeys(function (TableColumn $col) {
        return [$col->getName() => [
            'isResizable' => $col->isResizable(),
            'minWidth'    => $col->getMinWidth(),
            'maxWidth'    => $col->getMaxWidth(),
            'width'       => $col->getWidth(),
        ]];
    })->toArray();
@endphp

<x-dynamic-component
    :component="$getFieldWrapperView()"
    :field="$field"
>
    <div
        {{ 
            $attributes
                ->merge($getExtraAttributes(), escape: false)
                ->class([
                    'fi-fo-table-repeater',
                    'fi-compact' => $isCompact,
                ]) 
        }}
    >
        @if (count($items))
            <table
                class="fi-absolute-positioning-context"
                @if ($hasResizableColumns)
                    x-data="{
                        columns: @js($resizableColumnConfig),
                        columnWidths: {},
                        resizing: null,
                        startX: 0,
                        startWidth: 0,

                        init() {
                            Object.keys(this.columns).forEach(name => {
                                const col = this.columns[name];
                                if (col.width) {
                                    this.columnWidths[name] = parseInt(col.width, 10) || null;
                                }
                            });
                        },

                        getColumnStyle(name) {
                            const width = this.columnWidths[name];
                            const col = this.columns[name];

                            if (!width && col.width) {
                                return 'width: ' + col.width;
                            }

                            if (width) {
                                return 'width: ' + width + 'px';
                            }

                            return '';
                        },

                        startResize(event, columnName) {
                            const th = event.target.closest('th');
                            if (!th) return;

                            this.resizing = columnName;
                            this.startX = event.pageX;
                            this.startWidth = th.offsetWidth;

                            document.body.style.cursor = 'col-resize';
                            document.body.style.userSelect = 'none';

                            const onMouseMove = (e) => {
                                if (!this.resizing) return;

                                const diff = e.pageX - this.startX;
                                let newWidth = this.startWidth + diff;
                                const col = this.columns[this.resizing];

                                if (col.minWidth) {
                                    const min = parseInt(col.minWidth, 10);
                                    if (min && newWidth < min) newWidth = min;
                                }

                                if (col.maxWidth) {
                                    const max = parseInt(col.maxWidth, 10);
                                    if (max && newWidth > max) newWidth = max;
                                }

                                if (newWidth < 50) newWidth = 50;

                                this.columnWidths[this.resizing] = newWidth;
                            };

                            const onMouseUp = () => {
                                this.resizing = null;
                                document.body.style.cursor = '';
                                document.body.style.userSelect = '';
                                document.removeEventListener('mousemove', onMouseMove);
                                document.removeEventListener('mouseup', onMouseUp);
                            };

                            document.addEventListener('mousemove', onMouseMove);
                            document.addEventListener('mouseup', onMouseUp);
                        },

                        resetColumnWidth(name) {
                            const col = this.columns[name];
                            if (col.width) {
                                this.columnWidths[name] = parseInt(col.width, 10) || null;
                            } else {
                                delete this.columnWidths[name];
                            }
                        },
                    }"
                @endif
            >
                <thead>
                    <tr>
                        @if (
                            (count($items) > 1) 
                            && (
                                $isReorderableWithButtons 
                                || $isReorderableWithDragAndDrop
                            )
                        )
                            <th class="fi-fo-table-repeater-empty-header-cell" style="width: 45px"></th>
                        @endif

                        @foreach ($tableColumns as $tableColumn)
                            @php
                                $columnName = $tableColumn->getName();
                                $isResizable = $tableColumn->isResizable();
                            @endphp

                            <th
                                @class([
                                    'fi-wrapped' => $tableColumn->canHeaderWrap(),
                                    'fi-resizable-column' => $isResizable,
                                    (($columnAlignment = $tableColumn->getAlignment()) instanceof Alignment) ? ('fi-align-' . $columnAlignment->value) : $columnAlignment,
                                ])
                                @if ($hasResizableColumns && $isResizable)
                                    x-bind:style="getColumnStyle('{{ $columnName }}')"
                                    data-column="{{ $columnName }}"
                                @else
                                    @style([
                                        ('width: ' . ($columnWidth = $tableColumn->getWidth())) => filled($columnWidth),
                                    ])
                                @endif
                            >
                                <div class="fi-fo-table-repeater-header-content">
                                    @if (! $tableColumn->isHeaderLabelHidden())
                                        {{ $tableColumn->getLabel() }}

                                        @if ($tableColumn->isMarkedAsRequired())
                                            <sup class="fi-fo-table-repeater-header-required-mark pt-2">*</sup>
                                        @endif
                                    @else
                                        <span class="fi-sr-only">
                                            {{ $tableColumn->getLabel() }}
                                        </span>
                                    @endif
                                </div>

                                @if ($isResizable && $hasResizableColumns)
                                    <div
                                        class="fi-fo-table-repeater-resize-handle"
                                        x-on:mousedown.prevent="startResize($event, '{{ $columnName }}')"
                                        x-on:dblclick.prevent="resetColumnWidth('{{ $columnName }}')"
                                    ></div>
                                @endif
                            </th>
                        @endforeach

                        @if (
                            count($extraItemActions) 
                            || $isCloneable 
                            || $isDeletable
                        )
                            <th class="fi-fo-table-repeater-empty-header-cell text-center align-middle" style="width: 75px">
                                @if ($hasColumnManagerDropdown)
                                    <x-filament::dropdown
                                        shift
                                        placement="bottom-end"
                                        :max-height="$getColumnManagerMaxHeight()"
                                        :width="$getColumnManagerWidth()"
                                        :wire:key="$this->getId() . '.table.column-manager.' . $statePath"
                                        class="fi-ta-col-manager-dropdown inline-block"
                                    >
                                        <x-slot name="trigger">
                                            {{ $columnManagerTriggerAction }}
                                        </x-slot>

                                        <x-support::column-manager
                                            heading-tag="h2"
                                            :apply-action="$columnManagerApplyAction"
                                            :table-columns="$getMappedColumns()"
                                            :columns="$getColumnManagerColumns()"
                                            :has-reorderable-columns="false"
                                            :has-toggleable-columns="$hasToggleableColumns"
                                            :reorder-animation-duration="$getReorderAnimationDuration()"
                                            :repeater-key="$statePath"
                                        />
                                    </x-filament::dropdown>
                                @endif
                            </th>
                        @endif
                    </tr>
                </thead>

                <tbody
                    x-sortable
                    {{ 
                        (new ComponentAttributeBag)
                            ->merge([
                                'data-sortable-animation-duration' => $getReorderAnimationDuration(),
                                'x-on:end.stop' => '$event.oldDraggableIndex !== $event.newDraggableIndex && $wire.mountAction(\'reorder\', { items: $event.target.sortable.toArray() }, { schemaComponent: \'' . $key . '\' })',
                            ], escape: false) 
                    }}
                >
                    @foreach ($items as $itemKey => $item)
                        @php
                            $visibleExtraItemActions = collect($extraItemActions)->filter(fn (Action $action) => $action(['item' => $itemKey])->isVisible())->values()->all();
                            $cloneAction = $cloneAction(['item' => $itemKey]);
                            $cloneActionIsVisible = $isCloneable && $cloneAction->isVisible();
                            $deleteAction = $deleteAction(['item' => $itemKey]);
                            $deleteActionIsVisible = $isDeletable && $deleteAction->isVisible();
                            $moveDownAction = $moveDownAction(['item' => $itemKey])->disabled($loop->last);
                            $moveDownActionIsVisible = $isReorderableWithButtons && $moveDownAction->isVisible();
                            $moveUpAction = $moveUpAction(['item' => $itemKey])->disabled($loop->first);
                            $moveUpActionIsVisible = $isReorderableWithButtons && $moveUpAction->isVisible();
                            $reorderActionIsVisible = $isReorderableWithDragAndDrop && $reorderAction->isVisible();
                            $itemStatePath = $item->getStatePath();
                        @endphp

                        <tr
                            wire:key="{{ $item->getLivewireKey() }}.item"
                            x-sortable-item="{{ $itemKey }}"
                            x-on:click="
                                if ($event.target.closest('button, a, input, textarea, select, label, [role=button], [data-no-row-click]')) {
                                    return;
                                }

                                $el.querySelector('[data-row-click-action]')?.click();
                            "
                        >
                            @if (
                                (count($items) > 1) 
                                && (
                                    $isReorderableWithButtons 
                                    || $isReorderableWithDragAndDrop
                                )
                            )
                                <td class='p-2'>
                                    @if (
                                        $reorderActionIsVisible 
                                        || $moveUpActionIsVisible 
                                        || $moveDownActionIsVisible
                                    )
                                        <div>
                                            @if ($reorderActionIsVisible)
                                                <div x-on:click.stop>
                                                    {{ $reorderAction->extraAttributes(['x-sortable-handle' => true], merge: true) }}
                                                </div>
                                            @endif

                                            @if (
                                                $moveUpActionIsVisible 
                                                || $moveDownActionIsVisible
                                            )
                                                <div x-on:click.stop>
                                                    {{ $moveUpAction }}
                                                </div>

                                                <div x-on:click.stop>
                                                    {{ $moveDownAction }}
                                                </div>
                                            @endif
                                        </div>
                                    @endif
                                </td>
                            @endif

                            @php
                                $counter = 0;
                                $visibleColumns = collect($tableColumns)->mapWithKeys(fn ($tableColumn) => [$tableColumn->getName() => $tableColumn]);
                            @endphp

                            @foreach ($item->getComponents() as $schemaComponent)
                                @php
                                    throw_unless(
                                        $schemaComponent instanceof \Filament\Schemas\Components\Component,
                                        new Exception('Table repeaters must only contain schema components, but [' . $schemaComponent::class . '] was used.'),
                                    );
                                @endphp

                                @if ($visibleColumns->has($schemaComponent->getName()))
                                    @if ($schemaComponent instanceof \Filament\Forms\Components\Hidden)
                                        {{ $schemaComponent }}
                                    @else
                                        <td
                                            @if (! (
                                                $schemaComponent instanceof Action 
                                                || $schemaComponent instanceof ActionGroup
                                            ))
                                                @php
                                                    $schemaComponentStatePath = $schemaComponent->getStatePath();
                                                @endphp

                                                x-data="filamentSchemaComponent({
                                                    path: @js($schemaComponentStatePath),
                                                    containerPath: @js($itemStatePath),
                                                    isLive: @js($schemaComponent->isLive()),
                                                    $wire,
                                                })"
                                            @endif
                                        >
                                            {{ $schemaComponent }}
                                        </td>
                                    @endif
                                @endif
                            @endforeach

                            @if (
                                count($extraItemActions) 
                                || $isCloneable 
                                || $isDeletable
                            )
                                <td>
                                    @if (
                                        $visibleExtraItemActions 
                                        || $cloneActionIsVisible 
                                        || $deleteActionIsVisible
                                    )
                                        <div class="flex flex-row items-center justify-center gap-2">
                                            @foreach ($visibleExtraItemActions as $extraItemAction)
                                                <div x-on:click.stop>
                                                    {{ $extraItemAction(['item' => $itemKey]) }}
                                                </div>
                                            @endforeach

                                            @if ($cloneActionIsVisible)
                                                <div x-on:click.stop>
                                                    {{ $cloneAction }}
                                                </div>
                                            @endif

                                            @if ($deleteActionIsVisible)
                                                <div x-on:click.stop>
                                                    {{ $deleteAction }}
                                                </div>
                                            @endif
                                        </div>
                                    @endif
                                </td>
                            @endif
                        </tr>
                    @endforeach
                </tbody>

                @if ($hasSummary)
                    <tfoot class="fi-ta-row fi-ta-summary-row fi-striped">
                        <tr>
                            @if (
                                (count($items) > 1) 
                                && (
                                    $isReorderableWithButtons 
                                    || $isReorderableWithDragAndDrop
                                )
                            )
                                <td class="fi-ta-cell px-3 py-3"></td>
                            @endif

                            @foreach ($tableColumns as $tableColumn)
                                <td
                                    @class([
                                        'fi-ta-cell px-3 py-3 font-semibold',
                                        (($columnAlignment = $tableColumn->getAlignment()) instanceof Alignment) ? ('fi-align-' . $columnAlignment->value) : $columnAlignment,
                                    ])
                                >
                                    @if ($tableColumn->hasSummarizer())
                                        {{ $getSummaryForColumn($tableColumn->getName()) }}
                                    @endif
                                </td>
                            @endforeach

                            @if (
                                count($extraItemActions) 
                                || $isCloneable 
                                || $isDeletable
                            )
                                <td class="fi-ta-cell px-3 py-3"></td>
                            @endif
                        </tr>
                    </tfoot>
                @endif
            </table>
        @endif
    </div>

    <div class="flex items-center justify-center gap-3">
        @if (
            $isAddable 
            && $addAction->isVisible()
        )
            <div
                @class([
                    'fi-fo-table-repeater-add',
                    ($addActionAlignment instanceof Alignment) ? ('fi-align-' . $addActionAlignment->value) : $addActionAlignment,
                ])
            >
                {{ $addAction }}
            </div>
        @endif

        @foreach ($footerActions as $footerAction)
            @if ($footerAction->isVisible())
                <div class="fi-fo-table-repeater-add">
                    {{ $footerAction }}
                </div>
            @endif
        @endforeach
    </div>
</x-dynamic-component>
