local lastNotBehindTarget = 0
local lastNotFacingTarget = 0
local lastNotInRange = 0
local lastPetNotInRange = 0
local lastNothingToFetch = 0
local isMoving, lastMoved = false, 0
local isTurning, lastTurned = false, 0
local playerX, playerY, lastPlayerX, lastPlayerY
local facing, lastFacing
local events = {}
local following = false

function events:UI_ERROR_MESSAGE(message)
	if message == "You must be behind your target." then
		lastNotBehindTarget = GetTime()
	elseif message == "You are facing the wrong way!" then
		lastNotFacingTarget = GetTime()
	elseif message == "You are too far away!" then
		lastNotInRange = GetTime()
	elseif message == "Your Pet is out of range of the target." then
		lastPetNotInRange = GetTime()
	elseif message == "There is nothing to be fetched." then
		lastNothingToFetch = GetTime()
	end
end	
function events:AUTOFOLLOW_BEGIN()
	following = true
end	
function events:AUTOFOLLOW_END()
	following = false
end	

local function EventFunc(self, event, ...)
	events[event](event, ...)
end
local eventHandler = CreateFrame("Frame", nil, WorldFrame)
eventHandler:SetScript("OnEvent", EventFunc)
for eventname in pairs(events) do eventHandler:RegisterEvent(eventname) end	


eventHandler:SetScript("OnUpdate", function()
	if not WorldMapFrame:IsVisible() then
		lastPlayerX, lastPlayerY = playerX, playerY
		playerX, playerY = GetPlayerMapPosition("player")
		isMoving = playerX ~= lastPlayerX or playerY ~= lastPlayerY
		if isMoving then
			lastMoved = GetTime()
		end
	end
	
	lastFacing = facing
	facing = GetPlayerFacing()
	isTurning = facing ~= lastFacing
	if isTurning then
		lastTurned = GetTime()
	end
end)

WhatsNext:AddConditionalStatement("Following",{
	category="Position / Rotation",
	test = function(checkTable) 
		return following
	end,
	text = function(checkTable) 
		return "player is set to follow another unit."
	end,
	arguments = {}
})
WhatsNext:AddConditionalStatement("In Range",{
	category="Position / Rotation",
	test = function(checkTable) 
		--print(checkTable.unit .. " " .. LibStub("SpellRange-1.0").IsSpellInRange("Shear", "target") ==1 )
		return UnitName(tostring(checkTable.unit)) and LibStub("SpellRange-1.0").IsSpellInRange(WN_GetSpellName(checkTable.spellName), "target") == 1
	end,
	text = function(checkTable) 
		return GetUnitDisplayText(checkTable.unit) .. " is a valid target for and is within range of " .. WN_GetSpellName(checkTable.spellName) .. "."
	end,
	arguments = {
		spellName = {type = "spell", default = ""},
		unit = {type = "dropdown", default = "target", possibleValues = WhatsNext.valueLists.unitAny},
	}
})
WhatsNext:AddConditionalStatement("Target In 9.9 Yards",{
	category="Position / Rotation",
	test = function(checkTable) 
		return UnitName(tostring(checkTable.unit)) and CheckInteractDistance(tostring(checkTable.unit), 3)
	end,
	text = function(checkTable) 
		return GetUnitDisplayText(checkTable.unit) .. " is within  9.9 yards."
	end,
	arguments = {
		unit = {type = "dropdown", default = "target", possibleValues = WhatsNext.valueLists.unitAny},
	}
})
WhatsNext:AddConditionalStatement("Target In 11.11 Yards",{
	category="Position / Rotation",
	test = function(checkTable) 
		return UnitName(tostring(checkTable.unit)) and CheckInteractDistance(tostring(checkTable.unit), 2)
	end,
	text = function(checkTable) 
		return GetUnitDisplayText(checkTable.unit) .. " is within 11.11 yards."
	end,
	arguments = {
		unit = {type = "dropdown", default = "target", possibleValues = WhatsNext.valueLists.unitAny},
	}
})
WhatsNext:AddConditionalStatement("Target In 28 Yards",{
	category="Position / Rotation",
	test = function(checkTable) 
		return UnitName(tostring(checkTable.unit)) and CheckInteractDistance(tostring(checkTable.unit), 1)
	end,
	text = function(checkTable) 
		return GetUnitDisplayText(checkTable.unit) .. " is within 28 yards."
	end,
	arguments = {
		unit = {type = "dropdown", default = "target", possibleValues = WhatsNext.valueLists.unitAny},
	}
})
WhatsNext:AddConditionalStatement("Not Behind Target Detected",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastNotBehindTarget <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "has been detected player was not behind their target in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Not Facing Target Detected",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastNotFacingTarget <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "has been detected player was not facing their target in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Not In Range Detected",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastNotInRange <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "has been detected player was too far away from their target in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Pet Not In Range Detected",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastPetNotInRange <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "has been detected pet was too far away from their target in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Nothing To Be Fetched Detected",{
	category="Hunter",
	test = function(checkTable) 
		return GetTime() - lastNothingToFetch <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "has been detected pet has nothing to fetch in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Not Behind Target Detected Since Moving/Turning",{
	category="Position / Rotation",
	test = function(checkTable) 
		return  lastNotBehindTarget > lastMoved  and lastNotBehindTarget > lastTurned
	end,
	text = function(checkTable) 
		return "has been detected player was not behind their target since last moving or turning."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Not Facing Target Detected Since Moving/Turning",{
	category="Position / Rotation",
	test = function(checkTable) 
		return  lastNotFacingTarget > lastMoved and lastNotFacingTarget > lastTurned
	end,
	text = function(checkTable) 
		return "has been detected player was not facing their target since last moving or turning."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Not In Range Detected Since Moving/Turning",{
	category="Position / Rotation",
	test = function(checkTable) 
		return  lastNotInRange > lastMoved and lastNotInRange > lastTurned
	end,
	text = function(checkTable) 
		return "has been detected player was too far away from their target since last moving or turning."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Moved",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastMoved <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "player has moved in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Turned",{
	category="Position / Rotation",
	test = function(checkTable) 
		return GetTime() - lastTurned <= tonumber(checkTable.time)
	end,
	text = function(checkTable) 
		return "player has turned in the last " .. tostring(checkTable.time) .. " seconds."
	end,
	arguments = {
		time = {type = "integer", default = 0},
	}
})
WhatsNext:AddConditionalStatement("Moving",{
	category="Position / Rotation",
	test = function(checkTable)
		return isMoving
	end,
	text = function(checkTable)
		return "player is moving."
	end,
	arguments = {}
})
WhatsNext:AddConditionalStatement("Turning",{
	category="Position / Rotation",
	test = function(checkTable)
		return isTurning
	end,
	text = function(checkTable)
		return "player is turning."
	end,
	arguments = {}
})