<!-- eslint-disable @angular-eslint/template/button-has-type -->
<div
  #composerRoot
  class="relative min-w-0 w-full"
>
  @if (slashMenuOpen()) {
    <div class="pointer-events-auto absolute bottom-full left-0 right-0 z-30 mb-2 px-3 sm:px-4">
      <app-chat-slash-command-menu
        [commands]="slashCommandResults()"
        [activeIndex]="slashActiveIndex()"
        (commandPicked)="pickSlashCommand($event)"
        (activeIndexChanged)="onSlashActiveIndexChanged($event)"
      />
    </div>
  }

  @if (replyTo()) {
    <div
      appThemeNode="chatComposerReplyBar"
      class="pointer-events-auto flex items-center gap-2 bg-secondary/50 px-4 py-2"
    >
      <ng-icon
        name="lucideReply"
        class="h-4 w-4 text-muted-foreground"
      />
      <span class="flex-1 text-sm text-muted-foreground">
        {{ 'chat.composer.replyingTo' | translate: { name: replyTo()?.senderName } }}
      </span>
      <button
        (click)="clearReply()"
        class="grid h-6 w-6 place-items-center rounded transition-colors hover:bg-secondary"
      >
        <ng-icon
          name="lucideX"
          class="h-4 w-4 text-muted-foreground"
        />
      </button>
    </div>
  }

  <app-typing-indicator />

  @if (toolbarVisible()) {
    <div
      class="pointer-events-auto"
      (mousedown)="$event.preventDefault()"
      (mouseenter)="onToolbarMouseEnter()"
      (mouseleave)="onToolbarMouseLeave()"
    >
      <div
        appThemeNode="chatComposerToolbar"
        class="mx-4 -mb-2 flex flex-wrap items-center justify-start gap-2 rounded-lg border border-border bg-card/70 px-2 py-1 shadow-sm backdrop-blur"
      >
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyInline('**')"
        >
          <b>B</b>
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyInline('*')"
        >
          <i>I</i>
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyInline('~~')"
        >
          <s>S</s>
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyInline(inlineCodeToken)"
        >
          &#96;
        </button>
        <span class="mx-1 text-muted-foreground">|</span>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyHeading(1)"
        >
          H1
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyHeading(2)"
        >
          H2
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyHeading(3)"
        >
          H3
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyPrefix('> ')"
        >
          {{ 'chat.composer.toolbar.quote' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyPrefix('- ')"
        >
          {{ 'chat.composer.toolbar.bulletList' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyOrderedList()"
        >
          {{ 'chat.composer.toolbar.orderedList' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyCodeBlock()"
        >
          {{ 'chat.composer.toolbar.code' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyLink()"
        >
          {{ 'chat.composer.toolbar.link' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyImage()"
        >
          {{ 'chat.composer.toolbar.image' | translate }}
        </button>
        <button
          class="rounded px-2 py-1 text-xs hover:bg-secondary"
          (click)="applyHorizontalRule()"
        >
          {{ 'chat.composer.toolbar.horizontalRule' | translate }}
        </button>
      </div>
    </div>
  }

  <div class="min-w-0 w-full px-3 py-3 sm:p-4">
    <div
      appThemeNode="chatComposerInput"
      class="chat-input-wrapper relative min-w-0 w-full"
      (mouseenter)="inputHovered.set(true)"
      (mouseleave)="inputHovered.set(false)"
      (dragenter)="onDragEnter($event)"
      (dragover)="onDragOver($event)"
      (dragleave)="onDragLeave($event)"
      (drop)="onDrop($event)"
    >
      <div class="absolute bottom-3 right-3 z-10 flex items-center gap-2 m-0.5">
        @for (record of pluginComposerActions(); track record.id) {
          <button
            type="button"
            (click)="runPluginComposerAction(record.contribution)"
            class="inline-flex h-10 min-w-10 items-center justify-center gap-1.5 rounded-2xl border border-border/70 bg-secondary/55 px-3 text-[11px] font-semibold uppercase tracking-[0.2em] text-muted-foreground shadow-sm backdrop-blur-md transition-all duration-200 hover:-translate-y-0.5 hover:border-primary/35 hover:bg-secondary/90 hover:text-foreground"
            [class.opacity-100]="inputHovered()"
            [class.opacity-70]="!inputHovered()"
            [attr.aria-label]="record.contribution.label"
            [title]="record.contribution.label"
          >
            <span>{{ record.contribution.icon ?? record.contribution.label }}</span>
          </button>
        }

        @if (mergeComposerMediaActions()) {
          <div class="relative">
            <button
              type="button"
              (click)="$event.stopPropagation(); toggleComposerMediaMenu()"
              class="inline-flex h-11 w-11 items-center justify-center rounded-2xl border border-border/70 bg-secondary/55 text-muted-foreground shadow-sm backdrop-blur-md transition-all duration-200 hover:-translate-y-0.5 hover:border-primary/35 hover:bg-secondary/90 hover:text-foreground"
              [class.border-primary]="showComposerMediaMenu() || showEmojiPicker() || showKlipyGifPicker()"
              [class.opacity-100]="inputHovered() || showComposerMediaMenu() || showEmojiPicker() || showKlipyGifPicker()"
              [class.opacity-70]="!inputHovered() && !showComposerMediaMenu() && !showEmojiPicker() && !showKlipyGifPicker()"
              [class.text-primary]="showComposerMediaMenu() || showEmojiPicker() || showKlipyGifPicker()"
              [attr.aria-label]="'chat.composer.addAttachmentGifEmoji' | translate"
              [title]="'chat.composer.addAttachmentGifEmoji' | translate"
            >
              <ng-icon
                name="lucidePlus"
                class="h-5 w-5"
              />
            </button>

            @if (showComposerMediaMenu()) {
              <app-bottom-sheet
                [title]="'chat.composer.addToMessage' | translate"
                [ariaLabel]="'chat.composer.addToMessage' | translate"
                (dismissed)="closeComposerMediaMenu()"
              >
                <div class="flex flex-col py-1">
                  @for (option of composerMediaMenuOptions(); track option.action) {
                    <button
                      type="button"
                      class="flex w-full items-center gap-3 px-4 py-3 text-left text-sm text-foreground transition-colors hover:bg-secondary"
                      (click)="handleComposerMediaMenuAction(option.action)"
                    >
                      @switch (option.action) {
                        @case ('attachment') {
                          <ng-icon
                            name="lucidePaperclip"
                            class="h-5 w-5 text-muted-foreground"
                          />
                        }
                        @case ('gif') {
                          <ng-icon
                            name="lucideImage"
                            class="h-5 w-5 text-muted-foreground"
                          />
                        }
                        @case ('emoji') {
                          <ng-icon
                            name="lucideSmile"
                            class="h-5 w-5 text-muted-foreground"
                          />
                        }
                      }
                      <span>{{ option.labelKey | translate }}</span>
                    </button>
                  }
                </div>
              </app-bottom-sheet>
            }

            @if (showEmojiPicker()) {
              <app-bottom-sheet
                [title]="'chat.composer.emoji' | translate"
                [ariaLabel]="'chat.composer.emojiPickerAria' | translate"
                (dismissed)="closeEmojiPicker()"
              >
                <app-custom-emoji-picker
                  [compact]="false"
                  [inline]="true"
                  [currentUserId]="currentUserId()"
                  (emojiSelected)="insertEmoji($event)"
                  (dismissed)="closeEmojiPicker()"
                />
              </app-bottom-sheet>
            }
          </div>
        } @else {
          @if (shouldShowAttachmentButton()) {
            <button
              type="button"
              (click)="pickAttachmentsFromDevice()"
              class="inline-flex h-11 w-11 items-center justify-center rounded-2xl border border-border/70 bg-secondary/55 text-muted-foreground shadow-sm backdrop-blur-md transition-all duration-200 hover:-translate-y-0.5 hover:border-primary/35 hover:bg-secondary/90 hover:text-foreground md:h-10 md:w-10"
              [class.opacity-100]="inputHovered()"
              [class.opacity-70]="!inputHovered()"
              [attr.aria-label]="'chat.composer.attachFiles' | translate"
              [title]="'chat.composer.attachFiles' | translate"
            >
              <ng-icon
                name="lucidePaperclip"
                class="h-4 w-4"
              />
            </button>
          }

          @if (klipyEnabled()) {
            <button
              #klipyTrigger
              type="button"
              (click)="toggleKlipyGifPicker()"
              class="inline-flex h-10 min-w-10 items-center justify-center gap-1.5 rounded-2xl border border-border/70 bg-secondary/55 px-3 text-[11px] font-semibold uppercase tracking-[0.2em] text-muted-foreground shadow-sm backdrop-blur-md transition-all duration-200 hover:-translate-y-0.5 hover:border-primary/35 hover:bg-secondary/90 hover:text-foreground"
              [class.border-primary]="showKlipyGifPicker()"
              [class.opacity-100]="inputHovered() || showKlipyGifPicker()"
              [class.opacity-70]="!inputHovered() && !showKlipyGifPicker()"
              [class.shadow-none]="!inputHovered() && !showKlipyGifPicker()"
              [class.text-primary]="showKlipyGifPicker()"
              [attr.aria-label]="'chat.composer.searchKlipyGifs' | translate"
              [title]="'chat.composer.searchKlipyGifs' | translate"
            >
              <ng-icon
                name="lucideImage"
                class="h-4 w-4"
              />
              <span class="hidden sm:inline">{{ 'chat.composer.gif' | translate }}</span>
            </button>
          }

          <div class="relative">
            <button
              type="button"
              (click)="$event.stopPropagation(); toggleEmojiPicker()"
              (mouseenter)="randomizeEmojiButton()"
              class="inline-flex h-10 min-w-10 items-center justify-center rounded-2xl border border-border/70 bg-secondary/35 px-3 text-lg grayscale transition-all duration-200 hover:-translate-y-0.5 hover:border-primary/35 hover:bg-secondary/90 hover:grayscale-0"
              [class.opacity-100]="inputHovered() || showEmojiPicker()"
              [class.opacity-60]="!inputHovered() && !showEmojiPicker()"
              [class.grayscale-0]="showEmojiPicker()"
              [attr.aria-label]="'chat.composer.openEmojiSelector' | translate"
              [title]="'chat.composer.openEmojiSelector' | translate"
            >
              {{ emojiButton() }}
            </button>

            @if (showEmojiPicker()) {
              <div class="absolute bottom-full right-0 z-20 mb-2">
                <app-custom-emoji-picker
                  [currentUserId]="currentUserId()"
                  (emojiSelected)="insertEmoji($event)"
                  (dismissed)="closeEmojiPicker()"
                />
              </div>
            }
          </div>
        }

        <button
          appThemeNode="chatComposerSendButton"
          type="button"
          (click)="sendMessage()"
          [disabled]="!messageContent.trim() && pendingFiles.length === 0 && !pendingKlipyGif()"
          class="send-btn visible inline-flex h-11 w-11 items-center justify-center rounded-2xl bg-primary text-primary-foreground shadow-lg shadow-primary/25 ring-1 ring-primary/20 transition-all duration-200 hover:-translate-y-0.5 hover:bg-primary/90 disabled:translate-y-0 disabled:cursor-not-allowed disabled:bg-secondary disabled:text-muted-foreground disabled:shadow-none disabled:ring-0"
          [attr.aria-label]="'chat.composer.sendMessage' | translate"
          [title]="'chat.composer.sendMessage' | translate"
        >
          <ng-icon
            name="lucideSend"
            class="h-5 w-5"
          />
        </button>
      </div>

      <textarea
        #messageInputRef
        [attr.data-testid]="textareaTestId()"
        rows="1"
        [(ngModel)]="messageContent"
        (focus)="onInputFocus()"
        (blur)="onInputBlur()"
        (keydown)="onComposerKeydown($event)"
        (keydown.enter)="onEnter($event)"
        (input)="onInputChange(); autoResizeTextarea(); updateSlashCommandMenu()"
        (paste)="onPaste($event)"
        (dragenter)="onDragEnter($event)"
        (dragover)="onDragOver($event)"
        (dragleave)="onDragLeave($event)"
        (drop)="onDrop($event)"
        [placeholder]="'chat.composer.placeholder' | translate"
        class="chat-textarea w-full min-w-0 border-0 pl-4 text-foreground placeholder:text-muted-foreground focus:outline-none"
        [class.chat-textarea-expanded]="textareaExpanded()"
        [class.ctrl-resize]="ctrlHeld()"
        [ngClass]="composerTextareaPaddingClass()"
      ></textarea>

      @if (dragActive()) {
        <div class="pointer-events-none absolute inset-0 flex items-center justify-center border-2 border-dashed border-primary bg-primary/5">
          <div class="text-sm text-muted-foreground">{{ 'chat.composer.dropFilesToAttach' | translate }}</div>
        </div>
      }

      @if (pendingKlipyGif()) {
        <div class="mt-2 flex">
          <div class="group flex max-w-sm items-center gap-3 rounded-xl border border-border bg-secondary/60 px-2.5 py-2">
            <div class="relative h-12 w-12 overflow-hidden rounded-lg bg-secondary/80">
              <img
                [appChatImageProxyFallback]="pendingKlipyGif()!.previewUrl || pendingKlipyGif()!.url"
                [signalSource]="klipySignalSource()"
                [alt]="pendingKlipyGif()!.title || ('chat.composer.klipyGif' | translate)"
                class="h-full w-full object-cover"
                loading="lazy"
              />
              <span
                class="absolute bottom-1 left-1 rounded bg-black/70 px-1.5 py-0.5 text-[8px] font-semibold uppercase tracking-[0.18em] text-white/90"
              >
                {{ 'chat.composer.klipy' | translate }}
              </span>
            </div>
            <div class="min-w-0">
              <div class="text-xs font-medium text-foreground">{{ 'chat.composer.gifReadyToSend' | translate }}</div>
              <div class="max-w-[12rem] truncate text-[10px] text-muted-foreground">
                {{ pendingKlipyGif()!.title || ('chat.composer.klipyGif' | translate) }}
              </div>
            </div>
            <button
              type="button"
              (click)="removePendingKlipyGif()"
              class="rounded px-2 py-1 text-[10px] text-destructive transition-colors hover:bg-destructive/10"
            >
              {{ 'chat.composer.remove' | translate }}
            </button>
          </div>
        </div>
      }

      @if (pendingFiles.length > 0) {
        <div class="mt-2 flex flex-wrap gap-2">
          @for (file of pendingFiles; track file.name) {
            <div class="group flex items-center gap-2 rounded border border-border bg-secondary/60 px-2 py-1">
              <div class="max-w-[14rem] truncate text-xs font-medium">{{ file.name }}</div>
              <div class="text-[10px] text-muted-foreground">{{ formatBytes(file.size) }}</div>
              <button
                (click)="removePendingFile(file)"
                class="rounded bg-destructive/20 px-1 py-0.5 text-[10px] text-destructive opacity-70 group-hover:opacity-100"
              >
                {{ 'chat.composer.remove' | translate }}
              </button>
            </div>
          }
        </div>
      }
    </div>
  </div>
</div>
