// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
import React, {useState, useRef, useEffect, useMemo} from 'react'
import {useRouteMatch} from 'react-router-dom'
import {useIntl} from 'react-intl'
import {useHotkeys} from 'react-hotkeys-hook'
import {debounce} from 'lodash'

import CompassIcon from '../../widgets/icons/compassIcon'
import Editable from '../../widgets/editable'

import {useAppSelector, useAppDispatch} from '../../store/hooks'
import {getSearchText, setSearchText} from '../../store/searchText'

const ViewHeaderSearch = (): JSX.Element => {
    const searchText = useAppSelector<string>(getSearchText)
    const dispatch = useAppDispatch()
    const intl = useIntl()
    const match = useRouteMatch<{viewId?: string}>()

    const searchFieldRef = useRef<{focus(selectAll?: boolean): void}>(null)
    const [searchValue, setSearchValue] = useState(searchText)
    const [currentView, setCurrentView] = useState(match.params?.viewId)

    const dispatchSearchText = (value: string) => {
        dispatch(setSearchText(value))
    }

    const debouncedDispatchSearchText = useMemo(
        () => debounce(dispatchSearchText, 200), [])

    useEffect(() => {
        const viewId = match.params?.viewId
        if (viewId !== currentView) {
            setCurrentView(viewId)
            setSearchValue('')

            // Previously debounced calls to change the search text should be cancelled
            // to avoid resetting the search text.
            debouncedDispatchSearchText.cancel()
            dispatchSearchText('')
        }
    }, [match.url])

    useEffect(() => {
        return () => {
            debouncedDispatchSearchText.cancel()
        }
    }, [])

    useHotkeys('ctrl+shift+f,cmd+shift+f', () => {
        searchFieldRef.current?.focus(true)
    })

    return (
        <div className='board-search-field'>
            <CompassIcon
                icon='magnify'
                className='board-search-icon'
            />
            <Editable
                ref={searchFieldRef}
                value={searchValue}
                placeholderText={intl.formatMessage({id: 'ViewHeader.search-text', defaultMessage: 'Search cards'})}
                onChange={(value) => {
                    setSearchValue(value)
                    debouncedDispatchSearchText(value)
                }}
                onCancel={() => {
                    setSearchValue('')
                    debouncedDispatchSearchText('')
                }}
                onSave={() => {
                    debouncedDispatchSearchText(searchValue)
                }}
            />
        </div>
    )
}

export default ViewHeaderSearch
