-
-
Notifications
You must be signed in to change notification settings - Fork 7
Expand file tree
/
Copy pathChatCompat.lua
More file actions
155 lines (139 loc) · 6.3 KB
/
ChatCompat.lua
File metadata and controls
155 lines (139 loc) · 6.3 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
---------------------------------------------------------------------
-- ChatCompat.lua
-- Abstraction layer for Retail / Classic Chat APIs
-- Updated for Patch 12.0.0 (Midnight)
--
-- Purpose:
-- Unifies access to Chat APIs across all WoW versions
-- (Retail 12.0+, Classic Era, Burning Crusade, Wrath, Cataclysm)
---------------------------------------------------------------------
local ChatCompat = {}
---------------------------------------------------------------------
-- API Detection
---------------------------------------------------------------------
local function detectApi()
-- Since 12.0.0, always use C_ChatInfo.SendChatMessage
-- The old global SendChatMessage is deprecated but still available via fallback
local hasCChatInfo = type(C_ChatInfo) == "table"
and type(C_ChatInfo.SendChatMessage) == "function"
-- INSTANCE_CHAT is available in Retail and Wrath+
local supportsInstanceChat = ChatTypeInfo and ChatTypeInfo["INSTANCE_CHAT"] ~= nil
return {
useCChatInfo = hasCChatInfo,
supportsInstanceChat = supportsInstanceChat,
}
end
ChatCompat.api = detectApi()
---------------------------------------------------------------------
-- Unified SendChatMessage Wrapper
-- Sends a message via the correct API endpoint
--
-- Note: SendChatMessage is deprecated in Retail 12.0+ but still available
-- via Deprecated_ChatInfo.lua fallback. In Classic variants, it's the
-- primary API and not deprecated.
---------------------------------------------------------------------
function ChatCompat:Send(msg, chatType, language, channel)
if self.api.useCChatInfo then
-- Retail / Wrath Classic (12.0+: use C_ChatInfo.SendChatMessage)
return C_ChatInfo.SendChatMessage(msg, chatType, language, channel)
else
-- Classic Era / Burning Crusade / Cataclysm Classic
-- SendChatMessage is NOT deprecated in these versions
return SendChatMessage(msg, chatType, language, channel)
end
end
---------------------------------------------------------------------
-- Unified Hook Registration
-- AceHook-compatible
--
-- NOTE: Hooking SendChatMessage is problematic in modern WoW because
-- it's a protected function that can only be called by Blizzard code
-- in response to hardware events. Attempting to call it from within
-- a hook will trigger ADDON_ACTION_FORBIDDEN errors.
--
-- WARNING: Even hooking ChatEdit_SendText can cause issues in protected
-- environments (M+, raids, PvP) because calling the original function
-- will still trigger SendChatMessage internally.
--
-- PATCH 12.0.0 CHANGES:
-- - ChatEdit_SendText is now deprecated (but still available via fallback)
-- - New addon chat restrictions via CVar 'addonChatRestrictionsForced'
-- - New enum Enum.SendAddonMessageResult.AddOnMessageLockdown
-- - Event ADDON_RESTRICTION_STATE_CHANGED notifies when restrictions change
-- - "Secret Values" system can restrict addon operations on tainted paths
--
-- RECOMMENDED: Use direct text modification on the EditBox BEFORE
-- ChatEdit_SendText is called. This is the most compatible approach:
--
-- Example:
-- local origChatEdit_SendText = ChatEdit_SendText
-- ChatEdit_SendText = function(editBox, addHistory)
-- -- Modify editBox:GetText() and editBox:SetText() here
-- origChatEdit_SendText(editBox, addHistory)
-- end
--
-- This function is kept for backwards compatibility but is not recommended.
-- addon = your AceAddon with RawHook method
---------------------------------------------------------------------
function ChatCompat:HookSendChatMessage(addon)
if self.api.useCChatInfo then
-- Retail / Wrath Classic: Hook the C_ChatInfo.SendChatMessage
addon:RawHook(C_ChatInfo, "SendChatMessage", true)
else
-- Classic Era / TBC / Cata: Hook the global SendChatMessage
addon:RawHook("SendChatMessage", true)
end
end
---------------------------------------------------------------------
-- Unified Unhook
---------------------------------------------------------------------
function ChatCompat:UnhookSendChatMessage(addon)
if self.api.useCChatInfo then
addon:Unhook(C_ChatInfo, "SendChatMessage")
else
addon:Unhook("SendChatMessage")
end
end
---------------------------------------------------------------------
-- Helper: Is this chat type supported by this version?
--
-- Uses config to check if the chat type is enabled
-- Considers Classic limitations (e.g., no INSTANCE_CHAT)
---------------------------------------------------------------------
function ChatCompat:IsSupportedChatType(chatType, config)
if chatType == "SAY" and config.say then return true end
if chatType == "YELL" and config.yell then return true end
if chatType == "WHISPER" and config.whisper then return true end
if chatType == "GUILD" and config.guild then return true end
if chatType == "OFFICER" and config.officer then return true end
if chatType == "PARTY" and config.party then return true end
if chatType == "RAID" and config.raid then return true end
if chatType == "PARTY_LEADER" and config.party_leader then return true end
if chatType == "RAID_LEADER" and config.raid_leader then return true end
if chatType == "RAID_WARNING" and config.raid_warning then return true end
-- INSTANCE_CHAT only on Retail/Wrath+
if chatType == "INSTANCE_CHAT" and config.instance_chat and self.api.supportsInstanceChat then
return true
end
return false
end
---------------------------------------------------------------------
-- Info: API Details (Debug)
---------------------------------------------------------------------
function ChatCompat:GetApiInfo()
return {
useCChatInfo = self.api.useCChatInfo,
supportsInstanceChat = self.api.supportsInstanceChat,
}
end
---------------------------------------------------------------------
-- Registration as LibStub for other addons
---------------------------------------------------------------------
local MAJOR, MINOR = "ChatCompat", 1
local ChatCompatLib = LibStub:NewLibrary(MAJOR, MINOR)
if not ChatCompatLib then return end
-- Copy all functions to the library table
for k, v in pairs(ChatCompat) do
ChatCompatLib[k] = v
end
return ChatCompatLib