import {
  createEffect,
  createSignal,
  onMount,
  Show,
  type Component,
} from "solid-js";
import Scaffold from "../material/Scaffold";
import {
  Avatar,
  Button,
  IconButton,
  List,
  ListItemButton,
  ListItemIcon,
  ListItemSecondaryAction,
  ListItemText,
  Radio,
  Switch,
  Divider,
} from "@suid/material";
import {
  ArrowDropDown,
  Public as PublicIcon,
  Send,
  People as PeopleIcon,
  ThreeP as ThreePIcon,
  ListAlt as ListAltIcon,
  Visibility,
  Translate,
} from "@suid/icons-material";
import type { Account } from "../accounts/stores";
import tootComposers from "./TootComposer.module.css";
import { makeEventListener } from "@solid-primitives/event-listener";
import BottomSheet from "../material/BottomSheet";
import { useLanguage } from "../platform/i18n";
import iso639_1 from "iso-639-1";
import ChooseTootLang from "./ChooseTootLang";

type TootVisibility = "public" | "unlisted" | "private" | "direct";

const TootVisibilityPickerDialog: Component<{
  open?: boolean;
  onClose: () => void;
  visibility: TootVisibility;
  onVisibilityChange: (value: TootVisibility) => void;
}> = (props) => {
  type Kind = "public" | "private" | "direct";

  const kind = () =>
    props.visibility === "public" || props.visibility === "unlisted"
      ? "public"
      : props.visibility;

  const setKind = (nv: Kind) => {
    if (nv == "public") {
      props.onVisibilityChange(discoverable() ? "public" : "unlisted");
    } else {
      props.onVisibilityChange(nv);
    }
  };

  const discoverable = () => {
    return props.visibility === "public";
  };

  const setDiscoverable = (setter: (v: boolean) => boolean) => {
    const nval = setter(discoverable());
    props.onVisibilityChange(nval ? "public" : "unlisted"); // trigger change
  };

  return (
    <BottomSheet open={props.open} onClose={props.onClose} bottomUp>
      <Scaffold
        bottom={
          <div
            style={{
              "border-top": "1px solid #ddd",
              background: "var(--tutu-color-surface)",
              padding: "8px 16px",
              width: "100%",
              "text-align": "end",
            }}
          >
            <Button onClick={props.onClose}>Confirm</Button>
          </div>
        }
      >
        <List dense>
          <ListItemButton onClick={[setKind, "public"]}>
            <ListItemIcon>
              <PublicIcon />
            </ListItemIcon>
            <ListItemText
              primary="Public"
              secondary="Everyone can see this toot"
            ></ListItemText>
            <ListItemSecondaryAction>
              <Radio checked={kind() == "public"}></Radio>
            </ListItemSecondaryAction>
          </ListItemButton>

          <ListItemButton
            sx={{ paddingLeft: "40px" }}
            disabled={kind() !== "public"}
            onClick={() => setDiscoverable((x) => !x)}
          >
            <ListItemIcon>
              <ListAltIcon />
            </ListItemIcon>
            <ListItemText
              primary="Discoverable"
              secondary="The others can discover it on the exploration."
            ></ListItemText>
            <ListItemSecondaryAction>
              <Switch
                checked={discoverable()}
                disabled={kind() !== "public"}
              ></Switch>
            </ListItemSecondaryAction>
          </ListItemButton>

          <Divider />

          <ListItemButton onClick={[setKind, "private"]}>
            <ListItemIcon>
              <PeopleIcon />
            </ListItemIcon>
            <ListItemText
              primary="Only Followers"
              secondary="Visibile for followers only"
            ></ListItemText>
            <ListItemSecondaryAction>
              <Radio checked={kind() == "private"}></Radio>
            </ListItemSecondaryAction>
          </ListItemButton>

          <Divider />

          <ListItemButton onClick={[setKind, "direct"]}>
            <ListItemIcon>
              <ThreePIcon />
            </ListItemIcon>
            <ListItemText
              primary="Only Mentions"
              secondary="Visible for mentioned users only"
            ></ListItemText>
            <ListItemSecondaryAction>
              <Radio checked={kind() == "direct"}></Radio>
            </ListItemSecondaryAction>
          </ListItemButton>
        </List>
      </Scaffold>
    </BottomSheet>
  );
};

const TootLanguagePickerDialog: Component<{
  open?: boolean;
  onClose: () => void;
  code: string;
  onCodeChange: (nval: string) => void;
}> = (props) => {
  return (
    <BottomSheet open={props.open} onClose={props.onClose}>
      <Show when={props.open}>
        <ChooseTootLang
          code={props.code}
          onCodeChange={props.onCodeChange}
          onClose={props.onClose}
        />
      </Show>
    </BottomSheet>
  );
};

const ReplyEditor: Component<{
  profile: Account;
  replyToDisplayName: string;
  isTyping?: boolean;
  onTypingChange: (value: boolean) => void;
}> = (props) => {
  let inputRef: HTMLTextAreaElement;

  const typing = () => props.isTyping;
  const setTyping = (v: boolean) => props.onTypingChange(v);
  const [visibility, setVisibility] = createSignal<TootVisibility>("public");
  const [permPicker, setPermPicker] = createSignal(false);
  const [language, setLanguage] = createSignal("en");
  const [langPickerOpen, setLangPickerOpen] = createSignal(false);
  const appLanguage = useLanguage();

  createEffect(() => {
    const lang = appLanguage().split("-")[0];
    setLanguage(lang);
  });

  onMount(() => {
    makeEventListener(inputRef, "focus", () => setTyping(true));
  });

  const containerStyle = () =>
    typing() || permPicker()
      ? {
          position: "sticky" as const,
          top: "var(--scaffold-topbar-height, 0)",
          bottom: "var(--safe-area-inset-bottom, 0)",
          "z-index": 2,
        }
      : undefined;

  const visibilityText = () => {
    switch (visibility()) {
      case "public":
        return "Discoverable";
      case "unlisted":
        return "Public";
      case "private":
        return "Only Followers";
      case "direct":
        return "Only Mentions";
    }
  };

  return (
    <div
      class={tootComposers.composer}
      style={containerStyle()}
      onClick={(e) => inputRef.focus()}
    >
      <div class={tootComposers.replyInput}>
        <Avatar src={props.profile.inf?.avatar} sx={{marginLeft: '-0.25em'}} />
        <textarea
          ref={inputRef!}
          placeholder={`Reply to ${props.replyToDisplayName}...`}
          style={{ width: "100%", border: "none" }}
        ></textarea>
        <IconButton sx={{marginRight: '-0.5em'}}>
          <Send />
        </IconButton>
      </div>

      <div
        style={{
          display: "flex",
          "justify-content": "space-between",
          "margin-top": "8px",
          gap: "16px",
          "flex-flow": "row wrap",
        }}
      >
        <Button onClick={[setLangPickerOpen, true]}>
          <Translate sx={{ marginTop: "-0.25em", marginRight: "0.25em" }} />
          {iso639_1.getNativeName(language())}
          <ArrowDropDown sx={{ marginTop: "-0.25em" }} />
        </Button>
        <Button onClick={[setPermPicker, true]}>
          <Visibility sx={{ marginTop: "-0.15em", marginRight: "0.25em" }} />
          {visibilityText()}
          <ArrowDropDown sx={{ marginTop: "-0.25em" }} />
        </Button>
      </div>

      <TootVisibilityPickerDialog
        open={permPicker()}
        onClose={() => setPermPicker(false)}
        visibility={visibility()}
        onVisibilityChange={setVisibility}
      />

      <TootLanguagePickerDialog
        open={langPickerOpen()}
        onClose={() => setLangPickerOpen(false)}
        code={language()}
        onCodeChange={setLanguage}
      />
    </div>
  );
};

export default ReplyEditor;