675 lines
18 KiB
Lua
675 lines
18 KiB
Lua
|
--#################################################
|
|||
|
-- Main frame
|
|||
|
--#################################################
|
|||
|
|
|||
|
---------------------------------------------------
|
|||
|
-- FONTS
|
|||
|
---------------------------------------------------
|
|||
|
|
|||
|
surface.CreateFont("cats.small", {
|
|||
|
font = "Roboto Bold",
|
|||
|
extended = true,
|
|||
|
size = 16,
|
|||
|
weight = 500,
|
|||
|
})
|
|||
|
surface.CreateFont("cats.small-underline", {
|
|||
|
font = "Roboto Bold",
|
|||
|
extended = true,
|
|||
|
underline = true,
|
|||
|
size = 16,
|
|||
|
weight = 500,
|
|||
|
})
|
|||
|
|
|||
|
---------------------------------------------------
|
|||
|
-- HELPER FUNCTIONS
|
|||
|
---------------------------------------------------
|
|||
|
|
|||
|
-- apply table to action button
|
|||
|
local buttons -- declare here, fill later
|
|||
|
local function applyButton(pnl, name, ply, steamID)
|
|||
|
local data = buttons[name]
|
|||
|
if not data then data = {
|
|||
|
tooltip = 'error',
|
|||
|
icon = Material(octolib.icons.silk16('error')),
|
|||
|
click = function() end
|
|||
|
} end
|
|||
|
|
|||
|
pnl:SetToolTip(data.tooltip)
|
|||
|
pnl.icon = data.icon
|
|||
|
pnl.DoClick = function(self) data.click(self, ply, steamID) end
|
|||
|
end
|
|||
|
|
|||
|
-- nice time
|
|||
|
local function niceTime(time)
|
|||
|
|
|||
|
local h, m, s
|
|||
|
h = math.floor(time / 60 / 60)
|
|||
|
m = math.floor(time / 60) % 60
|
|||
|
s = math.floor(time) % 60
|
|||
|
|
|||
|
return string.format("%02i:%02i:%02i", h, m, s)
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
---------------------------------------------------
|
|||
|
-- CACHE
|
|||
|
---------------------------------------------------
|
|||
|
|
|||
|
-- icons cache
|
|||
|
local icons = {
|
|||
|
action_claim = Material(octolib.icons.silk16('accept_button')),
|
|||
|
action_unclaim = Material(octolib.icons.silk16('cancel')),
|
|||
|
actions = Material(octolib.icons.silk16('text_list_bullets')),
|
|||
|
action_callon = Material(octolib.icons.silk16('lightbulb_off')),
|
|||
|
action_calloff = Material(octolib.icons.silk16('lightbulb')),
|
|||
|
action_close = Material(octolib.icons.silk16('application_form_delete')),
|
|||
|
noStar = Material(octolib.icons.silk16('bullet_white')),
|
|||
|
star = Material(octolib.icons.silk16('star')),
|
|||
|
}
|
|||
|
|
|||
|
-- button tables
|
|||
|
buttons = {
|
|||
|
action_claim = {
|
|||
|
tooltip = cats.lang.action_claim,
|
|||
|
icon = icons.action_claim,
|
|||
|
click = function(self, ply, steamID)
|
|||
|
netstream.Start('cats.claimTicket', steamID, true)
|
|||
|
applyButton(self, 'action_unclaim', ply, steamID)
|
|||
|
end
|
|||
|
},
|
|||
|
action_unclaim = {
|
|||
|
tooltip = cats.lang.action_unclaim,
|
|||
|
icon = icons.action_unclaim,
|
|||
|
click = function(self, ply, steamID)
|
|||
|
netstream.Start('cats.claimTicket', steamID, false)
|
|||
|
applyButton(self, 'action_claim', ply, steamID)
|
|||
|
end
|
|||
|
},
|
|||
|
actions = {
|
|||
|
tooltip = cats.lang.actions,
|
|||
|
icon = icons.actions,
|
|||
|
click = function(self, ply)
|
|||
|
local m = DermaMenu()
|
|||
|
for i, act in ipairs( cats.config.commands ) do
|
|||
|
m:AddOption( act.text, function()
|
|||
|
act.click(ply)
|
|||
|
end):SetIcon(octolib.icons.silk16(act.icon or 'wand'))
|
|||
|
end
|
|||
|
m:SetPos( input.GetCursorPos() )
|
|||
|
m:Open()
|
|||
|
end
|
|||
|
},
|
|||
|
action_callon = {
|
|||
|
tooltip = cats.lang.action_callon,
|
|||
|
icon = icons.action_callon,
|
|||
|
click = function(self, ply)
|
|||
|
applyButton(self, 'action_calloff', ply, steamID)
|
|||
|
end
|
|||
|
},
|
|||
|
action_calloff = {
|
|||
|
tooltip = cats.lang.action_calloff,
|
|||
|
icon = icons.action_calloff,
|
|||
|
click = function(self, ply)
|
|||
|
applyButton(self, 'action_callon', ply, steamID)
|
|||
|
end
|
|||
|
},
|
|||
|
action_close = {
|
|||
|
tooltip = cats.lang.action_close,
|
|||
|
icon = icons.action_close,
|
|||
|
click = function(self, ply, steamID)
|
|||
|
netstream.Start('cats.closeTicket', steamID)
|
|||
|
end
|
|||
|
},
|
|||
|
}
|
|||
|
|
|||
|
-- default button list
|
|||
|
local actionList = {
|
|||
|
'action_claim',
|
|||
|
'actions',
|
|||
|
-- 'action_callon',
|
|||
|
'action_close',
|
|||
|
}
|
|||
|
|
|||
|
-- debug ticket data
|
|||
|
local debugTicket = {
|
|||
|
user = LocalPlayer(),
|
|||
|
userID = 'STEAM_X:X:XXXXXXXX',
|
|||
|
admin = LocalPlayer(),
|
|||
|
adminID = 'STEAM_X:X:XXXXXXXX',
|
|||
|
chatLog = {
|
|||
|
{"Зюзя", "Админ тп, застрял", false},
|
|||
|
{"СуперВася", "Ща, погоди", true},
|
|||
|
{"Зюзя", "Ну где вы???", false},
|
|||
|
{"УберПетя", "Бля, Вася, да вытащи ты его уже, наконец, он заебал вопить, как малое дите, сука, ебаный в рот", true},
|
|||
|
{"СуперВася", "Ну ща-ща, я дорешаю жалобу", true},
|
|||
|
{"УберПетя", "Да с хера ли ты берешь столько жалоб? Разберись сначала с одной, потом уж на другие иди", true},
|
|||
|
{"СуперВася", "Да хорошо, блять, но дай сейчас-то разберусь", true},
|
|||
|
{"Зюзя", "Идите оба нахуй, я выбрался уже", false},
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
-- my ticket
|
|||
|
local myTicket
|
|||
|
|
|||
|
---------------------------------------------------
|
|||
|
-- MAIN CODE
|
|||
|
---------------------------------------------------
|
|||
|
|
|||
|
-- add a ticket frame to container
|
|||
|
local function addTicketToFrame( data )
|
|||
|
|
|||
|
-- sound notification
|
|||
|
surface.PlaySound(cats.config.newTicketSound)
|
|||
|
|
|||
|
-- ticket panel
|
|||
|
local t = cats.ticketContainer:Add("DButton")
|
|||
|
t:SetSize(cats.config.spawnSize[1], 180)
|
|||
|
t:SetText('')
|
|||
|
t.expanded = true
|
|||
|
t.ticket = data -- apply ticket
|
|||
|
t.Paint = function(self, w, h)
|
|||
|
local user, admin = self.ticket.user, self.ticket.admin
|
|||
|
|
|||
|
surface.SetDrawColor(30,40,50, 220)
|
|||
|
surface.DrawRect(0, 0, w, h)
|
|||
|
if self.Hovered then
|
|||
|
surface.SetDrawColor(255,255,255, 2)
|
|||
|
surface.DrawRect(0, 0, w, h)
|
|||
|
end
|
|||
|
surface.SetDrawColor(0,0,0, 255)
|
|||
|
surface.DrawLine(0, -1, 0, h)
|
|||
|
surface.DrawLine(-1, h-1, w, h-1)
|
|||
|
surface.DrawLine(w-1, h, w-1, -1)
|
|||
|
|
|||
|
local time = '(' .. os.date( "%M:%S", CurTime() - self.ticket.created ) .. ')'
|
|||
|
local userName = IsValid(user) and user:Name() or cats.lang.userDisconnected
|
|||
|
draw.SimpleText(time .. ' ' .. userName, 'cats.small', 8, 15, Color(220,220,220), TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
|
|||
|
if IsValid(admin) then
|
|||
|
draw.SimpleText(admin:Name(), 'cats.small', w-8, 15, Color(180,200,240), TEXT_ALIGN_RIGHT, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
end
|
|||
|
t.DoClick = function(self)
|
|||
|
self.expanded = not self.expanded
|
|||
|
for i,v in ipairs(cats.ticketContainer:GetChildren()) do
|
|||
|
-- if self ~= v then v.expanded = false end
|
|||
|
v:InvalidateLayout(true)
|
|||
|
end
|
|||
|
cats.ticketContainer:Layout()
|
|||
|
timer.Simple(0, function()
|
|||
|
self.chatLog:GotoTextEnd()
|
|||
|
end)
|
|||
|
end
|
|||
|
t.PerformLayout = function(self)
|
|||
|
self:SetSize(self:GetParent():GetWide(), self.expanded and 180 or 30)
|
|||
|
self.controls:SetVisible(self.expanded)
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
-- controls for ticket
|
|||
|
local c = vgui.Create("DPanel", t)
|
|||
|
c:DockMargin(1,1,1,1)
|
|||
|
c:Dock(BOTTOM)
|
|||
|
c:SetTall(150)
|
|||
|
c.Paint = function() end
|
|||
|
t.controls = c
|
|||
|
|
|||
|
-- action buttons for controls
|
|||
|
t.controls.buttons = {}
|
|||
|
for i, v in pairs(actionList) do
|
|||
|
local b = vgui.Create("DButton", c)
|
|||
|
b:SetSize(30, 30)
|
|||
|
b:SetPos(0, (i-1)*30)
|
|||
|
b:SetText('')
|
|||
|
b.Paint = function(self, w, h)
|
|||
|
if self.Hovered then draw.RoundedBox(0, 0, 0, w, h, Color(255,255,255,2)) end
|
|||
|
surface.SetMaterial(self.icon)
|
|||
|
surface.SetDrawColor(255,255,255)
|
|||
|
surface.DrawTexturedRect(7, 7, 16, 16)
|
|||
|
end
|
|||
|
|
|||
|
applyButton(b, v, t.ticket.user, t.ticket.userID)
|
|||
|
t.controls.buttons[v] = b
|
|||
|
end
|
|||
|
|
|||
|
-- chat
|
|||
|
local cp = vgui.Create("DPanel", t.controls)
|
|||
|
cp:Dock(FILL)
|
|||
|
cp:DockMargin(30,0,0,0)
|
|||
|
cp.Paint = function(self, w, h)
|
|||
|
surface.SetDrawColor(0,0,0, 100)
|
|||
|
surface.DrawRect(0, 0, w, h-20)
|
|||
|
surface.SetDrawColor(0,0,0, 255)
|
|||
|
surface.DrawLine(0, h, 0, 0)
|
|||
|
surface.DrawLine(-1, 0, w, 0)
|
|||
|
surface.DrawLine(-1, h-21, w, h-21)
|
|||
|
end
|
|||
|
t.chat = cp
|
|||
|
|
|||
|
-- chat entry
|
|||
|
local ce = vgui.Create("DButton", t.chat)
|
|||
|
ce:Dock(BOTTOM)
|
|||
|
ce:SetText('')
|
|||
|
ce:SetTall(20)
|
|||
|
ce:SetCursor('beam')
|
|||
|
ce.Paint = function(self, w, h)
|
|||
|
if self.Hovered then draw.RoundedBox(0, 0, 0, w, h, Color(255,255,255,1)) end
|
|||
|
draw.SimpleText(cats.lang.sendMessage, 'cats.small', 8, 10, Color(220,220,220, 50), TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
ce.DoClick = function(self)
|
|||
|
Derma_StringRequest(
|
|||
|
cats.lang.sendMessage, cats.lang.typeYourMessage, '',
|
|||
|
function(val)
|
|||
|
netstream.Start('cats.dispatchMessage', data.userID, val)
|
|||
|
end,
|
|||
|
nil,
|
|||
|
cats.lang.ok, cats.lang.cancel
|
|||
|
)
|
|||
|
end
|
|||
|
|
|||
|
-- chat log
|
|||
|
local cl = vgui.Create("RichText", t.chat)
|
|||
|
cl:Dock(FILL)
|
|||
|
cl.Paint = function(self) -- WHAT. THE. FUCK.
|
|||
|
self.m_FontName = "cats.small"
|
|||
|
self:SetFontInternal("cats.small")
|
|||
|
self:SetUnderlineFont("cats.small-underline")
|
|||
|
self:SetBGColor(Color(0,0,0,0))
|
|||
|
self.Paint = nil
|
|||
|
end
|
|||
|
cl.ActionSignal = function(_, name, val)
|
|||
|
if name == "TextClicked" then
|
|||
|
octoesc.OpenURL(val)
|
|||
|
end
|
|||
|
end
|
|||
|
t.chatLog = cl
|
|||
|
|
|||
|
cats.ticketContainer[data.userID] = t
|
|||
|
cats.ticketFrame:PerformLayout()
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
local function addTicketChatLog(steamID, sender, msg, isAdmin)
|
|||
|
|
|||
|
octolib.func.chain({
|
|||
|
|
|||
|
function(reply)
|
|||
|
if not octolib.string.isSteamID(sender) then return reply(sender) end
|
|||
|
steamworks.RequestPlayerInfo(util.SteamIDTo64(sender), reply)
|
|||
|
end,
|
|||
|
|
|||
|
function(_, name)
|
|||
|
|
|||
|
local cl = cats.ticketContainer[steamID].chatLog
|
|||
|
if not IsValid(cl) then return end
|
|||
|
|
|||
|
if isAdmin then
|
|||
|
cl:InsertColorChange(50,120,180, 255)
|
|||
|
else
|
|||
|
cl:InsertColorChange(180,160,50, 255)
|
|||
|
end
|
|||
|
cl:AppendText("\n" .. name)
|
|||
|
|
|||
|
cl:InsertColorChange(220,220,220, 255)
|
|||
|
cl:AppendText(": ")
|
|||
|
|
|||
|
local data = octolib.string.splitByUrl(msg)
|
|||
|
for _,v in ipairs(data) do
|
|||
|
if type(v) == 'string' then
|
|||
|
cl:AppendText(v)
|
|||
|
else
|
|||
|
cl:InsertClickableTextStart(v[1])
|
|||
|
cl:InsertColorChange(0, 130, 255, 255)
|
|||
|
cl:AppendText(v[1])
|
|||
|
cl:InsertColorChange(220,220,220, 255)
|
|||
|
cl:InsertClickableTextEnd()
|
|||
|
end
|
|||
|
end
|
|||
|
|
|||
|
end,
|
|||
|
|
|||
|
})
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
-- generate main frame
|
|||
|
hook.Add("PlayerFinishedLoading", "cats", function()
|
|||
|
|
|||
|
if IsValid(cats.ticketFrame) then cats.ticketFrame:Remove() end
|
|||
|
local w, h = cats.config.spawnSize[1], cats.config.spawnSize[2]
|
|||
|
local x, y = cats.config.spawnPosAdmin[1], cats.config.spawnPosAdmin[2]
|
|||
|
|
|||
|
-- main frame
|
|||
|
local p0 = vgui.Create("DFrame")
|
|||
|
p0:SetSize(w, h)
|
|||
|
p0:SetPos(x, y)
|
|||
|
p0:DockPadding(0, 24, 0, 0)
|
|||
|
p0:SetTitle('')
|
|||
|
p0:ShowCloseButton(false)
|
|||
|
cats.ticketFrame = p0
|
|||
|
|
|||
|
-- scroll panel
|
|||
|
local p1 = vgui.Create("DScrollPanel", p0)
|
|||
|
p1:Dock(FILL)
|
|||
|
local oldLayout = p1.PerformLayout
|
|||
|
p1.PerformLayout = function(self)
|
|||
|
oldLayout(self)
|
|||
|
for i, v in ipairs(cats.ticketContainer:GetChildren()) do
|
|||
|
v:InvalidateLayout()
|
|||
|
end
|
|||
|
end
|
|||
|
local oldThink = p0.Think
|
|||
|
function p0:Think()
|
|||
|
if isfunction(oldThink) then oldThink(self) end
|
|||
|
p1:SetVisible(hook.Run('HUDShouldDraw', 'cats') ~= false)
|
|||
|
end
|
|||
|
|
|||
|
-- icon layout
|
|||
|
local p2 = vgui.Create("DIconLayout", p1)
|
|||
|
p2:Dock(FILL)
|
|||
|
p2:SetSpaceX(0)
|
|||
|
p2:SetSpaceY(0)
|
|||
|
cats.ticketContainer = p2
|
|||
|
|
|||
|
-- finish up main frame with some spicy hooks
|
|||
|
local oldLayout = p0.PerformLayout
|
|||
|
p0.PerformLayout = function(self)
|
|||
|
oldLayout(self)
|
|||
|
self:SetTall( math.min(p2:GetTall(), ScrH() - 100, 600) + 27 )
|
|||
|
self:SetVisible(#p2:GetChildren() > 0)
|
|||
|
end
|
|||
|
p0.Paint = function(self, w, h)
|
|||
|
if hook.Run('HUDShouldDraw', 'cats') == false then return end
|
|||
|
surface.SetDrawColor(30,40,50, 255)
|
|||
|
surface.DrawRect(0, 0, w, 24)
|
|||
|
surface.SetDrawColor(0,0,0, 255)
|
|||
|
surface.DrawOutlinedRect(0, 0, w, 24)
|
|||
|
draw.SimpleText(cats.lang.openTickets .. ' (' .. #p2:GetChildren() .. ')', 'cats.small', 8, 12, Color(220,220,220), TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
-- my ticket frame
|
|||
|
if IsValid(cats.myTicketFrame) then cats.myTicketFrame:Remove() end
|
|||
|
local function createMyTicket( data )
|
|||
|
|
|||
|
-- sound notification
|
|||
|
surface.PlaySound(cats.config.newTicketSound)
|
|||
|
|
|||
|
myTicket = data
|
|||
|
local w, h = cats.config.spawnSize[1], cats.config.spawnSize[2]
|
|||
|
local x, y = cats.config.spawnPosUser[1], cats.config.spawnPosUser[2]
|
|||
|
|
|||
|
-- ticket frame
|
|||
|
local t = vgui.Create("DFrame")
|
|||
|
t:ShowCloseButton(false)
|
|||
|
t:SetSize(w, 220)
|
|||
|
t:SetPos(x, y)
|
|||
|
t:DockPadding(0,30,0,0)
|
|||
|
t:SetTitle('')
|
|||
|
t.ticket = myTicket -- apply ticket
|
|||
|
t.Paint = function(self, w, h)
|
|||
|
if not self.visible then return end
|
|||
|
local user, admin = self.ticket.user, self.ticket.admin
|
|||
|
|
|||
|
surface.SetDrawColor(30,40,50, 220)
|
|||
|
surface.DrawRect(0, 0, w, h)
|
|||
|
surface.SetDrawColor(0,0,0, 255)
|
|||
|
surface.DrawOutlinedRect(0,0,w,h)
|
|||
|
|
|||
|
local time = '(' .. os.date( "%M:%S", CurTime() - self.ticket.created ) .. ')'
|
|||
|
draw.SimpleText(time .. ' ' .. cats.lang.myTicket, 'cats.small', 8, 15, Color(220,220,220), TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
|
|||
|
if IsValid(admin) then
|
|||
|
draw.SimpleText(admin:Name(), 'cats.small', w-8, 15, Color(180,200,240), TEXT_ALIGN_RIGHT, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
end
|
|||
|
|
|||
|
-- close ticket button
|
|||
|
surface.SetFont('cats.small')
|
|||
|
local tw, th = surface.GetTextSize(cats.lang.action_close)
|
|||
|
local b = vgui.Create("DButton", t)
|
|||
|
b:SetText('')
|
|||
|
b:SetSize(tw + 16,30)
|
|||
|
b:AlignRight(1)
|
|||
|
b.Paint = function(self, w, h)
|
|||
|
if self.Hovered then draw.RoundedBox(0, 0, 0, w, h, Color(255,255,255,1)) end
|
|||
|
draw.SimpleText(cats.lang.action_close, 'cats.small', w/2, h/2, Color(220,220,220), TEXT_ALIGN_CENTER, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
b.DoClick = function(self)
|
|||
|
netstream.Start('cats.closeTicket', LocalPlayer():SteamID())
|
|||
|
end
|
|||
|
t.closeBut = b
|
|||
|
|
|||
|
-- chat
|
|||
|
local cp = vgui.Create("DPanel", t)
|
|||
|
cp:Dock(FILL)
|
|||
|
cp.Paint = function(self, w, h)
|
|||
|
surface.SetDrawColor(0,0,0, 100)
|
|||
|
surface.DrawRect(0, 0, w, h-20)
|
|||
|
surface.SetDrawColor(0,0,0, 255)
|
|||
|
surface.DrawLine(0, h, 0, 0)
|
|||
|
surface.DrawLine(-1, 0, w, 0)
|
|||
|
surface.DrawLine(-1, h-21, w, h-21)
|
|||
|
end
|
|||
|
t.chat = cp
|
|||
|
|
|||
|
-- chat entry
|
|||
|
local ce = vgui.Create("DButton", t.chat)
|
|||
|
ce:Dock(BOTTOM)
|
|||
|
ce:SetText('')
|
|||
|
ce:SetTall(20)
|
|||
|
ce:SetCursor('beam')
|
|||
|
ce.Paint = function(self, w, h)
|
|||
|
if self.Hovered then draw.RoundedBox(0, 0, 0, w, h, Color(255,255,255,1)) end
|
|||
|
draw.SimpleText(cats.lang.sendMessage, 'cats.small', 8, 10, Color(220,220,220, 50), TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
|
|||
|
end
|
|||
|
ce.DoClick = function(self)
|
|||
|
Derma_StringRequest(
|
|||
|
cats.lang.sendMessage, cats.lang.typeYourMessage, '',
|
|||
|
function(val)
|
|||
|
netstream.Start('cats.dispatchMessage', LocalPlayer():SteamID(), val)
|
|||
|
end,
|
|||
|
nil,
|
|||
|
cats.lang.ok, cats.lang.cancel
|
|||
|
)
|
|||
|
end
|
|||
|
|
|||
|
-- chat log
|
|||
|
local cl = vgui.Create("RichText", t.chat)
|
|||
|
cl:Dock(FILL)
|
|||
|
cl.Paint = function(self) -- WHAT. THE. FUCK.
|
|||
|
self.m_FontName = "cats.small"
|
|||
|
self:SetFontInternal("cats.small")
|
|||
|
self:SetUnderlineFont("cats.small-underline")
|
|||
|
self:SetBGColor(Color(0,0,0,0))
|
|||
|
self.Paint = nil
|
|||
|
end
|
|||
|
cl.ActionSignal = function(_, name, val)
|
|||
|
if name == "TextClicked" then
|
|||
|
octoesc.OpenURL(val)
|
|||
|
end
|
|||
|
end
|
|||
|
t.chatLog = cl
|
|||
|
|
|||
|
-- You can't just set visibility for self because it stops thinking
|
|||
|
local oldThink = t.Think
|
|||
|
function t:Think()
|
|||
|
if isfunction(oldThink) then oldThink(self) end
|
|||
|
self.visible = hook.Run('HUDShouldDraw', 'cats') ~= false
|
|||
|
if not (myTicket and myTicket.adminID) then
|
|||
|
b:SetVisible(self.visible)
|
|||
|
end
|
|||
|
cp:SetVisible(self.visible)
|
|||
|
ce:SetVisible(self.visible)
|
|||
|
cl:SetVisible(self.visible)
|
|||
|
end
|
|||
|
|
|||
|
cats.myTicketFrame = t
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
local function addMyTicketChatLog(sender, msg, isAdmin)
|
|||
|
|
|||
|
octolib.func.chain({
|
|||
|
|
|||
|
function(reply)
|
|||
|
if not octolib.string.isSteamID(sender) then return reply(sender) end
|
|||
|
steamworks.RequestPlayerInfo(util.SteamIDTo64(sender), reply)
|
|||
|
end,
|
|||
|
|
|||
|
function(_, name)
|
|||
|
|
|||
|
local cl = cats.myTicketFrame.chatLog
|
|||
|
if not IsValid(cl) then return end
|
|||
|
|
|||
|
if isAdmin then
|
|||
|
cl:InsertColorChange(50,120,180, 255)
|
|||
|
else
|
|||
|
cl:InsertColorChange(180,160,50, 255)
|
|||
|
end
|
|||
|
cl:AppendText("\n" .. name)
|
|||
|
|
|||
|
cl:InsertColorChange(220,220,220, 255)
|
|||
|
cl:AppendText(": ")
|
|||
|
|
|||
|
local data = octolib.string.splitByUrl(msg)
|
|||
|
for _,v in ipairs(data) do
|
|||
|
if type(v) == 'string' then
|
|||
|
cl:AppendText(v)
|
|||
|
else
|
|||
|
cl:InsertClickableTextStart(v[1])
|
|||
|
cl:InsertColorChange(0, 130, 255, 255)
|
|||
|
cl:AppendText(v[1])
|
|||
|
cl:InsertColorChange(220,220,220, 255)
|
|||
|
cl:InsertClickableTextEnd()
|
|||
|
end
|
|||
|
end
|
|||
|
|
|||
|
end,
|
|||
|
|
|||
|
})
|
|||
|
|
|||
|
end
|
|||
|
|
|||
|
netstream.Hook('cats.dispatchMessage', function(steamID, sender, msg)
|
|||
|
|
|||
|
if steamID == LocalPlayer():SteamID() then
|
|||
|
if sender ~= LocalPlayer():SteamID() then surface.PlaySound(cats.config.newTicketSound) end
|
|||
|
if myTicket then
|
|||
|
addMyTicketChatLog(sender, msg, sender ~= LocalPlayer():SteamID())
|
|||
|
else
|
|||
|
createMyTicket({created = CurTime()})
|
|||
|
addMyTicketChatLog(sender, msg, sender ~= LocalPlayer():SteamID())
|
|||
|
end
|
|||
|
elseif IsValid(cats.ticketContainer[steamID]) then
|
|||
|
addTicketChatLog(steamID, sender, msg, sender ~= steamID)
|
|||
|
else
|
|||
|
local user = player.GetBySteamID(steamID)
|
|||
|
-- if not IsValid(user) then return end
|
|||
|
|
|||
|
addTicketToFrame({
|
|||
|
user = user,
|
|||
|
userID = steamID,
|
|||
|
created = CurTime(),
|
|||
|
})
|
|||
|
addTicketChatLog(steamID, sender, msg, sender ~= steamID)
|
|||
|
end
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
netstream.Hook('cats.claimTicket', function(steamID, admin, doClaim)
|
|||
|
|
|||
|
if not IsValid(admin) then return end
|
|||
|
|
|||
|
if steamID == LocalPlayer():SteamID() and myTicket then
|
|||
|
myTicket.admin = doClaim and admin or nil
|
|||
|
myTicket.adminID = doClaim and admin:SteamID() or nil
|
|||
|
cats.myTicketFrame.closeBut:SetVisible(not doClaim)
|
|||
|
elseif IsValid(cats.ticketContainer[steamID]) then
|
|||
|
local ticket = cats.ticketContainer[steamID].ticket
|
|||
|
ticket.admin = doClaim and admin or nil
|
|||
|
ticket.adminID = doClaim and admin:SteamID() or nil
|
|||
|
|
|||
|
if ticket.adminID ~= LocalPlayer():SteamID() then
|
|||
|
local b = cats.ticketContainer[steamID].controls.buttons['action_claim']
|
|||
|
local user = player.GetBySteamID(ticket.userID)
|
|||
|
if doClaim then
|
|||
|
applyButton(b, 'action_unclaim', user, ticket.userID)
|
|||
|
b:SetEnabled(false)
|
|||
|
else
|
|||
|
applyButton(b, 'action_claim', user, ticket.userID)
|
|||
|
b:SetEnabled(true)
|
|||
|
end
|
|||
|
end
|
|||
|
end
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
netstream.Hook('cats.closeTicket', function(steamID)
|
|||
|
|
|||
|
if steamID == LocalPlayer():SteamID() and myTicket then
|
|||
|
cats.myTicketFrame:Remove()
|
|||
|
myTicket = nil
|
|||
|
elseif IsValid(cats.ticketContainer[steamID]) then
|
|||
|
cats.ticketContainer[steamID].ticket = nil
|
|||
|
cats.ticketContainer[steamID]:Remove()
|
|||
|
cats.ticketFrame:PerformLayout()
|
|||
|
end
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
netstream.Hook('cats.syncTickets', function(tickets)
|
|||
|
|
|||
|
for steamID, t in pairs(tickets) do
|
|||
|
local user = player.GetBySteamID(steamID)
|
|||
|
if not IsValid(user) then continue end
|
|||
|
|
|||
|
addTicketToFrame({
|
|||
|
user = user,
|
|||
|
userID = steamID,
|
|||
|
created = t.createdGameTime,
|
|||
|
admin = t.admin,
|
|||
|
adminID = t.adminID
|
|||
|
})
|
|||
|
|
|||
|
if IsValid(t.admin) then
|
|||
|
local b = cats.ticketContainer[steamID].controls.buttons['action_claim']
|
|||
|
applyButton(b, 'action_unclaim', t.user, steamID)
|
|||
|
b:SetEnabled(false)
|
|||
|
end
|
|||
|
|
|||
|
for k, v in pairs(t.chatLog) do
|
|||
|
addTicketChatLog(steamID, v[1], v[2], v[3])
|
|||
|
end
|
|||
|
end
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
concommand.Add("cats_test_admin", function()
|
|||
|
|
|||
|
local steamID = LocalPlayer():SteamID()
|
|||
|
addTicketToFrame({
|
|||
|
user = LocalPlayer(),
|
|||
|
userID = steamID,
|
|||
|
created = CurTime(),
|
|||
|
admin = LocalPlayer(),
|
|||
|
adminID = steamID,
|
|||
|
})
|
|||
|
addTicketChatLog(steamID, "chelog", "Admin let me test my ticket!", false)
|
|||
|
addTicketChatLog(steamID, "Admin", "Alright.", true)
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
concommand.Add("cats_test_admin_clear", function()
|
|||
|
|
|||
|
cats.ticketContainer:Clear()
|
|||
|
|
|||
|
end)
|
|||
|
|
|||
|
concommand.Add("cats_test_myticket", function()
|
|||
|
|
|||
|
createMyTicket({created = CurTime()})
|
|||
|
addMyTicketChatLog("chelog", "Admin let me test my ticket!", false)
|
|||
|
addMyTicketChatLog("Admin", "Alright.", true)
|
|||
|
|
|||
|
end)
|