import { customElement, html, DeesElement, property, css, cssManager, type TemplateResult } from '@design.estate/dees-element';
import { demoFunc } from './dees-pagination.demo.js';
import { themeDefaultStyles } from '../00theme.js';

declare global {
  interface HTMLElementTagNameMap {
    'dees-pagination': DeesPagination;
  }
}

/**
 * A simple pagination component.
 * @fires page-change - Emitted when the page is changed. detail: { page: number }
 */
@customElement('dees-pagination')
export class DeesPagination extends DeesElement {
  public static demo = demoFunc;
  /** Current page (1-based) */
  @property({ type: Number, reflect: true })
  accessor page = 1;

  /** Total number of pages */
  @property({ type: Number, reflect: true })
  accessor total = 1;

  public static styles = [
    themeDefaultStyles,
    cssManager.defaultStyles,
    css`
      /* TODO: Migrate hardcoded values to --dees-* CSS variables */
      :host {
        display: inline-flex;
        align-items: center;
      }
      button {
        background: none;
        border: none;
        margin: 0 2px;
        padding: 6px 10px;
        font-size: 14px;
        cursor: pointer;
        color: ${cssManager.bdTheme('#333', '#ccc')};
        border-radius: 3px;
        transition: background 0.2s;
      }
      button:hover:not(:disabled) {
        background: ${cssManager.bdTheme('#eee', '#444')};
      }
      button:disabled {
        cursor: default;
        color: ${cssManager.bdTheme('#aaa', '#666')};
      }
      button.current {
        background: #0050b9;
        color: #fff;
        cursor: default;
      }
      span.ellipsis {
        margin: 0 4px;
        color: ${cssManager.bdTheme('#333', '#ccc')};
      }
    `,
  ];

  private get pages(): (number | string)[] {
    const pages: (number | string)[] = [];
    const total = this.total;
    const current = this.page;
    if (total <= 7) {
      for (let i = 1; i <= total; i++) {
        pages.push(i);
      }
    } else {
      pages.push(1);
      if (current > 4) {
        pages.push('...');
      }
      const start = Math.max(2, current - 2);
      const end = Math.min(total - 1, current + 2);
      for (let i = start; i <= end; i++) {
        pages.push(i);
      }
      if (current < total - 3) {
        pages.push('...');
      }
      pages.push(total);
    }
    return pages;
  }

  public render(): TemplateResult {
    return html`
      <button
        @click=${() => this.changePage(this.page - 1)}
        ?disabled=${this.page <= 1}
        aria-label="Previous page"
      >
        ‹
      </button>
      ${this.pages.map((p) =>
        p === '...'
          ? html`<span class="ellipsis">…</span>`
          : html`
              <button
                class="${p === this.page ? 'current' : ''}"
                @click=${() => this.changePage(p as number)}
                ?disabled=${p === this.page}
                aria-label="Page ${p}"
              >
                ${p}
              </button>
            `
      )}
      <button
        @click=${() => this.changePage(this.page + 1)}
        ?disabled=${this.page >= this.total}
        aria-label="Next page"
      >
        ›
      </button>
    `;
  }

  private changePage(newPage: number) {
    if (newPage < 1 || newPage > this.total || newPage === this.page) {
      return;
    }
    this.page = newPage;
    this.dispatchEvent(
      new CustomEvent('page-change', {
        detail: { page: this.page },
        bubbles: true,
      })
    );
  }
}