<script>
  import Icon from "$/client/components/Icon.svelte";
  import { onMount } from "svelte";
  import { log } from "$/client/logging.js";
  import api from "$/client/api.js";
  import { defer } from "$/client/helpers.js";
  import Toast from "$/client/components/Toasts.svelte";

  let all_icons = [];
  let icons_by_letters = {"a": []};
  let selected_letter = "a";
  let inactive = false;
  let icons = [];
  export let size=48;
  let search = "";
  export let labels=true;
  export let tight=false;
  let load_promise = defer();
  let send_toast;

  const order_pages = (in_icons) => {
    const letters = {};
    for(let icon_name of in_icons) {
      const first = icon_name[0];
      letters[first] = letters[first] || [];
      letters[first].push(icon_name);
    }

    return letters;
  }

  const search_icons = async (pattern) => {
    await load_promise; // lord I hate Svelte's lifecycle

    if(pattern.trim() === "") {
      icons_by_letters = order_pages(all_icons);
      icons = all_icons;
      selected_letter = Object.keys(icons_by_letters)[0];
    } else {
      icons = all_icons.filter(i => i.includes(pattern));

      if(icons.length > 0) {
        icons_by_letters = order_pages(icons);
        selected_letter = Object.keys(icons_by_letters)[0];
      }
    }

  }

  $: search_icons(search);

  const gen_code = (name) => {
    let results = `<Icon name="${name}" size="${size}" />`;

    navigator.clipboard.writeText(results).then(() => {
      send_toast(`${name} copied to clipboard.`);
    }, () => {
      send_toast(`${name} copy FAILED.`);
    });
  }

  onMount(async () => {
    const [status, data] = await api.get("/icons/index.json");

    if(status === 200) {
      all_icons = data;
      icons_by_letters = order_pages(all_icons);
      load_promise.resolve();
    } else {
      log.error("Invalid response", status, data);
      load_promise.reject();
    }
  });
</script>

<style>
  icons {
    display: grid;
    grid-template-columns: repeat(6, 1fr);
    grid-template-rows: auto;
    row-gap: 1rem;
  }

  icons.tight {
    grid-template-columns: repeat(10, 1fr);
  }

  icons icon {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
  }

  search-bar {
    display: flex;
    justify-content: space-evenly;
    flex-wrap: nowrap;
    height: 5ch;
    min-height: 5ch;
  }

  search-bar input#size {
    width: 6ch;
  }

  search-bar input#search {
    min-width: 30ch;
    max-width: 30ch;
    width: 30ch;
  }

  search-bar span {
    padding-right: 1rem;
  }

  content {
    display: flex;
    flex-direction: column;
    padding-top: 1rem;
  }

  display {
    display: flex;
    flex-direction: column;
    align-items: stretch;
  }

  display letters {
    display: grid;
    grid-template-rows: 1fr 1fr;
    grid-template-columns: repeat(13, 1fr);
    margin-bottom: 1rem;
  }

  display letters letter {
    font-size: 1.5em;
    font-weight: 600;
    text-align: center;
    padding: 1rem;
    border: 1px solid var(--value5);
  }

  display letters letter.selected {
    background-color: var(--color-bg-secondary);
  }

  @media only screen and (max-width: 900px) {
    icons {
      grid-template-columns: repeat(4, 1fr);
    }
  }

  @media only screen and (max-width: 600px) {
    icons {
      grid-template-columns: repeat(3, 1fr);
    }
  }
</style>

<content>
  <search-bar>
    <span on:click={ () => inactive = !inactive }>
      <Icon tooltip="Toggle inactive look." name={ inactive ? 'eye' : 'eye-off'} size="24" />
    </span>
    <input placeholder="Search names..." bind:value={ search } id="search" >
    <div>Pixel Size:</div>
    <input bind:value={ size } id="size" >
  </search-bar>

  {#if icons.length > 0}
    <display>
      <letters>
        {#each Object.keys(icons_by_letters) as letter}
          <letter class:selected={ letter === selected_letter } on:click={ () => selected_letter = letter }>{ letter }</letter>
        {/each}
      </letters>

      <icons class:tight={ tight }>
        {#each icons_by_letters[selected_letter] as name}
          <icon on:click={ () => gen_code(name) }>
            <Icon name={ name } size={ size } inactive={inactive}/>
            {#if labels}
              <span>{ name }</span>
            {/if}
          </icon>
        {/each}
      </icons>
    </display>
  {:else}
    <h1>No Icons match "{ search }"</h1>
  {/if}
  <Toast bind:send_toast orientation="bottom right" />
</content>
