/*
    Предрейсовые осмотры - мобильное приложение
    Компонент модального окна с полем ввода
*/

//---------------------
//Подключение библиотек
//---------------------

const React = require('react'); //React
const { Modal, View, TextInput, Pressable, Platform, StyleSheet, BackHandler } = require('react-native'); //Базовые компоненты
const AppText = require('./AppText'); //Общий текстовый компонент
const AppButton = require('./AppButton'); //Кнопка
const styles = require('../../styles/common/InputDialog.styles'); //Стили диалога

const OVERLAY_Z = 9999;

//-----------
//Тело модуля
//-----------

//Модальное окно с полем ввода
function InputDialog(
    {
        visible,
        title = 'Ввод данных',
        label,
        value = '',
        placeholder,
        keyboardType = 'default',
        autoCapitalize = 'none',
        confirmText = 'Сохранить',
        cancelText = 'Отмена',
        onConfirm,
        onCancel,
        validator,
        errorMessage
    },
    ref
) {
    //Локальное значение для редактирования
    const [inputValue, setInputValue] = React.useState(value);
    const inputRef = React.useRef(null);
    //На Android поле ввода изначально не фокусируемо, чтобы нативный слой видел «нет фокуса» и перехватывал сканер с первого символа (как на остальных экранах)
    const [inputFocusable, setInputFocusable] = React.useState(Platform.OS !== 'android');

    const focusFirstEditableInput = React.useCallback(() => {
        if (inputRef.current && typeof inputRef.current.focus === 'function') {
            inputRef.current.focus();
        }
    }, []);

    React.useImperativeHandle(
        ref,
        function exposeScannerApi() {
            return {
                setValueFromScanner(val) {
                    setInputValue(val != null ? String(val) : '');
                    if (Platform.OS === 'android') setInputFocusable(true);
                    focusFirstEditableInput();
                }
            };
        },
        [focusFirstEditableInput]
    );

    //После включения фокусируемости на Android — ставим фокус на поле (после setValueFromScanner)
    React.useEffect(
        function focusWhenFocusable() {
            if (Platform.OS !== 'android' || !inputFocusable) return;
            focusFirstEditableInput();
        },
        [inputFocusable, focusFirstEditableInput]
    );
    const [error, setError] = React.useState('');
    const [isFocused, setIsFocused] = React.useState(false);

    //Сброс значения и фокусируемости только при открытии диалога
    const prevVisibleRef = React.useRef(false);
    React.useEffect(() => {
        const justOpened = visible && !prevVisibleRef.current;
        prevVisibleRef.current = visible;
        if (justOpened) {
            setInputValue(value);
            setError('');
            if (Platform.OS === 'android') setInputFocusable(false);
        }
    }, [visible, value]);

    //Кнопка «Назад» на Android при overlay (без Modal) закрывает диалог
    React.useEffect(
        function backHandler() {
            if (Platform.OS !== 'android' || !visible) return;
            const sub = BackHandler.addEventListener('hardwareBackPress', function onBack() {
                handleCancel();
                return true;
            });
            return function remove() {
                sub.remove();
            };
        },
        [visible, handleCancel]
    );

    //Обработчик фокуса
    const handleFocus = React.useCallback(() => {
        setIsFocused(true);
    }, []);

    //Обработчик потери фокуса
    const handleBlur = React.useCallback(() => {
        setIsFocused(false);
    }, []);

    //Обработчик изменения текста
    const handleChangeText = React.useCallback(text => {
        setInputValue(text);
        setError('');
    }, []);

    //Валидация введённого значения
    const validateInput = React.useCallback(() => {
        if (typeof validator === 'function') {
            const validationResult = validator(inputValue);
            if (validationResult !== true) {
                setError(validationResult || errorMessage || 'Некорректное значение');
                return false;
            }
        }
        return true;
    }, [inputValue, validator, errorMessage]);

    //Обработчик подтверждения
    const handleConfirm = React.useCallback(() => {
        if (!validateInput()) {
            return;
        }

        if (typeof onConfirm === 'function') {
            onConfirm(inputValue.trim());
        }
    }, [inputValue, validateInput, onConfirm]);

    //Обработчик отмены
    const handleCancel = React.useCallback(() => {
        if (typeof onCancel === 'function') {
            onCancel();
        }
    }, [onCancel]);

    //Обработчик закрытия по кнопке "Назад" (Android)
    const handleRequestClose = React.useCallback(() => {
        handleCancel();
    }, [handleCancel]);

    const preventKeyActions = Platform.OS === 'android';
    const closePressableProps = preventKeyActions ? { focusable: false } : {};
    const cancelButtonFocusable = preventKeyActions ? false : undefined;
    const confirmButtonFocusable = preventKeyActions ? false : undefined;

    const dialogContent = (
        <View style={styles.container}>
            <View style={styles.header}>
                <AppText style={styles.title}>{title}</AppText>
                <Pressable
                    accessibilityRole="button"
                    accessibilityLabel="Закрыть"
                    onPress={handleCancel}
                    style={styles.closeButton}
                    {...closePressableProps}
                >
                    <AppText style={styles.closeButtonText}>×</AppText>
                </Pressable>
            </View>

            <View style={styles.content}>
                {label ? (
                    <AppText style={styles.label} variant="caption" weight="medium">
                        {label}
                    </AppText>
                ) : null}

                <TextInput
                    ref={inputRef}
                    style={[styles.input, isFocused && styles.inputFocused, error && styles.inputError]}
                    value={inputValue}
                    onChangeText={handleChangeText}
                    placeholder={placeholder}
                    placeholderTextColor={styles.placeholder.color}
                    keyboardType={keyboardType}
                    autoCapitalize={autoCapitalize}
                    multiline={true}
                    onFocus={handleFocus}
                    onBlur={handleBlur}
                    autoFocus={Platform.OS !== 'android'}
                    focusable={Platform.OS !== 'android' || inputFocusable}
                    selectTextOnFocus={true}
                    accessible={true}
                    accessibilityLabel={label || placeholder}
                    accessibilityRole="text"
                />

                {error ? (
                    <AppText style={styles.errorText} variant="caption">
                        {error}
                    </AppText>
                ) : null}
            </View>

            <View style={styles.buttonsRow}>
                <AppButton
                    title={cancelText}
                    onPress={handleCancel}
                    style={styles.cancelButton}
                    textStyle={styles.cancelButtonText}
                    focusable={cancelButtonFocusable}
                />
                <AppButton title={confirmText} onPress={handleConfirm} style={styles.confirmButton} focusable={confirmButtonFocusable} />
            </View>
        </View>
    );

    if (!visible) return null;

    if (Platform.OS === 'android') {
        return (
            <View style={[StyleSheet.absoluteFill, { zIndex: OVERLAY_Z, elevation: OVERLAY_Z }]} pointerEvents="auto">
                <View style={styles.backdrop} pointerEvents="auto">
                    {dialogContent}
                </View>
            </View>
        );
    }

    return (
        <Modal transparent={true} animationType="fade" statusBarTranslucent={true} visible={true} onRequestClose={handleRequestClose}>
            <View style={styles.backdrop}>{dialogContent}</View>
        </Modal>
    );
}

//----------------
//Интерфейс модуля
//----------------

module.exports = React.forwardRef(InputDialog);
