// SPDX-License-Identifier: LGPL-3.0-or-later

import QtQuick 2.12
import QtQuick.Layouts 1.12
import "../../.."
import "../../../Base"
import "../../../Base/HTile"

// FIXME: a b -> a @p b → @p doesn't trigger completion
// FIXME: close autocomplete when cursor moves away
HListView {
    id: root

    property HTextArea textArea
    property bool open: false

    property string originalText: ""
    property bool autoOpenCompleted: false
    property var usersCompleted: ({})  // {displayName: userId}

    readonly property bool autoOpen:
        autoOpenCompleted || textArea.text.match(/.*(^|\W)@[^\s]+$/)

    readonly property string wordToComplete:
        open ?
        (originalText || textArea.text).split(/\s/).slice(-1)[0].replace(
            autoOpen ? /^@/ : "", "",
        ) :
        ""

    function replaceLastWord(withText) {
        let lastWordStart = /(?:^|\s)[^\s]+$/.exec(textArea.text).index

        if (! (lastWordStart === 0 && ! textArea.text[0].match(/\s/)))
            lastWordStart += 1

        textArea.remove(lastWordStart, textArea.length)
        textArea.insertAtCursor(withText)
    }

    function previous() {
        if (open) {
            decrementCurrentIndex()
            return
        }

        open = true
        const args = [model.modelId, wordToComplete]
        py.callCoro("set_string_filter", args, decrementCurrentIndex)
    }

    function next() {
        if (open) {
            incrementCurrentIndex()
            return
        }

        open = true
        const args = [model.modelId, wordToComplete]
        py.callCoro("set_string_filter", args, incrementCurrentIndex)
    }

    function accept() {
        if (currentIndex !== -1) {
            const member = model.get(currentIndex)
            usersCompleted[member.display_name] = member.id
            usersCompletedChanged()
        }

        open = false
    }

    function cancel() {
        if (originalText)
            replaceLastWord(originalText.split(/\s/).splice(-1)[0])

        currentIndex = -1
        open         = false
    }


    visible: opacity > 0
    opacity: open && count ? 1 : 0
    implicitHeight: open && count ? Math.min(window.height, contentHeight) : 0
    model: ModelStore.get(chat.userId, chat.roomId, "autocompleted_members")

    delegate: HTile {
        width: root.width
        contentItem: HLabel { text: model.display_name + " (" + model.id + ")"}
        onClicked: {
            currentIndex = model.index
            root.open    = false
        }
    }

    onCountChanged: if (! count && open) open = false
    onAutoOpenChanged: open = autoOpen
    onOpenChanged: if (! open) {
        originalText      = ""
        currentIndex      = -1
        autoOpenCompleted = false
        py.callCoro("set_string_filter", [model.modelId, ""])
    }

    onWordToCompleteChanged: {
        if (! open) return
        py.callCoro("set_string_filter", [model.modelId, wordToComplete])
    }

    onCurrentIndexChanged: {
        if (currentIndex === -1) return
        if (! originalText) originalText = textArea.text
        if (autoOpen) autoOpenCompleted = true

        replaceLastWord(model.get(currentIndex).display_name)
    }

    Behavior on opacity { HNumberAnimation {} }
    Behavior on implicitHeight { HNumberAnimation {} }

    Connections {
        target: root.textArea

        function onTextChanged() {
            let changed = false

            for (const displayName of Object.keys(root.usersCompleted)) {
                if (! root.textArea.text.includes(displayName)) {
                    delete root.usersCompleted[displayName]
                    changed = true
                }
            }

            if (changed) root.usersCompletedChanged()
        }
    }
}