/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

import {
  classMap,
  html,
  ifDefined,
  when,
} from "chrome://global/content/vendor/lit.all.mjs";
import { MozLitElement } from "chrome://global/content/lit-utils.mjs";

/**
 * A collapsible card container to be used throughout Firefox View
 *
 * @property {string} sectionLabel - The aria-label used for the section landmark if the header is hidden with hideHeader
 * @property {boolean} hideHeader - Optional property given if the card container should not display a header
 * @property {boolean} isEmptyState - Optional property given if the card is used within an empty state
 * @property {boolean} isInnerCard - Optional property given if the card a nested card within another card and given a border rather than box-shadow
 * @property {boolean} preserveCollapseState - Whether or not the expanded/collapsed state should persist
 * @property {string} shortPageName - Page name that the 'View all' link will navigate to and the preserveCollapseState pref will use
 * @property {boolean} showViewAll - True if you need to display a 'View all' header link to navigate
 * @property {boolean} toggleDisabled - Optional property given if the card container should not be collapsible
 * @property {boolean} removeBlockEndMargin - True if you need to remove the block end margin on the card container
 */
class CardContainer extends MozLitElement {
  constructor() {
    super();
    this.initiallyExpanded = true;
    this.isExpanded = false;
    this.visible = false;
  }

  static properties = {
    sectionLabel: { type: String },
    hideHeader: { type: Boolean },
    isExpanded: { type: Boolean },
    isEmptyState: { type: Boolean },
    isInnerCard: { type: Boolean },
    preserveCollapseState: { type: Boolean },
    shortPageName: { type: String },
    showViewAll: { type: Boolean },
    toggleDisabled: { type: Boolean },
    removeBlockEndMargin: { type: Boolean },
    visible: { type: Boolean },
  };

  static queries = {
    detailsEl: "details",
    mainSlot: "slot[name=main]",
    summaryEl: "summary",
    viewAllLink: ".view-all-link",
  };

  get detailsExpanded() {
    return this.detailsEl.hasAttribute("open");
  }

  get detailsOpenPrefValue() {
    const prefName = this.shortPageName
      ? `browser.tabs.firefox-view.ui-state.${this.shortPageName}.open`
      : null;
    if (prefName && Services.prefs.prefHasUserValue(prefName)) {
      return Services.prefs.getBoolPref(prefName);
    }
    return null;
  }

  connectedCallback() {
    super.connectedCallback();
    this.isExpanded = this.detailsOpenPrefValue ?? this.initiallyExpanded;
  }

  onToggleContainer() {
    if (this.isExpanded == this.detailsExpanded) {
      return;
    }
    this.isExpanded = this.detailsExpanded;

    this.updateTabLists();

    if (!this.shortPageName) {
      return;
    }

    if (this.preserveCollapseState) {
      const prefName = this.shortPageName
        ? `browser.tabs.firefox-view.ui-state.${this.shortPageName}.open`
        : null;
      Services.prefs.setBoolPref(prefName, this.isExpanded);
    }

    // Record telemetry
    Glean.firefoxviewNext[
      `card${this.isExpanded ? "Expanded" : "Collapsed"}CardContainer`
    ].record({
      data_type: this.shortPageName,
    });
  }

  viewAllClicked() {
    this.dispatchEvent(
      new CustomEvent("card-container-view-all", {
        bubbles: true,
        composed: true,
      })
    );
  }

  willUpdate(changes) {
    if (changes.has("visible")) {
      this.updateTabLists();
    }
  }

  updateTabLists() {
    let tabLists = this.querySelectorAll(
      "fxview-tab-list, opentabs-tab-list, syncedtabs-tab-list"
    );
    if (tabLists) {
      tabLists.forEach(tabList => {
        tabList.updatesPaused = !this.visible || !this.isExpanded;
      });
    }
  }

  render() {
    return html`
      <link
        rel="stylesheet"
        href="chrome://browser/content/firefoxview/card-container.css"
      />
      ${when(
        this.toggleDisabled,
        () =>
          html`<div
            class=${classMap({
              "card-container": true,
              inner: this.isInnerCard,
              "empty-state": this.isEmptyState && !this.isInnerCard,
            })}
          >
            <span
              id="header"
              class="card-container-header"
              ?hidden=${ifDefined(this.hideHeader)}
              toggleDisabled
              ?withViewAll=${this.showViewAll}
            >
              <slot name="header"></slot>
              <slot name="secondary-header"></slot>
            </span>
            <a
              href="about:firefoxview#${this.shortPageName}"
              @click=${this.viewAllClicked}
              class="view-all-link"
              data-l10n-id="firefoxview-view-all-link"
              ?hidden=${!this.showViewAll}
            ></a>
            <slot name="main"></slot>
            <slot name="footer" class="card-container-footer"></slot>
          </div>`,
        () =>
          html`<details
            class=${classMap({
              "card-container": true,
              inner: this.isInnerCard,
              "empty-state": this.isEmptyState && !this.isInnerCard,
            })}
            ?open=${this.isExpanded}
            ?isOpenTabsView=${this.removeBlockEndMargin}
            @toggle=${this.onToggleContainer}
            role=${this.isInnerCard ? "presentation" : "group"}
          >
            <summary
              class="card-container-header"
              ?hidden=${ifDefined(this.hideHeader)}
              ?withViewAll=${this.showViewAll}
            >
              <span
                class="icon chevron-icon"
                role="presentation"
                data-l10n-id="firefoxview-collapse-button-${this.isExpanded
                  ? "hide"
                  : "show"}"
              ></span>
              <slot name="header"></slot>
            </summary>
            <a
              href="about:firefoxview#${this.shortPageName}"
              @click=${this.viewAllClicked}
              class="view-all-link"
              data-l10n-id="firefoxview-view-all-link"
              ?hidden=${!this.showViewAll}
            ></a>
            <slot name="main"></slot>
            <slot name="footer" class="card-container-footer"></slot>
          </details>`
      )}
    `;
  }
}
customElements.define("card-container", CardContainer);
