package content.region.morytania.handlers

import core.api.*
import content.global.skill.agility.AgilityHandler
import core.game.system.task.Pulse
import core.game.world.map.Location
import core.game.world.update.flag.context.Animation
import core.game.world.update.flag.context.Graphics
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.launch
import org.rs09.consts.NPCs
import org.rs09.consts.Scenery
import core.game.interaction.InteractionListener
import core.game.interaction.IntType
import kotlin.random.Random
import content.data.Quests
import core.game.interaction.InterfaceListener
import org.rs09.consts.Components

/**
 * File to be used for anything Morytania related.
 * Handles the summoning/altar cave enter and exit in Morytania.
 * @author Sir Kermit
 */

class MorytaniaListeners : InteractionListener {

    val SWAMP_GATES = intArrayOf(Scenery.GATE_3506, Scenery.GATE_3507)
    val GROTTO_EXIT = intArrayOf(3525, 3526)
    val GROTTO_BRIDGE = 3522
    val outside = Location.create(3439, 3337, 0)
    val inside = Location.create(3442, 9734, 1)

    private val swimAnim = Animation(6988)
    private val jumpAnim = Animation(1603)
    private val failWater = Location(3439,3330)
    private val failMessage = "You nearly drown in the disgusting swamp."
    private val splashGFX = Graphics(68)

    override fun defineListeners() {

        on(SWAMP_GATES, IntType.SCENERY, "open"){ player, node ->
            if(player.location.y == 3457){
                core.game.global.action.DoorActionHandler.handleAutowalkDoor(player, node.asScenery())
                sendMessage(player, "You skip gladly out of murky Mort Myre.")
                removeTimer<SwampDecayTimer>(player)
                GlobalScope.launch {
                    findLocalNPC(player, NPCs.ULIZIUS_1054)?.sendChat("Oh my! You're still alive!", 2)
                }
            } else {
                if (player.questRepository.hasStarted(Quests.NATURE_SPIRIT)) {
                    setAttribute(player, "swampgate", node)
                    openInterface(player, Components.CWS_WARNING_20_580)
                } else {
                    sendNPCDialogue(
                        player,
                        NPCs.ULIZIUS_1054,
                        "I'm sorry, but I'm afraid it's too dangerous to let you through this gate right now."
                    )
                }
            }
            return@on true
        }

        on(GROTTO_EXIT, IntType.SCENERY, "exit"){ player, node ->
            player.teleport(outside)
            return@on true
        }

        on(GROTTO_BRIDGE, IntType.SCENERY, "jump"){ player, node ->
            val start = node.location
            var failLand = Location(3438,3331)
            var failAnim = Animation(770)
            var fromGrotto = false

            lock(player,10)

            // Switch to south facing animations if jumping from Grotto
            if (start.y == 3331) {
                fromGrotto = true
                failAnim = Animation(771)
                failLand = Location(3438,3328)
            }
            if (AgilityHandler.hasFailed(player, 1, 0.1)) {
                val end = if (fromGrotto) failWater else start
                AgilityHandler.forceWalk(player, -1, start, end, failAnim, 15, 0.0, null,0).endAnimation = swimAnim
                AgilityHandler.forceWalk(player, -1, failWater, failLand, swimAnim, 15, 2.0, null,3)
                submitIndividualPulse(player, object : Pulse(2){
                    override fun pulse(): Boolean {
                        visualize(player,failAnim,splashGFX)
                        teleport(player,failWater)
                        // Deal 1-6 damage but wait until the player is back on land
                        AgilityHandler.fail(player,0,failLand,swimAnim,Random.nextInt(1,7),failMessage)
                        return true
                    }
                })
            }
            else{
                val end = if (fromGrotto) start.transform(0,-3,0) else start.transform(0,3,0)
                AgilityHandler.forceWalk(player, -1, start, end, jumpAnim, 15, 15.0, null,0)
            }
            return@on true
        }
    }
}

class warningInterface : InterfaceListener {
    override fun defineInterfaceListeners() {
        on(Components.CWS_WARNING_20_580) { player, _, _, buttonID, _, _ ->
            when(buttonID) {
                17 -> {
                    val gate = getAttribute(player, "swampgate", null) as? core.game.node.scenery.Scenery
                    if (gate != null) {
                        core.game.global.action.DoorActionHandler.handleAutowalkDoor(player, gate)
                        sendMessage(player, "You walk into the gloomy atmosphere of Mort Myre.")
                    }
                    closeInterface(player)
                }
                18 -> closeInterface(player)
            }
            removeAttribute(player, "swampgate")
            return@on true
        }
    }
}