<template>
  <div class="flex flex-col h-full">
    <!-- Filter / Sort Toolbar -->
    <div class="flex-shrink-0 flex items-center justify-between gap-2 border-b px-3 py-2">
      <div class="flex items-center gap-1.5">
        <Popover v-if="tasks.length > 0">
          <PopoverTrigger as-child>
            <Button variant="outline" size="sm" class="h-8 border-dashed">
              <ListFilter class="h-3.5 w-3.5 mr-1.5" />
              Tasks
              <Badge v-if="taskFilters.length > 0" variant="secondary" class="ml-1.5 rounded-sm px-1 font-normal">
                {{ taskFilters.length }}
              </Badge>
            </Button>
          </PopoverTrigger>
          <PopoverContent class="w-52 p-0" align="start">
            <Command>
              <CommandList>
                <CommandGroup>
                  <CheckableCommandItem
                    value="all"
                    :model-value="taskFilters.length === 0"
                    @update:model-value="taskFilters = []"
                  >
                    All Tasks
                  </CheckableCommandItem>
                </CommandGroup>
                <CommandSeparator />
                <CommandGroup>
                  <CheckableCommandItem
                    v-for="task in tasks"
                    :key="task.id"
                    :value="String(task.id)"
                    :model-value="taskFilters.includes(task.id)"
                    @update:model-value="toggleTaskFilter(task.id)"
                  >
                    {{ formatTaskType(task.task_type) }}
                  </CheckableCommandItem>
                </CommandGroup>
              </CommandList>
            </Command>
          </PopoverContent>
        </Popover>

        <Tooltip>
          <TooltipTrigger as-child>
            <Button
              :variant="showSubmissionNotes ? 'secondary' : 'outline'"
              size="icon-sm"
              @click="showSubmissionNotes = !showSubmissionNotes"
            >
              <Send class="h-3.5 w-3.5" />
              <span class="sr-only">Submission notes</span>
            </Button>
          </TooltipTrigger>
          <TooltipContent>Submission notes</TooltipContent>
        </Tooltip>

        <Tooltip>
          <TooltipTrigger as-child>
            <Button
              :variant="showClientOnly ? 'secondary' : 'outline'"
              size="icon-sm"
              @click="showClientOnly = !showClientOnly"
            >
              <Megaphone class="h-3.5 w-3.5" />
              <span class="sr-only">Client notes only</span>
            </Button>
          </TooltipTrigger>
          <TooltipContent>Client notes only</TooltipContent>
        </Tooltip>
      </div>

      <Select v-model="sortOrder">
        <SelectTrigger class="h-8 w-[130px] text-xs">
          <SelectValue />
        </SelectTrigger>
        <SelectContent>
          <SelectItem value="newest">Newest first</SelectItem>
          <SelectItem value="oldest">Oldest first</SelectItem>
        </SelectContent>
      </Select>
    </div>

    <!-- Notes History (Top) -->
    <div class="flex-1 overflow-y-auto p-4 space-y-4">
      <div v-if="combinedEntries.length === 0" class="flex flex-col items-center justify-center h-full text-muted-foreground">
        <MessageSquarePlus class="h-10 w-10 mb-2 opacity-50" />
        <p class="text-sm">No notes yet. Start the conversation below.</p>
      </div>

      <template v-for="entry in combinedEntries" :key="entry.id">
        <!-- Production Note -->
        <div v-if="entry.kind === 'note'" class="space-y-1">
          <div class="flex items-center gap-1.5">
            <Badge variant="outline" class="text-xs">{{ formatTaskType(taskTypeFor(entry.note.task_id)) }}</Badge>
            <Badge v-if="entry.note.note_type === 'client'" class="text-xs bg-orange-500 text-white border-transparent hover:bg-orange-500">Client</Badge>
          </div>
          <NoteItem
            :note="entry.note"
            :task-id="entry.note.task_id"
            date-format="absolute"
            hide-client-badge
            @note-updated="emit('notesUpdated')"
            @reply="handleReply"
          />
        </div>

        <!-- Submission Note (read-only) -->
        <div v-else class="space-y-1">
          <div class="flex items-center gap-1.5">
            <Badge variant="outline" class="text-xs">{{ formatTaskType(taskTypeFor(entry.submission.task_id)) }}</Badge>
            <Badge variant="secondary" class="text-xs">Submission v{{ entry.submission.version_number }}</Badge>
          </div>
          <div class="flex gap-3">
            <Avatar class="h-8 w-8 flex-shrink-0">
              <AvatarImage :src="getAvatarUrl(undefined, entry.submission.user_first_name, entry.submission.user_last_name)" />
              <AvatarFallback>{{ getInitials(entry.submission.user_first_name, entry.submission.user_last_name) }}</AvatarFallback>
            </Avatar>
            <div class="flex-1 min-w-0 rounded-2xl border bg-muted/50 px-3 py-2">
              <div class="flex items-center gap-2 flex-wrap">
                <span class="font-semibold text-sm">
                  {{ entry.submission.user_first_name }} {{ entry.submission.user_last_name }}
                </span>
                <span class="text-xs text-muted-foreground ml-auto flex items-center gap-1">
                  {{ formatDateOnly(entry.submission.submitted_at) }}
                  <Tooltip>
                    <TooltipTrigger as-child>
                      <Info class="h-3 w-3 cursor-help" />
                    </TooltipTrigger>
                    <TooltipContent>{{ formatDateTimeFull(entry.submission.submitted_at) }}</TooltipContent>
                  </Tooltip>
                </span>
              </div>
              <div class="text-sm whitespace-pre-wrap mt-0.5">{{ entry.submission.notes }}</div>
            </div>
          </div>
        </div>
      </template>
    </div>

    <!-- Note Input (Bottom) -->
    <div v-if="canCreateNote && tasks.length > 0" class="flex-shrink-0 border-t bg-background p-2 space-y-2">
      <div v-if="replyToNote" class="flex items-center justify-between gap-2 rounded-md bg-muted px-2 py-1.5 text-xs">
        <span class="truncate">
          Replying to <strong>{{ replyToNote.user_first_name }} {{ replyToNote.user_last_name }}</strong>
          <span class="text-muted-foreground">— {{ replyToNote.content }}</span>
        </span>
        <button type="button" class="flex-shrink-0 text-muted-foreground hover:text-foreground" @click="cancelReply">
          <X class="h-3 w-3" />
        </button>
      </div>

      <Select v-model="targetTaskId" :disabled="!!replyToNoteId">
        <SelectTrigger class="h-8 text-xs">
          <SelectValue placeholder="Select task..." />
        </SelectTrigger>
        <SelectContent>
          <SelectItem v-for="task in tasks" :key="task.id" :value="task.id">
            {{ formatTaskType(task.task_type) }}
          </SelectItem>
        </SelectContent>
      </Select>

      <div ref="composerRef">
        <Textarea
          v-model="newNoteContent"
          placeholder="Add a note..."
          rows="2"
          class="resize-none text-sm"
        />
      </div>
      <div class="flex items-center justify-between">
        <div class="flex gap-1">
          <Button
            type="button"
            size="sm"
            :variant="newNoteType === 'internal' ? 'secondary' : 'ghost'"
            @click="newNoteType = 'internal'"
          >
            Internal
          </Button>
          <Button
            type="button"
            size="sm"
            :variant="newNoteType === 'client' ? 'secondary' : 'ghost'"
            @click="newNoteType = 'client'"
          >
            Client
          </Button>
        </div>
        <Button
          size="sm"
          :disabled="!newNoteContent.trim() || !targetTaskId || submitting"
          @click="handleAddNote"
        >
          <MessageSquarePlus class="h-4 w-4 mr-2" />
          Add Note
        </Button>
      </div>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, computed, nextTick, watch } from 'vue'
import { Info, ListFilter, Megaphone, MessageSquarePlus, Send, X } from 'lucide-vue-next'
import { Button } from '@/components/ui/button'
import { Badge } from '@/components/ui/badge'
import { Textarea } from '@/components/ui/textarea'
import { Avatar, AvatarFallback, AvatarImage } from '@/components/ui/avatar'
import { Popover, PopoverContent, PopoverTrigger } from '@/components/ui/popover'
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'
import { Command, CommandGroup, CommandList, CommandSeparator, CheckableCommandItem } from '@/components/ui/command'
import { Tooltip, TooltipContent, TooltipTrigger } from '@/components/ui/tooltip'
import NoteItem from '@/components/task/NoteItem.vue'
import { taskService, type ProductionNote, type Submission, type NoteType } from '@/services/task'
import { usePermission } from '@/composables/usePermission'
import { useAvatarUrl } from '@/composables/useAvatarUrl'
import { useToast } from '@/components/ui/toast/use-toast'

interface EntityNoteTask {
  id: number
  task_type: string
}

const props = defineProps<{
  tasks: EntityNoteTask[]
  notes: ProductionNote[]
  submissions: Submission[]
}>()

const emit = defineEmits<{
  notesUpdated: []
}>()

const { toast } = useToast()
const { isCoordinatorOrAdmin } = usePermission()
const { getAvatarUrl } = useAvatarUrl()

const canCreateNote = computed(() => isCoordinatorOrAdmin.value)

const taskFilters = ref<number[]>([])
const sortOrder = ref<'newest' | 'oldest'>('newest')
const showSubmissionNotes = ref(true)
const showClientOnly = ref(false)

const newNoteContent = ref('')
const newNoteType = ref<NoteType>('internal')
const targetTaskId = ref<number | null>(null)
const submitting = ref(false)
const replyToNoteId = ref<number | null>(null)
const composerRef = ref<HTMLElement | null>(null)

watch(() => props.tasks, (tasks) => {
  if (!targetTaskId.value || !tasks.some(t => t.id === targetTaskId.value)) {
    targetTaskId.value = tasks[0]?.id ?? null
  }
}, { immediate: true })

function toggleTaskFilter(taskId: number) {
  const index = taskFilters.value.indexOf(taskId)
  if (index > -1) taskFilters.value.splice(index, 1)
  else taskFilters.value.push(taskId)
}

function isFilterActive(taskId: number): boolean {
  return taskFilters.value.length === 0 || taskFilters.value.includes(taskId)
}

function taskTypeFor(taskId: number): string {
  return props.tasks.find(t => t.id === taskId)?.task_type || ''
}

function formatTaskType(taskType: string): string {
  return taskType.split('_').map(word => word.charAt(0).toUpperCase() + word.slice(1)).join(' ')
}

function formatDateOnly(dateString: string): string {
  const date = new Date(dateString)
  const pad = (n: number) => String(n).padStart(2, '0')
  return `${date.getFullYear()}/${pad(date.getMonth() + 1)}/${pad(date.getDate())}`
}

function formatDateTimeFull(dateString: string): string {
  const date = new Date(dateString)
  const pad = (n: number) => String(n).padStart(2, '0')
  return `${date.getFullYear()}/${pad(date.getMonth() + 1)}/${pad(date.getDate())} ${pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}`
}

function getInitials(firstName: string, lastName: string): string {
  return `${firstName.charAt(0)}${lastName.charAt(0)}`.toUpperCase()
}

interface NoteEntry {
  kind: 'note'
  id: string
  date: string
  note: ProductionNote
}
interface SubmissionEntry {
  kind: 'submission'
  id: string
  date: string
  submission: Submission
}

const combinedEntries = computed<(NoteEntry | SubmissionEntry)[]>(() => {
  const noteEntries: NoteEntry[] = props.notes
    .filter(n => isFilterActive(n.task_id) && (!showClientOnly.value || n.note_type === 'client'))
    .map(n => ({ kind: 'note', id: `note-${n.id}`, date: n.created_at, note: n }))

  // Submissions have no internal/client distinction, so they don't qualify under "client notes only".
  const submissionEntries: SubmissionEntry[] = showSubmissionNotes.value && !showClientOnly.value
    ? props.submissions
        .filter(s => !!s.notes?.trim() && isFilterActive(s.task_id))
        .map(s => ({ kind: 'submission', id: `submission-${s.id}`, date: s.submitted_at, submission: s }))
    : []

  const direction = sortOrder.value === 'newest' ? -1 : 1
  return [...noteEntries, ...submissionEntries].sort(
    (a, b) => direction * (new Date(a.date).getTime() - new Date(b.date).getTime())
  )
})

function findNote(notes: ProductionNote[], id: number): ProductionNote | undefined {
  for (const note of notes) {
    if (note.id === id) return note
    if (note.child_notes) {
      const found = findNote(note.child_notes, id)
      if (found) return found
    }
  }
  return undefined
}

const replyToNote = computed(() => {
  if (replyToNoteId.value === null) return undefined
  return findNote(props.notes, replyToNoteId.value)
})

function handleReply(noteId: number) {
  const note = findNote(props.notes, noteId)
  if (!note) return
  replyToNoteId.value = noteId
  targetTaskId.value = note.task_id
  nextTick(() => {
    composerRef.value?.querySelector('textarea')?.focus()
  })
}

function cancelReply() {
  replyToNoteId.value = null
}

async function handleAddNote() {
  if (!newNoteContent.value.trim() || !targetTaskId.value) return

  submitting.value = true
  try {
    await taskService.createTaskNote(
      targetTaskId.value,
      newNoteContent.value,
      replyToNoteId.value || undefined,
      newNoteType.value
    )
    newNoteContent.value = ''
    newNoteType.value = 'internal'
    replyToNoteId.value = null
    emit('notesUpdated')
    toast({
      title: 'Success',
      description: 'Note added successfully'
    })
  } catch (error: any) {
    console.error('Error adding note:', error)
    toast({
      title: 'Error',
      description: error.response?.data?.detail || 'Failed to add note',
      variant: 'destructive'
    })
  } finally {
    submitting.value = false
  }
}
</script>
