import { Component, Input, Output, EventEmitter, ChangeDetectionStrategy, ViewEncapsulation } from '@angular/core';
import { CommonModule } from '@angular/common';

export interface KanbanColumn {
  id: string;
  title: string;
  items: KanbanItem[];
  maxItems?: number;
  disabled?: boolean;
}

export interface KanbanItem {
  id: string;
  title: string;
  description?: string;
  priority?: 'low' | 'medium' | 'high';
  tags?: string[];
  assignee?: string;
  dueDate?: Date;
}

export interface KanbanDragEvent {
  item: KanbanItem;
  fromColumn: string;
  toColumn: string;
  fromIndex: number;
  toIndex: number;
}

type KanbanSize = 'sm' | 'md' | 'lg';

@Component({
  selector: 'ui-kanban-board',
  standalone: true,
  imports: [CommonModule],
  changeDetection: ChangeDetectionStrategy.OnPush,
  encapsulation: ViewEncapsulation.None,
  template: `
    <div 
      class="ui-kanban-board"
      [class.ui-kanban-board--sm]="size === 'sm'"
      [class.ui-kanban-board--md]="size === 'md'"
      [class.ui-kanban-board--lg]="size === 'lg'"
      [class.ui-kanban-board--disabled]="disabled"
      role="application"
      [attr.aria-label]="ariaLabel || 'Kanban board'">
      
      <div class="ui-kanban-board__header" *ngIf="title">
        <h2 class="ui-kanban-board__title">{{ title }}</h2>
        @if (subtitle) {
          <p class="ui-kanban-board__subtitle">{{ subtitle }}</p>
        }
      </div>
      
      <div class="ui-kanban-board__columns" 
           role="group" 
           [attr.aria-label]="'Kanban columns with ' + columns.length + ' columns'">
        @for (column of columns; track column.id; let columnIndex = $index) {
          <div 
            class="ui-kanban-board__column"
            [class.ui-kanban-board__column--disabled]="column.disabled || disabled"
            [class.ui-kanban-board__column--full]="column.maxItems && column.items.length >= column.maxItems"
            [attr.data-column-id]="column.id"
            role="region"
            [attr.aria-label]="column.title + ' column with ' + column.items.length + ' items'"
            (dragover)="onDragOver($event, column)"
            (drop)="onDrop($event, column, columnIndex)">
            
            <div class="ui-kanban-board__column-header">
              <h3 class="ui-kanban-board__column-title">{{ column.title }}</h3>
              <span class="ui-kanban-board__column-count" 
                    [attr.aria-label]="column.items.length + ' items in this column'">
                {{ column.items.length }}
                @if (column.maxItems) {
                  <span class="ui-kanban-board__column-limit">/ {{ column.maxItems }}</span>
                }
              </span>
            </div>
            
            <div class="ui-kanban-board__column-content"
                 role="list">
              @for (item of column.items; track item.id; let itemIndex = $index) {
                <div 
                  class="ui-kanban-board__item"
                  [class.ui-kanban-board__item--priority-low]="item.priority === 'low'"
                  [class.ui-kanban-board__item--priority-medium]="item.priority === 'medium'"
                  [class.ui-kanban-board__item--priority-high]="item.priority === 'high'"
                  [class.ui-kanban-board__item--dragging]="draggedItem?.id === item.id"
                  [attr.data-item-id]="item.id"
                  [draggable]="!disabled && !column.disabled"
                  role="listitem"
                  [attr.aria-label]="getItemAriaLabel(item)"
                  [tabindex]="disabled || column.disabled ? -1 : 0"
                  (dragstart)="onDragStart($event, item, column.id, itemIndex)"
                  (dragend)="onDragEnd($event)"
                  (click)="onItemClick(item, column.id)"
                  (keydown)="onItemKeydown($event, item, column.id)">
                  
                  <div class="ui-kanban-board__item-header">
                    <h4 class="ui-kanban-board__item-title">{{ item.title }}</h4>
                    @if (item.priority) {
                      <span class="ui-kanban-board__item-priority" 
                            [attr.aria-label]="item.priority + ' priority'">
                        @switch (item.priority) {
                          @case ('high') { 🔴 }
                          @case ('medium') { 🟡 }
                          @case ('low') { 🟢 }
                        }
                      </span>
                    }
                  </div>
                  
                  @if (item.description) {
                    <p class="ui-kanban-board__item-description">{{ item.description }}</p>
                  }
                  
                  @if (item.tags && item.tags.length > 0) {
                    <div class="ui-kanban-board__item-tags" role="list" aria-label="Item tags">
                      @for (tag of item.tags; track tag) {
                        <span class="ui-kanban-board__item-tag" role="listitem">{{ tag }}</span>
                      }
                    </div>
                  }
                  
                  @if (item.assignee || item.dueDate) {
                    <div class="ui-kanban-board__item-meta">
                      @if (item.assignee) {
                        <span class="ui-kanban-board__item-assignee" 
                              [attr.aria-label]="'Assigned to ' + item.assignee">
                          👤 {{ item.assignee }}
                        </span>
                      }
                      @if (item.dueDate) {
                        <span class="ui-kanban-board__item-due-date" 
                              [attr.aria-label]="'Due date ' + (item.dueDate | date)">
                          📅 {{ item.dueDate | date:'short' }}
                        </span>
                      }
                    </div>
                  }
                </div>
              }
              
              @if (column.items.length === 0) {
                <div class="ui-kanban-board__empty-state" 
                     role="status" 
                     aria-label="No items in this column">
                  <p class="ui-kanban-board__empty-text">No items</p>
                </div>
              }
            </div>
          </div>
        }
      </div>
    </div>
  `,
  styleUrl: './kanban-board.component.scss'
})
export class KanbanBoardComponent {
  @Input() columns: KanbanColumn[] = [];
  @Input() size: KanbanSize = 'md';
  @Input() disabled = false;
  @Input() title?: string;
  @Input() subtitle?: string;
  @Input() ariaLabel?: string;
  
  @Output() itemMoved = new EventEmitter<KanbanDragEvent>();
  @Output() itemClicked = new EventEmitter<{ item: KanbanItem; columnId: string }>();
  @Output() columnChanged = new EventEmitter<{ column: KanbanColumn; action: 'add' | 'remove' | 'update' }>();
  
  draggedItem: KanbanItem | null = null;
  draggedFromColumn: string | null = null;
  draggedFromIndex: number | null = null;
  
  onDragStart(event: DragEvent, item: KanbanItem, columnId: string, itemIndex: number): void {
    if (this.disabled) {
      event.preventDefault();
      return;
    }
    
    this.draggedItem = item;
    this.draggedFromColumn = columnId;
    this.draggedFromIndex = itemIndex;
    
    if (event.dataTransfer) {
      event.dataTransfer.effectAllowed = 'move';
      event.dataTransfer.setData('text/plain', JSON.stringify({
        itemId: item.id,
        columnId,
        itemIndex
      }));
    }
  }
  
  onDragOver(event: DragEvent, column: KanbanColumn): void {
    if (this.disabled || column.disabled) {
      return;
    }
    
    event.preventDefault();
    
    if (event.dataTransfer) {
      event.dataTransfer.dropEffect = 'move';
    }
  }
  
  onDrop(event: DragEvent, column: KanbanColumn, columnIndex: number): void {
    event.preventDefault();
    
    if (this.disabled || column.disabled || !this.draggedItem || !this.draggedFromColumn) {
      return;
    }
    
    // Check if column is at capacity
    if (column.maxItems && column.items.length >= column.maxItems && column.id !== this.draggedFromColumn) {
      return;
    }
    
    const dragEvent: KanbanDragEvent = {
      item: this.draggedItem,
      fromColumn: this.draggedFromColumn,
      toColumn: column.id,
      fromIndex: this.draggedFromIndex!,
      toIndex: column.items.length
    };
    
    this.itemMoved.emit(dragEvent);
  }
  
  onDragEnd(event: DragEvent): void {
    this.draggedItem = null;
    this.draggedFromColumn = null;
    this.draggedFromIndex = null;
  }
  
  onItemClick(item: KanbanItem, columnId: string): void {
    if (!this.disabled) {
      this.itemClicked.emit({ item, columnId });
    }
  }
  
  onItemKeydown(event: KeyboardEvent, item: KanbanItem, columnId: string): void {
    if (event.key === 'Enter' || event.key === ' ') {
      event.preventDefault();
      this.onItemClick(item, columnId);
    }
  }
  
  getItemAriaLabel(item: KanbanItem): string {
    let label = `Item: ${item.title}`;
    if (item.description) {
      label += `, ${item.description}`;
    }
    if (item.priority) {
      label += `, ${item.priority} priority`;
    }
    if (item.assignee) {
      label += `, assigned to ${item.assignee}`;
    }
    return label;
  }
}