Quantcast
local addon = CreateFrame'Frame'
local addonname = ...

local origs = {
	BNGetFriendInfo = BNGetFriendInfo,
	BNGetFriendInfoByID = BNGetFriendInfoByID,
	AddMessage = {}
}
local origname = ""

UnitPopupButtons["BN_RENAME"] = { text = PET_RENAME, dist = 0 }
table.insert(UnitPopupMenus["BN_FRIEND"], 7, "BN_RENAME")
table.insert(UnitPopupMenus["BN_FRIEND_OFFLINE"], 2, "BN_RENAME")

local function UpdateName(origname, name)
	if name == origname or #name == 0 then
		MonikerDB[origname] = nil
	else
		MonikerDB[origname] = name
	end

	FriendsFrame_Update()
end

local function GetNickname(origname)
	return MonikerDB[origname] or origname
end

local function ConvertLink(text)
	return text:gsub("|HBNplayer:(.-):(.-):(.-):(.-):(.-)|h%[(.+)%]|h", function(a1, a2, a3, a4, a5, a6)
		return ("|HBNplayer:%s:%s:%s:%s:%s|h[%s]|h"):format(a1, a2, a3, a4, a5, GetNickname(a6))
	end)
end

local function AddMessage(self, text, ...)
	return origs.AddMessage[self](self, ConvertLink(text), ...)
end

local function HookChatFrame(cf)
	if not origs.AddMessage[cf] then
		origs.AddMessage[cf] = cf.AddMessage
		cf.AddMessage = AddMessage
	end
end

StaticPopupDialogs["BN_RENAME_FRIEND"] = {
	text = "Enter desired name of RealID friend or leave it empty if you want to use the original name",
	button1 = ACCEPT,
	button2 = CANCEL,
	hasEditBox = 1,
	hideOnEscape = 1,
	timeout = 0,
	exclusive = 1,

	OnAccept = function(self)
		local name = self.editBox:GetText()
		UpdateName(origname, name)
	end,

	EditBoxOnEnterPressed = function(self)
		local parent = self:GetParent()
		local name = parent.editBox:GetText()

		UpdateName(origname, name)
		parent:Hide()
	end,

	OnShow = function(self)
		local name = MonikerDB[origname] or ""
		self.editBox:SetText(name)
		self.editBox:SetFocus()
	end,
}

addon:RegisterEvent'ADDON_LOADED'
addon:SetScript('OnEvent', function(self, e, addon)
	if addon ~= addonname then return end

	MonikerDB = MonikerDB or {}

	local env = setmetatable({}, {__index = _G})

	function env.BNGetFriendInfo(...)
		local pid, firstname, lastname = origs.BNGetFriendInfo(...)
		local name = firstname..' '..lastname

		if MonikerDB[name] then
			firstname = MonikerDB[name]
			lastname = ""
		end

		return pid, firstname, lastname, select(4, origs.BNGetFriendInfo(...))
	end

	function env.BNGetFriendInfoByID(...)
		local pid, firstname, lastname = origs.BNGetFriendInfoByID(...)
		local name = firstname..' '..lastname

		if MonikerDB[name] then
			firstname = MonikerDB[name]
			lastname = ""
		end

		return pid, firstname, lastname, select(4, origs.BNGetFriendInfoByID(...))
	end

	setfenv(FriendsList_Update, env)
	setfenv(FriendsFrame_SetButton, env)
	setfenv(FriendsFrameTooltip_Show, env)
	setfenv(BNToastFrame_Show, env)
	setfenv(BNet_InitiateReport, env)
	setfenv(StaticPopupDialogs["SET_BNFRIENDNOTE"].OnShow, env)
	setfenv(FriendsFriendsFrame_Show, env)
	setfenv(BNConversationInvite_Update, env)

	hooksecurefunc("UnitPopup_OnClick", function(self)
		local dropdown = UIDROPDOWNMENU_INIT_MENU;
		local button = self.value

		if button == "BN_RENAME" then
			local pid, firstname, lastname = origs.BNGetFriendInfoByID(dropdown.presenceID)
			local name = firstname..' '..lastname

			origname = name

			StaticPopup_Show"BN_RENAME_FRIEND"
		end
	end)

	hooksecurefunc("FCF_SetWindowName", function(frame, name, ...)
		HookChatFrame(frame)

		local tab = _G[frame:GetName().."Tab"]
		if tab then
			tab:SetText(GetNickname(name))
		end
	end)

	for i = 1, NUM_CHAT_WINDOWS do
		HookChatFrame(_G['ChatFrame'..i])
	end
end)