import { useState } from 'react';
import type { ReactElement } from 'react';
import {
  ActivityIndicator,
  KeyboardAvoidingView,
  Platform,
  Pressable,
  StyleSheet,
  Text,
  TextInput,
  View,
} from 'react-native';
import { ApiError } from '@altricade/core/api';
import { useSession } from '@/stores/session';
import { Screen } from '@/components';
import { useTheme } from '@/theme';
import { spacing, radius, fontSize } from '@/theme';

type Mode = 'login' | 'register';

export const SignInScreen = (): ReactElement => {
  const { colors } = useTheme();
  const login = useSession((s) => s.login);
  const register = useSession((s) => s.register);

  const [mode, setMode] = useState<Mode>('login');
  const [username, setUsername] = useState('');
  const [displayName, setDisplayName] = useState('');
  const [password, setPassword] = useState('');
  const [error, setError] = useState<string | null>(null);
  const [busy, setBusy] = useState(false);

  const submit = (): void => {
    setBusy(true);
    setError(null);
    void (async () => {
      try {
        if (mode === 'login') {
          await login({ username: username.trim(), password });
        } else {
          await register({ username: username.trim(), displayName: displayName.trim(), password });
        }
      } catch (caught) {
        setError(caught instanceof ApiError ? caught.message : 'Something went wrong');
        setBusy(false);
      }
    })();
  };

  const inputStyle = [styles.input, { backgroundColor: colors.surface, color: colors.text }];

  return (
    <Screen>
      <KeyboardAvoidingView
        behavior={Platform.OS === 'ios' ? 'padding' : undefined}
        style={styles.flex}
      >
        <View style={styles.center}>
          <View style={[styles.mark, { backgroundColor: colors.accent }]}>
            <Text style={[styles.markText, { color: colors.onAccent }]}>Z</Text>
          </View>
          <Text style={[styles.title, { color: colors.text }]}>Zovi</Text>
          <Text style={[styles.tagline, { color: colors.textMuted }]}>
            {mode === 'login' ? 'Welcome back.' : 'Create your account.'}
          </Text>

          <TextInput
            style={inputStyle}
            placeholder="Username"
            placeholderTextColor={colors.textFaint}
            autoCapitalize="none"
            autoCorrect={false}
            value={username}
            onChangeText={setUsername}
          />
          {mode === 'register' ? (
            <TextInput
              style={inputStyle}
              placeholder="Display name"
              placeholderTextColor={colors.textFaint}
              value={displayName}
              onChangeText={setDisplayName}
            />
          ) : null}
          <TextInput
            style={inputStyle}
            placeholder="Password"
            placeholderTextColor={colors.textFaint}
            secureTextEntry
            value={password}
            onChangeText={setPassword}
          />

          {error !== null ? <Text style={[styles.error, { color: colors.danger }]}>{error}</Text> : null}

          <Pressable
            style={[styles.primary, { backgroundColor: colors.accent }, busy && { opacity: 0.6 }]}
            disabled={busy}
            onPress={submit}
          >
            {busy ? (
              <ActivityIndicator color={colors.onAccent} />
            ) : (
              <Text style={[styles.primaryText, { color: colors.onAccent }]}>
                {mode === 'login' ? 'Log in' : 'Create account'}
              </Text>
            )}
          </Pressable>

          <Pressable
            onPress={() => {
              setMode(mode === 'login' ? 'register' : 'login');
              setError(null);
            }}
          >
            <Text style={[styles.switch, { color: colors.accent }]}>
              {mode === 'login' ? 'Need an account? Sign up' : 'Have an account? Log in'}
            </Text>
          </Pressable>
        </View>
      </KeyboardAvoidingView>
    </Screen>
  );
};

const styles = StyleSheet.create({
  flex: { flex: 1 },
  center: { flex: 1, justifyContent: 'center', paddingHorizontal: spacing.xl },
  mark: {
    width: 56,
    height: 56,
    borderRadius: 18,
    alignItems: 'center',
    justifyContent: 'center',
    alignSelf: 'center',
    marginBottom: spacing.md,
  },
  markText: { fontSize: 28, fontWeight: '800' },
  title: { fontSize: 28, fontWeight: '700', textAlign: 'center' },
  tagline: { textAlign: 'center', marginTop: spacing.xs, marginBottom: spacing.xl },
  input: {
    borderRadius: radius.md,
    paddingHorizontal: spacing.lg,
    paddingVertical: spacing.md,
    fontSize: fontSize.base,
    marginBottom: spacing.md,
  },
  error: { fontSize: fontSize.sm, marginBottom: spacing.sm },
  primary: {
    borderRadius: radius.md,
    paddingVertical: spacing.md,
    alignItems: 'center',
    marginTop: spacing.xs,
  },
  primaryText: { fontSize: fontSize.md, fontWeight: '600' },
  switch: { textAlign: 'center', marginTop: spacing.xl, fontWeight: '600' },
});
