import React, { useMemo } from "react";
import { Box, Text } from "ink";
import TextInput from "./TextInput.js";
import { useSatoshisConversion } from "../hooks/useSatoshisConversion.js";

interface VariableInputFieldProps {
  variable: {
    id: string;
    name: string;
    type: string;
    hint?: string;
    value: string;
  };
  index: number;
  isFocused: boolean;
  onChange: (index: number, value: string) => void;
  onSubmit: () => void;
  borderColor: string;
  focusColor: string;
}

const SATOSHIS_PER_BCH = 100_000_000n;

/**
 * Returns true when the variable is an integer satoshis field.
 */
function isSatoshisVariable(variable: VariableInputFieldProps["variable"]): boolean {
  return (
    variable.type === "integer" &&
    variable.hint?.toLowerCase().includes("satoshi") === true
  );
}

/**
 * Parse a strict integer string into bigint.
 */
function parseSatoshis(value: string): bigint | null {
  const trimmed = value.trim();
  if (!/^[-]?\d+$/.test(trimmed)) {
    return null;
  }

  try {
    return BigInt(trimmed);
  } catch {
    return null;
  }
}

/**
 * Format satoshis as BCH with fixed 8 decimals, preserving bigint precision.
 */
function formatBchFromSatoshis(satoshis: bigint): string {
  const sign = satoshis < 0n ? "-" : "";
  const absolute = satoshis < 0n ? satoshis * -1n : satoshis;
  const whole = absolute / SATOSHIS_PER_BCH;
  const fractional = absolute % SATOSHIS_PER_BCH;
  return `${sign}${whole.toString()}.${fractional.toString().padStart(8, "0")} BCH`;
}

export function VariableInputField({
  variable,
  index,
  isFocused,
  onChange,
  onSubmit,
  borderColor,
  focusColor,
}: VariableInputFieldProps): React.ReactElement {
  const { currencyCode, formattedFiatPerBchRate, formatSatoshisToFiat } =
    useSatoshisConversion();
  const satoshisValue = useMemo(
    () => parseSatoshis(variable.value),
    [variable.value],
  );
  const formattedBch = useMemo(() => {
    if (satoshisValue === null) {
      return null;
    }
    return formatBchFromSatoshis(satoshisValue);
  }, [satoshisValue]);
  const formattedFiat = useMemo(() => {
    if (satoshisValue === null) {
      return null;
    }
    return formatSatoshisToFiat(satoshisValue);
  }, [satoshisValue, formatSatoshisToFiat]);
  const shouldShowSatoshisConversion = isSatoshisVariable(variable);

  return (
    <Box flexDirection="column" marginBottom={1}>
      <Text color={focusColor}>{variable.name}</Text>
      {variable.hint && (
        <Text color={borderColor} dimColor>
          ({variable.hint})
        </Text>
      )}
      <Box
        borderStyle="single"
        borderColor={isFocused ? focusColor : borderColor}
        paddingX={1}
        marginTop={1}
        gap={1}
      >
        <TextInput
          value={variable.value}
          onChange={(value) => onChange(index, value)}
          onSubmit={onSubmit}
          focus={isFocused}
          placeholder={`Enter ${variable.name}...`}
        />

        {/* TODO: this may need to be conditional. Need to play around with other templates though */}
        <Text color={borderColor} dimColor>{variable.hint}</Text>
        
      </Box>
      {shouldShowSatoshisConversion && (
        <Box flexDirection="column">
          {formattedBch ? (
            <>
              <Text color={borderColor} dimColor>
                {formattedBch}
              </Text>
              <Text color={borderColor} dimColor>
                {formattedFiat
                  ? `Approx. ${currencyCode}: ${formattedFiat}`
                  : `Approx. ${currencyCode}: waiting for live rate...`}
              </Text>
              {formattedFiatPerBchRate && (
                <Text color={borderColor} dimColor>
                  1 BCH = {formattedFiatPerBchRate}
                </Text>
              )}
            </>
          ) : (
            <Text color={borderColor} dimColor>
              Enter a whole satoshi amount to preview BCH/{currencyCode} conversion.
            </Text>
          )}
        </Box>
      )}
    </Box>
  );
}