+
+
+
+Games
+Create game +
+nrank do
+ game:GetService("PersonalServerService"):Demote(player)
+ end
+end
+--[[
+ called when player selects new privilege level from popup menu
+ @Args:
+ player player to set privileges on
+ nlevel new privilege level for this player
+--]]
+function OnPrivilegeLevelSelect(player,nlevel,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ debugprint('setting privilege level')
+ SetPrivilegeRank(player,nlevel)
+ HighlightMyRank(player,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+end
+
+--[[
+ Highlights current rank of this player in the popup menu
+ @Args:
+ player Player to check for rank on
+--]]
+function HighlightMyRank(player,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ BanPlayerButton.Image= 'http://www.roblox.com/asset/?id='..Images['LightPopupMid']
+ VisitorButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkPopupMid']
+ MemberButton.Image= 'http://www.roblox.com/asset/?id='..Images['LightPopupMid']
+ AdminButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkPopupBottom']
+
+ local rank=player.PersonalServerRank
+ if rank <= PrivilegeLevel['Banned'] then
+ BanPlayerButton.Image='http://www.roblox.com/asset/?id='..Images['LightBluePopupMid']
+ elseif rank <= PrivilegeLevel['Visitor'] then
+ VisitorButton.Image='http://www.roblox.com/asset/?id='..Images['DarkBluePopupMid']
+ elseif rank <= PrivilegeLevel['Member'] then
+ MemberButton.Image='http://www.roblox.com/asset/?id='..Images['LightBluePopupMid']
+ elseif rank <= PrivilegeLevel['Admin'] then
+ AdminButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkBluePopupBottom']
+ end
+end
+
+ --------------------------
+ -- Report abuse handling
+ --------------------------
+--[[
+ does final reporting of abuse on selected player, calls closeAbuseDialog
+--]]
+function OnSubmitAbuse()
+ if SubmitReportButton.Active then
+ if AbuseName and SelectedPlayer then
+ AbuseSettingsFrame.Visible = false
+ game.Players:ReportAbuse(SelectedPlayer, AbuseName, AbuseDescriptionBox.Text)
+ if AbuseName == "Rude or Mean Behavior" or AbuseName == "False Reporting Me" then
+ CalmingAbuseBox.Parent = ReportAbuseShield
+ else
+ debugprint('opening abuse box')
+ NormalAbuseBox.Parent = ReportAbuseShield
+ end
+ else
+ CloseAbuseDialog()
+ end
+ end
+end
+
+--[[
+ opens the abuse dialog, initialises text to display selectedplayer
+--]]
+function OpenAbuseDialog()
+ debugprint('adding report dialog')
+ AbusePlayerLabel.Text = SelectedPlayer.Name
+ --AbuseDescriptionBox.Text = ""
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ AbuseDescriptionBox=OriginalAbuseDescriptionBox:Clone()
+ AbuseDescriptionBox.Parent = AbuseDescriptionWrapper
+ ReportAbuseShield.Parent = ScreenGui
+ ClosePopUpPanel()
+end
+--[[
+ resets and closes abuse dialog
+--]]
+function CloseAbuseDialog()
+ AbuseName = nil
+ SubmitReportButton.Active = false
+ SubmitReportButton.Image = 'http://www.roblox.com/asset/?id=96502438' -- 96501119',
+ AbuseDescriptionBox:Destroy()
+ CalmingAbuseBox.Parent = nil
+ NormalAbuseBox.Parent = nil
+ ReportAbuseShield.Parent = nil
+ AbuseSettingsFrame.Visible = true
+end
+
+--[[
+ creates dropdownbox, registers all listeners for abuse dialog
+--]]
+function InitReportAbuse()
+
+ UpdateAbuseFunction = function(abuseText)
+ AbuseName = abuseText
+ if AbuseName and SelectedPlayer then
+ SubmitReportButton.Active = true
+ SubmitReportButton.Image = 'http://www.roblox.com/asset/?id=96501119'
+ end
+ end
+
+ AbuseDropDown, UpdateAbuseSelection = RbxGui.CreateDropDownMenu(Abuses, UpdateAbuseFunction, true)
+ AbuseDropDown.Name = "AbuseComboBox"
+ AbuseDropDown.Position = UDim2.new(0.425, 0, 0, 142)
+ AbuseDropDown.Size = UDim2.new(0.55,0,0,32)
+ AbuseDropDown.Parent = AbuseSettingsFrame
+
+
+ CancelReportButton.MouseButton1Click:connect(CloseAbuseDialog)
+ SubmitReportButton.MouseButton1Click:connect(OnSubmitAbuse)
+
+ CalmingAbuseBox:FindFirstChild('OkButton').MouseButton1Down:connect(CloseAbuseDialog)
+ NormalAbuseBox:FindFirstChild('OkButton').MouseButton1Down:connect(CloseAbuseDialog)
+end
+
+-------------------------------------
+-- Friend/unfriending
+-------------------------------------
+--[[
+ gets enum val of friend status, uses pcall for some reason?(from old playerlist)
+ @Args:
+ player player object to check if friends with
+ @Return: enum of friend status
+--]]
+local function GetFriendStatus(player)
+ if player == game.Players.LocalPlayer then
+ return Enum.FriendStatus.NotFriend
+ else
+ local success, result = pcall(function() return game.Players.LocalPlayer:GetFriendStatus(player) end)
+ if success then
+ return result
+ else
+ return Enum.FriendStatus.NotFriend
+ end
+ end
+end
+
+--[[
+ when friend button is clicked, tries to take appropriate action,
+ based on current friend status with SelectedPlayer
+--]]
+function OnFriendButtonSelect()
+
+ local friendStatus=GetFriendStatus(SelectedPlayer)
+ if friendStatus==Enum.FriendStatus.Friend then
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.Unknown or friendStatus==Enum.FriendStatus.NotFriend then
+ LocalPlayer:RequestFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.FriendRequestSent then
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.FriendRequestReceived then
+ LocalPlayer:RequestFriendship(SelectedPlayer)
+ end
+ --PersonalServerPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Quad", .5,true)
+ ClosePopUpPanel()
+ --PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+end
+
+function OnFriendRefuseButtonSelect()
+
+
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ ClosePopUpPanel()
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+end
+------------------------------------
+-- Player Entry Handling
+------------------------------------
+--[[
+ used by lua's table.sort to sort player entries
+--]]
+function PlayerSortFunction(a,b)
+ -- prevents flipping out leaderboard
+ if a['Score'] == b['Score'] then
+ return a['Player'].Name:upper() > b['Player'].Name:upper()
+ end
+ if not a['Score'] then return false end
+ if not b['Score'] then return true end
+ return a['Score'] < b['Score']
+end
+
+ ---------------------------------
+ -- Stat Handling
+ ---------------------------------
+ -- removes and closes all leaderboard stuffs
+function BlowThisPopsicleStand()
+ --ScreenGui:Destroy()
+ --script:Destroy()
+ --time to make the fanboys rage...
+ Tabify()
+end
+--[[
+ used by lua's table.sort to prioritize score entries
+--]]
+function StatSort(a,b)
+ -- primary stats should be shown before all others
+ if a.IsPrimary ~= b.IsPrimary then
+ return a.IsPrimary
+ end
+ -- if priorities are equal, then return the first added one
+ if a.Priority == b.Priority then
+ return a.AddId < b.AddId
+ end
+ return a.Priority < b.Priority
+end
+--[[
+ doing WAAY too much here, for optimization update only your team
+ @Args:
+ playerEntry Entry of player who had a stat change
+ property Name of stat changed
+--]]
+function StatChanged(playerEntry,property)
+
+ -- if(playerEntry['MyTeam']) then
+ -- UpdateSingleTeam(playerEntry['MyTeam'])
+ -- else
+ BaseUpdate()
+ -- end
+end
+--[[
+ Called when stat is added
+ if playerEntry is localplayer, will add to score names and re-sort the stats, and resize the width of the leaderboard
+ for all players, will add a listener for if this stat changes
+ if stat is a string value, crashes the leaderboard
+ Note:change crash to a 'tabify' leaderboard later
+ @Args:
+ nchild new child value to leaderstats
+ playerEntry entry this stat was added to
+--]]
+function StatAdded(nchild,playerEntry)
+ -- dont re - add a leaderstat I alreday have
+ while AddingStatLock do debugprint('in stat added function lock') wait(1/30) end
+ AddingStatLock = true
+ if not (nchild:IsA('StringValue') or nchild:IsA('IntValue') or nchild:IsA('BoolValue') or nchild:IsA('NumberValue') or nchild:IsA('DoubleConstrainedValue') or nchild:IsA('IntConstrainedValue')) then
+ BlowThisPopsicleStand()
+ else
+ local haveScore = false
+ for _,i in pairs(ScoreNames) do
+ if i['Name']==nchild.Name then haveScore=true end
+ end
+ if not haveScore then
+ local nstat = {}
+ nstat['Name'] = nchild.Name
+ nstat['Priority'] = 0
+ if(nchild:FindFirstChild('Priority')) then
+ nstat['Priority'] = nchild.Priority
+ end
+ nstat['IsPrimary'] = false
+ if(nchild:FindFirstChild('IsPrimary')) then
+ nstat['IsPrimary'] = true
+ end
+ nstat.AddId = AddId
+ AddId = AddId + 1
+ table.insert(ScoreNames,nstat)
+ table.sort(ScoreNames,StatSort)
+ if not StatTitles:FindFirstChild(nstat['Name']) then
+ CreateStatTitle(nstat['Name'])
+ end
+ UpdateMaximize()
+
+ end
+ end
+ AddingStatLock = false
+ StatChanged(playerEntry)
+ nchild.Changed:connect(function(property) StatChanged(playerEntry,property) end)
+
+
+end
+--returns whether any of the existing players has this stat
+function DoesStatExist(statName, exception)
+ for _,playerf in pairs(PlayerFrames) do
+ if playerf['Player'] ~= exception and playerf['Player']:FindFirstChild('leaderstats') and playerf['Player'].leaderstats:FindFirstChild(statName) then
+ --print('player:' .. playerf['Player'].Name ..' has stat')
+ return true
+ end
+ end
+ return false
+end
+
+
+
+--[[
+ Called when stat is removed from player
+ for all players, destroys the stat frame associated with this value,
+ then calls statchanged(to resize frame)
+ if playerEntry==localplayer, will remove from scorenames
+ @Args:
+ nchild ___value to be removed
+ playerEntry entry of player value is being removed from
+--]]
+function StatRemoved(nchild,playerEntry)
+ while AddingStatLock do debugprint('In Adding Stat Lock1') wait(1/30) end
+ AddingStatLock = true
+ if playerEntry['Frame']:FindFirstChild(nchild.Name) then
+ debugprint('Destroyed frame!')
+ playerEntry['Frame'][nchild.Name].Parent = nil
+ end
+ if not DoesStatExist(nchild.Name, playerEntry['Player']) then
+ for i,val in ipairs(ScoreNames) do
+ if val['Name'] == nchild.Name then
+ table.remove(ScoreNames,i)
+ if StatTitles:FindFirstChild(nchild.Name) then
+ StatTitles[nchild.Name]:Destroy()
+ end
+ for _,teamf in pairs(TeamFrames) do
+ if teamf['Frame']:FindFirstChild(nchild.Name) then
+ teamf['Frame'][nchild.Name]:Destroy()
+ end
+ end
+ end
+ end
+ end
+ AddingStatLock = false
+ StatChanged(playerEntry)
+end
+--[[
+ clears all stats from a given playerEntry
+ resets the HeadScore's Text property to an empty string
+ used when leaderstats are removed, or when new leaderstats are added(for weird edge case)+
+--]]
+function RemoveAllStats(playerEntry)
+ for i,val in ipairs(ScoreNames) do
+ StatRemoved(val,playerEntry)
+ end HeaderScore.Text = ''
+
+end
+
+
+function GetScoreValue(score)
+ if score:IsA('DoubleConstrainedValue') or score:IsA('IntConstrainedValue') then
+ return score.ConstrainedValue
+ elseif score:IsA('BoolValue') then
+ if score.Value then return 1 else return 0 end
+ else
+ return score.Value
+ end
+end
+--[[
+
+--]]
+function MakeScoreEntry(entry,scoreval,panel)
+ if not panel:FindFirstChild('PlayerScore') then return end
+ local nscoretxt = panel:FindFirstChild('PlayerScore'):Clone()
+ local thisScore = nil
+ --here lies the resting place of a once great and terrible bug
+ --may its treachery never be forgoten, lest its survivors fall for it again
+ --RIP the leaderstat bug, oct 2012-nov 2012
+ wait()
+ if entry['Player']:FindFirstChild('leaderstats') and entry['Player'].leaderstats:FindFirstChild(scoreval['Name']) then
+ thisScore = entry['Player']:FindFirstChild('leaderstats'):FindFirstChild(scoreval['Name'])
+ else
+ return
+ end
+
+ if not entry['Player'].Parent then return end
+
+ nscoretxt.Name = scoreval['Name']
+ nscoretxt.Text = tostring(GetScoreValue(thisScore))
+ if scoreval['Name'] == ScoreNames[1]['Name'] then
+ debugprint('changing score')
+ entry['Score'] = GetScoreValue(thisScore)
+ if entry['Player'] == LocalPlayer then HeaderScore.Text = tostring(GetScoreValue(thisScore)) end
+ end
+
+ thisScore.Changed:connect(function()
+ if not thisScore.Parent then return end
+ if scoreval['Name'] == ScoreNames[1]['Name'] then
+
+ entry['Score'] = GetScoreValue(thisScore)
+ if entry['Player'] == LocalPlayer then HeaderScore.Text = tostring(GetScoreValue(thisScore)) end
+ end
+ nscoretxt.Text = tostring(GetScoreValue(thisScore))
+ BaseUpdate()
+ end)
+ return nscoretxt
+
+end
+
+function CreateStatTitle(statName)
+
+ local ntitle = MiddleTemplate:FindFirstChild('PlayerScore'):Clone()
+ ntitle.Name = statName
+ ntitle.Text = statName
+ -- ntitle
+ if IsMaximized.Value then
+ ntitle.TextTransparency = 0
+ else
+ ntitle.TextTransparency = 1
+ end
+ ntitle.Parent = StatTitles
+end
+
+function RecreateScoreColumns(ptable)
+ while AddingStatLock do debugprint ('In Adding Stat Lock2') wait(1/30) end
+ AddingStatLock = true
+ local Xoffset=5--15 --current offset from Right
+ local maxXOffset=Xoffset
+ local MaxSizeColumn=0 --max size for this column
+
+ -- foreach known leaderstat
+ for j = #ScoreNames, 1,-1 do
+ local scoreval = ScoreNames[j]
+
+ MaxSizeColumn=0
+ -- for each entry in this player table
+ for i,entry in ipairs(ptable) do
+ local panel = entry['Frame']
+ local tplayer = entry['Player']
+ -- if this panel does not have an element named after this stat
+ if not panel:FindFirstChild(scoreval['Name']) then
+ -- make an entry for this object
+ local nentry = MakeScoreEntry(entry,scoreval,panel)
+ if nentry then
+ debugprint('adding '..nentry.Name..' to '..entry['Player'].Name )
+ nentry.Parent = panel
+ -- add score to team
+ if entry['MyTeam'] and entry['MyTeam'] ~= NeutralTeam and not entry['MyTeam']['Frame']:FindFirstChild(scoreval['Name']) then
+ local ntitle = nentry:Clone()
+ --ntitle.TextXAlignment = 'Right'
+ ntitle.Parent = entry['MyTeam']['Frame']
+ end
+
+ end
+ end
+ scoreval['XOffset']=Xoffset
+
+ if panel:FindFirstChild(scoreval['Name']) then
+ MaxSizeColumn=math.max(MaxSizeColumn,panel[scoreval['Name']].TextBounds.X)
+ end
+ end
+
+ if AreNamesExpanded.Value then
+ MaxSizeColumn=math.max(MaxSizeColumn,StatTitles[scoreval['Name'] ].TextBounds.X)
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new(RightEdgeSpace,-Xoffset,0,0),'Out','Linear',BASE_TWEEN,true)
+ else
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new((.4+((.6/#ScoreNames)*(j-1)))-1,0,0,0),'Out','Linear',BASE_TWEEN,true)
+ end
+ scoreval['ColumnSize']=MaxSizeColumn
+ Xoffset= Xoffset+SpacingPerStat+MaxSizeColumn
+ maxXOffset=math.max(Xoffset,maxXOffset)
+ end
+ NormalBounds = UDim2.new(0, BaseScreenXSize+maxXOffset-SpacingPerStat,0,800)
+ NormalPosition = UDim2.new(1 , -NormalBounds.X.Offset, NormalPosition.Y.Scale, 0)
+ UpdateHeaderNameSize()
+ UpdateMaximize()
+
+ AddingStatLock = false
+end
+ ---------------------------
+ -- Minimizing and maximizing
+ ---------------------------
+
+function ToggleMinimize()
+ IsMinimized.Value = not IsMinimized.Value
+ UpdateStatNames()
+end
+
+function ToggleMaximize()
+ IsMaximized.Value = not IsMaximized.Value
+ RecreateScoreColumns(PlayerFrames) --done to re-position stat names NOTE: optimize-able
+end
+
+function Tabify()
+ IsTabified.Value= true
+ IsMaximized.Value=false
+ IsMinimized.Value=true
+ UpdateMinimize()
+ IsTabified.Value= true
+ ScreenGui:TweenPosition(UDim2.new(NormalBounds.X.Scale, NormalBounds.X.Offset-10, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+end
+
+function UnTabify()
+ if IsTabified.Value then
+ IsTabified.Value= false
+ ScreenGui:TweenPosition(UDim2.new(0, 0, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+end
+
+--[[
+ Does more than it looks like
+ monitors positions of the clipping frames and bottom frames
+ called from EVERYWHERE, too much probably
+--]]
+function UpdateMinimize()
+
+ if IsMinimized.Value then
+ if IsMaximized.Value then
+ ToggleMaximize()
+ end
+ if not IsTabified.Value then
+ MainFrame.Size = UDim2.new(0.010, HeaderName.TextBounds.X, NormalBounds.Y.Scale,NormalBounds.Y.Offset)
+ MainFrame.Position = UDim2.new(.990, -HeaderName.TextBounds.X, NormalPosition.Y.Scale,0)
+ else
+ MainFrame.Size = NormalBounds
+ MainFrame.Position = NormalPosition
+ end
+ --(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale)
+ BottomClipFrame.Position = UDim2.new(0,0,-1,0)
+ BottomFrame.Position = UDim2.new(0,0,0,0)
+ FocusFrame.Size=UDim2.new(1,0,HeaderFrameHeight,0)
+ ExtendTab.Image = 'rbxasset://textures/ui/expandPlayerList.png'
+ else
+ if not IsMaximized.Value then
+ MainFrame.Size = NormalBounds
+ MainFrame.Position = NormalPosition
+ end
+ --do limiting
+ DefaultBottomClipPos = math.min(math.max(DefaultBottomClipPos,-1),-1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale))
+ UpdateScrollPosition()
+
+ BottomClipFrame.Position=UDim2.new(0,0,DefaultBottomClipPos,0)
+ local bottomPositon = (DefaultBottomClipPos+BottomClipFrame.Size.Y.Scale)
+ BottomFrame.Position=UDim2.new(0,0,bottomPositon,0)
+ FocusFrame.Size=UDim2.new(1,0,bottomPositon + HeaderFrameHeight,0)
+ ExtendTab.Image = 'rbxasset://textures/ui/expandPlayerList.png'
+ end
+end
+
+--[[
+ Manages the position/size of the mainFrame, swaps out different resolution images for the frame
+ fades in and out the stat names, moves position of headername and header score
+--]]
+function UpdateMaximize()
+ if IsMaximized.Value then
+ for j = 1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new(.4+((.6/#ScoreNames)*(j-1))-1,0,0,0),'Out','Linear',BASE_TWEEN,true)
+ end
+
+ if IsMinimized.Value then
+ ToggleMinimize()
+ else
+ UpdateMinimize()
+ end
+
+
+ MainFrame:TweenSizeAndPosition(MaximizedBounds,MaximizedPosition,'Out','Linear',BASE_TWEEN*1.2,true)
+ HeaderScore:TweenPosition(UDim2.new(0,0,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ HeaderName:TweenPosition(UDim2.new( - .1, - HeaderScore.TextBounds.x,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ for index, i in ipairs(MiddleFrames) do
+
+ if i:FindFirstChild('ClickListener') then
+ i.ClickListener.Size = UDim2.new(1,-2,i.ClickListener.Size.Y.Scale, i.ClickListener.Size.Y.Offset)
+ end
+
+ for j=1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ if i:FindFirstChild(scoreval['Name']) then
+ i[scoreval['Name']]:TweenPosition(UDim2.new(.4+((.6/#ScoreNames)*(j-1))-1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ end
+ end
+ end
+ for i,entry in ipairs(PlayerFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(.38,0,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+
+ for i,entry in ipairs(TeamFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(.38,0,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+
+ else
+ if not IsMinimized.Value then
+ MainFrame:TweenSizeAndPosition(NormalBounds,NormalPosition,'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+ HeaderScore:TweenPosition(UDim2.new(0,0,.4,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ HeaderName:TweenPosition(UDim2.new(0,0,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ for index, i in ipairs(MiddleFrames) do
+ if i:FindFirstChild('ClickListener') then
+ i.ClickListener.Size = UDim2.new(1, -2,i.ClickListener.Size.Y.Scale, i.ClickListener.Size.Y.Offset)
+ for j=1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ if i:FindFirstChild(scoreval['Name']) and scoreval['XOffset'] then
+ --print('updateing stat position: ' .. scoreval['Name'])
+ i[scoreval['Name']]:TweenPosition(UDim2.new(RightEdgeSpace,-scoreval['XOffset'],0,0), "Out", "Linear", BASE_TWEEN,true)
+ end
+ end
+ end
+ end
+
+ for i,entry in ipairs(TeamFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(0,BaseScreenXSize*.9,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+
+ end
+ for i,entry in ipairs(PlayerFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(0,BaseScreenXSize*.9,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+ end
+end
+
+function UpdateStatNames()
+ if not AreNamesExpanded.Value or IsMinimized.Value then
+ CloseNames()
+ else
+ ExpandNames()
+ end
+end
+
+function ExpandNames()
+ if #ScoreNames ~= 0 then
+ for _,i in pairs(StatTitles:GetChildren()) do
+ Spawn(function()TweenProperty(i,'TextTransparency',i.TextTransparency,0,BASE_TWEEN) end)
+ end
+ HeaderFrameHeight=.09
+ --as of writing, this and 'CloseNames' are the only places headerframe is resized
+ HeaderFrame:TweenSizeAndPosition(UDim2.new(HeaderFrame.Size.X.Scale, HeaderFrame.Size.X.Offset, HeaderFrameHeight,0),
+ HeaderFrame.Position,'Out','Linear',BASE_TWEEN*1.2,true)
+ TopClipFrame:TweenPosition(UDim2.new(TopClipFrame.Position.X.Scale,0,HeaderFrameHeight,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ BottomShiftFrame:TweenPosition(UDim2.new(0,0,HeaderFrameHeight,0), "Out", 'Linear', BASE_TWEEN*1.2,true)
+
+ end
+
+end
+
+function CloseNames()
+ if #ScoreNames ~= 0 then
+ HeaderFrameHeight=.07
+ if not (IsMaximized.Value) then
+ for _,i in pairs(StatTitles:GetChildren()) do
+ Spawn(function()TweenProperty(i,'TextTransparency',i.TextTransparency,1,BASE_TWEEN) end)
+ end
+ end
+ BottomShiftFrame:TweenPosition(UDim2.new(0,0,HeaderFrameHeight,0), "Out", 'Linear', BASE_TWEEN*1.2,true)
+ HeaderFrame:TweenSizeAndPosition(UDim2.new(HeaderFrame.Size.X.Scale, HeaderFrame.Size.X.Offset, HeaderFrameHeight,0),
+ HeaderFrame.Position,'Out','Linear',BASE_TWEEN*1.2,true)
+ TopClipFrame:TweenPosition(UDim2.new(TopClipFrame.Position.X.Scale,0,HeaderFrameHeight,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+end
+
+function OnScrollWheelMove(direction)
+ if not (IsTabified.Value or IsMinimized.Value or InPopupWaitForClick) then
+ local StartFrame = ListFrame.Position
+ local newFrameY = math.max(math.min(StartFrame.Y.Scale + (direction),GetMaxScroll()),GetMinScroll())
+
+ ListFrame.Position = UDim2.new(StartFrame.X.Scale,StartFrame.X.Offset,newFrameY,StartFrame.Y.Offset)
+ UpdateScrollPosition()
+ end
+end
+
+function AttachScrollWheel()
+ if ScrollWheelConnections then return end
+ ScrollWheelConnections = {}
+ table.insert(ScrollWheelConnections,Mouse.WheelForward:connect(function()
+ OnScrollWheelMove(.05)
+ end))
+ table.insert(ScrollWheelConnections,Mouse.WheelBackward:connect(function()
+ OnScrollWheelMove(-.05)
+ end))
+end
+
+function DetachScrollWheel()
+ if ScrollWheelConnections then
+ for _,i in pairs(ScrollWheelConnections) do
+ i:disconnect()
+ end
+ end
+ ScrollWheelConnections=nil
+end
+
+FocusFrame.MouseEnter:connect(function()
+ if not (IsMinimized.Value or IsTabified.Value) then
+ AttachScrollWheel()
+ end
+end)
+FocusFrame.MouseLeave:connect(function()
+ --if not (IsMaximized.Value or IsMinimized.Value) then
+ DetachScrollWheel()
+ --end
+end)
+
+ ------------------------
+ -- Scroll Bar functions
+ ------------------------
+--[[
+ updates whether the scroll bar should be showing, if it is showing, updates
+ the size of it
+--]]
+function UpdateScrollBarVisibility()
+ if AreAllEntriesOnScreen() then
+ ScrollBar.BackgroundTransparency = 1
+ else
+ ScrollBar.BackgroundTransparency = 0
+ UpdateScrollBarSize()
+ end
+end
+--[[
+ updates size of scrollbar depending on how many entries exist
+--]]
+function UpdateScrollBarSize()
+ local entryListSize = #MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale
+ local shownAreaSize = ((BottomClipFrame.Position.Y.Scale) + 1)
+ ScrollBar.Size = UDim2.new(1,0,shownAreaSize/entryListSize,0)
+
+end
+--[[
+ updates position of listframe so that no gaps at the bottom or top of the list are visible
+ updates position of scrollbar to match what parts of the list are visible
+--]]
+function UpdateScrollPosition()
+ local minPos = GetMinScroll()
+ local maxPos = GetMaxScroll()
+ local scrollLength = maxPos - minPos
+
+ local yscrollpos=math.max(math.min(ListFrame.Position.Y.Scale,maxPos),minPos)
+ ListFrame.Position=UDim2.new(ListFrame.Position.X.Scale,ListFrame.Position.X.Offset,yscrollpos,ListFrame.Position.Y.Offset)
+
+ local adjustedLength = 1 - ScrollBar.Size.Y.Scale
+ ScrollBar.Position = UDim2.new(0,0,adjustedLength - (adjustedLength * ((ListFrame.Position.Y.Scale - minPos)/scrollLength)),0)
+end
+
+--[[
+ WARNING:this is in a working state, but uses massive hacks
+ revize when global input is available
+ Manages scrolling of the playerlist on mouse drag
+--]]
+function StartDrag(entry,startx,starty)
+ local startDragTime = tick()
+ local stopDrag = false
+ local openPanel = true
+ local draggedFrame = WaitForChild(entry['Frame'],'ClickListener')
+ local function dragExit()
+ stopDrag = true
+
+ if entry['Player'] and SelectedPlayer and openPanel
+ and (entry['Player']~=LocalPlayer and (SelectedPlayer.userId>1 and LocalPlayer.userId>1)) then
+ ActivatePlayerEntryPanel(entry)
+ end
+ end
+ local startY = nil
+ local StartFrame = ListFrame.Position
+ local function dragpoll(nx,ny)
+ if not startY then
+ startY = AbsoluteToPercent(nx,ny).Y
+ end
+ local nowY = AbsoluteToPercent(nx,ny).Y
+ debugprint('drag dist:'..Vector2.new(startx-nx,starty-ny).magnitude)
+ if Vector2.new(startx-nx,starty-ny).magnitude>MOUSE_DRAG_DISTANCE then
+ openPanel=false
+ end
+
+ local newFrameY = math.max(math.min(StartFrame.Y.Scale + (nowY - startY),GetMaxScroll()),GetMinScroll())
+ ListFrame.Position = UDim2.new(StartFrame.X.Scale,StartFrame.X.Offset,newFrameY,StartFrame.Y.Offset)
+ UpdateScrollPosition()
+ end
+ WaitForClick(ScreenGui,dragpoll,dragExit)
+end
+
+
+function StartMinimizeDrag()
+ Delay(0,function()
+ local startTime=tick()
+ debugprint('Got Click2')
+ local stopDrag = false
+ local function dragExit()
+ --debugprint('undone click2')
+ if tick()-startTime<.25 then --was click
+ ToggleMinimize()
+ else --was drag
+ if (DefaultBottomClipPos >= -1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale)) then
+ DidMinimizeDrag = false
+ else
+ DidMinimizeDrag = true
+ end
+ if IsMinimized.Value then
+ ToggleMinimize()
+ end
+ end
+ stopDrag = true
+ end
+ local startY = nil
+ local StartFrame = DefaultBottomClipPos
+ local function dragpoll(nx,ny)
+ if not IsMinimized.Value then
+
+ if not startY then
+ startY = AbsoluteToPercent(nx,ny).Y
+ end
+ local nowY = AbsoluteToPercent(nx,ny).Y
+ local newFrameY
+ newFrameY = math.min(math.max(StartFrame + (nowY - startY),-1),-1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale))
+ DefaultBottomClipPos = newFrameY
+ UpdateMinimize()
+ ScrollBarFrame.Size= UDim2.new(ScrollBarFrame.Size.X.Scale,0,(DefaultBottomClipPos+BottomClipFrame.Size.Y.Scale),0)
+ ScrollBarFrame.Position= UDim2.new(ScrollBarFrame.Position.X.Scale,0,1-ScrollBarFrame.Size.Y.Scale,0)
+ UpdateScrollBarSize()
+ UpdateScrollPosition()
+ UpdateScrollBarVisibility()
+
+ end
+ end
+ Spawn(function() WaitForClick(ScreenGui,dragpoll,dragExit) end)
+ end)
+
+end
+
+ -------------------------------
+ -- Input Callback functions
+ -------------------------------
+IsMaximized.Value=false
+IsMinimized.Value=false
+IsMaximized.Changed:connect(UpdateMaximize)
+IsMinimized.Changed:connect(UpdateMinimize)
+
+ExtendButton.MouseButton1Down:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ else
+ StartMinimizeDrag()
+ end
+end)
+
+MaximizeButton.MouseButton1Click:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ elseif not AreNamesExpanded.Value then
+ AreNamesExpanded.Value = true
+ BaseUpdate()
+ else
+ ToggleMaximize()
+ end
+end)
+
+MaximizeButton.MouseButton2Click:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ elseif IsMaximized.Value then
+ ToggleMaximize()
+ elseif AreNamesExpanded.Value then
+ AreNamesExpanded.Value = false
+ BaseUpdate()
+ else
+ Tabify()
+ end
+end)
+
+
+-------------------------------
+-- MiddleFrames management
+-------------------------------
+--[[
+ adds a background frame to the listframe
+--]]
+function AddMiddleBGFrame()
+ local nBGFrame = MiddleBGTemplate:Clone()
+ nBGFrame.Position = UDim2.new(.5,0,((#MiddleFrameBackgrounds) * nBGFrame.Size.Y.Scale),0)
+ nBGFrame.Background.BackgroundTransparency = 1
+
+ nBGFrame.Parent = ListFrame
+ table.insert(MiddleFrameBackgrounds,nBGFrame)
+
+ if #MiddleFrameBackgrounds 1 do
+ fSize=fSize-1
+ tHeader.FontSize=FONT_SIZES[fSize]
+ wait(.2)
+ end
+ HeaderName.FontSize=tHeader.FontSize
+ tHeader:Destroy()
+ end)
+end
+ScreenGui.Changed:connect(UpdateHeaderNameSize)
+
+--[[
+ called only when the leaderstats object is added to a given player entry
+ removes old stats, adds any existing stats, and sets up listeners for new stats
+ @Args:
+ playerEntry A reference to the ENTRY(table) of the player who had leaderstats added
+--]]
+function LeaderstatsAdded(playerEntry)
+ --RemoveAllStats(playerEntry)
+ local nplayer = playerEntry['Player']
+ for _,i in pairs(nplayer.leaderstats:GetChildren()) do
+ StatAdded(i,playerEntry)
+ end
+ nplayer.leaderstats.ChildAdded:connect(function(nchild) StatAdded(nchild,playerEntry) end)
+ nplayer.leaderstats.ChildRemoved:connect(function(nchild) StatRemoved(nchild,playerEntry) end)
+end
+--[[
+ called when leaderstats object is removed from play in player entry
+ Note: may not be needed, might be able to just rely on leaderstats added
+ @Args:
+ oldLeaderstats leaderstats object to be removed
+ playerEntry A reference to the ENTRY(table) of the player
+--]]
+function LeaderstatsRemoved(oldLeaderstats,playerEntry)
+ while AddingFrameLock do debugprint('waiting to insert '..playerEntry['Player'].Name) wait(1/30) end
+ AddingFrameLock = true
+ RemoveAllStats(playerEntry)
+ AddingFrameLock = false
+end
+
+function ClosePopUpPanel()
+ if SelectedPlayerEntry then
+ local tframe = SelectedPlayerEntry['Frame']
+ Spawn(function() TweenProperty(tframe,'BackgroundTransparency',.5,1,BASE_TWEEN) end)
+ end
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ wait(.1)
+ InPopupWaitForClick= false
+ SelectedPlayerEntry = nil
+end
+
+--[[
+ prepares the needed popup to be tweened on screen, and updates the position of the popup clip
+ frame to match the selected player frame's position
+--]]
+function InitMovingPanel( entry, player)
+ PopUpClipFrame.Parent= ScreenGui
+
+ if PopUpPanel then
+ PopUpPanel:Destroy()
+ end
+ PopUpPanel= PopUpPanelTemplate:Clone()
+ PopUpPanel.Parent= PopUpClipFrame
+
+ local nextIndex = 2
+ local friendStatus = GetFriendStatus(player)
+ debugprint (tostring(friendStatus))
+ local showRankMenu = IsPersonalServer and LocalPlayer.PersonalServerRank >= PrivilegeLevel['Admin'] and LocalPlayer.PersonalServerRank > SelectedPlayer.PersonalServerRank
+
+
+ local ReportPlayerButton = MakePopupButton(PopUpPanel,'Report Player',0)
+ ReportPlayerButton.MouseButton1Click:connect(function() OpenAbuseDialog() end)
+
+ local enableFriendRequests = true
+
+ if enableFriendRequests then
+ local FriendPlayerButton = MakePopupButton(PopUpPanel,'Friend',1, not showRankMenu and friendStatus~=Enum.FriendStatus.FriendRequestReceived)
+ FriendPlayerButton.MouseButton1Click:connect(OnFriendButtonSelect)
+
+
+ if friendStatus==Enum.FriendStatus.Friend then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='UnFriend Player'
+ elseif friendStatus==Enum.FriendStatus.Unknown or friendStatus==Enum.FriendStatus.NotFriend then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Send Request'
+ elseif friendStatus==Enum.FriendStatus.FriendRequestSent then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Revoke Request'
+ elseif friendStatus==Enum.FriendStatus.FriendRequestReceived then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Accept Friend'
+ local FriendRefuseButton = MakePopupButton(PopUpPanel,'Decline Friend',2,not showRankMenu)
+ FriendRefuseButton.MouseButton1Click:connect(OnFriendRefuseButtonSelect)
+ nextIndex=nextIndex+1
+ end
+ end
+
+ if showRankMenu then
+ local BanPlayerButton = MakePopupButton(PopUpPanel,'Ban',nextIndex)
+ local VisitorButton = MakePopupButton(PopUpPanel,'Visitor',nextIndex+1)
+ local MemberButton = MakePopupButton(PopUpPanel,'Member',nextIndex+2)
+ local AdminButton = MakePopupButton(PopUpPanel,'Admin',nextIndex+3,true)
+
+ BanPlayerButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Banned'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ VisitorButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Visitor'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ MemberButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Member'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ AdminButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Admin'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+
+ HighlightMyRank(SelectedPlayer,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end
+
+ PopUpPanel:TweenPosition(UDim2.new(0,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ Delay(0, function()
+ local tconnection
+ tconnection = Mouse.Button1Down:connect(function()
+ tconnection:disconnect()
+ ClosePopUpPanel()
+ end)
+ end)
+
+ local myFrame = entry['Frame']
+ -- THIS IS GARBAGE.
+ -- if I parent to frame to auto update position, it gets clipped
+ -- sometimes garbage is the only option.
+ Spawn(function()
+ while InPopupWaitForClick do
+ PopUpClipFrame.Position=UDim2.new( 0,myFrame.AbsolutePosition.X-PopUpClipFrame.Size.X.Offset,0,myFrame.AbsolutePosition.Y)
+ wait()
+ end
+ end)
+
+end
+
+--[[
+ Called when a player entry in the leaderboard is clicked
+ either will highlight entry and start the drag event, or open a popup menu
+ @Args:
+ entry the player entry clicked
+--]]
+function OnPlayerEntrySelect(entry,startx,starty)
+
+ if not InPopupWaitForClick then
+
+ SelectedPlayerEntry = entry
+ SelectedPlayer = entry['Player']
+
+ StartDrag(entry,startx,starty)
+ end
+
+
+end
+
+function ActivatePlayerEntryPanel(entry)
+ entry['Frame'].BackgroundColor3 = Color3.new(0,1,1)
+ Spawn(function() TweenProperty(entry['Frame'],'BackgroundTransparency',1,.5,.5) end)
+ InPopupWaitForClick=true
+ InitMovingPanel(entry,entry['Player'])
+end
+
+--[[
+ the basic update for the playerlist mode's state,
+ assures the order and length of the player frames
+--]]
+function PlayerListModeUpdate()
+ RecreateScoreColumns(PlayerFrames)
+ table.sort(PlayerFrames,PlayerSortFunction)
+ for i,val in ipairs(PlayerFrames) do
+ MiddleFrames[i] = val['Frame']
+ end
+ for i = #PlayerFrames + 1,#MiddleFrames,1 do
+ MiddleFrames[i] = nil
+ end
+ UpdateMinimize()
+end
+--[[
+ this one's a doozie, happens when a player is added to the game
+ inits their player frame and player entry, assigns them to a team if possible,
+ and hooks up their leaderstats
+ @Args:
+ nplayer new player object to insert
+--]]
+function InsertPlayerFrame(nplayer)
+ while AddingFrameLock do debugprint('waiting to insert '..nplayer.Name) wait(1/30) end
+ AddingFrameLock = true
+
+ local nFrame = MiddleTemplate:Clone()
+ nFrame.ClickListener.BackgroundColor3 = Color3.new(0,0,0)
+ nFrame.ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nFrame.ClickListener.AutoButtonColor=false
+
+ local playerName = nplayer.Name
+ local clansEnabled, clanTag = pcall(function() nplayer:GetClanTag() end)
+ if clansEnabled and clanTag and clanTag ~= "" then
+ playerName = "[" .. tostring(clanTag) .. "] " .. playerName
+ end
+
+ WaitForChild(WaitForChild(nFrame,'TitleFrame'),'Title').Text = playerName
+
+ nFrame.Position = UDim2.new(1,0,((#MiddleFrames) * nFrame.Size.Y.Scale),0)
+
+ local nfriendstatus = GetFriendStatus(nplayer)
+
+ nFrame:FindFirstChild('BCLabel').Image = getMembershipTypeIcon(nplayer.MembershipType,nplayer.Name)
+ nFrame:FindFirstChild('FriendLabel').Image = getFriendStatusIcon(nfriendstatus)
+ nFrame.Name = nplayer.Name
+ WaitForChild(WaitForChild(nFrame,'TitleFrame'),'Title').Text = playerName
+
+ --move for bc label
+ nFrame.FriendLabel.Position=nFrame.FriendLabel.Position+UDim2.new(0,17,0,0)
+ nFrame.TitleFrame.Title.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+
+ if(nFrame:FindFirstChild('FriendLabel').Image ~= '') then
+ nFrame.TitleFrame.Title.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+ end
+
+ if nplayer.Name == LocalPlayer.Name then
+ nFrame.TitleFrame.Title.Font = 'ArialBold'
+ nFrame.PlayerScore.Font = 'ArialBold'
+ ChangeHeaderName(playerName)
+ local dropShadow = nFrame.TitleFrame.Title:Clone()
+ dropShadow.TextColor3 = Color3.new(0,0,0)
+ dropShadow.TextTransparency=0
+ dropShadow.ZIndex=2
+ dropShadow.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,1,0,1)
+ dropShadow.Name='DropShadow'
+ dropShadow.Parent= nFrame.TitleFrame
+ else
+ --Delay(2, function () OnFriendshipChanged(nplayer,LocalPlayer:GetFriendStatus(nplayer)) end)
+ end
+ nFrame.TitleFrame.Title.Font = 'ArialBold'
+
+
+ nFrame.Parent = ListFrame
+ nFrame.Position = UDim2.new(.5,0,((#MiddleFrames) * nFrame.Size.Y.Scale),0)
+ UpdateMinimize()
+ local nentry = {}
+ nentry['Frame'] = nFrame
+ nentry['Player'] = nplayer
+ nentry['ID'] = AddId
+ AddId = AddId + 1
+ table.insert(PlayerFrames,nentry)
+ if #TeamFrames~=0 then
+
+ if nplayer.Neutral then
+ nentry['MyTeam'] = nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else
+ AddPlayerToTeam(NeutralTeam,nentry)
+ end
+
+ else
+ local addedToTeam=false
+ for i,tval in ipairs(TeamFrames) do
+ if tval['MyTeam'].TeamColor == nplayer.TeamColor then
+ AddPlayerToTeam(tval,nentry)
+ nentry['MyTeam'] = tval
+ addedToTeam=true
+ end
+ end
+ if not addedToTeam then
+ nentry['MyTeam']=nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else
+ AddPlayerToTeam(NeutralTeam,nentry)
+ end
+ nentry['MyTeam'] = NeutralTeam
+ end
+ end
+
+ end
+
+ if nplayer:FindFirstChild('leaderstats') then
+ LeaderstatsAdded(nentry)
+ end
+
+ nplayer.ChildAdded:connect(function(nchild)
+ if nchild.Name == 'leaderstats' then
+ while AddingFrameLock do debugprint('in adding leaderstats lock') wait(1/30) end
+ if not nplayer:FindFirstChild("leaderstats") then return end
+ AddingFrameLock = true
+ LeaderstatsAdded(nentry)
+ AddingFrameLock = false
+ end
+ end)
+
+ nplayer.ChildRemoved:connect(function (nchild)
+ if nplayer==LocalPlayer and nchild.Name == 'leaderstats' then
+ LeaderstatsRemoved(nchild,nentry)
+ end
+ end)
+ nplayer.Changed:connect(function(prop)PlayerChanged(nentry,prop) end)
+
+ local listener = WaitForChild(nFrame,'ClickListener')
+ listener.Active = true
+ listener.MouseButton1Down:connect(function(nx,ny) OnPlayerEntrySelect(nentry, nx,ny) end)
+
+ AddMiddleBGFrame()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+--[[
+ Note:major optimization can be done here
+ removes this player's frame if it exists, calls base update
+--]]
+function RemovePlayerFrame(tplayer)
+ while AddingFrameLock do debugprint('in removing player frame lock') wait(1/30) end
+ AddingFrameLock = true
+
+ local tteam
+ for i,key in ipairs(PlayerFrames) do
+ if tplayer == key['Player'] then
+ if PopUpClipFrame.Parent == key['Frame'] then
+ PopUpClipFrame.Parent = nil
+ end
+ key['Frame']:Destroy()
+ tteam=key['MyTeam']
+ table.remove(PlayerFrames,i)
+ end
+ end
+ if tteam then
+ for j,tentry in ipairs(tteam['MyPlayers']) do
+ if tentry['Player'] == tplayer then
+ RemovePlayerFromTeam(tteam,j)
+ end
+ end
+ end
+
+ RemoveMiddleBGFrame()
+ UpdateMinimize()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+Players.ChildRemoved:connect(RemovePlayerFrame)
+
+----------------------------
+-- Team Callback Functions
+----------------------------
+--[[
+ turns a list of team entries with sub lists of players into a single ordered
+ list, in the correct order,and of the correct length
+ @Args:
+ tframes the team entries to unroll
+ outframes the list to unroll these entries into
+--]]
+function UnrollTeams(tframes,outframes)
+ local numEntries = 0
+ if NeutralTeam and not NeutralTeam['IsHidden'] then
+ for i,val in ipairs(NeutralTeam['MyPlayers']) do
+ numEntries = numEntries + 1
+ outframes[numEntries] = val['Frame']
+ end
+ numEntries = numEntries + 1
+ outframes[numEntries] = NeutralTeam['Frame']
+ end
+ for i,val in ipairs(tframes) do
+ if not val['IsHidden'] then
+ for j,pval in ipairs(val.MyPlayers) do
+ numEntries = numEntries + 1
+ outframes[numEntries] = pval['Frame']
+ end
+ numEntries = numEntries + 1
+ outframes[numEntries] = val['Frame']
+ end
+ end
+ -- clear any additional entries from outframes
+ for i = numEntries + 1,#outframes,1 do
+ outframes[i] = nil
+ end
+end
+--[[
+ uses lua's table.sort to sort the teams
+--]]
+function TeamSortFunc(a,b)
+ if a['TeamScore'] == b['TeamScore'] then
+ return a['ID'] < b['ID']
+ end
+ if not a['TeamScore'] then return false end
+ if not b['TeamScore'] then return true end
+ return a['TeamScore'] < b['TeamScore']
+
+end
+--[[
+ consider adding lock with wait for performance
+ sorts each of the team's player lists induvidually, adds up the team scores.
+ @Args:
+ tentries table of team entries
+--]]
+function SortTeams(tentries)
+
+ for i,val in ipairs(tentries) do
+
+ table.sort(val['MyPlayers'],PlayerSortFunction)
+ AddTeamScores(val)
+ end
+ table.sort(tentries,TeamSortFunc)
+end
+--[[
+ base update for team mode, adds up the scores of all teams, sorts them,
+ then unrolls them into middleframes
+--]]
+function TeamListModeUpdate()
+ RecreateScoreColumns(PlayerFrames)
+ SortTeams(TeamFrames)
+ if NeutralTeam then
+ AddTeamScores(NeutralTeam)
+ --RecreateScoreColumns(NeutralTeam['MyPlayers'])
+ end
+ UnrollTeams(TeamFrames,MiddleFrames)
+end
+--[[
+ adds up all the score of this team's players to form the team score
+ @Args:
+ team team entry to sum the scores of
+--]]
+function AddTeamScores(team)
+
+ for j = 1, #ScoreNames,1 do
+ local i = ScoreNames[j]
+ local tscore = 0
+ for _,j in ipairs(team['MyPlayers']) do
+ local tval = j['Player']:FindFirstChild('leaderstats') and j['Player'].leaderstats:FindFirstChild(i['Name'])
+ if tval and not tval:IsA('StringValue') then
+ tscore = tscore + GetScoreValue((j['Player'].leaderstats)[i['Name'] ])
+ end
+ end
+ if team['Frame']:FindFirstChild(i['Name']) then
+ --team['Frame'][i['Name'] ].Size = UDim2.new(1 - (ScrollBarFrame.Size.X.Scale * 2),- ((j-1) * SpacingPerStat),1,0)
+ team['Frame'][i['Name'] ].Text = tostring(tscore)
+ end
+ end
+ UpdateMinimize()
+
+end
+
+--[[
+ finds previous team this player was on, and if it exists calls removeplayerfromteam
+ @Args
+ entry Player entry
+--]]
+function FindRemovePlayerFromTeam(entry)
+ if entry['MyTeam'] then
+ for j,oldEntry in ipairs(entry['MyTeam']['MyPlayers']) do
+ if oldEntry['Player'] == entry['Player'] then
+ RemovePlayerFromTeam(entry['MyTeam'],j)
+ return
+ end
+ end
+ elseif NeutralTeam then
+ for j,oldEntry in ipairs(NeutralTeam['MyPlayers']) do
+ if oldEntry['Player'] == entry['Player'] then
+ RemovePlayerFromTeam(NeutralTeam,j)
+ return
+ end
+ end
+ end
+end
+--[[
+ removes a single player from a given team (not usually called directly)
+ @Args:
+ teamEntry team entry to remove player from
+ index index of player in 'MyPlayers' list to remove
+--]]
+function RemovePlayerFromTeam(teamEntry,index)
+ table.remove(teamEntry['MyPlayers'],index)
+ --if teamEntry['AutoHide'] and #teamEntry['MyPlayers'] == 0 then
+ if teamEntry==NeutralTeam and #teamEntry['MyPlayers']==0 then
+ RemoveNeutralTeam()
+ end
+end
+--[[
+ adds player entry entry to teamentry
+ removes them from any previous team
+ @Args:
+ teamEntry entry of team to add player to
+ entry player entry to add to this team
+--]]
+function AddPlayerToTeam(teamEntry,entry)
+ FindRemovePlayerFromTeam(entry)
+ table.insert(teamEntry['MyPlayers'],entry)
+ entry['MyTeam'] = teamEntry
+ if teamEntry['IsHidden'] then
+ teamEntry['Frame'].Parent = ListFrame
+ AddMiddleBGFrame()
+ end
+ teamEntry['IsHidden'] = false
+end
+
+
+function SetPlayerToTeam(entry)
+ FindRemovePlayerFromTeam(entry)
+ -- check to see if team exists, if it does add to that team
+ local setToTeam = false
+ for i,tframe in ipairs(TeamFrames) do
+ -- add my entry on the new team
+ if tframe['MyTeam'].TeamColor == entry['Player'].TeamColor then
+ AddPlayerToTeam(tframe,entry)
+ setToTeam = true
+ end
+ end
+ -- if player was set to an invalid team, then set it back to neutral
+ if not setToTeam and #(game.Teams:GetTeams())>0 then
+ debugprint(entry['Player'].Name..'could not find team')
+ entry['MyTeam']=nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else AddPlayerToTeam(NeutralTeam,entry) end
+ end
+end
+
+--[[
+ Note:another big one, consiter breaking up
+ called when any children of player changes
+ handles 'Neutral', teamColor, Name and MembershipType changes
+ @Args
+ entry Player entry changed
+ property name of property changed
+--]]
+function PlayerChanged(entry, property)
+ while PlayerChangedLock do
+ debugprint('in playerchanged lock')
+ wait(1/30)
+ end
+ PlayerChangedLock=true
+ if property == 'Neutral' then
+ -- if player changing to neutral
+ if entry['Player'].Neutral and #(game.Teams:GetTeams())>0 then
+ debugprint(entry['Player'].Name..'setting to neutral')
+ FindRemovePlayerFromTeam(entry)
+ entry['MyTeam']=nil
+ if not NeutralTeam then
+ debugprint(entry['Player'].Name..'creating neutral team')
+ AddNeutralTeam()
+ else
+ debugprint(entry['Player'].Name..'adding to neutral team')
+ AddPlayerToTeam(NeutralTeam,entry)
+ end
+ elseif #(game.Teams:GetTeams())>0 then -- else player switching to a team, or a weird edgecase
+ debugprint(entry['Player'].Name..'has been set non-neutral')
+ SetPlayerToTeam(entry)
+ end
+ BaseUpdate()
+ elseif property == 'TeamColor' and not entry['Player'].Neutral and entry['Player'] ~= entry['MyTeam'] then
+ debugprint(entry['Player'].Name..'setting to new team')
+ SetPlayerToTeam(entry)
+ BaseUpdate()
+ elseif property == 'Name' or property == 'MembershipType' then
+ entry['Frame']:FindFirstChild('BCLabel').Image = getMembershipTypeIcon(entry['Player'].MembershipType,entry['Player'].Name)
+ entry['Frame'].Name = entry['Player'].Name
+ entry['Frame'].TitleFrame.Title.Text = entry['Player'].Name
+ if(entry['Frame'].BCLabel.Image ~= '') then
+ entry['Frame'].TitleFrame.Title.Position=UDim2.new(.01, 30, .1, 0)
+ end
+ if entry['Player'] == LocalPlayer then
+ entry['Frame'].TitleFrame.DropShadow.Text= entry['Player'].Name
+ ChangeHeaderName(entry['Player'].Name)
+ end
+ BaseUpdate()
+ end
+ PlayerChangedLock=false
+end
+
+function OnFriendshipChanged(player,friendStatus)
+
+ Delay(.5,function()
+ debugprint('friend status changed for:'..player.Name .." ".. tostring(friendStatus) .. " vs " .. tostring(GetFriendStatus(player)) )
+ for _, entry in ipairs(PlayerFrames) do
+ if entry['Player']==player then
+ local nicon = getFriendStatusIcon(friendStatus)
+ if nicon == '' and entry['Frame'].FriendLabel.Image ~= '' then
+ entry['Frame'].TitleFrame.Title.Position=entry['Frame'].TitleFrame.Title.Position-UDim2.new(0,17,0,0)
+ elseif nicon ~= '' and entry['Frame'].FriendLabel.Image == '' then
+ entry['Frame'].TitleFrame.Title.Position=entry['Frame'].TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+ debugprint('confirmed status:'..player.Name)
+ end
+ entry['Frame'].FriendLabel.Image = nicon
+ return
+ end
+ end
+ end)
+end
+
+LocalPlayer.FriendStatusChanged:connect(OnFriendshipChanged)
+
+--[[
+ adds a neutral team if nessisary
+ Note: a lot of redundant code here, might want to refactor to share a function with insertteamframe
+--]]
+function AddNeutralTeam()
+ while NeutralTeamLock do debugprint('in neutral team 2 lock') wait() end
+ NeutralTeamLock = true
+
+ local defaultTeam = Instance.new('Team')
+ defaultTeam.TeamColor = BrickColor.new('White')
+ defaultTeam.Name = 'Neutral'
+ local nentry = {}
+ nentry['MyTeam'] = defaultTeam
+ nentry['MyPlayers'] = {}
+ nentry['Frame'] = MiddleTemplate:Clone()
+ WaitForChild(WaitForChild(nentry['Frame'],'TitleFrame'),'Title').Text = defaultTeam.Name
+ nentry['Frame'].TitleFrame.Position=UDim2.new(nentry['Frame'].TitleFrame.Position.X.Scale,nentry['Frame'].TitleFrame.Position.X.Offset,.1,0)
+ nentry['Frame'].TitleFrame.Size=UDim2.new(nentry['Frame'].TitleFrame.Size.X.Scale,nentry['Frame'].TitleFrame.Size.X.Offset,.8,0)
+ nentry['Frame'].TitleFrame.Title.Font = 'ArialBold'
+ nentry['Frame'].Position = UDim2.new(1,0,((#MiddleFrames) * nentry['Frame'].Size.Y.Scale),0)
+ WaitForChild(nentry['Frame'],'ClickListener').MouseButton1Down:connect(function(nx,ny) StartDrag(nentry,nx,ny) end)
+ nentry['Frame'].ClickListener.BackgroundColor3 = Color3.new(1,1,1)
+ nentry['Frame'].ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nentry['Frame'].ClickListener.AutoButtonColor=false
+ nentry['AutoHide'] = true
+ nentry['IsHidden'] = true
+ for _,i in pairs(PlayerFrames) do
+ if i['Player'].Neutral or not i['MyTeam'] then
+ AddPlayerToTeam(nentry,i)
+ end
+ end
+ if #nentry['MyPlayers'] > 0 then
+ NeutralTeam = nentry
+ UpdateMinimize()
+ BaseUpdate()
+ end
+ NeutralTeamLock = false
+end
+
+function RemoveNeutralTeam()
+ while NeutralTeamLock do debugprint('in neutral team lock') wait() end
+ NeutralTeamLock = true
+ NeutralTeam['Frame']:Destroy()
+ NeutralTeam=nil
+ RemoveMiddleBGFrame()
+ NeutralTeamLock = false
+end
+
+--[[
+
+--]]
+function TeamScoreChanged(entry,nscore)
+ WaitForChild(entry['Frame'],'PlayerScore').Text = tostring(nscore)
+ entry['TeamScore'] = nscore
+end
+--[[
+ called when child added to a team, used for autohide functionality
+ Note: still has teamscore, consiter removing
+--]]
+function TeamChildAdded(entry,nchild)
+ if nchild.Name == 'AutoHide' then
+ entry['AutoHide'] = true
+ elseif nchild.Name == 'TeamScore' then
+ WaitForChild(entry['Frame'],'PlayerScore').Text = tostring(nchild.Value)
+ entry['TeamScore'] = nchild.Value
+ nchild.Changed:connect(function() TeamScoreChanged(entry,nchild.Value) end)
+ end
+end
+--[[
+ called when child added to a team, used for autohide functionality
+ Note: still has teamscore, consiter removing
+--]]
+function TeamChildRemoved(entry,nchild)
+ if nchild.Name == 'AutoHide' then
+ entry['AutoHide'] = false
+ elseif nchild.Name == 'TeamScore' then
+ WaitForChild(entry['Frame'],'PlayerScore').Text = ""
+ entry['TeamScore'] = nil
+ end
+end
+
+function TeamChanged(entry, property)
+ if property=='Name' then
+ WaitForChild(WaitForChild(entry['Frame'],'TitleFrame'),'Title').Text = entry['MyTeam'].Name
+
+ elseif property=='TeamColor' then
+ entry['Frame'].ClickListener.BackgroundColor3 = entry['MyTeam'].TeamColor.Color
+
+ for _,i in pairs(TeamFrames) do
+ if i['MyTeam'].TeamColor == entry['MyTeam'] then
+ RemoveTeamFrame(entry['MyTeam']) --NO DUPLICATE TEAMS!
+ end
+ end
+
+ entry['MyPlayers']={}
+
+ for _,i in pairs(PlayerFrames) do
+ SetPlayerToTeam(i)
+ end
+ BaseUpdate()
+ end
+end
+
+--[[
+ creates team entry and frame for this team, sets up listeners for this team
+ adds any players intended for this team,Creates neutral team if this is the first team added
+ Note:might be best to break this into multiple functions to simplify
+ @Args:
+ nteam new team object added
+--]]
+function InsertTeamFrame(nteam)
+ while AddingFrameLock do debugprint('in adding team frame lock') wait(1/30) end
+ AddingFrameLock = true
+ --for _,i in pairs(TeamFrames) do
+ local nentry = {}
+ nentry['MyTeam'] = nteam
+ nentry['MyPlayers'] = {}
+ nentry['Frame'] = MiddleTemplate:Clone()
+ WaitForChild(WaitForChild(nentry['Frame'],'TitleFrame'),'Title').Text = nteam.Name
+ nentry['Frame'].TitleFrame.Title.Font = 'ArialBold'
+ nentry['Frame'].TitleFrame.Title.FontSize = 'Size18'
+ nentry['Frame'].Position = UDim2.new(0.5,0,((#MiddleFrames) * nentry['Frame'].Size.Y.Scale),0)
+ WaitForChild(nentry['Frame'],'ClickListener').MouseButton1Down:connect(function(nx,ny) StartDrag(nentry,nx,ny) end)
+ nentry['Frame'].ClickListener.BackgroundColor3 = nteam.TeamColor.Color
+ nentry['Frame'].ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nentry['Frame'].ClickListener.AutoButtonColor=false
+ AddId = AddId + 1
+ nentry['ID'] = AddId
+ nentry['AutoHide'] = false
+ if nteam:FindFirstChild('AutoHide') then
+ nentry['AutoHide'] = true
+ end
+ if nteam:FindFirstChild('TeamScore') then
+ TeamChildAdded(nentry,nteam.TeamScore)
+
+ end
+
+ nteam.ChildAdded:connect(function(nchild) TeamChildAdded(nentry,nchild) end)
+ nteam.ChildRemoved:connect(function(nchild) TeamChildRemoved(nentry,nchild) end)
+ nteam.Changed:connect(function(prop) TeamChanged(nentry,prop) end)
+
+ for _,i in pairs(PlayerFrames) do
+ if not i['Player'].Neutral and i['Player'].TeamColor == nteam.TeamColor then
+ AddPlayerToTeam(nentry,i)
+ end
+ end
+ nentry['IsHidden'] = false
+ if not nentry['AutoHide'] or #nentry['MyPlayers'] > 0 then
+ nentry['Frame'].Parent = ListFrame
+ AddMiddleBGFrame()
+ else
+ nentry['IsHidden'] = true
+ nentry['Frame'].Parent = nil
+ end
+
+ table.insert(TeamFrames,nentry)
+ UpdateMinimize()
+ BaseUpdate()
+ if #TeamFrames == 1 and not NeutralTeam then
+ AddNeutralTeam()
+ end
+ AddingFrameLock = false
+end
+--[[
+ removes team from team list
+ @Args:
+ nteam Teamobject to remove
+--]]
+function RemoveTeamFrame(nteam)
+ while AddingFrameLock do debugprint('in removing team frame lock') wait(1/30) end
+ AddingFrameLock = true
+ if IsMinimized.Value then
+ end
+ local myEntry
+ for i,key in ipairs(TeamFrames) do
+ if nteam == key['MyTeam'] then
+ myEntry = key
+ key['Frame']:Destroy()
+ table.remove(TeamFrames,i)
+ end
+ end
+ if #TeamFrames==0 then
+ debugprint('removeteamframe, remove neutral')
+ if NeutralTeam then
+ RemoveNeutralTeam()
+ end
+ end
+ for i,key in ipairs(myEntry['MyPlayers']) do
+ RemovePlayerFromTeam(myEntry,i)
+ PlayerChanged(key, 'TeamColor')
+ end
+ RemoveMiddleBGFrame()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+function TeamAdded(nteam)
+ InsertTeamFrame(nteam)
+end
+
+function TeamRemoved(nteam)
+ RemoveTeamFrame(nteam)
+end
+ ---------------------------------
+--[[
+ called when ANYTHING changes the state of the playerlist
+ re-sorts everything,assures correct positions of all elements
+--]]
+function BaseUpdate()
+ while BaseUpdateLock do debugprint('in baseupdate lock') wait(1/30) end
+ BaseUpdateLock = true
+ --print ('baseupdate')
+ UpdateStatNames()
+
+ if #TeamFrames == 0 and not NeutralTeam then
+ PlayerListModeUpdate()
+ else
+ TeamListModeUpdate()
+ end
+ for i,key in ipairs(MiddleFrames) do
+ if key.Parent ~= nil then
+ key.Position = UDim2.new(.5,0,((#MiddleFrames - (i)) * key.Size.Y.Scale),0)
+ end
+ end
+ if not IsMinimized.Value and #MiddleFrames>DefaultEntriesOnScreen then
+ UpdateScrollPosition()
+ end
+
+ UpdateMinimize()
+
+ UpdateScrollBarSize()
+ UpdateScrollPosition()
+
+ UpdateScrollBarVisibility()
+ --debugprint('EndBaseUpdate')
+ BaseUpdateLock = false
+end
+
+--[[
+ code for attaching tab key to maximizing player list
+--]]
+game.GuiService:AddKey("\t")
+local LastTabTime = time()
+game.GuiService.KeyPressed:connect(
+function(key)
+ if key == "\t" then
+ debugprint('caught tab key')
+ local modalCheck, isModal = pcall(function() return game.GuiService.IsModalDialog end)
+ if modalCheck == false or (modalCheck and isModal == false) then
+ if time() - LastTabTime > 0.4 then
+ LastTabTime = time()
+ if IsTabified.Value then
+ if not IsMaximized.Value then
+ ScreenGui:TweenPosition(UDim2.new(0, 0, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ IsMaximized.Value = true
+ else
+ ScreenGui:TweenPosition(UDim2.new(NormalBounds.X.Scale, NormalBounds.X.Offset-10, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ IsMaximized.Value = false
+ IsMinimized.Value=true
+ end
+ else
+ ToggleMaximize()
+ end
+
+ end
+ end
+ end
+end)
+
+
+function PlayersChildAdded(tplayer)
+ if tplayer:IsA('Player') then
+ Spawn(function() debugPlayerAdd(tplayer) end)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+function coreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.All or coreGuiType == Enum.CoreGuiType.PlayerList then
+ MainFrame.Visible = enabled
+ end
+end
+
+function TeamsChildAdded(nteam)
+ if nteam:IsA('Team') then
+ TeamAdded(nteam)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+function TeamsChildRemoved(nteam)
+ if nteam:IsA('Team') then
+ TeamRemoved(nteam)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+ ----------------------------
+ -- Hookups and initialization
+ ----------------------------
+function debugPlayerAdd(p)
+ InsertPlayerFrame(p)
+end
+
+pcall(function()
+ coreGuiChanged(Enum.CoreGuiType.PlayerList, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.PlayerList))
+ Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+end)
+
+while not game:GetService('Teams') do wait(1/30) debugprint('Waiting For Teams') end
+for _,i in pairs(game.Teams:GetTeams()) do TeamAdded(i) end
+for _,i in pairs(Players:GetPlayers()) do Spawn(function() debugPlayerAdd(i) end) end
+
+game.Teams.ChildAdded:connect(TeamsChildAdded)
+game.Teams.ChildRemoved:connect(TeamsChildRemoved)
+Players.ChildAdded:connect(PlayersChildAdded)
+
+InitReportAbuse()
+AreNamesExpanded.Value = true
+BaseUpdate()
+
+
+
+--UGGGLY,find a better way later
+wait(2)
+IsPersonalServer= not not game.Workspace:FindFirstChild("PSVariable")
+
+ ----------------------------
+ -- Running Logic
+ ----------------------------
+
+ --debug stuffs, will only run for 'newplayerlistisbad'
+ if LocalPlayer.Name == 'newplayerlistisbad' or LocalPlayer.Name == 'imtotallyadmin' then
+ debugFrame.Parent = ScreenGui
+ Spawn(function()
+ while true do
+ local str_players=''
+ for _,i in pairs(game.Players:GetPlayers()) do
+ str_players= str_players .." " .. i.Name
+ end
+ debugplayers.Text=str_players
+ wait(.5)
+ end
+ end)
+ end
+
+
diff --git a/asset/15 b/asset/15
new file mode 100644
index 0000000..18ae689
--- /dev/null
+++ b/asset/15
@@ -0,0 +1,589 @@
+--rbxassetid%15%
+-- This script creates almost all gui elements found in the backpack (warning: there are a lot!)
+-- TODO: automate this process
+
+local ICON_SIZE = 46
+
+local gui = script.Parent
+
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+local function IsPhone()
+ if Game:GetService("GuiService"):GetScreenResolution().Y <= 500 and IsTouchDevice() then
+ return true
+ end
+ return false
+end
+
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+-- First up is the current loadout
+local CurrentLoadout = Instance.new("Frame")
+CurrentLoadout.Name = "CurrentLoadout"
+CurrentLoadout.Position = UDim2.new(0.5, -300, 1, -85)
+CurrentLoadout.Size = UDim2.new(0, 600, 0, ICON_SIZE)
+CurrentLoadout.BackgroundTransparency = 1
+CurrentLoadout.RobloxLocked = true
+CurrentLoadout.Parent = gui
+
+local CLBackground = Instance.new('ImageLabel')
+CLBackground.Name = 'Background';
+CLBackground.Size = UDim2.new(1.2, 0, 1.2, 0);
+CLBackground.Image = "http://www.roblox.com/asset/?id=96536002"
+CLBackground.BackgroundTransparency = 1.0;
+CLBackground.Position = UDim2.new(-0.1, 0, -0.1, 0);
+CLBackground.ZIndex = 0.0;
+CLBackground.Parent = CurrentLoadout
+CLBackground.Visible = false
+
+local Debounce = Instance.new("BoolValue")
+Debounce.Name = "Debounce"
+Debounce.RobloxLocked = true
+Debounce.Parent = CurrentLoadout
+
+local BackpackButton = Instance.new("ImageButton")
+BackpackButton.RobloxLocked = true
+BackpackButton.Visible = false
+BackpackButton.Name = "BackpackButton"
+BackpackButton.BackgroundTransparency = 1
+BackpackButton.Image = "rbxasset://textures/ui/Backpack_Open.png"
+BackpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+BackpackButton.Size = UDim2.new(0, 14, 0, 9)
+waitForChild(gui,"ControlFrame")
+BackpackButton.Parent = gui.ControlFrame
+
+local NumSlots = 9
+
+if IsPhone() then
+ NumSlots = 3
+ CurrentLoadout.Size = UDim2.new(0,180,0,ICON_SIZE)
+ CurrentLoadout.Position = UDim2.new(0.5,-90,1,-85)
+end
+
+for i = 0, NumSlots do
+ local slotFrame = Instance.new("Frame")
+ slotFrame.RobloxLocked = true
+ slotFrame.BackgroundColor3 = Color3.new(0,0,0)
+ slotFrame.BackgroundTransparency = 1
+ slotFrame.BorderColor3 = Color3.new(1, 1, 1)
+ slotFrame.BorderSizePixel = 0
+ slotFrame.Name = "Slot" .. tostring(i)
+ slotFrame.ZIndex = 4.0
+ if i == 0 then
+ slotFrame.Position = UDim2.new(0.9, 48, 0, 0)
+ else
+ slotFrame.Position = UDim2.new((i - 1) * 0.1, (i-1)* 6,0,0)
+ end
+
+
+ slotFrame.Size = UDim2.new(0, ICON_SIZE, 0, ICON_SIZE)
+ slotFrame.Parent = CurrentLoadout
+
+ if gui.AbsoluteSize.Y <= 320 then
+ slotFrame.Position = UDim2.new(0, (i-1)* 60, 0, -50)
+ end
+ if gui.AbsoluteSize.Y <= 320 and i == 0 then
+ slotFrame:Destroy()
+ end
+end
+
+local TempSlot = Instance.new("ImageButton")
+TempSlot.Name = "TempSlot"
+TempSlot.Active = true
+TempSlot.Size = UDim2.new(1,0,1,0)
+TempSlot.BackgroundTransparency = 1.0
+TempSlot.Style = 'Custom'
+TempSlot.Visible = false
+TempSlot.RobloxLocked = true
+TempSlot.Parent = CurrentLoadout
+TempSlot.ZIndex = 3.0
+
+ local slotBackground = Instance.new('Frame')
+ slotBackground.Name = 'Background'
+ slotBackground.BackgroundTransparency = 1.0
+ slotBackground.Style = "DropShadow"
+ slotBackground.Position = UDim2.new(0, -10, 0, -10)
+ slotBackground.Size = UDim2.new(1, 20, 1, 20)
+ slotBackground.Parent = TempSlot
+
+ local HighLight = Instance.new('ImageLabel')
+ HighLight.Name = 'Highlight'
+ HighLight.BackgroundTransparency = 1.0
+ HighLight.Image = 'http://www.roblox.com/asset/?id=97643886'
+ HighLight.Size = UDim2.new(1, 0, 1, 0)
+ --HighLight.Parent = TempSlot
+ HighLight.Visible = false
+
+ -- TempSlot Children
+ local GearReference = Instance.new("ObjectValue")
+ GearReference.Name = "GearReference"
+ GearReference.RobloxLocked = true
+ GearReference.Parent = TempSlot
+
+
+ local ToolTipLabel = Instance.new("TextLabel")
+ ToolTipLabel.Name = "ToolTipLabel"
+ ToolTipLabel.RobloxLocked = true
+ ToolTipLabel.Text = ""
+ ToolTipLabel.BackgroundTransparency = 0.5
+ ToolTipLabel.BorderSizePixel = 0
+ ToolTipLabel.Visible = false
+ ToolTipLabel.TextColor3 = Color3.new(1,1,1)
+ ToolTipLabel.BackgroundColor3 = Color3.new(0,0,0)
+ ToolTipLabel.TextStrokeTransparency = 0
+ ToolTipLabel.Font = Enum.Font.ArialBold
+ ToolTipLabel.FontSize = Enum.FontSize.Size14
+ --ToolTipLabel.TextWrap = true
+ ToolTipLabel.Size = UDim2.new(1,60,0,20)
+ ToolTipLabel.Position = UDim2.new(0,-30,0,-30)
+ ToolTipLabel.Parent = TempSlot
+
+
+ local Kill = Instance.new("BoolValue")
+ Kill.Name = "Kill"
+ Kill.RobloxLocked = true
+ Kill.Parent = TempSlot
+
+ local GearImage = Instance.new("ImageLabel")
+ GearImage.Name = "GearImage"
+ GearImage.BackgroundTransparency = 1
+ GearImage.Position = UDim2.new(0, 0, 0, 0)
+ GearImage.Size = UDim2.new(1, 0, 1, 0)
+ GearImage.ZIndex = 5.0
+ GearImage.RobloxLocked = true
+ GearImage.Parent = TempSlot
+
+ local SlotNumber = Instance.new("TextLabel")
+ SlotNumber.Name = "SlotNumber"
+ SlotNumber.BackgroundTransparency = 1
+ SlotNumber.BorderSizePixel = 0
+ SlotNumber.Font = Enum.Font.ArialBold
+ SlotNumber.FontSize = Enum.FontSize.Size18
+ SlotNumber.Position = UDim2.new(0, 0, 0, 0)
+ SlotNumber.Size = UDim2.new(0,10,0,15)
+ SlotNumber.TextColor3 = Color3.new(1,1,1)
+ SlotNumber.TextTransparency = 0
+ SlotNumber.TextXAlignment = Enum.TextXAlignment.Left
+ SlotNumber.TextYAlignment = Enum.TextYAlignment.Bottom
+ SlotNumber.RobloxLocked = true
+ SlotNumber.Parent = TempSlot
+ SlotNumber.ZIndex = 5
+
+ if IsTouchDevice() then
+ SlotNumber.Visible = false
+ end
+
+ local SlotNumberDownShadow = SlotNumber:Clone()
+ SlotNumberDownShadow.Name = "SlotNumberDownShadow"
+ SlotNumberDownShadow.TextColor3 = Color3.new(0,0,0)
+ SlotNumberDownShadow.Position = UDim2.new(0, 1, 0, -1)
+ SlotNumberDownShadow.Parent = TempSlot
+ SlotNumberDownShadow.ZIndex = 2
+
+ local SlotNumberUpShadow = SlotNumberDownShadow:Clone()
+ SlotNumberUpShadow.Name = "SlotNumberUpShadow"
+ SlotNumberUpShadow.Position = UDim2.new(0, -1, 0, -1)
+ SlotNumberUpShadow.Parent = TempSlot
+
+ local GearText = Instance.new("TextLabel")
+ GearText.RobloxLocked = true
+ GearText.Name = "GearText"
+ GearText.BackgroundTransparency = 1
+ GearText.Font = Enum.Font.Arial
+ GearText.FontSize = Enum.FontSize.Size14
+ GearText.Position = UDim2.new(0,0,0,0)
+ GearText.Size = UDim2.new(1,0,1,0)
+ GearText.Text = ""
+ GearText.TextColor3 = Color3.new(1,1,1)
+ GearText.TextWrap = true
+ GearText.Parent = TempSlot
+ GearText.ZIndex = 5.0
+
+--- Great, now lets make the inventory!
+
+local Backpack = Instance.new("Frame")
+Backpack.RobloxLocked = true
+Backpack.Visible = false
+Backpack.Name = "Backpack"
+Backpack.Position = UDim2.new(0.5, 0, 0.5, 0)
+Backpack.BackgroundColor3 = Color3.new(32/255, 32/255, 32/255)
+Backpack.BackgroundTransparency = 0.5
+Backpack.BorderSizePixel = 0
+Backpack.Parent = gui
+Backpack.Active = true
+
+ -- Backpack Children
+ local SwapSlot = Instance.new("BoolValue")
+ SwapSlot.RobloxLocked = true
+ SwapSlot.Name = "SwapSlot"
+ SwapSlot.Parent = Backpack
+
+ -- SwapSlot Children
+ local Slot = Instance.new("IntValue")
+ Slot.RobloxLocked = true
+ Slot.Name = "Slot"
+ Slot.Parent = SwapSlot
+
+ local GearButton = Instance.new("ObjectValue")
+ GearButton.RobloxLocked = true
+ GearButton.Name = "GearButton"
+ GearButton.Parent = SwapSlot
+
+ local Tabs = Instance.new("Frame")
+ Tabs.Name = "Tabs"
+ Tabs.Visible = false
+ Tabs.Active = false
+ Tabs.RobloxLocked = true
+ Tabs.BackgroundColor3 = Color3.new(0,0,0)
+ Tabs.BackgroundTransparency = 0.08
+ Tabs.BorderSizePixel = 0
+ Tabs.Position = UDim2.new(0,0,-0.1,-4)
+ Tabs.Size = UDim2.new(1,0,0.1,4)
+ Tabs.Parent = Backpack
+
+ -- Tabs Children
+
+ local tabLine = Instance.new("Frame")
+ tabLine.RobloxLocked = true
+ tabLine.Name = "TabLine"
+ tabLine.BackgroundColor3 = Color3.new(53/255, 53/255, 53/255)
+ tabLine.BorderSizePixel = 0
+ tabLine.Position = UDim2.new(0,5,1,-4)
+ tabLine.Size = UDim2.new(1,-10,0,4)
+ tabLine.ZIndex = 2
+ tabLine.Parent = Tabs
+
+ local InventoryButton = Instance.new("TextButton")
+ InventoryButton.RobloxLocked = true
+ InventoryButton.Name = "InventoryButton"
+ InventoryButton.Size = UDim2.new(0,60,0,30)
+ InventoryButton.Position = UDim2.new(0,7,1,-31)
+ InventoryButton.BackgroundColor3 = Color3.new(1,1,1)
+ InventoryButton.BorderColor3 = Color3.new(1,1,1)
+ InventoryButton.Font = Enum.Font.ArialBold
+ InventoryButton.FontSize = Enum.FontSize.Size18
+ InventoryButton.Text = "Gear"
+ InventoryButton.AutoButtonColor = false
+ InventoryButton.TextColor3 = Color3.new(0,0,0)
+ InventoryButton.Selected = true
+ InventoryButton.Active = true
+ InventoryButton.ZIndex = 3
+ InventoryButton.Parent = Tabs
+
+ local closeButton = Instance.new("TextButton")
+ closeButton.RobloxLocked = true
+ closeButton.Name = "CloseButton"
+ closeButton.Font = Enum.Font.ArialBold
+ closeButton.FontSize = Enum.FontSize.Size24
+ closeButton.Position = UDim2.new(1,-33,0,4)
+ closeButton.Size = UDim2.new(0,30,0,30)
+ closeButton.Style = Enum.ButtonStyle.RobloxButton
+ closeButton.Text = ""
+ closeButton.TextColor3 = Color3.new(1,1,1)
+ closeButton.Parent = Tabs
+ closeButton.Modal = true
+
+ --closeButton child
+ local XImage = Instance.new("ImageLabel")
+ XImage.RobloxLocked = true
+ XImage.Name = "XImage"
+ game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id=75547445")
+ XImage.Image = "http://www.roblox.com/asset/?id=75547445" --TODO: move to rbxasset
+ XImage.BackgroundTransparency = 1
+ XImage.Position = UDim2.new(-.25,-1,-.25,-1)
+ XImage.Size = UDim2.new(1.5,2,1.5,2)
+ XImage.ZIndex = 2
+ XImage.Parent = closeButton
+
+ -- Generic Search gui used across backpack
+ local SearchFrame = Instance.new("Frame")
+ SearchFrame.RobloxLocked = true
+ SearchFrame.Name = "SearchFrame"
+ SearchFrame.BackgroundTransparency = 1
+ SearchFrame.Position = UDim2.new(1,-220,0,2)
+ SearchFrame.Size = UDim2.new(0,220,0,24)
+ SearchFrame.Parent = Backpack
+
+ -- SearchFrame Children
+ local SearchButton = Instance.new("ImageButton")
+ SearchButton.RobloxLocked = true
+ SearchButton.Name = "SearchButton"
+ SearchButton.Size = UDim2.new(0,25,0,25)
+ SearchButton.BackgroundTransparency = 1
+ SearchButton.Image = "rbxasset://textures/ui/SearchIcon.png"
+ SearchButton.Parent = SearchFrame
+
+ local SearchBoxFrame = Instance.new("TextButton")
+ SearchBoxFrame.RobloxLocked = true
+ SearchBoxFrame.Position = UDim2.new(0,25,0,-2)
+ SearchBoxFrame.Size = UDim2.new(1,-28,0,30)
+ SearchBoxFrame.Name = "SearchBoxFrame"
+ SearchBoxFrame.Text = ""
+ SearchBoxFrame.Style = Enum.ButtonStyle.RobloxRoundButton
+ SearchBoxFrame.Parent = SearchFrame
+
+ -- SearchBoxFrame Children
+ local SearchBox = Instance.new("TextBox")
+ SearchBox.RobloxLocked = true
+ SearchBox.Name = "SearchBox"
+ SearchBox.BackgroundTransparency = 1
+ SearchBox.Font = Enum.Font.ArialBold
+ SearchBox.FontSize = Enum.FontSize.Size12
+ SearchBox.Position = UDim2.new(0,-5,0,-5)
+ SearchBox.Size = UDim2.new(1,10,1,10)
+ SearchBox.TextColor3 = Color3.new(1,1,1)
+ SearchBox.TextXAlignment = Enum.TextXAlignment.Left
+ SearchBox.ZIndex = 2
+ SearchBox.TextWrap = true
+ SearchBox.Text = "Search..."
+ SearchBox.Parent = SearchBoxFrame
+
+
+ local ResetButton = Instance.new("TextButton")
+ ResetButton.RobloxLocked = true
+ ResetButton.Visible = false
+ ResetButton.Name = "ResetButton"
+ ResetButton.Position = UDim2.new(1,-26,0,3)
+ ResetButton.Size = UDim2.new(0,20,0,20)
+ ResetButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ ResetButton.Text = "X"
+ ResetButton.TextColor3 = Color3.new(1,1,1)
+ ResetButton.Font = Enum.Font.ArialBold
+ ResetButton.FontSize = Enum.FontSize.Size18
+ ResetButton.ZIndex = 3
+ ResetButton.Parent = SearchFrame
+
+------------------------------- GEAR -------------------------------------------------------
+ local Gear = Instance.new("Frame")
+ Gear.Name = "Gear"
+ Gear.RobloxLocked = true
+ Gear.BackgroundTransparency = 1
+ Gear.Size = UDim2.new(1,0,1,0)
+ Gear.ClipsDescendants = true
+ Gear.Parent = Backpack
+
+ -- Gear Children
+ local AssetsList = Instance.new("Frame")
+ AssetsList.RobloxLocked = true
+ AssetsList.Name = "AssetsList"
+ AssetsList.BackgroundTransparency = 1
+ AssetsList.Size = UDim2.new(0.2,0,1,0)
+ AssetsList.Style = Enum.FrameStyle.RobloxSquare
+ AssetsList.Visible = false
+ AssetsList.Parent = Gear
+
+ local GearGrid = Instance.new("Frame")
+ GearGrid.RobloxLocked = true
+ GearGrid.Name = "GearGrid"
+ GearGrid.Size = UDim2.new(0.95, 0, 1, 0)
+ GearGrid.BackgroundTransparency = 1
+ GearGrid.Parent = Gear
+
+
+ local GearButton = Instance.new("ImageButton")
+ GearButton.RobloxLocked = true
+ GearButton.Visible = false
+ GearButton.Name = "GearButton"
+ GearButton.Size = UDim2.new(0, ICON_SIZE, 0, ICON_SIZE)
+ GearButton.Style = 'Custom'
+ GearButton.Parent = GearGrid
+ GearButton.BackgroundTransparency = 1.0
+
+ local slotBackground = Instance.new('Frame')
+ slotBackground.Name = 'Background'
+ slotBackground.BackgroundTransparency = 1.0
+ slotBackground.Size = UDim2.new(1, 16, 1, 16)
+ slotBackground.Position = UDim2.new(0, -8, 0, -8)
+ slotBackground.Parent = GearButton
+ slotBackground.Style = "DropShadow"
+
+
+ -- GearButton Children
+ local GearReference = Instance.new("ObjectValue")
+ GearReference.RobloxLocked = true
+ GearReference.Name = "GearReference"
+ GearReference.Parent = GearButton
+
+ local GreyOutButton = Instance.new("Frame")
+ GreyOutButton.RobloxLocked = true
+ GreyOutButton.Name = "GreyOutButton"
+ GreyOutButton.BackgroundTransparency = 0.5
+ GreyOutButton.Size = UDim2.new(1,0,1,0)
+ GreyOutButton.Active = true
+ GreyOutButton.Visible = false
+ GreyOutButton.ZIndex = 3
+ GreyOutButton.Parent = GearButton
+
+ local GearText = Instance.new("TextLabel")
+ GearText.RobloxLocked = true
+ GearText.Name = "GearText"
+ GearText.BackgroundTransparency = 1
+ GearText.Font = Enum.Font.Arial
+ GearText.FontSize = Enum.FontSize.Size14
+ GearText.Position = UDim2.new(0,-8,0,-8)
+ GearText.Size = UDim2.new(1,16,1,16)
+ GearText.Text = ""
+ GearText.ZIndex = 2
+ GearText.TextColor3 = Color3.new(1,1,1)
+ GearText.TextWrap = true
+ GearText.Parent = GearButton
+
+ local GearGridScrollingArea = Instance.new("Frame")
+ GearGridScrollingArea.RobloxLocked = true
+ GearGridScrollingArea.Name = "GearGridScrollingArea"
+ GearGridScrollingArea.Position = UDim2.new(1, -19, 0, 35)
+ GearGridScrollingArea.Size = UDim2.new(0, 17, 1, -45)
+ GearGridScrollingArea.BackgroundTransparency = 1
+ GearGridScrollingArea.Parent = Gear
+
+ local GearLoadouts = Instance.new("Frame")
+ GearLoadouts.RobloxLocked = true
+ GearLoadouts.Name = "GearLoadouts"
+ GearLoadouts.BackgroundTransparency = 1
+ GearLoadouts.Position = UDim2.new(0.7,23,0.5,1)
+ GearLoadouts.Size = UDim2.new(0.3,-23,0.5,-1)
+ GearLoadouts.Parent = Gear
+ GearLoadouts.Visible = false
+
+ -- GearLoadouts Children
+ local GearLoadoutsHeader = Instance.new("Frame")
+ GearLoadoutsHeader.RobloxLocked = true
+ GearLoadoutsHeader.Name = "GearLoadoutsHeader"
+ GearLoadoutsHeader.BackgroundColor3 = Color3.new(0,0,0)
+ GearLoadoutsHeader.BackgroundTransparency = 0.2
+ GearLoadoutsHeader.BorderColor3 = Color3.new(1,0,0)
+ GearLoadoutsHeader.Size = UDim2.new(1,2,0.15,-1)
+ GearLoadoutsHeader.Parent = GearLoadouts
+
+ -- GearLoadoutsHeader Children
+ local LoadoutsHeaderText = Instance.new("TextLabel")
+ LoadoutsHeaderText.RobloxLocked = true
+ LoadoutsHeaderText.Name = "LoadoutsHeaderText"
+ LoadoutsHeaderText.BackgroundTransparency = 1
+ LoadoutsHeaderText.Font = Enum.Font.ArialBold
+ LoadoutsHeaderText.FontSize = Enum.FontSize.Size18
+ LoadoutsHeaderText.Size = UDim2.new(1,0,1,0)
+ LoadoutsHeaderText.Text = "Loadouts"
+ LoadoutsHeaderText.TextColor3 = Color3.new(1,1,1)
+ LoadoutsHeaderText.Parent = GearLoadoutsHeader
+
+ local GearLoadoutsScrollingArea = GearGridScrollingArea:clone()
+ GearLoadoutsScrollingArea.RobloxLocked = true
+ GearLoadoutsScrollingArea.Name = "GearLoadoutsScrollingArea"
+ GearLoadoutsScrollingArea.Position = UDim2.new(1,-15,0.15,2)
+ GearLoadoutsScrollingArea.Size = UDim2.new(0,17,0.85,-2)
+ GearLoadoutsScrollingArea.Parent = GearLoadouts
+
+ local LoadoutsList = Instance.new("Frame")
+ LoadoutsList.RobloxLocked = true
+ LoadoutsList.Name = "LoadoutsList"
+ LoadoutsList.Position = UDim2.new(0,0,0.15,2)
+ LoadoutsList.Size = UDim2.new(1,-17,0.85,-2)
+ LoadoutsList.Style = Enum.FrameStyle.RobloxSquare
+ LoadoutsList.Parent = GearLoadouts
+
+ local GearPreview = Instance.new("Frame")
+ GearPreview.RobloxLocked = true
+ GearPreview.Name = "GearPreview"
+ GearPreview.Position = UDim2.new(0.7,23,0,0)
+ GearPreview.Size = UDim2.new(0.3,-28,0.5,-1)
+ GearPreview.BackgroundTransparency = 1
+ GearPreview.ZIndex = 7
+ GearPreview.Parent = Gear
+
+ -- GearPreview Children
+ local GearStats = Instance.new("Frame")
+ GearStats.RobloxLocked = true
+ GearStats.Name = "GearStats"
+ GearStats.BackgroundTransparency = 1
+ GearStats.Position = UDim2.new(0,0,0.75,0)
+ GearStats.Size = UDim2.new(1,0,0.25,0)
+ GearStats.ZIndex = 8
+ GearStats.Parent = GearPreview
+
+ -- GearStats Children
+ local GearName = Instance.new("TextLabel")
+ GearName.RobloxLocked = true
+ GearName.Name = "GearName"
+ GearName.BackgroundTransparency = 1
+ GearName.Font = Enum.Font.ArialBold
+ GearName.FontSize = Enum.FontSize.Size18
+ GearName.Position = UDim2.new(0,-3,0,0)
+ GearName.Size = UDim2.new(1,6,1,5)
+ GearName.Text = ""
+ GearName.TextColor3 = Color3.new(1,1,1)
+ GearName.TextWrap = true
+ GearName.ZIndex = 9
+ GearName.Parent = GearStats
+
+ local GearImage = Instance.new("ImageLabel")
+ GearImage.RobloxLocked = true
+ GearImage.Name = "GearImage"
+ GearImage.Image = ""
+ GearImage.BackgroundTransparency = 1
+ GearImage.Position = UDim2.new(0.125,0,0,0)
+ GearImage.Size = UDim2.new(0.75,0,0.75,0)
+ GearImage.ZIndex = 8
+ GearImage.Parent = GearPreview
+
+ --GearImage Children
+ local GearIcons = Instance.new("Frame")
+ GearIcons.BackgroundColor3 = Color3.new(0,0,0)
+ GearIcons.BackgroundTransparency = 0.5
+ GearIcons.BorderSizePixel = 0
+ GearIcons.RobloxLocked = true
+ GearIcons.Name = "GearIcons"
+ GearIcons.Position = UDim2.new(0.4,2,0.85,-2)
+ GearIcons.Size = UDim2.new(0.6,0,0.15,0)
+ GearIcons.Visible = false
+ GearIcons.ZIndex = 9
+ GearIcons.Parent = GearImage
+
+ -- GearIcons Children
+ local GenreImage = Instance.new("ImageLabel")
+ GenreImage.RobloxLocked = true
+ GenreImage.Name = "GenreImage"
+ GenreImage.BackgroundColor3 = Color3.new(102/255,153/255,1)
+ GenreImage.BackgroundTransparency = 0.5
+ GenreImage.BorderSizePixel = 0
+ GenreImage.Size = UDim2.new(0.25,0,1,0)
+ GenreImage.Parent = GearIcons
+
+ local AttributeOneImage = GenreImage:clone()
+ AttributeOneImage.RobloxLocked = true
+ AttributeOneImage.Name = "AttributeOneImage"
+ AttributeOneImage.BackgroundColor3 = Color3.new(1,51/255,0)
+ AttributeOneImage.Position = UDim2.new(0.25,0,0,0)
+ AttributeOneImage.Parent = GearIcons
+
+ local AttributeTwoImage = GenreImage:clone()
+ AttributeTwoImage.RobloxLocked = true
+ AttributeTwoImage.Name = "AttributeTwoImage"
+ AttributeTwoImage.BackgroundColor3 = Color3.new(153/255,1,153/255)
+ AttributeTwoImage.Position = UDim2.new(0.5,0,0,0)
+ AttributeTwoImage.Parent = GearIcons
+
+ local AttributeThreeImage = GenreImage:clone()
+ AttributeThreeImage.RobloxLocked = true
+ AttributeThreeImage.Name = "AttributeThreeImage"
+ AttributeThreeImage.BackgroundColor3 = Color3.new(0,0.5,0.5)
+ AttributeThreeImage.Position = UDim2.new(0.75,0,0,0)
+ AttributeThreeImage.Parent = GearIcons
+
+script:Destroy()
\ No newline at end of file
diff --git a/asset/16 b/asset/16
new file mode 100644
index 0000000..4473b36
--- /dev/null
+++ b/asset/16
@@ -0,0 +1,417 @@
+--rbxassetid%16%
+-- This script manages context switches in the backpack (Gear to Wardrobe, etc.) and player state changes. Also manages global functions across different tabs (currently only search)
+
+-- basic functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+-- don't do anything if we are in an empty game
+waitForChild(game,"Players")
+if #game.Players:GetChildren() < 1 then
+ game.Players.ChildAdded:wait()
+end
+-- make sure everything is loaded in before we do anything
+-- get our local player
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+
+
+------------------------ Locals ------------------------------
+local backpack = script.Parent
+waitForChild(backpack,"Gear")
+
+local screen = script.Parent.Parent
+assert(screen:IsA("ScreenGui"))
+
+waitForChild(backpack, "Tabs")
+waitForChild(backpack.Tabs, "CloseButton")
+local closeButton = backpack.Tabs.CloseButton
+
+waitForChild(backpack.Tabs, "InventoryButton")
+local inventoryButton = backpack.Tabs.InventoryButton
+
+waitForChild(backpack.Parent,"ControlFrame")
+local backpackButton = waitForChild(backpack.Parent.ControlFrame,"BackpackButton")
+local currentTab = "gear"
+
+local searchFrame = waitForChild(backpack,"SearchFrame")
+waitForChild(backpack.SearchFrame,"SearchBoxFrame")
+local searchBox = waitForChild(backpack.SearchFrame.SearchBoxFrame,"SearchBox")
+local searchButton = waitForChild(backpack.SearchFrame,"SearchButton")
+local resetButton = waitForChild(backpack.SearchFrame,"ResetButton")
+
+local robloxGui = waitForChild(Game.CoreGui, 'RobloxGui')
+local currentLoadout = waitForChild(robloxGui, 'CurrentLoadout')
+
+local canToggle = true
+local readyForNextEvent = true
+local backpackIsOpen = false
+local active = true
+local disabledByDeveloper = false
+
+local humanoidDiedCon = nil
+
+local backpackButtonPos
+
+local guiTweenSpeed = 0.25 -- how quickly we open/close the backpack
+
+local searchDefaultText = "Search..."
+local tilde = "~"
+local backquote = "`"
+
+local backpackSize = UDim2.new(0, 600, 0, 400)
+
+if robloxGui.AbsoluteSize.Y <= 500 then
+ backpackSize = UDim2.new(0, 200, 0, 140)
+end
+
+
+------------------------ End Locals ---------------------------
+
+
+---------------------------------------- Public Event Setup ----------------------------------------
+
+function createPublicEvent(eventName)
+ assert(eventName, "eventName is nil")
+ assert(tostring(eventName),"eventName is not a string")
+
+ local newEvent = Instance.new("BindableEvent")
+ newEvent.Name = tostring(eventName)
+ newEvent.Parent = script
+
+ return newEvent
+end
+
+function createPublicFunction(funcName, invokeFunc)
+ assert(funcName, "funcName is nil")
+ assert(tostring(funcName), "funcName is not a string")
+ assert(invokeFunc, "invokeFunc is nil")
+ assert(type(invokeFunc) == "function", "invokeFunc should be of type 'function'")
+
+ local newFunction = Instance.new("BindableFunction")
+ newFunction.Name = tostring(funcName)
+ newFunction.OnInvoke = invokeFunc
+ newFunction.Parent = script
+
+ return newFunction
+end
+
+-- Events
+local resizeEvent = createPublicEvent("ResizeEvent")
+local backpackOpenEvent = createPublicEvent("BackpackOpenEvent")
+local backpackCloseEvent = createPublicEvent("BackpackCloseEvent")
+local tabClickedEvent = createPublicEvent("TabClickedEvent")
+local searchRequestedEvent = createPublicEvent("SearchRequestedEvent")
+---------------------------------------- End Public Event Setup ----------------------------------------
+
+
+
+--------------------------- Internal Functions ----------------------------------------
+
+function deactivateBackpack()
+ backpack.Visible = false
+ active = false
+end
+
+function activateBackpack()
+ initHumanoidDiedConnections()
+ active = true
+ backpack.Visible = backpackIsOpen
+ if backpackIsOpen then
+ toggleBackpack()
+ end
+end
+
+function initHumanoidDiedConnections()
+ if humanoidDiedCon then
+ humanoidDiedCon:disconnect()
+ end
+ waitForProperty(game.Players.LocalPlayer,"Character")
+ waitForChild(game.Players.LocalPlayer.Character,"Humanoid")
+ humanoidDiedCon = game.Players.LocalPlayer.Character.Humanoid.Died:connect(deactivateBackpack)
+end
+
+local hideBackpack = function()
+ backpackIsOpen = false
+ readyForNextEvent = false
+ backpackButton.Selected = false
+ resetSearch()
+ backpackCloseEvent:Fire(currentTab)
+ backpack.Tabs.Visible = false
+ searchFrame.Visible = false
+ backpack:TweenSizeAndPosition(UDim2.new(0, backpackSize.X.Offset,0, 0), UDim2.new(0.5, -backpackSize.X.Offset/2, 1, -85), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, guiTweenSpeed, true,
+ function()
+ game.GuiService:RemoveCenterDialog(backpack)
+ backpack.Visible = false
+ backpackButton.Selected = false
+ end)
+ delay(guiTweenSpeed,function()
+ game.GuiService:RemoveCenterDialog(backpack)
+ backpack.Visible = false
+ backpackButton.Selected = false
+ readyForNextEvent = true
+ canToggle = true
+ end)
+end
+
+function showBackpack()
+ game.GuiService:AddCenterDialog(backpack, Enum.CenterDialogType.PlayerInitiatedDialog,
+ function()
+ backpack.Visible = true
+ backpackButton.Selected = true
+ end,
+ function()
+ backpack.Visible = false
+ backpackButton.Selected = false
+ end)
+ backpack.Visible = true
+ backpackButton.Selected = true
+ backpack:TweenSizeAndPosition(backpackSize, UDim2.new(0.5, -backpackSize.X.Offset/2, 1, -backpackSize.Y.Offset - 88), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, guiTweenSpeed, true)
+ delay(guiTweenSpeed,function()
+ backpack.Tabs.Visible = false
+ searchFrame.Visible = true
+ backpackOpenEvent:Fire(currentTab)
+ canToggle = true
+ readyForNextEvent = true
+ backpackButton.Image = "rbxasset://textures/ui/Backpack_Close.png"
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -backpackSize.Y.Offset - 108)
+ end)
+end
+
+function toggleBackpack()
+ if not game.Players.LocalPlayer then return end
+ if not game.Players.LocalPlayer["Character"] then return end
+ if not canToggle then return end
+ if not readyForNextEvent then return end
+ readyForNextEvent = false
+ canToggle = false
+
+ backpackIsOpen = not backpackIsOpen
+
+ if backpackIsOpen then
+ showBackpack()
+ else
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+ backpackButton.Selected = false
+ backpackButton.Image = "rbxasset://textures/ui/Backpack_Open.png"
+ hideBackpack()
+
+
+ local clChildren = currentLoadout:GetChildren()
+ for i = 1, #clChildren do
+ if clChildren[i] and clChildren[i]:IsA('Frame') then
+ local frame = clChildren[i]
+ if #frame:GetChildren() > 0 then
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -108)
+ backpackButton.Visible = true
+ if frame:GetChildren()[1]:IsA('ImageButton') then
+ local imgButton = frame:GetChildren()[1]
+ imgButton.Active = true
+ imgButton.Draggable = false
+ end
+ end
+ end
+ end
+
+ end
+end
+
+function closeBackpack()
+ if backpackIsOpen then
+ toggleBackpack()
+ end
+end
+
+function setSelected(tab)
+ assert(tab)
+ assert(tab:IsA("TextButton"))
+
+ tab.BackgroundColor3 = Color3.new(1,1,1)
+ tab.TextColor3 = Color3.new(0,0,0)
+ tab.Selected = true
+ tab.ZIndex = 3
+end
+
+function setUnselected(tab)
+ assert(tab)
+ assert(tab:IsA("TextButton"))
+
+ tab.BackgroundColor3 = Color3.new(0,0,0)
+ tab.TextColor3 = Color3.new(1,1,1)
+ tab.Selected = false
+ tab.ZIndex = 1
+end
+
+function updateTabGui(selectedTab)
+ assert(selectedTab)
+
+ if selectedTab == "gear" then
+ setSelected(inventoryButton)
+ elseif selectedTab == "wardrobe" then
+ setUnselected(inventoryButton)
+ end
+end
+
+function mouseLeaveTab(button)
+ assert(button)
+ assert(button:IsA("TextButton"))
+
+ if button.Selected then return end
+
+ button.BackgroundColor3 = Color3.new(0,0,0)
+end
+
+function mouseOverTab(button)
+ assert(button)
+ assert(button:IsA("TextButton"))
+
+ if button.Selected then return end
+
+ button.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+end
+
+function newTabClicked(tabName)
+ assert(tabName)
+ tabName = string.lower(tabName)
+ currentTab = tabName
+
+ updateTabGui(tabName)
+ tabClickedEvent:Fire(tabName)
+ resetSearch()
+end
+
+function trim(s)
+ return (s:gsub("^%s*(.-)%s*$", "%1"))
+end
+
+function splitByWhitespace(text)
+ if type(text) ~= "string" then return nil end
+
+ local terms = {}
+ for token in string.gmatch(text, "[^%s]+") do
+ if string.len(token) > 0 then
+ table.insert(terms,token)
+ end
+ end
+ return terms
+end
+
+function resetSearchBoxGui()
+ resetButton.Visible = false
+ searchBox.Text = searchDefaultText
+end
+
+function doSearch()
+ local searchText = searchBox.Text
+ if searchText == "" then
+ resetSearch()
+ return
+ end
+ searchText = trim(searchText)
+ resetButton.Visible = true
+ termTable = splitByWhitespace(searchText)
+ searchRequestedEvent:Fire(searchText) -- todo: replace this with termtable when table passing is possible
+end
+
+function resetSearch()
+ resetSearchBoxGui()
+ searchRequestedEvent:Fire()
+end
+
+local backpackReady = function()
+ readyForNextEvent = true
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ active = enabled
+ disabledByDeveloper = not enabled
+
+ if disabledByDeveloper then
+ game:GetService("GuiService"):RemoveKey(tilde)
+ game:GetService("GuiService"):RemoveKey(backquote)
+ else
+ game:GetService("GuiService"):AddKey(tilde)
+ game:GetService("GuiService"):AddKey(backquote)
+ end
+
+ resetSearch()
+ searchFrame.Visible = enabled and backpackIsOpen
+
+ currentLoadout.Visible = enabled
+ backpack.Visible = false
+ backpackButton.Visible = enabled
+ end
+end
+
+--------------------------- End Internal Functions -------------------------------------
+
+
+------------------------------ Public Functions Setup -------------------------------------
+createPublicFunction("CloseBackpack", hideBackpack)
+createPublicFunction("BackpackReady", backpackReady)
+------------------------------ End Public Functions Setup ---------------------------------
+
+
+------------------------ Connections/Script Main -------------------------------------------
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+inventoryButton.MouseButton1Click:connect(function() newTabClicked("gear") end)
+inventoryButton.MouseEnter:connect(function() mouseOverTab(inventoryButton) end)
+inventoryButton.MouseLeave:connect(function() mouseLeaveTab(inventoryButton) end)
+
+closeButton.MouseButton1Click:connect(closeBackpack)
+
+screen.Changed:connect(function(prop)
+ if prop == "AbsoluteSize" then
+ resizeEvent:Fire(screen.AbsoluteSize)
+ end
+end)
+
+-- GuiService key setup
+game:GetService("GuiService"):AddKey(tilde)
+game:GetService("GuiService"):AddKey(backquote)
+game:GetService("GuiService").KeyPressed:connect(function(key)
+ if not active or disabledByDeveloper then return end
+ if key == tilde or key == backquote then
+ toggleBackpack()
+ end
+end)
+backpackButton.MouseButton1Click:connect(function()
+ if not active or disabledByDeveloper then return end
+ toggleBackpack()
+end)
+
+if game.Players.LocalPlayer["Character"] then
+ activateBackpack()
+end
+
+game.Players.LocalPlayer.CharacterAdded:connect(activateBackpack)
+
+-- search functions
+searchBox.FocusLost:connect(function(enterPressed)
+ if enterPressed or searchBox.Text ~= "" then
+ doSearch()
+ elseif searchBox.Text == "" then
+ resetSearch()
+ end
+end)
+searchButton.MouseButton1Click:connect(doSearch)
+resetButton.MouseButton1Click:connect(resetSearch)
+
+if searchFrame and robloxGui.AbsoluteSize.Y <= 500 then
+ searchFrame.RobloxLocked = false
+ searchFrame:Destroy()
+end
\ No newline at end of file
diff --git a/asset/17 b/asset/17
new file mode 100644
index 0000000..a8badb7
--- /dev/null
+++ b/asset/17
@@ -0,0 +1,872 @@
+--rbxassetid%17%
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ assert(instance)
+ assert(name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ assert(instance)
+ assert(property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+local RbxGui, msg = LoadLibrary("RbxGui")
+if not RbxGui then print("could not find RbxGui!") return end
+
+--- Begin Locals
+local StaticTabName = "gear"
+
+local backpack = script.Parent
+local screen = script.Parent.Parent
+
+local backpackItems = {}
+local buttons = {}
+
+local debounce = false
+local browsingMenu = false
+
+local mouseEnterCons = {}
+local mouseClickCons = {}
+
+local characterChildAddedCon = nil
+local characterChildRemovedCon = nil
+local backpackAddCon = nil
+
+local playerBackpack = waitForChild(player,"Backpack")
+
+waitForChild(backpack,"Tabs")
+
+waitForChild(backpack,"Gear")
+local gearPreview = waitForChild(backpack.Gear,"GearPreview")
+
+local scroller = waitForChild(backpack.Gear,"GearGridScrollingArea")
+
+local currentLoadout = waitForChild(backpack.Parent,"CurrentLoadout")
+
+local grid = waitForChild(backpack.Gear,"GearGrid")
+local gearButton = waitForChild(grid,"GearButton")
+
+local swapSlot = waitForChild(script.Parent,"SwapSlot")
+
+local backpackManager = waitForChild(script.Parent,"CoreScripts/BackpackScripts/BackpackManager")
+local backpackOpenEvent = waitForChild(backpackManager,"BackpackOpenEvent")
+local backpackCloseEvent = waitForChild(backpackManager,"BackpackCloseEvent")
+local tabClickedEvent = waitForChild(backpackManager,"TabClickedEvent")
+local resizeEvent = waitForChild(backpackManager,"ResizeEvent")
+local searchRequestedEvent = waitForChild(backpackManager,"SearchRequestedEvent")
+local tellBackpackReadyFunc = waitForChild(backpackManager,"BackpackReady")
+
+-- creating scroll bar early as to make sure items get placed correctly
+local scrollFrame, scrollUp, scrollDown, recalculateScroll = RbxGui.CreateScrollingFrame(nil, "grid", Vector2.new(6, 6))
+
+scrollFrame.Position = UDim2.new(0,0,0,30)
+scrollFrame.Size = UDim2.new(1,0,1,-30)
+scrollFrame.Parent = backpack.Gear.GearGrid
+
+local scrollBar = Instance.new("Frame")
+scrollBar.Name = "ScrollBar"
+scrollBar.BackgroundTransparency = 0.9
+scrollBar.BackgroundColor3 = Color3.new(1,1,1)
+scrollBar.BorderSizePixel = 0
+scrollBar.Size = UDim2.new(0, 17, 1, -36)
+scrollBar.Position = UDim2.new(0,0,0,18)
+scrollBar.Parent = scroller
+
+scrollDown.Position = UDim2.new(0,0,1,-17)
+
+scrollUp.Parent = scroller
+scrollDown.Parent = scroller
+
+local scrollFrameLoadout, scrollUpLoadout, scrollDownLoadout, recalculateScrollLoadout = RbxGui.CreateScrollingFrame()
+
+scrollFrameLoadout.Position = UDim2.new(0,0,0,0)
+scrollFrameLoadout.Size = UDim2.new(1,0,1,0)
+scrollFrameLoadout.Parent = backpack.Gear.GearLoadouts.LoadoutsList
+
+local LoadoutButton = Instance.new("TextButton")
+LoadoutButton.RobloxLocked = true
+LoadoutButton.Name = "LoadoutButton"
+LoadoutButton.Font = Enum.Font.ArialBold
+LoadoutButton.FontSize = Enum.FontSize.Size14
+LoadoutButton.Position = UDim2.new(0,0,0,0)
+LoadoutButton.Size = UDim2.new(1,0,0,32)
+LoadoutButton.Style = Enum.ButtonStyle.RobloxButton
+LoadoutButton.Text = "Loadout #1"
+LoadoutButton.TextColor3 = Color3.new(1,1,1)
+LoadoutButton.Parent = scrollFrameLoadout
+
+local LoadoutButtonTwo = LoadoutButton:clone()
+LoadoutButtonTwo.Text = "Loadout #2"
+LoadoutButtonTwo.Parent = scrollFrameLoadout
+
+local LoadoutButtonThree = LoadoutButton:clone()
+LoadoutButtonThree.Text = "Loadout #3"
+LoadoutButtonThree.Parent = scrollFrameLoadout
+
+local LoadoutButtonFour = LoadoutButton:clone()
+LoadoutButtonFour.Text = "Loadout #4"
+LoadoutButtonFour.Parent = scrollFrameLoadout
+
+local scrollBarLoadout = Instance.new("Frame")
+scrollBarLoadout.Name = "ScrollBarLoadout"
+scrollBarLoadout.BackgroundTransparency = 0.9
+scrollBarLoadout.BackgroundColor3 = Color3.new(1,1,1)
+scrollBarLoadout.BorderSizePixel = 0
+scrollBarLoadout.Size = UDim2.new(0, 17, 1, -36)
+scrollBarLoadout.Position = UDim2.new(0,0,0,18)
+scrollBarLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+
+scrollDownLoadout.Position = UDim2.new(0,0,1,-17)
+
+scrollUpLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+scrollDownLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+
+
+-- Begin Functions
+function removeFromMap(map,object)
+ for i = 1, #map do
+ if map[i] == object then
+ table.remove(map,i)
+ break
+ end
+ end
+end
+
+function robloxLock(instance)
+ instance.RobloxLocked = true
+ children = instance:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ robloxLock(child)
+ end
+ end
+end
+
+function resize()
+ local size = 0
+ if gearPreview.AbsoluteSize.Y > gearPreview.AbsoluteSize.X then
+ size = gearPreview.AbsoluteSize.X * 0.75
+ else
+ size = gearPreview.AbsoluteSize.Y * 0.75
+ end
+
+ waitForChild(gearPreview,"GearImage")
+ gearPreview.GearImage.Size = UDim2.new(0,size,0,size)
+ gearPreview.GearImage.Position = UDim2.new(0,gearPreview.AbsoluteSize.X/2 - size/2,0.75,-size)
+
+ resizeGrid()
+end
+
+function addToGrid(child)
+ if not child:IsA("Tool") then
+ if not child:IsA("HopperBin") then
+ return
+ end
+ end
+ if child:FindFirstChild("RobloxBuildTool") then return end
+
+ for i,v in pairs(backpackItems) do -- check to see if we already have this gear registered
+ if v == child then return end
+ end
+
+ table.insert(backpackItems,child)
+
+ local changeCon = child.Changed:connect(function(prop)
+ if prop == "Name" then
+ if buttons[child] then
+ if buttons[child].Image == "" then
+ buttons[child].GearText.Text = child.Name
+ end
+ end
+ end
+ end)
+ local ancestryCon = nil
+ ancestryCon = child.AncestryChanged:connect(function(theChild,theParent)
+ local thisObject = nil
+ for k,v in pairs(backpackItems) do
+ if v == child then
+ thisObject = v
+ break
+ end
+ end
+
+ waitForProperty(player,"Character")
+ waitForChild(player,"Backpack")
+ if (child.Parent ~= player.Backpack and child.Parent ~= player.Character) then
+ if ancestryCon then ancestryCon:disconnect() end
+ if changeCon then changeCon:disconnect() end
+
+ for k,v in pairs(backpackItems) do
+ if v == thisObject then
+ if mouseEnterCons[buttons[v]] then mouseEnterCons[buttons[v]]:disconnect() end
+ if mouseClickCons[buttons[v]] then mouseClickCons[buttons[v]]:disconnect() end
+ buttons[v].Parent = nil
+ buttons[v] = nil
+ break
+ end
+ end
+
+ removeFromMap(backpackItems,thisObject)
+
+ resizeGrid()
+ else
+ resizeGrid()
+ end
+ updateGridActive()
+ end)
+ resizeGrid()
+end
+
+function buttonClick(button)
+ if button:FindFirstChild("UnequipContextMenu") and not button.Active then
+ button.UnequipContextMenu.Visible = true
+ browsingMenu = true
+ end
+end
+
+function previewGear(button)
+ if not browsingMenu then
+ gearPreview.Visible = false
+ gearPreview.GearImage.Image = button.Image
+ gearPreview.GearStats.GearName.Text = button.GearReference.Value.Name
+ end
+end
+
+function findEmptySlot()
+ local smallestNum = nil
+ local loadout = currentLoadout:GetChildren()
+ for i = 1, #loadout do
+ if loadout[i]:IsA("Frame") and #loadout[i]:GetChildren() <= 0 then
+ local frameNum = tonumber(string.sub(loadout[i].Name,5))
+ if frameNum == 0 then frameNum = 10 end
+ if not smallestNum or (smallestNum > frameNum) then
+ smallestNum = frameNum
+ end
+ end
+ end
+ if smallestNum == 10 then smallestNum = 0 end
+ return smallestNum
+end
+
+function checkForSwap(button,x,y)
+ local loadoutChildren = currentLoadout:GetChildren()
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and string.find(loadoutChildren[i].Name,"Slot") then
+ if x >= loadoutChildren[i].AbsolutePosition.x and x <= (loadoutChildren[i].AbsolutePosition.x + loadoutChildren[i].AbsoluteSize.x) then
+ if y >= loadoutChildren[i].AbsolutePosition.y and y <= (loadoutChildren[i].AbsolutePosition.y + loadoutChildren[i].AbsoluteSize.y) then
+ local slot = tonumber(string.sub(loadoutChildren[i].Name,5))
+ swapGearSlot(slot,button)
+ return true
+ end
+ end
+ end
+ end
+ return false
+end
+
+function resizeGrid()
+ for k,v in pairs(backpackItems) do
+ if not v:FindFirstChild("RobloxBuildTool") then
+ if not buttons[v] then
+ local buttonClone = gearButton:clone()
+ buttonClone.Parent = grid.ScrollingFrame
+ buttonClone.Visible = true
+ buttonClone.Image = v.TextureId
+ if buttonClone.Image == "" then
+ buttonClone.GearText.Text = v.Name
+ end
+
+ buttonClone.GearReference.Value = v
+ buttonClone.Draggable = true
+ buttons[v] = buttonClone
+
+
+ if not IsTouchDevice() then
+ local unequipMenu = getGearContextMenu()
+
+
+ unequipMenu.Visible = false
+ unequipMenu.Parent = buttonClone
+ end
+
+ local beginPos = nil
+ buttonClone.DragBegin:connect(function(value)
+ waitForChild(buttonClone, 'Background')
+ buttonClone['Background'].ZIndex = 10
+ buttonClone.ZIndex = 10
+ beginPos = value
+ end)
+ buttonClone.DragStopped:connect(function(x,y)
+ waitForChild(buttonClone, 'Background')
+ buttonClone['Background'].ZIndex = 1.0
+ buttonClone.ZIndex = 2
+ if beginPos ~= buttonClone.Position then
+ if not checkForSwap(buttonClone,x,y) then
+ buttonClone:TweenPosition(beginPos,Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.5, true)
+ buttonClone.Draggable = false
+ delay(0.5,function()
+ buttonClone.Draggable = true
+ end)
+ else
+ buttonClone.Position = beginPos
+ end
+ end
+ end)
+ local clickTime = tick()
+ mouseEnterCons[buttonClone] = buttonClone.MouseEnter:connect(function() previewGear(buttonClone) end)
+ mouseClickCons[buttonClone] = buttonClone.MouseButton1Click:connect(function()
+ local newClickTime = tick()
+ if buttonClone.Active and (newClickTime - clickTime) < 0.5 then
+ local slot = findEmptySlot()
+ if slot then
+ buttonClone.ZIndex = 1
+ swapGearSlot(slot,buttonClone)
+ end
+ else
+ buttonClick(buttonClone)
+ end
+ clickTime = newClickTime
+ end)
+ end
+ end
+ end
+ recalculateScroll()
+end
+
+function showPartialGrid(subset)
+ for k,v in pairs(buttons) do
+ v.Parent = nil
+ end
+ if subset then
+ for k,v in pairs(subset) do
+ v.Parent = grid.ScrollingFrame
+ end
+ end
+ recalculateScroll()
+end
+
+function showEntireGrid()
+ for k,v in pairs(buttons) do
+ v.Parent = grid.ScrollingFrame
+ end
+ recalculateScroll()
+end
+
+function inLoadout(gear)
+ local children = currentLoadout:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("Frame") then
+ local button = children[i]:GetChildren()
+ if #button > 0 then
+ if button[1].GearReference.Value and button[1].GearReference.Value == gear then
+ return true
+ end
+ end
+ end
+ end
+ return false
+end
+
+function updateGridActive()
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ local gear = nil
+ local gearRef = buttons[v]:FindFirstChild("GearReference")
+
+ if gearRef then gear = gearRef.Value end
+
+ if not gear then
+ buttons[v].Active = false
+ elseif inLoadout(gear) then
+ buttons[v].Active = false
+ else
+ buttons[v].Active = true
+ end
+ end
+ end
+end
+
+function centerGear(loadoutChildren)
+ local gearButtons = {}
+ local lastSlotAdd = nil
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and #loadoutChildren[i]:GetChildren() > 0 then
+ if loadoutChildren[i].Name == "Slot0" then
+ lastSlotAdd = loadoutChildren[i]
+ else
+ table.insert(gearButtons, loadoutChildren[i])
+ end
+ end
+ end
+ if lastSlotAdd then table.insert(gearButtons,lastSlotAdd) end
+
+ local startPos = ( 1 - (#gearButtons * 0.1) ) / 2
+ for i = 1, #gearButtons do
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + ((i - 1) * 0.1),0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+end
+
+function tabClickHandler(tabName)
+ if tabName == StaticTabName then
+ backpackOpenHandler(tabName)
+ else
+ backpackCloseHandler(tabName)
+ end
+end
+
+function backpackOpenHandler(currentTab)
+ if currentTab and currentTab ~= StaticTabName then
+ backpack.Gear.Visible = false
+ return
+ end
+
+ backpack.Gear.Visible = true
+ updateGridActive()
+
+ resizeGrid()
+ resize()
+ tellBackpackReadyFunc:Invoke()
+end
+
+function backpackCloseHandler(currentTab)
+ if currentTab and currentTab ~= StaticTabName then
+ backpack.Gear.Visible = false
+ return
+ end
+
+ backpack.Gear.Visible = false
+
+ resizeGrid()
+ resize()
+ tellBackpackReadyFunc:Invoke()
+end
+
+function loadoutCheck(child, selectState)
+ if not child:IsA("ImageButton") then return end
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ if child:FindFirstChild("GearReference") and buttons[v]:FindFirstChild("GearReference") then
+ if buttons[v].GearReference.Value == child.GearReference.Value then
+ buttons[v].Active = selectState
+ break
+ end
+ end
+ end
+ end
+end
+
+function clearPreview()
+ gearPreview.GearImage.Image = ""
+ gearPreview.GearStats.GearName.Text = ""
+end
+
+function removeAllEquippedGear(physGear)
+ local stuff = player.Character:GetChildren()
+ for i = 1, #stuff do
+ if ( stuff[i]:IsA("Tool") or stuff[i]:IsA("HopperBin") ) and stuff[i] ~= physGear then
+ stuff[i].Parent = playerBackpack
+ end
+ end
+end
+
+function equipGear(physGear)
+ removeAllEquippedGear(physGear)
+ physGear.Parent = player.Character
+ updateGridActive()
+end
+
+function unequipGear(physGear)
+ physGear.Parent = playerBackpack
+ updateGridActive()
+end
+
+function highlight(button)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundColor3 = Color3.new(0.8,0.8,0.8)
+end
+function clearHighlight(button)
+ button.TextColor3 = Color3.new(1,1,1)
+ button.BackgroundColor3 = Color3.new(0,0,0)
+end
+
+function swapGearSlot(slot,gearButton)
+ if not swapSlot.Value then -- signal loadout to swap a gear out
+ swapSlot.Slot.Value = slot
+ swapSlot.GearButton.Value = gearButton
+ swapSlot.Value = true
+ updateGridActive()
+ end
+end
+
+
+local UnequipGearMenuClick = function(element, menu)
+ if type(element.Action) ~= "number" then return end
+ local num = element.Action
+ if num == 1 then -- remove from loadout
+ unequipGear(menu.Parent.GearReference.Value)
+ local inventoryButton = menu.Parent
+ local gearToUnequip = inventoryButton.GearReference.Value
+ local loadoutChildren = currentLoadout:GetChildren()
+ local slot = -1
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ local button = loadoutChildren[i]:GetChildren()
+ if button[1] and button[1].GearReference.Value == gearToUnequip then
+ slot = button[1].SlotNumber.Text
+ break
+ end
+ end
+ end
+ swapGearSlot(slot,nil)
+ end
+end
+
+function setupCharacterConnections()
+
+ if backpackAddCon then backpackAddCon:disconnect() end
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+
+ -- make sure we get all the children
+ local backpackChildren = game.Players.LocalPlayer.Backpack:GetChildren()
+ for i = 1, #backpackChildren do
+ addToGrid(backpackChildren[i])
+ end
+
+ if characterChildAddedCon then characterChildAddedCon:disconnect() end
+ characterChildAddedCon =
+ game.Players.LocalPlayer.Character.ChildAdded:connect(function(child)
+ addToGrid(child)
+ updateGridActive()
+ end)
+
+ if characterChildRemovedCon then characterChildRemovedCon:disconnect() end
+ characterChildRemovedCon =
+ game.Players.LocalPlayer.Character.ChildRemoved:connect(function(child)
+ updateGridActive()
+ end)
+
+ wait()
+ centerGear(currentLoadout:GetChildren())
+end
+
+function removeCharacterConnections()
+ if characterChildAddedCon then characterChildAddedCon:disconnect() end
+ if characterChildRemovedCon then characterChildRemovedCon:disconnect() end
+ if backpackAddCon then backpackAddCon:disconnect() end
+end
+
+function trim(s)
+ return (s:gsub("^%s*(.-)%s*$", "%1"))
+end
+
+function filterGear(terms)
+ local filteredGear = {}
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ local gearString = string.lower(buttons[v].GearReference.Value.Name)
+ gearString = trim(gearString)
+ for i = 1, #terms do
+ if string.match(gearString,terms[i]) then
+ table.insert(filteredGear,buttons[v])
+ break
+ end
+ end
+ end
+ end
+
+ return filteredGear
+end
+function splitByWhitespace(text)
+ if type(text) ~= "string" then return nil end
+
+ local terms = {}
+ for token in string.gmatch(text, "[^%s]+") do
+ if string.len(token) > 0 then
+ table.insert(terms,token)
+ end
+ end
+ return terms
+end
+function showSearchGear(searchTerms)
+ if not backpack.Gear.Visible then return end -- currently not active tab
+
+ local searchTermTable = splitByWhitespace(searchTerms)
+ if searchTermTable and (#searchTermTable > 0) then
+ currSearchTerms = searchTermTable
+ else
+ currSearchTerms = nil
+ end
+
+ if searchTermTable == nil then
+ showEntireGrid()
+ return
+ end
+
+ local filteredButtons = filterGear(currSearchTerms)
+ showPartialGrid(filteredButtons)
+end
+
+function nukeBackpack()
+ while #buttons > 0 do
+ table.remove(buttons)
+ end
+ buttons = {}
+ while #backpackItems > 0 do
+ table.remove(backpackItems)
+ end
+ backpackItems = {}
+ local scrollingFrameChildren = grid.ScrollingFrame:GetChildren()
+ for i = 1, #scrollingFrameChildren do
+ scrollingFrameChildren[i]:remove()
+ end
+end
+
+function getGearContextMenu()
+ local gearContextMenu = Instance.new("Frame")
+ gearContextMenu.Active = true
+ gearContextMenu.Name = "UnequipContextMenu"
+ gearContextMenu.Size = UDim2.new(0,115,0,70)
+ gearContextMenu.Position = UDim2.new(0,-16,0,-16)
+ gearContextMenu.BackgroundTransparency = 1
+ gearContextMenu.Visible = false
+
+ local gearContextMenuButton = Instance.new("TextButton")
+ gearContextMenuButton.Name = "UnequipContextMenuButton"
+ gearContextMenuButton.Text = ""
+ gearContextMenuButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ gearContextMenuButton.ZIndex = 8
+ gearContextMenuButton.Size = UDim2.new(1, 0, 1, -20)
+ gearContextMenuButton.Visible = true
+ gearContextMenuButton.Parent = gearContextMenu
+
+ local elementHeight = 12
+
+ local contextMenuElements = {}
+ local contextMenuElementsName = {"Remove Hotkey"}
+
+ for i = 1, #contextMenuElementsName do
+ local element = {}
+ element.Type = "Button"
+ element.Text = contextMenuElementsName[i]
+ element.Action = i
+ element.DoIt = UnequipGearMenuClick
+ table.insert(contextMenuElements,element)
+ end
+
+ for i, contextElement in ipairs(contextMenuElements) do
+ local element = contextElement
+ if element.Type == "Button" then
+ local button = Instance.new("TextButton")
+ button.Name = "UnequipContextButton" .. i
+ button.BackgroundColor3 = Color3.new(0,0,0)
+ button.BorderSizePixel = 0
+ button.TextXAlignment = Enum.TextXAlignment.Left
+ button.Text = " " .. contextElement.Text
+ button.Font = Enum.Font.Arial
+ button.FontSize = Enum.FontSize.Size14
+ button.Size = UDim2.new(1, 8, 0, elementHeight)
+ button.Position = UDim2.new(0,0,0,elementHeight * i)
+ button.TextColor3 = Color3.new(1,1,1)
+ button.ZIndex = 9
+ button.Parent = gearContextMenuButton
+
+ if not IsTouchDevice() then
+
+ button.MouseButton1Click:connect(function()
+ if button.Active and not gearContextMenu.Parent.Active then
+ local success, result = pcall(function() element.DoIt(element, gearContextMenu) end)
+ browsingMenu = false
+ gearContextMenu.Visible = false
+ clearHighlight(button)
+ clearPreview()
+ end
+ end)
+
+ button.MouseEnter:connect(function()
+ if button.Active and gearContextMenu.Parent.Active then
+ highlight(button)
+ end
+ end)
+ button.MouseLeave:connect(function()
+ if button.Active and gearContextMenu.Parent.Active then
+ clearHighlight(button)
+ end
+ end)
+ end
+
+ contextElement.Button = button
+ contextElement.Element = button
+ elseif element.Type == "Label" then
+ local frame = Instance.new("Frame")
+ frame.Name = "ContextLabel" .. i
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1, 8, 0, elementHeight)
+
+ local label = Instance.new("TextLabel")
+ label.Name = "Text1"
+ label.BackgroundTransparency = 1
+ label.BackgroundColor3 = Color3.new(1,1,1)
+ label.BorderSizePixel = 0
+ label.TextXAlignment = Enum.TextXAlignment.Left
+ label.Font = Enum.Font.ArialBold
+ label.FontSize = Enum.FontSize.Size14
+ label.Position = UDim2.new(0.0, 0, 0, 0)
+ label.Size = UDim2.new(0.5, 0, 1, 0)
+ label.TextColor3 = Color3.new(1,1,1)
+ label.ZIndex = 9
+ label.Parent = frame
+ element.Label1 = label
+
+ if element.GetText2 then
+ label = Instance.new("TextLabel")
+ label.Name = "Text2"
+ label.BackgroundTransparency = 1
+ label.BackgroundColor3 = Color3.new(1,1,1)
+ label.BorderSizePixel = 0
+ label.TextXAlignment = Enum.TextXAlignment.Right
+ label.Font = Enum.Font.Arial
+ label.FontSize = Enum.FontSize.Size14
+ label.Position = UDim2.new(0.5, 0, 0, 0)
+ label.Size = UDim2.new(0.5, 0, 1, 0)
+ label.TextColor3 = Color3.new(1,1,1)
+ label.ZIndex = 9
+ label.Parent = frame
+ element.Label2 = label
+ end
+ frame.Parent = gearContextMenuButton
+ element.Label = frame
+ element.Element = frame
+ end
+ end
+
+ gearContextMenu.ZIndex = 4
+ gearContextMenu.MouseLeave:connect(function()
+ browsingMenu = false
+ gearContextMenu.Visible = false
+ clearPreview()
+ end)
+ robloxLock(gearContextMenu)
+
+ return gearContextMenu
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ if not enabled then
+ backpack.Gear.Visible = false
+ end
+ end
+end
+
+
+local backpackChildren = player.Backpack:GetChildren()
+for i = 1, #backpackChildren do
+ addToGrid(backpackChildren[i])
+end
+
+------------------------- Start Lifelong Connections -----------------------
+
+
+resizeEvent.Event:connect(function(absSize)
+ if debounce then return end
+
+ debounce = true
+ wait()
+ resize()
+ resizeGrid()
+ debounce = false
+end)
+
+currentLoadout.ChildAdded:connect(function(child) loadoutCheck(child, false) end)
+currentLoadout.ChildRemoved:connect(function(child) loadoutCheck(child, true) end)
+
+currentLoadout.DescendantAdded:connect(function(descendant)
+ if not backpack.Visible and ( descendant:IsA("ImageButton") or descendant:IsA("TextButton") ) then
+ centerGear(currentLoadout:GetChildren())
+ end
+end)
+currentLoadout.DescendantRemoving:connect(function(descendant)
+ if not backpack.Visible and ( descendant:IsA("ImageButton") or descendant:IsA("TextButton") ) then
+ wait()
+ centerGear(currentLoadout:GetChildren())
+ end
+end)
+
+grid.MouseEnter:connect(function() clearPreview() end)
+grid.MouseLeave:connect(function() clearPreview() end)
+
+player.CharacterRemoving:connect(function()
+ removeCharacterConnections()
+ nukeBackpack()
+end)
+player.CharacterAdded:connect(function() setupCharacterConnections() end)
+
+player.ChildAdded:connect(function(child)
+ if child:IsA("Backpack") then
+ playerBackpack = child
+ if backpackAddCon then backpackAddCon:disconnect() end
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+ end
+end)
+
+swapSlot.Changed:connect(function()
+ if not swapSlot.Value then
+ updateGridActive()
+ end
+end)
+
+local loadoutChildren = currentLoadout:GetChildren()
+for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and string.find(loadoutChildren[i].Name,"Slot") then
+ loadoutChildren[i].ChildRemoved:connect(function()
+ updateGridActive()
+ end)
+ loadoutChildren[i].ChildAdded:connect(function()
+ updateGridActive()
+ end)
+ end
+end
+------------------------- End Lifelong Connections -----------------------
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+resize()
+resizeGrid()
+
+-- make sure any items in the loadout are accounted for in inventory
+local loadoutChildren = currentLoadout:GetChildren()
+for i = 1, #loadoutChildren do
+ loadoutCheck(loadoutChildren[i], false)
+end
+if not backpack.Visible then centerGear(currentLoadout:GetChildren()) end
+
+-- make sure that inventory is listening to gear reparenting
+if characterChildAddedCon == nil and game.Players.LocalPlayer["Character"] then
+ setupCharacterConnections()
+end
+if not backpackAddCon then
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+end
+
+backpackOpenEvent.Event:connect(backpackOpenHandler)
+backpackCloseEvent.Event:connect(backpackCloseHandler)
+tabClickedEvent.Event:connect(tabClickHandler)
+searchRequestedEvent.Event:connect(showSearchGear)
+
+recalculateScrollLoadout()
\ No newline at end of file
diff --git a/asset/18 b/asset/18
new file mode 100644
index 0000000..82bf5e0
--- /dev/null
+++ b/asset/18
@@ -0,0 +1,1090 @@
+--rbxassetid%18%
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local useCoreHealthBar = false
+pcall(function() useCoreHealthBar = Game.Players:GetUseCoreScriptHealthBar() end)
+
+
+local currentLoadout = script.Parent
+local StaticTabName = "gear"
+local backpackEnabled = true
+
+local robloxGui = game:GetService("CoreGui"):FindFirstChild("RobloxGui")
+assert(robloxGui)
+local controlFrame = waitForChild(robloxGui, 'ControlFrame')
+local backpackButton = waitForChild(controlFrame, 'BackpackButton')
+local backpack = waitForChild(robloxGui, 'Backpack')
+waitForChild(robloxGui,"CurrentLoadout")
+waitForChild(robloxGui.CurrentLoadout,"TempSlot")
+waitForChild(robloxGui.CurrentLoadout.TempSlot,"SlotNumber")
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+local function IsSmallScreen()
+ return (robloxGui.AbsoluteSize.Y <= 500)
+end
+
+local function moveHealthBar(pGui)
+ waitForChild(pGui, 'HealthGUI')
+ waitForChild(pGui['HealthGUI'], 'tray')
+ local tray = pGui['HealthGUI']['tray']
+ tray.Position = UDim2.new(0.5, -85, 1, -26)
+end
+
+local function setHealthBarVisible( pGui, visible )
+ waitForChild(pGui, 'HealthGUI')
+ waitForChild(pGui['HealthGUI'], 'tray')
+ local tray = pGui['HealthGUI']['tray']
+ tray.Visible = visible
+end
+
+
+--- Begin Locals
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+if not useCoreHealthBar then
+ waitForChild(player, 'PlayerGui')
+ Spawn(function()
+ moveHealthBar(player.PlayerGui)
+ end)
+end
+
+while player.Character == nil do wait(0.03) end
+local humanoid = waitForChild(player.Character, 'Humanoid')
+humanoid.Died:connect(function()
+ backpackButton.Visible = false
+end)
+
+waitForChild(game, "LocalBackpack")
+game.LocalBackpack:SetOldSchoolBackpack(false)
+
+waitForChild(currentLoadout.Parent,"Backpack")
+local guiBackpack = currentLoadout.Parent.Backpack
+
+local backpackManager = waitForChild(guiBackpack,"CoreScripts/BackpackScripts/BackpackManager")
+local backpackOpenEvent = waitForChild(backpackManager,"BackpackOpenEvent")
+local backpackCloseEvent = waitForChild(backpackManager,"BackpackCloseEvent")
+local tabClickedEvent = waitForChild(backpackManager,"TabClickedEvent")
+local resizeEvent = waitForChild(backpackManager,"ResizeEvent")
+
+local inGearTab = true
+
+local maxNumLoadoutItems = 10
+if IsSmallScreen() then
+ maxNumLoadoutItems = 4
+end
+
+
+local characterChildAddedCon = nil
+local backpackChildCon = nil
+
+local debounce = false
+
+local enlargeFactor = 1.18
+local buttonSizeEnlarge = UDim2.new(1 * enlargeFactor,0,1 * enlargeFactor,0)
+local buttonSizeNormal = UDim2.new(1,0,1,0)
+local enlargeOverride = true
+local guiTweenSpeed = 0.5
+
+local firstInstanceOfLoadout = false
+
+local inventory = {}
+
+local gearSlots = {}
+for i = 1, maxNumLoadoutItems do
+ gearSlots[i] = "empty"
+end
+
+local backpackWasOpened = false
+--- End Locals
+
+
+
+
+
+
+-- Begin Functions
+local function backpackIsOpen()
+ if guiBackpack then
+ return guiBackpack.Visible
+ end
+ return false
+end
+
+
+local function kill(prop,con,gear)
+ if con then con:disconnect() end
+ if prop == true and gear then
+ reorganizeLoadout(gear,false)
+ end
+end
+
+function registerNumberKeys()
+ for i = 0, 9 do
+ game:GetService("GuiService"):AddKey(tostring(i))
+ end
+end
+
+function unregisterNumberKeys()
+ for i = 0, 9 do
+ game:GetService("GuiService"):RemoveKey(tostring(i))
+ end
+end
+
+function characterInWorkspace()
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer["Character"] then
+ if game.Players.LocalPlayer.Character ~= nil then
+ if game.Players.LocalPlayer.Character.Parent ~= nil then
+ return true
+ end
+ end
+ end
+ end
+
+ return false
+end
+
+function removeGear(gear)
+ local emptySlot = nil
+ for i = 1, #gearSlots do
+ if gearSlots[i] == gear and gear.Parent ~= nil then
+ emptySlot = i
+ break
+ end
+ end
+ if emptySlot then
+ if gearSlots[emptySlot].GearReference.Value then
+ if gearSlots[emptySlot].GearReference.Value.Parent == game.Players.LocalPlayer.Character then -- if we currently have this equipped, unequip it
+ gearSlots[emptySlot].GearReference.Value.Parent = game.Players.LocalPlayer.Backpack
+ end
+
+ if gearSlots[emptySlot].GearReference.Value:IsA("HopperBin") and gearSlots[emptySlot].GearReference.Value.Active then -- this is an active hopperbin
+ gearSlots[emptySlot].GearReference.Value:Disable()
+ gearSlots[emptySlot].GearReference.Value.Active = false
+ end
+ end
+
+ gearSlots[emptySlot] = "empty"
+
+ local centerizeX = gear.Size.X.Scale/2
+ local centerizeY = gear.Size.Y.Scale/2
+ --[[gear:TweenSizeAndPosition(UDim2.new(0,0,0,0),
+ UDim2.new(gear.Position.X.Scale + centerizeX,gear.Position.X.Offset,gear.Position.Y.Scale + centerizeY,gear.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,guiTweenSpeed/4,true)]]
+ delay(0,
+ function()
+ gear:remove()
+ end)
+
+ Spawn(function()
+ while backpackIsOpen() do wait(0.03) end
+ waitForChild(player, 'Backpack')
+ local allEmpty = true
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= 'empty' then
+ allEmpty = false
+ end
+ end
+
+ if allEmpty then
+ if #player.Backpack:GetChildren() < 1 then
+ backpackButton.Visible = false
+ else
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+ end
+ end
+ end)
+ end
+end
+
+function insertGear(gear, addToSlot)
+ local pos = nil
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ pos = i
+ break
+ end
+ end
+
+ if pos == 1 and gearSlots[1] ~= "empty" then gear:remove() return end -- we are currently full, can't add in
+ else
+ pos = addToSlot
+ -- push all gear down one slot
+ local start = 1
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ start = i
+ break
+ end
+ end
+ for i = start, pos + 1, -1 do
+ gearSlots[i] = gearSlots[i - 1]
+ if i == 10 then
+ gearSlots[i].SlotNumber.Text = "0"
+ gearSlots[i].SlotNumberDownShadow.Text = "0"
+ gearSlots[i].SlotNumberUpShadow.Text = "0"
+ else
+ gearSlots[i].SlotNumber.Text = i
+ gearSlots[i].SlotNumberDownShadow.Text = i
+ gearSlots[i].SlotNumberUpShadow.Text = i
+ end
+ end
+ end
+
+ gearSlots[pos] = gear
+ if pos ~= maxNumLoadoutItems then
+ if(type(tostring(pos)) == "string") then
+ local posString = tostring(pos)
+ gear.SlotNumber.Text = posString
+ gear.SlotNumberDownShadow.Text = posString
+ gear.SlotNumberUpShadow.Text = posString
+ end
+ else -- tenth gear doesn't follow mathematical pattern :(
+ gear.SlotNumber.Text = "0"
+ gear.SlotNumberDownShadow.Text = "0"
+ gear.SlotNumberUpShadow.Text = "0"
+ end
+ gear.Visible = true
+
+ local con = nil
+ con = gear.Kill.Changed:connect(function(prop) kill(prop,con,gear) end)
+end
+
+
+function reorganizeLoadout(gear, inserting, equipped, addToSlot)
+ if inserting then -- add in gear
+ insertGear(gear, addToSlot)
+ else
+ removeGear(gear)
+ end
+ if gear ~= "empty" then gear.ZIndex = 1 end
+end
+
+function checkToolAncestry(child,parent)
+ if child:FindFirstChild("RobloxBuildTool") then return end -- don't show roblox build tools
+ if child:IsA("Tool") or child:IsA("HopperBin") then
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" and gearSlots[i].GearReference.Value == child then
+ if parent == nil then
+ gearSlots[i].Kill.Value = true
+ return false
+ elseif child.Parent == player.Character then
+ gearSlots[i].Selected = true
+ return true
+ elseif child.Parent == player.Backpack then
+ if child:IsA("Tool") or child:IsA("HopperBin") then gearSlots[i].Selected = false end
+ return true
+ else
+ gearSlots[i].Kill.Value = true
+ return false
+ end
+ return true
+ end
+ end
+ end
+end
+
+function removeAllEquippedGear(physGear)
+ local stuff = player.Character:GetChildren()
+ for i = 1, #stuff do
+ if ( stuff[i]:IsA("Tool") or stuff[i]:IsA("HopperBin") ) and stuff[i] ~= physGear then
+ if stuff[i]:IsA("Tool") then stuff[i].Parent = player.Backpack end
+ if stuff[i]:IsA("HopperBin") then
+ stuff[i]:Disable()
+ end
+ end
+ end
+end
+
+function hopperBinSwitcher(numKey, physGear)
+ if not physGear then return end
+
+ physGear:ToggleSelect()
+
+ if gearSlots[numKey] == "empty" then return end
+
+ if not physGear.Active then
+ gearSlots[numKey].Selected = false
+ normalizeButton(gearSlots[numKey])
+ else
+ gearSlots[numKey].Selected = true
+ enlargeButton(gearSlots[numKey])
+ end
+end
+
+function toolSwitcher(numKey)
+
+ if not gearSlots[numKey] then return end
+ local physGear = gearSlots[numKey].GearReference.Value
+ if physGear == nil then return end
+
+ removeAllEquippedGear(physGear) -- we don't remove this gear, as then we get a double switcheroo
+
+ local key = numKey
+ if numKey == 0 then key = 10 end
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] and gearSlots[i] ~= "empty" and i ~= key then
+ normalizeButton(gearSlots[i])
+ gearSlots[i].Selected = false
+ if gearSlots[i].GearReference and gearSlots[i].GearReference.Value and gearSlots[i].GearReference.Value:IsA("HopperBin") and gearSlots[i].GearReference.Value.Active then
+ gearSlots[i].GearReference.Value:ToggleSelect()
+ end
+ end
+ end
+
+ if physGear:IsA("HopperBin") then
+ hopperBinSwitcher(numKey,physGear)
+ else
+ if physGear.Parent == player.Character then
+ physGear.Parent = player.Backpack
+
+ if gearSlots[numKey] ~= "empty" then
+ gearSlots[numKey].Selected = false
+ normalizeButton(gearSlots[numKey])
+ end
+ else
+ --player.Character.Humanoid:EquipTool(physGear)
+
+ physGear.Parent = player.Character
+ gearSlots[numKey].Selected = true
+
+ enlargeButton(gearSlots[numKey])
+ end
+ end
+end
+
+
+function activateGear(num)
+ local numKey = nil
+ if num == "0" then
+ numKey = 10 -- why do lua indexes have to start at 1? :(
+ else
+ numKey = tonumber(num)
+ end
+
+ if(numKey == nil) then return end
+
+ if gearSlots[numKey] ~= "empty" then
+ toolSwitcher(numKey)
+ end
+end
+
+
+enlargeButton = function(button)
+ if button.Size.Y.Scale > 1 then return end
+ if not button.Parent then return end
+ if not button.Selected then return end
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i] ~= button then
+ normalizeButton(gearSlots[i])
+ end
+ end
+
+ if not enlargeOverride then
+ return
+ end
+
+ if button:FindFirstChild('Highlight') then
+ button.Highlight.Visible = true
+ end
+
+ if button:IsA("ImageButton") or button:IsA("TextButton") then
+ button.ZIndex = 5
+ local centerizeX = -(buttonSizeEnlarge.X.Scale - button.Size.X.Scale)/2
+ local centerizeY = -(buttonSizeEnlarge.Y.Scale - button.Size.Y.Scale)/2
+ button:TweenSizeAndPosition(buttonSizeEnlarge,
+ UDim2.new(button.Position.X.Scale + centerizeX,button.Position.X.Offset,button.Position.Y.Scale + centerizeY,button.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,guiTweenSpeed/5,enlargeOverride)
+ end
+end
+
+normalizeAllButtons = function()
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i] ~= button then
+ normalizeButton(gearSlots[i],0.1)
+ end
+ end
+end
+
+
+normalizeButton = function(button, speed)
+ if not button then return end
+ if button.Size.Y.Scale <= 1 then return end
+ if button.Selected then return end
+ if not button.Parent then return end
+
+ local moveSpeed = speed
+ if moveSpeed == nil or type(moveSpeed) ~= "number" then moveSpeed = guiTweenSpeed/5 end
+
+ if button:FindFirstChild('Highlight') then
+ button.Highlight.Visible = false
+ end
+
+ if button:IsA("ImageButton") or button:IsA("TextButton") then
+ button.ZIndex = 1
+ local inverseEnlarge = 1/enlargeFactor
+ local centerizeX = -(buttonSizeNormal.X.Scale - button.Size.X.Scale)/2
+ local centerizeY = -(buttonSizeNormal.Y.Scale - button.Size.Y.Scale)/2
+ button:TweenSizeAndPosition(buttonSizeNormal,
+ UDim2.new(button.Position.X.Scale + centerizeX,button.Position.X.Offset,button.Position.Y.Scale + centerizeY,button.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,moveSpeed,enlargeOverride)
+ end
+end
+
+local waitForDebounce = function()
+ while debounce do
+ wait()
+ end
+end
+
+function pointInRectangle(point,rectTopLeft,rectSize)
+ if point.x > rectTopLeft.x and point.x < (rectTopLeft.x + rectSize.x) then
+ if point.y > rectTopLeft.y and point.y < (rectTopLeft.y + rectSize.y) then
+ return true
+ end
+ end
+ return false
+end
+
+function swapGear(gearClone,toFrame)
+ local toFrameChildren = toFrame:GetChildren()
+ if #toFrameChildren == 1 then
+ if toFrameChildren[1]:FindFirstChild("SlotNumber") then
+
+ local toSlot = tonumber(toFrameChildren[1].SlotNumber.Text)
+ local gearCloneSlot = tonumber(gearClone.SlotNumber.Text)
+ if toSlot == 0 then toSlot = 10 end
+ if gearCloneSlot == 0 then gearCloneSlot = 10 end
+
+ gearSlots[toSlot] = gearClone
+ gearSlots[gearCloneSlot] = toFrameChildren[1]
+
+ toFrameChildren[1].SlotNumber.Text = gearClone.SlotNumber.Text
+ toFrameChildren[1].SlotNumberDownShadow.Text = gearClone.SlotNumber.Text
+ toFrameChildren[1].SlotNumberUpShadow.Text = gearClone.SlotNumber.Text
+
+ local subString = string.sub(toFrame.Name,5)
+ gearClone.SlotNumber.Text = subString
+ gearClone.SlotNumberDownShadow.Text = subString
+ gearClone.SlotNumberUpShadow.Text = subString
+
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,0,gearClone.Position.Y.Scale,0)
+ toFrameChildren[1].Position = UDim2.new(toFrameChildren[1].Position.X.Scale,0,toFrameChildren[1].Position.Y.Scale,0)
+
+ toFrameChildren[1].Parent = gearClone.Parent
+ gearClone.Parent = toFrame
+ end
+ else
+ local slotNum = tonumber(gearClone.SlotNumber.Text)
+ if slotNum == 0 then slotNum = 10 end
+ gearSlots[slotNum] = "empty" -- reset this gear slot
+
+ local subString = string.sub(toFrame.Name,5)
+ gearClone.SlotNumber.Text = subString
+ gearClone.SlotNumberDownShadow.Text = subString
+ gearClone.SlotNumberUpShadow.Text = subString
+
+ local toSlotNum = tonumber(gearClone.SlotNumber.Text)
+ if toSlotNum == 0 then toSlotNum = 10 end
+ gearSlots[toSlotNum] = gearClone
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,0,gearClone.Position.Y.Scale,0)
+ gearClone.Parent = toFrame
+ end
+end
+
+function resolveDrag(gearClone,x,y)
+ local mousePoint = Vector2.new(x,y)
+
+ local frame = gearClone.Parent
+ local frames = frame.Parent:GetChildren()
+
+ for i = 1, #frames do
+ if frames[i]:IsA("Frame") then
+ if pointInRectangle(mousePoint, frames[i].AbsolutePosition,frames[i].AbsoluteSize) then
+ swapGear(gearClone,frames[i])
+ return true
+ end
+ end
+ end
+
+ if x < frame.AbsolutePosition.x or x > ( frame.AbsolutePosition.x + frame.AbsoluteSize.x ) then
+ reorganizeLoadout(gearClone,false)
+ return false
+ elseif y < frame.AbsolutePosition.y or y > ( frame.AbsolutePosition.y + frame.AbsoluteSize.y ) then
+ reorganizeLoadout(gearClone,false)
+ return false
+ else
+ if dragBeginPos then gearClone.Position = dragBeginPos end
+ return -1
+ end
+end
+
+function unequipAllItems(dontEquipThis)
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i].GearReference.Value and gearSlots[i].GearReference.Value ~= dontEquipThis then
+ if gearSlots[i].GearReference.Value:IsA("HopperBin") then
+ gearSlots[i].GearReference.Value:Disable()
+ elseif gearSlots[i].GearReference.Value:IsA("Tool") then
+ gearSlots[i].GearReference.Value.Parent = game.Players.LocalPlayer.Backpack
+ end
+ gearSlots[i].Selected = false
+ end
+ end
+end
+
+function showToolTip(button, tip)
+ if button and button:FindFirstChild("ToolTipLabel") and button.ToolTipLabel:IsA("TextLabel") and not IsTouchDevice() then
+ button.ToolTipLabel.Text = tostring(tip)
+ local xSize = button.ToolTipLabel.TextBounds.X + 6
+ button.ToolTipLabel.Size = UDim2.new(0,xSize,0,20)
+ button.ToolTipLabel.Position = UDim2.new(0.5,-xSize/2,0,-30)
+ button.ToolTipLabel.Visible = true
+ end
+end
+
+function hideToolTip(button, tip)
+ if button and button:FindFirstChild("ToolTipLabel") and button.ToolTipLabel:IsA("TextLabel") then
+ button.ToolTipLabel.Visible = false
+ end
+end
+
+local addingPlayerChild = function(child, equipped, addToSlot, inventoryGearButton)
+ waitForDebounce()
+ debounce = true
+
+ if child:FindFirstChild("RobloxBuildTool") then debounce = false return end -- don't show roblox build tools
+ if not child:IsA("Tool") then
+ if not child:IsA("HopperBin") then
+ debounce = false
+ return -- we don't care about anything besides tools (sigh...)
+ end
+ end
+
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" and gearSlots[i].GearReference.Value == child then -- we already have gear, do nothing
+ debounce = false
+ return
+ end
+ end
+ end
+
+ local gearClone = currentLoadout.TempSlot:clone()
+ gearClone.Name = child.Name
+ gearClone.GearImage.Image = child.TextureId
+ if gearClone.GearImage.Image == "" then
+ gearClone.GearText.Text = child.Name
+ end
+ gearClone.GearReference.Value = child
+
+ gearClone.MouseEnter:connect(function()
+ local gear = gearClone.GearReference and gearClone.GearReference.Value
+ if gear:IsA("Tool") and gear.ToolTip ~= "" then
+ showToolTip(gearClone, gear.ToolTip)
+ end
+ end)
+
+ gearClone.MouseLeave:connect(function()
+ local gear = gearClone.GearReference and gearClone.GearReference.Value
+ if gear:IsA("Tool") and gear.ToolTip ~= "" then
+ hideToolTip(gearClone, gear.ToolTip)
+ end
+ end)
+
+ gearClone.RobloxLocked = true
+
+ local slotToMod = -1
+
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ slotToMod = i
+ break
+ end
+ end
+ else
+ slotToMod = addToSlot
+ end
+
+ if slotToMod == - 1 then -- No available slot to add in!
+ debounce = false
+ return
+ end
+
+ local slotNum = slotToMod % 10
+ local parent = currentLoadout:FindFirstChild("Slot"..tostring(slotNum))
+ gearClone.Parent = parent
+
+ if inventoryGearButton then
+ local absolutePositionFinal = inventoryGearButton.AbsolutePosition
+ local currentAbsolutePosition = gearClone.AbsolutePosition
+ local diff = absolutePositionFinal - currentAbsolutePosition
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,diff.x,gearClone.Position.Y.Scale,diff.y)
+ gearClone.ZIndex = 4
+ end
+
+ if addToSlot then
+ reorganizeLoadout(gearClone, true, equipped, addToSlot)
+ else
+ reorganizeLoadout(gearClone, true)
+ end
+
+ if gearClone.Parent == nil then debounce = false return end -- couldn't fit in (hopper is full!)
+
+ if equipped then
+ gearClone.Selected = true
+ unequipAllItems(child)
+ delay(guiTweenSpeed + 0.01,function() -- if our gear is equipped, we will want to enlarge it when done moving
+ if gearClone:FindFirstChild("GearReference") and ( (gearClone.GearReference.Value:IsA("Tool") and gearClone.GearReference.Value.Parent == player.Character) or
+ (gearClone.GearReference.Value:IsA("HopperBin") and gearClone.GearReference.Value.Active == true) ) then
+ enlargeButton(gearClone)
+ end
+ end)
+ end
+
+ local dragBeginPos = nil
+ local clickCon, buttonDeleteCon, mouseEnterCon, mouseLeaveCon, dragStop, dragBegin = nil
+ clickCon = gearClone.MouseButton1Click:connect(function()
+ if characterInWorkspace() then
+ if not gearClone.Draggable then
+ activateGear(gearClone.SlotNumber.Text)
+ end
+ end
+ end)
+ mouseEnterCon = gearClone.MouseEnter:connect(function()
+ if guiBackpack.Visible then
+ gearClone.Draggable = true
+ end
+ end)
+ dragBegin = gearClone.DragBegin:connect(function(pos)
+ dragBeginPos = pos
+ gearClone.ZIndex = 7
+ local children = gearClone:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("TextLabel") then
+ if string.find(children[i].Name,"Shadow") then
+ children[i].ZIndex = 8
+ else
+ children[i].ZIndex = 9
+ end
+ elseif children[i]:IsA("Frame") or children[i]:IsA("ImageLabel") then
+ children[i].ZIndex = 7
+ end
+ end
+ end)
+ dragStop = gearClone.DragStopped:connect(function(x,y)
+ if gearClone.Selected then
+ gearClone.ZIndex = 4
+ else
+ gearClone.ZIndex = 3
+ end
+ local children = gearClone:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("TextLabel") then
+ if string.find(children[i].Name,"Shadow") then
+ children[i].ZIndex = 3
+ else
+ children[i].ZIndex = 4
+ end
+ elseif children[i]:IsA("Frame") or children[i]:IsA("ImageLabel") then
+ children[i].ZIndex = 2
+ end
+ end
+ resolveDrag(gearClone,x,y)
+ end)
+ mouseLeaveCon = gearClone.MouseLeave:connect(function()
+ gearClone.Draggable = false
+ end)
+ buttonDeleteCon = gearClone.AncestryChanged:connect(function()
+ if gearClone.Parent and gearClone.Parent.Parent == currentLoadout then return end
+ if clickCon then clickCon:disconnect() end
+ if buttonDeleteCon then buttonDeleteCon:disconnect() end
+ if mouseEnterCon then mouseEnterCon:disconnect() end
+ if mouseLeaveCon then mouseLeaveCon:disconnect() end
+ if dragStop then dragStop:disconnect() end
+ if dragBegin then dragBegin:disconnect() end
+ end) -- this probably isn't necessary since objects are being deleted (probably), but this might still leak just in case
+
+ local childCon = nil
+ local childChangeCon = nil
+ childCon = child.AncestryChanged:connect(function(newChild,parent)
+ if not checkToolAncestry(newChild,parent) then
+ if childCon then childCon:disconnect() end
+ if childChangeCon then childChangeCon:disconnect() end
+ removeFromInventory(child)
+ elseif parent == game.Players.LocalPlayer.Backpack then
+ normalizeButton(gearClone)
+ end
+ end)
+
+ childChangeCon = child.Changed:connect(function(prop)
+ if prop == "Name" then
+ if gearClone and gearClone.GearImage.Image == "" then
+ gearClone.GearText.Text = child.Name
+ end
+ elseif prop == "Active" then
+ if child and child:IsA("HopperBin") then
+ if not child.Active then
+ gearClone.Selected = false
+ normalizeButton(gearClone)
+ end
+ end
+ elseif prop == "TextureId" then
+ gearClone.GearImage.Image = child.TextureId
+ end
+ end)
+
+ debounce = false
+
+ Spawn(function()
+ while backpackIsOpen() do wait(0.03) end
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= 'empty' then
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -108)
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ end
+ end
+ end)
+end
+
+function addToInventory(child)
+ if not child:IsA("Tool") or not child:IsA("HopperBin") then return end
+
+ local slot = nil
+ for i = 1, #inventory do
+ if inventory[i] and inventory[i] == child then return end
+ if not inventory[i] then slot = i end
+ end
+ if slot then
+ inventory[slot] = child
+ elseif #inventory < 1 then
+ inventory[1] = child
+ else
+ inventory[#inventory + 1] = child
+ end
+end
+
+function removeFromInventory(child)
+ for i = 1, #inventory do
+ if inventory[i] == child then
+ table.remove(inventory,i)
+ inventory[i] = nil
+ end
+ end
+end
+
+local spreadOutGear = function()
+ loadoutChildren = currentLoadout:GetChildren()
+
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ loadoutChildren[i].BackgroundTransparency = 0.5
+ local slot = tonumber(string.sub(loadoutChildren[i].Name,5))
+ if slot == 0 then slot = 10 end
+ if IsSmallScreen() then
+ loadoutChildren[i]:TweenPosition(UDim2.new(0,(slot-1) * 60,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ else
+ loadoutChildren[i]:TweenPosition(UDim2.new((slot - 1)/10,0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+ end
+ end
+end
+
+local centerGear = function()
+ loadoutChildren = currentLoadout:GetChildren()
+ local gearButtons = {}
+ local lastSlotAdd = nil
+
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ if #loadoutChildren[i]:GetChildren() > 0 then
+ if loadoutChildren[i].Name == "Slot0" then
+ lastSlotAdd = loadoutChildren[i]
+ else
+ table.insert(gearButtons, loadoutChildren[i])
+ end
+ end
+ loadoutChildren[i].BackgroundTransparency = 1
+ end
+ end
+ if lastSlotAdd then table.insert(gearButtons,lastSlotAdd) end
+
+ local startPos = ( 1 - (#gearButtons * 0.1) ) / 2
+ for i = 1, #gearButtons do
+ if IsSmallScreen() then
+ startPos = ( 0.5 - (#gearButtons * 0.333)/2 )
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + (i-1) * 0.33, 0, 0, 0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ else
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + ((i - 1) * 0.1),0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+ end
+end
+
+function editLoadout()
+ backpackWasOpened = true
+ if inGearTab then
+ spreadOutGear()
+ end
+end
+
+function readonlyLoadout()
+ if not inGearTab then
+ centerGear()
+ end
+end
+
+function setupBackpackListener()
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ backpackChildCon = player.Backpack.ChildAdded:connect(function(child)
+ if not firstInstanceOfLoadout then
+ firstInstanceOfLoadout = true
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ end
+ addingPlayerChild(child)
+ addToInventory(child)
+ end)
+end
+
+function playerCharacterChildAdded(child)
+ addingPlayerChild(child,true)
+ addToInventory(child)
+end
+
+function activateLoadout()
+ currentLoadout.Visible = true
+end
+
+function deactivateLoadout()
+ currentLoadout.Visible = false
+end
+
+function tabHandler(inFocus)
+ inGearTab = inFocus
+ if inFocus then
+ editLoadout()
+ else
+ readonlyLoadout()
+ end
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ currentLoadout.Visible = enabled -- Thanks, missing line. you know how to confuse everyone. >.<
+ backpackButton.Visible = enabled
+ backpackEnabled = enabled
+
+ if enabled then
+ registerNumberKeys()
+ else
+ unregisterNumberKeys()
+ end
+ end
+
+ if not useCoreHealthBar and coreGuiType == Enum.CoreGuiType.Health or coreGuiType == Enum.CoreGuiType.All then
+ setHealthBarVisible(game.Players.LocalPlayer.PlayerGui, enabled)
+ end
+end
+-- End Functions
+
+
+
+
+
+
+-- Begin Script
+registerNumberKeys()
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+if not useCoreHealthBar then
+ coreGuiChanged(Enum.CoreGuiType.Health, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health))
+end
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+wait() -- let stuff initialize incase this is first heartbeat...
+
+waitForChild(player,"Backpack")
+waitForProperty(player,"Character")
+
+-- not sure why this had no delay but the player.CharacterAdded one had one... this type of error would be easier to avoid with function reusage
+delay(1,function()
+ local backpackChildren = player.Backpack:GetChildren()
+ local size = math.min(10,#backpackChildren)
+ for i = 1, size do
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ addingPlayerChild(backpackChildren[i],false)
+ end
+ setupBackpackListener()
+end)
+
+delay(2, function()
+ --while true do
+ if not backpackWasOpened then
+ if IsSmallScreen() then
+ local cChildren = currentLoadout:GetChildren()
+ for i = 1, #cChildren do
+ local slotNum = tonumber(string.sub(cChildren[i].Name, 5, string.len(cChildren[i].Name)))
+ if type(slotNum) == 'number' then
+ cChildren[i].Position = UDim2.new(0, (slotNum-1) * 60, 0, 0)
+ end
+ end
+ end
+ end
+ wait(0.25)
+ --end
+end)
+
+if not useCoreHealthBar then
+ player.ChildAdded:connect(function(child)
+ if child:IsA('PlayerGui') then
+ moveHealthBar(child)
+ end
+ end)
+end
+
+waitForProperty(player,"Character")
+for i,v in ipairs(player.Character:GetChildren()) do
+ playerCharacterChildAdded(v)
+end
+characterChildAddedCon = player.Character.ChildAdded:connect(function(child) playerCharacterChildAdded(child) end)
+
+waitForChild(player.Character,"Humanoid")
+humanoidDiedCon = player.Character.Humanoid.Died:connect(function()
+ if humanoidDiedCon then humanoidDiedCon:disconnect() humanoidDiedCon = nil end
+ deactivateLoadout()
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ backpackWasOpened = false
+end)
+
+player.CharacterRemoving:connect(function()
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" then
+ gearSlots[i].Parent = nil
+ gearSlots[i] = "empty"
+ end
+ end
+end)
+
+player.CharacterAdded:connect(function()
+ waitForProperty(game.Players,"LocalPlayer")
+ player = game.Players.LocalPlayer -- make sure we are still looking at the correct character
+ waitForChild(player,"Backpack")
+
+
+ delay(1,function()
+ local backpackChildren = player.Backpack:GetChildren()
+ local size = math.min(10,#backpackChildren)
+ for i = 1, size do
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ addingPlayerChild(backpackChildren[i],false)
+ end
+ setupBackpackListener()
+ end)
+
+ activateLoadout()
+
+ if characterChildAddedCon then
+ characterChildAddedCon:disconnect()
+ characterChildAddedCon = nil
+ end
+
+ characterChildAddedCon =
+ player.Character.ChildAdded:connect(function(child)
+ addingPlayerChild(child,true)
+ end)
+
+ waitForChild(player.Character,"Humanoid")
+ if backpack.Visible then
+ backpackOpenEvent:Fire()
+ end
+ humanoidDiedCon =
+ player.Character.Humanoid.Died:connect(function()
+ if backpackEnabled then
+ backpackButton.Visible = false
+ end
+ firstInstanceOfLoadout = false
+ deactivateLoadout()
+
+ if humanoidDiedCon then humanoidDiedCon:disconnect() humanoidDiedCon = nil end
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ end)
+ if not useCoreHealthBar then
+ waitForChild(player, 'PlayerGui')
+ moveHealthBar(player.PlayerGui)
+ end
+ delay(2, function()
+ --while true do
+ if not backpackWasOpened then
+ if IsSmallScreen() then
+ local cChildren = currentLoadout:GetChildren()
+ for i = 1, #cChildren do
+ local slotNum = tonumber(string.sub(cChildren[i].Name, 5, string.len(cChildren[i].Name)))
+ if type(slotNum) == 'number' then
+ cChildren[i].Position = UDim2.new(0, (slotNum-1) * 60, 0, 0)
+ end
+ end
+ end
+ end
+ wait(0.25)
+ --end
+ end)
+end)
+
+waitForChild(guiBackpack,"SwapSlot")
+guiBackpack.SwapSlot.Changed:connect(function()
+ if guiBackpack.SwapSlot.Value then
+ local swapSlot = guiBackpack.SwapSlot
+ local pos = swapSlot.Slot.Value
+ if pos == 0 then pos = 10 end
+ if gearSlots[pos] then
+ reorganizeLoadout(gearSlots[pos],false)
+ end
+ if swapSlot.GearButton.Value then
+ addingPlayerChild(swapSlot.GearButton.Value.GearReference.Value,false,pos)
+ end
+ guiBackpack.SwapSlot.Value = false
+ end
+end)
+
+game:GetService("GuiService").KeyPressed:connect(function(key)
+ if characterInWorkspace() then
+ activateGear(key)
+ end
+end)
+
+backpackOpenEvent.Event:connect(editLoadout)
+backpackCloseEvent.Event:connect(centerGear)
+tabClickedEvent.Event:connect(function ( tabName )
+ tabHandler(tabName == StaticTabName)
+end)
diff --git a/asset/19 b/asset/19
new file mode 100644
index 0000000..448f7e0
--- /dev/null
+++ b/asset/19
@@ -0,0 +1,4041 @@
+--rbxassetid%21%
+local t = {}
+
+local function ScopedConnect(parentInstance, instance, event, signalFunc, syncFunc, removeFunc)
+ local eventConnection = nil
+
+ --Connection on parentInstance is scoped by parentInstance (when destroyed, it goes away)
+ local tryConnect = function()
+ if game:IsAncestorOf(parentInstance) then
+ --Entering the world, make sure we are connected/synced
+ if not eventConnection then
+ eventConnection = instance[event]:connect(signalFunc)
+ if syncFunc then syncFunc() end
+ end
+ else
+ --Probably leaving the world, so disconnect for now
+ if eventConnection then
+ eventConnection:disconnect()
+ if removeFunc then removeFunc() end
+ end
+ end
+ end
+
+ --Hook it up to ancestryChanged signal
+ local connection = parentInstance.AncestryChanged:connect(tryConnect)
+
+ --Now connect us if we're already in the world
+ tryConnect()
+
+ return connection
+end
+
+local function getScreenGuiAncestor(instance)
+ local localInstance = instance
+ while localInstance and not localInstance:IsA("ScreenGui") do
+ localInstance = localInstance.Parent
+ end
+ return localInstance
+end
+
+local function CreateButtons(frame, buttons, yPos, ySize)
+ local buttonNum = 1
+ local buttonObjs = {}
+ for i, obj in ipairs(buttons) do
+ local button = Instance.new("TextButton")
+ button.Name = "Button" .. buttonNum
+ button.Font = Enum.Font.Arial
+ button.FontSize = Enum.FontSize.Size18
+ button.AutoButtonColor = true
+ button.Modal = true
+ if obj["Style"] then
+ button.Style = obj.Style
+ else
+ button.Style = Enum.ButtonStyle.RobloxButton
+ end
+ if obj["ZIndex"] then
+ button.ZIndex = obj.ZIndex
+ end
+ button.Text = obj.Text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.MouseButton1Click:connect(obj.Function)
+ button.Parent = frame
+ buttonObjs[buttonNum] = button
+
+ buttonNum = buttonNum + 1
+ end
+ local numButtons = buttonNum-1
+
+ if numButtons == 1 then
+ frame.Button1.Position = UDim2.new(0.35, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.4,0,ySize.Scale, ySize.Offset)
+ elseif numButtons == 2 then
+ frame.Button1.Position = UDim2.new(0.1, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.8/3,0, ySize.Scale, ySize.Offset)
+
+ frame.Button2.Position = UDim2.new(0.55, 0, yPos.Scale, yPos.Offset)
+ frame.Button2.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+ elseif numButtons >= 3 then
+ local spacing = .1 / numButtons
+ local buttonSize = .9 / numButtons
+
+ buttonNum = 1
+ while buttonNum <= numButtons do
+ buttonObjs[buttonNum].Position = UDim2.new(spacing*buttonNum + (buttonNum-1) * buttonSize, 0, yPos.Scale, yPos.Offset)
+ buttonObjs[buttonNum].Size = UDim2.new(buttonSize, 0, ySize.Scale, ySize.Offset)
+ buttonNum = buttonNum + 1
+ end
+ end
+end
+
+local function setSliderPos(newAbsPosX,slider,sliderPosition,bar,steps)
+
+ local newStep = steps - 1 --otherwise we really get one more step than we want
+ local relativePosX = math.min(1, math.max(0, (newAbsPosX - bar.AbsolutePosition.X) / bar.AbsoluteSize.X ))
+ local wholeNum, remainder = math.modf(relativePosX * newStep)
+ if remainder > 0.5 then
+ wholeNum = wholeNum + 1
+ end
+ relativePosX = wholeNum/newStep
+
+ local result = math.ceil(relativePosX * newStep)
+ if sliderPosition.Value ~= (result + 1) then --only update if we moved a step
+ sliderPosition.Value = result + 1
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ end
+
+end
+
+local function cancelSlide(areaSoak)
+ areaSoak.Visible = false
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+end
+
+t.CreateStyledMessageDialog = function(title, message, style, buttons)
+ local frame = Instance.new("Frame")
+ frame.Size = UDim2.new(0.5, 0, 0, 165)
+ frame.Position = UDim2.new(0.25, 0, 0.5, -72.5)
+ frame.Name = "MessageDialog"
+ frame.Active = true
+ frame.Style = Enum.FrameStyle.RobloxRound
+
+ local styleImage = Instance.new("ImageLabel")
+ styleImage.Name = "StyleImage"
+ styleImage.BackgroundTransparency = 1
+ styleImage.Position = UDim2.new(0,5,0,15)
+ if style == "error" or style == "Error" then
+ styleImage.Size = UDim2.new(0, 71, 0, 71)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42565285"
+ elseif style == "notify" or style == "Notify" then
+ styleImage.Size = UDim2.new(0, 71, 0, 71)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42604978"
+ elseif style == "confirm" or style == "Confirm" then
+ styleImage.Size = UDim2.new(0, 74, 0, 76)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42557901"
+ else
+ return t.CreateMessageDialog(title,message,buttons)
+ end
+ styleImage.Parent = frame
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = title
+ titleLabel.TextStrokeTransparency = 0
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ titleLabel.Position = UDim2.new(0, 80, 0, 0)
+ titleLabel.Size = UDim2.new(1, -80, 0, 40)
+ titleLabel.Font = Enum.Font.ArialBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.TextXAlignment = Enum.TextXAlignment.Center
+ titleLabel.TextYAlignment = Enum.TextYAlignment.Center
+ titleLabel.Parent = frame
+
+ local messageLabel = Instance.new("TextLabel")
+ messageLabel.Name = "Message"
+ messageLabel.Text = message
+ messageLabel.TextStrokeTransparency = 0
+ messageLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ messageLabel.Position = UDim2.new(0.025, 80, 0, 45)
+ messageLabel.Size = UDim2.new(0.95, -80, 0, 55)
+ messageLabel.BackgroundTransparency = 1
+ messageLabel.Font = Enum.Font.Arial
+ messageLabel.FontSize = Enum.FontSize.Size18
+ messageLabel.TextWrap = true
+ messageLabel.TextXAlignment = Enum.TextXAlignment.Left
+ messageLabel.TextYAlignment = Enum.TextYAlignment.Top
+ messageLabel.Parent = frame
+
+ CreateButtons(frame, buttons, UDim.new(0, 105), UDim.new(0, 40) )
+
+ return frame
+end
+
+t.CreateMessageDialog = function(title, message, buttons)
+ local frame = Instance.new("Frame")
+ frame.Size = UDim2.new(0.5, 0, 0.5, 0)
+ frame.Position = UDim2.new(0.25, 0, 0.25, 0)
+ frame.Name = "MessageDialog"
+ frame.Active = true
+ frame.Style = Enum.FrameStyle.RobloxRound
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = title
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ titleLabel.Position = UDim2.new(0, 0, 0, 0)
+ titleLabel.Size = UDim2.new(1, 0, 0.15, 0)
+ titleLabel.Font = Enum.Font.ArialBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.TextXAlignment = Enum.TextXAlignment.Center
+ titleLabel.TextYAlignment = Enum.TextYAlignment.Center
+ titleLabel.Parent = frame
+
+ local messageLabel = Instance.new("TextLabel")
+ messageLabel.Name = "Message"
+ messageLabel.Text = message
+ messageLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ messageLabel.Position = UDim2.new(0.025, 0, 0.175, 0)
+ messageLabel.Size = UDim2.new(0.95, 0, .55, 0)
+ messageLabel.BackgroundTransparency = 1
+ messageLabel.Font = Enum.Font.Arial
+ messageLabel.FontSize = Enum.FontSize.Size18
+ messageLabel.TextWrap = true
+ messageLabel.TextXAlignment = Enum.TextXAlignment.Left
+ messageLabel.TextYAlignment = Enum.TextYAlignment.Top
+ messageLabel.Parent = frame
+
+ CreateButtons(frame, buttons, UDim.new(0.8,0), UDim.new(0.15, 0))
+
+ return frame
+end
+
+t.CreateDropDownMenu = function(items, onSelect, forRoblox, whiteSkin, baseZ)
+ local baseZIndex = 0
+ if (type(baseZ) == "number") then
+ baseZIndex = baseZ
+ end
+ local width = UDim.new(0, 100)
+ local height = UDim.new(0, 32)
+
+ local xPos = 0.055
+ local frame = Instance.new("Frame")
+ local textColor = Color3.new(1,1,1)
+ if (whiteSkin) then
+ textColor = Color3.new(0.5, 0.5, 0.5)
+ end
+ frame.Name = "DropDownMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(width, height)
+
+ local dropDownMenu = Instance.new("TextButton")
+ dropDownMenu.Name = "DropDownMenuButton"
+ dropDownMenu.TextWrap = true
+ dropDownMenu.TextColor3 = textColor
+ dropDownMenu.Text = "Choose One"
+ dropDownMenu.Font = Enum.Font.ArialBold
+ dropDownMenu.FontSize = Enum.FontSize.Size18
+ dropDownMenu.TextXAlignment = Enum.TextXAlignment.Left
+ dropDownMenu.TextYAlignment = Enum.TextYAlignment.Center
+ dropDownMenu.BackgroundTransparency = 1
+ dropDownMenu.AutoButtonColor = true
+ if (whiteSkin) then
+ dropDownMenu.Style = Enum.ButtonStyle.RobloxRoundDropdownButton
+ else
+ dropDownMenu.Style = Enum.ButtonStyle.RobloxButton
+ end
+ dropDownMenu.Size = UDim2.new(1,0,1,0)
+ dropDownMenu.Parent = frame
+ dropDownMenu.ZIndex = 2 + baseZIndex
+
+ local dropDownIcon = Instance.new("ImageLabel")
+ dropDownIcon.Name = "Icon"
+ dropDownIcon.Active = false
+ if (whiteSkin) then
+ dropDownIcon.Image = "rbxasset://textures/ui/dropdown_arrow.png"
+ dropDownIcon.Size = UDim2.new(0,16,0,12)
+ dropDownIcon.Position = UDim2.new(1,-17,0.5, -6)
+ else
+ dropDownIcon.Image = "http://www.roblox.com/asset/?id=45732894"
+ dropDownIcon.Size = UDim2.new(0,11,0,6)
+ dropDownIcon.Position = UDim2.new(1,-11,0.5, -2)
+ end
+ dropDownIcon.BackgroundTransparency = 1
+ dropDownIcon.Parent = dropDownMenu
+ dropDownIcon.ZIndex = 2 + baseZIndex
+
+ local itemCount = #items
+ local dropDownItemCount = #items
+ local useScrollButtons = false
+ if dropDownItemCount > 6 then
+ useScrollButtons = true
+ dropDownItemCount = 6
+ end
+
+ local droppedDownMenu = Instance.new("TextButton")
+ droppedDownMenu.Name = "List"
+ droppedDownMenu.Text = ""
+ droppedDownMenu.BackgroundTransparency = 1
+ --droppedDownMenu.AutoButtonColor = true
+ if (whiteSkin) then
+ droppedDownMenu.Style = Enum.ButtonStyle.RobloxRoundDropdownButton
+ else
+ droppedDownMenu.Style = Enum.ButtonStyle.RobloxButton
+ end
+ droppedDownMenu.Visible = false
+ droppedDownMenu.Active = true --Blocks clicks
+ droppedDownMenu.Position = UDim2.new(0,0,0,0)
+ droppedDownMenu.Size = UDim2.new(1,0, (1 + dropDownItemCount)*.8, 0)
+ droppedDownMenu.Parent = frame
+ droppedDownMenu.ZIndex = 2 + baseZIndex
+
+ local choiceButton = Instance.new("TextButton")
+ choiceButton.Name = "ChoiceButton"
+ choiceButton.BackgroundTransparency = 1
+ choiceButton.BorderSizePixel = 0
+ choiceButton.Text = "ReplaceMe"
+ choiceButton.TextColor3 = textColor
+ choiceButton.TextXAlignment = Enum.TextXAlignment.Left
+ choiceButton.TextYAlignment = Enum.TextYAlignment.Center
+ choiceButton.BackgroundColor3 = Color3.new(1, 1, 1)
+ choiceButton.Font = Enum.Font.Arial
+ choiceButton.FontSize = Enum.FontSize.Size18
+ if useScrollButtons then
+ choiceButton.Size = UDim2.new(1,-13, .8/((dropDownItemCount + 1)*.8),0)
+ else
+ choiceButton.Size = UDim2.new(1, 0, .8/((dropDownItemCount + 1)*.8),0)
+ end
+ choiceButton.TextWrap = true
+ choiceButton.ZIndex = 2 + baseZIndex
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = true
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 3 + baseZIndex
+
+ local dropDownSelected = false
+
+ local scrollUpButton
+ local scrollDownButton
+ local scrollMouseCount = 0
+
+ local setZIndex = function(baseZIndex)
+ droppedDownMenu.ZIndex = baseZIndex +1
+ if scrollUpButton then
+ scrollUpButton.ZIndex = baseZIndex + 3
+ end
+ if scrollDownButton then
+ scrollDownButton.ZIndex = baseZIndex + 3
+ end
+
+ local children = droppedDownMenu:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child.Name == "ChoiceButton" then
+ child.ZIndex = baseZIndex + 2
+ elseif child.Name == "ClickCaptureButton" then
+ child.ZIndex = baseZIndex
+ end
+ end
+ end
+ end
+
+ local scrollBarPosition = 1
+ local updateScroll = function()
+ if scrollUpButton then
+ scrollUpButton.Active = scrollBarPosition > 1
+ end
+ if scrollDownButton then
+ scrollDownButton.Active = scrollBarPosition + dropDownItemCount <= itemCount
+ end
+
+ local children = droppedDownMenu:GetChildren()
+ if not children then return end
+
+ local childNum = 1
+ for i, obj in ipairs(children) do
+ if obj.Name == "ChoiceButton" then
+ if childNum < scrollBarPosition or childNum >= scrollBarPosition + dropDownItemCount then
+ obj.Visible = false
+ else
+ obj.Position = UDim2.new(0,0,((childNum-scrollBarPosition+1)*.8)/((dropDownItemCount+1)*.8),0)
+ obj.Visible = true
+ end
+ obj.TextColor3 = textColor
+ obj.BackgroundTransparency = 1
+
+ childNum = childNum + 1
+ end
+ end
+ end
+ local toggleVisibility = function()
+ dropDownSelected = not dropDownSelected
+
+ areaSoak.Visible = not areaSoak.Visible
+ dropDownMenu.Visible = not dropDownSelected
+ droppedDownMenu.Visible = dropDownSelected
+ if dropDownSelected then
+ setZIndex(4 + baseZIndex)
+ else
+ setZIndex(2 + baseZIndex)
+ end
+ if useScrollButtons then
+ updateScroll()
+ end
+ end
+ droppedDownMenu.MouseButton1Click:connect(toggleVisibility)
+
+ local updateSelection = function(text)
+ local foundItem = false
+ local children = droppedDownMenu:GetChildren()
+ local childNum = 1
+ if children then
+ for i, obj in ipairs(children) do
+ if obj.Name == "ChoiceButton" then
+ if obj.Text == text then
+ obj.Font = Enum.Font.ArialBold
+ foundItem = true
+ scrollBarPosition = childNum
+ if (whiteSkin) then
+ obj.TextColor3 = Color3.new(90/255,142/255,233/255)
+ end
+ else
+ obj.Font = Enum.Font.Arial
+ if (whiteSkin) then
+ obj.TextColor3 = textColor
+ end
+ end
+ childNum = childNum + 1
+ end
+ end
+ end
+ if not text then
+ dropDownMenu.Text = "Choose One"
+ scrollBarPosition = 1
+ else
+ if not foundItem then
+ error("Invalid Selection Update -- " .. text)
+ end
+
+ if scrollBarPosition + dropDownItemCount > itemCount + 1 then
+ scrollBarPosition = itemCount - dropDownItemCount + 1
+ end
+
+ dropDownMenu.Text = text
+ end
+ end
+
+ local function scrollDown()
+ if scrollBarPosition + dropDownItemCount <= itemCount then
+ scrollBarPosition = scrollBarPosition + 1
+ updateScroll()
+ return true
+ end
+ return false
+ end
+ local function scrollUp()
+ if scrollBarPosition > 1 then
+ scrollBarPosition = scrollBarPosition - 1
+ updateScroll()
+ return true
+ end
+ return false
+ end
+
+ if useScrollButtons then
+ --Make some scroll buttons
+ scrollUpButton = Instance.new("ImageButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.BackgroundTransparency = 1
+ scrollUpButton.Image = "rbxasset://textures/ui/scrollbuttonUp.png"
+ scrollUpButton.Size = UDim2.new(0,17,0,17)
+ scrollUpButton.Position = UDim2.new(1,-11,(1*.8)/((dropDownItemCount+1)*.8),0)
+ scrollUpButton.MouseButton1Click:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollUpButton.MouseLeave:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollUpButton.MouseButton1Down:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+
+ scrollUp()
+ local val = scrollMouseCount
+ wait(0.5)
+ while val == scrollMouseCount do
+ if scrollUp() == false then
+ break
+ end
+ wait(0.1)
+ end
+ end)
+
+ scrollUpButton.Parent = droppedDownMenu
+
+ scrollDownButton = Instance.new("ImageButton")
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.BackgroundTransparency = 1
+ scrollDownButton.Image = "rbxasset://textures/ui/scrollbuttonDown.png"
+ scrollDownButton.Size = UDim2.new(0,17,0,17)
+ scrollDownButton.Position = UDim2.new(1,-11,1,-11)
+ scrollDownButton.Parent = droppedDownMenu
+ scrollDownButton.MouseButton1Click:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollDownButton.MouseLeave:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollDownButton.MouseButton1Down:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+
+ scrollDown()
+ local val = scrollMouseCount
+ wait(0.5)
+ while val == scrollMouseCount do
+ if scrollDown() == false then
+ break
+ end
+ wait(0.1)
+ end
+ end)
+
+ local scrollbar = Instance.new("ImageLabel")
+ scrollbar.Name = "ScrollBar"
+ scrollbar.Image = "rbxasset://textures/ui/scrollbar.png"
+ scrollbar.BackgroundTransparency = 1
+ scrollbar.Size = UDim2.new(0, 18, (dropDownItemCount*.8)/((dropDownItemCount+1)*.8), -(17) - 11 - 4)
+ scrollbar.Position = UDim2.new(1,-11,(1*.8)/((dropDownItemCount+1)*.8),17+2)
+ scrollbar.Parent = droppedDownMenu
+ end
+
+ for i,item in ipairs(items) do
+ -- needed to maintain local scope for items in event listeners below
+ local button = choiceButton:clone()
+ if forRoblox then
+ button.RobloxLocked = true
+ end
+ button.Text = item
+ button.Parent = droppedDownMenu
+ if (whiteSkin) then
+ button.TextColor3 = textColor
+ end
+
+ button.MouseButton1Click:connect(function()
+ --Remove Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ button.BackgroundTransparency = 1
+
+ updateSelection(item)
+ onSelect(item)
+
+ toggleVisibility()
+ end)
+ button.MouseEnter:connect(function()
+ --Add Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(0,0,0)
+ end
+ button.BackgroundTransparency = 0
+ end)
+
+ button.MouseLeave:connect(function()
+ --Remove Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ button.BackgroundTransparency = 1
+ end)
+ end
+
+ --This does the initial layout of the buttons
+ updateScroll()
+
+ frame.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(frame)
+ end
+ end)
+
+ dropDownMenu.MouseButton1Click:connect(toggleVisibility)
+ areaSoak.MouseButton1Click:connect(toggleVisibility)
+ return frame, updateSelection
+end
+
+t.CreatePropertyDropDownMenu = function(instance, property, enum)
+
+ local items = enum:GetEnumItems()
+ local names = {}
+ local nameToItem = {}
+ for i,obj in ipairs(items) do
+ names[i] = obj.Name
+ nameToItem[obj.Name] = obj
+ end
+
+ local frame
+ local updateSelection
+ frame, updateSelection = t.CreateDropDownMenu(names, function(text) instance[property] = nameToItem[text] end)
+
+ ScopedConnect(frame, instance, "Changed",
+ function(prop)
+ if prop == property then
+ updateSelection(instance[property].Name)
+ end
+ end,
+ function()
+ updateSelection(instance[property].Name)
+ end)
+
+ return frame
+end
+
+t.GetFontHeight = function(font, fontSize)
+ if font == nil or fontSize == nil then
+ error("Font and FontSize must be non-nil")
+ end
+
+ if font == Enum.Font.Legacy then
+ if fontSize == Enum.FontSize.Size8 then
+ return 12
+ elseif fontSize == Enum.FontSize.Size9 then
+ return 14
+ elseif fontSize == Enum.FontSize.Size10 then
+ return 15
+ elseif fontSize == Enum.FontSize.Size11 then
+ return 17
+ elseif fontSize == Enum.FontSize.Size12 then
+ return 18
+ elseif fontSize == Enum.FontSize.Size14 then
+ return 21
+ elseif fontSize == Enum.FontSize.Size18 then
+ return 27
+ elseif fontSize == Enum.FontSize.Size24 then
+ return 36
+ elseif fontSize == Enum.FontSize.Size36 then
+ return 54
+ elseif fontSize == Enum.FontSize.Size48 then
+ return 72
+ else
+ error("Unknown FontSize")
+ end
+ elseif font == Enum.Font.Arial or font == Enum.Font.ArialBold then
+ if fontSize == Enum.FontSize.Size8 then
+ return 8
+ elseif fontSize == Enum.FontSize.Size9 then
+ return 9
+ elseif fontSize == Enum.FontSize.Size10 then
+ return 10
+ elseif fontSize == Enum.FontSize.Size11 then
+ return 11
+ elseif fontSize == Enum.FontSize.Size12 then
+ return 12
+ elseif fontSize == Enum.FontSize.Size14 then
+ return 14
+ elseif fontSize == Enum.FontSize.Size18 then
+ return 18
+ elseif fontSize == Enum.FontSize.Size24 then
+ return 24
+ elseif fontSize == Enum.FontSize.Size36 then
+ return 36
+ elseif fontSize == Enum.FontSize.Size48 then
+ return 48
+ else
+ error("Unknown FontSize")
+ end
+ else
+ error("Unknown Font " .. font)
+ end
+end
+
+local function layoutGuiObjectsHelper(frame, guiObjects, settingsTable)
+ local totalPixels = frame.AbsoluteSize.Y
+ local pixelsRemaining = frame.AbsoluteSize.Y
+ for i, child in ipairs(guiObjects) do
+ if child:IsA("TextLabel") or child:IsA("TextButton") then
+ local isLabel = child:IsA("TextLabel")
+ if isLabel then
+ pixelsRemaining = pixelsRemaining - settingsTable["TextLabelPositionPadY"]
+ else
+ pixelsRemaining = pixelsRemaining - settingsTable["TextButtonPositionPadY"]
+ end
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, pixelsRemaining)
+
+ if child.TextFits and child.TextBounds.Y < pixelsRemaining then
+ child.Visible = true
+ if isLabel then
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.TextBounds.Y + settingsTable["TextLabelSizePadY"])
+ else
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.TextBounds.Y + settingsTable["TextButtonSizePadY"])
+ end
+
+ while not child.TextFits do
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.AbsoluteSize.Y + 1)
+ end
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+
+ if isLabel then
+ pixelsRemaining = pixelsRemaining - settingsTable["TextLabelPositionPadY"]
+ else
+ pixelsRemaining = pixelsRemaining - settingsTable["TextButtonPositionPadY"]
+ end
+ else
+ child.Visible = false
+ pixelsRemaining = -1
+ end
+
+ else
+ --GuiObject
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+ child.Visible = (pixelsRemaining >= 0)
+ end
+ end
+end
+
+t.LayoutGuiObjects = function(frame, guiObjects, settingsTable)
+ if not frame:IsA("GuiObject") then
+ error("Frame must be a GuiObject")
+ end
+ for i, child in ipairs(guiObjects) do
+ if not child:IsA("GuiObject") then
+ error("All elements that are layed out must be of type GuiObject")
+ end
+ end
+
+ if not settingsTable then
+ settingsTable = {}
+ end
+
+ if not settingsTable["TextLabelSizePadY"] then
+ settingsTable["TextLabelSizePadY"] = 0
+ end
+ if not settingsTable["TextLabelPositionPadY"] then
+ settingsTable["TextLabelPositionPadY"] = 0
+ end
+ if not settingsTable["TextButtonSizePadY"] then
+ settingsTable["TextButtonSizePadY"] = 12
+ end
+ if not settingsTable["TextButtonPositionPadY"] then
+ settingsTable["TextButtonPositionPadY"] = 2
+ end
+
+ --Wrapper frame takes care of styled objects
+ local wrapperFrame = Instance.new("Frame")
+ wrapperFrame.Name = "WrapperFrame"
+ wrapperFrame.BackgroundTransparency = 1
+ wrapperFrame.Size = UDim2.new(1,0,1,0)
+ wrapperFrame.Parent = frame
+
+ for i, child in ipairs(guiObjects) do
+ child.Parent = wrapperFrame
+ end
+
+ local recalculate = function()
+ wait()
+ layoutGuiObjectsHelper(wrapperFrame, guiObjects, settingsTable)
+ end
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ --Wait a heartbeat for it to sync in
+ recalculate(nil)
+ end
+ end)
+ frame.AncestryChanged:connect(recalculate)
+
+ layoutGuiObjectsHelper(wrapperFrame, guiObjects, settingsTable)
+end
+
+
+t.CreateSlider = function(steps,width,position)
+ local sliderGui = Instance.new("Frame")
+ sliderGui.Size = UDim2.new(1,0,1,0)
+ sliderGui.BackgroundTransparency = 1
+ sliderGui.Name = "SliderGui"
+
+ local sliderSteps = Instance.new("IntValue")
+ sliderSteps.Name = "SliderSteps"
+ sliderSteps.Value = steps
+ sliderSteps.Parent = sliderGui
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = false
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 4
+
+ sliderGui.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(sliderGui)
+ end
+ end)
+
+ local sliderPosition = Instance.new("IntValue")
+ sliderPosition.Name = "SliderPosition"
+ sliderPosition.Value = 0
+ sliderPosition.Parent = sliderGui
+
+ local id = math.random(1,100)
+
+ local bar = Instance.new("TextButton")
+ bar.Text = ""
+ bar.AutoButtonColor = false
+ bar.Name = "Bar"
+ bar.BackgroundColor3 = Color3.new(0,0,0)
+ if type(width) == "number" then
+ bar.Size = UDim2.new(0,width,0,5)
+ else
+ bar.Size = UDim2.new(0,200,0,5)
+ end
+ bar.BorderColor3 = Color3.new(95/255,95/255,95/255)
+ bar.ZIndex = 2
+ bar.Parent = sliderGui
+
+ if position["X"] and position["X"]["Scale"] and position["X"]["Offset"] and position["Y"] and position["Y"]["Scale"] and position["Y"]["Offset"] then
+ bar.Position = position
+ end
+
+ local slider = Instance.new("ImageButton")
+ slider.Name = "Slider"
+ slider.BackgroundTransparency = 1
+ slider.Image = "rbxasset://textures/ui/Slider.png"
+ slider.Position = UDim2.new(0,0,0.5,-10)
+ slider.Size = UDim2.new(0,20,0,20)
+ slider.ZIndex = 3
+ slider.Parent = bar
+
+ local areaSoakMouseMoveCon = nil
+
+ areaSoak.MouseLeave:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+ areaSoak.MouseButton1Up:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+
+ slider.MouseButton1Down:connect(function()
+ areaSoak.Visible = true
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+ areaSoakMouseMoveCon = areaSoak.MouseMoved:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+ end)
+
+ slider.MouseButton1Up:connect(function() cancelSlide(areaSoak) end)
+
+ sliderPosition.Changed:connect(function(prop)
+ sliderPosition.Value = math.min(steps, math.max(1,sliderPosition.Value))
+ local relativePosX = (sliderPosition.Value - 1) / (steps - 1)
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ end)
+
+ bar.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ return sliderGui, sliderPosition, sliderSteps
+
+end
+
+
+
+t.CreateSliderNew = function(steps,width,position)
+ local sliderGui = Instance.new("Frame")
+ sliderGui.Size = UDim2.new(1,0,1,0)
+ sliderGui.BackgroundTransparency = 1
+ sliderGui.Name = "SliderGui"
+
+ local sliderSteps = Instance.new("IntValue")
+ sliderSteps.Name = "SliderSteps"
+ sliderSteps.Value = steps
+ sliderSteps.Parent = sliderGui
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = false
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 6
+
+ sliderGui.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(sliderGui)
+ end
+ end)
+
+ local sliderPosition = Instance.new("IntValue")
+ sliderPosition.Name = "SliderPosition"
+ sliderPosition.Value = 0
+ sliderPosition.Parent = sliderGui
+
+ local id = math.random(1,100)
+
+ local sliderBarImgHeight = 7
+ local sliderBarCapImgWidth = 4
+
+ local bar = Instance.new("ImageButton")
+ bar.BackgroundTransparency = 1
+ bar.Image = "rbxasset://textures/ui/Slider-BKG-Center.png"
+ bar.Name = "Bar"
+ local displayWidth = 200
+ if type(width) == "number" then
+ bar.Size = UDim2.new(0,width - (sliderBarCapImgWidth * 2),0,sliderBarImgHeight)
+ displayWidth = width - (sliderBarCapImgWidth * 2)
+ else
+ bar.Size = UDim2.new(0,200,0,sliderBarImgHeight)
+ end
+ bar.ZIndex = 3
+ bar.Parent = sliderGui
+ if position["X"] and position["X"]["Scale"] and position["X"]["Offset"] and position["Y"] and position["Y"]["Scale"] and position["Y"]["Offset"] then
+ bar.Position = position
+ end
+
+ local barLeft = bar:clone()
+ barLeft.Name = "BarLeft"
+ barLeft.Image = "rbxasset://textures/ui/Slider-BKG-Left-Cap.png"
+ barLeft.Size = UDim2.new(0, sliderBarCapImgWidth, 0, sliderBarImgHeight)
+ barLeft.Position = UDim2.new(position.X.Scale, position.X.Offset - sliderBarCapImgWidth, position.Y.Scale, position.Y.Offset)
+ barLeft.Parent = sliderGui
+ barLeft.ZIndex = 3
+
+ local barRight = barLeft:clone()
+ barRight.Name = "BarRight"
+ barRight.Image = "rbxasset://textures/ui/Slider-BKG-Right-Cap.png"
+ barRight.Position = UDim2.new(position.X.Scale, position.X.Offset + displayWidth, position.Y.Scale, position.Y.Offset)
+ barRight.Parent = sliderGui
+
+ local fillLeft = barLeft:clone()
+ fillLeft.Name = "FillLeft"
+ fillLeft.Image = "rbxasset://textures/ui/Slider-Fill-Left-Cap.png"
+ fillLeft.Parent = sliderGui
+ fillLeft.ZIndex = 4
+
+ local fill = fillLeft:clone()
+ fill.Name = "Fill"
+ fill.Image = "rbxasset://textures/ui/Slider-Fill-Center.png"
+ fill.Parent = bar
+ fill.ZIndex = 4
+ fill.Position = UDim2.new(0, 0, 0, 0)
+ fill.Size = UDim2.new(0.5, 0, 1, 0)
+
+
+-- bar.Visible = false
+
+ local slider = Instance.new("ImageButton")
+ slider.Name = "Slider"
+ slider.BackgroundTransparency = 1
+ slider.Image = "rbxasset://textures/ui/slider_new_tab.png"
+ slider.Position = UDim2.new(0,0,0.5,-14)
+ slider.Size = UDim2.new(0,28,0,28)
+ slider.ZIndex = 5
+ slider.Parent = bar
+
+ local areaSoakMouseMoveCon = nil
+
+ areaSoak.MouseLeave:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+ areaSoak.MouseButton1Up:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+
+ slider.MouseButton1Down:connect(function()
+ areaSoak.Visible = true
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+ areaSoakMouseMoveCon = areaSoak.MouseMoved:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+ end)
+
+ slider.MouseButton1Up:connect(function() cancelSlide(areaSoak) end)
+
+ sliderPosition.Changed:connect(function(prop)
+ sliderPosition.Value = math.min(steps, math.max(1,sliderPosition.Value))
+ local relativePosX = (sliderPosition.Value - 1) / (steps - 1)
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ fill.Size = UDim2.new(relativePosX, 0, 1, 0)
+ end)
+
+ bar.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ fill.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ fillLeft.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+
+ return sliderGui, sliderPosition, sliderSteps
+
+end
+
+
+
+
+
+t.CreateTrueScrollingFrame = function()
+ local lowY = nil
+ local highY = nil
+
+ local dragCon = nil
+ local upCon = nil
+
+ local internalChange = false
+
+ local descendantsChangeConMap = {}
+
+ local scrollingFrame = Instance.new("Frame")
+ scrollingFrame.Name = "ScrollingFrame"
+ scrollingFrame.Active = true
+ scrollingFrame.Size = UDim2.new(1,0,1,0)
+ scrollingFrame.ClipsDescendants = true
+
+ local controlFrame = Instance.new("Frame")
+ controlFrame.Name = "ControlFrame"
+ controlFrame.BackgroundTransparency = 1
+ controlFrame.Size = UDim2.new(0,18,1,0)
+ controlFrame.Position = UDim2.new(1,-20,0,0)
+ controlFrame.Parent = scrollingFrame
+
+ local scrollBottom = Instance.new("BoolValue")
+ scrollBottom.Value = false
+ scrollBottom.Name = "ScrollBottom"
+ scrollBottom.Parent = controlFrame
+
+ local scrollUp = Instance.new("BoolValue")
+ scrollUp.Value = false
+ scrollUp.Name = "scrollUp"
+ scrollUp.Parent = controlFrame
+
+ local scrollUpButton = Instance.new("TextButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.Text = ""
+ scrollUpButton.AutoButtonColor = false
+ scrollUpButton.BackgroundColor3 = Color3.new(0,0,0)
+ scrollUpButton.BorderColor3 = Color3.new(1,1,1)
+ scrollUpButton.BackgroundTransparency = 0.5
+ scrollUpButton.Size = UDim2.new(0,18,0,18)
+ scrollUpButton.ZIndex = 2
+ scrollUpButton.Parent = controlFrame
+ for i = 1, 6 do
+ local triFrame = Instance.new("Frame")
+ triFrame.BorderColor3 = Color3.new(1,1,1)
+ triFrame.Name = "tri" .. tostring(i)
+ triFrame.ZIndex = 3
+ triFrame.BackgroundTransparency = 0.5
+ triFrame.Size = UDim2.new(0,12 - ((i -1) * 2),0,0)
+ triFrame.Position = UDim2.new(0,3 + (i -1),0.5,2 - (i -1))
+ triFrame.Parent = scrollUpButton
+ end
+ scrollUpButton.MouseEnter:connect(function()
+ scrollUpButton.BackgroundTransparency = 0.1
+ local upChildren = scrollUpButton:GetChildren()
+ for i = 1, #upChildren do
+ upChildren[i].BackgroundTransparency = 0.1
+ end
+ end)
+ scrollUpButton.MouseLeave:connect(function()
+ scrollUpButton.BackgroundTransparency = 0.5
+ local upChildren = scrollUpButton:GetChildren()
+ for i = 1, #upChildren do
+ upChildren[i].BackgroundTransparency = 0.5
+ end
+ end)
+
+ local scrollDownButton = scrollUpButton:clone()
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.Position = UDim2.new(0,0,1,-18)
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].Position = UDim2.new(0,3 + (i -1),0.5,-2 + (i - 1))
+ end
+ scrollDownButton.MouseEnter:connect(function()
+ scrollDownButton.BackgroundTransparency = 0.1
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].BackgroundTransparency = 0.1
+ end
+ end)
+ scrollDownButton.MouseLeave:connect(function()
+ scrollDownButton.BackgroundTransparency = 0.5
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].BackgroundTransparency = 0.5
+ end
+ end)
+ scrollDownButton.Parent = controlFrame
+
+ local scrollTrack = Instance.new("Frame")
+ scrollTrack.Name = "ScrollTrack"
+ scrollTrack.BackgroundTransparency = 1
+ scrollTrack.Size = UDim2.new(0,18,1,-38)
+ scrollTrack.Position = UDim2.new(0,0,0,19)
+ scrollTrack.Parent = controlFrame
+
+ local scrollbar = Instance.new("TextButton")
+ scrollbar.BackgroundColor3 = Color3.new(0,0,0)
+ scrollbar.BorderColor3 = Color3.new(1,1,1)
+ scrollbar.BackgroundTransparency = 0.5
+ scrollbar.AutoButtonColor = false
+ scrollbar.Text = ""
+ scrollbar.Active = true
+ scrollbar.Name = "ScrollBar"
+ scrollbar.ZIndex = 2
+ scrollbar.BackgroundTransparency = 0.5
+ scrollbar.Size = UDim2.new(0, 18, 0.1, 0)
+ scrollbar.Position = UDim2.new(0,0,0,0)
+ scrollbar.Parent = scrollTrack
+
+ local scrollNub = Instance.new("Frame")
+ scrollNub.Name = "ScrollNub"
+ scrollNub.BorderColor3 = Color3.new(1,1,1)
+ scrollNub.Size = UDim2.new(0,10,0,0)
+ scrollNub.Position = UDim2.new(0.5,-5,0.5,0)
+ scrollNub.ZIndex = 2
+ scrollNub.BackgroundTransparency = 0.5
+ scrollNub.Parent = scrollbar
+
+ local newNub = scrollNub:clone()
+ newNub.Position = UDim2.new(0.5,-5,0.5,-2)
+ newNub.Parent = scrollbar
+
+ local lastNub = scrollNub:clone()
+ lastNub.Position = UDim2.new(0.5,-5,0.5,2)
+ lastNub.Parent = scrollbar
+
+ scrollbar.MouseEnter:connect(function()
+ scrollbar.BackgroundTransparency = 0.1
+ scrollNub.BackgroundTransparency = 0.1
+ newNub.BackgroundTransparency = 0.1
+ lastNub.BackgroundTransparency = 0.1
+ end)
+ scrollbar.MouseLeave:connect(function()
+ scrollbar.BackgroundTransparency = 0.5
+ scrollNub.BackgroundTransparency = 0.5
+ newNub.BackgroundTransparency = 0.5
+ lastNub.BackgroundTransparency = 0.5
+ end)
+
+ local mouseDrag = Instance.new("ImageButton")
+ mouseDrag.Active = false
+ mouseDrag.Size = UDim2.new(1.5, 0, 1.5, 0)
+ mouseDrag.AutoButtonColor = false
+ mouseDrag.BackgroundTransparency = 1
+ mouseDrag.Name = "mouseDrag"
+ mouseDrag.Position = UDim2.new(-0.25, 0, -0.25, 0)
+ mouseDrag.ZIndex = 10
+
+ local function positionScrollBar(x,y,offset)
+ local oldPos = scrollbar.Position
+
+ if y < scrollTrack.AbsolutePosition.y then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,0,0)
+ return (oldPos ~= scrollbar.Position)
+ end
+
+ local relativeSize = scrollbar.AbsoluteSize.Y/scrollTrack.AbsoluteSize.Y
+
+ if y > (scrollTrack.AbsolutePosition.y + scrollTrack.AbsoluteSize.y) then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,1 - relativeSize,0)
+ return (oldPos ~= scrollbar.Position)
+ end
+ local newScaleYPos = (y - scrollTrack.AbsolutePosition.y - offset)/scrollTrack.AbsoluteSize.y
+ if newScaleYPos + relativeSize > 1 then
+ newScaleYPos = 1 - relativeSize
+ scrollBottom.Value = true
+ scrollUp.Value = false
+ elseif newScaleYPos <= 0 then
+ newScaleYPos = 0
+ scrollUp.Value = true
+ scrollBottom.Value = false
+ else
+ scrollUp.Value = false
+ scrollBottom.Value = false
+ end
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,newScaleYPos,0)
+
+ return (oldPos ~= scrollbar.Position)
+ end
+
+ local function drillDownSetHighLow(instance)
+ if not instance or not instance:IsA("GuiObject") then return end
+ if instance == controlFrame then return end
+ if instance:IsDescendantOf(controlFrame) then return end
+ if not instance.Visible then return end
+
+ if lowY and lowY > instance.AbsolutePosition.Y then
+ lowY = instance.AbsolutePosition.Y
+ elseif not lowY then
+ lowY = instance.AbsolutePosition.Y
+ end
+ if highY and highY < (instance.AbsolutePosition.Y + instance.AbsoluteSize.Y) then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ elseif not highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ end
+ local children = instance:GetChildren()
+ for i = 1, #children do
+ drillDownSetHighLow(children[i])
+ end
+ end
+
+ local function resetHighLow()
+ local firstChildren = scrollingFrame:GetChildren()
+
+ for i = 1, #firstChildren do
+ drillDownSetHighLow(firstChildren[i])
+ end
+ end
+
+ local function recalculate()
+ internalChange = true
+
+ local percentFrame = 0
+ if scrollbar.Position.Y.Scale > 0 then
+ if scrollbar.Visible then
+ percentFrame = scrollbar.Position.Y.Scale/((scrollTrack.AbsoluteSize.Y - scrollbar.AbsoluteSize.Y)/scrollTrack.AbsoluteSize.Y)
+ else
+ percentFrame = 0
+ end
+ end
+ if percentFrame > 0.99 then percentFrame = 1 end
+
+ local hiddenYAmount = (scrollingFrame.AbsoluteSize.Y - (highY - lowY)) * percentFrame
+
+ local guiChildren = scrollingFrame:GetChildren()
+ for i = 1, #guiChildren do
+ if guiChildren[i] ~= controlFrame then
+ guiChildren[i].Position = UDim2.new(guiChildren[i].Position.X.Scale,guiChildren[i].Position.X.Offset,
+ 0, math.ceil(guiChildren[i].AbsolutePosition.Y) - math.ceil(lowY) + hiddenYAmount)
+ end
+ end
+
+ lowY = nil
+ highY = nil
+ resetHighLow()
+ internalChange = false
+ end
+
+ local function setSliderSizeAndPosition()
+ if not highY or not lowY then return end
+
+ local totalYSpan = math.abs(highY - lowY)
+ if totalYSpan == 0 then
+ scrollbar.Visible = false
+ scrollDownButton.Visible = false
+ scrollUpButton.Visible = false
+
+ if dragCon then dragCon:disconnect() dragCon = nil end
+ if upCon then upCon:disconnect() upCon = nil end
+ return
+ end
+
+ local percentShown = scrollingFrame.AbsoluteSize.Y/totalYSpan
+ if percentShown >= 1 then
+ scrollbar.Visible = false
+ scrollDownButton.Visible = false
+ scrollUpButton.Visible = false
+ recalculate()
+ else
+ scrollbar.Visible = true
+ scrollDownButton.Visible = true
+ scrollUpButton.Visible = true
+
+ scrollbar.Size = UDim2.new(scrollbar.Size.X.Scale,scrollbar.Size.X.Offset,percentShown,0)
+ end
+
+ local percentPosition = (scrollingFrame.AbsolutePosition.Y - lowY)/totalYSpan
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,percentPosition,-scrollbar.AbsoluteSize.X/2)
+
+ if scrollbar.AbsolutePosition.y < scrollTrack.AbsolutePosition.y then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,0,0)
+ end
+
+ if (scrollbar.AbsolutePosition.y + scrollbar.AbsoluteSize.Y) > (scrollTrack.AbsolutePosition.y + scrollTrack.AbsoluteSize.y) then
+ local relativeSize = scrollbar.AbsoluteSize.Y/scrollTrack.AbsoluteSize.Y
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,1 - relativeSize,0)
+ end
+ end
+
+ local buttonScrollAmountPixels = 7
+ local reentrancyGuardScrollUp = false
+ local function doScrollUp()
+ if reentrancyGuardScrollUp then return end
+
+ reentrancyGuardScrollUp = true
+ if positionScrollBar(0,scrollbar.AbsolutePosition.Y - buttonScrollAmountPixels,0) then
+ recalculate()
+ end
+ reentrancyGuardScrollUp = false
+ end
+
+ local reentrancyGuardScrollDown = false
+ local function doScrollDown()
+ if reentrancyGuardScrollDown then return end
+
+ reentrancyGuardScrollDown = true
+ if positionScrollBar(0,scrollbar.AbsolutePosition.Y + buttonScrollAmountPixels,0) then
+ recalculate()
+ end
+ reentrancyGuardScrollDown = false
+ end
+
+ local function scrollUp(mouseYPos)
+ if scrollUpButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local upCon
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ upCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollUp()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollUp()
+ if mouseYPos and mouseYPos > scrollbar.AbsolutePosition.y then
+ break
+ end
+ if not scrollUpButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local function scrollDown(mouseYPos)
+ if scrollDownButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local downCon
+ downCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ downCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollDown()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollDown()
+ if mouseYPos and mouseYPos < (scrollbar.AbsolutePosition.y + scrollbar.AbsoluteSize.x) then
+ break
+ end
+ if not scrollDownButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ scrollbar.MouseButton1Down:connect(function(x,y)
+ if scrollbar.Active then
+ scrollStamp = tick()
+ local mouseOffset = y - scrollbar.AbsolutePosition.y
+ if dragCon then dragCon:disconnect() dragCon = nil end
+ if upCon then upCon:disconnect() upCon = nil end
+ local prevY = y
+ local reentrancyGuardMouseScroll = false
+ dragCon = mouseDrag.MouseMoved:connect(function(x,y)
+ if reentrancyGuardMouseScroll then return end
+
+ reentrancyGuardMouseScroll = true
+ if positionScrollBar(x,y,mouseOffset) then
+ recalculate()
+ end
+ reentrancyGuardMouseScroll = false
+
+ end)
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ dragCon:disconnect(); dragCon = nil
+ upCon:disconnect(); drag = nil
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ end
+ end)
+
+ local scrollMouseCount = 0
+
+ scrollUpButton.MouseButton1Down:connect(function()
+ scrollUp()
+ end)
+ scrollUpButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+ scrollDownButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollDownButton.MouseButton1Down:connect(function()
+ scrollDown()
+ end)
+
+ scrollbar.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+ local function heightCheck(instance)
+ if highY and (instance.AbsolutePosition.Y + instance.AbsoluteSize.Y) > highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ elseif not highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ end
+ setSliderSizeAndPosition()
+ end
+
+ local function highLowRecheck()
+ local oldLowY = lowY
+ local oldHighY = highY
+ lowY = nil
+ highY = nil
+ resetHighLow()
+
+ if (lowY ~= oldLowY) or (highY ~= oldHighY) then
+ setSliderSizeAndPosition()
+ end
+ end
+
+ local function descendantChanged(this, prop)
+ if internalChange then return end
+ if not this.Visible then return end
+
+ if prop == "Size" or prop == "Position" then
+ wait()
+ highLowRecheck()
+ end
+ end
+
+ scrollingFrame.DescendantAdded:connect(function(instance)
+ if not instance:IsA("GuiObject") then return end
+
+ if instance.Visible then
+ wait() -- wait a heartbeat for sizes to reconfig
+ highLowRecheck()
+ end
+
+ descendantsChangeConMap[instance] = instance.Changed:connect(function(prop) descendantChanged(instance, prop) end)
+ end)
+
+ scrollingFrame.DescendantRemoving:connect(function(instance)
+ if not instance:IsA("GuiObject") then return end
+ if descendantsChangeConMap[instance] then
+ descendantsChangeConMap[instance]:disconnect()
+ descendantsChangeConMap[instance] = nil
+ end
+ wait() -- wait a heartbeat for sizes to reconfig
+ highLowRecheck()
+ end)
+
+ scrollingFrame.Changed:connect(function(prop)
+ if prop == "AbsoluteSize" then
+ if not highY or not lowY then return end
+
+ highLowRecheck()
+ setSliderSizeAndPosition()
+ end
+ end)
+
+ return scrollingFrame, controlFrame
+end
+
+t.CreateScrollingFrame = function(orderList,scrollStyle)
+ local frame = Instance.new("Frame")
+ frame.Name = "ScrollingFrame"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+
+ local scrollUpButton = Instance.new("ImageButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.BackgroundTransparency = 1
+ scrollUpButton.Image = "rbxasset://textures/ui/scrollbuttonUp.png"
+ scrollUpButton.Size = UDim2.new(0,17,0,17)
+
+
+ local scrollDownButton = Instance.new("ImageButton")
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.BackgroundTransparency = 1
+ scrollDownButton.Image = "rbxasset://textures/ui/scrollbuttonDown.png"
+ scrollDownButton.Size = UDim2.new(0,17,0,17)
+
+ local scrollbar = Instance.new("ImageButton")
+ scrollbar.Name = "ScrollBar"
+ scrollbar.Image = "rbxasset://textures/ui/scrollbar.png"
+ scrollbar.BackgroundTransparency = 1
+ scrollbar.Size = UDim2.new(0, 18, 0, 150)
+
+ local scrollStamp = 0
+
+ local scrollDrag = Instance.new("ImageButton")
+ scrollDrag.Image = "http://www.roblox.com/asset/?id=61367186"
+ scrollDrag.Size = UDim2.new(1, 0, 0, 16)
+ scrollDrag.BackgroundTransparency = 1
+ scrollDrag.Name = "ScrollDrag"
+ scrollDrag.Active = true
+ scrollDrag.Parent = scrollbar
+
+ local mouseDrag = Instance.new("ImageButton")
+ mouseDrag.Active = false
+ mouseDrag.Size = UDim2.new(1.5, 0, 1.5, 0)
+ mouseDrag.AutoButtonColor = false
+ mouseDrag.BackgroundTransparency = 1
+ mouseDrag.Name = "mouseDrag"
+ mouseDrag.Position = UDim2.new(-0.25, 0, -0.25, 0)
+ mouseDrag.ZIndex = 10
+
+ local style = "simple"
+ if scrollStyle and tostring(scrollStyle) then
+ style = scrollStyle
+ end
+
+ local scrollPosition = 1
+ local rowSize = 0
+ local howManyDisplayed = 0
+
+ local layoutGridScrollBar = function()
+ howManyDisplayed = 0
+ local guiObjects = {}
+ if orderList then
+ for i, child in ipairs(orderList) do
+ if child.Parent == frame then
+ table.insert(guiObjects, child)
+ end
+ end
+ else
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ table.insert(guiObjects, child)
+ end
+ end
+ end
+ end
+ if #guiObjects == 0 then
+ scrollUpButton.Active = false
+ scrollDownButton.Active = false
+ scrollDrag.Active = false
+ scrollPosition = 1
+ return
+ end
+
+ if scrollPosition > #guiObjects then
+ scrollPosition = #guiObjects
+ end
+
+ if scrollPosition < 1 then scrollPosition = 1 end
+
+ local totalPixelsY = frame.AbsoluteSize.Y
+ local pixelsRemainingY = frame.AbsoluteSize.Y
+
+ local totalPixelsX = frame.AbsoluteSize.X
+
+ local xCounter = 0
+ local rowSizeCounter = 0
+ local setRowSize = true
+
+ local pixelsBelowScrollbar = 0
+ local pos = #guiObjects
+
+ local currentRowY = 0
+
+ pos = scrollPosition
+ --count up from current scroll position to fill out grid
+ while pos <= #guiObjects and pixelsBelowScrollbar < totalPixelsY do
+ xCounter = xCounter + guiObjects[pos].AbsoluteSize.X
+ --previous pos was the end of a row
+ if xCounter >= totalPixelsX then
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ currentRowY = 0
+ xCounter = guiObjects[pos].AbsoluteSize.X
+ end
+ if guiObjects[pos].AbsoluteSize.Y > currentRowY then
+ currentRowY = guiObjects[pos].AbsoluteSize.Y
+ end
+ pos = pos + 1
+ end
+ --Count wherever current row left off
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ currentRowY = 0
+
+ pos = scrollPosition - 1
+ xCounter = 0
+
+ --objects with varying X,Y dimensions can rarely cause minor errors
+ --rechecking every new scrollPosition is necessary to avoid 100% of errors
+
+ --count backwards from current scrollPosition to see if we can add more rows
+ while pixelsBelowScrollbar + currentRowY < totalPixelsY and pos >= 1 do
+ xCounter = xCounter + guiObjects[pos].AbsoluteSize.X
+ rowSizeCounter = rowSizeCounter + 1
+ if xCounter >= totalPixelsX then
+ rowSize = rowSizeCounter - 1
+ rowSizeCounter = 0
+ xCounter = guiObjects[pos].AbsoluteSize.X
+ if pixelsBelowScrollbar + currentRowY <= totalPixelsY then
+ --It fits, so back up our scroll position
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ if scrollPosition <= rowSize then
+ scrollPosition = 1
+ break
+ else
+ scrollPosition = scrollPosition - rowSize
+ end
+ currentRowY = 0
+ else
+ break
+ end
+ end
+
+ if guiObjects[pos].AbsoluteSize.Y > currentRowY then
+ currentRowY = guiObjects[pos].AbsoluteSize.Y
+ end
+
+ pos = pos - 1
+ end
+
+ --Do check last time if pos = 0
+ if (pos == 0) and (pixelsBelowScrollbar + currentRowY <= totalPixelsY) then
+ scrollPosition = 1
+ end
+
+ xCounter = 0
+ --pos = scrollPosition
+ rowSizeCounter = 0
+ setRowSize = true
+ local lastChildSize = 0
+
+ local xOffset,yOffset = 0
+ if guiObjects[1] then
+ yOffset = math.ceil(math.floor(math.fmod(totalPixelsY,guiObjects[1].AbsoluteSize.X))/2)
+ xOffset = math.ceil(math.floor(math.fmod(totalPixelsX,guiObjects[1].AbsoluteSize.Y))/2)
+ end
+
+ for i, child in ipairs(guiObjects) do
+ if i < scrollPosition then
+ --print("Hiding " .. child.Name)
+ child.Visible = false
+ else
+ if pixelsRemainingY < 0 then
+ --print("Out of Space " .. child.Name)
+ child.Visible = false
+ else
+ --print("Laying out " .. child.Name)
+ --GuiObject
+ if setRowSize then rowSizeCounter = rowSizeCounter + 1 end
+ if xCounter + child.AbsoluteSize.X >= totalPixelsX then
+ if setRowSize then
+ rowSize = rowSizeCounter - 1
+ setRowSize = false
+ end
+ xCounter = 0
+ pixelsRemainingY = pixelsRemainingY - child.AbsoluteSize.Y
+ end
+ child.Position = UDim2.new(child.Position.X.Scale,xCounter + xOffset, 0, totalPixelsY - pixelsRemainingY + yOffset)
+ xCounter = xCounter + child.AbsoluteSize.X
+ child.Visible = ((pixelsRemainingY - child.AbsoluteSize.Y) >= 0)
+ if child.Visible then
+ howManyDisplayed = howManyDisplayed + 1
+ end
+ lastChildSize = child.AbsoluteSize
+ end
+ end
+ end
+
+ scrollUpButton.Active = (scrollPosition > 1)
+ if lastChildSize == 0 then
+ scrollDownButton.Active = false
+ else
+ scrollDownButton.Active = ((pixelsRemainingY - lastChildSize.Y) < 0)
+ end
+ scrollDrag.Active = #guiObjects > howManyDisplayed
+ scrollDrag.Visible = scrollDrag.Active
+ end
+
+
+
+ local layoutSimpleScrollBar = function()
+ local guiObjects = {}
+ howManyDisplayed = 0
+
+ if orderList then
+ for i, child in ipairs(orderList) do
+ if child.Parent == frame then
+ table.insert(guiObjects, child)
+ end
+ end
+ else
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ table.insert(guiObjects, child)
+ end
+ end
+ end
+ end
+ if #guiObjects == 0 then
+ scrollUpButton.Active = false
+ scrollDownButton.Active = false
+ scrollDrag.Active = false
+ scrollPosition = 1
+ return
+ end
+
+ if scrollPosition > #guiObjects then
+ scrollPosition = #guiObjects
+ end
+
+ local totalPixels = frame.AbsoluteSize.Y
+ local pixelsRemaining = frame.AbsoluteSize.Y
+
+ local pixelsBelowScrollbar = 0
+ local pos = #guiObjects
+ while pixelsBelowScrollbar < totalPixels and pos >= 1 do
+ if pos >= scrollPosition then
+ pixelsBelowScrollbar = pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y
+ else
+ if pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y <= totalPixels then
+ --It fits, so back up our scroll position
+ pixelsBelowScrollbar = pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y
+ if scrollPosition <= 1 then
+ scrollPosition = 1
+ break
+ else
+ --local ("Backing up ScrollPosition from -- " ..scrollPosition)
+ scrollPosition = scrollPosition - 1
+ end
+ else
+ break
+ end
+ end
+ pos = pos - 1
+ end
+
+ pos = scrollPosition
+ for i, child in ipairs(guiObjects) do
+ if i < scrollPosition then
+ --print("Hiding " .. child.Name)
+ child.Visible = false
+ else
+ if pixelsRemaining < 0 then
+ --print("Out of Space " .. child.Name)
+ child.Visible = false
+ else
+ --print("Laying out " .. child.Name)
+ --GuiObject
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+ if (pixelsRemaining >= 0) then
+ child.Visible = true
+ howManyDisplayed = howManyDisplayed + 1
+ else
+ child.Visible = false
+ end
+ end
+ end
+ end
+ scrollUpButton.Active = (scrollPosition > 1)
+ scrollDownButton.Active = (pixelsRemaining < 0)
+ scrollDrag.Active = #guiObjects > howManyDisplayed
+ scrollDrag.Visible = scrollDrag.Active
+ end
+
+
+ local moveDragger = function()
+ local guiObjects = 0
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ guiObjects = guiObjects + 1
+ end
+ end
+ end
+
+ if not scrollDrag.Parent then return end
+
+ local dragSizeY = scrollDrag.Parent.AbsoluteSize.y * (1/(guiObjects - howManyDisplayed + 1))
+ if dragSizeY < 16 then dragSizeY = 16 end
+ scrollDrag.Size = UDim2.new(scrollDrag.Size.X.Scale,scrollDrag.Size.X.Offset,scrollDrag.Size.Y.Scale,dragSizeY)
+
+ local relativeYPos = (scrollPosition - 1)/(guiObjects - (howManyDisplayed))
+ if relativeYPos > 1 then relativeYPos = 1
+ elseif relativeYPos < 0 then relativeYPos = 0 end
+ local absYPos = 0
+
+ if relativeYPos ~= 0 then
+ absYPos = (relativeYPos * scrollbar.AbsoluteSize.y) - (relativeYPos * scrollDrag.AbsoluteSize.y)
+ end
+
+ scrollDrag.Position = UDim2.new(scrollDrag.Position.X.Scale,scrollDrag.Position.X.Offset,scrollDrag.Position.Y.Scale,absYPos)
+ end
+
+ local reentrancyGuard = false
+ local recalculate = function()
+ if reentrancyGuard then
+ return
+ end
+ reentrancyGuard = true
+ wait()
+ local success, err = nil
+ if style == "grid" then
+ success, err = pcall(function() layoutGridScrollBar() end)
+ elseif style == "simple" then
+ success, err = pcall(function() layoutSimpleScrollBar() end)
+ end
+ if not success then print(err) end
+ moveDragger()
+ reentrancyGuard = false
+ end
+
+ local doScrollUp = function()
+ scrollPosition = (scrollPosition) - rowSize
+ if scrollPosition < 1 then scrollPosition = 1 end
+ recalculate(nil)
+ end
+
+ local doScrollDown = function()
+ scrollPosition = (scrollPosition) + rowSize
+ recalculate(nil)
+ end
+
+ local scrollUp = function(mouseYPos)
+ if scrollUpButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local upCon
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ upCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollUp()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollUp()
+ if mouseYPos and mouseYPos > scrollDrag.AbsolutePosition.y then
+ break
+ end
+ if not scrollUpButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local scrollDown = function(mouseYPos)
+ if scrollDownButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local downCon
+ downCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ downCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollDown()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollDown()
+ if mouseYPos and mouseYPos < (scrollDrag.AbsolutePosition.y + scrollDrag.AbsoluteSize.x) then
+ break
+ end
+ if not scrollDownButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local y = 0
+ scrollDrag.MouseButton1Down:connect(function(x,y)
+ if scrollDrag.Active then
+ scrollStamp = tick()
+ local mouseOffset = y - scrollDrag.AbsolutePosition.y
+ local dragCon
+ local upCon
+ dragCon = mouseDrag.MouseMoved:connect(function(x,y)
+ local barAbsPos = scrollbar.AbsolutePosition.y
+ local barAbsSize = scrollbar.AbsoluteSize.y
+
+ local dragAbsSize = scrollDrag.AbsoluteSize.y
+ local barAbsOne = barAbsPos + barAbsSize - dragAbsSize
+ y = y - mouseOffset
+ y = y < barAbsPos and barAbsPos or y > barAbsOne and barAbsOne or y
+ y = y - barAbsPos
+
+ local guiObjects = 0
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ guiObjects = guiObjects + 1
+ end
+ end
+ end
+
+ local doublePercent = y/(barAbsSize-dragAbsSize)
+ local rowDiff = rowSize
+ local totalScrollCount = guiObjects - (howManyDisplayed - 1)
+ local newScrollPosition = math.floor((doublePercent * totalScrollCount) + 0.5) + rowDiff
+ if newScrollPosition < scrollPosition then
+ rowDiff = -rowDiff
+ end
+
+ if newScrollPosition < 1 then
+ newScrollPosition = 1
+ end
+
+ scrollPosition = newScrollPosition
+ recalculate(nil)
+ end)
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ dragCon:disconnect(); dragCon = nil
+ upCon:disconnect(); drag = nil
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ end
+ end)
+
+ local scrollMouseCount = 0
+
+ scrollUpButton.MouseButton1Down:connect(
+ function()
+ scrollUp()
+ end)
+ scrollUpButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+
+ scrollDownButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollDownButton.MouseButton1Down:connect(
+ function()
+ scrollDown()
+ end)
+
+ scrollbar.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollbar.MouseButton1Down:connect(
+ function(x,y)
+ if y > (scrollDrag.AbsoluteSize.y + scrollDrag.AbsolutePosition.y) then
+ scrollDown(y)
+ elseif y < (scrollDrag.AbsolutePosition.y) then
+ scrollUp(y)
+ end
+ end)
+
+
+ frame.ChildAdded:connect(function()
+ recalculate(nil)
+ end)
+
+ frame.ChildRemoved:connect(function()
+ recalculate(nil)
+ end)
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ --Wait a heartbeat for it to sync in
+ recalculate(nil)
+ end
+ end)
+ frame.AncestryChanged:connect(function() recalculate(nil) end)
+
+ return frame, scrollUpButton, scrollDownButton, recalculate, scrollbar
+end
+local function binaryGrow(min, max, fits)
+ if min > max then
+ return min
+ end
+ local biggestLegal = min
+
+ while min <= max do
+ local mid = min + math.floor((max - min) / 2)
+ if fits(mid) and (biggestLegal == nil or biggestLegal < mid) then
+ biggestLegal = mid
+
+ --Try growing
+ min = mid + 1
+ else
+ --Doesn't fit, shrink
+ max = mid - 1
+ end
+ end
+ return biggestLegal
+end
+
+
+local function binaryShrink(min, max, fits)
+ if min > max then
+ return min
+ end
+ local smallestLegal = max
+
+ while min <= max do
+ local mid = min + math.floor((max - min) / 2)
+ if fits(mid) and (smallestLegal == nil or smallestLegal > mid) then
+ smallestLegal = mid
+
+ --It fits, shrink
+ max = mid - 1
+ else
+ --Doesn't fit, grow
+ min = mid + 1
+ end
+ end
+ return smallestLegal
+end
+
+
+local function getGuiOwner(instance)
+ while instance ~= nil do
+ if instance:IsA("ScreenGui") or instance:IsA("BillboardGui") then
+ return instance
+ end
+ instance = instance.Parent
+ end
+ return nil
+end
+
+t.AutoTruncateTextObject = function(textLabel)
+ local text = textLabel.Text
+
+ local fullLabel = textLabel:Clone()
+ fullLabel.Name = "Full" .. textLabel.Name
+ fullLabel.BorderSizePixel = 0
+ fullLabel.BackgroundTransparency = 0
+ fullLabel.Text = text
+ fullLabel.TextXAlignment = Enum.TextXAlignment.Center
+ fullLabel.Position = UDim2.new(0,-3,0,0)
+ fullLabel.Size = UDim2.new(0,100,1,0)
+ fullLabel.Visible = false
+ fullLabel.Parent = textLabel
+
+ local shortText = nil
+ local mouseEnterConnection = nil
+ local mouseLeaveConnection= nil
+
+ local checkForResize = function()
+ if getGuiOwner(textLabel) == nil then
+ return
+ end
+ textLabel.Text = text
+ if textLabel.TextFits then
+ --Tear down the rollover if it is active
+ if mouseEnterConnection then
+ mouseEnterConnection:disconnect()
+ mouseEnterConnection = nil
+ end
+ if mouseLeaveConnection then
+ mouseLeaveConnection:disconnect()
+ mouseLeaveConnection = nil
+ end
+ else
+ local len = string.len(text)
+ textLabel.Text = text .. "~"
+
+ --Shrink the text
+ local textSize = binaryGrow(0, len,
+ function(pos)
+ if pos == 0 then
+ textLabel.Text = "~"
+ else
+ textLabel.Text = string.sub(text, 1, pos) .. "~"
+ end
+ return textLabel.TextFits
+ end)
+ shortText = string.sub(text, 1, textSize) .. "~"
+ textLabel.Text = shortText
+
+ --Make sure the fullLabel fits
+ if not fullLabel.TextFits then
+ --Already too small, grow it really bit to start
+ fullLabel.Size = UDim2.new(0, 10000, 1, 0)
+ end
+
+ --Okay, now try to binary shrink it back down
+ local fullLabelSize = binaryShrink(textLabel.AbsoluteSize.X,fullLabel.AbsoluteSize.X,
+ function(size)
+ fullLabel.Size = UDim2.new(0, size, 1, 0)
+ return fullLabel.TextFits
+ end)
+ fullLabel.Size = UDim2.new(0,fullLabelSize+6,1,0)
+
+ --Now setup the rollover effects, if they are currently off
+ if mouseEnterConnection == nil then
+ mouseEnterConnection = textLabel.MouseEnter:connect(
+ function()
+ fullLabel.ZIndex = textLabel.ZIndex + 1
+ fullLabel.Visible = true
+ --textLabel.Text = ""
+ end)
+ end
+ if mouseLeaveConnection == nil then
+ mouseLeaveConnection = textLabel.MouseLeave:connect(
+ function()
+ fullLabel.Visible = false
+ --textLabel.Text = shortText
+ end)
+ end
+ end
+ end
+ textLabel.AncestryChanged:connect(checkForResize)
+ textLabel.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ checkForResize()
+ end
+ end)
+
+ checkForResize()
+
+ local function changeText(newText)
+ text = newText
+ fullLabel.Text = text
+ checkForResize()
+ end
+
+ return textLabel, changeText
+end
+
+local function TransitionTutorialPages(fromPage, toPage, transitionFrame, currentPageValue)
+ if fromPage then
+ fromPage.Visible = false
+ if transitionFrame.Visible == false then
+ transitionFrame.Size = fromPage.Size
+ transitionFrame.Position = fromPage.Position
+ end
+ else
+ if transitionFrame.Visible == false then
+ transitionFrame.Size = UDim2.new(0.0,50,0.0,50)
+ transitionFrame.Position = UDim2.new(0.5,-25,0.5,-25)
+ end
+ end
+ transitionFrame.Visible = true
+ currentPageValue.Value = nil
+
+ local newsize, newPosition
+ if toPage then
+ --Make it visible so it resizes
+ toPage.Visible = true
+
+ newSize = toPage.Size
+ newPosition = toPage.Position
+
+ toPage.Visible = false
+ else
+ newSize = UDim2.new(0.0,50,0.0,50)
+ newPosition = UDim2.new(0.5,-25,0.5,-25)
+ end
+ transitionFrame:TweenSizeAndPosition(newSize, newPosition, Enum.EasingDirection.InOut, Enum.EasingStyle.Quad, 0.3, true,
+ function(state)
+ if state == Enum.TweenStatus.Completed then
+ transitionFrame.Visible = false
+ if toPage then
+ toPage.Visible = true
+ currentPageValue.Value = toPage
+ end
+ end
+ end)
+end
+
+t.CreateTutorial = function(name, tutorialKey, createButtons)
+ local frame = Instance.new("Frame")
+ frame.Name = "Tutorial-" .. name
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ frame.Position = UDim2.new(0.2, 0, 0.2, 0)
+
+ local transitionFrame = Instance.new("Frame")
+ transitionFrame.Name = "TransitionFrame"
+ transitionFrame.Style = Enum.FrameStyle.RobloxRound
+ transitionFrame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ transitionFrame.Position = UDim2.new(0.2, 0, 0.2, 0)
+ transitionFrame.Visible = false
+ transitionFrame.Parent = frame
+
+ local currentPageValue = Instance.new("ObjectValue")
+ currentPageValue.Name = "CurrentTutorialPage"
+ currentPageValue.Value = nil
+ currentPageValue.Parent = frame
+
+ local boolValue = Instance.new("BoolValue")
+ boolValue.Name = "Buttons"
+ boolValue.Value = createButtons
+ boolValue.Parent = frame
+
+ local pages = Instance.new("Frame")
+ pages.Name = "Pages"
+ pages.BackgroundTransparency = 1
+ pages.Size = UDim2.new(1,0,1,0)
+ pages.Parent = frame
+
+ local function getVisiblePageAndHideOthers()
+ local visiblePage = nil
+ local children = pages:GetChildren()
+ if children then
+ for i,child in ipairs(children) do
+ if child.Visible then
+ if visiblePage then
+ child.Visible = false
+ else
+ visiblePage = child
+ end
+ end
+ end
+ end
+ return visiblePage
+ end
+
+ local showTutorial = function(alwaysShow)
+ if alwaysShow or UserSettings().GameSettings:GetTutorialState(tutorialKey) == false then
+ print("Showing tutorial-",tutorialKey)
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+
+ local firstPage = pages:FindFirstChild("TutorialPage1")
+ if firstPage then
+ TransitionTutorialPages(currentTutorialPage, firstPage, transitionFrame, currentPageValue)
+ else
+ error("Could not find TutorialPage1")
+ end
+ end
+ end
+
+ local dismissTutorial = function()
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+
+ if currentTutorialPage then
+ TransitionTutorialPages(currentTutorialPage, nil, transitionFrame, currentPageValue)
+ end
+
+ UserSettings().GameSettings:SetTutorialState(tutorialKey, true)
+ end
+
+ local gotoPage = function(pageNum)
+ local page = pages:FindFirstChild("TutorialPage" .. pageNum)
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+ TransitionTutorialPages(currentTutorialPage, page, transitionFrame, currentPageValue)
+ end
+
+ return frame, showTutorial, dismissTutorial, gotoPage
+end
+
+local function CreateBasicTutorialPage(name, handleResize, skipTutorial, giveDoneButton)
+ local frame = Instance.new("Frame")
+ frame.Name = "TutorialPage"
+ frame.Style = Enum.FrameStyle.RobloxRound
+ frame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ frame.Position = UDim2.new(0.2, 0, 0.2, 0)
+ frame.Visible = false
+
+ local frameHeader = Instance.new("TextLabel")
+ frameHeader.Name = "Header"
+ frameHeader.Text = name
+ frameHeader.BackgroundTransparency = 1
+ frameHeader.FontSize = Enum.FontSize.Size24
+ frameHeader.Font = Enum.Font.ArialBold
+ frameHeader.TextColor3 = Color3.new(1,1,1)
+ frameHeader.TextXAlignment = Enum.TextXAlignment.Center
+ frameHeader.TextWrap = true
+ frameHeader.Size = UDim2.new(1,-55, 0, 22)
+ frameHeader.Position = UDim2.new(0,0,0,0)
+ frameHeader.Parent = frame
+
+ local skipButton = Instance.new("ImageButton")
+ skipButton.Name = "SkipButton"
+ skipButton.AutoButtonColor = false
+ skipButton.BackgroundTransparency = 1
+ skipButton.Image = "rbxasset://textures/ui/closeButton.png"
+ skipButton.MouseButton1Click:connect(function()
+ skipTutorial()
+ end)
+ skipButton.MouseEnter:connect(function()
+ skipButton.Image = "rbxasset://textures/ui/closeButton_dn.png"
+ end)
+ skipButton.MouseLeave:connect(function()
+ skipButton.Image = "rbxasset://textures/ui/closeButton.png"
+ end)
+ skipButton.Size = UDim2.new(0, 25, 0, 25)
+ skipButton.Position = UDim2.new(1, -25, 0, 0)
+ skipButton.Parent = frame
+
+
+ if giveDoneButton then
+ local doneButton = Instance.new("TextButton")
+ doneButton.Name = "DoneButton"
+ doneButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ doneButton.Text = "Done"
+ doneButton.TextColor3 = Color3.new(1,1,1)
+ doneButton.Font = Enum.Font.ArialBold
+ doneButton.FontSize = Enum.FontSize.Size18
+ doneButton.Size = UDim2.new(0,100,0,50)
+ doneButton.Position = UDim2.new(0.5,-50,1,-50)
+
+ if skipTutorial then
+ doneButton.MouseButton1Click:connect(function() skipTutorial() end)
+ end
+
+ doneButton.Parent = frame
+ end
+
+ local innerFrame = Instance.new("Frame")
+ innerFrame.Name = "ContentFrame"
+ innerFrame.BackgroundTransparency = 1
+ innerFrame.Position = UDim2.new(0,0,0,25)
+ innerFrame.Parent = frame
+
+ local nextButton = Instance.new("TextButton")
+ nextButton.Name = "NextButton"
+ nextButton.Text = "Next"
+ nextButton.TextColor3 = Color3.new(1,1,1)
+ nextButton.Font = Enum.Font.Arial
+ nextButton.FontSize = Enum.FontSize.Size18
+ nextButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ nextButton.Size = UDim2.new(0,80, 0, 32)
+ nextButton.Position = UDim2.new(0.5, 5, 1, -32)
+ nextButton.Active = false
+ nextButton.Visible = false
+ nextButton.Parent = frame
+
+ local prevButton = Instance.new("TextButton")
+ prevButton.Name = "PrevButton"
+ prevButton.Text = "Previous"
+ prevButton.TextColor3 = Color3.new(1,1,1)
+ prevButton.Font = Enum.Font.Arial
+ prevButton.FontSize = Enum.FontSize.Size18
+ prevButton.Style = Enum.ButtonStyle.RobloxButton
+ prevButton.Size = UDim2.new(0,80, 0, 32)
+ prevButton.Position = UDim2.new(0.5, -85, 1, -32)
+ prevButton.Active = false
+ prevButton.Visible = false
+ prevButton.Parent = frame
+
+ if giveDoneButton then
+ innerFrame.Size = UDim2.new(1,0,1,-75)
+ else
+ innerFrame.Size = UDim2.new(1,0,1,-22)
+ end
+
+ local parentConnection = nil
+
+ local function basicHandleResize()
+ if frame.Visible and frame.Parent then
+ local maxSize = math.min(frame.Parent.AbsoluteSize.X, frame.Parent.AbsoluteSize.Y)
+ handleResize(200,maxSize)
+ end
+ end
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "Parent" then
+ if parentConnection ~= nil then
+ parentConnection:disconnect()
+ parentConnection = nil
+ end
+ if frame.Parent and frame.Parent:IsA("GuiObject") then
+ parentConnection = frame.Parent.Changed:connect(
+ function(parentProp)
+ if parentProp == "AbsoluteSize" then
+ wait()
+ basicHandleResize()
+ end
+ end)
+ basicHandleResize()
+ end
+ end
+
+ if prop == "Visible" then
+ basicHandleResize()
+ end
+ end)
+
+ return frame, innerFrame
+end
+
+t.CreateTextTutorialPage = function(name, text, skipTutorialFunc)
+ local frame = nil
+ local contentFrame = nil
+
+ local textLabel = Instance.new("TextLabel")
+ textLabel.BackgroundTransparency = 1
+ textLabel.TextColor3 = Color3.new(1,1,1)
+ textLabel.Text = text
+ textLabel.TextWrap = true
+ textLabel.TextXAlignment = Enum.TextXAlignment.Left
+ textLabel.TextYAlignment = Enum.TextYAlignment.Center
+ textLabel.Font = Enum.Font.Arial
+ textLabel.FontSize = Enum.FontSize.Size14
+ textLabel.Size = UDim2.new(1,0,1,0)
+
+ local function handleResize(minSize, maxSize)
+ size = binaryShrink(minSize, maxSize,
+ function(size)
+ frame.Size = UDim2.new(0, size, 0, size)
+ return textLabel.TextFits
+ end)
+ frame.Size = UDim2.new(0, size, 0, size)
+ frame.Position = UDim2.new(0.5, -size/2, 0.5, -size/2)
+ end
+
+ frame, contentFrame = CreateBasicTutorialPage(name, handleResize, skipTutorialFunc)
+ textLabel.Parent = contentFrame
+
+ return frame
+end
+
+t.CreateImageTutorialPage = function(name, imageAsset, x, y, skipTutorialFunc, giveDoneButton)
+ local frame = nil
+ local contentFrame = nil
+
+ local imageLabel = Instance.new("ImageLabel")
+ imageLabel.BackgroundTransparency = 1
+ imageLabel.Image = imageAsset
+ imageLabel.Size = UDim2.new(0,x,0,y)
+ imageLabel.Position = UDim2.new(0.5,-x/2,0.5,-y/2)
+
+ local function handleResize(minSize, maxSize)
+ size = binaryShrink(minSize, maxSize,
+ function(size)
+ return size >= x and size >= y
+ end)
+ if size >= x and size >= y then
+ imageLabel.Size = UDim2.new(0,x, 0,y)
+ imageLabel.Position = UDim2.new(0.5,-x/2, 0.5, -y/2)
+ else
+ if x > y then
+ --X is limiter, so
+ imageLabel.Size = UDim2.new(1,0,y/x,0)
+ imageLabel.Position = UDim2.new(0,0, 0.5 - (y/x)/2, 0)
+ else
+ --Y is limiter
+ imageLabel.Size = UDim2.new(x/y,0,1, 0)
+ imageLabel.Position = UDim2.new(0.5-(x/y)/2, 0, 0, 0)
+ end
+ end
+ size = size + 50
+ frame.Size = UDim2.new(0, size, 0, size)
+ frame.Position = UDim2.new(0.5, -size/2, 0.5, -size/2)
+ end
+
+ frame, contentFrame = CreateBasicTutorialPage(name, handleResize, skipTutorialFunc, giveDoneButton)
+ imageLabel.Parent = contentFrame
+
+ return frame
+end
+
+t.AddTutorialPage = function(tutorial, tutorialPage)
+ local transitionFrame = tutorial.TransitionFrame
+ local currentPageValue = tutorial.CurrentTutorialPage
+
+ if not tutorial.Buttons.Value then
+ tutorialPage.NextButton.Parent = nil
+ tutorialPage.PrevButton.Parent = nil
+ end
+
+ local children = tutorial.Pages:GetChildren()
+ if children and #children > 0 then
+ tutorialPage.Name = "TutorialPage" .. (#children+1)
+ local previousPage = children[#children]
+ if not previousPage:IsA("GuiObject") then
+ error("All elements under Pages must be GuiObjects")
+ end
+
+ if tutorial.Buttons.Value then
+ if previousPage.NextButton.Active then
+ error("NextButton already Active on previousPage, please only add pages with RbxGui.AddTutorialPage function")
+ end
+ previousPage.NextButton.MouseButton1Click:connect(
+ function()
+ TransitionTutorialPages(previousPage, tutorialPage, transitionFrame, currentPageValue)
+ end)
+ previousPage.NextButton.Active = true
+ previousPage.NextButton.Visible = true
+
+ if tutorialPage.PrevButton.Active then
+ error("PrevButton already Active on tutorialPage, please only add pages with RbxGui.AddTutorialPage function")
+ end
+ tutorialPage.PrevButton.MouseButton1Click:connect(
+ function()
+ TransitionTutorialPages(tutorialPage, previousPage, transitionFrame, currentPageValue)
+ end)
+ tutorialPage.PrevButton.Active = true
+ tutorialPage.PrevButton.Visible = true
+ end
+
+ tutorialPage.Parent = tutorial.Pages
+ else
+ --First child
+ tutorialPage.Name = "TutorialPage1"
+ tutorialPage.Parent = tutorial.Pages
+ end
+end
+
+t.CreateSetPanel = function(userIdsForSets, objectSelected, dialogClosed, size, position, showAdminCategories, useAssetVersionId)
+
+ if not userIdsForSets then
+ error("CreateSetPanel: userIdsForSets (first arg) is nil, should be a table of number ids")
+ end
+ if type(userIdsForSets) ~= "table" and type(userIdsForSets) ~= "userdata" then
+ error("CreateSetPanel: userIdsForSets (first arg) is of type " ..type(userIdsForSets) .. ", should be of type table or userdata")
+ end
+ if not objectSelected then
+ error("CreateSetPanel: objectSelected (second arg) is nil, should be a callback function!")
+ end
+ if type(objectSelected) ~= "function" then
+ error("CreateSetPanel: objectSelected (second arg) is of type " .. type(objectSelected) .. ", should be of type function!")
+ end
+ if dialogClosed and type(dialogClosed) ~= "function" then
+ error("CreateSetPanel: dialogClosed (third arg) is of type " .. type(dialogClosed) .. ", should be of type function!")
+ end
+
+ if showAdminCategories == nil then -- by default, don't show beta sets
+ showAdminCategories = false
+ end
+
+ local arrayPosition = 1
+ local insertButtons = {}
+ local insertButtonCons = {}
+ local contents = nil
+ local setGui = nil
+
+ -- used for water selections
+ local waterForceDirection = "NegX"
+ local waterForce = "None"
+ local waterGui, waterTypeChangedEvent = nil
+
+ local Data = {}
+ Data.CurrentCategory = nil
+ Data.Category = {}
+ local SetCache = {}
+
+ local userCategoryButtons = nil
+
+ local buttonWidth = 64
+ local buttonHeight = buttonWidth
+
+ local SmallThumbnailUrl = nil
+ local LargeThumbnailUrl = nil
+ local BaseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+
+ if useAssetVersionId then
+ LargeThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=420&ht=420&assetversionid="
+ SmallThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=75&ht=75&assetversionid="
+ else
+ LargeThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=420&ht=420&aid="
+ SmallThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=75&ht=75&aid="
+ end
+
+ local function drillDownSetZIndex(parent, index)
+ local children = parent:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("GuiObject") then
+ children[i].ZIndex = index
+ end
+ drillDownSetZIndex(children[i], index)
+ end
+ end
+
+ -- for terrain stamping
+ local currTerrainDropDownFrame = nil
+ local terrainShapes = {"Block","Vertical Ramp","Corner Wedge","Inverse Corner Wedge","Horizontal Ramp","Auto-Wedge"}
+ local terrainShapeMap = {}
+ for i = 1, #terrainShapes do
+ terrainShapeMap[terrainShapes[i]] = i - 1
+ end
+ terrainShapeMap[terrainShapes[#terrainShapes]] = 6
+
+ local function createWaterGui()
+ local waterForceDirections = {"NegX","X","NegY","Y","NegZ","Z"}
+ local waterForces = {"None", "Small", "Medium", "Strong", "Max"}
+
+ local waterFrame = Instance.new("Frame")
+ waterFrame.Name = "WaterFrame"
+ waterFrame.Style = Enum.FrameStyle.RobloxSquare
+ waterFrame.Size = UDim2.new(0,150,0,110)
+ waterFrame.Visible = false
+
+ local waterForceLabel = Instance.new("TextLabel")
+ waterForceLabel.Name = "WaterForceLabel"
+ waterForceLabel.BackgroundTransparency = 1
+ waterForceLabel.Size = UDim2.new(1,0,0,12)
+ waterForceLabel.Font = Enum.Font.ArialBold
+ waterForceLabel.FontSize = Enum.FontSize.Size12
+ waterForceLabel.TextColor3 = Color3.new(1,1,1)
+ waterForceLabel.TextXAlignment = Enum.TextXAlignment.Left
+ waterForceLabel.Text = "Water Force"
+ waterForceLabel.Parent = waterFrame
+
+ local waterForceDirLabel = waterForceLabel:Clone()
+ waterForceDirLabel.Name = "WaterForceDirectionLabel"
+ waterForceDirLabel.Text = "Water Force Direction"
+ waterForceDirLabel.Position = UDim2.new(0,0,0,50)
+ waterForceDirLabel.Parent = waterFrame
+
+ local waterTypeChangedEvent = Instance.new("BindableEvent",waterFrame)
+ waterTypeChangedEvent.Name = "WaterTypeChangedEvent"
+
+ local waterForceDirectionSelectedFunc = function(newForceDirection)
+ waterForceDirection = newForceDirection
+ waterTypeChangedEvent:Fire({waterForce, waterForceDirection})
+ end
+ local waterForceSelectedFunc = function(newForce)
+ waterForce = newForce
+ waterTypeChangedEvent:Fire({waterForce, waterForceDirection})
+ end
+
+ local waterForceDirectionDropDown, forceWaterDirectionSelection = t.CreateDropDownMenu(waterForceDirections, waterForceDirectionSelectedFunc)
+ waterForceDirectionDropDown.Size = UDim2.new(1,0,0,25)
+ waterForceDirectionDropDown.Position = UDim2.new(0,0,1,3)
+ forceWaterDirectionSelection("NegX")
+ waterForceDirectionDropDown.Parent = waterForceDirLabel
+
+ local waterForceDropDown, forceWaterForceSelection = t.CreateDropDownMenu(waterForces, waterForceSelectedFunc)
+ forceWaterForceSelection("None")
+ waterForceDropDown.Size = UDim2.new(1,0,0,25)
+ waterForceDropDown.Position = UDim2.new(0,0,1,3)
+ waterForceDropDown.Parent = waterForceLabel
+
+ return waterFrame, waterTypeChangedEvent
+ end
+
+ -- Helper Function that contructs gui elements
+ local function createSetGui()
+
+ local setGui = Instance.new("ScreenGui")
+ setGui.Name = "SetGui"
+
+ local setPanel = Instance.new("Frame")
+ setPanel.Name = "SetPanel"
+ setPanel.Active = true
+ setPanel.BackgroundTransparency = 1
+ if position then
+ setPanel.Position = position
+ else
+ setPanel.Position = UDim2.new(0.2, 29, 0.1, 24)
+ end
+ if size then
+ setPanel.Size = size
+ else
+ setPanel.Size = UDim2.new(0.6, -58, 0.64, 0)
+ end
+ setPanel.Style = Enum.FrameStyle.RobloxRound
+ setPanel.ZIndex = 6
+ setPanel.Parent = setGui
+
+ -- Children of SetPanel
+ local itemPreview = Instance.new("Frame")
+ itemPreview.Name = "ItemPreview"
+ itemPreview.BackgroundTransparency = 1
+ itemPreview.Position = UDim2.new(0.8,5,0.085,0)
+ itemPreview.Size = UDim2.new(0.21,0,0.9,0)
+ itemPreview.ZIndex = 6
+ itemPreview.Parent = setPanel
+
+ -- Children of ItemPreview
+ local textPanel = Instance.new("Frame")
+ textPanel.Name = "TextPanel"
+ textPanel.BackgroundTransparency = 1
+ textPanel.Position = UDim2.new(0,0,0.45,0)
+ textPanel.Size = UDim2.new(1,0,0.55,0)
+ textPanel.ZIndex = 6
+ textPanel.Parent = itemPreview
+
+ -- Children of TextPanel
+ local rolloverText = Instance.new("TextLabel")
+ rolloverText.Name = "RolloverText"
+ rolloverText.BackgroundTransparency = 1
+ rolloverText.Size = UDim2.new(1,0,0,48)
+ rolloverText.ZIndex = 6
+ rolloverText.Font = Enum.Font.ArialBold
+ rolloverText.FontSize = Enum.FontSize.Size24
+ rolloverText.Text = ""
+ rolloverText.TextColor3 = Color3.new(1,1,1)
+ rolloverText.TextWrap = true
+ rolloverText.TextXAlignment = Enum.TextXAlignment.Left
+ rolloverText.TextYAlignment = Enum.TextYAlignment.Top
+ rolloverText.Parent = textPanel
+
+ local largePreview = Instance.new("ImageLabel")
+ largePreview.Name = "LargePreview"
+ largePreview.BackgroundTransparency = 1
+ largePreview.Image = ""
+ largePreview.Size = UDim2.new(1,0,0,170)
+ largePreview.ZIndex = 6
+ largePreview.Parent = itemPreview
+
+ local sets = Instance.new("Frame")
+ sets.Name = "Sets"
+ sets.BackgroundTransparency = 1
+ sets.Position = UDim2.new(0,0,0,5)
+ sets.Size = UDim2.new(0.23,0,1,-5)
+ sets.ZIndex = 6
+ sets.Parent = setPanel
+
+ -- Children of Sets
+ local line = Instance.new("Frame")
+ line.Name = "Line"
+ line.BackgroundColor3 = Color3.new(1,1,1)
+ line.BackgroundTransparency = 0.7
+ line.BorderSizePixel = 0
+ line.Position = UDim2.new(1,-3,0.06,0)
+ line.Size = UDim2.new(0,3,0.9,0)
+ line.ZIndex = 6
+ line.Parent = sets
+
+ local setsLists, controlFrame = t.CreateTrueScrollingFrame()
+ setsLists.Size = UDim2.new(1,-6,0.94,0)
+ setsLists.Position = UDim2.new(0,0,0.06,0)
+ setsLists.BackgroundTransparency = 1
+ setsLists.Name = "SetsLists"
+ setsLists.ZIndex = 6
+ setsLists.Parent = sets
+ drillDownSetZIndex(controlFrame, 7)
+
+ local setsHeader = Instance.new("TextLabel")
+ setsHeader.Name = "SetsHeader"
+ setsHeader.BackgroundTransparency = 1
+ setsHeader.Size = UDim2.new(0,47,0,24)
+ setsHeader.ZIndex = 6
+ setsHeader.Font = Enum.Font.ArialBold
+ setsHeader.FontSize = Enum.FontSize.Size24
+ setsHeader.Text = "Sets"
+ setsHeader.TextColor3 = Color3.new(1,1,1)
+ setsHeader.TextXAlignment = Enum.TextXAlignment.Left
+ setsHeader.TextYAlignment = Enum.TextYAlignment.Top
+ setsHeader.Parent = sets
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelButton"
+ cancelButton.Position = UDim2.new(1,-32,0,-2)
+ cancelButton.Size = UDim2.new(0,34,0,34)
+ cancelButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ cancelButton.ZIndex = 6
+ cancelButton.Text = ""
+ cancelButton.Modal = true
+ cancelButton.Parent = setPanel
+
+ -- Children of Cancel Button
+ local cancelImage = Instance.new("ImageLabel")
+ cancelImage.Name = "CancelImage"
+ cancelImage.BackgroundTransparency = 1
+ cancelImage.Image = "http://www.roblox.com/asset/?id=54135717"
+ cancelImage.Position = UDim2.new(0,-2,0,-2)
+ cancelImage.Size = UDim2.new(0,16,0,16)
+ cancelImage.ZIndex = 6
+ cancelImage.Parent = cancelButton
+
+ return setGui
+ end
+
+ local function createSetButton(text)
+ local setButton = Instance.new("TextButton")
+
+ if text then setButton.Text = text
+ else setButton.Text = "" end
+
+ setButton.AutoButtonColor = false
+ setButton.BackgroundTransparency = 1
+ setButton.BackgroundColor3 = Color3.new(1,1,1)
+ setButton.BorderSizePixel = 0
+ setButton.Size = UDim2.new(1,-5,0,18)
+ setButton.ZIndex = 6
+ setButton.Visible = false
+ setButton.Font = Enum.Font.Arial
+ setButton.FontSize = Enum.FontSize.Size18
+ setButton.TextColor3 = Color3.new(1,1,1)
+ setButton.TextXAlignment = Enum.TextXAlignment.Left
+
+ return setButton
+ end
+
+ local function buildSetButton(name, setId, setImageId, i, count)
+ local button = createSetButton(name)
+ button.Text = name
+ button.Name = "SetButton"
+ button.Visible = true
+
+ local setValue = Instance.new("IntValue")
+ setValue.Name = "SetId"
+ setValue.Value = setId
+ setValue.Parent = button
+
+ local setName = Instance.new("StringValue")
+ setName.Name = "SetName"
+ setName.Value = name
+ setName.Parent = button
+
+ return button
+ end
+
+ local function processCategory(sets)
+ local setButtons = {}
+ local numSkipped = 0
+ for i = 1, #sets do
+ if not showAdminCategories and sets[i].Name == "Beta" then
+ numSkipped = numSkipped + 1
+ else
+ setButtons[i - numSkipped] = buildSetButton(sets[i].Name, sets[i].CategoryId, sets[i].ImageAssetId, i - numSkipped, #sets)
+ end
+ end
+ return setButtons
+ end
+
+ local function handleResize()
+ wait() -- neccessary to insure heartbeat happened
+
+ local itemPreview = setGui.SetPanel.ItemPreview
+
+ itemPreview.LargePreview.Size = UDim2.new(1,0,0,itemPreview.AbsoluteSize.X)
+ itemPreview.LargePreview.Position = UDim2.new(0.5,-itemPreview.LargePreview.AbsoluteSize.X/2,0,0)
+ itemPreview.TextPanel.Position = UDim2.new(0,0,0,itemPreview.LargePreview.AbsoluteSize.Y)
+ itemPreview.TextPanel.Size = UDim2.new(1,0,0,itemPreview.AbsoluteSize.Y - itemPreview.LargePreview.AbsoluteSize.Y)
+ end
+
+ local function makeInsertAssetButton()
+ local insertAssetButtonExample = Instance.new("Frame")
+ insertAssetButtonExample.Name = "InsertAssetButtonExample"
+ insertAssetButtonExample.Position = UDim2.new(0,128,0,64)
+ insertAssetButtonExample.Size = UDim2.new(0,64,0,64)
+ insertAssetButtonExample.BackgroundTransparency = 1
+ insertAssetButtonExample.ZIndex = 6
+ insertAssetButtonExample.Visible = false
+
+ local assetId = Instance.new("IntValue")
+ assetId.Name = "AssetId"
+ assetId.Value = 0
+ assetId.Parent = insertAssetButtonExample
+
+ local assetName = Instance.new("StringValue")
+ assetName.Name = "AssetName"
+ assetName.Value = ""
+ assetName.Parent = insertAssetButtonExample
+
+ local button = Instance.new("TextButton")
+ button.Name = "Button"
+ button.Text = ""
+ button.Style = Enum.ButtonStyle.RobloxButton
+ button.Position = UDim2.new(0.025,0,0.025,0)
+ button.Size = UDim2.new(0.95,0,0.95,0)
+ button.ZIndex = 6
+ button.Parent = insertAssetButtonExample
+
+ local buttonImage = Instance.new("ImageLabel")
+ buttonImage.Name = "ButtonImage"
+ buttonImage.Image = ""
+ buttonImage.Position = UDim2.new(0,-7,0,-7)
+ buttonImage.Size = UDim2.new(1,14,1,14)
+ buttonImage.BackgroundTransparency = 1
+ buttonImage.ZIndex = 7
+ buttonImage.Parent = button
+
+ local configIcon = buttonImage:clone()
+ configIcon.Name = "ConfigIcon"
+ configIcon.Visible = false
+ configIcon.Position = UDim2.new(1,-23,1,-24)
+ configIcon.Size = UDim2.new(0,16,0,16)
+ configIcon.Image = ""
+ configIcon.ZIndex = 6
+ configIcon.Parent = insertAssetButtonExample
+
+ return insertAssetButtonExample
+ end
+
+ local function showLargePreview(insertButton)
+ if insertButton:FindFirstChild("AssetId") then
+ delay(0,function()
+ game:GetService("ContentProvider"):Preload(LargeThumbnailUrl .. tostring(insertButton.AssetId.Value))
+ setGui.SetPanel.ItemPreview.LargePreview.Image = LargeThumbnailUrl .. tostring(insertButton.AssetId.Value)
+ end)
+ end
+ if insertButton:FindFirstChild("AssetName") then
+ setGui.SetPanel.ItemPreview.TextPanel.RolloverText.Text = insertButton.AssetName.Value
+ end
+ end
+
+ local function selectTerrainShape(shape)
+ if currTerrainDropDownFrame then
+ objectSelected(tostring(currTerrainDropDownFrame.AssetName.Value), tonumber(currTerrainDropDownFrame.AssetId.Value), shape)
+ end
+ end
+
+ local function createTerrainTypeButton(name, parent)
+ local dropDownTextButton = Instance.new("TextButton")
+ dropDownTextButton.Name = name .. "Button"
+ dropDownTextButton.Font = Enum.Font.ArialBold
+ dropDownTextButton.FontSize = Enum.FontSize.Size14
+ dropDownTextButton.BorderSizePixel = 0
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ dropDownTextButton.Text = name
+ dropDownTextButton.TextXAlignment = Enum.TextXAlignment.Left
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.ZIndex = parent.ZIndex + 1
+ dropDownTextButton.Size = UDim2.new(0,parent.Size.X.Offset - 2,0,16)
+ dropDownTextButton.Position = UDim2.new(0,1,0,0)
+
+ dropDownTextButton.MouseEnter:connect(function()
+ dropDownTextButton.BackgroundTransparency = 0
+ dropDownTextButton.TextColor3 = Color3.new(0,0,0)
+ end)
+
+ dropDownTextButton.MouseLeave:connect(function()
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ end)
+
+ dropDownTextButton.MouseButton1Click:connect(function()
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ if dropDownTextButton.Parent and dropDownTextButton.Parent:IsA("GuiObject") then
+ dropDownTextButton.Parent.Visible = false
+ end
+ selectTerrainShape(terrainShapeMap[dropDownTextButton.Text])
+ end)
+
+ return dropDownTextButton
+ end
+
+ local function createTerrainDropDownMenu(zIndex)
+ local dropDown = Instance.new("Frame")
+ dropDown.Name = "TerrainDropDown"
+ dropDown.BackgroundColor3 = Color3.new(0,0,0)
+ dropDown.BorderColor3 = Color3.new(1,0,0)
+ dropDown.Size = UDim2.new(0,200,0,0)
+ dropDown.Visible = false
+ dropDown.ZIndex = zIndex
+ dropDown.Parent = setGui
+
+ for i = 1, #terrainShapes do
+ local shapeButton = createTerrainTypeButton(terrainShapes[i],dropDown)
+ shapeButton.Position = UDim2.new(0,1,0,(i - 1) * (shapeButton.Size.Y.Offset))
+ shapeButton.Parent = dropDown
+ dropDown.Size = UDim2.new(0,200,0,dropDown.Size.Y.Offset + (shapeButton.Size.Y.Offset))
+ end
+
+ dropDown.MouseLeave:connect(function()
+ dropDown.Visible = false
+ end)
+ end
+
+
+ local function createDropDownMenuButton(parent)
+ local dropDownButton = Instance.new("ImageButton")
+ dropDownButton.Name = "DropDownButton"
+ dropDownButton.Image = "http://www.roblox.com/asset/?id=67581509"
+ dropDownButton.BackgroundTransparency = 1
+ dropDownButton.Size = UDim2.new(0,16,0,16)
+ dropDownButton.Position = UDim2.new(1,-24,0,6)
+ dropDownButton.ZIndex = parent.ZIndex + 2
+ dropDownButton.Parent = parent
+
+ if not setGui:FindFirstChild("TerrainDropDown") then
+ createTerrainDropDownMenu(8)
+ end
+
+ dropDownButton.MouseButton1Click:connect(function()
+ setGui.TerrainDropDown.Visible = true
+ setGui.TerrainDropDown.Position = UDim2.new(0,parent.AbsolutePosition.X,0,parent.AbsolutePosition.Y)
+ currTerrainDropDownFrame = parent
+ end)
+ end
+
+ local function buildInsertButton()
+ local insertButton = makeInsertAssetButton()
+ insertButton.Name = "InsertAssetButton"
+ insertButton.Visible = true
+
+ if Data.Category[Data.CurrentCategory].SetName == "High Scalability" then
+ createDropDownMenuButton(insertButton)
+ end
+
+ local lastEnter = nil
+ local mouseEnterCon = insertButton.MouseEnter:connect(function()
+ lastEnter = insertButton
+ delay(0.1,function()
+ if lastEnter == insertButton then
+ showLargePreview(insertButton)
+ end
+ end)
+ end)
+ return insertButton, mouseEnterCon
+ end
+
+ local function realignButtonGrid(columns)
+ local x = 0
+ local y = 0
+ for i = 1, #insertButtons do
+ insertButtons[i].Position = UDim2.new(0, buttonWidth * x, 0, buttonHeight * y)
+ x = x + 1
+ if x >= columns then
+ x = 0
+ y = y + 1
+ end
+ end
+ end
+
+ local function setInsertButtonImageBehavior(insertFrame, visible, name, assetId)
+ if visible then
+ insertFrame.AssetName.Value = name
+ insertFrame.AssetId.Value = assetId
+ local newImageUrl = SmallThumbnailUrl .. assetId
+ if newImageUrl ~= insertFrame.Button.ButtonImage.Image then
+ delay(0,function()
+ game:GetService("ContentProvider"):Preload(SmallThumbnailUrl .. assetId)
+ if insertFrame:findFirstChild("Button") then
+ insertFrame.Button.ButtonImage.Image = SmallThumbnailUrl .. assetId
+ end
+ end)
+ end
+ table.insert(insertButtonCons,
+ insertFrame.Button.MouseButton1Click:connect(function()
+ -- special case for water, show water selection gui
+ local isWaterSelected = (name == "Water") and (Data.Category[Data.CurrentCategory].SetName == "High Scalability")
+ waterGui.Visible = isWaterSelected
+ if isWaterSelected then
+ objectSelected(name, tonumber(assetId), nil)
+ else
+ objectSelected(name, tonumber(assetId))
+ end
+ end)
+ )
+ insertFrame.Visible = true
+ else
+ insertFrame.Visible = false
+ end
+ end
+
+ local function loadSectionOfItems(setGui, rows, columns)
+ local pageSize = rows * columns
+
+ if arrayPosition > #contents then return end
+
+ local origArrayPos = arrayPosition
+
+ local yCopy = 0
+ for i = 1, pageSize + 1 do
+ if arrayPosition >= #contents + 1 then
+ break
+ end
+
+ local buttonCon
+ insertButtons[arrayPosition], buttonCon = buildInsertButton()
+ table.insert(insertButtonCons,buttonCon)
+ insertButtons[arrayPosition].Parent = setGui.SetPanel.ItemsFrame
+ arrayPosition = arrayPosition + 1
+ end
+ realignButtonGrid(columns)
+
+ local indexCopy = origArrayPos
+ for index = origArrayPos, arrayPosition do
+ if insertButtons[index] then
+ if contents[index] then
+
+ -- we don't want water to have a drop down button
+ if contents[index].Name == "Water" then
+ if Data.Category[Data.CurrentCategory].SetName == "High Scalability" then
+ insertButtons[index]:FindFirstChild("DropDownButton",true):Destroy()
+ end
+ end
+
+ local assetId
+ if useAssetVersionId then
+ assetId = contents[index].AssetVersionId
+ else
+ assetId = contents[index].AssetId
+ end
+ setInsertButtonImageBehavior(insertButtons[index], true, contents[index].Name, assetId)
+ else
+ break
+ end
+ else
+ break
+ end
+ indexCopy = index
+ end
+ end
+
+ local function setSetIndex()
+ Data.Category[Data.CurrentCategory].Index = 0
+
+ rows = 7
+ columns = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.X/buttonWidth)
+
+ contents = Data.Category[Data.CurrentCategory].Contents
+ if contents then
+ -- remove our buttons and their connections
+ for i = 1, #insertButtons do
+ insertButtons[i]:remove()
+ end
+ for i = 1, #insertButtonCons do
+ if insertButtonCons[i] then insertButtonCons[i]:disconnect() end
+ end
+ insertButtonCons = {}
+ insertButtons = {}
+
+ arrayPosition = 1
+ loadSectionOfItems(setGui, rows, columns)
+ end
+ end
+
+ local function selectSet(button, setName, setId, setIndex)
+ if button and Data.Category[Data.CurrentCategory] ~= nil then
+ if button ~= Data.Category[Data.CurrentCategory].Button then
+ Data.Category[Data.CurrentCategory].Button = button
+
+ if SetCache[setId] == nil then
+ SetCache[setId] = game:GetService("InsertService"):GetCollection(setId)
+ end
+ Data.Category[Data.CurrentCategory].Contents = SetCache[setId]
+
+ Data.Category[Data.CurrentCategory].SetName = setName
+ Data.Category[Data.CurrentCategory].SetId = setId
+ end
+ setSetIndex()
+ end
+ end
+
+ local function selectCategoryPage(buttons, page)
+ if buttons ~= Data.CurrentCategory then
+ if Data.CurrentCategory then
+ for key, button in pairs(Data.CurrentCategory) do
+ button.Visible = false
+ end
+ end
+
+ Data.CurrentCategory = buttons
+ if Data.Category[Data.CurrentCategory] == nil then
+ Data.Category[Data.CurrentCategory] = {}
+ if #buttons > 0 then
+ selectSet(buttons[1], buttons[1].SetName.Value, buttons[1].SetId.Value, 0)
+ end
+ else
+ Data.Category[Data.CurrentCategory].Button = nil
+ selectSet(Data.Category[Data.CurrentCategory].ButtonFrame, Data.Category[Data.CurrentCategory].SetName, Data.Category[Data.CurrentCategory].SetId, Data.Category[Data.CurrentCategory].Index)
+ end
+ end
+ end
+
+ local function selectCategory(category)
+ selectCategoryPage(category, 0)
+ end
+
+ local function resetAllSetButtonSelection()
+ local setButtons = setGui.SetPanel.Sets.SetsLists:GetChildren()
+ for i = 1, #setButtons do
+ if setButtons[i]:IsA("TextButton") then
+ setButtons[i].Selected = false
+ setButtons[i].BackgroundTransparency = 1
+ setButtons[i].TextColor3 = Color3.new(1,1,1)
+ setButtons[i].BackgroundColor3 = Color3.new(1,1,1)
+ end
+ end
+ end
+
+ local function populateSetsFrame()
+ local currRow = 0
+ for i = 1, #userCategoryButtons do
+ local button = userCategoryButtons[i]
+ button.Visible = true
+ button.Position = UDim2.new(0,5,0,currRow * button.Size.Y.Offset)
+ button.Parent = setGui.SetPanel.Sets.SetsLists
+
+ if i == 1 then -- we will have this selected by default, so show it
+ button.Selected = true
+ button.BackgroundColor3 = Color3.new(0,204/255,0)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundTransparency = 0
+ end
+
+ button.MouseEnter:connect(function()
+ if not button.Selected then
+ button.BackgroundTransparency = 0
+ button.TextColor3 = Color3.new(0,0,0)
+ end
+ end)
+ button.MouseLeave:connect(function()
+ if not button.Selected then
+ button.BackgroundTransparency = 1
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ end)
+ button.MouseButton1Click:connect(function()
+ resetAllSetButtonSelection()
+ button.Selected = not button.Selected
+ button.BackgroundColor3 = Color3.new(0,204/255,0)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundTransparency = 0
+ selectSet(button, button.Text, userCategoryButtons[i].SetId.Value, 0)
+ end)
+
+ currRow = currRow + 1
+ end
+
+ local buttons = setGui.SetPanel.Sets.SetsLists:GetChildren()
+
+ -- set first category as loaded for default
+ if buttons then
+ for i = 1, #buttons do
+ if buttons[i]:IsA("TextButton") then
+ selectSet(buttons[i], buttons[i].Text, userCategoryButtons[i].SetId.Value, 0)
+ selectCategory(userCategoryButtons)
+ break
+ end
+ end
+ end
+ end
+
+ setGui = createSetGui()
+ waterGui, waterTypeChangedEvent = createWaterGui()
+ waterGui.Position = UDim2.new(0,55,0,0)
+ waterGui.Parent = setGui
+ setGui.Changed:connect(function(prop) -- this resizes the preview image to always be the right size
+ if prop == "AbsoluteSize" then
+ handleResize()
+ setSetIndex()
+ end
+ end)
+
+ local scrollFrame, controlFrame = t.CreateTrueScrollingFrame()
+ scrollFrame.Size = UDim2.new(0.54,0,0.85,0)
+ scrollFrame.Position = UDim2.new(0.24,0,0.085,0)
+ scrollFrame.Name = "ItemsFrame"
+ scrollFrame.ZIndex = 6
+ scrollFrame.Parent = setGui.SetPanel
+ scrollFrame.BackgroundTransparency = 1
+
+ drillDownSetZIndex(controlFrame,7)
+
+ controlFrame.Parent = setGui.SetPanel
+ controlFrame.Position = UDim2.new(0.76, 5, 0, 0)
+
+ local debounce = false
+ controlFrame.ScrollBottom.Changed:connect(function(prop)
+ if controlFrame.ScrollBottom.Value == true then
+ if debounce then return end
+ debounce = true
+ loadSectionOfItems(setGui, rows, columns)
+ debounce = false
+ end
+ end)
+
+ local userData = {}
+ for id = 1, #userIdsForSets do
+ local newUserData = game:GetService("InsertService"):GetUserSets(userIdsForSets[id])
+ if newUserData and #newUserData > 2 then
+ -- start at #3 to skip over My Decals and My Models for each account
+ for category = 3, #newUserData do
+ if newUserData[category].Name == "High Scalability" then -- we want high scalability parts to show first
+ table.insert(userData,1,newUserData[category])
+ else
+ table.insert(userData, newUserData[category])
+ end
+ end
+ end
+
+ end
+ if userData then
+ userCategoryButtons = processCategory(userData)
+ end
+
+ rows = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.Y/buttonHeight)
+ columns = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.X/buttonWidth)
+
+ populateSetsFrame()
+
+ insertPanelCloseCon = setGui.SetPanel.CancelButton.MouseButton1Click:connect(function()
+ setGui.SetPanel.Visible = false
+ if dialogClosed then dialogClosed() end
+ end)
+
+ local setVisibilityFunction = function(visible)
+ if visible then
+ setGui.SetPanel.Visible = true
+ else
+ setGui.SetPanel.Visible = false
+ end
+ end
+
+ local getVisibilityFunction = function()
+ if setGui then
+ if setGui:FindFirstChild("SetPanel") then
+ return setGui.SetPanel.Visible
+ end
+ end
+
+ return false
+ end
+
+ return setGui, setVisibilityFunction, getVisibilityFunction, waterTypeChangedEvent
+end
+
+t.CreateTerrainMaterialSelector = function(size,position)
+ local terrainMaterialSelectionChanged = Instance.new("BindableEvent")
+ terrainMaterialSelectionChanged.Name = "TerrainMaterialSelectionChanged"
+
+ local selectedButton = nil
+
+ local frame = Instance.new("Frame")
+ frame.Name = "TerrainMaterialSelector"
+ if size then
+ frame.Size = size
+ else
+ frame.Size = UDim2.new(0, 245, 0, 230)
+ end
+ if position then
+ frame.Position = position
+ end
+ frame.BorderSizePixel = 0
+ frame.BackgroundColor3 = Color3.new(0,0,0)
+ frame.Active = true
+
+ terrainMaterialSelectionChanged.Parent = frame
+
+ local waterEnabled = true -- todo: turn this on when water is ready
+
+ local materialToImageMap = {}
+ local materialNames = {"Grass", "Sand", "Brick", "Granite", "Asphalt", "Iron", "Aluminum", "Gold", "Plank", "Log", "Gravel", "Cinder Block", "Stone Wall", "Concrete", "Plastic (red)", "Plastic (blue)"}
+ if waterEnabled then
+ table.insert(materialNames,"Water")
+ end
+ local currentMaterial = 1
+
+ function getEnumFromName(choice)
+ if choice == "Grass" then return 1 end
+ if choice == "Sand" then return 2 end
+ if choice == "Erase" then return 0 end
+ if choice == "Brick" then return 3 end
+ if choice == "Granite" then return 4 end
+ if choice == "Asphalt" then return 5 end
+ if choice == "Iron" then return 6 end
+ if choice == "Aluminum" then return 7 end
+ if choice == "Gold" then return 8 end
+ if choice == "Plank" then return 9 end
+ if choice == "Log" then return 10 end
+ if choice == "Gravel" then return 11 end
+ if choice == "Cinder Block" then return 12 end
+ if choice == "Stone Wall" then return 13 end
+ if choice == "Concrete" then return 14 end
+ if choice == "Plastic (red)" then return 15 end
+ if choice == "Plastic (blue)" then return 16 end
+ if choice == "Water" then return 17 end
+ end
+
+ function getNameFromEnum(choice)
+ if choice == Enum.CellMaterial.Grass or choice == 1 then return "Grass"end
+ if choice == Enum.CellMaterial.Sand or choice == 2 then return "Sand" end
+ if choice == Enum.CellMaterial.Empty or choice == 0 then return "Erase" end
+ if choice == Enum.CellMaterial.Brick or choice == 3 then return "Brick" end
+ if choice == Enum.CellMaterial.Granite or choice == 4 then return "Granite" end
+ if choice == Enum.CellMaterial.Asphalt or choice == 5 then return "Asphalt" end
+ if choice == Enum.CellMaterial.Iron or choice == 6 then return "Iron" end
+ if choice == Enum.CellMaterial.Aluminum or choice == 7 then return "Aluminum" end
+ if choice == Enum.CellMaterial.Gold or choice == 8 then return "Gold" end
+ if choice == Enum.CellMaterial.WoodPlank or choice == 9 then return "Plank" end
+ if choice == Enum.CellMaterial.WoodLog or choice == 10 then return "Log" end
+ if choice == Enum.CellMaterial.Gravel or choice == 11 then return "Gravel" end
+ if choice == Enum.CellMaterial.CinderBlock or choice == 12 then return "Cinder Block" end
+ if choice == Enum.CellMaterial.MossyStone or choice == 13 then return "Stone Wall" end
+ if choice == Enum.CellMaterial.Cement or choice == 14 then return "Concrete" end
+ if choice == Enum.CellMaterial.RedPlastic or choice == 15 then return "Plastic (red)" end
+ if choice == Enum.CellMaterial.BluePlastic or choice == 16 then return "Plastic (blue)" end
+
+ if waterEnabled then
+ if choice == Enum.CellMaterial.Water or choice == 17 then return "Water" end
+ end
+ end
+
+
+ local function updateMaterialChoice(choice)
+ currentMaterial = getEnumFromName(choice)
+ terrainMaterialSelectionChanged:Fire(currentMaterial)
+ end
+
+ -- we so need a better way to do this
+ for i,v in pairs(materialNames) do
+ materialToImageMap[v] = {}
+ if v == "Grass" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=56563112"
+ elseif v == "Sand" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=62356652"
+ elseif v == "Brick" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=65961537"
+ elseif v == "Granite" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532153"
+ elseif v == "Asphalt" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532038"
+ elseif v == "Iron" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532093"
+ elseif v == "Aluminum" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531995"
+ elseif v == "Gold" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532118"
+ elseif v == "Plastic (red)" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531848"
+ elseif v == "Plastic (blue)" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531924"
+ elseif v == "Plank" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532015"
+ elseif v == "Log" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532051"
+ elseif v == "Gravel" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532206"
+ elseif v == "Cinder Block" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532103"
+ elseif v == "Stone Wall" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531804"
+ elseif v == "Concrete" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532059"
+ elseif v == "Water" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=81407474"
+ else materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=66887593" -- fill in the rest here!!
+ end
+ end
+
+ local scrollFrame, scrollUp, scrollDown, recalculateScroll = t.CreateScrollingFrame(nil,"grid")
+ scrollFrame.Size = UDim2.new(0.85,0,1,0)
+ scrollFrame.Position = UDim2.new(0,0,0,0)
+ scrollFrame.Parent = frame
+
+ scrollUp.Parent = frame
+ scrollUp.Visible = true
+ scrollUp.Position = UDim2.new(1,-19,0,0)
+
+ scrollDown.Parent = frame
+ scrollDown.Visible = true
+ scrollDown.Position = UDim2.new(1,-19,1,-17)
+
+ local function goToNewMaterial(buttonWrap, materialName)
+ updateMaterialChoice(materialName)
+ buttonWrap.BackgroundTransparency = 0
+ selectedButton.BackgroundTransparency = 1
+ selectedButton = buttonWrap
+ end
+
+ local function createMaterialButton(name)
+ local buttonWrap = Instance.new("TextButton")
+ buttonWrap.Text = ""
+ buttonWrap.Size = UDim2.new(0,32,0,32)
+ buttonWrap.BackgroundColor3 = Color3.new(1,1,1)
+ buttonWrap.BorderSizePixel = 0
+ buttonWrap.BackgroundTransparency = 1
+ buttonWrap.AutoButtonColor = false
+ buttonWrap.Name = tostring(name)
+
+ local imageButton = Instance.new("ImageButton")
+ imageButton.AutoButtonColor = false
+ imageButton.BackgroundTransparency = 1
+ imageButton.Size = UDim2.new(0,30,0,30)
+ imageButton.Position = UDim2.new(0,1,0,1)
+ imageButton.Name = tostring(name)
+ imageButton.Parent = buttonWrap
+ imageButton.Image = materialToImageMap[name].Regular
+
+ local enumType = Instance.new("NumberValue")
+ enumType.Name = "EnumType"
+ enumType.Parent = buttonWrap
+ enumType.Value = 0
+
+ imageButton.MouseEnter:connect(function()
+ buttonWrap.BackgroundTransparency = 0
+ end)
+ imageButton.MouseLeave:connect(function()
+ if selectedButton ~= buttonWrap then
+ buttonWrap.BackgroundTransparency = 1
+ end
+ end)
+ imageButton.MouseButton1Click:connect(function()
+ if selectedButton ~= buttonWrap then
+ goToNewMaterial(buttonWrap, tostring(name))
+ end
+ end)
+
+ return buttonWrap
+ end
+
+ for i = 1, #materialNames do
+ local imageButton = createMaterialButton(materialNames[i])
+
+ if materialNames[i] == "Grass" then -- always start with grass as the default
+ selectedButton = imageButton
+ imageButton.BackgroundTransparency = 0
+ end
+
+ imageButton.Parent = scrollFrame
+ end
+
+ local forceTerrainMaterialSelection = function(newMaterialType)
+ if not newMaterialType then return end
+ if currentMaterial == newMaterialType then return end
+
+ local matName = getNameFromEnum(newMaterialType)
+ local buttons = scrollFrame:GetChildren()
+ for i = 1, #buttons do
+ if buttons[i].Name == "Plastic (blue)" and matName == "Plastic (blue)" then goToNewMaterial(buttons[i],matName) return end
+ if buttons[i].Name == "Plastic (red)" and matName == "Plastic (red)" then goToNewMaterial(buttons[i],matName) return end
+ if string.find(buttons[i].Name, matName) then
+ goToNewMaterial(buttons[i],matName)
+ return
+ end
+ end
+ end
+
+ frame.Changed:connect(function ( prop )
+ if prop == "AbsoluteSize" then
+ recalculateScroll()
+ end
+ end)
+
+ recalculateScroll()
+ return frame, terrainMaterialSelectionChanged, forceTerrainMaterialSelection
+end
+
+t.CreateLoadingFrame = function(name,size,position)
+ game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id=35238053")
+
+ local loadingFrame = Instance.new("Frame")
+ loadingFrame.Name = "LoadingFrame"
+ loadingFrame.Style = Enum.FrameStyle.RobloxRound
+
+ if size then loadingFrame.Size = size
+ else loadingFrame.Size = UDim2.new(0,300,0,160) end
+ if position then loadingFrame.Position = position
+ else loadingFrame.Position = UDim2.new(0.5, -150, 0.5,-80) end
+
+ local loadingBar = Instance.new("Frame")
+ loadingBar.Name = "LoadingBar"
+ loadingBar.BackgroundColor3 = Color3.new(0,0,0)
+ loadingBar.BorderColor3 = Color3.new(79/255,79/255,79/255)
+ loadingBar.Position = UDim2.new(0,0,0,41)
+ loadingBar.Size = UDim2.new(1,0,0,30)
+ loadingBar.Parent = loadingFrame
+
+ local loadingGreenBar = Instance.new("ImageLabel")
+ loadingGreenBar.Name = "LoadingGreenBar"
+ loadingGreenBar.Image = "http://www.roblox.com/asset/?id=35238053"
+ loadingGreenBar.Position = UDim2.new(0,0,0,0)
+ loadingGreenBar.Size = UDim2.new(0,0,1,0)
+ loadingGreenBar.Visible = false
+ loadingGreenBar.Parent = loadingBar
+
+ local loadingPercent = Instance.new("TextLabel")
+ loadingPercent.Name = "LoadingPercent"
+ loadingPercent.BackgroundTransparency = 1
+ loadingPercent.Position = UDim2.new(0,0,1,0)
+ loadingPercent.Size = UDim2.new(1,0,0,14)
+ loadingPercent.Font = Enum.Font.Arial
+ loadingPercent.Text = "0%"
+ loadingPercent.FontSize = Enum.FontSize.Size14
+ loadingPercent.TextColor3 = Color3.new(1,1,1)
+ loadingPercent.Parent = loadingBar
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelButton"
+ cancelButton.Position = UDim2.new(0.5,-60,1,-40)
+ cancelButton.Size = UDim2.new(0,120,0,40)
+ cancelButton.Font = Enum.Font.Arial
+ cancelButton.FontSize = Enum.FontSize.Size18
+ cancelButton.TextColor3 = Color3.new(1,1,1)
+ cancelButton.Text = "Cancel"
+ cancelButton.Style = Enum.ButtonStyle.RobloxButton
+ cancelButton.Parent = loadingFrame
+
+ local loadingName = Instance.new("TextLabel")
+ loadingName.Name = "loadingName"
+ loadingName.BackgroundTransparency = 1
+ loadingName.Size = UDim2.new(1,0,0,18)
+ loadingName.Position = UDim2.new(0,0,0,2)
+ loadingName.Font = Enum.Font.Arial
+ loadingName.Text = name
+ loadingName.TextColor3 = Color3.new(1,1,1)
+ loadingName.TextStrokeTransparency = 1
+ loadingName.FontSize = Enum.FontSize.Size18
+ loadingName.Parent = loadingFrame
+
+ local cancelButtonClicked = Instance.new("BindableEvent")
+ cancelButtonClicked.Name = "CancelButtonClicked"
+ cancelButtonClicked.Parent = cancelButton
+ cancelButton.MouseButton1Click:connect(function()
+ cancelButtonClicked:Fire()
+ end)
+
+ local updateLoadingGuiPercent = function(percent, tweenAction, tweenLength)
+ if percent and type(percent) ~= "number" then
+ error("updateLoadingGuiPercent expects number as argument, got",type(percent),"instead")
+ end
+
+ local newSize = nil
+ if percent < 0 then
+ newSize = UDim2.new(0,0,1,0)
+ elseif percent > 1 then
+ newSize = UDim2.new(1,0,1,0)
+ else
+ newSize = UDim2.new(percent,0,1,0)
+ end
+
+ if tweenAction then
+ if not tweenLength then
+ error("updateLoadingGuiPercent is set to tween new percentage, but got no tween time length! Please pass this in as third argument")
+ end
+
+ if (newSize.X.Scale > 0) then
+ loadingGreenBar.Visible = true
+ loadingGreenBar:TweenSize( newSize,
+ Enum.EasingDirection.Out,
+ Enum.EasingStyle.Quad,
+ tweenLength,
+ true)
+ else
+ loadingGreenBar:TweenSize( newSize,
+ Enum.EasingDirection.Out,
+ Enum.EasingStyle.Quad,
+ tweenLength,
+ true,
+ function()
+ if (newSize.X.Scale < 0) then
+ loadingGreenBar.Visible = false
+ end
+ end)
+ end
+
+ else
+ loadingGreenBar.Size = newSize
+ loadingGreenBar.Visible = (newSize.X.Scale > 0)
+ end
+ end
+
+ loadingGreenBar.Changed:connect(function(prop)
+ if prop == "Size" then
+ loadingPercent.Text = tostring( math.ceil(loadingGreenBar.Size.X.Scale * 100) ) .. "%"
+ end
+ end)
+
+ return loadingFrame, updateLoadingGuiPercent, cancelButtonClicked
+end
+
+t.CreatePluginFrame = function (name,size,position,scrollable,parent)
+ function createMenuButton(size,position,text,fontsize,name,parent)
+ local button = Instance.new("TextButton",parent)
+ button.AutoButtonColor = false
+ button.Name = name
+ button.BackgroundTransparency = 1
+ button.Position = position
+ button.Size = size
+ button.Font = Enum.Font.ArialBold
+ button.FontSize = fontsize
+ button.Text = text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.BorderSizePixel = 0
+ button.BackgroundColor3 = Color3.new(20/255,20/255,20/255)
+
+ button.MouseEnter:connect(function ( )
+ if button.Selected then return end
+ button.BackgroundTransparency = 0
+ end)
+ button.MouseLeave:connect(function ( )
+ if button.Selected then return end
+ button.BackgroundTransparency = 1
+ end)
+
+ return button
+
+ end
+
+ local dragBar = Instance.new("Frame",parent)
+ dragBar.Name = tostring(name) .. "DragBar"
+ dragBar.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+ dragBar.BorderColor3 = Color3.new(0,0,0)
+ if size then
+ dragBar.Size = UDim2.new(size.X.Scale,size.X.Offset,0,20) + UDim2.new(0,20,0,0)
+ else
+ dragBar.Size = UDim2.new(0,183,0,20)
+ end
+ if position then
+ dragBar.Position = position
+ end
+ dragBar.Active = true
+ dragBar.Draggable = true
+ --dragBar.Visible = false
+ dragBar.MouseEnter:connect(function ( )
+ dragBar.BackgroundColor3 = Color3.new(49/255,49/255,49/255)
+ end)
+ dragBar.MouseLeave:connect(function ( )
+ dragBar.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+ end)
+
+ -- plugin name label
+ local pluginNameLabel = Instance.new("TextLabel",dragBar)
+ pluginNameLabel.Name = "BarNameLabel"
+ pluginNameLabel.Text = " " .. tostring(name)
+ pluginNameLabel.TextColor3 = Color3.new(1,1,1)
+ pluginNameLabel.TextStrokeTransparency = 0
+ pluginNameLabel.Size = UDim2.new(1,0,1,0)
+ pluginNameLabel.Font = Enum.Font.ArialBold
+ pluginNameLabel.FontSize = Enum.FontSize.Size18
+ pluginNameLabel.TextXAlignment = Enum.TextXAlignment.Left
+ pluginNameLabel.BackgroundTransparency = 1
+
+ -- close button
+ local closeButton = createMenuButton(UDim2.new(0,15,0,17),UDim2.new(1,-16,0.5,-8),"X",Enum.FontSize.Size14,"CloseButton",dragBar)
+ local closeEvent = Instance.new("BindableEvent")
+ closeEvent.Name = "CloseEvent"
+ closeEvent.Parent = closeButton
+ closeButton.MouseButton1Click:connect(function ()
+ closeEvent:Fire()
+ closeButton.BackgroundTransparency = 1
+ end)
+
+ -- help button
+ local helpButton = createMenuButton(UDim2.new(0,15,0,17),UDim2.new(1,-51,0.5,-8),"?",Enum.FontSize.Size14,"HelpButton",dragBar)
+ local helpFrame = Instance.new("Frame",dragBar)
+ helpFrame.Name = "HelpFrame"
+ helpFrame.BackgroundColor3 = Color3.new(0,0,0)
+ helpFrame.Size = UDim2.new(0,300,0,552)
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ helpFrame.Active = true
+ helpFrame.BorderSizePixel = 0
+ helpFrame.Visible = false
+
+ helpButton.MouseButton1Click:connect(function( )
+ helpFrame.Visible = not helpFrame.Visible
+ if helpFrame.Visible then
+ helpButton.Selected = true
+ helpButton.BackgroundTransparency = 0
+ local screenGui = getScreenGuiAncestor(helpFrame)
+ if screenGui then
+ if helpFrame.AbsolutePosition.X + helpFrame.AbsoluteSize.X > screenGui.AbsoluteSize.X then --position on left hand side
+ helpFrame.Position = UDim2.new(0,-5 - helpFrame.AbsoluteSize.X,0,0)
+ else -- position on right hand side
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ end
+ else
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ end
+ else
+ helpButton.Selected = false
+ helpButton.BackgroundTransparency = 1
+ end
+ end)
+
+ local minimizeButton = createMenuButton(UDim2.new(0,16,0,17),UDim2.new(1,-34,0.5,-8),"-",Enum.FontSize.Size14,"MinimizeButton",dragBar)
+ minimizeButton.TextYAlignment = Enum.TextYAlignment.Top
+
+ local minimizeFrame = Instance.new("Frame",dragBar)
+ minimizeFrame.Name = "MinimizeFrame"
+ minimizeFrame.BackgroundColor3 = Color3.new(73/255,73/255,73/255)
+ minimizeFrame.BorderColor3 = Color3.new(0,0,0)
+ minimizeFrame.Position = UDim2.new(0,0,1,0)
+ if size then
+ minimizeFrame.Size = UDim2.new(size.X.Scale,size.X.Offset,0,50) + UDim2.new(0,20,0,0)
+ else
+ minimizeFrame.Size = UDim2.new(0,183,0,50)
+ end
+ minimizeFrame.Visible = false
+
+ local minimizeBigButton = Instance.new("TextButton",minimizeFrame)
+ minimizeBigButton.Position = UDim2.new(0.5,-50,0.5,-20)
+ minimizeBigButton.Name = "MinimizeButton"
+ minimizeBigButton.Size = UDim2.new(0,100,0,40)
+ minimizeBigButton.Style = Enum.ButtonStyle.RobloxButton
+ minimizeBigButton.Font = Enum.Font.ArialBold
+ minimizeBigButton.FontSize = Enum.FontSize.Size18
+ minimizeBigButton.TextColor3 = Color3.new(1,1,1)
+ minimizeBigButton.Text = "Show"
+
+ local separatingLine = Instance.new("Frame",dragBar)
+ separatingLine.Name = "SeparatingLine"
+ separatingLine.BackgroundColor3 = Color3.new(115/255,115/255,115/255)
+ separatingLine.BorderSizePixel = 0
+ separatingLine.Position = UDim2.new(1,-18,0.5,-7)
+ separatingLine.Size = UDim2.new(0,1,0,14)
+
+ local otherSeparatingLine = separatingLine:clone()
+ otherSeparatingLine.Position = UDim2.new(1,-35,0.5,-7)
+ otherSeparatingLine.Parent = dragBar
+
+ local widgetContainer = Instance.new("Frame",dragBar)
+ widgetContainer.Name = "WidgetContainer"
+ widgetContainer.BackgroundTransparency = 1
+ widgetContainer.Position = UDim2.new(0,0,1,0)
+ widgetContainer.BorderColor3 = Color3.new(0,0,0)
+ if not scrollable then
+ widgetContainer.BackgroundTransparency = 0
+ widgetContainer.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ end
+
+ if size then
+ if scrollable then
+ widgetContainer.Size = size
+ else
+ widgetContainer.Size = UDim2.new(0,dragBar.AbsoluteSize.X,size.Y.Scale,size.Y.Offset)
+ end
+ else
+ if scrollable then
+ widgetContainer.Size = UDim2.new(0,163,0,400)
+ else
+ widgetContainer.Size = UDim2.new(0,dragBar.AbsoluteSize.X,0,400)
+ end
+ end
+ if position then
+ widgetContainer.Position = position + UDim2.new(0,0,0,20)
+ end
+
+ local frame,control,verticalDragger = nil
+ if scrollable then
+ --frame for widgets
+ frame,control = t.CreateTrueScrollingFrame()
+ frame.Size = UDim2.new(1, 0, 1, 0)
+ frame.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ frame.BorderColor3 = Color3.new(0,0,0)
+ frame.Active = true
+ frame.Parent = widgetContainer
+ control.Parent = dragBar
+ control.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ control.BorderSizePixel = 0
+ control.BackgroundTransparency = 0
+ control.Position = UDim2.new(1,-21,1,1)
+ if size then
+ control.Size = UDim2.new(0,21,size.Y.Scale,size.Y.Offset)
+ else
+ control.Size = UDim2.new(0,21,0,400)
+ end
+ control:FindFirstChild("ScrollDownButton").Position = UDim2.new(0,0,1,-20)
+
+ local fakeLine = Instance.new("Frame",control)
+ fakeLine.Name = "FakeLine"
+ fakeLine.BorderSizePixel = 0
+ fakeLine.BackgroundColor3 = Color3.new(0,0,0)
+ fakeLine.Size = UDim2.new(0,1,1,1)
+ fakeLine.Position = UDim2.new(1,0,0,0)
+
+ verticalDragger = Instance.new("TextButton",widgetContainer)
+ verticalDragger.ZIndex = 2
+ verticalDragger.AutoButtonColor = false
+ verticalDragger.Name = "VerticalDragger"
+ verticalDragger.BackgroundColor3 = Color3.new(50/255,50/255,50/255)
+ verticalDragger.BorderColor3 = Color3.new(0,0,0)
+ verticalDragger.Size = UDim2.new(1,20,0,20)
+ verticalDragger.Position = UDim2.new(0,0,1,0)
+ verticalDragger.Active = true
+ verticalDragger.Text = ""
+
+ local scrubFrame = Instance.new("Frame",verticalDragger)
+ scrubFrame.Name = "ScrubFrame"
+ scrubFrame.BackgroundColor3 = Color3.new(1,1,1)
+ scrubFrame.BorderSizePixel = 0
+ scrubFrame.Position = UDim2.new(0.5,-5,0.5,0)
+ scrubFrame.Size = UDim2.new(0,10,0,1)
+ scrubFrame.ZIndex = 5
+ local scrubTwo = scrubFrame:clone()
+ scrubTwo.Position = UDim2.new(0.5,-5,0.5,-2)
+ scrubTwo.Parent = verticalDragger
+ local scrubThree = scrubFrame:clone()
+ scrubThree.Position = UDim2.new(0.5,-5,0.5,2)
+ scrubThree.Parent = verticalDragger
+
+ local areaSoak = Instance.new("TextButton",getScreenGuiAncestor(parent))
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.BorderSizePixel = 0
+ areaSoak.Text = ""
+ areaSoak.ZIndex = 10
+ areaSoak.Visible = false
+ areaSoak.Active = true
+
+ local draggingVertical = false
+ local startYPos = nil
+ verticalDragger.MouseEnter:connect(function ()
+ verticalDragger.BackgroundColor3 = Color3.new(60/255,60/255,60/255)
+ end)
+ verticalDragger.MouseLeave:connect(function ()
+ verticalDragger.BackgroundColor3 = Color3.new(50/255,50/255,50/255)
+ end)
+ verticalDragger.MouseButton1Down:connect(function(x,y)
+ draggingVertical = true
+ areaSoak.Visible = true
+ startYPos = y
+ end)
+ areaSoak.MouseButton1Up:connect(function ( )
+ draggingVertical = false
+ areaSoak.Visible = false
+ end)
+ areaSoak.MouseMoved:connect(function(x,y)
+ if not draggingVertical then return end
+
+ local yDelta = y - startYPos
+ if not control.ScrollDownButton.Visible and yDelta > 0 then
+ return
+ end
+
+ if (widgetContainer.Size.Y.Offset + yDelta) < 150 then
+ widgetContainer.Size = UDim2.new(widgetContainer.Size.X.Scale, widgetContainer.Size.X.Offset,widgetContainer.Size.Y.Scale,150)
+ control.Size = UDim2.new (0,21,0,150)
+ return
+ end
+
+ startYPos = y
+
+ if widgetContainer.Size.Y.Offset + yDelta >= 0 then
+ widgetContainer.Size = UDim2.new(widgetContainer.Size.X.Scale, widgetContainer.Size.X.Offset,widgetContainer.Size.Y.Scale,widgetContainer.Size.Y.Offset + yDelta)
+ control.Size = UDim2.new(0,21,0,control.Size.Y.Offset + yDelta )
+ end
+ end)
+ end
+
+ local function switchMinimize()
+ minimizeFrame.Visible = not minimizeFrame.Visible
+ if scrollable then
+ frame.Visible = not frame.Visible
+ verticalDragger.Visible = not verticalDragger.Visible
+ control.Visible = not control.Visible
+ else
+ widgetContainer.Visible = not widgetContainer.Visible
+ end
+
+ if minimizeFrame.Visible then
+ minimizeButton.Text = "+"
+ else
+ minimizeButton.Text = "-"
+ end
+ end
+
+ minimizeBigButton.MouseButton1Click:connect(function ( )
+ switchMinimize()
+ end)
+
+ minimizeButton.MouseButton1Click:connect(function( )
+ switchMinimize()
+ end)
+
+ if scrollable then
+ return dragBar, frame, helpFrame, closeEvent
+ else
+ return dragBar, widgetContainer, helpFrame, closeEvent
+ end
+end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "CreatePropertyDropDownMenu" or funcNameOrFunc == t.CreatePropertyDropDownMenu then
+ return "Function CreatePropertyDropDownMenu. " ..
+ "Arguments: (instance, propertyName, enumType). " ..
+ "Side effect: returns a container with a drop-down-box that is linked to the 'property' field of 'instance' which is of type 'enumType'"
+ end
+ if funcNameOrFunc == "CreateDropDownMenu" or funcNameOrFunc == t.CreateDropDownMenu then
+ return "Function CreateDropDownMenu. " ..
+ "Arguments: (items, onItemSelected). " ..
+ "Side effect: Returns 2 results, a container to the gui object and a 'updateSelection' function for external updating. The container is a drop-down-box created around a list of items"
+ end
+ if funcNameOrFunc == "CreateMessageDialog" or funcNameOrFunc == t.CreateMessageDialog then
+ return "Function CreateMessageDialog. " ..
+ "Arguments: (title, message, buttons). " ..
+ "Side effect: Returns a gui object of a message box with 'title' and 'message' as passed in. 'buttons' input is an array of Tables contains a 'Text' and 'Function' field for the text/callback of each button"
+ end
+ if funcNameOrFunc == "CreateStyledMessageDialog" or funcNameOrFunc == t.CreateStyledMessageDialog then
+ return "Function CreateStyledMessageDialog. " ..
+ "Arguments: (title, message, style, buttons). " ..
+ "Side effect: Returns a gui object of a message box with 'title' and 'message' as passed in. 'buttons' input is an array of Tables contains a 'Text' and 'Function' field for the text/callback of each button, 'style' is a string, either Error, Notify or Confirm"
+ end
+ if funcNameOrFunc == "GetFontHeight" or funcNameOrFunc == t.GetFontHeight then
+ return "Function GetFontHeight. " ..
+ "Arguments: (font, fontSize). " ..
+ "Side effect: returns the size in pixels of the given font + fontSize"
+ end
+ if funcNameOrFunc == "LayoutGuiObjects" or funcNameOrFunc == t.LayoutGuiObjects then
+
+ end
+ if funcNameOrFunc == "CreateScrollingFrame" or funcNameOrFunc == t.CreateScrollingFrame then
+ return "Function CreateScrollingFrame. " ..
+ "Arguments: (orderList, style) " ..
+ "Side effect: returns 4 objects, (scrollFrame, scrollUpButton, scrollDownButton, recalculateFunction). 'scrollFrame' can be filled with GuiObjects. It will lay them out and allow scrollUpButton/scrollDownButton to interact with them. Orderlist is optional (and specifies the order to layout the children. Without orderlist, it uses the children order. style is also optional, and allows for a 'grid' styling if style is passed 'grid' as a string. recalculateFunction can be called when a relayout is needed (when orderList changes)"
+ end
+ if funcNameOrFunc == "CreateTrueScrollingFrame" or funcNameOrFunc == t.CreateTrueScrollingFrame then
+ return "Function CreateTrueScrollingFrame. " ..
+ "Arguments: (nil) " ..
+ "Side effect: returns 2 objects, (scrollFrame, controlFrame). 'scrollFrame' can be filled with GuiObjects, and they will be clipped if not inside the frame's bounds. controlFrame has children scrollup and scrolldown, as well as a slider. controlFrame can be parented to any guiobject and it will readjust itself to fit."
+ end
+ if funcNameOrFunc == "AutoTruncateTextObject" or funcNameOrFunc == t.AutoTruncateTextObject then
+ return "Function AutoTruncateTextObject. " ..
+ "Arguments: (textLabel) " ..
+ "Side effect: returns 2 objects, (textLabel, changeText). The 'textLabel' input is modified to automatically truncate text (with ellipsis), if it gets too small to fit. 'changeText' is a function that can be used to change the text, it takes 1 string as an argument"
+ end
+ if funcNameOrFunc == "CreateSlider" or funcNameOrFunc == t.CreateSlider then
+ return "Function CreateSlider. " ..
+ "Arguments: (steps, width, position) " ..
+ "Side effect: returns 2 objects, (sliderGui, sliderPosition). The 'steps' argument specifies how many different positions the slider can hold along the bar. 'width' specifies in pixels how wide the bar should be (modifiable afterwards if desired). 'position' argument should be a UDim2 for slider positioning. 'sliderPosition' is an IntValue whose current .Value specifies the specific step the slider is currently on."
+ end
+ if funcNameOrFunc == "CreateSliderNew" or funcNameOrFunc == t.CreateSliderNew then
+ return "Function CreateSliderNew. " ..
+ "Arguments: (steps, width, position) " ..
+ "Side effect: returns 2 objects, (sliderGui, sliderPosition). The 'steps' argument specifies how many different positions the slider can hold along the bar. 'width' specifies in pixels how wide the bar should be (modifiable afterwards if desired). 'position' argument should be a UDim2 for slider positioning. 'sliderPosition' is an IntValue whose current .Value specifies the specific step the slider is currently on."
+ end
+ if funcNameOrFunc == "CreateLoadingFrame" or funcNameOrFunc == t.CreateLoadingFrame then
+ return "Function CreateLoadingFrame. " ..
+ "Arguments: (name, size, position) " ..
+ "Side effect: Creates a gui that can be manipulated to show progress for a particular action. Name appears above the loading bar, and size and position are udim2 values (both size and position are optional arguments). Returns 3 arguments, the first being the gui created. The second being updateLoadingGuiPercent, which is a bindable function. This function takes one argument (two optionally), which should be a number between 0 and 1, representing the percentage the loading gui should be at. The second argument to this function is a boolean value that if set to true will tween the current percentage value to the new percentage value, therefore our third argument is how long this tween should take. Our third returned argument is a BindableEvent, that when fired means that someone clicked the cancel button on the dialog."
+ end
+ if funcNameOrFunc == "CreateTerrainMaterialSelector" or funcNameOrFunc == t.CreateTerrainMaterialSelector then
+ return "Function CreateTerrainMaterialSelector. " ..
+ "Arguments: (size, position) " ..
+ "Side effect: Size and position are UDim2 values that specifies the selector's size and position. Both size and position are optional arguments. This method returns 3 objects (terrainSelectorGui, terrainSelected, forceTerrainSelection). terrainSelectorGui is just the gui object that we generate with this function, parent it as you like. TerrainSelected is a BindableEvent that is fired whenever a new terrain type is selected in the gui. ForceTerrainSelection is a function that takes an argument of Enum.CellMaterial and will force the gui to show that material as currently selected."
+ end
+ end
+
+return t
diff --git a/asset/2 b/asset/2
new file mode 100644
index 0000000..11b1bf1
--- /dev/null
+++ b/asset/2
@@ -0,0 +1,23 @@
+--rbxassetid%2%
+-- Library Registration Script
+-- This script is used to register RbxLua libraries on game servers, so game scripts have
+-- access to all of the libraries (otherwise only local scripts do)
+
+local sc = game:GetService("ScriptContext")
+local tries = 0
+
+while not sc and tries < 3 do
+ tries = tries + 1
+ sc = game:GetService("ScriptContext")
+ wait(0.2)
+end
+
+if sc then
+ sc:RegisterLibrary("Libraries/RbxGui", "21")
+ sc:RegisterLibrary("Libraries/RbxGear", "22")
+ sc:RegisterLibrary("Libraries/RbxUtility", "23")
+ sc:RegisterLibrary("Libraries/RbxStamper", "24")
+ sc:LibraryRegistrationComplete()
+else
+ print("failed to find script context, libraries did not load")
+end
diff --git a/asset/20 b/asset/20
new file mode 100644
index 0000000..57b772c
--- /dev/null
+++ b/asset/20
@@ -0,0 +1,24 @@
+--rbxassetid%22%
+local t = {}
+
+t.Foo =
+ function()
+ print("foo")
+ end
+
+t.Bar =
+ function()
+ print("bar")
+ end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "Foo" or funcNameOrFunc == t.Foo then
+ return "Function Foo. Arguments: None. Side effect: prints foo"
+ elseif funcNameOrFunc == "Bar" or funcNameOrFunc == t.Bar then
+ return "Function Bar. Arguments: None. Side effect: prints bar"
+ end
+ end
+
+return t
\ No newline at end of file
diff --git a/asset/29 b/asset/29
new file mode 100644
index 0000000..6306806
--- /dev/null
+++ b/asset/29
@@ -0,0 +1,1118 @@
+--rbxassetid%23%
+local t = {}
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------JSON Functions Begin----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+
+ --JSON Encoder and Parser for Lua 5.1
+ --
+ --Copyright 2007 Shaun Brown (http://www.chipmunkav.com)
+ --All Rights Reserved.
+
+ --Permission is hereby granted, free of charge, to any person
+ --obtaining a copy of this software to deal in the Software without
+ --restriction, including without limitation the rights to use,
+ --copy, modify, merge, publish, distribute, sublicense, and/or
+ --sell copies of the Software, and to permit persons to whom the
+ --Software is furnished to do so, subject to the following conditions:
+
+ --The above copyright notice and this permission notice shall be
+ --included in all copies or substantial portions of the Software.
+ --If you find this software useful please give www.chipmunkav.com a mention.
+
+ --THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ --EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ --OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ --IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR
+ --ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
+ --CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ --CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+local string = string
+local math = math
+local table = table
+local error = error
+local tonumber = tonumber
+local tostring = tostring
+local type = type
+local setmetatable = setmetatable
+local pairs = pairs
+local ipairs = ipairs
+local assert = assert
+local Chipmunk = Chipmunk
+
+
+local StringBuilder = {
+ buffer = {}
+}
+
+function StringBuilder:New()
+ local o = {}
+ setmetatable(o, self)
+ self.__index = self
+ o.buffer = {}
+ return o
+end
+
+function StringBuilder:Append(s)
+ self.buffer[#self.buffer+1] = s
+end
+
+function StringBuilder:ToString()
+ return table.concat(self.buffer)
+end
+
+local JsonWriter = {
+ backslashes = {
+ ['\b'] = "\\b",
+ ['\t'] = "\\t",
+ ['\n'] = "\\n",
+ ['\f'] = "\\f",
+ ['\r'] = "\\r",
+ ['"'] = "\\\"",
+ ['\\'] = "\\\\",
+ ['/'] = "\\/"
+ }
+}
+
+function JsonWriter:New()
+ local o = {}
+ o.writer = StringBuilder:New()
+ setmetatable(o, self)
+ self.__index = self
+ return o
+end
+
+function JsonWriter:Append(s)
+ self.writer:Append(s)
+end
+
+function JsonWriter:ToString()
+ return self.writer:ToString()
+end
+
+function JsonWriter:Write(o)
+ local t = type(o)
+ if t == "nil" then
+ self:WriteNil()
+ elseif t == "boolean" then
+ self:WriteString(o)
+ elseif t == "number" then
+ self:WriteString(o)
+ elseif t == "string" then
+ self:ParseString(o)
+ elseif t == "table" then
+ self:WriteTable(o)
+ elseif t == "function" then
+ self:WriteFunction(o)
+ elseif t == "thread" then
+ self:WriteError(o)
+ elseif t == "userdata" then
+ self:WriteError(o)
+ end
+end
+
+function JsonWriter:WriteNil()
+ self:Append("null")
+end
+
+function JsonWriter:WriteString(o)
+ self:Append(tostring(o))
+end
+
+function JsonWriter:ParseString(s)
+ self:Append('"')
+ self:Append(string.gsub(s, "[%z%c\\\"/]", function(n)
+ local c = self.backslashes[n]
+ if c then return c end
+ return string.format("\\u%.4X", string.byte(n))
+ end))
+ self:Append('"')
+end
+
+function JsonWriter:IsArray(t)
+ local count = 0
+ local isindex = function(k)
+ if type(k) == "number" and k > 0 then
+ if math.floor(k) == k then
+ return true
+ end
+ end
+ return false
+ end
+ for k,v in pairs(t) do
+ if not isindex(k) then
+ return false, '{', '}'
+ else
+ count = math.max(count, k)
+ end
+ end
+ return true, '[', ']', count
+end
+
+function JsonWriter:WriteTable(t)
+ local ba, st, et, n = self:IsArray(t)
+ self:Append(st)
+ if ba then
+ for i = 1, n do
+ self:Write(t[i])
+ if i < n then
+ self:Append(',')
+ end
+ end
+ else
+ local first = true;
+ for k, v in pairs(t) do
+ if not first then
+ self:Append(',')
+ end
+ first = false;
+ self:ParseString(k)
+ self:Append(':')
+ self:Write(v)
+ end
+ end
+ self:Append(et)
+end
+
+function JsonWriter:WriteError(o)
+ error(string.format(
+ "Encoding of %s unsupported",
+ tostring(o)))
+end
+
+function JsonWriter:WriteFunction(o)
+ if o == Null then
+ self:WriteNil()
+ else
+ self:WriteError(o)
+ end
+end
+
+local StringReader = {
+ s = "",
+ i = 0
+}
+
+function StringReader:New(s)
+ local o = {}
+ setmetatable(o, self)
+ self.__index = self
+ o.s = s or o.s
+ return o
+end
+
+function StringReader:Peek()
+ local i = self.i + 1
+ if i <= #self.s then
+ return string.sub(self.s, i, i)
+ end
+ return nil
+end
+
+function StringReader:Next()
+ self.i = self.i+1
+ if self.i <= #self.s then
+ return string.sub(self.s, self.i, self.i)
+ end
+ return nil
+end
+
+function StringReader:All()
+ return self.s
+end
+
+local JsonReader = {
+ escapes = {
+ ['t'] = '\t',
+ ['n'] = '\n',
+ ['f'] = '\f',
+ ['r'] = '\r',
+ ['b'] = '\b',
+ }
+}
+
+function JsonReader:New(s)
+ local o = {}
+ o.reader = StringReader:New(s)
+ setmetatable(o, self)
+ self.__index = self
+ return o;
+end
+
+function JsonReader:Read()
+ self:SkipWhiteSpace()
+ local peek = self:Peek()
+ if peek == nil then
+ error(string.format(
+ "Nil string: '%s'",
+ self:All()))
+ elseif peek == '{' then
+ return self:ReadObject()
+ elseif peek == '[' then
+ return self:ReadArray()
+ elseif peek == '"' then
+ return self:ReadString()
+ elseif string.find(peek, "[%+%-%d]") then
+ return self:ReadNumber()
+ elseif peek == 't' then
+ return self:ReadTrue()
+ elseif peek == 'f' then
+ return self:ReadFalse()
+ elseif peek == 'n' then
+ return self:ReadNull()
+ elseif peek == '/' then
+ self:ReadComment()
+ return self:Read()
+ else
+ return nil
+ end
+end
+
+function JsonReader:ReadTrue()
+ self:TestReservedWord{'t','r','u','e'}
+ return true
+end
+
+function JsonReader:ReadFalse()
+ self:TestReservedWord{'f','a','l','s','e'}
+ return false
+end
+
+function JsonReader:ReadNull()
+ self:TestReservedWord{'n','u','l','l'}
+ return nil
+end
+
+function JsonReader:TestReservedWord(t)
+ for i, v in ipairs(t) do
+ if self:Next() ~= v then
+ error(string.format(
+ "Error reading '%s': %s",
+ table.concat(t),
+ self:All()))
+ end
+ end
+end
+
+function JsonReader:ReadNumber()
+ local result = self:Next()
+ local peek = self:Peek()
+ while peek ~= nil and string.find(
+ peek,
+ "[%+%-%d%.eE]") do
+ result = result .. self:Next()
+ peek = self:Peek()
+ end
+ result = tonumber(result)
+ if result == nil then
+ error(string.format(
+ "Invalid number: '%s'",
+ result))
+ else
+ return result
+ end
+end
+
+function JsonReader:ReadString()
+ local result = ""
+ assert(self:Next() == '"')
+ while self:Peek() ~= '"' do
+ local ch = self:Next()
+ if ch == '\\' then
+ ch = self:Next()
+ if self.escapes[ch] then
+ ch = self.escapes[ch]
+ end
+ end
+ result = result .. ch
+ end
+ assert(self:Next() == '"')
+ local fromunicode = function(m)
+ return string.char(tonumber(m, 16))
+ end
+ return string.gsub(
+ result,
+ "u%x%x(%x%x)",
+ fromunicode)
+end
+
+function JsonReader:ReadComment()
+ assert(self:Next() == '/')
+ local second = self:Next()
+ if second == '/' then
+ self:ReadSingleLineComment()
+ elseif second == '*' then
+ self:ReadBlockComment()
+ else
+ error(string.format(
+ "Invalid comment: %s",
+ self:All()))
+ end
+end
+
+function JsonReader:ReadBlockComment()
+ local done = false
+ while not done do
+ local ch = self:Next()
+ if ch == '*' and self:Peek() == '/' then
+ done = true
+ end
+ if not done and
+ ch == '/' and
+ self:Peek() == "*" then
+ error(string.format(
+ "Invalid comment: %s, '/*' illegal.",
+ self:All()))
+ end
+ end
+ self:Next()
+end
+
+function JsonReader:ReadSingleLineComment()
+ local ch = self:Next()
+ while ch ~= '\r' and ch ~= '\n' do
+ ch = self:Next()
+ end
+end
+
+function JsonReader:ReadArray()
+ local result = {}
+ assert(self:Next() == '[')
+ local done = false
+ if self:Peek() == ']' then
+ done = true;
+ end
+ while not done do
+ local item = self:Read()
+ result[#result+1] = item
+ self:SkipWhiteSpace()
+ if self:Peek() == ']' then
+ done = true
+ end
+ if not done then
+ local ch = self:Next()
+ if ch ~= ',' then
+ error(string.format(
+ "Invalid array: '%s' due to: '%s'",
+ self:All(), ch))
+ end
+ end
+ end
+ assert(']' == self:Next())
+ return result
+end
+
+function JsonReader:ReadObject()
+ local result = {}
+ assert(self:Next() == '{')
+ local done = false
+ if self:Peek() == '}' then
+ done = true
+ end
+ while not done do
+ local key = self:Read()
+ if type(key) ~= "string" then
+ error(string.format(
+ "Invalid non-string object key: %s",
+ key))
+ end
+ self:SkipWhiteSpace()
+ local ch = self:Next()
+ if ch ~= ':' then
+ error(string.format(
+ "Invalid object: '%s' due to: '%s'",
+ self:All(),
+ ch))
+ end
+ self:SkipWhiteSpace()
+ local val = self:Read()
+ result[key] = val
+ self:SkipWhiteSpace()
+ if self:Peek() == '}' then
+ done = true
+ end
+ if not done then
+ ch = self:Next()
+ if ch ~= ',' then
+ error(string.format(
+ "Invalid array: '%s' near: '%s'",
+ self:All(),
+ ch))
+ end
+ end
+ end
+ assert(self:Next() == "}")
+ return result
+end
+
+function JsonReader:SkipWhiteSpace()
+ local p = self:Peek()
+ while p ~= nil and string.find(p, "[%s/]") do
+ if p == '/' then
+ self:ReadComment()
+ else
+ self:Next()
+ end
+ p = self:Peek()
+ end
+end
+
+function JsonReader:Peek()
+ return self.reader:Peek()
+end
+
+function JsonReader:Next()
+ return self.reader:Next()
+end
+
+function JsonReader:All()
+ return self.reader:All()
+end
+
+function Encode(o)
+ local writer = JsonWriter:New()
+ writer:Write(o)
+ return writer:ToString()
+end
+
+function Decode(s)
+ local reader = JsonReader:New(s)
+ return reader:Read()
+end
+
+function Null()
+ return Null
+end
+-------------------- End JSON Parser ------------------------
+
+t.DecodeJSON = function(jsonString)
+ pcall(function() warn("RbxUtility.DecodeJSON is deprecated, please use Game:GetService('HttpService'):JSONDecode() instead.") end)
+
+ if type(jsonString) == "string" then
+ return Decode(jsonString)
+ end
+ print("RbxUtil.DecodeJSON expects string argument!")
+ return nil
+end
+
+t.EncodeJSON = function(jsonTable)
+ pcall(function() warn("RbxUtility.EncodeJSON is deprecated, please use Game:GetService('HttpService'):JSONEncode() instead.") end)
+ return Encode(jsonTable)
+end
+
+
+
+
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--------------------------------------------Terrain Utilities Begin-----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--makes a wedge at location x, y, z
+--sets cell x, y, z to default material if parameter is provided, if not sets cell x, y, z to be whatever material it previously w
+--returns true if made a wedge, false if the cell remains a block
+t.MakeWedge = function(x, y, z, defaultmaterial)
+ return game:GetService("Terrain"):AutoWedgeCell(x,y,z)
+end
+
+t.SelectTerrainRegion = function(regionToSelect, color, selectEmptyCells, selectionParent)
+ local terrain = game.Workspace:FindFirstChild("Terrain")
+ if not terrain then return end
+
+ assert(regionToSelect)
+ assert(color)
+
+ if not type(regionToSelect) == "Region3" then
+ error("regionToSelect (first arg), should be of type Region3, but is type",type(regionToSelect))
+ end
+ if not type(color) == "BrickColor" then
+ error("color (second arg), should be of type BrickColor, but is type",type(color))
+ end
+
+ -- frequently used terrain calls (speeds up call, no lookup necessary)
+ local GetCell = terrain.GetCell
+ local WorldToCellPreferSolid = terrain.WorldToCellPreferSolid
+ local CellCenterToWorld = terrain.CellCenterToWorld
+ local emptyMaterial = Enum.CellMaterial.Empty
+
+ -- container for all adornments, passed back to user
+ local selectionContainer = Instance.new("Model")
+ selectionContainer.Name = "SelectionContainer"
+ selectionContainer.Archivable = false
+ if selectionParent then
+ selectionContainer.Parent = selectionParent
+ else
+ selectionContainer.Parent = game.Workspace
+ end
+
+ local updateSelection = nil -- function we return to allow user to update selection
+ local currentKeepAliveTag = nil -- a tag that determines whether adorns should be destroyed
+ local aliveCounter = 0 -- helper for currentKeepAliveTag
+ local lastRegion = nil -- used to stop updates that do nothing
+ local adornments = {} -- contains all adornments
+ local reusableAdorns = {}
+
+ local selectionPart = Instance.new("Part")
+ selectionPart.Name = "SelectionPart"
+ selectionPart.Transparency = 1
+ selectionPart.Anchored = true
+ selectionPart.Locked = true
+ selectionPart.CanCollide = false
+ selectionPart.FormFactor = Enum.FormFactor.Custom
+ selectionPart.Size = Vector3.new(4.2,4.2,4.2)
+
+ local selectionBox = Instance.new("SelectionBox")
+
+ -- srs translation from region3 to region3int16
+ function Region3ToRegion3int16(region3)
+ local theLowVec = region3.CFrame.p - (region3.Size/2) + Vector3.new(2,2,2)
+ local lowCell = WorldToCellPreferSolid(terrain,theLowVec)
+
+ local theHighVec = region3.CFrame.p + (region3.Size/2) - Vector3.new(2,2,2)
+ local highCell = WorldToCellPreferSolid(terrain, theHighVec)
+
+ local highIntVec = Vector3int16.new(highCell.x,highCell.y,highCell.z)
+ local lowIntVec = Vector3int16.new(lowCell.x,lowCell.y,lowCell.z)
+
+ return Region3int16.new(lowIntVec,highIntVec)
+ end
+
+ -- helper function that creates the basis for a selection box
+ function createAdornment(theColor)
+ local selectionPartClone = nil
+ local selectionBoxClone = nil
+
+ if #reusableAdorns > 0 then
+ selectionPartClone = reusableAdorns[1]["part"]
+ selectionBoxClone = reusableAdorns[1]["box"]
+ table.remove(reusableAdorns,1)
+
+ selectionBoxClone.Visible = true
+ else
+ selectionPartClone = selectionPart:Clone()
+ selectionPartClone.Archivable = false
+
+ selectionBoxClone = selectionBox:Clone()
+ selectionBoxClone.Archivable = false
+
+ selectionBoxClone.Adornee = selectionPartClone
+ selectionBoxClone.Parent = selectionContainer
+
+ selectionBoxClone.Adornee = selectionPartClone
+
+ selectionBoxClone.Parent = selectionContainer
+ end
+
+ if theColor then
+ selectionBoxClone.Color = theColor
+ end
+
+ return selectionPartClone, selectionBoxClone
+ end
+
+ -- iterates through all current adornments and deletes any that don't have latest tag
+ function cleanUpAdornments()
+ for cellPos, adornTable in pairs(adornments) do
+
+ if adornTable.KeepAlive ~= currentKeepAliveTag then -- old news, we should get rid of this
+ adornTable.SelectionBox.Visible = false
+ table.insert(reusableAdorns,{part = adornTable.SelectionPart, box = adornTable.SelectionBox})
+ adornments[cellPos] = nil
+ end
+ end
+ end
+
+ -- helper function to update tag
+ function incrementAliveCounter()
+ aliveCounter = aliveCounter + 1
+ if aliveCounter > 1000000 then
+ aliveCounter = 0
+ end
+ return aliveCounter
+ end
+
+ -- finds full cells in region and adorns each cell with a box, with the argument color
+ function adornFullCellsInRegion(region, color)
+ local regionBegin = region.CFrame.p - (region.Size/2) + Vector3.new(2,2,2)
+ local regionEnd = region.CFrame.p + (region.Size/2) - Vector3.new(2,2,2)
+
+ local cellPosBegin = WorldToCellPreferSolid(terrain, regionBegin)
+ local cellPosEnd = WorldToCellPreferSolid(terrain, regionEnd)
+
+ currentKeepAliveTag = incrementAliveCounter()
+ for y = cellPosBegin.y, cellPosEnd.y do
+ for z = cellPosBegin.z, cellPosEnd.z do
+ for x = cellPosBegin.x, cellPosEnd.x do
+ local cellMaterial = GetCell(terrain, x, y, z)
+
+ if cellMaterial ~= emptyMaterial then
+ local cframePos = CellCenterToWorld(terrain, x, y, z)
+ local cellPos = Vector3int16.new(x,y,z)
+
+ local updated = false
+ for cellPosAdorn, adornTable in pairs(adornments) do
+ if cellPosAdorn == cellPos then
+ adornTable.KeepAlive = currentKeepAliveTag
+ if color then
+ adornTable.SelectionBox.Color = color
+ end
+ updated = true
+ break
+ end
+ end
+
+ if not updated then
+ local selectionPart, selectionBox = createAdornment(color)
+ selectionPart.Size = Vector3.new(4,4,4)
+ selectionPart.CFrame = CFrame.new(cframePos)
+ local adornTable = {SelectionPart = selectionPart, SelectionBox = selectionBox, KeepAlive = currentKeepAliveTag}
+ adornments[cellPos] = adornTable
+ end
+ end
+ end
+ end
+ end
+ cleanUpAdornments()
+ end
+
+
+ ------------------------------------- setup code ------------------------------
+ lastRegion = regionToSelect
+
+ if selectEmptyCells then -- use one big selection to represent the area selected
+ local selectionPart, selectionBox = createAdornment(color)
+
+ selectionPart.Size = regionToSelect.Size
+ selectionPart.CFrame = regionToSelect.CFrame
+
+ adornments.SelectionPart = selectionPart
+ adornments.SelectionBox = selectionBox
+
+ updateSelection =
+ function (newRegion, color)
+ if newRegion and newRegion ~= lastRegion then
+ lastRegion = newRegion
+ selectionPart.Size = newRegion.Size
+ selectionPart.CFrame = newRegion.CFrame
+ end
+ if color then
+ selectionBox.Color = color
+ end
+ end
+ else -- use individual cell adorns to represent the area selected
+ adornFullCellsInRegion(regionToSelect, color)
+ updateSelection =
+ function (newRegion, color)
+ if newRegion and newRegion ~= lastRegion then
+ lastRegion = newRegion
+ adornFullCellsInRegion(newRegion, color)
+ end
+ end
+
+ end
+
+ local destroyFunc = function()
+ updateSelection = nil
+ if selectionContainer then selectionContainer:Destroy() end
+ adornments = nil
+ end
+
+ return updateSelection, destroyFunc
+end
+
+-----------------------------Terrain Utilities End-----------------------------
+
+
+
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------Signal class begin------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--[[
+A 'Signal' object identical to the internal RBXScriptSignal object in it's public API and semantics. This function
+can be used to create "custom events" for user-made code.
+API:
+Method :connect( function handler )
+ Arguments: The function to connect to.
+ Returns: A new connection object which can be used to disconnect the connection
+ Description: Connects this signal to the function specified by |handler|. That is, when |fire( ... )| is called for
+ the signal the |handler| will be called with the arguments given to |fire( ... )|. Note, the functions
+ connected to a signal are called in NO PARTICULAR ORDER, so connecting one function after another does
+ NOT mean that the first will be called before the second as a result of a call to |fire|.
+
+Method :disconnect()
+ Arguments: None
+ Returns: None
+ Description: Disconnects all of the functions connected to this signal.
+
+Method :fire( ... )
+ Arguments: Any arguments are accepted
+ Returns: None
+ Description: Calls all of the currently connected functions with the given arguments.
+
+Method :wait()
+ Arguments: None
+ Returns: The arguments given to fire
+ Description: This call blocks until
+]]
+
+function t.CreateSignal()
+ local this = {}
+
+ local mBindableEvent = Instance.new('BindableEvent')
+ local mAllCns = {} --all connection objects returned by mBindableEvent::connect
+
+ --main functions
+ function this:connect(func)
+ if self ~= this then error("connect must be called with `:`, not `.`", 2) end
+ if type(func) ~= 'function' then
+ error("Argument #1 of connect must be a function, got a "..type(func), 2)
+ end
+ local cn = mBindableEvent.Event:connect(func)
+ mAllCns[cn] = true
+ local pubCn = {}
+ function pubCn:disconnect()
+ cn:disconnect()
+ mAllCns[cn] = nil
+ end
+ return pubCn
+ end
+ function this:disconnect()
+ if self ~= this then error("disconnect must be called with `:`, not `.`", 2) end
+ for cn, _ in pairs(mAllCns) do
+ cn:disconnect()
+ mAllCns[cn] = nil
+ end
+ end
+ function this:wait()
+ if self ~= this then error("wait must be called with `:`, not `.`", 2) end
+ return mBindableEvent.Event:wait()
+ end
+ function this:fire(...)
+ if self ~= this then error("fire must be called with `:`, not `.`", 2) end
+ mBindableEvent:Fire(...)
+ end
+
+ return this
+end
+
+------------------------------------------------- Sigal class End ------------------------------------------------------
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+-----------------------------------------------Create Function Begins---------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--[[
+A "Create" function for easy creation of Roblox instances. The function accepts a string which is the classname of
+the object to be created. The function then returns another function which either accepts accepts no arguments, in
+which case it simply creates an object of the given type, or a table argument that may contain several types of data,
+in which case it mutates the object in varying ways depending on the nature of the aggregate data. These are the
+type of data and what operation each will perform:
+1) A string key mapping to some value:
+ Key-Value pairs in this form will be treated as properties of the object, and will be assigned in NO PARTICULAR
+ ORDER. If the order in which properties is assigned matter, then they must be assigned somewhere else than the
+ |Create| call's body.
+
+2) An integral key mapping to another Instance:
+ Normal numeric keys mapping to Instances will be treated as children if the object being created, and will be
+ parented to it. This allows nice recursive calls to Create to create a whole hierarchy of objects without a
+ need for temporary variables to store references to those objects.
+
+3) A key which is a value returned from Create.Event( eventname ), and a value which is a function function
+ The Create.E( string ) function provides a limited way to connect to signals inside of a Create hierarchy
+ for those who really want such a functionality. The name of the event whose name is passed to
+ Create.E( string )
+
+4) A key which is the Create function itself, and a value which is a function
+ The function will be run with the argument of the object itself after all other initialization of the object is
+ done by create. This provides a way to do arbitrary things involving the object from withing the create
+ hierarchy.
+ Note: This function is called SYNCHRONOUSLY, that means that you should only so initialization in
+ it, not stuff which requires waiting, as the Create call will block until it returns. While waiting in the
+ constructor callback function is possible, it is probably not a good design choice.
+ Note: Since the constructor function is called after all other initialization, a Create block cannot have two
+ constructor functions, as it would not be possible to call both of them last, also, this would be unnecessary.
+
+
+Some example usages:
+
+A simple example which uses the Create function to create a model object and assign two of it's properties.
+local model = Create'Model'{
+ Name = 'A New model',
+ Parent = game.Workspace,
+}
+
+
+An example where a larger hierarchy of object is made. After the call the hierarchy will look like this:
+Model_Container
+ |-ObjectValue
+ | |
+ | `-BoolValueChild
+ `-IntValue
+
+local model = Create'Model'{
+ Name = 'Model_Container',
+ Create'ObjectValue'{
+ Create'BoolValue'{
+ Name = 'BoolValueChild',
+ },
+ },
+ Create'IntValue'{},
+}
+
+
+An example using the event syntax:
+
+local part = Create'Part'{
+ [Create.E'Touched'] = function(part)
+ print("I was touched by "..part.Name)
+ end,
+}
+
+
+An example using the general constructor syntax:
+
+local model = Create'Part'{
+ [Create] = function(this)
+ print("Constructor running!")
+ this.Name = GetGlobalFoosAndBars(this)
+ end,
+}
+
+
+Note: It is also perfectly legal to save a reference to the function returned by a call Create, this will not cause
+ any unexpected behavior. EG:
+ local partCreatingFunction = Create'Part'
+ local part = partCreatingFunction()
+]]
+
+--the Create function need to be created as a functor, not a function, in order to support the Create.E syntax, so it
+--will be created in several steps rather than as a single function declaration.
+local function Create_PrivImpl(objectType)
+ if type(objectType) ~= 'string' then
+ error("Argument of Create must be a string", 2)
+ end
+ --return the proxy function that gives us the nice Create'string'{data} syntax
+ --The first function call is a function call using Lua's single-string-argument syntax
+ --The second function call is using Lua's single-table-argument syntax
+ --Both can be chained together for the nice effect.
+ return function(dat)
+ --default to nothing, to handle the no argument given case
+ dat = dat or {}
+
+ --make the object to mutate
+ local obj = Instance.new(objectType)
+
+ --stored constructor function to be called after other initialization
+ local ctor = nil
+
+ for k, v in pairs(dat) do
+ --add property
+ if type(k) == 'string' then
+ obj[k] = v
+
+
+ --add child
+ elseif type(k) == 'number' then
+ if type(v) ~= 'userdata' then
+ error("Bad entry in Create body: Numeric keys must be paired with children, got a: "..type(v), 2)
+ end
+ v.Parent = obj
+
+
+ --event connect
+ elseif type(k) == 'table' and k.__eventname then
+ if type(v) ~= 'function' then
+ error("Bad entry in Create body: Key `[Create.E\'"..k.__eventname.."\']` must have a function value\
+ got: "..tostring(v), 2)
+ end
+ obj[k.__eventname]:connect(v)
+
+
+ --define constructor function
+ elseif k == t.Create then
+ if type(v) ~= 'function' then
+ error("Bad entry in Create body: Key `[Create]` should be paired with a constructor function, \
+ got: "..tostring(v), 2)
+ elseif ctor then
+ --ctor already exists, only one allowed
+ error("Bad entry in Create body: Only one constructor function is allowed", 2)
+ end
+ ctor = v
+
+
+ else
+ error("Bad entry ("..tostring(k).." => "..tostring(v)..") in Create body", 2)
+ end
+ end
+
+ --apply constructor function if it exists
+ if ctor then
+ ctor(obj)
+ end
+
+ --return the completed object
+ return obj
+ end
+end
+
+--now, create the functor:
+t.Create = setmetatable({}, {__call = function(tb, ...) return Create_PrivImpl(...) end})
+
+--and create the "Event.E" syntax stub. Really it's just a stub to construct a table which our Create
+--function can recognize as special.
+t.Create.E = function(eventName)
+ return {__eventname = eventName}
+end
+
+-------------------------------------------------Create function End----------------------------------------------------
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------Documentation Begin-----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "DecodeJSON" or funcNameOrFunc == t.DecodeJSON then
+ return "Function DecodeJSON. " ..
+ "Arguments: (string). " ..
+ "Side effect: returns a table with all parsed JSON values"
+ end
+ if funcNameOrFunc == "EncodeJSON" or funcNameOrFunc == t.EncodeJSON then
+ return "Function EncodeJSON. " ..
+ "Arguments: (table). " ..
+ "Side effect: returns a string composed of argument table in JSON data format"
+ end
+ if funcNameOrFunc == "MakeWedge" or funcNameOrFunc == t.MakeWedge then
+ return "Function MakeWedge. " ..
+ "Arguments: (x, y, z, [default material]). " ..
+ "Description: Makes a wedge at location x, y, z. Sets cell x, y, z to default material if "..
+ "parameter is provided, if not sets cell x, y, z to be whatever material it previously was. "..
+ "Returns true if made a wedge, false if the cell remains a block "
+ end
+ if funcNameOrFunc == "SelectTerrainRegion" or funcNameOrFunc == t.SelectTerrainRegion then
+ return "Function SelectTerrainRegion. " ..
+ "Arguments: (regionToSelect, color, selectEmptyCells, selectionParent). " ..
+ "Description: Selects all terrain via a series of selection boxes within the regionToSelect " ..
+ "(this should be a region3 value). The selection box color is detemined by the color argument " ..
+ "(should be a brickcolor value). SelectionParent is the parent that the selection model gets placed to (optional)." ..
+ "SelectEmptyCells is bool, when true will select all cells in the " ..
+ "region, otherwise we only select non-empty cells. Returns a function that can update the selection," ..
+ "arguments to said function are a new region3 to select, and the adornment color (color arg is optional). " ..
+ "Also returns a second function that takes no arguments and destroys the selection"
+ end
+ if funcNameOrFunc == "CreateSignal" or funcNameOrFunc == t.CreateSignal then
+ return "Function CreateSignal. "..
+ "Arguments: None. "..
+ "Returns: The newly created Signal object. This object is identical to the RBXScriptSignal class "..
+ "used for events in Objects, but is a Lua-side object so it can be used to create custom events in"..
+ "Lua code. "..
+ "Methods of the Signal object: :connect, :wait, :fire, :disconnect. "..
+ "For more info you can pass the method name to the Help function, or view the wiki page "..
+ "for this library. EG: Help('Signal:connect')."
+ end
+ if funcNameOrFunc == "Signal:connect" then
+ return "Method Signal:connect. "..
+ "Arguments: (function handler). "..
+ "Return: A connection object which can be used to disconnect the connection to this handler. "..
+ "Description: Connectes a handler function to this Signal, so that when |fire| is called the "..
+ "handler function will be called with the arguments passed to |fire|."
+ end
+ if funcNameOrFunc == "Signal:wait" then
+ return "Method Signal:wait. "..
+ "Arguments: None. "..
+ "Returns: The arguments passed to the next call to |fire|. "..
+ "Description: This call does not return until the next call to |fire| is made, at which point it "..
+ "will return the values which were passed as arguments to that |fire| call."
+ end
+ if funcNameOrFunc == "Signal:fire" then
+ return "Method Signal:fire. "..
+ "Arguments: Any number of arguments of any type. "..
+ "Returns: None. "..
+ "Description: This call will invoke any connected handler functions, and notify any waiting code "..
+ "attached to this Signal to continue, with the arguments passed to this function. Note: The calls "..
+ "to handlers are made asynchronously, so this call will return immediately regardless of how long "..
+ "it takes the connected handler functions to complete."
+ end
+ if funcNameOrFunc == "Signal:disconnect" then
+ return "Method Signal:disconnect. "..
+ "Arguments: None. "..
+ "Returns: None. "..
+ "Description: This call disconnects all handlers attacched to this function, note however, it "..
+ "does NOT make waiting code continue, as is the behavior of normal Roblox events. This method "..
+ "can also be called on the connection object which is returned from Signal:connect to only "..
+ "disconnect a single handler, as opposed to this method, which will disconnect all handlers."
+ end
+ if funcNameOrFunc == "Create" then
+ return "Function Create. "..
+ "Arguments: A table containing information about how to construct a collection of objects. "..
+ "Returns: The constructed objects. "..
+ "Descrition: Create is a very powerfull function, whose description is too long to fit here, and "..
+ "is best described via example, please see the wiki page for a description of how to use it."
+ end
+ end
+
+--------------------------------------------Documentation Ends----------------------------------------------------------
+
+return t
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/asset/3 b/asset/3
new file mode 100644
index 0000000..df676f6
--- /dev/null
+++ b/asset/3
@@ -0,0 +1 @@
+--rbxassetid%3%
\ No newline at end of file
diff --git a/asset/30 b/asset/30
new file mode 100644
index 0000000..aba965d
--- /dev/null
+++ b/asset/30
@@ -0,0 +1,2208 @@
+--rbxassetid%24%
+local t = {}
+
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+-- Do a line/plane intersection. The line starts at the camera. The plane is at y == 0, normal(0, 1, 0)
+--
+-- vectorPos - End point of the line.
+--
+-- Return:
+-- cellPos - The terrain cell intersection point if there is one, vectorPos if there isn't.
+-- hit - Whether there was a plane intersection. Value is true if there was, false if not.
+function PlaneIntersection(vectorPos)
+ local hit = false
+ local currCamera = game.Workspace.CurrentCamera
+ local startPos = Vector3.new(currCamera.CoordinateFrame.p.X, currCamera.CoordinateFrame.p.Y, currCamera.CoordinateFrame.p.Z)
+ local endPos = Vector3.new(vectorPos.X, vectorPos.Y, vectorPos.Z)
+ local normal = Vector3.new(0, 1, 0)
+ local p3 = Vector3.new(0, 0, 0)
+ local startEndDot = normal:Dot(endPos - startPos)
+ local cellPos = vectorPos
+ if startEndDot ~= 0 then
+ local t = normal:Dot(p3 - startPos) / startEndDot
+ if(t >=0 and t <=1) then
+ local intersection = ((endPos - startPos) * t) + startPos
+ cellPos = game.Workspace.Terrain:WorldToCell(intersection)
+ hit = true
+ end
+ end
+
+ return cellPos, hit
+end
+
+
+-- Purpose:
+-- Checks for terrain touched by the mouse hit.
+-- Will do a plane intersection if no terrain is touched.
+--
+-- mouse - Mouse to check the .hit for.
+--
+-- Return:
+-- cellPos - Cell position hit. Nil if none.
+function GetTerrainForMouse(mouse)
+ -- There was no target, so all it could be is a plane intersection.
+ -- Check for a plane intersection. If there isn't one then nothing will get hit.
+ local cell = game.Workspace.Terrain:WorldToCellPreferSolid(Vector3.new(mouse.hit.x, mouse.hit.y, mouse.hit.z))
+ local planeLoc = nil
+ -- If nothing was hit, do the plane intersection.
+ if 0 == game.Workspace.Terrain:GetCell(cell.X, cell.Y, cell.Z).Value then
+ cell = nil
+ planeLoc, hit = PlaneIntersection(Vector3.new(mouse.hit.x, mouse.hit.y, mouse.hit.z))
+ if hit then
+ cell = planeLoc
+ end
+ end
+ return cell
+end
+
+-- setup helper functions
+local insertBoundingBoxOverlapVector = Vector3.new(.3, .3, .3) -- we can still stamp if our character extrudes into the target stamping space by .3 or fewer units
+
+-- rotates a model by yAngle radians about the global y-axis
+local function rotatePartAndChildren(part, rotCF, offsetFromOrigin)
+ -- rotate this thing, if it's a part
+ if part:IsA("BasePart") then
+ part.CFrame = (rotCF * (part.CFrame - offsetFromOrigin)) + offsetFromOrigin
+ end
+
+ -- recursively do the same to all children
+ local partChildren = part:GetChildren()
+ for c = 1, #partChildren do rotatePartAndChildren(partChildren[c], rotCF, offsetFromOrigin) end
+end
+
+local function modelRotate(model, yAngle)
+ local rotCF = CFrame.Angles(0, yAngle, 0)
+ local offsetFromOrigin = model:GetModelCFrame().p
+
+ rotatePartAndChildren(model, rotCF, offsetFromOrigin)
+end
+
+
+local function collectParts(object, baseParts, scripts, decals)
+ if object:IsA("BasePart") then
+ baseParts[#baseParts+1] = object
+ elseif object:IsA("Script") then
+ scripts[#scripts+1] = object
+ elseif object:IsA("Decal") then
+ decals[#decals+1] = object
+ end
+
+ for index,child in pairs(object:GetChildren()) do
+ collectParts(child, baseParts, scripts, decals)
+ end
+end
+
+local function clusterPartsInRegion(startVector, endVector)
+ local cluster = game.Workspace:FindFirstChild("Terrain")
+
+ local startCell = cluster:WorldToCell(startVector)
+ local endCell = cluster:WorldToCell(endVector)
+
+ local startX = startCell.X
+ local startY = startCell.Y
+ local startZ = startCell.Z
+
+ local endX = endCell.X
+ local endY = endCell.Y
+ local endZ = endCell.Z
+
+ if startX < cluster.MaxExtents.Min.X then startX = cluster.MaxExtents.Min.X end
+ if startY < cluster.MaxExtents.Min.Y then startY = cluster.MaxExtents.Min.Y end
+ if startZ < cluster.MaxExtents.Min.Z then startZ = cluster.MaxExtents.Min.Z end
+
+ if endX > cluster.MaxExtents.Max.X then endX = cluster.MaxExtents.Max.X end
+ if endY > cluster.MaxExtents.Max.Y then endY = cluster.MaxExtents.Max.Y end
+ if endZ > cluster.MaxExtents.Max.Z then endZ = cluster.MaxExtents.Max.Z end
+
+ for x = startX, endX do
+ for y = startY, endY do
+ for z = startZ, endZ do
+ if (cluster:GetCell(x, y, z).Value) > 0 then return true end
+ end
+ end
+ end
+
+ return false
+end
+
+local function findSeatsInModel(parent, seatTable)
+ if not parent then return end
+
+ if parent.className == "Seat" or parent.className == "VehicleSeat" then
+ table.insert(seatTable, parent)
+ end
+ local myChildren = parent:GetChildren()
+ for j = 1, #myChildren do
+ findSeatsInModel(myChildren[j], seatTable)
+ end
+end
+
+local function setSeatEnabledStatus(model, isEnabled)
+ local seatList = {}
+ findSeatsInModel(model, seatList)
+
+ if isEnabled then
+ -- remove any welds called "SeatWeld" in seats
+ for i = 1, #seatList do
+ local nextSeat = seatList[i]:FindFirstChild("SeatWeld")
+ while nextSeat do nextSeat:Remove() nextSeat = seatList[i]:FindFirstChild("SeatWeld") end
+ end
+ else
+ -- put a weld called "SeatWeld" in every seat
+ -- this tricks it into thinking there's already someone sitting there, and it won't make you sit XD
+ for i = 1, #seatList do
+ local fakeWeld = Instance.new("Weld")
+ fakeWeld.Name = "SeatWeld"
+ fakeWeld.Parent = seatList[i]
+ end
+ end
+end
+
+local function autoAlignToFace(parts)
+ local aatf = parts:FindFirstChild("AutoAlignToFace")
+ if aatf then return aatf.Value else return false end
+end
+
+local function getClosestAlignedWorldDirection(aVector3InWorld)
+ local xDir = Vector3.new(1,0,0)
+ local yDir = Vector3.new(0,1,0)
+ local zDir = Vector3.new(0,0,1)
+ local xDot = aVector3InWorld.x * xDir.x + aVector3InWorld.y * xDir.y + aVector3InWorld.z * xDir.z
+ local yDot = aVector3InWorld.x * yDir.x + aVector3InWorld.y * yDir.y + aVector3InWorld.z * yDir.z
+ local zDot = aVector3InWorld.x * zDir.x + aVector3InWorld.y * zDir.y + aVector3InWorld.z * zDir.z
+
+ if math.abs(xDot) > math.abs(yDot) and math.abs(xDot) > math.abs(zDot) then
+ if xDot > 0 then
+ return 0
+ else
+ return 3
+ end
+ elseif math.abs(yDot) > math.abs(xDot) and math.abs(yDot) > math.abs(zDot) then
+ if yDot > 0 then
+ return 1
+ else
+ return 4
+ end
+ else
+ if zDot > 0 then
+ return 2
+ else
+ return 5
+ end
+ end
+end
+
+local function positionPartsAtCFrame3(aCFrame, currentParts)
+ local insertCFrame = nil
+ if not currentParts then return currentParts end
+ if currentParts and (currentParts:IsA("Model") or currentParts:IsA("Tool")) then
+ insertCFrame = currentParts:GetModelCFrame()
+ currentParts:TranslateBy(aCFrame.p - insertCFrame.p)
+ else
+ currentParts.CFrame = aCFrame
+ end
+ return currentParts
+end
+
+local function calcRayHitTime(rayStart, raySlope, intersectionPlane)
+ if math.abs(raySlope) < .01 then return 0 end -- 0 slope --> we just say intersection time is 0, and sidestep this dimension
+ return (intersectionPlane - rayStart) / raySlope
+end
+
+local function modelTargetSurface(partOrModel, rayStart, rayEnd)
+ if not partOrModel then
+ return 0
+ end
+
+ local modelCFrame = nil
+ local modelSize = nil
+ if partOrModel:IsA("Model") then
+ modelCFrame = partOrModel:GetModelCFrame()
+ modelSize = partOrModel:GetModelSize()
+ else
+ modelCFrame = partOrModel.CFrame
+ modelSize = partOrModel.Size
+ end
+
+ local mouseRayStart = modelCFrame:pointToObjectSpace(rayStart)
+ local mouseRayEnd = modelCFrame:pointToObjectSpace(rayEnd)
+ local mouseSlope = mouseRayEnd - mouseRayStart
+
+ local xPositive = 1
+ local yPositive = 1
+ local zPositive = 1
+ if mouseSlope.X > 0 then xPositive = -1 end
+ if mouseSlope.Y > 0 then yPositive = -1 end
+ if mouseSlope.Z > 0 then zPositive = -1 end
+
+ -- find which surface the transformed mouse ray hits (using modelSize):
+ local xHitTime = calcRayHitTime(mouseRayStart.X, mouseSlope.X, modelSize.X/2 * xPositive)
+ local yHitTime = calcRayHitTime(mouseRayStart.Y, mouseSlope.Y, modelSize.Y/2 * yPositive)
+ local zHitTime = calcRayHitTime(mouseRayStart.Z, mouseSlope.Z, modelSize.Z/2 * zPositive)
+
+ local hitFace = 0
+
+ --if xHitTime >= 0 and yHitTime >= 0 and zHitTime >= 0 then
+ if xHitTime > yHitTime then
+ if xHitTime > zHitTime then
+ -- xFace is hit
+ hitFace = 1*xPositive
+ else
+ -- zFace is hit
+ hitFace = 3*zPositive
+ end
+ else
+ if yHitTime > zHitTime then
+ -- yFace is hit
+ hitFace = 2*yPositive
+ else
+ -- zFace is hit
+ hitFace = 3*zPositive
+ end
+ end
+
+ return hitFace
+end
+
+local function getBoundingBox2(partOrModel)
+
+ -- for models, the bounding box is defined as the minimum and maximum individual part bounding boxes
+ -- relative to the first part's coordinate frame.
+ local minVec = Vector3.new(math.huge, math.huge, math.huge)
+ local maxVec = Vector3.new(-math.huge, -math.huge, -math.huge)
+
+ if partOrModel:IsA("Terrain") then
+ minVec = Vector3.new(-2, -2, -2)
+ maxVec = Vector3.new(2, 2, 2)
+ elseif partOrModel:IsA("BasePart") then
+ minVec = -0.5 * partOrModel.Size
+ maxVec = -minVec
+ else
+ maxVec = partOrModel:GetModelSize()*0.5
+ minVec = -maxVec
+ end
+
+ -- Adjust bounding box to reflect what the model or part author wants in terms of justification
+ local justifyValue = partOrModel:FindFirstChild("Justification")
+ if justifyValue ~= nil then
+ -- find the multiple of 4 that contains the model
+ justify = justifyValue.Value
+ two = Vector3.new(2, 2, 2)
+ actualBox = maxVec - minVec - Vector3.new(0.01, 0.01, 0.01)
+ containingGridBox = Vector3.new(4 * math.ceil(actualBox.x/4), 4 * math.ceil(actualBox.y/4), 4 * math.ceil(actualBox.z/4))
+ adjustment = containingGridBox - actualBox
+ minVec = minVec - 0.5 * adjustment * justify
+ maxVec = maxVec + 0.5 * adjustment * (two - justify)
+ end
+
+ return minVec, maxVec
+end
+
+local function getBoundingBoxInWorldCoordinates(partOrModel)
+ local minVec = Vector3.new(math.huge, math.huge, math.huge)
+ local maxVec = Vector3.new(-math.huge, -math.huge, -math.huge)
+
+ if partOrModel:IsA("BasePart") and not partOrModel:IsA("Terrain") then
+ vec1 = partOrModel.CFrame:pointToWorldSpace(-0.5 * partOrModel.Size)
+ vec2 = partOrModel.CFrame:pointToWorldSpace(0.5 * partOrModel.Size)
+ minVec = Vector3.new(math.min(vec1.X, vec2.X), math.min(vec1.Y, vec2.Y), math.min(vec1.Z, vec2.Z))
+ maxVec = Vector3.new(math.max(vec1.X, vec2.X), math.max(vec1.Y, vec2.Y), math.max(vec1.Z, vec2.Z))
+ elseif partOrModel:IsA("Terrain") then
+ -- we shouldn't have to deal with this case
+ --minVec = Vector3.new(-2, -2, -2)
+ --maxVec = Vector3.new(2, 2, 2)
+ else
+ vec1 = partOrModel:GetModelCFrame():pointToWorldSpace(-0.5 * partOrModel:GetModelSize())
+ vec2 = partOrModel:GetModelCFrame():pointToWorldSpace(0.5 * partOrModel:GetModelSize())
+ minVec = Vector3.new(math.min(vec1.X, vec2.X), math.min(vec1.Y, vec2.Y), math.min(vec1.Z, vec2.Z))
+ maxVec = Vector3.new(math.max(vec1.X, vec2.X), math.max(vec1.Y, vec2.Y), math.max(vec1.Z, vec2.Z))
+ end
+
+ return minVec, maxVec
+end
+
+local function getTargetPartBoundingBox(targetPart)
+ if targetPart.Parent:FindFirstChild("RobloxModel") ~= nil then
+ return getBoundingBox2(targetPart.Parent)
+ else
+ return getBoundingBox2(targetPart)
+ end
+end
+
+local function getMouseTargetCFrame(targetPart)
+ if targetPart.Parent:FindFirstChild("RobloxModel") ~= nil then
+ if targetPart.Parent:IsA("Tool") then return targetPart.Parent.Handle.CFrame
+ else return targetPart.Parent:GetModelCFrame() end
+ else
+ return targetPart.CFrame
+ end
+end
+
+local function isBlocker(part) -- returns whether or not we want to cancel the stamp because we're blocked by this part
+ if not part then return false end
+ if not part.Parent then return false end
+ if part:FindFirstChild("Humanoid") then return false end
+ if part:FindFirstChild("RobloxStamper") or part:FindFirstChild("RobloxModel") then return true end
+ if part:IsA("Part") and not part.CanCollide then return false end
+ if part == game.Lighting then return false end
+ return isBlocker(part.Parent)
+end
+
+-- helper function to determine if a character can be pushed upwards by a certain amount
+-- character is 5 studs tall, we'll check a 1.5 x 1.5 x 4.5 box around char, with center .5 studs below torsocenter
+local function spaceAboveCharacter(charTorso, newTorsoY, stampData)
+ local partsAboveChar = game.Workspace:FindPartsInRegion3(
+ Region3.new(Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) - Vector3.new(.75, 2.75, .75),
+ Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) + Vector3.new(.75, 1.75, .75)),
+ charTorso.Parent,
+ 100)
+
+ for j = 1, #partsAboveChar do
+ if partsAboveChar[j].CanCollide and not partsAboveChar[j]:IsDescendantOf(stampData.CurrentParts) then return false end
+ end
+
+ if clusterPartsInRegion(Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) - Vector3.new(.75, 2.75, .75),
+ Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) + Vector3.new(.75, 1.75, .75)) then
+ return false
+ end
+
+ return true
+end
+
+
+local function findConfigAtMouseTarget(Mouse, stampData)
+ -- *Critical Assumption* :
+ -- This function assumes the target CF axes are orthogonal with the target bounding box faces
+ -- And, it assumes the insert CF axes are orthongonal with the insert bounding box faces
+ -- Therefore, insertion will not work with angled faces on wedges or other "non-block" parts, nor
+ -- will it work for parts in a model that are not orthogonally aligned with the model's CF.
+
+ if not Mouse then return nil end -- This can happen sometimes, return if so
+ if not stampData then error("findConfigAtMouseTarget: stampData is nil") return nil end
+ if not stampData["CurrentParts"] then return nil end
+
+ local grid = 4.0
+ local admissibleConfig = false
+ local targetConfig = CFrame.new(0,0,0)
+
+ local minBB, maxBB = getBoundingBox2(stampData.CurrentParts)
+ local diagBB = maxBB - minBB
+
+ local insertCFrame
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ insertCFrame = stampData.CurrentParts:GetModelCFrame()
+ else
+ insertCFrame = stampData.CurrentParts.CFrame
+ end
+
+ if Mouse then
+ if stampData.CurrentParts:IsA("Tool") then
+ Mouse.TargetFilter = stampData.CurrentParts.Handle
+ else
+ Mouse.TargetFilter = stampData.CurrentParts
+ end
+ end
+
+ local hitPlane = false
+ local targetPart = nil
+ local success = pcall(function() targetPart = Mouse.Target end)
+
+ if not success then-- or targetPart == nil then
+ return admissibleConfig, targetConfig
+ end
+
+ local mouseHitInWorld = Vector3.new(0, 0, 0)
+ if Mouse then
+ mouseHitInWorld = Vector3.new(Mouse.Hit.x, Mouse.Hit.y, Mouse.Hit.z)
+ end
+
+ local cellPos = nil
+
+ -- Nothing was hit, so check for the default plane.
+ if nil == targetPart then
+ cellPos = GetTerrainForMouse(Mouse)
+ if nil == cellPos then
+ hitPlane = false
+ return admissibleConfig, targetConfig
+ else
+ targetPart = game.Workspace.Terrain
+ hitPlane = true
+ -- Take into account error that will occur.
+ cellPos = Vector3.new(cellPos.X - 1, cellPos.Y, cellPos.Z)
+ mouseHitInWorld = game.Workspace.Terrain:CellCenterToWorld(cellPos.x, cellPos.y, cellPos.z)
+ end
+ end
+
+ -- test mouse hit location
+ local minBBTarget, maxBBTarget = getTargetPartBoundingBox(targetPart)
+ local diagBBTarget = maxBBTarget - minBBTarget
+ local targetCFrame = getMouseTargetCFrame(targetPart)
+
+ if targetPart:IsA("Terrain") then
+ if not cluster then cluster = game.Workspace:FindFirstChild("Terrain") end
+ local cellID = cluster:WorldToCellPreferSolid(mouseHitInWorld)
+ if hitPlane then
+ cellID = cellPos
+ end
+
+ targetCFrame = CFrame.new(game.Workspace.Terrain:CellCenterToWorld(cellID.x, cellID.y, cellID.z))
+ end
+
+ local mouseHitInTarget = targetCFrame:pointToObjectSpace(mouseHitInWorld)
+ local targetVectorInWorld = Vector3.new(0,0,0)
+ if Mouse then
+ -- DON'T WANT THIS IN TERMS OF THE MODEL CFRAME! (.TargetSurface is in terms of the part CFrame, so this would break, right? [HotThoth])
+ -- (ideally, we would want to make the Mouse.TargetSurface a model-targetsurface instead, but for testing will be using the converse)
+ --targetVectorInWorld = targetCFrame:vectorToWorldSpace(Vector3.FromNormalId(Mouse.TargetSurface))
+ targetVectorInWorld = targetPart.CFrame:vectorToWorldSpace(Vector3.FromNormalId(Mouse.TargetSurface)) -- better, but model cframe would be best
+ --[[if targetPart.Parent:IsA("Model") then
+ local hitFace = modelTargetSurface(targetPart.Parent, Mouse.Hit.p, game.Workspace.CurrentCamera.CoordinateFrame.p) -- best, if you get it right
+ local WORLD_AXES = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)}
+ if hitFace > 0 then
+ targetVectorInWorld = targetCFrame:vectorToWorldSpace(WORLD_AXES[hitFace])
+ elseif hitFace < 0 then
+ targetVectorInWorld = targetCFrame:vectorToWorldSpace(-WORLD_AXES[-hitFace])
+ end
+ end]]
+ end
+
+ local targetRefPointInTarget
+ local clampToSurface
+
+ if getClosestAlignedWorldDirection(targetVectorInWorld) == 0 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ clampToSurface = Vector3.new(0,1,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 3 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, -1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(1, -1, -1))
+ clampToSurface = Vector3.new(0,1,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 1 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, 1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ clampToSurface = Vector3.new(1,0,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 4 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, 1, 1))
+ clampToSurface = Vector3.new(1,0,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 2 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, -1))
+ clampToSurface = Vector3.new(1,1,0)
+ else
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(1, -1, -1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(1, -1, 1))
+ clampToSurface = Vector3.new(1,1,0)
+ end
+
+ targetRefPointInTarget = targetRefPointInTarget * (0.5 * diagBBTarget) + 0.5 * (maxBBTarget + minBBTarget)
+ insertRefPointInInsert = insertRefPointInInsert * (0.5 * diagBB) + 0.5 * (maxBB + minBB)
+
+ -- To Do: For cases that are not aligned to the world grid, account for the minimal rotation
+ -- needed to bring the Insert part(s) into alignment with the Target Part
+ -- Apply the rotation here
+
+ local delta = mouseHitInTarget - targetRefPointInTarget
+ local deltaClamped = Vector3.new(grid * math.modf(delta.x/grid), grid * math.modf(delta.y/grid), grid * math.modf(delta.z/grid))
+ deltaClamped = deltaClamped * clampToSurface
+ local targetTouchInTarget = deltaClamped + targetRefPointInTarget
+
+ local TargetTouchRelToWorld = targetCFrame:pointToWorldSpace(targetTouchInTarget)
+ local InsertTouchInWorld = insertCFrame:vectorToWorldSpace(insertRefPointInInsert)
+ local posInsertOriginInWorld = TargetTouchRelToWorld - InsertTouchInWorld
+
+ local x, y, z, R00, R01, R02, R10, R11, R12, R20, R21, R22 = insertCFrame:components()
+ targetConfig = CFrame.new(posInsertOriginInWorld.x, posInsertOriginInWorld.y, posInsertOriginInWorld.z, R00, R01, R02, R10, R11, R12, R20, R21, R22)
+ admissibleConfig = true
+
+ return admissibleConfig, targetConfig, getClosestAlignedWorldDirection(targetVectorInWorld)
+end
+
+local function truncateToCircleEighth(bigValue, littleValue)
+ local big = math.abs(bigValue)
+ local little = math.abs(littleValue)
+ local hypotenuse = math.sqrt(big*big + little*little)
+ local frac = little / hypotenuse
+
+ local bigSign = 1
+ local littleSign = 1
+ if bigValue < 0 then bigSign = -1 end
+ if littleValue < 0 then littleSign = -1 end
+
+ if frac > .382683432 then
+ -- between 22.5 and 45 degrees, so truncate to 45-degree tilt
+ return .707106781 * hypotenuse * bigSign, .707106781 * hypotenuse * littleSign
+ else
+ -- between 0 and 22.5 degrees, so truncate to 0-degree tilt
+ return hypotenuse * bigSign, 0
+ end
+end
+
+
+local function saveTheWelds(object, manualWeldTable, manualWeldParentTable)
+ if object:IsA("ManualWeld") or object:IsA("Rotate") then
+ table.insert(manualWeldTable, object)
+ table.insert(manualWeldParentTable, object.Parent)
+ else
+ local children = object:GetChildren()
+ for i = 1, #children do
+ saveTheWelds(children[i], manualWeldTable, manualWeldParentTable)
+ end
+ end
+end
+
+local function restoreTheWelds(manualWeldTable, manualWeldParentTable)
+ for i = 1, #manualWeldTable do
+ manualWeldTable[i].Parent = manualWeldParentTable[i]
+ end
+end
+
+t.CanEditRegion = function(partOrModel, EditRegion) -- todo: use model and stamper metadata
+ if not EditRegion then return true, false end
+
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(partOrModel)
+
+ if minBB.X < EditRegion.CFrame.p.X - EditRegion.Size.X/2 or
+ minBB.Y < EditRegion.CFrame.p.Y - EditRegion.Size.Y/2 or
+ minBB.Z < EditRegion.CFrame.p.Z - EditRegion.Size.Z/2 then
+ return false, false
+ end
+
+ if maxBB.X > EditRegion.CFrame.p.X + EditRegion.Size.X/2 or
+ maxBB.Y > EditRegion.CFrame.p.Y + EditRegion.Size.Y/2 or
+ maxBB.Z > EditRegion.CFrame.p.Z + EditRegion.Size.Z/2 then
+ return false, false
+ end
+
+ return true, false
+end
+
+t.GetStampModel = function(assetId, terrainShape, useAssetVersionId)
+ if assetId == 0 then
+ return nil, "No Asset"
+ end
+ if assetId < 0 then
+ return nil, "Negative Asset"
+ end
+
+ local function UnlockInstances(object)
+ if object:IsA("BasePart") then
+ object.Locked = false
+ end
+ for index,child in pairs(object:GetChildren()) do
+ UnlockInstances(child)
+ end
+ end
+
+ local function getClosestColorToTerrainMaterial(terrainValue)
+ if terrainValue == 1 then
+ return BrickColor.new("Bright green")
+ elseif terrainValue == 2 then
+ return BrickColor.new("Bright yellow")
+ elseif terrainValue == 3 then
+ return BrickColor.new("Bright red")
+ elseif terrainValue == 4 then
+ return BrickColor.new("Sand red")
+ elseif terrainValue == 5 then
+ return BrickColor.new("Black")
+ elseif terrainValue == 6 then
+ return BrickColor.new("Dark stone grey")
+ elseif terrainValue == 7 then
+ return BrickColor.new("Sand blue")
+ elseif terrainValue == 8 then
+ return BrickColor.new("Deep orange")
+ elseif terrainValue == 9 then
+ return BrickColor.new("Dark orange")
+ elseif terrainValue == 10 then
+ return BrickColor.new("Reddish brown")
+ elseif terrainValue == 11 then
+ return BrickColor.new("Light orange")
+ elseif terrainValue == 12 then
+ return BrickColor.new("Light stone grey")
+ elseif terrainValue == 13 then
+ return BrickColor.new("Sand green")
+ elseif terrainValue == 14 then
+ return BrickColor.new("Medium stone grey")
+ elseif terrainValue == 15 then
+ return BrickColor.new("Really red")
+ elseif terrainValue == 16 then
+ return BrickColor.new("Really blue")
+ elseif terrainValue == 17 then
+ return BrickColor.new("Bright blue")
+ else
+ return BrickColor.new("Bright green")
+ end
+ end
+
+ local function setupFakeTerrainPart(cellMat, cellType, cellOrient)
+ local newTerrainPiece = nil
+ if (cellType == 1 or cellType == 4) then newTerrainPiece = Instance.new("WedgePart") newTerrainPiece.formFactor = "Custom"
+ elseif (cellType == 2) then newTerrainPiece = Instance.new("CornerWedgePart")
+ else newTerrainPiece = Instance.new("Part") newTerrainPiece.formFactor = "Custom" end
+ newTerrainPiece.Name = "MegaClusterCube"
+ newTerrainPiece.Size = Vector3.new(4, 4, 4)
+ newTerrainPiece.BottomSurface = "Smooth"
+ newTerrainPiece.TopSurface = "Smooth"
+
+ -- can add decals or textures here if feeling particularly adventurous... for now, can make a table of look-up colors
+ newTerrainPiece.BrickColor = getClosestColorToTerrainMaterial(cellMat)
+
+ local sideways = 0
+ local flipped = math.pi
+ if cellType == 4 then sideways = -math.pi/2 end
+ if cellType == 2 or cellType == 3 then flipped = 0 end
+ newTerrainPiece.CFrame = CFrame.Angles(0, math.pi/2*cellOrient + flipped, sideways)
+
+ if cellType == 3 then
+ local inverseCornerWedgeMesh = Instance.new("SpecialMesh")
+ inverseCornerWedgeMesh.MeshType = "FileMesh"
+ inverseCornerWedgeMesh.MeshId = "http://www.roblox.com/asset/?id=66832495"
+ inverseCornerWedgeMesh.Scale = Vector3.new(2, 2, 2)
+ inverseCornerWedgeMesh.Parent = newTerrainPiece
+ end
+
+ local materialTag = Instance.new("Vector3Value")
+ materialTag.Value = Vector3.new(cellMat, cellType, cellOrient)
+ materialTag.Name = "ClusterMaterial"
+ materialTag.Parent = newTerrainPiece
+
+ return newTerrainPiece
+ end
+
+ -- This call will cause a "wait" until the data comes back
+ -- below we wait a max of 8 seconds before deciding to bail out on loading
+ local root
+ local loader
+ loading = true
+ if useAssetVersionId then
+ loader = coroutine.create(function()
+ root = game:GetService("InsertService"):LoadAssetVersion(assetId)
+ loading = false
+ end)
+ coroutine.resume(loader)
+ else
+ loader = coroutine.create(function()
+ root = game:GetService("InsertService"):LoadAsset(assetId)
+ loading = false
+ end)
+ coroutine.resume(loader)
+ end
+
+ local lastGameTime = 0
+ local totalTime = 0
+ local maxWait = 8
+ while loading and totalTime < maxWait do
+ lastGameTime = tick()
+ wait(1)
+ totalTime = totalTime + tick() - lastGameTime
+ end
+ loading = false
+
+ if totalTime >= maxWait then
+ return nil, "Load Time Fail"
+ end
+
+
+ if root == nil then
+ return nil, "Load Asset Fail"
+ end
+
+ if not root:IsA("Model") then
+ return nil, "Load Type Fail"
+ end
+
+ local instances = root:GetChildren()
+ if #instances == 0 then
+ return nil, "Empty Model Fail"
+ end
+
+ --Unlock all parts that are inserted, to make sure they are editable
+ UnlockInstances(root)
+
+ --Continue the insert process
+ root = root:GetChildren()[1]
+
+ --Examine the contents and decide what it looks like
+ for pos, instance in pairs(instances) do
+ if instance:IsA("Team") then
+ instance.Parent = game:GetService("Teams")
+ elseif instance:IsA("Sky") then
+ local lightingService = game:GetService("Lighting")
+ for index,child in pairs(lightingService:GetChildren()) do
+ if child:IsA("Sky") then
+ child:Remove();
+ end
+ end
+ instance.Parent = lightingService
+ return
+ end
+ end
+
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if root:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", root)
+ stringTag.Name = "RobloxModel"
+
+ if root:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", root)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ if terrainShape then
+ if root.Name == "MegaClusterCube" then
+ if (terrainShape == 6) then -- insert an autowedging tag
+ local autowedgeTag = Instance.new("BoolValue")
+ autowedgeTag.Name = "AutoWedge"
+ autowedgeTag.Parent = root
+ else
+ local clusterTag = root:FindFirstChild("ClusterMaterial")
+ if clusterTag then
+ if clusterTag:IsA("Vector3Value") then
+ root = setupFakeTerrainPart(clusterTag.Value.X, terrainShape, clusterTag.Value.Z)
+ else
+ root = setupFakeTerrainPart(clusterTag.Value, terrainShape, 0)
+ end
+ else
+ root = setupFakeTerrainPart(1, terrainShape, 0)
+ end
+ end
+ end
+ end
+
+ return root
+end
+
+
+
+t.SetupStamperDragger = function(modelToStamp, Mouse, StampInModel, AllowedStampRegion, StampFailedFunc)
+ if not modelToStamp then
+ error("SetupStamperDragger: modelToStamp (first arg) is nil! Should be a stamper model")
+ return nil
+ end
+ if not modelToStamp:IsA("Model") and not modelToStamp:IsA("BasePart") then
+ error("SetupStamperDragger: modelToStamp (first arg) is neither a Model or Part!")
+ return nil
+ end
+ if not Mouse then
+ error("SetupStamperDragger: Mouse (second arg) is nil! Should be a mouse object")
+ return nil
+ end
+ if not Mouse:IsA("Mouse") then
+ error("SetupStamperDragger: Mouse (second arg) is not of type Mouse!")
+ return nil
+ end
+
+ local stampInModel = nil
+ local allowedStampRegion = nil
+ local stampFailedFunc = nil
+ if StampInModel then
+ if not StampInModel:IsA("Model") then
+ error("SetupStamperDragger: StampInModel (optional third arg) is not of type 'Model'")
+ return nil
+ end
+ if not AllowedStampRegion then
+ error("SetupStamperDragger: AllowedStampRegion (optional fourth arg) is nil when StampInModel (optional third arg) is defined")
+ return nil
+ end
+ stampFailedFunc = StampFailedFunc
+ stampInModel = StampInModel
+ allowedStampRegion = AllowedStampRegion
+ end
+
+ -- Init all state variables
+ local gInitial90DegreeRotations = 0
+ local stampData = nil
+ local mouseTarget = nil
+
+ local errorBox = Instance.new("SelectionBox")
+ errorBox.Color = BrickColor.new("Bright red")
+ errorBox.Transparency = 0
+ errorBox.Archivable = false
+
+ -- for megacluster MEGA STAMPING
+ local adornPart = Instance.new("Part")
+ adornPart.Parent = nil
+ adornPart.formFactor = "Custom"
+ adornPart.Size = Vector3.new(4, 4, 4)
+ adornPart.CFrame = CFrame.new()
+ adornPart.Archivable = false
+
+ local adorn = Instance.new("SelectionBox")
+ adorn.Color = BrickColor.new("Toothpaste")
+ adorn.Adornee = adornPart
+ adorn.Visible = true
+ adorn.Transparency = 0
+ adorn.Name = "HighScalabilityStamperLine"
+ adorn.Archivable = false
+
+ local HighScalabilityLine = {}
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.End = nil
+ HighScalabilityLine.Adorn = adorn
+ HighScalabilityLine.AdornPart = adornPart
+ HighScalabilityLine.InternalLine = nil
+ HighScalabilityLine.NewHint = true
+
+ HighScalabilityLine.MorePoints = {nil, nil}
+ HighScalabilityLine.MoreLines = {nil, nil}
+ HighScalabilityLine.Dimensions = 1
+
+ local control = {}
+ local movingLock = false
+ local stampUpLock = false
+ local unstampableSurface = false
+ local mouseCons = {}
+ local keyCon = nil
+
+ local stamped = Instance.new("BoolValue")
+ stamped.Archivable = false
+ stamped.Value = false
+
+ local lastTarget = {}
+ lastTarget.TerrainOrientation = 0
+ lastTarget.CFrame = 0
+
+ local cellInfo = {}
+ cellInfo.Material = 1
+ cellInfo.clusterType = 0
+ cellInfo.clusterOrientation = 0
+
+ local function isMegaClusterPart()
+ if not stampData then return false end
+ if not stampData.CurrentParts then return false end
+
+ return ( stampData.CurrentParts:FindFirstChild("ClusterMaterial",true) or (stampData.CurrentParts.Name == "MegaClusterCube") )
+ end
+
+ local function DoHighScalabilityRegionSelect()
+ local megaCube = stampData.CurrentParts:FindFirstChild("MegaClusterCube")
+ if not megaCube then
+ if not stampData.CurrentParts.Name == "MegaClusterCube" then
+ return
+ else
+ megaCube = stampData.CurrentParts
+ end
+ end
+
+ HighScalabilityLine.End = megaCube.CFrame.p
+ local line = nil
+ local line2 = Vector3.new(0, 0, 0)
+ local line3 = Vector3.new(0, 0, 0)
+
+ if HighScalabilityLine.Dimensions == 1 then
+ -- extract the line from these positions and limit to a 2D plane made from 2 of the world axes
+ -- then use dominating axis to limit line to be at 45-degree intervals
+ -- will use this internal representation of the line for the actual stamping
+ line = (HighScalabilityLine.End - HighScalabilityLine.Start)
+
+ if math.abs(line.X) < math.abs(line.Y) then
+ if math.abs(line.X) < math.abs(line.Z) then
+ -- limit to Y/Z plane, domination unknown
+ local newY, newZ
+ if (math.abs(line.Y) > math.abs(line.Z)) then
+ newY, newZ = truncateToCircleEighth(line.Y, line.Z)
+ else
+ newZ, newY = truncateToCircleEighth(line.Z, line.Y)
+ end
+ line = Vector3.new(0, newY, newZ)
+ else
+ -- limit to X/Y plane, with Y dominating
+ local newY, newX = truncateToCircleEighth(line.Y, line.X)
+ line = Vector3.new(newX, newY, 0)
+ end
+ else
+ if math.abs(line.Y) < math.abs(line.Z) then
+ -- limit to X/Z plane, domination unknown
+ local newX, newZ
+ if math.abs(line.X) > math.abs(line.Z) then
+ newX, newZ = truncateToCircleEighth(line.X, line.Z)
+ else
+ newZ, newX = truncateToCircleEighth(line.Z, line.X)
+ end
+ line = Vector3.new(newX, 0, newZ)
+ else
+ -- limit to X/Y plane, with X dominating
+ local newX, newY = truncateToCircleEighth(line.X, line.Y)
+ line = Vector3.new(newX, newY, 0)
+ end
+ end
+ HighScalabilityLine.InternalLine = line
+
+ elseif HighScalabilityLine.Dimensions == 2 then
+ line = HighScalabilityLine.MoreLines[1]
+ line2 = HighScalabilityLine.End - HighScalabilityLine.MorePoints[1]
+
+ -- take out any component of line2 along line1, so you get perpendicular to line1 component
+ line2 = line2 - line.unit*line.unit:Dot(line2)
+
+ tempCFrame = CFrame.new(HighScalabilityLine.Start, HighScalabilityLine.Start + line)
+
+ -- then zero out whichever is the smaller component
+ local yAxis = tempCFrame:vectorToWorldSpace(Vector3.new(0, 1, 0))
+ local xAxis = tempCFrame:vectorToWorldSpace(Vector3.new(1, 0, 0))
+
+ local xComp = xAxis:Dot(line2)
+ local yComp = yAxis:Dot(line2)
+
+ if math.abs(yComp) > math.abs(xComp) then
+ line2 = line2 - xAxis * xComp
+ else
+ line2 = line2 - yAxis * yComp
+ end
+
+ HighScalabilityLine.InternalLine = line2
+
+ elseif HighScalabilityLine.Dimensions == 3 then
+ line = HighScalabilityLine.MoreLines[1]
+ line2 = HighScalabilityLine.MoreLines[2]
+ line3 = HighScalabilityLine.End - HighScalabilityLine.MorePoints[2]
+
+ -- zero out all components of previous lines
+ line3 = line3 - line.unit * line.unit:Dot(line3)
+ line3 = line3 - line2.unit * line2.unit:Dot(line3)
+
+ HighScalabilityLine.InternalLine = line3
+ end
+
+ -- resize the "line" graphic to be the correct size and orientation
+ tempCFrame = CFrame.new(HighScalabilityLine.Start, HighScalabilityLine.Start + line)
+
+ if HighScalabilityLine.Dimensions == 1 then -- faster calculation for line
+ HighScalabilityLine.AdornPart.Size = Vector3.new(4, 4, line.magnitude + 4)
+ HighScalabilityLine.AdornPart.CFrame = tempCFrame + tempCFrame:vectorToWorldSpace(Vector3.new(2, 2, 2) - HighScalabilityLine.AdornPart.Size/2)
+ else
+ local boxSize = tempCFrame:vectorToObjectSpace(line + line2 + line3)
+ HighScalabilityLine.AdornPart.Size = Vector3.new(4, 4, 4) + Vector3.new(math.abs(boxSize.X), math.abs(boxSize.Y), math.abs(boxSize.Z))
+ HighScalabilityLine.AdornPart.CFrame = tempCFrame + tempCFrame:vectorToWorldSpace(boxSize/2)
+ end
+
+ -- make player able to see this ish
+
+ local gui = nil
+ if game.Players["LocalPlayer"] then
+ gui = game.Players.LocalPlayer:FindFirstChild("PlayerGui")
+ if gui and gui:IsA("PlayerGui") then
+ if HighScalabilityLine.Dimensions == 1 and line.magnitude > 3 then -- don't show if mouse hasn't moved enough
+ HighScalabilityLine.Adorn.Parent = gui
+ elseif HighScalabilityLine.Dimensions > 1 then
+ HighScalabilityLine.Adorn.Parent = gui
+ end
+ end
+ end
+
+ if gui == nil then -- we are in studio
+ gui = game:GetService("CoreGui")
+ if HighScalabilityLine.Dimensions == 1 and line.magnitude > 3 then -- don't show if mouse hasn't moved enough
+ HighScalabilityLine.Adorn.Parent = gui
+ elseif HighScalabilityLine.Dimensions > 1 then
+ HighScalabilityLine.Adorn.Parent = gui
+ end
+ end
+ end
+
+
+ local function DoStamperMouseMove(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseMove: Mouse is nil")
+ return
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseMove: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return
+ end
+
+ -- There wasn't a target (no part or terrain), so check for plane intersection.
+ if not Mouse.Target then
+ local cellPos = GetTerrainForMouse(Mouse)
+ if nil == cellPos then
+ return
+ end
+ end
+
+ if not stampData then
+ return
+ end
+
+ -- don't move with dragger - will move in one step on mouse down
+ -- draw ghost at acceptable positions
+ configFound, targetCFrame, targetSurface = findConfigAtMouseTarget(Mouse, stampData)
+ if not configFound then
+ error("RbxStamper.DoStamperMouseMove No configFound, returning")
+ return
+ end
+
+ local numRotations = 0 -- update this according to how many rotations you need to get it to target surface
+ if autoAlignToFace(stampData.CurrentParts) and targetSurface ~= 1 and targetSurface ~= 4 then -- pre-rotate the flag or portrait so it's aligned correctly
+ if targetSurface == 3 then numRotations = 0 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 0 then numRotations = 2 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 5 then numRotations = 3 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 2 then numRotations = 1 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ end
+ end
+
+ local ry = math.pi/2
+ gInitial90DegreeRotations = gInitial90DegreeRotations + numRotations
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry*numRotations, 0)
+ modelRotate(stampData.CurrentParts, ry*numRotations)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry*numRotations, 0) * stampData.CurrentParts.CFrame
+ end
+
+ -- CODE TO CHECK FOR DRAGGING GHOST PART INTO A COLLIDING STATE
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(stampData.CurrentParts)
+
+ -- need to offset by distance to be dragged
+ local currModelCFrame = nil
+ if stampData.CurrentParts:IsA("Model") then
+ currModelCFrame = stampData.CurrentParts:GetModelCFrame()
+ else
+ currModelCFrame = stampData.CurrentParts.CFrame
+ end
+
+ minBB = minBB + targetCFrame.p - currModelCFrame.p
+ maxBB = maxBB + targetCFrame.p - currModelCFrame.p
+
+ -- don't drag into terrain
+ if clusterPartsInRegion(minBB + insertBoundingBoxOverlapVector, maxBB - insertBoundingBoxOverlapVector) then
+ if lastTarget.CFrame then
+ if (stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)) then
+ local theClusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if theClusterMaterial:IsA("Vector3Value") then
+ local stampClusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if stampClusterMaterial then
+ stampClusterMaterial = clusterMat
+ end
+ end
+ end
+ end
+ return
+ end
+
+ -- if we are stamping a terrain part, make sure it goes on the grid! Otherwise preview block could be placed off grid, but stamped on grid
+ if isMegaClusterPart() then
+ local cellToStamp = game.Workspace.Terrain:WorldToCell(targetCFrame.p)
+ local newCFramePosition = game.Workspace.Terrain:CellCenterToWorld(cellToStamp.X, cellToStamp.Y, cellToStamp.Z)
+ local x, y, z, R00, R01, R02, R10, R11, R12, R20, R21, R22 = targetCFrame:components()
+ targetCFrame = CFrame.new(newCFramePosition.X,newCFramePosition.Y,newCFramePosition.Z,R00, R01, R02, R10, R11, R12, R20, R21, R22)
+ end
+
+ positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+ lastTarget.CFrame = targetCFrame -- successful positioning, so update 'dat cframe
+ if stampData.CurrentParts:FindFirstChild("ClusterMaterial", true) then
+ local clusterMat = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMat:IsA("Vector3Value") then
+ lastTarget.TerrainOrientation = clusterMat.Value.Z
+ end
+ end
+
+
+ -- auto break joints code
+ if Mouse and Mouse.Target and Mouse.Target.Parent then
+ local modelInfo = Mouse.Target:FindFirstChild("RobloxModel")
+ if not modelInfo then modelInfo = Mouse.Target.Parent:FindFirstChild("RobloxModel") end
+
+ local myModelInfo = stampData.CurrentParts:FindFirstChild("UnstampableFaces")
+
+ --if (modelInfo and modelInfo.Parent:FindFirstChild("UnstampableFaces")) or (modelInfo and myModelInfo) then -- need better targetSurface calcs
+ if (true) then
+ local breakingFaces = ""
+ local myBreakingFaces = ""
+ if modelInfo and modelInfo.Parent:FindFirstChild("UnstampableFaces") then breakingFaces = modelInfo.Parent.UnstampableFaces.Value end
+ if myModelInfo then myBreakingFaces = myModelInfo.Value end
+ local hitFace = 0
+
+ if modelInfo then hitFace = modelTargetSurface(modelInfo.Parent, game.Workspace.CurrentCamera.CoordinateFrame.p, Mouse.Hit.p) end
+
+ -- are we stamping TO an unstampable surface?
+ for bf in string.gmatch(breakingFaces, "[^,]+") do
+ if hitFace == tonumber(bf) then
+ -- return before we hit the JointsService code below!
+ unstampableSurface = true
+ game.JointsService:ClearJoinAfterMoveJoints() -- clear the JointsService cache
+ return
+ end
+ end
+
+ -- now we have to cast the ray back in the other direction to find the surface we're stamping FROM
+ hitFace = modelTargetSurface(stampData.CurrentParts, Mouse.Hit.p, game.Workspace.CurrentCamera.CoordinateFrame.p)
+
+ -- are we stamping WITH an unstampable surface?
+ for bf in string.gmatch(myBreakingFaces, "[^,]+") do
+ if hitFace == tonumber(bf) then
+ unstampableSurface = true
+ game.JointsService:ClearJoinAfterMoveJoints() -- clear the JointsService cache
+ return
+ end
+ end
+
+ -- just need to match breakingFace against targetSurface using rotation supplied by modelCFrame
+ -- targetSurface: 1 is top, 4 is bottom,
+ end
+ end
+
+ -- to show joints during the mouse move
+ unstampableSurface = false
+ game.JointsService:SetJoinAfterMoveInstance(stampData.CurrentParts)
+
+ -- most common mouse inactive error occurs here, so check mouse active one more time in a pcall
+ if not pcall(function()
+ if Mouse and Mouse.Target and Mouse.Target.Parent:FindFirstChild("RobloxModel") == nil then
+ return
+ else
+ return
+ end
+ end)
+ then
+ error("Error: RbxStamper.DoStamperMouseMove Mouse is nil on second check")
+ game.JointsService:ClearJoinAfterMoveJoints()
+ Mouse = nil
+ return
+ end
+
+ if Mouse and Mouse.Target and Mouse.Target.Parent:FindFirstChild("RobloxModel") == nil then
+ game.JointsService:SetJoinAfterMoveTarget(Mouse.Target)
+ else
+ game.JointsService:SetJoinAfterMoveTarget(nil)
+ end
+ game.JointsService:ShowPermissibleJoints()
+
+ -- here we allow for a line of high-scalability parts
+ if isMegaClusterPart() and HighScalabilityLine and HighScalabilityLine.Start then
+ DoHighScalabilityRegionSelect()
+ end
+ end
+
+ local function setupKeyListener(key, Mouse)
+ if control and control["Paused"] then return end -- don't do this if we have no stamp
+
+ key = string.lower(key)
+ if key == 'r' and not autoAlignToFace(stampData.CurrentParts) then -- rotate the model
+ gInitial90DegreeRotations = gInitial90DegreeRotations + 1
+
+ -- Update orientation value if this is a fake terrain part
+ local clusterValues = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterValues and clusterValues:IsA("Vector3Value") then
+ clusterValues.Value = Vector3.new(clusterValues.Value.X, clusterValues.Value.Y, (clusterValues.Value.Z + 1) % 4)
+ end
+
+ -- Rotate the parts or all the parts in the model
+ local ry = math.pi/2
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry, 0)
+ modelRotate(stampData.CurrentParts, ry)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry, 0) * stampData.CurrentParts.CFrame
+ end
+
+ -- After rotating, update the position
+ configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+ if configFound then
+ positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+
+ -- update everything else in MouseMove
+ DoStamperMouseMove(Mouse)
+ end
+ elseif key == 'c' then -- try to expand our high scalability dragger dimension
+ if HighScalabilityLine.InternalLine and HighScalabilityLine.InternalLine.magnitude > 0 and HighScalabilityLine.Dimensions < 3 then
+ HighScalabilityLine.MorePoints[HighScalabilityLine.Dimensions] = HighScalabilityLine.End
+ HighScalabilityLine.MoreLines[HighScalabilityLine.Dimensions] = HighScalabilityLine.InternalLine
+ HighScalabilityLine.Dimensions = HighScalabilityLine.Dimensions + 1
+ HighScalabilityLine.NewHint = true
+ end
+ end
+ end
+
+ keyCon = Mouse.KeyDown:connect(function(key) -- init key connection (keeping code close to func)
+ setupKeyListener(key, Mouse)
+ end)
+
+ local function resetHighScalabilityLine()
+ if HighScalabilityLine then
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.End = nil
+ HighScalabilityLine.InternalLine = nil
+ HighScalabilityLine.NewHint = true
+ end
+ end
+
+ local function flashRedBox()
+ local gui = game.CoreGui
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer:FindFirstChild("PlayerGui") then
+ gui = game.Players.LocalPlayer.PlayerGui
+ end
+ end
+ end
+ if not stampData["ErrorBox"] then return end
+
+ stampData.ErrorBox.Parent = gui
+ if stampData.CurrentParts:IsA("Tool") then
+ stampData.ErrorBox.Adornee = stampData.CurrentParts.Handle
+ else
+ stampData.ErrorBox.Adornee = stampData.CurrentParts
+ end
+
+ delay(0,function()
+ for i = 1, 3 do
+ if stampData["ErrorBox"] then stampData.ErrorBox.Visible = true end
+ wait(0.13)
+ if stampData["ErrorBox"] then stampData.ErrorBox.Visible = false end
+ wait(0.13)
+ end
+ if stampData["ErrorBox"] then
+ stampData.ErrorBox.Adornee = nil
+ stampData.ErrorBox.Parent = Tool
+ end
+ end)
+ end
+
+ local function DoStamperMouseDown(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseDown: Mouse is nil")
+ return
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseDown: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return
+ end
+ if not stampData then
+ return
+ end
+
+ if isMegaClusterPart() then
+ if Mouse and HighScalabilityLine then
+ local megaCube = stampData.CurrentParts:FindFirstChild("MegaClusterCube", true)
+ local terrain = game.Workspace.Terrain
+ if megaCube then
+ HighScalabilityLine.Dimensions = 1
+ local tempCell = terrain:WorldToCell(megaCube.CFrame.p)
+ HighScalabilityLine.Start = terrain:CellCenterToWorld(tempCell.X, tempCell.Y, tempCell.Z)
+ return
+ else
+ HighScalabilityLine.Dimensions = 1
+ local tempCell = terrain:WorldToCell(stampData.CurrentParts.CFrame.p)
+ HighScalabilityLine.Start = terrain:CellCenterToWorld(tempCell.X, tempCell.Y, tempCell.Z)
+ return
+ end
+ end
+ end
+ end
+
+ local function loadSurfaceTypes(part, surfaces)
+ part.TopSurface = surfaces[1]
+ part.BottomSurface = surfaces[2]
+ part.LeftSurface = surfaces[3]
+ part.RightSurface = surfaces[4]
+ part.FrontSurface = surfaces[5]
+ part.BackSurface = surfaces[6]
+ end
+
+ local function saveSurfaceTypes(part, myTable)
+ local tempTable = {}
+ tempTable[1] = part.TopSurface
+ tempTable[2] = part.BottomSurface
+ tempTable[3] = part.LeftSurface
+ tempTable[4] = part.RightSurface
+ tempTable[5] = part.FrontSurface
+ tempTable[6] = part.BackSurface
+
+ myTable[part] = tempTable
+ end
+
+ local function makeSurfaceUnjoinable(part, surface)
+ -- TODO: FILL OUT!
+ end
+
+ local function prepareModel(model)
+ if not model then return nil end
+
+ local gDesiredTrans = 0.7
+ local gStaticTrans = 1
+
+ local clone = model:Clone()
+ local scripts = {}
+ local parts = {}
+ local decals = {}
+
+ stampData = {}
+ stampData.DisabledScripts = {}
+ stampData.TransparencyTable = {}
+ stampData.MaterialTable = {}
+ stampData.CanCollideTable = {}
+ stampData.AnchoredTable = {}
+ stampData.ArchivableTable = {}
+ stampData.DecalTransparencyTable = {}
+ stampData.SurfaceTypeTable = {}
+
+ collectParts(clone, parts, scripts, decals)
+
+ if #parts <= 0 then return nil, "no parts found in modelToStamp" end
+
+ for index,script in pairs(scripts) do
+ if not(script.Disabled) then
+ script.Disabled = true
+ stampData.DisabledScripts[#stampData.DisabledScripts + 1] = script
+ end
+ end
+ for index, part in pairs(parts) do
+ stampData.TransparencyTable[part] = part.Transparency
+ part.Transparency = gStaticTrans + (1 - gStaticTrans) * part.Transparency
+ stampData.MaterialTable[part] = part.Material
+ part.Material = Enum.Material.Plastic
+ stampData.CanCollideTable[part] = part.CanCollide
+ part.CanCollide = false
+ stampData.AnchoredTable[part] = part.Anchored
+ part.Anchored = true
+ stampData.ArchivableTable[part] = part.Archivable
+ part.Archivable = false
+
+ saveSurfaceTypes(part, stampData.SurfaceTypeTable)
+
+ local fadeInDelayTime = 0.5
+ local transFadeInTime = 0.5
+ delay(0,function()
+ wait(fadeInDelayTime) -- give it some time to be completely transparent
+
+ local begTime = tick()
+ local currTime = begTime
+ while (currTime - begTime) < transFadeInTime and part and part:IsA("BasePart") and part.Transparency > gDesiredTrans do
+ local newTrans = 1 - (((currTime - begTime)/transFadeInTime) * (gStaticTrans - gDesiredTrans))
+ if stampData["TransparencyTable"] and stampData.TransparencyTable[part] then
+ part.Transparency = newTrans + (1 - newTrans) * stampData.TransparencyTable[part]
+ end
+ wait(0.03)
+ currTime = tick()
+ end
+ if part and part:IsA("BasePart") then
+ if stampData["TransparencyTable"] and stampData.TransparencyTable[part] then
+ part.Transparency = gDesiredTrans + (1 - gDesiredTrans) * stampData.TransparencyTable[part]
+ end
+ end
+ end)
+ end
+
+ for index, decal in pairs(decals) do
+ stampData.DecalTransparencyTable[decal] = decal.Transparency
+ decal.Transparency = gDesiredTrans + (1 - gDesiredTrans) * decal.Transparency
+ end
+
+ -- disable all seats
+ setSeatEnabledStatus(clone, true)
+ setSeatEnabledStatus(clone, false)
+
+ stampData.CurrentParts = clone
+
+ -- if auto-alignable, we enforce a pre-rotation to the canonical "0-frame"
+ if autoAlignToFace(clone) then
+ stampData.CurrentParts:ResetOrientationToIdentity()
+ gInitial90DegreeRotations = 0
+ else -- pre-rotate if necessary
+ local ry = gInitial90DegreeRotations * math.pi/2
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry, 0)
+ modelRotate(stampData.CurrentParts, ry)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry, 0) * stampData.CurrentParts.CFrame
+ end
+ end
+
+ -- since we're cloning the old model instead of the new one, we will need to update the orientation based on the original value AND how many more
+ -- rotations we expect since then [either that or we need to store the just-stamped clusterMaterial.Value.Z somewhere]. This should fix the terrain rotation
+ -- issue (fingers crossed) [HotThoth]
+
+ local clusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMaterial and clusterMaterial:IsA("Vector3Value") then
+ clusterMaterial.Value = Vector3.new(clusterMaterial.Value.X, clusterMaterial.Value.Y, (clusterMaterial.Value.Z + gInitial90DegreeRotations) % 4)
+ end
+
+ -- After rotating, update the position
+ local configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+ if configFound then
+ stampData.CurrentParts = positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+ end
+
+ -- to show joints during the mouse move
+ game.JointsService:SetJoinAfterMoveInstance(stampData.CurrentParts)
+
+ return clone, parts
+ end
+
+ local function checkTerrainBlockCollisions(cellPos, checkHighScalabilityStamp)
+ local cellCenterToWorld = game.Workspace.Terrain.CellCenterToWorld
+ local cellCenter = cellCenterToWorld(game.Workspace.Terrain, cellPos.X, cellPos.Y, cellPos.Z)
+ local cellBlockingParts = game.Workspace:FindPartsInRegion3(Region3.new(cellCenter - Vector3.new(2, 2, 2) + insertBoundingBoxOverlapVector, cellCenter + Vector3.new(2, 2, 2) - insertBoundingBoxOverlapVector), stampData.CurrentParts, 100)
+
+ local skipThisCell = false
+
+ for b = 1, #cellBlockingParts do
+ if isBlocker(cellBlockingParts[b]) then skipThisCell = true break end
+ end
+
+ if not skipThisCell then
+ -- pop players up above any set cells
+ local alreadyPushedUp = {}
+ -- if no blocking model below, then see if stamping on top of a character
+ for b = 1, #cellBlockingParts do
+ if cellBlockingParts[b].Parent and
+ not alreadyPushedUp[cellBlockingParts[b].Parent] and
+ cellBlockingParts[b].Parent:FindFirstChild("Humanoid") and
+ cellBlockingParts[b].Parent:FindFirstChild("Humanoid"):IsA("Humanoid") then
+ -----------------------------------------------------------------------------------
+ local blockingPersonTorso = cellBlockingParts[b].Parent:FindFirstChild("Torso")
+ alreadyPushedUp[cellBlockingParts[b].Parent] = true
+
+ if blockingPersonTorso then
+ -- if so, let's push the person upwards so they pop on top of the stamped model/part (but only if there's space above them)
+ local newY = cellCenter.Y + 5
+ if spaceAboveCharacter(blockingPersonTorso, newY, stampData) then
+ blockingPersonTorso.CFrame = blockingPersonTorso.CFrame + Vector3.new(0, newY - blockingPersonTorso.CFrame.p.Y, 0)
+ else
+ -- if no space, we just skip this one
+ skipThisCell = true
+ break
+ end
+ end
+ -----------------------------------------------------------------------------------
+ end
+ end
+ end
+
+ if not skipThisCell then -- if we STILL aren't skipping... then we're good to go!
+ local canSetCell = true
+
+ if checkHighScalabilityStamp then -- check to see if cell is in region, if not we'll skip set
+ if allowedStampRegion then
+ local cellPos = cellCenterToWorld(game.Workspace.Terrain, cellPos.X, cellPos.Y, cellPos.Z)
+ if cellPos.X + 2 > allowedStampRegion.CFrame.p.X + allowedStampRegion.Size.X/2 then
+ canSetCell = false
+ elseif cellPos.X - 2 < allowedStampRegion.CFrame.p.X - allowedStampRegion.Size.X/2 then
+ canSetCell = false
+ elseif cellPos.Y + 2 > allowedStampRegion.CFrame.p.Y + allowedStampRegion.Size.Y/2 then
+ canSetCell = false
+ elseif cellPos.Y - 2 < allowedStampRegion.CFrame.p.Y - allowedStampRegion.Size.Y/2 then
+ canSetCell = false
+ elseif cellPos.Z + 2 > allowedStampRegion.CFrame.p.Z + allowedStampRegion.Size.Z/2 then
+ canSetCell = false
+ elseif cellPos.Z - 2 < allowedStampRegion.CFrame.p.Z - allowedStampRegion.Size.Z/2 then
+ canSetCell = false
+ end
+ end
+ end
+
+ return canSetCell
+ end
+ return false
+ end
+
+
+ local function ResolveMegaClusterStamp(checkHighScalabilityStamp)
+ local cellSet = false
+
+ local cluser = game.Workspace.Terrain
+
+ local line = HighScalabilityLine.InternalLine
+ local cMax = game.Workspace.Terrain.MaxExtents.Max
+ local cMin = game.Workspace.Terrain.MaxExtents.Min
+
+ local clusterMaterial = 1 -- default is grass
+ local clusterType = 0 -- default is brick
+ local clusterOrientation = 0 -- default is 0 rotation
+
+ local autoWedgeClusterParts = false
+ if stampData.CurrentParts:FindFirstChild("AutoWedge") then autoWedgeClusterParts = true end
+
+ if stampData.CurrentParts:FindFirstChild("ClusterMaterial", true) then
+ clusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMaterial:IsA("Vector3Value") then
+ clusterType = clusterMaterial.Value.Y
+ clusterOrientation = clusterMaterial.Value.Z
+ clusterMaterial = clusterMaterial.Value.X
+ elseif clusterMaterial:IsA("IntValue") then
+ clusterMaterial = clusterMaterial.Value
+ end
+ end
+
+ if HighScalabilityLine.Adorn.Parent and HighScalabilityLine.Start and ((HighScalabilityLine.Dimensions > 1) or (line and line.magnitude > 0)) then
+ local startCell = game.Workspace.Terrain:WorldToCell(HighScalabilityLine.Start)
+ local xInc = {0,0,0}
+ local yInc = {0,0,0}
+ local zInc = {0,0,0}
+
+ local cluster = game.Workspace.Terrain
+
+ local incrementVect = {nil, nil, nil}
+ local stepVect = {Vector3.new(0, 0, 0), Vector3.new(0, 0, 0), Vector3.new(0, 0, 0)}
+
+ local worldAxes = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)}
+
+ local lines = {}
+ if HighScalabilityLine.Dimensions > 1 then table.insert(lines, HighScalabilityLine.MoreLines[1]) end
+ if line and line.magnitude > 0 then table.insert(lines, line) end
+ if HighScalabilityLine.Dimensions > 2 then table.insert(lines, HighScalabilityLine.MoreLines[2]) end
+
+ for i = 1, #lines do
+ lines[i] = Vector3.new(math.floor(lines[i].X+.5), math.floor(lines[i].Y+.5), math.floor(lines[i].Z+.5)) -- round to integers
+
+ if lines[i].X > 0 then xInc[i] = 1 elseif lines[i].X < 0 then xInc[i] = -1 end
+ if lines[i].Y > 0 then yInc[i] = 1 elseif lines[i].Y < 0 then yInc[i] = -1 end
+ if lines[i].Z > 0 then zInc[i] = 1 elseif lines[i].Z < 0 then zInc[i] = -1 end
+
+ incrementVect[i] = Vector3.new(xInc[i], yInc[i], zInc[i])
+ if incrementVect[i].magnitude < .9 then incrementVect[i] = nil end
+ end
+
+
+ if not lines[2] then lines[2] = Vector3.new(0, 0, 0) end
+ if not lines[3] then lines[3] = Vector3.new(0, 0, 0) end
+
+ local waterForceTag = stampData.CurrentParts:FindFirstChild("WaterForceTag", true)
+ local waterForceDirectionTag = stampData.CurrentParts:FindFirstChild("WaterForceDirectionTag", true)
+
+ while (stepVect[3].magnitude*4 <= lines[3].magnitude) do
+ local outerStepVectIndex = 1
+ while outerStepVectIndex < 4 do
+ stepVect[2] = Vector3.new(0, 0, 0)
+ while (stepVect[2].magnitude*4 <= lines[2].magnitude) do
+ local innerStepVectIndex = 1
+ while innerStepVectIndex < 4 do
+ stepVect[1] = Vector3.new(0, 0, 0)
+ while (stepVect[1].magnitude*4 <= lines[1].magnitude) do
+ local stepVectSum = stepVect[1] + stepVect[2] + stepVect[3]
+ local cellPos = Vector3int16.new(startCell.X + stepVectSum.X, startCell.Y + stepVectSum.Y, startCell.Z + stepVectSum.Z)
+ if cellPos.X >= cMin.X and cellPos.Y >= cMin.Y and cellPos.Z >= cMin.Z and cellPos.X < cMax.X and cellPos.Y < cMax.Y and cellPos.Z < cMax.Z then
+ -- check if overlaps player or part
+ local okToStampTerrainBlock = checkTerrainBlockCollisions(cellPos, checkHighScalabilityStamp)
+
+ if okToStampTerrainBlock then
+ if waterForceTag then
+ cluster:SetWaterCell(cellPos.X, cellPos.Y, cellPos.Z, Enum.WaterForce[waterForceTag.Value], Enum.WaterDirection[waterForceDirectionTag.Value])
+ else
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterMaterial, clusterType, clusterOrientation)
+ end
+ cellSet = true
+
+ -- auto-wedge it?
+ if (autoWedgeClusterParts) then
+ game.Workspace.Terrain:AutowedgeCells(Region3int16.new(Vector3int16.new(cellPos.x - 1, cellPos.y - 1, cellPos.z - 1),
+ Vector3int16.new(cellPos.x + 1, cellPos.y + 1, cellPos.z + 1)))
+ end
+ end
+ end
+ stepVect[1] = stepVect[1] + incrementVect[1]
+ end
+ if incrementVect[2] then
+ while innerStepVectIndex < 4 and worldAxes[innerStepVectIndex]:Dot(incrementVect[2]) == 0 do
+ innerStepVectIndex = innerStepVectIndex + 1
+ end
+ if innerStepVectIndex < 4 then
+ stepVect[2] = stepVect[2] + worldAxes[innerStepVectIndex] * worldAxes[innerStepVectIndex]:Dot(incrementVect[2])
+ end
+ innerStepVectIndex = innerStepVectIndex + 1
+ else
+ stepVect[2] = Vector3.new(1, 0, 0)
+ innerStepVectIndex = 4 -- skip all remaining loops
+ end
+ if (stepVect[2].magnitude*4 > lines[2].magnitude) then innerStepVectIndex = 4 end
+ end
+ end
+ if incrementVect[3] then
+ while outerStepVectIndex < 4 and worldAxes[outerStepVectIndex]:Dot(incrementVect[3]) == 0 do
+ outerStepVectIndex = outerStepVectIndex + 1
+ end
+ if outerStepVectIndex < 4 then
+ stepVect[3] = stepVect[3] + worldAxes[outerStepVectIndex] * worldAxes[outerStepVectIndex]:Dot(incrementVect[3])
+ end
+ outerStepVectIndex = outerStepVectIndex + 1
+ else -- skip all remaining loops
+ stepVect[3] = Vector3.new(1, 0, 0) outerStepVectIndex = 4
+ end
+ if (stepVect[3].magnitude*4 > lines[3].magnitude) then outerStepVectIndex = 4 end
+ end
+ end
+ end
+
+ -- and also get rid of any HighScalabilityLine stuff if it's there
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.Adorn.Parent = nil
+
+ -- Mark for undo.
+ if cellSet then
+ stampData.CurrentParts.Parent = nil
+ pcall(function() game:GetService("ChangeHistoryService"): SetWaypoint("StamperMulti") end)
+ end
+
+ return cellSet
+ end
+
+ local function DoStamperMouseUp(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseUp: Mouse is nil")
+ return false
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseUp: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return false
+ end
+
+ if not stampData.Dragger then
+ error("Error: RbxStamper.DoStamperMouseUp: stampData.Dragger is nil")
+ return false
+ end
+
+ if not HighScalabilityLine then
+ return false
+ end
+
+ local checkHighScalabilityStamp = nil
+ if stampInModel then
+ local canStamp = nil
+ local isHSLPart = isMegaClusterPart()
+
+ if isHSLPart and
+ HighScalabilityLine and
+ HighScalabilityLine.Start and
+ HighScalabilityLine.InternalLine and
+ HighScalabilityLine.InternalLine.magnitude > 0 then -- we have an HSL line, test later
+ canStamp = true
+ checkHighScalabilityStamp = true
+ else
+ canStamp, checkHighScalabilityStamp = t.CanEditRegion(stampData.CurrentParts, allowedStampRegion)
+ end
+
+ if not canStamp then
+ if stampFailedFunc then
+ stampFailedFunc()
+ end
+ return false
+ end
+ end
+
+ -- if unstampable face, then don't let us stamp there!
+ if unstampableSurface then
+ flashRedBox()
+ return false
+ end
+
+ -- recheck if we can stamp, as we just moved part
+ canStamp, checkHighScalabilityStamp = t.CanEditRegion(stampData.CurrentParts, allowedStampRegion)
+ if not canStamp then
+ if stampFailedFunc then
+ stampFailedFunc()
+ end
+ return false
+ end
+
+ -- Prevent part from being stamped on top of a player
+
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(stampData.CurrentParts)
+
+ -- HotThoth's note: Now that above CurrentParts positioning has been commented out, to be truly correct, we would need to use the
+ -- value of configFound from the previous onStamperMouseMove call which moved the CurrentParts
+ -- Shouldn't this be true when lastTargetCFrame has been set and false otherwise?
+ configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+
+ if configFound and not HighScalabilityLine.Adorn.Parent then
+ if clusterPartsInRegion(minBB + insertBoundingBoxOverlapVector, maxBB - insertBoundingBoxOverlapVector) then
+ flashRedBox()
+ return false
+ end
+
+ local blockingParts = game.Workspace:FindPartsInRegion3(Region3.new(minBB + insertBoundingBoxOverlapVector,
+ maxBB - insertBoundingBoxOverlapVector),
+ stampData.CurrentParts,
+ 100)
+
+
+ for b = 1, #blockingParts do
+ if isBlocker(blockingParts[b]) then
+ flashRedBox()
+ return false
+ end
+ end
+
+ local alreadyPushedUp = {}
+ -- if no blocking model below, then see if stamping on top of a character
+ for b = 1, #blockingParts do
+ if blockingParts[b].Parent and
+ not alreadyPushedUp[blockingParts[b].Parent] and
+ blockingParts[b].Parent:FindFirstChild("Humanoid") and
+ blockingParts[b].Parent:FindFirstChild("Humanoid"):IsA("Humanoid") then
+ ---------------------------------------------------------------------------
+ local blockingPersonTorso = blockingParts[b].Parent:FindFirstChild("Torso")
+ alreadyPushedUp[blockingParts[b].Parent] = true
+
+ if blockingPersonTorso then
+ -- if so, let's push the person upwards so they pop on top of the stamped model/part (but only if there's space above them)
+ local newY = maxBB.Y + 3
+ if spaceAboveCharacter(blockingPersonTorso, newY, stampData) then
+ blockingPersonTorso.CFrame = blockingPersonTorso.CFrame + Vector3.new(0, newY - blockingPersonTorso.CFrame.p.Y, 0)
+ else
+ -- if no space, we just error
+ flashRedBox()
+ return false
+ end
+ end
+ ---------------------------------------------------------------------------
+ end
+ end
+
+ elseif (not configFound) and not (HighScalabilityLine.Start and HighScalabilityLine.Adorn.Parent) then -- if no config then only stamp if it's a real HSL!
+ resetHighScalabilityLine()
+ return false
+ end
+
+ -- something will be stamped! so set the "StampedSomething" toggle to true
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer["Character"] then
+ local localChar = game.Players.LocalPlayer.Character
+ local stampTracker = localChar:FindFirstChild("StampTracker")
+ if stampTracker and not stampTracker.Value then
+ stampTracker.Value = true
+ end
+ end
+ end
+ end
+
+ -- if we drew a line of mega parts, stamp them out
+ if HighScalabilityLine.Start and HighScalabilityLine.Adorn.Parent and isMegaClusterPart() then
+ if ResolveMegaClusterStamp(checkHighScalabilityStamp) or checkHighScalabilityStamp then
+ -- kill the ghost part
+ stampData.CurrentParts.Parent = nil
+ return true
+ end
+ end
+
+ -- not High-Scalability-Line-Based, so behave normally [and get rid of any HSL stuff]
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.Adorn.Parent = nil
+
+ local cluster = game.Workspace.Terrain
+
+ -- if target point is in cluster, just use cluster:SetCell
+ if isMegaClusterPart() then
+ -- if targetCFrame is inside cluster, just set that cell to 1 and return
+ --local cellPos = cluster:WorldToCell(targetCFrame.p)
+
+ local cellPos
+ if stampData.CurrentParts:IsA("Model") then cellPos = cluster:WorldToCell(stampData.CurrentParts:GetModelCFrame().p)
+ else cellPos = cluster:WorldToCell(stampData.CurrentParts.CFrame.p) end
+
+ local cMax = game.Workspace.Terrain.MaxExtents.Max
+ local cMin = game.Workspace.Terrain.MaxExtents.Min
+
+ if checkTerrainBlockCollisions(cellPos, false) then
+
+ local clusterValues = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ local waterForceTag = stampData.CurrentParts:FindFirstChild("WaterForceTag", true)
+ local waterForceDirectionTag = stampData.CurrentParts:FindFirstChild("WaterForceDirectionTag", true)
+
+ if cellPos.X >= cMin.X and cellPos.Y >= cMin.Y and cellPos.Z >= cMin.Z and cellPos.X < cMax.X and cellPos.Y < cMax.Y and cellPos.Z < cMax.Z then
+
+ if waterForceTag then
+ cluster:SetWaterCell(cellPos.X, cellPos.Y, cellPos.Z, Enum.WaterForce[waterForceTag.Value], Enum.WaterDirection[waterForceDirectionTag.Value])
+ elseif not clusterValues then
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, cellInfo.Material, cellInfo.clusterType, gInitial90DegreeRotations % 4)
+ elseif clusterValues:IsA("Vector3Value") then
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterValues.Value.X, clusterValues.Value.Y, clusterValues.Value.Z)
+ else
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterValues.Value, 0, 0)
+ end
+
+ local autoWedgeClusterParts = false
+ if stampData.CurrentParts:FindFirstChild("AutoWedge") then autoWedgeClusterParts = true end
+
+ -- auto-wedge it
+ if (autoWedgeClusterParts) then
+ game.Workspace.Terrain:AutowedgeCells(
+ Region3int16.new(
+ Vector3int16.new(cellPos.x - 1, cellPos.y - 1, cellPos.z - 1),
+ Vector3int16.new(cellPos.x + 1, cellPos.y + 1, cellPos.z + 1)
+ )
+ )
+ end
+
+ -- kill the ghost part
+ stampData.CurrentParts.Parent = nil
+
+ -- Mark for undo. It has to happen here or the selection display will come back also.
+ pcall(function() game:GetService("ChangeHistoryService"):SetWaypoint("StamperSingle") end)
+ return true
+ end
+ else
+ -- you tried to stamp a HSL-single part where one does not belong!
+ flashRedBox()
+ return false
+ end
+ end
+
+ local function getPlayer()
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ return game.Players.LocalPlayer
+ end
+ end
+ return nil
+ end
+
+
+ -- Post process: after positioning the part or model, restore transparency, material, anchored and collide states and create joints
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ if stampData.CurrentParts:IsA("Model") then
+ -- Tyler's magical hack-code for allowing/preserving clones of both Surface and Manual Welds... just don't ask X<
+ local manualWeldTable = {}
+ local manualWeldParentTable = {}
+ saveTheWelds(stampData.CurrentParts, manualWeldTable, manualWeldParentTable)
+ stampData.CurrentParts:BreakJoints()
+ stampData.CurrentParts:MakeJoints()
+ restoreTheWelds(manualWeldTable, manualWeldParentTable)
+ end
+
+ -- if it's a model, we also want to fill in the playerID and playerName tags, if it has those (e.g. for the friend-only door)
+ playerIdTag = stampData.CurrentParts:FindFirstChild("PlayerIdTag")
+ playerNameTag = stampData.CurrentParts:FindFirstChild("PlayerNameTag")
+ if playerIdTag ~= nil then
+ tempPlayerValue = getPlayer()
+ if tempPlayerValue ~= nil then playerIdTag.Value = tempPlayerValue.userId end
+ end
+ if playerNameTag ~= nil then
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ tempPlayerValue = game.Players.LocalPlayer
+ if tempPlayerValue ~= nil then playerNameTag.Value = tempPlayerValue.Name end
+ end
+ end
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if stampData.CurrentParts:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag.Name = "RobloxModel"
+
+ if stampData.CurrentParts:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ else
+ stampData.CurrentParts:BreakJoints()
+ if stampData.CurrentParts:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ -- make sure all the joints are activated before restoring anchor states
+ if not createJoints then game.JointsService:CreateJoinAfterMoveJoints() end
+
+ -- Restore the original properties for all parts being stamped
+ for part, transparency in pairs(stampData.TransparencyTable) do
+ part.Transparency = transparency
+ end
+ for part, archivable in pairs(stampData.ArchivableTable) do
+ part.Archivable = archivable
+ end
+ for part, material in pairs(stampData.MaterialTable) do
+ part.Material = material
+ end
+ for part, collide in pairs(stampData.CanCollideTable) do
+ part.CanCollide = collide
+ end
+ for part, anchored in pairs(stampData.AnchoredTable) do
+ part.Anchored = anchored
+ end
+ for decal, transparency in pairs(stampData.DecalTransparencyTable) do
+ decal.Transparency = transparency
+ end
+
+ for part, surfaces in pairs(stampData.SurfaceTypeTable) do
+ loadSurfaceTypes(part, surfaces)
+ end
+
+ if isMegaClusterPart() then
+ stampData.CurrentParts.Transparency = 0
+ end
+
+ -- re-enable all seats
+ setSeatEnabledStatus(stampData.CurrentParts, true)
+
+ stampData.TransparencyTable = nil
+ stampData.ArchivableTable = nil
+ stampData.MaterialTable = nil
+ stampData.CanCollideTable = nil
+ stampData.AnchoredTable = nil
+ stampData.SurfaceTypeTable = nil
+
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if stampData.CurrentParts:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag.Name = "RobloxModel"
+ end
+
+ -- and make sure we don't delete it, now that it's not a ghost part
+ if ghostRemovalScript then ghostRemovalScript.Parent = nil end
+
+ --Re-enable the scripts
+ for index,script in pairs(stampData.DisabledScripts) do
+ script.Disabled = false
+ end
+
+ --Now that they are all marked enabled, reinsert them into the world so they start running
+ for index,script in pairs(stampData.DisabledScripts) do
+ local oldParent = script.Parent
+ script.Parent = nil
+ script:Clone().Parent = oldParent
+ end
+
+ -- clear out more data
+ stampData.DisabledScripts = nil
+ stampData.Dragger = nil
+ stampData.CurrentParts = nil
+
+ pcall(function() game:GetService("ChangeHistoryService"): SetWaypoint("StampedObject") end)
+ return true
+ end
+
+ local function pauseStamper()
+ for i = 1, #mouseCons do -- stop the mouse from doing anything
+ mouseCons[i]:disconnect()
+ mouseCons[i] = nil
+ end
+ mouseCons = {}
+
+ if stampData and stampData.CurrentParts then -- remove our ghost part
+ stampData.CurrentParts.Parent = nil
+ stampData.CurrentParts:Remove()
+ end
+
+ resetHighScalabilityLine()
+
+ game.JointsService:ClearJoinAfterMoveJoints()
+ end
+
+
+ local function prepareUnjoinableSurfaces(modelCFrame, parts, whichSurface)
+ local AXIS_VECTORS = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)} -- maybe last one is negative? TODO: check this!
+ local isPositive = 1
+ if whichSurface < 0 then isPositive = isPositive * -1 whichSurface = whichSurface*-1 end
+ local surfaceNormal = isPositive * modelCFrame:vectorToWorldSpace(AXIS_VECTORS[whichSurface])
+
+ for i = 1, #parts do
+ local currPart = parts[i]
+
+ -- now just need to find which surface of currPart most closely match surfaceNormal and then set that to Unjoinable
+ local surfaceNormalInLocalCoords = currPart.CFrame:vectorToObjectSpace(surfaceNormal)
+ if math.abs(surfaceNormalInLocalCoords.X) > math.abs(surfaceNormalInLocalCoords.Y) then
+ if math.abs(surfaceNormalInLocalCoords.X) > math.abs(surfaceNormalInLocalCoords.Z) then
+ if surfaceNormalInLocalCoords.X > 0 then currPart.RightSurface = "Unjoinable" else currPart.LeftSurface = "Unjoinable" end
+ else
+ if surfaceNormalInLocalCoords.Z > 0 then currPart.BackSurface = "Unjoinable" else currPart.FrontSurface = "Unjoinable" end
+ end
+ else
+ if math.abs(surfaceNormalInLocalCoords.Y) > math.abs(surfaceNormalInLocalCoords.Z) then
+ if surfaceNormalInLocalCoords.Y > 0 then currPart.TopSurface = "Unjoinable" else currPart.BottomSurface = "Unjoinable" end
+ else
+ if surfaceNormalInLocalCoords.Z > 0 then currPart.BackSurface = "Unjoinable" else currPart.FrontSurface = "Unjoinable" end
+ end
+ end
+ end
+ end
+
+ local function resumeStamper()
+ clone, parts = prepareModel(modelToStamp)
+
+ if not clone or not parts then
+ return
+ end
+
+ -- if we have unjoinable faces, then we want to change those surfaces to be Unjoinable
+ local unjoinableTag = clone:FindFirstChild("UnjoinableFaces", true)
+ if unjoinableTag then
+ for unjoinableSurface in string.gmatch(unjoinableTag.Value, "[^,]*") do
+ if tonumber(unjoinableSurface) then
+ if clone:IsA("Model") then
+ prepareUnjoinableSurfaces(clone:GetModelCFrame(), parts, tonumber(unjoinableSurface))
+ else
+ prepareUnjoinableSurfaces(clone.CFrame, parts, tonumber(unjoinableSurface))
+ end
+ end
+ end
+ end
+
+ stampData.ErrorBox = errorBox
+ if stampInModel then
+ clone.Parent = stampInModel
+ else
+ clone.Parent = game.Workspace
+ end
+
+ if clone:FindFirstChild("ClusterMaterial", true) then -- extract all info from vector
+ clusterMaterial = clone:FindFirstChild("ClusterMaterial", true)
+ if (clusterMaterial:IsA("Vector3Value")) then
+ cellInfo.Material = clusterMaterial.Value.X
+ cellInfo.clusterType = clusterMaterial.Value.Y
+ cellInfo.clusterOrientation = clusterMaterial.Value.Z
+ elseif clusterMaterial:IsA("IntValue") then
+ cellInfo.Material = clusterMaterial.Value
+ end
+ end
+
+ pcall(function() mouseTarget = Mouse.Target end)
+
+ if mouseTarget and mouseTarget.Parent:FindFirstChild("RobloxModel") == nil then
+ game.JointsService:SetJoinAfterMoveTarget(mouseTarget)
+ else
+ game.JointsService:SetJoinAfterMoveTarget(nil)
+ end
+ game.JointsService:ShowPermissibleJoints()
+
+ for index, object in pairs(stampData.DisabledScripts) do
+ if object.Name == "GhostRemovalScript" then
+ object.Parent = stampData.CurrentParts
+ end
+ end
+
+ stampData.Dragger = Instance.new("Dragger")
+
+ --Begin a movement by faking a MouseDown signal
+ stampData.Dragger:MouseDown(parts[1], Vector3.new(0,0,0), parts)
+ stampData.Dragger:MouseUp()
+
+ DoStamperMouseMove(Mouse)
+
+ table.insert(mouseCons,Mouse.Move:connect(function()
+ if movingLock or stampUpLock then return end
+ movingLock = true
+ DoStamperMouseMove(Mouse)
+ movingLock = false
+ end))
+
+ table.insert(mouseCons,Mouse.Button1Down:connect(function()
+ DoStamperMouseDown(Mouse)
+ end))
+
+ table.insert(mouseCons,Mouse.Button1Up:connect(function()
+ stampUpLock = true
+ while movingLock do wait() end
+ stamped.Value = DoStamperMouseUp(Mouse)
+ resetHighScalabilityLine()
+ stampUpLock = false
+ end))
+
+ stamped.Value = false
+ end
+
+ local function resetStamperState(newModelToStamp)
+
+ -- if we have a new model, swap it out
+ if newModelToStamp then
+ if not newModelToStamp:IsA("Model") and not newModelToStamp:IsA("BasePart") then
+ error("resetStamperState: newModelToStamp (first arg) is not nil, but not a model or part!")
+ end
+ modelToStamp = newModelToStamp
+ end
+
+ -- first clear our state
+ pauseStamper()
+ -- now lets load in the new model
+ resumeStamper()
+
+ end
+
+ -- load the model initially
+ resetStamperState()
+
+
+ -- setup the control table we pass back to the user
+ control.Stamped = stamped -- BoolValue that fires when user stamps
+ control.Paused = false
+
+ control.LoadNewModel = function(newStampModel) -- allows us to specify a new stamper model to be used with this stamper
+ if newStampModel and not newStampModel:IsA("Model") and not newStampModel:IsA("BasePart") then
+ error("Control.LoadNewModel: newStampModel (first arg) is not a Model or Part!")
+ return nil
+ end
+ resetStamperState(newStampModel)
+ end
+
+ control.ReloadModel = function() -- will automatically set stamper to get a new model of current model and start stamping with new model
+ resetStamperState()
+ end
+
+ control.Pause = function() -- temporarily stops stamping, use resume to start up again
+ if not control.Paused then
+ pauseStamper()
+ control.Paused = true
+ else
+ print("RbxStamper Warning: Tried to call Control.Pause() when already paused")
+ end
+ end
+
+ control.Resume = function() -- resumes stamping, if currently paused
+ if control.Paused then
+ resumeStamper()
+ control.Paused = false
+ else
+ print("RbxStamper Warning: Tried to call Control.Resume() without Pausing First")
+ end
+ end
+
+ control.ResetRotation = function() -- resets the model rotation so new models are at default orientation
+ -- gInitial90DegreeRotations = 0
+ -- Note: This function will not always work quite the way we want it to; we will have to build this out further so it works with
+ -- High-Scalability and with the new model orientation setting methods (model:ResetOrientationToIdentity()) [HotThoth]
+ end
+
+ control.Destroy = function() -- Stops current Stamp operation and destroys control construct
+ for i = 1, #mouseCons do
+ mouseCons[i]:disconnect()
+ mouseCons[i] = nil
+ end
+
+ if keyCon then
+ keyCon:disconnect()
+ end
+
+ game.JointsService:ClearJoinAfterMoveJoints()
+
+ if adorn then adorn:Destroy() end
+ if adornPart then adornPart:Destroy() end
+ if errorBox then errorBox:Destroy() end
+ if stampData then
+ if stampData["Dragger"] then
+ stampData.Dragger:Destroy()
+ end
+ if stampData.CurrentParts then
+ stampData.CurrentParts:Destroy()
+ end
+ end
+ if control and control["Stamped"] then
+ control.Stamped:Destroy()
+ end
+ control = nil
+ end
+
+ return control
+end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "GetStampModel" or funcNameOrFunc == t.GetStampModel then
+ return "Function GetStampModel. Arguments: assetId, useAssetVersionId. assetId is the asset to load in, define useAssetVersionId as true if assetId is a version id instead of a relative assetId. Side effect: returns a model of the assetId, or a string with error message if something fails"
+ end
+ if funcNameOrFunc == "SetupStamperDragger" or funcNameOrFunc == t.SetupStamperDragger then
+ return "Function SetupStamperDragger. Side Effect: Creates 4x4 stamping mechanism for building out parts quickly. Arguments: ModelToStamp, Mouse, LegalStampCheckFunction. ModelToStamp should be a Model or Part, preferrably loaded from RbxStamper.GetStampModel and should have extents that are multiples of 4. Mouse should be a mouse object (obtained from things such as Tool.OnEquipped), used to drag parts around 'stamp' them out. LegalStampCheckFunction is optional, used as a callback with a table argument (table is full of instances about to be stamped). Function should return either true or false, false stopping the stamp action."
+ end
+ end
+
+return t
diff --git a/asset/4 b/asset/4
new file mode 100644
index 0000000..5e9d9be
--- /dev/null
+++ b/asset/4
@@ -0,0 +1,2379 @@
+--rbxassetid%4%
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+--Include
+local Create = assert(LoadLibrary("RbxUtility")).Create
+
+
+-- A Few Script Globals
+local gui
+if script.Parent:FindFirstChild("ControlFrame") then
+ gui = script.Parent:FindFirstChild("ControlFrame")
+else
+ gui = script.Parent
+end
+
+local helpButton = nil
+local updateCameraDropDownSelection = nil
+local updateVideoCaptureDropDownSelection = nil
+local updateSmartCameraDropDownSelection = nil
+local updateTouchMovementDropDownSelection = nil
+local tweenTime = 0.2
+
+local mouseLockLookScreenUrl = "http://www.roblox.com/asset?id=54071825"
+local classicLookScreenUrl = "http://www.roblox.com/Asset?id=45915798"
+
+local hasGraphicsSlider = true
+local GraphicsQualityLevels = 10 -- how many levels we allow on graphics slider
+local recordingVideo = false
+
+local volumeFlagExists, volumeFlagValue = pcall(function () return settings():GetFFlag("VolumeControlInGameEnabled") end)
+local hasVolumeSlider = volumeFlagExists and volumeFlagValue
+
+local currentMenuSelection = nil
+local lastMenuSelection = {}
+
+local defaultPosition = UDim2.new(0,0,0,0)
+
+local centerDialogs = {}
+local mainShield = nil
+
+local testReport = false
+
+local inStudioMode = UserSettings().GameSettings:InStudioMode()
+-- REMOVE WHEN NOT TESTING
+-- inStudioMode = false
+
+local macClient = false
+local success, isMac = pcall(function() return not game.GuiService.IsWindows end)
+macClient = success and isMac
+-- REMOVE WHEN NOT TESTING
+--macClient = true
+
+local customCameraDefaultType = "Default (Classic)"
+local touchClient = false
+pcall(function() touchClient = game:GetService("UserInputService").TouchEnabled end)
+-- REMOVE WHEN NOT TESTING
+-- touchClient = true
+if touchClient then
+ hasGraphicsSlider = false
+ customCameraDefaultType = "Default (Follow)"
+end
+
+local function Color3I(r,g,b)
+ return Color3.new(r/255,g/255,b/255)
+end
+
+local function robloxLock(instance)
+ instance.RobloxLocked = true
+ children = instance:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ robloxLock(child)
+ end
+ end
+end
+
+function resumeGameFunction(shield)
+ shield.Settings:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ delay(tweenTime,function()
+ shield.Visible = false
+ for i = 1, #centerDialogs do
+ centerDialogs[i].Visible = false
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ end
+ game.GuiService:RemoveCenterDialog(shield)
+ settingsButton.Active = true
+ currentMenuSelection = nil
+ lastMenuSelection = {}
+ pcall(function() game:GetService("UserInputService").OverrideMouseIconEnabled = false end)
+ end)
+end
+
+function goToMenu(container,menuName, moveDirection,size,position)
+ if type(menuName) ~= "string" then return end
+
+ table.insert(lastMenuSelection,currentMenuSelection)
+ if menuName == "GameMainMenu" then
+ lastMenuSelection = {}
+ end
+
+ local containerChildren = container:GetChildren()
+ local selectedMenu = false
+ for i = 1, #containerChildren do
+ if containerChildren[i].Name == menuName then
+ containerChildren[i].Visible = true
+ currentMenuSelection = {container = container,name = menuName, direction = moveDirection, lastSize = size}
+ selectedMenu = true
+ if size and position then
+ containerChildren[i]:TweenSizeAndPosition(size,position,Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif size then
+ containerChildren[i]:TweenSizeAndPosition(size,UDim2.new(0.5,-size.X.Offset/2,0.5,-size.Y.Offset/2),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ else
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end
+ else
+ if moveDirection == "left" then
+ containerChildren[i]:TweenPosition(UDim2.new(-1,-525,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "right" then
+ containerChildren[i]:TweenPosition(UDim2.new(1,525,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "up" then
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,-1,-400),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "down" then
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,1,400),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end
+ delay(tweenTime,function()
+ containerChildren[i].Visible = false
+ end)
+ end
+ end
+end
+
+function resetLocalCharacter()
+ local player = game.Players.LocalPlayer
+ if player then
+ if player.Character and player.Character:FindFirstChild("Humanoid") then
+ player.Character.Humanoid.Health = 0
+ end
+ end
+end
+
+local function createTextButton(text,style,fontSize,buttonSize,buttonPosition)
+ local newTextButton = Instance.new("TextButton")
+ newTextButton.Font = Enum.Font.SourceSansBold
+ newTextButton.FontSize = fontSize
+ newTextButton.Size = buttonSize
+ newTextButton.Position = buttonPosition
+ newTextButton.Style = style
+ newTextButton.TextColor3 = Color3.new(1,1,1)
+ newTextButton.Text = text
+ return newTextButton
+end
+
+local function CreateTextButtons(frame, buttons, yPos, ySize)
+ if #buttons < 1 then
+ error("Must have more than one button")
+ end
+
+ local buttonNum = 1
+ local buttonObjs = {}
+
+ local function toggleSelection(button)
+ for i, obj in ipairs(buttonObjs) do
+ if obj == button then
+ obj.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ else
+ obj.Style = Enum.ButtonStyle.RobloxRoundButton
+ end
+ end
+ end
+
+ for i, obj in ipairs(buttons) do
+ local button = Instance.new("TextButton")
+ button.Name = "Button" .. buttonNum
+ button.Font = Enum.Font.SourceSansBold
+ button.FontSize = Enum.FontSize.Size18
+ button.AutoButtonColor = true
+ button.Style = Enum.ButtonStyle.RobloxRoundButton
+ button.Text = obj.Text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.MouseButton1Click:connect(function() toggleSelection(button) obj.Function() end)
+ button.Parent = frame
+ button.ZIndex = 8
+ buttonObjs[buttonNum] = button
+
+ buttonNum = buttonNum + 1
+ end
+
+ toggleSelection(buttonObjs[1])
+
+ local numButtons = buttonNum-1
+
+ if numButtons == 1 then
+ frame.Button1.Position = UDim2.new(0.35, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.4,0,ySize.Scale, ySize.Offset)
+ elseif numButtons == 2 then
+ frame.Button1.Position = UDim2.new(0.1, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+
+ frame.Button2.Position = UDim2.new(0.55, 0, yPos.Scale, yPos.Offset)
+ frame.Button2.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+ elseif numButtons >= 3 then
+ local spacing = .1 / numButtons
+ local buttonSize = .9 / numButtons
+
+ buttonNum = 1
+ while buttonNum <= numButtons do
+ buttonObjs[buttonNum].Position = UDim2.new(spacing*buttonNum + (buttonNum-1) * buttonSize, 0, yPos.Scale, yPos.Offset)
+ buttonObjs[buttonNum].Size = UDim2.new(buttonSize, 0, ySize.Scale, ySize.Offset)
+ buttonNum = buttonNum + 1
+ end
+ end
+end
+
+function setRecordGui(recording, stopRecordButton, recordVideoButton)
+ if recording then
+ stopRecordButton.Visible = true
+ recordVideoButton.Text = "Stop Recording"
+ else
+ stopRecordButton.Visible = false
+ recordVideoButton.Text = "Record Video"
+ end
+end
+
+function recordVideoClick(recordVideoButton, stopRecordButton)
+ recordingVideo = not recordingVideo
+ setRecordGui(recordingVideo, stopRecordButton, recordVideoButton)
+end
+
+local currentlyToggling = false;
+local DevConsoleToggle = nil;
+
+delay(0, function()
+ DevConsoleToggle = gui:WaitForChild("ToggleDevConsole")
+end)
+
+function toggleDeveloperConsole()
+ if not DevConsoleToggle then
+ return
+ end
+
+ DevConsoleToggle:Invoke()
+end
+
+function backToGame(buttonClicked, shield, settingsButton)
+ buttonClicked.Parent.Parent.Parent.Parent.Visible = false
+ shield.Visible = false
+ for i = 1, #centerDialogs do
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ centerDialogs[i].Visible = false
+ end
+ centerDialogs = {}
+ game.GuiService:RemoveCenterDialog(shield)
+ settingsButton.Active = true
+end
+
+function setDisabledState(guiObject)
+ if not guiObject then return end
+
+ if guiObject:IsA("TextLabel") then
+ guiObject.TextTransparency = 0.9
+ elseif guiObject:IsA("TextButton") then
+ guiObject.TextTransparency = 0.9
+ guiObject.Active = false
+ else
+ if guiObject["ClassName"] then
+ print("setDisabledState() got object of unsupported type. object type is ",guiObject.ClassName)
+ end
+ end
+end
+
+local function createHelpDialog(baseZIndex)
+
+ if helpButton == nil then
+ if gui:FindFirstChild("TopLeftControl") and gui.TopLeftControl:FindFirstChild("Help") then
+ helpButton = gui.TopLeftControl.Help
+ elseif gui:FindFirstChild("BottomRightControl") and gui.BottomRightControl:FindFirstChild("Help") then
+ helpButton = gui.BottomRightControl.Help
+ end
+ end
+
+ local shield = Instance.new("Frame")
+ shield.Name = "HelpDialogShield"
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 2
+
+ local helpDialog = Instance.new("Frame")
+ helpDialog.Name = "HelpDialog"
+ helpDialog.Style = Enum.FrameStyle.DropShadow
+ helpDialog.Position = UDim2.new(.2, 0, .2, 0)
+ helpDialog.Size = UDim2.new(0.6, 0, 0.6, 0)
+ helpDialog.Active = true
+ helpDialog.Parent = shield
+ helpDialog.ZIndex = baseZIndex + 2
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = "Keyboard & Mouse Controls"
+ titleLabel.Font = Enum.Font.SourceSansBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.Position = UDim2.new(0, 0, 0.025, 0)
+ titleLabel.Size = UDim2.new(1, 0, 0, 40)
+ titleLabel.TextColor3 = Color3.new(1,1,1)
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.Parent = helpDialog
+ titleLabel.ZIndex = baseZIndex + 2
+
+ local buttonRow = Instance.new("Frame")
+ buttonRow.Name = "Buttons"
+ buttonRow.Position = UDim2.new(0.1, 0, .07, 40)
+ buttonRow.Size = UDim2.new(0.8, 0, 0, 45)
+ buttonRow.BackgroundTransparency = 1
+ buttonRow.Parent = helpDialog
+ buttonRow.ZIndex = baseZIndex + 2
+
+ local imageFrame = Instance.new("Frame")
+ imageFrame.Name = "ImageFrame"
+ imageFrame.Position = UDim2.new(0.05, 0, 0.075, 80)
+ imageFrame.Size = UDim2.new(0.9, 0, .9, -120)
+ imageFrame.BackgroundTransparency = 1
+ imageFrame.Parent = helpDialog
+ imageFrame.ZIndex = baseZIndex + 2
+
+ local layoutFrame = Instance.new("Frame")
+ layoutFrame.Name = "LayoutFrame"
+ layoutFrame.Position = UDim2.new(0.5, 0, 0, 0)
+ layoutFrame.Size = UDim2.new(1.5, 0, 1, 0)
+ layoutFrame.BackgroundTransparency = 1
+ layoutFrame.SizeConstraint = Enum.SizeConstraint.RelativeYY
+ layoutFrame.Parent = imageFrame
+ layoutFrame.ZIndex = baseZIndex + 2
+
+ local image = Instance.new("ImageLabel")
+ image.Name = "Image"
+ if UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ image.Image = mouseLockLookScreenUrl
+ else
+ image.Image = classicLookScreenUrl
+ end
+ image.Position = UDim2.new(-0.5, 0, 0, 0)
+ image.Size = UDim2.new(1, 0, 1, 0)
+ image.BackgroundTransparency = 1
+ image.Parent = layoutFrame
+ image.ZIndex = baseZIndex + 2
+
+ local buttons = {}
+ buttons[1] = {}
+ buttons[1].Text = "Look"
+ buttons[1].Function = function()
+ if UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ image.Image = mouseLockLookScreenUrl
+ else
+ image.Image = classicLookScreenUrl
+ end
+ end
+ buttons[2] = {}
+ buttons[2].Text = "Move"
+ buttons[2].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45915811"
+ end
+ buttons[3] = {}
+ buttons[3].Text = "Gear"
+ buttons[3].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45917596"
+ end
+ buttons[4] = {}
+ buttons[4].Text = "Zoom"
+ buttons[4].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45915825"
+ end
+
+ CreateTextButtons(buttonRow, buttons, UDim.new(0, 0), UDim.new(1,0))
+
+ local devConsoleButton = Create'TextButton'{
+ Name = "DeveloperConsoleButton";
+ Text = "Log";
+ Size = UDim2.new(0,60,0,30);
+ Style = Enum.ButtonStyle.RobloxRoundButton;
+ Position = UDim2.new(1,-65,1,-35);
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ TextColor3 = Color3.new(1,1,1);
+ ZIndex = baseZIndex + 4;
+ BackgroundTransparency = 1;
+ Parent = helpDialog;
+ }
+
+ Create'TextLabel'{
+ Name = "DeveloperConsoleButton";
+ Text = "F9";
+ Size = UDim2.new(0,14,0,14);
+ Position = UDim2.new(1,-6,0, -2);
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size12;
+ TextColor3 = Color3.new(0,1,0);
+ ZIndex = baseZIndex + 4;
+ BackgroundTransparency = 1;
+ Parent = devConsoleButton;
+ }
+
+ waitForProperty(game.Players, "LocalPlayer")
+ game.Players.LocalPlayer:GetMouse().KeyDown:connect(function(key)
+ if string.byte(key) == 34 then --F9
+ toggleDeveloperConsole()
+ end
+ end)
+
+ devConsoleButton.MouseButton1Click:connect(function()
+ toggleDeveloperConsole()
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end)
+
+ -- set up listeners for type of mouse mode, but keep constructing gui at same time
+ delay(0, function()
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield,"Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle, "GameSettingsMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu, "CameraField")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField, "DropDownMenuButton")
+ gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField.DropDownMenuButton.Changed:connect(function(prop)
+ if prop ~= "Text" then return end
+ if buttonRow.Button1.Style == Enum.ButtonStyle.RobloxRoundDefaultButton then -- only change if this is the currently selected panel
+ if gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField.DropDownMenuButton.Text == "Classic" then
+ image.Image = classicLookScreenUrl
+ else
+ image.Image = mouseLockLookScreenUrl
+ end
+ end
+ end)
+ end)
+
+
+ local okBtn = Instance.new("TextButton")
+ okBtn.Name = "OkBtn"
+ okBtn.Text = "OK"
+ okBtn.Modal = true
+ okBtn.Size = UDim2.new(0.3, 0, 0, 45)
+ okBtn.Position = UDim2.new(0.35, 0, .975, -50)
+ okBtn.Font = Enum.Font.SourceSansBold
+ okBtn.FontSize = Enum.FontSize.Size18
+ okBtn.BackgroundTransparency = 1
+ okBtn.TextColor3 = Color3.new(1,1,1)
+ okBtn.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ okBtn.ZIndex = baseZIndex + 2
+ okBtn.MouseButton1Click:connect(
+ function()
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end)
+ okBtn.Parent = helpDialog
+
+ robloxLock(shield)
+ return shield
+end
+
+local function createLeaveConfirmationMenu(baseZIndex,shield)
+ local frame = Instance.new("Frame")
+ frame.Name = "LeaveConfirmationMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+ frame.Position = UDim2.new(0,0,2,400)
+ frame.ZIndex = baseZIndex + 4
+
+ local yesButton = createTextButton("Leave",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,313,0.8,0))
+ yesButton.Name = "YesButton"
+ yesButton.ZIndex = baseZIndex + 4
+ yesButton.Parent = frame
+ yesButton.Modal = true
+ yesButton:SetVerb("Exit")
+
+ local noButton = createTextButton("Stay",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,90,0.8,0))
+ noButton.Name = "NoButton"
+ noButton.Parent = frame
+ noButton.ZIndex = baseZIndex + 4
+ noButton.MouseButton1Click:connect(function()
+ goToMenu(shield.Settings.SettingsStyle,"GameMainMenu","down",UDim2.new(0,525,0,430))
+ shield.Settings:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end)
+
+ local leaveText = Instance.new("TextLabel")
+ leaveText.Name = "LeaveText"
+ leaveText.Text = "Leave this game?"
+ leaveText.Size = UDim2.new(1,0,0.8,0)
+ leaveText.TextWrap = true
+ leaveText.TextColor3 = Color3.new(1,1,1)
+ leaveText.Font = Enum.Font.SourceSansBold
+ leaveText.FontSize = Enum.FontSize.Size36
+ leaveText.BackgroundTransparency = 1
+ leaveText.ZIndex = baseZIndex + 4
+ leaveText.Parent = frame
+
+ return frame
+end
+
+local function createResetConfirmationMenu(baseZIndex,shield)
+ local frame = Instance.new("Frame")
+ frame.Name = "ResetConfirmationMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+ frame.Position = UDim2.new(0,0,2,400)
+ frame.ZIndex = baseZIndex + 4
+
+ local yesButton = createTextButton("Reset",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,313,0,280))
+ yesButton.Name = "YesButton"
+ yesButton.ZIndex = baseZIndex + 4
+ yesButton.Parent = frame
+ yesButton.Modal = true
+ yesButton.MouseButton1Click:connect(function()
+ resumeGameFunction(shield)
+ resetLocalCharacter()
+ end)
+
+ local noButton = createTextButton("Cancel",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,90,0,280))
+ noButton.Name = "NoButton"
+ noButton.Parent = frame
+ noButton.ZIndex = baseZIndex + 4
+ noButton.MouseButton1Click:connect(function()
+ goToMenu(shield.Settings.SettingsStyle,"GameMainMenu","down",UDim2.new(0,525,0,430))
+ shield.Settings:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end)
+
+ local resetCharacterText = Instance.new("TextLabel")
+ resetCharacterText.Name = "ResetCharacterText"
+ resetCharacterText.Text = "Are you sure you want to reset your character?"
+ resetCharacterText.Size = UDim2.new(1,0,0.8,0)
+ resetCharacterText.TextWrap = true
+ resetCharacterText.TextColor3 = Color3.new(1,1,1)
+ resetCharacterText.Font = Enum.Font.SourceSansBold
+ resetCharacterText.FontSize = Enum.FontSize.Size36
+ resetCharacterText.BackgroundTransparency = 1
+ resetCharacterText.ZIndex = baseZIndex + 4
+ resetCharacterText.Parent = frame
+
+ local fineResetCharacterText = resetCharacterText:Clone()
+ fineResetCharacterText.Name = "FineResetCharacterText"
+ fineResetCharacterText.Text = "You will be put back on a spawn point"
+ fineResetCharacterText.Size = UDim2.new(0,303,0,18)
+ fineResetCharacterText.Position = UDim2.new(0, 109, 0, 215)
+ fineResetCharacterText.FontSize = Enum.FontSize.Size18
+ fineResetCharacterText.Parent = frame
+
+ return frame
+end
+
+local function createGameMainMenu(baseZIndex, shield)
+
+ local buttonTop = 54
+
+ local gameMainMenuFrame = Instance.new("Frame")
+ gameMainMenuFrame.Name = "GameMainMenu"
+ gameMainMenuFrame.BackgroundTransparency = 1
+ gameMainMenuFrame.Size = UDim2.new(1,0,1,0)
+ gameMainMenuFrame.ZIndex = baseZIndex + 4
+ gameMainMenuFrame.Parent = settingsFrame
+
+ -- GameMainMenu Children
+
+ -- RESUME GAME
+ local resumeGameButton = createTextButton("Resume Game",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ resumeGameButton.Name = "resumeGameButton"
+ resumeGameButton.ZIndex = baseZIndex + 4
+ resumeGameButton.Parent = gameMainMenuFrame
+ resumeGameButton.Modal = true
+ resumeGameButton.MouseButton1Click:connect(function() resumeGameFunction(shield) end)
+ buttonTop = buttonTop + 51
+
+ -- RESET CHARACTER
+ local resetButton = createTextButton("Reset Character",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ resetButton.Name = "ResetButton"
+ resetButton.ZIndex = baseZIndex + 4
+ resetButton.Parent = gameMainMenuFrame
+ buttonTop = buttonTop + 51
+
+ -- GAME SETTINGS
+ local gameSettingsButton = createTextButton("Game Settings",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ gameSettingsButton.Name = "SettingsButton"
+ gameSettingsButton.ZIndex = baseZIndex + 4
+ gameSettingsButton.Parent = gameMainMenuFrame
+ buttonTop = buttonTop + 51
+
+ -- HELP BUTTON
+ local robloxHelpButton = createTextButton("Help",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,164,0,50),UDim2.new(0,92,0,buttonTop))
+ robloxHelpButton.Name = "HelpButton"
+ robloxHelpButton.ZIndex = baseZIndex + 4
+ robloxHelpButton.Parent = gameMainMenuFrame
+ robloxHelpButton.Visible = not touchClient
+ if macClient or touchClient then
+ robloxHelpButton.Size = UDim2.new(0,340,0,50)
+ robloxHelpButton.FontSize = Enum.FontSize.Size24
+ end
+
+ helpButton = robloxHelpButton
+
+ local helpDialog = createHelpDialog(baseZIndex)
+ helpDialog.Parent = gui
+
+ helpButton.MouseButton1Click:connect(
+ function()
+ table.insert(centerDialogs,helpDialog)
+ game.GuiService:AddCenterDialog(helpDialog, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ helpDialog.Visible = true
+ mainShield.Visible = false
+ end,
+ --HideFunction
+ function()
+ helpDialog.Visible = false
+ end)
+ end)
+ helpButton.Active = true
+
+ -- SCREEN SHOT
+ local screenshotButton = createTextButton("Screenshot",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,168,0,50),UDim2.new(0,264,0,buttonTop))
+ screenshotButton.Name = "ScreenshotButton"
+ screenshotButton.ZIndex = baseZIndex + 4
+ screenshotButton.Parent = gameMainMenuFrame
+ screenshotButton.Visible = not macClient and not touchClient
+ screenshotButton:SetVerb("Screenshot")
+
+ if not touchClient then
+ buttonTop = buttonTop + 51
+ end
+
+ -- REPORT ABUSE
+ local reportAbuseButton = createTextButton("Report Abuse",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,164,0,50),UDim2.new(0,92,0,buttonTop))
+ reportAbuseButton.Name = "ReportAbuseButton"
+ reportAbuseButton.ZIndex = baseZIndex + 4
+ reportAbuseButton.Parent = gameMainMenuFrame
+ if macClient or touchClient then
+ reportAbuseButton.Size = UDim2.new(0,340,0,50)
+ reportAbuseButton.FontSize = Enum.FontSize.Size24
+ end
+
+ -- RECORD VIDEO
+ local recordVideoButton = createTextButton("Record Video",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,168,0,50),UDim2.new(0,264,0,buttonTop))
+ recordVideoButton.Name = "RecordVideoButton"
+ recordVideoButton.ZIndex = baseZIndex + 4
+ recordVideoButton.Parent = gameMainMenuFrame
+ recordVideoButton.Visible = not macClient and not touchClient
+ recordVideoButton:SetVerb("RecordToggle")
+
+ local stopRecordButton = Instance.new("ImageButton")
+ stopRecordButton.Name = "StopRecordButton"
+ stopRecordButton.BackgroundTransparency = 1
+ stopRecordButton.Image = "rbxasset://textures/ui/RecordStop.png"
+ stopRecordButton.Size = UDim2.new(0,59,0,27)
+ stopRecordButton:SetVerb("RecordToggle")
+
+ stopRecordButton.MouseButton1Click:connect(function() recordVideoClick(recordVideoButton, stopRecordButton) end)
+ stopRecordButton.Visible = false
+ stopRecordButton.Parent = gui
+ buttonTop = buttonTop + 51
+
+ -- LEAVE GAME
+ local leaveGameButton = createTextButton("Leave Game",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ leaveGameButton.Name = "LeaveGameButton"
+ leaveGameButton.ZIndex = baseZIndex + 4
+ leaveGameButton.Parent = gameMainMenuFrame
+
+ return gameMainMenuFrame
+end
+
+local function createGameSettingsMenu(baseZIndex, shield)
+ local gameSettingsMenuFrame = Instance.new("Frame")
+ gameSettingsMenuFrame.Name = "GameSettingsMenu"
+ gameSettingsMenuFrame.BackgroundTransparency = 1
+ gameSettingsMenuFrame.Size = UDim2.new(1,0,1,0)
+ gameSettingsMenuFrame.ZIndex = baseZIndex + 4
+
+ local itemTop = 0
+ if game:GetService("GuiService"):GetScreenResolution().y <= 500 then
+ itemTop = 50
+ end
+ ----------------------------------------------------------------------------------------------------
+ -- C A M E R A C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+
+ if not touchClient then
+ local cameraLabel = Instance.new("TextLabel")
+ cameraLabel.Name = "CameraLabel"
+ cameraLabel.Text = "Character & Camera Controls"
+ cameraLabel.Font = Enum.Font.SourceSansBold
+ cameraLabel.FontSize = Enum.FontSize.Size18
+ cameraLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ cameraLabel.Size = UDim2.new(0,224,0,18)
+ cameraLabel.TextColor3 = Color3I(255,255,255)
+ cameraLabel.TextXAlignment = Enum.TextXAlignment.Left
+ cameraLabel.BackgroundTransparency = 1
+ cameraLabel.ZIndex = baseZIndex + 4
+ cameraLabel.Parent = gameSettingsMenuFrame
+
+ local mouseLockLabel = game.CoreGui.RobloxGui:FindFirstChild("MouseLockLabel",true)
+
+ local enumItems = Enum.ControlMode:GetEnumItems()
+ local enumNames = {}
+ local enumNameToItem = {}
+ for i,obj in ipairs(enumItems) do
+ enumNames[i] = obj.Name
+ enumNameToItem[obj.Name] = obj
+ end
+
+ local cameraDropDown
+ cameraDropDown, updateCameraDropDownSelection = RbxGui.CreateDropDownMenu(enumNames,
+ function(text)
+ UserSettings().GameSettings.ControlMode = enumNameToItem[text]
+
+ pcall(function()
+ if mouseLockLabel and UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ mouseLockLabel.Visible = true
+ elseif mouseLockLabel then
+ mouseLockLabel.Visible = false
+ end
+ end)
+ end, false, true, baseZIndex)
+ cameraDropDown.Name = "CameraField"
+ cameraDropDown.ZIndex = baseZIndex + 4
+ cameraDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ cameraDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ cameraDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ cameraDropDown.Size = UDim2.new(0,200,0,32)
+ cameraDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- V I D E O C A P T U R E S E T T I N G S
+ ----------------------------------------------------------------------------------------------------
+
+ local syncVideoCaptureSetting = nil
+
+ if not macClient and not touchClient then
+ local videoCaptureLabel = Instance.new("TextLabel")
+ videoCaptureLabel.Name = "VideoCaptureLabel"
+ videoCaptureLabel.Text = "After Capturing Video"
+ videoCaptureLabel.Font = Enum.Font.SourceSansBold
+ videoCaptureLabel.FontSize = Enum.FontSize.Size18
+ videoCaptureLabel.Position = UDim2.new(0,32,0,itemTop + 6)
+ videoCaptureLabel.Size = UDim2.new(0,164,0,18)
+ videoCaptureLabel.BackgroundTransparency = 1
+ videoCaptureLabel.TextColor3 = Color3I(255,255,255)
+ videoCaptureLabel.TextXAlignment = Enum.TextXAlignment.Left
+ videoCaptureLabel.ZIndex = baseZIndex + 4
+ videoCaptureLabel.Parent = gameSettingsMenuFrame
+
+ local videoNames = {}
+ local videoNameToItem = {}
+ videoNames[1] = "Just Save to Disk"
+ videoNameToItem[videoNames[1]] = Enum.UploadSetting["Never"]
+ videoNames[2] = "Upload to YouTube"
+ videoNameToItem[videoNames[2]] = Enum.UploadSetting["Ask me first"]
+
+ local videoCaptureDropDown = nil
+ videoCaptureDropDown, updateVideoCaptureDropDownSelection = RbxGui.CreateDropDownMenu(videoNames,
+ function(text)
+ UserSettings().GameSettings.VideoUploadPromptBehavior = videoNameToItem[text]
+ end, false, true, baseZIndex)
+ videoCaptureDropDown.Name = "VideoCaptureField"
+ videoCaptureDropDown.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ videoCaptureDropDown.Size = UDim2.new(0,200,0,32)
+ videoCaptureDropDown.Parent = gameSettingsMenuFrame
+
+ syncVideoCaptureSetting = function()
+ if UserSettings().GameSettings.VideoUploadPromptBehavior == Enum.UploadSetting["Never"] then
+ updateVideoCaptureDropDownSelection(videoNames[1])
+ elseif UserSettings().GameSettings.VideoUploadPromptBehavior == Enum.UploadSetting["Ask me first"] then
+ updateVideoCaptureDropDownSelection(videoNames[2])
+ else
+ UserSettings().GameSettings.VideoUploadPromptBehavior = Enum.UploadSetting["Ask me first"]
+ updateVideoCaptureDropDownSelection(videoNames[2])
+ end
+ end
+ itemTop = itemTop + 35
+ end
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- C U S T O M C A M E R A C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+
+ local smartCameraLabel = Instance.new("TextLabel")
+ smartCameraLabel.Name = "SmartCameraLabel"
+ smartCameraLabel.Text = "Camera Mode"
+ smartCameraLabel.Font = Enum.Font.SourceSansBold
+ smartCameraLabel.FontSize = Enum.FontSize.Size18
+ smartCameraLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ smartCameraLabel.Size = UDim2.new(0,224,0,18)
+ smartCameraLabel.TextColor3 = Color3I(255,255,255)
+ smartCameraLabel.TextXAlignment = Enum.TextXAlignment.Left
+ smartCameraLabel.BackgroundTransparency = 1
+ smartCameraLabel.ZIndex = baseZIndex + 4
+ smartCameraLabel.Parent = gameSettingsMenuFrame
+
+ local smartEnumItems = nil
+ smartEnumItems = Enum.CustomCameraMode:GetEnumItems()
+
+ local smartEnumNames = {}
+ local smartEnumNameToItem = {}
+
+ for i,obj in pairs(smartEnumItems) do
+ local displayName = obj.Name
+ if (obj.Name == "Default") then
+ displayName = customCameraDefaultType
+ end
+ smartEnumNames[i] = displayName
+ smartEnumNameToItem[displayName] = obj.Value
+ end
+
+ local smartCameraDropDown
+ smartCameraDropDown, updateSmartCameraDropDownSelection = RbxGui.CreateDropDownMenu(smartEnumNames,
+ function(text)
+ UserSettings().GameSettings.CameraMode = smartEnumNameToItem[text]
+ end, false, true, baseZIndex)
+ smartCameraDropDown.Name = "SmartCameraField"
+ smartCameraDropDown.ZIndex = baseZIndex + 4
+ smartCameraDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ smartCameraDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ smartCameraDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ smartCameraDropDown.Size = UDim2.new(0,200,0,32)
+ smartCameraDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- T O U C H M O V E M E N T C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+ if (touchClient) then
+ local touchMovementLabel = Instance.new("TextLabel")
+ touchMovementLabel.Name = "TouchMovementLabel"
+ touchMovementLabel.Text = "Movement Mode"
+ touchMovementLabel.Font = Enum.Font.SourceSansBold
+ touchMovementLabel.FontSize = Enum.FontSize.Size18
+ touchMovementLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ touchMovementLabel.Size = UDim2.new(0,224,0,18)
+ touchMovementLabel.TextColor3 = Color3I(255,255,255)
+ touchMovementLabel.TextXAlignment = Enum.TextXAlignment.Left
+ touchMovementLabel.BackgroundTransparency = 1
+ touchMovementLabel.ZIndex = baseZIndex + 4
+ touchMovementLabel.Parent = gameSettingsMenuFrame
+
+ local touchEnumItems = Enum.TouchMovementMode:GetEnumItems()
+ local touchEnumNames = {}
+ local touchEnumNameToItem = {}
+ for i,obj in ipairs(touchEnumItems) do
+ local displayName = obj.Name
+ if (obj.Name == "Default") then
+ displayName = "Default (Thumbstick)"
+ end
+ touchEnumNames[i] = displayName
+ touchEnumNameToItem[displayName] = obj
+ end
+
+ local touchMovementDropDown
+ touchMovementDropDown, updateTouchMovementDropDownSelection = RbxGui.CreateDropDownMenu(touchEnumNames,
+ function(text)
+ UserSettings().GameSettings.TouchMovementMode = touchEnumNameToItem[text]
+ end, false, true, baseZIndex)
+ touchMovementDropDown.Name = "touchMovementField"
+ touchMovementDropDown.ZIndex = baseZIndex + 4
+ touchMovementDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ touchMovementDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ touchMovementDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ touchMovementDropDown.Size = UDim2.new(0,200,0,32)
+ touchMovementDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- F U L L S C R E E N M O D E
+ ----------------------------------------------------------------------------------------------------
+
+ local fullscreenText = nil
+ local fullscreenShortcut = nil
+ local fullscreenCheckbox = nil
+
+ if not touchClient then
+
+ itemTop = itemTop + 15
+
+ fullscreenText = Instance.new("TextLabel")
+ fullscreenText.Name = "FullscreenText"
+ fullscreenText.Text = "Fullscreen Mode"
+
+ fullscreenText.Position = UDim2.new(0,31,0,itemTop + 6)
+ fullscreenText.Size = UDim2.new(0,224,0,18)
+
+ fullscreenText.Font = Enum.Font.SourceSansBold
+ fullscreenText.FontSize = Enum.FontSize.Size18
+ fullscreenText.TextXAlignment = Enum.TextXAlignment.Left
+ fullscreenText.TextColor3 = Color3.new(1,1,1)
+ fullscreenText.ZIndex = baseZIndex + 4
+ fullscreenText.BackgroundTransparency = 1
+ fullscreenText.Parent = gameSettingsMenuFrame
+
+ fullscreenCheckbox = createTextButton("",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,32,0,32),UDim2.new(0, 270, 0, itemTop- 4))
+ fullscreenCheckbox.Name = "FullscreenCheckbox"
+ fullscreenCheckbox.ZIndex = baseZIndex + 4
+ fullscreenCheckbox.Parent = gameSettingsMenuFrame
+ fullscreenCheckbox:SetVerb("ToggleFullScreen")
+ if UserSettings().GameSettings:InFullScreen() then fullscreenCheckbox.Text = "X" end
+ if hasGraphicsSlider then
+ UserSettings().GameSettings.FullscreenChanged:connect(function(isFullscreen)
+ if isFullscreen then
+ fullscreenCheckbox.Text = "X"
+ else
+ fullscreenCheckbox.Text = ""
+ end
+ end)
+ else
+ fullscreenCheckbox.MouseButton1Click:connect(function()
+ if fullscreenCheckbox.Text == "" then
+ fullscreenCheckbox.Text = "X"
+ else
+ fullscreenCheckbox.Text = ""
+ end
+ end)
+ end
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- G R A P H I C S S L I D E R
+ ----------------------------------------------------------------------------------------------------
+ local graphicsSlider, graphicsLevel = nil
+ if hasGraphicsSlider then
+ local graphicsQualityYOffset = -45
+
+ local qualityText = Instance.new("TextLabel")
+ qualityText.Name = "QualityText"
+ qualityText.Text = "Graphics Quality"
+ qualityText.Size = UDim2.new(0,224,0,18)
+ qualityText.Position = UDim2.new(0,31,0,239 + graphicsQualityYOffset)
+
+ qualityText.TextXAlignment = Enum.TextXAlignment.Left
+ qualityText.Font = Enum.Font.SourceSansBold
+ qualityText.FontSize = Enum.FontSize.Size18
+ qualityText.TextColor3 = Color3.new(1,1,1)
+ qualityText.ZIndex = baseZIndex + 4
+ qualityText.BackgroundTransparency = 1
+ qualityText.Parent = gameSettingsMenuFrame
+ qualityText.Visible = not inStudioMode
+
+ local autoText = qualityText:clone()
+ autoText.Name = "AutoText"
+ autoText.Text = "Auto"
+ autoText.Position = UDim2.new(0,270,0,214 + graphicsQualityYOffset)
+ autoText.TextColor3 = Color3.new(128/255,128/255,128/255)
+ autoText.Size = UDim2.new(0,34,0,18)
+ autoText.Parent = gameSettingsMenuFrame
+ autoText.Visible = not inStudioMode
+
+ local fasterText = autoText:clone()
+ fasterText.Name = "FasterText"
+ fasterText.Text = "Faster"
+ fasterText.Position = UDim2.new(0,185,0,274 + graphicsQualityYOffset)
+ fasterText.TextColor3 = Color3.new(95,95,95)
+ fasterText.FontSize = Enum.FontSize.Size14
+ fasterText.Parent = gameSettingsMenuFrame
+ fasterText.Visible = not inStudioMode
+
+ local betterQualityText = autoText:clone()
+ betterQualityText.Name = "BetterQualityText"
+ betterQualityText.Text = "Better Quality"
+ betterQualityText.TextWrap = true
+ betterQualityText.Size = UDim2.new(0,41,0,28)
+ betterQualityText.Position = UDim2.new(0,390,0,269 + graphicsQualityYOffset)
+ betterQualityText.TextColor3 = Color3.new(95,95,95)
+ betterQualityText.FontSize = Enum.FontSize.Size14
+ betterQualityText.Parent = gameSettingsMenuFrame
+ betterQualityText.Visible = not inStudioMode
+
+ local autoGraphicsButton = createTextButton("X",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,32,0,32),UDim2.new(0,270,0,230 + graphicsQualityYOffset))
+ autoGraphicsButton.Name = "AutoGraphicsButton"
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ autoGraphicsButton.Parent = gameSettingsMenuFrame
+ autoGraphicsButton.Visible = not inStudioMode
+
+ graphicsSlider, graphicsLevel = RbxGui.CreateSliderNew(GraphicsQualityLevels,150,UDim2.new(0, 230, 0, 280 + graphicsQualityYOffset)) -- graphics - 1 because slider starts at 1 instead of 0
+ graphicsSlider.Parent = gameSettingsMenuFrame
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 5
+ graphicsSlider.Visible = not inStudioMode
+ graphicsLevel.Value = math.floor((settings().Rendering:GetMaxQualityLevel() - 1)/2)
+
+ local graphicsSetter = Instance.new("TextBox")
+ graphicsSetter.Name = "GraphicsSetter"
+ graphicsSetter.BackgroundColor3 = Color3.new(0,0,0)
+ graphicsSetter.BorderColor3 = Color3.new(128/255,128/255,128/255)
+ graphicsSetter.Size = UDim2.new(0,50,0,25)
+ graphicsSetter.Position = UDim2.new(0,450,0,269 + graphicsQualityYOffset)
+ graphicsSetter.TextColor3 = Color3.new(1,1,1)
+ graphicsSetter.Font = Enum.Font.SourceSansBold
+ graphicsSetter.FontSize = Enum.FontSize.Size18
+ graphicsSetter.Text = "Auto"
+ graphicsSetter.ZIndex = 1
+ graphicsSetter.TextWrap = true
+ graphicsSetter.Parent = gameSettingsMenuFrame
+ graphicsSetter.Visible = not inStudioMode
+
+ local isAutoGraphics = true
+ if not inStudioMode then
+ isAutoGraphics = (UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic)
+ else
+ settings().Rendering.EnableFRM = false
+ end
+
+ local listenToGraphicsLevelChange = true
+
+ local function setAutoGraphicsGui(active)
+ isAutoGraphics = active
+ if active then
+ autoGraphicsButton.Text = "X"
+ betterQualityText.ZIndex = 1
+ fasterText.ZIndex = 1
+ graphicsSlider.Bar.ZIndex = 1
+ graphicsSlider.BarLeft.ZIndex = 1
+ graphicsSlider.BarRight.ZIndex = 1
+ graphicsSlider.Bar.Fill.ZIndex = 1
+ graphicsSlider.FillLeft.ZIndex = 1
+ graphicsSlider.Bar.Slider.ZIndex = 1
+ graphicsSetter.ZIndex = 1
+ graphicsSetter.Text = "Auto"
+ else
+ autoGraphicsButton.Text = ""
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 6
+ graphicsSlider.BarLeft.ZIndex = baseZIndex + 4
+ graphicsSlider.BarRight.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Fill.ZIndex = baseZIndex + 5
+ graphicsSlider.FillLeft.ZIndex = baseZIndex + 5
+ betterQualityText.ZIndex = baseZIndex + 4
+ fasterText.ZIndex = baseZIndex + 4
+ graphicsSetter.ZIndex = baseZIndex + 4
+ end
+ end
+
+ local function goToAutoGraphics()
+ setAutoGraphicsGui(true)
+
+ UserSettings().GameSettings.SavedQualityLevel = Enum.SavedQualitySetting.Automatic
+
+ settings().Rendering.QualityLevel = Enum.QualityLevel.Automatic
+ end
+
+ local function setGraphicsQualityLevel(newLevel)
+ local percentage = newLevel/GraphicsQualityLevels
+ local newSetting = math.floor((settings().Rendering:GetMaxQualityLevel() - 1) * percentage)
+ if newSetting == 20 then -- Level 20 is the same as level 21, except it doesn't render ambient occlusion
+ newSetting = 21
+ elseif newLevel == 1 then -- make sure we can go to lowest settings (for terrible computers)
+ newSetting = 1
+ elseif newSetting > settings().Rendering:GetMaxQualityLevel() then
+ newSetting = settings().Rendering:GetMaxQualityLevel() - 1
+ end
+
+ UserSettings().GameSettings.SavedQualityLevel = newLevel
+ settings().Rendering.QualityLevel = newSetting
+ end
+
+ local function goToManualGraphics(explicitLevel)
+ setAutoGraphicsGui(false)
+
+ if explicitLevel then
+ graphicsLevel.Value = explicitLevel
+ else
+ graphicsLevel.Value = math.floor((settings().Rendering.AutoFRMLevel/(settings().Rendering:GetMaxQualityLevel() - 1)) * GraphicsQualityLevels)
+ end
+
+ if explicitLevel == graphicsLevel.Value then -- make sure we are actually in right graphics mode
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ end
+
+ if not explicitLevel then
+ UserSettings().GameSettings.SavedQualityLevel = graphicsLevel.Value
+ end
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ end
+
+ local function showAutoGraphics()
+ autoText.ZIndex = baseZIndex + 4
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ end
+
+ local function hideAutoGraphics()
+ autoText.ZIndex = 1
+ autoGraphicsButton.ZIndex = 1
+ end
+
+ local function showManualGraphics()
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 5
+ betterQualityText.ZIndex = baseZIndex + 4
+ fasterText.ZIndex = baseZIndex + 4
+ graphicsSetter.ZIndex = baseZIndex + 4
+ end
+
+ local function hideManualGraphics()
+ betterQualityText.ZIndex = 1
+ fasterText.ZIndex = 1
+ graphicsSlider.Bar.ZIndex = 1
+ graphicsSlider.Bar.Slider.ZIndex = 1
+ graphicsSetter.ZIndex = 1
+ end
+
+ local function translateSavedQualityLevelToInt(savedQualityLevel)
+ if savedQualityLevel == Enum.SavedQualitySetting.Automatic then
+ return 0
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel1 then
+ return 1
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel2 then
+ return 2
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel3 then
+ return 3
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel4 then
+ return 4
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel5 then
+ return 5
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel6 then
+ return 6
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel7 then
+ return 7
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel8 then
+ return 8
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel9 then
+ return 9
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel10 then
+ return 10
+ end
+ end
+
+ local function enableGraphicsWidget()
+ settings().Rendering.EnableFRM = true
+
+ isAutoGraphics = (UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic)
+ if isAutoGraphics then
+ showAutoGraphics()
+ goToAutoGraphics()
+ else
+ showAutoGraphics()
+ showManualGraphics()
+ goToManualGraphics(translateSavedQualityLevelToInt(UserSettings().GameSettings.SavedQualityLevel))
+ end
+ end
+
+ local function disableGraphicsWidget()
+ hideManualGraphics()
+ hideAutoGraphics()
+ settings().Rendering.EnableFRM = false
+ end
+
+ graphicsSetter.FocusLost:connect(function()
+ if isAutoGraphics then
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ return
+ end
+
+ local newGraphicsValue = tonumber(graphicsSetter.Text)
+ if newGraphicsValue == nil then
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ return
+ end
+
+ if newGraphicsValue < 1 then newGraphicsValue = 1
+ elseif newGraphicsValue >= settings().Rendering:GetMaxQualityLevel() then
+ newGraphicsValue = settings().Rendering:GetMaxQualityLevel() - 1
+ end
+
+ graphicsLevel.Value = newGraphicsValue
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ end)
+
+ graphicsLevel.Changed:connect(function(prop)
+ if isAutoGraphics then return end
+ if not listenToGraphicsLevelChange then return end
+
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ end)
+
+ -- setup our graphic mode on load
+ if inStudioMode or UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic then
+ if inStudioMode then
+ settings().Rendering.EnableFRM = false
+ disableGraphicsWidget()
+ else
+ settings().Rendering.EnableFRM = true
+ goToAutoGraphics()
+ end
+ else
+ settings().Rendering.EnableFRM = true
+ goToManualGraphics(translateSavedQualityLevelToInt(UserSettings().GameSettings.SavedQualityLevel))
+ end
+
+ autoGraphicsButton.MouseButton1Click:connect(function()
+ if inStudioMode and not game.Players.LocalPlayer then return end
+
+ if not isAutoGraphics then
+ goToAutoGraphics()
+ else
+ goToManualGraphics(graphicsLevel.Value)
+ end
+ end)
+
+ local lastUpdate = nil
+ game.GraphicsQualityChangeRequest:connect(function(graphicsIncrease)
+ if isAutoGraphics then return end -- only can set graphics in manual mode
+
+ if graphicsIncrease then
+ if (graphicsLevel.Value + 1) > GraphicsQualityLevels then return end
+ graphicsLevel.Value = graphicsLevel.Value + 1
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+
+ game:GetService("GuiService"):SendNotification("Graphics Quality",
+ "Increased to (" .. graphicsSetter.Text .. ")",
+ "",
+ 2,
+ function()
+ end)
+ else
+ if (graphicsLevel.Value - 1) <= 0 then return end
+ graphicsLevel.Value = graphicsLevel.Value - 1
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+
+ game:GetService("GuiService"):SendNotification("Graphics Quality",
+ "Decreased to (" .. graphicsSetter.Text .. ")",
+ "",
+ 2,
+ function()
+ end)
+ end
+ end)
+
+ game.Players.PlayerAdded:connect(function(player)
+ if player == game.Players.LocalPlayer and inStudioMode then
+ enableGraphicsWidget()
+ end
+ end)
+ game.Players.PlayerRemoving:connect(function(player)
+ if player == game.Players.LocalPlayer and inStudioMode then
+ disableGraphicsWidget()
+ end
+ end)
+
+ local wasManualGraphics = (settings().Rendering.QualityLevel ~= Enum.QualityLevel.Automatic)
+ if inStudioMode and not game.Players.LocalPlayer then
+ disableGraphicsWidget()
+ elseif inStudioMode then
+ enableGraphicsWidget()
+ end
+ if hasGraphicsSlider then
+ UserSettings().GameSettings.StudioModeChanged:connect(function(isStudioMode)
+ inStudioMode = isStudioMode
+ if isStudioMode then
+ wasManualGraphics = (settings().Rendering.QualityLevel ~= Enum.QualityLevel.Automatic)
+ goToAutoGraphics()
+ autoGraphicsButton.ZIndex = 1
+ autoText.ZIndex = 1
+ else
+ if wasManualGraphics then
+ goToManualGraphics()
+ end
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ autoText.ZIndex = baseZIndex + 4
+ end
+ end)
+ end
+
+ if graphicsSlider and graphicsSlider.Bar and graphicsSlider.Visible then
+ itemTop = graphicsSlider.Bar.Position.Y.Offset + 20
+ end
+ end
+ ----------------------------------------------------------------------------------------------------
+ -- V O L U M E S L I D E R
+ ----------------------------------------------------------------------------------------------------
+ if hasVolumeSlider then
+ local maxVolumeLevel = 256
+
+ local volumeText = Instance.new("TextLabel")
+ volumeText.Name = "VolumeText"
+ volumeText.Text = "Volume"
+ volumeText.Size = UDim2.new(0,224,0,18)
+
+ local volumeTextOffset = 25
+ if graphicsSlider and not graphicsSlider.Visible then
+ volumeTextOffset = volumeTextOffset + 30
+ end
+ volumeText.Position = UDim2.new(0,31,0, itemTop + volumeTextOffset)
+
+ volumeText.TextXAlignment = Enum.TextXAlignment.Left
+ volumeText.Font = Enum.Font.SourceSansBold
+ volumeText.FontSize = Enum.FontSize.Size18
+ volumeText.TextColor3 = Color3.new(1,1,1)
+ volumeText.ZIndex = baseZIndex + 4
+ volumeText.BackgroundTransparency = 1
+ volumeText.Parent = gameSettingsMenuFrame
+ volumeText.Visible = true
+
+ local volumeSliderOffset = 32
+ if graphicsSlider and not graphicsSlider.Visible then
+ volumeSliderOffset = volumeSliderOffset + 30
+ end
+ local volumeSlider, volumeLevel = RbxGui.CreateSliderNew( maxVolumeLevel,256,UDim2.new(0, 180, 0, itemTop + volumeSliderOffset) )
+ volumeSlider.Parent = gameSettingsMenuFrame
+ volumeSlider.Bar.ZIndex = baseZIndex + 3
+ volumeSlider.Bar.Slider.ZIndex = baseZIndex + 4
+ volumeSlider.BarLeft.ZIndex = baseZIndex + 3
+ volumeSlider.BarRight.ZIndex = baseZIndex + 3
+ volumeSlider.Bar.Fill.ZIndex = baseZIndex + 3
+ volumeSlider.FillLeft.ZIndex = baseZIndex + 3
+ volumeSlider.Visible = true
+ volumeLevel.Value = math.min(math.max(UserSettings().GameSettings.MasterVolume * maxVolumeLevel, 1), maxVolumeLevel)
+
+ volumeLevel.Changed:connect(function(prop)
+ local volume = volumeLevel.Value - 1 -- smallest value is 1, so need to subtract one for muting
+ UserSettings().GameSettings.MasterVolume = volume/maxVolumeLevel
+ end)
+
+ itemTop = itemTop + volumeSliderOffset
+ end
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- O K B U T T O N
+ ----------------------------------------------------------------------------------------------------
+
+
+ local backButton
+ if hasGraphicsSlider then
+ backButton = createTextButton("OK",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,180,0,50),UDim2.new(0,170,0,315))
+ backButton.Modal = true
+ else
+ backButton = createTextButton("OK",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,180,0,50),UDim2.new(0,170,0,270))
+ backButton.Modal = true
+ end
+
+ backButton.Name = "BackButton"
+ backButton.ZIndex = baseZIndex + 4
+ backButton.Parent = gameSettingsMenuFrame
+
+ return gameSettingsMenuFrame
+end
+
+local showMainMenu = nil
+
+if LoadLibrary then
+ RbxGui = LoadLibrary("RbxGui")
+ local baseZIndex = 4
+if UserSettings then
+
+ waitForChild(gui,"TopLeftControl")
+ waitForChild(gui,"BottomLeftControl")
+
+
+ local settingButtonParent = gui:WaitForChild("TopLeftControl")
+ local createSettingsDialog = function()
+ if touchClient then
+ waitForChild(gui,"TopLeftControl")
+ else
+ settingButtonParent = gui:WaitForChild("BottomLeftControl")
+ end
+
+ settingsButton = settingButtonParent:FindFirstChild("SettingsButton")
+
+ if settingsButton == nil then
+ settingsButton = Instance.new("ImageButton")
+ settingsButton.Name = "SettingsButton"
+ settingsButton.Image = "rbxasset://textures/ui/homeButton.png"
+ settingsButton.BackgroundTransparency = 1
+ settingsButton.Active = false
+ settingsButton.Size = UDim2.new(0,36,0,28)
+ if (touchClient) then
+ settingsButton.Position = UDim2.new(0,2,0,5)
+ else
+ settingsButton.Position = UDim2.new(0, 15, 1, -42)
+ end
+ settingsButton.Parent = settingButtonParent
+ end
+
+ local shield = Instance.new("TextButton")
+ shield.Text = ""
+ shield.Name = "UserSettingsShield"
+ shield.Active = true
+ shield.AutoButtonColor = false
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 2
+ mainShield = shield
+
+ local frame = Instance.new("Frame")
+ frame.Name = "Settings"
+ frame.Position = UDim2.new(0.5, -262, -0.5, -200)
+ frame.Size = UDim2.new(0, 525, 0, 430)
+ frame.BackgroundTransparency = 1
+ frame.Active = true
+ frame.Parent = shield
+
+ local settingsFrame = Instance.new("Frame")
+ settingsFrame.Name = "SettingsStyle"
+ settingsFrame.Size = UDim2.new(1, 0, 1, 0)
+ settingsFrame.Style = Enum.FrameStyle.DropShadow
+ settingsFrame.Active = true
+ settingsFrame.ZIndex = baseZIndex + 3
+ settingsFrame.Parent = frame
+
+ local gameMainMenu = createGameMainMenu(baseZIndex, shield)
+ gameMainMenu.Parent = settingsFrame
+
+ gameMainMenu.ScreenshotButton.MouseButton1Click:connect(function()
+ backToGame(gameMainMenu.ScreenshotButton, shield, settingsButton)
+ end)
+
+ gameMainMenu.RecordVideoButton.MouseButton1Click:connect(function()
+ recordVideoClick(gameMainMenu.RecordVideoButton, gui.StopRecordButton)
+ backToGame(gameMainMenu.RecordVideoButton, shield, settingsButton)
+ end)
+
+ if settings():FindFirstChild("Game Options") then
+ pcall(function()
+ settings():FindFirstChild("Game Options").VideoRecordingChangeRequest:connect(function(recording)
+ recordingVideo = recording
+ setRecordGui(recording, gui.StopRecordButton, gameMainMenu.RecordVideoButton)
+ end)
+ end)
+ end
+
+ game.CoreGui.RobloxGui.Changed:connect(function(prop) -- We have stopped recording when we resize
+ if prop == "AbsoluteSize" and recordingVideo then
+ recordVideoClick(gameMainMenu.RecordVideoButton, gui.StopRecordButton)
+ end
+ end)
+
+ function localPlayerChange()
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ if game.Players.LocalPlayer then
+ settings().Rendering.EnableFRM = true
+ elseif inStudioMode then
+ settings().Rendering.EnableFRM = false
+ end
+ end
+
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ if game.Players.LocalPlayer ~= nil then
+ game.Players.LocalPlayer.Changed:connect(function()
+ localPlayerChange()
+ end)
+ else
+ delay(0,function()
+ waitForProperty(game.Players,"LocalPlayer")
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ game.Players.LocalPlayer.Changed:connect(function()
+ localPlayerChange()
+ end)
+ end)
+ end
+
+ gameMainMenu.ReportAbuseButton.Visible = game:FindFirstChild("NetworkClient")
+ -- TODO: remove line below when not testing report abuse
+ if (testReport) then
+ gameMainMenu.ReportAbuseButton.Visible = true
+ end
+ if not gameMainMenu.ReportAbuseButton.Visible then
+ game.ChildAdded:connect(function(child)
+ if child:IsA("NetworkClient") then
+ gameMainMenu.ReportAbuseButton.Visible = game:FindFirstChild("NetworkClient")
+ end
+ end)
+ end
+
+ gameMainMenu.ResetButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"ResetConfirmationMenu","up",UDim2.new(0,525,0,370))
+ end)
+
+ local leaveGameButton = gameMainMenu:FindFirstChild("LeaveGameButton")
+ if (leaveGameButton) then
+ gameMainMenu.LeaveGameButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"LeaveConfirmationMenu","down",UDim2.new(0,525,0,300))
+ end)
+ end
+
+ showMainMenu = function(overrideMenu, overrideDir, overrideSize)
+ if shield.Visible and overrideMenu then
+ goToMenu(settingsFrame,overrideMenu,overrideDir,overrideSize)
+ return
+ end
+
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --showFunction
+ function()
+ settingsButton.Active = false
+ if updateCameraDropDownSelection ~= nil then
+ updateCameraDropDownSelection(UserSettings().GameSettings.ControlMode.Name)
+ end
+
+ local cameraMode = UserSettings().GameSettings.CameraMode.Name
+ if (cameraMode == "Default") then
+ cameraMode = customCameraDefaultType
+ end
+ updateSmartCameraDropDownSelection(cameraMode)
+
+ if updateTouchMovementDropDownSelection ~= nil then
+ local moveMode = UserSettings().GameSettings.TouchMovementMode.Name
+ if (moveMode == "Default") then
+ moveMode = "Default (Thumbstick)"
+ end
+ updateTouchMovementDropDownSelection(moveMode)
+ end
+
+ pcall(function() game:GetService("UserInputService").OverrideMouseIconEnabled = true end)
+
+
+ if syncVideoCaptureSetting then
+ syncVideoCaptureSetting()
+ end
+
+ local menuToGoTo = "GameMainMenu"
+ local direction = "right"
+ local menuSize = UDim2.new(0,525,0,430)
+
+ if overrideMenu then
+ menuToGoTo = overrideMenu
+ end
+ if overrideDir then
+ direction = overrideDir
+ end
+ if overrideSize then
+ menuSize = overrideSize
+ end
+
+ goToMenu(settingsFrame,menuToGoTo,direction,menuSize)
+ shield.Visible = true
+ shield.Active = true
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end,
+ --hideFunction
+ function()
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ shield.Visible = false
+ settingsButton.Active = true
+ end)
+ end
+
+ game:GetService("GuiService").EscapeKeyPressed:connect(function()
+ if currentMenuSelection == nil then
+ showMainMenu()
+ elseif #lastMenuSelection > 0 then
+ if #centerDialogs > 0 then
+ for i = 1, #centerDialogs do
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ centerDialogs[i].Visible = false
+ end
+ centerDialogs = {}
+ end
+
+ goToMenu(lastMenuSelection[#lastMenuSelection]["container"],lastMenuSelection[#lastMenuSelection]["name"],
+ lastMenuSelection[#lastMenuSelection]["direction"],lastMenuSelection[#lastMenuSelection]["lastSize"])
+
+ table.remove(lastMenuSelection,#lastMenuSelection)
+ if #lastMenuSelection == 1 then -- apparently lua can't reduce count to 0... T_T
+ lastMenuSelection = {}
+ end
+ else
+ resumeGameFunction(shield)
+ end
+ end)
+
+ local gameSettingsMenu = createGameSettingsMenu(baseZIndex, shield)
+ gameSettingsMenu.Visible = false
+ gameSettingsMenu.Parent = settingsFrame
+
+ gameMainMenu.SettingsButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"GameSettingsMenu","left",UDim2.new(0,525,0,350))
+ end)
+
+ gameSettingsMenu.BackButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"GameMainMenu","right",UDim2.new(0,525,0,430))
+ end)
+
+ local resetConfirmationWindow = createResetConfirmationMenu(baseZIndex, shield)
+ resetConfirmationWindow.Visible = false
+ resetConfirmationWindow.Parent = settingsFrame
+
+ local leaveConfirmationWindow = createLeaveConfirmationMenu(baseZIndex,shield)
+ leaveConfirmationWindow.Visible = false
+ leaveConfirmationWindow.Parent = settingsFrame
+
+ robloxLock(shield)
+
+ settingsButton.MouseButton1Click:connect(
+ function()
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --showFunction
+ function()
+ settingsButton.Active = false
+ if updateCameraDropDownSelection ~= nil then
+ updateCameraDropDownSelection(UserSettings().GameSettings.ControlMode.Name)
+ end
+
+ local cameraMode = UserSettings().GameSettings.CameraMode.Name
+ if (cameraMode == "Default") then
+ cameraMode = customCameraDefaultType
+ end
+ updateSmartCameraDropDownSelection(cameraMode)
+
+ if updateTouchMovementDropDownSelection ~= nil then
+ local moveMode = UserSettings().GameSettings.TouchMovementMode.Name
+ if (moveMode == "Default") then
+ moveMode = "Default (Thumbstick)"
+ end
+ updateTouchMovementDropDownSelection(moveMode)
+ end
+
+ if syncVideoCaptureSetting then
+ syncVideoCaptureSetting()
+ end
+
+ goToMenu(settingsFrame,"GameMainMenu","right",UDim2.new(0,525,0,430))
+ shield.Visible = true
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end,
+ --hideFunction
+ function()
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ shield.Visible = false
+ settingsButton.Active = true
+ end)
+ end)
+
+ return shield
+ end
+
+ delay(0, function()
+ createSettingsDialog().Parent = gui
+
+ settingButtonParent.SettingsButton.Active = true
+-- settingButtonParent.SettingsButton.Position = UDim2.new(0,2,0,-2)
+
+ if mouseLockLabel and UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ mouseLockLabel.Visible = true
+ elseif mouseLockLabel then
+ mouseLockLabel.Visible = false
+ end
+
+ -- our script has loaded, get rid of older buttons now
+ local leaveGameButton = gui.BottomLeftControl:FindFirstChild("Exit")
+ if leaveGameButton then leaveGameButton:Remove() end
+
+ local topLeft = gui:FindFirstChild("TopLeftControl")
+ if topLeft then
+ leaveGameButton = topLeft:FindFirstChild("Exit")
+ if leaveGameButton then leaveGameButton:Remove() end
+
+ if settingButtonParent ~= topLeft then
+ topLeft:Remove()
+ end
+ end
+ --]]
+ end)
+
+end --UserSettings call
+
+local createSaveDialogs = function()
+ local shield = Instance.new("TextButton")
+ shield.Text = ""
+ shield.AutoButtonColor = false
+ shield.Name = "SaveDialogShield"
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex+1
+
+ local clearAndResetDialog
+ local save
+ local saveLocal
+ local dontSave
+ local cancel
+
+ local messageBoxButtons = {}
+ messageBoxButtons[1] = {}
+ messageBoxButtons[1].Text = "Save"
+ messageBoxButtons[1].Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ messageBoxButtons[1].Function = function() save() end
+ messageBoxButtons[1].ZIndex = baseZIndex+3
+ messageBoxButtons[2] = {}
+ messageBoxButtons[2].Text = "Cancel"
+ messageBoxButtons[2].Function = function() cancel() end
+ messageBoxButtons[2].Style = Enum.ButtonStyle.RobloxRoundButton
+ messageBoxButtons[2].ZIndex = baseZIndex+3
+ messageBoxButtons[3] = {}
+ messageBoxButtons[3].Text = "Don't Save"
+ messageBoxButtons[3].Function = function() dontSave() end
+ messageBoxButtons[3].Style = Enum.ButtonStyle.RobloxRoundButton
+ messageBoxButtons[3].ZIndex = baseZIndex+3
+
+ local saveDialogMessageBox = RbxGui.CreateStyledMessageDialog("Unsaved Changes", "Save your changes to ROBLOX before leaving?", "Confirm", messageBoxButtons)
+ saveDialogMessageBox.Visible = true
+ saveDialogMessageBox.Parent = shield
+ saveDialogMessageBox.ZIndex = baseZIndex+2
+ saveDialogMessageBox.Style = Enum.FrameStyle.DropShadow
+ saveDialogMessageBox.Title.ZIndex = baseZIndex+3
+ saveDialogMessageBox.Message.ZIndex = baseZIndex+3
+ saveDialogMessageBox.StyleImage.ZIndex = baseZIndex+3
+
+
+ local errorBoxButtons = {}
+
+ local buttonOffset = 1
+ if game.LocalSaveEnabled then
+ errorBoxButtons[buttonOffset] = {}
+ errorBoxButtons[buttonOffset].Text = "Save to Disk"
+ errorBoxButtons[buttonOffset].Function = function() saveLocal() end
+ buttonOffset = buttonOffset + 1
+ end
+ errorBoxButtons[buttonOffset] = {}
+ errorBoxButtons[buttonOffset].Text = "Keep Playing"
+ errorBoxButtons[buttonOffset].Function = function() cancel() end
+ errorBoxButtons[buttonOffset].Style = Enum.ButtonStyle.RobloxRoundButton
+ errorBoxButtons[buttonOffset].ZIndex = baseZIndex+3
+ errorBoxButtons[buttonOffset+1] = {}
+ errorBoxButtons[buttonOffset+1].Text = "Don't Save"
+ errorBoxButtons[buttonOffset+1].Function = function() dontSave() end
+ errorBoxButtons[buttonOffset+1].Style = Enum.ButtonStyle.RobloxRoundButton
+ errorBoxButtons[buttonOffset+1].ZIndex = baseZIndex+3
+
+ local errorDialogMessageBox = RbxGui.CreateStyledMessageDialog("Upload Failed", "Sorry, we could not save your changes to ROBLOX. If this problem continues to occur, please make sure your Roblox account has a verified email address.", "Error", errorBoxButtons)
+ errorDialogMessageBox.Visible = false
+ errorDialogMessageBox.Parent = shield
+ errorDialogMessageBox.ZIndex = baseZIndex+2
+ errorDialogMessageBox.Style = Enum.FrameStyle.DropShadow
+ errorDialogMessageBox.Title.ZIndex = baseZIndex+3
+ errorDialogMessageBox.Message.ZIndex = baseZIndex+3
+ errorDialogMessageBox.StyleImage.ZIndex = baseZIndex+3
+
+ local spinnerDialog = Instance.new("Frame")
+ spinnerDialog.Name = "SpinnerDialog"
+ spinnerDialog.Style = Enum.FrameStyle.DropShadow
+ spinnerDialog.Size = UDim2.new(0, 350, 0, 150)
+ spinnerDialog.Position = UDim2.new(.5, -175, .5, -75)
+ spinnerDialog.Visible = false
+ spinnerDialog.Active = true
+ spinnerDialog.ZIndex = baseZIndex+1
+ spinnerDialog.Parent = shield
+
+ local waitingLabel = Instance.new("TextLabel")
+ waitingLabel.Name = "WaitingLabel"
+ waitingLabel.Text = "Saving to ROBLOX..."
+ waitingLabel.Font = Enum.Font.SourceSansBold
+ waitingLabel.FontSize = Enum.FontSize.Size18
+ waitingLabel.Position = UDim2.new(0.5, 25, 0.5, 0)
+ waitingLabel.TextColor3 = Color3.new(1,1,1)
+ waitingLabel.ZIndex = baseZIndex+2
+ waitingLabel.Parent = spinnerDialog
+
+ local spinnerFrame = Instance.new("Frame")
+ spinnerFrame.Name = "Spinner"
+ spinnerFrame.Size = UDim2.new(0, 80, 0, 80)
+ spinnerFrame.Position = UDim2.new(0.5, -150, 0.5, -40)
+ spinnerFrame.BackgroundTransparency = 1
+ spinnerFrame.ZIndex = baseZIndex+2
+ spinnerFrame.Parent = spinnerDialog
+
+ local spinnerIcons = {}
+ local spinnerNum = 1
+ while spinnerNum <= 8 do
+ local spinnerImage = Instance.new("ImageLabel")
+ spinnerImage.Name = "Spinner"..spinnerNum
+ spinnerImage.Size = UDim2.new(0, 16, 0, 16)
+ spinnerImage.Position = UDim2.new(.5+.3*math.cos(math.rad(45*spinnerNum)), -8, .5+.3*math.sin(math.rad(45*spinnerNum)), -8)
+ spinnerImage.BackgroundTransparency = 1
+ spinnerImage.Image = "http://www.roblox.com/Asset?id=45880710"
+ spinnerImage.ZIndex = baseZIndex+3
+ spinnerImage.Parent = spinnerFrame
+
+ spinnerIcons[spinnerNum] = spinnerImage
+ spinnerNum = spinnerNum + 1
+ end
+
+ save = function()
+ saveDialogMessageBox.Visible = false
+
+ --Show the spinner dialog
+ spinnerDialog.Visible = true
+ local spin = true
+ --Make it spin
+ delay(0, function()
+ local spinPos = 0
+ while spin do
+ local pos = 0
+
+ while pos < 8 do
+ if pos == spinPos or pos == ((spinPos+1)%8) then
+ spinnerIcons[pos+1].Image = "http://www.roblox.com/Asset?id=45880668"
+ else
+ spinnerIcons[pos+1].Image = "http://www.roblox.com/Asset?id=45880710"
+ end
+
+ pos = pos + 1
+ end
+ spinPos = (spinPos + 1) % 8
+ wait(0.2)
+ end
+ end)
+
+ --Do the save while the spinner is going, function will wait
+ local result = game:SaveToRoblox()
+ if not result then
+ --Try once more
+ result = game:SaveToRoblox()
+ end
+
+ --Hide the spinner dialog
+ spinnerDialog.Visible = false
+ --And cause the delay thread to stop
+ spin = false
+
+ --Now process the result
+ if result then
+ --Success, close
+ game:FinishShutdown(false)
+ clearAndResetDialog()
+ else
+ --Failure, show the second dialog prompt
+ errorDialogMessageBox.Visible = true
+ end
+ end
+
+ saveLocal = function()
+ errorDialogMessageBox.Visible = false
+ game:FinishShutdown(true)
+ clearAndResetDialog()
+ end
+
+ dontSave = function()
+ saveDialogMessageBox.Visible = false
+ errorDialogMessageBox.Visible = false
+ game:FinishShutdown(false)
+ clearAndResetDialog()
+ end
+ cancel = function()
+ saveDialogMessageBox.Visible = false
+ errorDialogMessageBox.Visible = false
+ clearAndResetDialog()
+ end
+
+ clearAndResetDialog = function()
+ saveDialogMessageBox.Visible = true
+ errorDialogMessageBox.Visible = false
+ spinnerDialog.Visible = false
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end
+
+ robloxLock(shield)
+ shield.Visible = false
+ return shield
+end
+
+local createReportAbuseDialog = function()
+ --Only show things if we are a NetworkClient
+ -- TODO: add line back in when not testing report abuse
+ if not testReport then
+ waitForChild(game,"NetworkClient")
+ end
+
+ waitForChild(game,"Players")
+ waitForProperty(game.Players, "LocalPlayer")
+ local localPlayer = game.Players.LocalPlayer
+
+ local reportAbuseButton
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield, "Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle,"GameMainMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu, "ReportAbuseButton")
+ reportAbuseButton = gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu.ReportAbuseButton
+
+ local shield = Instance.new("TextButton")
+ shield.Name = "ReportAbuseShield"
+ shield.Text = ""
+ shield.AutoButtonColor = false
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 1
+
+ local closeAndResetDialgo
+
+ local messageBoxButtons = {}
+ messageBoxButtons[1] = {}
+ messageBoxButtons[1].Text = "Ok"
+ messageBoxButtons[1].Modal = true
+ messageBoxButtons[1].Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ messageBoxButtons[1].ZIndex = baseZIndex+3
+ messageBoxButtons[1].Function = function() closeAndResetDialog() end
+ local calmingMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!", "Our moderators will review the chat logs and determine what happened. The other user is probably just trying to make you mad.\n\nIf anyone used swear words, inappropriate language, or threatened you in real life, please report them for Bad Words or Threats", messageBoxButtons)
+ calmingMessageBox.Visible = false
+ calmingMessageBox.Parent = shield
+ calmingMessageBox.ZIndex = baseZIndex+2
+ calmingMessageBox.Style = Enum.FrameStyle.DropShadow
+ calmingMessageBox.Title.ZIndex = baseZIndex+3
+ calmingMessageBox.Message.ZIndex = baseZIndex+3
+
+ local recordedMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!","We've recorded your report for evaluation.", messageBoxButtons)
+ recordedMessageBox.Visible = false
+ recordedMessageBox.Parent = shield
+ recordedMessageBox.ZIndex = baseZIndex+2
+ recordedMessageBox.Style = Enum.FrameStyle.DropShadow
+ recordedMessageBox.Title.ZIndex = baseZIndex+3
+ recordedMessageBox.Message.ZIndex = baseZIndex+3
+
+ local normalMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!", "Our moderators will review the chat logs and determine what happened.", messageBoxButtons)
+ normalMessageBox.Visible = false
+ normalMessageBox.Parent = shield
+ normalMessageBox.ZIndex = baseZIndex+2
+ normalMessageBox.Style = Enum.FrameStyle.DropShadow
+ normalMessageBox.Title.ZIndex = baseZIndex+3
+ normalMessageBox.Message.ZIndex = baseZIndex+3
+
+ local frame = Instance.new("Frame")
+ frame.Name = "Settings"
+ frame.Position = UDim2.new(0.5, -240, 0.5, -160)
+ frame.Size = UDim2.new(0.0, 480, 0.0, 320)
+ frame.BackgroundTransparency = 1
+ frame.Active = true
+ frame.Parent = shield
+
+ local settingsFrame = Instance.new("Frame")
+ settingsFrame.Name = "ReportAbuseStyle"
+ settingsFrame.Size = UDim2.new(1, 0, 1, 0)
+ settingsFrame.Style = Enum.FrameStyle.DropShadow
+ settingsFrame.Active = true
+ settingsFrame.ZIndex = baseZIndex + 1
+ settingsFrame.Parent = frame
+
+ local description = Instance.new("TextLabel")
+ description.Name = "Description"
+ description.Text = "This will send a complete report to a moderator. The moderator will review the chat log and take appropriate action."
+ description.TextColor3 = Color3I(221,221,221)
+ description.Position = UDim2.new(0, 10, 0, 10)
+ description.Size = UDim2.new(1, -20, 0, 40)
+ description.BackgroundTransparency = 1
+ description.Font = Enum.Font.SourceSans
+ description.FontSize = Enum.FontSize.Size18
+ description.TextWrap = true
+ description.ZIndex = baseZIndex + 2
+ description.TextXAlignment = Enum.TextXAlignment.Left
+ description.TextYAlignment = Enum.TextYAlignment.Top
+ description.Parent = settingsFrame
+
+ local playerLabel = Instance.new("TextLabel")
+ playerLabel.Name = "PlayerLabel"
+ playerLabel.Text = "Which player?"
+ playerLabel.BackgroundTransparency = 1
+ playerLabel.Font = Enum.Font.SourceSans
+ playerLabel.FontSize = Enum.FontSize.Size18
+ playerLabel.Position = UDim2.new(0.025,20,0,92)
+ playerLabel.Size = UDim2.new(0.4,0,0,36)
+ playerLabel.TextColor3 = Color3I(255,255,255)
+ playerLabel.TextXAlignment = Enum.TextXAlignment.Left
+ playerLabel.ZIndex = baseZIndex + 2
+ playerLabel.Parent = settingsFrame
+
+ local gameOrPlayerLabel = Instance.new("TextLabel")
+ gameOrPlayerLabel.Name = "TypeLabel"
+ gameOrPlayerLabel.Text = "Game or Player:"
+ gameOrPlayerLabel.BackgroundTransparency = 1
+ gameOrPlayerLabel.Font = Enum.Font.SourceSans
+ gameOrPlayerLabel.FontSize = Enum.FontSize.Size18
+ gameOrPlayerLabel.Position = UDim2.new(0.025,20,0,55)
+ gameOrPlayerLabel.Size = UDim2.new(0.4,0,0,36)
+ gameOrPlayerLabel.TextColor3 = Color3I(255,255,255)
+ gameOrPlayerLabel.TextXAlignment = Enum.TextXAlignment.Left
+ gameOrPlayerLabel.ZIndex = baseZIndex + 2
+ gameOrPlayerLabel.Parent = settingsFrame
+
+ local abuseLabel = Instance.new("TextLabel")
+ abuseLabel.Name = "AbuseLabel"
+ abuseLabel.Text = "Type of Abuse:"
+ abuseLabel.Font = Enum.Font.SourceSans
+ abuseLabel.BackgroundTransparency = 1
+ abuseLabel.FontSize = Enum.FontSize.Size18
+ abuseLabel.Position = UDim2.new(0.025,20,0,131)
+ abuseLabel.Size = UDim2.new(0.4,0,0,36)
+ abuseLabel.TextColor3 = Color3I(255,255,255)
+ abuseLabel.TextXAlignment = Enum.TextXAlignment.Left
+ abuseLabel.ZIndex = baseZIndex + 2
+ abuseLabel.Parent = settingsFrame
+
+ local abusingPlayer = nil
+ local abuse = nil
+ local submitReportButton = nil
+ local gameOrPlayer = nil
+
+ local updatePlayerSelection = nil
+ local createPlayersDropDown = function()
+ local players = game:GetService("Players")
+ local playerNames = {}
+ local nameToPlayer = {}
+ local children = players:GetChildren()
+ local pos = 1
+ if children then
+ for i, player in ipairs(children) do
+ if player:IsA("Player") and player ~= localPlayer then
+ playerNames[pos] = player.Name
+ nameToPlayer[player.Name] = player
+ pos = pos + 1
+ end
+ end
+ end
+ local playerDropDown = nil
+ playerDropDown, updatePlayerSelection = RbxGui.CreateDropDownMenu(playerNames,
+ function(playerName)
+ abusingPlayer = nameToPlayer[playerName]
+ if abuse and abusingPlayer then
+ submitReportButton.Active = true
+ end
+ end, false, true, baseZIndex)
+ playerDropDown.Name = "PlayersComboBox"
+ playerDropDown.ZIndex = baseZIndex + 2
+ playerDropDown.Position = UDim2.new(.425, 0, 0, 94)
+ playerDropDown.Size = UDim2.new(.55,0,0,32)
+
+ return playerDropDown
+ end
+
+ local gameOrPlayerTable = {"Game","Player"}
+ local gameOrPlayerDropDown = nil
+ gameOrPlayerDropDown = RbxGui.CreateDropDownMenu(gameOrPlayerTable,
+ function(gameOrPlayerText)
+ gameOrPlayer = gameOrPlayerText
+ if gameOrPlayer == "Game" then
+ submitReportButton.Active = true
+ playerLabel.Visible = false
+ local playerDropDown = gameOrPlayerDropDown.Parent:FindFirstChild("PlayersComboBox")
+ if playerDropDown then
+ playerDropDown.Visible = false
+ end
+ else
+ playerLabel.Visible = true
+ local playerDropDown = gameOrPlayerDropDown.Parent:FindFirstChild("PlayersComboBox")
+ if playerDropDown then
+ playerDropDown.Visible = true
+ end
+ end
+ end, true, true, baseZIndex)
+ gameOrPlayerDropDown.Name = "TypeComboBox"
+ gameOrPlayerDropDown.ZIndex = baseZIndex + 2
+ gameOrPlayerDropDown.Position = UDim2.new(0.425, 0, 0, 55)
+ gameOrPlayerDropDown.Size = UDim2.new(0.55,0,0,32)
+ gameOrPlayerDropDown.Parent = settingsFrame
+
+ local abuses = {"Swearing","Bullying","Scamming","Dating","Cheating/Exploiting","Personal Questions","Offsite Links","Bad Model or Script","Bad Username"}
+ local abuseDropDown, updateAbuseSelection = RbxGui.CreateDropDownMenu(abuses,
+ function(abuseText)
+ abuse = abuseText
+ if abuse and abusingPlayer then
+ submitReportButton.Active = true
+ end
+ end, true, true, baseZIndex)
+ abuseDropDown.Name = "AbuseComboBox"
+ abuseDropDown.ZIndex = baseZIndex + 2
+ abuseDropDown.Position = UDim2.new(0.425, 0, 0, 133)
+ abuseDropDown.Size = UDim2.new(0.55,0,0,32)
+ abuseDropDown.Parent = settingsFrame
+
+ local shortDescriptionLabel = Instance.new("TextLabel")
+ shortDescriptionLabel.Name = "ShortDescriptionLabel"
+ shortDescriptionLabel.Text = "Short Description: (optional)"
+ shortDescriptionLabel.Font = Enum.Font.SourceSans
+ shortDescriptionLabel.FontSize = Enum.FontSize.Size18
+ shortDescriptionLabel.Position = UDim2.new(0.025,0,0,165)
+ shortDescriptionLabel.Size = UDim2.new(0.95,0,0,36)
+ shortDescriptionLabel.TextColor3 = Color3I(255,255,255)
+ shortDescriptionLabel.TextXAlignment = Enum.TextXAlignment.Left
+ shortDescriptionLabel.BackgroundTransparency = 1
+ shortDescriptionLabel.ZIndex = baseZIndex + 2
+ shortDescriptionLabel.Parent = settingsFrame
+
+ local shortDescriptionWrapper = Instance.new("Frame")
+ shortDescriptionWrapper.Name = "ShortDescriptionWrapper"
+ shortDescriptionWrapper.Position = UDim2.new(0.025,0,0,195)
+ shortDescriptionWrapper.Size = UDim2.new(0.95,0,1,-250)
+ shortDescriptionWrapper.BackgroundColor3 = Color3I(206,206,206)
+ shortDescriptionWrapper.BorderSizePixel = 0
+ shortDescriptionWrapper.ZIndex = baseZIndex + 2
+ shortDescriptionWrapper.Parent = settingsFrame
+
+ local shortDescriptionBox = Instance.new("TextBox")
+ shortDescriptionBox.Name = "TextBox"
+ shortDescriptionBox.Text = ""
+ shortDescriptionBox.ClearTextOnFocus = false
+ shortDescriptionBox.Font = Enum.Font.SourceSans
+ shortDescriptionBox.FontSize = Enum.FontSize.Size18
+ shortDescriptionBox.Position = UDim2.new(0,3,0,3)
+ shortDescriptionBox.Size = UDim2.new(1,-6,1,-6)
+ shortDescriptionBox.TextColor3 = Color3I(0,0,0)
+ shortDescriptionBox.TextXAlignment = Enum.TextXAlignment.Left
+ shortDescriptionBox.TextYAlignment = Enum.TextYAlignment.Top
+ shortDescriptionBox.TextWrap = true
+ shortDescriptionBox.BackgroundColor3 = Color3I(206,206,206)
+ shortDescriptionBox.BorderColor3 = Color3I(206,206,206)
+ shortDescriptionBox.ZIndex = baseZIndex + 2
+ shortDescriptionBox.Parent = shortDescriptionWrapper
+
+ submitReportButton = Instance.new("TextButton")
+ submitReportButton.Name = "SubmitReportBtn"
+ submitReportButton.Active = false
+ submitReportButton.Modal = true
+ submitReportButton.Font = Enum.Font.SourceSans
+ submitReportButton.FontSize = Enum.FontSize.Size18
+ submitReportButton.Position = UDim2.new(0.1, 0, 1, -50)
+ submitReportButton.Size = UDim2.new(0.35,0,0,40)
+ submitReportButton.AutoButtonColor = true
+ submitReportButton.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ submitReportButton.Text = "Submit Report"
+ submitReportButton.TextColor3 = Color3I(255,255,255)
+ submitReportButton.ZIndex = baseZIndex + 2
+ submitReportButton.Parent = settingsFrame
+
+ submitReportButton.MouseButton1Click:connect(function()
+ if submitReportButton.Active then
+ if abuse and abusingPlayer then
+ frame.Visible = false
+ if gameOrPlayer == "Player" then
+ game.Players:ReportAbuse(abusingPlayer, abuse, shortDescriptionBox.Text)
+ else
+ game.Players:ReportAbuse(nil, abuse, shortDescriptionBox.Text)
+ end
+ if abuse == "Cheating/Exploiting" then
+ recordedMessageBox.Visible = true
+ elseif abuse == "Bullying" or abuse == "Swearing" then
+ calmingMessageBox.Visible = true
+ else
+ normalMessageBox.Visible = true
+ end
+ else
+ closeAndResetDialog()
+ end
+ end
+ end)
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelBtn"
+ cancelButton.Font = Enum.Font.SourceSans
+ cancelButton.FontSize = Enum.FontSize.Size18
+ cancelButton.Position = UDim2.new(0.55, 0, 1, -50)
+ cancelButton.Size = UDim2.new(0.35,0,0,40)
+ cancelButton.AutoButtonColor = true
+ cancelButton.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ cancelButton.Text = "Cancel"
+ cancelButton.TextColor3 = Color3I(255,255,255)
+ cancelButton.ZIndex = baseZIndex + 2
+ cancelButton.Parent = settingsFrame
+
+ closeAndResetDialog = function()
+ --Delete old player combo box
+ local oldComboBox = settingsFrame:FindFirstChild("PlayersComboBox")
+ if oldComboBox then
+ oldComboBox.Parent = nil
+ end
+
+ abusingPlayer = nil updatePlayerSelection(nil)
+ abuse = nil updateAbuseSelection(nil)
+ submitReportButton.Active = false
+ shortDescriptionBox.Text = ""
+ frame.Visible = true
+ calmingMessageBox.Visible = false
+ recordedMessageBox.Visible = false
+ normalMessageBox.Visible = false
+ shield.Visible = false
+ reportAbuseButton.Active = true
+ game.GuiService:RemoveCenterDialog(shield)
+ end
+
+ cancelButton.MouseButton1Click:connect(closeAndResetDialog)
+
+ reportAbuseButton.MouseButton1Click:connect(
+ function()
+ createPlayersDropDown().Parent = settingsFrame
+ table.insert(centerDialogs,shield)
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ reportAbuseButton.Active = false
+ shield.Visible = true
+ mainShield.Visible = false
+ end,
+ --HideFunction
+ function()
+ reportAbuseButton.Active = true
+ shield.Visible = false
+ end)
+ end)
+
+ robloxLock(shield)
+ return shield
+end
+
+local createChatBar = function()
+ --Only show a chat bar if we are a NetworkClient
+ waitForChild(game, "NetworkClient")
+
+ waitForChild(game, "Players")
+ waitForProperty(game.Players, "LocalPlayer")
+
+ local chatBar = Instance.new("Frame")
+ chatBar.Name = "ChatBar"
+ chatBar.Size = UDim2.new(1, 0, 0, 22)
+ chatBar.Position = UDim2.new(0, 0, 1, 0)
+ chatBar.BackgroundColor3 = Color3.new(0,0,0)
+ chatBar.BorderSizePixel = 0
+
+ local chatBox = Instance.new("TextBox")
+ chatBox.Text = ""
+ chatBox.Visible = false
+ chatBox.Size = UDim2.new(1,-4,1,0)
+ chatBox.Position = UDim2.new(0,2,0,0)
+ chatBox.TextXAlignment = Enum.TextXAlignment.Left
+ chatBox.Font = Enum.Font.SourceSansBold
+ chatBox.ClearTextOnFocus = false
+ chatBox.FontSize = Enum.FontSize.Size14
+ chatBox.TextColor3 = Color3.new(1,1,1)
+ chatBox.BackgroundTransparency = 1
+ --chatBox.Parent = chatBar
+
+ local chatButton = Instance.new("TextButton")
+ chatButton.Size = UDim2.new(1,-4,1,0)
+ chatButton.Position = UDim2.new(0,2,0,0)
+ chatButton.AutoButtonColor = false
+ chatButton.Text = "To chat click here or press \"/\" key"
+ chatButton.TextXAlignment = Enum.TextXAlignment.Left
+ chatButton.Font = Enum.Font.SourceSansBold
+ chatButton.FontSize = Enum.FontSize.Size14
+ chatButton.TextColor3 = Color3.new(1,1,1)
+ chatButton.BackgroundTransparency = 1
+ --chatButton.Parent = chatBar
+
+ local activateChat = function()
+ if chatBox.Visible then
+ return
+ end
+ chatButton.Visible = false
+ chatBox.Text = ""
+ chatBox.Visible = true
+ chatBox:CaptureFocus()
+ end
+
+ chatButton.MouseButton1Click:connect(activateChat)
+
+ local hotKeyEnabled = true
+ local toggleHotKey = function(value)
+ hotKeyEnabled = value
+ end
+
+ local guiService = game:GetService("GuiService")
+ local newChatMode = pcall(function()
+ --guiService:AddSpecialKey(Enum.SpecialKey.ChatHotkey)
+ --guiService.SpecialKeyPressed:connect(function(key) if key == Enum.SpecialKey.ChatHotkey and hotKeyEnabled then activateChat() end end)
+ end)
+ if not newChatMode then
+ --guiService:AddKey("/")
+ --guiService.KeyPressed:connect(function(key) if key == "/" and hotKeyEnabled then activateChat() end end)
+ end
+
+ chatBox.FocusLost:connect(
+ function(enterPressed)
+ if enterPressed then
+ if chatBox.Text ~= "" then
+ local str = chatBox.Text
+ if string.sub(str, 1, 1) == '%' then
+ game.Players:TeamChat(string.sub(str, 2))
+ else
+ game.Players:Chat(str)
+ end
+ end
+ end
+ chatBox.Text = ""
+ chatBox.Visible = false
+ chatButton.Visible = true
+ end)
+ robloxLock(chatBar)
+ return chatBar, toggleHotKey
+end
+
+--Spawn a thread for the Save dialogs
+local isSaveDialogSupported = pcall(function() local var = game.LocalSaveEnabled end)
+if isSaveDialogSupported then
+ delay(0,
+ function()
+ local saveDialogs = createSaveDialogs()
+ saveDialogs.Parent = gui
+
+ game.RequestShutdown = function()
+ table.insert(centerDialogs,saveDialogs)
+ game.GuiService:AddCenterDialog(saveDialogs, Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ saveDialogs.Visible = true
+ end,
+ --HideFunction
+ function()
+ saveDialogs.Visible = false
+ end)
+
+ return true
+ end
+ end)
+end
+
+--Spawn a thread to listen to leave game prompts
+Spawn(function()
+ local showLeaveEvent = nil
+ pcall(function() showLeaveEvent = Game:GetService("GuiService").ShowLeaveConfirmation end)
+ if not showLeaveEvent then return end
+
+ function showLeaveConfirmation()
+ if showMainMenu then
+ showMainMenu("LeaveConfirmationMenu","down",UDim2.new(0,525,0,300))
+ end
+ end
+
+ Game:GetService("GuiService").ShowLeaveConfirmation:connect(function( )
+ if currentMenuSelection == nil then
+ showLeaveConfirmation()
+ else
+ resumeGameFunction(gui.UserSettingsShield)
+ end
+ end)
+end)
+
+--Spawn a thread for the Report Abuse dialogs
+delay(0,
+ function()
+ createReportAbuseDialog().Parent = gui
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield, "Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle,"GameMainMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu, "ReportAbuseButton")
+ gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu.ReportAbuseButton.Active = true
+ end)
+
+end --LoadLibrary if
diff --git a/asset/5 b/asset/5
new file mode 100644
index 0000000..4df2fa2
--- /dev/null
+++ b/asset/5
@@ -0,0 +1,110 @@
+--rbxassetid%5%
+local controlFrame = script.Parent:FindFirstChild("ControlFrame")
+
+if not controlFrame then return end
+
+local topLeftControl = controlFrame:FindFirstChild("TopLeftControl")
+local bottomLeftControl = controlFrame:FindFirstChild("BottomLeftControl")
+local bottomRightControl = controlFrame:FindFirstChild("BottomRightControl")
+
+
+local frameTip = Instance.new("TextLabel")
+frameTip.Name = "ToolTip"
+frameTip.Text = ""
+frameTip.Font = Enum.Font.ArialBold
+frameTip.FontSize = Enum.FontSize.Size12
+frameTip.TextColor3 = Color3.new(1,1,1)
+frameTip.BorderSizePixel = 0
+frameTip.ZIndex = 10
+frameTip.Size = UDim2.new(2,0,1,0)
+frameTip.Position = UDim2.new(1,0,0,0)
+frameTip.BackgroundColor3 = Color3.new(0,0,0)
+frameTip.BackgroundTransparency = 1
+frameTip.TextTransparency = 1
+frameTip.TextWrap = true
+
+local inside = Instance.new("BoolValue")
+inside.Name = "inside"
+inside.Value = false
+inside.Parent = frameTip
+
+function setUpListeners(frameToListen)
+ local fadeSpeed = 0.1
+ frameToListen.Parent.MouseEnter:connect(function()
+ if frameToListen:FindFirstChild("inside") then
+ frameToListen.inside.Value = true
+ wait(1.2)
+ if frameToListen.inside.Value then
+ while frameToListen.inside.Value and frameToListen.BackgroundTransparency > 0 do
+ frameToListen.BackgroundTransparency = frameToListen.BackgroundTransparency - fadeSpeed
+ frameToListen.TextTransparency = frameToListen.TextTransparency - fadeSpeed
+ wait()
+ end
+ end
+ end
+ end)
+ function killTip(killFrame)
+ killFrame.inside.Value = false
+ killFrame.BackgroundTransparency = 1
+ killFrame.TextTransparency = 1
+ end
+ frameToListen.Parent.MouseLeave:connect(function() killTip(frameToListen) end)
+ frameToListen.Parent.MouseButton1Click:connect(function() killTip(frameToListen) end)
+end
+
+function createSettingsButtonTip(parent)
+ if parent == nil then
+ parent = bottomLeftControl:FindFirstChild("SettingsButton")
+ end
+
+ local toolTip = frameTip:clone()
+ toolTip.RobloxLocked = true
+ toolTip.Text = "Settings/Leave Game"
+ toolTip.Position = UDim2.new(0,0,0,-18)
+ toolTip.Size = UDim2.new(0,120,0,20)
+ toolTip.Parent = parent
+ setUpListeners(toolTip)
+end
+
+wait(5) -- make sure we are loaded in, won't need tool tips for first 5 seconds anyway
+
+---------------- set up Bottom Left Tool Tips -------------------------
+
+local bottomLeftChildren = bottomLeftControl:GetChildren()
+local hasSettingsTip = false
+
+for i = 1, #bottomLeftChildren do
+
+ if bottomLeftChildren[i].Name == "Exit" then
+ local exitTip = frameTip:clone()
+ exitTip.RobloxLocked = true
+ exitTip.Text = "Leave Place"
+ exitTip.Position = UDim2.new(0,0,-1,0)
+ exitTip.Size = UDim2.new(1,0,1,0)
+ exitTip.Parent = bottomLeftChildren[i]
+ setUpListeners(exitTip)
+ elseif bottomLeftChildren[i].Name == "SettingsButton" then
+ hasSettingsTip = true
+ createSettingsButtonTip(bottomLeftChildren[i])
+ end
+end
+
+---------------- set up Bottom Right Tool Tips -------------------------
+
+local bottomRightChildren = bottomRightControl:GetChildren()
+
+for i = 1, #bottomRightChildren do
+ if bottomRightChildren[i].Name:find("Camera") ~= nil then
+ local cameraTip = frameTip:clone()
+ cameraTip.RobloxLocked = true
+ cameraTip.Text = "Camera View"
+ if bottomRightChildren[i].Name:find("Zoom") then
+ cameraTip.Position = UDim2.new(-1,0,-1.5)
+ else
+ cameraTip.Position = UDim2.new(0,0,-1.5,0)
+ end
+ cameraTip.Size = UDim2.new(2,0,1.25,0)
+ cameraTip.Parent = bottomRightChildren[i]
+ setUpListeners(cameraTip)
+ end
+end
diff --git a/asset/7 b/asset/7
new file mode 100644
index 0000000..a2acb1f
--- /dev/null
+++ b/asset/7
@@ -0,0 +1,558 @@
+--rbxassetid%7%
+function waitForProperty(instance, name)
+ while not instance[name] do
+ instance.Changed:wait()
+ end
+end
+
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+
+local mainFrame
+local choices = {}
+local lastChoice
+local choiceMap = {}
+local currentConversationDialog
+local currentConversationPartner
+local currentAbortDialogScript
+
+local tooFarAwayMessage = "You are too far away to chat!"
+local tooFarAwaySize = 300
+local characterWanderedOffMessage = "Chat ended because you walked away"
+local characterWanderedOffSize = 350
+local conversationTimedOut = "Chat ended because you didn't reply"
+local conversationTimedOutSize = 350
+
+local player
+local screenGui
+local chatNotificationGui
+local messageDialog
+local timeoutScript
+local reenableDialogScript
+local dialogMap = {}
+local dialogConnections = {}
+
+local gui = nil
+waitForChild(game,"CoreGui")
+waitForChild(game.CoreGui,"RobloxGui")
+if game.CoreGui.RobloxGui:FindFirstChild("ControlFrame") then
+ gui = game.CoreGui.RobloxGui.ControlFrame
+else
+ gui = game.CoreGui.RobloxGui
+end
+
+function currentTone()
+ if currentConversationDialog then
+ return currentConversationDialog.Tone
+ else
+ return Enum.DialogTone.Neutral
+ end
+end
+
+
+function createChatNotificationGui()
+ chatNotificationGui = Instance.new("BillboardGui")
+ chatNotificationGui.Name = "ChatNotificationGui"
+ chatNotificationGui.ExtentsOffset = Vector3.new(0,1,0)
+ chatNotificationGui.Size = UDim2.new(4, 0, 5.42857122, 0)
+ chatNotificationGui.SizeOffset = Vector2.new(0,0)
+ chatNotificationGui.StudsOffset = Vector3.new(0.4, 4.3, 0)
+ chatNotificationGui.Enabled = true
+ chatNotificationGui.RobloxLocked = true
+ chatNotificationGui.Active = true
+
+ local image = Instance.new("ImageLabel")
+ image.Name = "Image"
+ image.Active = false
+ image.BackgroundTransparency = 1
+ image.Position = UDim2.new(0,0,0,0)
+ image.Size = UDim2.new(1.0,0,1.0,0)
+ image.Image = ""
+ image.RobloxLocked = true
+ image.Parent = chatNotificationGui
+
+
+ local button = Instance.new("ImageButton")
+ button.Name = "Button"
+ button.AutoButtonColor = false
+ button.Position = UDim2.new(0.0879999995, 0, 0.0529999994, 0)
+ button.Size = UDim2.new(0.829999983, 0, 0.460000008, 0)
+ button.Image = ""
+ button.BackgroundTransparency = 1
+ button.RobloxLocked = true
+ button.Parent = image
+end
+
+function getChatColor(tone)
+ if tone == Enum.DialogTone.Neutral then
+ return Enum.ChatColor.Blue
+ elseif tone == Enum.DialogTone.Friendly then
+ return Enum.ChatColor.Green
+ elseif tone == Enum.DialogTone.Enemy then
+ return Enum.ChatColor.Red
+ end
+end
+
+function styleChoices(tone)
+ for i, obj in pairs(choices) do
+ resetColor(obj, tone)
+ end
+ resetColor(lastChoice, tone)
+end
+
+function styleMainFrame(tone)
+ if tone == Enum.DialogTone.Neutral then
+ mainFrame.Style = Enum.FrameStyle.ChatBlue
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botBlue_tailRight.png"
+ elseif tone == Enum.DialogTone.Friendly then
+ mainFrame.Style = Enum.FrameStyle.ChatGreen
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botGreen_tailRight.png"
+ elseif tone == Enum.DialogTone.Enemy then
+ mainFrame.Style = Enum.FrameStyle.ChatRed
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botRed_tailRight.png"
+ end
+
+ styleChoices(tone)
+end
+function setChatNotificationTone(gui, purpose, tone)
+ if tone == Enum.DialogTone.Neutral then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botBlue_notify_bkg.png"
+ elseif tone == Enum.DialogTone.Friendly then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botGreen_notify_bkg.png"
+ elseif tone == Enum.DialogTone.Enemy then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botRed_notify_bkg.png"
+ end
+ if purpose == Enum.DialogPurpose.Quest then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_bang.png"
+ elseif purpose == Enum.DialogPurpose.Help then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_question.png"
+ elseif purpose == Enum.DialogPurpose.Shop then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_money.png"
+ end
+end
+
+function createMessageDialog()
+ messageDialog = Instance.new("Frame");
+ messageDialog.Name = "DialogScriptMessage"
+ messageDialog.Style = Enum.FrameStyle.RobloxRound
+ messageDialog.Visible = false
+
+ local text = Instance.new("TextLabel")
+ text.Name = "Text"
+ text.Position = UDim2.new(0,0,0,-1)
+ text.Size = UDim2.new(1,0,1,0)
+ text.FontSize = Enum.FontSize.Size14
+ text.BackgroundTransparency = 1
+ text.TextColor3 = Color3.new(1,1,1)
+ text.RobloxLocked = true
+ text.Parent = messageDialog
+end
+
+function showMessage(msg, size)
+ messageDialog.Text.Text = msg
+ messageDialog.Size = UDim2.new(0,size,0,40)
+ messageDialog.Position = UDim2.new(0.5, -size/2, 0.5, -40)
+ messageDialog.Visible = true
+ wait(2)
+ messageDialog.Visible = false
+end
+
+function variableDelay(str)
+ local length = math.min(string.len(str), 100)
+ wait(0.75 + ((length/75) * 1.5))
+end
+
+function resetColor(frame, tone)
+ if tone == Enum.DialogTone.Neutral then
+ frame.BackgroundColor3 = Color3.new(0/255, 0/255, 179/255)
+ frame.Number.TextColor3 = Color3.new(45/255, 142/255, 245/255)
+ elseif tone == Enum.DialogTone.Friendly then
+ frame.BackgroundColor3 = Color3.new(0/255, 77/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(0/255, 190/255, 0/255)
+ elseif tone == Enum.DialogTone.Enemy then
+ frame.BackgroundColor3 = Color3.new(140/255, 0/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(255/255,88/255, 79/255)
+ end
+end
+
+function highlightColor(frame, tone)
+ if tone == Enum.DialogTone.Neutral then
+ frame.BackgroundColor3 = Color3.new(2/255, 108/255, 255/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ elseif tone == Enum.DialogTone.Friendly then
+ frame.BackgroundColor3 = Color3.new(0/255, 128/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ elseif tone == Enum.DialogTone.Enemy then
+ frame.BackgroundColor3 = Color3.new(204/255, 0/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ end
+end
+
+function wanderDialog()
+ mainFrame.Visible = false
+ endDialog()
+ showMessage(characterWanderedOffMessage, characterWanderedOffSize)
+end
+
+function timeoutDialog()
+ mainFrame.Visible = false
+ endDialog()
+ showMessage(conversationTimedOut, conversationTimedOutSize)
+end
+function normalEndDialog()
+ endDialog()
+end
+
+function endDialog()
+ if currentAbortDialogScript then
+ currentAbortDialogScript:Remove()
+ currentAbortDialogScript = nil
+ end
+
+ local dialog = currentConversationDialog
+ currentConversationDialog = nil
+ if dialog and dialog.InUse then
+ local reenableScript = reenableDialogScript:Clone()
+ reenableScript.archivable = false
+ reenableScript.Disabled = false
+ reenableScript.Parent = dialog
+ end
+
+ for dialog, gui in pairs(dialogMap) do
+ if dialog and gui then
+ gui.Enabled = not dialog.InUse
+ end
+ end
+
+ currentConversationPartner = nil
+end
+
+function sanitizeMessage(msg)
+ if string.len(msg) == 0 then
+ return "..."
+ else
+ return msg
+ end
+end
+
+function selectChoice(choice)
+ renewKillswitch(currentConversationDialog)
+
+ --First hide the Gui
+ mainFrame.Visible = false
+ if choice == lastChoice then
+ game.Chat:Chat(game.Players.LocalPlayer.Character, "Goodbye!", getChatColor(currentTone()))
+
+ normalEndDialog()
+ else
+ local dialogChoice = choiceMap[choice]
+
+ game.Chat:Chat(game.Players.LocalPlayer.Character, sanitizeMessage(dialogChoice.UserDialog), getChatColor(currentTone()))
+ wait(1)
+ currentConversationDialog:SignalDialogChoiceSelected(player, dialogChoice)
+ game.Chat:Chat(currentConversationPartner, sanitizeMessage(dialogChoice.ResponseDialog), getChatColor(currentTone()))
+
+ variableDelay(dialogChoice.ResponseDialog)
+ presentDialogChoices(currentConversationPartner, dialogChoice:GetChildren())
+ end
+end
+
+function newChoice(numberText)
+ local frame = Instance.new("TextButton")
+ frame.BackgroundColor3 = Color3.new(0/255, 0/255, 179/255)
+ frame.AutoButtonColor = false
+ frame.BorderSizePixel = 0
+ frame.Text = ""
+ frame.MouseEnter:connect(function() highlightColor(frame, currentTone()) end)
+ frame.MouseLeave:connect(function() resetColor(frame, currentTone()) end)
+ frame.MouseButton1Click:connect(function() selectChoice(frame) end)
+ frame.RobloxLocked = true
+
+ local number = Instance.new("TextLabel")
+ number.Name = "Number"
+ number.TextColor3 = Color3.new(127/255, 212/255, 255/255)
+ number.Text = numberText
+ number.FontSize = Enum.FontSize.Size14
+ number.BackgroundTransparency = 1
+ number.Position = UDim2.new(0,4,0,2)
+ number.Size = UDim2.new(0,20,0,24)
+ number.TextXAlignment = Enum.TextXAlignment.Left
+ number.TextYAlignment = Enum.TextYAlignment.Top
+ number.RobloxLocked = true
+ number.Parent = frame
+
+ local prompt = Instance.new("TextLabel")
+ prompt.Name = "UserPrompt"
+ prompt.BackgroundTransparency = 1
+ prompt.TextColor3 = Color3.new(1,1,1)
+ prompt.FontSize = Enum.FontSize.Size14
+ prompt.Position = UDim2.new(0,28, 0, 2)
+ prompt.Size = UDim2.new(1,-32, 1, -4)
+ prompt.TextXAlignment = Enum.TextXAlignment.Left
+ prompt.TextYAlignment = Enum.TextYAlignment.Top
+ prompt.TextWrap = true
+ prompt.RobloxLocked = true
+ prompt.Parent = frame
+
+ return frame
+end
+function initialize(parent)
+ choices[1] = newChoice("1)")
+ choices[2] = newChoice("2)")
+ choices[3] = newChoice("3)")
+ choices[4] = newChoice("4)")
+
+ lastChoice = newChoice("5)")
+ lastChoice.UserPrompt.Text = "Goodbye!"
+ lastChoice.Size = UDim2.new(1,0,0,28)
+
+ mainFrame = Instance.new("Frame")
+ mainFrame.Name = "UserDialogArea"
+ mainFrame.Size = UDim2.new(0, 350, 0, 200)
+ mainFrame.Style = Enum.FrameStyle.ChatBlue
+ mainFrame.Visible = false
+
+ imageLabel = Instance.new("ImageLabel")
+ imageLabel.Name = "Tail"
+ imageLabel.Size = UDim2.new(0,62,0,53)
+ imageLabel.Position = UDim2.new(1,8,0.25)
+ imageLabel.Image = "rbxasset://textures/chatBubble_botBlue_tailRight.png"
+ imageLabel.BackgroundTransparency = 1
+ imageLabel.RobloxLocked = true
+ imageLabel.Parent = mainFrame
+
+ for n, obj in pairs(choices) do
+ obj.RobloxLocked = true
+ obj.Parent = mainFrame
+ end
+ lastChoice.RobloxLocked = true
+ lastChoice.Parent = mainFrame
+
+ mainFrame.RobloxLocked = true
+ mainFrame.Parent = parent
+end
+
+function presentDialogChoices(talkingPart, dialogChoices)
+ if not currentConversationDialog then
+ return
+ end
+
+ currentConversationPartner = talkingPart
+ sortedDialogChoices = {}
+ for n, obj in pairs(dialogChoices) do
+ if obj:IsA("DialogChoice") then
+ table.insert(sortedDialogChoices, obj)
+ end
+ end
+ table.sort(sortedDialogChoices, function(a,b) return a.Name < b.Name end)
+
+ if #sortedDialogChoices == 0 then
+ normalEndDialog()
+ return
+ end
+
+ local pos = 1
+ local yPosition = 0
+ choiceMap = {}
+ for n, obj in pairs(choices) do
+ obj.Visible = false
+ end
+
+ for n, obj in pairs(sortedDialogChoices) do
+ if pos <= #choices then
+ --3 lines is the maximum, set it to that temporarily
+ choices[pos].Size = UDim2.new(1, 0, 0, 24*3)
+ choices[pos].UserPrompt.Text = obj.UserDialog
+ local height = math.ceil(choices[pos].UserPrompt.TextBounds.Y/24)*24
+
+ choices[pos].Position = UDim2.new(0, 0, 0, yPosition)
+ choices[pos].Size = UDim2.new(1, 0, 0, height)
+ choices[pos].Visible = true
+
+ choiceMap[choices[pos]] = obj
+
+ yPosition = yPosition + height
+ pos = pos + 1
+ end
+ end
+
+ lastChoice.Position = UDim2.new(0,0,0,yPosition)
+ lastChoice.Number.Text = pos .. ")"
+
+ mainFrame.Size = UDim2.new(0, 350, 0, yPosition+24+32)
+ mainFrame.Position = UDim2.new(0,20,0.0, -mainFrame.Size.Y.Offset-20)
+ styleMainFrame(currentTone())
+ mainFrame.Visible = true
+end
+
+function doDialog(dialog)
+ while not Instance.Lock(dialog, player) do
+ wait()
+ end
+
+ if dialog.InUse then
+ Instance.Unlock(dialog)
+ return
+ else
+ dialog.InUse = true
+ Instance.Unlock(dialog)
+ end
+
+ currentConversationDialog = dialog
+ game.Chat:Chat(dialog.Parent, dialog.InitialPrompt, getChatColor(dialog.Tone))
+ variableDelay(dialog.InitialPrompt)
+
+ presentDialogChoices(dialog.Parent, dialog:GetChildren())
+end
+
+function renewKillswitch(dialog)
+ if currentAbortDialogScript then
+ currentAbortDialogScript:Remove()
+ currentAbortDialogScript = nil
+ end
+
+ currentAbortDialogScript = timeoutScript:Clone()
+ currentAbortDialogScript.archivable = false
+ currentAbortDialogScript.Disabled = false
+ currentAbortDialogScript.Parent = dialog
+end
+
+function checkForLeaveArea()
+ while currentConversationDialog do
+ if currentConversationDialog.Parent and (player:DistanceFromCharacter(currentConversationDialog.Parent.Position) >= currentConversationDialog.ConversationDistance) then
+ wanderDialog()
+ end
+ wait(1)
+ end
+end
+
+function startDialog(dialog)
+ if dialog.Parent and dialog.Parent:IsA("BasePart") then
+ if player:DistanceFromCharacter(dialog.Parent.Position) >= dialog.ConversationDistance then
+ showMessage(tooFarAwayMessage, tooFarAwaySize)
+ return
+ end
+
+ for dialog, gui in pairs(dialogMap) do
+ if dialog and gui then
+ gui.Enabled = false
+ end
+ end
+
+ renewKillswitch(dialog)
+
+ delay(1, checkForLeaveArea)
+ doDialog(dialog)
+ end
+end
+
+function removeDialog(dialog)
+ if dialogMap[dialog] then
+ dialogMap[dialog]:Remove()
+ dialogMap[dialog] = nil
+ end
+ if dialogConnections[dialog] then
+ dialogConnections[dialog]:disconnect()
+ dialogConnections[dialog] = nil
+ end
+end
+
+function addDialog(dialog)
+ if dialog.Parent then
+ if dialog.Parent:IsA("BasePart") then
+ local chatGui = chatNotificationGui:clone()
+ chatGui.Enabled = not dialog.InUse
+ chatGui.Adornee = dialog.Parent
+ chatGui.RobloxLocked = true
+ chatGui.Parent = game.CoreGui
+ chatGui.Image.Button.MouseButton1Click:connect(function() startDialog(dialog) end)
+ setChatNotificationTone(chatGui, dialog.Purpose, dialog.Tone)
+
+ dialogMap[dialog] = chatGui
+
+ dialogConnections[dialog] = dialog.Changed:connect(function(prop)
+ if prop == "Parent" and dialog.Parent then
+ --This handles the reparenting case, seperate from removal case
+ removeDialog(dialog)
+ addDialog(dialog)
+ elseif prop == "InUse" then
+ chatGui.Enabled = not currentConversationDialog and not dialog.InUse
+ if dialog == currentConversationDialog then
+ timeoutDialog()
+ end
+ elseif prop == "Tone" or prop == "Purpose" then
+ setChatNotificationTone(chatGui, dialog.Purpose, dialog.Tone)
+ end
+ end)
+ else -- still need to listen to parent changes even if current parent is not a BasePart
+ dialogConnections[dialog] = dialog.Changed:connect(function(prop)
+ if prop == "Parent" and dialog.Parent then
+ --This handles the reparenting case, seperate from removal case
+ removeDialog(dialog)
+ addDialog(dialog)
+ end
+ end)
+ end
+ end
+end
+
+function fetchScripts()
+ local model = game:GetService("InsertService"):LoadAsset(39226062)
+ if type(model) == "string" then -- load failed, lets try again
+ wait(0.1)
+ model = game:GetService("InsertService"):LoadAsset(39226062)
+ end
+ if type(model) == "string" then -- not going to work, lets bail
+ return
+ end
+
+ waitForChild(model,"TimeoutScript")
+ timeoutScript = model.TimeoutScript
+ waitForChild(model,"ReenableDialogScript")
+ reenableDialogScript = model.ReenableDialogScript
+end
+
+function onLoad()
+ waitForProperty(game.Players, "LocalPlayer")
+ player = game.Players.LocalPlayer
+ waitForProperty(player, "Character")
+
+ --print("Fetching Scripts")
+ fetchScripts()
+
+ --print("Creating Guis")
+ createChatNotificationGui()
+
+ --print("Creating MessageDialog")
+ createMessageDialog()
+ messageDialog.RobloxLocked = true
+ messageDialog.Parent = gui
+
+ --print("Waiting for BottomLeftControl")
+ waitForChild(gui, "BottomLeftControl")
+
+ --print("Initializing Frame")
+ local frame = Instance.new("Frame")
+ frame.Name = "DialogFrame"
+ frame.Position = UDim2.new(0,0,0,0)
+ frame.Size = UDim2.new(0,0,0,0)
+ frame.BackgroundTransparency = 1
+ frame.RobloxLocked = true
+ frame.Parent = gui.BottomLeftControl
+ initialize(frame)
+
+ --print("Adding Dialogs")
+ game.CollectionService.ItemAdded:connect(function(obj) if obj:IsA("Dialog") then addDialog(obj) end end)
+ game.CollectionService.ItemRemoved:connect(function(obj) if obj:IsA("Dialog") then removeDialog(obj) end end)
+ for i, obj in pairs(game.CollectionService:GetCollection("Dialog")) do
+ if obj:IsA("Dialog") then
+ addDialog(obj)
+ end
+ end
+end
+
+onLoad()
\ No newline at end of file
diff --git a/asset/8 b/asset/8
new file mode 100644
index 0000000..896aec3
--- /dev/null
+++ b/asset/8
@@ -0,0 +1,1368 @@
+--rbxassetid%8%
+--Include
+local Create = assert(LoadLibrary("RbxUtility")).Create
+
+-- A Few Script Globals
+local gui
+if script.Parent:FindFirstChild("ControlFrame") then
+ gui = script.Parent:FindFirstChild("ControlFrame")
+else
+ gui = script.Parent
+end
+
+-- Dev-Console Root
+
+local Dev_Container = Create'Frame'{
+ Name = 'DevConsoleContainer';
+ Parent = gui;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.9;
+ Position = UDim2.new(0, 100, 0, 10);
+ Size = UDim2.new(0.5, 20, 0.5, 20);
+ Visible = false;
+ BackgroundTransparency = 0.9;
+}
+
+local ToggleConsole = Create'BindableFunction'{
+ Name = 'ToggleDevConsole';
+ Parent = gui
+}
+
+
+local devConsoleInitialized = false
+function initializeDeveloperConsole()
+ if devConsoleInitialized then
+ return
+ end
+ devConsoleInitialized = true
+
+ ---Dev-Console Variables
+ local LOCAL_CONSOLE = 1
+ local SERVER_CONSOLE = 2
+ local SERVER_STATS = 3
+
+ local MAX_LIST_SIZE = 1000
+
+ local minimumSize = Vector2.new(350, 180)
+ local currentConsole = LOCAL_CONSOLE
+
+ local localMessageList = {}
+ local serverMessageList = {}
+
+ local localOffset = 0
+ local serverOffset = 0
+ local serverStatsOffset = 0
+
+ local errorToggleOn = true
+ local warningToggleOn = true
+ local infoToggleOn = true
+ local outputToggleOn = true
+ local wordWrapToggleOn = false
+
+ local textHolderSize = 0
+
+ local frameNumber = 0
+
+ --Create Dev-Console
+
+ local Dev_Body = Create'Frame'{
+ Name = 'Body';
+ Parent = Dev_Container;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 21);
+ Size = UDim2.new(1, 0, 1, -25);
+ }
+
+ local Dev_OptionsHolder = Create'Frame'{
+ Name = 'OptionsHolder';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 318, 0, 0);
+ Size = UDim2.new(1, -355, 0, 24);
+ ClipsDescendants = true
+ }
+
+ local Dev_OptionsBar = Create'Frame'{
+ Name = 'OptionsBar';
+ Parent = Dev_OptionsHolder;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0.0, -250, 0, 4);
+ Size = UDim2.new(0, 234, 0, 18);
+ }
+
+ local Dev_ErrorToggleFilter = Create'TextButton'{
+ Name = 'ErrorToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 0, 0);
+ Position = UDim2.new(0, 115, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 0, 0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_ErrorToggleFilter;
+ BackgroundColor3 = Color3.new(1.0,0,0);
+ BorderColor3 = Color3.new(1.0, 0, 0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_InfoToggleFilter = Create'TextButton'{
+ Name = 'InfoToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(0.4, 0.5, 1.0);
+ Position = UDim2.new(0, 65, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(0.4, 0.5, 1.0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_InfoToggleFilter;
+ BackgroundColor3 = Color3.new(0.4, 0.5, 1.0);
+ BorderColor3 = Color3.new(0.4, 0.5, 1.0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_OutputToggleFilter = Create'TextButton'{
+ Name = 'OutputToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 40, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 1.0, 1.0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_OutputToggleFilter;
+ BackgroundColor3 = Color3.new(1.0, 1.0, 1.0);
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_WarningToggleFilter = Create'TextButton'{
+ Name = 'WarningToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 0.6, 0.4);
+ Position = UDim2.new(0, 90, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 0.6, 0.4);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_WarningToggleFilter;
+ BackgroundColor3 = Color3.new(1.0, 0.6, 0.4);
+ BorderColor3 = Color3.new(1.0, 0.6, 0.4);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_WordWrapToggle = Create'TextButton'{
+ Name = 'WordWrapToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(0.8, 0.8, 0.8);
+ Position = UDim2.new(0, 215, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(0.8, 0.8, 0.8);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_WordWrapToggle;
+ BackgroundColor3 = Color3.new(0.8, 0.8, 0.8);
+ BorderColor3 = Color3.new(0.8, 0.8, 0.8);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ Visible = false
+ }
+
+ Create'TextLabel'{
+ Name = 'Filter';
+ Parent = Dev_OptionsBar;
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 40, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Filter";
+ TextColor3 = Color3.new(1, 1, 1);
+ }
+
+ Create'TextLabel'{
+ Name = 'WordWrap';
+ Parent = Dev_OptionsBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 150, 0, 0);
+ Size = UDim2.new(0, 50, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Word Wrap";
+ TextColor3 = Color3.new(1, 1, 1);
+ }
+
+ local Dev_ScrollBar = Create'Frame'{
+ Name = 'ScrollBar';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.9;
+ Position = UDim2.new(1, -20, 0, 26);
+ Size = UDim2.new(0, 20, 1, -50);
+ Visible = false;
+ BackgroundTransparency = 0.9;
+ }
+
+ local Dev_ScrollArea = Create'Frame'{
+ Name = 'ScrollArea';
+ Parent = Dev_ScrollBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 23);
+ Size = UDim2.new(1, 0, 1, -46);
+ BackgroundTransparency = 1;
+ }
+
+ local Dev_Handle = Create'ImageButton'{
+ Name = 'Handle';
+ Parent = Dev_ScrollArea;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, .2, 0);
+ Size = UDim2.new(0, 20, 0, 40);
+ BackgroundTransparency = 0.5;
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_Handle;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0.5, -8);
+ Rotation = 180;
+ Size = UDim2.new(1, 0, 0, 16);
+ Image = "http://www.roblox.com/Asset?id=151205881";
+ }
+
+ local Dev_DownButton = Create'ImageButton'{
+ Name = 'Down';
+ Parent = Dev_ScrollBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 1, -20);
+ Size = UDim2.new(0, 20, 0, 20);
+ BackgroundTransparency = 0.5;
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_DownButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Rotation = 180;
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ local Dev_UpButton = Create'ImageButton'{
+ Name = 'Up';
+ Parent = Dev_ScrollBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_UpButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ local flagExists, flagValue = pcall(function () return settings():GetFFlag("ConsoleCodeExecutionEnabled") end)
+ local codeExecutionEnabled = flagExists and flagValue
+ local isCreator = game.Players.LocalPlayer.userId == game.CreatorId
+ local function shouldShowCommandBar()
+ return codeExecutionEnabled and isCreator
+ end
+ local function getCommandBarOffset()
+ return shouldShowCommandBar() and currentConsole == SERVER_CONSOLE and -22 or 0
+ end
+
+ local Dev_TextBox = Create'Frame'{
+ Name = 'TextBox';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.6;
+ Position = UDim2.new(0, 2, 0, 26);
+ Size = UDim2.new(1, -4, 1, -28);
+ ClipsDescendants = true;
+ }
+
+ local Dev_TextHolder = Create'Frame'{
+ Name = 'TextHolder';
+ Parent = Dev_TextBox;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ }
+
+ local Dev_OptionsButton = Create'ImageButton'{
+ Name = 'OptionsButton';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 298, 0, 2);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_OptionsButton;
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ Rotation = 0;
+ Image = "http://www.roblox.com/Asset?id=152093917";
+ }
+
+ local Dev_CommandBar = Create'Frame'{
+ Name = "CommandBar";
+ Parent = Dev_Container;
+ BackgroundTransparency = 0;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BorderSizePixel = 0;
+ Size = UDim2.new(1, -25, 0, 24);
+ Position = UDim2.new(0, 2, 1, -28);
+ Visible = false;
+ ZIndex = 2;
+ BorderSizePixel = 0;
+ }
+
+ local Dev_CommandBarTextBox = Create'TextBox'{
+ Name = 'CommandBarTextBox';
+ Parent = Dev_CommandBar;
+ BackgroundTransparency = 1;
+ MultiLine = false;
+ ZIndex = 2;
+ Position = UDim2.new(0, 25, 0, 2);
+ Size = UDim2.new(1, -30, 0, 20);
+ Font = Enum.Font.Legacy;
+ FontSize = Enum.FontSize.Size10;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Center;
+ Text = "Code goes here";
+ }
+
+ Create'TextLabel'{
+ Name = "PromptLabel";
+ Parent = Dev_CommandBar;
+ BackgroundTransparency = 1;
+ Size = UDim2.new(0, 20, 1, 0);
+ Position = UDim2.new(0, 5, 0, 0);
+ Font = Enum.Font.Legacy;
+ FontSize = Enum.FontSize.Size10;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextXAlignment = Enum.TextXAlignment.Center;
+ TextYAlignment = Enum.TextYAlignment.Center;
+ ZIndex = 2;
+ Text = ">";
+ }
+
+ Dev_CommandBarTextBox.FocusLost:connect(function(enterPressed)
+ if enterPressed then
+ local code = Dev_CommandBarTextBox.Text
+ game:GetService("LogService"):ExecuteScript(code)
+ Dev_CommandBarTextBox.Text = ""
+
+ -- scroll to the bottom of the console
+ serverOffset = 0
+ Dev_CommandBarTextBox:CaptureFocus()
+ end
+ end)
+
+ local Dev_ResizeButton = Create'ImageButton'{
+ Name = 'ResizeButton';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(1, -20, 1, -20);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_ResizeButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 6, 0, 6);
+ Size = UDim2.new(0.8, 0, 0.8, 0);
+ Rotation = 135;
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ Create'TextButton'{
+ Name = 'LocalConsole';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.6;
+ Position = UDim2.new(0, 7, 0, 5);
+ Size = UDim2.new(0, 90, 0, 20);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Local Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ Create'TextButton'{
+ Name = 'ServerConsole';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.8;
+ Position = UDim2.new(0, 102, 0, 5);
+ Size = UDim2.new(0, 90, 0, 17);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Server Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ Create'TextButton'{
+ Name = 'ServerStats';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.8;
+ Position = UDim2.new(0, 197, 0, 5);
+ Size = UDim2.new(0, 90, 0, 17);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Server Stats";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ local Dev_TitleBar = Create'Frame'{
+ Name = 'TitleBar';
+ Parent = Dev_Container;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 0, 20);
+ }
+
+ local Dev_CloseButton = Create'ImageButton'{
+ Name = 'CloseButton';
+ Parent = Dev_TitleBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(1, -20, 0, 0);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Parent = Dev_CloseButton;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Image = "http://www.roblox.com/Asset?id=151205852";
+ }
+
+ Create'TextButton'{
+ Name = 'TextButton';
+ Parent = Dev_TitleBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, -23, 1, 0);
+ Text = "";
+ }
+
+ Create'TextLabel'{
+ Name = 'TitleText';
+ Parent = Dev_TitleBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 185, 0, 20);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size18;
+ Text = "Server Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ Text = "Roblox Developer Console";
+ TextYAlignment = Enum.TextYAlignment.Top;
+ }
+
+ local Dev_StatsChartFrame = Create'Frame'{
+ Name = 'ChartFrame';
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 0.5;
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 250, 0, 100);
+ }
+
+ Create'TextLabel'{
+ Name = 'TitleText';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 0.5;
+ BackgroundColor3 = Color3.new(255,0,0);
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 0, 15);
+ Text = "";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 39);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartMaxValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 15);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "Max: ";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartMinValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 27);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "Min: ";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ local Dev_StatsChartBar = Create'TextLabel'{
+ Name = 'StatsChartBar';
+ BackgroundColor3 = Color3.new(0,255,0);
+ Position = UDim2.new(0, 0, 0, 52);
+ Size = UDim2.new(0, 5, 0, 40);
+ Text = "";
+ }
+
+ ---Saved Mouse Information
+ local previousMousePos = nil
+ local pPos = nil
+
+ local previousMousePosResize = nil
+ local pSize = nil
+
+ local previousMousePosScroll = nil
+ local pScrollHandle = nil
+ local pOffset = nil
+
+ local scrollUpIsDown = false
+ local scrollDownIsDown = false
+
+ function clean()
+ previousMousePos = nil
+ pPos = nil
+ previousMousePosResize = nil
+ pSize = nil
+ previousMousePosScroll = nil
+ pScrollHandle = nil
+ pOffset = nil
+ scrollUpIsDown = false
+ scrollDownIsDown = false
+ end
+
+ -- Set up server stat charts
+ local numBars = 40
+ local numCharts = 0
+ local charts = {}
+ local statsListenerConnection = nil
+
+ function initStatsListener()
+ if (statsListenerConnection == nil) then
+ game.NetworkClient:GetChildren()[1]:RequestServerStats(true)
+ statsListenerConnection = game.NetworkClient:GetChildren()[1].StatsReceived:connect(refreshCharts)
+ end
+ end
+
+ function removeStatsListener()
+ if (statsListenerConnection ~= nil) then
+ game.NetworkClient:GetChildren()[1]:RequestServerStats(false)
+ statsListenerConnection:disconnect()
+ statsListenerConnection = nil
+ end
+ end
+
+ function createChart(_frame)
+ local chart = {
+ frame = _frame,
+ values = {},
+ bars = {},
+ curIndex = 0
+ }
+ return chart
+ end
+
+ function setupCharts(name)
+ local newChart = createChart(Dev_StatsChartFrame:Clone())
+ newChart.frame.Parent = Dev_TextHolder
+ newChart.frame.TitleText.Text = name
+ local newPos = 5 + numCharts * 110
+ newChart.frame.Position = UDim2.new(0, 5, 0, newPos);
+ for i = 1, numBars do
+ local bar = Dev_StatsChartBar:Clone()
+ bar.Position = UDim2.new(bar.Position.X.Scale, i * (bar.Size.X.Offset + 1), bar.Position.Y.Scale, bar.Position.Y.Offset)
+ bar.Parent = newChart.frame
+ table.insert(newChart.bars, bar)
+ end
+
+ charts[name] = newChart
+ numCharts = numCharts + 1
+ textHolderSize = newPos + 110
+ end
+
+ function clearCharts()
+ for i, chart in pairs(charts) do
+ chart.frame.Parent = nil
+ charts[i] = nil
+ end
+ numCharts = 0
+ end
+
+ function refreshCharts(stats)
+ for name, stat in pairs(stats) do
+ if (charts[name] == nil) then
+ setupCharts(name)
+ end
+
+ local chart = charts[name]
+ chart.curIndex = chart.curIndex + 1
+
+ -- remove old data
+ if chart.curIndex > numBars + 1 then
+ chart.curIndex = numBars + 1
+ table.remove(chart.values, 1)
+ end
+
+ chart.values[chart.curIndex] = stat
+
+ updateChart(chart)
+ end
+ end
+
+ function updateChart(chart)
+ local maxValue = .0001
+ local minValue = chart.values[chart.curIndex]
+
+ for i = chart.curIndex, chart.curIndex-numBars, -1 do
+ if i == 0 then break end
+ if chart.values[i] > maxValue then maxValue = chart.values[i] end
+ if chart.values[i] < minValue then minValue = chart.values[i] end
+ end
+
+ chart.frame.ChartValue.Text = "Current: "..chart.values[chart.curIndex]
+ chart.frame.ChartMaxValue.Text = "Max: "..maxValue
+ chart.frame.ChartMinValue.Text = "Min: "..minValue
+
+ for i = 1,numBars do
+
+ if chart.curIndex - i + 1 < 1 then
+ chart.bars[i].BackgroundTransparency = 1
+ else
+ chart.bars[i].BackgroundTransparency = 0
+
+ chart.bars[i].Size = UDim2.new(chart.bars[i].Size.X.Scale, chart.bars[i].Size.X.Offset, chart.bars[i].Size.Y.Scale,
+ Dev_StatsChartBar.Size.Y.Offset * (chart.values[chart.curIndex - i + 1] / maxValue))
+
+ chart.bars[i].Position = UDim2.new(chart.bars[i].Position.X.Scale, chart.bars[i].Position.X.Offset, Dev_StatsChartBar.Position.Y.Scale,
+ Dev_StatsChartBar.Position.Y.Offset + (45 - chart.bars[i].Size.Y.Offset))
+ end
+
+ end
+ end
+
+ ---Handle Dev-Console Position
+ function refreshConsolePosition(x, y)
+ if not previousMousePos then
+ return
+ end
+
+ local delta = Vector2.new(x, y) - previousMousePos
+ Dev_Container.Position = UDim2.new(0, pPos.X + delta.X, 0, pPos.Y + delta.Y)
+ end
+
+ Dev_TitleBar.TextButton.MouseButton1Down:connect(function(x, y)
+ previousMousePos = Vector2.new(x, y)
+ pPos = Dev_Container.AbsolutePosition
+ end)
+
+ Dev_TitleBar.TextButton.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+ ---Handle Dev-Console Size
+ function refreshConsoleSize(x, y)
+ if not previousMousePosResize then
+ return
+ end
+
+ local delta = Vector2.new(x, y) - previousMousePosResize
+ Dev_Container.Size = UDim2.new(0, math.max(pSize.X + delta.X, minimumSize.X), 0, math.max(pSize.Y + delta.Y, minimumSize.Y))
+ end
+ Dev_Container.Body.ResizeButton.MouseButton1Down:connect(function(x, y)
+ previousMousePosResize = Vector2.new(x, y)
+ pSize = Dev_Container.AbsoluteSize
+ end)
+
+ Dev_Container.Body.ResizeButton.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+
+ ---Handle Dev-Console Close Button
+ Dev_TitleBar.CloseButton.MouseButton1Down:connect(function(x, y)
+ Dev_Container.Visible = false
+ end)
+
+ Dev_Container.TitleBar.CloseButton.MouseButton1Up:connect(function()
+ clean()
+ removeStatsListener()
+ clearCharts()
+ end)
+
+ local optionsHidden = true
+ local animating = false
+ --Options
+ function startAnimation()
+ if animating then return end
+ animating = true
+
+ repeat
+ if optionsHidden then
+ frameNumber = frameNumber - 1
+ else
+ frameNumber = frameNumber + 1
+ end
+
+ local x = frameNumber / 5
+ local smoothStep = x * x * (3 - (2 * x))
+ Dev_OptionsButton.ImageLabel.Rotation = smoothStep * 5 * 9
+ Dev_OptionsBar.Position = UDim2.new(0, (smoothStep * 5 * 50) - 250, 0, 4)
+
+ wait()
+ if (frameNumber <= 0 and optionsHidden) or (frameNumber >= 5 and not optionsHidden) then
+ animating = false
+ end
+ until not animating
+ end
+
+ Dev_OptionsButton.MouseButton1Down:connect(function(x, y)
+ optionsHidden = not optionsHidden
+ startAnimation()
+ end)
+
+ --Scroll Position
+
+ function changeOffset(value)
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = localOffset + value
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = serverOffset + value
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = serverStatsOffset + value
+ end
+
+ repositionList()
+ end
+
+ --Refresh Dev-Console Text
+ function refreshTextHolderForReal()
+ local childMessages = Dev_TextHolder:GetChildren()
+
+ local messageList = {}
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ messageList = localMessageList
+ elseif (currentConsole == SERVER_CONSOLE) then
+ messageList = serverMessageList
+ end
+
+ local posOffset = 0
+
+ for i = 1, #childMessages do
+ childMessages[i].Visible = false
+ end
+
+ for i = 1, #messageList do
+ local message
+
+ local movePosition = false
+
+ if i > #childMessages then
+ message = Create'TextLabel'{
+ Name = 'Message';
+ Parent = Dev_TextHolder;
+ BackgroundTransparency = 1;
+ TextXAlignment = 'Left';
+ Size = UDim2.new(1, 0, 0, 14);
+ FontSize = 'Size10';
+ ZIndex = 1;
+ }
+ movePosition = true
+ else
+ message = childMessages[i]
+ end
+
+ if (outputToggleOn or messageList[i].Type ~= Enum.MessageType.MessageOutput) and
+ (infoToggleOn or messageList[i].Type ~= Enum.MessageType.MessageInfo) and
+ (warningToggleOn or messageList[i].Type ~= Enum.MessageType.MessageWarning) and
+ (errorToggleOn or messageList[i].Type ~= Enum.MessageType.MessageError) then
+ message.TextWrapped = wordWrapToggleOn
+ message.Size = UDim2.new(0.98, 0, 0, 2000)
+ message.Parent = Dev_Container
+ message.Text = messageList[i].Time.." -- "..messageList[i].Message
+
+ message.Size = UDim2.new(0.98, 0, 0, message.TextBounds.Y)
+ message.Position = UDim2.new(0, 5, 0, posOffset)
+ message.Parent = Dev_TextHolder
+ posOffset = posOffset + message.TextBounds.Y
+
+ if movePosition then
+ if (currentConsole == LOCAL_CONSOLE and localOffset > 0) or (currentConsole == SERVER_CONSOLE and serverOffset > 0) then
+ changeOffset(message.TextBounds.Y)
+ end
+ end
+
+ message.Visible = true
+
+ if messageList[i].Type == Enum.MessageType.MessageError then
+ message.TextColor3 = Color3.new(1, 0, 0)
+ elseif messageList[i].Type == Enum.MessageType.MessageInfo then
+ message.TextColor3 = Color3.new(0.4, 0.5, 1)
+ elseif messageList[i].Type == Enum.MessageType.MessageWarning then
+ message.TextColor3 = Color3.new(1, 0.6, 0.4)
+ else
+ message.TextColor3 = Color3.new(1, 1, 1)
+ end
+ end
+
+
+ end
+
+ textHolderSize = posOffset
+
+ repositionList()
+
+ end
+
+ -- Refreshing the textholder every 0.1 (if needed) is good enough, surely fast enough
+ -- We don't want it to update 50x in a tick because there are 50 messages in that tick
+ -- (Whenever for one reason or another a lot of output comes in, it can lag
+ -- This will make it behave better in a situation of a lot of output comming in)
+ local refreshQueued = false
+ function refreshTextHolder()
+ if refreshQueued or currentConsole == SERVER_STATS then return end
+ Delay(0.1,function()
+ refreshQueued = false
+ refreshTextHolderForReal()
+ end) refreshQueued = true
+ end
+
+ --Handle Dev-Console Scrollbar
+
+ local inside = 0
+ function holdingUpButton()
+ if scrollUpIsDown then
+ return
+ end
+ scrollUpIsDown = true
+ wait(.6)
+ inside = inside + 1
+ while scrollUpIsDown and inside < 2 do
+ wait()
+ changeOffset(12)
+ end
+ inside = inside - 1
+ end
+
+ function holdingDownButton()
+ if scrollDownIsDown then
+ return
+ end
+ scrollDownIsDown = true
+ wait(.6)
+ inside = inside + 1
+ while scrollDownIsDown and inside < 2 do
+ wait()
+ changeOffset(-12)
+ end
+ inside = inside - 1
+ end
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Click:connect(function()
+ changeOffset(10)
+ end)
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Down:connect(function()
+ changeOffset(10)
+ holdingUpButton()
+ end)
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ Dev_Container.Body.ScrollBar.Down.MouseButton1Down:connect(function()
+ changeOffset(-10)
+ holdingDownButton()
+ end)
+
+ Dev_Container.Body.ScrollBar.Down.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ function handleScroll(x, y)
+ if not previousMousePosScroll then
+ return
+ end
+
+ local delta = (Vector2.new(x, y) - previousMousePosScroll).Y
+
+ local backRatio = 1 - (Dev_Container.Body.TextBox.AbsoluteSize.Y / Dev_TextHolder.AbsoluteSize.Y)
+
+ local movementSize = Dev_ScrollArea.AbsoluteSize.Y - Dev_ScrollArea.Handle.AbsoluteSize.Y
+ local normalDelta = math.max(math.min(delta, movementSize), 0 - movementSize)
+ local normalRatio = normalDelta / movementSize
+
+ local textMovementSize = (backRatio * Dev_TextHolder.AbsoluteSize.Y)
+ local offsetChange = textMovementSize * normalRatio
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = pOffset - offsetChange
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = pOffset - offsetChange
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = pOffset - offsetChange
+ end
+ end
+
+ Dev_ScrollArea.Handle.MouseButton1Down:connect(function(x, y)
+ previousMousePosScroll = Vector2.new(x, y)
+ pScrollHandle = Dev_ScrollArea.Handle.AbsolutePosition
+ if (currentConsole == LOCAL_CONSOLE) then
+ pOffset = localOffset
+ elseif (currentConsole == SERVER_CONSOLE) then
+ pOffset = serverOffset
+ elseif (currentConsole == SERVER_STATS) then
+ pOffset = serverStatsOffset
+ end
+
+ end)
+
+ Dev_ScrollArea.Handle.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+ local function existsInsideContainer(container, x, y)
+ local pos = container.AbsolutePosition
+ local size = container.AbsoluteSize
+ if x < pos.X or x > pos.X + size.X or y < pos.y or y > pos.y + size.y then
+ return false
+ end
+ return true
+ end
+
+
+
+ --Refresh Dev-Console Message Positions
+ function repositionList()
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = math.min(math.max(localOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = math.min(math.max(serverOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = math.min(math.max(serverStatsOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ end
+
+ local ratio = Dev_Container.Body.TextBox.AbsoluteSize.Y / Dev_TextHolder.AbsoluteSize.Y
+
+ if ratio >= 1 then
+ Dev_Container.Body.ScrollBar.Visible = false
+ Dev_Container.Body.TextBox.Size = UDim2.new(1, -4, 1, -28 + getCommandBarOffset())
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize)
+ end
+
+
+ else
+ Dev_Container.Body.ScrollBar.Visible = true
+ Dev_Container.Body.TextBox.Size = UDim2.new(1, -25, 1, -28 + getCommandBarOffset())
+
+ local backRatio = 1 - ratio
+ local offsetRatio
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ offsetRatio = localOffset / Dev_TextHolder.AbsoluteSize.Y
+ elseif (currentConsole == SERVER_CONSOLE) then
+ offsetRatio = serverOffset / Dev_TextHolder.AbsoluteSize.Y
+ elseif (currentConsole == SERVER_STATS) then
+ offsetRatio = (serverStatsOffset / Dev_TextHolder.AbsoluteSize.Y)
+ end
+
+ local topRatio = math.max(0, backRatio - offsetRatio)
+ local scrollHandleSize = math.max((Dev_ScrollArea.AbsoluteSize.Y) * ratio, 21)
+
+ local scrollRatio = scrollHandleSize / Dev_ScrollArea.AbsoluteSize.Y
+ local ratioConversion = (1 - scrollRatio) / (1 - ratio)
+
+ local topScrollRatio = topRatio * ratioConversion
+
+ local sPos = math.min((Dev_ScrollArea.AbsoluteSize.Y) * topScrollRatio, Dev_ScrollArea.AbsoluteSize.Y - scrollHandleSize)
+
+ Dev_ScrollArea.Handle.Size = UDim2.new(1, 0, 0, scrollHandleSize)
+ Dev_ScrollArea.Handle.Position = UDim2.new(0, 0, 0, sPos)
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + localOffset)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + serverOffset)
+ elseif (currentConsole == SERVER_STATS) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + serverStatsOffset)
+ end
+
+ end
+ end
+
+ -- Easy, fast, and working nicely
+ local function numberWithZero(num)
+ return (num < 10 and "0" or "")..num
+ end
+
+ local str = "%s:%s:%s"
+
+ function ConvertTimeStamp(timeStamp)
+ local localTime = timeStamp - os.time() + math.floor(tick())
+ local dayTime = localTime % 86400
+
+ local hour = math.floor(dayTime/3600)
+
+ dayTime = dayTime - (hour * 3600)
+ local minute = math.floor(dayTime/60)
+
+ dayTime = dayTime - (minute * 60)
+ local second = dayTime
+
+ local h = numberWithZero(hour)
+ local m = numberWithZero(minute)
+ local s = numberWithZero(dayTime)
+
+ return str:format(h,m,s)
+ end
+
+ --Filter
+
+ Dev_OptionsBar.ErrorToggleButton.MouseButton1Down:connect(function(x, y)
+ errorToggleOn = not errorToggleOn
+ Dev_OptionsBar.ErrorToggleButton.CheckFrame.Visible = errorToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.WarningToggleButton.MouseButton1Down:connect(function(x, y)
+ warningToggleOn = not warningToggleOn
+ Dev_OptionsBar.WarningToggleButton.CheckFrame.Visible = warningToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.InfoToggleButton.MouseButton1Down:connect(function(x, y)
+ infoToggleOn = not infoToggleOn
+ Dev_OptionsBar.InfoToggleButton.CheckFrame.Visible = infoToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.OutputToggleButton.MouseButton1Down:connect(function(x, y)
+ outputToggleOn = not outputToggleOn
+ Dev_OptionsBar.OutputToggleButton.CheckFrame.Visible = outputToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.WordWrapToggleButton.MouseButton1Down:connect(function(x, y)
+ wordWrapToggleOn = not wordWrapToggleOn
+ Dev_OptionsBar.WordWrapToggleButton.CheckFrame.Visible = wordWrapToggleOn
+ refreshTextHolder()
+ end)
+
+ ---Dev-Console Message Functionality
+ function AddLocalMessage(str, messageType, timeStamp)
+ localMessageList[#localMessageList+1] = {Message = str, Time = ConvertTimeStamp(timeStamp), Type = messageType}
+ while #localMessageList > MAX_LIST_SIZE do
+ table.remove(localMessageList, 1)
+ end
+
+ refreshTextHolder()
+ end
+
+ function AddServerMessage(str, messageType, timeStamp)
+ serverMessageList[#serverMessageList+1] = {Message = str, Time = ConvertTimeStamp(timeStamp), Type = messageType}
+ while #serverMessageList > MAX_LIST_SIZE do
+ table.remove(serverMessageList, 1)
+ end
+
+ refreshTextHolder()
+ end
+
+
+
+ --Handle Dev-Console Local/Server Buttons
+ Dev_Container.Body.LocalConsole.MouseButton1Click:connect(function(x, y)
+ if (currentConsole ~= LOCAL_CONSOLE) then
+
+ if (currentConsole == SERVER_STATS) then
+ removeStatsListener()
+ clearCharts()
+ end
+
+ Dev_Container.CommandBar.Visible = false
+
+ currentConsole = LOCAL_CONSOLE
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ localConsole.Size = UDim2.new(0, 90, 0, 20)
+ serverConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverStats.Size = UDim2.new(0, 90, 0, 17)
+ localConsole.BackgroundTransparency = 0.6
+ serverConsole.BackgroundTransparency = 0.8
+ serverStats.BackgroundTransparency = 0.8
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+ end
+
+ refreshTextHolder()
+ end
+ end)
+
+ Dev_Container.Body.LocalConsole.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ local serverHistoryRequested = false;
+
+ Dev_Container.Body.ServerConsole.MouseButton1Click:connect(function(x, y)
+
+ if not serverHistoryRequested then
+ serverHistoryRequested = true
+ game:GetService("LogService"):RequestServerOutput()
+ end
+
+ if (currentConsole ~= SERVER_CONSOLE) then
+
+ Dev_Container.CommandBar.Visible = shouldShowCommandBar()
+
+ if (currentConsole == SERVER_STATS) then
+ removeStatsListener()
+ clearCharts()
+ end
+
+ currentConsole = SERVER_CONSOLE
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ serverConsole.Size = UDim2.new(0, 90, 0, 20)
+ localConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverConsole.BackgroundTransparency = 0.6
+ localConsole.BackgroundTransparency = 0.8
+ serverStats.BackgroundTransparency = 0.8
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+ end
+
+ refreshTextHolder()
+ end
+ end)
+
+ ---Extra Mouse Handlers for Dev-Console
+ Dev_Container.Body.ServerConsole.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ Dev_Container.Body.ServerStats.MouseButton1Click:connect(function(x, y)
+ if (currentConsole ~= SERVER_STATS) then
+
+ Dev_Container.CommandBar.Visible = false
+
+ currentConsole = SERVER_STATS
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ serverStats.Size = UDim2.new(0, 90, 0, 20)
+ serverConsole.Size = UDim2.new(0, 90, 0, 17)
+ localConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverStats.BackgroundTransparency = 0.6
+ serverConsole.BackgroundTransparency = 0.8
+ localConsole.BackgroundTransparency = 0.8
+
+ -- clear holder of log entries
+ local messages = Dev_TextHolder:GetChildren()
+ for i = 1, #messages do
+ messages[i].Visible = false
+ end
+
+ pcall(function() initStatsListener() end)
+
+ end
+ end)
+
+ Dev_Container.Body.ServerStats.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local LocalMouse = game.Players.LocalPlayer:GetMouse()
+ LocalMouse.Move:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+
+ refreshTextHolder()
+ repositionList()
+ end)
+
+ LocalMouse.Button1Up:connect(function()
+ clean()
+ end)
+
+ LocalMouse.WheelForward:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ if existsInsideContainer(Dev_Container, LocalMouse.X, LocalMouse.Y) then
+ changeOffset(10)
+ end
+ end)
+
+ LocalMouse.WheelBackward:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ if existsInsideContainer(Dev_Container, LocalMouse.X, LocalMouse.Y) then
+ changeOffset(-10)
+ end
+ end)
+
+ end
+
+ Dev_ScrollArea.Handle.MouseButton1Down:connect(function()
+ repositionList()
+ end)
+
+
+ ---Populate Dev-Console with dummy messages
+
+ local history = game:GetService("LogService"):GetLogHistory()
+
+ for i = 1, #history do
+ AddLocalMessage(history[i].message, history[i].messageType, history[i].timestamp)
+ end
+
+ game:GetService("LogService").MessageOut:connect(function(message, messageType)
+ AddLocalMessage(message, messageType, os.time())
+ end)
+
+ game:GetService("LogService").ServerMessageOut:connect(AddServerMessage)
+
+end
+
+local currentlyToggling = false
+function ToggleConsole.OnInvoke()
+ if currentlyToggling then
+ return
+ end
+
+ currentlyToggling = true
+ initializeDeveloperConsole()
+ Dev_Container.Visible = not Dev_Container.Visible
+ currentlyToggling = false
+
+ if not Dev_Container.Visible then
+ removeStatsListener()
+ clearCharts()
+ end
+
+end
diff --git a/asset/9 b/asset/9
new file mode 100644
index 0000000..52cce26
--- /dev/null
+++ b/asset/9
@@ -0,0 +1,73 @@
+--rbxassetid%9%
+--build our gui
+
+local popupFrame = Instance.new("Frame")
+popupFrame.Position = UDim2.new(0.5,-165,0.5,-175)
+popupFrame.Size = UDim2.new(0,330,0,350)
+popupFrame.Style = Enum.FrameStyle.DropShadow
+popupFrame.ZIndex = 4
+popupFrame.Name = "Popup"
+popupFrame.Visible = false
+popupFrame.Parent = script.Parent
+
+local darken = popupFrame:clone()
+darken.Size = UDim2.new(1,16,1,16)
+darken.Position = UDim2.new(0,-8,0,-8)
+darken.Name = "Darken"
+darken.ZIndex = 1
+darken.Parent = popupFrame
+
+local acceptButton = Instance.new("TextButton")
+acceptButton.Position = UDim2.new(0,20,0,270)
+acceptButton.Size = UDim2.new(0,100,0,50)
+acceptButton.Font = Enum.Font.ArialBold
+acceptButton.FontSize = Enum.FontSize.Size24
+acceptButton.Style = Enum.ButtonStyle.RobloxRoundButton
+acceptButton.TextColor3 = Color3.new(248/255,248/255,248/255)
+acceptButton.Text = "Yes"
+acceptButton.ZIndex = 5
+acceptButton.Name = "AcceptButton"
+acceptButton.Parent = popupFrame
+
+local declineButton = acceptButton:clone()
+declineButton.Position = UDim2.new(1,-120,0,270)
+declineButton.Text = "No"
+declineButton.Name = "DeclineButton"
+declineButton.Parent = popupFrame
+
+local okButton = acceptButton:clone()
+okButton.Name = "OKButton"
+okButton.Text = "OK"
+okButton.Position = UDim2.new(0.5,-50,0,270)
+okButton.Visible = false
+okButton.Parent = popupFrame
+
+local popupImage = Instance.new("ImageLabel")
+popupImage.BackgroundTransparency = 1
+popupImage.Position = UDim2.new(0.5,-140,0,10)
+popupImage.Size = UDim2.new(0,280,0,280)
+popupImage.ZIndex = 3
+popupImage.Name = "PopupImage"
+popupImage.Parent = popupFrame
+
+local backing = Instance.new("ImageLabel")
+backing.BackgroundTransparency = 1
+backing.Size = UDim2.new(1,0,1,0)
+backing.Image = "http://www.roblox.com/asset/?id=47574181"
+backing.Name = "Backing"
+backing.ZIndex = 2
+backing.Parent = popupImage
+
+local popupText = Instance.new("TextLabel")
+popupText.Name = "PopupText"
+popupText.Size = UDim2.new(1,0,0.8,0)
+popupText.Font = Enum.Font.ArialBold
+popupText.FontSize = Enum.FontSize.Size36
+popupText.BackgroundTransparency = 1
+popupText.Text = "Hello I'm a popup"
+popupText.TextColor3 = Color3.new(248/255,248/255,248/255)
+popupText.TextWrap = true
+popupText.ZIndex = 5
+popupText.Parent = popupFrame
+
+script:remove()
\ No newline at end of file
diff --git a/asset/GetScriptState.ashx b/asset/GetScriptState.ashx
new file mode 100644
index 0000000..ce614d3
--- /dev/null
+++ b/asset/GetScriptState.ashx
@@ -0,0 +1 @@
+0 0 0 00 0 0 0
\ No newline at end of file
diff --git a/asset/PrivateKey.pem b/asset/PrivateKey.pem
new file mode 100644
index 0000000..929a8d7
--- /dev/null
+++ b/asset/PrivateKey.pem
@@ -0,0 +1,3 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIICXgIBAAKBgQDJ9itcSsBa9FNyE1jBn4OBfOYsMSSJWyi0Jgn6qXNvSzLks7INwmkqejrEc4WOdUNjQ6XaoAK/vmBf7oMQJ+xuDl47rYVqLGW0JAKPSbn0QA19bmr3eSIyUeqrhfwRGn4YLBDm6CMu+m8P/VaDU1qSxPd2PuIpLmTlKFMcF+HWEQIDAQABAoGBAL49+x5W89c5q5kbjFHnlpLVOmSKbiZNDoyUAHZ0RF6j8W7prmGzrijrNoxzXW2SHEZXJNZKQAyqolH7dM41LUnaIWizNoIkuJKIb+HWzQlnu75KLNyVDtlMyTNnwTfHkAQ6vmRv8f8S74ZXlj+SKNVjd0p0R+TSqh4NHzNZkNC5AkEA33wCzFtvZJv5cVbc8Ak8VmmSdoPN9HBHuJ1BJ/VTYrd9NmGoxbb2Ixfc3kVItD1NMLs9Jo3x8VKyC0fP90KAIwJBAOdYgtK4QGJHco48J37K3g9r4Kjidv933ADnkZefhTGE4ycakv5gcvnMWbcjHRPv3a7r39+ukgsbNB7BdyKWWjsCQBsewHQuMGFkMCwZ32vdow3Vd+mb6xVbvshfhPWlZr4XCEHeLg34OvxdO/dZLw54VfKw9iXEmfSwFV0bFNiroEMCQQCB05AHBNNM09+bpnJbmykm6lk3LW+uSesyrsFrn1+1vGdlSGp5SlL7kAxA0/m7eH6lbUVDV8opZWjIYbWjuVCFAkEAv8rLnjBwqbNY1O67a4rXh4DJZ7lHm5meX7+YcW5haB4GGyZpikVXYEcfwcM5A03dTKgljLbcDT8diO5RTOsDEg==
+-----END RSA PRIVATE KEY-----
\ No newline at end of file
diff --git a/asset/backup/1 b/asset/backup/1
new file mode 100644
index 0000000..49c4e8f
--- /dev/null
+++ b/asset/backup/1
@@ -0,0 +1,94 @@
+%1%
+-- Creates all neccessary scripts for the gui on initial load, everything except build tools
+-- Created by Ben T. 10/29/10
+-- Please note that these are loaded in a specific order to diminish errors/perceived load time by user
+
+local scriptContext = game:GetService("ScriptContext")
+local touchEnabled = false
+pcall(function() touchEnabled = game:GetService("UserInputService").TouchEnabled end)
+
+-- library registration
+scriptContext:AddCoreScript(2, scriptContext,"/Libraries/LibraryRegistration/LibraryRegistration")
+
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+-- Responsible for tracking logging items
+local scriptContext = game:GetService("ScriptContext")
+scriptContext:AddCoreScript(3, scriptContext, "CoreScripts/Sections")
+
+waitForChild(game:GetService("CoreGui"),"RobloxGui")
+local screenGui = game:GetService("CoreGui"):FindFirstChild("RobloxGui")
+
+-- SettingsScript
+scriptContext:AddCoreScript(4,screenGui,"CoreScripts/Settings")
+
+if not touchEnabled then
+ -- ToolTipper (creates tool tips for gui)
+ scriptContext:AddCoreScript(5,screenGui,"CoreScripts/ToolTip")
+else
+ -- no
+end
+
+-- MainBotChatScript
+scriptContext:AddCoreScript(7,screenGui,"CoreScripts/MainBotChatScript")
+
+-- Developer Console Script
+scriptContext:AddCoreScript(8,screenGui,"CoreScripts/DeveloperConsole")
+
+-- Popup Script
+scriptContext:AddCoreScript(9,screenGui,"CoreScripts/PopupScript")
+-- Friend Notification Script (probably can use this script to expand out to other notifications)
+scriptContext:AddCoreScript(10,screenGui,"CoreScripts/NotificationScript")
+-- Chat script
+scriptContext:AddCoreScript(11, screenGui, "CoreScripts/ChatScript2")
+-- Purchase Prompt Script
+scriptContext:AddCoreScript(12, screenGui, "CoreScripts/PurchasePromptScript")
+-- Health Script
+scriptContext:AddCoreScript(13, screenGui, "CoreScripts/HealthScript")
+
+if not touchEnabled then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+elseif screenGui.AbsoluteSize.Y >= 500 then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+else
+ delay(5, function()
+ if screenGui.AbsoluteSize.Y >= 500 then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+ end
+ end)
+end
+
+if game.CoreGui.Version >= 3 then
+ -- Backpack Builder, creates most of the backpack gui
+ scriptContext:AddCoreScript(15,screenGui,"CoreScripts/BackpackScripts/BackpackBuilder")
+
+ waitForChild(screenGui,"CurrentLoadout")
+ waitForChild(screenGui,"Backpack")
+ local Backpack = screenGui.Backpack
+
+ -- Manager handles all big backpack state changes, other scripts subscribe to this and do things accordingly
+ if game.CoreGui.Version >= 7 then
+ scriptContext:AddCoreScript(16,Backpack,"CoreScripts/BackpackScripts/BackpackManager")
+ end
+
+ -- Backpack Gear (handles all backpack gear tab stuff)
+ game:GetService("ScriptContext"):AddCoreScript(17,Backpack,"CoreScripts/BackpackScripts/BackpackGear")
+ -- Loadout Script, used for gear hotkeys
+ scriptContext:AddCoreScript(18,screenGui.CurrentLoadout,"CoreScripts/BackpackScripts/LoadoutScript")
+ if game.CoreGui.Version >= 8 then
+ -- Wardrobe script handles all character dressing operations
+ scriptContext:AddCoreScript(-1,Backpack,"CoreScripts/BackpackScripts/BackpackWardrobe")
+ end
+end
\ No newline at end of file
diff --git a/asset/backup/10 b/asset/backup/10
new file mode 100644
index 0000000..a6863e6
--- /dev/null
+++ b/asset/backup/10
@@ -0,0 +1,329 @@
+%10%
+function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+waitForProperty(game.Players,"LocalPlayer")
+waitForChild(script.Parent,"Popup")
+waitForChild(script.Parent.Popup,"AcceptButton")
+script.Parent.Popup.AcceptButton.Modal = true
+
+local localPlayer = game.Players.LocalPlayer
+local teleportUI = nil
+
+local acceptedTeleport = Instance.new("IntValue")
+
+local friendRequestBlacklist = {}
+
+local teleportEnabled = true
+
+local makePopupInvisible = function()
+ if script.Parent.Popup then script.Parent.Popup.Visible = false end
+end
+
+function makeFriend(fromPlayer,toPlayer)
+
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup == nil then return end -- there is no popup!
+ if popup.Visible then return end -- currently popping something, abort!
+ if friendRequestBlacklist[fromPlayer] then return end -- previously cancelled friend request, we don't want it!
+
+ popup.PopupText.Text = "Accept Friend Request from " .. tostring(fromPlayer.Name) .. "?"
+ popup.PopupImage.Image = "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=352&y=352"
+
+ showTwoButtons()
+ popup.Visible = true
+ popup.AcceptButton.Text = "Accept"
+ popup.DeclineButton.Text = "Decline"
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+
+ local yesCon, noCon
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ popup.Visible = false
+ toPlayer:RequestFriendship(fromPlayer)
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ popup.Visible = false
+ toPlayer:RevokeFriendship(fromPlayer)
+ friendRequestBlacklist[fromPlayer] = true
+
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+end
+
+
+game.Players.FriendRequestEvent:connect(function(fromPlayer,toPlayer,event)
+
+ -- if this doesn't involve me, then do nothing
+ if fromPlayer ~= localPlayer and toPlayer ~= localPlayer then return end
+
+ if fromPlayer == localPlayer then
+ if event == Enum.FriendRequestEvent.Accept then
+ game:GetService("GuiService"):SendNotification("You are Friends",
+ "With " .. toPlayer.Name .. "!",
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(toPlayer.userId).."&x=48&y=48",
+ 5,
+ function()
+
+ end)
+ end
+ elseif toPlayer == localPlayer then
+ if event == Enum.FriendRequestEvent.Issue then
+ if friendRequestBlacklist[fromPlayer] then return end -- previously cancelled friend request, we don't want it!
+ game:GetService("GuiService"):SendNotification("Friend Request",
+ "From " .. fromPlayer.Name,
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=48&y=48",
+ 8,
+ function()
+ makeFriend(fromPlayer,toPlayer)
+ end)
+ elseif event == Enum.FriendRequestEvent.Accept then
+ game:GetService("GuiService"):SendNotification("You are Friends",
+ "With " .. fromPlayer.Name .. "!",
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=48&y=48",
+ 5,
+ function()
+
+ end)
+ end
+ end
+end)
+
+function showOneButton()
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup then
+ popup.OKButton.Visible = true
+ popup.DeclineButton.Visible = false
+ popup.AcceptButton.Visible = false
+ end
+end
+
+function showTwoButtons()
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup then
+ popup.OKButton.Visible = false
+ popup.DeclineButton.Visible = true
+ popup.AcceptButton.Visible = true
+ end
+end
+
+function onTeleport(teleportState, placeId, spawnName)
+ if game:GetService("TeleportService").CustomizedTeleportUI == false then
+ if teleportState == Enum.TeleportState.Started then
+ showTeleportUI("Teleport started...", 0)
+ elseif teleportState == Enum.TeleportState.WaitingForServer then
+ showTeleportUI("Requesting server...", 0)
+ elseif teleportState == Enum.TeleportState.InProgress then
+ showTeleportUI("Teleporting...", 0)
+ elseif teleportState == Enum.TeleportState.Failed then
+ showTeleportUI("Teleport failed. Insufficient privileges or target place does not exist.", 3)
+ end
+ end
+end
+
+function showTeleportUI(message, timer)
+ if teleportUI ~= nil then
+ teleportUI:Remove()
+ end
+ waitForChild(localPlayer, "PlayerGui")
+ teleportUI = Instance.new("Message", localPlayer.PlayerGui)
+ teleportUI.Text = message
+ if timer > 0 then
+ wait(timer)
+ teleportUI:Remove()
+ end
+end
+
+if teleportEnabled then
+
+ localPlayer.OnTeleport:connect(onTeleport)
+
+ game:GetService("TeleportService").ErrorCallback = function(message)
+ local popup = script.Parent:FindFirstChild("Popup")
+ showOneButton()
+ popup.PopupText.Text = message
+ local clickCon
+ clickCon = popup.OKButton.MouseButton1Click:connect(function()
+ game:GetService("TeleportService"):TeleportCancel()
+ if clickCon then clickCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showOneButton()
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+
+ end
+ game:GetService("TeleportService").ConfirmationCallback = function(message, placeId, spawnName)
+ local popup = script.Parent:FindFirstChild("Popup")
+ popup.PopupText.Text = message
+ popup.PopupImage.Image = ""
+
+ local yesCon, noCon
+
+ local function killCons()
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ killCons()
+ local success, err = pcall(function() game:GetService("TeleportService"):TeleportImpl(placeId,spawnName) end)
+ if not success then
+ showOneButton()
+ popup.PopupText.Text = err
+ local clickCon
+ clickCon = popup.OKButton.MouseButton1Click:connect(function()
+ if clickCon then clickCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showOneButton()
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ killCons()
+ local success = pcall(function() game:GetService("TeleportService"):TeleportCancel() end)
+ end)
+
+ local centerDialogSuccess = pcall(function() game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showTwoButtons()
+ popup.AcceptButton.Text = "Leave"
+ popup.DeclineButton.Text = "Stay"
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end)
+
+ if centerDialogSuccess == false then
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup.AcceptButton.Text = "Leave"
+ popup.DeclineButton.Text = "Stay"
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end
+ return true
+
+ end
+end
+
+game:GetService("MarketplaceService").ClientLuaDialogRequested:connect(function(message, accept, decline)
+ local popup = script.Parent:FindFirstChild("Popup")
+ popup.PopupText.Text = message
+ popup.PopupImage.Image = ""
+
+ local yesCon, noCon
+
+ local function killCons()
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ killCons()
+ game:GetService("MarketplaceService"):SignalServerLuaDialogClosed(true);
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ killCons()
+ game:GetService("MarketplaceService"):SignalServerLuaDialogClosed(false);
+ end)
+
+ local centerDialogSuccess = pcall(function() game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ function()
+ showTwoButtons()
+ popup.AcceptButton.Text = accept
+ popup.DeclineButton.Text = decline
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end)
+
+ if centerDialogSuccess == false then
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup.AcceptButton.Text = accept
+ popup.DeclineButton.Text = decline
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end
+
+ return true
+
+end)
+
+local noOptFunc = function ()
+ -- do nothing
+end
+
+Game:GetService("PointsService").PointsAwarded:connect( function(userId, pointsAwarded, userBalanceInGame, userTotalBalance)
+ if userId == Game.Players.LocalPlayer.userId then
+ if pointsAwarded > 0 then
+ game:GetService("GuiService"):SendNotification("Points Awarded!",
+ "You received " ..tostring(pointsAwarded) .. " points!",
+ "http://www.roblox.com/asset?id=155363793",
+ 5,
+ noOptFunc)
+ elseif pointsAwarded < 0 then
+ game:GetService("GuiService"):SendNotification("Points Lost!",
+ "You lost " ..tostring(-pointsAwarded) .. " points!",
+ "http://www.roblox.com/asset?id=155363793",
+ 5,
+ noOptFunc)
+ end
+ end
+end)
+
+-- Since we can't get the image right, let's just use a nice notification icon
+Game:GetService("BadgeService").BadgeAwarded:connect( function(message, userId, badgeId)
+ if userId == Game.Players.LocalPlayer.userId then
+ game:GetService("GuiService"):SendNotification("Badge Awarded!",
+ message,
+ "http://www.roblox.com/asset?id=177200377",
+ 5,
+ noOptFunc)
+ end
+end)
diff --git a/asset/backup/11 b/asset/backup/11
new file mode 100644
index 0000000..df54438
--- /dev/null
+++ b/asset/backup/11
@@ -0,0 +1,1756 @@
+%11%
+--[[
+ // FileName: ChatScript.lua
+ // Written by: SolarCrane
+ // Description: Code for lua side chat on ROBLOX.
+]]
+
+--[[ CONSTANTS ]]
+local FORCE_CHAT_GUI = false
+local USE_PLAYER_GUI_TESTING = false
+
+local ADMIN_LIST = {
+ ['68465808'] = true, -- IMightBeLying
+ ['32345429'] = true, -- Rbadam
+ ['48453004'] = true, -- Adamintygum
+ ['57705391'] = true, -- androidtest
+ ['58491921'] = true, -- RobloxFrenchie
+ ['29341155'] = true, -- JacksSmirkingRevenge
+ ['60629145'] = true, -- Mandaari
+ ['6729993'] = true, -- vaiobot
+ ['9804369'] = true, -- Goddessnoob
+ ['67906358'] = true, -- Thr33pakShak3r
+ ['41101356'] = true, -- effward
+ ['29667843'] = true, -- Blockhaak
+ ['26076267'] = true, -- Drewbda
+ ['65171466'] = true, -- triptych999
+ ['264635'] = true, -- Tone
+ ['59257875'] = true, -- fasterbuilder19
+ ['30068452'] = true, -- Zeuxcg
+ ['53627251'] = true, -- concol2
+ ['56449'] = true, -- ReeseMcBlox
+ ['7210880'] = true, -- Jeditkacheff
+ ['35187797'] = true, -- ChiefJustus
+ ['21964644'] = true, -- Ellissar
+ ['63971416'] = true, -- geekndestroy
+ ['111627'] = true, -- Noob007
+ ['482238'] = true, -- Limon
+ ['39861325'] = true, -- hawkington
+ ['32580099'] = true, -- Tabemono
+ ['504316'] = true, -- BrightEyes
+ ['35825637'] = true, -- Monsterinc3D
+ ['55311255'] = true, -- IsolatedEvent
+ ['48988254'] = true, -- CountOnConnor
+ ['357346'] = true, -- Scubasomething
+ ['28969907'] = true, -- OnlyTwentyCharacters
+ ['17707636'] = true, -- LordRugdumph
+ ['26714811'] = true, -- bellavour
+ ['24941'] = true, -- david.baszucki
+ ['13057592'] = true, -- ibanez2189
+ ['66766775'] = true, -- ConvexHero
+ ['13268404'] = true, -- Sorcus
+ ['26065068'] = true, -- DeeAna00
+ ['4108667'] = true, -- TheLorekt
+ ['605367'] = true, -- MSE6
+ ['28350010'] = true, -- CorgiParade
+ ['1636196'] = true, -- Varia
+ ['27861308'] = true, -- 4runningwolves
+ ['26699190'] = true, -- pulmoesflor
+ ['9733258'] = true, -- Olive71
+ ['2284059'] = true, -- groundcontroll2
+ ['28080592'] = true, -- GuruKrish
+ ['28137935'] = true, -- Countvelcro
+ ['25964666'] = true, -- IltaLumi
+ ['31221099'] = true, -- juanjuan23
+ ['13965343'] = true, -- OstrichSized
+ ['541489'] = true, -- jackintheblox
+ ['38324232'] = true, -- SlingshotJunkie
+ ['146569'] = true, -- gordonrox24
+ ['61666252'] = true, -- sharpnine
+ ['25540124'] = true, -- Motornerve
+ ['29044576'] = true, -- watchmedogood
+ ['49626068'] = true, -- jmargh
+ ['57352126'] = true, -- JayKorean
+ ['25682044'] = true, -- Foyle
+ ['1113299'] = true, -- MajorTom4321
+ ['30598693'] = true, -- supernovacaine
+ ['1311'] = true, -- FFJosh
+ ['23603273'] = true, -- Sickenedmonkey
+ ['28568151'] = true, -- Doughtless
+ ['8298697'] = true, -- KBUX
+ ['39871898'] = true, -- totallynothere
+ ['57708043'] = true, -- ErzaStar
+ ['22'] = true, -- Keith
+ ['2430782'] = true, -- Chro
+ ['29373363'] = true, -- SolarCrane
+ ['29116915'] = true, -- GloriousSalt
+ ['6783205'] = true, -- UristMcSparks
+ ['62155769'] = true, -- ITOlaurEN
+ ['24162607'] = true, -- Malcomso
+ ['66692187'] = true, -- HeySeptember
+ ['80254'] = true, -- Stickmasterluke
+ ['66093461'] = true, -- chefdeletat
+ ['62968051'] = true, -- windlight13
+ ['80119'] = true, -- Stravant
+ ['61890000'] = true, -- imaginationsensation
+ ['916'] = true, -- Matt Dusek
+ ['4550725'] = true, -- CrimmsonGhost
+ ['59737068'] = true, -- Mcrtest
+ ['5600283'] = true, -- Seranok
+ ['48656806'] = true, -- maxvee
+ ['48656806'] = true, -- Coatp0cketninja
+ ['35231885'] = true, -- Screenme
+ ['55958416'] = true, -- b1tsh1ft
+ ['51763936'] = true, -- ConvexRumbler
+ ['59638684'] = true, -- mpliner476
+ ['44231609'] = true, -- Totbl
+ ['16906083'] = true, -- Aquabot8
+ ['23984372'] = true, -- grossinger
+ ['13416513'] = true, -- Merely
+ ['27416429'] = true, -- CDakkar
+ ['46526337'] = true, -- logitek00
+ ['21969613'] = true, -- Siekiera
+ ['39488230'] = true, -- Robloxkidsaccount
+ ['60425210'] = true, -- flotsamthespork
+ ['16732061'] = true, -- Soggoth
+ ['33904052'] = true, -- Phil
+ ['39882028'] = true, -- OrcaSparkles
+ ['62060462'] = true, -- skullgoblin
+ ['29044708'] = true, -- RickROSStheB0SS
+ ['15782010'] = true, -- ArgonPirate
+ ['6949935'] = true, -- NobleDragon
+ ['41256555'] = true, -- Squidcod
+ ['16150324'] = true, -- Raeglyn
+ ['24419770'] = true, -- Xerolayne
+ ['20396599'] = true, -- Robloxsai
+ ['55579189'] = true, -- Briarroze
+ ['21641566'] = true, -- hawkeyebandit
+ ['39871292'] = true, -- DapperBuffalo
+ ['48725400'] = true, -- Vukota
+ ['60880618'] = true, -- swiftstone
+ ['8736269'] = true, -- Gemlocker
+ ['17199995'] = true, -- Tarabyte
+ ['6983145'] = true, -- Timobius
+ ['20048521'] = true, -- Tobotrobot
+ ['1644345'] = true, -- Foster008
+ ['33067469'] = true, -- Twberg
+ ['57741156'] = true, -- DarthVaden
+ ['51164101'] = true, -- Khanovich
+ ['61380399'] = true, -- oLEFTo
+ ['39876101'] = true, -- CodeWriter
+ ['23598967'] = true, -- VladTheFirst
+ ['39299049'] = true, -- Phaedre
+ ['39855185'] = true, -- gorroth
+ ['61004766'] = true, -- jynj1984
+ ['10261020'] = true, -- RoboYZ
+ ['44564747'] = true, -- ZodiacZak
+}
+
+local CHAT_COLORS =
+{
+ BrickColor.new("Bright red"),
+ BrickColor.new("Bright blue"),
+ BrickColor.new("Earth green"),
+ BrickColor.new("Bright violet"),
+ BrickColor.new("Bright orange"),
+ BrickColor.new("Bright yellow"),
+ BrickColor.new("Light reddish violet"),
+ BrickColor.new("Brick yellow"),
+}
+-- These emotes are copy-pastad from the humanoidLocalAnimateKeyframe script
+local EMOTE_NAMES = {wave = true, point = true, dance = true, dance2 = true, dance3 = true, laugh = true, cheer = true}
+local MESSAGES_FADE_OUT_TIME = 30
+--[[ END OF CONSTANTS ]]
+
+--[[ SERVICES ]]
+local RunService = game:GetService('RunService')
+local CoreGuiService = game:GetService('CoreGui')
+local PlayersService = game:GetService('Players')
+local DebrisService = game:GetService('Debris')
+local GuiService = game:GetService('GuiService')
+local InputService = game:GetService('UserInputService')
+local StarterGui = game:GetService('StarterGui')
+--[[ END OF SERVICES ]]
+
+--[[ SCRIPT VARIABLES ]]
+
+-- I am not fond of waiting at the top of the script here...
+while PlayersService.LocalPlayer == nil do PlayersService.ChildAdded:wait() end
+local Player = PlayersService.LocalPlayer
+-- GuiRoot will act as the top-node for parenting GUIs
+local GuiRoot = nil
+if USE_PLAYER_GUI_TESTING then
+ GuiRoot = Instance.new("ScreenGui")
+ GuiRoot.Name = "RobloxGui"
+ GuiRoot.Parent = Player:WaitForChild('PlayerGui')
+else
+ GuiRoot = CoreGuiService:WaitForChild('RobloxGui')
+end
+--[[ END OF SCRIPT VARIABLES ]]
+
+local Util = {}
+do
+ -- Check if we are running on a touch device
+ function Util.IsTouchDevice()
+ local touchEnabled = false
+ pcall(function() touchEnabled = InputService.TouchEnabled end)
+ return touchEnabled
+ end
+
+ function Util.Create(instanceType)
+ return function(data)
+ local obj = Instance.new(instanceType)
+ for k, v in pairs(data) do
+ if type(k) == 'number' then
+ v.Parent = obj
+ else
+ obj[k] = v
+ end
+ end
+ return obj
+ end
+ end
+
+ function Util.Clamp(low, high, input)
+ return math.max(low, math.min(high, input))
+ end
+
+ function Util.Linear(t, b, c, d)
+ if t >= d then return b + c end
+
+ return c*t/d + b
+ end
+
+ function Util.EaseOutQuad(t, b, c, d)
+ if t >= d then return b + c end
+
+ t = t/d;
+ return -c * t*(t-2) + b
+ end
+
+ function Util.EaseInOutQuad(t, b, c, d)
+ if t >= d then return b + c end
+
+ t = t / (d/2);
+ if (t < 1) then return c/2*t*t + b end;
+ t = t - 1;
+ return -c/2 * (t*(t-2) - 1) + b;
+ end
+
+ function Util.PropertyTweener(instance, prop, start, final, duration, easingFunc, cbFunc)
+ local this = {}
+ this.StartTime = tick()
+ this.EndTime = this.StartTime + duration
+ this.Cancelled = false
+
+ local finished = false
+ local percentComplete = 0
+ spawn(function()
+ local now = tick()
+ while now < this.EndTime and instance do
+ if this.Cancelled then
+ return
+ end
+ instance[prop] = easingFunc(now - this.StartTime, start, final - start, duration)
+ percentComplete = Util.Clamp(0, 1, (now - this.StartTime) / duration)
+ RunService.RenderStepped:wait()
+ now = tick()
+ end
+ if this.Cancelled == false and instance then
+ instance[prop] = final
+ finished = true
+ percentComplete = 1
+ if cbFunc then
+ cbFunc()
+ end
+ end
+ end)
+
+ function this:GetPercentComplete()
+ return percentComplete
+ end
+
+ function this:IsFinished()
+ return finished
+ end
+
+ function this:Cancel()
+ this.Cancelled = true
+ end
+
+ return this
+ end
+
+ function Util.Signal()
+ local sig = {}
+
+ local mSignaler = Instance.new('BindableEvent')
+
+ local mArgData = nil
+ local mArgDataCount = nil
+
+ function sig:fire(...)
+ mArgData = {...}
+ mArgDataCount = select('#', ...)
+ mSignaler:Fire()
+ end
+
+ function sig:connect(f)
+ if not f then error("connect(nil)", 2) end
+ return mSignaler.Event:connect(function()
+ f(unpack(mArgData, 1, mArgDataCount))
+ end)
+ end
+
+ function sig:wait()
+ mSignaler.Event:wait()
+ assert(mArgData, "Missing arg data, likely due to :TweenSize/Position corrupting threadrefs.")
+ return unpack(mArgData, 1, mArgDataCount)
+ end
+
+ return sig
+ end
+
+ function Util.DisconnectEvent(conn)
+ if conn then
+ conn:disconnect()
+ end
+ return nil
+ end
+
+ function Util.SetGUIInsetBounds(x, y)
+ local success, _ = pcall(function() GuiService:SetGlobalGuiInset(0, x, 0, y) end)
+ if not success then
+ pcall(function() GuiService:SetGlobalSizeOffsetPixel(-x, -y) end) -- Legacy GUI-offset function
+ end
+ end
+
+ local baseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+ baseUrl = string.gsub(baseUrl,"/m.","/www.") --mobile site does not work for this stuff!
+ function Util.GetSecureApiBaseUrl()
+ local secureApiUrl = baseUrl
+ secureApiUrl = string.gsub(secureApiUrl,"http","https")
+ secureApiUrl = string.gsub(secureApiUrl,"www","api")
+ return secureApiUrl
+ end
+
+ function Util.GetPlayerByName(playerName)
+ -- O(n), may be faster if I store a reverse hash from the players list; can't trust FindFirstChild in PlayersService because anything can be parented to there.
+ local lowerName = string.lower(playerName)
+ for _, player in pairs(PlayersService:GetPlayers()) do
+ if string.lower(player.Name) == lowerName then
+ return player
+ end
+ end
+ return nil -- Found no player
+ end
+
+ local function GetNameValue(pName)
+ local value = 0
+ for index = 1, #pName do
+ local cValue = string.byte(string.sub(pName, index, index))
+ local reverseIndex = #pName - index + 1
+ if #pName%2 == 1 then
+ reverseIndex = reverseIndex - 1
+ end
+ if reverseIndex%4 >= 2 then
+ cValue = -cValue
+ end
+ value = value + cValue
+ end
+ return value%8
+ end
+
+ function Util.ComputeChatColor(pName)
+ return CHAT_COLORS[GetNameValue(pName) + 1].Color
+ end
+
+ -- This is a memo-izing function
+ local testLabel = Instance.new('TextLabel')
+ testLabel.TextWrapped = true;
+ testLabel.Position = UDim2.new(1,0,1,0)
+ testLabel.Parent = GuiRoot -- Note: We have to parent it to check TextBounds
+ -- The TextSizeCache table looks like this Text->Font->sizeBounds->FontSize
+ local TextSizeCache = {}
+ function Util.GetStringTextBounds(text, font, fontSize, sizeBounds)
+ -- If no sizeBounds are specified use some huge number
+ sizeBounds = sizeBounds or false
+ if not TextSizeCache[text] then
+ TextSizeCache[text] = {}
+ end
+ if not TextSizeCache[text][font] then
+ TextSizeCache[text][font] = {}
+ end
+ if not TextSizeCache[text][font][sizeBounds] then
+ TextSizeCache[text][font][sizeBounds] = {}
+ end
+ if not TextSizeCache[text][font][sizeBounds][fontSize] then
+ testLabel.Text = text
+ testLabel.Font = font
+ testLabel.FontSize = fontSize
+ if sizeBounds then
+ testLabel.TextWrapped = true;
+ testLabel.Size = sizeBounds
+ else
+ testLabel.TextWrapped = false;
+ end
+ TextSizeCache[text][font][sizeBounds][fontSize] = testLabel.TextBounds
+ end
+ return TextSizeCache[text][font][sizeBounds][fontSize]
+ end
+end
+
+local SelectChatModeEvent = Util.Signal()
+local SelectPlayerEvent = Util.Signal()
+
+local function CreateChatMessage()
+ local this = {}
+
+ this.Settings =
+ {
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size14;
+ }
+
+ function this:OnResize()
+ -- Nothing!
+ end
+
+ function this:FadeIn()
+ local gui = this:GetGui()
+ if gui then
+ --Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ gui.Visible = true
+ end
+ end
+
+ function this:FadeOut()
+ local gui = this:GetGui()
+ if gui then
+ --Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ gui.Visible = false
+ end
+ end
+
+ function this:GetGui()
+ return this.Container
+ end
+
+ function this:Destroy()
+ if this.Container ~= nil then
+ this.Container:Destroy()
+ this.Container = nil
+ end
+ end
+
+ return this
+end
+
+local function CreateSystemChatMessage(chattedMessage)
+ local this = CreateChatMessage()
+
+ this.chatMessage = chattedMessage
+
+ function this:OnResize(containerSize)
+ if this.Container and this.ChatMessage then
+ this.Container.Size = UDim2.new(1,0,0,1000)
+ local textHeight = this.ChatMessage.TextBounds.Y
+ this.Container.Size = UDim2.new(1,0,0,textHeight)
+ return textHeight
+ end
+ end
+
+ local function CreateMessageGuiElement()
+ local systemMesasgeDisplayText = this.chatMessage or ""
+ local systemMessageSize = Util.GetStringTextBounds(systemMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize, UDim2.new(0, 400, 0, 1000))
+
+ local container = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Position = UDim2.new(0, 0, 0, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+
+ local chatMessage = Util.Create'TextLabel'
+ {
+ Name = 'SystemChatMessage';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ Text = systemMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+
+ container.Size = UDim2.new(1, 0, 0, systemMessageSize.Y);
+ this.Container = container
+ this.ChatMessage = chatMessage
+ end
+
+ CreateMessageGuiElement()
+
+ return this
+end
+
+local function CreatePlayerChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ local this = CreateChatMessage()
+
+ this.PlayerChatType = playerChatType
+ this.SendingPlayer = sendingPlayer
+ this.RawMessageContent = chattedMessage
+ this.ReceivingPlayer = receivingPlayer
+ this.ReceivedTime = tick()
+
+ this.Neutral = this.SendingPlayer and this.SendingPlayer.Neutral or true
+ this.TeamColor = this.SendingPlayer and this.SendingPlayer.TeamColor or BrickColor.new("White")
+
+ function this:OnResize(containerSize)
+ if this.Container and this.ChatMessage then
+ this.Container.Size = UDim2.new(1,0,0,1000)
+ local textHeight = this.ChatMessage.TextBounds.Y
+ this.Container.Size = UDim2.new(1,0,0,textHeight)
+ return textHeight
+ end
+ end
+
+ function this:FormatMessage()
+ local result = ""
+ if this.RawMessageContent then
+ local message = this.RawMessageContent
+
+ if string.sub(message, 1, 3) == '/e ' or string.sub(message, 1, 7) == '/emote ' then
+ if this.SendingPlayer then
+ result = this.SendingPlayer.Name .. " emotes."
+ end
+ else
+ result = message
+ end
+ end
+ return result
+ end
+
+ function this:FormatChatType()
+ if this.PlayerChatType then
+ if this.PlayerChatType == Enum.PlayerChatType.All then
+ --return "[All]"
+ elseif this.PlayerChatType == Enum.PlayerChatType.Team then
+ return "[Team]"
+ elseif this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ -- nothing!
+ end
+ end
+ end
+
+ function this:FormatPlayerNameText()
+ local playerName = ""
+ -- If we are sending a whisper to someone, then we should show their name
+ if this.PlayerChatType == Enum.PlayerChatType.Whisper and this.SendingPlayer and this.SendingPlayer == Player then
+ playerName = (this.ReceivingPlayer and this.ReceivingPlayer.Name or "")
+ else
+ playerName = (this.SendingPlayer and this.SendingPlayer.Name or "")
+ end
+ return "[" .. playerName .. "]"
+ end
+
+ function this:Destroy()
+ if this.Container ~= nil then
+ this.Container:Destroy()
+ this.Container = nil
+ end
+ this.ClickedOnModeConn = Util.DisconnectEvent(this.ClickedOnModeConn)
+ this.ClickedOnPlayerConn = Util.DisconnectEvent(this.ClickedOnPlayerConn)
+ end
+
+ local function CreateMessageGuiElement()
+ local toMesasgeDisplayText = "To: "
+ local toMessageSize = Util.GetStringTextBounds(toMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize)
+ local fromMesasgeDisplayText = "From: "
+ local fromMessageSize = Util.GetStringTextBounds(fromMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize)
+ local chatTypeDisplayText = this:FormatChatType()
+ local chatTypeSize = chatTypeDisplayText and Util.GetStringTextBounds(chatTypeDisplayText, this.Settings.Font, this.Settings.FontSize) or Vector2.new(0,0)
+ local playerNameDisplayText = this:FormatPlayerNameText()
+ local playerNameSize = Util.GetStringTextBounds(playerNameDisplayText, this.Settings.Font, this.Settings.FontSize)
+
+ local singleSpaceSize = Util.GetStringTextBounds(" ", this.Settings.Font, this.Settings.FontSize)
+ local numNeededSpaces = math.ceil(playerNameSize.X / singleSpaceSize.X) + 1
+ local chatMessageDisplayText = string.rep(" ", numNeededSpaces) .. this:FormatMessage()
+ local chatMessageSize = Util.GetStringTextBounds(chatMessageDisplayText, this.Settings.Font, this.Settings.FontSize, UDim2.new(0, 400 - 5 - playerNameSize.X, 0, 1000))
+
+
+ local playerColor = Color3.new(1,1,1)
+ if this.SendingPlayer then
+ if this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ if this.SendingPlayer == Player and this.ReceivingPlayer then
+ playerColor = Util.ComputeChatColor(this.ReceivingPlayer.Name)
+ else
+ playerColor = Util.ComputeChatColor(this.SendingPlayer.Name)
+ end
+ else
+ if this.SendingPlayer.Neutral then
+ playerColor = Util.ComputeChatColor(this.SendingPlayer.Name)
+ else
+ playerColor = this.SendingPlayer.TeamColor.Color
+ end
+ end
+ end
+
+ local container = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Position = UDim2.new(0, 0, 0, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+ local xOffset = 0
+
+ if this.SendingPlayer and this.SendingPlayer == Player and this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ local whisperToText = Util.Create'TextLabel'
+ {
+ Name = 'WhisperTo';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, toMessageSize.X, 0, toMessageSize.Y);
+ Text = toMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ xOffset = xOffset + toMessageSize.X
+ elseif this.SendingPlayer and this.SendingPlayer ~= Player and this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ local whisperFromText = Util.Create'TextLabel'
+ {
+ Name = 'whisperFromText';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, fromMessageSize.X, 0, fromMessageSize.Y);
+ Text = fromMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ xOffset = xOffset + fromMessageSize.X
+ else
+ local userNameDot = Util.Create'ImageLabel'
+ {
+ Name = "UserNameDot";
+ Size = UDim2.new(0, 14, 0, 14);
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 2);
+ BorderSizePixel = 0;
+ Image = "rbxasset://textures/ui/chat_teamButton.png";
+ ImageColor3 = playerColor;
+ Parent = container;
+ }
+ xOffset = xOffset + 14 + 3
+ end
+ if chatTypeDisplayText then
+ local chatModeButton = Util.Create(Util.IsTouchDevice() and 'TextLabel' or 'TextButton')
+ {
+ Name = 'ChatMode';
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = chatTypeDisplayText;
+ TextColor3 = Color3.new(255/255, 255/255, 243/255);
+ Position = UDim2.new(0, xOffset, 0, 0);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ Size = UDim2.new(0, chatTypeSize.X, 0, chatTypeSize.Y);
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container
+ }
+ if chatModeButton:IsA('TextButton') then
+ this.ClickedOnModeConn = chatModeButton.MouseButton1Click:connect(function()
+ SelectChatModeEvent:fire(this.PlayerChatType)
+ end)
+ end
+ if this.PlayerChatType == Enum.PlayerChatType.Team then
+ chatModeButton.TextColor3 = playerColor
+ end
+ xOffset = xOffset + chatTypeSize.X + 1
+ end
+ local userNameButton = Util.Create(Util.IsTouchDevice() and 'TextLabel' or 'TextButton')
+ {
+ Name = 'PlayerName';
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = playerNameDisplayText;
+ TextColor3 = playerColor;
+ Position = UDim2.new(0, xOffset, 0, 0);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ Size = UDim2.new(0, playerNameSize.X, 0, playerNameSize.Y);
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container
+ }
+ if userNameButton:IsA('TextButton') then
+ this.ClickedOnPlayerConn = userNameButton.MouseButton1Click:connect(function()
+ SelectPlayerEvent:fire(this.SendingPlayer)
+ end)
+ end
+
+ local chatMessage = Util.Create'TextLabel'
+ {
+ Name = 'ChatMessage';
+ Position = UDim2.new(0, xOffset, 0, 0);
+ Size = UDim2.new(1, -xOffset, 1, 0);
+ Text = chatMessageDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(255/255, 255/255, 243/255);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ -- Check if they got moderated and put up a real message instead of Label
+ if chatMessage.Text == 'Label' and chatMessageDisplayText ~= 'Label' then
+ chatMessage.Text = string.rep(" ", numNeededSpaces) .. '[Content Deleted]'
+ end
+ if this.SendingPlayer and ADMIN_LIST[tostring(this.SendingPlayer.userId)] then
+ chatMessage.TextColor3 = Color3.new(1, 215/255, 0)
+ end
+ chatMessage.Size = chatMessage.Size + UDim2.new(0, 0, 0, chatMessage.TextBounds.Y);
+
+ container.Size = UDim2.new(1, 0, 0, math.max(chatMessageSize.Y, userNameButton.Size.Y.Offset));
+ this.Container = container
+ this.ChatMessage = chatMessage
+ end
+
+ CreateMessageGuiElement()
+
+ return this
+end
+
+local function CreateChatBarWidget(settings)
+ local this = {}
+
+ -- MessageModes: {All, Team, Whisper}
+ this.MessageMode = "All"
+ this.TargetWhisperPlayer = nil
+ this.Settings = settings
+
+ this.ChatBarGainedFocusEvent = Util.Signal()
+ this.ChatBarLostFocusEvent = Util.Signal()
+ this.ChatCommandEvent = Util.Signal() -- success, actionType, captures
+ this.ChatErrorEvent = Util.Signal() -- success, actionType, captures
+
+ this.ChatMatchingRegex =
+ {
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/w (%w+)") end] = "Whisper";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/whisper (%w+)") end] = "Whisper";
+
+ [function(chatBarText) return string.find(chatBarText, "^%%") end] = "Team";
+ [function(chatBarText) return string.find(chatBarText, "^(TEAM)") end] = "Team";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/t") end] = "Team";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/team") end] = "Team";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/a") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/all") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/s") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/say") end] = "All";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/e") end] = "Emote";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/emote") end] = "Emote";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/%?") end] = "Help";
+ }
+
+ local ChatModesDict =
+ {
+ ['Whisper'] = 'Whisper';
+ ['Team'] = 'Team';
+ ['All'] = 'All';
+ [Enum.PlayerChatType.Whisper] = 'Whisper';
+ [Enum.PlayerChatType.Team] = 'Team';
+ [Enum.PlayerChatType.All] = 'All';
+ }
+
+ local function TearDownEvents()
+ -- Note: This is a new api so we need to pcall it
+ pcall(function() GuiService:RemoveSpecialKey(Enum.SpecialKey.ChatHotkey) end)
+ this.SpecialKeyPressedConn = Util.DisconnectEvent(this.SpecialKeyPressedConn)
+ this.ClickToChatButtonConn = Util.DisconnectEvent(this.ClickToChatButtonConn)
+ this.ChatBarFocusLostConn = Util.DisconnectEvent(this.ChatBarFocusLostConn)
+ this.ChatBarLostFocusConn = Util.DisconnectEvent(this.ChatBarLostFocusConn)
+ this.SelectChatModeConn = Util.DisconnectEvent(this.SelectChatModeConn)
+ this.SelectPlayerConn = Util.DisconnectEvent(this.SelectPlayerConn)
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ end
+
+ local function HookUpEvents()
+ TearDownEvents() -- Cleanup old events
+
+ -- ChatHotKey is '/'
+ GuiService:AddSpecialKey(Enum.SpecialKey.ChatHotkey)
+ this.SpecialKeyPressedConn = GuiService.SpecialKeyPressed:connect(function(key)
+ if key == Enum.SpecialKey.ChatHotkey then
+ this:FocusChatBar()
+ end
+ end)
+
+ if this.ClickToChatButton then this.ClickToChatButtonConn = this.ClickToChatButton.MouseButton1Click:connect(function() this:FocusChatBar() end) end
+
+ if this.ChatBar then this.ChatBarFocusLostConn = this.ChatBar.FocusLost:connect(function(...) this.ChatBarLostFocusEvent:fire(...) end) end
+
+ if this.ChatBarLostFocusEvent then this.ChatBarLostFocusConn = this.ChatBarLostFocusEvent:connect(function(...) this:OnChatBarFocusLost(...) end) end
+
+ this.SelectChatModeConn = SelectChatModeEvent:connect(function(chatType)
+ this:SetMessageMode(chatType)
+ this:FocusChatBar()
+ end)
+
+ this.SelectPlayerConn = SelectPlayerEvent:connect(function(chatPlayer)
+ this.TargetWhisperPlayer = chatPlayer
+ this:SetMessageMode("Whisper")
+ this:FocusChatBar()
+ end)
+ end
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if enabled then
+ HookUpEvents()
+ else
+ TearDownEvents()
+ end
+ if this.ChatBarContainer then
+ this.ChatBarContainer.Visible = enabled
+ end
+ end
+ end
+
+ function this:IsAChatMode(mode)
+ return ChatModesDict[mode] ~= nil
+ end
+
+ function this:IsAnEmoteMode(mode)
+ return mode == "Emote"
+ end
+
+ function this:ProcessChatBarModes(requireWhitespaceAfterChatMode)
+ local matchedAChatCommand = false
+ if this.ChatBar then
+ local chatBarText = this:SanitizeInput(this:GetChatBarText())
+ for regexFunc, actionType in pairs(this.ChatMatchingRegex) do
+ local start, finish, capture = regexFunc(chatBarText)
+ if start and finish then
+ -- The following line is for whether or not to try setting the chatmode as-you-type
+ -- versus when you press enter.
+ local whitespaceAfterSlashCommand = string.find(string.sub(chatBarText, finish+1, finish+1), "%s")
+ if (not requireWhitespaceAfterChatMode and finish == #chatBarText) or whitespaceAfterSlashCommand then
+ if this:IsAChatMode(actionType) then
+ if actionType == "Whisper" then
+ local targetPlayer = capture and Util.GetPlayerByName(capture)
+ if targetPlayer then --and targetPlayer ~= Player then
+ this.TargetWhisperPlayer = targetPlayer
+ -- start from two over to eat the space or tab character after the slash command
+ this:SetChatBarText(string.sub(chatBarText, finish + 2))
+ this:SetMessageMode(actionType)
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ else
+ this:SetChatBarText("")
+ this.ChatCommandEvent:fire(false, actionType, capture)
+ end
+ else
+ -- start from two over to eat the space or tab character after the slash command
+ this:SetChatBarText(string.sub(chatBarText, finish + 2))
+ this:SetMessageMode(actionType)
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ end
+ elseif actionType == "Emote" then
+ -- You can only emote to everyone.
+ this:SetMessageMode('All')
+ elseif not requireWhitespaceAfterChatMode then -- Some non-chat related command
+ if actionType == "Help" then
+ this:SetChatBarText("") -- Clear the chat so we don't send /? to everyone
+ end
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ end
+ -- should we break here since we already matched a slash command or keep going?
+ matchedAChatCommand = true
+ end
+ end
+ end
+ end
+ return matchedAChatCommand
+ end
+
+ local previousText = ""
+ function this:OnChatBarTextChanged()
+ if not Util.IsTouchDevice() then
+ this:ProcessChatBarModes(true)
+ local newText = this:GetChatBarText()
+ if #newText > this.Settings.MaxCharactersInMessage then
+ local fixedText = ""
+ -- This is a hack to deal with the bug that holding down a key for repeated input doesn't trigger the textChanged event
+ if #newText == #previousText + 1 then
+ fixedText = string.sub(previousText, 1, this.Settings.MaxCharactersInMessage)
+ else
+ fixedText = string.sub(newText, 1, this.Settings.MaxCharactersInMessage)
+ end
+ this:SetChatBarText(fixedText)
+ previousText = fixedText
+ -- TODO: Flash Max Characters Feedback
+ else
+ previousText = newText
+ end
+ end
+ end
+
+ function this:GetChatBarText()
+ return this.ChatBar and this.ChatBar.Text or ""
+ end
+
+ function this:SetChatBarText(newText)
+ if this.ChatBar then
+ this.ChatBar.Text = newText
+ end
+ end
+
+ function this:GetMessageMode()
+ return this.MessageMode
+ end
+
+ function this:SetMessageMode(newMessageMode)
+ newMessageMode = ChatModesDict[newMessageMode]
+ if this.MessageMode ~= newMessageMode then
+ this.MessageMode = newMessageMode
+ if this.ChatModeText then
+ if newMessageMode == 'Whisper' then
+ -- TODO: also update this when they change players to whisper to
+ local chatRecipientText = "[" .. (this.TargetWhisperPlayer and this.TargetWhisperPlayer.Name or "") .. "]"
+ local chatRecipientTextBounds = Util.GetStringTextBounds(chatRecipientText, this.ChatModeText.Font, this.ChatModeText.FontSize)
+
+ this.ChatModeText.TextColor3 = this.Settings.WhisperTextColor
+ this.ChatModeText.Text = chatRecipientText
+ this.ChatModeText.Size = UDim2.new(0, chatRecipientTextBounds.X, 1, 0)
+ elseif newMessageMode == 'Team' then
+ local chatTeamText = '[Team]'
+ local chatTeamTextBounds = Util.GetStringTextBounds(chatTeamText, this.ChatModeText.Font, this.ChatModeText.FontSize)
+
+ this.ChatModeText.TextColor3 = this.Settings.TeamTextColor
+ this.ChatModeText.Text = "[Team]"
+ this.ChatModeText.Size = UDim2.new(0, chatTeamTextBounds.X, 1, 0)
+ else
+ this.ChatModeText.Text = ""
+ this.ChatModeText.Size = UDim2.new(0, 0, 1, 0)
+ end
+ if this.ChatBar then
+ local offset = this.ChatModeText.Size.X.Offset + this.ChatModeText.Position.X.Offset
+ this.ChatBar.Size = UDim2.new(1, -offset - 5, 1, 0)
+ this.ChatBar.Position = UDim2.new(0, offset + 5, 0, 0)
+ end
+ end
+ end
+ end
+
+ function this:FocusChatBar()
+ if this.ChatBar then
+ this.ChatBar:CaptureFocus()
+ if self.ClickToChatButton then
+ self.ClickToChatButton.Visible = false
+ end
+ if this.ChatModeText then
+ this.ChatModeText.Visible = true
+ end
+ this.ChatBarChangedConn = Util.DisconnectEvent(this.ChatBarChangedConn)
+ this.ChatBarChangedConn = this.ChatBar.Changed:connect(function(prop)
+ if prop == "Text" then
+ this:OnChatBarTextChanged()
+ end
+ end)
+ if Util.IsTouchDevice() then
+ this.ChatBar.Visible = true
+ this:SetMessageMode('All') -- Don't remember message mode on mobile devices
+ else
+ -- Use a count to make sure you double backspace out of a chatmode; less likely to accidently do it.
+ local count = 0
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ this.FocusChatBarInputBeganConn = InputService.InputBegan:connect(function(inputObj)
+ if inputObj.KeyCode == Enum.KeyCode.Backspace and this:GetChatBarText() == "" then
+ if count == 0 then
+ count = count + 1
+ else
+ this:SetMessageMode('All')
+ end
+ else
+ count = 0
+ end
+ end)
+ end
+ this.ChatBarGainedFocusEvent:fire()
+ end
+ end
+
+ function this:SanitizeInput(input)
+ local sanitizedInput = input
+ -- Chomp the whitespace at the front and end of the string
+ -- TODO: maybe only chop off the front space if there are more than a few?
+ local _, _, capture = string.find(sanitizedInput, "^%s*(.*)%s*$")
+ sanitizedInput = capture or ""
+
+ return sanitizedInput
+ end
+
+ function this:OnChatBarFocusLost(enterPressed)
+ if self.ChatBar then
+ if Util.IsTouchDevice() then
+ self.ChatBar.Visible = false
+ end
+ if enterPressed then
+ local didMatchSlashCommand = this:ProcessChatBarModes(false)
+ local cText = this:SanitizeInput(this:GetChatBarText())
+ if cText ~= "" then
+ if not didMatchSlashCommand and string.sub(cText,1,1) == "/" then
+ this.ChatCommandEvent:fire(false, "Unknown", cText)
+ else
+ local currentMessageMode = this:GetMessageMode()
+ -- {All, Team, Whisper}
+ if currentMessageMode == 'Team' then
+ if Player and Player.Neutral == true then
+ this.ChatErrorEvent:fire("You are not in any team.")
+ else
+ pcall(function() PlayersService:TeamChat(cText) end)
+ end
+ elseif currentMessageMode == 'Whisper' then
+ if this.TargetWhisperPlayer then
+ if this.TargetWhisperPlayer == Player then
+ this.ChatErrorEvent:fire("You cannot send a whisper to yourself.")
+ else
+ pcall(function() PlayersService:WhisperChat(cText, this.TargetWhisperPlayer) end)
+ end
+ else
+ this.ChatErrorEvent:fire("Invalid whisper target.")
+ end
+ elseif currentMessageMode == 'All' then
+ pcall(function() PlayersService:Chat(cText) end)
+ else
+ spawn(function() error("ChatScript: Unknown Message Mode of " .. tostring(currentMessageMode)) end)
+ end
+ end
+ end
+ this:SetChatBarText("")
+ end
+ end
+ if self.ClickToChatButton then
+ self.ClickToChatButton.Visible = true
+ end
+ if this.ChatModeText then
+ this.ChatModeText.Visible = false
+ end
+ this.ChatBarChangedConn = Util.DisconnectEvent(this.ChatBarChangedConn)
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ end
+
+ local function CreateChatBar()
+ local chatBarContainer = Util.Create'Frame'
+ {
+ Name = 'ChatBarContainer';
+ Position = UDim2.new(0, 0, 1, 0);
+ Size = UDim2.new(1, 0, 0, 20);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 0.25;
+ };
+ local clickToChatButton = Util.Create'TextButton'
+ {
+ Name = 'ClickToChat';
+ Position = UDim2.new(0,9,0,0);
+ Size = UDim2.new(1, -9, 1, 0);
+ BackgroundTransparency = 1;
+ ZIndex = 3;
+ Text = 'To chat click here or press "/" key';
+ TextColor3 = this.Settings.GlobalTextColor;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ Parent = chatBarContainer;
+ }
+ local chatBar = Util.Create'TextBox'
+ {
+ Name = 'ChatBar';
+ Position = UDim2.new(0, 9, 0, 0);
+ Size = UDim2.new(1, -9, 1, 0);
+ Text = "";
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextColor3 = this.Settings.GlobalTextColor;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ ClearTextOnFocus = false;
+ Visible = not Util.IsTouchDevice();
+ Parent = chatBarContainer;
+ }
+ local chatModeText = Util.Create'TextButton'
+ {
+ Name = 'ChatModeText';
+ Position = UDim2.new(0, 9, 0, 0);
+ Size = UDim2.new(1, -9, 1, 0);
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = '';
+ TextColor3 = this.Settings.WhisperTextColor;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ Parent = chatBarContainer;
+ }
+
+ this.ChatBarContainer = chatBarContainer
+ this.ClickToChatButton = clickToChatButton
+ this.ChatBar = chatBar
+ this.ChatModeText = chatModeText
+ this.ChatBarContainer.Parent = GuiRoot
+ end
+
+ CreateChatBar()
+ return this
+end
+
+local function CreateChatWindowWidget(settings)
+ local this = {}
+ this.Settings = settings
+ this.Chats = {}
+ this.BackgroundVisible = false
+
+ this.ChatWindowPagingConn = nil
+
+ local lastMoveTime = tick()
+ local lastEnterTime = tick()
+ local lastLeaveTime = tick()
+
+ local lastFadeOutTime = 0
+ local lastFadeInTime = 0
+
+ local FadeLock = false
+
+ local function PointInChatWindow(pt)
+ local point0 = this.ChatContainer.AbsolutePosition
+ local point1 = point0 + this.ChatContainer.AbsoluteSize
+ return point0.X <= pt.X and point1.X >= pt.X and
+ point0.Y <= pt.Y and point1.Y >= pt.Y
+ end
+
+ function this:IsHovering()
+ --return lastEnterTime > lastLeaveTime
+ if this.ChatContainer and this.LastMousePosition then
+ return PointInChatWindow(this.LastMousePosition)
+ end
+ return false
+ end
+
+ function this:SetFadeLock(lock)
+ FadeLock = lock
+ end
+
+ function this:GetFadeLock()
+ return FadeLock
+ end
+
+ function this:FadeIn(duration, lockFade)
+ if not FadeLock then
+ duration = duration or 0.75
+ -- fade in
+ if this.BackgroundTweener then
+ this.BackgroundTweener:Cancel()
+ end
+ lastFadeInTime = tick()
+ this.ScrollingFrame.ScrollingEnabled = true
+ this.BackgroundTweener = Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 0.7, duration, Util.Linear)
+ this.BackgroundVisible = true
+ this:FadeInChats()
+
+ this.ChatWindowPagingConn = Util.DisconnectEvent(this.ChatWindowPagingConn)
+ this.ChatWindowPagingConn = InputService.InputBegan:connect(function(inputObject)
+ local key = inputObject.KeyCode
+ if key == Enum.KeyCode.PageUp then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasPosition.Y - this.ScrollingFrame.AbsoluteSize.Y))
+ elseif key == Enum.KeyCode.PageDown then
+ this.ScrollingFrame.CanvasPosition =
+ Vector2.new(0, Util.Clamp(0, --min
+ this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y, --max
+ this.ScrollingFrame.CanvasPosition.Y + this.ScrollingFrame.AbsoluteSize.Y))
+ elseif key == Enum.KeyCode.Home then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, 0)
+ elseif key == Enum.KeyCode.End then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y)
+ end
+ end)
+ end
+ end
+ function this:FadeOut(duration, unlockFade)
+ if not FadeLock then
+ duration = duration or 0.75
+ -- fade out
+ if this.BackgroundTweener then
+ this.BackgroundTweener:Cancel()
+ end
+ lastFadeOutTime = tick()
+ this.ScrollingFrame.ScrollingEnabled = false
+ this.BackgroundTweener = Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ this.BackgroundVisible = false
+
+ this.ChatWindowPagingConn = Util.DisconnectEvent(this.ChatWindowPagingConn)
+
+ local now = lastFadeOutTime
+ delay(MESSAGES_FADE_OUT_TIME, function()
+ if lastFadeOutTime > lastFadeInTime and now == lastFadeOutTime then
+ this:FadeOutChats()
+ end
+ end)
+ end
+ end
+
+ function this:FadeInChats()
+ -- TODO: only bother with this loop if we know chats have been faded out, could be quicker than this
+ for index, message in pairs(this.Chats) do
+ message:FadeIn()
+ end
+ end
+
+ function this:FadeOutChats()
+ for index, message in pairs(this.Chats) do
+ message:FadeOut()
+ end
+ end
+
+ function this:OnResize()
+ local isScrolledDown = this:IsScrolledDown()
+
+ local ySize = 0
+
+ if this.ScrollingFrame then
+ for index, message in pairs(this.Chats) do
+ local newHeight = message:OnResize(this.ScrollingFrame.AbsoluteSize)
+ if newHeight then
+ local chatMessageElement = message:GetGui()
+ if chatMessageElement then
+ local chatMessageElementYSize = chatMessageElement.Size.Y.Offset
+ chatMessageElement.Position = UDim2.new(0, 0, 0, ySize)
+ ySize = ySize + chatMessageElementYSize
+ end
+ end
+ end
+ end
+ if this.MessageContainer and this.ScrollingFrame then
+ this.MessageContainer .Size = UDim2.new(
+ 1,
+ this.ScrollingFrame.Size.X.Offset - this.ScrollingFrame.ScrollBarThickness - this.ScrollingFrame.Position.X.Offset,
+ 0,
+ ySize)
+
+ this.ScrollingFrame.CanvasSize = UDim2.new(this.ScrollingFrame.CanvasSize.X.Scale, this.ScrollingFrame.CanvasSize.X.Offset, this.ScrollingFrame.CanvasSize.Y.Scale, ySize)
+ if isScrolledDown then
+ local function UpdateScrollDown()
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasSize.Y.Offset - math.max(0, this.ScrollingFrame.AbsoluteSize.Y)))
+ end
+ UpdateScrollDown()
+ -- Have to do it after a delay as well because when you resize not all of the absolutesize have been updated yet
+ delay(0, UpdateScrollDown)
+ end
+ end
+ end
+
+ function this:PushMessageIntoQueue(chatMessage)
+ table.insert(this.Chats, chatMessage)
+
+ local isScrolledDown = this:IsScrolledDown()
+
+ local chatMessageElement = chatMessage:GetGui()
+
+ chatMessageElement.Parent = this.MessageContainer
+ chatMessage:OnResize()
+ local ySize = this.MessageContainer.Size.Y.Offset
+ local chatMessageElementYSize = UDim2.new(0, 0, 0, chatMessageElement.Size.Y.Offset)
+
+ chatMessageElement.Position = chatMessageElement.Position + UDim2.new(0, 0, 0, ySize)
+ this.MessageContainer.Size = this.MessageContainer.Size + chatMessageElementYSize
+ this.ScrollingFrame.CanvasSize = this.ScrollingFrame.CanvasSize + chatMessageElementYSize
+
+ if this.Settings.MaxWindowChatMessages < #this.Chats then
+ this:RemoveOldestMessage()
+ end
+ if isScrolledDown then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y))
+ else
+ -- Raise unread message alert!
+ end
+ this:FadeInChats()
+ end
+
+ function this:AddSystemChatMessage(chattedMessage)
+ local chatMessage = CreateSystemChatMessage(chattedMessage)
+ this:PushMessageIntoQueue(chatMessage)
+ end
+
+ function this:AddChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ local chatMessage = CreatePlayerChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ this:PushMessageIntoQueue(chatMessage)
+ end
+
+ function this:RemoveOldestMessage()
+ local oldestChat = this.Chats[1]
+ if oldestChat then
+ return this:RemoveChatMessage(oldestChat)
+ end
+ end
+
+ function this:RemoveChatMessage(chatMessage)
+ if chatMessage then
+ for index, message in pairs(this.Chats) do
+ if chatMessage == message then
+ local guiObj = chatMessage:GetGui()
+ if guiObj then
+ local ySize = guiObj.Size.Y.Offset
+ this.ScrollingFrame.CanvasSize = this.ScrollingFrame.CanvasSize - UDim2.new(0,0,0,ySize)
+ guiObj.Parent = nil
+ end
+ message:Destroy()
+ return table.remove(this.Chats, index)
+ end
+ end
+ end
+ end
+
+ function this:IsScrolledDown()
+ local yCanvasSize = this.ScrollingFrame.CanvasSize.Y.Offset
+ local yContainerSize = this.ScrollingFrame.AbsoluteSize.Y
+ local yScrolledPosition = this.ScrollingFrame.CanvasPosition.Y
+ -- Check if the messages are at the bottom
+ return yCanvasSize < yContainerSize or
+ yCanvasSize - yScrolledPosition >= yContainerSize - 2 -- Fuzzy equals here
+ end
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if this.ChatContainer then
+ this.ChatContainer.Visible = enabled
+ end
+ end
+ -- If we are using bubble-chat then do not show chat window
+ if this.ChatContainer and not PlayersService.ClassicChat then
+ this.ChatContainer.Visible = false
+ end
+ end
+
+ local function CreateChatWindow()
+ local container = Util.Create'Frame'
+ {
+ Name = 'ChatWindowContainer';
+ -- Height is a multiple of chat message height, maybe keep this value at 150 and move that padding into the messageContainer
+ Size = UDim2.new(0.33, 0, 0.25, 0);
+ Position = UDim2.new(0, 20, 0, 50);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+ local scrollingFrame = Util.Create'ScrollingFrame'
+ {
+ Name = 'ChatWindow';
+ Size = UDim2.new(1, -4 - 10, 1, -20);
+ CanvasSize = UDim2.new(1, -4 - 10, 0, 0);
+ Position = UDim2.new(0, 10, 0, 10);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ BottomImage = "rbxasset://textures/ui/scroll-bottom.png";
+ MidImage = "rbxasset://textures/ui/scroll-middle.png";
+ TopImage = "rbxasset://textures/ui/scroll-top.png";
+ ScrollBarThickness = 7;
+ BorderSizePixel = 0;
+ ScrollingEnabled = false;
+ Parent = container;
+ };
+ local messageContainer = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Size = UDim2.new(1, 0, 0, 0);
+ Position = UDim2.new(0, 0, 1, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ Parent = scrollingFrame
+ };
+
+ -- This is some trickery we are doing to make the first chat messages appear at the bottom and go towards the top.
+ local function OnChatWindowResize(prop)
+ if prop == 'AbsoluteSize' then
+ messageContainer.Position = UDim2.new(0, 0, 1, -messageContainer.Size.Y.Offset)
+ elseif prop == 'ScrollBarThickness' then
+ messageContainer.Size = UDim2.new(
+ messageContainer.Size.X.Scale,
+ scrollingFrame.Size.X.Offset - scrollingFrame.ScrollBarThickness - scrollingFrame.Position.X.Offset,
+ messageContainer.Size.Y.Scale,
+ messageContainer.Size.Y.Offset)
+ end
+ end
+ container.Changed:connect(function(prop) if prop == 'AbsoluteSize' then this:OnResize() end end)
+
+ local function RobloxClientScreenSizeChanged(newSize)
+ if container then
+ -- Phone
+ if newSize.X <= 640 then
+ container.Size = UDim2.new(0.5,0,0.5,0) - container.Position
+ -- Tablet
+ elseif newSize.X <= 1024 then
+ container.Size = UDim2.new(0.4,0,0.3,0) - container.Position
+ -- Desktop
+ else
+ container.Size = UDim2.new(0.33,0,0.25,0) - container.Position
+ end
+ end
+ end
+
+ GuiRoot.Changed:connect(function(prop) if prop == "AbsoluteSize" then RobloxClientScreenSizeChanged(GuiRoot.AbsoluteSize) end end)
+ RobloxClientScreenSizeChanged(GuiRoot.AbsoluteSize)
+
+ messageContainer.Changed:connect(OnChatWindowResize)
+ scrollingFrame.Changed:connect(OnChatWindowResize)
+
+ this.ChatContainer = container
+ this.ScrollingFrame = scrollingFrame
+ this.MessageContainer = messageContainer
+ this.ChatContainer.Parent = GuiRoot
+
+ --- BACKGROUND FADING CODE ---
+ -- This is so we don't accidentally fade out when we are scrolling and mess with the scrollbar.
+ local dontFadeOutOnMouseLeave = false
+
+ if Util:IsTouchDevice() then
+ local touchCount = 0
+ this.InputBeganConn = InputService.InputBegan:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.Touch and inputObject.UserInputState == Enum.UserInputState.Begin then
+ if PointInChatWindow(Vector2.new(inputObject.Position.X, inputObject.Position.Y)) then
+ touchCount = touchCount + 1
+ dontFadeOutOnMouseLeave = true
+ end
+ end
+ end)
+
+ this.InputEndedConn = InputService.InputEnded:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.Touch and inputObject.UserInputState == Enum.UserInputState.End then
+ local endedCount = touchCount
+ wait(2)
+ if touchCount == endedCount then
+ dontFadeOutOnMouseLeave = false
+ end
+ end
+ end)
+
+ spawn(function()
+ while true do
+ wait()
+ if this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut(0.25)
+ end
+ end
+ end
+ end)
+ else
+ this.LastMousePosition = Vector2.new()
+
+ this.MouseEnterFrameConn = this.ChatContainer.MouseEnter:connect(function()
+ lastEnterTime = tick()
+ if this.BackgroundTweener and not this.BackgroundTweener:IsFinished() and not this.BackgroundVisible then
+ this:FadeIn()
+ end
+ end)
+
+ this.MouseMoveConn = InputService.InputChanged:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseMovement then
+ lastMoveTime = tick()
+ this.LastMousePosition = Vector2.new(inputObject.Position.X, inputObject.Position.Y)
+ if this.BackgroundTweener and this.BackgroundTweener:GetPercentComplete() < 0.5 and this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut()
+ end
+ end
+ end
+ end)
+
+ local clickCount = 0
+ this.InputBeganConn = InputService.InputBegan:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseButton1 and inputObject.UserInputState == Enum.UserInputState.Begin then
+ if PointInChatWindow(Vector2.new(inputObject.Position.X, inputObject.Position.Y)) then
+ clickCount = clickCount + 1
+ dontFadeOutOnMouseLeave = true
+ end
+ end
+ end)
+
+ this.InputEndedConn = InputService.InputEnded:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseButton1 and inputObject.UserInputState == Enum.UserInputState.End then
+ local nowCount = clickCount
+ wait(2)
+ if nowCount == clickCount then
+ dontFadeOutOnMouseLeave = false
+ end
+ end
+ end)
+
+ this.MouseLeaveFrameConn = this.ChatContainer.MouseLeave:connect(function()
+ lastLeaveTime = tick()
+ if this.BackgroundTweener and not this.BackgroundTweener:IsFinished() and this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut()
+ end
+ end
+ end)
+
+ spawn(function()
+ while true do
+ wait()
+ if this:IsHovering() then
+ if tick() - lastMoveTime > 2 and not this.BackgroundVisible then
+ this:FadeIn()
+ end
+ else -- not this:IsHovering()
+ if this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut(0.25)
+ end
+ end
+ end
+ end
+ end)
+ end
+ --- END OF BACKGROUND FADING CODE ---
+ end
+
+ CreateChatWindow()
+
+ return this
+end
+
+
+local function CreateChat()
+ local this = {}
+
+ this.Settings =
+ {
+ GlobalTextColor = Color3.new(255/255, 255/255, 243/255);
+ WhisperTextColor = Color3.new(77/255, 139/255, 255/255);
+ TeamTextColor = Color3.new(230/255, 207/255, 0);
+ MaxWindowChatMessages = 100;
+ MaxCharactersInMessage = 140; -- Same as a tweet :D
+ }
+
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if Util:IsTouchDevice() then
+ Util.SetGUIInsetBounds(0, 0)
+ else
+ if enabled then
+ -- Reserve bottom 20 pixels for our chat bar
+ Util.SetGUIInsetBounds(0, 20)
+ else
+ Util.SetGUIInsetBounds(0, 0)
+ end
+ end
+ end
+ if this.ChatWindowWidget then
+ this.ChatWindowWidget:CoreGuiChanged(coreGuiType, enabled)
+ end
+ if this.ChatBarWidget then
+ this.ChatBarWidget:CoreGuiChanged(coreGuiType, enabled)
+ end
+ end
+
+ -- This event has 4 callback arguments
+ -- Enum.PlayerChatType.{All|Team|Whisper}, chatPlayer, message, targetPlayer
+ function this:OnPlayerChatted(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ if this.ChatWindowWidget then
+ this.ChatWindowWidget:AddChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ end
+ end
+
+ function this:OnPlayerAdded()
+ this.PlayerChattedConn = Util.DisconnectEvent(this.PlayerChattedConn)
+ this.PlayerChattedConn = PlayersService.PlayerChatted:connect(function(...)
+ this:OnPlayerChatted(...)
+ end)
+ end
+
+ function this:GetBlockedPlayersAsync()
+ local secureBaseUrl = Util.GetSecureApiBaseUrl()
+ local url = secureBaseUrl .. "userblock/getblockedusers" .. "?" .. "userId=" .. tostring(Player.userId) .. "&" .. "page=" .. "1"
+ local blockList = nil
+ local success, msg = ypcall(function()
+ local request = game:HttpGetAsync(url)
+ blockList = request and game:GetService('HttpService'):DecodeJSON(request)
+ end)
+ if blockList and blockList['success'] == true then
+ return blockList['userList']
+ end
+ end
+
+ function this:CreateTouchDeviceChatButton()
+ return Util.Create'ImageButton'
+ {
+ Name = 'TouchDeviceChatButton';
+ Size = UDim2.new(0, 128, 0, 32);
+ Position = UDim2.new(0, 88, 0, 0);
+ BackgroundTransparency = 1.0;
+ Image = 'http://www.roblox.com/asset/?id=97078724';
+ };
+ end
+
+ function this:PrintWelcome()
+ this.ChatWindowWidget:AddSystemChatMessage("Welcome to Roblox")
+ this.ChatWindowWidget:AddSystemChatMessage("Please type /? for a list of commands")
+ end
+
+ function this:PrintHelp()
+ this.ChatWindowWidget:AddSystemChatMessage("Help Menu")
+ this.ChatWindowWidget:AddSystemChatMessage("Chat Commands:")
+ this.ChatWindowWidget:AddSystemChatMessage("/w [PlayerName] or /whisper [PlayerName] - Whisper Chat")
+ this.ChatWindowWidget:AddSystemChatMessage("/t or /team - Team Chat")
+ this.ChatWindowWidget:AddSystemChatMessage("/a or /all - All Chat")
+ end
+
+ function this:CreateGUI()
+ if Player.ChatMode == Enum.ChatMode.TextAndMenu or FORCE_CHAT_GUI then
+ -- NOTE: eventually we will make multiple chat window frames
+ -- Settings is a table, which makes it a pointing and is kosher to pass by reference
+ this.ChatWindowWidget = CreateChatWindowWidget(this.Settings)
+ this.ChatBarWidget = CreateChatBarWidget(this.Settings)
+
+ local focusCount = 0
+ this.ChatBarWidget.ChatBarGainedFocusEvent:connect(function()
+ focusCount = focusCount + 1
+ this.ChatWindowWidget:FadeIn(0.25)
+ this.ChatWindowWidget:SetFadeLock(true)
+ end)
+ this.ChatBarWidget.ChatBarLostFocusEvent:connect(function()
+ local focusNow = focusCount
+ if Util:IsTouchDevice() then
+ wait(2)
+ if focusNow == focusCount then
+ this.ChatWindowWidget:SetFadeLock(false)
+ end
+ else
+ this.ChatWindowWidget:SetFadeLock(false)
+ end
+ end)
+
+ this.ChatBarWidget.ChatErrorEvent:connect(function(msg)
+ if msg then
+ this.ChatWindowWidget:AddSystemChatMessage(msg)
+ end
+ end)
+
+ this.ChatBarWidget.ChatCommandEvent:connect(function(success, actionType, capture)
+ if actionType == "Help" then
+ this:PrintHelp()
+ elseif actionType == "Whisper" then
+ if success == false then
+ local playerName = capture and tostring(capture) or "Unknown"
+ this.ChatWindowWidget:AddSystemChatMessage("Unable to Send a Whisper to Player: " .. playerName)
+ end
+ elseif actionType == "Unknown" then
+ if success == false then
+ local commandText = capture and tostring(capture) or "Unknown"
+ this.ChatWindowWidget:AddSystemChatMessage("Invalid Slash Command: " .. commandText)
+ end
+ end
+ end)
+
+ if Util.IsTouchDevice() then
+ local mobileChatButton = this:CreateTouchDeviceChatButton()
+ mobileChatButton.Parent = GuiRoot
+
+ mobileChatButton.TouchTap:connect(function()
+ mobileChatButton.Visible = false
+ if this.ChatBarWidget then
+ this.ChatBarWidget:FocusChatBar()
+ end
+ end)
+
+ this.ChatBarWidget.ChatBarLostFocusEvent:connect(function()
+ mobileChatButton.Visible = true
+ end)
+ end
+ end
+ end
+
+ function this:Initialize()
+ --spawn(function()
+ -- this:GetBlockedPlayersAsync()
+ --end)
+
+ this:OnPlayerAdded()
+ -- Upsettingly, it seems everytime a player is added, you have to redo the connection
+ -- NOTE: PlayerAdded only fires on the server, hence ChildAdded is used here
+ PlayersService.ChildAdded:connect(function()
+ this:OnPlayerAdded()
+ end)
+
+ this:CreateGUI()
+
+ pcall(function()
+ this:CoreGuiChanged(Enum.CoreGuiType.Chat, StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Chat))
+ this.CoreGuiChangedConn = Util.DisconnectEvent(this.CoreGuiChangedConn)
+ this.CoreGuiChangedConn = StarterGui.CoreGuiChangedSignal:connect(
+ function(coreGuiType,enabled)
+ this:CoreGuiChanged(coreGuiType, enabled)
+ end)
+ end)
+
+ this:PrintWelcome()
+ end
+
+ return this
+end
+
+
+-- Run the script
+do
+ local ChatInstance = CreateChat()
+ ChatInstance:Initialize()
+end
diff --git a/asset/backup/12 b/asset/backup/12
new file mode 100644
index 0000000..f751ba5
--- /dev/null
+++ b/asset/backup/12
@@ -0,0 +1,1295 @@
+%12%
+-- this script creates the gui and sends the web requests for in game purchase prompts
+
+-- wait for important items to appear
+while not Game do
+ wait(0.1)
+end
+while not game:GetService("MarketplaceService") do
+ wait(0.1)
+end
+while not game:FindFirstChild("CoreGui") do
+ wait(0.1)
+end
+while not game.CoreGui:FindFirstChild("RobloxGui") do
+ wait(0.1)
+end
+
+-------------------------------- Global Variables ----------------------------------------
+-- utility variables
+local RbxUtility = nil
+local baseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+baseUrl = string.gsub(baseUrl,"/m.","/www.") --mobile site does not work for this stuff!
+
+local doNativePurchasing = true
+
+-- data variables
+local currentProductInfo, currentAssetId, currentCurrencyType, currentCurrencyAmount, currentEquipOnPurchase, currentProductId, currentServerResponseTable, thirdPartyProductName
+local checkingPlayerFunds = false
+local purchasingConsumable = false
+
+-- gui variables
+local currentlyPrompting = false
+local currentlyPurchasing = false
+local purchaseDialog, errorDialog = nil
+local tweenTime = 0.3
+local showPosition = UDim2.new(0.5,-217,0.5,-146)
+local hidePosition = UDim2.new(0.5,-217,1,25)
+local isSmallScreen = nil
+local spinning = false
+local spinnerIcons = nil
+local smallScreenThreshold = 450
+local renderSteppedConnection = nil
+
+-- user facing images
+local assetUrls = {}
+local assetUrl = "http://www.roblox.com/Asset/?id="
+local errorImageUrl = assetUrl .. "42557901" table.insert(assetUrls, errorImageUrl)
+local buyImageUrl = assetUrl .. "142494143" table.insert(assetUrls,buyImageUrl)
+local cancelButtonImageUrl = assetUrl .. "142494219" table.insert(assetUrls, cancelButtonImageUrl)
+local freeButtonImageDownUrl = assetUrl .. "104651761" table.insert(assetUrls, freeButtonImageDownUrl)
+local loadingImage = assetUrl .. "143116791" table.insert(assetUrls,loadingImage)
+
+-- user facing string
+local buyHeaderText = "Buy Item"
+local takeHeaderText = "Take Item"
+local buyFailedHeaderText = "An Error Occurred"
+
+local errorPurchasesDisabledText = "In-game purchases are disabled"
+local errorPurchasesBuyRobuxText = "your account does not have enough Robux"
+local errorPurchasesUnknownText = "Roblox is performing maintenance"
+
+local purchaseSucceededText = "Your purchase of itemName succeeded!"
+local purchaseFailedText = "Your purchase of itemName failed because errorReason. Your account has not been charged. Please try again soon."
+local productPurchaseText = "Would you like to buy the itemName assetType for currencyTypecurrencyAmount?"
+local productPurchaseTixOnlyText = "Would you like to buy the itemName assetType for currencyAmount currencyType?"
+local freeItemPurchaseText = "Would you like to take the assetType itemName for FREE?"
+local freeItemBalanceText = "Your balance of Robux or Tix will not be affected by this transaction."
+local upgradeBCText = "You require an upgrade to your Builders Club membership to purchase this item. Click 'Buy Builders Club' to upgrade."
+local productPurchaseWithMoreRobuxText = "Buy robuxToBuyAmount$R to get itemName assetType."
+local productPurchaseWithMoreRobuxRemainderText = "The remaining purchaseRemainder$R will be credited to your ROBUX balance."
+local balanceFutureTenseText = "Your balance after this transaction will be "
+local balanceCurrentTenseText = "Your balance is now "
+
+-- robux product arrays
+local bcRobuxProducts = {90, 180, 270, 360, 450, 1000, 2750}
+local nonBcRobuxProducts = {80, 160, 240, 320, 400, 800, 2000}
+-------------------------------- End Global Variables ----------------------------------------
+
+
+----------------------------- Util Functions ---------------------------------------------
+function getSecureApiBaseUrl()
+ local secureApiUrl = baseUrl
+ secureApiUrl = string.gsub(secureApiUrl,"http","https")
+ secureApiUrl = string.gsub(secureApiUrl,"www","api")
+ return secureApiUrl
+end
+
+function getRbxUtility()
+ if not RbxUtility then
+ RbxUtility = LoadLibrary("RbxUtility")
+ end
+ return RbxUtility
+end
+
+function preloadAssets()
+ for i = 1, #assetUrls do
+ game:GetService("ContentProvider"):Preload(assetUrls[i])
+ end
+end
+----------------------------- End Util Functions ---------------------------------------------
+
+
+-------------------------------- Accept/Decline Functions --------------------------------------
+function removeCurrentPurchaseInfo()
+ currentAssetId = nil
+ currentCurrencyType = nil
+ currentCurrencyAmount = nil
+ currentEquipOnPurchase = nil
+ currentProductId = nil
+ currentProductInfo = nil
+ currentServerResponseTable = nil
+
+ checkingPlayerFunds = false
+end
+
+function userPurchaseActionsEnded(isSuccess)
+ checkingPlayerFunds = false
+
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = false
+
+ if isSuccess then -- show the user we bought the item successfully, when they close this dialog we will call signalPromptEnded
+ local newPurchasedSucceededText = string.gsub( purchaseSucceededText,"itemName", tostring(currentProductInfo["Name"]))
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedSucceededText
+
+ local playerBalance = getPlayerBalance()
+ local keyWord = "robux"
+ if currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ local afterBalanceNumber = playerBalance[keyWord]
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balanceCurrentTenseText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkPurchasedButton)
+ hidePurchasing()
+ else -- otherwise we didn't purchase, no need to show anything, just signal and close dialog
+ signalPromptEnded(isSuccess)
+ end
+end
+
+function signalPromptEnded(isSuccess)
+ closePurchasePrompt()
+ if purchasingConsumable then
+ game:GetService("MarketplaceService"):SignalPromptProductPurchaseFinished(game.Players.LocalPlayer.userId, currentProductId, isSuccess)
+ else
+ game:GetService("MarketplaceService"):SignalPromptPurchaseFinished(game.Players.LocalPlayer, currentAssetId, isSuccess)
+ end
+ removeCurrentPurchaseInfo()
+end
+
+function getClosestRobuxProduct(amountNeededToBuy, robuxProductArray)
+ local closest = robuxProductArray[1];
+ local closestIndex = 1
+
+ for i = 1, #robuxProductArray do
+ if ( math.abs(robuxProductArray[i] - amountNeededToBuy) < math.abs(closest - amountNeededToBuy) ) then
+ closest = robuxProductArray[i]
+ closestIndex = i
+ end
+ end
+
+ if closest < amountNeededToBuy then
+ closest = robuxProductArray[1 + closestIndex]
+ end
+
+ return closest
+end
+
+--todo: get productIds from server instead of embedding values
+function getMinimumProductNeededForPurchase(amountNeededToBuy)
+ local isBcMember = (Game.Players.LocalPlayer.MembershipType ~= Enum.MembershipType.None)
+ local productAmount = nil
+
+ if isBcMember then
+ productAmount = getClosestRobuxProduct(amountNeededToBuy, bcRobuxProducts)
+ else
+ productAmount = getClosestRobuxProduct(amountNeededToBuy, nonBcRobuxProducts)
+ end
+
+ local isAndroid = false
+ pcall(function() isAndroid = (Game:GetService("UserInputService"):GetPlatform() == Enum.Platform.Android) end)
+
+ local prependString = ""
+ local appendString = ""
+ local appPrefix = ""
+
+ if isAndroid then
+ prependString = "robux"
+ if isBcMember then
+ appendString = "bc"
+ end
+ appPrefix = "com.roblox.client."
+ else
+ if isBcMember then
+ appendString = "RobuxBC"
+ else
+ appendString = "RobuxNonBC"
+ end
+
+ appPrefix = "com.roblox.robloxmobile."
+ end
+
+ local productString = appPrefix .. prependString .. tostring(productAmount) .. appendString
+
+ return productAmount, productString
+end
+
+function getClosestRobuxProductToBuyItem(productAmount, playerBalanceInRobux)
+ local amountNeededToBuy = productAmount - playerBalanceInRobux
+ local amountToBuy, productName = getMinimumProductNeededForPurchase(amountNeededToBuy)
+ local remainderAfterPurchase = amountToBuy - productAmount
+
+ return amountToBuy, remainderAfterPurchase, productName
+end
+
+function canUseNewRobuxToProductFlow()
+ return (Game:GetService("UserInputService").TouchEnabled and doNativePurchasing)
+end
+
+-- make sure our gui displays the proper purchase data, and set the productid we will try and buy if use specifies a buy action
+function updatePurchasePromptData(insufficientFunds)
+ local newItemDescription = ""
+
+ -- id to use when we request a purchase
+ if not currentProductId then
+ currentProductId = currentProductInfo["ProductId"]
+ end
+
+ if isFreeItem() then
+ newItemDescription = string.gsub( freeItemPurchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ setHeaderText(takeHeaderText)
+ elseif insufficientFunds and canUseNewRobuxToProductFlow() then
+ local purchaseText = productPurchaseWithMoreRobuxText
+
+ local playerBalance = getPlayerBalance()
+ if not playerBalance then
+ newItemDescription = "Could not retrieve your balance. Please try again later."
+ elseif canUseNewRobuxToProductFlow() then
+ local amountToBuy, remainderAfterPurchase, productName = getClosestRobuxProductToBuyItem(currentCurrencyAmount, playerBalance["robux"])
+ thirdPartyProductName = productName
+
+ newItemDescription = string.gsub( purchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ newItemDescription = string.gsub( newItemDescription,"robuxToBuyAmount", tostring(amountToBuy))
+
+ if remainderAfterPurchase > 0 then
+ newItemDescription = newItemDescription .. " " .. string.gsub( productPurchaseWithMoreRobuxRemainderText,"purchaseRemainder", tostring(remainderAfterPurchase))
+ end
+ end
+ setHeaderText(buyHeaderText)
+ else
+ local purchaseText = productPurchaseText
+ if currentProductIsTixOnly() then
+ purchaseText = productPurchaseTixOnlyText
+ end
+
+ newItemDescription = string.gsub( purchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ newItemDescription = string.gsub( newItemDescription,"currencyType", tostring(currencyTypeToString(currentCurrencyType)) )
+ newItemDescription = string.gsub( newItemDescription,"currencyAmount", tostring(currentCurrencyAmount))
+ setHeaderText(buyHeaderText)
+ end
+
+ purchaseDialog.BodyFrame.ItemDescription.Text = newItemDescription
+
+ if purchasingConsumable then
+ purchaseDialog.BodyFrame.ItemPreview.Image = baseUrl .. "thumbs/asset.ashx?assetid=" .. tostring(currentProductInfo["IconImageAssetId"]) .. '&x=100&y=100&format=png'
+ else
+ purchaseDialog.BodyFrame.ItemPreview.Image = baseUrl .. "thumbs/asset.ashx?assetid=" .. tostring(currentAssetId) .. '&x=100&y=100&format=png'
+ end
+end
+
+function checkIfCanPurchase()
+ if checkingPlayerFunds then
+ local canPurchase, insufficientFunds, notRightBC = canPurchaseItem() -- check again to see if we can buy item
+ if not canPurchase or (insufficientFunds or notRightBC) then -- wait a bit and try a few more times
+ local retries = 20
+ while retries > 0 and (insufficientFunds or notRightBC) and checkingPlayerFunds and canPurchase do
+ wait(0.5)
+ canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ retries = retries - 1
+ end
+ end
+ if canPurchase and not insufficientFunds then
+ -- we can buy item! set our buttons up and we will exit this loop
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyButton,purchaseDialog.BodyFrame.CancelButton, purchaseDialog.BodyFrame.AfterBalanceText)
+ end
+ end
+end
+
+function closePurchasePrompt()
+ purchaseDialog:TweenPosition(hidePosition, Enum.EasingDirection.Out, Enum.EasingStyle.Quad, tweenTime, true, function()
+ game.GuiService:RemoveCenterDialog(purchaseDialog)
+ hidePurchasing()
+
+ purchaseDialog.Visible = false
+ currentlyPrompting = false
+ currentlyPurchasing = false
+
+ Game:GetService("UserInputService").ModalEnabled = false
+ end)
+end
+
+function showPurchasePrompt()
+ local canPurchase, insufficientFunds, notRightBC, override, descText = canPurchaseItem()
+
+ if canPurchase then
+ updatePurchasePromptData(insufficientFunds)
+
+ if override and descText then
+ purchaseDialog.BodyFrame.ItemDescription.Text = descText
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = false
+ end
+ game.GuiService:AddCenterDialog(purchaseDialog, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ -- set the state for our buttons
+ purchaseDialog.Visible = true
+
+ if not currentlyPurchasing then
+ if isFreeItem() then
+ setButtonsVisible(purchaseDialog.BodyFrame.FreeButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif notRightBC then
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyBCButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif insufficientFunds then
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyRobuxButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif override then
+ if currentProductIsTixOnly() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+ end
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyDisabledButton, purchaseDialog.BodyFrame.CancelButton)
+ else
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyButton, purchaseDialog.BodyFrame.CancelButton)
+ end
+ end
+
+ Game:GetService("UserInputService").ModalEnabled = true
+
+ purchaseDialog:TweenPosition(showPosition, Enum.EasingDirection.Out, Enum.EasingStyle.Quad, tweenTime, true)
+ end,
+ --HideFunction
+ function()
+ Game:GetService("UserInputService").ModalEnabled = false
+ purchaseDialog.Visible = false
+ end)
+ else -- we failed in prompting a purchase, do a decline
+ doDeclinePurchase()
+ end
+end
+
+-- given an asset id, this function will grab that asset from the website, and return the first "Tool" object found inside it
+function getToolAssetID(assetID)
+ local newTool = game:GetService("InsertService"):LoadAsset(assetID)
+ if not newTool then return nil end
+
+ if newTool:IsA("Tool") then
+ return newTool
+ end
+
+ local toolChildren = newTool:GetChildren()
+ for i = 1, #toolChildren do
+ if toolChildren[i]:IsA("Tool") then
+ return toolChildren[i]
+ end
+ end
+ return nil
+end
+
+-- the user tried to purchase by clicking the purchase button, but something went wrong.
+-- let them know their account was not charged, and that they do not own the item yet.
+function purchaseFailed(errorType)
+ local name = "Item"
+ if currentProductInfo then name = currentProductInfo["Name"] end
+
+ local newPurchasedFailedText = string.gsub( purchaseFailedText,"itemName", tostring(name))
+
+ if errorType == "inGamePurchasesDisabled" then
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesDisabledText) )
+ elseif errorType == "didNotBuyRobux" then
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesBuyRobuxText) )
+ else
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesUnknownText) )
+ end
+
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedFailedText
+ purchaseDialog.BodyFrame.ItemPreview.Image = errorImageUrl
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = ""
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkButton)
+
+ setHeaderText(buyFailedHeaderText)
+
+ hidePurchasing()
+end
+
+-- user has specified they want to buy an item, now try to attempt to buy it for them
+function doAcceptPurchase(currencyPreferredByUser)
+ if currentlyPurchasing then return end
+ currentlyPurchasing = true
+
+ showPurchasing() -- shows a purchasing ui (shows spinner)
+
+ local startTime = tick()
+
+ -- http call to do the purchase
+ local response = "none"
+ local url = nil
+
+ local flagExists, flagValue = pcall(function() return settings():GetFFlag("AddRequestIdToDeveloperProductPurchases") end)
+ local reliableDevProductEnabled = flagExists and flagValue
+ -- consumables need to use a different url
+ if purchasingConsumable then
+ url = getSecureApiBaseUrl() .. "marketplace/submitpurchase?productId=" .. tostring(currentProductId) ..
+ "¤cyTypeId=" .. tostring(currencyEnumToInt(currentCurrencyType)) ..
+ "&expectedUnitPrice=" .. tostring(currentCurrencyAmount) ..
+ "&placeId=" .. tostring(Game.PlaceId)
+ if reliableDevProductEnabled then
+ local h = game:GetService("HttpService")
+ url = url .. "&requestId=" .. h:UrlEncode(h:GenerateGUID(false))
+ end
+ else
+ url = getSecureApiBaseUrl() .. "marketplace/purchase?productId=" .. tostring(currentProductId) ..
+ "¤cyTypeId=" .. tostring(currencyEnumToInt(currentCurrencyType)) ..
+ "&purchasePrice=" .. tostring(currentCurrencyAmount) ..
+ "&locationType=Game" .. "&locationId=" .. Game.PlaceId
+ end
+
+ local success, reason = ypcall(function()
+ response = game:HttpPostAsync(url, "RobloxPurchaseRequest")
+ end)
+
+ if reliableDevProductEnabled and purchasingConsumable then
+ local retriesLeft = 3
+ local gotGoodResponse = success and response ~= "none" and response ~= nil and response ~= ''
+ while retriesLeft > 0 and (not gotGoodResponse) do
+ wait(1)
+ retriesLeft = retriesLeft - 1
+ success, reason = ypcall(function()
+ response = game:HttpPostAsync(url, "RobloxPurchaseRequest")
+ end)
+ gotGoodResponse = success and response ~= "none" and response ~= nil and response ~= ''
+ end
+
+ game:ReportInGoogleAnalytics("Developer Product", "Purchase",
+ gotGoodResponse and ("success. Retries = " .. (3 - retriesLeft)) or ("failure: " .. tostring(reason)), 1)
+ end
+
+ -- debug output for us (found in the logs from local)
+ print("doAcceptPurchase success from ypcall is ",success,"reason is",reason)
+
+ if (tick() - startTime) < 1 then
+ wait(1) -- allow the purchasing waiting dialog to at least be readable (otherwise it might flash, looks bad)...
+ end
+
+ -- check to make sure purchase actually happened on the web end
+ if response == "none" or response == nil or response == '' then
+ print("did not get a proper response from web on purchase of",currentAssetId,currentProductId)
+ purchaseFailed()
+ return
+ end
+
+ -- parse our response, decide how to react
+ response = getRbxUtility().DecodeJSON(response)
+
+ if response then
+ if response["success"] == false then
+ if response["status"] ~= "AlreadyOwned" then
+ print("web return response of fail on purchase of",currentAssetId,currentProductId)
+ if (response["status"] == "EconomyDisabled") then
+ purchaseFailed("inGamePurchasesDisabled")
+ else
+ purchaseFailed()
+ end
+ return
+ end
+ end
+ else
+ print("web return response of non parsable JSON on purchase of",currentAssetId)
+ purchaseFailed()
+ return
+ end
+
+ -- check to see if this item was bought, and if we want to equip it (also need to make sure the asset type was gear)
+ if currentEquipOnPurchase and success and currentAssetId and tonumber(currentProductInfo["AssetTypeId"]) == 19 then
+ local tool = getToolAssetID(tonumber(currentAssetId))
+ if tool then
+ tool.Parent = game.Players.LocalPlayer.Backpack
+ end
+ end
+
+ if purchasingConsumable then
+ if not response["receipt"] then
+ print("tried to buy productId, but no receipt returned. productId was",currentProductId)
+ purchaseFailed()
+ return
+ end
+ Game:GetService("MarketplaceService"):SignalClientPurchaseSuccess( tostring(response["receipt"]), game.Players.LocalPlayer.userId, currentProductId )
+ else
+ userPurchaseActionsEnded(success)
+ end
+end
+
+-- user pressed the cancel button, just remove all purchasing prompts
+function doDeclinePurchase()
+ if currentlyPurchasing then return end
+ userPurchaseActionsEnded(false)
+end
+-------------------------------- End Accept/Decline Functions --------------------------------------
+
+
+---------------------------------------------- Currency Functions ---------------------------------------------
+-- enums have no implicit conversion to numbers in lua, has to have a function to do this
+function currencyEnumToInt(currencyEnum)
+ if currencyEnum == Enum.CurrencyType.Robux or currencyEnum == Enum.CurrencyType.Default then
+ return 1
+ elseif currencyEnum == Enum.CurrencyType.Tix then
+ return 2
+ end
+end
+
+-- oi, this isn't so ugly anymore
+function assetTypeToString(assetType)
+ local assetTypes = {
+ [1] = "Image";
+ [2] = "T-Shirt";
+ [3] = "Audio";
+ [4] = "Mesh";
+ [5] = "Lua";
+ [6] = "HTML";
+ [7] = "Text";
+ [8] = "Hat";
+ [9] = "Place";
+ [10] = "Model";
+ [11] = "Shirt";
+ [12] = "Pants";
+ [13] = "Decal";
+ [16] = "Avatar";
+ [17] = "Head";
+ [18] = "Face";
+ [19] = "Gear";
+ [21] = "Badge";
+ [22] = "Group Emblem";
+ [24] = "Animation";
+ [25] = "Arms";
+ [26] = "Legs";
+ [27] = "Torso";
+ [28] = "Right Arm";
+ [29] = "Left Arm";
+ [30] = "Left Leg";
+ [31] = "Right Leg";
+ [32] = "Package";
+ [33] = "YouTube Video";
+ [34] = "Game Pass";
+ [0] = "Product";
+ }
+ return assetTypes[assetType] or ""
+end
+
+function currencyTypeToString(currencyType)
+ if currencyType == Enum.CurrencyType.Tix then
+ return "Tix"
+ else
+ return "R$"
+ end
+end
+
+-- figure out what currency to use based on the currency you can actually sell the item in and what the script specified
+function setCurrencyAmountAndType(priceInRobux, priceInTix)
+ if currentCurrencyType == Enum.CurrencyType.Default or currentCurrencyType == Enum.CurrencyType.Robux then -- sell for default (user doesn't care) or robux
+ if priceInRobux ~= nil and priceInRobux ~= 0 then -- we can sell for robux
+ currentCurrencyAmount = priceInRobux
+ currentCurrencyType = Enum.CurrencyType.Robux
+ else -- have to use tix
+ currentCurrencyAmount = priceInTix
+ currentCurrencyType = Enum.CurrencyType.Tix
+ end
+ elseif currentCurrencyType == Enum.CurrencyType.Tix then -- we want to sell for tix
+ if priceInTix ~= nil and priceInTix ~= 0 then -- we can sell for tix
+ currentCurrencyAmount = priceInTix
+ currentCurrencyType = Enum.CurrencyType.Tix
+ else -- have to use robux
+ currentCurrencyAmount = priceInRobux
+ currentCurrencyType = Enum.CurrencyType.Robux
+ end
+ else
+ return false
+ end
+
+ if currentCurrencyAmount == nil then
+ return false
+ end
+
+ return true
+end
+
+-- will get the player's balance of robux and tix, return in a table
+function getPlayerBalance()
+ local playerBalance = nil
+ local success, errorCode = ypcall(function() playerBalance = game:HttpGetAsync(getSecureApiBaseUrl() .. "currency/balance") end)
+ if not success then
+ print("Get player balance failed because",errorCode)
+ return nil
+ end
+
+ if playerBalance == '' then
+ return nil
+ end
+
+ playerBalance = getRbxUtility().DecodeJSON(playerBalance)
+
+ return playerBalance
+end
+
+-- should open an external default browser window to this url
+function openBuyCurrencyWindow()
+ checkingPlayerFunds = true
+ game:GetService("GuiService"):OpenBrowserWindow(baseUrl .. "Upgrades/Robux.aspx")
+end
+
+function buyEnoughCurrencyForProduct()
+ showPurchasing()
+ Game.MarketplaceService:PromptNativePurchase(Game.Players.LocalPlayer, thirdPartyProductName)
+end
+
+function openBCUpSellWindow()
+ checkingPlayerFunds = true
+ Game:GetService('GuiService'):OpenBrowserWindow(baseUrl .. "Upgrades/BuildersClubMemberships.aspx")
+end
+
+-- set up the gui text at the bottom of the prompt (alerts user to how much money they will have left, or if they need to buy more to buy the item)
+function updateAfterBalanceText(playerBalance, notRightBc, balancePreText)
+ if isFreeItem() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = freeItemBalanceText
+ return true, false
+ end
+
+ local keyWord = nil
+ if currentCurrencyType == Enum.CurrencyType.Robux then
+ keyWord = "robux"
+ elseif currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ if not keyWord then
+ return false
+ end
+
+ local playerBalanceNumber = tonumber(playerBalance[keyWord])
+ if not playerBalanceNumber then
+ return false
+ end
+
+ local afterBalanceNumber = playerBalanceNumber - currentCurrencyAmount
+
+ -- check to see if we have enough of the desired currency to allow a purchase, if not we need to prompt user to buy robux
+ if not notRightBc then
+ if afterBalanceNumber < 0 and keyWord == "robux" then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = ""
+ return true, true
+ elseif afterBalanceNumber < 0 and keyWord == "tickets" then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = "You need " .. tostring(-afterBalanceNumber) .. " " .. currencyTypeToString(currentCurrencyType) .. " more to buy this item."
+ return true, true -- user can't buy more tickets, so we say fail the transaction (maybe instead we can prompt them to trade currency???)
+ end
+ else
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = upgradeBCText
+ return true, false
+ end
+
+ if currentProductIsTixOnly() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balancePreText) .. tostring(afterBalanceNumber) .. " " .. currencyTypeToString(currentCurrencyType) .. "."
+ else
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balancePreText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+ end
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+ return true, false
+end
+
+function isFreeItem()
+ -- Apparently free items have 'IsForSale' set to false, but 'IsPublicDomain' set to true
+ -- Example: https://api.roblox.com/marketplace/productinfo?assetid=163811695
+ -- I've tested it, if you take it off the public domain, 'IsPublicDomain' is of course false
+ return currentProductInfo and currentProductInfo["IsPublicDomain"] == true
+end
+---------------------------------------------- End Currency Functions ---------------------------------------------
+
+
+---------------------------------------------- Data Functions -----------------------------------------------------
+
+-- more enum to int fun!
+function membershipTypeToNumber(membership)
+ if membership == Enum.MembershipType.None then
+ return 0
+ elseif membership == Enum.MembershipType.BuildersClub then
+ return 1
+ elseif membership == Enum.MembershipType.TurboBuildersClub then
+ return 2
+ elseif membership == Enum.MembershipType.OutrageousBuildersClub then
+ return 3
+ end
+
+ return -1
+end
+
+function currentProductIsTixOnly()
+ local priceInRobux = currentProductInfo["PriceInRobux"]
+ local priceInTix = currentProductInfo["PriceInTickets"]
+
+ if priceInRobux == nil then return true end
+ priceInRobux = tonumber(priceInRobux)
+ if priceInRobux == nil then return true end
+
+ if priceInTix == nil then return false end
+ priceInTix = tonumber(priceInTix)
+ if priceInTix == nil then return false end
+
+ return (priceInRobux <= 0 and priceInTix > 0)
+end
+
+-- This functions checks to make sure the purchase is even possible, if not it returns false and we don't prompt user (some situations require user feedback when we won't prompt)
+function canPurchaseItem()
+
+ -- first we see if player already owns the asset/get the productinfo
+ local playerOwnsAsset = false
+ local notRightBc = false
+ local descText = nil
+ local getProductSuccess = false
+ local getProductErrorReason = ""
+
+ if purchasingConsumable then
+ getProductSuccess, getProductErrorReason = pcall(function() currentProductInfo = game:GetService("MarketplaceService"):GetProductInfo(currentProductId, Enum.InfoType.Product) end)
+ else
+ getProductSuccess, getProductErrorReason = pcall(function() currentProductInfo = game:GetService("MarketplaceService"):GetProductInfo(currentAssetId) end)
+ end
+
+ if getProductSuccess == false or currentProductInfo == nil then
+ print("could not get product info because",getProductErrorReason)
+ descText = "In-game sales are temporarily disabled. Please try again later."
+ return false, nil, nil, true, descText
+ end
+
+ if not purchasingConsumable then
+ if not currentAssetId then
+ return false
+ end
+ if currentAssetId <= 0 then
+ return false
+ end
+
+ local success, errorCode = ypcall(function() playerOwnsAsset = game:HttpGetAsync(getSecureApiBaseUrl()
+ .. "ownership/hasAsset?userId="
+ .. tostring(game.Players.LocalPlayer.userId)
+ .. "&assetId=" .. tostring(currentAssetId))
+ end)
+
+ if not success then
+ return false
+ end
+
+ if playerOwnsAsset == true or playerOwnsAsset == "true" then
+ descText = "You already own this item."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ -- For public models, as there is still the freeButton, indicating it should be
+ -- available, while this function (canPurchaseItem) doesn't count on free stuff
+ if isFreeItem() then
+ return true
+ end
+
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+
+ -- next we parse through product info and see if we can purchase
+
+ if type(currentProductInfo) ~= "table" then
+ currentProductInfo = getRbxUtility().DecodeJSON(currentProductInfo)
+ end
+
+ if not currentProductInfo then
+ descText = "Could not get product info. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ if currentProductInfo["IsForSale"] == false and currentProductInfo["IsPublicDomain"] == false then
+ descText = "This item is no longer for sale."
+ return true, nil, nil, true, descText
+ end
+
+ -- now we start talking money, making sure we are going to be able to purchase this
+ if not setCurrencyAmountAndType(tonumber(currentProductInfo["PriceInRobux"]), tonumber(currentProductInfo["PriceInTickets"])) then
+ descText = "We couldn't retrieve the price of the item correctly. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ local playerBalance = getPlayerBalance()
+ if not playerBalance then
+ descText = "Could not retrieve your balance. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ if tonumber(currentProductInfo["MinimumMembershipLevel"]) > membershipTypeToNumber(game.Players.LocalPlayer.MembershipType) then
+ notRightBc = true
+ end
+
+ local updatedBalance, insufficientFunds = updateAfterBalanceText(playerBalance, notRightBc, balanceFutureTenseText)
+
+ if notRightBc then
+ purchaseDialog.BodyFrame.AfterBalanceText.Active = true
+ return true, insufficientFunds, notRightBc, false
+ end
+
+ if currentProductInfo["ContentRatingTypeId"] == 1 then
+ if game.Players.LocalPlayer:GetUnder13() then
+ descText = "Your account is under 13 so purchase of this item is not allowed."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ if (currentProductInfo["IsLimited"] == true or currentProductInfo["IsLimitedUnique"] == true) and
+ (currentProductInfo["Remaining"] == "" or currentProductInfo["Remaining"] == 0 or currentProductInfo["Remaining"] == nil) then
+ descText = "All copies of this item have been sold out! Try buying from other users on www.roblox.com."
+ return true, nil, nil, true, descText
+ end
+
+ if not updatedBalance then
+ descText = 'Could not update your balance. Please check back after some time.'
+ return true, nil, nil, true, descText
+ end
+
+ if insufficientFunds then
+ -- if this is a ticket only time and we don't have enough, tell the user to get more tix
+ if currentProductIsTixOnly() then
+ descText = "This item costs more tickets than you currently have! Try trading currency on www.roblox.com to get more tickets."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ -- we use insufficient funds to display a prompt to buy more robux
+ return true, insufficientFunds
+end
+
+---------------------------------------------- End Data Functions -----------------------------------------------------
+
+
+---------------------------------------------- Gui Functions ----------------------------------------------
+function startSpinner()
+ if purchaseDialog.PurchasingFrame.Visible then return end
+ purchaseDialog.PurchasingFrame.Visible = true
+
+ renderSteppedConnection = Game:GetService("RunService").RenderStepped:connect(function()
+ purchaseDialog.PurchasingFrame.PurchasingSpinnerOuter.Rotation = purchaseDialog.PurchasingFrame.PurchasingSpinnerOuter.Rotation + 7
+ purchaseDialog.PurchasingFrame.PurchasingSpinnerInner.Rotation = purchaseDialog.PurchasingFrame.PurchasingSpinnerInner.Rotation - 9
+ end)
+end
+
+function stopSpinner()
+ if renderSteppedConnection then
+ renderSteppedConnection:disconnect()
+ renderSteppedConnection = nil
+ purchaseDialog.PurchasingFrame.Visible = false
+ end
+end
+
+-- next two functions control the "Purchasing..." overlay
+function showPurchasing()
+ startSpinner()
+end
+
+function hidePurchasing()
+ stopSpinner()
+end
+
+-- convenience method to say exactly what buttons should be visible (all others are not!)
+function setButtonsVisible(...)
+ local args = {...}
+ local argCount = select('#', ...)
+
+ local bodyFrameChildren = purchaseDialog.BodyFrame:GetChildren()
+ for i = 1, #bodyFrameChildren do
+ if bodyFrameChildren[i]:IsA("GuiButton") then
+ bodyFrameChildren[i].Visible = false
+ for j = 1, argCount do
+ if bodyFrameChildren[i] == args[j] then
+ bodyFrameChildren[i].Visible = true
+ break
+ end
+ end
+ end
+ end
+end
+
+-- all the gui init. Would be nice if this didn't have to be a script
+function createPurchasePromptGui()
+ purchaseDialog = Instance.new("Frame")
+ purchaseDialog.Name = "PurchaseFrame"
+ purchaseDialog.Size = UDim2.new(0,435,0,292)
+ purchaseDialog.Position = hidePosition
+ purchaseDialog.Active = true
+ purchaseDialog.Visible = false
+ purchaseDialog.BackgroundColor3 = Color3.new(225/255,225/255,225/255)
+ purchaseDialog.BorderSizePixel = 0
+ purchaseDialog.ZIndex = 8
+ purchaseDialog.Parent = game.CoreGui.RobloxGui
+
+ local bodyFrame = Instance.new("Frame")
+ bodyFrame.Name = "BodyFrame"
+ bodyFrame.Active = true
+ bodyFrame.Size = UDim2.new(1,-10,1,-55)
+ bodyFrame.Position = UDim2.new(0,5,0,50)
+ bodyFrame.BackgroundColor3 = Color3.new(1, 1, 1)
+ bodyFrame.BorderSizePixel = 0
+ bodyFrame.ZIndex = 8
+ bodyFrame.Parent = purchaseDialog
+
+ local titleLabel = createTextObject("TitleLabel", "Buy Item", "TextLabel", Enum.FontSize.Size36)
+ titleLabel.Active = true
+ titleLabel.Font = Enum.Font.SourceSansBold
+ titleLabel.TextColor3 = Color3.new(54/255,54/255,54/255)
+ titleLabel.ZIndex = 8
+ titleLabel.Size = UDim2.new(1,0,0,50)
+ titleLabel.Parent = purchaseDialog
+
+ local distanceBetweenButtons = 20
+
+ local cancelButton = createImageButton("CancelButton")
+ cancelButton.Position = UDim2.new(0.5,(distanceBetweenButtons/2),1,-100)
+ cancelButton.BorderColor3 = Color3.new(86/255,86/255,86/255)
+ cancelButton.Parent = bodyFrame
+ cancelButton.Modal = true
+ cancelButton.ZIndex = 8
+ cancelButton.Image = cancelButtonImageUrl
+ cancelButton.MouseButton1Up:connect(function( )
+ cancelButton.Image = cancelButtonImageUrl
+ end)
+ cancelButton.MouseLeave:connect(function( )
+ cancelButton.Image = cancelButtonImageUrl
+ end)
+ cancelButton.MouseButton1Click:connect(doDeclinePurchase)
+
+ local cancelText = createTextObject("CancelText","Cancel","TextLabel",Enum.FontSize.Size24)
+ cancelText.TextColor3 = Color3.new(1,1,1)
+ cancelText.Size = UDim2.new(1,0,1,0)
+ cancelText.ZIndex = 8
+ cancelText.Parent = cancelButton
+
+ local cancelHoverFrame = Instance.new("Frame")
+ cancelHoverFrame.Name = "HoverFrame"
+ cancelHoverFrame.Size = UDim2.new(1,0,1,0)
+ cancelHoverFrame.BackgroundColor3 = Color3.new(1,1,1)
+ cancelHoverFrame.BackgroundTransparency = 0.7
+ cancelHoverFrame.BorderSizePixel = 0
+ cancelHoverFrame.Visible = false
+ cancelHoverFrame.ZIndex = 8
+ cancelHoverFrame.Parent = cancelButton
+ cancelButton.MouseEnter:connect(function()
+ cancelHoverFrame.Visible = true
+ end)
+ cancelButton.MouseLeave:connect(function( )
+ cancelHoverFrame.Visible = false
+ end)
+ cancelButton.MouseButton1Click:connect(function( )
+ cancelHoverFrame.Visible = false
+ end)
+
+ local buyButton = createImageButton("BuyButton")
+ buyButton.Position = UDim2.new(0.5,-117-(distanceBetweenButtons/2),1,-100)
+ buyButton.BorderColor3 = Color3.new(0,112/255,1/255)
+ buyButton.Image = buyImageUrl
+ buyButton.ZIndex = 8
+ buyButton.Parent = bodyFrame
+
+ local buyText = createTextObject("BuyText","Buy Now","TextLabel",Enum.FontSize.Size24)
+ buyText.ZIndex = 8
+ buyText.TextColor3 = Color3.new(1,1,1)
+ buyText.Size = UDim2.new(1,0,1,0)
+ buyText.Parent = buyButton
+
+ local buyHoverFrame = cancelHoverFrame:Clone()
+ buyButton.MouseEnter:connect(function()
+ buyHoverFrame.Visible = true
+ end)
+ buyButton.MouseLeave:connect(function( )
+ buyHoverFrame.Visible = false
+ end)
+ buyButton.MouseButton1Click:connect(function( )
+ buyHoverFrame.Visible = false
+ end)
+ buyHoverFrame.Parent = buyButton
+
+ local buyDisabledButton = buyButton:Clone()
+ buyDisabledButton.Name = "BuyDisabledButton"
+ buyDisabledButton.AutoButtonColor = false
+ buyDisabledButton.Visible = false
+ buyDisabledButton.Active = false
+ buyDisabledButton.Parent = bodyFrame
+
+ local buyRobux = buyButton:Clone()
+ buyRobux.Name = "BuyRobuxButton"
+ buyRobux.AutoButtonColor = false
+ buyRobux.Visible = false
+ buyRobux.ZIndex = 8
+
+ if canUseNewRobuxToProductFlow() then
+ buyRobux.BuyText.Text = "Buy"
+ else
+ buyRobux.BuyText.Text = "Buy R$"
+ end
+
+ buyRobux.MouseEnter:connect(function()
+ buyRobux.HoverFrame.Visible = true
+ end)
+ buyRobux.MouseLeave:connect(function( )
+ buyRobux.HoverFrame.Visible = false
+ end)
+ buyRobux.MouseButton1Click:connect(function( )
+ buyRobux.HoverFrame.Visible = false
+
+ if canUseNewRobuxToProductFlow() then
+ buyEnoughCurrencyForProduct()
+ else
+ openBuyCurrencyWindow()
+ end
+ end)
+ buyRobux.Parent = bodyFrame
+
+ local buyBC = buyRobux:Clone()
+ buyBC.Name = "BuyBCButton"
+ buyBC.BuyText.Text = "Buy Builders Club"
+ buyBC.MouseEnter:connect(function()
+ buyBC.HoverFrame.Visible = true
+ end)
+ buyBC.MouseLeave:connect(function( )
+ buyBC.HoverFrame.Visible = false
+ end)
+ buyBC.MouseButton1Click:connect(function( )
+ buyBC.HoverFrame.Visible = false
+ openBCUpSellWindow()
+ end)
+ buyBC.Parent = bodyFrame
+
+ local freeButton = buyButton:Clone()
+ freeButton.BuyText.Text = "Take Free"
+ freeButton.BackgroundTransparency = 1
+ freeButton.Name = "FreeButton"
+ freeButton.Visible = false
+ freeButton.MouseEnter:connect(function()
+ freeButton.HoverFrame.Visible = true
+ end)
+ freeButton.MouseButton1Click:connect(function( )
+ freeButton.HoverFrame.Visible = false
+ end)
+ freeButton.MouseLeave:connect(function( )
+ freeButton.HoverFrame.Visible = false
+ end)
+ freeButton.Parent = bodyFrame
+
+ local okButton = buyButton:Clone()
+ okButton.BuyText.Text = "Ok"
+ okButton.Name = "OkButton"
+ okButton.Visible = false
+ okButton.Position = UDim2.new(0.5,-okButton.Size.X.Offset/2,1,-100)
+ okButton.Modal = true
+ okButton.MouseEnter:connect(function()
+ okButton.HoverFrame.Visible = true
+ end)
+ okButton.MouseButton1Click:connect(function( )
+ okButton.HoverFrame.Visible = false
+ signalPromptEnded(false)
+ end)
+ okButton.MouseLeave:connect(function( )
+ okButton.HoverFrame.Visible = false
+ end)
+ okButton.Parent = bodyFrame
+
+ local okPurchasedButton = okButton:Clone()
+ okPurchasedButton.Name = "OkPurchasedButton"
+ okPurchasedButton.MouseEnter:connect(function()
+ okPurchasedButton.HoverFrame.Visible = true
+ end)
+ okPurchasedButton.MouseLeave:connect(function( )
+ okPurchasedButton.HoverFrame.Visible = false
+ end)
+ okPurchasedButton.MouseButton1Click:connect(function()
+ okPurchasedButton.HoverFrame.Visible = false
+ if purchasingConsumable then
+ userPurchaseProductActionsEnded(true)
+ else
+ signalPromptEnded(true)
+ end
+ end)
+ okPurchasedButton.Parent = bodyFrame
+
+ buyButton.MouseButton1Click:connect(function() doAcceptPurchase(Enum.CurrencyType.Robux) end)
+ freeButton.MouseButton1Click:connect(function() doAcceptPurchase(false) end)
+
+ local itemPreview = Instance.new("ImageLabel")
+ itemPreview.Name = "ItemPreview"
+ itemPreview.BackgroundTransparency = 1
+ itemPreview.BorderSizePixel = 0
+ itemPreview.Position = UDim2.new(0,20,0,20)
+ itemPreview.Size = UDim2.new(0,100,0,100)
+ itemPreview.ZIndex = 9
+ itemPreview.Parent = bodyFrame
+
+ local itemDescription = createTextObject("ItemDescription","","TextLabel",Enum.FontSize.Size18)
+ itemDescription.TextXAlignment = Enum.TextXAlignment.Left
+ itemDescription.Position = UDim2.new(0.5, -70, 0, 10)
+ itemDescription.Size = UDim2.new(0,245,0,115)
+ itemDescription.TextColor3 = Color3.new(54/255,54/255,54/255)
+ itemDescription.ZIndex = 8
+ itemDescription.Parent = bodyFrame
+
+ local afterBalanceText = createTextObject("AfterBalanceText","","TextLabel",Enum.FontSize.Size14)
+ afterBalanceText.BackgroundTransparency = 1
+ afterBalanceText.TextColor3 = Color3.new(102/255,102/255,102/255)
+ afterBalanceText.Position = UDim2.new(0,5,1,-33)
+ afterBalanceText.Size = UDim2.new(1,-10,0,28)
+ afterBalanceText.ZIndex = 8
+ afterBalanceText.Parent = bodyFrame
+
+ local purchasingFrame = Instance.new("Frame")
+ purchasingFrame.Name = "PurchasingFrame"
+ purchasingFrame.Size = UDim2.new(1,0,1,0)
+ purchasingFrame.BackgroundColor3 = Color3.new(0,0,0)
+ purchasingFrame.BackgroundTransparency = 0.05
+ purchasingFrame.BorderSizePixel = 0
+ purchasingFrame.ZIndex = 9
+ purchasingFrame.Visible = false
+ purchasingFrame.Active = true
+ purchasingFrame.Parent = purchaseDialog
+
+ local purchasingLabel = createTextObject("PurchasingLabel","Purchasing","TextLabel",Enum.FontSize.Size48)
+ purchasingLabel.Size = UDim2.new(1,0,1,0)
+ purchasingLabel.Position = UDim2.new(0,0,0,-24)
+ purchasingLabel.ZIndex = 10
+ purchasingLabel.Parent = purchasingFrame
+
+ local purchasingSpinner = Instance.new("ImageLabel")
+ purchasingSpinner.Name = "PurchasingSpinnerOuter"
+ purchasingSpinner.Image = loadingImage
+ purchasingSpinner.BackgroundTransparency = 1
+ purchasingSpinner.BorderSizePixel = 0
+ purchasingSpinner.Size = UDim2.new(0,64,0,64)
+ purchasingSpinner.Position = UDim2.new(0.5,-32,0.5,32)
+ purchasingSpinner.ZIndex = 10
+ purchasingSpinner.Parent = purchasingFrame
+
+ local purchasingSpinnerInner = purchasingSpinner:Clone()
+ purchasingSpinnerInner.BackgroundTransparency = 1
+ purchasingSpinnerInner.Name = "PurchasingSpinnerInner"
+ purchasingSpinnerInner.Size = UDim2.new(0,32,0,32)
+ purchasingSpinnerInner.Position = UDim2.new(0.5,-16,0.5,48)
+ purchasingSpinnerInner.Parent = purchasingFrame
+end
+
+-- next 2 functions are convenienvce creation functions for guis
+function createTextObject(name, text, type, size)
+ local textLabel = Instance.new(type)
+ textLabel.Font = Enum.Font.SourceSans
+ textLabel.TextColor3 = Color3.new(217/255, 217/255, 217/255)
+ textLabel.TextWrapped = true
+ textLabel.Name = name
+ textLabel.Text = text
+ textLabel.BackgroundTransparency = 1
+ textLabel.BorderSizePixel = 0
+ textLabel.FontSize = size
+
+ return textLabel
+end
+
+function createImageButton(name)
+ local imageButton = Instance.new("ImageButton")
+ imageButton.Size = UDim2.new(0,117,0,60)
+ imageButton.Name = name
+ return imageButton
+end
+
+function setHeaderText(text)
+ purchaseDialog.TitleLabel.Text = text
+end
+
+function doPurchasePrompt(player, assetId, equipIfPurchased, currencyType, productId)
+ if not purchaseDialog then
+ createPurchasePromptGui()
+ end
+
+ if player == game.Players.LocalPlayer then
+ if currentlyPrompting then return end
+
+ currentlyPrompting = true
+
+ currentAssetId = assetId
+ currentProductId = productId
+ currentCurrencyType = currencyType
+ currentEquipOnPurchase = equipIfPurchased
+
+ purchasingConsumable = (currentProductId ~= nil)
+
+ showPurchasePrompt()
+ end
+end
+
+function userPurchaseProductActionsEnded(userIsClosingDialog)
+ checkingPlayerFunds = false
+
+ if userIsClosingDialog then
+ closePurchasePrompt()
+ if currentServerResponseTable then
+ local isPurchased = false
+ if tostring(currentServerResponseTable["isValid"]):lower() == "true" then
+ isPurchased = true
+ end
+
+ Game:GetService("MarketplaceService"):SignalPromptProductPurchaseFinished(tonumber(currentServerResponseTable["playerId"]), tonumber(currentServerResponseTable["productId"]), isPurchased)
+ end
+ removeCurrentPurchaseInfo()
+ else
+ if tostring(currentServerResponseTable["isValid"]):lower() == "true" then
+ local newPurchasedSucceededText = string.gsub( purchaseSucceededText,"itemName", tostring(currentProductInfo["Name"]))
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedSucceededText
+
+ local playerBalance = getPlayerBalance()
+ local keyWord = "robux"
+ if currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ local afterBalanceNumber = playerBalance[keyWord]
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balanceCurrentTenseText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkPurchasedButton)
+ hidePurchasing()
+ else
+ purchaseFailed()
+ end
+ end
+end
+
+function doProcessServerPurchaseResponse(serverResponseTable)
+ if not serverResponseTable then
+ purchaseFailed()
+ return
+ end
+
+ if serverResponseTable["playerId"] and tonumber(serverResponseTable["playerId"]) == game.Players.LocalPlayer.userId then
+ currentServerResponseTable = serverResponseTable
+ userPurchaseProductActionsEnded(false)
+ end
+end
+
+---------------------------------------------- End Gui Functions ----------------------------------------------
+
+
+---------------------------------------------- Script Event start/initialization ----------------------------------------------
+preloadAssets()
+
+game:GetService("MarketplaceService").PromptProductPurchaseRequested:connect(function(player, productId, equipIfPurchased, currencyType)
+ doPurchasePrompt(player, nil, equipIfPurchased, currencyType, productId)
+end)
+
+Game:GetService("MarketplaceService").PromptPurchaseRequested:connect(function(player, assetId, equipIfPurchased, currencyType)
+ doPurchasePrompt(player, assetId, equipIfPurchased, currencyType, nil)
+end)
+
+Game:GetService("MarketplaceService").ServerPurchaseVerification:connect(function(serverResponseTable)
+ doProcessServerPurchaseResponse(serverResponseTable)
+end)
+
+Game:GetService("GuiService").BrowserWindowClosed:connect(checkIfCanPurchase)
+
+if not canUseNewRobuxToProductFlow() then return end
+
+Game.MarketplaceService.NativePurchaseFinished:connect(function(player, productId, wasPurchased)
+ if wasPurchased then
+
+ -- try for 20 seconds to see if we get the funds if we purchased something
+ local retriesLeft = 40
+ local canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ while canPurchase and insufficientFunds and retriesLeft > 0 do
+ wait(0.5)
+ canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ retriesLeft = retriesLeft - 1
+ end
+
+ if canPurchase and not insufficientFunds and not notRightBC then
+ doAcceptPurchase(Enum.CurrencyType.Robux)
+ else
+ purchaseFailed("didNotBuyRobux")
+ end
+ else
+ purchaseFailed("didNotBuyRobux")
+ end
+end)
diff --git a/asset/backup/13 b/asset/backup/13
new file mode 100644
index 0000000..54d0610
--- /dev/null
+++ b/asset/backup/13
@@ -0,0 +1,317 @@
+%13%
+--[[
+ This script controls the gui the player sees in regards to his or her health.
+ Can be turned with Game.StarterGui:SetCoreGuiEnabled(Enum.CoreGuiType.Health,false)
+ Copyright ROBLOX 2014. Written by Ben Tkacheff.
+--]]
+
+---------------------------------------------------------------------
+-- Initialize/Variables
+while not Game do
+ wait(1/60)
+end
+while not Game.Players do
+ wait(1/60)
+end
+
+local useCoreHealthBar = false
+local success = pcall(function() useCoreHealthBar = Game.Players:GetUseCoreScriptHealthBar() end)
+if not success or not useCoreHealthBar then
+ return
+end
+
+local currentHumanoid = nil
+
+local HealthGui = nil
+local lastHealth = 100
+local HealthPercentageForOverlay = 5
+local maxBarTweenTime = 0.3
+local greenColor = Color3.new(0.2, 1, 0.2)
+local redColor = Color3.new(1, 0.2, 0.2)
+local yellowColor = Color3.new(1, 1, 0.2)
+
+local guiEnabled = false
+local healthChangedConnection = nil
+local humanoidDiedConnection = nil
+local characterAddedConnection = nil
+
+local greenBarImage = "rbxasset://textures/ui/Health-BKG-Center.png"
+local greenBarImageLeft = "rbxasset://textures/ui/Health-BKG-Left-Cap.png"
+local greenBarImageRight = "rbxasset://textures/ui/Health-BKG-Right-Cap.png"
+local hurtOverlayImage = "http://www.roblox.com/asset/?id=34854607"
+
+Game:GetService("ContentProvider"):Preload(greenBarImage)
+Game:GetService("ContentProvider"):Preload(hurtOverlayImage)
+
+while not Game.Players.LocalPlayer do
+ wait(1/60)
+end
+
+---------------------------------------------------------------------
+-- Functions
+
+local capHeight = 15
+local capWidth = 7
+
+function CreateGui()
+ if HealthGui and #HealthGui:GetChildren() > 0 then
+ HealthGui.Parent = Game.CoreGui.RobloxGui
+ return
+ end
+
+ local hurtOverlay = Instance.new("ImageLabel")
+ hurtOverlay.Name = "HurtOverlay"
+ hurtOverlay.BackgroundTransparency = 1
+ hurtOverlay.Image = hurtOverlayImage
+ hurtOverlay.Position = UDim2.new(-10,0,-10,0)
+ hurtOverlay.Size = UDim2.new(20,0,20,0)
+ hurtOverlay.Visible = false
+ hurtOverlay.Parent = HealthGui
+
+ local healthFrame = Instance.new("Frame")
+ healthFrame.Name = "HealthFrame"
+ healthFrame.BackgroundTransparency = 1
+ healthFrame.BackgroundColor3 = Color3.new(1,1,1)
+ healthFrame.BorderColor3 = Color3.new(0,0,0)
+ healthFrame.BorderSizePixel = 0
+ healthFrame.Position = UDim2.new(0.5,-85,1,-20)
+ healthFrame.Size = UDim2.new(0,170,0,capHeight)
+ healthFrame.Parent = HealthGui
+
+
+ local healthBarBackCenter = Instance.new("ImageLabel")
+ healthBarBackCenter.Name = "healthBarBackCenter"
+ healthBarBackCenter.BackgroundTransparency = 1
+ healthBarBackCenter.Image = greenBarImage
+ healthBarBackCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBarBackCenter.Position = UDim2.new(0,capWidth,0,0)
+ healthBarBackCenter.Parent = healthFrame
+ healthBarBackCenter.ImageColor3 = Color3.new(1,1,1)
+
+ local healthBarBackLeft = Instance.new("ImageLabel")
+ healthBarBackLeft.Name = "healthBarBackLeft"
+ healthBarBackLeft.BackgroundTransparency = 1
+ healthBarBackLeft.Image = greenBarImageLeft
+ healthBarBackLeft.Size = UDim2.new(0,capWidth,1,0)
+ healthBarBackLeft.Position = UDim2.new(0,0,0,0)
+ healthBarBackLeft.Parent = healthFrame
+ healthBarBackLeft.ImageColor3 = Color3.new(1,1,1)
+
+ local healthBarBackRight = Instance.new("ImageLabel")
+ healthBarBackRight.Name = "healthBarBackRight"
+ healthBarBackRight.BackgroundTransparency = 1
+ healthBarBackRight.Image = greenBarImageRight
+ healthBarBackRight.Size = UDim2.new(0,capWidth,1,0)
+ healthBarBackRight.Position = UDim2.new(1,-capWidth,0,0)
+ healthBarBackRight.Parent = healthFrame
+ healthBarBackRight.ImageColor3 = Color3.new(1,1,1)
+
+
+ local healthBar = Instance.new("Frame")
+ healthBar.Name = "HealthBar"
+ healthBar.BackgroundTransparency = 1
+ healthBar.BackgroundColor3 = Color3.new(1,1,1)
+ healthBar.BorderColor3 = Color3.new(0,0,0)
+ healthBar.BorderSizePixel = 0
+ healthBar.ClipsDescendants = true
+ healthBar.Position = UDim2.new(0, 0, 0, 0)
+ healthBar.Size = UDim2.new(1,0,1,0)
+ healthBar.Parent = healthFrame
+
+
+ local healthBarCenter = Instance.new("ImageLabel")
+ healthBarCenter.Name = "healthBarCenter"
+ healthBarCenter.BackgroundTransparency = 1
+ healthBarCenter.Image = greenBarImage
+ healthBarCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBarCenter.Position = UDim2.new(0,capWidth,0,0)
+ healthBarCenter.Parent = healthBar
+ healthBarCenter.ImageColor3 = greenColor
+
+ local healthBarLeft = Instance.new("ImageLabel")
+ healthBarLeft.Name = "healthBarLeft"
+ healthBarLeft.BackgroundTransparency = 1
+ healthBarLeft.Image = greenBarImageLeft
+ healthBarLeft.Size = UDim2.new(0,capWidth,1,0)
+ healthBarLeft.Position = UDim2.new(0,0,0,0)
+ healthBarLeft.Parent = healthBar
+ healthBarLeft.ImageColor3 = greenColor
+
+ local healthBarRight = Instance.new("ImageLabel")
+ healthBarRight.Name = "healthBarRight"
+ healthBarRight.BackgroundTransparency = 1
+ healthBarRight.Image = greenBarImageRight
+ healthBarRight.Size = UDim2.new(0,capWidth,1,0)
+ healthBarRight.Position = UDim2.new(1,-capWidth,0,0)
+ healthBarRight.Parent = healthBar
+ healthBarRight.ImageColor3 = greenColor
+
+ HealthGui.Parent = Game.CoreGui.RobloxGui
+end
+
+function UpdateGui(health)
+ if not HealthGui then return end
+
+ local healthFrame = HealthGui:FindFirstChild("HealthFrame")
+ if not healthFrame then return end
+
+ local healthBar = healthFrame:FindFirstChild("HealthBar")
+ if not healthBar then return end
+
+ -- If more than 1/4 health, bar = green. Else, bar = red.
+ local percentHealth = (health/currentHumanoid.MaxHealth)
+ if percentHealth ~= percentHealth then
+ percentHealth = 1
+ healthBar.healthBarCenter.ImageColor3 = yellowColor
+ healthBar.healthBarRight.ImageColor3 = yellowColor
+ healthBar.healthBarLeft.ImageColor3 = yellowColor
+ elseif percentHealth > 0.25 then
+ healthBar.healthBarCenter.ImageColor3 = greenColor
+ healthBar.healthBarRight.ImageColor3 = greenColor
+ healthBar.healthBarLeft.ImageColor3 = greenColor
+ else
+ healthBar.healthBarCenter.ImageColor3 = redColor
+ healthBar.healthBarRight.ImageColor3 = redColor
+ healthBar.healthBarLeft.ImageColor3 = redColor
+ end
+
+ local width = (health / currentHumanoid.MaxHealth)
+ width = math.max(math.min(width,1),0) -- make sure width is between 0 and 1
+ if width ~= width then width = 1 end
+
+ local healthDelta = lastHealth - health
+ lastHealth = health
+
+ local percentOfTotalHealth = math.abs(healthDelta/currentHumanoid.MaxHealth)
+ percentOfTotalHealth = math.max(math.min(percentOfTotalHealth,1),0) -- make sure percentOfTotalHealth is between 0 and 1
+ if percentOfTotalHealth ~= percentOfTotalHealth then percentOfTotalHealth = 1 end
+
+ local newHealthSize = UDim2.new(width,0,1,0)
+
+ healthBar.Size = newHealthSize
+
+ local sizeX = healthBar.AbsoluteSize.X
+ if sizeX < capWidth then
+ healthBar.healthBarCenter.Visible = false
+ healthBar.healthBarRight.Visible = false
+ elseif sizeX < (2*capWidth + 1) then
+ healthBar.healthBarCenter.Visible = true
+ healthBar.healthBarCenter.Size = UDim2.new(0,sizeX - capWidth,1,0)
+ healthBar.healthBarRight.Visible = false
+ else
+ healthBar.healthBarCenter.Visible = true
+ healthBar.healthBarCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBar.healthBarRight.Visible = true
+ end
+
+ local thresholdForHurtOverlay = currentHumanoid.MaxHealth * (HealthPercentageForOverlay/100)
+
+ if healthDelta >= thresholdForHurtOverlay then
+ AnimateHurtOverlay()
+ end
+
+end
+
+function AnimateHurtOverlay()
+ if not HealthGui then return end
+
+ local overlay = HealthGui:FindFirstChild("HurtOverlay")
+ if not overlay then return end
+
+ local newSize = UDim2.new(20, 0, 20, 0)
+ local newPos = UDim2.new(-10, 0, -10, 0)
+
+ if overlay:IsDescendantOf(Game) then
+ -- stop any tweens on overlay
+ overlay:TweenSizeAndPosition(newSize,newPos,Enum.EasingDirection.Out,Enum.EasingStyle.Linear,0,true,function()
+
+ -- show the gui
+ overlay.Size = UDim2.new(1,0,1,0)
+ overlay.Position = UDim2.new(0,0,0,0)
+ overlay.Visible = true
+
+ -- now tween the hide
+ if overlay:IsDescendantOf(Game) then
+ overlay:TweenSizeAndPosition(newSize,newPos,Enum.EasingDirection.Out,Enum.EasingStyle.Quad,10,false,function()
+ overlay.Visible = false
+ end)
+ else
+ overlay.Size = newSize
+ overlay.Position = newPos
+ end
+ end)
+ else
+ overlay.Size = newSize
+ overlay.Position = newPos
+ end
+
+end
+
+function humanoidDied()
+ UpdateGui(0)
+end
+
+function disconnectPlayerConnections()
+ if characterAddedConnection then characterAddedConnection:disconnect() end
+ if humanoidDiedConnection then humanoidDiedConnection:disconnect() end
+ if healthChangedConnection then healthChangedConnection:disconnect() end
+end
+
+function newPlayerCharacter()
+ disconnectPlayerConnections()
+ startGui()
+end
+
+function startGui()
+ characterAddedConnection = Game.Players.LocalPlayer.CharacterAdded:connect(newPlayerCharacter)
+
+ local character = Game.Players.LocalPlayer.Character
+ if not character then
+ return
+ end
+
+ currentHumanoid = character:WaitForChild("Humanoid")
+ if not currentHumanoid then
+ return
+ end
+
+ if not Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health) then
+ return
+ end
+
+ healthChangedConnection = currentHumanoid.HealthChanged:connect(UpdateGui)
+ humanoidDiedConnection = currentHumanoid.Died:connect(humanoidDied)
+ UpdateGui(currentHumanoid.Health)
+
+ CreateGui()
+end
+
+
+
+---------------------------------------------------------------------
+-- Start Script
+
+HealthGui = Instance.new("Frame")
+HealthGui.Name = "HealthGui"
+HealthGui.BackgroundTransparency = 1
+HealthGui.Size = UDim2.new(1,0,1,0)
+
+Game.StarterGui.CoreGuiChangedSignal:connect(function(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Health or coreGuiType == Enum.CoreGuiType.All then
+ if guiEnabled and not enabled then
+ if HealthGui then
+ HealthGui.Parent = nil
+ end
+ disconnectPlayerConnections()
+ elseif not guiEnabled and enabled then
+ startGui()
+ end
+
+ guiEnabled = enabled
+ end
+end)
+
+if Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health) then
+ guiEnabled = true
+ startGui()
+end
\ No newline at end of file
diff --git a/asset/backup/14 b/asset/backup/14
new file mode 100644
index 0000000..6895ea1
--- /dev/null
+++ b/asset/backup/14
@@ -0,0 +1,3056 @@
+%14%
+--------------------
+-- Super Util
+--------------------
+
+local ADMINS =
+{
+ MAO = 1,
+ adamintygum = 1,
+ androidtest = 1,
+ robloxfrenchie = 1,
+ jackssmirkingrevenge = 1,
+ mandaari = 1,
+ vaiobot = 1,
+ goddessnoob = 1,
+ thr33pakshak3r = 1,
+ effward = 1,
+ blockhaak = 1,
+ drewbda = 1,
+ triptych999 = 1,
+ tone = 1,
+ fasterbuilder19 = 1,
+ zeuxcg = 1,
+ concol2 = 1,
+ reesemcblox = 1,
+ jeditkacheff = 'http://www.roblox.com/asset/?id=134032333',
+ chiefjustus = 1,
+ ellissar = 1,
+ geekndestroy = 1,
+ noob007 = 1,
+ limon = 1,
+ hawkington = 1,
+ tabemono = 1,
+ autoconfig = 1,
+ brighteyes = 1,
+ monsterinc3d = 1,
+ isolatedevent = 1,
+ countonconnor = 1,
+ scubasomething = 1,
+ onlytwentycharacters = 1,
+ lordrugdumph = 1,
+ bellavour = 1,
+ ['david.baszucki'] = 1,
+ ibanez2189 = 1,
+ convexhero = 1,
+ sorcus = 'http://www.roblox.com/asset/?id=113059239',
+ deeana00 = 1,
+ thelorekt = 1,
+ ['mse6'] = 1,
+ corgiparade = 1,
+ varia = 1,
+ ['4runningwolves'] = 1,
+ pulmoesflor = 1,
+ olive71 = 1,
+ groundcontroll2 = 1,
+ gurukrish = 1,
+ countvelcro = 1,
+ iltalumi = 1,
+ juanjuan23 = 1,
+ ostrichsized = 1,
+ jackintheblox = 1,
+ slingshotjunkie = 1,
+ gordonrox24 = 1,
+ sharpnine = 1,
+ motornerve = 1,
+ watchmedogood = 1,
+ jmargh = 1,
+ jaykorean = 1,
+ foyle = 1,
+ majortom4321 = 1,
+ shedletsky = 'http://www.roblox.com/asset/?id=105897927',
+ supernovacaine = 1,
+ ffjosh = 1,
+ sickenedmonkey = 1,
+ doughtless = 1,
+ kbux = 1,
+ totallynothere = 1,
+ erzastar = 1,
+ keith = 1,
+ chro = 1,
+ solarcrane = 1,
+ glorioussalt = 1,
+ imightbelying = 1,
+ uristmcsparks = 1,
+ itolauren = 1,
+ malcomso = 1,
+ heyseptember = 1,
+ stickmasterluke = 1,
+ windlight13 = 1,
+ stravant = 1,
+ imaginationsensation = 1,
+ ['matt.dusek'] = 1,
+ crimmsonghost = 1,
+ mcrtest = 1,
+ maxvee = 1,
+ coatp0cketninja = 1,
+ screenme = 1,
+ b1tsh1ft = 1,
+ convexrumbler = 1,
+ mpliner476 = 1,
+ totbl = 1,
+ aquabot8 = 1,
+ grossinger = 1,
+ merely = 1,
+ cdakkar = 1,
+ siekiera = 1,
+ robloxkidsaccount = 1,
+ flotsamthespork = 1,
+ soggoth = 1,
+ phil = 1,
+ orcasparkles = 1,
+ skullgoblin = 1,
+ rickrosstheb0ss = 1,
+ argonpirate = 1,
+ nobledragon = 1,
+ squidcod = 1,
+ raeglyn = 1,
+ xerolayne = 1,
+ robloxsai = 'http://www.roblox.com/asset/?id=161078086',
+ briarroze = 1,
+ hawkeyebandit = 1,
+ dapperbuffalo = 1,
+ vukota = 1,
+ swiftstone = 1,
+ gemlocker = 1,
+ tarabyte = 1,
+ timobius = 1,
+ tobotrobot = 1,
+ foster008 = 1,
+ twberg = 1,
+ darthvaden = 1,
+ khanovich = 1,
+ codewriter = 1,
+ olefto = 1,
+ vladthefirst = 1,
+ phaedre = 1,
+ gorroth = 1,
+ jynj1984 = 1,
+ roboyz = 1,
+ zodiaczak = 1,
+}
+
+
+local Images = {
+ bottomDark = '94691904',
+ bottomLight = '94691940',
+ midDark = '94691980',
+ midLight = '94692025',
+ LargeDark = '96098866',
+ LargeLight = '96098920',
+ LargeHeader = '96097470',
+ NormalHeader = '94692054',
+ LargeBottom = '96397271',
+ NormalBottom = '94754966',
+ DarkBluePopupMid = '97114905',
+ LightBluePopupMid = '97114905',
+ DarkPopupMid = '97112126',
+ LightPopupMid = '97109338',
+ DarkBluePopupTop = '97114838',
+ DarkBluePopupBottom = '97114758',
+ DarkPopupBottom = '100869219',
+ LightPopupBottom = '97109175',
+}
+
+local BASE_TWEEN = .25
+
+local MOUSE_HOLD_TIME = .15
+local MOUSE_DRAG_DISTANCE = 15
+
+local BACKGROUND_TRANSPARENCY = 0.7
+--[[
+ Generic object Create function, which I am using to create Gui's
+ Thanks to Stravant!
+--]]
+local Obj = {}
+function Obj.Create(guiType)
+ return function(data)
+ local obj = Instance.new(guiType)
+ for k, v in pairs(data) do
+ if type(k) == 'number' then
+ v.Parent = obj
+ else
+ obj[k] = v
+ end
+ end
+ return obj
+ end
+end
+
+--[[
+ makes a full sized background for a guiobject
+ @Args:
+ imgName asset name of image to fill background
+ @Return: background gui object
+--]]
+function MakeBackgroundGuiObjOld(imgName)
+ return Obj.Create'ImageLabel'
+ {
+ Name = 'Background',
+ BackgroundTransparency = 1,
+ Image = imgName,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ }
+end
+
+function MakeBackgroundGuiObj(imgName)
+ return Obj.Create'Frame'
+ {
+ Name = 'Background',
+ BackgroundTransparency = BACKGROUND_TRANSPARENCY,
+ BackgroundColor3 = Color3.new(0,0,0),
+ BorderSizePixel = 0,
+ Position = UDim2.new(0, 1, 0, 1),
+ Size = UDim2.new(1,-2,1,-2),
+ }
+end
+
+
+--[[ turns 255 integer color value to a color3 --]]
+function Color3I(r,g,b)
+ return Color3.new(r/255,g/255,b/255)
+end
+
+--[[
+ Gets correct icon for builder's club status to display by name
+ @Args:
+ membershipType Enum of membership status
+ @Return: string of image asset
+--]]
+function getMembershipTypeIcon(membershipType,playerName)
+ if ADMINS[string.lower(playerName)]~=nil then
+ if ADMINS[string.lower(playerName)] == 1 then
+ return "http://www.roblox.com/asset/?id=99727663"
+ else
+ return ADMINS[string.lower(playerName)]
+ end
+ elseif membershipType == Enum.MembershipType.None then
+ return ""
+ elseif membershipType == Enum.MembershipType.BuildersClub then
+ return "rbxasset://textures/ui/TinyBcIcon.png"
+ elseif membershipType == Enum.MembershipType.TurboBuildersClub then
+ return "rbxasset://textures/ui/TinyTbcIcon.png"
+ elseif membershipType == Enum.MembershipType.OutrageousBuildersClub then
+ return "rbxasset://textures/ui/TinyObcIcon.png"
+ else
+ error("Unknown membershipType" .. membershipType)
+ end
+end
+
+local function getFriendStatusIcon(friendStatus)
+ if friendStatus == Enum.FriendStatus.Unknown or friendStatus == Enum.FriendStatus.NotFriend then
+ return ""
+ elseif friendStatus == Enum.FriendStatus.Friend then
+ return "http://www.roblox.com/asset/?id=99749771"
+ elseif friendStatus == Enum.FriendStatus.FriendRequestSent then
+ return "http://www.roblox.com/asset/?id=99776888"
+ elseif friendStatus == Enum.FriendStatus.FriendRequestReceived then
+ return "http://www.roblox.com/asset/?id=99776838"
+ else
+ error("Unknown FriendStatus: " .. friendStatus)
+ end
+end
+
+
+--[[
+ Utility function to create buttons for the popup menus
+ @Args:
+ nparent what to parent this button to
+ ntext text to put on this button
+ index number index of this entry in menu
+ last is this the last element of the popup menu
+ @Return: a popup menu button
+--]]
+function MakePopupButton(nparent,ntext,index,last)
+ local tobj = Obj.Create"ImageButton"
+ {
+ Name = 'ReportButton',
+ BackgroundTransparency = 1,
+ BackgroundColor3 = Color3.new(0, 0, 0),
+ Position = UDim2.new(0,0,1*index,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ ZIndex=7,
+ Obj.Create'TextLabel'
+ {
+ Name = 'ButtonText',
+ BackgroundTransparency = 0.6,
+ BackgroundColor3 = Color3.new(0, 0, 0),
+ Position = UDim2.new(.07, 0, .07, 0),
+ Size = UDim2.new(.86,0,.86,0),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = ntext,
+ FontSize = 'Size14',
+ TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeTransparency = 1,
+ ZIndex=7,
+ },
+ Parent = nparent,
+ }
+
+ return tobj
+end
+
+
+--[[
+ obligatory wait for child function
+ @Args:
+ parent Parent object to look for child in
+ child name of child object to look for
+ @Return: object waited for
+--]]
+function WaitForChild(parent,child)
+ while not parent:FindFirstChild(child) do
+ wait() debugprint(" child "..parent.Name.." waiting for "..child)
+ end
+ return parent[child]
+end
+
+ ---------------------------
+ -- Workspace Objects
+ ---------------------------
+
+-- might want to move all this to an init function, wait for localplayer elsewhere
+local Players = game:GetService('Players')
+-- make sure this doesn't run on the server(it will if you dont do this)
+while not Players.LocalPlayer do
+ Players.Changed:wait()
+end
+
+local LocalPlayer = Players.LocalPlayer
+local Mouse = LocalPlayer:GetMouse()
+
+local ScreenGui = Obj.Create"Frame"
+{
+ Name = 'PlayerListScreen',
+ Size = UDim2.new(1, 0, 1, 0),
+ BackgroundTransparency = 1,
+ Parent = script.Parent
+}
+local MainFrame = Obj.Create"Frame"
+{
+ Name = 'LeaderBoardFrame',
+ Position = UDim2.new(1, -150, 0.005, 0),
+ Size = UDim2.new(0, 150, 0, 800),
+ BackgroundTransparency = 1,
+ Parent = ScreenGui,
+}
+
+--frame used for expanding leaderstats when frame is 'focused'
+local FocusFrame = Obj.Create"Frame"
+{
+ Name = 'FocusFrame',
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1, 0, 0, 100),
+ BackgroundTransparency = 1,
+ Active = true,
+ Parent = MainFrame,
+}
+
+local TemplateFrameYSize = 0.670000017
+
+ -- HEADER
+local HeaderFrame = Obj.Create"Frame"
+{
+ Name = 'Header',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,0,0),
+ Size = UDim2.new(1, 0, .07, 0),
+ Parent = MainFrame,
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=94692054'),
+}
+ local HeaderFrameHeight = HeaderFrame.Size.Y.Scale
+ local MaximizeButton = Obj.Create"ImageButton"
+ {
+ Name = 'MaximizeButton',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ Parent = HeaderFrame,
+ }
+ local HeaderName = Obj.Create"TextLabel"
+ {
+ Name = 'PlayerName',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, .05, 0),
+ Size = UDim2.new(.98,0,.38,0),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = LocalPlayer.Name,
+ FontSize='Size24',
+ --TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+ local HeaderScore = Obj.Create"TextLabel"
+ {
+ Name = 'PlayerScore',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, .4, 0),
+ Size = UDim2.new(.98,0,0,30),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = '',
+ FontSize='Size24',
+ TextYAlignment = 'Top',
+ --TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeTransparency = 1,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Top',
+ }
+ -- BOTTOM
+ --used for shifting bottom frame for mouse over effects
+local BottomShiftFrame = Obj.Create"Frame"
+{
+ Name= 'BottomShiftFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,HeaderFrameHeight,0),
+ Size = UDim2.new(1,0,1,0),
+ Parent=MainFrame,
+}
+ local BottomFrame = Obj.Create"Frame"
+ {
+ Name = 'Bottom',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,.07,0),
+ Size = UDim2.new(1, 0, .03, 0),
+ Parent = BottomShiftFrame,
+ }
+ local ExtendButton = Obj.Create"ImageButton"
+ {
+ Name = 'bigbutton',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1.5,0),
+ ZIndex = 3,
+ Parent = BottomFrame,
+ }
+ local ExtendTab = Obj.Create"ImageButton"
+ {
+ Name = 'extendTab',
+ Active = true,
+ BackgroundTransparency = 1,
+ Image = 'rbxasset://textures/ui/expandPlayerList.png',
+ Position = UDim2.new(.608, 0, .3, 0),
+ Size = UDim2.new(0,27,0,11),
+ Parent = BottomFrame,
+ }
+local TopClipFrame = Obj.Create"Frame"
+{
+ Name = 'ListFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(-1,0,.07,0),
+ Size = UDim2.new(2, 0, 1, 0),
+ Parent = MainFrame,
+ ClipsDescendants = true,
+}
+ local BottomClipFrame = Obj.Create"Frame"
+ {
+ Name = 'BottomFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0, - .8,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ Parent = TopClipFrame,
+ ClipsDescendants = true,
+ }
+ local ScrollBarFrame = Obj.Create"Frame"
+ {
+ Name = 'ScrollBarFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.987,0,.8,0),
+ Size = UDim2.new(.01, 0, .2, 0),
+ Parent = BottomClipFrame,
+ }
+ local ScrollBar = Obj.Create"Frame"
+ {
+ Name = 'ScrollBar',
+ BackgroundTransparency = 0,
+ BackgroundColor3 = Color3.new(.2,.2,.2),
+ Position = UDim2.new(0,0,0,0),
+ Size = UDim2.new(1, 0, .5, 0),
+ ZIndex = 5,
+ Parent = ScrollBarFrame,
+
+ }
+ local ListFrame = Obj.Create"Frame"
+ {
+ Name = 'SubFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,.8,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ Parent = BottomClipFrame,
+ }
+local PopUpClipFrame = Obj.Create"Frame"
+{
+ Name = 'PopUpFrame',
+ BackgroundTransparency = 1,
+ SizeConstraint='RelativeXX',
+ Position = MainFrame.Position + UDim2.new( 0,-150,0,0),
+ Size = UDim2.new(0,150,0,800),
+ Parent = MainFrame,
+ ClipsDescendants = true,
+ ZIndex=7,
+}
+local PopUpPanel = nil
+ local PopUpPanelTemplate = Obj.Create"Frame"
+ {
+ Name = 'Panel',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(1,0,0,0),
+ Size = UDim2.new(1,0,.032,0),
+ Parent = PopUpClipFrame,
+ }
+
+local StatTitles = Obj.Create"Frame"
+{
+ Name = 'StatTitles',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,1,-10),
+ Size = UDim2.new(1, 0, 0, 0),
+ Parent = HeaderFrame,
+}
+
+local IsMinimized = Instance.new('BoolValue')
+local IsMaximized = Instance.new('BoolValue')
+local IsTabified = Instance.new('BoolValue')
+local AreNamesExpanded = Instance.new('BoolValue')
+
+
+local MiddleTemplate = Obj.Create"Frame"
+{
+ Name = 'MidTemplate',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(100,0,.07,0),
+ Size = UDim2.new(.5, 0, .025, 0),--UDim2.new(1, 0, .03, 0),
+ Obj.Create'ImageLabel'
+ {
+ Name = 'BCLabel',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.005, 5, .20, -2),
+ Size = UDim2.new(0,16,0,16),
+ SizeConstraint = 'RelativeYY',
+ Image = "",
+ ZIndex = 4,
+ },
+ Obj.Create'ImageLabel'
+ {
+ Name = 'FriendLabel',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.005, 5, .15, 0),
+ Size = UDim2.new(0,16,0,16),
+ SizeConstraint = 'RelativeYY',
+ Image = "",
+ ZIndex = 4,
+ },
+ Obj.Create"ImageButton"
+ {
+ Name = 'ClickListener',
+ Active = true,
+ BackgroundTransparency = 1,
+ BorderSizePixel = 0,
+ Position = UDim2.new(0, 1, 0, 1),
+ Size = UDim2.new(1, -2,1,-2),
+ ZIndex = 3,
+ },
+ Obj.Create"Frame"
+ {
+ Name = 'TitleFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.01, 0, 0, 0),
+ Size = UDim2.new(0,140,1,0),
+ BorderSizePixel = 0,
+ ClipsDescendants=true,
+ Obj.Create"TextLabel"
+ {
+ Name = 'Title',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 5, 0, 0),
+ Size = UDim2.new(100,0,1,0),
+ Font = 'Arial',
+ FontSize='Size14',
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = 'Left',
+ TextYAlignment = 'Center',
+ ZIndex = 3,
+ },
+ },
+
+ Obj.Create"TextLabel"
+ {
+ Name = 'PlayerScore',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ Font = 'ArialBold',
+ Text = '',
+ FontSize='Size14',
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ ZIndex = 3,
+ },
+ --Obj.Create'IntValue'{Name = 'ID'},
+ --Obj.Create'ObjectValue'{Name = 'Player'},
+ --Obj.Create'IntValue'{Name = 'Score'},
+ ZIndex = 3,
+}
+local MiddleBGTemplate = Obj.Create"Frame"
+{
+ Name = 'MidBGTemplate',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(100,0,.07,0),
+ Size = UDim2.new(.5, 0, .025, 0),--UDim2.new(1, 0, .03, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=94692025'),
+
+}
+
+ -- REPORT ABUSE OBJECTS
+
+local ReportAbuseShield = Obj.Create"TextButton"
+{
+ Name = "ReportAbuseShield",
+ Text = "",
+ AutoButtonColor = false,
+ Active = true,
+ Visible = true,
+ Size = UDim2.new(1,0,1,0),
+ BackgroundColor3 = Color3I(51,51,51),
+ BorderColor3 = Color3I(27,42,53),
+ BackgroundTransparency = 1,
+}
+
+local ReportAbuseFrame = Obj.Create "Frame"
+{
+ Name = "Settings",
+ Position = UDim2.new(0.5, - 250, 0.5, - 200),
+ Size = UDim2.new(0.0, 500, 0.0, 400),
+ BackgroundTransparency = 1,
+ Active = true,
+ Parent = ReportAbuseShield,
+}
+
+local AbuseSettingsFrame = Obj.Create"Frame"
+{
+ Name = "ReportAbuseStyle",
+ Size = UDim2.new(1, 0, 1, 0),
+ Active = true,
+ BackgroundTransparency = 1,
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96488767'), -- 96480351'),
+ Obj.Create"TextLabel"
+ {
+ Name = "Title",
+ Text = "Report Abuse",
+ TextColor3 = Color3I(221,221,221),
+ Position = UDim2.new(0.5, 0, 0, 30),
+ Font = Enum.Font.ArialBold,
+ FontSize = Enum.FontSize.Size36,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "Description",
+ Text = "This will send a complete report to a moderator. The moderator will review the chat log and take appropriate action.",
+ TextColor3 = Color3I(221,221,221),
+ Position = UDim2.new(.01, 0, 0, 55),
+ Size = UDim2.new(.99, 0, 0, 40),
+ BackgroundTransparency = 1,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ TextWrap = true,
+ TextXAlignment = Enum.TextXAlignment.Left,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "AbuseLabel",
+ Text = "What did they do?",
+ Font = Enum.Font.Arial,
+ BackgroundTransparency = 1,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,140),
+ Size = UDim2.new(0.4,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "ShortDescriptionLabel",
+ Text = "Short Description: (optional)",
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,180),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ BackgroundTransparency = 1,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "ReportingPlayerLabel",
+ Text = "Reporting Player",
+ BackgroundTransparency = 1,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,100),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ Parent = AbuseSettingsFrame
+ },
+
+ Parent = ReportAbuseFrame,
+}
+
+local AbusePlayerLabel = Obj.Create"TextLabel"
+{
+ Name = "PlayerLabel",
+ Text = "",
+ BackgroundTransparency = 1,
+ Font = Enum.Font.ArialBold,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,100),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Right,
+ Parent = AbuseSettingsFrame
+}
+
+local SubmitReportButton = Obj.Create"ImageButton"
+{
+ Name = "SubmitReportBtn",
+ Active = false,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.5, - 200, 1, - 80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = false,
+ Image = 'http://www.roblox.com/asset/?id=96502438', -- 96501119',
+ Parent = AbuseSettingsFrame,
+}
+
+local CancelReportButton = Obj.Create"ImageButton"
+{
+ Name = "CancelBtn",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, 50, 1, - 80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96500683',
+ Parent = AbuseSettingsFrame,
+}
+
+local AbuseDescriptionWrapper = Obj.Create"Frame"
+{
+ Name = "AbuseDescriptionWrapper",
+ Position = UDim2.new(0.025,0,0,220),
+ Size = UDim2.new(0.95,0,1, - 310),
+ BackgroundColor3 = Color3I(0,0,0),
+ BorderSizePixel = 0,
+ Parent = AbuseSettingsFrame,
+}
+
+local AbuseDescriptionBox
+
+local OriginalAbuseDescriptionBox = Obj.Create"TextBox"
+{
+ Name = "TextBox",
+ Text = "",
+ ClearTextOnFocus = false,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0,3,0,3),
+ Size = UDim2.new(1, - 6,1, - 6),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ TextWrap = true,
+ BackgroundColor3 = Color3I(0,0,0),
+ BorderSizePixel = 0,
+}
+
+local CalmingAbuseBox = Obj.Create'Frame'
+{
+ Name = 'AbuseFeedbackBox',
+ BackgroundTransparency = 1,
+ Position=UDim2.new(0.25, 0, 0.300000012, 0),
+ Size=UDim2.new(0.5, 0, 0.370000005, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96506233'),
+ Obj.Create'TextLabel'
+ {
+ Name = 'Header',
+ Position=UDim2.new(0,10,.05,0),
+ Size=UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextXAlignment = Enum.TextXAlignment.Center,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ Text = 'Thanks for your report!',
+ TextColor3 = Color3.new(1,1,1),
+ FontSize = Enum.FontSize.Size48,
+ Font = 'ArialBold',
+ },
+ Obj.Create'TextLabel'
+ {
+ Name = 'content',
+ Position = UDim2.new(0,10,.20,0),
+ Size = UDim2.new(1, -30, .40, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ Text = 'Our moderators will review the chat logs and determine what happened. The other user is probably just trying to make you mad.\n\nIf anyone used swear words, inappropriate language, or threatened you in real life, please report them for Bad Words or Threats',
+ TextWrapped = true,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ FontSize = Enum.FontSize.Size24,
+ Font = 'Arial',
+ },
+ Obj.Create'ImageButton'
+ {
+ Name = "OkButton",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, -75, 1, -80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96507959',
+ }
+}
+local NormalAbuseBox = Obj.Create'Frame'
+{
+ Name = 'AbuseFeedbackBox',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.25, 0, 0.300000012, 0),
+ Size = UDim2.new(0.5, 0, 0.370000005, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96506233'),
+ Obj.Create'TextLabel'
+ {
+ Name = 'Header',
+ Position = UDim2.new(0,10,.05,0),
+ Size = UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = Enum.TextXAlignment.Center,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ Text = 'Thanks for your report!',
+ FontSize = Enum.FontSize.Size48,
+ Font ='ArialBold'
+ },
+ Obj.Create'TextLabel'
+ {
+ Name = 'content',
+ Position = UDim2.new(0,10,.20,0),
+ Size = UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ Text = "Our moderators will review the chat logs and determine what happened.",
+ TextWrapped = true,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ FontSize = Enum.FontSize.Size24,
+ Font = 'Arial',
+ },
+ Obj.Create'ImageButton'
+ {
+ Name = "OkButton",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, -75, 1, -80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96507959',
+ },
+}
+
+local BigButton=Instance.new('ImageButton')
+ BigButton.Size=UDim2.new(1,0,1,0)
+ BigButton.BackgroundTransparency=1
+ BigButton.ZIndex=8
+ BigButton.Visible=false
+ --BigButton.Active=false
+ BigButton.Parent=ScreenGui
+
+
+ local debugFrame = Obj.Create"Frame"
+ {
+ Name = 'debugframe',
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(0, 150, 0, 800),--0.99000001
+ BackgroundTransparency = 1,
+
+ }
+ local debugplayers = Obj.Create"TextLabel"
+ {
+ BackgroundTransparency = .8,
+ Position = UDim2.new(0, 0, .01, 0),
+ Size = UDim2.new(1,0,.5,0),
+ Parent = debugFrame,
+ Font = 'ArialBold',
+ Text = '--',
+ FontSize='Size14',
+ TextWrapped=true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+ local debugOutput = Obj.Create"TextLabel"
+ {
+ BackgroundTransparency = .8,
+ Position = UDim2.new(0, 0, .5, 0),
+ Size = UDim2.new(1,0,.5,0),
+ Parent = debugFrame,
+ Font = 'ArialBold',
+ Text = '--',
+ FontSize='Size14',
+ TextWrapped=true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+
+
+--[[
+ simple function to toggle the display of debug output
+--]]
+local DebugPrintEnabled=true
+function debugprint(str)
+ --print(str)
+ if DebugPrintEnabled then
+ debugOutput.Text=str
+ end
+end
+
+
+ -------------------------
+ -- Script objects
+ -------------------------
+local RbxGui = assert(LoadLibrary('RbxGui'))
+
+ -- number of entries to show if you click minimize
+local DefaultEntriesOnScreen = 8
+
+
+
+
+
+for _,i in pairs(Images) do
+ Game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id="..i)
+end
+
+ -- ordered array of 'score data', each entry has:
+ -- Name(String)
+ -- Priority(number)
+ -- IsPrimary (bool, should it be shown in upper right)
+ -- MaxLength (integer, of the length of the longest element for this column)
+local ScoreNames = {}
+ -- prevents flipping in playerlist panels
+local AddId = 0
+ -- intermediate table form of all player entries in format of:
+ -- Frame
+ -- Player
+ -- Score
+ -- ID
+ -- MyTeam (team ENRTY(not actual team) I am currently on)
+local PlayerFrames = {}
+ -- intermediate ordered frame array, composed of Entrys of
+ -- Frame
+ -- MyTeam (my team object)
+ -- MyPlayers ( an ordered array of all player frames in team )
+ -- AutoHide (bool saying whether it should be hidden)
+ -- IsHidden (bool)
+ -- ID (int to prevent flipping out of leaderboard, fun times)
+local TeamFrames = {}
+ -- one special entry from teamFrames, for unaffiliated players, only shown if players non - empty
+local NeutralTeam = nil
+
+ -- final 'to be displayed' list of frames
+local MiddleFrames = {}
+local MiddleFrameBackgrounds = {}
+local MiddleFrameHeight = .03
+ -- time of last click
+local LastClick = 0
+local ButtonCooldown = .25
+
+local OnIos = false
+pcall(function() OnIos = Game:GetService('UserInputService').TouchEnabled end)
+
+
+ -- you get 200 of x screen space per stat added, start width 16%
+local BaseScreenXSize = 150
+local SpacingPerStat = 10 --spacing between stats
+
+
+local MaximizedBounds = UDim2.new(.5,0,1,0)
+local MaximizedPosition = UDim2.new(.25,0,.1,0)
+local NormalBounds = UDim2.new(0,BaseScreenXSize, 0, 800)
+local NormalPosition = UDim2.new(1 , - BaseScreenXSize, 0.005, 0)
+
+local MinimizedBounds = UDim2.new(0, BaseScreenXSize, 0.99000001, 0)
+
+--free space to give last stat on the right
+local RightEdgeSpace = -.04
+
+ -- where the scroll par currently is positioned
+local ScrollPosition = 0.75999999
+local IsDragging = false -- am I dragging the player list
+
+local DefaultBottomClipPos = BottomClipFrame.Position.Y.Scale
+
+local LastSelectedPlayerEntry = nil
+local SelectedPlayerEntry = nil
+local SelectedPlayer = nil
+
+ -- locks(semaphores) for stopping race conditions
+local AddingFrameLock = false
+local ChangingOrderLock = false
+local AddingStatLock = false
+local BaseUpdateLock = false
+local WaitForClickLock = false
+local InPopupWaitForClick=false
+local PlayerChangedLock = false
+local NeutralTeamLock = false
+
+local ScrollWheelConnections = {}
+
+
+local DefaultListSize = 15
+if not OnIos then DefaultListSize = 24 end
+local DidMinimizeDrag = false
+
+--local PlaceCreatorId=game.CreatorId
+
+ -- report abuse objects
+local AbuseName
+local Abuses = {
+ "Bad Words or Threats",
+ "Bad Username",
+ "Talking about Dating",
+ "Account Trading or Sharing",
+ "Asking Personal Questions",
+ "Rude or Mean Behavior",
+ "False Reporting Me"
+}
+local UpdateAbuseFunction
+local AbuseDropDown, UpdateAbuseSelection
+
+local PrivilegeLevel =
+{
+ Owner = 255,
+ Admin = 240,
+ Member = 128,
+ Visitor = 10,
+ Banned = 0,
+}
+
+
+local IsPersonalServer = not not game.Workspace:FindFirstChild("PSVariable")
+
+game.Workspace.ChildAdded:connect(function(nchild)
+ if nchild.Name=='PSVariable' and nchild:IsA('BoolValue') then
+ IsPersonalServer=true
+ end
+end)
+ -------------------------------
+ -- Static Functions
+ -------------------------------
+function GetTotalEntries()
+ return math.min(#MiddleFrameBackgrounds,DefaultEntriesOnScreen)
+end
+
+function GetEntryListLength()
+ local numEnts=#PlayerFrames+#TeamFrames
+ if NeutralTeam then
+ numEnts=numEnts+1
+ end
+ return numEnts
+end
+
+function AreAllEntriesOnScreen()
+ return #MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale <= 1 + DefaultBottomClipPos
+end
+
+function GetLengthOfVisbleScroll()
+ return 1 + DefaultBottomClipPos
+end
+
+function GetMaxScroll()
+ return DefaultBottomClipPos * - 1
+end
+ -- can be optimized by caching when this varible changes
+function GetMinScroll()
+ if AreAllEntriesOnScreen() then
+ return GetMaxScroll()
+ else
+ return (GetMaxScroll() - (#MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale)) + (1 + DefaultBottomClipPos)
+ end
+end
+
+function AbsoluteToPercent(x,y)
+ return Vector2.new(x,y)/ScreenGui.AbsoluteSize
+end
+--[[
+ tweens property of element from starta to enda over length of time
+ Warning: should be put in a Spawn call
+ @Args:
+ element textobject to tween transparency on
+ propName
+ starta alpha to start tweening
+ enda alpha to end tweening on
+ length how many seconds to spend tweening
+--]]
+function TweenProperty(obj, propName, inita, enda, length)
+ local startTime = tick()
+ while tick()-startTimenrank do
+ game:GetService("PersonalServerService"):Demote(player)
+ end
+end
+--[[
+ called when player selects new privilege level from popup menu
+ @Args:
+ player player to set privileges on
+ nlevel new privilege level for this player
+--]]
+function OnPrivilegeLevelSelect(player,nlevel,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ debugprint('setting privilege level')
+ SetPrivilegeRank(player,nlevel)
+ HighlightMyRank(player,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+end
+
+--[[
+ Highlights current rank of this player in the popup menu
+ @Args:
+ player Player to check for rank on
+--]]
+function HighlightMyRank(player,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ BanPlayerButton.Image= 'http://www.roblox.com/asset/?id='..Images['LightPopupMid']
+ VisitorButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkPopupMid']
+ MemberButton.Image= 'http://www.roblox.com/asset/?id='..Images['LightPopupMid']
+ AdminButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkPopupBottom']
+
+ local rank=player.PersonalServerRank
+ if rank <= PrivilegeLevel['Banned'] then
+ BanPlayerButton.Image='http://www.roblox.com/asset/?id='..Images['LightBluePopupMid']
+ elseif rank <= PrivilegeLevel['Visitor'] then
+ VisitorButton.Image='http://www.roblox.com/asset/?id='..Images['DarkBluePopupMid']
+ elseif rank <= PrivilegeLevel['Member'] then
+ MemberButton.Image='http://www.roblox.com/asset/?id='..Images['LightBluePopupMid']
+ elseif rank <= PrivilegeLevel['Admin'] then
+ AdminButton.Image= 'http://www.roblox.com/asset/?id='..Images['DarkBluePopupBottom']
+ end
+end
+
+ --------------------------
+ -- Report abuse handling
+ --------------------------
+--[[
+ does final reporting of abuse on selected player, calls closeAbuseDialog
+--]]
+function OnSubmitAbuse()
+ if SubmitReportButton.Active then
+ if AbuseName and SelectedPlayer then
+ AbuseSettingsFrame.Visible = false
+ game.Players:ReportAbuse(SelectedPlayer, AbuseName, AbuseDescriptionBox.Text)
+ if AbuseName == "Rude or Mean Behavior" or AbuseName == "False Reporting Me" then
+ CalmingAbuseBox.Parent = ReportAbuseShield
+ else
+ debugprint('opening abuse box')
+ NormalAbuseBox.Parent = ReportAbuseShield
+ end
+ else
+ CloseAbuseDialog()
+ end
+ end
+end
+
+--[[
+ opens the abuse dialog, initialises text to display selectedplayer
+--]]
+function OpenAbuseDialog()
+ debugprint('adding report dialog')
+ AbusePlayerLabel.Text = SelectedPlayer.Name
+ --AbuseDescriptionBox.Text = ""
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ AbuseDescriptionBox=OriginalAbuseDescriptionBox:Clone()
+ AbuseDescriptionBox.Parent = AbuseDescriptionWrapper
+ ReportAbuseShield.Parent = ScreenGui
+ ClosePopUpPanel()
+end
+--[[
+ resets and closes abuse dialog
+--]]
+function CloseAbuseDialog()
+ AbuseName = nil
+ SubmitReportButton.Active = false
+ SubmitReportButton.Image = 'http://www.roblox.com/asset/?id=96502438' -- 96501119',
+ AbuseDescriptionBox:Destroy()
+ CalmingAbuseBox.Parent = nil
+ NormalAbuseBox.Parent = nil
+ ReportAbuseShield.Parent = nil
+ AbuseSettingsFrame.Visible = true
+end
+
+--[[
+ creates dropdownbox, registers all listeners for abuse dialog
+--]]
+function InitReportAbuse()
+
+ UpdateAbuseFunction = function(abuseText)
+ AbuseName = abuseText
+ if AbuseName and SelectedPlayer then
+ SubmitReportButton.Active = true
+ SubmitReportButton.Image = 'http://www.roblox.com/asset/?id=96501119'
+ end
+ end
+
+ AbuseDropDown, UpdateAbuseSelection = RbxGui.CreateDropDownMenu(Abuses, UpdateAbuseFunction, true)
+ AbuseDropDown.Name = "AbuseComboBox"
+ AbuseDropDown.Position = UDim2.new(0.425, 0, 0, 142)
+ AbuseDropDown.Size = UDim2.new(0.55,0,0,32)
+ AbuseDropDown.Parent = AbuseSettingsFrame
+
+
+ CancelReportButton.MouseButton1Click:connect(CloseAbuseDialog)
+ SubmitReportButton.MouseButton1Click:connect(OnSubmitAbuse)
+
+ CalmingAbuseBox:FindFirstChild('OkButton').MouseButton1Down:connect(CloseAbuseDialog)
+ NormalAbuseBox:FindFirstChild('OkButton').MouseButton1Down:connect(CloseAbuseDialog)
+end
+
+-------------------------------------
+-- Friend/unfriending
+-------------------------------------
+--[[
+ gets enum val of friend status, uses pcall for some reason?(from old playerlist)
+ @Args:
+ player player object to check if friends with
+ @Return: enum of friend status
+--]]
+local function GetFriendStatus(player)
+ if player == game.Players.LocalPlayer then
+ return Enum.FriendStatus.NotFriend
+ else
+ local success, result = pcall(function() return game.Players.LocalPlayer:GetFriendStatus(player) end)
+ if success then
+ return result
+ else
+ return Enum.FriendStatus.NotFriend
+ end
+ end
+end
+
+--[[
+ when friend button is clicked, tries to take appropriate action,
+ based on current friend status with SelectedPlayer
+--]]
+function OnFriendButtonSelect()
+
+ local friendStatus=GetFriendStatus(SelectedPlayer)
+ if friendStatus==Enum.FriendStatus.Friend then
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.Unknown or friendStatus==Enum.FriendStatus.NotFriend then
+ LocalPlayer:RequestFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.FriendRequestSent then
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ elseif friendStatus==Enum.FriendStatus.FriendRequestReceived then
+ LocalPlayer:RequestFriendship(SelectedPlayer)
+ end
+ --PersonalServerPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Quad", .5,true)
+ ClosePopUpPanel()
+ --PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+end
+
+function OnFriendRefuseButtonSelect()
+
+
+ LocalPlayer:RevokeFriendship(SelectedPlayer)
+ ClosePopUpPanel()
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+end
+------------------------------------
+-- Player Entry Handling
+------------------------------------
+--[[
+ used by lua's table.sort to sort player entries
+--]]
+function PlayerSortFunction(a,b)
+ -- prevents flipping out leaderboard
+ if a['Score'] == b['Score'] then
+ return a['Player'].Name:upper() > b['Player'].Name:upper()
+ end
+ if not a['Score'] then return false end
+ if not b['Score'] then return true end
+ return a['Score'] < b['Score']
+end
+
+ ---------------------------------
+ -- Stat Handling
+ ---------------------------------
+ -- removes and closes all leaderboard stuffs
+function BlowThisPopsicleStand()
+ --ScreenGui:Destroy()
+ --script:Destroy()
+ --time to make the fanboys rage...
+ Tabify()
+end
+--[[
+ used by lua's table.sort to prioritize score entries
+--]]
+function StatSort(a,b)
+ -- primary stats should be shown before all others
+ if a.IsPrimary ~= b.IsPrimary then
+ return a.IsPrimary
+ end
+ -- if priorities are equal, then return the first added one
+ if a.Priority == b.Priority then
+ return a.AddId < b.AddId
+ end
+ return a.Priority < b.Priority
+end
+--[[
+ doing WAAY too much here, for optimization update only your team
+ @Args:
+ playerEntry Entry of player who had a stat change
+ property Name of stat changed
+--]]
+function StatChanged(playerEntry,property)
+
+ -- if(playerEntry['MyTeam']) then
+ -- UpdateSingleTeam(playerEntry['MyTeam'])
+ -- else
+ BaseUpdate()
+ -- end
+end
+--[[
+ Called when stat is added
+ if playerEntry is localplayer, will add to score names and re-sort the stats, and resize the width of the leaderboard
+ for all players, will add a listener for if this stat changes
+ if stat is a string value, crashes the leaderboard
+ Note:change crash to a 'tabify' leaderboard later
+ @Args:
+ nchild new child value to leaderstats
+ playerEntry entry this stat was added to
+--]]
+function StatAdded(nchild,playerEntry)
+ -- dont re - add a leaderstat I alreday have
+ while AddingStatLock do debugprint('in stat added function lock') wait(1/30) end
+ AddingStatLock = true
+ if not (nchild:IsA('StringValue') or nchild:IsA('IntValue') or nchild:IsA('BoolValue') or nchild:IsA('NumberValue') or nchild:IsA('DoubleConstrainedValue') or nchild:IsA('IntConstrainedValue')) then
+ BlowThisPopsicleStand()
+ else
+ local haveScore = false
+ for _,i in pairs(ScoreNames) do
+ if i['Name']==nchild.Name then haveScore=true end
+ end
+ if not haveScore then
+ local nstat = {}
+ nstat['Name'] = nchild.Name
+ nstat['Priority'] = 0
+ if(nchild:FindFirstChild('Priority')) then
+ nstat['Priority'] = nchild.Priority
+ end
+ nstat['IsPrimary'] = false
+ if(nchild:FindFirstChild('IsPrimary')) then
+ nstat['IsPrimary'] = true
+ end
+ nstat.AddId = AddId
+ AddId = AddId + 1
+ table.insert(ScoreNames,nstat)
+ table.sort(ScoreNames,StatSort)
+ if not StatTitles:FindFirstChild(nstat['Name']) then
+ CreateStatTitle(nstat['Name'])
+ end
+ UpdateMaximize()
+
+ end
+ end
+ AddingStatLock = false
+ StatChanged(playerEntry)
+ nchild.Changed:connect(function(property) StatChanged(playerEntry,property) end)
+
+
+end
+--returns whether any of the existing players has this stat
+function DoesStatExist(statName, exception)
+ for _,playerf in pairs(PlayerFrames) do
+ if playerf['Player'] ~= exception and playerf['Player']:FindFirstChild('leaderstats') and playerf['Player'].leaderstats:FindFirstChild(statName) then
+ --print('player:' .. playerf['Player'].Name ..' has stat')
+ return true
+ end
+ end
+ return false
+end
+
+
+
+--[[
+ Called when stat is removed from player
+ for all players, destroys the stat frame associated with this value,
+ then calls statchanged(to resize frame)
+ if playerEntry==localplayer, will remove from scorenames
+ @Args:
+ nchild ___value to be removed
+ playerEntry entry of player value is being removed from
+--]]
+function StatRemoved(nchild,playerEntry)
+ while AddingStatLock do debugprint('In Adding Stat Lock1') wait(1/30) end
+ AddingStatLock = true
+ if playerEntry['Frame']:FindFirstChild(nchild.Name) then
+ debugprint('Destroyed frame!')
+ playerEntry['Frame'][nchild.Name].Parent = nil
+ end
+ if not DoesStatExist(nchild.Name, playerEntry['Player']) then
+ for i,val in ipairs(ScoreNames) do
+ if val['Name'] == nchild.Name then
+ table.remove(ScoreNames,i)
+ if StatTitles:FindFirstChild(nchild.Name) then
+ StatTitles[nchild.Name]:Destroy()
+ end
+ for _,teamf in pairs(TeamFrames) do
+ if teamf['Frame']:FindFirstChild(nchild.Name) then
+ teamf['Frame'][nchild.Name]:Destroy()
+ end
+ end
+ end
+ end
+ end
+ AddingStatLock = false
+ StatChanged(playerEntry)
+end
+--[[
+ clears all stats from a given playerEntry
+ resets the HeadScore's Text property to an empty string
+ used when leaderstats are removed, or when new leaderstats are added(for weird edge case)+
+--]]
+function RemoveAllStats(playerEntry)
+ for i,val in ipairs(ScoreNames) do
+ StatRemoved(val,playerEntry)
+ end HeaderScore.Text = ''
+
+end
+
+
+function GetScoreValue(score)
+ if score:IsA('DoubleConstrainedValue') or score:IsA('IntConstrainedValue') then
+ return score.ConstrainedValue
+ elseif score:IsA('BoolValue') then
+ if score.Value then return 1 else return 0 end
+ else
+ return score.Value
+ end
+end
+--[[
+
+--]]
+function MakeScoreEntry(entry,scoreval,panel)
+ if not panel:FindFirstChild('PlayerScore') then return end
+ local nscoretxt = panel:FindFirstChild('PlayerScore'):Clone()
+ local thisScore = nil
+ --here lies the resting place of a once great and terrible bug
+ --may its treachery never be forgoten, lest its survivors fall for it again
+ --RIP the leaderstat bug, oct 2012-nov 2012
+ wait()
+ if entry['Player']:FindFirstChild('leaderstats') and entry['Player'].leaderstats:FindFirstChild(scoreval['Name']) then
+ thisScore = entry['Player']:FindFirstChild('leaderstats'):FindFirstChild(scoreval['Name'])
+ else
+ return
+ end
+
+ if not entry['Player'].Parent then return end
+
+ nscoretxt.Name = scoreval['Name']
+ nscoretxt.Text = tostring(GetScoreValue(thisScore))
+ if scoreval['Name'] == ScoreNames[1]['Name'] then
+ debugprint('changing score')
+ entry['Score'] = GetScoreValue(thisScore)
+ if entry['Player'] == LocalPlayer then HeaderScore.Text = tostring(GetScoreValue(thisScore)) end
+ end
+
+ thisScore.Changed:connect(function()
+ if not thisScore.Parent then return end
+ if scoreval['Name'] == ScoreNames[1]['Name'] then
+
+ entry['Score'] = GetScoreValue(thisScore)
+ if entry['Player'] == LocalPlayer then HeaderScore.Text = tostring(GetScoreValue(thisScore)) end
+ end
+ nscoretxt.Text = tostring(GetScoreValue(thisScore))
+ BaseUpdate()
+ end)
+ return nscoretxt
+
+end
+
+function CreateStatTitle(statName)
+
+ local ntitle = MiddleTemplate:FindFirstChild('PlayerScore'):Clone()
+ ntitle.Name = statName
+ ntitle.Text = statName
+ -- ntitle
+ if IsMaximized.Value then
+ ntitle.TextTransparency = 0
+ else
+ ntitle.TextTransparency = 1
+ end
+ ntitle.Parent = StatTitles
+end
+
+function RecreateScoreColumns(ptable)
+ while AddingStatLock do debugprint ('In Adding Stat Lock2') wait(1/30) end
+ AddingStatLock = true
+ local Xoffset=5--15 --current offset from Right
+ local maxXOffset=Xoffset
+ local MaxSizeColumn=0 --max size for this column
+
+ -- foreach known leaderstat
+ for j = #ScoreNames, 1,-1 do
+ local scoreval = ScoreNames[j]
+
+ MaxSizeColumn=0
+ -- for each entry in this player table
+ for i,entry in ipairs(ptable) do
+ local panel = entry['Frame']
+ local tplayer = entry['Player']
+ -- if this panel does not have an element named after this stat
+ if not panel:FindFirstChild(scoreval['Name']) then
+ -- make an entry for this object
+ local nentry = MakeScoreEntry(entry,scoreval,panel)
+ if nentry then
+ debugprint('adding '..nentry.Name..' to '..entry['Player'].Name )
+ nentry.Parent = panel
+ -- add score to team
+ if entry['MyTeam'] and entry['MyTeam'] ~= NeutralTeam and not entry['MyTeam']['Frame']:FindFirstChild(scoreval['Name']) then
+ local ntitle = nentry:Clone()
+ --ntitle.TextXAlignment = 'Right'
+ ntitle.Parent = entry['MyTeam']['Frame']
+ end
+
+ end
+ end
+ scoreval['XOffset']=Xoffset
+
+ if panel:FindFirstChild(scoreval['Name']) then
+ MaxSizeColumn=math.max(MaxSizeColumn,panel[scoreval['Name']].TextBounds.X)
+ end
+ end
+
+ if AreNamesExpanded.Value then
+ MaxSizeColumn=math.max(MaxSizeColumn,StatTitles[scoreval['Name'] ].TextBounds.X)
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new(RightEdgeSpace,-Xoffset,0,0),'Out','Linear',BASE_TWEEN,true)
+ else
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new((.4+((.6/#ScoreNames)*(j-1)))-1,0,0,0),'Out','Linear',BASE_TWEEN,true)
+ end
+ scoreval['ColumnSize']=MaxSizeColumn
+ Xoffset= Xoffset+SpacingPerStat+MaxSizeColumn
+ maxXOffset=math.max(Xoffset,maxXOffset)
+ end
+ NormalBounds = UDim2.new(0, BaseScreenXSize+maxXOffset-SpacingPerStat,0,800)
+ NormalPosition = UDim2.new(1 , -NormalBounds.X.Offset, NormalPosition.Y.Scale, 0)
+ UpdateHeaderNameSize()
+ UpdateMaximize()
+
+ AddingStatLock = false
+end
+ ---------------------------
+ -- Minimizing and maximizing
+ ---------------------------
+
+function ToggleMinimize()
+ IsMinimized.Value = not IsMinimized.Value
+ UpdateStatNames()
+end
+
+function ToggleMaximize()
+ IsMaximized.Value = not IsMaximized.Value
+ RecreateScoreColumns(PlayerFrames) --done to re-position stat names NOTE: optimize-able
+end
+
+function Tabify()
+ IsTabified.Value= true
+ IsMaximized.Value=false
+ IsMinimized.Value=true
+ UpdateMinimize()
+ IsTabified.Value= true
+ ScreenGui:TweenPosition(UDim2.new(NormalBounds.X.Scale, NormalBounds.X.Offset-10, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+end
+
+function UnTabify()
+ if IsTabified.Value then
+ IsTabified.Value= false
+ ScreenGui:TweenPosition(UDim2.new(0, 0, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+end
+
+--[[
+ Does more than it looks like
+ monitors positions of the clipping frames and bottom frames
+ called from EVERYWHERE, too much probably
+--]]
+function UpdateMinimize()
+
+ if IsMinimized.Value then
+ if IsMaximized.Value then
+ ToggleMaximize()
+ end
+ if not IsTabified.Value then
+ MainFrame.Size = UDim2.new(0.010, HeaderName.TextBounds.X, NormalBounds.Y.Scale,NormalBounds.Y.Offset)
+ MainFrame.Position = UDim2.new(.990, -HeaderName.TextBounds.X, NormalPosition.Y.Scale,0)
+ else
+ MainFrame.Size = NormalBounds
+ MainFrame.Position = NormalPosition
+ end
+ --(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale)
+ BottomClipFrame.Position = UDim2.new(0,0,-1,0)
+ BottomFrame.Position = UDim2.new(0,0,0,0)
+ FocusFrame.Size=UDim2.new(1,0,HeaderFrameHeight,0)
+ ExtendTab.Image = 'rbxasset://textures/ui/expandPlayerList.png'
+ else
+ if not IsMaximized.Value then
+ MainFrame.Size = NormalBounds
+ MainFrame.Position = NormalPosition
+ end
+ --do limiting
+ DefaultBottomClipPos = math.min(math.max(DefaultBottomClipPos,-1),-1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale))
+ UpdateScrollPosition()
+
+ BottomClipFrame.Position=UDim2.new(0,0,DefaultBottomClipPos,0)
+ local bottomPositon = (DefaultBottomClipPos+BottomClipFrame.Size.Y.Scale)
+ BottomFrame.Position=UDim2.new(0,0,bottomPositon,0)
+ FocusFrame.Size=UDim2.new(1,0,bottomPositon + HeaderFrameHeight,0)
+ ExtendTab.Image = 'rbxasset://textures/ui/expandPlayerList.png'
+ end
+end
+
+--[[
+ Manages the position/size of the mainFrame, swaps out different resolution images for the frame
+ fades in and out the stat names, moves position of headername and header score
+--]]
+function UpdateMaximize()
+ if IsMaximized.Value then
+ for j = 1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ StatTitles[scoreval['Name'] ]:TweenPosition(UDim2.new(.4+((.6/#ScoreNames)*(j-1))-1,0,0,0),'Out','Linear',BASE_TWEEN,true)
+ end
+
+ if IsMinimized.Value then
+ ToggleMinimize()
+ else
+ UpdateMinimize()
+ end
+
+
+ MainFrame:TweenSizeAndPosition(MaximizedBounds,MaximizedPosition,'Out','Linear',BASE_TWEEN*1.2,true)
+ HeaderScore:TweenPosition(UDim2.new(0,0,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ HeaderName:TweenPosition(UDim2.new( - .1, - HeaderScore.TextBounds.x,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ for index, i in ipairs(MiddleFrames) do
+
+ if i:FindFirstChild('ClickListener') then
+ i.ClickListener.Size = UDim2.new(1,-2,i.ClickListener.Size.Y.Scale, i.ClickListener.Size.Y.Offset)
+ end
+
+ for j=1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ if i:FindFirstChild(scoreval['Name']) then
+ i[scoreval['Name']]:TweenPosition(UDim2.new(.4+((.6/#ScoreNames)*(j-1))-1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ end
+ end
+ end
+ for i,entry in ipairs(PlayerFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(.38,0,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+
+ for i,entry in ipairs(TeamFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(.38,0,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+
+ else
+ if not IsMinimized.Value then
+ MainFrame:TweenSizeAndPosition(NormalBounds,NormalPosition,'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+ HeaderScore:TweenPosition(UDim2.new(0,0,.4,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ HeaderName:TweenPosition(UDim2.new(0,0,HeaderName.Position.Y.Scale,0), "Out", "Linear", BASE_TWEEN*1.2,true)
+ for index, i in ipairs(MiddleFrames) do
+ if i:FindFirstChild('ClickListener') then
+ i.ClickListener.Size = UDim2.new(1, -2,i.ClickListener.Size.Y.Scale, i.ClickListener.Size.Y.Offset)
+ for j=1, #ScoreNames,1 do
+ local scoreval = ScoreNames[j]
+ if i:FindFirstChild(scoreval['Name']) and scoreval['XOffset'] then
+ --print('updateing stat position: ' .. scoreval['Name'])
+ i[scoreval['Name']]:TweenPosition(UDim2.new(RightEdgeSpace,-scoreval['XOffset'],0,0), "Out", "Linear", BASE_TWEEN,true)
+ end
+ end
+ end
+ end
+
+ for i,entry in ipairs(TeamFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(0,BaseScreenXSize*.9,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+
+ end
+ for i,entry in ipairs(PlayerFrames) do
+ WaitForChild(entry['Frame'],'TitleFrame').Size=UDim2.new(0,BaseScreenXSize*.9,entry['Frame'].TitleFrame.Size.Y.Scale,0)
+ end
+ end
+end
+
+function UpdateStatNames()
+ if not AreNamesExpanded.Value or IsMinimized.Value then
+ CloseNames()
+ else
+ ExpandNames()
+ end
+end
+
+function ExpandNames()
+ if #ScoreNames ~= 0 then
+ for _,i in pairs(StatTitles:GetChildren()) do
+ Spawn(function()TweenProperty(i,'TextTransparency',i.TextTransparency,0,BASE_TWEEN) end)
+ end
+ HeaderFrameHeight=.09
+ --as of writing, this and 'CloseNames' are the only places headerframe is resized
+ HeaderFrame:TweenSizeAndPosition(UDim2.new(HeaderFrame.Size.X.Scale, HeaderFrame.Size.X.Offset, HeaderFrameHeight,0),
+ HeaderFrame.Position,'Out','Linear',BASE_TWEEN*1.2,true)
+ TopClipFrame:TweenPosition(UDim2.new(TopClipFrame.Position.X.Scale,0,HeaderFrameHeight,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ BottomShiftFrame:TweenPosition(UDim2.new(0,0,HeaderFrameHeight,0), "Out", 'Linear', BASE_TWEEN*1.2,true)
+
+ end
+
+end
+
+function CloseNames()
+ if #ScoreNames ~= 0 then
+ HeaderFrameHeight=.07
+ if not (IsMaximized.Value) then
+ for _,i in pairs(StatTitles:GetChildren()) do
+ Spawn(function()TweenProperty(i,'TextTransparency',i.TextTransparency,1,BASE_TWEEN) end)
+ end
+ end
+ BottomShiftFrame:TweenPosition(UDim2.new(0,0,HeaderFrameHeight,0), "Out", 'Linear', BASE_TWEEN*1.2,true)
+ HeaderFrame:TweenSizeAndPosition(UDim2.new(HeaderFrame.Size.X.Scale, HeaderFrame.Size.X.Offset, HeaderFrameHeight,0),
+ HeaderFrame.Position,'Out','Linear',BASE_TWEEN*1.2,true)
+ TopClipFrame:TweenPosition(UDim2.new(TopClipFrame.Position.X.Scale,0,HeaderFrameHeight,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ end
+end
+
+function OnScrollWheelMove(direction)
+ if not (IsTabified.Value or IsMinimized.Value or InPopupWaitForClick) then
+ local StartFrame = ListFrame.Position
+ local newFrameY = math.max(math.min(StartFrame.Y.Scale + (direction),GetMaxScroll()),GetMinScroll())
+
+ ListFrame.Position = UDim2.new(StartFrame.X.Scale,StartFrame.X.Offset,newFrameY,StartFrame.Y.Offset)
+ UpdateScrollPosition()
+ end
+end
+
+function AttachScrollWheel()
+ if ScrollWheelConnections then return end
+ ScrollWheelConnections = {}
+ table.insert(ScrollWheelConnections,Mouse.WheelForward:connect(function()
+ OnScrollWheelMove(.05)
+ end))
+ table.insert(ScrollWheelConnections,Mouse.WheelBackward:connect(function()
+ OnScrollWheelMove(-.05)
+ end))
+end
+
+function DetachScrollWheel()
+ if ScrollWheelConnections then
+ for _,i in pairs(ScrollWheelConnections) do
+ i:disconnect()
+ end
+ end
+ ScrollWheelConnections=nil
+end
+
+FocusFrame.MouseEnter:connect(function()
+ if not (IsMinimized.Value or IsTabified.Value) then
+ AttachScrollWheel()
+ end
+end)
+FocusFrame.MouseLeave:connect(function()
+ --if not (IsMaximized.Value or IsMinimized.Value) then
+ DetachScrollWheel()
+ --end
+end)
+
+ ------------------------
+ -- Scroll Bar functions
+ ------------------------
+--[[
+ updates whether the scroll bar should be showing, if it is showing, updates
+ the size of it
+--]]
+function UpdateScrollBarVisibility()
+ if AreAllEntriesOnScreen() then
+ ScrollBar.BackgroundTransparency = 1
+ else
+ ScrollBar.BackgroundTransparency = 0
+ UpdateScrollBarSize()
+ end
+end
+--[[
+ updates size of scrollbar depending on how many entries exist
+--]]
+function UpdateScrollBarSize()
+ local entryListSize = #MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale
+ local shownAreaSize = ((BottomClipFrame.Position.Y.Scale) + 1)
+ ScrollBar.Size = UDim2.new(1,0,shownAreaSize/entryListSize,0)
+
+end
+--[[
+ updates position of listframe so that no gaps at the bottom or top of the list are visible
+ updates position of scrollbar to match what parts of the list are visible
+--]]
+function UpdateScrollPosition()
+ local minPos = GetMinScroll()
+ local maxPos = GetMaxScroll()
+ local scrollLength = maxPos - minPos
+
+ local yscrollpos=math.max(math.min(ListFrame.Position.Y.Scale,maxPos),minPos)
+ ListFrame.Position=UDim2.new(ListFrame.Position.X.Scale,ListFrame.Position.X.Offset,yscrollpos,ListFrame.Position.Y.Offset)
+
+ local adjustedLength = 1 - ScrollBar.Size.Y.Scale
+ ScrollBar.Position = UDim2.new(0,0,adjustedLength - (adjustedLength * ((ListFrame.Position.Y.Scale - minPos)/scrollLength)),0)
+end
+
+--[[
+ WARNING:this is in a working state, but uses massive hacks
+ revize when global input is available
+ Manages scrolling of the playerlist on mouse drag
+--]]
+function StartDrag(entry,startx,starty)
+ local startDragTime = tick()
+ local stopDrag = false
+ local openPanel = true
+ local draggedFrame = WaitForChild(entry['Frame'],'ClickListener')
+ local function dragExit()
+ stopDrag = true
+
+ if entry['Player'] and SelectedPlayer and openPanel
+ and (entry['Player']~=LocalPlayer and (SelectedPlayer.userId>1 and LocalPlayer.userId>1)) then
+ ActivatePlayerEntryPanel(entry)
+ end
+ end
+ local startY = nil
+ local StartFrame = ListFrame.Position
+ local function dragpoll(nx,ny)
+ if not startY then
+ startY = AbsoluteToPercent(nx,ny).Y
+ end
+ local nowY = AbsoluteToPercent(nx,ny).Y
+ debugprint('drag dist:'..Vector2.new(startx-nx,starty-ny).magnitude)
+ if Vector2.new(startx-nx,starty-ny).magnitude>MOUSE_DRAG_DISTANCE then
+ openPanel=false
+ end
+
+ local newFrameY = math.max(math.min(StartFrame.Y.Scale + (nowY - startY),GetMaxScroll()),GetMinScroll())
+ ListFrame.Position = UDim2.new(StartFrame.X.Scale,StartFrame.X.Offset,newFrameY,StartFrame.Y.Offset)
+ UpdateScrollPosition()
+ end
+ WaitForClick(ScreenGui,dragpoll,dragExit)
+end
+
+
+function StartMinimizeDrag()
+ Delay(0,function()
+ local startTime=tick()
+ debugprint('Got Click2')
+ local stopDrag = false
+ local function dragExit()
+ --debugprint('undone click2')
+ if tick()-startTime<.25 then --was click
+ ToggleMinimize()
+ else --was drag
+ if (DefaultBottomClipPos >= -1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale)) then
+ DidMinimizeDrag = false
+ else
+ DidMinimizeDrag = true
+ end
+ if IsMinimized.Value then
+ ToggleMinimize()
+ end
+ end
+ stopDrag = true
+ end
+ local startY = nil
+ local StartFrame = DefaultBottomClipPos
+ local function dragpoll(nx,ny)
+ if not IsMinimized.Value then
+
+ if not startY then
+ startY = AbsoluteToPercent(nx,ny).Y
+ end
+ local nowY = AbsoluteToPercent(nx,ny).Y
+ local newFrameY
+ newFrameY = math.min(math.max(StartFrame + (nowY - startY),-1),-1+(#MiddleFrameBackgrounds*MiddleBGTemplate.Size.Y.Scale))
+ DefaultBottomClipPos = newFrameY
+ UpdateMinimize()
+ ScrollBarFrame.Size= UDim2.new(ScrollBarFrame.Size.X.Scale,0,(DefaultBottomClipPos+BottomClipFrame.Size.Y.Scale),0)
+ ScrollBarFrame.Position= UDim2.new(ScrollBarFrame.Position.X.Scale,0,1-ScrollBarFrame.Size.Y.Scale,0)
+ UpdateScrollBarSize()
+ UpdateScrollPosition()
+ UpdateScrollBarVisibility()
+
+ end
+ end
+ Spawn(function() WaitForClick(ScreenGui,dragpoll,dragExit) end)
+ end)
+
+end
+
+ -------------------------------
+ -- Input Callback functions
+ -------------------------------
+IsMaximized.Value=false
+IsMinimized.Value=false
+IsMaximized.Changed:connect(UpdateMaximize)
+IsMinimized.Changed:connect(UpdateMinimize)
+
+ExtendButton.MouseButton1Down:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ else
+ StartMinimizeDrag()
+ end
+end)
+
+MaximizeButton.MouseButton1Click:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ elseif not AreNamesExpanded.Value then
+ AreNamesExpanded.Value = true
+ BaseUpdate()
+ else
+ ToggleMaximize()
+ end
+end)
+
+MaximizeButton.MouseButton2Click:connect(function()
+ if(time() - LastClick < ButtonCooldown) or InPopupWaitForClick then return end
+ LastClick = time()
+ if IsTabified.Value then
+ UnTabify()
+ elseif IsMaximized.Value then
+ ToggleMaximize()
+ elseif AreNamesExpanded.Value then
+ AreNamesExpanded.Value = false
+ BaseUpdate()
+ else
+ Tabify()
+ end
+end)
+
+
+-------------------------------
+-- MiddleFrames management
+-------------------------------
+--[[
+ adds a background frame to the listframe
+--]]
+function AddMiddleBGFrame()
+ local nBGFrame = MiddleBGTemplate:Clone()
+ nBGFrame.Position = UDim2.new(.5,0,((#MiddleFrameBackgrounds) * nBGFrame.Size.Y.Scale),0)
+ nBGFrame.Background.BackgroundTransparency = 1
+
+ nBGFrame.Parent = ListFrame
+ table.insert(MiddleFrameBackgrounds,nBGFrame)
+
+ if #MiddleFrameBackgrounds 1 do
+ fSize=fSize-1
+ tHeader.FontSize=FONT_SIZES[fSize]
+ wait(.2)
+ end
+ HeaderName.FontSize=tHeader.FontSize
+ tHeader:Destroy()
+ end)
+end
+ScreenGui.Changed:connect(UpdateHeaderNameSize)
+
+--[[
+ called only when the leaderstats object is added to a given player entry
+ removes old stats, adds any existing stats, and sets up listeners for new stats
+ @Args:
+ playerEntry A reference to the ENTRY(table) of the player who had leaderstats added
+--]]
+function LeaderstatsAdded(playerEntry)
+ --RemoveAllStats(playerEntry)
+ local nplayer = playerEntry['Player']
+ for _,i in pairs(nplayer.leaderstats:GetChildren()) do
+ StatAdded(i,playerEntry)
+ end
+ nplayer.leaderstats.ChildAdded:connect(function(nchild) StatAdded(nchild,playerEntry) end)
+ nplayer.leaderstats.ChildRemoved:connect(function(nchild) StatRemoved(nchild,playerEntry) end)
+end
+--[[
+ called when leaderstats object is removed from play in player entry
+ Note: may not be needed, might be able to just rely on leaderstats added
+ @Args:
+ oldLeaderstats leaderstats object to be removed
+ playerEntry A reference to the ENTRY(table) of the player
+--]]
+function LeaderstatsRemoved(oldLeaderstats,playerEntry)
+ while AddingFrameLock do debugprint('waiting to insert '..playerEntry['Player'].Name) wait(1/30) end
+ AddingFrameLock = true
+ RemoveAllStats(playerEntry)
+ AddingFrameLock = false
+end
+
+function ClosePopUpPanel()
+ if SelectedPlayerEntry then
+ local tframe = SelectedPlayerEntry['Frame']
+ Spawn(function() TweenProperty(tframe,'BackgroundTransparency',.5,1,BASE_TWEEN) end)
+ end
+ PopUpPanel:TweenPosition(UDim2.new(1,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ wait(.1)
+ InPopupWaitForClick= false
+ SelectedPlayerEntry = nil
+end
+
+--[[
+ prepares the needed popup to be tweened on screen, and updates the position of the popup clip
+ frame to match the selected player frame's position
+--]]
+function InitMovingPanel( entry, player)
+ PopUpClipFrame.Parent= ScreenGui
+
+ if PopUpPanel then
+ PopUpPanel:Destroy()
+ end
+ PopUpPanel= PopUpPanelTemplate:Clone()
+ PopUpPanel.Parent= PopUpClipFrame
+
+ local nextIndex = 2
+ local friendStatus = GetFriendStatus(player)
+ debugprint (tostring(friendStatus))
+ local showRankMenu = IsPersonalServer and LocalPlayer.PersonalServerRank >= PrivilegeLevel['Admin'] and LocalPlayer.PersonalServerRank > SelectedPlayer.PersonalServerRank
+
+
+ local ReportPlayerButton = MakePopupButton(PopUpPanel,'Report Player',0)
+ ReportPlayerButton.MouseButton1Click:connect(function() OpenAbuseDialog() end)
+
+ local enableFriendRequests = true
+
+ if enableFriendRequests then
+ local FriendPlayerButton = MakePopupButton(PopUpPanel,'Friend',1, not showRankMenu and friendStatus~=Enum.FriendStatus.FriendRequestReceived)
+ FriendPlayerButton.MouseButton1Click:connect(OnFriendButtonSelect)
+
+
+ if friendStatus==Enum.FriendStatus.Friend then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='UnFriend Player'
+ elseif friendStatus==Enum.FriendStatus.Unknown or friendStatus==Enum.FriendStatus.NotFriend then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Send Request'
+ elseif friendStatus==Enum.FriendStatus.FriendRequestSent then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Revoke Request'
+ elseif friendStatus==Enum.FriendStatus.FriendRequestReceived then
+ FriendPlayerButton:FindFirstChild('ButtonText').Text='Accept Friend'
+ local FriendRefuseButton = MakePopupButton(PopUpPanel,'Decline Friend',2,not showRankMenu)
+ FriendRefuseButton.MouseButton1Click:connect(OnFriendRefuseButtonSelect)
+ nextIndex=nextIndex+1
+ end
+ end
+
+ if showRankMenu then
+ local BanPlayerButton = MakePopupButton(PopUpPanel,'Ban',nextIndex)
+ local VisitorButton = MakePopupButton(PopUpPanel,'Visitor',nextIndex+1)
+ local MemberButton = MakePopupButton(PopUpPanel,'Member',nextIndex+2)
+ local AdminButton = MakePopupButton(PopUpPanel,'Admin',nextIndex+3,true)
+
+ BanPlayerButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Banned'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ VisitorButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Visitor'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ MemberButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Member'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+ AdminButton.MouseButton1Click:connect(function()
+ OnPrivilegeLevelSelect(player,PrivilegeLevel['Admin'],BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end)
+
+ HighlightMyRank(SelectedPlayer,BanPlayerButton,VisitorButton,MemberButton,AdminButton)
+ end
+
+ PopUpPanel:TweenPosition(UDim2.new(0,0,0,0), "Out", "Linear", BASE_TWEEN,true)
+ Delay(0, function()
+ local tconnection
+ tconnection = Mouse.Button1Down:connect(function()
+ tconnection:disconnect()
+ ClosePopUpPanel()
+ end)
+ end)
+
+ local myFrame = entry['Frame']
+ -- THIS IS GARBAGE.
+ -- if I parent to frame to auto update position, it gets clipped
+ -- sometimes garbage is the only option.
+ Spawn(function()
+ while InPopupWaitForClick do
+ PopUpClipFrame.Position=UDim2.new( 0,myFrame.AbsolutePosition.X-PopUpClipFrame.Size.X.Offset,0,myFrame.AbsolutePosition.Y)
+ wait()
+ end
+ end)
+
+end
+
+--[[
+ Called when a player entry in the leaderboard is clicked
+ either will highlight entry and start the drag event, or open a popup menu
+ @Args:
+ entry the player entry clicked
+--]]
+function OnPlayerEntrySelect(entry,startx,starty)
+
+ if not InPopupWaitForClick then
+
+ SelectedPlayerEntry = entry
+ SelectedPlayer = entry['Player']
+
+ StartDrag(entry,startx,starty)
+ end
+
+
+end
+
+function ActivatePlayerEntryPanel(entry)
+ entry['Frame'].BackgroundColor3 = Color3.new(0,1,1)
+ Spawn(function() TweenProperty(entry['Frame'],'BackgroundTransparency',1,.5,.5) end)
+ InPopupWaitForClick=true
+ InitMovingPanel(entry,entry['Player'])
+end
+
+--[[
+ the basic update for the playerlist mode's state,
+ assures the order and length of the player frames
+--]]
+function PlayerListModeUpdate()
+ RecreateScoreColumns(PlayerFrames)
+ table.sort(PlayerFrames,PlayerSortFunction)
+ for i,val in ipairs(PlayerFrames) do
+ MiddleFrames[i] = val['Frame']
+ end
+ for i = #PlayerFrames + 1,#MiddleFrames,1 do
+ MiddleFrames[i] = nil
+ end
+ UpdateMinimize()
+end
+--[[
+ this one's a doozie, happens when a player is added to the game
+ inits their player frame and player entry, assigns them to a team if possible,
+ and hooks up their leaderstats
+ @Args:
+ nplayer new player object to insert
+--]]
+function InsertPlayerFrame(nplayer)
+ while AddingFrameLock do debugprint('waiting to insert '..nplayer.Name) wait(1/30) end
+ AddingFrameLock = true
+
+ local nFrame = MiddleTemplate:Clone()
+ nFrame.ClickListener.BackgroundColor3 = Color3.new(0,0,0)
+ nFrame.ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nFrame.ClickListener.AutoButtonColor=false
+
+ local playerName = nplayer.Name
+ local clansEnabled, clanTag = pcall(function() nplayer:GetClanTag() end)
+ if clansEnabled and clanTag and clanTag ~= "" then
+ playerName = "[" .. tostring(clanTag) .. "] " .. playerName
+ end
+
+ WaitForChild(WaitForChild(nFrame,'TitleFrame'),'Title').Text = playerName
+
+ nFrame.Position = UDim2.new(1,0,((#MiddleFrames) * nFrame.Size.Y.Scale),0)
+
+ local nfriendstatus = GetFriendStatus(nplayer)
+
+ nFrame:FindFirstChild('BCLabel').Image = getMembershipTypeIcon(nplayer.MembershipType,nplayer.Name)
+ nFrame:FindFirstChild('FriendLabel').Image = getFriendStatusIcon(nfriendstatus)
+ nFrame.Name = nplayer.Name
+ WaitForChild(WaitForChild(nFrame,'TitleFrame'),'Title').Text = playerName
+
+ --move for bc label
+ nFrame.FriendLabel.Position=nFrame.FriendLabel.Position+UDim2.new(0,17,0,0)
+ nFrame.TitleFrame.Title.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+
+ if(nFrame:FindFirstChild('FriendLabel').Image ~= '') then
+ nFrame.TitleFrame.Title.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+ end
+
+ if nplayer.Name == LocalPlayer.Name then
+ nFrame.TitleFrame.Title.Font = 'ArialBold'
+ nFrame.PlayerScore.Font = 'ArialBold'
+ ChangeHeaderName(playerName)
+ local dropShadow = nFrame.TitleFrame.Title:Clone()
+ dropShadow.TextColor3 = Color3.new(0,0,0)
+ dropShadow.TextTransparency=0
+ dropShadow.ZIndex=2
+ dropShadow.Position=nFrame.TitleFrame.Title.Position+UDim2.new(0,1,0,1)
+ dropShadow.Name='DropShadow'
+ dropShadow.Parent= nFrame.TitleFrame
+ else
+ --Delay(2, function () OnFriendshipChanged(nplayer,LocalPlayer:GetFriendStatus(nplayer)) end)
+ end
+ nFrame.TitleFrame.Title.Font = 'ArialBold'
+
+
+ nFrame.Parent = ListFrame
+ nFrame.Position = UDim2.new(.5,0,((#MiddleFrames) * nFrame.Size.Y.Scale),0)
+ UpdateMinimize()
+ local nentry = {}
+ nentry['Frame'] = nFrame
+ nentry['Player'] = nplayer
+ nentry['ID'] = AddId
+ AddId = AddId + 1
+ table.insert(PlayerFrames,nentry)
+ if #TeamFrames~=0 then
+
+ if nplayer.Neutral then
+ nentry['MyTeam'] = nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else
+ AddPlayerToTeam(NeutralTeam,nentry)
+ end
+
+ else
+ local addedToTeam=false
+ for i,tval in ipairs(TeamFrames) do
+ if tval['MyTeam'].TeamColor == nplayer.TeamColor then
+ AddPlayerToTeam(tval,nentry)
+ nentry['MyTeam'] = tval
+ addedToTeam=true
+ end
+ end
+ if not addedToTeam then
+ nentry['MyTeam']=nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else
+ AddPlayerToTeam(NeutralTeam,nentry)
+ end
+ nentry['MyTeam'] = NeutralTeam
+ end
+ end
+
+ end
+
+ if nplayer:FindFirstChild('leaderstats') then
+ LeaderstatsAdded(nentry)
+ end
+
+ nplayer.ChildAdded:connect(function(nchild)
+ if nchild.Name == 'leaderstats' then
+ while AddingFrameLock do debugprint('in adding leaderstats lock') wait(1/30) end
+ if not nplayer:FindFirstChild("leaderstats") then return end
+ AddingFrameLock = true
+ LeaderstatsAdded(nentry)
+ AddingFrameLock = false
+ end
+ end)
+
+ nplayer.ChildRemoved:connect(function (nchild)
+ if nplayer==LocalPlayer and nchild.Name == 'leaderstats' then
+ LeaderstatsRemoved(nchild,nentry)
+ end
+ end)
+ nplayer.Changed:connect(function(prop)PlayerChanged(nentry,prop) end)
+
+ local listener = WaitForChild(nFrame,'ClickListener')
+ listener.Active = true
+ listener.MouseButton1Down:connect(function(nx,ny) OnPlayerEntrySelect(nentry, nx,ny) end)
+
+ AddMiddleBGFrame()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+--[[
+ Note:major optimization can be done here
+ removes this player's frame if it exists, calls base update
+--]]
+function RemovePlayerFrame(tplayer)
+ while AddingFrameLock do debugprint('in removing player frame lock') wait(1/30) end
+ AddingFrameLock = true
+
+ local tteam
+ for i,key in ipairs(PlayerFrames) do
+ if tplayer == key['Player'] then
+ if PopUpClipFrame.Parent == key['Frame'] then
+ PopUpClipFrame.Parent = nil
+ end
+ key['Frame']:Destroy()
+ tteam=key['MyTeam']
+ table.remove(PlayerFrames,i)
+ end
+ end
+ if tteam then
+ for j,tentry in ipairs(tteam['MyPlayers']) do
+ if tentry['Player'] == tplayer then
+ RemovePlayerFromTeam(tteam,j)
+ end
+ end
+ end
+
+ RemoveMiddleBGFrame()
+ UpdateMinimize()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+Players.ChildRemoved:connect(RemovePlayerFrame)
+
+----------------------------
+-- Team Callback Functions
+----------------------------
+--[[
+ turns a list of team entries with sub lists of players into a single ordered
+ list, in the correct order,and of the correct length
+ @Args:
+ tframes the team entries to unroll
+ outframes the list to unroll these entries into
+--]]
+function UnrollTeams(tframes,outframes)
+ local numEntries = 0
+ if NeutralTeam and not NeutralTeam['IsHidden'] then
+ for i,val in ipairs(NeutralTeam['MyPlayers']) do
+ numEntries = numEntries + 1
+ outframes[numEntries] = val['Frame']
+ end
+ numEntries = numEntries + 1
+ outframes[numEntries] = NeutralTeam['Frame']
+ end
+ for i,val in ipairs(tframes) do
+ if not val['IsHidden'] then
+ for j,pval in ipairs(val.MyPlayers) do
+ numEntries = numEntries + 1
+ outframes[numEntries] = pval['Frame']
+ end
+ numEntries = numEntries + 1
+ outframes[numEntries] = val['Frame']
+ end
+ end
+ -- clear any additional entries from outframes
+ for i = numEntries + 1,#outframes,1 do
+ outframes[i] = nil
+ end
+end
+--[[
+ uses lua's table.sort to sort the teams
+--]]
+function TeamSortFunc(a,b)
+ if a['TeamScore'] == b['TeamScore'] then
+ return a['ID'] < b['ID']
+ end
+ if not a['TeamScore'] then return false end
+ if not b['TeamScore'] then return true end
+ return a['TeamScore'] < b['TeamScore']
+
+end
+--[[
+ consider adding lock with wait for performance
+ sorts each of the team's player lists induvidually, adds up the team scores.
+ @Args:
+ tentries table of team entries
+--]]
+function SortTeams(tentries)
+
+ for i,val in ipairs(tentries) do
+
+ table.sort(val['MyPlayers'],PlayerSortFunction)
+ AddTeamScores(val)
+ end
+ table.sort(tentries,TeamSortFunc)
+end
+--[[
+ base update for team mode, adds up the scores of all teams, sorts them,
+ then unrolls them into middleframes
+--]]
+function TeamListModeUpdate()
+ RecreateScoreColumns(PlayerFrames)
+ SortTeams(TeamFrames)
+ if NeutralTeam then
+ AddTeamScores(NeutralTeam)
+ --RecreateScoreColumns(NeutralTeam['MyPlayers'])
+ end
+ UnrollTeams(TeamFrames,MiddleFrames)
+end
+--[[
+ adds up all the score of this team's players to form the team score
+ @Args:
+ team team entry to sum the scores of
+--]]
+function AddTeamScores(team)
+
+ for j = 1, #ScoreNames,1 do
+ local i = ScoreNames[j]
+ local tscore = 0
+ for _,j in ipairs(team['MyPlayers']) do
+ local tval = j['Player']:FindFirstChild('leaderstats') and j['Player'].leaderstats:FindFirstChild(i['Name'])
+ if tval and not tval:IsA('StringValue') then
+ tscore = tscore + GetScoreValue((j['Player'].leaderstats)[i['Name'] ])
+ end
+ end
+ if team['Frame']:FindFirstChild(i['Name']) then
+ --team['Frame'][i['Name'] ].Size = UDim2.new(1 - (ScrollBarFrame.Size.X.Scale * 2),- ((j-1) * SpacingPerStat),1,0)
+ team['Frame'][i['Name'] ].Text = tostring(tscore)
+ end
+ end
+ UpdateMinimize()
+
+end
+
+--[[
+ finds previous team this player was on, and if it exists calls removeplayerfromteam
+ @Args
+ entry Player entry
+--]]
+function FindRemovePlayerFromTeam(entry)
+ if entry['MyTeam'] then
+ for j,oldEntry in ipairs(entry['MyTeam']['MyPlayers']) do
+ if oldEntry['Player'] == entry['Player'] then
+ RemovePlayerFromTeam(entry['MyTeam'],j)
+ return
+ end
+ end
+ elseif NeutralTeam then
+ for j,oldEntry in ipairs(NeutralTeam['MyPlayers']) do
+ if oldEntry['Player'] == entry['Player'] then
+ RemovePlayerFromTeam(NeutralTeam,j)
+ return
+ end
+ end
+ end
+end
+--[[
+ removes a single player from a given team (not usually called directly)
+ @Args:
+ teamEntry team entry to remove player from
+ index index of player in 'MyPlayers' list to remove
+--]]
+function RemovePlayerFromTeam(teamEntry,index)
+ table.remove(teamEntry['MyPlayers'],index)
+ --if teamEntry['AutoHide'] and #teamEntry['MyPlayers'] == 0 then
+ if teamEntry==NeutralTeam and #teamEntry['MyPlayers']==0 then
+ RemoveNeutralTeam()
+ end
+end
+--[[
+ adds player entry entry to teamentry
+ removes them from any previous team
+ @Args:
+ teamEntry entry of team to add player to
+ entry player entry to add to this team
+--]]
+function AddPlayerToTeam(teamEntry,entry)
+ FindRemovePlayerFromTeam(entry)
+ table.insert(teamEntry['MyPlayers'],entry)
+ entry['MyTeam'] = teamEntry
+ if teamEntry['IsHidden'] then
+ teamEntry['Frame'].Parent = ListFrame
+ AddMiddleBGFrame()
+ end
+ teamEntry['IsHidden'] = false
+end
+
+
+function SetPlayerToTeam(entry)
+ FindRemovePlayerFromTeam(entry)
+ -- check to see if team exists, if it does add to that team
+ local setToTeam = false
+ for i,tframe in ipairs(TeamFrames) do
+ -- add my entry on the new team
+ if tframe['MyTeam'].TeamColor == entry['Player'].TeamColor then
+ AddPlayerToTeam(tframe,entry)
+ setToTeam = true
+ end
+ end
+ -- if player was set to an invalid team, then set it back to neutral
+ if not setToTeam and #(game.Teams:GetTeams())>0 then
+ debugprint(entry['Player'].Name..'could not find team')
+ entry['MyTeam']=nil
+ if not NeutralTeam then
+ AddNeutralTeam()
+ else AddPlayerToTeam(NeutralTeam,entry) end
+ end
+end
+
+--[[
+ Note:another big one, consiter breaking up
+ called when any children of player changes
+ handles 'Neutral', teamColor, Name and MembershipType changes
+ @Args
+ entry Player entry changed
+ property name of property changed
+--]]
+function PlayerChanged(entry, property)
+ while PlayerChangedLock do
+ debugprint('in playerchanged lock')
+ wait(1/30)
+ end
+ PlayerChangedLock=true
+ if property == 'Neutral' then
+ -- if player changing to neutral
+ if entry['Player'].Neutral and #(game.Teams:GetTeams())>0 then
+ debugprint(entry['Player'].Name..'setting to neutral')
+ FindRemovePlayerFromTeam(entry)
+ entry['MyTeam']=nil
+ if not NeutralTeam then
+ debugprint(entry['Player'].Name..'creating neutral team')
+ AddNeutralTeam()
+ else
+ debugprint(entry['Player'].Name..'adding to neutral team')
+ AddPlayerToTeam(NeutralTeam,entry)
+ end
+ elseif #(game.Teams:GetTeams())>0 then -- else player switching to a team, or a weird edgecase
+ debugprint(entry['Player'].Name..'has been set non-neutral')
+ SetPlayerToTeam(entry)
+ end
+ BaseUpdate()
+ elseif property == 'TeamColor' and not entry['Player'].Neutral and entry['Player'] ~= entry['MyTeam'] then
+ debugprint(entry['Player'].Name..'setting to new team')
+ SetPlayerToTeam(entry)
+ BaseUpdate()
+ elseif property == 'Name' or property == 'MembershipType' then
+ entry['Frame']:FindFirstChild('BCLabel').Image = getMembershipTypeIcon(entry['Player'].MembershipType,entry['Player'].Name)
+ entry['Frame'].Name = entry['Player'].Name
+ entry['Frame'].TitleFrame.Title.Text = entry['Player'].Name
+ if(entry['Frame'].BCLabel.Image ~= '') then
+ entry['Frame'].TitleFrame.Title.Position=UDim2.new(.01, 30, .1, 0)
+ end
+ if entry['Player'] == LocalPlayer then
+ entry['Frame'].TitleFrame.DropShadow.Text= entry['Player'].Name
+ ChangeHeaderName(entry['Player'].Name)
+ end
+ BaseUpdate()
+ end
+ PlayerChangedLock=false
+end
+
+function OnFriendshipChanged(player,friendStatus)
+
+ Delay(.5,function()
+ debugprint('friend status changed for:'..player.Name .." ".. tostring(friendStatus) .. " vs " .. tostring(GetFriendStatus(player)) )
+ for _, entry in ipairs(PlayerFrames) do
+ if entry['Player']==player then
+ local nicon = getFriendStatusIcon(friendStatus)
+ if nicon == '' and entry['Frame'].FriendLabel.Image ~= '' then
+ entry['Frame'].TitleFrame.Title.Position=entry['Frame'].TitleFrame.Title.Position-UDim2.new(0,17,0,0)
+ elseif nicon ~= '' and entry['Frame'].FriendLabel.Image == '' then
+ entry['Frame'].TitleFrame.Title.Position=entry['Frame'].TitleFrame.Title.Position+UDim2.new(0,17,0,0)
+ debugprint('confirmed status:'..player.Name)
+ end
+ entry['Frame'].FriendLabel.Image = nicon
+ return
+ end
+ end
+ end)
+end
+
+LocalPlayer.FriendStatusChanged:connect(OnFriendshipChanged)
+
+--[[
+ adds a neutral team if nessisary
+ Note: a lot of redundant code here, might want to refactor to share a function with insertteamframe
+--]]
+function AddNeutralTeam()
+ while NeutralTeamLock do debugprint('in neutral team 2 lock') wait() end
+ NeutralTeamLock = true
+
+ local defaultTeam = Instance.new('Team')
+ defaultTeam.TeamColor = BrickColor.new('White')
+ defaultTeam.Name = 'Neutral'
+ local nentry = {}
+ nentry['MyTeam'] = defaultTeam
+ nentry['MyPlayers'] = {}
+ nentry['Frame'] = MiddleTemplate:Clone()
+ WaitForChild(WaitForChild(nentry['Frame'],'TitleFrame'),'Title').Text = defaultTeam.Name
+ nentry['Frame'].TitleFrame.Position=UDim2.new(nentry['Frame'].TitleFrame.Position.X.Scale,nentry['Frame'].TitleFrame.Position.X.Offset,.1,0)
+ nentry['Frame'].TitleFrame.Size=UDim2.new(nentry['Frame'].TitleFrame.Size.X.Scale,nentry['Frame'].TitleFrame.Size.X.Offset,.8,0)
+ nentry['Frame'].TitleFrame.Title.Font = 'ArialBold'
+ nentry['Frame'].Position = UDim2.new(1,0,((#MiddleFrames) * nentry['Frame'].Size.Y.Scale),0)
+ WaitForChild(nentry['Frame'],'ClickListener').MouseButton1Down:connect(function(nx,ny) StartDrag(nentry,nx,ny) end)
+ nentry['Frame'].ClickListener.BackgroundColor3 = Color3.new(1,1,1)
+ nentry['Frame'].ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nentry['Frame'].ClickListener.AutoButtonColor=false
+ nentry['AutoHide'] = true
+ nentry['IsHidden'] = true
+ for _,i in pairs(PlayerFrames) do
+ if i['Player'].Neutral or not i['MyTeam'] then
+ AddPlayerToTeam(nentry,i)
+ end
+ end
+ if #nentry['MyPlayers'] > 0 then
+ NeutralTeam = nentry
+ UpdateMinimize()
+ BaseUpdate()
+ end
+ NeutralTeamLock = false
+end
+
+function RemoveNeutralTeam()
+ while NeutralTeamLock do debugprint('in neutral team lock') wait() end
+ NeutralTeamLock = true
+ NeutralTeam['Frame']:Destroy()
+ NeutralTeam=nil
+ RemoveMiddleBGFrame()
+ NeutralTeamLock = false
+end
+
+--[[
+
+--]]
+function TeamScoreChanged(entry,nscore)
+ WaitForChild(entry['Frame'],'PlayerScore').Text = tostring(nscore)
+ entry['TeamScore'] = nscore
+end
+--[[
+ called when child added to a team, used for autohide functionality
+ Note: still has teamscore, consiter removing
+--]]
+function TeamChildAdded(entry,nchild)
+ if nchild.Name == 'AutoHide' then
+ entry['AutoHide'] = true
+ elseif nchild.Name == 'TeamScore' then
+ WaitForChild(entry['Frame'],'PlayerScore').Text = tostring(nchild.Value)
+ entry['TeamScore'] = nchild.Value
+ nchild.Changed:connect(function() TeamScoreChanged(entry,nchild.Value) end)
+ end
+end
+--[[
+ called when child added to a team, used for autohide functionality
+ Note: still has teamscore, consiter removing
+--]]
+function TeamChildRemoved(entry,nchild)
+ if nchild.Name == 'AutoHide' then
+ entry['AutoHide'] = false
+ elseif nchild.Name == 'TeamScore' then
+ WaitForChild(entry['Frame'],'PlayerScore').Text = ""
+ entry['TeamScore'] = nil
+ end
+end
+
+function TeamChanged(entry, property)
+ if property=='Name' then
+ WaitForChild(WaitForChild(entry['Frame'],'TitleFrame'),'Title').Text = entry['MyTeam'].Name
+
+ elseif property=='TeamColor' then
+ entry['Frame'].ClickListener.BackgroundColor3 = entry['MyTeam'].TeamColor.Color
+
+ for _,i in pairs(TeamFrames) do
+ if i['MyTeam'].TeamColor == entry['MyTeam'] then
+ RemoveTeamFrame(entry['MyTeam']) --NO DUPLICATE TEAMS!
+ end
+ end
+
+ entry['MyPlayers']={}
+
+ for _,i in pairs(PlayerFrames) do
+ SetPlayerToTeam(i)
+ end
+ BaseUpdate()
+ end
+end
+
+--[[
+ creates team entry and frame for this team, sets up listeners for this team
+ adds any players intended for this team,Creates neutral team if this is the first team added
+ Note:might be best to break this into multiple functions to simplify
+ @Args:
+ nteam new team object added
+--]]
+function InsertTeamFrame(nteam)
+ while AddingFrameLock do debugprint('in adding team frame lock') wait(1/30) end
+ AddingFrameLock = true
+ --for _,i in pairs(TeamFrames) do
+ local nentry = {}
+ nentry['MyTeam'] = nteam
+ nentry['MyPlayers'] = {}
+ nentry['Frame'] = MiddleTemplate:Clone()
+ WaitForChild(WaitForChild(nentry['Frame'],'TitleFrame'),'Title').Text = nteam.Name
+ nentry['Frame'].TitleFrame.Title.Font = 'ArialBold'
+ nentry['Frame'].TitleFrame.Title.FontSize = 'Size18'
+ nentry['Frame'].Position = UDim2.new(0.5,0,((#MiddleFrames) * nentry['Frame'].Size.Y.Scale),0)
+ WaitForChild(nentry['Frame'],'ClickListener').MouseButton1Down:connect(function(nx,ny) StartDrag(nentry,nx,ny) end)
+ nentry['Frame'].ClickListener.BackgroundColor3 = nteam.TeamColor.Color
+ nentry['Frame'].ClickListener.BackgroundTransparency = BACKGROUND_TRANSPARENCY
+ nentry['Frame'].ClickListener.AutoButtonColor=false
+ AddId = AddId + 1
+ nentry['ID'] = AddId
+ nentry['AutoHide'] = false
+ if nteam:FindFirstChild('AutoHide') then
+ nentry['AutoHide'] = true
+ end
+ if nteam:FindFirstChild('TeamScore') then
+ TeamChildAdded(nentry,nteam.TeamScore)
+
+ end
+
+ nteam.ChildAdded:connect(function(nchild) TeamChildAdded(nentry,nchild) end)
+ nteam.ChildRemoved:connect(function(nchild) TeamChildRemoved(nentry,nchild) end)
+ nteam.Changed:connect(function(prop) TeamChanged(nentry,prop) end)
+
+ for _,i in pairs(PlayerFrames) do
+ if not i['Player'].Neutral and i['Player'].TeamColor == nteam.TeamColor then
+ AddPlayerToTeam(nentry,i)
+ end
+ end
+ nentry['IsHidden'] = false
+ if not nentry['AutoHide'] or #nentry['MyPlayers'] > 0 then
+ nentry['Frame'].Parent = ListFrame
+ AddMiddleBGFrame()
+ else
+ nentry['IsHidden'] = true
+ nentry['Frame'].Parent = nil
+ end
+
+ table.insert(TeamFrames,nentry)
+ UpdateMinimize()
+ BaseUpdate()
+ if #TeamFrames == 1 and not NeutralTeam then
+ AddNeutralTeam()
+ end
+ AddingFrameLock = false
+end
+--[[
+ removes team from team list
+ @Args:
+ nteam Teamobject to remove
+--]]
+function RemoveTeamFrame(nteam)
+ while AddingFrameLock do debugprint('in removing team frame lock') wait(1/30) end
+ AddingFrameLock = true
+ if IsMinimized.Value then
+ end
+ local myEntry
+ for i,key in ipairs(TeamFrames) do
+ if nteam == key['MyTeam'] then
+ myEntry = key
+ key['Frame']:Destroy()
+ table.remove(TeamFrames,i)
+ end
+ end
+ if #TeamFrames==0 then
+ debugprint('removeteamframe, remove neutral')
+ if NeutralTeam then
+ RemoveNeutralTeam()
+ end
+ end
+ for i,key in ipairs(myEntry['MyPlayers']) do
+ RemovePlayerFromTeam(myEntry,i)
+ PlayerChanged(key, 'TeamColor')
+ end
+ RemoveMiddleBGFrame()
+ BaseUpdate()
+ AddingFrameLock = false
+end
+
+function TeamAdded(nteam)
+ InsertTeamFrame(nteam)
+end
+
+function TeamRemoved(nteam)
+ RemoveTeamFrame(nteam)
+end
+ ---------------------------------
+--[[
+ called when ANYTHING changes the state of the playerlist
+ re-sorts everything,assures correct positions of all elements
+--]]
+function BaseUpdate()
+ while BaseUpdateLock do debugprint('in baseupdate lock') wait(1/30) end
+ BaseUpdateLock = true
+ --print ('baseupdate')
+ UpdateStatNames()
+
+ if #TeamFrames == 0 and not NeutralTeam then
+ PlayerListModeUpdate()
+ else
+ TeamListModeUpdate()
+ end
+ for i,key in ipairs(MiddleFrames) do
+ if key.Parent ~= nil then
+ key.Position = UDim2.new(.5,0,((#MiddleFrames - (i)) * key.Size.Y.Scale),0)
+ end
+ end
+ if not IsMinimized.Value and #MiddleFrames>DefaultEntriesOnScreen then
+ UpdateScrollPosition()
+ end
+
+ UpdateMinimize()
+
+ UpdateScrollBarSize()
+ UpdateScrollPosition()
+
+ UpdateScrollBarVisibility()
+ --debugprint('EndBaseUpdate')
+ BaseUpdateLock = false
+end
+
+--[[
+ code for attaching tab key to maximizing player list
+--]]
+game.GuiService:AddKey("\t")
+local LastTabTime = time()
+game.GuiService.KeyPressed:connect(
+function(key)
+ if key == "\t" then
+ debugprint('caught tab key')
+ local modalCheck, isModal = pcall(function() return game.GuiService.IsModalDialog end)
+ if modalCheck == false or (modalCheck and isModal == false) then
+ if time() - LastTabTime > 0.4 then
+ LastTabTime = time()
+ if IsTabified.Value then
+ if not IsMaximized.Value then
+ ScreenGui:TweenPosition(UDim2.new(0, 0, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ IsMaximized.Value = true
+ else
+ ScreenGui:TweenPosition(UDim2.new(NormalBounds.X.Scale, NormalBounds.X.Offset-10, 0,0),'Out','Linear',BASE_TWEEN*1.2,true)
+ IsMaximized.Value = false
+ IsMinimized.Value=true
+ end
+ else
+ ToggleMaximize()
+ end
+
+ end
+ end
+ end
+end)
+
+
+function PlayersChildAdded(tplayer)
+ if tplayer:IsA('Player') then
+ Spawn(function() debugPlayerAdd(tplayer) end)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+function coreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.All or coreGuiType == Enum.CoreGuiType.PlayerList then
+ MainFrame.Visible = enabled
+ end
+end
+
+function TeamsChildAdded(nteam)
+ if nteam:IsA('Team') then
+ TeamAdded(nteam)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+function TeamsChildRemoved(nteam)
+ if nteam:IsA('Team') then
+ TeamRemoved(nteam)
+ else
+ BlowThisPopsicleStand()
+ end
+end
+
+ ----------------------------
+ -- Hookups and initialization
+ ----------------------------
+function debugPlayerAdd(p)
+ InsertPlayerFrame(p)
+end
+
+pcall(function()
+ coreGuiChanged(Enum.CoreGuiType.PlayerList, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.PlayerList))
+ Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+end)
+
+while not game:GetService('Teams') do wait(1/30) debugprint('Waiting For Teams') end
+for _,i in pairs(game.Teams:GetTeams()) do TeamAdded(i) end
+for _,i in pairs(Players:GetPlayers()) do Spawn(function() debugPlayerAdd(i) end) end
+
+game.Teams.ChildAdded:connect(TeamsChildAdded)
+game.Teams.ChildRemoved:connect(TeamsChildRemoved)
+Players.ChildAdded:connect(PlayersChildAdded)
+
+InitReportAbuse()
+AreNamesExpanded.Value = true
+BaseUpdate()
+
+
+
+--UGGGLY,find a better way later
+wait(2)
+IsPersonalServer= not not game.Workspace:FindFirstChild("PSVariable")
+
+ ----------------------------
+ -- Running Logic
+ ----------------------------
+
+ --debug stuffs, will only run for 'newplayerlistisbad'
+ if LocalPlayer.Name == 'newplayerlistisbad' or LocalPlayer.Name == 'imtotallyadmin' then
+ debugFrame.Parent = ScreenGui
+ Spawn(function()
+ while true do
+ local str_players=''
+ for _,i in pairs(game.Players:GetPlayers()) do
+ str_players= str_players .." " .. i.Name
+ end
+ debugplayers.Text=str_players
+ wait(.5)
+ end
+ end)
+ end
+
+
diff --git a/asset/backup/15 b/asset/backup/15
new file mode 100644
index 0000000..438bf7a
--- /dev/null
+++ b/asset/backup/15
@@ -0,0 +1,589 @@
+%15%
+-- This script creates almost all gui elements found in the backpack (warning: there are a lot!)
+-- TODO: automate this process
+
+local ICON_SIZE = 46
+
+local gui = script.Parent
+
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+local function IsPhone()
+ if Game:GetService("GuiService"):GetScreenResolution().Y <= 500 and IsTouchDevice() then
+ return true
+ end
+ return false
+end
+
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+-- First up is the current loadout
+local CurrentLoadout = Instance.new("Frame")
+CurrentLoadout.Name = "CurrentLoadout"
+CurrentLoadout.Position = UDim2.new(0.5, -300, 1, -85)
+CurrentLoadout.Size = UDim2.new(0, 600, 0, ICON_SIZE)
+CurrentLoadout.BackgroundTransparency = 1
+CurrentLoadout.RobloxLocked = true
+CurrentLoadout.Parent = gui
+
+local CLBackground = Instance.new('ImageLabel')
+CLBackground.Name = 'Background';
+CLBackground.Size = UDim2.new(1.2, 0, 1.2, 0);
+CLBackground.Image = "http://www.roblox.com/asset/?id=96536002"
+CLBackground.BackgroundTransparency = 1.0;
+CLBackground.Position = UDim2.new(-0.1, 0, -0.1, 0);
+CLBackground.ZIndex = 0.0;
+CLBackground.Parent = CurrentLoadout
+CLBackground.Visible = false
+
+local Debounce = Instance.new("BoolValue")
+Debounce.Name = "Debounce"
+Debounce.RobloxLocked = true
+Debounce.Parent = CurrentLoadout
+
+local BackpackButton = Instance.new("ImageButton")
+BackpackButton.RobloxLocked = true
+BackpackButton.Visible = false
+BackpackButton.Name = "BackpackButton"
+BackpackButton.BackgroundTransparency = 1
+BackpackButton.Image = "rbxasset://textures/ui/Backpack_Open.png"
+BackpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+BackpackButton.Size = UDim2.new(0, 14, 0, 9)
+waitForChild(gui,"ControlFrame")
+BackpackButton.Parent = gui.ControlFrame
+
+local NumSlots = 9
+
+if IsPhone() then
+ NumSlots = 3
+ CurrentLoadout.Size = UDim2.new(0,180,0,ICON_SIZE)
+ CurrentLoadout.Position = UDim2.new(0.5,-90,1,-85)
+end
+
+for i = 0, NumSlots do
+ local slotFrame = Instance.new("Frame")
+ slotFrame.RobloxLocked = true
+ slotFrame.BackgroundColor3 = Color3.new(0,0,0)
+ slotFrame.BackgroundTransparency = 1
+ slotFrame.BorderColor3 = Color3.new(1, 1, 1)
+ slotFrame.BorderSizePixel = 0
+ slotFrame.Name = "Slot" .. tostring(i)
+ slotFrame.ZIndex = 4.0
+ if i == 0 then
+ slotFrame.Position = UDim2.new(0.9, 48, 0, 0)
+ else
+ slotFrame.Position = UDim2.new((i - 1) * 0.1, (i-1)* 6,0,0)
+ end
+
+
+ slotFrame.Size = UDim2.new(0, ICON_SIZE, 0, ICON_SIZE)
+ slotFrame.Parent = CurrentLoadout
+
+ if gui.AbsoluteSize.Y <= 320 then
+ slotFrame.Position = UDim2.new(0, (i-1)* 60, 0, -50)
+ end
+ if gui.AbsoluteSize.Y <= 320 and i == 0 then
+ slotFrame:Destroy()
+ end
+end
+
+local TempSlot = Instance.new("ImageButton")
+TempSlot.Name = "TempSlot"
+TempSlot.Active = true
+TempSlot.Size = UDim2.new(1,0,1,0)
+TempSlot.BackgroundTransparency = 1.0
+TempSlot.Style = 'Custom'
+TempSlot.Visible = false
+TempSlot.RobloxLocked = true
+TempSlot.Parent = CurrentLoadout
+TempSlot.ZIndex = 3.0
+
+ local slotBackground = Instance.new('Frame')
+ slotBackground.Name = 'Background'
+ slotBackground.BackgroundTransparency = 1.0
+ slotBackground.Style = "DropShadow"
+ slotBackground.Position = UDim2.new(0, -10, 0, -10)
+ slotBackground.Size = UDim2.new(1, 20, 1, 20)
+ slotBackground.Parent = TempSlot
+
+ local HighLight = Instance.new('ImageLabel')
+ HighLight.Name = 'Highlight'
+ HighLight.BackgroundTransparency = 1.0
+ HighLight.Image = 'http://www.roblox.com/asset/?id=97643886'
+ HighLight.Size = UDim2.new(1, 0, 1, 0)
+ --HighLight.Parent = TempSlot
+ HighLight.Visible = false
+
+ -- TempSlot Children
+ local GearReference = Instance.new("ObjectValue")
+ GearReference.Name = "GearReference"
+ GearReference.RobloxLocked = true
+ GearReference.Parent = TempSlot
+
+
+ local ToolTipLabel = Instance.new("TextLabel")
+ ToolTipLabel.Name = "ToolTipLabel"
+ ToolTipLabel.RobloxLocked = true
+ ToolTipLabel.Text = ""
+ ToolTipLabel.BackgroundTransparency = 0.5
+ ToolTipLabel.BorderSizePixel = 0
+ ToolTipLabel.Visible = false
+ ToolTipLabel.TextColor3 = Color3.new(1,1,1)
+ ToolTipLabel.BackgroundColor3 = Color3.new(0,0,0)
+ ToolTipLabel.TextStrokeTransparency = 0
+ ToolTipLabel.Font = Enum.Font.ArialBold
+ ToolTipLabel.FontSize = Enum.FontSize.Size14
+ --ToolTipLabel.TextWrap = true
+ ToolTipLabel.Size = UDim2.new(1,60,0,20)
+ ToolTipLabel.Position = UDim2.new(0,-30,0,-30)
+ ToolTipLabel.Parent = TempSlot
+
+
+ local Kill = Instance.new("BoolValue")
+ Kill.Name = "Kill"
+ Kill.RobloxLocked = true
+ Kill.Parent = TempSlot
+
+ local GearImage = Instance.new("ImageLabel")
+ GearImage.Name = "GearImage"
+ GearImage.BackgroundTransparency = 1
+ GearImage.Position = UDim2.new(0, 0, 0, 0)
+ GearImage.Size = UDim2.new(1, 0, 1, 0)
+ GearImage.ZIndex = 5.0
+ GearImage.RobloxLocked = true
+ GearImage.Parent = TempSlot
+
+ local SlotNumber = Instance.new("TextLabel")
+ SlotNumber.Name = "SlotNumber"
+ SlotNumber.BackgroundTransparency = 1
+ SlotNumber.BorderSizePixel = 0
+ SlotNumber.Font = Enum.Font.ArialBold
+ SlotNumber.FontSize = Enum.FontSize.Size18
+ SlotNumber.Position = UDim2.new(0, 0, 0, 0)
+ SlotNumber.Size = UDim2.new(0,10,0,15)
+ SlotNumber.TextColor3 = Color3.new(1,1,1)
+ SlotNumber.TextTransparency = 0
+ SlotNumber.TextXAlignment = Enum.TextXAlignment.Left
+ SlotNumber.TextYAlignment = Enum.TextYAlignment.Bottom
+ SlotNumber.RobloxLocked = true
+ SlotNumber.Parent = TempSlot
+ SlotNumber.ZIndex = 5
+
+ if IsTouchDevice() then
+ SlotNumber.Visible = false
+ end
+
+ local SlotNumberDownShadow = SlotNumber:Clone()
+ SlotNumberDownShadow.Name = "SlotNumberDownShadow"
+ SlotNumberDownShadow.TextColor3 = Color3.new(0,0,0)
+ SlotNumberDownShadow.Position = UDim2.new(0, 1, 0, -1)
+ SlotNumberDownShadow.Parent = TempSlot
+ SlotNumberDownShadow.ZIndex = 2
+
+ local SlotNumberUpShadow = SlotNumberDownShadow:Clone()
+ SlotNumberUpShadow.Name = "SlotNumberUpShadow"
+ SlotNumberUpShadow.Position = UDim2.new(0, -1, 0, -1)
+ SlotNumberUpShadow.Parent = TempSlot
+
+ local GearText = Instance.new("TextLabel")
+ GearText.RobloxLocked = true
+ GearText.Name = "GearText"
+ GearText.BackgroundTransparency = 1
+ GearText.Font = Enum.Font.Arial
+ GearText.FontSize = Enum.FontSize.Size14
+ GearText.Position = UDim2.new(0,0,0,0)
+ GearText.Size = UDim2.new(1,0,1,0)
+ GearText.Text = ""
+ GearText.TextColor3 = Color3.new(1,1,1)
+ GearText.TextWrap = true
+ GearText.Parent = TempSlot
+ GearText.ZIndex = 5.0
+
+--- Great, now lets make the inventory!
+
+local Backpack = Instance.new("Frame")
+Backpack.RobloxLocked = true
+Backpack.Visible = false
+Backpack.Name = "Backpack"
+Backpack.Position = UDim2.new(0.5, 0, 0.5, 0)
+Backpack.BackgroundColor3 = Color3.new(32/255, 32/255, 32/255)
+Backpack.BackgroundTransparency = 0.5
+Backpack.BorderSizePixel = 0
+Backpack.Parent = gui
+Backpack.Active = true
+
+ -- Backpack Children
+ local SwapSlot = Instance.new("BoolValue")
+ SwapSlot.RobloxLocked = true
+ SwapSlot.Name = "SwapSlot"
+ SwapSlot.Parent = Backpack
+
+ -- SwapSlot Children
+ local Slot = Instance.new("IntValue")
+ Slot.RobloxLocked = true
+ Slot.Name = "Slot"
+ Slot.Parent = SwapSlot
+
+ local GearButton = Instance.new("ObjectValue")
+ GearButton.RobloxLocked = true
+ GearButton.Name = "GearButton"
+ GearButton.Parent = SwapSlot
+
+ local Tabs = Instance.new("Frame")
+ Tabs.Name = "Tabs"
+ Tabs.Visible = false
+ Tabs.Active = false
+ Tabs.RobloxLocked = true
+ Tabs.BackgroundColor3 = Color3.new(0,0,0)
+ Tabs.BackgroundTransparency = 0.08
+ Tabs.BorderSizePixel = 0
+ Tabs.Position = UDim2.new(0,0,-0.1,-4)
+ Tabs.Size = UDim2.new(1,0,0.1,4)
+ Tabs.Parent = Backpack
+
+ -- Tabs Children
+
+ local tabLine = Instance.new("Frame")
+ tabLine.RobloxLocked = true
+ tabLine.Name = "TabLine"
+ tabLine.BackgroundColor3 = Color3.new(53/255, 53/255, 53/255)
+ tabLine.BorderSizePixel = 0
+ tabLine.Position = UDim2.new(0,5,1,-4)
+ tabLine.Size = UDim2.new(1,-10,0,4)
+ tabLine.ZIndex = 2
+ tabLine.Parent = Tabs
+
+ local InventoryButton = Instance.new("TextButton")
+ InventoryButton.RobloxLocked = true
+ InventoryButton.Name = "InventoryButton"
+ InventoryButton.Size = UDim2.new(0,60,0,30)
+ InventoryButton.Position = UDim2.new(0,7,1,-31)
+ InventoryButton.BackgroundColor3 = Color3.new(1,1,1)
+ InventoryButton.BorderColor3 = Color3.new(1,1,1)
+ InventoryButton.Font = Enum.Font.ArialBold
+ InventoryButton.FontSize = Enum.FontSize.Size18
+ InventoryButton.Text = "Gear"
+ InventoryButton.AutoButtonColor = false
+ InventoryButton.TextColor3 = Color3.new(0,0,0)
+ InventoryButton.Selected = true
+ InventoryButton.Active = true
+ InventoryButton.ZIndex = 3
+ InventoryButton.Parent = Tabs
+
+ local closeButton = Instance.new("TextButton")
+ closeButton.RobloxLocked = true
+ closeButton.Name = "CloseButton"
+ closeButton.Font = Enum.Font.ArialBold
+ closeButton.FontSize = Enum.FontSize.Size24
+ closeButton.Position = UDim2.new(1,-33,0,4)
+ closeButton.Size = UDim2.new(0,30,0,30)
+ closeButton.Style = Enum.ButtonStyle.RobloxButton
+ closeButton.Text = ""
+ closeButton.TextColor3 = Color3.new(1,1,1)
+ closeButton.Parent = Tabs
+ closeButton.Modal = true
+
+ --closeButton child
+ local XImage = Instance.new("ImageLabel")
+ XImage.RobloxLocked = true
+ XImage.Name = "XImage"
+ game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id=75547445")
+ XImage.Image = "http://www.roblox.com/asset/?id=75547445" --TODO: move to rbxasset
+ XImage.BackgroundTransparency = 1
+ XImage.Position = UDim2.new(-.25,-1,-.25,-1)
+ XImage.Size = UDim2.new(1.5,2,1.5,2)
+ XImage.ZIndex = 2
+ XImage.Parent = closeButton
+
+ -- Generic Search gui used across backpack
+ local SearchFrame = Instance.new("Frame")
+ SearchFrame.RobloxLocked = true
+ SearchFrame.Name = "SearchFrame"
+ SearchFrame.BackgroundTransparency = 1
+ SearchFrame.Position = UDim2.new(1,-220,0,2)
+ SearchFrame.Size = UDim2.new(0,220,0,24)
+ SearchFrame.Parent = Backpack
+
+ -- SearchFrame Children
+ local SearchButton = Instance.new("ImageButton")
+ SearchButton.RobloxLocked = true
+ SearchButton.Name = "SearchButton"
+ SearchButton.Size = UDim2.new(0,25,0,25)
+ SearchButton.BackgroundTransparency = 1
+ SearchButton.Image = "rbxasset://textures/ui/SearchIcon.png"
+ SearchButton.Parent = SearchFrame
+
+ local SearchBoxFrame = Instance.new("TextButton")
+ SearchBoxFrame.RobloxLocked = true
+ SearchBoxFrame.Position = UDim2.new(0,25,0,-2)
+ SearchBoxFrame.Size = UDim2.new(1,-28,0,30)
+ SearchBoxFrame.Name = "SearchBoxFrame"
+ SearchBoxFrame.Text = ""
+ SearchBoxFrame.Style = Enum.ButtonStyle.RobloxRoundButton
+ SearchBoxFrame.Parent = SearchFrame
+
+ -- SearchBoxFrame Children
+ local SearchBox = Instance.new("TextBox")
+ SearchBox.RobloxLocked = true
+ SearchBox.Name = "SearchBox"
+ SearchBox.BackgroundTransparency = 1
+ SearchBox.Font = Enum.Font.ArialBold
+ SearchBox.FontSize = Enum.FontSize.Size12
+ SearchBox.Position = UDim2.new(0,-5,0,-5)
+ SearchBox.Size = UDim2.new(1,10,1,10)
+ SearchBox.TextColor3 = Color3.new(1,1,1)
+ SearchBox.TextXAlignment = Enum.TextXAlignment.Left
+ SearchBox.ZIndex = 2
+ SearchBox.TextWrap = true
+ SearchBox.Text = "Search..."
+ SearchBox.Parent = SearchBoxFrame
+
+
+ local ResetButton = Instance.new("TextButton")
+ ResetButton.RobloxLocked = true
+ ResetButton.Visible = false
+ ResetButton.Name = "ResetButton"
+ ResetButton.Position = UDim2.new(1,-26,0,3)
+ ResetButton.Size = UDim2.new(0,20,0,20)
+ ResetButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ ResetButton.Text = "X"
+ ResetButton.TextColor3 = Color3.new(1,1,1)
+ ResetButton.Font = Enum.Font.ArialBold
+ ResetButton.FontSize = Enum.FontSize.Size18
+ ResetButton.ZIndex = 3
+ ResetButton.Parent = SearchFrame
+
+------------------------------- GEAR -------------------------------------------------------
+ local Gear = Instance.new("Frame")
+ Gear.Name = "Gear"
+ Gear.RobloxLocked = true
+ Gear.BackgroundTransparency = 1
+ Gear.Size = UDim2.new(1,0,1,0)
+ Gear.ClipsDescendants = true
+ Gear.Parent = Backpack
+
+ -- Gear Children
+ local AssetsList = Instance.new("Frame")
+ AssetsList.RobloxLocked = true
+ AssetsList.Name = "AssetsList"
+ AssetsList.BackgroundTransparency = 1
+ AssetsList.Size = UDim2.new(0.2,0,1,0)
+ AssetsList.Style = Enum.FrameStyle.RobloxSquare
+ AssetsList.Visible = false
+ AssetsList.Parent = Gear
+
+ local GearGrid = Instance.new("Frame")
+ GearGrid.RobloxLocked = true
+ GearGrid.Name = "GearGrid"
+ GearGrid.Size = UDim2.new(0.95, 0, 1, 0)
+ GearGrid.BackgroundTransparency = 1
+ GearGrid.Parent = Gear
+
+
+ local GearButton = Instance.new("ImageButton")
+ GearButton.RobloxLocked = true
+ GearButton.Visible = false
+ GearButton.Name = "GearButton"
+ GearButton.Size = UDim2.new(0, ICON_SIZE, 0, ICON_SIZE)
+ GearButton.Style = 'Custom'
+ GearButton.Parent = GearGrid
+ GearButton.BackgroundTransparency = 1.0
+
+ local slotBackground = Instance.new('Frame')
+ slotBackground.Name = 'Background'
+ slotBackground.BackgroundTransparency = 1.0
+ slotBackground.Size = UDim2.new(1, 16, 1, 16)
+ slotBackground.Position = UDim2.new(0, -8, 0, -8)
+ slotBackground.Parent = GearButton
+ slotBackground.Style = "DropShadow"
+
+
+ -- GearButton Children
+ local GearReference = Instance.new("ObjectValue")
+ GearReference.RobloxLocked = true
+ GearReference.Name = "GearReference"
+ GearReference.Parent = GearButton
+
+ local GreyOutButton = Instance.new("Frame")
+ GreyOutButton.RobloxLocked = true
+ GreyOutButton.Name = "GreyOutButton"
+ GreyOutButton.BackgroundTransparency = 0.5
+ GreyOutButton.Size = UDim2.new(1,0,1,0)
+ GreyOutButton.Active = true
+ GreyOutButton.Visible = false
+ GreyOutButton.ZIndex = 3
+ GreyOutButton.Parent = GearButton
+
+ local GearText = Instance.new("TextLabel")
+ GearText.RobloxLocked = true
+ GearText.Name = "GearText"
+ GearText.BackgroundTransparency = 1
+ GearText.Font = Enum.Font.Arial
+ GearText.FontSize = Enum.FontSize.Size14
+ GearText.Position = UDim2.new(0,-8,0,-8)
+ GearText.Size = UDim2.new(1,16,1,16)
+ GearText.Text = ""
+ GearText.ZIndex = 2
+ GearText.TextColor3 = Color3.new(1,1,1)
+ GearText.TextWrap = true
+ GearText.Parent = GearButton
+
+ local GearGridScrollingArea = Instance.new("Frame")
+ GearGridScrollingArea.RobloxLocked = true
+ GearGridScrollingArea.Name = "GearGridScrollingArea"
+ GearGridScrollingArea.Position = UDim2.new(1, -19, 0, 35)
+ GearGridScrollingArea.Size = UDim2.new(0, 17, 1, -45)
+ GearGridScrollingArea.BackgroundTransparency = 1
+ GearGridScrollingArea.Parent = Gear
+
+ local GearLoadouts = Instance.new("Frame")
+ GearLoadouts.RobloxLocked = true
+ GearLoadouts.Name = "GearLoadouts"
+ GearLoadouts.BackgroundTransparency = 1
+ GearLoadouts.Position = UDim2.new(0.7,23,0.5,1)
+ GearLoadouts.Size = UDim2.new(0.3,-23,0.5,-1)
+ GearLoadouts.Parent = Gear
+ GearLoadouts.Visible = false
+
+ -- GearLoadouts Children
+ local GearLoadoutsHeader = Instance.new("Frame")
+ GearLoadoutsHeader.RobloxLocked = true
+ GearLoadoutsHeader.Name = "GearLoadoutsHeader"
+ GearLoadoutsHeader.BackgroundColor3 = Color3.new(0,0,0)
+ GearLoadoutsHeader.BackgroundTransparency = 0.2
+ GearLoadoutsHeader.BorderColor3 = Color3.new(1,0,0)
+ GearLoadoutsHeader.Size = UDim2.new(1,2,0.15,-1)
+ GearLoadoutsHeader.Parent = GearLoadouts
+
+ -- GearLoadoutsHeader Children
+ local LoadoutsHeaderText = Instance.new("TextLabel")
+ LoadoutsHeaderText.RobloxLocked = true
+ LoadoutsHeaderText.Name = "LoadoutsHeaderText"
+ LoadoutsHeaderText.BackgroundTransparency = 1
+ LoadoutsHeaderText.Font = Enum.Font.ArialBold
+ LoadoutsHeaderText.FontSize = Enum.FontSize.Size18
+ LoadoutsHeaderText.Size = UDim2.new(1,0,1,0)
+ LoadoutsHeaderText.Text = "Loadouts"
+ LoadoutsHeaderText.TextColor3 = Color3.new(1,1,1)
+ LoadoutsHeaderText.Parent = GearLoadoutsHeader
+
+ local GearLoadoutsScrollingArea = GearGridScrollingArea:clone()
+ GearLoadoutsScrollingArea.RobloxLocked = true
+ GearLoadoutsScrollingArea.Name = "GearLoadoutsScrollingArea"
+ GearLoadoutsScrollingArea.Position = UDim2.new(1,-15,0.15,2)
+ GearLoadoutsScrollingArea.Size = UDim2.new(0,17,0.85,-2)
+ GearLoadoutsScrollingArea.Parent = GearLoadouts
+
+ local LoadoutsList = Instance.new("Frame")
+ LoadoutsList.RobloxLocked = true
+ LoadoutsList.Name = "LoadoutsList"
+ LoadoutsList.Position = UDim2.new(0,0,0.15,2)
+ LoadoutsList.Size = UDim2.new(1,-17,0.85,-2)
+ LoadoutsList.Style = Enum.FrameStyle.RobloxSquare
+ LoadoutsList.Parent = GearLoadouts
+
+ local GearPreview = Instance.new("Frame")
+ GearPreview.RobloxLocked = true
+ GearPreview.Name = "GearPreview"
+ GearPreview.Position = UDim2.new(0.7,23,0,0)
+ GearPreview.Size = UDim2.new(0.3,-28,0.5,-1)
+ GearPreview.BackgroundTransparency = 1
+ GearPreview.ZIndex = 7
+ GearPreview.Parent = Gear
+
+ -- GearPreview Children
+ local GearStats = Instance.new("Frame")
+ GearStats.RobloxLocked = true
+ GearStats.Name = "GearStats"
+ GearStats.BackgroundTransparency = 1
+ GearStats.Position = UDim2.new(0,0,0.75,0)
+ GearStats.Size = UDim2.new(1,0,0.25,0)
+ GearStats.ZIndex = 8
+ GearStats.Parent = GearPreview
+
+ -- GearStats Children
+ local GearName = Instance.new("TextLabel")
+ GearName.RobloxLocked = true
+ GearName.Name = "GearName"
+ GearName.BackgroundTransparency = 1
+ GearName.Font = Enum.Font.ArialBold
+ GearName.FontSize = Enum.FontSize.Size18
+ GearName.Position = UDim2.new(0,-3,0,0)
+ GearName.Size = UDim2.new(1,6,1,5)
+ GearName.Text = ""
+ GearName.TextColor3 = Color3.new(1,1,1)
+ GearName.TextWrap = true
+ GearName.ZIndex = 9
+ GearName.Parent = GearStats
+
+ local GearImage = Instance.new("ImageLabel")
+ GearImage.RobloxLocked = true
+ GearImage.Name = "GearImage"
+ GearImage.Image = ""
+ GearImage.BackgroundTransparency = 1
+ GearImage.Position = UDim2.new(0.125,0,0,0)
+ GearImage.Size = UDim2.new(0.75,0,0.75,0)
+ GearImage.ZIndex = 8
+ GearImage.Parent = GearPreview
+
+ --GearImage Children
+ local GearIcons = Instance.new("Frame")
+ GearIcons.BackgroundColor3 = Color3.new(0,0,0)
+ GearIcons.BackgroundTransparency = 0.5
+ GearIcons.BorderSizePixel = 0
+ GearIcons.RobloxLocked = true
+ GearIcons.Name = "GearIcons"
+ GearIcons.Position = UDim2.new(0.4,2,0.85,-2)
+ GearIcons.Size = UDim2.new(0.6,0,0.15,0)
+ GearIcons.Visible = false
+ GearIcons.ZIndex = 9
+ GearIcons.Parent = GearImage
+
+ -- GearIcons Children
+ local GenreImage = Instance.new("ImageLabel")
+ GenreImage.RobloxLocked = true
+ GenreImage.Name = "GenreImage"
+ GenreImage.BackgroundColor3 = Color3.new(102/255,153/255,1)
+ GenreImage.BackgroundTransparency = 0.5
+ GenreImage.BorderSizePixel = 0
+ GenreImage.Size = UDim2.new(0.25,0,1,0)
+ GenreImage.Parent = GearIcons
+
+ local AttributeOneImage = GenreImage:clone()
+ AttributeOneImage.RobloxLocked = true
+ AttributeOneImage.Name = "AttributeOneImage"
+ AttributeOneImage.BackgroundColor3 = Color3.new(1,51/255,0)
+ AttributeOneImage.Position = UDim2.new(0.25,0,0,0)
+ AttributeOneImage.Parent = GearIcons
+
+ local AttributeTwoImage = GenreImage:clone()
+ AttributeTwoImage.RobloxLocked = true
+ AttributeTwoImage.Name = "AttributeTwoImage"
+ AttributeTwoImage.BackgroundColor3 = Color3.new(153/255,1,153/255)
+ AttributeTwoImage.Position = UDim2.new(0.5,0,0,0)
+ AttributeTwoImage.Parent = GearIcons
+
+ local AttributeThreeImage = GenreImage:clone()
+ AttributeThreeImage.RobloxLocked = true
+ AttributeThreeImage.Name = "AttributeThreeImage"
+ AttributeThreeImage.BackgroundColor3 = Color3.new(0,0.5,0.5)
+ AttributeThreeImage.Position = UDim2.new(0.75,0,0,0)
+ AttributeThreeImage.Parent = GearIcons
+
+script:Destroy()
\ No newline at end of file
diff --git a/asset/backup/16 b/asset/backup/16
new file mode 100644
index 0000000..33af1b5
--- /dev/null
+++ b/asset/backup/16
@@ -0,0 +1,416 @@
+-- This script manages context switches in the backpack (Gear to Wardrobe, etc.) and player state changes. Also manages global functions across different tabs (currently only search)
+
+-- basic functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+-- don't do anything if we are in an empty game
+waitForChild(game,"Players")
+if #game.Players:GetChildren() < 1 then
+ game.Players.ChildAdded:wait()
+end
+-- make sure everything is loaded in before we do anything
+-- get our local player
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+
+
+------------------------ Locals ------------------------------
+local backpack = script.Parent
+waitForChild(backpack,"Gear")
+
+local screen = script.Parent.Parent
+assert(screen:IsA("ScreenGui"))
+
+waitForChild(backpack, "Tabs")
+waitForChild(backpack.Tabs, "CloseButton")
+local closeButton = backpack.Tabs.CloseButton
+
+waitForChild(backpack.Tabs, "InventoryButton")
+local inventoryButton = backpack.Tabs.InventoryButton
+
+waitForChild(backpack.Parent,"ControlFrame")
+local backpackButton = waitForChild(backpack.Parent.ControlFrame,"BackpackButton")
+local currentTab = "gear"
+
+local searchFrame = waitForChild(backpack,"SearchFrame")
+waitForChild(backpack.SearchFrame,"SearchBoxFrame")
+local searchBox = waitForChild(backpack.SearchFrame.SearchBoxFrame,"SearchBox")
+local searchButton = waitForChild(backpack.SearchFrame,"SearchButton")
+local resetButton = waitForChild(backpack.SearchFrame,"ResetButton")
+
+local robloxGui = waitForChild(Game.CoreGui, 'RobloxGui')
+local currentLoadout = waitForChild(robloxGui, 'CurrentLoadout')
+
+local canToggle = true
+local readyForNextEvent = true
+local backpackIsOpen = false
+local active = true
+local disabledByDeveloper = false
+
+local humanoidDiedCon = nil
+
+local backpackButtonPos
+
+local guiTweenSpeed = 0.25 -- how quickly we open/close the backpack
+
+local searchDefaultText = "Search..."
+local tilde = "~"
+local backquote = "`"
+
+local backpackSize = UDim2.new(0, 600, 0, 400)
+
+if robloxGui.AbsoluteSize.Y <= 500 then
+ backpackSize = UDim2.new(0, 200, 0, 140)
+end
+
+
+------------------------ End Locals ---------------------------
+
+
+---------------------------------------- Public Event Setup ----------------------------------------
+
+function createPublicEvent(eventName)
+ assert(eventName, "eventName is nil")
+ assert(tostring(eventName),"eventName is not a string")
+
+ local newEvent = Instance.new("BindableEvent")
+ newEvent.Name = tostring(eventName)
+ newEvent.Parent = script
+
+ return newEvent
+end
+
+function createPublicFunction(funcName, invokeFunc)
+ assert(funcName, "funcName is nil")
+ assert(tostring(funcName), "funcName is not a string")
+ assert(invokeFunc, "invokeFunc is nil")
+ assert(type(invokeFunc) == "function", "invokeFunc should be of type 'function'")
+
+ local newFunction = Instance.new("BindableFunction")
+ newFunction.Name = tostring(funcName)
+ newFunction.OnInvoke = invokeFunc
+ newFunction.Parent = script
+
+ return newFunction
+end
+
+-- Events
+local resizeEvent = createPublicEvent("ResizeEvent")
+local backpackOpenEvent = createPublicEvent("BackpackOpenEvent")
+local backpackCloseEvent = createPublicEvent("BackpackCloseEvent")
+local tabClickedEvent = createPublicEvent("TabClickedEvent")
+local searchRequestedEvent = createPublicEvent("SearchRequestedEvent")
+---------------------------------------- End Public Event Setup ----------------------------------------
+
+
+
+--------------------------- Internal Functions ----------------------------------------
+
+function deactivateBackpack()
+ backpack.Visible = false
+ active = false
+end
+
+function activateBackpack()
+ initHumanoidDiedConnections()
+ active = true
+ backpack.Visible = backpackIsOpen
+ if backpackIsOpen then
+ toggleBackpack()
+ end
+end
+
+function initHumanoidDiedConnections()
+ if humanoidDiedCon then
+ humanoidDiedCon:disconnect()
+ end
+ waitForProperty(game.Players.LocalPlayer,"Character")
+ waitForChild(game.Players.LocalPlayer.Character,"Humanoid")
+ humanoidDiedCon = game.Players.LocalPlayer.Character.Humanoid.Died:connect(deactivateBackpack)
+end
+
+local hideBackpack = function()
+ backpackIsOpen = false
+ readyForNextEvent = false
+ backpackButton.Selected = false
+ resetSearch()
+ backpackCloseEvent:Fire(currentTab)
+ backpack.Tabs.Visible = false
+ searchFrame.Visible = false
+ backpack:TweenSizeAndPosition(UDim2.new(0, backpackSize.X.Offset,0, 0), UDim2.new(0.5, -backpackSize.X.Offset/2, 1, -85), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, guiTweenSpeed, true,
+ function()
+ game.GuiService:RemoveCenterDialog(backpack)
+ backpack.Visible = false
+ backpackButton.Selected = false
+ end)
+ delay(guiTweenSpeed,function()
+ game.GuiService:RemoveCenterDialog(backpack)
+ backpack.Visible = false
+ backpackButton.Selected = false
+ readyForNextEvent = true
+ canToggle = true
+ end)
+end
+
+function showBackpack()
+ game.GuiService:AddCenterDialog(backpack, Enum.CenterDialogType.PlayerInitiatedDialog,
+ function()
+ backpack.Visible = true
+ backpackButton.Selected = true
+ end,
+ function()
+ backpack.Visible = false
+ backpackButton.Selected = false
+ end)
+ backpack.Visible = true
+ backpackButton.Selected = true
+ backpack:TweenSizeAndPosition(backpackSize, UDim2.new(0.5, -backpackSize.X.Offset/2, 1, -backpackSize.Y.Offset - 88), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, guiTweenSpeed, true)
+ delay(guiTweenSpeed,function()
+ backpack.Tabs.Visible = false
+ searchFrame.Visible = true
+ backpackOpenEvent:Fire(currentTab)
+ canToggle = true
+ readyForNextEvent = true
+ backpackButton.Image = "rbxasset://textures/ui/Backpack_Close.png"
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -backpackSize.Y.Offset - 108)
+ end)
+end
+
+function toggleBackpack()
+ if not game.Players.LocalPlayer then return end
+ if not game.Players.LocalPlayer["Character"] then return end
+ if not canToggle then return end
+ if not readyForNextEvent then return end
+ readyForNextEvent = false
+ canToggle = false
+
+ backpackIsOpen = not backpackIsOpen
+
+ if backpackIsOpen then
+ showBackpack()
+ else
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+ backpackButton.Selected = false
+ backpackButton.Image = "rbxasset://textures/ui/Backpack_Open.png"
+ hideBackpack()
+
+
+ local clChildren = currentLoadout:GetChildren()
+ for i = 1, #clChildren do
+ if clChildren[i] and clChildren[i]:IsA('Frame') then
+ local frame = clChildren[i]
+ if #frame:GetChildren() > 0 then
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -108)
+ backpackButton.Visible = true
+ if frame:GetChildren()[1]:IsA('ImageButton') then
+ local imgButton = frame:GetChildren()[1]
+ imgButton.Active = true
+ imgButton.Draggable = false
+ end
+ end
+ end
+ end
+
+ end
+end
+
+function closeBackpack()
+ if backpackIsOpen then
+ toggleBackpack()
+ end
+end
+
+function setSelected(tab)
+ assert(tab)
+ assert(tab:IsA("TextButton"))
+
+ tab.BackgroundColor3 = Color3.new(1,1,1)
+ tab.TextColor3 = Color3.new(0,0,0)
+ tab.Selected = true
+ tab.ZIndex = 3
+end
+
+function setUnselected(tab)
+ assert(tab)
+ assert(tab:IsA("TextButton"))
+
+ tab.BackgroundColor3 = Color3.new(0,0,0)
+ tab.TextColor3 = Color3.new(1,1,1)
+ tab.Selected = false
+ tab.ZIndex = 1
+end
+
+function updateTabGui(selectedTab)
+ assert(selectedTab)
+
+ if selectedTab == "gear" then
+ setSelected(inventoryButton)
+ elseif selectedTab == "wardrobe" then
+ setUnselected(inventoryButton)
+ end
+end
+
+function mouseLeaveTab(button)
+ assert(button)
+ assert(button:IsA("TextButton"))
+
+ if button.Selected then return end
+
+ button.BackgroundColor3 = Color3.new(0,0,0)
+end
+
+function mouseOverTab(button)
+ assert(button)
+ assert(button:IsA("TextButton"))
+
+ if button.Selected then return end
+
+ button.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+end
+
+function newTabClicked(tabName)
+ assert(tabName)
+ tabName = string.lower(tabName)
+ currentTab = tabName
+
+ updateTabGui(tabName)
+ tabClickedEvent:Fire(tabName)
+ resetSearch()
+end
+
+function trim(s)
+ return (s:gsub("^%s*(.-)%s*$", "%1"))
+end
+
+function splitByWhitespace(text)
+ if type(text) ~= "string" then return nil end
+
+ local terms = {}
+ for token in string.gmatch(text, "[^%s]+") do
+ if string.len(token) > 0 then
+ table.insert(terms,token)
+ end
+ end
+ return terms
+end
+
+function resetSearchBoxGui()
+ resetButton.Visible = false
+ searchBox.Text = searchDefaultText
+end
+
+function doSearch()
+ local searchText = searchBox.Text
+ if searchText == "" then
+ resetSearch()
+ return
+ end
+ searchText = trim(searchText)
+ resetButton.Visible = true
+ termTable = splitByWhitespace(searchText)
+ searchRequestedEvent:Fire(searchText) -- todo: replace this with termtable when table passing is possible
+end
+
+function resetSearch()
+ resetSearchBoxGui()
+ searchRequestedEvent:Fire()
+end
+
+local backpackReady = function()
+ readyForNextEvent = true
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ active = enabled
+ disabledByDeveloper = not enabled
+
+ if disabledByDeveloper then
+ game:GetService("GuiService"):RemoveKey(tilde)
+ game:GetService("GuiService"):RemoveKey(backquote)
+ else
+ game:GetService("GuiService"):AddKey(tilde)
+ game:GetService("GuiService"):AddKey(backquote)
+ end
+
+ resetSearch()
+ searchFrame.Visible = enabled and backpackIsOpen
+
+ currentLoadout.Visible = enabled
+ backpack.Visible = false
+ backpackButton.Visible = enabled
+ end
+end
+
+--------------------------- End Internal Functions -------------------------------------
+
+
+------------------------------ Public Functions Setup -------------------------------------
+createPublicFunction("CloseBackpack", hideBackpack)
+createPublicFunction("BackpackReady", backpackReady)
+------------------------------ End Public Functions Setup ---------------------------------
+
+
+------------------------ Connections/Script Main -------------------------------------------
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+inventoryButton.MouseButton1Click:connect(function() newTabClicked("gear") end)
+inventoryButton.MouseEnter:connect(function() mouseOverTab(inventoryButton) end)
+inventoryButton.MouseLeave:connect(function() mouseLeaveTab(inventoryButton) end)
+
+closeButton.MouseButton1Click:connect(closeBackpack)
+
+screen.Changed:connect(function(prop)
+ if prop == "AbsoluteSize" then
+ resizeEvent:Fire(screen.AbsoluteSize)
+ end
+end)
+
+-- GuiService key setup
+game:GetService("GuiService"):AddKey(tilde)
+game:GetService("GuiService"):AddKey(backquote)
+game:GetService("GuiService").KeyPressed:connect(function(key)
+ if not active or disabledByDeveloper then return end
+ if key == tilde or key == backquote then
+ toggleBackpack()
+ end
+end)
+backpackButton.MouseButton1Click:connect(function()
+ if not active or disabledByDeveloper then return end
+ toggleBackpack()
+end)
+
+if game.Players.LocalPlayer["Character"] then
+ activateBackpack()
+end
+
+game.Players.LocalPlayer.CharacterAdded:connect(activateBackpack)
+
+-- search functions
+searchBox.FocusLost:connect(function(enterPressed)
+ if enterPressed or searchBox.Text ~= "" then
+ doSearch()
+ elseif searchBox.Text == "" then
+ resetSearch()
+ end
+end)
+searchButton.MouseButton1Click:connect(doSearch)
+resetButton.MouseButton1Click:connect(resetSearch)
+
+if searchFrame and robloxGui.AbsoluteSize.Y <= 500 then
+ searchFrame.RobloxLocked = false
+ searchFrame:Destroy()
+end
\ No newline at end of file
diff --git a/asset/backup/17 b/asset/backup/17
new file mode 100644
index 0000000..259c3fb
--- /dev/null
+++ b/asset/backup/17
@@ -0,0 +1,872 @@
+%17%
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ assert(instance)
+ assert(name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ assert(instance)
+ assert(property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+local RbxGui, msg = LoadLibrary("RbxGui")
+if not RbxGui then print("could not find RbxGui!") return end
+
+--- Begin Locals
+local StaticTabName = "gear"
+
+local backpack = script.Parent
+local screen = script.Parent.Parent
+
+local backpackItems = {}
+local buttons = {}
+
+local debounce = false
+local browsingMenu = false
+
+local mouseEnterCons = {}
+local mouseClickCons = {}
+
+local characterChildAddedCon = nil
+local characterChildRemovedCon = nil
+local backpackAddCon = nil
+
+local playerBackpack = waitForChild(player,"Backpack")
+
+waitForChild(backpack,"Tabs")
+
+waitForChild(backpack,"Gear")
+local gearPreview = waitForChild(backpack.Gear,"GearPreview")
+
+local scroller = waitForChild(backpack.Gear,"GearGridScrollingArea")
+
+local currentLoadout = waitForChild(backpack.Parent,"CurrentLoadout")
+
+local grid = waitForChild(backpack.Gear,"GearGrid")
+local gearButton = waitForChild(grid,"GearButton")
+
+local swapSlot = waitForChild(script.Parent,"SwapSlot")
+
+local backpackManager = waitForChild(script.Parent,"CoreScripts/BackpackScripts/BackpackManager")
+local backpackOpenEvent = waitForChild(backpackManager,"BackpackOpenEvent")
+local backpackCloseEvent = waitForChild(backpackManager,"BackpackCloseEvent")
+local tabClickedEvent = waitForChild(backpackManager,"TabClickedEvent")
+local resizeEvent = waitForChild(backpackManager,"ResizeEvent")
+local searchRequestedEvent = waitForChild(backpackManager,"SearchRequestedEvent")
+local tellBackpackReadyFunc = waitForChild(backpackManager,"BackpackReady")
+
+-- creating scroll bar early as to make sure items get placed correctly
+local scrollFrame, scrollUp, scrollDown, recalculateScroll = RbxGui.CreateScrollingFrame(nil, "grid", Vector2.new(6, 6))
+
+scrollFrame.Position = UDim2.new(0,0,0,30)
+scrollFrame.Size = UDim2.new(1,0,1,-30)
+scrollFrame.Parent = backpack.Gear.GearGrid
+
+local scrollBar = Instance.new("Frame")
+scrollBar.Name = "ScrollBar"
+scrollBar.BackgroundTransparency = 0.9
+scrollBar.BackgroundColor3 = Color3.new(1,1,1)
+scrollBar.BorderSizePixel = 0
+scrollBar.Size = UDim2.new(0, 17, 1, -36)
+scrollBar.Position = UDim2.new(0,0,0,18)
+scrollBar.Parent = scroller
+
+scrollDown.Position = UDim2.new(0,0,1,-17)
+
+scrollUp.Parent = scroller
+scrollDown.Parent = scroller
+
+local scrollFrameLoadout, scrollUpLoadout, scrollDownLoadout, recalculateScrollLoadout = RbxGui.CreateScrollingFrame()
+
+scrollFrameLoadout.Position = UDim2.new(0,0,0,0)
+scrollFrameLoadout.Size = UDim2.new(1,0,1,0)
+scrollFrameLoadout.Parent = backpack.Gear.GearLoadouts.LoadoutsList
+
+local LoadoutButton = Instance.new("TextButton")
+LoadoutButton.RobloxLocked = true
+LoadoutButton.Name = "LoadoutButton"
+LoadoutButton.Font = Enum.Font.ArialBold
+LoadoutButton.FontSize = Enum.FontSize.Size14
+LoadoutButton.Position = UDim2.new(0,0,0,0)
+LoadoutButton.Size = UDim2.new(1,0,0,32)
+LoadoutButton.Style = Enum.ButtonStyle.RobloxButton
+LoadoutButton.Text = "Loadout #1"
+LoadoutButton.TextColor3 = Color3.new(1,1,1)
+LoadoutButton.Parent = scrollFrameLoadout
+
+local LoadoutButtonTwo = LoadoutButton:clone()
+LoadoutButtonTwo.Text = "Loadout #2"
+LoadoutButtonTwo.Parent = scrollFrameLoadout
+
+local LoadoutButtonThree = LoadoutButton:clone()
+LoadoutButtonThree.Text = "Loadout #3"
+LoadoutButtonThree.Parent = scrollFrameLoadout
+
+local LoadoutButtonFour = LoadoutButton:clone()
+LoadoutButtonFour.Text = "Loadout #4"
+LoadoutButtonFour.Parent = scrollFrameLoadout
+
+local scrollBarLoadout = Instance.new("Frame")
+scrollBarLoadout.Name = "ScrollBarLoadout"
+scrollBarLoadout.BackgroundTransparency = 0.9
+scrollBarLoadout.BackgroundColor3 = Color3.new(1,1,1)
+scrollBarLoadout.BorderSizePixel = 0
+scrollBarLoadout.Size = UDim2.new(0, 17, 1, -36)
+scrollBarLoadout.Position = UDim2.new(0,0,0,18)
+scrollBarLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+
+scrollDownLoadout.Position = UDim2.new(0,0,1,-17)
+
+scrollUpLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+scrollDownLoadout.Parent = backpack.Gear.GearLoadouts.GearLoadoutsScrollingArea
+
+
+-- Begin Functions
+function removeFromMap(map,object)
+ for i = 1, #map do
+ if map[i] == object then
+ table.remove(map,i)
+ break
+ end
+ end
+end
+
+function robloxLock(instance)
+ instance.RobloxLocked = true
+ children = instance:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ robloxLock(child)
+ end
+ end
+end
+
+function resize()
+ local size = 0
+ if gearPreview.AbsoluteSize.Y > gearPreview.AbsoluteSize.X then
+ size = gearPreview.AbsoluteSize.X * 0.75
+ else
+ size = gearPreview.AbsoluteSize.Y * 0.75
+ end
+
+ waitForChild(gearPreview,"GearImage")
+ gearPreview.GearImage.Size = UDim2.new(0,size,0,size)
+ gearPreview.GearImage.Position = UDim2.new(0,gearPreview.AbsoluteSize.X/2 - size/2,0.75,-size)
+
+ resizeGrid()
+end
+
+function addToGrid(child)
+ if not child:IsA("Tool") then
+ if not child:IsA("HopperBin") then
+ return
+ end
+ end
+ if child:FindFirstChild("RobloxBuildTool") then return end
+
+ for i,v in pairs(backpackItems) do -- check to see if we already have this gear registered
+ if v == child then return end
+ end
+
+ table.insert(backpackItems,child)
+
+ local changeCon = child.Changed:connect(function(prop)
+ if prop == "Name" then
+ if buttons[child] then
+ if buttons[child].Image == "" then
+ buttons[child].GearText.Text = child.Name
+ end
+ end
+ end
+ end)
+ local ancestryCon = nil
+ ancestryCon = child.AncestryChanged:connect(function(theChild,theParent)
+ local thisObject = nil
+ for k,v in pairs(backpackItems) do
+ if v == child then
+ thisObject = v
+ break
+ end
+ end
+
+ waitForProperty(player,"Character")
+ waitForChild(player,"Backpack")
+ if (child.Parent ~= player.Backpack and child.Parent ~= player.Character) then
+ if ancestryCon then ancestryCon:disconnect() end
+ if changeCon then changeCon:disconnect() end
+
+ for k,v in pairs(backpackItems) do
+ if v == thisObject then
+ if mouseEnterCons[buttons[v]] then mouseEnterCons[buttons[v]]:disconnect() end
+ if mouseClickCons[buttons[v]] then mouseClickCons[buttons[v]]:disconnect() end
+ buttons[v].Parent = nil
+ buttons[v] = nil
+ break
+ end
+ end
+
+ removeFromMap(backpackItems,thisObject)
+
+ resizeGrid()
+ else
+ resizeGrid()
+ end
+ updateGridActive()
+ end)
+ resizeGrid()
+end
+
+function buttonClick(button)
+ if button:FindFirstChild("UnequipContextMenu") and not button.Active then
+ button.UnequipContextMenu.Visible = true
+ browsingMenu = true
+ end
+end
+
+function previewGear(button)
+ if not browsingMenu then
+ gearPreview.Visible = false
+ gearPreview.GearImage.Image = button.Image
+ gearPreview.GearStats.GearName.Text = button.GearReference.Value.Name
+ end
+end
+
+function findEmptySlot()
+ local smallestNum = nil
+ local loadout = currentLoadout:GetChildren()
+ for i = 1, #loadout do
+ if loadout[i]:IsA("Frame") and #loadout[i]:GetChildren() <= 0 then
+ local frameNum = tonumber(string.sub(loadout[i].Name,5))
+ if frameNum == 0 then frameNum = 10 end
+ if not smallestNum or (smallestNum > frameNum) then
+ smallestNum = frameNum
+ end
+ end
+ end
+ if smallestNum == 10 then smallestNum = 0 end
+ return smallestNum
+end
+
+function checkForSwap(button,x,y)
+ local loadoutChildren = currentLoadout:GetChildren()
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and string.find(loadoutChildren[i].Name,"Slot") then
+ if x >= loadoutChildren[i].AbsolutePosition.x and x <= (loadoutChildren[i].AbsolutePosition.x + loadoutChildren[i].AbsoluteSize.x) then
+ if y >= loadoutChildren[i].AbsolutePosition.y and y <= (loadoutChildren[i].AbsolutePosition.y + loadoutChildren[i].AbsoluteSize.y) then
+ local slot = tonumber(string.sub(loadoutChildren[i].Name,5))
+ swapGearSlot(slot,button)
+ return true
+ end
+ end
+ end
+ end
+ return false
+end
+
+function resizeGrid()
+ for k,v in pairs(backpackItems) do
+ if not v:FindFirstChild("RobloxBuildTool") then
+ if not buttons[v] then
+ local buttonClone = gearButton:clone()
+ buttonClone.Parent = grid.ScrollingFrame
+ buttonClone.Visible = true
+ buttonClone.Image = v.TextureId
+ if buttonClone.Image == "" then
+ buttonClone.GearText.Text = v.Name
+ end
+
+ buttonClone.GearReference.Value = v
+ buttonClone.Draggable = true
+ buttons[v] = buttonClone
+
+
+ if not IsTouchDevice() then
+ local unequipMenu = getGearContextMenu()
+
+
+ unequipMenu.Visible = false
+ unequipMenu.Parent = buttonClone
+ end
+
+ local beginPos = nil
+ buttonClone.DragBegin:connect(function(value)
+ waitForChild(buttonClone, 'Background')
+ buttonClone['Background'].ZIndex = 10
+ buttonClone.ZIndex = 10
+ beginPos = value
+ end)
+ buttonClone.DragStopped:connect(function(x,y)
+ waitForChild(buttonClone, 'Background')
+ buttonClone['Background'].ZIndex = 1.0
+ buttonClone.ZIndex = 2
+ if beginPos ~= buttonClone.Position then
+ if not checkForSwap(buttonClone,x,y) then
+ buttonClone:TweenPosition(beginPos,Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.5, true)
+ buttonClone.Draggable = false
+ delay(0.5,function()
+ buttonClone.Draggable = true
+ end)
+ else
+ buttonClone.Position = beginPos
+ end
+ end
+ end)
+ local clickTime = tick()
+ mouseEnterCons[buttonClone] = buttonClone.MouseEnter:connect(function() previewGear(buttonClone) end)
+ mouseClickCons[buttonClone] = buttonClone.MouseButton1Click:connect(function()
+ local newClickTime = tick()
+ if buttonClone.Active and (newClickTime - clickTime) < 0.5 then
+ local slot = findEmptySlot()
+ if slot then
+ buttonClone.ZIndex = 1
+ swapGearSlot(slot,buttonClone)
+ end
+ else
+ buttonClick(buttonClone)
+ end
+ clickTime = newClickTime
+ end)
+ end
+ end
+ end
+ recalculateScroll()
+end
+
+function showPartialGrid(subset)
+ for k,v in pairs(buttons) do
+ v.Parent = nil
+ end
+ if subset then
+ for k,v in pairs(subset) do
+ v.Parent = grid.ScrollingFrame
+ end
+ end
+ recalculateScroll()
+end
+
+function showEntireGrid()
+ for k,v in pairs(buttons) do
+ v.Parent = grid.ScrollingFrame
+ end
+ recalculateScroll()
+end
+
+function inLoadout(gear)
+ local children = currentLoadout:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("Frame") then
+ local button = children[i]:GetChildren()
+ if #button > 0 then
+ if button[1].GearReference.Value and button[1].GearReference.Value == gear then
+ return true
+ end
+ end
+ end
+ end
+ return false
+end
+
+function updateGridActive()
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ local gear = nil
+ local gearRef = buttons[v]:FindFirstChild("GearReference")
+
+ if gearRef then gear = gearRef.Value end
+
+ if not gear then
+ buttons[v].Active = false
+ elseif inLoadout(gear) then
+ buttons[v].Active = false
+ else
+ buttons[v].Active = true
+ end
+ end
+ end
+end
+
+function centerGear(loadoutChildren)
+ local gearButtons = {}
+ local lastSlotAdd = nil
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and #loadoutChildren[i]:GetChildren() > 0 then
+ if loadoutChildren[i].Name == "Slot0" then
+ lastSlotAdd = loadoutChildren[i]
+ else
+ table.insert(gearButtons, loadoutChildren[i])
+ end
+ end
+ end
+ if lastSlotAdd then table.insert(gearButtons,lastSlotAdd) end
+
+ local startPos = ( 1 - (#gearButtons * 0.1) ) / 2
+ for i = 1, #gearButtons do
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + ((i - 1) * 0.1),0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+end
+
+function tabClickHandler(tabName)
+ if tabName == StaticTabName then
+ backpackOpenHandler(tabName)
+ else
+ backpackCloseHandler(tabName)
+ end
+end
+
+function backpackOpenHandler(currentTab)
+ if currentTab and currentTab ~= StaticTabName then
+ backpack.Gear.Visible = false
+ return
+ end
+
+ backpack.Gear.Visible = true
+ updateGridActive()
+
+ resizeGrid()
+ resize()
+ tellBackpackReadyFunc:Invoke()
+end
+
+function backpackCloseHandler(currentTab)
+ if currentTab and currentTab ~= StaticTabName then
+ backpack.Gear.Visible = false
+ return
+ end
+
+ backpack.Gear.Visible = false
+
+ resizeGrid()
+ resize()
+ tellBackpackReadyFunc:Invoke()
+end
+
+function loadoutCheck(child, selectState)
+ if not child:IsA("ImageButton") then return end
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ if child:FindFirstChild("GearReference") and buttons[v]:FindFirstChild("GearReference") then
+ if buttons[v].GearReference.Value == child.GearReference.Value then
+ buttons[v].Active = selectState
+ break
+ end
+ end
+ end
+ end
+end
+
+function clearPreview()
+ gearPreview.GearImage.Image = ""
+ gearPreview.GearStats.GearName.Text = ""
+end
+
+function removeAllEquippedGear(physGear)
+ local stuff = player.Character:GetChildren()
+ for i = 1, #stuff do
+ if ( stuff[i]:IsA("Tool") or stuff[i]:IsA("HopperBin") ) and stuff[i] ~= physGear then
+ stuff[i].Parent = playerBackpack
+ end
+ end
+end
+
+function equipGear(physGear)
+ removeAllEquippedGear(physGear)
+ physGear.Parent = player.Character
+ updateGridActive()
+end
+
+function unequipGear(physGear)
+ physGear.Parent = playerBackpack
+ updateGridActive()
+end
+
+function highlight(button)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundColor3 = Color3.new(0.8,0.8,0.8)
+end
+function clearHighlight(button)
+ button.TextColor3 = Color3.new(1,1,1)
+ button.BackgroundColor3 = Color3.new(0,0,0)
+end
+
+function swapGearSlot(slot,gearButton)
+ if not swapSlot.Value then -- signal loadout to swap a gear out
+ swapSlot.Slot.Value = slot
+ swapSlot.GearButton.Value = gearButton
+ swapSlot.Value = true
+ updateGridActive()
+ end
+end
+
+
+local UnequipGearMenuClick = function(element, menu)
+ if type(element.Action) ~= "number" then return end
+ local num = element.Action
+ if num == 1 then -- remove from loadout
+ unequipGear(menu.Parent.GearReference.Value)
+ local inventoryButton = menu.Parent
+ local gearToUnequip = inventoryButton.GearReference.Value
+ local loadoutChildren = currentLoadout:GetChildren()
+ local slot = -1
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ local button = loadoutChildren[i]:GetChildren()
+ if button[1] and button[1].GearReference.Value == gearToUnequip then
+ slot = button[1].SlotNumber.Text
+ break
+ end
+ end
+ end
+ swapGearSlot(slot,nil)
+ end
+end
+
+function setupCharacterConnections()
+
+ if backpackAddCon then backpackAddCon:disconnect() end
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+
+ -- make sure we get all the children
+ local backpackChildren = game.Players.LocalPlayer.Backpack:GetChildren()
+ for i = 1, #backpackChildren do
+ addToGrid(backpackChildren[i])
+ end
+
+ if characterChildAddedCon then characterChildAddedCon:disconnect() end
+ characterChildAddedCon =
+ game.Players.LocalPlayer.Character.ChildAdded:connect(function(child)
+ addToGrid(child)
+ updateGridActive()
+ end)
+
+ if characterChildRemovedCon then characterChildRemovedCon:disconnect() end
+ characterChildRemovedCon =
+ game.Players.LocalPlayer.Character.ChildRemoved:connect(function(child)
+ updateGridActive()
+ end)
+
+ wait()
+ centerGear(currentLoadout:GetChildren())
+end
+
+function removeCharacterConnections()
+ if characterChildAddedCon then characterChildAddedCon:disconnect() end
+ if characterChildRemovedCon then characterChildRemovedCon:disconnect() end
+ if backpackAddCon then backpackAddCon:disconnect() end
+end
+
+function trim(s)
+ return (s:gsub("^%s*(.-)%s*$", "%1"))
+end
+
+function filterGear(terms)
+ local filteredGear = {}
+ for k,v in pairs(backpackItems) do
+ if buttons[v] then
+ local gearString = string.lower(buttons[v].GearReference.Value.Name)
+ gearString = trim(gearString)
+ for i = 1, #terms do
+ if string.match(gearString,terms[i]) then
+ table.insert(filteredGear,buttons[v])
+ break
+ end
+ end
+ end
+ end
+
+ return filteredGear
+end
+function splitByWhitespace(text)
+ if type(text) ~= "string" then return nil end
+
+ local terms = {}
+ for token in string.gmatch(text, "[^%s]+") do
+ if string.len(token) > 0 then
+ table.insert(terms,token)
+ end
+ end
+ return terms
+end
+function showSearchGear(searchTerms)
+ if not backpack.Gear.Visible then return end -- currently not active tab
+
+ local searchTermTable = splitByWhitespace(searchTerms)
+ if searchTermTable and (#searchTermTable > 0) then
+ currSearchTerms = searchTermTable
+ else
+ currSearchTerms = nil
+ end
+
+ if searchTermTable == nil then
+ showEntireGrid()
+ return
+ end
+
+ local filteredButtons = filterGear(currSearchTerms)
+ showPartialGrid(filteredButtons)
+end
+
+function nukeBackpack()
+ while #buttons > 0 do
+ table.remove(buttons)
+ end
+ buttons = {}
+ while #backpackItems > 0 do
+ table.remove(backpackItems)
+ end
+ backpackItems = {}
+ local scrollingFrameChildren = grid.ScrollingFrame:GetChildren()
+ for i = 1, #scrollingFrameChildren do
+ scrollingFrameChildren[i]:remove()
+ end
+end
+
+function getGearContextMenu()
+ local gearContextMenu = Instance.new("Frame")
+ gearContextMenu.Active = true
+ gearContextMenu.Name = "UnequipContextMenu"
+ gearContextMenu.Size = UDim2.new(0,115,0,70)
+ gearContextMenu.Position = UDim2.new(0,-16,0,-16)
+ gearContextMenu.BackgroundTransparency = 1
+ gearContextMenu.Visible = false
+
+ local gearContextMenuButton = Instance.new("TextButton")
+ gearContextMenuButton.Name = "UnequipContextMenuButton"
+ gearContextMenuButton.Text = ""
+ gearContextMenuButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ gearContextMenuButton.ZIndex = 8
+ gearContextMenuButton.Size = UDim2.new(1, 0, 1, -20)
+ gearContextMenuButton.Visible = true
+ gearContextMenuButton.Parent = gearContextMenu
+
+ local elementHeight = 12
+
+ local contextMenuElements = {}
+ local contextMenuElementsName = {"Remove Hotkey"}
+
+ for i = 1, #contextMenuElementsName do
+ local element = {}
+ element.Type = "Button"
+ element.Text = contextMenuElementsName[i]
+ element.Action = i
+ element.DoIt = UnequipGearMenuClick
+ table.insert(contextMenuElements,element)
+ end
+
+ for i, contextElement in ipairs(contextMenuElements) do
+ local element = contextElement
+ if element.Type == "Button" then
+ local button = Instance.new("TextButton")
+ button.Name = "UnequipContextButton" .. i
+ button.BackgroundColor3 = Color3.new(0,0,0)
+ button.BorderSizePixel = 0
+ button.TextXAlignment = Enum.TextXAlignment.Left
+ button.Text = " " .. contextElement.Text
+ button.Font = Enum.Font.Arial
+ button.FontSize = Enum.FontSize.Size14
+ button.Size = UDim2.new(1, 8, 0, elementHeight)
+ button.Position = UDim2.new(0,0,0,elementHeight * i)
+ button.TextColor3 = Color3.new(1,1,1)
+ button.ZIndex = 9
+ button.Parent = gearContextMenuButton
+
+ if not IsTouchDevice() then
+
+ button.MouseButton1Click:connect(function()
+ if button.Active and not gearContextMenu.Parent.Active then
+ local success, result = pcall(function() element.DoIt(element, gearContextMenu) end)
+ browsingMenu = false
+ gearContextMenu.Visible = false
+ clearHighlight(button)
+ clearPreview()
+ end
+ end)
+
+ button.MouseEnter:connect(function()
+ if button.Active and gearContextMenu.Parent.Active then
+ highlight(button)
+ end
+ end)
+ button.MouseLeave:connect(function()
+ if button.Active and gearContextMenu.Parent.Active then
+ clearHighlight(button)
+ end
+ end)
+ end
+
+ contextElement.Button = button
+ contextElement.Element = button
+ elseif element.Type == "Label" then
+ local frame = Instance.new("Frame")
+ frame.Name = "ContextLabel" .. i
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1, 8, 0, elementHeight)
+
+ local label = Instance.new("TextLabel")
+ label.Name = "Text1"
+ label.BackgroundTransparency = 1
+ label.BackgroundColor3 = Color3.new(1,1,1)
+ label.BorderSizePixel = 0
+ label.TextXAlignment = Enum.TextXAlignment.Left
+ label.Font = Enum.Font.ArialBold
+ label.FontSize = Enum.FontSize.Size14
+ label.Position = UDim2.new(0.0, 0, 0, 0)
+ label.Size = UDim2.new(0.5, 0, 1, 0)
+ label.TextColor3 = Color3.new(1,1,1)
+ label.ZIndex = 9
+ label.Parent = frame
+ element.Label1 = label
+
+ if element.GetText2 then
+ label = Instance.new("TextLabel")
+ label.Name = "Text2"
+ label.BackgroundTransparency = 1
+ label.BackgroundColor3 = Color3.new(1,1,1)
+ label.BorderSizePixel = 0
+ label.TextXAlignment = Enum.TextXAlignment.Right
+ label.Font = Enum.Font.Arial
+ label.FontSize = Enum.FontSize.Size14
+ label.Position = UDim2.new(0.5, 0, 0, 0)
+ label.Size = UDim2.new(0.5, 0, 1, 0)
+ label.TextColor3 = Color3.new(1,1,1)
+ label.ZIndex = 9
+ label.Parent = frame
+ element.Label2 = label
+ end
+ frame.Parent = gearContextMenuButton
+ element.Label = frame
+ element.Element = frame
+ end
+ end
+
+ gearContextMenu.ZIndex = 4
+ gearContextMenu.MouseLeave:connect(function()
+ browsingMenu = false
+ gearContextMenu.Visible = false
+ clearPreview()
+ end)
+ robloxLock(gearContextMenu)
+
+ return gearContextMenu
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ if not enabled then
+ backpack.Gear.Visible = false
+ end
+ end
+end
+
+
+local backpackChildren = player.Backpack:GetChildren()
+for i = 1, #backpackChildren do
+ addToGrid(backpackChildren[i])
+end
+
+------------------------- Start Lifelong Connections -----------------------
+
+
+resizeEvent.Event:connect(function(absSize)
+ if debounce then return end
+
+ debounce = true
+ wait()
+ resize()
+ resizeGrid()
+ debounce = false
+end)
+
+currentLoadout.ChildAdded:connect(function(child) loadoutCheck(child, false) end)
+currentLoadout.ChildRemoved:connect(function(child) loadoutCheck(child, true) end)
+
+currentLoadout.DescendantAdded:connect(function(descendant)
+ if not backpack.Visible and ( descendant:IsA("ImageButton") or descendant:IsA("TextButton") ) then
+ centerGear(currentLoadout:GetChildren())
+ end
+end)
+currentLoadout.DescendantRemoving:connect(function(descendant)
+ if not backpack.Visible and ( descendant:IsA("ImageButton") or descendant:IsA("TextButton") ) then
+ wait()
+ centerGear(currentLoadout:GetChildren())
+ end
+end)
+
+grid.MouseEnter:connect(function() clearPreview() end)
+grid.MouseLeave:connect(function() clearPreview() end)
+
+player.CharacterRemoving:connect(function()
+ removeCharacterConnections()
+ nukeBackpack()
+end)
+player.CharacterAdded:connect(function() setupCharacterConnections() end)
+
+player.ChildAdded:connect(function(child)
+ if child:IsA("Backpack") then
+ playerBackpack = child
+ if backpackAddCon then backpackAddCon:disconnect() end
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+ end
+end)
+
+swapSlot.Changed:connect(function()
+ if not swapSlot.Value then
+ updateGridActive()
+ end
+end)
+
+local loadoutChildren = currentLoadout:GetChildren()
+for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") and string.find(loadoutChildren[i].Name,"Slot") then
+ loadoutChildren[i].ChildRemoved:connect(function()
+ updateGridActive()
+ end)
+ loadoutChildren[i].ChildAdded:connect(function()
+ updateGridActive()
+ end)
+ end
+end
+------------------------- End Lifelong Connections -----------------------
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+resize()
+resizeGrid()
+
+-- make sure any items in the loadout are accounted for in inventory
+local loadoutChildren = currentLoadout:GetChildren()
+for i = 1, #loadoutChildren do
+ loadoutCheck(loadoutChildren[i], false)
+end
+if not backpack.Visible then centerGear(currentLoadout:GetChildren()) end
+
+-- make sure that inventory is listening to gear reparenting
+if characterChildAddedCon == nil and game.Players.LocalPlayer["Character"] then
+ setupCharacterConnections()
+end
+if not backpackAddCon then
+ backpackAddCon = game.Players.LocalPlayer.Backpack.ChildAdded:connect(function(child) addToGrid(child) end)
+end
+
+backpackOpenEvent.Event:connect(backpackOpenHandler)
+backpackCloseEvent.Event:connect(backpackCloseHandler)
+tabClickedEvent.Event:connect(tabClickHandler)
+searchRequestedEvent.Event:connect(showSearchGear)
+
+recalculateScrollLoadout()
\ No newline at end of file
diff --git a/asset/backup/18 b/asset/backup/18
new file mode 100644
index 0000000..33f83b9
--- /dev/null
+++ b/asset/backup/18
@@ -0,0 +1,1090 @@
+%18%
+-- A couple of necessary functions
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+ return instance:FindFirstChild(name)
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+local useCoreHealthBar = false
+pcall(function() useCoreHealthBar = Game.Players:GetUseCoreScriptHealthBar() end)
+
+
+local currentLoadout = script.Parent
+local StaticTabName = "gear"
+local backpackEnabled = true
+
+local robloxGui = game:GetService("CoreGui"):FindFirstChild("RobloxGui")
+assert(robloxGui)
+local controlFrame = waitForChild(robloxGui, 'ControlFrame')
+local backpackButton = waitForChild(controlFrame, 'BackpackButton')
+local backpack = waitForChild(robloxGui, 'Backpack')
+waitForChild(robloxGui,"CurrentLoadout")
+waitForChild(robloxGui.CurrentLoadout,"TempSlot")
+waitForChild(robloxGui.CurrentLoadout.TempSlot,"SlotNumber")
+
+local function IsTouchDevice()
+ return Game:GetService('UserInputService').TouchEnabled
+end
+
+local function IsSmallScreen()
+ return (robloxGui.AbsoluteSize.Y <= 500)
+end
+
+local function moveHealthBar(pGui)
+ waitForChild(pGui, 'HealthGUI')
+ waitForChild(pGui['HealthGUI'], 'tray')
+ local tray = pGui['HealthGUI']['tray']
+ tray.Position = UDim2.new(0.5, -85, 1, -26)
+end
+
+local function setHealthBarVisible( pGui, visible )
+ waitForChild(pGui, 'HealthGUI')
+ waitForChild(pGui['HealthGUI'], 'tray')
+ local tray = pGui['HealthGUI']['tray']
+ tray.Visible = visible
+end
+
+
+--- Begin Locals
+waitForChild(game,"Players")
+waitForProperty(game.Players,"LocalPlayer")
+local player = game.Players.LocalPlayer
+
+if not useCoreHealthBar then
+ waitForChild(player, 'PlayerGui')
+ Spawn(function()
+ moveHealthBar(player.PlayerGui)
+ end)
+end
+
+while player.Character == nil do wait(0.03) end
+local humanoid = waitForChild(player.Character, 'Humanoid')
+humanoid.Died:connect(function()
+ backpackButton.Visible = false
+end)
+
+waitForChild(game, "LocalBackpack")
+game.LocalBackpack:SetOldSchoolBackpack(false)
+
+waitForChild(currentLoadout.Parent,"Backpack")
+local guiBackpack = currentLoadout.Parent.Backpack
+
+local backpackManager = waitForChild(guiBackpack,"CoreScripts/BackpackScripts/BackpackManager")
+local backpackOpenEvent = waitForChild(backpackManager,"BackpackOpenEvent")
+local backpackCloseEvent = waitForChild(backpackManager,"BackpackCloseEvent")
+local tabClickedEvent = waitForChild(backpackManager,"TabClickedEvent")
+local resizeEvent = waitForChild(backpackManager,"ResizeEvent")
+
+local inGearTab = true
+
+local maxNumLoadoutItems = 10
+if IsSmallScreen() then
+ maxNumLoadoutItems = 4
+end
+
+
+local characterChildAddedCon = nil
+local backpackChildCon = nil
+
+local debounce = false
+
+local enlargeFactor = 1.18
+local buttonSizeEnlarge = UDim2.new(1 * enlargeFactor,0,1 * enlargeFactor,0)
+local buttonSizeNormal = UDim2.new(1,0,1,0)
+local enlargeOverride = true
+local guiTweenSpeed = 0.5
+
+local firstInstanceOfLoadout = false
+
+local inventory = {}
+
+local gearSlots = {}
+for i = 1, maxNumLoadoutItems do
+ gearSlots[i] = "empty"
+end
+
+local backpackWasOpened = false
+--- End Locals
+
+
+
+
+
+
+-- Begin Functions
+local function backpackIsOpen()
+ if guiBackpack then
+ return guiBackpack.Visible
+ end
+ return false
+end
+
+
+local function kill(prop,con,gear)
+ if con then con:disconnect() end
+ if prop == true and gear then
+ reorganizeLoadout(gear,false)
+ end
+end
+
+function registerNumberKeys()
+ for i = 0, 9 do
+ game:GetService("GuiService"):AddKey(tostring(i))
+ end
+end
+
+function unregisterNumberKeys()
+ for i = 0, 9 do
+ game:GetService("GuiService"):RemoveKey(tostring(i))
+ end
+end
+
+function characterInWorkspace()
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer["Character"] then
+ if game.Players.LocalPlayer.Character ~= nil then
+ if game.Players.LocalPlayer.Character.Parent ~= nil then
+ return true
+ end
+ end
+ end
+ end
+
+ return false
+end
+
+function removeGear(gear)
+ local emptySlot = nil
+ for i = 1, #gearSlots do
+ if gearSlots[i] == gear and gear.Parent ~= nil then
+ emptySlot = i
+ break
+ end
+ end
+ if emptySlot then
+ if gearSlots[emptySlot].GearReference.Value then
+ if gearSlots[emptySlot].GearReference.Value.Parent == game.Players.LocalPlayer.Character then -- if we currently have this equipped, unequip it
+ gearSlots[emptySlot].GearReference.Value.Parent = game.Players.LocalPlayer.Backpack
+ end
+
+ if gearSlots[emptySlot].GearReference.Value:IsA("HopperBin") and gearSlots[emptySlot].GearReference.Value.Active then -- this is an active hopperbin
+ gearSlots[emptySlot].GearReference.Value:Disable()
+ gearSlots[emptySlot].GearReference.Value.Active = false
+ end
+ end
+
+ gearSlots[emptySlot] = "empty"
+
+ local centerizeX = gear.Size.X.Scale/2
+ local centerizeY = gear.Size.Y.Scale/2
+ --[[gear:TweenSizeAndPosition(UDim2.new(0,0,0,0),
+ UDim2.new(gear.Position.X.Scale + centerizeX,gear.Position.X.Offset,gear.Position.Y.Scale + centerizeY,gear.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,guiTweenSpeed/4,true)]]
+ delay(0,
+ function()
+ gear:remove()
+ end)
+
+ Spawn(function()
+ while backpackIsOpen() do wait(0.03) end
+ waitForChild(player, 'Backpack')
+ local allEmpty = true
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= 'empty' then
+ allEmpty = false
+ end
+ end
+
+ if allEmpty then
+ if #player.Backpack:GetChildren() < 1 then
+ backpackButton.Visible = false
+ else
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+ end
+ end
+ end)
+ end
+end
+
+function insertGear(gear, addToSlot)
+ local pos = nil
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ pos = i
+ break
+ end
+ end
+
+ if pos == 1 and gearSlots[1] ~= "empty" then gear:remove() return end -- we are currently full, can't add in
+ else
+ pos = addToSlot
+ -- push all gear down one slot
+ local start = 1
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ start = i
+ break
+ end
+ end
+ for i = start, pos + 1, -1 do
+ gearSlots[i] = gearSlots[i - 1]
+ if i == 10 then
+ gearSlots[i].SlotNumber.Text = "0"
+ gearSlots[i].SlotNumberDownShadow.Text = "0"
+ gearSlots[i].SlotNumberUpShadow.Text = "0"
+ else
+ gearSlots[i].SlotNumber.Text = i
+ gearSlots[i].SlotNumberDownShadow.Text = i
+ gearSlots[i].SlotNumberUpShadow.Text = i
+ end
+ end
+ end
+
+ gearSlots[pos] = gear
+ if pos ~= maxNumLoadoutItems then
+ if(type(tostring(pos)) == "string") then
+ local posString = tostring(pos)
+ gear.SlotNumber.Text = posString
+ gear.SlotNumberDownShadow.Text = posString
+ gear.SlotNumberUpShadow.Text = posString
+ end
+ else -- tenth gear doesn't follow mathematical pattern :(
+ gear.SlotNumber.Text = "0"
+ gear.SlotNumberDownShadow.Text = "0"
+ gear.SlotNumberUpShadow.Text = "0"
+ end
+ gear.Visible = true
+
+ local con = nil
+ con = gear.Kill.Changed:connect(function(prop) kill(prop,con,gear) end)
+end
+
+
+function reorganizeLoadout(gear, inserting, equipped, addToSlot)
+ if inserting then -- add in gear
+ insertGear(gear, addToSlot)
+ else
+ removeGear(gear)
+ end
+ if gear ~= "empty" then gear.ZIndex = 1 end
+end
+
+function checkToolAncestry(child,parent)
+ if child:FindFirstChild("RobloxBuildTool") then return end -- don't show roblox build tools
+ if child:IsA("Tool") or child:IsA("HopperBin") then
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" and gearSlots[i].GearReference.Value == child then
+ if parent == nil then
+ gearSlots[i].Kill.Value = true
+ return false
+ elseif child.Parent == player.Character then
+ gearSlots[i].Selected = true
+ return true
+ elseif child.Parent == player.Backpack then
+ if child:IsA("Tool") or child:IsA("HopperBin") then gearSlots[i].Selected = false end
+ return true
+ else
+ gearSlots[i].Kill.Value = true
+ return false
+ end
+ return true
+ end
+ end
+ end
+end
+
+function removeAllEquippedGear(physGear)
+ local stuff = player.Character:GetChildren()
+ for i = 1, #stuff do
+ if ( stuff[i]:IsA("Tool") or stuff[i]:IsA("HopperBin") ) and stuff[i] ~= physGear then
+ if stuff[i]:IsA("Tool") then stuff[i].Parent = player.Backpack end
+ if stuff[i]:IsA("HopperBin") then
+ stuff[i]:Disable()
+ end
+ end
+ end
+end
+
+function hopperBinSwitcher(numKey, physGear)
+ if not physGear then return end
+
+ physGear:ToggleSelect()
+
+ if gearSlots[numKey] == "empty" then return end
+
+ if not physGear.Active then
+ gearSlots[numKey].Selected = false
+ normalizeButton(gearSlots[numKey])
+ else
+ gearSlots[numKey].Selected = true
+ enlargeButton(gearSlots[numKey])
+ end
+end
+
+function toolSwitcher(numKey)
+
+ if not gearSlots[numKey] then return end
+ local physGear = gearSlots[numKey].GearReference.Value
+ if physGear == nil then return end
+
+ removeAllEquippedGear(physGear) -- we don't remove this gear, as then we get a double switcheroo
+
+ local key = numKey
+ if numKey == 0 then key = 10 end
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] and gearSlots[i] ~= "empty" and i ~= key then
+ normalizeButton(gearSlots[i])
+ gearSlots[i].Selected = false
+ if gearSlots[i].GearReference and gearSlots[i].GearReference.Value and gearSlots[i].GearReference.Value:IsA("HopperBin") and gearSlots[i].GearReference.Value.Active then
+ gearSlots[i].GearReference.Value:ToggleSelect()
+ end
+ end
+ end
+
+ if physGear:IsA("HopperBin") then
+ hopperBinSwitcher(numKey,physGear)
+ else
+ if physGear.Parent == player.Character then
+ physGear.Parent = player.Backpack
+
+ if gearSlots[numKey] ~= "empty" then
+ gearSlots[numKey].Selected = false
+ normalizeButton(gearSlots[numKey])
+ end
+ else
+ --player.Character.Humanoid:EquipTool(physGear)
+
+ physGear.Parent = player.Character
+ gearSlots[numKey].Selected = true
+
+ enlargeButton(gearSlots[numKey])
+ end
+ end
+end
+
+
+function activateGear(num)
+ local numKey = nil
+ if num == "0" then
+ numKey = 10 -- why do lua indexes have to start at 1? :(
+ else
+ numKey = tonumber(num)
+ end
+
+ if(numKey == nil) then return end
+
+ if gearSlots[numKey] ~= "empty" then
+ toolSwitcher(numKey)
+ end
+end
+
+
+enlargeButton = function(button)
+ if button.Size.Y.Scale > 1 then return end
+ if not button.Parent then return end
+ if not button.Selected then return end
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i] ~= button then
+ normalizeButton(gearSlots[i])
+ end
+ end
+
+ if not enlargeOverride then
+ return
+ end
+
+ if button:FindFirstChild('Highlight') then
+ button.Highlight.Visible = true
+ end
+
+ if button:IsA("ImageButton") or button:IsA("TextButton") then
+ button.ZIndex = 5
+ local centerizeX = -(buttonSizeEnlarge.X.Scale - button.Size.X.Scale)/2
+ local centerizeY = -(buttonSizeEnlarge.Y.Scale - button.Size.Y.Scale)/2
+ button:TweenSizeAndPosition(buttonSizeEnlarge,
+ UDim2.new(button.Position.X.Scale + centerizeX,button.Position.X.Offset,button.Position.Y.Scale + centerizeY,button.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,guiTweenSpeed/5,enlargeOverride)
+ end
+end
+
+normalizeAllButtons = function()
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i] ~= button then
+ normalizeButton(gearSlots[i],0.1)
+ end
+ end
+end
+
+
+normalizeButton = function(button, speed)
+ if not button then return end
+ if button.Size.Y.Scale <= 1 then return end
+ if button.Selected then return end
+ if not button.Parent then return end
+
+ local moveSpeed = speed
+ if moveSpeed == nil or type(moveSpeed) ~= "number" then moveSpeed = guiTweenSpeed/5 end
+
+ if button:FindFirstChild('Highlight') then
+ button.Highlight.Visible = false
+ end
+
+ if button:IsA("ImageButton") or button:IsA("TextButton") then
+ button.ZIndex = 1
+ local inverseEnlarge = 1/enlargeFactor
+ local centerizeX = -(buttonSizeNormal.X.Scale - button.Size.X.Scale)/2
+ local centerizeY = -(buttonSizeNormal.Y.Scale - button.Size.Y.Scale)/2
+ button:TweenSizeAndPosition(buttonSizeNormal,
+ UDim2.new(button.Position.X.Scale + centerizeX,button.Position.X.Offset,button.Position.Y.Scale + centerizeY,button.Position.Y.Offset),
+ Enum.EasingDirection.Out, Enum.EasingStyle.Quad,moveSpeed,enlargeOverride)
+ end
+end
+
+local waitForDebounce = function()
+ while debounce do
+ wait()
+ end
+end
+
+function pointInRectangle(point,rectTopLeft,rectSize)
+ if point.x > rectTopLeft.x and point.x < (rectTopLeft.x + rectSize.x) then
+ if point.y > rectTopLeft.y and point.y < (rectTopLeft.y + rectSize.y) then
+ return true
+ end
+ end
+ return false
+end
+
+function swapGear(gearClone,toFrame)
+ local toFrameChildren = toFrame:GetChildren()
+ if #toFrameChildren == 1 then
+ if toFrameChildren[1]:FindFirstChild("SlotNumber") then
+
+ local toSlot = tonumber(toFrameChildren[1].SlotNumber.Text)
+ local gearCloneSlot = tonumber(gearClone.SlotNumber.Text)
+ if toSlot == 0 then toSlot = 10 end
+ if gearCloneSlot == 0 then gearCloneSlot = 10 end
+
+ gearSlots[toSlot] = gearClone
+ gearSlots[gearCloneSlot] = toFrameChildren[1]
+
+ toFrameChildren[1].SlotNumber.Text = gearClone.SlotNumber.Text
+ toFrameChildren[1].SlotNumberDownShadow.Text = gearClone.SlotNumber.Text
+ toFrameChildren[1].SlotNumberUpShadow.Text = gearClone.SlotNumber.Text
+
+ local subString = string.sub(toFrame.Name,5)
+ gearClone.SlotNumber.Text = subString
+ gearClone.SlotNumberDownShadow.Text = subString
+ gearClone.SlotNumberUpShadow.Text = subString
+
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,0,gearClone.Position.Y.Scale,0)
+ toFrameChildren[1].Position = UDim2.new(toFrameChildren[1].Position.X.Scale,0,toFrameChildren[1].Position.Y.Scale,0)
+
+ toFrameChildren[1].Parent = gearClone.Parent
+ gearClone.Parent = toFrame
+ end
+ else
+ local slotNum = tonumber(gearClone.SlotNumber.Text)
+ if slotNum == 0 then slotNum = 10 end
+ gearSlots[slotNum] = "empty" -- reset this gear slot
+
+ local subString = string.sub(toFrame.Name,5)
+ gearClone.SlotNumber.Text = subString
+ gearClone.SlotNumberDownShadow.Text = subString
+ gearClone.SlotNumberUpShadow.Text = subString
+
+ local toSlotNum = tonumber(gearClone.SlotNumber.Text)
+ if toSlotNum == 0 then toSlotNum = 10 end
+ gearSlots[toSlotNum] = gearClone
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,0,gearClone.Position.Y.Scale,0)
+ gearClone.Parent = toFrame
+ end
+end
+
+function resolveDrag(gearClone,x,y)
+ local mousePoint = Vector2.new(x,y)
+
+ local frame = gearClone.Parent
+ local frames = frame.Parent:GetChildren()
+
+ for i = 1, #frames do
+ if frames[i]:IsA("Frame") then
+ if pointInRectangle(mousePoint, frames[i].AbsolutePosition,frames[i].AbsoluteSize) then
+ swapGear(gearClone,frames[i])
+ return true
+ end
+ end
+ end
+
+ if x < frame.AbsolutePosition.x or x > ( frame.AbsolutePosition.x + frame.AbsoluteSize.x ) then
+ reorganizeLoadout(gearClone,false)
+ return false
+ elseif y < frame.AbsolutePosition.y or y > ( frame.AbsolutePosition.y + frame.AbsoluteSize.y ) then
+ reorganizeLoadout(gearClone,false)
+ return false
+ else
+ if dragBeginPos then gearClone.Position = dragBeginPos end
+ return -1
+ end
+end
+
+function unequipAllItems(dontEquipThis)
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then break end
+ if gearSlots[i].GearReference.Value and gearSlots[i].GearReference.Value ~= dontEquipThis then
+ if gearSlots[i].GearReference.Value:IsA("HopperBin") then
+ gearSlots[i].GearReference.Value:Disable()
+ elseif gearSlots[i].GearReference.Value:IsA("Tool") then
+ gearSlots[i].GearReference.Value.Parent = game.Players.LocalPlayer.Backpack
+ end
+ gearSlots[i].Selected = false
+ end
+ end
+end
+
+function showToolTip(button, tip)
+ if button and button:FindFirstChild("ToolTipLabel") and button.ToolTipLabel:IsA("TextLabel") and not IsTouchDevice() then
+ button.ToolTipLabel.Text = tostring(tip)
+ local xSize = button.ToolTipLabel.TextBounds.X + 6
+ button.ToolTipLabel.Size = UDim2.new(0,xSize,0,20)
+ button.ToolTipLabel.Position = UDim2.new(0.5,-xSize/2,0,-30)
+ button.ToolTipLabel.Visible = true
+ end
+end
+
+function hideToolTip(button, tip)
+ if button and button:FindFirstChild("ToolTipLabel") and button.ToolTipLabel:IsA("TextLabel") then
+ button.ToolTipLabel.Visible = false
+ end
+end
+
+local addingPlayerChild = function(child, equipped, addToSlot, inventoryGearButton)
+ waitForDebounce()
+ debounce = true
+
+ if child:FindFirstChild("RobloxBuildTool") then debounce = false return end -- don't show roblox build tools
+ if not child:IsA("Tool") then
+ if not child:IsA("HopperBin") then
+ debounce = false
+ return -- we don't care about anything besides tools (sigh...)
+ end
+ end
+
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" and gearSlots[i].GearReference.Value == child then -- we already have gear, do nothing
+ debounce = false
+ return
+ end
+ end
+ end
+
+ local gearClone = currentLoadout.TempSlot:clone()
+ gearClone.Name = child.Name
+ gearClone.GearImage.Image = child.TextureId
+ if gearClone.GearImage.Image == "" then
+ gearClone.GearText.Text = child.Name
+ end
+ gearClone.GearReference.Value = child
+
+ gearClone.MouseEnter:connect(function()
+ local gear = gearClone.GearReference and gearClone.GearReference.Value
+ if gear:IsA("Tool") and gear.ToolTip ~= "" then
+ showToolTip(gearClone, gear.ToolTip)
+ end
+ end)
+
+ gearClone.MouseLeave:connect(function()
+ local gear = gearClone.GearReference and gearClone.GearReference.Value
+ if gear:IsA("Tool") and gear.ToolTip ~= "" then
+ hideToolTip(gearClone, gear.ToolTip)
+ end
+ end)
+
+ gearClone.RobloxLocked = true
+
+ local slotToMod = -1
+
+ if not addToSlot then
+ for i = 1, #gearSlots do
+ if gearSlots[i] == "empty" then
+ slotToMod = i
+ break
+ end
+ end
+ else
+ slotToMod = addToSlot
+ end
+
+ if slotToMod == - 1 then -- No available slot to add in!
+ debounce = false
+ return
+ end
+
+ local slotNum = slotToMod % 10
+ local parent = currentLoadout:FindFirstChild("Slot"..tostring(slotNum))
+ gearClone.Parent = parent
+
+ if inventoryGearButton then
+ local absolutePositionFinal = inventoryGearButton.AbsolutePosition
+ local currentAbsolutePosition = gearClone.AbsolutePosition
+ local diff = absolutePositionFinal - currentAbsolutePosition
+ gearClone.Position = UDim2.new(gearClone.Position.X.Scale,diff.x,gearClone.Position.Y.Scale,diff.y)
+ gearClone.ZIndex = 4
+ end
+
+ if addToSlot then
+ reorganizeLoadout(gearClone, true, equipped, addToSlot)
+ else
+ reorganizeLoadout(gearClone, true)
+ end
+
+ if gearClone.Parent == nil then debounce = false return end -- couldn't fit in (hopper is full!)
+
+ if equipped then
+ gearClone.Selected = true
+ unequipAllItems(child)
+ delay(guiTweenSpeed + 0.01,function() -- if our gear is equipped, we will want to enlarge it when done moving
+ if gearClone:FindFirstChild("GearReference") and ( (gearClone.GearReference.Value:IsA("Tool") and gearClone.GearReference.Value.Parent == player.Character) or
+ (gearClone.GearReference.Value:IsA("HopperBin") and gearClone.GearReference.Value.Active == true) ) then
+ enlargeButton(gearClone)
+ end
+ end)
+ end
+
+ local dragBeginPos = nil
+ local clickCon, buttonDeleteCon, mouseEnterCon, mouseLeaveCon, dragStop, dragBegin = nil
+ clickCon = gearClone.MouseButton1Click:connect(function()
+ if characterInWorkspace() then
+ if not gearClone.Draggable then
+ activateGear(gearClone.SlotNumber.Text)
+ end
+ end
+ end)
+ mouseEnterCon = gearClone.MouseEnter:connect(function()
+ if guiBackpack.Visible then
+ gearClone.Draggable = true
+ end
+ end)
+ dragBegin = gearClone.DragBegin:connect(function(pos)
+ dragBeginPos = pos
+ gearClone.ZIndex = 7
+ local children = gearClone:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("TextLabel") then
+ if string.find(children[i].Name,"Shadow") then
+ children[i].ZIndex = 8
+ else
+ children[i].ZIndex = 9
+ end
+ elseif children[i]:IsA("Frame") or children[i]:IsA("ImageLabel") then
+ children[i].ZIndex = 7
+ end
+ end
+ end)
+ dragStop = gearClone.DragStopped:connect(function(x,y)
+ if gearClone.Selected then
+ gearClone.ZIndex = 4
+ else
+ gearClone.ZIndex = 3
+ end
+ local children = gearClone:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("TextLabel") then
+ if string.find(children[i].Name,"Shadow") then
+ children[i].ZIndex = 3
+ else
+ children[i].ZIndex = 4
+ end
+ elseif children[i]:IsA("Frame") or children[i]:IsA("ImageLabel") then
+ children[i].ZIndex = 2
+ end
+ end
+ resolveDrag(gearClone,x,y)
+ end)
+ mouseLeaveCon = gearClone.MouseLeave:connect(function()
+ gearClone.Draggable = false
+ end)
+ buttonDeleteCon = gearClone.AncestryChanged:connect(function()
+ if gearClone.Parent and gearClone.Parent.Parent == currentLoadout then return end
+ if clickCon then clickCon:disconnect() end
+ if buttonDeleteCon then buttonDeleteCon:disconnect() end
+ if mouseEnterCon then mouseEnterCon:disconnect() end
+ if mouseLeaveCon then mouseLeaveCon:disconnect() end
+ if dragStop then dragStop:disconnect() end
+ if dragBegin then dragBegin:disconnect() end
+ end) -- this probably isn't necessary since objects are being deleted (probably), but this might still leak just in case
+
+ local childCon = nil
+ local childChangeCon = nil
+ childCon = child.AncestryChanged:connect(function(newChild,parent)
+ if not checkToolAncestry(newChild,parent) then
+ if childCon then childCon:disconnect() end
+ if childChangeCon then childChangeCon:disconnect() end
+ removeFromInventory(child)
+ elseif parent == game.Players.LocalPlayer.Backpack then
+ normalizeButton(gearClone)
+ end
+ end)
+
+ childChangeCon = child.Changed:connect(function(prop)
+ if prop == "Name" then
+ if gearClone and gearClone.GearImage.Image == "" then
+ gearClone.GearText.Text = child.Name
+ end
+ elseif prop == "Active" then
+ if child and child:IsA("HopperBin") then
+ if not child.Active then
+ gearClone.Selected = false
+ normalizeButton(gearClone)
+ end
+ end
+ elseif prop == "TextureId" then
+ gearClone.GearImage.Image = child.TextureId
+ end
+ end)
+
+ debounce = false
+
+ Spawn(function()
+ while backpackIsOpen() do wait(0.03) end
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -55)
+
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= 'empty' then
+ backpackButton.Position = UDim2.new(0.5, -7, 1, -108)
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ end
+ end
+ end)
+end
+
+function addToInventory(child)
+ if not child:IsA("Tool") or not child:IsA("HopperBin") then return end
+
+ local slot = nil
+ for i = 1, #inventory do
+ if inventory[i] and inventory[i] == child then return end
+ if not inventory[i] then slot = i end
+ end
+ if slot then
+ inventory[slot] = child
+ elseif #inventory < 1 then
+ inventory[1] = child
+ else
+ inventory[#inventory + 1] = child
+ end
+end
+
+function removeFromInventory(child)
+ for i = 1, #inventory do
+ if inventory[i] == child then
+ table.remove(inventory,i)
+ inventory[i] = nil
+ end
+ end
+end
+
+local spreadOutGear = function()
+ loadoutChildren = currentLoadout:GetChildren()
+
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ loadoutChildren[i].BackgroundTransparency = 0.5
+ local slot = tonumber(string.sub(loadoutChildren[i].Name,5))
+ if slot == 0 then slot = 10 end
+ if IsSmallScreen() then
+ loadoutChildren[i]:TweenPosition(UDim2.new(0,(slot-1) * 60,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ else
+ loadoutChildren[i]:TweenPosition(UDim2.new((slot - 1)/10,0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+ end
+ end
+end
+
+local centerGear = function()
+ loadoutChildren = currentLoadout:GetChildren()
+ local gearButtons = {}
+ local lastSlotAdd = nil
+
+ for i = 1, #loadoutChildren do
+ if loadoutChildren[i]:IsA("Frame") then
+ if #loadoutChildren[i]:GetChildren() > 0 then
+ if loadoutChildren[i].Name == "Slot0" then
+ lastSlotAdd = loadoutChildren[i]
+ else
+ table.insert(gearButtons, loadoutChildren[i])
+ end
+ end
+ loadoutChildren[i].BackgroundTransparency = 1
+ end
+ end
+ if lastSlotAdd then table.insert(gearButtons,lastSlotAdd) end
+
+ local startPos = ( 1 - (#gearButtons * 0.1) ) / 2
+ for i = 1, #gearButtons do
+ if IsSmallScreen() then
+ startPos = ( 0.5 - (#gearButtons * 0.333)/2 )
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + (i-1) * 0.33, 0, 0, 0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ else
+ gearButtons[i]:TweenPosition(UDim2.new(startPos + ((i - 1) * 0.1),0,0,0), Enum.EasingDirection.Out, Enum.EasingStyle.Quad, 0.25, true)
+ end
+ end
+end
+
+function editLoadout()
+ backpackWasOpened = true
+ if inGearTab then
+ spreadOutGear()
+ end
+end
+
+function readonlyLoadout()
+ if not inGearTab then
+ centerGear()
+ end
+end
+
+function setupBackpackListener()
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ backpackChildCon = player.Backpack.ChildAdded:connect(function(child)
+ if not firstInstanceOfLoadout then
+ firstInstanceOfLoadout = true
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ end
+ addingPlayerChild(child)
+ addToInventory(child)
+ end)
+end
+
+function playerCharacterChildAdded(child)
+ addingPlayerChild(child,true)
+ addToInventory(child)
+end
+
+function activateLoadout()
+ currentLoadout.Visible = true
+end
+
+function deactivateLoadout()
+ currentLoadout.Visible = false
+end
+
+function tabHandler(inFocus)
+ inGearTab = inFocus
+ if inFocus then
+ editLoadout()
+ else
+ readonlyLoadout()
+ end
+end
+
+function coreGuiChanged(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Backpack or coreGuiType == Enum.CoreGuiType.All then
+ currentLoadout.Visible = enabled -- Thanks, missing line. you know how to confuse everyone. >.<
+ backpackButton.Visible = enabled
+ backpackEnabled = enabled
+
+ if enabled then
+ registerNumberKeys()
+ else
+ unregisterNumberKeys()
+ end
+ end
+
+ if not useCoreHealthBar and coreGuiType == Enum.CoreGuiType.Health or coreGuiType == Enum.CoreGuiType.All then
+ setHealthBarVisible(game.Players.LocalPlayer.PlayerGui, enabled)
+ end
+end
+-- End Functions
+
+
+
+
+
+
+-- Begin Script
+registerNumberKeys()
+
+coreGuiChanged(Enum.CoreGuiType.Backpack, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Backpack))
+if not useCoreHealthBar then
+ coreGuiChanged(Enum.CoreGuiType.Health, Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health))
+end
+Game.StarterGui.CoreGuiChangedSignal:connect(coreGuiChanged)
+
+wait() -- let stuff initialize incase this is first heartbeat...
+
+waitForChild(player,"Backpack")
+waitForProperty(player,"Character")
+
+-- not sure why this had no delay but the player.CharacterAdded one had one... this type of error would be easier to avoid with function reusage
+delay(1,function()
+ local backpackChildren = player.Backpack:GetChildren()
+ local size = math.min(10,#backpackChildren)
+ for i = 1, size do
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ addingPlayerChild(backpackChildren[i],false)
+ end
+ setupBackpackListener()
+end)
+
+delay(2, function()
+ --while true do
+ if not backpackWasOpened then
+ if IsSmallScreen() then
+ local cChildren = currentLoadout:GetChildren()
+ for i = 1, #cChildren do
+ local slotNum = tonumber(string.sub(cChildren[i].Name, 5, string.len(cChildren[i].Name)))
+ if type(slotNum) == 'number' then
+ cChildren[i].Position = UDim2.new(0, (slotNum-1) * 60, 0, 0)
+ end
+ end
+ end
+ end
+ wait(0.25)
+ --end
+end)
+
+if not useCoreHealthBar then
+ player.ChildAdded:connect(function(child)
+ if child:IsA('PlayerGui') then
+ moveHealthBar(child)
+ end
+ end)
+end
+
+waitForProperty(player,"Character")
+for i,v in ipairs(player.Character:GetChildren()) do
+ playerCharacterChildAdded(v)
+end
+characterChildAddedCon = player.Character.ChildAdded:connect(function(child) playerCharacterChildAdded(child) end)
+
+waitForChild(player.Character,"Humanoid")
+humanoidDiedCon = player.Character.Humanoid.Died:connect(function()
+ if humanoidDiedCon then humanoidDiedCon:disconnect() humanoidDiedCon = nil end
+ deactivateLoadout()
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ backpackWasOpened = false
+end)
+
+player.CharacterRemoving:connect(function()
+ for i = 1, #gearSlots do
+ if gearSlots[i] ~= "empty" then
+ gearSlots[i].Parent = nil
+ gearSlots[i] = "empty"
+ end
+ end
+end)
+
+player.CharacterAdded:connect(function()
+ waitForProperty(game.Players,"LocalPlayer")
+ player = game.Players.LocalPlayer -- make sure we are still looking at the correct character
+ waitForChild(player,"Backpack")
+
+
+ delay(1,function()
+ local backpackChildren = player.Backpack:GetChildren()
+ local size = math.min(10,#backpackChildren)
+ for i = 1, size do
+ if backpackEnabled then
+ backpackButton.Visible = true
+ end
+ addingPlayerChild(backpackChildren[i],false)
+ end
+ setupBackpackListener()
+ end)
+
+ activateLoadout()
+
+ if characterChildAddedCon then
+ characterChildAddedCon:disconnect()
+ characterChildAddedCon = nil
+ end
+
+ characterChildAddedCon =
+ player.Character.ChildAdded:connect(function(child)
+ addingPlayerChild(child,true)
+ end)
+
+ waitForChild(player.Character,"Humanoid")
+ if backpack.Visible then
+ backpackOpenEvent:Fire()
+ end
+ humanoidDiedCon =
+ player.Character.Humanoid.Died:connect(function()
+ if backpackEnabled then
+ backpackButton.Visible = false
+ end
+ firstInstanceOfLoadout = false
+ deactivateLoadout()
+
+ if humanoidDiedCon then humanoidDiedCon:disconnect() humanoidDiedCon = nil end
+ if backpackChildCon then backpackChildCon:disconnect() backpackChildCon = nil end
+ end)
+ if not useCoreHealthBar then
+ waitForChild(player, 'PlayerGui')
+ moveHealthBar(player.PlayerGui)
+ end
+ delay(2, function()
+ --while true do
+ if not backpackWasOpened then
+ if IsSmallScreen() then
+ local cChildren = currentLoadout:GetChildren()
+ for i = 1, #cChildren do
+ local slotNum = tonumber(string.sub(cChildren[i].Name, 5, string.len(cChildren[i].Name)))
+ if type(slotNum) == 'number' then
+ cChildren[i].Position = UDim2.new(0, (slotNum-1) * 60, 0, 0)
+ end
+ end
+ end
+ end
+ wait(0.25)
+ --end
+ end)
+end)
+
+waitForChild(guiBackpack,"SwapSlot")
+guiBackpack.SwapSlot.Changed:connect(function()
+ if guiBackpack.SwapSlot.Value then
+ local swapSlot = guiBackpack.SwapSlot
+ local pos = swapSlot.Slot.Value
+ if pos == 0 then pos = 10 end
+ if gearSlots[pos] then
+ reorganizeLoadout(gearSlots[pos],false)
+ end
+ if swapSlot.GearButton.Value then
+ addingPlayerChild(swapSlot.GearButton.Value.GearReference.Value,false,pos)
+ end
+ guiBackpack.SwapSlot.Value = false
+ end
+end)
+
+game:GetService("GuiService").KeyPressed:connect(function(key)
+ if characterInWorkspace() then
+ activateGear(key)
+ end
+end)
+
+backpackOpenEvent.Event:connect(editLoadout)
+backpackCloseEvent.Event:connect(centerGear)
+tabClickedEvent.Event:connect(function ( tabName )
+ tabHandler(tabName == StaticTabName)
+end)
diff --git a/asset/backup/2 b/asset/backup/2
new file mode 100644
index 0000000..e06f57a
--- /dev/null
+++ b/asset/backup/2
@@ -0,0 +1,23 @@
+%2%
+-- Library Registration Script
+-- This script is used to register RbxLua libraries on game servers, so game scripts have
+-- access to all of the libraries (otherwise only local scripts do)
+
+local sc = game:GetService("ScriptContext")
+local tries = 0
+
+while not sc and tries < 3 do
+ tries = tries + 1
+ sc = game:GetService("ScriptContext")
+ wait(0.2)
+end
+
+if sc then
+ sc:RegisterLibrary("Libraries/RbxGui", "21")
+ sc:RegisterLibrary("Libraries/RbxGear", "22")
+ sc:RegisterLibrary("Libraries/RbxUtility", "23")
+ sc:RegisterLibrary("Libraries/RbxStamper", "24")
+ sc:LibraryRegistrationComplete()
+else
+ print("failed to find script context, libraries did not load")
+end
diff --git a/asset/backup/21 b/asset/backup/21
new file mode 100644
index 0000000..5d8ebbe
--- /dev/null
+++ b/asset/backup/21
@@ -0,0 +1,4041 @@
+%21%
+local t = {}
+
+local function ScopedConnect(parentInstance, instance, event, signalFunc, syncFunc, removeFunc)
+ local eventConnection = nil
+
+ --Connection on parentInstance is scoped by parentInstance (when destroyed, it goes away)
+ local tryConnect = function()
+ if game:IsAncestorOf(parentInstance) then
+ --Entering the world, make sure we are connected/synced
+ if not eventConnection then
+ eventConnection = instance[event]:connect(signalFunc)
+ if syncFunc then syncFunc() end
+ end
+ else
+ --Probably leaving the world, so disconnect for now
+ if eventConnection then
+ eventConnection:disconnect()
+ if removeFunc then removeFunc() end
+ end
+ end
+ end
+
+ --Hook it up to ancestryChanged signal
+ local connection = parentInstance.AncestryChanged:connect(tryConnect)
+
+ --Now connect us if we're already in the world
+ tryConnect()
+
+ return connection
+end
+
+local function getScreenGuiAncestor(instance)
+ local localInstance = instance
+ while localInstance and not localInstance:IsA("ScreenGui") do
+ localInstance = localInstance.Parent
+ end
+ return localInstance
+end
+
+local function CreateButtons(frame, buttons, yPos, ySize)
+ local buttonNum = 1
+ local buttonObjs = {}
+ for i, obj in ipairs(buttons) do
+ local button = Instance.new("TextButton")
+ button.Name = "Button" .. buttonNum
+ button.Font = Enum.Font.Arial
+ button.FontSize = Enum.FontSize.Size18
+ button.AutoButtonColor = true
+ button.Modal = true
+ if obj["Style"] then
+ button.Style = obj.Style
+ else
+ button.Style = Enum.ButtonStyle.RobloxButton
+ end
+ if obj["ZIndex"] then
+ button.ZIndex = obj.ZIndex
+ end
+ button.Text = obj.Text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.MouseButton1Click:connect(obj.Function)
+ button.Parent = frame
+ buttonObjs[buttonNum] = button
+
+ buttonNum = buttonNum + 1
+ end
+ local numButtons = buttonNum-1
+
+ if numButtons == 1 then
+ frame.Button1.Position = UDim2.new(0.35, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.4,0,ySize.Scale, ySize.Offset)
+ elseif numButtons == 2 then
+ frame.Button1.Position = UDim2.new(0.1, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.8/3,0, ySize.Scale, ySize.Offset)
+
+ frame.Button2.Position = UDim2.new(0.55, 0, yPos.Scale, yPos.Offset)
+ frame.Button2.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+ elseif numButtons >= 3 then
+ local spacing = .1 / numButtons
+ local buttonSize = .9 / numButtons
+
+ buttonNum = 1
+ while buttonNum <= numButtons do
+ buttonObjs[buttonNum].Position = UDim2.new(spacing*buttonNum + (buttonNum-1) * buttonSize, 0, yPos.Scale, yPos.Offset)
+ buttonObjs[buttonNum].Size = UDim2.new(buttonSize, 0, ySize.Scale, ySize.Offset)
+ buttonNum = buttonNum + 1
+ end
+ end
+end
+
+local function setSliderPos(newAbsPosX,slider,sliderPosition,bar,steps)
+
+ local newStep = steps - 1 --otherwise we really get one more step than we want
+ local relativePosX = math.min(1, math.max(0, (newAbsPosX - bar.AbsolutePosition.X) / bar.AbsoluteSize.X ))
+ local wholeNum, remainder = math.modf(relativePosX * newStep)
+ if remainder > 0.5 then
+ wholeNum = wholeNum + 1
+ end
+ relativePosX = wholeNum/newStep
+
+ local result = math.ceil(relativePosX * newStep)
+ if sliderPosition.Value ~= (result + 1) then --only update if we moved a step
+ sliderPosition.Value = result + 1
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ end
+
+end
+
+local function cancelSlide(areaSoak)
+ areaSoak.Visible = false
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+end
+
+t.CreateStyledMessageDialog = function(title, message, style, buttons)
+ local frame = Instance.new("Frame")
+ frame.Size = UDim2.new(0.5, 0, 0, 165)
+ frame.Position = UDim2.new(0.25, 0, 0.5, -72.5)
+ frame.Name = "MessageDialog"
+ frame.Active = true
+ frame.Style = Enum.FrameStyle.RobloxRound
+
+ local styleImage = Instance.new("ImageLabel")
+ styleImage.Name = "StyleImage"
+ styleImage.BackgroundTransparency = 1
+ styleImage.Position = UDim2.new(0,5,0,15)
+ if style == "error" or style == "Error" then
+ styleImage.Size = UDim2.new(0, 71, 0, 71)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42565285"
+ elseif style == "notify" or style == "Notify" then
+ styleImage.Size = UDim2.new(0, 71, 0, 71)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42604978"
+ elseif style == "confirm" or style == "Confirm" then
+ styleImage.Size = UDim2.new(0, 74, 0, 76)
+ styleImage.Image = "http://www.roblox.com/asset/?id=42557901"
+ else
+ return t.CreateMessageDialog(title,message,buttons)
+ end
+ styleImage.Parent = frame
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = title
+ titleLabel.TextStrokeTransparency = 0
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ titleLabel.Position = UDim2.new(0, 80, 0, 0)
+ titleLabel.Size = UDim2.new(1, -80, 0, 40)
+ titleLabel.Font = Enum.Font.ArialBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.TextXAlignment = Enum.TextXAlignment.Center
+ titleLabel.TextYAlignment = Enum.TextYAlignment.Center
+ titleLabel.Parent = frame
+
+ local messageLabel = Instance.new("TextLabel")
+ messageLabel.Name = "Message"
+ messageLabel.Text = message
+ messageLabel.TextStrokeTransparency = 0
+ messageLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ messageLabel.Position = UDim2.new(0.025, 80, 0, 45)
+ messageLabel.Size = UDim2.new(0.95, -80, 0, 55)
+ messageLabel.BackgroundTransparency = 1
+ messageLabel.Font = Enum.Font.Arial
+ messageLabel.FontSize = Enum.FontSize.Size18
+ messageLabel.TextWrap = true
+ messageLabel.TextXAlignment = Enum.TextXAlignment.Left
+ messageLabel.TextYAlignment = Enum.TextYAlignment.Top
+ messageLabel.Parent = frame
+
+ CreateButtons(frame, buttons, UDim.new(0, 105), UDim.new(0, 40) )
+
+ return frame
+end
+
+t.CreateMessageDialog = function(title, message, buttons)
+ local frame = Instance.new("Frame")
+ frame.Size = UDim2.new(0.5, 0, 0.5, 0)
+ frame.Position = UDim2.new(0.25, 0, 0.25, 0)
+ frame.Name = "MessageDialog"
+ frame.Active = true
+ frame.Style = Enum.FrameStyle.RobloxRound
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = title
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ titleLabel.Position = UDim2.new(0, 0, 0, 0)
+ titleLabel.Size = UDim2.new(1, 0, 0.15, 0)
+ titleLabel.Font = Enum.Font.ArialBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.TextXAlignment = Enum.TextXAlignment.Center
+ titleLabel.TextYAlignment = Enum.TextYAlignment.Center
+ titleLabel.Parent = frame
+
+ local messageLabel = Instance.new("TextLabel")
+ messageLabel.Name = "Message"
+ messageLabel.Text = message
+ messageLabel.TextColor3 = Color3.new(221/255,221/255,221/255)
+ messageLabel.Position = UDim2.new(0.025, 0, 0.175, 0)
+ messageLabel.Size = UDim2.new(0.95, 0, .55, 0)
+ messageLabel.BackgroundTransparency = 1
+ messageLabel.Font = Enum.Font.Arial
+ messageLabel.FontSize = Enum.FontSize.Size18
+ messageLabel.TextWrap = true
+ messageLabel.TextXAlignment = Enum.TextXAlignment.Left
+ messageLabel.TextYAlignment = Enum.TextYAlignment.Top
+ messageLabel.Parent = frame
+
+ CreateButtons(frame, buttons, UDim.new(0.8,0), UDim.new(0.15, 0))
+
+ return frame
+end
+
+t.CreateDropDownMenu = function(items, onSelect, forRoblox, whiteSkin, baseZ)
+ local baseZIndex = 0
+ if (type(baseZ) == "number") then
+ baseZIndex = baseZ
+ end
+ local width = UDim.new(0, 100)
+ local height = UDim.new(0, 32)
+
+ local xPos = 0.055
+ local frame = Instance.new("Frame")
+ local textColor = Color3.new(1,1,1)
+ if (whiteSkin) then
+ textColor = Color3.new(0.5, 0.5, 0.5)
+ end
+ frame.Name = "DropDownMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(width, height)
+
+ local dropDownMenu = Instance.new("TextButton")
+ dropDownMenu.Name = "DropDownMenuButton"
+ dropDownMenu.TextWrap = true
+ dropDownMenu.TextColor3 = textColor
+ dropDownMenu.Text = "Choose One"
+ dropDownMenu.Font = Enum.Font.ArialBold
+ dropDownMenu.FontSize = Enum.FontSize.Size18
+ dropDownMenu.TextXAlignment = Enum.TextXAlignment.Left
+ dropDownMenu.TextYAlignment = Enum.TextYAlignment.Center
+ dropDownMenu.BackgroundTransparency = 1
+ dropDownMenu.AutoButtonColor = true
+ if (whiteSkin) then
+ dropDownMenu.Style = Enum.ButtonStyle.RobloxRoundDropdownButton
+ else
+ dropDownMenu.Style = Enum.ButtonStyle.RobloxButton
+ end
+ dropDownMenu.Size = UDim2.new(1,0,1,0)
+ dropDownMenu.Parent = frame
+ dropDownMenu.ZIndex = 2 + baseZIndex
+
+ local dropDownIcon = Instance.new("ImageLabel")
+ dropDownIcon.Name = "Icon"
+ dropDownIcon.Active = false
+ if (whiteSkin) then
+ dropDownIcon.Image = "rbxasset://textures/ui/dropdown_arrow.png"
+ dropDownIcon.Size = UDim2.new(0,16,0,12)
+ dropDownIcon.Position = UDim2.new(1,-17,0.5, -6)
+ else
+ dropDownIcon.Image = "http://www.roblox.com/asset/?id=45732894"
+ dropDownIcon.Size = UDim2.new(0,11,0,6)
+ dropDownIcon.Position = UDim2.new(1,-11,0.5, -2)
+ end
+ dropDownIcon.BackgroundTransparency = 1
+ dropDownIcon.Parent = dropDownMenu
+ dropDownIcon.ZIndex = 2 + baseZIndex
+
+ local itemCount = #items
+ local dropDownItemCount = #items
+ local useScrollButtons = false
+ if dropDownItemCount > 6 then
+ useScrollButtons = true
+ dropDownItemCount = 6
+ end
+
+ local droppedDownMenu = Instance.new("TextButton")
+ droppedDownMenu.Name = "List"
+ droppedDownMenu.Text = ""
+ droppedDownMenu.BackgroundTransparency = 1
+ --droppedDownMenu.AutoButtonColor = true
+ if (whiteSkin) then
+ droppedDownMenu.Style = Enum.ButtonStyle.RobloxRoundDropdownButton
+ else
+ droppedDownMenu.Style = Enum.ButtonStyle.RobloxButton
+ end
+ droppedDownMenu.Visible = false
+ droppedDownMenu.Active = true --Blocks clicks
+ droppedDownMenu.Position = UDim2.new(0,0,0,0)
+ droppedDownMenu.Size = UDim2.new(1,0, (1 + dropDownItemCount)*.8, 0)
+ droppedDownMenu.Parent = frame
+ droppedDownMenu.ZIndex = 2 + baseZIndex
+
+ local choiceButton = Instance.new("TextButton")
+ choiceButton.Name = "ChoiceButton"
+ choiceButton.BackgroundTransparency = 1
+ choiceButton.BorderSizePixel = 0
+ choiceButton.Text = "ReplaceMe"
+ choiceButton.TextColor3 = textColor
+ choiceButton.TextXAlignment = Enum.TextXAlignment.Left
+ choiceButton.TextYAlignment = Enum.TextYAlignment.Center
+ choiceButton.BackgroundColor3 = Color3.new(1, 1, 1)
+ choiceButton.Font = Enum.Font.Arial
+ choiceButton.FontSize = Enum.FontSize.Size18
+ if useScrollButtons then
+ choiceButton.Size = UDim2.new(1,-13, .8/((dropDownItemCount + 1)*.8),0)
+ else
+ choiceButton.Size = UDim2.new(1, 0, .8/((dropDownItemCount + 1)*.8),0)
+ end
+ choiceButton.TextWrap = true
+ choiceButton.ZIndex = 2 + baseZIndex
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = true
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 3 + baseZIndex
+
+ local dropDownSelected = false
+
+ local scrollUpButton
+ local scrollDownButton
+ local scrollMouseCount = 0
+
+ local setZIndex = function(baseZIndex)
+ droppedDownMenu.ZIndex = baseZIndex +1
+ if scrollUpButton then
+ scrollUpButton.ZIndex = baseZIndex + 3
+ end
+ if scrollDownButton then
+ scrollDownButton.ZIndex = baseZIndex + 3
+ end
+
+ local children = droppedDownMenu:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child.Name == "ChoiceButton" then
+ child.ZIndex = baseZIndex + 2
+ elseif child.Name == "ClickCaptureButton" then
+ child.ZIndex = baseZIndex
+ end
+ end
+ end
+ end
+
+ local scrollBarPosition = 1
+ local updateScroll = function()
+ if scrollUpButton then
+ scrollUpButton.Active = scrollBarPosition > 1
+ end
+ if scrollDownButton then
+ scrollDownButton.Active = scrollBarPosition + dropDownItemCount <= itemCount
+ end
+
+ local children = droppedDownMenu:GetChildren()
+ if not children then return end
+
+ local childNum = 1
+ for i, obj in ipairs(children) do
+ if obj.Name == "ChoiceButton" then
+ if childNum < scrollBarPosition or childNum >= scrollBarPosition + dropDownItemCount then
+ obj.Visible = false
+ else
+ obj.Position = UDim2.new(0,0,((childNum-scrollBarPosition+1)*.8)/((dropDownItemCount+1)*.8),0)
+ obj.Visible = true
+ end
+ obj.TextColor3 = textColor
+ obj.BackgroundTransparency = 1
+
+ childNum = childNum + 1
+ end
+ end
+ end
+ local toggleVisibility = function()
+ dropDownSelected = not dropDownSelected
+
+ areaSoak.Visible = not areaSoak.Visible
+ dropDownMenu.Visible = not dropDownSelected
+ droppedDownMenu.Visible = dropDownSelected
+ if dropDownSelected then
+ setZIndex(4 + baseZIndex)
+ else
+ setZIndex(2 + baseZIndex)
+ end
+ if useScrollButtons then
+ updateScroll()
+ end
+ end
+ droppedDownMenu.MouseButton1Click:connect(toggleVisibility)
+
+ local updateSelection = function(text)
+ local foundItem = false
+ local children = droppedDownMenu:GetChildren()
+ local childNum = 1
+ if children then
+ for i, obj in ipairs(children) do
+ if obj.Name == "ChoiceButton" then
+ if obj.Text == text then
+ obj.Font = Enum.Font.ArialBold
+ foundItem = true
+ scrollBarPosition = childNum
+ if (whiteSkin) then
+ obj.TextColor3 = Color3.new(90/255,142/255,233/255)
+ end
+ else
+ obj.Font = Enum.Font.Arial
+ if (whiteSkin) then
+ obj.TextColor3 = textColor
+ end
+ end
+ childNum = childNum + 1
+ end
+ end
+ end
+ if not text then
+ dropDownMenu.Text = "Choose One"
+ scrollBarPosition = 1
+ else
+ if not foundItem then
+ error("Invalid Selection Update -- " .. text)
+ end
+
+ if scrollBarPosition + dropDownItemCount > itemCount + 1 then
+ scrollBarPosition = itemCount - dropDownItemCount + 1
+ end
+
+ dropDownMenu.Text = text
+ end
+ end
+
+ local function scrollDown()
+ if scrollBarPosition + dropDownItemCount <= itemCount then
+ scrollBarPosition = scrollBarPosition + 1
+ updateScroll()
+ return true
+ end
+ return false
+ end
+ local function scrollUp()
+ if scrollBarPosition > 1 then
+ scrollBarPosition = scrollBarPosition - 1
+ updateScroll()
+ return true
+ end
+ return false
+ end
+
+ if useScrollButtons then
+ --Make some scroll buttons
+ scrollUpButton = Instance.new("ImageButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.BackgroundTransparency = 1
+ scrollUpButton.Image = "rbxasset://textures/ui/scrollbuttonUp.png"
+ scrollUpButton.Size = UDim2.new(0,17,0,17)
+ scrollUpButton.Position = UDim2.new(1,-11,(1*.8)/((dropDownItemCount+1)*.8),0)
+ scrollUpButton.MouseButton1Click:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollUpButton.MouseLeave:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollUpButton.MouseButton1Down:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+
+ scrollUp()
+ local val = scrollMouseCount
+ wait(0.5)
+ while val == scrollMouseCount do
+ if scrollUp() == false then
+ break
+ end
+ wait(0.1)
+ end
+ end)
+
+ scrollUpButton.Parent = droppedDownMenu
+
+ scrollDownButton = Instance.new("ImageButton")
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.BackgroundTransparency = 1
+ scrollDownButton.Image = "rbxasset://textures/ui/scrollbuttonDown.png"
+ scrollDownButton.Size = UDim2.new(0,17,0,17)
+ scrollDownButton.Position = UDim2.new(1,-11,1,-11)
+ scrollDownButton.Parent = droppedDownMenu
+ scrollDownButton.MouseButton1Click:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollDownButton.MouseLeave:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+ end)
+ scrollDownButton.MouseButton1Down:connect(
+ function()
+ scrollMouseCount = scrollMouseCount + 1
+
+ scrollDown()
+ local val = scrollMouseCount
+ wait(0.5)
+ while val == scrollMouseCount do
+ if scrollDown() == false then
+ break
+ end
+ wait(0.1)
+ end
+ end)
+
+ local scrollbar = Instance.new("ImageLabel")
+ scrollbar.Name = "ScrollBar"
+ scrollbar.Image = "rbxasset://textures/ui/scrollbar.png"
+ scrollbar.BackgroundTransparency = 1
+ scrollbar.Size = UDim2.new(0, 18, (dropDownItemCount*.8)/((dropDownItemCount+1)*.8), -(17) - 11 - 4)
+ scrollbar.Position = UDim2.new(1,-11,(1*.8)/((dropDownItemCount+1)*.8),17+2)
+ scrollbar.Parent = droppedDownMenu
+ end
+
+ for i,item in ipairs(items) do
+ -- needed to maintain local scope for items in event listeners below
+ local button = choiceButton:clone()
+ if forRoblox then
+ button.RobloxLocked = true
+ end
+ button.Text = item
+ button.Parent = droppedDownMenu
+ if (whiteSkin) then
+ button.TextColor3 = textColor
+ end
+
+ button.MouseButton1Click:connect(function()
+ --Remove Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ button.BackgroundTransparency = 1
+
+ updateSelection(item)
+ onSelect(item)
+
+ toggleVisibility()
+ end)
+ button.MouseEnter:connect(function()
+ --Add Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(0,0,0)
+ end
+ button.BackgroundTransparency = 0
+ end)
+
+ button.MouseLeave:connect(function()
+ --Remove Highlight
+ if (not whiteSkin) then
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ button.BackgroundTransparency = 1
+ end)
+ end
+
+ --This does the initial layout of the buttons
+ updateScroll()
+
+ frame.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(frame)
+ end
+ end)
+
+ dropDownMenu.MouseButton1Click:connect(toggleVisibility)
+ areaSoak.MouseButton1Click:connect(toggleVisibility)
+ return frame, updateSelection
+end
+
+t.CreatePropertyDropDownMenu = function(instance, property, enum)
+
+ local items = enum:GetEnumItems()
+ local names = {}
+ local nameToItem = {}
+ for i,obj in ipairs(items) do
+ names[i] = obj.Name
+ nameToItem[obj.Name] = obj
+ end
+
+ local frame
+ local updateSelection
+ frame, updateSelection = t.CreateDropDownMenu(names, function(text) instance[property] = nameToItem[text] end)
+
+ ScopedConnect(frame, instance, "Changed",
+ function(prop)
+ if prop == property then
+ updateSelection(instance[property].Name)
+ end
+ end,
+ function()
+ updateSelection(instance[property].Name)
+ end)
+
+ return frame
+end
+
+t.GetFontHeight = function(font, fontSize)
+ if font == nil or fontSize == nil then
+ error("Font and FontSize must be non-nil")
+ end
+
+ if font == Enum.Font.Legacy then
+ if fontSize == Enum.FontSize.Size8 then
+ return 12
+ elseif fontSize == Enum.FontSize.Size9 then
+ return 14
+ elseif fontSize == Enum.FontSize.Size10 then
+ return 15
+ elseif fontSize == Enum.FontSize.Size11 then
+ return 17
+ elseif fontSize == Enum.FontSize.Size12 then
+ return 18
+ elseif fontSize == Enum.FontSize.Size14 then
+ return 21
+ elseif fontSize == Enum.FontSize.Size18 then
+ return 27
+ elseif fontSize == Enum.FontSize.Size24 then
+ return 36
+ elseif fontSize == Enum.FontSize.Size36 then
+ return 54
+ elseif fontSize == Enum.FontSize.Size48 then
+ return 72
+ else
+ error("Unknown FontSize")
+ end
+ elseif font == Enum.Font.Arial or font == Enum.Font.ArialBold then
+ if fontSize == Enum.FontSize.Size8 then
+ return 8
+ elseif fontSize == Enum.FontSize.Size9 then
+ return 9
+ elseif fontSize == Enum.FontSize.Size10 then
+ return 10
+ elseif fontSize == Enum.FontSize.Size11 then
+ return 11
+ elseif fontSize == Enum.FontSize.Size12 then
+ return 12
+ elseif fontSize == Enum.FontSize.Size14 then
+ return 14
+ elseif fontSize == Enum.FontSize.Size18 then
+ return 18
+ elseif fontSize == Enum.FontSize.Size24 then
+ return 24
+ elseif fontSize == Enum.FontSize.Size36 then
+ return 36
+ elseif fontSize == Enum.FontSize.Size48 then
+ return 48
+ else
+ error("Unknown FontSize")
+ end
+ else
+ error("Unknown Font " .. font)
+ end
+end
+
+local function layoutGuiObjectsHelper(frame, guiObjects, settingsTable)
+ local totalPixels = frame.AbsoluteSize.Y
+ local pixelsRemaining = frame.AbsoluteSize.Y
+ for i, child in ipairs(guiObjects) do
+ if child:IsA("TextLabel") or child:IsA("TextButton") then
+ local isLabel = child:IsA("TextLabel")
+ if isLabel then
+ pixelsRemaining = pixelsRemaining - settingsTable["TextLabelPositionPadY"]
+ else
+ pixelsRemaining = pixelsRemaining - settingsTable["TextButtonPositionPadY"]
+ end
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, pixelsRemaining)
+
+ if child.TextFits and child.TextBounds.Y < pixelsRemaining then
+ child.Visible = true
+ if isLabel then
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.TextBounds.Y + settingsTable["TextLabelSizePadY"])
+ else
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.TextBounds.Y + settingsTable["TextButtonSizePadY"])
+ end
+
+ while not child.TextFits do
+ child.Size = UDim2.new(child.Size.X.Scale, child.Size.X.Offset, 0, child.AbsoluteSize.Y + 1)
+ end
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+
+ if isLabel then
+ pixelsRemaining = pixelsRemaining - settingsTable["TextLabelPositionPadY"]
+ else
+ pixelsRemaining = pixelsRemaining - settingsTable["TextButtonPositionPadY"]
+ end
+ else
+ child.Visible = false
+ pixelsRemaining = -1
+ end
+
+ else
+ --GuiObject
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+ child.Visible = (pixelsRemaining >= 0)
+ end
+ end
+end
+
+t.LayoutGuiObjects = function(frame, guiObjects, settingsTable)
+ if not frame:IsA("GuiObject") then
+ error("Frame must be a GuiObject")
+ end
+ for i, child in ipairs(guiObjects) do
+ if not child:IsA("GuiObject") then
+ error("All elements that are layed out must be of type GuiObject")
+ end
+ end
+
+ if not settingsTable then
+ settingsTable = {}
+ end
+
+ if not settingsTable["TextLabelSizePadY"] then
+ settingsTable["TextLabelSizePadY"] = 0
+ end
+ if not settingsTable["TextLabelPositionPadY"] then
+ settingsTable["TextLabelPositionPadY"] = 0
+ end
+ if not settingsTable["TextButtonSizePadY"] then
+ settingsTable["TextButtonSizePadY"] = 12
+ end
+ if not settingsTable["TextButtonPositionPadY"] then
+ settingsTable["TextButtonPositionPadY"] = 2
+ end
+
+ --Wrapper frame takes care of styled objects
+ local wrapperFrame = Instance.new("Frame")
+ wrapperFrame.Name = "WrapperFrame"
+ wrapperFrame.BackgroundTransparency = 1
+ wrapperFrame.Size = UDim2.new(1,0,1,0)
+ wrapperFrame.Parent = frame
+
+ for i, child in ipairs(guiObjects) do
+ child.Parent = wrapperFrame
+ end
+
+ local recalculate = function()
+ wait()
+ layoutGuiObjectsHelper(wrapperFrame, guiObjects, settingsTable)
+ end
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ --Wait a heartbeat for it to sync in
+ recalculate(nil)
+ end
+ end)
+ frame.AncestryChanged:connect(recalculate)
+
+ layoutGuiObjectsHelper(wrapperFrame, guiObjects, settingsTable)
+end
+
+
+t.CreateSlider = function(steps,width,position)
+ local sliderGui = Instance.new("Frame")
+ sliderGui.Size = UDim2.new(1,0,1,0)
+ sliderGui.BackgroundTransparency = 1
+ sliderGui.Name = "SliderGui"
+
+ local sliderSteps = Instance.new("IntValue")
+ sliderSteps.Name = "SliderSteps"
+ sliderSteps.Value = steps
+ sliderSteps.Parent = sliderGui
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = false
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 4
+
+ sliderGui.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(sliderGui)
+ end
+ end)
+
+ local sliderPosition = Instance.new("IntValue")
+ sliderPosition.Name = "SliderPosition"
+ sliderPosition.Value = 0
+ sliderPosition.Parent = sliderGui
+
+ local id = math.random(1,100)
+
+ local bar = Instance.new("TextButton")
+ bar.Text = ""
+ bar.AutoButtonColor = false
+ bar.Name = "Bar"
+ bar.BackgroundColor3 = Color3.new(0,0,0)
+ if type(width) == "number" then
+ bar.Size = UDim2.new(0,width,0,5)
+ else
+ bar.Size = UDim2.new(0,200,0,5)
+ end
+ bar.BorderColor3 = Color3.new(95/255,95/255,95/255)
+ bar.ZIndex = 2
+ bar.Parent = sliderGui
+
+ if position["X"] and position["X"]["Scale"] and position["X"]["Offset"] and position["Y"] and position["Y"]["Scale"] and position["Y"]["Offset"] then
+ bar.Position = position
+ end
+
+ local slider = Instance.new("ImageButton")
+ slider.Name = "Slider"
+ slider.BackgroundTransparency = 1
+ slider.Image = "rbxasset://textures/ui/Slider.png"
+ slider.Position = UDim2.new(0,0,0.5,-10)
+ slider.Size = UDim2.new(0,20,0,20)
+ slider.ZIndex = 3
+ slider.Parent = bar
+
+ local areaSoakMouseMoveCon = nil
+
+ areaSoak.MouseLeave:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+ areaSoak.MouseButton1Up:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+
+ slider.MouseButton1Down:connect(function()
+ areaSoak.Visible = true
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+ areaSoakMouseMoveCon = areaSoak.MouseMoved:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+ end)
+
+ slider.MouseButton1Up:connect(function() cancelSlide(areaSoak) end)
+
+ sliderPosition.Changed:connect(function(prop)
+ sliderPosition.Value = math.min(steps, math.max(1,sliderPosition.Value))
+ local relativePosX = (sliderPosition.Value - 1) / (steps - 1)
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ end)
+
+ bar.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ return sliderGui, sliderPosition, sliderSteps
+
+end
+
+
+
+t.CreateSliderNew = function(steps,width,position)
+ local sliderGui = Instance.new("Frame")
+ sliderGui.Size = UDim2.new(1,0,1,0)
+ sliderGui.BackgroundTransparency = 1
+ sliderGui.Name = "SliderGui"
+
+ local sliderSteps = Instance.new("IntValue")
+ sliderSteps.Name = "SliderSteps"
+ sliderSteps.Value = steps
+ sliderSteps.Parent = sliderGui
+
+ local areaSoak = Instance.new("TextButton")
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Text = ""
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.Active = false
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.Visible = false
+ areaSoak.ZIndex = 6
+
+ sliderGui.AncestryChanged:connect(function(child,parent)
+ if parent == nil then
+ areaSoak.Parent = nil
+ else
+ areaSoak.Parent = getScreenGuiAncestor(sliderGui)
+ end
+ end)
+
+ local sliderPosition = Instance.new("IntValue")
+ sliderPosition.Name = "SliderPosition"
+ sliderPosition.Value = 0
+ sliderPosition.Parent = sliderGui
+
+ local id = math.random(1,100)
+
+ local sliderBarImgHeight = 7
+ local sliderBarCapImgWidth = 4
+
+ local bar = Instance.new("ImageButton")
+ bar.BackgroundTransparency = 1
+ bar.Image = "rbxasset://textures/ui/Slider-BKG-Center.png"
+ bar.Name = "Bar"
+ local displayWidth = 200
+ if type(width) == "number" then
+ bar.Size = UDim2.new(0,width - (sliderBarCapImgWidth * 2),0,sliderBarImgHeight)
+ displayWidth = width - (sliderBarCapImgWidth * 2)
+ else
+ bar.Size = UDim2.new(0,200,0,sliderBarImgHeight)
+ end
+ bar.ZIndex = 3
+ bar.Parent = sliderGui
+ if position["X"] and position["X"]["Scale"] and position["X"]["Offset"] and position["Y"] and position["Y"]["Scale"] and position["Y"]["Offset"] then
+ bar.Position = position
+ end
+
+ local barLeft = bar:clone()
+ barLeft.Name = "BarLeft"
+ barLeft.Image = "rbxasset://textures/ui/Slider-BKG-Left-Cap.png"
+ barLeft.Size = UDim2.new(0, sliderBarCapImgWidth, 0, sliderBarImgHeight)
+ barLeft.Position = UDim2.new(position.X.Scale, position.X.Offset - sliderBarCapImgWidth, position.Y.Scale, position.Y.Offset)
+ barLeft.Parent = sliderGui
+ barLeft.ZIndex = 3
+
+ local barRight = barLeft:clone()
+ barRight.Name = "BarRight"
+ barRight.Image = "rbxasset://textures/ui/Slider-BKG-Right-Cap.png"
+ barRight.Position = UDim2.new(position.X.Scale, position.X.Offset + displayWidth, position.Y.Scale, position.Y.Offset)
+ barRight.Parent = sliderGui
+
+ local fillLeft = barLeft:clone()
+ fillLeft.Name = "FillLeft"
+ fillLeft.Image = "rbxasset://textures/ui/Slider-Fill-Left-Cap.png"
+ fillLeft.Parent = sliderGui
+ fillLeft.ZIndex = 4
+
+ local fill = fillLeft:clone()
+ fill.Name = "Fill"
+ fill.Image = "rbxasset://textures/ui/Slider-Fill-Center.png"
+ fill.Parent = bar
+ fill.ZIndex = 4
+ fill.Position = UDim2.new(0, 0, 0, 0)
+ fill.Size = UDim2.new(0.5, 0, 1, 0)
+
+
+-- bar.Visible = false
+
+ local slider = Instance.new("ImageButton")
+ slider.Name = "Slider"
+ slider.BackgroundTransparency = 1
+ slider.Image = "rbxasset://textures/ui/slider_new_tab.png"
+ slider.Position = UDim2.new(0,0,0.5,-14)
+ slider.Size = UDim2.new(0,28,0,28)
+ slider.ZIndex = 5
+ slider.Parent = bar
+
+ local areaSoakMouseMoveCon = nil
+
+ areaSoak.MouseLeave:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+ areaSoak.MouseButton1Up:connect(function()
+ if areaSoak.Visible then
+ cancelSlide(areaSoak)
+ end
+ end)
+
+ slider.MouseButton1Down:connect(function()
+ areaSoak.Visible = true
+ if areaSoakMouseMoveCon then areaSoakMouseMoveCon:disconnect() end
+ areaSoakMouseMoveCon = areaSoak.MouseMoved:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+ end)
+
+ slider.MouseButton1Up:connect(function() cancelSlide(areaSoak) end)
+
+ sliderPosition.Changed:connect(function(prop)
+ sliderPosition.Value = math.min(steps, math.max(1,sliderPosition.Value))
+ local relativePosX = (sliderPosition.Value - 1) / (steps - 1)
+ slider.Position = UDim2.new(relativePosX,-slider.AbsoluteSize.X/2,slider.Position.Y.Scale,slider.Position.Y.Offset)
+ fill.Size = UDim2.new(relativePosX, 0, 1, 0)
+ end)
+
+ bar.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ fill.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+ fillLeft.MouseButton1Down:connect(function(x,y)
+ setSliderPos(x,slider,sliderPosition,bar,steps)
+ end)
+
+
+ return sliderGui, sliderPosition, sliderSteps
+
+end
+
+
+
+
+
+t.CreateTrueScrollingFrame = function()
+ local lowY = nil
+ local highY = nil
+
+ local dragCon = nil
+ local upCon = nil
+
+ local internalChange = false
+
+ local descendantsChangeConMap = {}
+
+ local scrollingFrame = Instance.new("Frame")
+ scrollingFrame.Name = "ScrollingFrame"
+ scrollingFrame.Active = true
+ scrollingFrame.Size = UDim2.new(1,0,1,0)
+ scrollingFrame.ClipsDescendants = true
+
+ local controlFrame = Instance.new("Frame")
+ controlFrame.Name = "ControlFrame"
+ controlFrame.BackgroundTransparency = 1
+ controlFrame.Size = UDim2.new(0,18,1,0)
+ controlFrame.Position = UDim2.new(1,-20,0,0)
+ controlFrame.Parent = scrollingFrame
+
+ local scrollBottom = Instance.new("BoolValue")
+ scrollBottom.Value = false
+ scrollBottom.Name = "ScrollBottom"
+ scrollBottom.Parent = controlFrame
+
+ local scrollUp = Instance.new("BoolValue")
+ scrollUp.Value = false
+ scrollUp.Name = "scrollUp"
+ scrollUp.Parent = controlFrame
+
+ local scrollUpButton = Instance.new("TextButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.Text = ""
+ scrollUpButton.AutoButtonColor = false
+ scrollUpButton.BackgroundColor3 = Color3.new(0,0,0)
+ scrollUpButton.BorderColor3 = Color3.new(1,1,1)
+ scrollUpButton.BackgroundTransparency = 0.5
+ scrollUpButton.Size = UDim2.new(0,18,0,18)
+ scrollUpButton.ZIndex = 2
+ scrollUpButton.Parent = controlFrame
+ for i = 1, 6 do
+ local triFrame = Instance.new("Frame")
+ triFrame.BorderColor3 = Color3.new(1,1,1)
+ triFrame.Name = "tri" .. tostring(i)
+ triFrame.ZIndex = 3
+ triFrame.BackgroundTransparency = 0.5
+ triFrame.Size = UDim2.new(0,12 - ((i -1) * 2),0,0)
+ triFrame.Position = UDim2.new(0,3 + (i -1),0.5,2 - (i -1))
+ triFrame.Parent = scrollUpButton
+ end
+ scrollUpButton.MouseEnter:connect(function()
+ scrollUpButton.BackgroundTransparency = 0.1
+ local upChildren = scrollUpButton:GetChildren()
+ for i = 1, #upChildren do
+ upChildren[i].BackgroundTransparency = 0.1
+ end
+ end)
+ scrollUpButton.MouseLeave:connect(function()
+ scrollUpButton.BackgroundTransparency = 0.5
+ local upChildren = scrollUpButton:GetChildren()
+ for i = 1, #upChildren do
+ upChildren[i].BackgroundTransparency = 0.5
+ end
+ end)
+
+ local scrollDownButton = scrollUpButton:clone()
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.Position = UDim2.new(0,0,1,-18)
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].Position = UDim2.new(0,3 + (i -1),0.5,-2 + (i - 1))
+ end
+ scrollDownButton.MouseEnter:connect(function()
+ scrollDownButton.BackgroundTransparency = 0.1
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].BackgroundTransparency = 0.1
+ end
+ end)
+ scrollDownButton.MouseLeave:connect(function()
+ scrollDownButton.BackgroundTransparency = 0.5
+ local downChildren = scrollDownButton:GetChildren()
+ for i = 1, #downChildren do
+ downChildren[i].BackgroundTransparency = 0.5
+ end
+ end)
+ scrollDownButton.Parent = controlFrame
+
+ local scrollTrack = Instance.new("Frame")
+ scrollTrack.Name = "ScrollTrack"
+ scrollTrack.BackgroundTransparency = 1
+ scrollTrack.Size = UDim2.new(0,18,1,-38)
+ scrollTrack.Position = UDim2.new(0,0,0,19)
+ scrollTrack.Parent = controlFrame
+
+ local scrollbar = Instance.new("TextButton")
+ scrollbar.BackgroundColor3 = Color3.new(0,0,0)
+ scrollbar.BorderColor3 = Color3.new(1,1,1)
+ scrollbar.BackgroundTransparency = 0.5
+ scrollbar.AutoButtonColor = false
+ scrollbar.Text = ""
+ scrollbar.Active = true
+ scrollbar.Name = "ScrollBar"
+ scrollbar.ZIndex = 2
+ scrollbar.BackgroundTransparency = 0.5
+ scrollbar.Size = UDim2.new(0, 18, 0.1, 0)
+ scrollbar.Position = UDim2.new(0,0,0,0)
+ scrollbar.Parent = scrollTrack
+
+ local scrollNub = Instance.new("Frame")
+ scrollNub.Name = "ScrollNub"
+ scrollNub.BorderColor3 = Color3.new(1,1,1)
+ scrollNub.Size = UDim2.new(0,10,0,0)
+ scrollNub.Position = UDim2.new(0.5,-5,0.5,0)
+ scrollNub.ZIndex = 2
+ scrollNub.BackgroundTransparency = 0.5
+ scrollNub.Parent = scrollbar
+
+ local newNub = scrollNub:clone()
+ newNub.Position = UDim2.new(0.5,-5,0.5,-2)
+ newNub.Parent = scrollbar
+
+ local lastNub = scrollNub:clone()
+ lastNub.Position = UDim2.new(0.5,-5,0.5,2)
+ lastNub.Parent = scrollbar
+
+ scrollbar.MouseEnter:connect(function()
+ scrollbar.BackgroundTransparency = 0.1
+ scrollNub.BackgroundTransparency = 0.1
+ newNub.BackgroundTransparency = 0.1
+ lastNub.BackgroundTransparency = 0.1
+ end)
+ scrollbar.MouseLeave:connect(function()
+ scrollbar.BackgroundTransparency = 0.5
+ scrollNub.BackgroundTransparency = 0.5
+ newNub.BackgroundTransparency = 0.5
+ lastNub.BackgroundTransparency = 0.5
+ end)
+
+ local mouseDrag = Instance.new("ImageButton")
+ mouseDrag.Active = false
+ mouseDrag.Size = UDim2.new(1.5, 0, 1.5, 0)
+ mouseDrag.AutoButtonColor = false
+ mouseDrag.BackgroundTransparency = 1
+ mouseDrag.Name = "mouseDrag"
+ mouseDrag.Position = UDim2.new(-0.25, 0, -0.25, 0)
+ mouseDrag.ZIndex = 10
+
+ local function positionScrollBar(x,y,offset)
+ local oldPos = scrollbar.Position
+
+ if y < scrollTrack.AbsolutePosition.y then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,0,0)
+ return (oldPos ~= scrollbar.Position)
+ end
+
+ local relativeSize = scrollbar.AbsoluteSize.Y/scrollTrack.AbsoluteSize.Y
+
+ if y > (scrollTrack.AbsolutePosition.y + scrollTrack.AbsoluteSize.y) then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,1 - relativeSize,0)
+ return (oldPos ~= scrollbar.Position)
+ end
+ local newScaleYPos = (y - scrollTrack.AbsolutePosition.y - offset)/scrollTrack.AbsoluteSize.y
+ if newScaleYPos + relativeSize > 1 then
+ newScaleYPos = 1 - relativeSize
+ scrollBottom.Value = true
+ scrollUp.Value = false
+ elseif newScaleYPos <= 0 then
+ newScaleYPos = 0
+ scrollUp.Value = true
+ scrollBottom.Value = false
+ else
+ scrollUp.Value = false
+ scrollBottom.Value = false
+ end
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,newScaleYPos,0)
+
+ return (oldPos ~= scrollbar.Position)
+ end
+
+ local function drillDownSetHighLow(instance)
+ if not instance or not instance:IsA("GuiObject") then return end
+ if instance == controlFrame then return end
+ if instance:IsDescendantOf(controlFrame) then return end
+ if not instance.Visible then return end
+
+ if lowY and lowY > instance.AbsolutePosition.Y then
+ lowY = instance.AbsolutePosition.Y
+ elseif not lowY then
+ lowY = instance.AbsolutePosition.Y
+ end
+ if highY and highY < (instance.AbsolutePosition.Y + instance.AbsoluteSize.Y) then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ elseif not highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ end
+ local children = instance:GetChildren()
+ for i = 1, #children do
+ drillDownSetHighLow(children[i])
+ end
+ end
+
+ local function resetHighLow()
+ local firstChildren = scrollingFrame:GetChildren()
+
+ for i = 1, #firstChildren do
+ drillDownSetHighLow(firstChildren[i])
+ end
+ end
+
+ local function recalculate()
+ internalChange = true
+
+ local percentFrame = 0
+ if scrollbar.Position.Y.Scale > 0 then
+ if scrollbar.Visible then
+ percentFrame = scrollbar.Position.Y.Scale/((scrollTrack.AbsoluteSize.Y - scrollbar.AbsoluteSize.Y)/scrollTrack.AbsoluteSize.Y)
+ else
+ percentFrame = 0
+ end
+ end
+ if percentFrame > 0.99 then percentFrame = 1 end
+
+ local hiddenYAmount = (scrollingFrame.AbsoluteSize.Y - (highY - lowY)) * percentFrame
+
+ local guiChildren = scrollingFrame:GetChildren()
+ for i = 1, #guiChildren do
+ if guiChildren[i] ~= controlFrame then
+ guiChildren[i].Position = UDim2.new(guiChildren[i].Position.X.Scale,guiChildren[i].Position.X.Offset,
+ 0, math.ceil(guiChildren[i].AbsolutePosition.Y) - math.ceil(lowY) + hiddenYAmount)
+ end
+ end
+
+ lowY = nil
+ highY = nil
+ resetHighLow()
+ internalChange = false
+ end
+
+ local function setSliderSizeAndPosition()
+ if not highY or not lowY then return end
+
+ local totalYSpan = math.abs(highY - lowY)
+ if totalYSpan == 0 then
+ scrollbar.Visible = false
+ scrollDownButton.Visible = false
+ scrollUpButton.Visible = false
+
+ if dragCon then dragCon:disconnect() dragCon = nil end
+ if upCon then upCon:disconnect() upCon = nil end
+ return
+ end
+
+ local percentShown = scrollingFrame.AbsoluteSize.Y/totalYSpan
+ if percentShown >= 1 then
+ scrollbar.Visible = false
+ scrollDownButton.Visible = false
+ scrollUpButton.Visible = false
+ recalculate()
+ else
+ scrollbar.Visible = true
+ scrollDownButton.Visible = true
+ scrollUpButton.Visible = true
+
+ scrollbar.Size = UDim2.new(scrollbar.Size.X.Scale,scrollbar.Size.X.Offset,percentShown,0)
+ end
+
+ local percentPosition = (scrollingFrame.AbsolutePosition.Y - lowY)/totalYSpan
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,percentPosition,-scrollbar.AbsoluteSize.X/2)
+
+ if scrollbar.AbsolutePosition.y < scrollTrack.AbsolutePosition.y then
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,0,0)
+ end
+
+ if (scrollbar.AbsolutePosition.y + scrollbar.AbsoluteSize.Y) > (scrollTrack.AbsolutePosition.y + scrollTrack.AbsoluteSize.y) then
+ local relativeSize = scrollbar.AbsoluteSize.Y/scrollTrack.AbsoluteSize.Y
+ scrollbar.Position = UDim2.new(scrollbar.Position.X.Scale,scrollbar.Position.X.Offset,1 - relativeSize,0)
+ end
+ end
+
+ local buttonScrollAmountPixels = 7
+ local reentrancyGuardScrollUp = false
+ local function doScrollUp()
+ if reentrancyGuardScrollUp then return end
+
+ reentrancyGuardScrollUp = true
+ if positionScrollBar(0,scrollbar.AbsolutePosition.Y - buttonScrollAmountPixels,0) then
+ recalculate()
+ end
+ reentrancyGuardScrollUp = false
+ end
+
+ local reentrancyGuardScrollDown = false
+ local function doScrollDown()
+ if reentrancyGuardScrollDown then return end
+
+ reentrancyGuardScrollDown = true
+ if positionScrollBar(0,scrollbar.AbsolutePosition.Y + buttonScrollAmountPixels,0) then
+ recalculate()
+ end
+ reentrancyGuardScrollDown = false
+ end
+
+ local function scrollUp(mouseYPos)
+ if scrollUpButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local upCon
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ upCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollUp()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollUp()
+ if mouseYPos and mouseYPos > scrollbar.AbsolutePosition.y then
+ break
+ end
+ if not scrollUpButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local function scrollDown(mouseYPos)
+ if scrollDownButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local downCon
+ downCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ downCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollDown()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollDown()
+ if mouseYPos and mouseYPos < (scrollbar.AbsolutePosition.y + scrollbar.AbsoluteSize.x) then
+ break
+ end
+ if not scrollDownButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ scrollbar.MouseButton1Down:connect(function(x,y)
+ if scrollbar.Active then
+ scrollStamp = tick()
+ local mouseOffset = y - scrollbar.AbsolutePosition.y
+ if dragCon then dragCon:disconnect() dragCon = nil end
+ if upCon then upCon:disconnect() upCon = nil end
+ local prevY = y
+ local reentrancyGuardMouseScroll = false
+ dragCon = mouseDrag.MouseMoved:connect(function(x,y)
+ if reentrancyGuardMouseScroll then return end
+
+ reentrancyGuardMouseScroll = true
+ if positionScrollBar(x,y,mouseOffset) then
+ recalculate()
+ end
+ reentrancyGuardMouseScroll = false
+
+ end)
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ dragCon:disconnect(); dragCon = nil
+ upCon:disconnect(); drag = nil
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ end
+ end)
+
+ local scrollMouseCount = 0
+
+ scrollUpButton.MouseButton1Down:connect(function()
+ scrollUp()
+ end)
+ scrollUpButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+ scrollDownButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollDownButton.MouseButton1Down:connect(function()
+ scrollDown()
+ end)
+
+ scrollbar.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+ local function heightCheck(instance)
+ if highY and (instance.AbsolutePosition.Y + instance.AbsoluteSize.Y) > highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ elseif not highY then
+ highY = instance.AbsolutePosition.Y + instance.AbsoluteSize.Y
+ end
+ setSliderSizeAndPosition()
+ end
+
+ local function highLowRecheck()
+ local oldLowY = lowY
+ local oldHighY = highY
+ lowY = nil
+ highY = nil
+ resetHighLow()
+
+ if (lowY ~= oldLowY) or (highY ~= oldHighY) then
+ setSliderSizeAndPosition()
+ end
+ end
+
+ local function descendantChanged(this, prop)
+ if internalChange then return end
+ if not this.Visible then return end
+
+ if prop == "Size" or prop == "Position" then
+ wait()
+ highLowRecheck()
+ end
+ end
+
+ scrollingFrame.DescendantAdded:connect(function(instance)
+ if not instance:IsA("GuiObject") then return end
+
+ if instance.Visible then
+ wait() -- wait a heartbeat for sizes to reconfig
+ highLowRecheck()
+ end
+
+ descendantsChangeConMap[instance] = instance.Changed:connect(function(prop) descendantChanged(instance, prop) end)
+ end)
+
+ scrollingFrame.DescendantRemoving:connect(function(instance)
+ if not instance:IsA("GuiObject") then return end
+ if descendantsChangeConMap[instance] then
+ descendantsChangeConMap[instance]:disconnect()
+ descendantsChangeConMap[instance] = nil
+ end
+ wait() -- wait a heartbeat for sizes to reconfig
+ highLowRecheck()
+ end)
+
+ scrollingFrame.Changed:connect(function(prop)
+ if prop == "AbsoluteSize" then
+ if not highY or not lowY then return end
+
+ highLowRecheck()
+ setSliderSizeAndPosition()
+ end
+ end)
+
+ return scrollingFrame, controlFrame
+end
+
+t.CreateScrollingFrame = function(orderList,scrollStyle)
+ local frame = Instance.new("Frame")
+ frame.Name = "ScrollingFrame"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+
+ local scrollUpButton = Instance.new("ImageButton")
+ scrollUpButton.Name = "ScrollUpButton"
+ scrollUpButton.BackgroundTransparency = 1
+ scrollUpButton.Image = "rbxasset://textures/ui/scrollbuttonUp.png"
+ scrollUpButton.Size = UDim2.new(0,17,0,17)
+
+
+ local scrollDownButton = Instance.new("ImageButton")
+ scrollDownButton.Name = "ScrollDownButton"
+ scrollDownButton.BackgroundTransparency = 1
+ scrollDownButton.Image = "rbxasset://textures/ui/scrollbuttonDown.png"
+ scrollDownButton.Size = UDim2.new(0,17,0,17)
+
+ local scrollbar = Instance.new("ImageButton")
+ scrollbar.Name = "ScrollBar"
+ scrollbar.Image = "rbxasset://textures/ui/scrollbar.png"
+ scrollbar.BackgroundTransparency = 1
+ scrollbar.Size = UDim2.new(0, 18, 0, 150)
+
+ local scrollStamp = 0
+
+ local scrollDrag = Instance.new("ImageButton")
+ scrollDrag.Image = "http://www.roblox.com/asset/?id=61367186"
+ scrollDrag.Size = UDim2.new(1, 0, 0, 16)
+ scrollDrag.BackgroundTransparency = 1
+ scrollDrag.Name = "ScrollDrag"
+ scrollDrag.Active = true
+ scrollDrag.Parent = scrollbar
+
+ local mouseDrag = Instance.new("ImageButton")
+ mouseDrag.Active = false
+ mouseDrag.Size = UDim2.new(1.5, 0, 1.5, 0)
+ mouseDrag.AutoButtonColor = false
+ mouseDrag.BackgroundTransparency = 1
+ mouseDrag.Name = "mouseDrag"
+ mouseDrag.Position = UDim2.new(-0.25, 0, -0.25, 0)
+ mouseDrag.ZIndex = 10
+
+ local style = "simple"
+ if scrollStyle and tostring(scrollStyle) then
+ style = scrollStyle
+ end
+
+ local scrollPosition = 1
+ local rowSize = 0
+ local howManyDisplayed = 0
+
+ local layoutGridScrollBar = function()
+ howManyDisplayed = 0
+ local guiObjects = {}
+ if orderList then
+ for i, child in ipairs(orderList) do
+ if child.Parent == frame then
+ table.insert(guiObjects, child)
+ end
+ end
+ else
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ table.insert(guiObjects, child)
+ end
+ end
+ end
+ end
+ if #guiObjects == 0 then
+ scrollUpButton.Active = false
+ scrollDownButton.Active = false
+ scrollDrag.Active = false
+ scrollPosition = 1
+ return
+ end
+
+ if scrollPosition > #guiObjects then
+ scrollPosition = #guiObjects
+ end
+
+ if scrollPosition < 1 then scrollPosition = 1 end
+
+ local totalPixelsY = frame.AbsoluteSize.Y
+ local pixelsRemainingY = frame.AbsoluteSize.Y
+
+ local totalPixelsX = frame.AbsoluteSize.X
+
+ local xCounter = 0
+ local rowSizeCounter = 0
+ local setRowSize = true
+
+ local pixelsBelowScrollbar = 0
+ local pos = #guiObjects
+
+ local currentRowY = 0
+
+ pos = scrollPosition
+ --count up from current scroll position to fill out grid
+ while pos <= #guiObjects and pixelsBelowScrollbar < totalPixelsY do
+ xCounter = xCounter + guiObjects[pos].AbsoluteSize.X
+ --previous pos was the end of a row
+ if xCounter >= totalPixelsX then
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ currentRowY = 0
+ xCounter = guiObjects[pos].AbsoluteSize.X
+ end
+ if guiObjects[pos].AbsoluteSize.Y > currentRowY then
+ currentRowY = guiObjects[pos].AbsoluteSize.Y
+ end
+ pos = pos + 1
+ end
+ --Count wherever current row left off
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ currentRowY = 0
+
+ pos = scrollPosition - 1
+ xCounter = 0
+
+ --objects with varying X,Y dimensions can rarely cause minor errors
+ --rechecking every new scrollPosition is necessary to avoid 100% of errors
+
+ --count backwards from current scrollPosition to see if we can add more rows
+ while pixelsBelowScrollbar + currentRowY < totalPixelsY and pos >= 1 do
+ xCounter = xCounter + guiObjects[pos].AbsoluteSize.X
+ rowSizeCounter = rowSizeCounter + 1
+ if xCounter >= totalPixelsX then
+ rowSize = rowSizeCounter - 1
+ rowSizeCounter = 0
+ xCounter = guiObjects[pos].AbsoluteSize.X
+ if pixelsBelowScrollbar + currentRowY <= totalPixelsY then
+ --It fits, so back up our scroll position
+ pixelsBelowScrollbar = pixelsBelowScrollbar + currentRowY
+ if scrollPosition <= rowSize then
+ scrollPosition = 1
+ break
+ else
+ scrollPosition = scrollPosition - rowSize
+ end
+ currentRowY = 0
+ else
+ break
+ end
+ end
+
+ if guiObjects[pos].AbsoluteSize.Y > currentRowY then
+ currentRowY = guiObjects[pos].AbsoluteSize.Y
+ end
+
+ pos = pos - 1
+ end
+
+ --Do check last time if pos = 0
+ if (pos == 0) and (pixelsBelowScrollbar + currentRowY <= totalPixelsY) then
+ scrollPosition = 1
+ end
+
+ xCounter = 0
+ --pos = scrollPosition
+ rowSizeCounter = 0
+ setRowSize = true
+ local lastChildSize = 0
+
+ local xOffset,yOffset = 0
+ if guiObjects[1] then
+ yOffset = math.ceil(math.floor(math.fmod(totalPixelsY,guiObjects[1].AbsoluteSize.X))/2)
+ xOffset = math.ceil(math.floor(math.fmod(totalPixelsX,guiObjects[1].AbsoluteSize.Y))/2)
+ end
+
+ for i, child in ipairs(guiObjects) do
+ if i < scrollPosition then
+ --print("Hiding " .. child.Name)
+ child.Visible = false
+ else
+ if pixelsRemainingY < 0 then
+ --print("Out of Space " .. child.Name)
+ child.Visible = false
+ else
+ --print("Laying out " .. child.Name)
+ --GuiObject
+ if setRowSize then rowSizeCounter = rowSizeCounter + 1 end
+ if xCounter + child.AbsoluteSize.X >= totalPixelsX then
+ if setRowSize then
+ rowSize = rowSizeCounter - 1
+ setRowSize = false
+ end
+ xCounter = 0
+ pixelsRemainingY = pixelsRemainingY - child.AbsoluteSize.Y
+ end
+ child.Position = UDim2.new(child.Position.X.Scale,xCounter + xOffset, 0, totalPixelsY - pixelsRemainingY + yOffset)
+ xCounter = xCounter + child.AbsoluteSize.X
+ child.Visible = ((pixelsRemainingY - child.AbsoluteSize.Y) >= 0)
+ if child.Visible then
+ howManyDisplayed = howManyDisplayed + 1
+ end
+ lastChildSize = child.AbsoluteSize
+ end
+ end
+ end
+
+ scrollUpButton.Active = (scrollPosition > 1)
+ if lastChildSize == 0 then
+ scrollDownButton.Active = false
+ else
+ scrollDownButton.Active = ((pixelsRemainingY - lastChildSize.Y) < 0)
+ end
+ scrollDrag.Active = #guiObjects > howManyDisplayed
+ scrollDrag.Visible = scrollDrag.Active
+ end
+
+
+
+ local layoutSimpleScrollBar = function()
+ local guiObjects = {}
+ howManyDisplayed = 0
+
+ if orderList then
+ for i, child in ipairs(orderList) do
+ if child.Parent == frame then
+ table.insert(guiObjects, child)
+ end
+ end
+ else
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ table.insert(guiObjects, child)
+ end
+ end
+ end
+ end
+ if #guiObjects == 0 then
+ scrollUpButton.Active = false
+ scrollDownButton.Active = false
+ scrollDrag.Active = false
+ scrollPosition = 1
+ return
+ end
+
+ if scrollPosition > #guiObjects then
+ scrollPosition = #guiObjects
+ end
+
+ local totalPixels = frame.AbsoluteSize.Y
+ local pixelsRemaining = frame.AbsoluteSize.Y
+
+ local pixelsBelowScrollbar = 0
+ local pos = #guiObjects
+ while pixelsBelowScrollbar < totalPixels and pos >= 1 do
+ if pos >= scrollPosition then
+ pixelsBelowScrollbar = pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y
+ else
+ if pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y <= totalPixels then
+ --It fits, so back up our scroll position
+ pixelsBelowScrollbar = pixelsBelowScrollbar + guiObjects[pos].AbsoluteSize.Y
+ if scrollPosition <= 1 then
+ scrollPosition = 1
+ break
+ else
+ --local ("Backing up ScrollPosition from -- " ..scrollPosition)
+ scrollPosition = scrollPosition - 1
+ end
+ else
+ break
+ end
+ end
+ pos = pos - 1
+ end
+
+ pos = scrollPosition
+ for i, child in ipairs(guiObjects) do
+ if i < scrollPosition then
+ --print("Hiding " .. child.Name)
+ child.Visible = false
+ else
+ if pixelsRemaining < 0 then
+ --print("Out of Space " .. child.Name)
+ child.Visible = false
+ else
+ --print("Laying out " .. child.Name)
+ --GuiObject
+ child.Position = UDim2.new(child.Position.X.Scale, child.Position.X.Offset, 0, totalPixels - pixelsRemaining)
+ pixelsRemaining = pixelsRemaining - child.AbsoluteSize.Y
+ if (pixelsRemaining >= 0) then
+ child.Visible = true
+ howManyDisplayed = howManyDisplayed + 1
+ else
+ child.Visible = false
+ end
+ end
+ end
+ end
+ scrollUpButton.Active = (scrollPosition > 1)
+ scrollDownButton.Active = (pixelsRemaining < 0)
+ scrollDrag.Active = #guiObjects > howManyDisplayed
+ scrollDrag.Visible = scrollDrag.Active
+ end
+
+
+ local moveDragger = function()
+ local guiObjects = 0
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ guiObjects = guiObjects + 1
+ end
+ end
+ end
+
+ if not scrollDrag.Parent then return end
+
+ local dragSizeY = scrollDrag.Parent.AbsoluteSize.y * (1/(guiObjects - howManyDisplayed + 1))
+ if dragSizeY < 16 then dragSizeY = 16 end
+ scrollDrag.Size = UDim2.new(scrollDrag.Size.X.Scale,scrollDrag.Size.X.Offset,scrollDrag.Size.Y.Scale,dragSizeY)
+
+ local relativeYPos = (scrollPosition - 1)/(guiObjects - (howManyDisplayed))
+ if relativeYPos > 1 then relativeYPos = 1
+ elseif relativeYPos < 0 then relativeYPos = 0 end
+ local absYPos = 0
+
+ if relativeYPos ~= 0 then
+ absYPos = (relativeYPos * scrollbar.AbsoluteSize.y) - (relativeYPos * scrollDrag.AbsoluteSize.y)
+ end
+
+ scrollDrag.Position = UDim2.new(scrollDrag.Position.X.Scale,scrollDrag.Position.X.Offset,scrollDrag.Position.Y.Scale,absYPos)
+ end
+
+ local reentrancyGuard = false
+ local recalculate = function()
+ if reentrancyGuard then
+ return
+ end
+ reentrancyGuard = true
+ wait()
+ local success, err = nil
+ if style == "grid" then
+ success, err = pcall(function() layoutGridScrollBar() end)
+ elseif style == "simple" then
+ success, err = pcall(function() layoutSimpleScrollBar() end)
+ end
+ if not success then print(err) end
+ moveDragger()
+ reentrancyGuard = false
+ end
+
+ local doScrollUp = function()
+ scrollPosition = (scrollPosition) - rowSize
+ if scrollPosition < 1 then scrollPosition = 1 end
+ recalculate(nil)
+ end
+
+ local doScrollDown = function()
+ scrollPosition = (scrollPosition) + rowSize
+ recalculate(nil)
+ end
+
+ local scrollUp = function(mouseYPos)
+ if scrollUpButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local upCon
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ upCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollUp()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollUp()
+ if mouseYPos and mouseYPos > scrollDrag.AbsolutePosition.y then
+ break
+ end
+ if not scrollUpButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local scrollDown = function(mouseYPos)
+ if scrollDownButton.Active then
+ scrollStamp = tick()
+ local current = scrollStamp
+ local downCon
+ downCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ downCon:disconnect()
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ doScrollDown()
+ wait(0.2)
+ local t = tick()
+ local w = 0.1
+ while scrollStamp == current do
+ doScrollDown()
+ if mouseYPos and mouseYPos < (scrollDrag.AbsolutePosition.y + scrollDrag.AbsoluteSize.x) then
+ break
+ end
+ if not scrollDownButton.Active then break end
+ if tick()-t > 5 then
+ w = 0
+ elseif tick()-t > 2 then
+ w = 0.06
+ end
+ wait(w)
+ end
+ end
+ end
+
+ local y = 0
+ scrollDrag.MouseButton1Down:connect(function(x,y)
+ if scrollDrag.Active then
+ scrollStamp = tick()
+ local mouseOffset = y - scrollDrag.AbsolutePosition.y
+ local dragCon
+ local upCon
+ dragCon = mouseDrag.MouseMoved:connect(function(x,y)
+ local barAbsPos = scrollbar.AbsolutePosition.y
+ local barAbsSize = scrollbar.AbsoluteSize.y
+
+ local dragAbsSize = scrollDrag.AbsoluteSize.y
+ local barAbsOne = barAbsPos + barAbsSize - dragAbsSize
+ y = y - mouseOffset
+ y = y < barAbsPos and barAbsPos or y > barAbsOne and barAbsOne or y
+ y = y - barAbsPos
+
+ local guiObjects = 0
+ local children = frame:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ if child:IsA("GuiObject") then
+ guiObjects = guiObjects + 1
+ end
+ end
+ end
+
+ local doublePercent = y/(barAbsSize-dragAbsSize)
+ local rowDiff = rowSize
+ local totalScrollCount = guiObjects - (howManyDisplayed - 1)
+ local newScrollPosition = math.floor((doublePercent * totalScrollCount) + 0.5) + rowDiff
+ if newScrollPosition < scrollPosition then
+ rowDiff = -rowDiff
+ end
+
+ if newScrollPosition < 1 then
+ newScrollPosition = 1
+ end
+
+ scrollPosition = newScrollPosition
+ recalculate(nil)
+ end)
+ upCon = mouseDrag.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ mouseDrag.Parent = nil
+ dragCon:disconnect(); dragCon = nil
+ upCon:disconnect(); drag = nil
+ end)
+ mouseDrag.Parent = getScreenGuiAncestor(scrollbar)
+ end
+ end)
+
+ local scrollMouseCount = 0
+
+ scrollUpButton.MouseButton1Down:connect(
+ function()
+ scrollUp()
+ end)
+ scrollUpButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+
+
+ scrollDownButton.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollDownButton.MouseButton1Down:connect(
+ function()
+ scrollDown()
+ end)
+
+ scrollbar.MouseButton1Up:connect(function()
+ scrollStamp = tick()
+ end)
+ scrollbar.MouseButton1Down:connect(
+ function(x,y)
+ if y > (scrollDrag.AbsoluteSize.y + scrollDrag.AbsolutePosition.y) then
+ scrollDown(y)
+ elseif y < (scrollDrag.AbsolutePosition.y) then
+ scrollUp(y)
+ end
+ end)
+
+
+ frame.ChildAdded:connect(function()
+ recalculate(nil)
+ end)
+
+ frame.ChildRemoved:connect(function()
+ recalculate(nil)
+ end)
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ --Wait a heartbeat for it to sync in
+ recalculate(nil)
+ end
+ end)
+ frame.AncestryChanged:connect(function() recalculate(nil) end)
+
+ return frame, scrollUpButton, scrollDownButton, recalculate, scrollbar
+end
+local function binaryGrow(min, max, fits)
+ if min > max then
+ return min
+ end
+ local biggestLegal = min
+
+ while min <= max do
+ local mid = min + math.floor((max - min) / 2)
+ if fits(mid) and (biggestLegal == nil or biggestLegal < mid) then
+ biggestLegal = mid
+
+ --Try growing
+ min = mid + 1
+ else
+ --Doesn't fit, shrink
+ max = mid - 1
+ end
+ end
+ return biggestLegal
+end
+
+
+local function binaryShrink(min, max, fits)
+ if min > max then
+ return min
+ end
+ local smallestLegal = max
+
+ while min <= max do
+ local mid = min + math.floor((max - min) / 2)
+ if fits(mid) and (smallestLegal == nil or smallestLegal > mid) then
+ smallestLegal = mid
+
+ --It fits, shrink
+ max = mid - 1
+ else
+ --Doesn't fit, grow
+ min = mid + 1
+ end
+ end
+ return smallestLegal
+end
+
+
+local function getGuiOwner(instance)
+ while instance ~= nil do
+ if instance:IsA("ScreenGui") or instance:IsA("BillboardGui") then
+ return instance
+ end
+ instance = instance.Parent
+ end
+ return nil
+end
+
+t.AutoTruncateTextObject = function(textLabel)
+ local text = textLabel.Text
+
+ local fullLabel = textLabel:Clone()
+ fullLabel.Name = "Full" .. textLabel.Name
+ fullLabel.BorderSizePixel = 0
+ fullLabel.BackgroundTransparency = 0
+ fullLabel.Text = text
+ fullLabel.TextXAlignment = Enum.TextXAlignment.Center
+ fullLabel.Position = UDim2.new(0,-3,0,0)
+ fullLabel.Size = UDim2.new(0,100,1,0)
+ fullLabel.Visible = false
+ fullLabel.Parent = textLabel
+
+ local shortText = nil
+ local mouseEnterConnection = nil
+ local mouseLeaveConnection= nil
+
+ local checkForResize = function()
+ if getGuiOwner(textLabel) == nil then
+ return
+ end
+ textLabel.Text = text
+ if textLabel.TextFits then
+ --Tear down the rollover if it is active
+ if mouseEnterConnection then
+ mouseEnterConnection:disconnect()
+ mouseEnterConnection = nil
+ end
+ if mouseLeaveConnection then
+ mouseLeaveConnection:disconnect()
+ mouseLeaveConnection = nil
+ end
+ else
+ local len = string.len(text)
+ textLabel.Text = text .. "~"
+
+ --Shrink the text
+ local textSize = binaryGrow(0, len,
+ function(pos)
+ if pos == 0 then
+ textLabel.Text = "~"
+ else
+ textLabel.Text = string.sub(text, 1, pos) .. "~"
+ end
+ return textLabel.TextFits
+ end)
+ shortText = string.sub(text, 1, textSize) .. "~"
+ textLabel.Text = shortText
+
+ --Make sure the fullLabel fits
+ if not fullLabel.TextFits then
+ --Already too small, grow it really bit to start
+ fullLabel.Size = UDim2.new(0, 10000, 1, 0)
+ end
+
+ --Okay, now try to binary shrink it back down
+ local fullLabelSize = binaryShrink(textLabel.AbsoluteSize.X,fullLabel.AbsoluteSize.X,
+ function(size)
+ fullLabel.Size = UDim2.new(0, size, 1, 0)
+ return fullLabel.TextFits
+ end)
+ fullLabel.Size = UDim2.new(0,fullLabelSize+6,1,0)
+
+ --Now setup the rollover effects, if they are currently off
+ if mouseEnterConnection == nil then
+ mouseEnterConnection = textLabel.MouseEnter:connect(
+ function()
+ fullLabel.ZIndex = textLabel.ZIndex + 1
+ fullLabel.Visible = true
+ --textLabel.Text = ""
+ end)
+ end
+ if mouseLeaveConnection == nil then
+ mouseLeaveConnection = textLabel.MouseLeave:connect(
+ function()
+ fullLabel.Visible = false
+ --textLabel.Text = shortText
+ end)
+ end
+ end
+ end
+ textLabel.AncestryChanged:connect(checkForResize)
+ textLabel.Changed:connect(
+ function(prop)
+ if prop == "AbsoluteSize" then
+ checkForResize()
+ end
+ end)
+
+ checkForResize()
+
+ local function changeText(newText)
+ text = newText
+ fullLabel.Text = text
+ checkForResize()
+ end
+
+ return textLabel, changeText
+end
+
+local function TransitionTutorialPages(fromPage, toPage, transitionFrame, currentPageValue)
+ if fromPage then
+ fromPage.Visible = false
+ if transitionFrame.Visible == false then
+ transitionFrame.Size = fromPage.Size
+ transitionFrame.Position = fromPage.Position
+ end
+ else
+ if transitionFrame.Visible == false then
+ transitionFrame.Size = UDim2.new(0.0,50,0.0,50)
+ transitionFrame.Position = UDim2.new(0.5,-25,0.5,-25)
+ end
+ end
+ transitionFrame.Visible = true
+ currentPageValue.Value = nil
+
+ local newsize, newPosition
+ if toPage then
+ --Make it visible so it resizes
+ toPage.Visible = true
+
+ newSize = toPage.Size
+ newPosition = toPage.Position
+
+ toPage.Visible = false
+ else
+ newSize = UDim2.new(0.0,50,0.0,50)
+ newPosition = UDim2.new(0.5,-25,0.5,-25)
+ end
+ transitionFrame:TweenSizeAndPosition(newSize, newPosition, Enum.EasingDirection.InOut, Enum.EasingStyle.Quad, 0.3, true,
+ function(state)
+ if state == Enum.TweenStatus.Completed then
+ transitionFrame.Visible = false
+ if toPage then
+ toPage.Visible = true
+ currentPageValue.Value = toPage
+ end
+ end
+ end)
+end
+
+t.CreateTutorial = function(name, tutorialKey, createButtons)
+ local frame = Instance.new("Frame")
+ frame.Name = "Tutorial-" .. name
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ frame.Position = UDim2.new(0.2, 0, 0.2, 0)
+
+ local transitionFrame = Instance.new("Frame")
+ transitionFrame.Name = "TransitionFrame"
+ transitionFrame.Style = Enum.FrameStyle.RobloxRound
+ transitionFrame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ transitionFrame.Position = UDim2.new(0.2, 0, 0.2, 0)
+ transitionFrame.Visible = false
+ transitionFrame.Parent = frame
+
+ local currentPageValue = Instance.new("ObjectValue")
+ currentPageValue.Name = "CurrentTutorialPage"
+ currentPageValue.Value = nil
+ currentPageValue.Parent = frame
+
+ local boolValue = Instance.new("BoolValue")
+ boolValue.Name = "Buttons"
+ boolValue.Value = createButtons
+ boolValue.Parent = frame
+
+ local pages = Instance.new("Frame")
+ pages.Name = "Pages"
+ pages.BackgroundTransparency = 1
+ pages.Size = UDim2.new(1,0,1,0)
+ pages.Parent = frame
+
+ local function getVisiblePageAndHideOthers()
+ local visiblePage = nil
+ local children = pages:GetChildren()
+ if children then
+ for i,child in ipairs(children) do
+ if child.Visible then
+ if visiblePage then
+ child.Visible = false
+ else
+ visiblePage = child
+ end
+ end
+ end
+ end
+ return visiblePage
+ end
+
+ local showTutorial = function(alwaysShow)
+ if alwaysShow or UserSettings().GameSettings:GetTutorialState(tutorialKey) == false then
+ print("Showing tutorial-",tutorialKey)
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+
+ local firstPage = pages:FindFirstChild("TutorialPage1")
+ if firstPage then
+ TransitionTutorialPages(currentTutorialPage, firstPage, transitionFrame, currentPageValue)
+ else
+ error("Could not find TutorialPage1")
+ end
+ end
+ end
+
+ local dismissTutorial = function()
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+
+ if currentTutorialPage then
+ TransitionTutorialPages(currentTutorialPage, nil, transitionFrame, currentPageValue)
+ end
+
+ UserSettings().GameSettings:SetTutorialState(tutorialKey, true)
+ end
+
+ local gotoPage = function(pageNum)
+ local page = pages:FindFirstChild("TutorialPage" .. pageNum)
+ local currentTutorialPage = getVisiblePageAndHideOthers()
+ TransitionTutorialPages(currentTutorialPage, page, transitionFrame, currentPageValue)
+ end
+
+ return frame, showTutorial, dismissTutorial, gotoPage
+end
+
+local function CreateBasicTutorialPage(name, handleResize, skipTutorial, giveDoneButton)
+ local frame = Instance.new("Frame")
+ frame.Name = "TutorialPage"
+ frame.Style = Enum.FrameStyle.RobloxRound
+ frame.Size = UDim2.new(0.6, 0, 0.6, 0)
+ frame.Position = UDim2.new(0.2, 0, 0.2, 0)
+ frame.Visible = false
+
+ local frameHeader = Instance.new("TextLabel")
+ frameHeader.Name = "Header"
+ frameHeader.Text = name
+ frameHeader.BackgroundTransparency = 1
+ frameHeader.FontSize = Enum.FontSize.Size24
+ frameHeader.Font = Enum.Font.ArialBold
+ frameHeader.TextColor3 = Color3.new(1,1,1)
+ frameHeader.TextXAlignment = Enum.TextXAlignment.Center
+ frameHeader.TextWrap = true
+ frameHeader.Size = UDim2.new(1,-55, 0, 22)
+ frameHeader.Position = UDim2.new(0,0,0,0)
+ frameHeader.Parent = frame
+
+ local skipButton = Instance.new("ImageButton")
+ skipButton.Name = "SkipButton"
+ skipButton.AutoButtonColor = false
+ skipButton.BackgroundTransparency = 1
+ skipButton.Image = "rbxasset://textures/ui/closeButton.png"
+ skipButton.MouseButton1Click:connect(function()
+ skipTutorial()
+ end)
+ skipButton.MouseEnter:connect(function()
+ skipButton.Image = "rbxasset://textures/ui/closeButton_dn.png"
+ end)
+ skipButton.MouseLeave:connect(function()
+ skipButton.Image = "rbxasset://textures/ui/closeButton.png"
+ end)
+ skipButton.Size = UDim2.new(0, 25, 0, 25)
+ skipButton.Position = UDim2.new(1, -25, 0, 0)
+ skipButton.Parent = frame
+
+
+ if giveDoneButton then
+ local doneButton = Instance.new("TextButton")
+ doneButton.Name = "DoneButton"
+ doneButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ doneButton.Text = "Done"
+ doneButton.TextColor3 = Color3.new(1,1,1)
+ doneButton.Font = Enum.Font.ArialBold
+ doneButton.FontSize = Enum.FontSize.Size18
+ doneButton.Size = UDim2.new(0,100,0,50)
+ doneButton.Position = UDim2.new(0.5,-50,1,-50)
+
+ if skipTutorial then
+ doneButton.MouseButton1Click:connect(function() skipTutorial() end)
+ end
+
+ doneButton.Parent = frame
+ end
+
+ local innerFrame = Instance.new("Frame")
+ innerFrame.Name = "ContentFrame"
+ innerFrame.BackgroundTransparency = 1
+ innerFrame.Position = UDim2.new(0,0,0,25)
+ innerFrame.Parent = frame
+
+ local nextButton = Instance.new("TextButton")
+ nextButton.Name = "NextButton"
+ nextButton.Text = "Next"
+ nextButton.TextColor3 = Color3.new(1,1,1)
+ nextButton.Font = Enum.Font.Arial
+ nextButton.FontSize = Enum.FontSize.Size18
+ nextButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ nextButton.Size = UDim2.new(0,80, 0, 32)
+ nextButton.Position = UDim2.new(0.5, 5, 1, -32)
+ nextButton.Active = false
+ nextButton.Visible = false
+ nextButton.Parent = frame
+
+ local prevButton = Instance.new("TextButton")
+ prevButton.Name = "PrevButton"
+ prevButton.Text = "Previous"
+ prevButton.TextColor3 = Color3.new(1,1,1)
+ prevButton.Font = Enum.Font.Arial
+ prevButton.FontSize = Enum.FontSize.Size18
+ prevButton.Style = Enum.ButtonStyle.RobloxButton
+ prevButton.Size = UDim2.new(0,80, 0, 32)
+ prevButton.Position = UDim2.new(0.5, -85, 1, -32)
+ prevButton.Active = false
+ prevButton.Visible = false
+ prevButton.Parent = frame
+
+ if giveDoneButton then
+ innerFrame.Size = UDim2.new(1,0,1,-75)
+ else
+ innerFrame.Size = UDim2.new(1,0,1,-22)
+ end
+
+ local parentConnection = nil
+
+ local function basicHandleResize()
+ if frame.Visible and frame.Parent then
+ local maxSize = math.min(frame.Parent.AbsoluteSize.X, frame.Parent.AbsoluteSize.Y)
+ handleResize(200,maxSize)
+ end
+ end
+
+ frame.Changed:connect(
+ function(prop)
+ if prop == "Parent" then
+ if parentConnection ~= nil then
+ parentConnection:disconnect()
+ parentConnection = nil
+ end
+ if frame.Parent and frame.Parent:IsA("GuiObject") then
+ parentConnection = frame.Parent.Changed:connect(
+ function(parentProp)
+ if parentProp == "AbsoluteSize" then
+ wait()
+ basicHandleResize()
+ end
+ end)
+ basicHandleResize()
+ end
+ end
+
+ if prop == "Visible" then
+ basicHandleResize()
+ end
+ end)
+
+ return frame, innerFrame
+end
+
+t.CreateTextTutorialPage = function(name, text, skipTutorialFunc)
+ local frame = nil
+ local contentFrame = nil
+
+ local textLabel = Instance.new("TextLabel")
+ textLabel.BackgroundTransparency = 1
+ textLabel.TextColor3 = Color3.new(1,1,1)
+ textLabel.Text = text
+ textLabel.TextWrap = true
+ textLabel.TextXAlignment = Enum.TextXAlignment.Left
+ textLabel.TextYAlignment = Enum.TextYAlignment.Center
+ textLabel.Font = Enum.Font.Arial
+ textLabel.FontSize = Enum.FontSize.Size14
+ textLabel.Size = UDim2.new(1,0,1,0)
+
+ local function handleResize(minSize, maxSize)
+ size = binaryShrink(minSize, maxSize,
+ function(size)
+ frame.Size = UDim2.new(0, size, 0, size)
+ return textLabel.TextFits
+ end)
+ frame.Size = UDim2.new(0, size, 0, size)
+ frame.Position = UDim2.new(0.5, -size/2, 0.5, -size/2)
+ end
+
+ frame, contentFrame = CreateBasicTutorialPage(name, handleResize, skipTutorialFunc)
+ textLabel.Parent = contentFrame
+
+ return frame
+end
+
+t.CreateImageTutorialPage = function(name, imageAsset, x, y, skipTutorialFunc, giveDoneButton)
+ local frame = nil
+ local contentFrame = nil
+
+ local imageLabel = Instance.new("ImageLabel")
+ imageLabel.BackgroundTransparency = 1
+ imageLabel.Image = imageAsset
+ imageLabel.Size = UDim2.new(0,x,0,y)
+ imageLabel.Position = UDim2.new(0.5,-x/2,0.5,-y/2)
+
+ local function handleResize(minSize, maxSize)
+ size = binaryShrink(minSize, maxSize,
+ function(size)
+ return size >= x and size >= y
+ end)
+ if size >= x and size >= y then
+ imageLabel.Size = UDim2.new(0,x, 0,y)
+ imageLabel.Position = UDim2.new(0.5,-x/2, 0.5, -y/2)
+ else
+ if x > y then
+ --X is limiter, so
+ imageLabel.Size = UDim2.new(1,0,y/x,0)
+ imageLabel.Position = UDim2.new(0,0, 0.5 - (y/x)/2, 0)
+ else
+ --Y is limiter
+ imageLabel.Size = UDim2.new(x/y,0,1, 0)
+ imageLabel.Position = UDim2.new(0.5-(x/y)/2, 0, 0, 0)
+ end
+ end
+ size = size + 50
+ frame.Size = UDim2.new(0, size, 0, size)
+ frame.Position = UDim2.new(0.5, -size/2, 0.5, -size/2)
+ end
+
+ frame, contentFrame = CreateBasicTutorialPage(name, handleResize, skipTutorialFunc, giveDoneButton)
+ imageLabel.Parent = contentFrame
+
+ return frame
+end
+
+t.AddTutorialPage = function(tutorial, tutorialPage)
+ local transitionFrame = tutorial.TransitionFrame
+ local currentPageValue = tutorial.CurrentTutorialPage
+
+ if not tutorial.Buttons.Value then
+ tutorialPage.NextButton.Parent = nil
+ tutorialPage.PrevButton.Parent = nil
+ end
+
+ local children = tutorial.Pages:GetChildren()
+ if children and #children > 0 then
+ tutorialPage.Name = "TutorialPage" .. (#children+1)
+ local previousPage = children[#children]
+ if not previousPage:IsA("GuiObject") then
+ error("All elements under Pages must be GuiObjects")
+ end
+
+ if tutorial.Buttons.Value then
+ if previousPage.NextButton.Active then
+ error("NextButton already Active on previousPage, please only add pages with RbxGui.AddTutorialPage function")
+ end
+ previousPage.NextButton.MouseButton1Click:connect(
+ function()
+ TransitionTutorialPages(previousPage, tutorialPage, transitionFrame, currentPageValue)
+ end)
+ previousPage.NextButton.Active = true
+ previousPage.NextButton.Visible = true
+
+ if tutorialPage.PrevButton.Active then
+ error("PrevButton already Active on tutorialPage, please only add pages with RbxGui.AddTutorialPage function")
+ end
+ tutorialPage.PrevButton.MouseButton1Click:connect(
+ function()
+ TransitionTutorialPages(tutorialPage, previousPage, transitionFrame, currentPageValue)
+ end)
+ tutorialPage.PrevButton.Active = true
+ tutorialPage.PrevButton.Visible = true
+ end
+
+ tutorialPage.Parent = tutorial.Pages
+ else
+ --First child
+ tutorialPage.Name = "TutorialPage1"
+ tutorialPage.Parent = tutorial.Pages
+ end
+end
+
+t.CreateSetPanel = function(userIdsForSets, objectSelected, dialogClosed, size, position, showAdminCategories, useAssetVersionId)
+
+ if not userIdsForSets then
+ error("CreateSetPanel: userIdsForSets (first arg) is nil, should be a table of number ids")
+ end
+ if type(userIdsForSets) ~= "table" and type(userIdsForSets) ~= "userdata" then
+ error("CreateSetPanel: userIdsForSets (first arg) is of type " ..type(userIdsForSets) .. ", should be of type table or userdata")
+ end
+ if not objectSelected then
+ error("CreateSetPanel: objectSelected (second arg) is nil, should be a callback function!")
+ end
+ if type(objectSelected) ~= "function" then
+ error("CreateSetPanel: objectSelected (second arg) is of type " .. type(objectSelected) .. ", should be of type function!")
+ end
+ if dialogClosed and type(dialogClosed) ~= "function" then
+ error("CreateSetPanel: dialogClosed (third arg) is of type " .. type(dialogClosed) .. ", should be of type function!")
+ end
+
+ if showAdminCategories == nil then -- by default, don't show beta sets
+ showAdminCategories = false
+ end
+
+ local arrayPosition = 1
+ local insertButtons = {}
+ local insertButtonCons = {}
+ local contents = nil
+ local setGui = nil
+
+ -- used for water selections
+ local waterForceDirection = "NegX"
+ local waterForce = "None"
+ local waterGui, waterTypeChangedEvent = nil
+
+ local Data = {}
+ Data.CurrentCategory = nil
+ Data.Category = {}
+ local SetCache = {}
+
+ local userCategoryButtons = nil
+
+ local buttonWidth = 64
+ local buttonHeight = buttonWidth
+
+ local SmallThumbnailUrl = nil
+ local LargeThumbnailUrl = nil
+ local BaseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+
+ if useAssetVersionId then
+ LargeThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=420&ht=420&assetversionid="
+ SmallThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=75&ht=75&assetversionid="
+ else
+ LargeThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=420&ht=420&aid="
+ SmallThumbnailUrl = BaseUrl .. "Game/Tools/ThumbnailAsset.ashx?fmt=png&wd=75&ht=75&aid="
+ end
+
+ local function drillDownSetZIndex(parent, index)
+ local children = parent:GetChildren()
+ for i = 1, #children do
+ if children[i]:IsA("GuiObject") then
+ children[i].ZIndex = index
+ end
+ drillDownSetZIndex(children[i], index)
+ end
+ end
+
+ -- for terrain stamping
+ local currTerrainDropDownFrame = nil
+ local terrainShapes = {"Block","Vertical Ramp","Corner Wedge","Inverse Corner Wedge","Horizontal Ramp","Auto-Wedge"}
+ local terrainShapeMap = {}
+ for i = 1, #terrainShapes do
+ terrainShapeMap[terrainShapes[i]] = i - 1
+ end
+ terrainShapeMap[terrainShapes[#terrainShapes]] = 6
+
+ local function createWaterGui()
+ local waterForceDirections = {"NegX","X","NegY","Y","NegZ","Z"}
+ local waterForces = {"None", "Small", "Medium", "Strong", "Max"}
+
+ local waterFrame = Instance.new("Frame")
+ waterFrame.Name = "WaterFrame"
+ waterFrame.Style = Enum.FrameStyle.RobloxSquare
+ waterFrame.Size = UDim2.new(0,150,0,110)
+ waterFrame.Visible = false
+
+ local waterForceLabel = Instance.new("TextLabel")
+ waterForceLabel.Name = "WaterForceLabel"
+ waterForceLabel.BackgroundTransparency = 1
+ waterForceLabel.Size = UDim2.new(1,0,0,12)
+ waterForceLabel.Font = Enum.Font.ArialBold
+ waterForceLabel.FontSize = Enum.FontSize.Size12
+ waterForceLabel.TextColor3 = Color3.new(1,1,1)
+ waterForceLabel.TextXAlignment = Enum.TextXAlignment.Left
+ waterForceLabel.Text = "Water Force"
+ waterForceLabel.Parent = waterFrame
+
+ local waterForceDirLabel = waterForceLabel:Clone()
+ waterForceDirLabel.Name = "WaterForceDirectionLabel"
+ waterForceDirLabel.Text = "Water Force Direction"
+ waterForceDirLabel.Position = UDim2.new(0,0,0,50)
+ waterForceDirLabel.Parent = waterFrame
+
+ local waterTypeChangedEvent = Instance.new("BindableEvent",waterFrame)
+ waterTypeChangedEvent.Name = "WaterTypeChangedEvent"
+
+ local waterForceDirectionSelectedFunc = function(newForceDirection)
+ waterForceDirection = newForceDirection
+ waterTypeChangedEvent:Fire({waterForce, waterForceDirection})
+ end
+ local waterForceSelectedFunc = function(newForce)
+ waterForce = newForce
+ waterTypeChangedEvent:Fire({waterForce, waterForceDirection})
+ end
+
+ local waterForceDirectionDropDown, forceWaterDirectionSelection = t.CreateDropDownMenu(waterForceDirections, waterForceDirectionSelectedFunc)
+ waterForceDirectionDropDown.Size = UDim2.new(1,0,0,25)
+ waterForceDirectionDropDown.Position = UDim2.new(0,0,1,3)
+ forceWaterDirectionSelection("NegX")
+ waterForceDirectionDropDown.Parent = waterForceDirLabel
+
+ local waterForceDropDown, forceWaterForceSelection = t.CreateDropDownMenu(waterForces, waterForceSelectedFunc)
+ forceWaterForceSelection("None")
+ waterForceDropDown.Size = UDim2.new(1,0,0,25)
+ waterForceDropDown.Position = UDim2.new(0,0,1,3)
+ waterForceDropDown.Parent = waterForceLabel
+
+ return waterFrame, waterTypeChangedEvent
+ end
+
+ -- Helper Function that contructs gui elements
+ local function createSetGui()
+
+ local setGui = Instance.new("ScreenGui")
+ setGui.Name = "SetGui"
+
+ local setPanel = Instance.new("Frame")
+ setPanel.Name = "SetPanel"
+ setPanel.Active = true
+ setPanel.BackgroundTransparency = 1
+ if position then
+ setPanel.Position = position
+ else
+ setPanel.Position = UDim2.new(0.2, 29, 0.1, 24)
+ end
+ if size then
+ setPanel.Size = size
+ else
+ setPanel.Size = UDim2.new(0.6, -58, 0.64, 0)
+ end
+ setPanel.Style = Enum.FrameStyle.RobloxRound
+ setPanel.ZIndex = 6
+ setPanel.Parent = setGui
+
+ -- Children of SetPanel
+ local itemPreview = Instance.new("Frame")
+ itemPreview.Name = "ItemPreview"
+ itemPreview.BackgroundTransparency = 1
+ itemPreview.Position = UDim2.new(0.8,5,0.085,0)
+ itemPreview.Size = UDim2.new(0.21,0,0.9,0)
+ itemPreview.ZIndex = 6
+ itemPreview.Parent = setPanel
+
+ -- Children of ItemPreview
+ local textPanel = Instance.new("Frame")
+ textPanel.Name = "TextPanel"
+ textPanel.BackgroundTransparency = 1
+ textPanel.Position = UDim2.new(0,0,0.45,0)
+ textPanel.Size = UDim2.new(1,0,0.55,0)
+ textPanel.ZIndex = 6
+ textPanel.Parent = itemPreview
+
+ -- Children of TextPanel
+ local rolloverText = Instance.new("TextLabel")
+ rolloverText.Name = "RolloverText"
+ rolloverText.BackgroundTransparency = 1
+ rolloverText.Size = UDim2.new(1,0,0,48)
+ rolloverText.ZIndex = 6
+ rolloverText.Font = Enum.Font.ArialBold
+ rolloverText.FontSize = Enum.FontSize.Size24
+ rolloverText.Text = ""
+ rolloverText.TextColor3 = Color3.new(1,1,1)
+ rolloverText.TextWrap = true
+ rolloverText.TextXAlignment = Enum.TextXAlignment.Left
+ rolloverText.TextYAlignment = Enum.TextYAlignment.Top
+ rolloverText.Parent = textPanel
+
+ local largePreview = Instance.new("ImageLabel")
+ largePreview.Name = "LargePreview"
+ largePreview.BackgroundTransparency = 1
+ largePreview.Image = ""
+ largePreview.Size = UDim2.new(1,0,0,170)
+ largePreview.ZIndex = 6
+ largePreview.Parent = itemPreview
+
+ local sets = Instance.new("Frame")
+ sets.Name = "Sets"
+ sets.BackgroundTransparency = 1
+ sets.Position = UDim2.new(0,0,0,5)
+ sets.Size = UDim2.new(0.23,0,1,-5)
+ sets.ZIndex = 6
+ sets.Parent = setPanel
+
+ -- Children of Sets
+ local line = Instance.new("Frame")
+ line.Name = "Line"
+ line.BackgroundColor3 = Color3.new(1,1,1)
+ line.BackgroundTransparency = 0.7
+ line.BorderSizePixel = 0
+ line.Position = UDim2.new(1,-3,0.06,0)
+ line.Size = UDim2.new(0,3,0.9,0)
+ line.ZIndex = 6
+ line.Parent = sets
+
+ local setsLists, controlFrame = t.CreateTrueScrollingFrame()
+ setsLists.Size = UDim2.new(1,-6,0.94,0)
+ setsLists.Position = UDim2.new(0,0,0.06,0)
+ setsLists.BackgroundTransparency = 1
+ setsLists.Name = "SetsLists"
+ setsLists.ZIndex = 6
+ setsLists.Parent = sets
+ drillDownSetZIndex(controlFrame, 7)
+
+ local setsHeader = Instance.new("TextLabel")
+ setsHeader.Name = "SetsHeader"
+ setsHeader.BackgroundTransparency = 1
+ setsHeader.Size = UDim2.new(0,47,0,24)
+ setsHeader.ZIndex = 6
+ setsHeader.Font = Enum.Font.ArialBold
+ setsHeader.FontSize = Enum.FontSize.Size24
+ setsHeader.Text = "Sets"
+ setsHeader.TextColor3 = Color3.new(1,1,1)
+ setsHeader.TextXAlignment = Enum.TextXAlignment.Left
+ setsHeader.TextYAlignment = Enum.TextYAlignment.Top
+ setsHeader.Parent = sets
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelButton"
+ cancelButton.Position = UDim2.new(1,-32,0,-2)
+ cancelButton.Size = UDim2.new(0,34,0,34)
+ cancelButton.Style = Enum.ButtonStyle.RobloxButtonDefault
+ cancelButton.ZIndex = 6
+ cancelButton.Text = ""
+ cancelButton.Modal = true
+ cancelButton.Parent = setPanel
+
+ -- Children of Cancel Button
+ local cancelImage = Instance.new("ImageLabel")
+ cancelImage.Name = "CancelImage"
+ cancelImage.BackgroundTransparency = 1
+ cancelImage.Image = "http://www.roblox.com/asset/?id=54135717"
+ cancelImage.Position = UDim2.new(0,-2,0,-2)
+ cancelImage.Size = UDim2.new(0,16,0,16)
+ cancelImage.ZIndex = 6
+ cancelImage.Parent = cancelButton
+
+ return setGui
+ end
+
+ local function createSetButton(text)
+ local setButton = Instance.new("TextButton")
+
+ if text then setButton.Text = text
+ else setButton.Text = "" end
+
+ setButton.AutoButtonColor = false
+ setButton.BackgroundTransparency = 1
+ setButton.BackgroundColor3 = Color3.new(1,1,1)
+ setButton.BorderSizePixel = 0
+ setButton.Size = UDim2.new(1,-5,0,18)
+ setButton.ZIndex = 6
+ setButton.Visible = false
+ setButton.Font = Enum.Font.Arial
+ setButton.FontSize = Enum.FontSize.Size18
+ setButton.TextColor3 = Color3.new(1,1,1)
+ setButton.TextXAlignment = Enum.TextXAlignment.Left
+
+ return setButton
+ end
+
+ local function buildSetButton(name, setId, setImageId, i, count)
+ local button = createSetButton(name)
+ button.Text = name
+ button.Name = "SetButton"
+ button.Visible = true
+
+ local setValue = Instance.new("IntValue")
+ setValue.Name = "SetId"
+ setValue.Value = setId
+ setValue.Parent = button
+
+ local setName = Instance.new("StringValue")
+ setName.Name = "SetName"
+ setName.Value = name
+ setName.Parent = button
+
+ return button
+ end
+
+ local function processCategory(sets)
+ local setButtons = {}
+ local numSkipped = 0
+ for i = 1, #sets do
+ if not showAdminCategories and sets[i].Name == "Beta" then
+ numSkipped = numSkipped + 1
+ else
+ setButtons[i - numSkipped] = buildSetButton(sets[i].Name, sets[i].CategoryId, sets[i].ImageAssetId, i - numSkipped, #sets)
+ end
+ end
+ return setButtons
+ end
+
+ local function handleResize()
+ wait() -- neccessary to insure heartbeat happened
+
+ local itemPreview = setGui.SetPanel.ItemPreview
+
+ itemPreview.LargePreview.Size = UDim2.new(1,0,0,itemPreview.AbsoluteSize.X)
+ itemPreview.LargePreview.Position = UDim2.new(0.5,-itemPreview.LargePreview.AbsoluteSize.X/2,0,0)
+ itemPreview.TextPanel.Position = UDim2.new(0,0,0,itemPreview.LargePreview.AbsoluteSize.Y)
+ itemPreview.TextPanel.Size = UDim2.new(1,0,0,itemPreview.AbsoluteSize.Y - itemPreview.LargePreview.AbsoluteSize.Y)
+ end
+
+ local function makeInsertAssetButton()
+ local insertAssetButtonExample = Instance.new("Frame")
+ insertAssetButtonExample.Name = "InsertAssetButtonExample"
+ insertAssetButtonExample.Position = UDim2.new(0,128,0,64)
+ insertAssetButtonExample.Size = UDim2.new(0,64,0,64)
+ insertAssetButtonExample.BackgroundTransparency = 1
+ insertAssetButtonExample.ZIndex = 6
+ insertAssetButtonExample.Visible = false
+
+ local assetId = Instance.new("IntValue")
+ assetId.Name = "AssetId"
+ assetId.Value = 0
+ assetId.Parent = insertAssetButtonExample
+
+ local assetName = Instance.new("StringValue")
+ assetName.Name = "AssetName"
+ assetName.Value = ""
+ assetName.Parent = insertAssetButtonExample
+
+ local button = Instance.new("TextButton")
+ button.Name = "Button"
+ button.Text = ""
+ button.Style = Enum.ButtonStyle.RobloxButton
+ button.Position = UDim2.new(0.025,0,0.025,0)
+ button.Size = UDim2.new(0.95,0,0.95,0)
+ button.ZIndex = 6
+ button.Parent = insertAssetButtonExample
+
+ local buttonImage = Instance.new("ImageLabel")
+ buttonImage.Name = "ButtonImage"
+ buttonImage.Image = ""
+ buttonImage.Position = UDim2.new(0,-7,0,-7)
+ buttonImage.Size = UDim2.new(1,14,1,14)
+ buttonImage.BackgroundTransparency = 1
+ buttonImage.ZIndex = 7
+ buttonImage.Parent = button
+
+ local configIcon = buttonImage:clone()
+ configIcon.Name = "ConfigIcon"
+ configIcon.Visible = false
+ configIcon.Position = UDim2.new(1,-23,1,-24)
+ configIcon.Size = UDim2.new(0,16,0,16)
+ configIcon.Image = ""
+ configIcon.ZIndex = 6
+ configIcon.Parent = insertAssetButtonExample
+
+ return insertAssetButtonExample
+ end
+
+ local function showLargePreview(insertButton)
+ if insertButton:FindFirstChild("AssetId") then
+ delay(0,function()
+ game:GetService("ContentProvider"):Preload(LargeThumbnailUrl .. tostring(insertButton.AssetId.Value))
+ setGui.SetPanel.ItemPreview.LargePreview.Image = LargeThumbnailUrl .. tostring(insertButton.AssetId.Value)
+ end)
+ end
+ if insertButton:FindFirstChild("AssetName") then
+ setGui.SetPanel.ItemPreview.TextPanel.RolloverText.Text = insertButton.AssetName.Value
+ end
+ end
+
+ local function selectTerrainShape(shape)
+ if currTerrainDropDownFrame then
+ objectSelected(tostring(currTerrainDropDownFrame.AssetName.Value), tonumber(currTerrainDropDownFrame.AssetId.Value), shape)
+ end
+ end
+
+ local function createTerrainTypeButton(name, parent)
+ local dropDownTextButton = Instance.new("TextButton")
+ dropDownTextButton.Name = name .. "Button"
+ dropDownTextButton.Font = Enum.Font.ArialBold
+ dropDownTextButton.FontSize = Enum.FontSize.Size14
+ dropDownTextButton.BorderSizePixel = 0
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ dropDownTextButton.Text = name
+ dropDownTextButton.TextXAlignment = Enum.TextXAlignment.Left
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.ZIndex = parent.ZIndex + 1
+ dropDownTextButton.Size = UDim2.new(0,parent.Size.X.Offset - 2,0,16)
+ dropDownTextButton.Position = UDim2.new(0,1,0,0)
+
+ dropDownTextButton.MouseEnter:connect(function()
+ dropDownTextButton.BackgroundTransparency = 0
+ dropDownTextButton.TextColor3 = Color3.new(0,0,0)
+ end)
+
+ dropDownTextButton.MouseLeave:connect(function()
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ end)
+
+ dropDownTextButton.MouseButton1Click:connect(function()
+ dropDownTextButton.BackgroundTransparency = 1
+ dropDownTextButton.TextColor3 = Color3.new(1,1,1)
+ if dropDownTextButton.Parent and dropDownTextButton.Parent:IsA("GuiObject") then
+ dropDownTextButton.Parent.Visible = false
+ end
+ selectTerrainShape(terrainShapeMap[dropDownTextButton.Text])
+ end)
+
+ return dropDownTextButton
+ end
+
+ local function createTerrainDropDownMenu(zIndex)
+ local dropDown = Instance.new("Frame")
+ dropDown.Name = "TerrainDropDown"
+ dropDown.BackgroundColor3 = Color3.new(0,0,0)
+ dropDown.BorderColor3 = Color3.new(1,0,0)
+ dropDown.Size = UDim2.new(0,200,0,0)
+ dropDown.Visible = false
+ dropDown.ZIndex = zIndex
+ dropDown.Parent = setGui
+
+ for i = 1, #terrainShapes do
+ local shapeButton = createTerrainTypeButton(terrainShapes[i],dropDown)
+ shapeButton.Position = UDim2.new(0,1,0,(i - 1) * (shapeButton.Size.Y.Offset))
+ shapeButton.Parent = dropDown
+ dropDown.Size = UDim2.new(0,200,0,dropDown.Size.Y.Offset + (shapeButton.Size.Y.Offset))
+ end
+
+ dropDown.MouseLeave:connect(function()
+ dropDown.Visible = false
+ end)
+ end
+
+
+ local function createDropDownMenuButton(parent)
+ local dropDownButton = Instance.new("ImageButton")
+ dropDownButton.Name = "DropDownButton"
+ dropDownButton.Image = "http://www.roblox.com/asset/?id=67581509"
+ dropDownButton.BackgroundTransparency = 1
+ dropDownButton.Size = UDim2.new(0,16,0,16)
+ dropDownButton.Position = UDim2.new(1,-24,0,6)
+ dropDownButton.ZIndex = parent.ZIndex + 2
+ dropDownButton.Parent = parent
+
+ if not setGui:FindFirstChild("TerrainDropDown") then
+ createTerrainDropDownMenu(8)
+ end
+
+ dropDownButton.MouseButton1Click:connect(function()
+ setGui.TerrainDropDown.Visible = true
+ setGui.TerrainDropDown.Position = UDim2.new(0,parent.AbsolutePosition.X,0,parent.AbsolutePosition.Y)
+ currTerrainDropDownFrame = parent
+ end)
+ end
+
+ local function buildInsertButton()
+ local insertButton = makeInsertAssetButton()
+ insertButton.Name = "InsertAssetButton"
+ insertButton.Visible = true
+
+ if Data.Category[Data.CurrentCategory].SetName == "High Scalability" then
+ createDropDownMenuButton(insertButton)
+ end
+
+ local lastEnter = nil
+ local mouseEnterCon = insertButton.MouseEnter:connect(function()
+ lastEnter = insertButton
+ delay(0.1,function()
+ if lastEnter == insertButton then
+ showLargePreview(insertButton)
+ end
+ end)
+ end)
+ return insertButton, mouseEnterCon
+ end
+
+ local function realignButtonGrid(columns)
+ local x = 0
+ local y = 0
+ for i = 1, #insertButtons do
+ insertButtons[i].Position = UDim2.new(0, buttonWidth * x, 0, buttonHeight * y)
+ x = x + 1
+ if x >= columns then
+ x = 0
+ y = y + 1
+ end
+ end
+ end
+
+ local function setInsertButtonImageBehavior(insertFrame, visible, name, assetId)
+ if visible then
+ insertFrame.AssetName.Value = name
+ insertFrame.AssetId.Value = assetId
+ local newImageUrl = SmallThumbnailUrl .. assetId
+ if newImageUrl ~= insertFrame.Button.ButtonImage.Image then
+ delay(0,function()
+ game:GetService("ContentProvider"):Preload(SmallThumbnailUrl .. assetId)
+ if insertFrame:findFirstChild("Button") then
+ insertFrame.Button.ButtonImage.Image = SmallThumbnailUrl .. assetId
+ end
+ end)
+ end
+ table.insert(insertButtonCons,
+ insertFrame.Button.MouseButton1Click:connect(function()
+ -- special case for water, show water selection gui
+ local isWaterSelected = (name == "Water") and (Data.Category[Data.CurrentCategory].SetName == "High Scalability")
+ waterGui.Visible = isWaterSelected
+ if isWaterSelected then
+ objectSelected(name, tonumber(assetId), nil)
+ else
+ objectSelected(name, tonumber(assetId))
+ end
+ end)
+ )
+ insertFrame.Visible = true
+ else
+ insertFrame.Visible = false
+ end
+ end
+
+ local function loadSectionOfItems(setGui, rows, columns)
+ local pageSize = rows * columns
+
+ if arrayPosition > #contents then return end
+
+ local origArrayPos = arrayPosition
+
+ local yCopy = 0
+ for i = 1, pageSize + 1 do
+ if arrayPosition >= #contents + 1 then
+ break
+ end
+
+ local buttonCon
+ insertButtons[arrayPosition], buttonCon = buildInsertButton()
+ table.insert(insertButtonCons,buttonCon)
+ insertButtons[arrayPosition].Parent = setGui.SetPanel.ItemsFrame
+ arrayPosition = arrayPosition + 1
+ end
+ realignButtonGrid(columns)
+
+ local indexCopy = origArrayPos
+ for index = origArrayPos, arrayPosition do
+ if insertButtons[index] then
+ if contents[index] then
+
+ -- we don't want water to have a drop down button
+ if contents[index].Name == "Water" then
+ if Data.Category[Data.CurrentCategory].SetName == "High Scalability" then
+ insertButtons[index]:FindFirstChild("DropDownButton",true):Destroy()
+ end
+ end
+
+ local assetId
+ if useAssetVersionId then
+ assetId = contents[index].AssetVersionId
+ else
+ assetId = contents[index].AssetId
+ end
+ setInsertButtonImageBehavior(insertButtons[index], true, contents[index].Name, assetId)
+ else
+ break
+ end
+ else
+ break
+ end
+ indexCopy = index
+ end
+ end
+
+ local function setSetIndex()
+ Data.Category[Data.CurrentCategory].Index = 0
+
+ rows = 7
+ columns = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.X/buttonWidth)
+
+ contents = Data.Category[Data.CurrentCategory].Contents
+ if contents then
+ -- remove our buttons and their connections
+ for i = 1, #insertButtons do
+ insertButtons[i]:remove()
+ end
+ for i = 1, #insertButtonCons do
+ if insertButtonCons[i] then insertButtonCons[i]:disconnect() end
+ end
+ insertButtonCons = {}
+ insertButtons = {}
+
+ arrayPosition = 1
+ loadSectionOfItems(setGui, rows, columns)
+ end
+ end
+
+ local function selectSet(button, setName, setId, setIndex)
+ if button and Data.Category[Data.CurrentCategory] ~= nil then
+ if button ~= Data.Category[Data.CurrentCategory].Button then
+ Data.Category[Data.CurrentCategory].Button = button
+
+ if SetCache[setId] == nil then
+ SetCache[setId] = game:GetService("InsertService"):GetCollection(setId)
+ end
+ Data.Category[Data.CurrentCategory].Contents = SetCache[setId]
+
+ Data.Category[Data.CurrentCategory].SetName = setName
+ Data.Category[Data.CurrentCategory].SetId = setId
+ end
+ setSetIndex()
+ end
+ end
+
+ local function selectCategoryPage(buttons, page)
+ if buttons ~= Data.CurrentCategory then
+ if Data.CurrentCategory then
+ for key, button in pairs(Data.CurrentCategory) do
+ button.Visible = false
+ end
+ end
+
+ Data.CurrentCategory = buttons
+ if Data.Category[Data.CurrentCategory] == nil then
+ Data.Category[Data.CurrentCategory] = {}
+ if #buttons > 0 then
+ selectSet(buttons[1], buttons[1].SetName.Value, buttons[1].SetId.Value, 0)
+ end
+ else
+ Data.Category[Data.CurrentCategory].Button = nil
+ selectSet(Data.Category[Data.CurrentCategory].ButtonFrame, Data.Category[Data.CurrentCategory].SetName, Data.Category[Data.CurrentCategory].SetId, Data.Category[Data.CurrentCategory].Index)
+ end
+ end
+ end
+
+ local function selectCategory(category)
+ selectCategoryPage(category, 0)
+ end
+
+ local function resetAllSetButtonSelection()
+ local setButtons = setGui.SetPanel.Sets.SetsLists:GetChildren()
+ for i = 1, #setButtons do
+ if setButtons[i]:IsA("TextButton") then
+ setButtons[i].Selected = false
+ setButtons[i].BackgroundTransparency = 1
+ setButtons[i].TextColor3 = Color3.new(1,1,1)
+ setButtons[i].BackgroundColor3 = Color3.new(1,1,1)
+ end
+ end
+ end
+
+ local function populateSetsFrame()
+ local currRow = 0
+ for i = 1, #userCategoryButtons do
+ local button = userCategoryButtons[i]
+ button.Visible = true
+ button.Position = UDim2.new(0,5,0,currRow * button.Size.Y.Offset)
+ button.Parent = setGui.SetPanel.Sets.SetsLists
+
+ if i == 1 then -- we will have this selected by default, so show it
+ button.Selected = true
+ button.BackgroundColor3 = Color3.new(0,204/255,0)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundTransparency = 0
+ end
+
+ button.MouseEnter:connect(function()
+ if not button.Selected then
+ button.BackgroundTransparency = 0
+ button.TextColor3 = Color3.new(0,0,0)
+ end
+ end)
+ button.MouseLeave:connect(function()
+ if not button.Selected then
+ button.BackgroundTransparency = 1
+ button.TextColor3 = Color3.new(1,1,1)
+ end
+ end)
+ button.MouseButton1Click:connect(function()
+ resetAllSetButtonSelection()
+ button.Selected = not button.Selected
+ button.BackgroundColor3 = Color3.new(0,204/255,0)
+ button.TextColor3 = Color3.new(0,0,0)
+ button.BackgroundTransparency = 0
+ selectSet(button, button.Text, userCategoryButtons[i].SetId.Value, 0)
+ end)
+
+ currRow = currRow + 1
+ end
+
+ local buttons = setGui.SetPanel.Sets.SetsLists:GetChildren()
+
+ -- set first category as loaded for default
+ if buttons then
+ for i = 1, #buttons do
+ if buttons[i]:IsA("TextButton") then
+ selectSet(buttons[i], buttons[i].Text, userCategoryButtons[i].SetId.Value, 0)
+ selectCategory(userCategoryButtons)
+ break
+ end
+ end
+ end
+ end
+
+ setGui = createSetGui()
+ waterGui, waterTypeChangedEvent = createWaterGui()
+ waterGui.Position = UDim2.new(0,55,0,0)
+ waterGui.Parent = setGui
+ setGui.Changed:connect(function(prop) -- this resizes the preview image to always be the right size
+ if prop == "AbsoluteSize" then
+ handleResize()
+ setSetIndex()
+ end
+ end)
+
+ local scrollFrame, controlFrame = t.CreateTrueScrollingFrame()
+ scrollFrame.Size = UDim2.new(0.54,0,0.85,0)
+ scrollFrame.Position = UDim2.new(0.24,0,0.085,0)
+ scrollFrame.Name = "ItemsFrame"
+ scrollFrame.ZIndex = 6
+ scrollFrame.Parent = setGui.SetPanel
+ scrollFrame.BackgroundTransparency = 1
+
+ drillDownSetZIndex(controlFrame,7)
+
+ controlFrame.Parent = setGui.SetPanel
+ controlFrame.Position = UDim2.new(0.76, 5, 0, 0)
+
+ local debounce = false
+ controlFrame.ScrollBottom.Changed:connect(function(prop)
+ if controlFrame.ScrollBottom.Value == true then
+ if debounce then return end
+ debounce = true
+ loadSectionOfItems(setGui, rows, columns)
+ debounce = false
+ end
+ end)
+
+ local userData = {}
+ for id = 1, #userIdsForSets do
+ local newUserData = game:GetService("InsertService"):GetUserSets(userIdsForSets[id])
+ if newUserData and #newUserData > 2 then
+ -- start at #3 to skip over My Decals and My Models for each account
+ for category = 3, #newUserData do
+ if newUserData[category].Name == "High Scalability" then -- we want high scalability parts to show first
+ table.insert(userData,1,newUserData[category])
+ else
+ table.insert(userData, newUserData[category])
+ end
+ end
+ end
+
+ end
+ if userData then
+ userCategoryButtons = processCategory(userData)
+ end
+
+ rows = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.Y/buttonHeight)
+ columns = math.floor(setGui.SetPanel.ItemsFrame.AbsoluteSize.X/buttonWidth)
+
+ populateSetsFrame()
+
+ insertPanelCloseCon = setGui.SetPanel.CancelButton.MouseButton1Click:connect(function()
+ setGui.SetPanel.Visible = false
+ if dialogClosed then dialogClosed() end
+ end)
+
+ local setVisibilityFunction = function(visible)
+ if visible then
+ setGui.SetPanel.Visible = true
+ else
+ setGui.SetPanel.Visible = false
+ end
+ end
+
+ local getVisibilityFunction = function()
+ if setGui then
+ if setGui:FindFirstChild("SetPanel") then
+ return setGui.SetPanel.Visible
+ end
+ end
+
+ return false
+ end
+
+ return setGui, setVisibilityFunction, getVisibilityFunction, waterTypeChangedEvent
+end
+
+t.CreateTerrainMaterialSelector = function(size,position)
+ local terrainMaterialSelectionChanged = Instance.new("BindableEvent")
+ terrainMaterialSelectionChanged.Name = "TerrainMaterialSelectionChanged"
+
+ local selectedButton = nil
+
+ local frame = Instance.new("Frame")
+ frame.Name = "TerrainMaterialSelector"
+ if size then
+ frame.Size = size
+ else
+ frame.Size = UDim2.new(0, 245, 0, 230)
+ end
+ if position then
+ frame.Position = position
+ end
+ frame.BorderSizePixel = 0
+ frame.BackgroundColor3 = Color3.new(0,0,0)
+ frame.Active = true
+
+ terrainMaterialSelectionChanged.Parent = frame
+
+ local waterEnabled = true -- todo: turn this on when water is ready
+
+ local materialToImageMap = {}
+ local materialNames = {"Grass", "Sand", "Brick", "Granite", "Asphalt", "Iron", "Aluminum", "Gold", "Plank", "Log", "Gravel", "Cinder Block", "Stone Wall", "Concrete", "Plastic (red)", "Plastic (blue)"}
+ if waterEnabled then
+ table.insert(materialNames,"Water")
+ end
+ local currentMaterial = 1
+
+ function getEnumFromName(choice)
+ if choice == "Grass" then return 1 end
+ if choice == "Sand" then return 2 end
+ if choice == "Erase" then return 0 end
+ if choice == "Brick" then return 3 end
+ if choice == "Granite" then return 4 end
+ if choice == "Asphalt" then return 5 end
+ if choice == "Iron" then return 6 end
+ if choice == "Aluminum" then return 7 end
+ if choice == "Gold" then return 8 end
+ if choice == "Plank" then return 9 end
+ if choice == "Log" then return 10 end
+ if choice == "Gravel" then return 11 end
+ if choice == "Cinder Block" then return 12 end
+ if choice == "Stone Wall" then return 13 end
+ if choice == "Concrete" then return 14 end
+ if choice == "Plastic (red)" then return 15 end
+ if choice == "Plastic (blue)" then return 16 end
+ if choice == "Water" then return 17 end
+ end
+
+ function getNameFromEnum(choice)
+ if choice == Enum.CellMaterial.Grass or choice == 1 then return "Grass"end
+ if choice == Enum.CellMaterial.Sand or choice == 2 then return "Sand" end
+ if choice == Enum.CellMaterial.Empty or choice == 0 then return "Erase" end
+ if choice == Enum.CellMaterial.Brick or choice == 3 then return "Brick" end
+ if choice == Enum.CellMaterial.Granite or choice == 4 then return "Granite" end
+ if choice == Enum.CellMaterial.Asphalt or choice == 5 then return "Asphalt" end
+ if choice == Enum.CellMaterial.Iron or choice == 6 then return "Iron" end
+ if choice == Enum.CellMaterial.Aluminum or choice == 7 then return "Aluminum" end
+ if choice == Enum.CellMaterial.Gold or choice == 8 then return "Gold" end
+ if choice == Enum.CellMaterial.WoodPlank or choice == 9 then return "Plank" end
+ if choice == Enum.CellMaterial.WoodLog or choice == 10 then return "Log" end
+ if choice == Enum.CellMaterial.Gravel or choice == 11 then return "Gravel" end
+ if choice == Enum.CellMaterial.CinderBlock or choice == 12 then return "Cinder Block" end
+ if choice == Enum.CellMaterial.MossyStone or choice == 13 then return "Stone Wall" end
+ if choice == Enum.CellMaterial.Cement or choice == 14 then return "Concrete" end
+ if choice == Enum.CellMaterial.RedPlastic or choice == 15 then return "Plastic (red)" end
+ if choice == Enum.CellMaterial.BluePlastic or choice == 16 then return "Plastic (blue)" end
+
+ if waterEnabled then
+ if choice == Enum.CellMaterial.Water or choice == 17 then return "Water" end
+ end
+ end
+
+
+ local function updateMaterialChoice(choice)
+ currentMaterial = getEnumFromName(choice)
+ terrainMaterialSelectionChanged:Fire(currentMaterial)
+ end
+
+ -- we so need a better way to do this
+ for i,v in pairs(materialNames) do
+ materialToImageMap[v] = {}
+ if v == "Grass" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=56563112"
+ elseif v == "Sand" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=62356652"
+ elseif v == "Brick" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=65961537"
+ elseif v == "Granite" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532153"
+ elseif v == "Asphalt" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532038"
+ elseif v == "Iron" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532093"
+ elseif v == "Aluminum" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531995"
+ elseif v == "Gold" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532118"
+ elseif v == "Plastic (red)" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531848"
+ elseif v == "Plastic (blue)" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531924"
+ elseif v == "Plank" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532015"
+ elseif v == "Log" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532051"
+ elseif v == "Gravel" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532206"
+ elseif v == "Cinder Block" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532103"
+ elseif v == "Stone Wall" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67531804"
+ elseif v == "Concrete" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=67532059"
+ elseif v == "Water" then materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=81407474"
+ else materialToImageMap[v].Regular = "http://www.roblox.com/asset/?id=66887593" -- fill in the rest here!!
+ end
+ end
+
+ local scrollFrame, scrollUp, scrollDown, recalculateScroll = t.CreateScrollingFrame(nil,"grid")
+ scrollFrame.Size = UDim2.new(0.85,0,1,0)
+ scrollFrame.Position = UDim2.new(0,0,0,0)
+ scrollFrame.Parent = frame
+
+ scrollUp.Parent = frame
+ scrollUp.Visible = true
+ scrollUp.Position = UDim2.new(1,-19,0,0)
+
+ scrollDown.Parent = frame
+ scrollDown.Visible = true
+ scrollDown.Position = UDim2.new(1,-19,1,-17)
+
+ local function goToNewMaterial(buttonWrap, materialName)
+ updateMaterialChoice(materialName)
+ buttonWrap.BackgroundTransparency = 0
+ selectedButton.BackgroundTransparency = 1
+ selectedButton = buttonWrap
+ end
+
+ local function createMaterialButton(name)
+ local buttonWrap = Instance.new("TextButton")
+ buttonWrap.Text = ""
+ buttonWrap.Size = UDim2.new(0,32,0,32)
+ buttonWrap.BackgroundColor3 = Color3.new(1,1,1)
+ buttonWrap.BorderSizePixel = 0
+ buttonWrap.BackgroundTransparency = 1
+ buttonWrap.AutoButtonColor = false
+ buttonWrap.Name = tostring(name)
+
+ local imageButton = Instance.new("ImageButton")
+ imageButton.AutoButtonColor = false
+ imageButton.BackgroundTransparency = 1
+ imageButton.Size = UDim2.new(0,30,0,30)
+ imageButton.Position = UDim2.new(0,1,0,1)
+ imageButton.Name = tostring(name)
+ imageButton.Parent = buttonWrap
+ imageButton.Image = materialToImageMap[name].Regular
+
+ local enumType = Instance.new("NumberValue")
+ enumType.Name = "EnumType"
+ enumType.Parent = buttonWrap
+ enumType.Value = 0
+
+ imageButton.MouseEnter:connect(function()
+ buttonWrap.BackgroundTransparency = 0
+ end)
+ imageButton.MouseLeave:connect(function()
+ if selectedButton ~= buttonWrap then
+ buttonWrap.BackgroundTransparency = 1
+ end
+ end)
+ imageButton.MouseButton1Click:connect(function()
+ if selectedButton ~= buttonWrap then
+ goToNewMaterial(buttonWrap, tostring(name))
+ end
+ end)
+
+ return buttonWrap
+ end
+
+ for i = 1, #materialNames do
+ local imageButton = createMaterialButton(materialNames[i])
+
+ if materialNames[i] == "Grass" then -- always start with grass as the default
+ selectedButton = imageButton
+ imageButton.BackgroundTransparency = 0
+ end
+
+ imageButton.Parent = scrollFrame
+ end
+
+ local forceTerrainMaterialSelection = function(newMaterialType)
+ if not newMaterialType then return end
+ if currentMaterial == newMaterialType then return end
+
+ local matName = getNameFromEnum(newMaterialType)
+ local buttons = scrollFrame:GetChildren()
+ for i = 1, #buttons do
+ if buttons[i].Name == "Plastic (blue)" and matName == "Plastic (blue)" then goToNewMaterial(buttons[i],matName) return end
+ if buttons[i].Name == "Plastic (red)" and matName == "Plastic (red)" then goToNewMaterial(buttons[i],matName) return end
+ if string.find(buttons[i].Name, matName) then
+ goToNewMaterial(buttons[i],matName)
+ return
+ end
+ end
+ end
+
+ frame.Changed:connect(function ( prop )
+ if prop == "AbsoluteSize" then
+ recalculateScroll()
+ end
+ end)
+
+ recalculateScroll()
+ return frame, terrainMaterialSelectionChanged, forceTerrainMaterialSelection
+end
+
+t.CreateLoadingFrame = function(name,size,position)
+ game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id=35238053")
+
+ local loadingFrame = Instance.new("Frame")
+ loadingFrame.Name = "LoadingFrame"
+ loadingFrame.Style = Enum.FrameStyle.RobloxRound
+
+ if size then loadingFrame.Size = size
+ else loadingFrame.Size = UDim2.new(0,300,0,160) end
+ if position then loadingFrame.Position = position
+ else loadingFrame.Position = UDim2.new(0.5, -150, 0.5,-80) end
+
+ local loadingBar = Instance.new("Frame")
+ loadingBar.Name = "LoadingBar"
+ loadingBar.BackgroundColor3 = Color3.new(0,0,0)
+ loadingBar.BorderColor3 = Color3.new(79/255,79/255,79/255)
+ loadingBar.Position = UDim2.new(0,0,0,41)
+ loadingBar.Size = UDim2.new(1,0,0,30)
+ loadingBar.Parent = loadingFrame
+
+ local loadingGreenBar = Instance.new("ImageLabel")
+ loadingGreenBar.Name = "LoadingGreenBar"
+ loadingGreenBar.Image = "http://www.roblox.com/asset/?id=35238053"
+ loadingGreenBar.Position = UDim2.new(0,0,0,0)
+ loadingGreenBar.Size = UDim2.new(0,0,1,0)
+ loadingGreenBar.Visible = false
+ loadingGreenBar.Parent = loadingBar
+
+ local loadingPercent = Instance.new("TextLabel")
+ loadingPercent.Name = "LoadingPercent"
+ loadingPercent.BackgroundTransparency = 1
+ loadingPercent.Position = UDim2.new(0,0,1,0)
+ loadingPercent.Size = UDim2.new(1,0,0,14)
+ loadingPercent.Font = Enum.Font.Arial
+ loadingPercent.Text = "0%"
+ loadingPercent.FontSize = Enum.FontSize.Size14
+ loadingPercent.TextColor3 = Color3.new(1,1,1)
+ loadingPercent.Parent = loadingBar
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelButton"
+ cancelButton.Position = UDim2.new(0.5,-60,1,-40)
+ cancelButton.Size = UDim2.new(0,120,0,40)
+ cancelButton.Font = Enum.Font.Arial
+ cancelButton.FontSize = Enum.FontSize.Size18
+ cancelButton.TextColor3 = Color3.new(1,1,1)
+ cancelButton.Text = "Cancel"
+ cancelButton.Style = Enum.ButtonStyle.RobloxButton
+ cancelButton.Parent = loadingFrame
+
+ local loadingName = Instance.new("TextLabel")
+ loadingName.Name = "loadingName"
+ loadingName.BackgroundTransparency = 1
+ loadingName.Size = UDim2.new(1,0,0,18)
+ loadingName.Position = UDim2.new(0,0,0,2)
+ loadingName.Font = Enum.Font.Arial
+ loadingName.Text = name
+ loadingName.TextColor3 = Color3.new(1,1,1)
+ loadingName.TextStrokeTransparency = 1
+ loadingName.FontSize = Enum.FontSize.Size18
+ loadingName.Parent = loadingFrame
+
+ local cancelButtonClicked = Instance.new("BindableEvent")
+ cancelButtonClicked.Name = "CancelButtonClicked"
+ cancelButtonClicked.Parent = cancelButton
+ cancelButton.MouseButton1Click:connect(function()
+ cancelButtonClicked:Fire()
+ end)
+
+ local updateLoadingGuiPercent = function(percent, tweenAction, tweenLength)
+ if percent and type(percent) ~= "number" then
+ error("updateLoadingGuiPercent expects number as argument, got",type(percent),"instead")
+ end
+
+ local newSize = nil
+ if percent < 0 then
+ newSize = UDim2.new(0,0,1,0)
+ elseif percent > 1 then
+ newSize = UDim2.new(1,0,1,0)
+ else
+ newSize = UDim2.new(percent,0,1,0)
+ end
+
+ if tweenAction then
+ if not tweenLength then
+ error("updateLoadingGuiPercent is set to tween new percentage, but got no tween time length! Please pass this in as third argument")
+ end
+
+ if (newSize.X.Scale > 0) then
+ loadingGreenBar.Visible = true
+ loadingGreenBar:TweenSize( newSize,
+ Enum.EasingDirection.Out,
+ Enum.EasingStyle.Quad,
+ tweenLength,
+ true)
+ else
+ loadingGreenBar:TweenSize( newSize,
+ Enum.EasingDirection.Out,
+ Enum.EasingStyle.Quad,
+ tweenLength,
+ true,
+ function()
+ if (newSize.X.Scale < 0) then
+ loadingGreenBar.Visible = false
+ end
+ end)
+ end
+
+ else
+ loadingGreenBar.Size = newSize
+ loadingGreenBar.Visible = (newSize.X.Scale > 0)
+ end
+ end
+
+ loadingGreenBar.Changed:connect(function(prop)
+ if prop == "Size" then
+ loadingPercent.Text = tostring( math.ceil(loadingGreenBar.Size.X.Scale * 100) ) .. "%"
+ end
+ end)
+
+ return loadingFrame, updateLoadingGuiPercent, cancelButtonClicked
+end
+
+t.CreatePluginFrame = function (name,size,position,scrollable,parent)
+ function createMenuButton(size,position,text,fontsize,name,parent)
+ local button = Instance.new("TextButton",parent)
+ button.AutoButtonColor = false
+ button.Name = name
+ button.BackgroundTransparency = 1
+ button.Position = position
+ button.Size = size
+ button.Font = Enum.Font.ArialBold
+ button.FontSize = fontsize
+ button.Text = text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.BorderSizePixel = 0
+ button.BackgroundColor3 = Color3.new(20/255,20/255,20/255)
+
+ button.MouseEnter:connect(function ( )
+ if button.Selected then return end
+ button.BackgroundTransparency = 0
+ end)
+ button.MouseLeave:connect(function ( )
+ if button.Selected then return end
+ button.BackgroundTransparency = 1
+ end)
+
+ return button
+
+ end
+
+ local dragBar = Instance.new("Frame",parent)
+ dragBar.Name = tostring(name) .. "DragBar"
+ dragBar.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+ dragBar.BorderColor3 = Color3.new(0,0,0)
+ if size then
+ dragBar.Size = UDim2.new(size.X.Scale,size.X.Offset,0,20) + UDim2.new(0,20,0,0)
+ else
+ dragBar.Size = UDim2.new(0,183,0,20)
+ end
+ if position then
+ dragBar.Position = position
+ end
+ dragBar.Active = true
+ dragBar.Draggable = true
+ --dragBar.Visible = false
+ dragBar.MouseEnter:connect(function ( )
+ dragBar.BackgroundColor3 = Color3.new(49/255,49/255,49/255)
+ end)
+ dragBar.MouseLeave:connect(function ( )
+ dragBar.BackgroundColor3 = Color3.new(39/255,39/255,39/255)
+ end)
+
+ -- plugin name label
+ local pluginNameLabel = Instance.new("TextLabel",dragBar)
+ pluginNameLabel.Name = "BarNameLabel"
+ pluginNameLabel.Text = " " .. tostring(name)
+ pluginNameLabel.TextColor3 = Color3.new(1,1,1)
+ pluginNameLabel.TextStrokeTransparency = 0
+ pluginNameLabel.Size = UDim2.new(1,0,1,0)
+ pluginNameLabel.Font = Enum.Font.ArialBold
+ pluginNameLabel.FontSize = Enum.FontSize.Size18
+ pluginNameLabel.TextXAlignment = Enum.TextXAlignment.Left
+ pluginNameLabel.BackgroundTransparency = 1
+
+ -- close button
+ local closeButton = createMenuButton(UDim2.new(0,15,0,17),UDim2.new(1,-16,0.5,-8),"X",Enum.FontSize.Size14,"CloseButton",dragBar)
+ local closeEvent = Instance.new("BindableEvent")
+ closeEvent.Name = "CloseEvent"
+ closeEvent.Parent = closeButton
+ closeButton.MouseButton1Click:connect(function ()
+ closeEvent:Fire()
+ closeButton.BackgroundTransparency = 1
+ end)
+
+ -- help button
+ local helpButton = createMenuButton(UDim2.new(0,15,0,17),UDim2.new(1,-51,0.5,-8),"?",Enum.FontSize.Size14,"HelpButton",dragBar)
+ local helpFrame = Instance.new("Frame",dragBar)
+ helpFrame.Name = "HelpFrame"
+ helpFrame.BackgroundColor3 = Color3.new(0,0,0)
+ helpFrame.Size = UDim2.new(0,300,0,552)
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ helpFrame.Active = true
+ helpFrame.BorderSizePixel = 0
+ helpFrame.Visible = false
+
+ helpButton.MouseButton1Click:connect(function( )
+ helpFrame.Visible = not helpFrame.Visible
+ if helpFrame.Visible then
+ helpButton.Selected = true
+ helpButton.BackgroundTransparency = 0
+ local screenGui = getScreenGuiAncestor(helpFrame)
+ if screenGui then
+ if helpFrame.AbsolutePosition.X + helpFrame.AbsoluteSize.X > screenGui.AbsoluteSize.X then --position on left hand side
+ helpFrame.Position = UDim2.new(0,-5 - helpFrame.AbsoluteSize.X,0,0)
+ else -- position on right hand side
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ end
+ else
+ helpFrame.Position = UDim2.new(1,5,0,0)
+ end
+ else
+ helpButton.Selected = false
+ helpButton.BackgroundTransparency = 1
+ end
+ end)
+
+ local minimizeButton = createMenuButton(UDim2.new(0,16,0,17),UDim2.new(1,-34,0.5,-8),"-",Enum.FontSize.Size14,"MinimizeButton",dragBar)
+ minimizeButton.TextYAlignment = Enum.TextYAlignment.Top
+
+ local minimizeFrame = Instance.new("Frame",dragBar)
+ minimizeFrame.Name = "MinimizeFrame"
+ minimizeFrame.BackgroundColor3 = Color3.new(73/255,73/255,73/255)
+ minimizeFrame.BorderColor3 = Color3.new(0,0,0)
+ minimizeFrame.Position = UDim2.new(0,0,1,0)
+ if size then
+ minimizeFrame.Size = UDim2.new(size.X.Scale,size.X.Offset,0,50) + UDim2.new(0,20,0,0)
+ else
+ minimizeFrame.Size = UDim2.new(0,183,0,50)
+ end
+ minimizeFrame.Visible = false
+
+ local minimizeBigButton = Instance.new("TextButton",minimizeFrame)
+ minimizeBigButton.Position = UDim2.new(0.5,-50,0.5,-20)
+ minimizeBigButton.Name = "MinimizeButton"
+ minimizeBigButton.Size = UDim2.new(0,100,0,40)
+ minimizeBigButton.Style = Enum.ButtonStyle.RobloxButton
+ minimizeBigButton.Font = Enum.Font.ArialBold
+ minimizeBigButton.FontSize = Enum.FontSize.Size18
+ minimizeBigButton.TextColor3 = Color3.new(1,1,1)
+ minimizeBigButton.Text = "Show"
+
+ local separatingLine = Instance.new("Frame",dragBar)
+ separatingLine.Name = "SeparatingLine"
+ separatingLine.BackgroundColor3 = Color3.new(115/255,115/255,115/255)
+ separatingLine.BorderSizePixel = 0
+ separatingLine.Position = UDim2.new(1,-18,0.5,-7)
+ separatingLine.Size = UDim2.new(0,1,0,14)
+
+ local otherSeparatingLine = separatingLine:clone()
+ otherSeparatingLine.Position = UDim2.new(1,-35,0.5,-7)
+ otherSeparatingLine.Parent = dragBar
+
+ local widgetContainer = Instance.new("Frame",dragBar)
+ widgetContainer.Name = "WidgetContainer"
+ widgetContainer.BackgroundTransparency = 1
+ widgetContainer.Position = UDim2.new(0,0,1,0)
+ widgetContainer.BorderColor3 = Color3.new(0,0,0)
+ if not scrollable then
+ widgetContainer.BackgroundTransparency = 0
+ widgetContainer.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ end
+
+ if size then
+ if scrollable then
+ widgetContainer.Size = size
+ else
+ widgetContainer.Size = UDim2.new(0,dragBar.AbsoluteSize.X,size.Y.Scale,size.Y.Offset)
+ end
+ else
+ if scrollable then
+ widgetContainer.Size = UDim2.new(0,163,0,400)
+ else
+ widgetContainer.Size = UDim2.new(0,dragBar.AbsoluteSize.X,0,400)
+ end
+ end
+ if position then
+ widgetContainer.Position = position + UDim2.new(0,0,0,20)
+ end
+
+ local frame,control,verticalDragger = nil
+ if scrollable then
+ --frame for widgets
+ frame,control = t.CreateTrueScrollingFrame()
+ frame.Size = UDim2.new(1, 0, 1, 0)
+ frame.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ frame.BorderColor3 = Color3.new(0,0,0)
+ frame.Active = true
+ frame.Parent = widgetContainer
+ control.Parent = dragBar
+ control.BackgroundColor3 = Color3.new(72/255,72/255,72/255)
+ control.BorderSizePixel = 0
+ control.BackgroundTransparency = 0
+ control.Position = UDim2.new(1,-21,1,1)
+ if size then
+ control.Size = UDim2.new(0,21,size.Y.Scale,size.Y.Offset)
+ else
+ control.Size = UDim2.new(0,21,0,400)
+ end
+ control:FindFirstChild("ScrollDownButton").Position = UDim2.new(0,0,1,-20)
+
+ local fakeLine = Instance.new("Frame",control)
+ fakeLine.Name = "FakeLine"
+ fakeLine.BorderSizePixel = 0
+ fakeLine.BackgroundColor3 = Color3.new(0,0,0)
+ fakeLine.Size = UDim2.new(0,1,1,1)
+ fakeLine.Position = UDim2.new(1,0,0,0)
+
+ verticalDragger = Instance.new("TextButton",widgetContainer)
+ verticalDragger.ZIndex = 2
+ verticalDragger.AutoButtonColor = false
+ verticalDragger.Name = "VerticalDragger"
+ verticalDragger.BackgroundColor3 = Color3.new(50/255,50/255,50/255)
+ verticalDragger.BorderColor3 = Color3.new(0,0,0)
+ verticalDragger.Size = UDim2.new(1,20,0,20)
+ verticalDragger.Position = UDim2.new(0,0,1,0)
+ verticalDragger.Active = true
+ verticalDragger.Text = ""
+
+ local scrubFrame = Instance.new("Frame",verticalDragger)
+ scrubFrame.Name = "ScrubFrame"
+ scrubFrame.BackgroundColor3 = Color3.new(1,1,1)
+ scrubFrame.BorderSizePixel = 0
+ scrubFrame.Position = UDim2.new(0.5,-5,0.5,0)
+ scrubFrame.Size = UDim2.new(0,10,0,1)
+ scrubFrame.ZIndex = 5
+ local scrubTwo = scrubFrame:clone()
+ scrubTwo.Position = UDim2.new(0.5,-5,0.5,-2)
+ scrubTwo.Parent = verticalDragger
+ local scrubThree = scrubFrame:clone()
+ scrubThree.Position = UDim2.new(0.5,-5,0.5,2)
+ scrubThree.Parent = verticalDragger
+
+ local areaSoak = Instance.new("TextButton",getScreenGuiAncestor(parent))
+ areaSoak.Name = "AreaSoak"
+ areaSoak.Size = UDim2.new(1,0,1,0)
+ areaSoak.BackgroundTransparency = 1
+ areaSoak.BorderSizePixel = 0
+ areaSoak.Text = ""
+ areaSoak.ZIndex = 10
+ areaSoak.Visible = false
+ areaSoak.Active = true
+
+ local draggingVertical = false
+ local startYPos = nil
+ verticalDragger.MouseEnter:connect(function ()
+ verticalDragger.BackgroundColor3 = Color3.new(60/255,60/255,60/255)
+ end)
+ verticalDragger.MouseLeave:connect(function ()
+ verticalDragger.BackgroundColor3 = Color3.new(50/255,50/255,50/255)
+ end)
+ verticalDragger.MouseButton1Down:connect(function(x,y)
+ draggingVertical = true
+ areaSoak.Visible = true
+ startYPos = y
+ end)
+ areaSoak.MouseButton1Up:connect(function ( )
+ draggingVertical = false
+ areaSoak.Visible = false
+ end)
+ areaSoak.MouseMoved:connect(function(x,y)
+ if not draggingVertical then return end
+
+ local yDelta = y - startYPos
+ if not control.ScrollDownButton.Visible and yDelta > 0 then
+ return
+ end
+
+ if (widgetContainer.Size.Y.Offset + yDelta) < 150 then
+ widgetContainer.Size = UDim2.new(widgetContainer.Size.X.Scale, widgetContainer.Size.X.Offset,widgetContainer.Size.Y.Scale,150)
+ control.Size = UDim2.new (0,21,0,150)
+ return
+ end
+
+ startYPos = y
+
+ if widgetContainer.Size.Y.Offset + yDelta >= 0 then
+ widgetContainer.Size = UDim2.new(widgetContainer.Size.X.Scale, widgetContainer.Size.X.Offset,widgetContainer.Size.Y.Scale,widgetContainer.Size.Y.Offset + yDelta)
+ control.Size = UDim2.new(0,21,0,control.Size.Y.Offset + yDelta )
+ end
+ end)
+ end
+
+ local function switchMinimize()
+ minimizeFrame.Visible = not minimizeFrame.Visible
+ if scrollable then
+ frame.Visible = not frame.Visible
+ verticalDragger.Visible = not verticalDragger.Visible
+ control.Visible = not control.Visible
+ else
+ widgetContainer.Visible = not widgetContainer.Visible
+ end
+
+ if minimizeFrame.Visible then
+ minimizeButton.Text = "+"
+ else
+ minimizeButton.Text = "-"
+ end
+ end
+
+ minimizeBigButton.MouseButton1Click:connect(function ( )
+ switchMinimize()
+ end)
+
+ minimizeButton.MouseButton1Click:connect(function( )
+ switchMinimize()
+ end)
+
+ if scrollable then
+ return dragBar, frame, helpFrame, closeEvent
+ else
+ return dragBar, widgetContainer, helpFrame, closeEvent
+ end
+end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "CreatePropertyDropDownMenu" or funcNameOrFunc == t.CreatePropertyDropDownMenu then
+ return "Function CreatePropertyDropDownMenu. " ..
+ "Arguments: (instance, propertyName, enumType). " ..
+ "Side effect: returns a container with a drop-down-box that is linked to the 'property' field of 'instance' which is of type 'enumType'"
+ end
+ if funcNameOrFunc == "CreateDropDownMenu" or funcNameOrFunc == t.CreateDropDownMenu then
+ return "Function CreateDropDownMenu. " ..
+ "Arguments: (items, onItemSelected). " ..
+ "Side effect: Returns 2 results, a container to the gui object and a 'updateSelection' function for external updating. The container is a drop-down-box created around a list of items"
+ end
+ if funcNameOrFunc == "CreateMessageDialog" or funcNameOrFunc == t.CreateMessageDialog then
+ return "Function CreateMessageDialog. " ..
+ "Arguments: (title, message, buttons). " ..
+ "Side effect: Returns a gui object of a message box with 'title' and 'message' as passed in. 'buttons' input is an array of Tables contains a 'Text' and 'Function' field for the text/callback of each button"
+ end
+ if funcNameOrFunc == "CreateStyledMessageDialog" or funcNameOrFunc == t.CreateStyledMessageDialog then
+ return "Function CreateStyledMessageDialog. " ..
+ "Arguments: (title, message, style, buttons). " ..
+ "Side effect: Returns a gui object of a message box with 'title' and 'message' as passed in. 'buttons' input is an array of Tables contains a 'Text' and 'Function' field for the text/callback of each button, 'style' is a string, either Error, Notify or Confirm"
+ end
+ if funcNameOrFunc == "GetFontHeight" or funcNameOrFunc == t.GetFontHeight then
+ return "Function GetFontHeight. " ..
+ "Arguments: (font, fontSize). " ..
+ "Side effect: returns the size in pixels of the given font + fontSize"
+ end
+ if funcNameOrFunc == "LayoutGuiObjects" or funcNameOrFunc == t.LayoutGuiObjects then
+
+ end
+ if funcNameOrFunc == "CreateScrollingFrame" or funcNameOrFunc == t.CreateScrollingFrame then
+ return "Function CreateScrollingFrame. " ..
+ "Arguments: (orderList, style) " ..
+ "Side effect: returns 4 objects, (scrollFrame, scrollUpButton, scrollDownButton, recalculateFunction). 'scrollFrame' can be filled with GuiObjects. It will lay them out and allow scrollUpButton/scrollDownButton to interact with them. Orderlist is optional (and specifies the order to layout the children. Without orderlist, it uses the children order. style is also optional, and allows for a 'grid' styling if style is passed 'grid' as a string. recalculateFunction can be called when a relayout is needed (when orderList changes)"
+ end
+ if funcNameOrFunc == "CreateTrueScrollingFrame" or funcNameOrFunc == t.CreateTrueScrollingFrame then
+ return "Function CreateTrueScrollingFrame. " ..
+ "Arguments: (nil) " ..
+ "Side effect: returns 2 objects, (scrollFrame, controlFrame). 'scrollFrame' can be filled with GuiObjects, and they will be clipped if not inside the frame's bounds. controlFrame has children scrollup and scrolldown, as well as a slider. controlFrame can be parented to any guiobject and it will readjust itself to fit."
+ end
+ if funcNameOrFunc == "AutoTruncateTextObject" or funcNameOrFunc == t.AutoTruncateTextObject then
+ return "Function AutoTruncateTextObject. " ..
+ "Arguments: (textLabel) " ..
+ "Side effect: returns 2 objects, (textLabel, changeText). The 'textLabel' input is modified to automatically truncate text (with ellipsis), if it gets too small to fit. 'changeText' is a function that can be used to change the text, it takes 1 string as an argument"
+ end
+ if funcNameOrFunc == "CreateSlider" or funcNameOrFunc == t.CreateSlider then
+ return "Function CreateSlider. " ..
+ "Arguments: (steps, width, position) " ..
+ "Side effect: returns 2 objects, (sliderGui, sliderPosition). The 'steps' argument specifies how many different positions the slider can hold along the bar. 'width' specifies in pixels how wide the bar should be (modifiable afterwards if desired). 'position' argument should be a UDim2 for slider positioning. 'sliderPosition' is an IntValue whose current .Value specifies the specific step the slider is currently on."
+ end
+ if funcNameOrFunc == "CreateSliderNew" or funcNameOrFunc == t.CreateSliderNew then
+ return "Function CreateSliderNew. " ..
+ "Arguments: (steps, width, position) " ..
+ "Side effect: returns 2 objects, (sliderGui, sliderPosition). The 'steps' argument specifies how many different positions the slider can hold along the bar. 'width' specifies in pixels how wide the bar should be (modifiable afterwards if desired). 'position' argument should be a UDim2 for slider positioning. 'sliderPosition' is an IntValue whose current .Value specifies the specific step the slider is currently on."
+ end
+ if funcNameOrFunc == "CreateLoadingFrame" or funcNameOrFunc == t.CreateLoadingFrame then
+ return "Function CreateLoadingFrame. " ..
+ "Arguments: (name, size, position) " ..
+ "Side effect: Creates a gui that can be manipulated to show progress for a particular action. Name appears above the loading bar, and size and position are udim2 values (both size and position are optional arguments). Returns 3 arguments, the first being the gui created. The second being updateLoadingGuiPercent, which is a bindable function. This function takes one argument (two optionally), which should be a number between 0 and 1, representing the percentage the loading gui should be at. The second argument to this function is a boolean value that if set to true will tween the current percentage value to the new percentage value, therefore our third argument is how long this tween should take. Our third returned argument is a BindableEvent, that when fired means that someone clicked the cancel button on the dialog."
+ end
+ if funcNameOrFunc == "CreateTerrainMaterialSelector" or funcNameOrFunc == t.CreateTerrainMaterialSelector then
+ return "Function CreateTerrainMaterialSelector. " ..
+ "Arguments: (size, position) " ..
+ "Side effect: Size and position are UDim2 values that specifies the selector's size and position. Both size and position are optional arguments. This method returns 3 objects (terrainSelectorGui, terrainSelected, forceTerrainSelection). terrainSelectorGui is just the gui object that we generate with this function, parent it as you like. TerrainSelected is a BindableEvent that is fired whenever a new terrain type is selected in the gui. ForceTerrainSelection is a function that takes an argument of Enum.CellMaterial and will force the gui to show that material as currently selected."
+ end
+ end
+
+return t
diff --git a/asset/backup/22 b/asset/backup/22
new file mode 100644
index 0000000..fcc8503
--- /dev/null
+++ b/asset/backup/22
@@ -0,0 +1,24 @@
+%22%
+local t = {}
+
+t.Foo =
+ function()
+ print("foo")
+ end
+
+t.Bar =
+ function()
+ print("bar")
+ end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "Foo" or funcNameOrFunc == t.Foo then
+ return "Function Foo. Arguments: None. Side effect: prints foo"
+ elseif funcNameOrFunc == "Bar" or funcNameOrFunc == t.Bar then
+ return "Function Bar. Arguments: None. Side effect: prints bar"
+ end
+ end
+
+return t
\ No newline at end of file
diff --git a/asset/backup/23 b/asset/backup/23
new file mode 100644
index 0000000..cbc47a1
--- /dev/null
+++ b/asset/backup/23
@@ -0,0 +1,1118 @@
+%23%
+local t = {}
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------JSON Functions Begin----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+
+ --JSON Encoder and Parser for Lua 5.1
+ --
+ --Copyright 2007 Shaun Brown (http://www.chipmunkav.com)
+ --All Rights Reserved.
+
+ --Permission is hereby granted, free of charge, to any person
+ --obtaining a copy of this software to deal in the Software without
+ --restriction, including without limitation the rights to use,
+ --copy, modify, merge, publish, distribute, sublicense, and/or
+ --sell copies of the Software, and to permit persons to whom the
+ --Software is furnished to do so, subject to the following conditions:
+
+ --The above copyright notice and this permission notice shall be
+ --included in all copies or substantial portions of the Software.
+ --If you find this software useful please give www.chipmunkav.com a mention.
+
+ --THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ --EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ --OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ --IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR
+ --ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
+ --CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ --CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+local string = string
+local math = math
+local table = table
+local error = error
+local tonumber = tonumber
+local tostring = tostring
+local type = type
+local setmetatable = setmetatable
+local pairs = pairs
+local ipairs = ipairs
+local assert = assert
+local Chipmunk = Chipmunk
+
+
+local StringBuilder = {
+ buffer = {}
+}
+
+function StringBuilder:New()
+ local o = {}
+ setmetatable(o, self)
+ self.__index = self
+ o.buffer = {}
+ return o
+end
+
+function StringBuilder:Append(s)
+ self.buffer[#self.buffer+1] = s
+end
+
+function StringBuilder:ToString()
+ return table.concat(self.buffer)
+end
+
+local JsonWriter = {
+ backslashes = {
+ ['\b'] = "\\b",
+ ['\t'] = "\\t",
+ ['\n'] = "\\n",
+ ['\f'] = "\\f",
+ ['\r'] = "\\r",
+ ['"'] = "\\\"",
+ ['\\'] = "\\\\",
+ ['/'] = "\\/"
+ }
+}
+
+function JsonWriter:New()
+ local o = {}
+ o.writer = StringBuilder:New()
+ setmetatable(o, self)
+ self.__index = self
+ return o
+end
+
+function JsonWriter:Append(s)
+ self.writer:Append(s)
+end
+
+function JsonWriter:ToString()
+ return self.writer:ToString()
+end
+
+function JsonWriter:Write(o)
+ local t = type(o)
+ if t == "nil" then
+ self:WriteNil()
+ elseif t == "boolean" then
+ self:WriteString(o)
+ elseif t == "number" then
+ self:WriteString(o)
+ elseif t == "string" then
+ self:ParseString(o)
+ elseif t == "table" then
+ self:WriteTable(o)
+ elseif t == "function" then
+ self:WriteFunction(o)
+ elseif t == "thread" then
+ self:WriteError(o)
+ elseif t == "userdata" then
+ self:WriteError(o)
+ end
+end
+
+function JsonWriter:WriteNil()
+ self:Append("null")
+end
+
+function JsonWriter:WriteString(o)
+ self:Append(tostring(o))
+end
+
+function JsonWriter:ParseString(s)
+ self:Append('"')
+ self:Append(string.gsub(s, "[%z%c\\\"/]", function(n)
+ local c = self.backslashes[n]
+ if c then return c end
+ return string.format("\\u%.4X", string.byte(n))
+ end))
+ self:Append('"')
+end
+
+function JsonWriter:IsArray(t)
+ local count = 0
+ local isindex = function(k)
+ if type(k) == "number" and k > 0 then
+ if math.floor(k) == k then
+ return true
+ end
+ end
+ return false
+ end
+ for k,v in pairs(t) do
+ if not isindex(k) then
+ return false, '{', '}'
+ else
+ count = math.max(count, k)
+ end
+ end
+ return true, '[', ']', count
+end
+
+function JsonWriter:WriteTable(t)
+ local ba, st, et, n = self:IsArray(t)
+ self:Append(st)
+ if ba then
+ for i = 1, n do
+ self:Write(t[i])
+ if i < n then
+ self:Append(',')
+ end
+ end
+ else
+ local first = true;
+ for k, v in pairs(t) do
+ if not first then
+ self:Append(',')
+ end
+ first = false;
+ self:ParseString(k)
+ self:Append(':')
+ self:Write(v)
+ end
+ end
+ self:Append(et)
+end
+
+function JsonWriter:WriteError(o)
+ error(string.format(
+ "Encoding of %s unsupported",
+ tostring(o)))
+end
+
+function JsonWriter:WriteFunction(o)
+ if o == Null then
+ self:WriteNil()
+ else
+ self:WriteError(o)
+ end
+end
+
+local StringReader = {
+ s = "",
+ i = 0
+}
+
+function StringReader:New(s)
+ local o = {}
+ setmetatable(o, self)
+ self.__index = self
+ o.s = s or o.s
+ return o
+end
+
+function StringReader:Peek()
+ local i = self.i + 1
+ if i <= #self.s then
+ return string.sub(self.s, i, i)
+ end
+ return nil
+end
+
+function StringReader:Next()
+ self.i = self.i+1
+ if self.i <= #self.s then
+ return string.sub(self.s, self.i, self.i)
+ end
+ return nil
+end
+
+function StringReader:All()
+ return self.s
+end
+
+local JsonReader = {
+ escapes = {
+ ['t'] = '\t',
+ ['n'] = '\n',
+ ['f'] = '\f',
+ ['r'] = '\r',
+ ['b'] = '\b',
+ }
+}
+
+function JsonReader:New(s)
+ local o = {}
+ o.reader = StringReader:New(s)
+ setmetatable(o, self)
+ self.__index = self
+ return o;
+end
+
+function JsonReader:Read()
+ self:SkipWhiteSpace()
+ local peek = self:Peek()
+ if peek == nil then
+ error(string.format(
+ "Nil string: '%s'",
+ self:All()))
+ elseif peek == '{' then
+ return self:ReadObject()
+ elseif peek == '[' then
+ return self:ReadArray()
+ elseif peek == '"' then
+ return self:ReadString()
+ elseif string.find(peek, "[%+%-%d]") then
+ return self:ReadNumber()
+ elseif peek == 't' then
+ return self:ReadTrue()
+ elseif peek == 'f' then
+ return self:ReadFalse()
+ elseif peek == 'n' then
+ return self:ReadNull()
+ elseif peek == '/' then
+ self:ReadComment()
+ return self:Read()
+ else
+ return nil
+ end
+end
+
+function JsonReader:ReadTrue()
+ self:TestReservedWord{'t','r','u','e'}
+ return true
+end
+
+function JsonReader:ReadFalse()
+ self:TestReservedWord{'f','a','l','s','e'}
+ return false
+end
+
+function JsonReader:ReadNull()
+ self:TestReservedWord{'n','u','l','l'}
+ return nil
+end
+
+function JsonReader:TestReservedWord(t)
+ for i, v in ipairs(t) do
+ if self:Next() ~= v then
+ error(string.format(
+ "Error reading '%s': %s",
+ table.concat(t),
+ self:All()))
+ end
+ end
+end
+
+function JsonReader:ReadNumber()
+ local result = self:Next()
+ local peek = self:Peek()
+ while peek ~= nil and string.find(
+ peek,
+ "[%+%-%d%.eE]") do
+ result = result .. self:Next()
+ peek = self:Peek()
+ end
+ result = tonumber(result)
+ if result == nil then
+ error(string.format(
+ "Invalid number: '%s'",
+ result))
+ else
+ return result
+ end
+end
+
+function JsonReader:ReadString()
+ local result = ""
+ assert(self:Next() == '"')
+ while self:Peek() ~= '"' do
+ local ch = self:Next()
+ if ch == '\\' then
+ ch = self:Next()
+ if self.escapes[ch] then
+ ch = self.escapes[ch]
+ end
+ end
+ result = result .. ch
+ end
+ assert(self:Next() == '"')
+ local fromunicode = function(m)
+ return string.char(tonumber(m, 16))
+ end
+ return string.gsub(
+ result,
+ "u%x%x(%x%x)",
+ fromunicode)
+end
+
+function JsonReader:ReadComment()
+ assert(self:Next() == '/')
+ local second = self:Next()
+ if second == '/' then
+ self:ReadSingleLineComment()
+ elseif second == '*' then
+ self:ReadBlockComment()
+ else
+ error(string.format(
+ "Invalid comment: %s",
+ self:All()))
+ end
+end
+
+function JsonReader:ReadBlockComment()
+ local done = false
+ while not done do
+ local ch = self:Next()
+ if ch == '*' and self:Peek() == '/' then
+ done = true
+ end
+ if not done and
+ ch == '/' and
+ self:Peek() == "*" then
+ error(string.format(
+ "Invalid comment: %s, '/*' illegal.",
+ self:All()))
+ end
+ end
+ self:Next()
+end
+
+function JsonReader:ReadSingleLineComment()
+ local ch = self:Next()
+ while ch ~= '\r' and ch ~= '\n' do
+ ch = self:Next()
+ end
+end
+
+function JsonReader:ReadArray()
+ local result = {}
+ assert(self:Next() == '[')
+ local done = false
+ if self:Peek() == ']' then
+ done = true;
+ end
+ while not done do
+ local item = self:Read()
+ result[#result+1] = item
+ self:SkipWhiteSpace()
+ if self:Peek() == ']' then
+ done = true
+ end
+ if not done then
+ local ch = self:Next()
+ if ch ~= ',' then
+ error(string.format(
+ "Invalid array: '%s' due to: '%s'",
+ self:All(), ch))
+ end
+ end
+ end
+ assert(']' == self:Next())
+ return result
+end
+
+function JsonReader:ReadObject()
+ local result = {}
+ assert(self:Next() == '{')
+ local done = false
+ if self:Peek() == '}' then
+ done = true
+ end
+ while not done do
+ local key = self:Read()
+ if type(key) ~= "string" then
+ error(string.format(
+ "Invalid non-string object key: %s",
+ key))
+ end
+ self:SkipWhiteSpace()
+ local ch = self:Next()
+ if ch ~= ':' then
+ error(string.format(
+ "Invalid object: '%s' due to: '%s'",
+ self:All(),
+ ch))
+ end
+ self:SkipWhiteSpace()
+ local val = self:Read()
+ result[key] = val
+ self:SkipWhiteSpace()
+ if self:Peek() == '}' then
+ done = true
+ end
+ if not done then
+ ch = self:Next()
+ if ch ~= ',' then
+ error(string.format(
+ "Invalid array: '%s' near: '%s'",
+ self:All(),
+ ch))
+ end
+ end
+ end
+ assert(self:Next() == "}")
+ return result
+end
+
+function JsonReader:SkipWhiteSpace()
+ local p = self:Peek()
+ while p ~= nil and string.find(p, "[%s/]") do
+ if p == '/' then
+ self:ReadComment()
+ else
+ self:Next()
+ end
+ p = self:Peek()
+ end
+end
+
+function JsonReader:Peek()
+ return self.reader:Peek()
+end
+
+function JsonReader:Next()
+ return self.reader:Next()
+end
+
+function JsonReader:All()
+ return self.reader:All()
+end
+
+function Encode(o)
+ local writer = JsonWriter:New()
+ writer:Write(o)
+ return writer:ToString()
+end
+
+function Decode(s)
+ local reader = JsonReader:New(s)
+ return reader:Read()
+end
+
+function Null()
+ return Null
+end
+-------------------- End JSON Parser ------------------------
+
+t.DecodeJSON = function(jsonString)
+ pcall(function() warn("RbxUtility.DecodeJSON is deprecated, please use Game:GetService('HttpService'):JSONDecode() instead.") end)
+
+ if type(jsonString) == "string" then
+ return Decode(jsonString)
+ end
+ print("RbxUtil.DecodeJSON expects string argument!")
+ return nil
+end
+
+t.EncodeJSON = function(jsonTable)
+ pcall(function() warn("RbxUtility.EncodeJSON is deprecated, please use Game:GetService('HttpService'):JSONEncode() instead.") end)
+ return Encode(jsonTable)
+end
+
+
+
+
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--------------------------------------------Terrain Utilities Begin-----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--makes a wedge at location x, y, z
+--sets cell x, y, z to default material if parameter is provided, if not sets cell x, y, z to be whatever material it previously w
+--returns true if made a wedge, false if the cell remains a block
+t.MakeWedge = function(x, y, z, defaultmaterial)
+ return game:GetService("Terrain"):AutoWedgeCell(x,y,z)
+end
+
+t.SelectTerrainRegion = function(regionToSelect, color, selectEmptyCells, selectionParent)
+ local terrain = game.Workspace:FindFirstChild("Terrain")
+ if not terrain then return end
+
+ assert(regionToSelect)
+ assert(color)
+
+ if not type(regionToSelect) == "Region3" then
+ error("regionToSelect (first arg), should be of type Region3, but is type",type(regionToSelect))
+ end
+ if not type(color) == "BrickColor" then
+ error("color (second arg), should be of type BrickColor, but is type",type(color))
+ end
+
+ -- frequently used terrain calls (speeds up call, no lookup necessary)
+ local GetCell = terrain.GetCell
+ local WorldToCellPreferSolid = terrain.WorldToCellPreferSolid
+ local CellCenterToWorld = terrain.CellCenterToWorld
+ local emptyMaterial = Enum.CellMaterial.Empty
+
+ -- container for all adornments, passed back to user
+ local selectionContainer = Instance.new("Model")
+ selectionContainer.Name = "SelectionContainer"
+ selectionContainer.Archivable = false
+ if selectionParent then
+ selectionContainer.Parent = selectionParent
+ else
+ selectionContainer.Parent = game.Workspace
+ end
+
+ local updateSelection = nil -- function we return to allow user to update selection
+ local currentKeepAliveTag = nil -- a tag that determines whether adorns should be destroyed
+ local aliveCounter = 0 -- helper for currentKeepAliveTag
+ local lastRegion = nil -- used to stop updates that do nothing
+ local adornments = {} -- contains all adornments
+ local reusableAdorns = {}
+
+ local selectionPart = Instance.new("Part")
+ selectionPart.Name = "SelectionPart"
+ selectionPart.Transparency = 1
+ selectionPart.Anchored = true
+ selectionPart.Locked = true
+ selectionPart.CanCollide = false
+ selectionPart.FormFactor = Enum.FormFactor.Custom
+ selectionPart.Size = Vector3.new(4.2,4.2,4.2)
+
+ local selectionBox = Instance.new("SelectionBox")
+
+ -- srs translation from region3 to region3int16
+ function Region3ToRegion3int16(region3)
+ local theLowVec = region3.CFrame.p - (region3.Size/2) + Vector3.new(2,2,2)
+ local lowCell = WorldToCellPreferSolid(terrain,theLowVec)
+
+ local theHighVec = region3.CFrame.p + (region3.Size/2) - Vector3.new(2,2,2)
+ local highCell = WorldToCellPreferSolid(terrain, theHighVec)
+
+ local highIntVec = Vector3int16.new(highCell.x,highCell.y,highCell.z)
+ local lowIntVec = Vector3int16.new(lowCell.x,lowCell.y,lowCell.z)
+
+ return Region3int16.new(lowIntVec,highIntVec)
+ end
+
+ -- helper function that creates the basis for a selection box
+ function createAdornment(theColor)
+ local selectionPartClone = nil
+ local selectionBoxClone = nil
+
+ if #reusableAdorns > 0 then
+ selectionPartClone = reusableAdorns[1]["part"]
+ selectionBoxClone = reusableAdorns[1]["box"]
+ table.remove(reusableAdorns,1)
+
+ selectionBoxClone.Visible = true
+ else
+ selectionPartClone = selectionPart:Clone()
+ selectionPartClone.Archivable = false
+
+ selectionBoxClone = selectionBox:Clone()
+ selectionBoxClone.Archivable = false
+
+ selectionBoxClone.Adornee = selectionPartClone
+ selectionBoxClone.Parent = selectionContainer
+
+ selectionBoxClone.Adornee = selectionPartClone
+
+ selectionBoxClone.Parent = selectionContainer
+ end
+
+ if theColor then
+ selectionBoxClone.Color = theColor
+ end
+
+ return selectionPartClone, selectionBoxClone
+ end
+
+ -- iterates through all current adornments and deletes any that don't have latest tag
+ function cleanUpAdornments()
+ for cellPos, adornTable in pairs(adornments) do
+
+ if adornTable.KeepAlive ~= currentKeepAliveTag then -- old news, we should get rid of this
+ adornTable.SelectionBox.Visible = false
+ table.insert(reusableAdorns,{part = adornTable.SelectionPart, box = adornTable.SelectionBox})
+ adornments[cellPos] = nil
+ end
+ end
+ end
+
+ -- helper function to update tag
+ function incrementAliveCounter()
+ aliveCounter = aliveCounter + 1
+ if aliveCounter > 1000000 then
+ aliveCounter = 0
+ end
+ return aliveCounter
+ end
+
+ -- finds full cells in region and adorns each cell with a box, with the argument color
+ function adornFullCellsInRegion(region, color)
+ local regionBegin = region.CFrame.p - (region.Size/2) + Vector3.new(2,2,2)
+ local regionEnd = region.CFrame.p + (region.Size/2) - Vector3.new(2,2,2)
+
+ local cellPosBegin = WorldToCellPreferSolid(terrain, regionBegin)
+ local cellPosEnd = WorldToCellPreferSolid(terrain, regionEnd)
+
+ currentKeepAliveTag = incrementAliveCounter()
+ for y = cellPosBegin.y, cellPosEnd.y do
+ for z = cellPosBegin.z, cellPosEnd.z do
+ for x = cellPosBegin.x, cellPosEnd.x do
+ local cellMaterial = GetCell(terrain, x, y, z)
+
+ if cellMaterial ~= emptyMaterial then
+ local cframePos = CellCenterToWorld(terrain, x, y, z)
+ local cellPos = Vector3int16.new(x,y,z)
+
+ local updated = false
+ for cellPosAdorn, adornTable in pairs(adornments) do
+ if cellPosAdorn == cellPos then
+ adornTable.KeepAlive = currentKeepAliveTag
+ if color then
+ adornTable.SelectionBox.Color = color
+ end
+ updated = true
+ break
+ end
+ end
+
+ if not updated then
+ local selectionPart, selectionBox = createAdornment(color)
+ selectionPart.Size = Vector3.new(4,4,4)
+ selectionPart.CFrame = CFrame.new(cframePos)
+ local adornTable = {SelectionPart = selectionPart, SelectionBox = selectionBox, KeepAlive = currentKeepAliveTag}
+ adornments[cellPos] = adornTable
+ end
+ end
+ end
+ end
+ end
+ cleanUpAdornments()
+ end
+
+
+ ------------------------------------- setup code ------------------------------
+ lastRegion = regionToSelect
+
+ if selectEmptyCells then -- use one big selection to represent the area selected
+ local selectionPart, selectionBox = createAdornment(color)
+
+ selectionPart.Size = regionToSelect.Size
+ selectionPart.CFrame = regionToSelect.CFrame
+
+ adornments.SelectionPart = selectionPart
+ adornments.SelectionBox = selectionBox
+
+ updateSelection =
+ function (newRegion, color)
+ if newRegion and newRegion ~= lastRegion then
+ lastRegion = newRegion
+ selectionPart.Size = newRegion.Size
+ selectionPart.CFrame = newRegion.CFrame
+ end
+ if color then
+ selectionBox.Color = color
+ end
+ end
+ else -- use individual cell adorns to represent the area selected
+ adornFullCellsInRegion(regionToSelect, color)
+ updateSelection =
+ function (newRegion, color)
+ if newRegion and newRegion ~= lastRegion then
+ lastRegion = newRegion
+ adornFullCellsInRegion(newRegion, color)
+ end
+ end
+
+ end
+
+ local destroyFunc = function()
+ updateSelection = nil
+ if selectionContainer then selectionContainer:Destroy() end
+ adornments = nil
+ end
+
+ return updateSelection, destroyFunc
+end
+
+-----------------------------Terrain Utilities End-----------------------------
+
+
+
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------Signal class begin------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--[[
+A 'Signal' object identical to the internal RBXScriptSignal object in it's public API and semantics. This function
+can be used to create "custom events" for user-made code.
+API:
+Method :connect( function handler )
+ Arguments: The function to connect to.
+ Returns: A new connection object which can be used to disconnect the connection
+ Description: Connects this signal to the function specified by |handler|. That is, when |fire( ... )| is called for
+ the signal the |handler| will be called with the arguments given to |fire( ... )|. Note, the functions
+ connected to a signal are called in NO PARTICULAR ORDER, so connecting one function after another does
+ NOT mean that the first will be called before the second as a result of a call to |fire|.
+
+Method :disconnect()
+ Arguments: None
+ Returns: None
+ Description: Disconnects all of the functions connected to this signal.
+
+Method :fire( ... )
+ Arguments: Any arguments are accepted
+ Returns: None
+ Description: Calls all of the currently connected functions with the given arguments.
+
+Method :wait()
+ Arguments: None
+ Returns: The arguments given to fire
+ Description: This call blocks until
+]]
+
+function t.CreateSignal()
+ local this = {}
+
+ local mBindableEvent = Instance.new('BindableEvent')
+ local mAllCns = {} --all connection objects returned by mBindableEvent::connect
+
+ --main functions
+ function this:connect(func)
+ if self ~= this then error("connect must be called with `:`, not `.`", 2) end
+ if type(func) ~= 'function' then
+ error("Argument #1 of connect must be a function, got a "..type(func), 2)
+ end
+ local cn = mBindableEvent.Event:connect(func)
+ mAllCns[cn] = true
+ local pubCn = {}
+ function pubCn:disconnect()
+ cn:disconnect()
+ mAllCns[cn] = nil
+ end
+ return pubCn
+ end
+ function this:disconnect()
+ if self ~= this then error("disconnect must be called with `:`, not `.`", 2) end
+ for cn, _ in pairs(mAllCns) do
+ cn:disconnect()
+ mAllCns[cn] = nil
+ end
+ end
+ function this:wait()
+ if self ~= this then error("wait must be called with `:`, not `.`", 2) end
+ return mBindableEvent.Event:wait()
+ end
+ function this:fire(...)
+ if self ~= this then error("fire must be called with `:`, not `.`", 2) end
+ mBindableEvent:Fire(...)
+ end
+
+ return this
+end
+
+------------------------------------------------- Sigal class End ------------------------------------------------------
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+-----------------------------------------------Create Function Begins---------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+--[[
+A "Create" function for easy creation of Roblox instances. The function accepts a string which is the classname of
+the object to be created. The function then returns another function which either accepts accepts no arguments, in
+which case it simply creates an object of the given type, or a table argument that may contain several types of data,
+in which case it mutates the object in varying ways depending on the nature of the aggregate data. These are the
+type of data and what operation each will perform:
+1) A string key mapping to some value:
+ Key-Value pairs in this form will be treated as properties of the object, and will be assigned in NO PARTICULAR
+ ORDER. If the order in which properties is assigned matter, then they must be assigned somewhere else than the
+ |Create| call's body.
+
+2) An integral key mapping to another Instance:
+ Normal numeric keys mapping to Instances will be treated as children if the object being created, and will be
+ parented to it. This allows nice recursive calls to Create to create a whole hierarchy of objects without a
+ need for temporary variables to store references to those objects.
+
+3) A key which is a value returned from Create.Event( eventname ), and a value which is a function function
+ The Create.E( string ) function provides a limited way to connect to signals inside of a Create hierarchy
+ for those who really want such a functionality. The name of the event whose name is passed to
+ Create.E( string )
+
+4) A key which is the Create function itself, and a value which is a function
+ The function will be run with the argument of the object itself after all other initialization of the object is
+ done by create. This provides a way to do arbitrary things involving the object from withing the create
+ hierarchy.
+ Note: This function is called SYNCHRONOUSLY, that means that you should only so initialization in
+ it, not stuff which requires waiting, as the Create call will block until it returns. While waiting in the
+ constructor callback function is possible, it is probably not a good design choice.
+ Note: Since the constructor function is called after all other initialization, a Create block cannot have two
+ constructor functions, as it would not be possible to call both of them last, also, this would be unnecessary.
+
+
+Some example usages:
+
+A simple example which uses the Create function to create a model object and assign two of it's properties.
+local model = Create'Model'{
+ Name = 'A New model',
+ Parent = game.Workspace,
+}
+
+
+An example where a larger hierarchy of object is made. After the call the hierarchy will look like this:
+Model_Container
+ |-ObjectValue
+ | |
+ | `-BoolValueChild
+ `-IntValue
+
+local model = Create'Model'{
+ Name = 'Model_Container',
+ Create'ObjectValue'{
+ Create'BoolValue'{
+ Name = 'BoolValueChild',
+ },
+ },
+ Create'IntValue'{},
+}
+
+
+An example using the event syntax:
+
+local part = Create'Part'{
+ [Create.E'Touched'] = function(part)
+ print("I was touched by "..part.Name)
+ end,
+}
+
+
+An example using the general constructor syntax:
+
+local model = Create'Part'{
+ [Create] = function(this)
+ print("Constructor running!")
+ this.Name = GetGlobalFoosAndBars(this)
+ end,
+}
+
+
+Note: It is also perfectly legal to save a reference to the function returned by a call Create, this will not cause
+ any unexpected behavior. EG:
+ local partCreatingFunction = Create'Part'
+ local part = partCreatingFunction()
+]]
+
+--the Create function need to be created as a functor, not a function, in order to support the Create.E syntax, so it
+--will be created in several steps rather than as a single function declaration.
+local function Create_PrivImpl(objectType)
+ if type(objectType) ~= 'string' then
+ error("Argument of Create must be a string", 2)
+ end
+ --return the proxy function that gives us the nice Create'string'{data} syntax
+ --The first function call is a function call using Lua's single-string-argument syntax
+ --The second function call is using Lua's single-table-argument syntax
+ --Both can be chained together for the nice effect.
+ return function(dat)
+ --default to nothing, to handle the no argument given case
+ dat = dat or {}
+
+ --make the object to mutate
+ local obj = Instance.new(objectType)
+
+ --stored constructor function to be called after other initialization
+ local ctor = nil
+
+ for k, v in pairs(dat) do
+ --add property
+ if type(k) == 'string' then
+ obj[k] = v
+
+
+ --add child
+ elseif type(k) == 'number' then
+ if type(v) ~= 'userdata' then
+ error("Bad entry in Create body: Numeric keys must be paired with children, got a: "..type(v), 2)
+ end
+ v.Parent = obj
+
+
+ --event connect
+ elseif type(k) == 'table' and k.__eventname then
+ if type(v) ~= 'function' then
+ error("Bad entry in Create body: Key `[Create.E\'"..k.__eventname.."\']` must have a function value\
+ got: "..tostring(v), 2)
+ end
+ obj[k.__eventname]:connect(v)
+
+
+ --define constructor function
+ elseif k == t.Create then
+ if type(v) ~= 'function' then
+ error("Bad entry in Create body: Key `[Create]` should be paired with a constructor function, \
+ got: "..tostring(v), 2)
+ elseif ctor then
+ --ctor already exists, only one allowed
+ error("Bad entry in Create body: Only one constructor function is allowed", 2)
+ end
+ ctor = v
+
+
+ else
+ error("Bad entry ("..tostring(k).." => "..tostring(v)..") in Create body", 2)
+ end
+ end
+
+ --apply constructor function if it exists
+ if ctor then
+ ctor(obj)
+ end
+
+ --return the completed object
+ return obj
+ end
+end
+
+--now, create the functor:
+t.Create = setmetatable({}, {__call = function(tb, ...) return Create_PrivImpl(...) end})
+
+--and create the "Event.E" syntax stub. Really it's just a stub to construct a table which our Create
+--function can recognize as special.
+t.Create.E = function(eventName)
+ return {__eventname = eventName}
+end
+
+-------------------------------------------------Create function End----------------------------------------------------
+
+
+
+
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------Documentation Begin-----------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+------------------------------------------------------------------------------------------------------------------------
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "DecodeJSON" or funcNameOrFunc == t.DecodeJSON then
+ return "Function DecodeJSON. " ..
+ "Arguments: (string). " ..
+ "Side effect: returns a table with all parsed JSON values"
+ end
+ if funcNameOrFunc == "EncodeJSON" or funcNameOrFunc == t.EncodeJSON then
+ return "Function EncodeJSON. " ..
+ "Arguments: (table). " ..
+ "Side effect: returns a string composed of argument table in JSON data format"
+ end
+ if funcNameOrFunc == "MakeWedge" or funcNameOrFunc == t.MakeWedge then
+ return "Function MakeWedge. " ..
+ "Arguments: (x, y, z, [default material]). " ..
+ "Description: Makes a wedge at location x, y, z. Sets cell x, y, z to default material if "..
+ "parameter is provided, if not sets cell x, y, z to be whatever material it previously was. "..
+ "Returns true if made a wedge, false if the cell remains a block "
+ end
+ if funcNameOrFunc == "SelectTerrainRegion" or funcNameOrFunc == t.SelectTerrainRegion then
+ return "Function SelectTerrainRegion. " ..
+ "Arguments: (regionToSelect, color, selectEmptyCells, selectionParent). " ..
+ "Description: Selects all terrain via a series of selection boxes within the regionToSelect " ..
+ "(this should be a region3 value). The selection box color is detemined by the color argument " ..
+ "(should be a brickcolor value). SelectionParent is the parent that the selection model gets placed to (optional)." ..
+ "SelectEmptyCells is bool, when true will select all cells in the " ..
+ "region, otherwise we only select non-empty cells. Returns a function that can update the selection," ..
+ "arguments to said function are a new region3 to select, and the adornment color (color arg is optional). " ..
+ "Also returns a second function that takes no arguments and destroys the selection"
+ end
+ if funcNameOrFunc == "CreateSignal" or funcNameOrFunc == t.CreateSignal then
+ return "Function CreateSignal. "..
+ "Arguments: None. "..
+ "Returns: The newly created Signal object. This object is identical to the RBXScriptSignal class "..
+ "used for events in Objects, but is a Lua-side object so it can be used to create custom events in"..
+ "Lua code. "..
+ "Methods of the Signal object: :connect, :wait, :fire, :disconnect. "..
+ "For more info you can pass the method name to the Help function, or view the wiki page "..
+ "for this library. EG: Help('Signal:connect')."
+ end
+ if funcNameOrFunc == "Signal:connect" then
+ return "Method Signal:connect. "..
+ "Arguments: (function handler). "..
+ "Return: A connection object which can be used to disconnect the connection to this handler. "..
+ "Description: Connectes a handler function to this Signal, so that when |fire| is called the "..
+ "handler function will be called with the arguments passed to |fire|."
+ end
+ if funcNameOrFunc == "Signal:wait" then
+ return "Method Signal:wait. "..
+ "Arguments: None. "..
+ "Returns: The arguments passed to the next call to |fire|. "..
+ "Description: This call does not return until the next call to |fire| is made, at which point it "..
+ "will return the values which were passed as arguments to that |fire| call."
+ end
+ if funcNameOrFunc == "Signal:fire" then
+ return "Method Signal:fire. "..
+ "Arguments: Any number of arguments of any type. "..
+ "Returns: None. "..
+ "Description: This call will invoke any connected handler functions, and notify any waiting code "..
+ "attached to this Signal to continue, with the arguments passed to this function. Note: The calls "..
+ "to handlers are made asynchronously, so this call will return immediately regardless of how long "..
+ "it takes the connected handler functions to complete."
+ end
+ if funcNameOrFunc == "Signal:disconnect" then
+ return "Method Signal:disconnect. "..
+ "Arguments: None. "..
+ "Returns: None. "..
+ "Description: This call disconnects all handlers attacched to this function, note however, it "..
+ "does NOT make waiting code continue, as is the behavior of normal Roblox events. This method "..
+ "can also be called on the connection object which is returned from Signal:connect to only "..
+ "disconnect a single handler, as opposed to this method, which will disconnect all handlers."
+ end
+ if funcNameOrFunc == "Create" then
+ return "Function Create. "..
+ "Arguments: A table containing information about how to construct a collection of objects. "..
+ "Returns: The constructed objects. "..
+ "Descrition: Create is a very powerfull function, whose description is too long to fit here, and "..
+ "is best described via example, please see the wiki page for a description of how to use it."
+ end
+ end
+
+--------------------------------------------Documentation Ends----------------------------------------------------------
+
+return t
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/asset/backup/24 b/asset/backup/24
new file mode 100644
index 0000000..fde5076
--- /dev/null
+++ b/asset/backup/24
@@ -0,0 +1,2208 @@
+%24%
+local t = {}
+
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+-- Do a line/plane intersection. The line starts at the camera. The plane is at y == 0, normal(0, 1, 0)
+--
+-- vectorPos - End point of the line.
+--
+-- Return:
+-- cellPos - The terrain cell intersection point if there is one, vectorPos if there isn't.
+-- hit - Whether there was a plane intersection. Value is true if there was, false if not.
+function PlaneIntersection(vectorPos)
+ local hit = false
+ local currCamera = game.Workspace.CurrentCamera
+ local startPos = Vector3.new(currCamera.CoordinateFrame.p.X, currCamera.CoordinateFrame.p.Y, currCamera.CoordinateFrame.p.Z)
+ local endPos = Vector3.new(vectorPos.X, vectorPos.Y, vectorPos.Z)
+ local normal = Vector3.new(0, 1, 0)
+ local p3 = Vector3.new(0, 0, 0)
+ local startEndDot = normal:Dot(endPos - startPos)
+ local cellPos = vectorPos
+ if startEndDot ~= 0 then
+ local t = normal:Dot(p3 - startPos) / startEndDot
+ if(t >=0 and t <=1) then
+ local intersection = ((endPos - startPos) * t) + startPos
+ cellPos = game.Workspace.Terrain:WorldToCell(intersection)
+ hit = true
+ end
+ end
+
+ return cellPos, hit
+end
+
+
+-- Purpose:
+-- Checks for terrain touched by the mouse hit.
+-- Will do a plane intersection if no terrain is touched.
+--
+-- mouse - Mouse to check the .hit for.
+--
+-- Return:
+-- cellPos - Cell position hit. Nil if none.
+function GetTerrainForMouse(mouse)
+ -- There was no target, so all it could be is a plane intersection.
+ -- Check for a plane intersection. If there isn't one then nothing will get hit.
+ local cell = game.Workspace.Terrain:WorldToCellPreferSolid(Vector3.new(mouse.hit.x, mouse.hit.y, mouse.hit.z))
+ local planeLoc = nil
+ -- If nothing was hit, do the plane intersection.
+ if 0 == game.Workspace.Terrain:GetCell(cell.X, cell.Y, cell.Z).Value then
+ cell = nil
+ planeLoc, hit = PlaneIntersection(Vector3.new(mouse.hit.x, mouse.hit.y, mouse.hit.z))
+ if hit then
+ cell = planeLoc
+ end
+ end
+ return cell
+end
+
+-- setup helper functions
+local insertBoundingBoxOverlapVector = Vector3.new(.3, .3, .3) -- we can still stamp if our character extrudes into the target stamping space by .3 or fewer units
+
+-- rotates a model by yAngle radians about the global y-axis
+local function rotatePartAndChildren(part, rotCF, offsetFromOrigin)
+ -- rotate this thing, if it's a part
+ if part:IsA("BasePart") then
+ part.CFrame = (rotCF * (part.CFrame - offsetFromOrigin)) + offsetFromOrigin
+ end
+
+ -- recursively do the same to all children
+ local partChildren = part:GetChildren()
+ for c = 1, #partChildren do rotatePartAndChildren(partChildren[c], rotCF, offsetFromOrigin) end
+end
+
+local function modelRotate(model, yAngle)
+ local rotCF = CFrame.Angles(0, yAngle, 0)
+ local offsetFromOrigin = model:GetModelCFrame().p
+
+ rotatePartAndChildren(model, rotCF, offsetFromOrigin)
+end
+
+
+local function collectParts(object, baseParts, scripts, decals)
+ if object:IsA("BasePart") then
+ baseParts[#baseParts+1] = object
+ elseif object:IsA("Script") then
+ scripts[#scripts+1] = object
+ elseif object:IsA("Decal") then
+ decals[#decals+1] = object
+ end
+
+ for index,child in pairs(object:GetChildren()) do
+ collectParts(child, baseParts, scripts, decals)
+ end
+end
+
+local function clusterPartsInRegion(startVector, endVector)
+ local cluster = game.Workspace:FindFirstChild("Terrain")
+
+ local startCell = cluster:WorldToCell(startVector)
+ local endCell = cluster:WorldToCell(endVector)
+
+ local startX = startCell.X
+ local startY = startCell.Y
+ local startZ = startCell.Z
+
+ local endX = endCell.X
+ local endY = endCell.Y
+ local endZ = endCell.Z
+
+ if startX < cluster.MaxExtents.Min.X then startX = cluster.MaxExtents.Min.X end
+ if startY < cluster.MaxExtents.Min.Y then startY = cluster.MaxExtents.Min.Y end
+ if startZ < cluster.MaxExtents.Min.Z then startZ = cluster.MaxExtents.Min.Z end
+
+ if endX > cluster.MaxExtents.Max.X then endX = cluster.MaxExtents.Max.X end
+ if endY > cluster.MaxExtents.Max.Y then endY = cluster.MaxExtents.Max.Y end
+ if endZ > cluster.MaxExtents.Max.Z then endZ = cluster.MaxExtents.Max.Z end
+
+ for x = startX, endX do
+ for y = startY, endY do
+ for z = startZ, endZ do
+ if (cluster:GetCell(x, y, z).Value) > 0 then return true end
+ end
+ end
+ end
+
+ return false
+end
+
+local function findSeatsInModel(parent, seatTable)
+ if not parent then return end
+
+ if parent.className == "Seat" or parent.className == "VehicleSeat" then
+ table.insert(seatTable, parent)
+ end
+ local myChildren = parent:GetChildren()
+ for j = 1, #myChildren do
+ findSeatsInModel(myChildren[j], seatTable)
+ end
+end
+
+local function setSeatEnabledStatus(model, isEnabled)
+ local seatList = {}
+ findSeatsInModel(model, seatList)
+
+ if isEnabled then
+ -- remove any welds called "SeatWeld" in seats
+ for i = 1, #seatList do
+ local nextSeat = seatList[i]:FindFirstChild("SeatWeld")
+ while nextSeat do nextSeat:Remove() nextSeat = seatList[i]:FindFirstChild("SeatWeld") end
+ end
+ else
+ -- put a weld called "SeatWeld" in every seat
+ -- this tricks it into thinking there's already someone sitting there, and it won't make you sit XD
+ for i = 1, #seatList do
+ local fakeWeld = Instance.new("Weld")
+ fakeWeld.Name = "SeatWeld"
+ fakeWeld.Parent = seatList[i]
+ end
+ end
+end
+
+local function autoAlignToFace(parts)
+ local aatf = parts:FindFirstChild("AutoAlignToFace")
+ if aatf then return aatf.Value else return false end
+end
+
+local function getClosestAlignedWorldDirection(aVector3InWorld)
+ local xDir = Vector3.new(1,0,0)
+ local yDir = Vector3.new(0,1,0)
+ local zDir = Vector3.new(0,0,1)
+ local xDot = aVector3InWorld.x * xDir.x + aVector3InWorld.y * xDir.y + aVector3InWorld.z * xDir.z
+ local yDot = aVector3InWorld.x * yDir.x + aVector3InWorld.y * yDir.y + aVector3InWorld.z * yDir.z
+ local zDot = aVector3InWorld.x * zDir.x + aVector3InWorld.y * zDir.y + aVector3InWorld.z * zDir.z
+
+ if math.abs(xDot) > math.abs(yDot) and math.abs(xDot) > math.abs(zDot) then
+ if xDot > 0 then
+ return 0
+ else
+ return 3
+ end
+ elseif math.abs(yDot) > math.abs(xDot) and math.abs(yDot) > math.abs(zDot) then
+ if yDot > 0 then
+ return 1
+ else
+ return 4
+ end
+ else
+ if zDot > 0 then
+ return 2
+ else
+ return 5
+ end
+ end
+end
+
+local function positionPartsAtCFrame3(aCFrame, currentParts)
+ local insertCFrame = nil
+ if not currentParts then return currentParts end
+ if currentParts and (currentParts:IsA("Model") or currentParts:IsA("Tool")) then
+ insertCFrame = currentParts:GetModelCFrame()
+ currentParts:TranslateBy(aCFrame.p - insertCFrame.p)
+ else
+ currentParts.CFrame = aCFrame
+ end
+ return currentParts
+end
+
+local function calcRayHitTime(rayStart, raySlope, intersectionPlane)
+ if math.abs(raySlope) < .01 then return 0 end -- 0 slope --> we just say intersection time is 0, and sidestep this dimension
+ return (intersectionPlane - rayStart) / raySlope
+end
+
+local function modelTargetSurface(partOrModel, rayStart, rayEnd)
+ if not partOrModel then
+ return 0
+ end
+
+ local modelCFrame = nil
+ local modelSize = nil
+ if partOrModel:IsA("Model") then
+ modelCFrame = partOrModel:GetModelCFrame()
+ modelSize = partOrModel:GetModelSize()
+ else
+ modelCFrame = partOrModel.CFrame
+ modelSize = partOrModel.Size
+ end
+
+ local mouseRayStart = modelCFrame:pointToObjectSpace(rayStart)
+ local mouseRayEnd = modelCFrame:pointToObjectSpace(rayEnd)
+ local mouseSlope = mouseRayEnd - mouseRayStart
+
+ local xPositive = 1
+ local yPositive = 1
+ local zPositive = 1
+ if mouseSlope.X > 0 then xPositive = -1 end
+ if mouseSlope.Y > 0 then yPositive = -1 end
+ if mouseSlope.Z > 0 then zPositive = -1 end
+
+ -- find which surface the transformed mouse ray hits (using modelSize):
+ local xHitTime = calcRayHitTime(mouseRayStart.X, mouseSlope.X, modelSize.X/2 * xPositive)
+ local yHitTime = calcRayHitTime(mouseRayStart.Y, mouseSlope.Y, modelSize.Y/2 * yPositive)
+ local zHitTime = calcRayHitTime(mouseRayStart.Z, mouseSlope.Z, modelSize.Z/2 * zPositive)
+
+ local hitFace = 0
+
+ --if xHitTime >= 0 and yHitTime >= 0 and zHitTime >= 0 then
+ if xHitTime > yHitTime then
+ if xHitTime > zHitTime then
+ -- xFace is hit
+ hitFace = 1*xPositive
+ else
+ -- zFace is hit
+ hitFace = 3*zPositive
+ end
+ else
+ if yHitTime > zHitTime then
+ -- yFace is hit
+ hitFace = 2*yPositive
+ else
+ -- zFace is hit
+ hitFace = 3*zPositive
+ end
+ end
+
+ return hitFace
+end
+
+local function getBoundingBox2(partOrModel)
+
+ -- for models, the bounding box is defined as the minimum and maximum individual part bounding boxes
+ -- relative to the first part's coordinate frame.
+ local minVec = Vector3.new(math.huge, math.huge, math.huge)
+ local maxVec = Vector3.new(-math.huge, -math.huge, -math.huge)
+
+ if partOrModel:IsA("Terrain") then
+ minVec = Vector3.new(-2, -2, -2)
+ maxVec = Vector3.new(2, 2, 2)
+ elseif partOrModel:IsA("BasePart") then
+ minVec = -0.5 * partOrModel.Size
+ maxVec = -minVec
+ else
+ maxVec = partOrModel:GetModelSize()*0.5
+ minVec = -maxVec
+ end
+
+ -- Adjust bounding box to reflect what the model or part author wants in terms of justification
+ local justifyValue = partOrModel:FindFirstChild("Justification")
+ if justifyValue ~= nil then
+ -- find the multiple of 4 that contains the model
+ justify = justifyValue.Value
+ two = Vector3.new(2, 2, 2)
+ actualBox = maxVec - minVec - Vector3.new(0.01, 0.01, 0.01)
+ containingGridBox = Vector3.new(4 * math.ceil(actualBox.x/4), 4 * math.ceil(actualBox.y/4), 4 * math.ceil(actualBox.z/4))
+ adjustment = containingGridBox - actualBox
+ minVec = minVec - 0.5 * adjustment * justify
+ maxVec = maxVec + 0.5 * adjustment * (two - justify)
+ end
+
+ return minVec, maxVec
+end
+
+local function getBoundingBoxInWorldCoordinates(partOrModel)
+ local minVec = Vector3.new(math.huge, math.huge, math.huge)
+ local maxVec = Vector3.new(-math.huge, -math.huge, -math.huge)
+
+ if partOrModel:IsA("BasePart") and not partOrModel:IsA("Terrain") then
+ vec1 = partOrModel.CFrame:pointToWorldSpace(-0.5 * partOrModel.Size)
+ vec2 = partOrModel.CFrame:pointToWorldSpace(0.5 * partOrModel.Size)
+ minVec = Vector3.new(math.min(vec1.X, vec2.X), math.min(vec1.Y, vec2.Y), math.min(vec1.Z, vec2.Z))
+ maxVec = Vector3.new(math.max(vec1.X, vec2.X), math.max(vec1.Y, vec2.Y), math.max(vec1.Z, vec2.Z))
+ elseif partOrModel:IsA("Terrain") then
+ -- we shouldn't have to deal with this case
+ --minVec = Vector3.new(-2, -2, -2)
+ --maxVec = Vector3.new(2, 2, 2)
+ else
+ vec1 = partOrModel:GetModelCFrame():pointToWorldSpace(-0.5 * partOrModel:GetModelSize())
+ vec2 = partOrModel:GetModelCFrame():pointToWorldSpace(0.5 * partOrModel:GetModelSize())
+ minVec = Vector3.new(math.min(vec1.X, vec2.X), math.min(vec1.Y, vec2.Y), math.min(vec1.Z, vec2.Z))
+ maxVec = Vector3.new(math.max(vec1.X, vec2.X), math.max(vec1.Y, vec2.Y), math.max(vec1.Z, vec2.Z))
+ end
+
+ return minVec, maxVec
+end
+
+local function getTargetPartBoundingBox(targetPart)
+ if targetPart.Parent:FindFirstChild("RobloxModel") ~= nil then
+ return getBoundingBox2(targetPart.Parent)
+ else
+ return getBoundingBox2(targetPart)
+ end
+end
+
+local function getMouseTargetCFrame(targetPart)
+ if targetPart.Parent:FindFirstChild("RobloxModel") ~= nil then
+ if targetPart.Parent:IsA("Tool") then return targetPart.Parent.Handle.CFrame
+ else return targetPart.Parent:GetModelCFrame() end
+ else
+ return targetPart.CFrame
+ end
+end
+
+local function isBlocker(part) -- returns whether or not we want to cancel the stamp because we're blocked by this part
+ if not part then return false end
+ if not part.Parent then return false end
+ if part:FindFirstChild("Humanoid") then return false end
+ if part:FindFirstChild("RobloxStamper") or part:FindFirstChild("RobloxModel") then return true end
+ if part:IsA("Part") and not part.CanCollide then return false end
+ if part == game.Lighting then return false end
+ return isBlocker(part.Parent)
+end
+
+-- helper function to determine if a character can be pushed upwards by a certain amount
+-- character is 5 studs tall, we'll check a 1.5 x 1.5 x 4.5 box around char, with center .5 studs below torsocenter
+local function spaceAboveCharacter(charTorso, newTorsoY, stampData)
+ local partsAboveChar = game.Workspace:FindPartsInRegion3(
+ Region3.new(Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) - Vector3.new(.75, 2.75, .75),
+ Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) + Vector3.new(.75, 1.75, .75)),
+ charTorso.Parent,
+ 100)
+
+ for j = 1, #partsAboveChar do
+ if partsAboveChar[j].CanCollide and not partsAboveChar[j]:IsDescendantOf(stampData.CurrentParts) then return false end
+ end
+
+ if clusterPartsInRegion(Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) - Vector3.new(.75, 2.75, .75),
+ Vector3.new(charTorso.Position.X, newTorsoY, charTorso.Position.Z) + Vector3.new(.75, 1.75, .75)) then
+ return false
+ end
+
+ return true
+end
+
+
+local function findConfigAtMouseTarget(Mouse, stampData)
+ -- *Critical Assumption* :
+ -- This function assumes the target CF axes are orthogonal with the target bounding box faces
+ -- And, it assumes the insert CF axes are orthongonal with the insert bounding box faces
+ -- Therefore, insertion will not work with angled faces on wedges or other "non-block" parts, nor
+ -- will it work for parts in a model that are not orthogonally aligned with the model's CF.
+
+ if not Mouse then return nil end -- This can happen sometimes, return if so
+ if not stampData then error("findConfigAtMouseTarget: stampData is nil") return nil end
+ if not stampData["CurrentParts"] then return nil end
+
+ local grid = 4.0
+ local admissibleConfig = false
+ local targetConfig = CFrame.new(0,0,0)
+
+ local minBB, maxBB = getBoundingBox2(stampData.CurrentParts)
+ local diagBB = maxBB - minBB
+
+ local insertCFrame
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ insertCFrame = stampData.CurrentParts:GetModelCFrame()
+ else
+ insertCFrame = stampData.CurrentParts.CFrame
+ end
+
+ if Mouse then
+ if stampData.CurrentParts:IsA("Tool") then
+ Mouse.TargetFilter = stampData.CurrentParts.Handle
+ else
+ Mouse.TargetFilter = stampData.CurrentParts
+ end
+ end
+
+ local hitPlane = false
+ local targetPart = nil
+ local success = pcall(function() targetPart = Mouse.Target end)
+
+ if not success then-- or targetPart == nil then
+ return admissibleConfig, targetConfig
+ end
+
+ local mouseHitInWorld = Vector3.new(0, 0, 0)
+ if Mouse then
+ mouseHitInWorld = Vector3.new(Mouse.Hit.x, Mouse.Hit.y, Mouse.Hit.z)
+ end
+
+ local cellPos = nil
+
+ -- Nothing was hit, so check for the default plane.
+ if nil == targetPart then
+ cellPos = GetTerrainForMouse(Mouse)
+ if nil == cellPos then
+ hitPlane = false
+ return admissibleConfig, targetConfig
+ else
+ targetPart = game.Workspace.Terrain
+ hitPlane = true
+ -- Take into account error that will occur.
+ cellPos = Vector3.new(cellPos.X - 1, cellPos.Y, cellPos.Z)
+ mouseHitInWorld = game.Workspace.Terrain:CellCenterToWorld(cellPos.x, cellPos.y, cellPos.z)
+ end
+ end
+
+ -- test mouse hit location
+ local minBBTarget, maxBBTarget = getTargetPartBoundingBox(targetPart)
+ local diagBBTarget = maxBBTarget - minBBTarget
+ local targetCFrame = getMouseTargetCFrame(targetPart)
+
+ if targetPart:IsA("Terrain") then
+ if not cluster then cluster = game.Workspace:FindFirstChild("Terrain") end
+ local cellID = cluster:WorldToCellPreferSolid(mouseHitInWorld)
+ if hitPlane then
+ cellID = cellPos
+ end
+
+ targetCFrame = CFrame.new(game.Workspace.Terrain:CellCenterToWorld(cellID.x, cellID.y, cellID.z))
+ end
+
+ local mouseHitInTarget = targetCFrame:pointToObjectSpace(mouseHitInWorld)
+ local targetVectorInWorld = Vector3.new(0,0,0)
+ if Mouse then
+ -- DON'T WANT THIS IN TERMS OF THE MODEL CFRAME! (.TargetSurface is in terms of the part CFrame, so this would break, right? [HotThoth])
+ -- (ideally, we would want to make the Mouse.TargetSurface a model-targetsurface instead, but for testing will be using the converse)
+ --targetVectorInWorld = targetCFrame:vectorToWorldSpace(Vector3.FromNormalId(Mouse.TargetSurface))
+ targetVectorInWorld = targetPart.CFrame:vectorToWorldSpace(Vector3.FromNormalId(Mouse.TargetSurface)) -- better, but model cframe would be best
+ --[[if targetPart.Parent:IsA("Model") then
+ local hitFace = modelTargetSurface(targetPart.Parent, Mouse.Hit.p, game.Workspace.CurrentCamera.CoordinateFrame.p) -- best, if you get it right
+ local WORLD_AXES = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)}
+ if hitFace > 0 then
+ targetVectorInWorld = targetCFrame:vectorToWorldSpace(WORLD_AXES[hitFace])
+ elseif hitFace < 0 then
+ targetVectorInWorld = targetCFrame:vectorToWorldSpace(-WORLD_AXES[-hitFace])
+ end
+ end]]
+ end
+
+ local targetRefPointInTarget
+ local clampToSurface
+
+ if getClosestAlignedWorldDirection(targetVectorInWorld) == 0 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ clampToSurface = Vector3.new(0,1,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 3 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, -1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(1, -1, -1))
+ clampToSurface = Vector3.new(0,1,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 1 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, 1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ clampToSurface = Vector3.new(1,0,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 4 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, 1, 1))
+ clampToSurface = Vector3.new(1,0,1)
+ elseif getClosestAlignedWorldDirection(targetVectorInWorld) == 2 then
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(-1, -1, 1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(-1, -1, -1))
+ clampToSurface = Vector3.new(1,1,0)
+ else
+ targetRefPointInTarget = targetCFrame:vectorToObjectSpace(Vector3.new(1, -1, -1))
+ insertRefPointInInsert = insertCFrame:vectorToObjectSpace(Vector3.new(1, -1, 1))
+ clampToSurface = Vector3.new(1,1,0)
+ end
+
+ targetRefPointInTarget = targetRefPointInTarget * (0.5 * diagBBTarget) + 0.5 * (maxBBTarget + minBBTarget)
+ insertRefPointInInsert = insertRefPointInInsert * (0.5 * diagBB) + 0.5 * (maxBB + minBB)
+
+ -- To Do: For cases that are not aligned to the world grid, account for the minimal rotation
+ -- needed to bring the Insert part(s) into alignment with the Target Part
+ -- Apply the rotation here
+
+ local delta = mouseHitInTarget - targetRefPointInTarget
+ local deltaClamped = Vector3.new(grid * math.modf(delta.x/grid), grid * math.modf(delta.y/grid), grid * math.modf(delta.z/grid))
+ deltaClamped = deltaClamped * clampToSurface
+ local targetTouchInTarget = deltaClamped + targetRefPointInTarget
+
+ local TargetTouchRelToWorld = targetCFrame:pointToWorldSpace(targetTouchInTarget)
+ local InsertTouchInWorld = insertCFrame:vectorToWorldSpace(insertRefPointInInsert)
+ local posInsertOriginInWorld = TargetTouchRelToWorld - InsertTouchInWorld
+
+ local x, y, z, R00, R01, R02, R10, R11, R12, R20, R21, R22 = insertCFrame:components()
+ targetConfig = CFrame.new(posInsertOriginInWorld.x, posInsertOriginInWorld.y, posInsertOriginInWorld.z, R00, R01, R02, R10, R11, R12, R20, R21, R22)
+ admissibleConfig = true
+
+ return admissibleConfig, targetConfig, getClosestAlignedWorldDirection(targetVectorInWorld)
+end
+
+local function truncateToCircleEighth(bigValue, littleValue)
+ local big = math.abs(bigValue)
+ local little = math.abs(littleValue)
+ local hypotenuse = math.sqrt(big*big + little*little)
+ local frac = little / hypotenuse
+
+ local bigSign = 1
+ local littleSign = 1
+ if bigValue < 0 then bigSign = -1 end
+ if littleValue < 0 then littleSign = -1 end
+
+ if frac > .382683432 then
+ -- between 22.5 and 45 degrees, so truncate to 45-degree tilt
+ return .707106781 * hypotenuse * bigSign, .707106781 * hypotenuse * littleSign
+ else
+ -- between 0 and 22.5 degrees, so truncate to 0-degree tilt
+ return hypotenuse * bigSign, 0
+ end
+end
+
+
+local function saveTheWelds(object, manualWeldTable, manualWeldParentTable)
+ if object:IsA("ManualWeld") or object:IsA("Rotate") then
+ table.insert(manualWeldTable, object)
+ table.insert(manualWeldParentTable, object.Parent)
+ else
+ local children = object:GetChildren()
+ for i = 1, #children do
+ saveTheWelds(children[i], manualWeldTable, manualWeldParentTable)
+ end
+ end
+end
+
+local function restoreTheWelds(manualWeldTable, manualWeldParentTable)
+ for i = 1, #manualWeldTable do
+ manualWeldTable[i].Parent = manualWeldParentTable[i]
+ end
+end
+
+t.CanEditRegion = function(partOrModel, EditRegion) -- todo: use model and stamper metadata
+ if not EditRegion then return true, false end
+
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(partOrModel)
+
+ if minBB.X < EditRegion.CFrame.p.X - EditRegion.Size.X/2 or
+ minBB.Y < EditRegion.CFrame.p.Y - EditRegion.Size.Y/2 or
+ minBB.Z < EditRegion.CFrame.p.Z - EditRegion.Size.Z/2 then
+ return false, false
+ end
+
+ if maxBB.X > EditRegion.CFrame.p.X + EditRegion.Size.X/2 or
+ maxBB.Y > EditRegion.CFrame.p.Y + EditRegion.Size.Y/2 or
+ maxBB.Z > EditRegion.CFrame.p.Z + EditRegion.Size.Z/2 then
+ return false, false
+ end
+
+ return true, false
+end
+
+t.GetStampModel = function(assetId, terrainShape, useAssetVersionId)
+ if assetId == 0 then
+ return nil, "No Asset"
+ end
+ if assetId < 0 then
+ return nil, "Negative Asset"
+ end
+
+ local function UnlockInstances(object)
+ if object:IsA("BasePart") then
+ object.Locked = false
+ end
+ for index,child in pairs(object:GetChildren()) do
+ UnlockInstances(child)
+ end
+ end
+
+ local function getClosestColorToTerrainMaterial(terrainValue)
+ if terrainValue == 1 then
+ return BrickColor.new("Bright green")
+ elseif terrainValue == 2 then
+ return BrickColor.new("Bright yellow")
+ elseif terrainValue == 3 then
+ return BrickColor.new("Bright red")
+ elseif terrainValue == 4 then
+ return BrickColor.new("Sand red")
+ elseif terrainValue == 5 then
+ return BrickColor.new("Black")
+ elseif terrainValue == 6 then
+ return BrickColor.new("Dark stone grey")
+ elseif terrainValue == 7 then
+ return BrickColor.new("Sand blue")
+ elseif terrainValue == 8 then
+ return BrickColor.new("Deep orange")
+ elseif terrainValue == 9 then
+ return BrickColor.new("Dark orange")
+ elseif terrainValue == 10 then
+ return BrickColor.new("Reddish brown")
+ elseif terrainValue == 11 then
+ return BrickColor.new("Light orange")
+ elseif terrainValue == 12 then
+ return BrickColor.new("Light stone grey")
+ elseif terrainValue == 13 then
+ return BrickColor.new("Sand green")
+ elseif terrainValue == 14 then
+ return BrickColor.new("Medium stone grey")
+ elseif terrainValue == 15 then
+ return BrickColor.new("Really red")
+ elseif terrainValue == 16 then
+ return BrickColor.new("Really blue")
+ elseif terrainValue == 17 then
+ return BrickColor.new("Bright blue")
+ else
+ return BrickColor.new("Bright green")
+ end
+ end
+
+ local function setupFakeTerrainPart(cellMat, cellType, cellOrient)
+ local newTerrainPiece = nil
+ if (cellType == 1 or cellType == 4) then newTerrainPiece = Instance.new("WedgePart") newTerrainPiece.formFactor = "Custom"
+ elseif (cellType == 2) then newTerrainPiece = Instance.new("CornerWedgePart")
+ else newTerrainPiece = Instance.new("Part") newTerrainPiece.formFactor = "Custom" end
+ newTerrainPiece.Name = "MegaClusterCube"
+ newTerrainPiece.Size = Vector3.new(4, 4, 4)
+ newTerrainPiece.BottomSurface = "Smooth"
+ newTerrainPiece.TopSurface = "Smooth"
+
+ -- can add decals or textures here if feeling particularly adventurous... for now, can make a table of look-up colors
+ newTerrainPiece.BrickColor = getClosestColorToTerrainMaterial(cellMat)
+
+ local sideways = 0
+ local flipped = math.pi
+ if cellType == 4 then sideways = -math.pi/2 end
+ if cellType == 2 or cellType == 3 then flipped = 0 end
+ newTerrainPiece.CFrame = CFrame.Angles(0, math.pi/2*cellOrient + flipped, sideways)
+
+ if cellType == 3 then
+ local inverseCornerWedgeMesh = Instance.new("SpecialMesh")
+ inverseCornerWedgeMesh.MeshType = "FileMesh"
+ inverseCornerWedgeMesh.MeshId = "http://www.roblox.com/asset/?id=66832495"
+ inverseCornerWedgeMesh.Scale = Vector3.new(2, 2, 2)
+ inverseCornerWedgeMesh.Parent = newTerrainPiece
+ end
+
+ local materialTag = Instance.new("Vector3Value")
+ materialTag.Value = Vector3.new(cellMat, cellType, cellOrient)
+ materialTag.Name = "ClusterMaterial"
+ materialTag.Parent = newTerrainPiece
+
+ return newTerrainPiece
+ end
+
+ -- This call will cause a "wait" until the data comes back
+ -- below we wait a max of 8 seconds before deciding to bail out on loading
+ local root
+ local loader
+ loading = true
+ if useAssetVersionId then
+ loader = coroutine.create(function()
+ root = game:GetService("InsertService"):LoadAssetVersion(assetId)
+ loading = false
+ end)
+ coroutine.resume(loader)
+ else
+ loader = coroutine.create(function()
+ root = game:GetService("InsertService"):LoadAsset(assetId)
+ loading = false
+ end)
+ coroutine.resume(loader)
+ end
+
+ local lastGameTime = 0
+ local totalTime = 0
+ local maxWait = 8
+ while loading and totalTime < maxWait do
+ lastGameTime = tick()
+ wait(1)
+ totalTime = totalTime + tick() - lastGameTime
+ end
+ loading = false
+
+ if totalTime >= maxWait then
+ return nil, "Load Time Fail"
+ end
+
+
+ if root == nil then
+ return nil, "Load Asset Fail"
+ end
+
+ if not root:IsA("Model") then
+ return nil, "Load Type Fail"
+ end
+
+ local instances = root:GetChildren()
+ if #instances == 0 then
+ return nil, "Empty Model Fail"
+ end
+
+ --Unlock all parts that are inserted, to make sure they are editable
+ UnlockInstances(root)
+
+ --Continue the insert process
+ root = root:GetChildren()[1]
+
+ --Examine the contents and decide what it looks like
+ for pos, instance in pairs(instances) do
+ if instance:IsA("Team") then
+ instance.Parent = game:GetService("Teams")
+ elseif instance:IsA("Sky") then
+ local lightingService = game:GetService("Lighting")
+ for index,child in pairs(lightingService:GetChildren()) do
+ if child:IsA("Sky") then
+ child:Remove();
+ end
+ end
+ instance.Parent = lightingService
+ return
+ end
+ end
+
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if root:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", root)
+ stringTag.Name = "RobloxModel"
+
+ if root:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", root)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ if terrainShape then
+ if root.Name == "MegaClusterCube" then
+ if (terrainShape == 6) then -- insert an autowedging tag
+ local autowedgeTag = Instance.new("BoolValue")
+ autowedgeTag.Name = "AutoWedge"
+ autowedgeTag.Parent = root
+ else
+ local clusterTag = root:FindFirstChild("ClusterMaterial")
+ if clusterTag then
+ if clusterTag:IsA("Vector3Value") then
+ root = setupFakeTerrainPart(clusterTag.Value.X, terrainShape, clusterTag.Value.Z)
+ else
+ root = setupFakeTerrainPart(clusterTag.Value, terrainShape, 0)
+ end
+ else
+ root = setupFakeTerrainPart(1, terrainShape, 0)
+ end
+ end
+ end
+ end
+
+ return root
+end
+
+
+
+t.SetupStamperDragger = function(modelToStamp, Mouse, StampInModel, AllowedStampRegion, StampFailedFunc)
+ if not modelToStamp then
+ error("SetupStamperDragger: modelToStamp (first arg) is nil! Should be a stamper model")
+ return nil
+ end
+ if not modelToStamp:IsA("Model") and not modelToStamp:IsA("BasePart") then
+ error("SetupStamperDragger: modelToStamp (first arg) is neither a Model or Part!")
+ return nil
+ end
+ if not Mouse then
+ error("SetupStamperDragger: Mouse (second arg) is nil! Should be a mouse object")
+ return nil
+ end
+ if not Mouse:IsA("Mouse") then
+ error("SetupStamperDragger: Mouse (second arg) is not of type Mouse!")
+ return nil
+ end
+
+ local stampInModel = nil
+ local allowedStampRegion = nil
+ local stampFailedFunc = nil
+ if StampInModel then
+ if not StampInModel:IsA("Model") then
+ error("SetupStamperDragger: StampInModel (optional third arg) is not of type 'Model'")
+ return nil
+ end
+ if not AllowedStampRegion then
+ error("SetupStamperDragger: AllowedStampRegion (optional fourth arg) is nil when StampInModel (optional third arg) is defined")
+ return nil
+ end
+ stampFailedFunc = StampFailedFunc
+ stampInModel = StampInModel
+ allowedStampRegion = AllowedStampRegion
+ end
+
+ -- Init all state variables
+ local gInitial90DegreeRotations = 0
+ local stampData = nil
+ local mouseTarget = nil
+
+ local errorBox = Instance.new("SelectionBox")
+ errorBox.Color = BrickColor.new("Bright red")
+ errorBox.Transparency = 0
+ errorBox.Archivable = false
+
+ -- for megacluster MEGA STAMPING
+ local adornPart = Instance.new("Part")
+ adornPart.Parent = nil
+ adornPart.formFactor = "Custom"
+ adornPart.Size = Vector3.new(4, 4, 4)
+ adornPart.CFrame = CFrame.new()
+ adornPart.Archivable = false
+
+ local adorn = Instance.new("SelectionBox")
+ adorn.Color = BrickColor.new("Toothpaste")
+ adorn.Adornee = adornPart
+ adorn.Visible = true
+ adorn.Transparency = 0
+ adorn.Name = "HighScalabilityStamperLine"
+ adorn.Archivable = false
+
+ local HighScalabilityLine = {}
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.End = nil
+ HighScalabilityLine.Adorn = adorn
+ HighScalabilityLine.AdornPart = adornPart
+ HighScalabilityLine.InternalLine = nil
+ HighScalabilityLine.NewHint = true
+
+ HighScalabilityLine.MorePoints = {nil, nil}
+ HighScalabilityLine.MoreLines = {nil, nil}
+ HighScalabilityLine.Dimensions = 1
+
+ local control = {}
+ local movingLock = false
+ local stampUpLock = false
+ local unstampableSurface = false
+ local mouseCons = {}
+ local keyCon = nil
+
+ local stamped = Instance.new("BoolValue")
+ stamped.Archivable = false
+ stamped.Value = false
+
+ local lastTarget = {}
+ lastTarget.TerrainOrientation = 0
+ lastTarget.CFrame = 0
+
+ local cellInfo = {}
+ cellInfo.Material = 1
+ cellInfo.clusterType = 0
+ cellInfo.clusterOrientation = 0
+
+ local function isMegaClusterPart()
+ if not stampData then return false end
+ if not stampData.CurrentParts then return false end
+
+ return ( stampData.CurrentParts:FindFirstChild("ClusterMaterial",true) or (stampData.CurrentParts.Name == "MegaClusterCube") )
+ end
+
+ local function DoHighScalabilityRegionSelect()
+ local megaCube = stampData.CurrentParts:FindFirstChild("MegaClusterCube")
+ if not megaCube then
+ if not stampData.CurrentParts.Name == "MegaClusterCube" then
+ return
+ else
+ megaCube = stampData.CurrentParts
+ end
+ end
+
+ HighScalabilityLine.End = megaCube.CFrame.p
+ local line = nil
+ local line2 = Vector3.new(0, 0, 0)
+ local line3 = Vector3.new(0, 0, 0)
+
+ if HighScalabilityLine.Dimensions == 1 then
+ -- extract the line from these positions and limit to a 2D plane made from 2 of the world axes
+ -- then use dominating axis to limit line to be at 45-degree intervals
+ -- will use this internal representation of the line for the actual stamping
+ line = (HighScalabilityLine.End - HighScalabilityLine.Start)
+
+ if math.abs(line.X) < math.abs(line.Y) then
+ if math.abs(line.X) < math.abs(line.Z) then
+ -- limit to Y/Z plane, domination unknown
+ local newY, newZ
+ if (math.abs(line.Y) > math.abs(line.Z)) then
+ newY, newZ = truncateToCircleEighth(line.Y, line.Z)
+ else
+ newZ, newY = truncateToCircleEighth(line.Z, line.Y)
+ end
+ line = Vector3.new(0, newY, newZ)
+ else
+ -- limit to X/Y plane, with Y dominating
+ local newY, newX = truncateToCircleEighth(line.Y, line.X)
+ line = Vector3.new(newX, newY, 0)
+ end
+ else
+ if math.abs(line.Y) < math.abs(line.Z) then
+ -- limit to X/Z plane, domination unknown
+ local newX, newZ
+ if math.abs(line.X) > math.abs(line.Z) then
+ newX, newZ = truncateToCircleEighth(line.X, line.Z)
+ else
+ newZ, newX = truncateToCircleEighth(line.Z, line.X)
+ end
+ line = Vector3.new(newX, 0, newZ)
+ else
+ -- limit to X/Y plane, with X dominating
+ local newX, newY = truncateToCircleEighth(line.X, line.Y)
+ line = Vector3.new(newX, newY, 0)
+ end
+ end
+ HighScalabilityLine.InternalLine = line
+
+ elseif HighScalabilityLine.Dimensions == 2 then
+ line = HighScalabilityLine.MoreLines[1]
+ line2 = HighScalabilityLine.End - HighScalabilityLine.MorePoints[1]
+
+ -- take out any component of line2 along line1, so you get perpendicular to line1 component
+ line2 = line2 - line.unit*line.unit:Dot(line2)
+
+ tempCFrame = CFrame.new(HighScalabilityLine.Start, HighScalabilityLine.Start + line)
+
+ -- then zero out whichever is the smaller component
+ local yAxis = tempCFrame:vectorToWorldSpace(Vector3.new(0, 1, 0))
+ local xAxis = tempCFrame:vectorToWorldSpace(Vector3.new(1, 0, 0))
+
+ local xComp = xAxis:Dot(line2)
+ local yComp = yAxis:Dot(line2)
+
+ if math.abs(yComp) > math.abs(xComp) then
+ line2 = line2 - xAxis * xComp
+ else
+ line2 = line2 - yAxis * yComp
+ end
+
+ HighScalabilityLine.InternalLine = line2
+
+ elseif HighScalabilityLine.Dimensions == 3 then
+ line = HighScalabilityLine.MoreLines[1]
+ line2 = HighScalabilityLine.MoreLines[2]
+ line3 = HighScalabilityLine.End - HighScalabilityLine.MorePoints[2]
+
+ -- zero out all components of previous lines
+ line3 = line3 - line.unit * line.unit:Dot(line3)
+ line3 = line3 - line2.unit * line2.unit:Dot(line3)
+
+ HighScalabilityLine.InternalLine = line3
+ end
+
+ -- resize the "line" graphic to be the correct size and orientation
+ tempCFrame = CFrame.new(HighScalabilityLine.Start, HighScalabilityLine.Start + line)
+
+ if HighScalabilityLine.Dimensions == 1 then -- faster calculation for line
+ HighScalabilityLine.AdornPart.Size = Vector3.new(4, 4, line.magnitude + 4)
+ HighScalabilityLine.AdornPart.CFrame = tempCFrame + tempCFrame:vectorToWorldSpace(Vector3.new(2, 2, 2) - HighScalabilityLine.AdornPart.Size/2)
+ else
+ local boxSize = tempCFrame:vectorToObjectSpace(line + line2 + line3)
+ HighScalabilityLine.AdornPart.Size = Vector3.new(4, 4, 4) + Vector3.new(math.abs(boxSize.X), math.abs(boxSize.Y), math.abs(boxSize.Z))
+ HighScalabilityLine.AdornPart.CFrame = tempCFrame + tempCFrame:vectorToWorldSpace(boxSize/2)
+ end
+
+ -- make player able to see this ish
+
+ local gui = nil
+ if game.Players["LocalPlayer"] then
+ gui = game.Players.LocalPlayer:FindFirstChild("PlayerGui")
+ if gui and gui:IsA("PlayerGui") then
+ if HighScalabilityLine.Dimensions == 1 and line.magnitude > 3 then -- don't show if mouse hasn't moved enough
+ HighScalabilityLine.Adorn.Parent = gui
+ elseif HighScalabilityLine.Dimensions > 1 then
+ HighScalabilityLine.Adorn.Parent = gui
+ end
+ end
+ end
+
+ if gui == nil then -- we are in studio
+ gui = game:GetService("CoreGui")
+ if HighScalabilityLine.Dimensions == 1 and line.magnitude > 3 then -- don't show if mouse hasn't moved enough
+ HighScalabilityLine.Adorn.Parent = gui
+ elseif HighScalabilityLine.Dimensions > 1 then
+ HighScalabilityLine.Adorn.Parent = gui
+ end
+ end
+ end
+
+
+ local function DoStamperMouseMove(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseMove: Mouse is nil")
+ return
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseMove: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return
+ end
+
+ -- There wasn't a target (no part or terrain), so check for plane intersection.
+ if not Mouse.Target then
+ local cellPos = GetTerrainForMouse(Mouse)
+ if nil == cellPos then
+ return
+ end
+ end
+
+ if not stampData then
+ return
+ end
+
+ -- don't move with dragger - will move in one step on mouse down
+ -- draw ghost at acceptable positions
+ configFound, targetCFrame, targetSurface = findConfigAtMouseTarget(Mouse, stampData)
+ if not configFound then
+ error("RbxStamper.DoStamperMouseMove No configFound, returning")
+ return
+ end
+
+ local numRotations = 0 -- update this according to how many rotations you need to get it to target surface
+ if autoAlignToFace(stampData.CurrentParts) and targetSurface ~= 1 and targetSurface ~= 4 then -- pre-rotate the flag or portrait so it's aligned correctly
+ if targetSurface == 3 then numRotations = 0 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 0 then numRotations = 2 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 5 then numRotations = 3 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ elseif targetSurface == 2 then numRotations = 1 - gInitial90DegreeRotations + autoAlignToFace(stampData.CurrentParts)
+ end
+ end
+
+ local ry = math.pi/2
+ gInitial90DegreeRotations = gInitial90DegreeRotations + numRotations
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry*numRotations, 0)
+ modelRotate(stampData.CurrentParts, ry*numRotations)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry*numRotations, 0) * stampData.CurrentParts.CFrame
+ end
+
+ -- CODE TO CHECK FOR DRAGGING GHOST PART INTO A COLLIDING STATE
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(stampData.CurrentParts)
+
+ -- need to offset by distance to be dragged
+ local currModelCFrame = nil
+ if stampData.CurrentParts:IsA("Model") then
+ currModelCFrame = stampData.CurrentParts:GetModelCFrame()
+ else
+ currModelCFrame = stampData.CurrentParts.CFrame
+ end
+
+ minBB = minBB + targetCFrame.p - currModelCFrame.p
+ maxBB = maxBB + targetCFrame.p - currModelCFrame.p
+
+ -- don't drag into terrain
+ if clusterPartsInRegion(minBB + insertBoundingBoxOverlapVector, maxBB - insertBoundingBoxOverlapVector) then
+ if lastTarget.CFrame then
+ if (stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)) then
+ local theClusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if theClusterMaterial:IsA("Vector3Value") then
+ local stampClusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if stampClusterMaterial then
+ stampClusterMaterial = clusterMat
+ end
+ end
+ end
+ end
+ return
+ end
+
+ -- if we are stamping a terrain part, make sure it goes on the grid! Otherwise preview block could be placed off grid, but stamped on grid
+ if isMegaClusterPart() then
+ local cellToStamp = game.Workspace.Terrain:WorldToCell(targetCFrame.p)
+ local newCFramePosition = game.Workspace.Terrain:CellCenterToWorld(cellToStamp.X, cellToStamp.Y, cellToStamp.Z)
+ local x, y, z, R00, R01, R02, R10, R11, R12, R20, R21, R22 = targetCFrame:components()
+ targetCFrame = CFrame.new(newCFramePosition.X,newCFramePosition.Y,newCFramePosition.Z,R00, R01, R02, R10, R11, R12, R20, R21, R22)
+ end
+
+ positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+ lastTarget.CFrame = targetCFrame -- successful positioning, so update 'dat cframe
+ if stampData.CurrentParts:FindFirstChild("ClusterMaterial", true) then
+ local clusterMat = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMat:IsA("Vector3Value") then
+ lastTarget.TerrainOrientation = clusterMat.Value.Z
+ end
+ end
+
+
+ -- auto break joints code
+ if Mouse and Mouse.Target and Mouse.Target.Parent then
+ local modelInfo = Mouse.Target:FindFirstChild("RobloxModel")
+ if not modelInfo then modelInfo = Mouse.Target.Parent:FindFirstChild("RobloxModel") end
+
+ local myModelInfo = stampData.CurrentParts:FindFirstChild("UnstampableFaces")
+
+ --if (modelInfo and modelInfo.Parent:FindFirstChild("UnstampableFaces")) or (modelInfo and myModelInfo) then -- need better targetSurface calcs
+ if (true) then
+ local breakingFaces = ""
+ local myBreakingFaces = ""
+ if modelInfo and modelInfo.Parent:FindFirstChild("UnstampableFaces") then breakingFaces = modelInfo.Parent.UnstampableFaces.Value end
+ if myModelInfo then myBreakingFaces = myModelInfo.Value end
+ local hitFace = 0
+
+ if modelInfo then hitFace = modelTargetSurface(modelInfo.Parent, game.Workspace.CurrentCamera.CoordinateFrame.p, Mouse.Hit.p) end
+
+ -- are we stamping TO an unstampable surface?
+ for bf in string.gmatch(breakingFaces, "[^,]+") do
+ if hitFace == tonumber(bf) then
+ -- return before we hit the JointsService code below!
+ unstampableSurface = true
+ game.JointsService:ClearJoinAfterMoveJoints() -- clear the JointsService cache
+ return
+ end
+ end
+
+ -- now we have to cast the ray back in the other direction to find the surface we're stamping FROM
+ hitFace = modelTargetSurface(stampData.CurrentParts, Mouse.Hit.p, game.Workspace.CurrentCamera.CoordinateFrame.p)
+
+ -- are we stamping WITH an unstampable surface?
+ for bf in string.gmatch(myBreakingFaces, "[^,]+") do
+ if hitFace == tonumber(bf) then
+ unstampableSurface = true
+ game.JointsService:ClearJoinAfterMoveJoints() -- clear the JointsService cache
+ return
+ end
+ end
+
+ -- just need to match breakingFace against targetSurface using rotation supplied by modelCFrame
+ -- targetSurface: 1 is top, 4 is bottom,
+ end
+ end
+
+ -- to show joints during the mouse move
+ unstampableSurface = false
+ game.JointsService:SetJoinAfterMoveInstance(stampData.CurrentParts)
+
+ -- most common mouse inactive error occurs here, so check mouse active one more time in a pcall
+ if not pcall(function()
+ if Mouse and Mouse.Target and Mouse.Target.Parent:FindFirstChild("RobloxModel") == nil then
+ return
+ else
+ return
+ end
+ end)
+ then
+ error("Error: RbxStamper.DoStamperMouseMove Mouse is nil on second check")
+ game.JointsService:ClearJoinAfterMoveJoints()
+ Mouse = nil
+ return
+ end
+
+ if Mouse and Mouse.Target and Mouse.Target.Parent:FindFirstChild("RobloxModel") == nil then
+ game.JointsService:SetJoinAfterMoveTarget(Mouse.Target)
+ else
+ game.JointsService:SetJoinAfterMoveTarget(nil)
+ end
+ game.JointsService:ShowPermissibleJoints()
+
+ -- here we allow for a line of high-scalability parts
+ if isMegaClusterPart() and HighScalabilityLine and HighScalabilityLine.Start then
+ DoHighScalabilityRegionSelect()
+ end
+ end
+
+ local function setupKeyListener(key, Mouse)
+ if control and control["Paused"] then return end -- don't do this if we have no stamp
+
+ key = string.lower(key)
+ if key == 'r' and not autoAlignToFace(stampData.CurrentParts) then -- rotate the model
+ gInitial90DegreeRotations = gInitial90DegreeRotations + 1
+
+ -- Update orientation value if this is a fake terrain part
+ local clusterValues = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterValues and clusterValues:IsA("Vector3Value") then
+ clusterValues.Value = Vector3.new(clusterValues.Value.X, clusterValues.Value.Y, (clusterValues.Value.Z + 1) % 4)
+ end
+
+ -- Rotate the parts or all the parts in the model
+ local ry = math.pi/2
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry, 0)
+ modelRotate(stampData.CurrentParts, ry)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry, 0) * stampData.CurrentParts.CFrame
+ end
+
+ -- After rotating, update the position
+ configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+ if configFound then
+ positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+
+ -- update everything else in MouseMove
+ DoStamperMouseMove(Mouse)
+ end
+ elseif key == 'c' then -- try to expand our high scalability dragger dimension
+ if HighScalabilityLine.InternalLine and HighScalabilityLine.InternalLine.magnitude > 0 and HighScalabilityLine.Dimensions < 3 then
+ HighScalabilityLine.MorePoints[HighScalabilityLine.Dimensions] = HighScalabilityLine.End
+ HighScalabilityLine.MoreLines[HighScalabilityLine.Dimensions] = HighScalabilityLine.InternalLine
+ HighScalabilityLine.Dimensions = HighScalabilityLine.Dimensions + 1
+ HighScalabilityLine.NewHint = true
+ end
+ end
+ end
+
+ keyCon = Mouse.KeyDown:connect(function(key) -- init key connection (keeping code close to func)
+ setupKeyListener(key, Mouse)
+ end)
+
+ local function resetHighScalabilityLine()
+ if HighScalabilityLine then
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.End = nil
+ HighScalabilityLine.InternalLine = nil
+ HighScalabilityLine.NewHint = true
+ end
+ end
+
+ local function flashRedBox()
+ local gui = game.CoreGui
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer:FindFirstChild("PlayerGui") then
+ gui = game.Players.LocalPlayer.PlayerGui
+ end
+ end
+ end
+ if not stampData["ErrorBox"] then return end
+
+ stampData.ErrorBox.Parent = gui
+ if stampData.CurrentParts:IsA("Tool") then
+ stampData.ErrorBox.Adornee = stampData.CurrentParts.Handle
+ else
+ stampData.ErrorBox.Adornee = stampData.CurrentParts
+ end
+
+ delay(0,function()
+ for i = 1, 3 do
+ if stampData["ErrorBox"] then stampData.ErrorBox.Visible = true end
+ wait(0.13)
+ if stampData["ErrorBox"] then stampData.ErrorBox.Visible = false end
+ wait(0.13)
+ end
+ if stampData["ErrorBox"] then
+ stampData.ErrorBox.Adornee = nil
+ stampData.ErrorBox.Parent = Tool
+ end
+ end)
+ end
+
+ local function DoStamperMouseDown(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseDown: Mouse is nil")
+ return
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseDown: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return
+ end
+ if not stampData then
+ return
+ end
+
+ if isMegaClusterPart() then
+ if Mouse and HighScalabilityLine then
+ local megaCube = stampData.CurrentParts:FindFirstChild("MegaClusterCube", true)
+ local terrain = game.Workspace.Terrain
+ if megaCube then
+ HighScalabilityLine.Dimensions = 1
+ local tempCell = terrain:WorldToCell(megaCube.CFrame.p)
+ HighScalabilityLine.Start = terrain:CellCenterToWorld(tempCell.X, tempCell.Y, tempCell.Z)
+ return
+ else
+ HighScalabilityLine.Dimensions = 1
+ local tempCell = terrain:WorldToCell(stampData.CurrentParts.CFrame.p)
+ HighScalabilityLine.Start = terrain:CellCenterToWorld(tempCell.X, tempCell.Y, tempCell.Z)
+ return
+ end
+ end
+ end
+ end
+
+ local function loadSurfaceTypes(part, surfaces)
+ part.TopSurface = surfaces[1]
+ part.BottomSurface = surfaces[2]
+ part.LeftSurface = surfaces[3]
+ part.RightSurface = surfaces[4]
+ part.FrontSurface = surfaces[5]
+ part.BackSurface = surfaces[6]
+ end
+
+ local function saveSurfaceTypes(part, myTable)
+ local tempTable = {}
+ tempTable[1] = part.TopSurface
+ tempTable[2] = part.BottomSurface
+ tempTable[3] = part.LeftSurface
+ tempTable[4] = part.RightSurface
+ tempTable[5] = part.FrontSurface
+ tempTable[6] = part.BackSurface
+
+ myTable[part] = tempTable
+ end
+
+ local function makeSurfaceUnjoinable(part, surface)
+ -- TODO: FILL OUT!
+ end
+
+ local function prepareModel(model)
+ if not model then return nil end
+
+ local gDesiredTrans = 0.7
+ local gStaticTrans = 1
+
+ local clone = model:Clone()
+ local scripts = {}
+ local parts = {}
+ local decals = {}
+
+ stampData = {}
+ stampData.DisabledScripts = {}
+ stampData.TransparencyTable = {}
+ stampData.MaterialTable = {}
+ stampData.CanCollideTable = {}
+ stampData.AnchoredTable = {}
+ stampData.ArchivableTable = {}
+ stampData.DecalTransparencyTable = {}
+ stampData.SurfaceTypeTable = {}
+
+ collectParts(clone, parts, scripts, decals)
+
+ if #parts <= 0 then return nil, "no parts found in modelToStamp" end
+
+ for index,script in pairs(scripts) do
+ if not(script.Disabled) then
+ script.Disabled = true
+ stampData.DisabledScripts[#stampData.DisabledScripts + 1] = script
+ end
+ end
+ for index, part in pairs(parts) do
+ stampData.TransparencyTable[part] = part.Transparency
+ part.Transparency = gStaticTrans + (1 - gStaticTrans) * part.Transparency
+ stampData.MaterialTable[part] = part.Material
+ part.Material = Enum.Material.Plastic
+ stampData.CanCollideTable[part] = part.CanCollide
+ part.CanCollide = false
+ stampData.AnchoredTable[part] = part.Anchored
+ part.Anchored = true
+ stampData.ArchivableTable[part] = part.Archivable
+ part.Archivable = false
+
+ saveSurfaceTypes(part, stampData.SurfaceTypeTable)
+
+ local fadeInDelayTime = 0.5
+ local transFadeInTime = 0.5
+ delay(0,function()
+ wait(fadeInDelayTime) -- give it some time to be completely transparent
+
+ local begTime = tick()
+ local currTime = begTime
+ while (currTime - begTime) < transFadeInTime and part and part:IsA("BasePart") and part.Transparency > gDesiredTrans do
+ local newTrans = 1 - (((currTime - begTime)/transFadeInTime) * (gStaticTrans - gDesiredTrans))
+ if stampData["TransparencyTable"] and stampData.TransparencyTable[part] then
+ part.Transparency = newTrans + (1 - newTrans) * stampData.TransparencyTable[part]
+ end
+ wait(0.03)
+ currTime = tick()
+ end
+ if part and part:IsA("BasePart") then
+ if stampData["TransparencyTable"] and stampData.TransparencyTable[part] then
+ part.Transparency = gDesiredTrans + (1 - gDesiredTrans) * stampData.TransparencyTable[part]
+ end
+ end
+ end)
+ end
+
+ for index, decal in pairs(decals) do
+ stampData.DecalTransparencyTable[decal] = decal.Transparency
+ decal.Transparency = gDesiredTrans + (1 - gDesiredTrans) * decal.Transparency
+ end
+
+ -- disable all seats
+ setSeatEnabledStatus(clone, true)
+ setSeatEnabledStatus(clone, false)
+
+ stampData.CurrentParts = clone
+
+ -- if auto-alignable, we enforce a pre-rotation to the canonical "0-frame"
+ if autoAlignToFace(clone) then
+ stampData.CurrentParts:ResetOrientationToIdentity()
+ gInitial90DegreeRotations = 0
+ else -- pre-rotate if necessary
+ local ry = gInitial90DegreeRotations * math.pi/2
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ --stampData.CurrentParts:Rotate(0, ry, 0)
+ modelRotate(stampData.CurrentParts, ry)
+ else
+ stampData.CurrentParts.CFrame = CFrame.fromEulerAnglesXYZ(0, ry, 0) * stampData.CurrentParts.CFrame
+ end
+ end
+
+ -- since we're cloning the old model instead of the new one, we will need to update the orientation based on the original value AND how many more
+ -- rotations we expect since then [either that or we need to store the just-stamped clusterMaterial.Value.Z somewhere]. This should fix the terrain rotation
+ -- issue (fingers crossed) [HotThoth]
+
+ local clusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMaterial and clusterMaterial:IsA("Vector3Value") then
+ clusterMaterial.Value = Vector3.new(clusterMaterial.Value.X, clusterMaterial.Value.Y, (clusterMaterial.Value.Z + gInitial90DegreeRotations) % 4)
+ end
+
+ -- After rotating, update the position
+ local configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+ if configFound then
+ stampData.CurrentParts = positionPartsAtCFrame3(targetCFrame, stampData.CurrentParts)
+ end
+
+ -- to show joints during the mouse move
+ game.JointsService:SetJoinAfterMoveInstance(stampData.CurrentParts)
+
+ return clone, parts
+ end
+
+ local function checkTerrainBlockCollisions(cellPos, checkHighScalabilityStamp)
+ local cellCenterToWorld = game.Workspace.Terrain.CellCenterToWorld
+ local cellCenter = cellCenterToWorld(game.Workspace.Terrain, cellPos.X, cellPos.Y, cellPos.Z)
+ local cellBlockingParts = game.Workspace:FindPartsInRegion3(Region3.new(cellCenter - Vector3.new(2, 2, 2) + insertBoundingBoxOverlapVector, cellCenter + Vector3.new(2, 2, 2) - insertBoundingBoxOverlapVector), stampData.CurrentParts, 100)
+
+ local skipThisCell = false
+
+ for b = 1, #cellBlockingParts do
+ if isBlocker(cellBlockingParts[b]) then skipThisCell = true break end
+ end
+
+ if not skipThisCell then
+ -- pop players up above any set cells
+ local alreadyPushedUp = {}
+ -- if no blocking model below, then see if stamping on top of a character
+ for b = 1, #cellBlockingParts do
+ if cellBlockingParts[b].Parent and
+ not alreadyPushedUp[cellBlockingParts[b].Parent] and
+ cellBlockingParts[b].Parent:FindFirstChild("Humanoid") and
+ cellBlockingParts[b].Parent:FindFirstChild("Humanoid"):IsA("Humanoid") then
+ -----------------------------------------------------------------------------------
+ local blockingPersonTorso = cellBlockingParts[b].Parent:FindFirstChild("Torso")
+ alreadyPushedUp[cellBlockingParts[b].Parent] = true
+
+ if blockingPersonTorso then
+ -- if so, let's push the person upwards so they pop on top of the stamped model/part (but only if there's space above them)
+ local newY = cellCenter.Y + 5
+ if spaceAboveCharacter(blockingPersonTorso, newY, stampData) then
+ blockingPersonTorso.CFrame = blockingPersonTorso.CFrame + Vector3.new(0, newY - blockingPersonTorso.CFrame.p.Y, 0)
+ else
+ -- if no space, we just skip this one
+ skipThisCell = true
+ break
+ end
+ end
+ -----------------------------------------------------------------------------------
+ end
+ end
+ end
+
+ if not skipThisCell then -- if we STILL aren't skipping... then we're good to go!
+ local canSetCell = true
+
+ if checkHighScalabilityStamp then -- check to see if cell is in region, if not we'll skip set
+ if allowedStampRegion then
+ local cellPos = cellCenterToWorld(game.Workspace.Terrain, cellPos.X, cellPos.Y, cellPos.Z)
+ if cellPos.X + 2 > allowedStampRegion.CFrame.p.X + allowedStampRegion.Size.X/2 then
+ canSetCell = false
+ elseif cellPos.X - 2 < allowedStampRegion.CFrame.p.X - allowedStampRegion.Size.X/2 then
+ canSetCell = false
+ elseif cellPos.Y + 2 > allowedStampRegion.CFrame.p.Y + allowedStampRegion.Size.Y/2 then
+ canSetCell = false
+ elseif cellPos.Y - 2 < allowedStampRegion.CFrame.p.Y - allowedStampRegion.Size.Y/2 then
+ canSetCell = false
+ elseif cellPos.Z + 2 > allowedStampRegion.CFrame.p.Z + allowedStampRegion.Size.Z/2 then
+ canSetCell = false
+ elseif cellPos.Z - 2 < allowedStampRegion.CFrame.p.Z - allowedStampRegion.Size.Z/2 then
+ canSetCell = false
+ end
+ end
+ end
+
+ return canSetCell
+ end
+ return false
+ end
+
+
+ local function ResolveMegaClusterStamp(checkHighScalabilityStamp)
+ local cellSet = false
+
+ local cluser = game.Workspace.Terrain
+
+ local line = HighScalabilityLine.InternalLine
+ local cMax = game.Workspace.Terrain.MaxExtents.Max
+ local cMin = game.Workspace.Terrain.MaxExtents.Min
+
+ local clusterMaterial = 1 -- default is grass
+ local clusterType = 0 -- default is brick
+ local clusterOrientation = 0 -- default is 0 rotation
+
+ local autoWedgeClusterParts = false
+ if stampData.CurrentParts:FindFirstChild("AutoWedge") then autoWedgeClusterParts = true end
+
+ if stampData.CurrentParts:FindFirstChild("ClusterMaterial", true) then
+ clusterMaterial = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ if clusterMaterial:IsA("Vector3Value") then
+ clusterType = clusterMaterial.Value.Y
+ clusterOrientation = clusterMaterial.Value.Z
+ clusterMaterial = clusterMaterial.Value.X
+ elseif clusterMaterial:IsA("IntValue") then
+ clusterMaterial = clusterMaterial.Value
+ end
+ end
+
+ if HighScalabilityLine.Adorn.Parent and HighScalabilityLine.Start and ((HighScalabilityLine.Dimensions > 1) or (line and line.magnitude > 0)) then
+ local startCell = game.Workspace.Terrain:WorldToCell(HighScalabilityLine.Start)
+ local xInc = {0,0,0}
+ local yInc = {0,0,0}
+ local zInc = {0,0,0}
+
+ local cluster = game.Workspace.Terrain
+
+ local incrementVect = {nil, nil, nil}
+ local stepVect = {Vector3.new(0, 0, 0), Vector3.new(0, 0, 0), Vector3.new(0, 0, 0)}
+
+ local worldAxes = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)}
+
+ local lines = {}
+ if HighScalabilityLine.Dimensions > 1 then table.insert(lines, HighScalabilityLine.MoreLines[1]) end
+ if line and line.magnitude > 0 then table.insert(lines, line) end
+ if HighScalabilityLine.Dimensions > 2 then table.insert(lines, HighScalabilityLine.MoreLines[2]) end
+
+ for i = 1, #lines do
+ lines[i] = Vector3.new(math.floor(lines[i].X+.5), math.floor(lines[i].Y+.5), math.floor(lines[i].Z+.5)) -- round to integers
+
+ if lines[i].X > 0 then xInc[i] = 1 elseif lines[i].X < 0 then xInc[i] = -1 end
+ if lines[i].Y > 0 then yInc[i] = 1 elseif lines[i].Y < 0 then yInc[i] = -1 end
+ if lines[i].Z > 0 then zInc[i] = 1 elseif lines[i].Z < 0 then zInc[i] = -1 end
+
+ incrementVect[i] = Vector3.new(xInc[i], yInc[i], zInc[i])
+ if incrementVect[i].magnitude < .9 then incrementVect[i] = nil end
+ end
+
+
+ if not lines[2] then lines[2] = Vector3.new(0, 0, 0) end
+ if not lines[3] then lines[3] = Vector3.new(0, 0, 0) end
+
+ local waterForceTag = stampData.CurrentParts:FindFirstChild("WaterForceTag", true)
+ local waterForceDirectionTag = stampData.CurrentParts:FindFirstChild("WaterForceDirectionTag", true)
+
+ while (stepVect[3].magnitude*4 <= lines[3].magnitude) do
+ local outerStepVectIndex = 1
+ while outerStepVectIndex < 4 do
+ stepVect[2] = Vector3.new(0, 0, 0)
+ while (stepVect[2].magnitude*4 <= lines[2].magnitude) do
+ local innerStepVectIndex = 1
+ while innerStepVectIndex < 4 do
+ stepVect[1] = Vector3.new(0, 0, 0)
+ while (stepVect[1].magnitude*4 <= lines[1].magnitude) do
+ local stepVectSum = stepVect[1] + stepVect[2] + stepVect[3]
+ local cellPos = Vector3int16.new(startCell.X + stepVectSum.X, startCell.Y + stepVectSum.Y, startCell.Z + stepVectSum.Z)
+ if cellPos.X >= cMin.X and cellPos.Y >= cMin.Y and cellPos.Z >= cMin.Z and cellPos.X < cMax.X and cellPos.Y < cMax.Y and cellPos.Z < cMax.Z then
+ -- check if overlaps player or part
+ local okToStampTerrainBlock = checkTerrainBlockCollisions(cellPos, checkHighScalabilityStamp)
+
+ if okToStampTerrainBlock then
+ if waterForceTag then
+ cluster:SetWaterCell(cellPos.X, cellPos.Y, cellPos.Z, Enum.WaterForce[waterForceTag.Value], Enum.WaterDirection[waterForceDirectionTag.Value])
+ else
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterMaterial, clusterType, clusterOrientation)
+ end
+ cellSet = true
+
+ -- auto-wedge it?
+ if (autoWedgeClusterParts) then
+ game.Workspace.Terrain:AutowedgeCells(Region3int16.new(Vector3int16.new(cellPos.x - 1, cellPos.y - 1, cellPos.z - 1),
+ Vector3int16.new(cellPos.x + 1, cellPos.y + 1, cellPos.z + 1)))
+ end
+ end
+ end
+ stepVect[1] = stepVect[1] + incrementVect[1]
+ end
+ if incrementVect[2] then
+ while innerStepVectIndex < 4 and worldAxes[innerStepVectIndex]:Dot(incrementVect[2]) == 0 do
+ innerStepVectIndex = innerStepVectIndex + 1
+ end
+ if innerStepVectIndex < 4 then
+ stepVect[2] = stepVect[2] + worldAxes[innerStepVectIndex] * worldAxes[innerStepVectIndex]:Dot(incrementVect[2])
+ end
+ innerStepVectIndex = innerStepVectIndex + 1
+ else
+ stepVect[2] = Vector3.new(1, 0, 0)
+ innerStepVectIndex = 4 -- skip all remaining loops
+ end
+ if (stepVect[2].magnitude*4 > lines[2].magnitude) then innerStepVectIndex = 4 end
+ end
+ end
+ if incrementVect[3] then
+ while outerStepVectIndex < 4 and worldAxes[outerStepVectIndex]:Dot(incrementVect[3]) == 0 do
+ outerStepVectIndex = outerStepVectIndex + 1
+ end
+ if outerStepVectIndex < 4 then
+ stepVect[3] = stepVect[3] + worldAxes[outerStepVectIndex] * worldAxes[outerStepVectIndex]:Dot(incrementVect[3])
+ end
+ outerStepVectIndex = outerStepVectIndex + 1
+ else -- skip all remaining loops
+ stepVect[3] = Vector3.new(1, 0, 0) outerStepVectIndex = 4
+ end
+ if (stepVect[3].magnitude*4 > lines[3].magnitude) then outerStepVectIndex = 4 end
+ end
+ end
+ end
+
+ -- and also get rid of any HighScalabilityLine stuff if it's there
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.Adorn.Parent = nil
+
+ -- Mark for undo.
+ if cellSet then
+ stampData.CurrentParts.Parent = nil
+ pcall(function() game:GetService("ChangeHistoryService"): SetWaypoint("StamperMulti") end)
+ end
+
+ return cellSet
+ end
+
+ local function DoStamperMouseUp(Mouse)
+ if not Mouse then
+ error("Error: RbxStamper.DoStamperMouseUp: Mouse is nil")
+ return false
+ end
+ if not Mouse:IsA("Mouse") then
+ error("Error: RbxStamper.DoStamperMouseUp: Mouse is of type", Mouse.className,"should be of type Mouse")
+ return false
+ end
+
+ if not stampData.Dragger then
+ error("Error: RbxStamper.DoStamperMouseUp: stampData.Dragger is nil")
+ return false
+ end
+
+ if not HighScalabilityLine then
+ return false
+ end
+
+ local checkHighScalabilityStamp = nil
+ if stampInModel then
+ local canStamp = nil
+ local isHSLPart = isMegaClusterPart()
+
+ if isHSLPart and
+ HighScalabilityLine and
+ HighScalabilityLine.Start and
+ HighScalabilityLine.InternalLine and
+ HighScalabilityLine.InternalLine.magnitude > 0 then -- we have an HSL line, test later
+ canStamp = true
+ checkHighScalabilityStamp = true
+ else
+ canStamp, checkHighScalabilityStamp = t.CanEditRegion(stampData.CurrentParts, allowedStampRegion)
+ end
+
+ if not canStamp then
+ if stampFailedFunc then
+ stampFailedFunc()
+ end
+ return false
+ end
+ end
+
+ -- if unstampable face, then don't let us stamp there!
+ if unstampableSurface then
+ flashRedBox()
+ return false
+ end
+
+ -- recheck if we can stamp, as we just moved part
+ canStamp, checkHighScalabilityStamp = t.CanEditRegion(stampData.CurrentParts, allowedStampRegion)
+ if not canStamp then
+ if stampFailedFunc then
+ stampFailedFunc()
+ end
+ return false
+ end
+
+ -- Prevent part from being stamped on top of a player
+
+ local minBB, maxBB = getBoundingBoxInWorldCoordinates(stampData.CurrentParts)
+
+ -- HotThoth's note: Now that above CurrentParts positioning has been commented out, to be truly correct, we would need to use the
+ -- value of configFound from the previous onStamperMouseMove call which moved the CurrentParts
+ -- Shouldn't this be true when lastTargetCFrame has been set and false otherwise?
+ configFound, targetCFrame = findConfigAtMouseTarget(Mouse, stampData)
+
+ if configFound and not HighScalabilityLine.Adorn.Parent then
+ if clusterPartsInRegion(minBB + insertBoundingBoxOverlapVector, maxBB - insertBoundingBoxOverlapVector) then
+ flashRedBox()
+ return false
+ end
+
+ local blockingParts = game.Workspace:FindPartsInRegion3(Region3.new(minBB + insertBoundingBoxOverlapVector,
+ maxBB - insertBoundingBoxOverlapVector),
+ stampData.CurrentParts,
+ 100)
+
+
+ for b = 1, #blockingParts do
+ if isBlocker(blockingParts[b]) then
+ flashRedBox()
+ return false
+ end
+ end
+
+ local alreadyPushedUp = {}
+ -- if no blocking model below, then see if stamping on top of a character
+ for b = 1, #blockingParts do
+ if blockingParts[b].Parent and
+ not alreadyPushedUp[blockingParts[b].Parent] and
+ blockingParts[b].Parent:FindFirstChild("Humanoid") and
+ blockingParts[b].Parent:FindFirstChild("Humanoid"):IsA("Humanoid") then
+ ---------------------------------------------------------------------------
+ local blockingPersonTorso = blockingParts[b].Parent:FindFirstChild("Torso")
+ alreadyPushedUp[blockingParts[b].Parent] = true
+
+ if blockingPersonTorso then
+ -- if so, let's push the person upwards so they pop on top of the stamped model/part (but only if there's space above them)
+ local newY = maxBB.Y + 3
+ if spaceAboveCharacter(blockingPersonTorso, newY, stampData) then
+ blockingPersonTorso.CFrame = blockingPersonTorso.CFrame + Vector3.new(0, newY - blockingPersonTorso.CFrame.p.Y, 0)
+ else
+ -- if no space, we just error
+ flashRedBox()
+ return false
+ end
+ end
+ ---------------------------------------------------------------------------
+ end
+ end
+
+ elseif (not configFound) and not (HighScalabilityLine.Start and HighScalabilityLine.Adorn.Parent) then -- if no config then only stamp if it's a real HSL!
+ resetHighScalabilityLine()
+ return false
+ end
+
+ -- something will be stamped! so set the "StampedSomething" toggle to true
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ if game.Players.LocalPlayer["Character"] then
+ local localChar = game.Players.LocalPlayer.Character
+ local stampTracker = localChar:FindFirstChild("StampTracker")
+ if stampTracker and not stampTracker.Value then
+ stampTracker.Value = true
+ end
+ end
+ end
+ end
+
+ -- if we drew a line of mega parts, stamp them out
+ if HighScalabilityLine.Start and HighScalabilityLine.Adorn.Parent and isMegaClusterPart() then
+ if ResolveMegaClusterStamp(checkHighScalabilityStamp) or checkHighScalabilityStamp then
+ -- kill the ghost part
+ stampData.CurrentParts.Parent = nil
+ return true
+ end
+ end
+
+ -- not High-Scalability-Line-Based, so behave normally [and get rid of any HSL stuff]
+ HighScalabilityLine.Start = nil
+ HighScalabilityLine.Adorn.Parent = nil
+
+ local cluster = game.Workspace.Terrain
+
+ -- if target point is in cluster, just use cluster:SetCell
+ if isMegaClusterPart() then
+ -- if targetCFrame is inside cluster, just set that cell to 1 and return
+ --local cellPos = cluster:WorldToCell(targetCFrame.p)
+
+ local cellPos
+ if stampData.CurrentParts:IsA("Model") then cellPos = cluster:WorldToCell(stampData.CurrentParts:GetModelCFrame().p)
+ else cellPos = cluster:WorldToCell(stampData.CurrentParts.CFrame.p) end
+
+ local cMax = game.Workspace.Terrain.MaxExtents.Max
+ local cMin = game.Workspace.Terrain.MaxExtents.Min
+
+ if checkTerrainBlockCollisions(cellPos, false) then
+
+ local clusterValues = stampData.CurrentParts:FindFirstChild("ClusterMaterial", true)
+ local waterForceTag = stampData.CurrentParts:FindFirstChild("WaterForceTag", true)
+ local waterForceDirectionTag = stampData.CurrentParts:FindFirstChild("WaterForceDirectionTag", true)
+
+ if cellPos.X >= cMin.X and cellPos.Y >= cMin.Y and cellPos.Z >= cMin.Z and cellPos.X < cMax.X and cellPos.Y < cMax.Y and cellPos.Z < cMax.Z then
+
+ if waterForceTag then
+ cluster:SetWaterCell(cellPos.X, cellPos.Y, cellPos.Z, Enum.WaterForce[waterForceTag.Value], Enum.WaterDirection[waterForceDirectionTag.Value])
+ elseif not clusterValues then
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, cellInfo.Material, cellInfo.clusterType, gInitial90DegreeRotations % 4)
+ elseif clusterValues:IsA("Vector3Value") then
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterValues.Value.X, clusterValues.Value.Y, clusterValues.Value.Z)
+ else
+ cluster:SetCell(cellPos.X, cellPos.Y, cellPos.Z, clusterValues.Value, 0, 0)
+ end
+
+ local autoWedgeClusterParts = false
+ if stampData.CurrentParts:FindFirstChild("AutoWedge") then autoWedgeClusterParts = true end
+
+ -- auto-wedge it
+ if (autoWedgeClusterParts) then
+ game.Workspace.Terrain:AutowedgeCells(
+ Region3int16.new(
+ Vector3int16.new(cellPos.x - 1, cellPos.y - 1, cellPos.z - 1),
+ Vector3int16.new(cellPos.x + 1, cellPos.y + 1, cellPos.z + 1)
+ )
+ )
+ end
+
+ -- kill the ghost part
+ stampData.CurrentParts.Parent = nil
+
+ -- Mark for undo. It has to happen here or the selection display will come back also.
+ pcall(function() game:GetService("ChangeHistoryService"):SetWaypoint("StamperSingle") end)
+ return true
+ end
+ else
+ -- you tried to stamp a HSL-single part where one does not belong!
+ flashRedBox()
+ return false
+ end
+ end
+
+ local function getPlayer()
+ if game:FindFirstChild("Players") then
+ if game.Players["LocalPlayer"] then
+ return game.Players.LocalPlayer
+ end
+ end
+ return nil
+ end
+
+
+ -- Post process: after positioning the part or model, restore transparency, material, anchored and collide states and create joints
+ if stampData.CurrentParts:IsA("Model") or stampData.CurrentParts:IsA("Tool") then
+ if stampData.CurrentParts:IsA("Model") then
+ -- Tyler's magical hack-code for allowing/preserving clones of both Surface and Manual Welds... just don't ask X<
+ local manualWeldTable = {}
+ local manualWeldParentTable = {}
+ saveTheWelds(stampData.CurrentParts, manualWeldTable, manualWeldParentTable)
+ stampData.CurrentParts:BreakJoints()
+ stampData.CurrentParts:MakeJoints()
+ restoreTheWelds(manualWeldTable, manualWeldParentTable)
+ end
+
+ -- if it's a model, we also want to fill in the playerID and playerName tags, if it has those (e.g. for the friend-only door)
+ playerIdTag = stampData.CurrentParts:FindFirstChild("PlayerIdTag")
+ playerNameTag = stampData.CurrentParts:FindFirstChild("PlayerNameTag")
+ if playerIdTag ~= nil then
+ tempPlayerValue = getPlayer()
+ if tempPlayerValue ~= nil then playerIdTag.Value = tempPlayerValue.userId end
+ end
+ if playerNameTag ~= nil then
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ tempPlayerValue = game.Players.LocalPlayer
+ if tempPlayerValue ~= nil then playerNameTag.Value = tempPlayerValue.Name end
+ end
+ end
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if stampData.CurrentParts:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag.Name = "RobloxModel"
+
+ if stampData.CurrentParts:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ else
+ stampData.CurrentParts:BreakJoints()
+ if stampData.CurrentParts:FindFirstChild("RobloxStamper") == nil then
+ local stringTag2 = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag2.Name = "RobloxStamper"
+ end
+ end
+
+ -- make sure all the joints are activated before restoring anchor states
+ if not createJoints then game.JointsService:CreateJoinAfterMoveJoints() end
+
+ -- Restore the original properties for all parts being stamped
+ for part, transparency in pairs(stampData.TransparencyTable) do
+ part.Transparency = transparency
+ end
+ for part, archivable in pairs(stampData.ArchivableTable) do
+ part.Archivable = archivable
+ end
+ for part, material in pairs(stampData.MaterialTable) do
+ part.Material = material
+ end
+ for part, collide in pairs(stampData.CanCollideTable) do
+ part.CanCollide = collide
+ end
+ for part, anchored in pairs(stampData.AnchoredTable) do
+ part.Anchored = anchored
+ end
+ for decal, transparency in pairs(stampData.DecalTransparencyTable) do
+ decal.Transparency = transparency
+ end
+
+ for part, surfaces in pairs(stampData.SurfaceTypeTable) do
+ loadSurfaceTypes(part, surfaces)
+ end
+
+ if isMegaClusterPart() then
+ stampData.CurrentParts.Transparency = 0
+ end
+
+ -- re-enable all seats
+ setSeatEnabledStatus(stampData.CurrentParts, true)
+
+ stampData.TransparencyTable = nil
+ stampData.ArchivableTable = nil
+ stampData.MaterialTable = nil
+ stampData.CanCollideTable = nil
+ stampData.AnchoredTable = nil
+ stampData.SurfaceTypeTable = nil
+
+ -- ...and tag all inserted models for subsequent origin identification
+ -- if no RobloxModel tag already exists, then add it.
+ if stampData.CurrentParts:FindFirstChild("RobloxModel") == nil then
+ local stringTag = Instance.new("BoolValue", stampData.CurrentParts)
+ stringTag.Name = "RobloxModel"
+ end
+
+ -- and make sure we don't delete it, now that it's not a ghost part
+ if ghostRemovalScript then ghostRemovalScript.Parent = nil end
+
+ --Re-enable the scripts
+ for index,script in pairs(stampData.DisabledScripts) do
+ script.Disabled = false
+ end
+
+ --Now that they are all marked enabled, reinsert them into the world so they start running
+ for index,script in pairs(stampData.DisabledScripts) do
+ local oldParent = script.Parent
+ script.Parent = nil
+ script:Clone().Parent = oldParent
+ end
+
+ -- clear out more data
+ stampData.DisabledScripts = nil
+ stampData.Dragger = nil
+ stampData.CurrentParts = nil
+
+ pcall(function() game:GetService("ChangeHistoryService"): SetWaypoint("StampedObject") end)
+ return true
+ end
+
+ local function pauseStamper()
+ for i = 1, #mouseCons do -- stop the mouse from doing anything
+ mouseCons[i]:disconnect()
+ mouseCons[i] = nil
+ end
+ mouseCons = {}
+
+ if stampData and stampData.CurrentParts then -- remove our ghost part
+ stampData.CurrentParts.Parent = nil
+ stampData.CurrentParts:Remove()
+ end
+
+ resetHighScalabilityLine()
+
+ game.JointsService:ClearJoinAfterMoveJoints()
+ end
+
+
+ local function prepareUnjoinableSurfaces(modelCFrame, parts, whichSurface)
+ local AXIS_VECTORS = {Vector3.new(1, 0, 0), Vector3.new(0, 1, 0), Vector3.new(0, 0, 1)} -- maybe last one is negative? TODO: check this!
+ local isPositive = 1
+ if whichSurface < 0 then isPositive = isPositive * -1 whichSurface = whichSurface*-1 end
+ local surfaceNormal = isPositive * modelCFrame:vectorToWorldSpace(AXIS_VECTORS[whichSurface])
+
+ for i = 1, #parts do
+ local currPart = parts[i]
+
+ -- now just need to find which surface of currPart most closely match surfaceNormal and then set that to Unjoinable
+ local surfaceNormalInLocalCoords = currPart.CFrame:vectorToObjectSpace(surfaceNormal)
+ if math.abs(surfaceNormalInLocalCoords.X) > math.abs(surfaceNormalInLocalCoords.Y) then
+ if math.abs(surfaceNormalInLocalCoords.X) > math.abs(surfaceNormalInLocalCoords.Z) then
+ if surfaceNormalInLocalCoords.X > 0 then currPart.RightSurface = "Unjoinable" else currPart.LeftSurface = "Unjoinable" end
+ else
+ if surfaceNormalInLocalCoords.Z > 0 then currPart.BackSurface = "Unjoinable" else currPart.FrontSurface = "Unjoinable" end
+ end
+ else
+ if math.abs(surfaceNormalInLocalCoords.Y) > math.abs(surfaceNormalInLocalCoords.Z) then
+ if surfaceNormalInLocalCoords.Y > 0 then currPart.TopSurface = "Unjoinable" else currPart.BottomSurface = "Unjoinable" end
+ else
+ if surfaceNormalInLocalCoords.Z > 0 then currPart.BackSurface = "Unjoinable" else currPart.FrontSurface = "Unjoinable" end
+ end
+ end
+ end
+ end
+
+ local function resumeStamper()
+ clone, parts = prepareModel(modelToStamp)
+
+ if not clone or not parts then
+ return
+ end
+
+ -- if we have unjoinable faces, then we want to change those surfaces to be Unjoinable
+ local unjoinableTag = clone:FindFirstChild("UnjoinableFaces", true)
+ if unjoinableTag then
+ for unjoinableSurface in string.gmatch(unjoinableTag.Value, "[^,]*") do
+ if tonumber(unjoinableSurface) then
+ if clone:IsA("Model") then
+ prepareUnjoinableSurfaces(clone:GetModelCFrame(), parts, tonumber(unjoinableSurface))
+ else
+ prepareUnjoinableSurfaces(clone.CFrame, parts, tonumber(unjoinableSurface))
+ end
+ end
+ end
+ end
+
+ stampData.ErrorBox = errorBox
+ if stampInModel then
+ clone.Parent = stampInModel
+ else
+ clone.Parent = game.Workspace
+ end
+
+ if clone:FindFirstChild("ClusterMaterial", true) then -- extract all info from vector
+ clusterMaterial = clone:FindFirstChild("ClusterMaterial", true)
+ if (clusterMaterial:IsA("Vector3Value")) then
+ cellInfo.Material = clusterMaterial.Value.X
+ cellInfo.clusterType = clusterMaterial.Value.Y
+ cellInfo.clusterOrientation = clusterMaterial.Value.Z
+ elseif clusterMaterial:IsA("IntValue") then
+ cellInfo.Material = clusterMaterial.Value
+ end
+ end
+
+ pcall(function() mouseTarget = Mouse.Target end)
+
+ if mouseTarget and mouseTarget.Parent:FindFirstChild("RobloxModel") == nil then
+ game.JointsService:SetJoinAfterMoveTarget(mouseTarget)
+ else
+ game.JointsService:SetJoinAfterMoveTarget(nil)
+ end
+ game.JointsService:ShowPermissibleJoints()
+
+ for index, object in pairs(stampData.DisabledScripts) do
+ if object.Name == "GhostRemovalScript" then
+ object.Parent = stampData.CurrentParts
+ end
+ end
+
+ stampData.Dragger = Instance.new("Dragger")
+
+ --Begin a movement by faking a MouseDown signal
+ stampData.Dragger:MouseDown(parts[1], Vector3.new(0,0,0), parts)
+ stampData.Dragger:MouseUp()
+
+ DoStamperMouseMove(Mouse)
+
+ table.insert(mouseCons,Mouse.Move:connect(function()
+ if movingLock or stampUpLock then return end
+ movingLock = true
+ DoStamperMouseMove(Mouse)
+ movingLock = false
+ end))
+
+ table.insert(mouseCons,Mouse.Button1Down:connect(function()
+ DoStamperMouseDown(Mouse)
+ end))
+
+ table.insert(mouseCons,Mouse.Button1Up:connect(function()
+ stampUpLock = true
+ while movingLock do wait() end
+ stamped.Value = DoStamperMouseUp(Mouse)
+ resetHighScalabilityLine()
+ stampUpLock = false
+ end))
+
+ stamped.Value = false
+ end
+
+ local function resetStamperState(newModelToStamp)
+
+ -- if we have a new model, swap it out
+ if newModelToStamp then
+ if not newModelToStamp:IsA("Model") and not newModelToStamp:IsA("BasePart") then
+ error("resetStamperState: newModelToStamp (first arg) is not nil, but not a model or part!")
+ end
+ modelToStamp = newModelToStamp
+ end
+
+ -- first clear our state
+ pauseStamper()
+ -- now lets load in the new model
+ resumeStamper()
+
+ end
+
+ -- load the model initially
+ resetStamperState()
+
+
+ -- setup the control table we pass back to the user
+ control.Stamped = stamped -- BoolValue that fires when user stamps
+ control.Paused = false
+
+ control.LoadNewModel = function(newStampModel) -- allows us to specify a new stamper model to be used with this stamper
+ if newStampModel and not newStampModel:IsA("Model") and not newStampModel:IsA("BasePart") then
+ error("Control.LoadNewModel: newStampModel (first arg) is not a Model or Part!")
+ return nil
+ end
+ resetStamperState(newStampModel)
+ end
+
+ control.ReloadModel = function() -- will automatically set stamper to get a new model of current model and start stamping with new model
+ resetStamperState()
+ end
+
+ control.Pause = function() -- temporarily stops stamping, use resume to start up again
+ if not control.Paused then
+ pauseStamper()
+ control.Paused = true
+ else
+ print("RbxStamper Warning: Tried to call Control.Pause() when already paused")
+ end
+ end
+
+ control.Resume = function() -- resumes stamping, if currently paused
+ if control.Paused then
+ resumeStamper()
+ control.Paused = false
+ else
+ print("RbxStamper Warning: Tried to call Control.Resume() without Pausing First")
+ end
+ end
+
+ control.ResetRotation = function() -- resets the model rotation so new models are at default orientation
+ -- gInitial90DegreeRotations = 0
+ -- Note: This function will not always work quite the way we want it to; we will have to build this out further so it works with
+ -- High-Scalability and with the new model orientation setting methods (model:ResetOrientationToIdentity()) [HotThoth]
+ end
+
+ control.Destroy = function() -- Stops current Stamp operation and destroys control construct
+ for i = 1, #mouseCons do
+ mouseCons[i]:disconnect()
+ mouseCons[i] = nil
+ end
+
+ if keyCon then
+ keyCon:disconnect()
+ end
+
+ game.JointsService:ClearJoinAfterMoveJoints()
+
+ if adorn then adorn:Destroy() end
+ if adornPart then adornPart:Destroy() end
+ if errorBox then errorBox:Destroy() end
+ if stampData then
+ if stampData["Dragger"] then
+ stampData.Dragger:Destroy()
+ end
+ if stampData.CurrentParts then
+ stampData.CurrentParts:Destroy()
+ end
+ end
+ if control and control["Stamped"] then
+ control.Stamped:Destroy()
+ end
+ control = nil
+ end
+
+ return control
+end
+
+t.Help =
+ function(funcNameOrFunc)
+ --input argument can be a string or a function. Should return a description (of arguments and expected side effects)
+ if funcNameOrFunc == "GetStampModel" or funcNameOrFunc == t.GetStampModel then
+ return "Function GetStampModel. Arguments: assetId, useAssetVersionId. assetId is the asset to load in, define useAssetVersionId as true if assetId is a version id instead of a relative assetId. Side effect: returns a model of the assetId, or a string with error message if something fails"
+ end
+ if funcNameOrFunc == "SetupStamperDragger" or funcNameOrFunc == t.SetupStamperDragger then
+ return "Function SetupStamperDragger. Side Effect: Creates 4x4 stamping mechanism for building out parts quickly. Arguments: ModelToStamp, Mouse, LegalStampCheckFunction. ModelToStamp should be a Model or Part, preferrably loaded from RbxStamper.GetStampModel and should have extents that are multiples of 4. Mouse should be a mouse object (obtained from things such as Tool.OnEquipped), used to drag parts around 'stamp' them out. LegalStampCheckFunction is optional, used as a callback with a table argument (table is full of instances about to be stamped). Function should return either true or false, false stopping the stamp action."
+ end
+ end
+
+return t
diff --git a/asset/backup/3 b/asset/backup/3
new file mode 100644
index 0000000..c99fc72
--- /dev/null
+++ b/asset/backup/3
@@ -0,0 +1 @@
+%3%
\ No newline at end of file
diff --git a/asset/backup/4 b/asset/backup/4
new file mode 100644
index 0000000..38dabe1
--- /dev/null
+++ b/asset/backup/4
@@ -0,0 +1,2379 @@
+%4%
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+--Include
+local Create = assert(LoadLibrary("RbxUtility")).Create
+
+
+-- A Few Script Globals
+local gui
+if script.Parent:FindFirstChild("ControlFrame") then
+ gui = script.Parent:FindFirstChild("ControlFrame")
+else
+ gui = script.Parent
+end
+
+local helpButton = nil
+local updateCameraDropDownSelection = nil
+local updateVideoCaptureDropDownSelection = nil
+local updateSmartCameraDropDownSelection = nil
+local updateTouchMovementDropDownSelection = nil
+local tweenTime = 0.2
+
+local mouseLockLookScreenUrl = "http://www.roblox.com/asset?id=54071825"
+local classicLookScreenUrl = "http://www.roblox.com/Asset?id=45915798"
+
+local hasGraphicsSlider = true
+local GraphicsQualityLevels = 10 -- how many levels we allow on graphics slider
+local recordingVideo = false
+
+local volumeFlagExists, volumeFlagValue = pcall(function () return settings():GetFFlag("VolumeControlInGameEnabled") end)
+local hasVolumeSlider = volumeFlagExists and volumeFlagValue
+
+local currentMenuSelection = nil
+local lastMenuSelection = {}
+
+local defaultPosition = UDim2.new(0,0,0,0)
+
+local centerDialogs = {}
+local mainShield = nil
+
+local testReport = false
+
+local inStudioMode = UserSettings().GameSettings:InStudioMode()
+-- REMOVE WHEN NOT TESTING
+-- inStudioMode = false
+
+local macClient = false
+local success, isMac = pcall(function() return not game.GuiService.IsWindows end)
+macClient = success and isMac
+-- REMOVE WHEN NOT TESTING
+--macClient = true
+
+local customCameraDefaultType = "Default (Classic)"
+local touchClient = false
+pcall(function() touchClient = game:GetService("UserInputService").TouchEnabled end)
+-- REMOVE WHEN NOT TESTING
+-- touchClient = true
+if touchClient then
+ hasGraphicsSlider = false
+ customCameraDefaultType = "Default (Follow)"
+end
+
+local function Color3I(r,g,b)
+ return Color3.new(r/255,g/255,b/255)
+end
+
+local function robloxLock(instance)
+ instance.RobloxLocked = true
+ children = instance:GetChildren()
+ if children then
+ for i, child in ipairs(children) do
+ robloxLock(child)
+ end
+ end
+end
+
+function resumeGameFunction(shield)
+ shield.Settings:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ delay(tweenTime,function()
+ shield.Visible = false
+ for i = 1, #centerDialogs do
+ centerDialogs[i].Visible = false
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ end
+ game.GuiService:RemoveCenterDialog(shield)
+ settingsButton.Active = true
+ currentMenuSelection = nil
+ lastMenuSelection = {}
+ pcall(function() game:GetService("UserInputService").OverrideMouseIconEnabled = false end)
+ end)
+end
+
+function goToMenu(container,menuName, moveDirection,size,position)
+ if type(menuName) ~= "string" then return end
+
+ table.insert(lastMenuSelection,currentMenuSelection)
+ if menuName == "GameMainMenu" then
+ lastMenuSelection = {}
+ end
+
+ local containerChildren = container:GetChildren()
+ local selectedMenu = false
+ for i = 1, #containerChildren do
+ if containerChildren[i].Name == menuName then
+ containerChildren[i].Visible = true
+ currentMenuSelection = {container = container,name = menuName, direction = moveDirection, lastSize = size}
+ selectedMenu = true
+ if size and position then
+ containerChildren[i]:TweenSizeAndPosition(size,position,Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif size then
+ containerChildren[i]:TweenSizeAndPosition(size,UDim2.new(0.5,-size.X.Offset/2,0.5,-size.Y.Offset/2),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ else
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end
+ else
+ if moveDirection == "left" then
+ containerChildren[i]:TweenPosition(UDim2.new(-1,-525,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "right" then
+ containerChildren[i]:TweenPosition(UDim2.new(1,525,0,0),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "up" then
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,-1,-400),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ elseif moveDirection == "down" then
+ containerChildren[i]:TweenPosition(UDim2.new(0,0,1,400),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end
+ delay(tweenTime,function()
+ containerChildren[i].Visible = false
+ end)
+ end
+ end
+end
+
+function resetLocalCharacter()
+ local player = game.Players.LocalPlayer
+ if player then
+ if player.Character and player.Character:FindFirstChild("Humanoid") then
+ player.Character.Humanoid.Health = 0
+ end
+ end
+end
+
+local function createTextButton(text,style,fontSize,buttonSize,buttonPosition)
+ local newTextButton = Instance.new("TextButton")
+ newTextButton.Font = Enum.Font.SourceSansBold
+ newTextButton.FontSize = fontSize
+ newTextButton.Size = buttonSize
+ newTextButton.Position = buttonPosition
+ newTextButton.Style = style
+ newTextButton.TextColor3 = Color3.new(1,1,1)
+ newTextButton.Text = text
+ return newTextButton
+end
+
+local function CreateTextButtons(frame, buttons, yPos, ySize)
+ if #buttons < 1 then
+ error("Must have more than one button")
+ end
+
+ local buttonNum = 1
+ local buttonObjs = {}
+
+ local function toggleSelection(button)
+ for i, obj in ipairs(buttonObjs) do
+ if obj == button then
+ obj.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ else
+ obj.Style = Enum.ButtonStyle.RobloxRoundButton
+ end
+ end
+ end
+
+ for i, obj in ipairs(buttons) do
+ local button = Instance.new("TextButton")
+ button.Name = "Button" .. buttonNum
+ button.Font = Enum.Font.SourceSansBold
+ button.FontSize = Enum.FontSize.Size18
+ button.AutoButtonColor = true
+ button.Style = Enum.ButtonStyle.RobloxRoundButton
+ button.Text = obj.Text
+ button.TextColor3 = Color3.new(1,1,1)
+ button.MouseButton1Click:connect(function() toggleSelection(button) obj.Function() end)
+ button.Parent = frame
+ button.ZIndex = 8
+ buttonObjs[buttonNum] = button
+
+ buttonNum = buttonNum + 1
+ end
+
+ toggleSelection(buttonObjs[1])
+
+ local numButtons = buttonNum-1
+
+ if numButtons == 1 then
+ frame.Button1.Position = UDim2.new(0.35, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.4,0,ySize.Scale, ySize.Offset)
+ elseif numButtons == 2 then
+ frame.Button1.Position = UDim2.new(0.1, 0, yPos.Scale, yPos.Offset)
+ frame.Button1.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+
+ frame.Button2.Position = UDim2.new(0.55, 0, yPos.Scale, yPos.Offset)
+ frame.Button2.Size = UDim2.new(.35,0, ySize.Scale, ySize.Offset)
+ elseif numButtons >= 3 then
+ local spacing = .1 / numButtons
+ local buttonSize = .9 / numButtons
+
+ buttonNum = 1
+ while buttonNum <= numButtons do
+ buttonObjs[buttonNum].Position = UDim2.new(spacing*buttonNum + (buttonNum-1) * buttonSize, 0, yPos.Scale, yPos.Offset)
+ buttonObjs[buttonNum].Size = UDim2.new(buttonSize, 0, ySize.Scale, ySize.Offset)
+ buttonNum = buttonNum + 1
+ end
+ end
+end
+
+function setRecordGui(recording, stopRecordButton, recordVideoButton)
+ if recording then
+ stopRecordButton.Visible = true
+ recordVideoButton.Text = "Stop Recording"
+ else
+ stopRecordButton.Visible = false
+ recordVideoButton.Text = "Record Video"
+ end
+end
+
+function recordVideoClick(recordVideoButton, stopRecordButton)
+ recordingVideo = not recordingVideo
+ setRecordGui(recordingVideo, stopRecordButton, recordVideoButton)
+end
+
+local currentlyToggling = false;
+local DevConsoleToggle = nil;
+
+delay(0, function()
+ DevConsoleToggle = gui:WaitForChild("ToggleDevConsole")
+end)
+
+function toggleDeveloperConsole()
+ if not DevConsoleToggle then
+ return
+ end
+
+ DevConsoleToggle:Invoke()
+end
+
+function backToGame(buttonClicked, shield, settingsButton)
+ buttonClicked.Parent.Parent.Parent.Parent.Visible = false
+ shield.Visible = false
+ for i = 1, #centerDialogs do
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ centerDialogs[i].Visible = false
+ end
+ centerDialogs = {}
+ game.GuiService:RemoveCenterDialog(shield)
+ settingsButton.Active = true
+end
+
+function setDisabledState(guiObject)
+ if not guiObject then return end
+
+ if guiObject:IsA("TextLabel") then
+ guiObject.TextTransparency = 0.9
+ elseif guiObject:IsA("TextButton") then
+ guiObject.TextTransparency = 0.9
+ guiObject.Active = false
+ else
+ if guiObject["ClassName"] then
+ print("setDisabledState() got object of unsupported type. object type is ",guiObject.ClassName)
+ end
+ end
+end
+
+local function createHelpDialog(baseZIndex)
+
+ if helpButton == nil then
+ if gui:FindFirstChild("TopLeftControl") and gui.TopLeftControl:FindFirstChild("Help") then
+ helpButton = gui.TopLeftControl.Help
+ elseif gui:FindFirstChild("BottomRightControl") and gui.BottomRightControl:FindFirstChild("Help") then
+ helpButton = gui.BottomRightControl.Help
+ end
+ end
+
+ local shield = Instance.new("Frame")
+ shield.Name = "HelpDialogShield"
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 2
+
+ local helpDialog = Instance.new("Frame")
+ helpDialog.Name = "HelpDialog"
+ helpDialog.Style = Enum.FrameStyle.DropShadow
+ helpDialog.Position = UDim2.new(.2, 0, .2, 0)
+ helpDialog.Size = UDim2.new(0.6, 0, 0.6, 0)
+ helpDialog.Active = true
+ helpDialog.Parent = shield
+ helpDialog.ZIndex = baseZIndex + 2
+
+ local titleLabel = Instance.new("TextLabel")
+ titleLabel.Name = "Title"
+ titleLabel.Text = "Keyboard & Mouse Controls"
+ titleLabel.Font = Enum.Font.SourceSansBold
+ titleLabel.FontSize = Enum.FontSize.Size36
+ titleLabel.Position = UDim2.new(0, 0, 0.025, 0)
+ titleLabel.Size = UDim2.new(1, 0, 0, 40)
+ titleLabel.TextColor3 = Color3.new(1,1,1)
+ titleLabel.BackgroundTransparency = 1
+ titleLabel.Parent = helpDialog
+ titleLabel.ZIndex = baseZIndex + 2
+
+ local buttonRow = Instance.new("Frame")
+ buttonRow.Name = "Buttons"
+ buttonRow.Position = UDim2.new(0.1, 0, .07, 40)
+ buttonRow.Size = UDim2.new(0.8, 0, 0, 45)
+ buttonRow.BackgroundTransparency = 1
+ buttonRow.Parent = helpDialog
+ buttonRow.ZIndex = baseZIndex + 2
+
+ local imageFrame = Instance.new("Frame")
+ imageFrame.Name = "ImageFrame"
+ imageFrame.Position = UDim2.new(0.05, 0, 0.075, 80)
+ imageFrame.Size = UDim2.new(0.9, 0, .9, -120)
+ imageFrame.BackgroundTransparency = 1
+ imageFrame.Parent = helpDialog
+ imageFrame.ZIndex = baseZIndex + 2
+
+ local layoutFrame = Instance.new("Frame")
+ layoutFrame.Name = "LayoutFrame"
+ layoutFrame.Position = UDim2.new(0.5, 0, 0, 0)
+ layoutFrame.Size = UDim2.new(1.5, 0, 1, 0)
+ layoutFrame.BackgroundTransparency = 1
+ layoutFrame.SizeConstraint = Enum.SizeConstraint.RelativeYY
+ layoutFrame.Parent = imageFrame
+ layoutFrame.ZIndex = baseZIndex + 2
+
+ local image = Instance.new("ImageLabel")
+ image.Name = "Image"
+ if UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ image.Image = mouseLockLookScreenUrl
+ else
+ image.Image = classicLookScreenUrl
+ end
+ image.Position = UDim2.new(-0.5, 0, 0, 0)
+ image.Size = UDim2.new(1, 0, 1, 0)
+ image.BackgroundTransparency = 1
+ image.Parent = layoutFrame
+ image.ZIndex = baseZIndex + 2
+
+ local buttons = {}
+ buttons[1] = {}
+ buttons[1].Text = "Look"
+ buttons[1].Function = function()
+ if UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ image.Image = mouseLockLookScreenUrl
+ else
+ image.Image = classicLookScreenUrl
+ end
+ end
+ buttons[2] = {}
+ buttons[2].Text = "Move"
+ buttons[2].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45915811"
+ end
+ buttons[3] = {}
+ buttons[3].Text = "Gear"
+ buttons[3].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45917596"
+ end
+ buttons[4] = {}
+ buttons[4].Text = "Zoom"
+ buttons[4].Function = function()
+ image.Image = "http://www.roblox.com/Asset?id=45915825"
+ end
+
+ CreateTextButtons(buttonRow, buttons, UDim.new(0, 0), UDim.new(1,0))
+
+ local devConsoleButton = Create'TextButton'{
+ Name = "DeveloperConsoleButton";
+ Text = "Log";
+ Size = UDim2.new(0,60,0,30);
+ Style = Enum.ButtonStyle.RobloxRoundButton;
+ Position = UDim2.new(1,-65,1,-35);
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ TextColor3 = Color3.new(1,1,1);
+ ZIndex = baseZIndex + 4;
+ BackgroundTransparency = 1;
+ Parent = helpDialog;
+ }
+
+ Create'TextLabel'{
+ Name = "DeveloperConsoleButton";
+ Text = "F9";
+ Size = UDim2.new(0,14,0,14);
+ Position = UDim2.new(1,-6,0, -2);
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size12;
+ TextColor3 = Color3.new(0,1,0);
+ ZIndex = baseZIndex + 4;
+ BackgroundTransparency = 1;
+ Parent = devConsoleButton;
+ }
+
+ waitForProperty(game.Players, "LocalPlayer")
+ game.Players.LocalPlayer:GetMouse().KeyDown:connect(function(key)
+ if string.byte(key) == 34 then --F9
+ toggleDeveloperConsole()
+ end
+ end)
+
+ devConsoleButton.MouseButton1Click:connect(function()
+ toggleDeveloperConsole()
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end)
+
+ -- set up listeners for type of mouse mode, but keep constructing gui at same time
+ delay(0, function()
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield,"Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle, "GameSettingsMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu, "CameraField")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField, "DropDownMenuButton")
+ gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField.DropDownMenuButton.Changed:connect(function(prop)
+ if prop ~= "Text" then return end
+ if buttonRow.Button1.Style == Enum.ButtonStyle.RobloxRoundDefaultButton then -- only change if this is the currently selected panel
+ if gui.UserSettingsShield.Settings.SettingsStyle.GameSettingsMenu.CameraField.DropDownMenuButton.Text == "Classic" then
+ image.Image = classicLookScreenUrl
+ else
+ image.Image = mouseLockLookScreenUrl
+ end
+ end
+ end)
+ end)
+
+
+ local okBtn = Instance.new("TextButton")
+ okBtn.Name = "OkBtn"
+ okBtn.Text = "OK"
+ okBtn.Modal = true
+ okBtn.Size = UDim2.new(0.3, 0, 0, 45)
+ okBtn.Position = UDim2.new(0.35, 0, .975, -50)
+ okBtn.Font = Enum.Font.SourceSansBold
+ okBtn.FontSize = Enum.FontSize.Size18
+ okBtn.BackgroundTransparency = 1
+ okBtn.TextColor3 = Color3.new(1,1,1)
+ okBtn.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ okBtn.ZIndex = baseZIndex + 2
+ okBtn.MouseButton1Click:connect(
+ function()
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end)
+ okBtn.Parent = helpDialog
+
+ robloxLock(shield)
+ return shield
+end
+
+local function createLeaveConfirmationMenu(baseZIndex,shield)
+ local frame = Instance.new("Frame")
+ frame.Name = "LeaveConfirmationMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+ frame.Position = UDim2.new(0,0,2,400)
+ frame.ZIndex = baseZIndex + 4
+
+ local yesButton = createTextButton("Leave",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,313,0.8,0))
+ yesButton.Name = "YesButton"
+ yesButton.ZIndex = baseZIndex + 4
+ yesButton.Parent = frame
+ yesButton.Modal = true
+ yesButton:SetVerb("Exit")
+
+ local noButton = createTextButton("Stay",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,90,0.8,0))
+ noButton.Name = "NoButton"
+ noButton.Parent = frame
+ noButton.ZIndex = baseZIndex + 4
+ noButton.MouseButton1Click:connect(function()
+ goToMenu(shield.Settings.SettingsStyle,"GameMainMenu","down",UDim2.new(0,525,0,430))
+ shield.Settings:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end)
+
+ local leaveText = Instance.new("TextLabel")
+ leaveText.Name = "LeaveText"
+ leaveText.Text = "Leave this game?"
+ leaveText.Size = UDim2.new(1,0,0.8,0)
+ leaveText.TextWrap = true
+ leaveText.TextColor3 = Color3.new(1,1,1)
+ leaveText.Font = Enum.Font.SourceSansBold
+ leaveText.FontSize = Enum.FontSize.Size36
+ leaveText.BackgroundTransparency = 1
+ leaveText.ZIndex = baseZIndex + 4
+ leaveText.Parent = frame
+
+ return frame
+end
+
+local function createResetConfirmationMenu(baseZIndex,shield)
+ local frame = Instance.new("Frame")
+ frame.Name = "ResetConfirmationMenu"
+ frame.BackgroundTransparency = 1
+ frame.Size = UDim2.new(1,0,1,0)
+ frame.Position = UDim2.new(0,0,2,400)
+ frame.ZIndex = baseZIndex + 4
+
+ local yesButton = createTextButton("Reset",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,313,0,280))
+ yesButton.Name = "YesButton"
+ yesButton.ZIndex = baseZIndex + 4
+ yesButton.Parent = frame
+ yesButton.Modal = true
+ yesButton.MouseButton1Click:connect(function()
+ resumeGameFunction(shield)
+ resetLocalCharacter()
+ end)
+
+ local noButton = createTextButton("Cancel",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,128,0,50),UDim2.new(0,90,0,280))
+ noButton.Name = "NoButton"
+ noButton.Parent = frame
+ noButton.ZIndex = baseZIndex + 4
+ noButton.MouseButton1Click:connect(function()
+ goToMenu(shield.Settings.SettingsStyle,"GameMainMenu","down",UDim2.new(0,525,0,430))
+ shield.Settings:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end)
+
+ local resetCharacterText = Instance.new("TextLabel")
+ resetCharacterText.Name = "ResetCharacterText"
+ resetCharacterText.Text = "Are you sure you want to reset your character?"
+ resetCharacterText.Size = UDim2.new(1,0,0.8,0)
+ resetCharacterText.TextWrap = true
+ resetCharacterText.TextColor3 = Color3.new(1,1,1)
+ resetCharacterText.Font = Enum.Font.SourceSansBold
+ resetCharacterText.FontSize = Enum.FontSize.Size36
+ resetCharacterText.BackgroundTransparency = 1
+ resetCharacterText.ZIndex = baseZIndex + 4
+ resetCharacterText.Parent = frame
+
+ local fineResetCharacterText = resetCharacterText:Clone()
+ fineResetCharacterText.Name = "FineResetCharacterText"
+ fineResetCharacterText.Text = "You will be put back on a spawn point"
+ fineResetCharacterText.Size = UDim2.new(0,303,0,18)
+ fineResetCharacterText.Position = UDim2.new(0, 109, 0, 215)
+ fineResetCharacterText.FontSize = Enum.FontSize.Size18
+ fineResetCharacterText.Parent = frame
+
+ return frame
+end
+
+local function createGameMainMenu(baseZIndex, shield)
+
+ local buttonTop = 54
+
+ local gameMainMenuFrame = Instance.new("Frame")
+ gameMainMenuFrame.Name = "GameMainMenu"
+ gameMainMenuFrame.BackgroundTransparency = 1
+ gameMainMenuFrame.Size = UDim2.new(1,0,1,0)
+ gameMainMenuFrame.ZIndex = baseZIndex + 4
+ gameMainMenuFrame.Parent = settingsFrame
+
+ -- GameMainMenu Children
+
+ -- RESUME GAME
+ local resumeGameButton = createTextButton("Resume Game",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ resumeGameButton.Name = "resumeGameButton"
+ resumeGameButton.ZIndex = baseZIndex + 4
+ resumeGameButton.Parent = gameMainMenuFrame
+ resumeGameButton.Modal = true
+ resumeGameButton.MouseButton1Click:connect(function() resumeGameFunction(shield) end)
+ buttonTop = buttonTop + 51
+
+ -- RESET CHARACTER
+ local resetButton = createTextButton("Reset Character",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ resetButton.Name = "ResetButton"
+ resetButton.ZIndex = baseZIndex + 4
+ resetButton.Parent = gameMainMenuFrame
+ buttonTop = buttonTop + 51
+
+ -- GAME SETTINGS
+ local gameSettingsButton = createTextButton("Game Settings",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ gameSettingsButton.Name = "SettingsButton"
+ gameSettingsButton.ZIndex = baseZIndex + 4
+ gameSettingsButton.Parent = gameMainMenuFrame
+ buttonTop = buttonTop + 51
+
+ -- HELP BUTTON
+ local robloxHelpButton = createTextButton("Help",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,164,0,50),UDim2.new(0,92,0,buttonTop))
+ robloxHelpButton.Name = "HelpButton"
+ robloxHelpButton.ZIndex = baseZIndex + 4
+ robloxHelpButton.Parent = gameMainMenuFrame
+ robloxHelpButton.Visible = not touchClient
+ if macClient or touchClient then
+ robloxHelpButton.Size = UDim2.new(0,340,0,50)
+ robloxHelpButton.FontSize = Enum.FontSize.Size24
+ end
+
+ helpButton = robloxHelpButton
+
+ local helpDialog = createHelpDialog(baseZIndex)
+ helpDialog.Parent = gui
+
+ helpButton.MouseButton1Click:connect(
+ function()
+ table.insert(centerDialogs,helpDialog)
+ game.GuiService:AddCenterDialog(helpDialog, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ helpDialog.Visible = true
+ mainShield.Visible = false
+ end,
+ --HideFunction
+ function()
+ helpDialog.Visible = false
+ end)
+ end)
+ helpButton.Active = true
+
+ -- SCREEN SHOT
+ local screenshotButton = createTextButton("Screenshot",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,168,0,50),UDim2.new(0,264,0,buttonTop))
+ screenshotButton.Name = "ScreenshotButton"
+ screenshotButton.ZIndex = baseZIndex + 4
+ screenshotButton.Parent = gameMainMenuFrame
+ screenshotButton.Visible = not macClient and not touchClient
+ screenshotButton:SetVerb("Screenshot")
+
+ if not touchClient then
+ buttonTop = buttonTop + 51
+ end
+
+ -- REPORT ABUSE
+ local reportAbuseButton = createTextButton("Report Abuse",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,164,0,50),UDim2.new(0,92,0,buttonTop))
+ reportAbuseButton.Name = "ReportAbuseButton"
+ reportAbuseButton.ZIndex = baseZIndex + 4
+ reportAbuseButton.Parent = gameMainMenuFrame
+ if macClient or touchClient then
+ reportAbuseButton.Size = UDim2.new(0,340,0,50)
+ reportAbuseButton.FontSize = Enum.FontSize.Size24
+ end
+
+ -- RECORD VIDEO
+ local recordVideoButton = createTextButton("Record Video",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,168,0,50),UDim2.new(0,264,0,buttonTop))
+ recordVideoButton.Name = "RecordVideoButton"
+ recordVideoButton.ZIndex = baseZIndex + 4
+ recordVideoButton.Parent = gameMainMenuFrame
+ recordVideoButton.Visible = not macClient and not touchClient
+ recordVideoButton:SetVerb("RecordToggle")
+
+ local stopRecordButton = Instance.new("ImageButton")
+ stopRecordButton.Name = "StopRecordButton"
+ stopRecordButton.BackgroundTransparency = 1
+ stopRecordButton.Image = "rbxasset://textures/ui/RecordStop.png"
+ stopRecordButton.Size = UDim2.new(0,59,0,27)
+ stopRecordButton:SetVerb("RecordToggle")
+
+ stopRecordButton.MouseButton1Click:connect(function() recordVideoClick(recordVideoButton, stopRecordButton) end)
+ stopRecordButton.Visible = false
+ stopRecordButton.Parent = gui
+ buttonTop = buttonTop + 51
+
+ -- LEAVE GAME
+ local leaveGameButton = createTextButton("Leave Game",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size24,UDim2.new(0,340,0,50),UDim2.new(0.5,-170,0,buttonTop))
+ leaveGameButton.Name = "LeaveGameButton"
+ leaveGameButton.ZIndex = baseZIndex + 4
+ leaveGameButton.Parent = gameMainMenuFrame
+
+ return gameMainMenuFrame
+end
+
+local function createGameSettingsMenu(baseZIndex, shield)
+ local gameSettingsMenuFrame = Instance.new("Frame")
+ gameSettingsMenuFrame.Name = "GameSettingsMenu"
+ gameSettingsMenuFrame.BackgroundTransparency = 1
+ gameSettingsMenuFrame.Size = UDim2.new(1,0,1,0)
+ gameSettingsMenuFrame.ZIndex = baseZIndex + 4
+
+ local itemTop = 0
+ if game:GetService("GuiService"):GetScreenResolution().y <= 500 then
+ itemTop = 50
+ end
+ ----------------------------------------------------------------------------------------------------
+ -- C A M E R A C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+
+ if not touchClient then
+ local cameraLabel = Instance.new("TextLabel")
+ cameraLabel.Name = "CameraLabel"
+ cameraLabel.Text = "Character & Camera Controls"
+ cameraLabel.Font = Enum.Font.SourceSansBold
+ cameraLabel.FontSize = Enum.FontSize.Size18
+ cameraLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ cameraLabel.Size = UDim2.new(0,224,0,18)
+ cameraLabel.TextColor3 = Color3I(255,255,255)
+ cameraLabel.TextXAlignment = Enum.TextXAlignment.Left
+ cameraLabel.BackgroundTransparency = 1
+ cameraLabel.ZIndex = baseZIndex + 4
+ cameraLabel.Parent = gameSettingsMenuFrame
+
+ local mouseLockLabel = game.CoreGui.RobloxGui:FindFirstChild("MouseLockLabel",true)
+
+ local enumItems = Enum.ControlMode:GetEnumItems()
+ local enumNames = {}
+ local enumNameToItem = {}
+ for i,obj in ipairs(enumItems) do
+ enumNames[i] = obj.Name
+ enumNameToItem[obj.Name] = obj
+ end
+
+ local cameraDropDown
+ cameraDropDown, updateCameraDropDownSelection = RbxGui.CreateDropDownMenu(enumNames,
+ function(text)
+ UserSettings().GameSettings.ControlMode = enumNameToItem[text]
+
+ pcall(function()
+ if mouseLockLabel and UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ mouseLockLabel.Visible = true
+ elseif mouseLockLabel then
+ mouseLockLabel.Visible = false
+ end
+ end)
+ end, false, true, baseZIndex)
+ cameraDropDown.Name = "CameraField"
+ cameraDropDown.ZIndex = baseZIndex + 4
+ cameraDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ cameraDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ cameraDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ cameraDropDown.Size = UDim2.new(0,200,0,32)
+ cameraDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- V I D E O C A P T U R E S E T T I N G S
+ ----------------------------------------------------------------------------------------------------
+
+ local syncVideoCaptureSetting = nil
+
+ if not macClient and not touchClient then
+ local videoCaptureLabel = Instance.new("TextLabel")
+ videoCaptureLabel.Name = "VideoCaptureLabel"
+ videoCaptureLabel.Text = "After Capturing Video"
+ videoCaptureLabel.Font = Enum.Font.SourceSansBold
+ videoCaptureLabel.FontSize = Enum.FontSize.Size18
+ videoCaptureLabel.Position = UDim2.new(0,32,0,itemTop + 6)
+ videoCaptureLabel.Size = UDim2.new(0,164,0,18)
+ videoCaptureLabel.BackgroundTransparency = 1
+ videoCaptureLabel.TextColor3 = Color3I(255,255,255)
+ videoCaptureLabel.TextXAlignment = Enum.TextXAlignment.Left
+ videoCaptureLabel.ZIndex = baseZIndex + 4
+ videoCaptureLabel.Parent = gameSettingsMenuFrame
+
+ local videoNames = {}
+ local videoNameToItem = {}
+ videoNames[1] = "Just Save to Disk"
+ videoNameToItem[videoNames[1]] = Enum.UploadSetting["Never"]
+ videoNames[2] = "Upload to YouTube"
+ videoNameToItem[videoNames[2]] = Enum.UploadSetting["Ask me first"]
+
+ local videoCaptureDropDown = nil
+ videoCaptureDropDown, updateVideoCaptureDropDownSelection = RbxGui.CreateDropDownMenu(videoNames,
+ function(text)
+ UserSettings().GameSettings.VideoUploadPromptBehavior = videoNameToItem[text]
+ end, false, true, baseZIndex)
+ videoCaptureDropDown.Name = "VideoCaptureField"
+ videoCaptureDropDown.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ videoCaptureDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ videoCaptureDropDown.Size = UDim2.new(0,200,0,32)
+ videoCaptureDropDown.Parent = gameSettingsMenuFrame
+
+ syncVideoCaptureSetting = function()
+ if UserSettings().GameSettings.VideoUploadPromptBehavior == Enum.UploadSetting["Never"] then
+ updateVideoCaptureDropDownSelection(videoNames[1])
+ elseif UserSettings().GameSettings.VideoUploadPromptBehavior == Enum.UploadSetting["Ask me first"] then
+ updateVideoCaptureDropDownSelection(videoNames[2])
+ else
+ UserSettings().GameSettings.VideoUploadPromptBehavior = Enum.UploadSetting["Ask me first"]
+ updateVideoCaptureDropDownSelection(videoNames[2])
+ end
+ end
+ itemTop = itemTop + 35
+ end
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- C U S T O M C A M E R A C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+
+ local smartCameraLabel = Instance.new("TextLabel")
+ smartCameraLabel.Name = "SmartCameraLabel"
+ smartCameraLabel.Text = "Camera Mode"
+ smartCameraLabel.Font = Enum.Font.SourceSansBold
+ smartCameraLabel.FontSize = Enum.FontSize.Size18
+ smartCameraLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ smartCameraLabel.Size = UDim2.new(0,224,0,18)
+ smartCameraLabel.TextColor3 = Color3I(255,255,255)
+ smartCameraLabel.TextXAlignment = Enum.TextXAlignment.Left
+ smartCameraLabel.BackgroundTransparency = 1
+ smartCameraLabel.ZIndex = baseZIndex + 4
+ smartCameraLabel.Parent = gameSettingsMenuFrame
+
+ local smartEnumItems = nil
+ smartEnumItems = Enum.CustomCameraMode:GetEnumItems()
+
+ local smartEnumNames = {}
+ local smartEnumNameToItem = {}
+
+ for i,obj in pairs(smartEnumItems) do
+ local displayName = obj.Name
+ if (obj.Name == "Default") then
+ displayName = customCameraDefaultType
+ end
+ smartEnumNames[i] = displayName
+ smartEnumNameToItem[displayName] = obj.Value
+ end
+
+ local smartCameraDropDown
+ smartCameraDropDown, updateSmartCameraDropDownSelection = RbxGui.CreateDropDownMenu(smartEnumNames,
+ function(text)
+ UserSettings().GameSettings.CameraMode = smartEnumNameToItem[text]
+ end, false, true, baseZIndex)
+ smartCameraDropDown.Name = "SmartCameraField"
+ smartCameraDropDown.ZIndex = baseZIndex + 4
+ smartCameraDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ smartCameraDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ smartCameraDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ smartCameraDropDown.Size = UDim2.new(0,200,0,32)
+ smartCameraDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- T O U C H M O V E M E N T C O N T R O L S
+ ----------------------------------------------------------------------------------------------------
+ if (touchClient) then
+ local touchMovementLabel = Instance.new("TextLabel")
+ touchMovementLabel.Name = "TouchMovementLabel"
+ touchMovementLabel.Text = "Movement Mode"
+ touchMovementLabel.Font = Enum.Font.SourceSansBold
+ touchMovementLabel.FontSize = Enum.FontSize.Size18
+ touchMovementLabel.Position = UDim2.new(0,31,0,itemTop + 6)
+ touchMovementLabel.Size = UDim2.new(0,224,0,18)
+ touchMovementLabel.TextColor3 = Color3I(255,255,255)
+ touchMovementLabel.TextXAlignment = Enum.TextXAlignment.Left
+ touchMovementLabel.BackgroundTransparency = 1
+ touchMovementLabel.ZIndex = baseZIndex + 4
+ touchMovementLabel.Parent = gameSettingsMenuFrame
+
+ local touchEnumItems = Enum.TouchMovementMode:GetEnumItems()
+ local touchEnumNames = {}
+ local touchEnumNameToItem = {}
+ for i,obj in ipairs(touchEnumItems) do
+ local displayName = obj.Name
+ if (obj.Name == "Default") then
+ displayName = "Default (Thumbstick)"
+ end
+ touchEnumNames[i] = displayName
+ touchEnumNameToItem[displayName] = obj
+ end
+
+ local touchMovementDropDown
+ touchMovementDropDown, updateTouchMovementDropDownSelection = RbxGui.CreateDropDownMenu(touchEnumNames,
+ function(text)
+ UserSettings().GameSettings.TouchMovementMode = touchEnumNameToItem[text]
+ end, false, true, baseZIndex)
+ touchMovementDropDown.Name = "touchMovementField"
+ touchMovementDropDown.ZIndex = baseZIndex + 4
+ touchMovementDropDown.DropDownMenuButton.ZIndex = baseZIndex + 4
+ touchMovementDropDown.DropDownMenuButton.Icon.ZIndex = baseZIndex + 4
+ touchMovementDropDown.Position = UDim2.new(0, 270, 0, itemTop)
+ touchMovementDropDown.Size = UDim2.new(0,200,0,32)
+ touchMovementDropDown.Parent = gameSettingsMenuFrame
+
+ itemTop = itemTop + 35
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- F U L L S C R E E N M O D E
+ ----------------------------------------------------------------------------------------------------
+
+ local fullscreenText = nil
+ local fullscreenShortcut = nil
+ local fullscreenCheckbox = nil
+
+ if not touchClient then
+
+ itemTop = itemTop + 15
+
+ fullscreenText = Instance.new("TextLabel")
+ fullscreenText.Name = "FullscreenText"
+ fullscreenText.Text = "Fullscreen Mode"
+
+ fullscreenText.Position = UDim2.new(0,31,0,itemTop + 6)
+ fullscreenText.Size = UDim2.new(0,224,0,18)
+
+ fullscreenText.Font = Enum.Font.SourceSansBold
+ fullscreenText.FontSize = Enum.FontSize.Size18
+ fullscreenText.TextXAlignment = Enum.TextXAlignment.Left
+ fullscreenText.TextColor3 = Color3.new(1,1,1)
+ fullscreenText.ZIndex = baseZIndex + 4
+ fullscreenText.BackgroundTransparency = 1
+ fullscreenText.Parent = gameSettingsMenuFrame
+
+ fullscreenCheckbox = createTextButton("",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,32,0,32),UDim2.new(0, 270, 0, itemTop- 4))
+ fullscreenCheckbox.Name = "FullscreenCheckbox"
+ fullscreenCheckbox.ZIndex = baseZIndex + 4
+ fullscreenCheckbox.Parent = gameSettingsMenuFrame
+ fullscreenCheckbox:SetVerb("ToggleFullScreen")
+ if UserSettings().GameSettings:InFullScreen() then fullscreenCheckbox.Text = "X" end
+ if hasGraphicsSlider then
+ UserSettings().GameSettings.FullscreenChanged:connect(function(isFullscreen)
+ if isFullscreen then
+ fullscreenCheckbox.Text = "X"
+ else
+ fullscreenCheckbox.Text = ""
+ end
+ end)
+ else
+ fullscreenCheckbox.MouseButton1Click:connect(function()
+ if fullscreenCheckbox.Text == "" then
+ fullscreenCheckbox.Text = "X"
+ else
+ fullscreenCheckbox.Text = ""
+ end
+ end)
+ end
+ end
+
+ ----------------------------------------------------------------------------------------------------
+ -- G R A P H I C S S L I D E R
+ ----------------------------------------------------------------------------------------------------
+ local graphicsSlider, graphicsLevel = nil
+ if hasGraphicsSlider then
+ local graphicsQualityYOffset = -45
+
+ local qualityText = Instance.new("TextLabel")
+ qualityText.Name = "QualityText"
+ qualityText.Text = "Graphics Quality"
+ qualityText.Size = UDim2.new(0,224,0,18)
+ qualityText.Position = UDim2.new(0,31,0,239 + graphicsQualityYOffset)
+
+ qualityText.TextXAlignment = Enum.TextXAlignment.Left
+ qualityText.Font = Enum.Font.SourceSansBold
+ qualityText.FontSize = Enum.FontSize.Size18
+ qualityText.TextColor3 = Color3.new(1,1,1)
+ qualityText.ZIndex = baseZIndex + 4
+ qualityText.BackgroundTransparency = 1
+ qualityText.Parent = gameSettingsMenuFrame
+ qualityText.Visible = not inStudioMode
+
+ local autoText = qualityText:clone()
+ autoText.Name = "AutoText"
+ autoText.Text = "Auto"
+ autoText.Position = UDim2.new(0,270,0,214 + graphicsQualityYOffset)
+ autoText.TextColor3 = Color3.new(128/255,128/255,128/255)
+ autoText.Size = UDim2.new(0,34,0,18)
+ autoText.Parent = gameSettingsMenuFrame
+ autoText.Visible = not inStudioMode
+
+ local fasterText = autoText:clone()
+ fasterText.Name = "FasterText"
+ fasterText.Text = "Faster"
+ fasterText.Position = UDim2.new(0,185,0,274 + graphicsQualityYOffset)
+ fasterText.TextColor3 = Color3.new(95,95,95)
+ fasterText.FontSize = Enum.FontSize.Size14
+ fasterText.Parent = gameSettingsMenuFrame
+ fasterText.Visible = not inStudioMode
+
+ local betterQualityText = autoText:clone()
+ betterQualityText.Name = "BetterQualityText"
+ betterQualityText.Text = "Better Quality"
+ betterQualityText.TextWrap = true
+ betterQualityText.Size = UDim2.new(0,41,0,28)
+ betterQualityText.Position = UDim2.new(0,390,0,269 + graphicsQualityYOffset)
+ betterQualityText.TextColor3 = Color3.new(95,95,95)
+ betterQualityText.FontSize = Enum.FontSize.Size14
+ betterQualityText.Parent = gameSettingsMenuFrame
+ betterQualityText.Visible = not inStudioMode
+
+ local autoGraphicsButton = createTextButton("X",Enum.ButtonStyle.RobloxRoundButton,Enum.FontSize.Size18,UDim2.new(0,32,0,32),UDim2.new(0,270,0,230 + graphicsQualityYOffset))
+ autoGraphicsButton.Name = "AutoGraphicsButton"
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ autoGraphicsButton.Parent = gameSettingsMenuFrame
+ autoGraphicsButton.Visible = not inStudioMode
+
+ graphicsSlider, graphicsLevel = RbxGui.CreateSliderNew(GraphicsQualityLevels,150,UDim2.new(0, 230, 0, 280 + graphicsQualityYOffset)) -- graphics - 1 because slider starts at 1 instead of 0
+ graphicsSlider.Parent = gameSettingsMenuFrame
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 5
+ graphicsSlider.Visible = not inStudioMode
+ graphicsLevel.Value = math.floor((settings().Rendering:GetMaxQualityLevel() - 1)/2)
+
+ local graphicsSetter = Instance.new("TextBox")
+ graphicsSetter.Name = "GraphicsSetter"
+ graphicsSetter.BackgroundColor3 = Color3.new(0,0,0)
+ graphicsSetter.BorderColor3 = Color3.new(128/255,128/255,128/255)
+ graphicsSetter.Size = UDim2.new(0,50,0,25)
+ graphicsSetter.Position = UDim2.new(0,450,0,269 + graphicsQualityYOffset)
+ graphicsSetter.TextColor3 = Color3.new(1,1,1)
+ graphicsSetter.Font = Enum.Font.SourceSansBold
+ graphicsSetter.FontSize = Enum.FontSize.Size18
+ graphicsSetter.Text = "Auto"
+ graphicsSetter.ZIndex = 1
+ graphicsSetter.TextWrap = true
+ graphicsSetter.Parent = gameSettingsMenuFrame
+ graphicsSetter.Visible = not inStudioMode
+
+ local isAutoGraphics = true
+ if not inStudioMode then
+ isAutoGraphics = (UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic)
+ else
+ settings().Rendering.EnableFRM = false
+ end
+
+ local listenToGraphicsLevelChange = true
+
+ local function setAutoGraphicsGui(active)
+ isAutoGraphics = active
+ if active then
+ autoGraphicsButton.Text = "X"
+ betterQualityText.ZIndex = 1
+ fasterText.ZIndex = 1
+ graphicsSlider.Bar.ZIndex = 1
+ graphicsSlider.BarLeft.ZIndex = 1
+ graphicsSlider.BarRight.ZIndex = 1
+ graphicsSlider.Bar.Fill.ZIndex = 1
+ graphicsSlider.FillLeft.ZIndex = 1
+ graphicsSlider.Bar.Slider.ZIndex = 1
+ graphicsSetter.ZIndex = 1
+ graphicsSetter.Text = "Auto"
+ else
+ autoGraphicsButton.Text = ""
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 6
+ graphicsSlider.BarLeft.ZIndex = baseZIndex + 4
+ graphicsSlider.BarRight.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Fill.ZIndex = baseZIndex + 5
+ graphicsSlider.FillLeft.ZIndex = baseZIndex + 5
+ betterQualityText.ZIndex = baseZIndex + 4
+ fasterText.ZIndex = baseZIndex + 4
+ graphicsSetter.ZIndex = baseZIndex + 4
+ end
+ end
+
+ local function goToAutoGraphics()
+ setAutoGraphicsGui(true)
+
+ UserSettings().GameSettings.SavedQualityLevel = Enum.SavedQualitySetting.Automatic
+
+ settings().Rendering.QualityLevel = Enum.QualityLevel.Automatic
+ end
+
+ local function setGraphicsQualityLevel(newLevel)
+ local percentage = newLevel/GraphicsQualityLevels
+ local newSetting = math.floor((settings().Rendering:GetMaxQualityLevel() - 1) * percentage)
+ if newSetting == 20 then -- Level 20 is the same as level 21, except it doesn't render ambient occlusion
+ newSetting = 21
+ elseif newLevel == 1 then -- make sure we can go to lowest settings (for terrible computers)
+ newSetting = 1
+ elseif newSetting > settings().Rendering:GetMaxQualityLevel() then
+ newSetting = settings().Rendering:GetMaxQualityLevel() - 1
+ end
+
+ UserSettings().GameSettings.SavedQualityLevel = newLevel
+ settings().Rendering.QualityLevel = newSetting
+ end
+
+ local function goToManualGraphics(explicitLevel)
+ setAutoGraphicsGui(false)
+
+ if explicitLevel then
+ graphicsLevel.Value = explicitLevel
+ else
+ graphicsLevel.Value = math.floor((settings().Rendering.AutoFRMLevel/(settings().Rendering:GetMaxQualityLevel() - 1)) * GraphicsQualityLevels)
+ end
+
+ if explicitLevel == graphicsLevel.Value then -- make sure we are actually in right graphics mode
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ end
+
+ if not explicitLevel then
+ UserSettings().GameSettings.SavedQualityLevel = graphicsLevel.Value
+ end
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ end
+
+ local function showAutoGraphics()
+ autoText.ZIndex = baseZIndex + 4
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ end
+
+ local function hideAutoGraphics()
+ autoText.ZIndex = 1
+ autoGraphicsButton.ZIndex = 1
+ end
+
+ local function showManualGraphics()
+ graphicsSlider.Bar.ZIndex = baseZIndex + 4
+ graphicsSlider.Bar.Slider.ZIndex = baseZIndex + 5
+ betterQualityText.ZIndex = baseZIndex + 4
+ fasterText.ZIndex = baseZIndex + 4
+ graphicsSetter.ZIndex = baseZIndex + 4
+ end
+
+ local function hideManualGraphics()
+ betterQualityText.ZIndex = 1
+ fasterText.ZIndex = 1
+ graphicsSlider.Bar.ZIndex = 1
+ graphicsSlider.Bar.Slider.ZIndex = 1
+ graphicsSetter.ZIndex = 1
+ end
+
+ local function translateSavedQualityLevelToInt(savedQualityLevel)
+ if savedQualityLevel == Enum.SavedQualitySetting.Automatic then
+ return 0
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel1 then
+ return 1
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel2 then
+ return 2
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel3 then
+ return 3
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel4 then
+ return 4
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel5 then
+ return 5
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel6 then
+ return 6
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel7 then
+ return 7
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel8 then
+ return 8
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel9 then
+ return 9
+ elseif savedQualityLevel == Enum.SavedQualitySetting.QualityLevel10 then
+ return 10
+ end
+ end
+
+ local function enableGraphicsWidget()
+ settings().Rendering.EnableFRM = true
+
+ isAutoGraphics = (UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic)
+ if isAutoGraphics then
+ showAutoGraphics()
+ goToAutoGraphics()
+ else
+ showAutoGraphics()
+ showManualGraphics()
+ goToManualGraphics(translateSavedQualityLevelToInt(UserSettings().GameSettings.SavedQualityLevel))
+ end
+ end
+
+ local function disableGraphicsWidget()
+ hideManualGraphics()
+ hideAutoGraphics()
+ settings().Rendering.EnableFRM = false
+ end
+
+ graphicsSetter.FocusLost:connect(function()
+ if isAutoGraphics then
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ return
+ end
+
+ local newGraphicsValue = tonumber(graphicsSetter.Text)
+ if newGraphicsValue == nil then
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ return
+ end
+
+ if newGraphicsValue < 1 then newGraphicsValue = 1
+ elseif newGraphicsValue >= settings().Rendering:GetMaxQualityLevel() then
+ newGraphicsValue = settings().Rendering:GetMaxQualityLevel() - 1
+ end
+
+ graphicsLevel.Value = newGraphicsValue
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ end)
+
+ graphicsLevel.Changed:connect(function(prop)
+ if isAutoGraphics then return end
+ if not listenToGraphicsLevelChange then return end
+
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+ end)
+
+ -- setup our graphic mode on load
+ if inStudioMode or UserSettings().GameSettings.SavedQualityLevel == Enum.SavedQualitySetting.Automatic then
+ if inStudioMode then
+ settings().Rendering.EnableFRM = false
+ disableGraphicsWidget()
+ else
+ settings().Rendering.EnableFRM = true
+ goToAutoGraphics()
+ end
+ else
+ settings().Rendering.EnableFRM = true
+ goToManualGraphics(translateSavedQualityLevelToInt(UserSettings().GameSettings.SavedQualityLevel))
+ end
+
+ autoGraphicsButton.MouseButton1Click:connect(function()
+ if inStudioMode and not game.Players.LocalPlayer then return end
+
+ if not isAutoGraphics then
+ goToAutoGraphics()
+ else
+ goToManualGraphics(graphicsLevel.Value)
+ end
+ end)
+
+ local lastUpdate = nil
+ game.GraphicsQualityChangeRequest:connect(function(graphicsIncrease)
+ if isAutoGraphics then return end -- only can set graphics in manual mode
+
+ if graphicsIncrease then
+ if (graphicsLevel.Value + 1) > GraphicsQualityLevels then return end
+ graphicsLevel.Value = graphicsLevel.Value + 1
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+
+ game:GetService("GuiService"):SendNotification("Graphics Quality",
+ "Increased to (" .. graphicsSetter.Text .. ")",
+ "",
+ 2,
+ function()
+ end)
+ else
+ if (graphicsLevel.Value - 1) <= 0 then return end
+ graphicsLevel.Value = graphicsLevel.Value - 1
+ graphicsSetter.Text = tostring(graphicsLevel.Value)
+ setGraphicsQualityLevel(graphicsLevel.Value)
+
+ game:GetService("GuiService"):SendNotification("Graphics Quality",
+ "Decreased to (" .. graphicsSetter.Text .. ")",
+ "",
+ 2,
+ function()
+ end)
+ end
+ end)
+
+ game.Players.PlayerAdded:connect(function(player)
+ if player == game.Players.LocalPlayer and inStudioMode then
+ enableGraphicsWidget()
+ end
+ end)
+ game.Players.PlayerRemoving:connect(function(player)
+ if player == game.Players.LocalPlayer and inStudioMode then
+ disableGraphicsWidget()
+ end
+ end)
+
+ local wasManualGraphics = (settings().Rendering.QualityLevel ~= Enum.QualityLevel.Automatic)
+ if inStudioMode and not game.Players.LocalPlayer then
+ disableGraphicsWidget()
+ elseif inStudioMode then
+ enableGraphicsWidget()
+ end
+ if hasGraphicsSlider then
+ UserSettings().GameSettings.StudioModeChanged:connect(function(isStudioMode)
+ inStudioMode = isStudioMode
+ if isStudioMode then
+ wasManualGraphics = (settings().Rendering.QualityLevel ~= Enum.QualityLevel.Automatic)
+ goToAutoGraphics()
+ autoGraphicsButton.ZIndex = 1
+ autoText.ZIndex = 1
+ else
+ if wasManualGraphics then
+ goToManualGraphics()
+ end
+ autoGraphicsButton.ZIndex = baseZIndex + 4
+ autoText.ZIndex = baseZIndex + 4
+ end
+ end)
+ end
+
+ if graphicsSlider and graphicsSlider.Bar and graphicsSlider.Visible then
+ itemTop = graphicsSlider.Bar.Position.Y.Offset + 20
+ end
+ end
+ ----------------------------------------------------------------------------------------------------
+ -- V O L U M E S L I D E R
+ ----------------------------------------------------------------------------------------------------
+ if hasVolumeSlider then
+ local maxVolumeLevel = 256
+
+ local volumeText = Instance.new("TextLabel")
+ volumeText.Name = "VolumeText"
+ volumeText.Text = "Volume"
+ volumeText.Size = UDim2.new(0,224,0,18)
+
+ local volumeTextOffset = 25
+ if graphicsSlider and not graphicsSlider.Visible then
+ volumeTextOffset = volumeTextOffset + 30
+ end
+ volumeText.Position = UDim2.new(0,31,0, itemTop + volumeTextOffset)
+
+ volumeText.TextXAlignment = Enum.TextXAlignment.Left
+ volumeText.Font = Enum.Font.SourceSansBold
+ volumeText.FontSize = Enum.FontSize.Size18
+ volumeText.TextColor3 = Color3.new(1,1,1)
+ volumeText.ZIndex = baseZIndex + 4
+ volumeText.BackgroundTransparency = 1
+ volumeText.Parent = gameSettingsMenuFrame
+ volumeText.Visible = true
+
+ local volumeSliderOffset = 32
+ if graphicsSlider and not graphicsSlider.Visible then
+ volumeSliderOffset = volumeSliderOffset + 30
+ end
+ local volumeSlider, volumeLevel = RbxGui.CreateSliderNew( maxVolumeLevel,256,UDim2.new(0, 180, 0, itemTop + volumeSliderOffset) )
+ volumeSlider.Parent = gameSettingsMenuFrame
+ volumeSlider.Bar.ZIndex = baseZIndex + 3
+ volumeSlider.Bar.Slider.ZIndex = baseZIndex + 4
+ volumeSlider.BarLeft.ZIndex = baseZIndex + 3
+ volumeSlider.BarRight.ZIndex = baseZIndex + 3
+ volumeSlider.Bar.Fill.ZIndex = baseZIndex + 3
+ volumeSlider.FillLeft.ZIndex = baseZIndex + 3
+ volumeSlider.Visible = true
+ volumeLevel.Value = math.min(math.max(UserSettings().GameSettings.MasterVolume * maxVolumeLevel, 1), maxVolumeLevel)
+
+ volumeLevel.Changed:connect(function(prop)
+ local volume = volumeLevel.Value - 1 -- smallest value is 1, so need to subtract one for muting
+ UserSettings().GameSettings.MasterVolume = volume/maxVolumeLevel
+ end)
+
+ itemTop = itemTop + volumeSliderOffset
+ end
+
+
+ ----------------------------------------------------------------------------------------------------
+ -- O K B U T T O N
+ ----------------------------------------------------------------------------------------------------
+
+
+ local backButton
+ if hasGraphicsSlider then
+ backButton = createTextButton("OK",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,180,0,50),UDim2.new(0,170,0,315))
+ backButton.Modal = true
+ else
+ backButton = createTextButton("OK",Enum.ButtonStyle.RobloxRoundDefaultButton,Enum.FontSize.Size24,UDim2.new(0,180,0,50),UDim2.new(0,170,0,270))
+ backButton.Modal = true
+ end
+
+ backButton.Name = "BackButton"
+ backButton.ZIndex = baseZIndex + 4
+ backButton.Parent = gameSettingsMenuFrame
+
+ return gameSettingsMenuFrame
+end
+
+local showMainMenu = nil
+
+if LoadLibrary then
+ RbxGui = LoadLibrary("RbxGui")
+ local baseZIndex = 4
+if UserSettings then
+
+ waitForChild(gui,"TopLeftControl")
+ waitForChild(gui,"BottomLeftControl")
+
+
+ local settingButtonParent = gui:WaitForChild("TopLeftControl")
+ local createSettingsDialog = function()
+ if touchClient then
+ waitForChild(gui,"TopLeftControl")
+ else
+ settingButtonParent = gui:WaitForChild("BottomLeftControl")
+ end
+
+ settingsButton = settingButtonParent:FindFirstChild("SettingsButton")
+
+ if settingsButton == nil then
+ settingsButton = Instance.new("ImageButton")
+ settingsButton.Name = "SettingsButton"
+ settingsButton.Image = "rbxasset://textures/ui/homeButton.png"
+ settingsButton.BackgroundTransparency = 1
+ settingsButton.Active = false
+ settingsButton.Size = UDim2.new(0,36,0,28)
+ if (touchClient) then
+ settingsButton.Position = UDim2.new(0,2,0,5)
+ else
+ settingsButton.Position = UDim2.new(0, 15, 1, -42)
+ end
+ settingsButton.Parent = settingButtonParent
+ end
+
+ local shield = Instance.new("TextButton")
+ shield.Text = ""
+ shield.Name = "UserSettingsShield"
+ shield.Active = true
+ shield.AutoButtonColor = false
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 2
+ mainShield = shield
+
+ local frame = Instance.new("Frame")
+ frame.Name = "Settings"
+ frame.Position = UDim2.new(0.5, -262, -0.5, -200)
+ frame.Size = UDim2.new(0, 525, 0, 430)
+ frame.BackgroundTransparency = 1
+ frame.Active = true
+ frame.Parent = shield
+
+ local settingsFrame = Instance.new("Frame")
+ settingsFrame.Name = "SettingsStyle"
+ settingsFrame.Size = UDim2.new(1, 0, 1, 0)
+ settingsFrame.Style = Enum.FrameStyle.DropShadow
+ settingsFrame.Active = true
+ settingsFrame.ZIndex = baseZIndex + 3
+ settingsFrame.Parent = frame
+
+ local gameMainMenu = createGameMainMenu(baseZIndex, shield)
+ gameMainMenu.Parent = settingsFrame
+
+ gameMainMenu.ScreenshotButton.MouseButton1Click:connect(function()
+ backToGame(gameMainMenu.ScreenshotButton, shield, settingsButton)
+ end)
+
+ gameMainMenu.RecordVideoButton.MouseButton1Click:connect(function()
+ recordVideoClick(gameMainMenu.RecordVideoButton, gui.StopRecordButton)
+ backToGame(gameMainMenu.RecordVideoButton, shield, settingsButton)
+ end)
+
+ if settings():FindFirstChild("Game Options") then
+ pcall(function()
+ settings():FindFirstChild("Game Options").VideoRecordingChangeRequest:connect(function(recording)
+ recordingVideo = recording
+ setRecordGui(recording, gui.StopRecordButton, gameMainMenu.RecordVideoButton)
+ end)
+ end)
+ end
+
+ game.CoreGui.RobloxGui.Changed:connect(function(prop) -- We have stopped recording when we resize
+ if prop == "AbsoluteSize" and recordingVideo then
+ recordVideoClick(gameMainMenu.RecordVideoButton, gui.StopRecordButton)
+ end
+ end)
+
+ function localPlayerChange()
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ if game.Players.LocalPlayer then
+ settings().Rendering.EnableFRM = true
+ elseif inStudioMode then
+ settings().Rendering.EnableFRM = false
+ end
+ end
+
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ if game.Players.LocalPlayer ~= nil then
+ game.Players.LocalPlayer.Changed:connect(function()
+ localPlayerChange()
+ end)
+ else
+ delay(0,function()
+ waitForProperty(game.Players,"LocalPlayer")
+ gameMainMenu.ResetButton.Visible = game.Players.LocalPlayer
+ game.Players.LocalPlayer.Changed:connect(function()
+ localPlayerChange()
+ end)
+ end)
+ end
+
+ gameMainMenu.ReportAbuseButton.Visible = game:FindFirstChild("NetworkClient")
+ -- TODO: remove line below when not testing report abuse
+ if (testReport) then
+ gameMainMenu.ReportAbuseButton.Visible = true
+ end
+ if not gameMainMenu.ReportAbuseButton.Visible then
+ game.ChildAdded:connect(function(child)
+ if child:IsA("NetworkClient") then
+ gameMainMenu.ReportAbuseButton.Visible = game:FindFirstChild("NetworkClient")
+ end
+ end)
+ end
+
+ gameMainMenu.ResetButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"ResetConfirmationMenu","up",UDim2.new(0,525,0,370))
+ end)
+
+ local leaveGameButton = gameMainMenu:FindFirstChild("LeaveGameButton")
+ if (leaveGameButton) then
+ gameMainMenu.LeaveGameButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"LeaveConfirmationMenu","down",UDim2.new(0,525,0,300))
+ end)
+ end
+
+ showMainMenu = function(overrideMenu, overrideDir, overrideSize)
+ if shield.Visible and overrideMenu then
+ goToMenu(settingsFrame,overrideMenu,overrideDir,overrideSize)
+ return
+ end
+
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --showFunction
+ function()
+ settingsButton.Active = false
+ if updateCameraDropDownSelection ~= nil then
+ updateCameraDropDownSelection(UserSettings().GameSettings.ControlMode.Name)
+ end
+
+ local cameraMode = UserSettings().GameSettings.CameraMode.Name
+ if (cameraMode == "Default") then
+ cameraMode = customCameraDefaultType
+ end
+ updateSmartCameraDropDownSelection(cameraMode)
+
+ if updateTouchMovementDropDownSelection ~= nil then
+ local moveMode = UserSettings().GameSettings.TouchMovementMode.Name
+ if (moveMode == "Default") then
+ moveMode = "Default (Thumbstick)"
+ end
+ updateTouchMovementDropDownSelection(moveMode)
+ end
+
+ pcall(function() game:GetService("UserInputService").OverrideMouseIconEnabled = true end)
+
+
+ if syncVideoCaptureSetting then
+ syncVideoCaptureSetting()
+ end
+
+ local menuToGoTo = "GameMainMenu"
+ local direction = "right"
+ local menuSize = UDim2.new(0,525,0,430)
+
+ if overrideMenu then
+ menuToGoTo = overrideMenu
+ end
+ if overrideDir then
+ direction = overrideDir
+ end
+ if overrideSize then
+ menuSize = overrideSize
+ end
+
+ goToMenu(settingsFrame,menuToGoTo,direction,menuSize)
+ shield.Visible = true
+ shield.Active = true
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end,
+ --hideFunction
+ function()
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ shield.Visible = false
+ settingsButton.Active = true
+ end)
+ end
+
+ game:GetService("GuiService").EscapeKeyPressed:connect(function()
+ if currentMenuSelection == nil then
+ showMainMenu()
+ elseif #lastMenuSelection > 0 then
+ if #centerDialogs > 0 then
+ for i = 1, #centerDialogs do
+ game.GuiService:RemoveCenterDialog(centerDialogs[i])
+ centerDialogs[i].Visible = false
+ end
+ centerDialogs = {}
+ end
+
+ goToMenu(lastMenuSelection[#lastMenuSelection]["container"],lastMenuSelection[#lastMenuSelection]["name"],
+ lastMenuSelection[#lastMenuSelection]["direction"],lastMenuSelection[#lastMenuSelection]["lastSize"])
+
+ table.remove(lastMenuSelection,#lastMenuSelection)
+ if #lastMenuSelection == 1 then -- apparently lua can't reduce count to 0... T_T
+ lastMenuSelection = {}
+ end
+ else
+ resumeGameFunction(shield)
+ end
+ end)
+
+ local gameSettingsMenu = createGameSettingsMenu(baseZIndex, shield)
+ gameSettingsMenu.Visible = false
+ gameSettingsMenu.Parent = settingsFrame
+
+ gameMainMenu.SettingsButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"GameSettingsMenu","left",UDim2.new(0,525,0,350))
+ end)
+
+ gameSettingsMenu.BackButton.MouseButton1Click:connect(function()
+ goToMenu(settingsFrame,"GameMainMenu","right",UDim2.new(0,525,0,430))
+ end)
+
+ local resetConfirmationWindow = createResetConfirmationMenu(baseZIndex, shield)
+ resetConfirmationWindow.Visible = false
+ resetConfirmationWindow.Parent = settingsFrame
+
+ local leaveConfirmationWindow = createLeaveConfirmationMenu(baseZIndex,shield)
+ leaveConfirmationWindow.Visible = false
+ leaveConfirmationWindow.Parent = settingsFrame
+
+ robloxLock(shield)
+
+ settingsButton.MouseButton1Click:connect(
+ function()
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --showFunction
+ function()
+ settingsButton.Active = false
+ if updateCameraDropDownSelection ~= nil then
+ updateCameraDropDownSelection(UserSettings().GameSettings.ControlMode.Name)
+ end
+
+ local cameraMode = UserSettings().GameSettings.CameraMode.Name
+ if (cameraMode == "Default") then
+ cameraMode = customCameraDefaultType
+ end
+ updateSmartCameraDropDownSelection(cameraMode)
+
+ if updateTouchMovementDropDownSelection ~= nil then
+ local moveMode = UserSettings().GameSettings.TouchMovementMode.Name
+ if (moveMode == "Default") then
+ moveMode = "Default (Thumbstick)"
+ end
+ updateTouchMovementDropDownSelection(moveMode)
+ end
+
+ if syncVideoCaptureSetting then
+ syncVideoCaptureSetting()
+ end
+
+ goToMenu(settingsFrame,"GameMainMenu","right",UDim2.new(0,525,0,430))
+ shield.Visible = true
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ end,
+ --hideFunction
+ function()
+ settingsFrame.Parent:TweenPosition(UDim2.new(0.5, -262,-0.5, -200),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ settingsFrame.Parent:TweenSize(UDim2.new(0,525,0,430),Enum.EasingDirection.InOut,Enum.EasingStyle.Sine,tweenTime,true)
+ shield.Visible = false
+ settingsButton.Active = true
+ end)
+ end)
+
+ return shield
+ end
+
+ delay(0, function()
+ createSettingsDialog().Parent = gui
+
+ settingButtonParent.SettingsButton.Active = true
+-- settingButtonParent.SettingsButton.Position = UDim2.new(0,2,0,-2)
+
+ if mouseLockLabel and UserSettings().GameSettings.ControlMode == Enum.ControlMode["Mouse Lock Switch"] then
+ mouseLockLabel.Visible = true
+ elseif mouseLockLabel then
+ mouseLockLabel.Visible = false
+ end
+
+ -- our script has loaded, get rid of older buttons now
+ local leaveGameButton = gui.BottomLeftControl:FindFirstChild("Exit")
+ if leaveGameButton then leaveGameButton:Remove() end
+
+ local topLeft = gui:FindFirstChild("TopLeftControl")
+ if topLeft then
+ leaveGameButton = topLeft:FindFirstChild("Exit")
+ if leaveGameButton then leaveGameButton:Remove() end
+
+ if settingButtonParent ~= topLeft then
+ topLeft:Remove()
+ end
+ end
+ --]]
+ end)
+
+end --UserSettings call
+
+local createSaveDialogs = function()
+ local shield = Instance.new("TextButton")
+ shield.Text = ""
+ shield.AutoButtonColor = false
+ shield.Name = "SaveDialogShield"
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex+1
+
+ local clearAndResetDialog
+ local save
+ local saveLocal
+ local dontSave
+ local cancel
+
+ local messageBoxButtons = {}
+ messageBoxButtons[1] = {}
+ messageBoxButtons[1].Text = "Save"
+ messageBoxButtons[1].Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ messageBoxButtons[1].Function = function() save() end
+ messageBoxButtons[1].ZIndex = baseZIndex+3
+ messageBoxButtons[2] = {}
+ messageBoxButtons[2].Text = "Cancel"
+ messageBoxButtons[2].Function = function() cancel() end
+ messageBoxButtons[2].Style = Enum.ButtonStyle.RobloxRoundButton
+ messageBoxButtons[2].ZIndex = baseZIndex+3
+ messageBoxButtons[3] = {}
+ messageBoxButtons[3].Text = "Don't Save"
+ messageBoxButtons[3].Function = function() dontSave() end
+ messageBoxButtons[3].Style = Enum.ButtonStyle.RobloxRoundButton
+ messageBoxButtons[3].ZIndex = baseZIndex+3
+
+ local saveDialogMessageBox = RbxGui.CreateStyledMessageDialog("Unsaved Changes", "Save your changes to ROBLOX before leaving?", "Confirm", messageBoxButtons)
+ saveDialogMessageBox.Visible = true
+ saveDialogMessageBox.Parent = shield
+ saveDialogMessageBox.ZIndex = baseZIndex+2
+ saveDialogMessageBox.Style = Enum.FrameStyle.DropShadow
+ saveDialogMessageBox.Title.ZIndex = baseZIndex+3
+ saveDialogMessageBox.Message.ZIndex = baseZIndex+3
+ saveDialogMessageBox.StyleImage.ZIndex = baseZIndex+3
+
+
+ local errorBoxButtons = {}
+
+ local buttonOffset = 1
+ if game.LocalSaveEnabled then
+ errorBoxButtons[buttonOffset] = {}
+ errorBoxButtons[buttonOffset].Text = "Save to Disk"
+ errorBoxButtons[buttonOffset].Function = function() saveLocal() end
+ buttonOffset = buttonOffset + 1
+ end
+ errorBoxButtons[buttonOffset] = {}
+ errorBoxButtons[buttonOffset].Text = "Keep Playing"
+ errorBoxButtons[buttonOffset].Function = function() cancel() end
+ errorBoxButtons[buttonOffset].Style = Enum.ButtonStyle.RobloxRoundButton
+ errorBoxButtons[buttonOffset].ZIndex = baseZIndex+3
+ errorBoxButtons[buttonOffset+1] = {}
+ errorBoxButtons[buttonOffset+1].Text = "Don't Save"
+ errorBoxButtons[buttonOffset+1].Function = function() dontSave() end
+ errorBoxButtons[buttonOffset+1].Style = Enum.ButtonStyle.RobloxRoundButton
+ errorBoxButtons[buttonOffset+1].ZIndex = baseZIndex+3
+
+ local errorDialogMessageBox = RbxGui.CreateStyledMessageDialog("Upload Failed", "Sorry, we could not save your changes to ROBLOX. If this problem continues to occur, please make sure your Roblox account has a verified email address.", "Error", errorBoxButtons)
+ errorDialogMessageBox.Visible = false
+ errorDialogMessageBox.Parent = shield
+ errorDialogMessageBox.ZIndex = baseZIndex+2
+ errorDialogMessageBox.Style = Enum.FrameStyle.DropShadow
+ errorDialogMessageBox.Title.ZIndex = baseZIndex+3
+ errorDialogMessageBox.Message.ZIndex = baseZIndex+3
+ errorDialogMessageBox.StyleImage.ZIndex = baseZIndex+3
+
+ local spinnerDialog = Instance.new("Frame")
+ spinnerDialog.Name = "SpinnerDialog"
+ spinnerDialog.Style = Enum.FrameStyle.DropShadow
+ spinnerDialog.Size = UDim2.new(0, 350, 0, 150)
+ spinnerDialog.Position = UDim2.new(.5, -175, .5, -75)
+ spinnerDialog.Visible = false
+ spinnerDialog.Active = true
+ spinnerDialog.ZIndex = baseZIndex+1
+ spinnerDialog.Parent = shield
+
+ local waitingLabel = Instance.new("TextLabel")
+ waitingLabel.Name = "WaitingLabel"
+ waitingLabel.Text = "Saving to ROBLOX..."
+ waitingLabel.Font = Enum.Font.SourceSansBold
+ waitingLabel.FontSize = Enum.FontSize.Size18
+ waitingLabel.Position = UDim2.new(0.5, 25, 0.5, 0)
+ waitingLabel.TextColor3 = Color3.new(1,1,1)
+ waitingLabel.ZIndex = baseZIndex+2
+ waitingLabel.Parent = spinnerDialog
+
+ local spinnerFrame = Instance.new("Frame")
+ spinnerFrame.Name = "Spinner"
+ spinnerFrame.Size = UDim2.new(0, 80, 0, 80)
+ spinnerFrame.Position = UDim2.new(0.5, -150, 0.5, -40)
+ spinnerFrame.BackgroundTransparency = 1
+ spinnerFrame.ZIndex = baseZIndex+2
+ spinnerFrame.Parent = spinnerDialog
+
+ local spinnerIcons = {}
+ local spinnerNum = 1
+ while spinnerNum <= 8 do
+ local spinnerImage = Instance.new("ImageLabel")
+ spinnerImage.Name = "Spinner"..spinnerNum
+ spinnerImage.Size = UDim2.new(0, 16, 0, 16)
+ spinnerImage.Position = UDim2.new(.5+.3*math.cos(math.rad(45*spinnerNum)), -8, .5+.3*math.sin(math.rad(45*spinnerNum)), -8)
+ spinnerImage.BackgroundTransparency = 1
+ spinnerImage.Image = "http://www.roblox.com/Asset?id=45880710"
+ spinnerImage.ZIndex = baseZIndex+3
+ spinnerImage.Parent = spinnerFrame
+
+ spinnerIcons[spinnerNum] = spinnerImage
+ spinnerNum = spinnerNum + 1
+ end
+
+ save = function()
+ saveDialogMessageBox.Visible = false
+
+ --Show the spinner dialog
+ spinnerDialog.Visible = true
+ local spin = true
+ --Make it spin
+ delay(0, function()
+ local spinPos = 0
+ while spin do
+ local pos = 0
+
+ while pos < 8 do
+ if pos == spinPos or pos == ((spinPos+1)%8) then
+ spinnerIcons[pos+1].Image = "http://www.roblox.com/Asset?id=45880668"
+ else
+ spinnerIcons[pos+1].Image = "http://www.roblox.com/Asset?id=45880710"
+ end
+
+ pos = pos + 1
+ end
+ spinPos = (spinPos + 1) % 8
+ wait(0.2)
+ end
+ end)
+
+ --Do the save while the spinner is going, function will wait
+ local result = game:SaveToRoblox()
+ if not result then
+ --Try once more
+ result = game:SaveToRoblox()
+ end
+
+ --Hide the spinner dialog
+ spinnerDialog.Visible = false
+ --And cause the delay thread to stop
+ spin = false
+
+ --Now process the result
+ if result then
+ --Success, close
+ game:FinishShutdown(false)
+ clearAndResetDialog()
+ else
+ --Failure, show the second dialog prompt
+ errorDialogMessageBox.Visible = true
+ end
+ end
+
+ saveLocal = function()
+ errorDialogMessageBox.Visible = false
+ game:FinishShutdown(true)
+ clearAndResetDialog()
+ end
+
+ dontSave = function()
+ saveDialogMessageBox.Visible = false
+ errorDialogMessageBox.Visible = false
+ game:FinishShutdown(false)
+ clearAndResetDialog()
+ end
+ cancel = function()
+ saveDialogMessageBox.Visible = false
+ errorDialogMessageBox.Visible = false
+ clearAndResetDialog()
+ end
+
+ clearAndResetDialog = function()
+ saveDialogMessageBox.Visible = true
+ errorDialogMessageBox.Visible = false
+ spinnerDialog.Visible = false
+ shield.Visible = false
+ game.GuiService:RemoveCenterDialog(shield)
+ end
+
+ robloxLock(shield)
+ shield.Visible = false
+ return shield
+end
+
+local createReportAbuseDialog = function()
+ --Only show things if we are a NetworkClient
+ -- TODO: add line back in when not testing report abuse
+ if not testReport then
+ waitForChild(game,"NetworkClient")
+ end
+
+ waitForChild(game,"Players")
+ waitForProperty(game.Players, "LocalPlayer")
+ local localPlayer = game.Players.LocalPlayer
+
+ local reportAbuseButton
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield, "Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle,"GameMainMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu, "ReportAbuseButton")
+ reportAbuseButton = gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu.ReportAbuseButton
+
+ local shield = Instance.new("TextButton")
+ shield.Name = "ReportAbuseShield"
+ shield.Text = ""
+ shield.AutoButtonColor = false
+ shield.Active = true
+ shield.Visible = false
+ shield.Size = UDim2.new(1,0,1,0)
+ shield.BackgroundColor3 = Color3I(51,51,51)
+ shield.BorderColor3 = Color3I(27,42,53)
+ shield.BackgroundTransparency = 0.4
+ shield.ZIndex = baseZIndex + 1
+
+ local closeAndResetDialgo
+
+ local messageBoxButtons = {}
+ messageBoxButtons[1] = {}
+ messageBoxButtons[1].Text = "Ok"
+ messageBoxButtons[1].Modal = true
+ messageBoxButtons[1].Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ messageBoxButtons[1].ZIndex = baseZIndex+3
+ messageBoxButtons[1].Function = function() closeAndResetDialog() end
+ local calmingMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!", "Our moderators will review the chat logs and determine what happened. The other user is probably just trying to make you mad.\n\nIf anyone used swear words, inappropriate language, or threatened you in real life, please report them for Bad Words or Threats", messageBoxButtons)
+ calmingMessageBox.Visible = false
+ calmingMessageBox.Parent = shield
+ calmingMessageBox.ZIndex = baseZIndex+2
+ calmingMessageBox.Style = Enum.FrameStyle.DropShadow
+ calmingMessageBox.Title.ZIndex = baseZIndex+3
+ calmingMessageBox.Message.ZIndex = baseZIndex+3
+
+ local recordedMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!","We've recorded your report for evaluation.", messageBoxButtons)
+ recordedMessageBox.Visible = false
+ recordedMessageBox.Parent = shield
+ recordedMessageBox.ZIndex = baseZIndex+2
+ recordedMessageBox.Style = Enum.FrameStyle.DropShadow
+ recordedMessageBox.Title.ZIndex = baseZIndex+3
+ recordedMessageBox.Message.ZIndex = baseZIndex+3
+
+ local normalMessageBox = RbxGui.CreateMessageDialog("Thanks for your report!", "Our moderators will review the chat logs and determine what happened.", messageBoxButtons)
+ normalMessageBox.Visible = false
+ normalMessageBox.Parent = shield
+ normalMessageBox.ZIndex = baseZIndex+2
+ normalMessageBox.Style = Enum.FrameStyle.DropShadow
+ normalMessageBox.Title.ZIndex = baseZIndex+3
+ normalMessageBox.Message.ZIndex = baseZIndex+3
+
+ local frame = Instance.new("Frame")
+ frame.Name = "Settings"
+ frame.Position = UDim2.new(0.5, -240, 0.5, -160)
+ frame.Size = UDim2.new(0.0, 480, 0.0, 320)
+ frame.BackgroundTransparency = 1
+ frame.Active = true
+ frame.Parent = shield
+
+ local settingsFrame = Instance.new("Frame")
+ settingsFrame.Name = "ReportAbuseStyle"
+ settingsFrame.Size = UDim2.new(1, 0, 1, 0)
+ settingsFrame.Style = Enum.FrameStyle.DropShadow
+ settingsFrame.Active = true
+ settingsFrame.ZIndex = baseZIndex + 1
+ settingsFrame.Parent = frame
+
+ local description = Instance.new("TextLabel")
+ description.Name = "Description"
+ description.Text = "This will send a complete report to a moderator. The moderator will review the chat log and take appropriate action."
+ description.TextColor3 = Color3I(221,221,221)
+ description.Position = UDim2.new(0, 10, 0, 10)
+ description.Size = UDim2.new(1, -20, 0, 40)
+ description.BackgroundTransparency = 1
+ description.Font = Enum.Font.SourceSans
+ description.FontSize = Enum.FontSize.Size18
+ description.TextWrap = true
+ description.ZIndex = baseZIndex + 2
+ description.TextXAlignment = Enum.TextXAlignment.Left
+ description.TextYAlignment = Enum.TextYAlignment.Top
+ description.Parent = settingsFrame
+
+ local playerLabel = Instance.new("TextLabel")
+ playerLabel.Name = "PlayerLabel"
+ playerLabel.Text = "Which player?"
+ playerLabel.BackgroundTransparency = 1
+ playerLabel.Font = Enum.Font.SourceSans
+ playerLabel.FontSize = Enum.FontSize.Size18
+ playerLabel.Position = UDim2.new(0.025,20,0,92)
+ playerLabel.Size = UDim2.new(0.4,0,0,36)
+ playerLabel.TextColor3 = Color3I(255,255,255)
+ playerLabel.TextXAlignment = Enum.TextXAlignment.Left
+ playerLabel.ZIndex = baseZIndex + 2
+ playerLabel.Parent = settingsFrame
+
+ local gameOrPlayerLabel = Instance.new("TextLabel")
+ gameOrPlayerLabel.Name = "TypeLabel"
+ gameOrPlayerLabel.Text = "Game or Player:"
+ gameOrPlayerLabel.BackgroundTransparency = 1
+ gameOrPlayerLabel.Font = Enum.Font.SourceSans
+ gameOrPlayerLabel.FontSize = Enum.FontSize.Size18
+ gameOrPlayerLabel.Position = UDim2.new(0.025,20,0,55)
+ gameOrPlayerLabel.Size = UDim2.new(0.4,0,0,36)
+ gameOrPlayerLabel.TextColor3 = Color3I(255,255,255)
+ gameOrPlayerLabel.TextXAlignment = Enum.TextXAlignment.Left
+ gameOrPlayerLabel.ZIndex = baseZIndex + 2
+ gameOrPlayerLabel.Parent = settingsFrame
+
+ local abuseLabel = Instance.new("TextLabel")
+ abuseLabel.Name = "AbuseLabel"
+ abuseLabel.Text = "Type of Abuse:"
+ abuseLabel.Font = Enum.Font.SourceSans
+ abuseLabel.BackgroundTransparency = 1
+ abuseLabel.FontSize = Enum.FontSize.Size18
+ abuseLabel.Position = UDim2.new(0.025,20,0,131)
+ abuseLabel.Size = UDim2.new(0.4,0,0,36)
+ abuseLabel.TextColor3 = Color3I(255,255,255)
+ abuseLabel.TextXAlignment = Enum.TextXAlignment.Left
+ abuseLabel.ZIndex = baseZIndex + 2
+ abuseLabel.Parent = settingsFrame
+
+ local abusingPlayer = nil
+ local abuse = nil
+ local submitReportButton = nil
+ local gameOrPlayer = nil
+
+ local updatePlayerSelection = nil
+ local createPlayersDropDown = function()
+ local players = game:GetService("Players")
+ local playerNames = {}
+ local nameToPlayer = {}
+ local children = players:GetChildren()
+ local pos = 1
+ if children then
+ for i, player in ipairs(children) do
+ if player:IsA("Player") and player ~= localPlayer then
+ playerNames[pos] = player.Name
+ nameToPlayer[player.Name] = player
+ pos = pos + 1
+ end
+ end
+ end
+ local playerDropDown = nil
+ playerDropDown, updatePlayerSelection = RbxGui.CreateDropDownMenu(playerNames,
+ function(playerName)
+ abusingPlayer = nameToPlayer[playerName]
+ if abuse and abusingPlayer then
+ submitReportButton.Active = true
+ end
+ end, false, true, baseZIndex)
+ playerDropDown.Name = "PlayersComboBox"
+ playerDropDown.ZIndex = baseZIndex + 2
+ playerDropDown.Position = UDim2.new(.425, 0, 0, 94)
+ playerDropDown.Size = UDim2.new(.55,0,0,32)
+
+ return playerDropDown
+ end
+
+ local gameOrPlayerTable = {"Game","Player"}
+ local gameOrPlayerDropDown = nil
+ gameOrPlayerDropDown = RbxGui.CreateDropDownMenu(gameOrPlayerTable,
+ function(gameOrPlayerText)
+ gameOrPlayer = gameOrPlayerText
+ if gameOrPlayer == "Game" then
+ submitReportButton.Active = true
+ playerLabel.Visible = false
+ local playerDropDown = gameOrPlayerDropDown.Parent:FindFirstChild("PlayersComboBox")
+ if playerDropDown then
+ playerDropDown.Visible = false
+ end
+ else
+ playerLabel.Visible = true
+ local playerDropDown = gameOrPlayerDropDown.Parent:FindFirstChild("PlayersComboBox")
+ if playerDropDown then
+ playerDropDown.Visible = true
+ end
+ end
+ end, true, true, baseZIndex)
+ gameOrPlayerDropDown.Name = "TypeComboBox"
+ gameOrPlayerDropDown.ZIndex = baseZIndex + 2
+ gameOrPlayerDropDown.Position = UDim2.new(0.425, 0, 0, 55)
+ gameOrPlayerDropDown.Size = UDim2.new(0.55,0,0,32)
+ gameOrPlayerDropDown.Parent = settingsFrame
+
+ local abuses = {"Swearing","Bullying","Scamming","Dating","Cheating/Exploiting","Personal Questions","Offsite Links","Bad Model or Script","Bad Username"}
+ local abuseDropDown, updateAbuseSelection = RbxGui.CreateDropDownMenu(abuses,
+ function(abuseText)
+ abuse = abuseText
+ if abuse and abusingPlayer then
+ submitReportButton.Active = true
+ end
+ end, true, true, baseZIndex)
+ abuseDropDown.Name = "AbuseComboBox"
+ abuseDropDown.ZIndex = baseZIndex + 2
+ abuseDropDown.Position = UDim2.new(0.425, 0, 0, 133)
+ abuseDropDown.Size = UDim2.new(0.55,0,0,32)
+ abuseDropDown.Parent = settingsFrame
+
+ local shortDescriptionLabel = Instance.new("TextLabel")
+ shortDescriptionLabel.Name = "ShortDescriptionLabel"
+ shortDescriptionLabel.Text = "Short Description: (optional)"
+ shortDescriptionLabel.Font = Enum.Font.SourceSans
+ shortDescriptionLabel.FontSize = Enum.FontSize.Size18
+ shortDescriptionLabel.Position = UDim2.new(0.025,0,0,165)
+ shortDescriptionLabel.Size = UDim2.new(0.95,0,0,36)
+ shortDescriptionLabel.TextColor3 = Color3I(255,255,255)
+ shortDescriptionLabel.TextXAlignment = Enum.TextXAlignment.Left
+ shortDescriptionLabel.BackgroundTransparency = 1
+ shortDescriptionLabel.ZIndex = baseZIndex + 2
+ shortDescriptionLabel.Parent = settingsFrame
+
+ local shortDescriptionWrapper = Instance.new("Frame")
+ shortDescriptionWrapper.Name = "ShortDescriptionWrapper"
+ shortDescriptionWrapper.Position = UDim2.new(0.025,0,0,195)
+ shortDescriptionWrapper.Size = UDim2.new(0.95,0,1,-250)
+ shortDescriptionWrapper.BackgroundColor3 = Color3I(206,206,206)
+ shortDescriptionWrapper.BorderSizePixel = 0
+ shortDescriptionWrapper.ZIndex = baseZIndex + 2
+ shortDescriptionWrapper.Parent = settingsFrame
+
+ local shortDescriptionBox = Instance.new("TextBox")
+ shortDescriptionBox.Name = "TextBox"
+ shortDescriptionBox.Text = ""
+ shortDescriptionBox.ClearTextOnFocus = false
+ shortDescriptionBox.Font = Enum.Font.SourceSans
+ shortDescriptionBox.FontSize = Enum.FontSize.Size18
+ shortDescriptionBox.Position = UDim2.new(0,3,0,3)
+ shortDescriptionBox.Size = UDim2.new(1,-6,1,-6)
+ shortDescriptionBox.TextColor3 = Color3I(0,0,0)
+ shortDescriptionBox.TextXAlignment = Enum.TextXAlignment.Left
+ shortDescriptionBox.TextYAlignment = Enum.TextYAlignment.Top
+ shortDescriptionBox.TextWrap = true
+ shortDescriptionBox.BackgroundColor3 = Color3I(206,206,206)
+ shortDescriptionBox.BorderColor3 = Color3I(206,206,206)
+ shortDescriptionBox.ZIndex = baseZIndex + 2
+ shortDescriptionBox.Parent = shortDescriptionWrapper
+
+ submitReportButton = Instance.new("TextButton")
+ submitReportButton.Name = "SubmitReportBtn"
+ submitReportButton.Active = false
+ submitReportButton.Modal = true
+ submitReportButton.Font = Enum.Font.SourceSans
+ submitReportButton.FontSize = Enum.FontSize.Size18
+ submitReportButton.Position = UDim2.new(0.1, 0, 1, -50)
+ submitReportButton.Size = UDim2.new(0.35,0,0,40)
+ submitReportButton.AutoButtonColor = true
+ submitReportButton.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ submitReportButton.Text = "Submit Report"
+ submitReportButton.TextColor3 = Color3I(255,255,255)
+ submitReportButton.ZIndex = baseZIndex + 2
+ submitReportButton.Parent = settingsFrame
+
+ submitReportButton.MouseButton1Click:connect(function()
+ if submitReportButton.Active then
+ if abuse and abusingPlayer then
+ frame.Visible = false
+ if gameOrPlayer == "Player" then
+ game.Players:ReportAbuse(abusingPlayer, abuse, shortDescriptionBox.Text)
+ else
+ game.Players:ReportAbuse(nil, abuse, shortDescriptionBox.Text)
+ end
+ if abuse == "Cheating/Exploiting" then
+ recordedMessageBox.Visible = true
+ elseif abuse == "Bullying" or abuse == "Swearing" then
+ calmingMessageBox.Visible = true
+ else
+ normalMessageBox.Visible = true
+ end
+ else
+ closeAndResetDialog()
+ end
+ end
+ end)
+
+ local cancelButton = Instance.new("TextButton")
+ cancelButton.Name = "CancelBtn"
+ cancelButton.Font = Enum.Font.SourceSans
+ cancelButton.FontSize = Enum.FontSize.Size18
+ cancelButton.Position = UDim2.new(0.55, 0, 1, -50)
+ cancelButton.Size = UDim2.new(0.35,0,0,40)
+ cancelButton.AutoButtonColor = true
+ cancelButton.Style = Enum.ButtonStyle.RobloxRoundDefaultButton
+ cancelButton.Text = "Cancel"
+ cancelButton.TextColor3 = Color3I(255,255,255)
+ cancelButton.ZIndex = baseZIndex + 2
+ cancelButton.Parent = settingsFrame
+
+ closeAndResetDialog = function()
+ --Delete old player combo box
+ local oldComboBox = settingsFrame:FindFirstChild("PlayersComboBox")
+ if oldComboBox then
+ oldComboBox.Parent = nil
+ end
+
+ abusingPlayer = nil updatePlayerSelection(nil)
+ abuse = nil updateAbuseSelection(nil)
+ submitReportButton.Active = false
+ shortDescriptionBox.Text = ""
+ frame.Visible = true
+ calmingMessageBox.Visible = false
+ recordedMessageBox.Visible = false
+ normalMessageBox.Visible = false
+ shield.Visible = false
+ reportAbuseButton.Active = true
+ game.GuiService:RemoveCenterDialog(shield)
+ end
+
+ cancelButton.MouseButton1Click:connect(closeAndResetDialog)
+
+ reportAbuseButton.MouseButton1Click:connect(
+ function()
+ createPlayersDropDown().Parent = settingsFrame
+ table.insert(centerDialogs,shield)
+ game.GuiService:AddCenterDialog(shield, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ reportAbuseButton.Active = false
+ shield.Visible = true
+ mainShield.Visible = false
+ end,
+ --HideFunction
+ function()
+ reportAbuseButton.Active = true
+ shield.Visible = false
+ end)
+ end)
+
+ robloxLock(shield)
+ return shield
+end
+
+local createChatBar = function()
+ --Only show a chat bar if we are a NetworkClient
+ waitForChild(game, "NetworkClient")
+
+ waitForChild(game, "Players")
+ waitForProperty(game.Players, "LocalPlayer")
+
+ local chatBar = Instance.new("Frame")
+ chatBar.Name = "ChatBar"
+ chatBar.Size = UDim2.new(1, 0, 0, 22)
+ chatBar.Position = UDim2.new(0, 0, 1, 0)
+ chatBar.BackgroundColor3 = Color3.new(0,0,0)
+ chatBar.BorderSizePixel = 0
+
+ local chatBox = Instance.new("TextBox")
+ chatBox.Text = ""
+ chatBox.Visible = false
+ chatBox.Size = UDim2.new(1,-4,1,0)
+ chatBox.Position = UDim2.new(0,2,0,0)
+ chatBox.TextXAlignment = Enum.TextXAlignment.Left
+ chatBox.Font = Enum.Font.SourceSansBold
+ chatBox.ClearTextOnFocus = false
+ chatBox.FontSize = Enum.FontSize.Size14
+ chatBox.TextColor3 = Color3.new(1,1,1)
+ chatBox.BackgroundTransparency = 1
+ --chatBox.Parent = chatBar
+
+ local chatButton = Instance.new("TextButton")
+ chatButton.Size = UDim2.new(1,-4,1,0)
+ chatButton.Position = UDim2.new(0,2,0,0)
+ chatButton.AutoButtonColor = false
+ chatButton.Text = "To chat click here or press \"/\" key"
+ chatButton.TextXAlignment = Enum.TextXAlignment.Left
+ chatButton.Font = Enum.Font.SourceSansBold
+ chatButton.FontSize = Enum.FontSize.Size14
+ chatButton.TextColor3 = Color3.new(1,1,1)
+ chatButton.BackgroundTransparency = 1
+ --chatButton.Parent = chatBar
+
+ local activateChat = function()
+ if chatBox.Visible then
+ return
+ end
+ chatButton.Visible = false
+ chatBox.Text = ""
+ chatBox.Visible = true
+ chatBox:CaptureFocus()
+ end
+
+ chatButton.MouseButton1Click:connect(activateChat)
+
+ local hotKeyEnabled = true
+ local toggleHotKey = function(value)
+ hotKeyEnabled = value
+ end
+
+ local guiService = game:GetService("GuiService")
+ local newChatMode = pcall(function()
+ --guiService:AddSpecialKey(Enum.SpecialKey.ChatHotkey)
+ --guiService.SpecialKeyPressed:connect(function(key) if key == Enum.SpecialKey.ChatHotkey and hotKeyEnabled then activateChat() end end)
+ end)
+ if not newChatMode then
+ --guiService:AddKey("/")
+ --guiService.KeyPressed:connect(function(key) if key == "/" and hotKeyEnabled then activateChat() end end)
+ end
+
+ chatBox.FocusLost:connect(
+ function(enterPressed)
+ if enterPressed then
+ if chatBox.Text ~= "" then
+ local str = chatBox.Text
+ if string.sub(str, 1, 1) == '%' then
+ game.Players:TeamChat(string.sub(str, 2))
+ else
+ game.Players:Chat(str)
+ end
+ end
+ end
+ chatBox.Text = ""
+ chatBox.Visible = false
+ chatButton.Visible = true
+ end)
+ robloxLock(chatBar)
+ return chatBar, toggleHotKey
+end
+
+--Spawn a thread for the Save dialogs
+local isSaveDialogSupported = pcall(function() local var = game.LocalSaveEnabled end)
+if isSaveDialogSupported then
+ delay(0,
+ function()
+ local saveDialogs = createSaveDialogs()
+ saveDialogs.Parent = gui
+
+ game.RequestShutdown = function()
+ table.insert(centerDialogs,saveDialogs)
+ game.GuiService:AddCenterDialog(saveDialogs, Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ saveDialogs.Visible = true
+ end,
+ --HideFunction
+ function()
+ saveDialogs.Visible = false
+ end)
+
+ return true
+ end
+ end)
+end
+
+--Spawn a thread to listen to leave game prompts
+Spawn(function()
+ local showLeaveEvent = nil
+ pcall(function() showLeaveEvent = Game:GetService("GuiService").ShowLeaveConfirmation end)
+ if not showLeaveEvent then return end
+
+ function showLeaveConfirmation()
+ if showMainMenu then
+ showMainMenu("LeaveConfirmationMenu","down",UDim2.new(0,525,0,300))
+ end
+ end
+
+ Game:GetService("GuiService").ShowLeaveConfirmation:connect(function( )
+ if currentMenuSelection == nil then
+ showLeaveConfirmation()
+ else
+ resumeGameFunction(gui.UserSettingsShield)
+ end
+ end)
+end)
+
+--Spawn a thread for the Report Abuse dialogs
+delay(0,
+ function()
+ createReportAbuseDialog().Parent = gui
+ waitForChild(gui,"UserSettingsShield")
+ waitForChild(gui.UserSettingsShield, "Settings")
+ waitForChild(gui.UserSettingsShield.Settings,"SettingsStyle")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle,"GameMainMenu")
+ waitForChild(gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu, "ReportAbuseButton")
+ gui.UserSettingsShield.Settings.SettingsStyle.GameMainMenu.ReportAbuseButton.Active = true
+ end)
+
+end --LoadLibrary if
diff --git a/asset/backup/5 b/asset/backup/5
new file mode 100644
index 0000000..033ec2b
--- /dev/null
+++ b/asset/backup/5
@@ -0,0 +1,110 @@
+%5%
+local controlFrame = script.Parent:FindFirstChild("ControlFrame")
+
+if not controlFrame then return end
+
+local topLeftControl = controlFrame:FindFirstChild("TopLeftControl")
+local bottomLeftControl = controlFrame:FindFirstChild("BottomLeftControl")
+local bottomRightControl = controlFrame:FindFirstChild("BottomRightControl")
+
+
+local frameTip = Instance.new("TextLabel")
+frameTip.Name = "ToolTip"
+frameTip.Text = ""
+frameTip.Font = Enum.Font.ArialBold
+frameTip.FontSize = Enum.FontSize.Size12
+frameTip.TextColor3 = Color3.new(1,1,1)
+frameTip.BorderSizePixel = 0
+frameTip.ZIndex = 10
+frameTip.Size = UDim2.new(2,0,1,0)
+frameTip.Position = UDim2.new(1,0,0,0)
+frameTip.BackgroundColor3 = Color3.new(0,0,0)
+frameTip.BackgroundTransparency = 1
+frameTip.TextTransparency = 1
+frameTip.TextWrap = true
+
+local inside = Instance.new("BoolValue")
+inside.Name = "inside"
+inside.Value = false
+inside.Parent = frameTip
+
+function setUpListeners(frameToListen)
+ local fadeSpeed = 0.1
+ frameToListen.Parent.MouseEnter:connect(function()
+ if frameToListen:FindFirstChild("inside") then
+ frameToListen.inside.Value = true
+ wait(1.2)
+ if frameToListen.inside.Value then
+ while frameToListen.inside.Value and frameToListen.BackgroundTransparency > 0 do
+ frameToListen.BackgroundTransparency = frameToListen.BackgroundTransparency - fadeSpeed
+ frameToListen.TextTransparency = frameToListen.TextTransparency - fadeSpeed
+ wait()
+ end
+ end
+ end
+ end)
+ function killTip(killFrame)
+ killFrame.inside.Value = false
+ killFrame.BackgroundTransparency = 1
+ killFrame.TextTransparency = 1
+ end
+ frameToListen.Parent.MouseLeave:connect(function() killTip(frameToListen) end)
+ frameToListen.Parent.MouseButton1Click:connect(function() killTip(frameToListen) end)
+end
+
+function createSettingsButtonTip(parent)
+ if parent == nil then
+ parent = bottomLeftControl:FindFirstChild("SettingsButton")
+ end
+
+ local toolTip = frameTip:clone()
+ toolTip.RobloxLocked = true
+ toolTip.Text = "Settings/Leave Game"
+ toolTip.Position = UDim2.new(0,0,0,-18)
+ toolTip.Size = UDim2.new(0,120,0,20)
+ toolTip.Parent = parent
+ setUpListeners(toolTip)
+end
+
+wait(5) -- make sure we are loaded in, won't need tool tips for first 5 seconds anyway
+
+---------------- set up Bottom Left Tool Tips -------------------------
+
+local bottomLeftChildren = bottomLeftControl:GetChildren()
+local hasSettingsTip = false
+
+for i = 1, #bottomLeftChildren do
+
+ if bottomLeftChildren[i].Name == "Exit" then
+ local exitTip = frameTip:clone()
+ exitTip.RobloxLocked = true
+ exitTip.Text = "Leave Place"
+ exitTip.Position = UDim2.new(0,0,-1,0)
+ exitTip.Size = UDim2.new(1,0,1,0)
+ exitTip.Parent = bottomLeftChildren[i]
+ setUpListeners(exitTip)
+ elseif bottomLeftChildren[i].Name == "SettingsButton" then
+ hasSettingsTip = true
+ createSettingsButtonTip(bottomLeftChildren[i])
+ end
+end
+
+---------------- set up Bottom Right Tool Tips -------------------------
+
+local bottomRightChildren = bottomRightControl:GetChildren()
+
+for i = 1, #bottomRightChildren do
+ if bottomRightChildren[i].Name:find("Camera") ~= nil then
+ local cameraTip = frameTip:clone()
+ cameraTip.RobloxLocked = true
+ cameraTip.Text = "Camera View"
+ if bottomRightChildren[i].Name:find("Zoom") then
+ cameraTip.Position = UDim2.new(-1,0,-1.5)
+ else
+ cameraTip.Position = UDim2.new(0,0,-1.5,0)
+ end
+ cameraTip.Size = UDim2.new(2,0,1.25,0)
+ cameraTip.Parent = bottomRightChildren[i]
+ setUpListeners(cameraTip)
+ end
+end
diff --git a/asset/backup/7 b/asset/backup/7
new file mode 100644
index 0000000..c3f9448
--- /dev/null
+++ b/asset/backup/7
@@ -0,0 +1,558 @@
+%7%
+function waitForProperty(instance, name)
+ while not instance[name] do
+ instance.Changed:wait()
+ end
+end
+
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+
+local mainFrame
+local choices = {}
+local lastChoice
+local choiceMap = {}
+local currentConversationDialog
+local currentConversationPartner
+local currentAbortDialogScript
+
+local tooFarAwayMessage = "You are too far away to chat!"
+local tooFarAwaySize = 300
+local characterWanderedOffMessage = "Chat ended because you walked away"
+local characterWanderedOffSize = 350
+local conversationTimedOut = "Chat ended because you didn't reply"
+local conversationTimedOutSize = 350
+
+local player
+local screenGui
+local chatNotificationGui
+local messageDialog
+local timeoutScript
+local reenableDialogScript
+local dialogMap = {}
+local dialogConnections = {}
+
+local gui = nil
+waitForChild(game,"CoreGui")
+waitForChild(game.CoreGui,"RobloxGui")
+if game.CoreGui.RobloxGui:FindFirstChild("ControlFrame") then
+ gui = game.CoreGui.RobloxGui.ControlFrame
+else
+ gui = game.CoreGui.RobloxGui
+end
+
+function currentTone()
+ if currentConversationDialog then
+ return currentConversationDialog.Tone
+ else
+ return Enum.DialogTone.Neutral
+ end
+end
+
+
+function createChatNotificationGui()
+ chatNotificationGui = Instance.new("BillboardGui")
+ chatNotificationGui.Name = "ChatNotificationGui"
+ chatNotificationGui.ExtentsOffset = Vector3.new(0,1,0)
+ chatNotificationGui.Size = UDim2.new(4, 0, 5.42857122, 0)
+ chatNotificationGui.SizeOffset = Vector2.new(0,0)
+ chatNotificationGui.StudsOffset = Vector3.new(0.4, 4.3, 0)
+ chatNotificationGui.Enabled = true
+ chatNotificationGui.RobloxLocked = true
+ chatNotificationGui.Active = true
+
+ local image = Instance.new("ImageLabel")
+ image.Name = "Image"
+ image.Active = false
+ image.BackgroundTransparency = 1
+ image.Position = UDim2.new(0,0,0,0)
+ image.Size = UDim2.new(1.0,0,1.0,0)
+ image.Image = ""
+ image.RobloxLocked = true
+ image.Parent = chatNotificationGui
+
+
+ local button = Instance.new("ImageButton")
+ button.Name = "Button"
+ button.AutoButtonColor = false
+ button.Position = UDim2.new(0.0879999995, 0, 0.0529999994, 0)
+ button.Size = UDim2.new(0.829999983, 0, 0.460000008, 0)
+ button.Image = ""
+ button.BackgroundTransparency = 1
+ button.RobloxLocked = true
+ button.Parent = image
+end
+
+function getChatColor(tone)
+ if tone == Enum.DialogTone.Neutral then
+ return Enum.ChatColor.Blue
+ elseif tone == Enum.DialogTone.Friendly then
+ return Enum.ChatColor.Green
+ elseif tone == Enum.DialogTone.Enemy then
+ return Enum.ChatColor.Red
+ end
+end
+
+function styleChoices(tone)
+ for i, obj in pairs(choices) do
+ resetColor(obj, tone)
+ end
+ resetColor(lastChoice, tone)
+end
+
+function styleMainFrame(tone)
+ if tone == Enum.DialogTone.Neutral then
+ mainFrame.Style = Enum.FrameStyle.ChatBlue
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botBlue_tailRight.png"
+ elseif tone == Enum.DialogTone.Friendly then
+ mainFrame.Style = Enum.FrameStyle.ChatGreen
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botGreen_tailRight.png"
+ elseif tone == Enum.DialogTone.Enemy then
+ mainFrame.Style = Enum.FrameStyle.ChatRed
+ mainFrame.Tail.Image = "rbxasset://textures/chatBubble_botRed_tailRight.png"
+ end
+
+ styleChoices(tone)
+end
+function setChatNotificationTone(gui, purpose, tone)
+ if tone == Enum.DialogTone.Neutral then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botBlue_notify_bkg.png"
+ elseif tone == Enum.DialogTone.Friendly then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botGreen_notify_bkg.png"
+ elseif tone == Enum.DialogTone.Enemy then
+ gui.Image.Image = "rbxasset://textures/chatBubble_botRed_notify_bkg.png"
+ end
+ if purpose == Enum.DialogPurpose.Quest then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_bang.png"
+ elseif purpose == Enum.DialogPurpose.Help then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_question.png"
+ elseif purpose == Enum.DialogPurpose.Shop then
+ gui.Image.Button.Image = "rbxasset://textures/chatBubble_bot_notify_money.png"
+ end
+end
+
+function createMessageDialog()
+ messageDialog = Instance.new("Frame");
+ messageDialog.Name = "DialogScriptMessage"
+ messageDialog.Style = Enum.FrameStyle.RobloxRound
+ messageDialog.Visible = false
+
+ local text = Instance.new("TextLabel")
+ text.Name = "Text"
+ text.Position = UDim2.new(0,0,0,-1)
+ text.Size = UDim2.new(1,0,1,0)
+ text.FontSize = Enum.FontSize.Size14
+ text.BackgroundTransparency = 1
+ text.TextColor3 = Color3.new(1,1,1)
+ text.RobloxLocked = true
+ text.Parent = messageDialog
+end
+
+function showMessage(msg, size)
+ messageDialog.Text.Text = msg
+ messageDialog.Size = UDim2.new(0,size,0,40)
+ messageDialog.Position = UDim2.new(0.5, -size/2, 0.5, -40)
+ messageDialog.Visible = true
+ wait(2)
+ messageDialog.Visible = false
+end
+
+function variableDelay(str)
+ local length = math.min(string.len(str), 100)
+ wait(0.75 + ((length/75) * 1.5))
+end
+
+function resetColor(frame, tone)
+ if tone == Enum.DialogTone.Neutral then
+ frame.BackgroundColor3 = Color3.new(0/255, 0/255, 179/255)
+ frame.Number.TextColor3 = Color3.new(45/255, 142/255, 245/255)
+ elseif tone == Enum.DialogTone.Friendly then
+ frame.BackgroundColor3 = Color3.new(0/255, 77/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(0/255, 190/255, 0/255)
+ elseif tone == Enum.DialogTone.Enemy then
+ frame.BackgroundColor3 = Color3.new(140/255, 0/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(255/255,88/255, 79/255)
+ end
+end
+
+function highlightColor(frame, tone)
+ if tone == Enum.DialogTone.Neutral then
+ frame.BackgroundColor3 = Color3.new(2/255, 108/255, 255/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ elseif tone == Enum.DialogTone.Friendly then
+ frame.BackgroundColor3 = Color3.new(0/255, 128/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ elseif tone == Enum.DialogTone.Enemy then
+ frame.BackgroundColor3 = Color3.new(204/255, 0/255, 0/255)
+ frame.Number.TextColor3 = Color3.new(1, 1, 1)
+ end
+end
+
+function wanderDialog()
+ mainFrame.Visible = false
+ endDialog()
+ showMessage(characterWanderedOffMessage, characterWanderedOffSize)
+end
+
+function timeoutDialog()
+ mainFrame.Visible = false
+ endDialog()
+ showMessage(conversationTimedOut, conversationTimedOutSize)
+end
+function normalEndDialog()
+ endDialog()
+end
+
+function endDialog()
+ if currentAbortDialogScript then
+ currentAbortDialogScript:Remove()
+ currentAbortDialogScript = nil
+ end
+
+ local dialog = currentConversationDialog
+ currentConversationDialog = nil
+ if dialog and dialog.InUse then
+ local reenableScript = reenableDialogScript:Clone()
+ reenableScript.archivable = false
+ reenableScript.Disabled = false
+ reenableScript.Parent = dialog
+ end
+
+ for dialog, gui in pairs(dialogMap) do
+ if dialog and gui then
+ gui.Enabled = not dialog.InUse
+ end
+ end
+
+ currentConversationPartner = nil
+end
+
+function sanitizeMessage(msg)
+ if string.len(msg) == 0 then
+ return "..."
+ else
+ return msg
+ end
+end
+
+function selectChoice(choice)
+ renewKillswitch(currentConversationDialog)
+
+ --First hide the Gui
+ mainFrame.Visible = false
+ if choice == lastChoice then
+ game.Chat:Chat(game.Players.LocalPlayer.Character, "Goodbye!", getChatColor(currentTone()))
+
+ normalEndDialog()
+ else
+ local dialogChoice = choiceMap[choice]
+
+ game.Chat:Chat(game.Players.LocalPlayer.Character, sanitizeMessage(dialogChoice.UserDialog), getChatColor(currentTone()))
+ wait(1)
+ currentConversationDialog:SignalDialogChoiceSelected(player, dialogChoice)
+ game.Chat:Chat(currentConversationPartner, sanitizeMessage(dialogChoice.ResponseDialog), getChatColor(currentTone()))
+
+ variableDelay(dialogChoice.ResponseDialog)
+ presentDialogChoices(currentConversationPartner, dialogChoice:GetChildren())
+ end
+end
+
+function newChoice(numberText)
+ local frame = Instance.new("TextButton")
+ frame.BackgroundColor3 = Color3.new(0/255, 0/255, 179/255)
+ frame.AutoButtonColor = false
+ frame.BorderSizePixel = 0
+ frame.Text = ""
+ frame.MouseEnter:connect(function() highlightColor(frame, currentTone()) end)
+ frame.MouseLeave:connect(function() resetColor(frame, currentTone()) end)
+ frame.MouseButton1Click:connect(function() selectChoice(frame) end)
+ frame.RobloxLocked = true
+
+ local number = Instance.new("TextLabel")
+ number.Name = "Number"
+ number.TextColor3 = Color3.new(127/255, 212/255, 255/255)
+ number.Text = numberText
+ number.FontSize = Enum.FontSize.Size14
+ number.BackgroundTransparency = 1
+ number.Position = UDim2.new(0,4,0,2)
+ number.Size = UDim2.new(0,20,0,24)
+ number.TextXAlignment = Enum.TextXAlignment.Left
+ number.TextYAlignment = Enum.TextYAlignment.Top
+ number.RobloxLocked = true
+ number.Parent = frame
+
+ local prompt = Instance.new("TextLabel")
+ prompt.Name = "UserPrompt"
+ prompt.BackgroundTransparency = 1
+ prompt.TextColor3 = Color3.new(1,1,1)
+ prompt.FontSize = Enum.FontSize.Size14
+ prompt.Position = UDim2.new(0,28, 0, 2)
+ prompt.Size = UDim2.new(1,-32, 1, -4)
+ prompt.TextXAlignment = Enum.TextXAlignment.Left
+ prompt.TextYAlignment = Enum.TextYAlignment.Top
+ prompt.TextWrap = true
+ prompt.RobloxLocked = true
+ prompt.Parent = frame
+
+ return frame
+end
+function initialize(parent)
+ choices[1] = newChoice("1)")
+ choices[2] = newChoice("2)")
+ choices[3] = newChoice("3)")
+ choices[4] = newChoice("4)")
+
+ lastChoice = newChoice("5)")
+ lastChoice.UserPrompt.Text = "Goodbye!"
+ lastChoice.Size = UDim2.new(1,0,0,28)
+
+ mainFrame = Instance.new("Frame")
+ mainFrame.Name = "UserDialogArea"
+ mainFrame.Size = UDim2.new(0, 350, 0, 200)
+ mainFrame.Style = Enum.FrameStyle.ChatBlue
+ mainFrame.Visible = false
+
+ imageLabel = Instance.new("ImageLabel")
+ imageLabel.Name = "Tail"
+ imageLabel.Size = UDim2.new(0,62,0,53)
+ imageLabel.Position = UDim2.new(1,8,0.25)
+ imageLabel.Image = "rbxasset://textures/chatBubble_botBlue_tailRight.png"
+ imageLabel.BackgroundTransparency = 1
+ imageLabel.RobloxLocked = true
+ imageLabel.Parent = mainFrame
+
+ for n, obj in pairs(choices) do
+ obj.RobloxLocked = true
+ obj.Parent = mainFrame
+ end
+ lastChoice.RobloxLocked = true
+ lastChoice.Parent = mainFrame
+
+ mainFrame.RobloxLocked = true
+ mainFrame.Parent = parent
+end
+
+function presentDialogChoices(talkingPart, dialogChoices)
+ if not currentConversationDialog then
+ return
+ end
+
+ currentConversationPartner = talkingPart
+ sortedDialogChoices = {}
+ for n, obj in pairs(dialogChoices) do
+ if obj:IsA("DialogChoice") then
+ table.insert(sortedDialogChoices, obj)
+ end
+ end
+ table.sort(sortedDialogChoices, function(a,b) return a.Name < b.Name end)
+
+ if #sortedDialogChoices == 0 then
+ normalEndDialog()
+ return
+ end
+
+ local pos = 1
+ local yPosition = 0
+ choiceMap = {}
+ for n, obj in pairs(choices) do
+ obj.Visible = false
+ end
+
+ for n, obj in pairs(sortedDialogChoices) do
+ if pos <= #choices then
+ --3 lines is the maximum, set it to that temporarily
+ choices[pos].Size = UDim2.new(1, 0, 0, 24*3)
+ choices[pos].UserPrompt.Text = obj.UserDialog
+ local height = math.ceil(choices[pos].UserPrompt.TextBounds.Y/24)*24
+
+ choices[pos].Position = UDim2.new(0, 0, 0, yPosition)
+ choices[pos].Size = UDim2.new(1, 0, 0, height)
+ choices[pos].Visible = true
+
+ choiceMap[choices[pos]] = obj
+
+ yPosition = yPosition + height
+ pos = pos + 1
+ end
+ end
+
+ lastChoice.Position = UDim2.new(0,0,0,yPosition)
+ lastChoice.Number.Text = pos .. ")"
+
+ mainFrame.Size = UDim2.new(0, 350, 0, yPosition+24+32)
+ mainFrame.Position = UDim2.new(0,20,0.0, -mainFrame.Size.Y.Offset-20)
+ styleMainFrame(currentTone())
+ mainFrame.Visible = true
+end
+
+function doDialog(dialog)
+ while not Instance.Lock(dialog, player) do
+ wait()
+ end
+
+ if dialog.InUse then
+ Instance.Unlock(dialog)
+ return
+ else
+ dialog.InUse = true
+ Instance.Unlock(dialog)
+ end
+
+ currentConversationDialog = dialog
+ game.Chat:Chat(dialog.Parent, dialog.InitialPrompt, getChatColor(dialog.Tone))
+ variableDelay(dialog.InitialPrompt)
+
+ presentDialogChoices(dialog.Parent, dialog:GetChildren())
+end
+
+function renewKillswitch(dialog)
+ if currentAbortDialogScript then
+ currentAbortDialogScript:Remove()
+ currentAbortDialogScript = nil
+ end
+
+ currentAbortDialogScript = timeoutScript:Clone()
+ currentAbortDialogScript.archivable = false
+ currentAbortDialogScript.Disabled = false
+ currentAbortDialogScript.Parent = dialog
+end
+
+function checkForLeaveArea()
+ while currentConversationDialog do
+ if currentConversationDialog.Parent and (player:DistanceFromCharacter(currentConversationDialog.Parent.Position) >= currentConversationDialog.ConversationDistance) then
+ wanderDialog()
+ end
+ wait(1)
+ end
+end
+
+function startDialog(dialog)
+ if dialog.Parent and dialog.Parent:IsA("BasePart") then
+ if player:DistanceFromCharacter(dialog.Parent.Position) >= dialog.ConversationDistance then
+ showMessage(tooFarAwayMessage, tooFarAwaySize)
+ return
+ end
+
+ for dialog, gui in pairs(dialogMap) do
+ if dialog and gui then
+ gui.Enabled = false
+ end
+ end
+
+ renewKillswitch(dialog)
+
+ delay(1, checkForLeaveArea)
+ doDialog(dialog)
+ end
+end
+
+function removeDialog(dialog)
+ if dialogMap[dialog] then
+ dialogMap[dialog]:Remove()
+ dialogMap[dialog] = nil
+ end
+ if dialogConnections[dialog] then
+ dialogConnections[dialog]:disconnect()
+ dialogConnections[dialog] = nil
+ end
+end
+
+function addDialog(dialog)
+ if dialog.Parent then
+ if dialog.Parent:IsA("BasePart") then
+ local chatGui = chatNotificationGui:clone()
+ chatGui.Enabled = not dialog.InUse
+ chatGui.Adornee = dialog.Parent
+ chatGui.RobloxLocked = true
+ chatGui.Parent = game.CoreGui
+ chatGui.Image.Button.MouseButton1Click:connect(function() startDialog(dialog) end)
+ setChatNotificationTone(chatGui, dialog.Purpose, dialog.Tone)
+
+ dialogMap[dialog] = chatGui
+
+ dialogConnections[dialog] = dialog.Changed:connect(function(prop)
+ if prop == "Parent" and dialog.Parent then
+ --This handles the reparenting case, seperate from removal case
+ removeDialog(dialog)
+ addDialog(dialog)
+ elseif prop == "InUse" then
+ chatGui.Enabled = not currentConversationDialog and not dialog.InUse
+ if dialog == currentConversationDialog then
+ timeoutDialog()
+ end
+ elseif prop == "Tone" or prop == "Purpose" then
+ setChatNotificationTone(chatGui, dialog.Purpose, dialog.Tone)
+ end
+ end)
+ else -- still need to listen to parent changes even if current parent is not a BasePart
+ dialogConnections[dialog] = dialog.Changed:connect(function(prop)
+ if prop == "Parent" and dialog.Parent then
+ --This handles the reparenting case, seperate from removal case
+ removeDialog(dialog)
+ addDialog(dialog)
+ end
+ end)
+ end
+ end
+end
+
+function fetchScripts()
+ local model = game:GetService("InsertService"):LoadAsset(39226062)
+ if type(model) == "string" then -- load failed, lets try again
+ wait(0.1)
+ model = game:GetService("InsertService"):LoadAsset(39226062)
+ end
+ if type(model) == "string" then -- not going to work, lets bail
+ return
+ end
+
+ waitForChild(model,"TimeoutScript")
+ timeoutScript = model.TimeoutScript
+ waitForChild(model,"ReenableDialogScript")
+ reenableDialogScript = model.ReenableDialogScript
+end
+
+function onLoad()
+ waitForProperty(game.Players, "LocalPlayer")
+ player = game.Players.LocalPlayer
+ waitForProperty(player, "Character")
+
+ --print("Fetching Scripts")
+ fetchScripts()
+
+ --print("Creating Guis")
+ createChatNotificationGui()
+
+ --print("Creating MessageDialog")
+ createMessageDialog()
+ messageDialog.RobloxLocked = true
+ messageDialog.Parent = gui
+
+ --print("Waiting for BottomLeftControl")
+ waitForChild(gui, "BottomLeftControl")
+
+ --print("Initializing Frame")
+ local frame = Instance.new("Frame")
+ frame.Name = "DialogFrame"
+ frame.Position = UDim2.new(0,0,0,0)
+ frame.Size = UDim2.new(0,0,0,0)
+ frame.BackgroundTransparency = 1
+ frame.RobloxLocked = true
+ frame.Parent = gui.BottomLeftControl
+ initialize(frame)
+
+ --print("Adding Dialogs")
+ game.CollectionService.ItemAdded:connect(function(obj) if obj:IsA("Dialog") then addDialog(obj) end end)
+ game.CollectionService.ItemRemoved:connect(function(obj) if obj:IsA("Dialog") then removeDialog(obj) end end)
+ for i, obj in pairs(game.CollectionService:GetCollection("Dialog")) do
+ if obj:IsA("Dialog") then
+ addDialog(obj)
+ end
+ end
+end
+
+onLoad()
\ No newline at end of file
diff --git a/asset/backup/8 b/asset/backup/8
new file mode 100644
index 0000000..34589f1
--- /dev/null
+++ b/asset/backup/8
@@ -0,0 +1,1368 @@
+%8%
+--Include
+local Create = assert(LoadLibrary("RbxUtility")).Create
+
+-- A Few Script Globals
+local gui
+if script.Parent:FindFirstChild("ControlFrame") then
+ gui = script.Parent:FindFirstChild("ControlFrame")
+else
+ gui = script.Parent
+end
+
+-- Dev-Console Root
+
+local Dev_Container = Create'Frame'{
+ Name = 'DevConsoleContainer';
+ Parent = gui;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.9;
+ Position = UDim2.new(0, 100, 0, 10);
+ Size = UDim2.new(0.5, 20, 0.5, 20);
+ Visible = false;
+ BackgroundTransparency = 0.9;
+}
+
+local ToggleConsole = Create'BindableFunction'{
+ Name = 'ToggleDevConsole';
+ Parent = gui
+}
+
+
+local devConsoleInitialized = false
+function initializeDeveloperConsole()
+ if devConsoleInitialized then
+ return
+ end
+ devConsoleInitialized = true
+
+ ---Dev-Console Variables
+ local LOCAL_CONSOLE = 1
+ local SERVER_CONSOLE = 2
+ local SERVER_STATS = 3
+
+ local MAX_LIST_SIZE = 1000
+
+ local minimumSize = Vector2.new(350, 180)
+ local currentConsole = LOCAL_CONSOLE
+
+ local localMessageList = {}
+ local serverMessageList = {}
+
+ local localOffset = 0
+ local serverOffset = 0
+ local serverStatsOffset = 0
+
+ local errorToggleOn = true
+ local warningToggleOn = true
+ local infoToggleOn = true
+ local outputToggleOn = true
+ local wordWrapToggleOn = false
+
+ local textHolderSize = 0
+
+ local frameNumber = 0
+
+ --Create Dev-Console
+
+ local Dev_Body = Create'Frame'{
+ Name = 'Body';
+ Parent = Dev_Container;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 21);
+ Size = UDim2.new(1, 0, 1, -25);
+ }
+
+ local Dev_OptionsHolder = Create'Frame'{
+ Name = 'OptionsHolder';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 318, 0, 0);
+ Size = UDim2.new(1, -355, 0, 24);
+ ClipsDescendants = true
+ }
+
+ local Dev_OptionsBar = Create'Frame'{
+ Name = 'OptionsBar';
+ Parent = Dev_OptionsHolder;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0.0, -250, 0, 4);
+ Size = UDim2.new(0, 234, 0, 18);
+ }
+
+ local Dev_ErrorToggleFilter = Create'TextButton'{
+ Name = 'ErrorToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 0, 0);
+ Position = UDim2.new(0, 115, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 0, 0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_ErrorToggleFilter;
+ BackgroundColor3 = Color3.new(1.0,0,0);
+ BorderColor3 = Color3.new(1.0, 0, 0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_InfoToggleFilter = Create'TextButton'{
+ Name = 'InfoToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(0.4, 0.5, 1.0);
+ Position = UDim2.new(0, 65, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(0.4, 0.5, 1.0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_InfoToggleFilter;
+ BackgroundColor3 = Color3.new(0.4, 0.5, 1.0);
+ BorderColor3 = Color3.new(0.4, 0.5, 1.0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_OutputToggleFilter = Create'TextButton'{
+ Name = 'OutputToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 40, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 1.0, 1.0);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_OutputToggleFilter;
+ BackgroundColor3 = Color3.new(1.0, 1.0, 1.0);
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_WarningToggleFilter = Create'TextButton'{
+ Name = 'WarningToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(1.0, 0.6, 0.4);
+ Position = UDim2.new(0, 90, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(1.0, 0.6, 0.4);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_WarningToggleFilter;
+ BackgroundColor3 = Color3.new(1.0, 0.6, 0.4);
+ BorderColor3 = Color3.new(1.0, 0.6, 0.4);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ }
+
+ local Dev_WordWrapToggle = Create'TextButton'{
+ Name = 'WordWrapToggleButton';
+ Parent = Dev_OptionsBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BorderColor3 = Color3.new(0.8, 0.8, 0.8);
+ Position = UDim2.new(0, 215, 0, 0);
+ Size = UDim2.new(0, 18, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "";
+ TextColor3 = Color3.new(0.8, 0.8, 0.8);
+ }
+
+ Create'Frame'{
+ Name = 'CheckFrame';
+ Parent = Dev_WordWrapToggle;
+ BackgroundColor3 = Color3.new(0.8, 0.8, 0.8);
+ BorderColor3 = Color3.new(0.8, 0.8, 0.8);
+ Position = UDim2.new(0, 4, 0, 4);
+ Size = UDim2.new(0, 10, 0, 10);
+ Visible = false
+ }
+
+ Create'TextLabel'{
+ Name = 'Filter';
+ Parent = Dev_OptionsBar;
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 40, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Filter";
+ TextColor3 = Color3.new(1, 1, 1);
+ }
+
+ Create'TextLabel'{
+ Name = 'WordWrap';
+ Parent = Dev_OptionsBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 150, 0, 0);
+ Size = UDim2.new(0, 50, 0, 18);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Word Wrap";
+ TextColor3 = Color3.new(1, 1, 1);
+ }
+
+ local Dev_ScrollBar = Create'Frame'{
+ Name = 'ScrollBar';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.9;
+ Position = UDim2.new(1, -20, 0, 26);
+ Size = UDim2.new(0, 20, 1, -50);
+ Visible = false;
+ BackgroundTransparency = 0.9;
+ }
+
+ local Dev_ScrollArea = Create'Frame'{
+ Name = 'ScrollArea';
+ Parent = Dev_ScrollBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 23);
+ Size = UDim2.new(1, 0, 1, -46);
+ BackgroundTransparency = 1;
+ }
+
+ local Dev_Handle = Create'ImageButton'{
+ Name = 'Handle';
+ Parent = Dev_ScrollArea;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, .2, 0);
+ Size = UDim2.new(0, 20, 0, 40);
+ BackgroundTransparency = 0.5;
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_Handle;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0.5, -8);
+ Rotation = 180;
+ Size = UDim2.new(1, 0, 0, 16);
+ Image = "http://www.roblox.com/Asset?id=151205881";
+ }
+
+ local Dev_DownButton = Create'ImageButton'{
+ Name = 'Down';
+ Parent = Dev_ScrollBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 1, -20);
+ Size = UDim2.new(0, 20, 0, 20);
+ BackgroundTransparency = 0.5;
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_DownButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Rotation = 180;
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ local Dev_UpButton = Create'ImageButton'{
+ Name = 'Up';
+ Parent = Dev_ScrollBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_UpButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ local flagExists, flagValue = pcall(function () return settings():GetFFlag("ConsoleCodeExecutionEnabled") end)
+ local codeExecutionEnabled = flagExists and flagValue
+ local isCreator = game.Players.LocalPlayer.userId == game.CreatorId
+ local function shouldShowCommandBar()
+ return codeExecutionEnabled and isCreator
+ end
+ local function getCommandBarOffset()
+ return shouldShowCommandBar() and currentConsole == SERVER_CONSOLE and -22 or 0
+ end
+
+ local Dev_TextBox = Create'Frame'{
+ Name = 'TextBox';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.6;
+ Position = UDim2.new(0, 2, 0, 26);
+ Size = UDim2.new(1, -4, 1, -28);
+ ClipsDescendants = true;
+ }
+
+ local Dev_TextHolder = Create'Frame'{
+ Name = 'TextHolder';
+ Parent = Dev_TextBox;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ }
+
+ local Dev_OptionsButton = Create'ImageButton'{
+ Name = 'OptionsButton';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 298, 0, 2);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_OptionsButton;
+ BackgroundTransparency = 1.0;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ Rotation = 0;
+ Image = "http://www.roblox.com/Asset?id=152093917";
+ }
+
+ local Dev_CommandBar = Create'Frame'{
+ Name = "CommandBar";
+ Parent = Dev_Container;
+ BackgroundTransparency = 0;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BorderSizePixel = 0;
+ Size = UDim2.new(1, -25, 0, 24);
+ Position = UDim2.new(0, 2, 1, -28);
+ Visible = false;
+ ZIndex = 2;
+ BorderSizePixel = 0;
+ }
+
+ local Dev_CommandBarTextBox = Create'TextBox'{
+ Name = 'CommandBarTextBox';
+ Parent = Dev_CommandBar;
+ BackgroundTransparency = 1;
+ MultiLine = false;
+ ZIndex = 2;
+ Position = UDim2.new(0, 25, 0, 2);
+ Size = UDim2.new(1, -30, 0, 20);
+ Font = Enum.Font.Legacy;
+ FontSize = Enum.FontSize.Size10;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Center;
+ Text = "Code goes here";
+ }
+
+ Create'TextLabel'{
+ Name = "PromptLabel";
+ Parent = Dev_CommandBar;
+ BackgroundTransparency = 1;
+ Size = UDim2.new(0, 20, 1, 0);
+ Position = UDim2.new(0, 5, 0, 0);
+ Font = Enum.Font.Legacy;
+ FontSize = Enum.FontSize.Size10;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextXAlignment = Enum.TextXAlignment.Center;
+ TextYAlignment = Enum.TextYAlignment.Center;
+ ZIndex = 2;
+ Text = ">";
+ }
+
+ Dev_CommandBarTextBox.FocusLost:connect(function(enterPressed)
+ if enterPressed then
+ local code = Dev_CommandBarTextBox.Text
+ game:GetService("LogService"):ExecuteScript(code)
+ Dev_CommandBarTextBox.Text = ""
+
+ -- scroll to the bottom of the console
+ serverOffset = 0
+ Dev_CommandBarTextBox:CaptureFocus()
+ end
+ end)
+
+ local Dev_ResizeButton = Create'ImageButton'{
+ Name = 'ResizeButton';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(1, -20, 1, -20);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Name = 'ImageLabel';
+ Parent = Dev_ResizeButton;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 6, 0, 6);
+ Size = UDim2.new(0.8, 0, 0.8, 0);
+ Rotation = 135;
+ Image = "http://www.roblox.com/Asset?id=151205813";
+ }
+
+ Create'TextButton'{
+ Name = 'LocalConsole';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.6;
+ Position = UDim2.new(0, 7, 0, 5);
+ Size = UDim2.new(0, 90, 0, 20);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Local Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ Create'TextButton'{
+ Name = 'ServerConsole';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.8;
+ Position = UDim2.new(0, 102, 0, 5);
+ Size = UDim2.new(0, 90, 0, 17);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Server Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ Create'TextButton'{
+ Name = 'ServerStats';
+ Parent = Dev_Body;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.8;
+ Position = UDim2.new(0, 197, 0, 5);
+ Size = UDim2.new(0, 90, 0, 17);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ Text = "Server Stats";
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Center;
+ }
+
+ local Dev_TitleBar = Create'Frame'{
+ Name = 'TitleBar';
+ Parent = Dev_Container;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 0, 20);
+ }
+
+ local Dev_CloseButton = Create'ImageButton'{
+ Name = 'CloseButton';
+ Parent = Dev_TitleBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(1, -20, 0, 0);
+ Size = UDim2.new(0, 20, 0, 20);
+ }
+
+ Create'ImageLabel'{
+ Parent = Dev_CloseButton;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 3, 0, 3);
+ Size = UDim2.new(0, 14, 0, 14);
+ Image = "http://www.roblox.com/Asset?id=151205852";
+ }
+
+ Create'TextButton'{
+ Name = 'TextButton';
+ Parent = Dev_TitleBar;
+ BackgroundColor3 = Color3.new(0,0,0);
+ BackgroundTransparency = 0.5;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, -23, 1, 0);
+ Text = "";
+ }
+
+ Create'TextLabel'{
+ Name = 'TitleText';
+ Parent = Dev_TitleBar;
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 185, 0, 20);
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size18;
+ Text = "Server Console";
+ TextColor3 = Color3.new(1, 1, 1);
+ Text = "Roblox Developer Console";
+ TextYAlignment = Enum.TextYAlignment.Top;
+ }
+
+ local Dev_StatsChartFrame = Create'Frame'{
+ Name = 'ChartFrame';
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 0.5;
+ BorderColor3 = Color3.new(1.0, 1.0, 1.0);
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, 250, 0, 100);
+ }
+
+ Create'TextLabel'{
+ Name = 'TitleText';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 0.5;
+ BackgroundColor3 = Color3.new(255,0,0);
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 0, 15);
+ Text = "";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 39);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartMaxValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 15);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "Max: ";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ Create'TextLabel'{
+ Name = 'ChartMinValue';
+ Parent = Dev_StatsChartFrame;
+ BackgroundTransparency = 1.0;
+ BackgroundColor3 = Color3.new(0,0,0);
+ Position = UDim2.new(0, 5, 0, 27);
+ Size = UDim2.new(0, 100, 0, 15);
+ Text = "Min: ";
+ Font = "SourceSansBold";
+ FontSize = Enum.FontSize.Size14;
+ TextColor3 = Color3.new(1, 1, 1);
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ }
+
+ local Dev_StatsChartBar = Create'TextLabel'{
+ Name = 'StatsChartBar';
+ BackgroundColor3 = Color3.new(0,255,0);
+ Position = UDim2.new(0, 0, 0, 52);
+ Size = UDim2.new(0, 5, 0, 40);
+ Text = "";
+ }
+
+ ---Saved Mouse Information
+ local previousMousePos = nil
+ local pPos = nil
+
+ local previousMousePosResize = nil
+ local pSize = nil
+
+ local previousMousePosScroll = nil
+ local pScrollHandle = nil
+ local pOffset = nil
+
+ local scrollUpIsDown = false
+ local scrollDownIsDown = false
+
+ function clean()
+ previousMousePos = nil
+ pPos = nil
+ previousMousePosResize = nil
+ pSize = nil
+ previousMousePosScroll = nil
+ pScrollHandle = nil
+ pOffset = nil
+ scrollUpIsDown = false
+ scrollDownIsDown = false
+ end
+
+ -- Set up server stat charts
+ local numBars = 40
+ local numCharts = 0
+ local charts = {}
+ local statsListenerConnection = nil
+
+ function initStatsListener()
+ if (statsListenerConnection == nil) then
+ game.NetworkClient:GetChildren()[1]:RequestServerStats(true)
+ statsListenerConnection = game.NetworkClient:GetChildren()[1].StatsReceived:connect(refreshCharts)
+ end
+ end
+
+ function removeStatsListener()
+ if (statsListenerConnection ~= nil) then
+ game.NetworkClient:GetChildren()[1]:RequestServerStats(false)
+ statsListenerConnection:disconnect()
+ statsListenerConnection = nil
+ end
+ end
+
+ function createChart(_frame)
+ local chart = {
+ frame = _frame,
+ values = {},
+ bars = {},
+ curIndex = 0
+ }
+ return chart
+ end
+
+ function setupCharts(name)
+ local newChart = createChart(Dev_StatsChartFrame:Clone())
+ newChart.frame.Parent = Dev_TextHolder
+ newChart.frame.TitleText.Text = name
+ local newPos = 5 + numCharts * 110
+ newChart.frame.Position = UDim2.new(0, 5, 0, newPos);
+ for i = 1, numBars do
+ local bar = Dev_StatsChartBar:Clone()
+ bar.Position = UDim2.new(bar.Position.X.Scale, i * (bar.Size.X.Offset + 1), bar.Position.Y.Scale, bar.Position.Y.Offset)
+ bar.Parent = newChart.frame
+ table.insert(newChart.bars, bar)
+ end
+
+ charts[name] = newChart
+ numCharts = numCharts + 1
+ textHolderSize = newPos + 110
+ end
+
+ function clearCharts()
+ for i, chart in pairs(charts) do
+ chart.frame.Parent = nil
+ charts[i] = nil
+ end
+ numCharts = 0
+ end
+
+ function refreshCharts(stats)
+ for name, stat in pairs(stats) do
+ if (charts[name] == nil) then
+ setupCharts(name)
+ end
+
+ local chart = charts[name]
+ chart.curIndex = chart.curIndex + 1
+
+ -- remove old data
+ if chart.curIndex > numBars + 1 then
+ chart.curIndex = numBars + 1
+ table.remove(chart.values, 1)
+ end
+
+ chart.values[chart.curIndex] = stat
+
+ updateChart(chart)
+ end
+ end
+
+ function updateChart(chart)
+ local maxValue = .0001
+ local minValue = chart.values[chart.curIndex]
+
+ for i = chart.curIndex, chart.curIndex-numBars, -1 do
+ if i == 0 then break end
+ if chart.values[i] > maxValue then maxValue = chart.values[i] end
+ if chart.values[i] < minValue then minValue = chart.values[i] end
+ end
+
+ chart.frame.ChartValue.Text = "Current: "..chart.values[chart.curIndex]
+ chart.frame.ChartMaxValue.Text = "Max: "..maxValue
+ chart.frame.ChartMinValue.Text = "Min: "..minValue
+
+ for i = 1,numBars do
+
+ if chart.curIndex - i + 1 < 1 then
+ chart.bars[i].BackgroundTransparency = 1
+ else
+ chart.bars[i].BackgroundTransparency = 0
+
+ chart.bars[i].Size = UDim2.new(chart.bars[i].Size.X.Scale, chart.bars[i].Size.X.Offset, chart.bars[i].Size.Y.Scale,
+ Dev_StatsChartBar.Size.Y.Offset * (chart.values[chart.curIndex - i + 1] / maxValue))
+
+ chart.bars[i].Position = UDim2.new(chart.bars[i].Position.X.Scale, chart.bars[i].Position.X.Offset, Dev_StatsChartBar.Position.Y.Scale,
+ Dev_StatsChartBar.Position.Y.Offset + (45 - chart.bars[i].Size.Y.Offset))
+ end
+
+ end
+ end
+
+ ---Handle Dev-Console Position
+ function refreshConsolePosition(x, y)
+ if not previousMousePos then
+ return
+ end
+
+ local delta = Vector2.new(x, y) - previousMousePos
+ Dev_Container.Position = UDim2.new(0, pPos.X + delta.X, 0, pPos.Y + delta.Y)
+ end
+
+ Dev_TitleBar.TextButton.MouseButton1Down:connect(function(x, y)
+ previousMousePos = Vector2.new(x, y)
+ pPos = Dev_Container.AbsolutePosition
+ end)
+
+ Dev_TitleBar.TextButton.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+ ---Handle Dev-Console Size
+ function refreshConsoleSize(x, y)
+ if not previousMousePosResize then
+ return
+ end
+
+ local delta = Vector2.new(x, y) - previousMousePosResize
+ Dev_Container.Size = UDim2.new(0, math.max(pSize.X + delta.X, minimumSize.X), 0, math.max(pSize.Y + delta.Y, minimumSize.Y))
+ end
+ Dev_Container.Body.ResizeButton.MouseButton1Down:connect(function(x, y)
+ previousMousePosResize = Vector2.new(x, y)
+ pSize = Dev_Container.AbsoluteSize
+ end)
+
+ Dev_Container.Body.ResizeButton.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+
+ ---Handle Dev-Console Close Button
+ Dev_TitleBar.CloseButton.MouseButton1Down:connect(function(x, y)
+ Dev_Container.Visible = false
+ end)
+
+ Dev_Container.TitleBar.CloseButton.MouseButton1Up:connect(function()
+ clean()
+ removeStatsListener()
+ clearCharts()
+ end)
+
+ local optionsHidden = true
+ local animating = false
+ --Options
+ function startAnimation()
+ if animating then return end
+ animating = true
+
+ repeat
+ if optionsHidden then
+ frameNumber = frameNumber - 1
+ else
+ frameNumber = frameNumber + 1
+ end
+
+ local x = frameNumber / 5
+ local smoothStep = x * x * (3 - (2 * x))
+ Dev_OptionsButton.ImageLabel.Rotation = smoothStep * 5 * 9
+ Dev_OptionsBar.Position = UDim2.new(0, (smoothStep * 5 * 50) - 250, 0, 4)
+
+ wait()
+ if (frameNumber <= 0 and optionsHidden) or (frameNumber >= 5 and not optionsHidden) then
+ animating = false
+ end
+ until not animating
+ end
+
+ Dev_OptionsButton.MouseButton1Down:connect(function(x, y)
+ optionsHidden = not optionsHidden
+ startAnimation()
+ end)
+
+ --Scroll Position
+
+ function changeOffset(value)
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = localOffset + value
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = serverOffset + value
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = serverStatsOffset + value
+ end
+
+ repositionList()
+ end
+
+ --Refresh Dev-Console Text
+ function refreshTextHolderForReal()
+ local childMessages = Dev_TextHolder:GetChildren()
+
+ local messageList = {}
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ messageList = localMessageList
+ elseif (currentConsole == SERVER_CONSOLE) then
+ messageList = serverMessageList
+ end
+
+ local posOffset = 0
+
+ for i = 1, #childMessages do
+ childMessages[i].Visible = false
+ end
+
+ for i = 1, #messageList do
+ local message
+
+ local movePosition = false
+
+ if i > #childMessages then
+ message = Create'TextLabel'{
+ Name = 'Message';
+ Parent = Dev_TextHolder;
+ BackgroundTransparency = 1;
+ TextXAlignment = 'Left';
+ Size = UDim2.new(1, 0, 0, 14);
+ FontSize = 'Size10';
+ ZIndex = 1;
+ }
+ movePosition = true
+ else
+ message = childMessages[i]
+ end
+
+ if (outputToggleOn or messageList[i].Type ~= Enum.MessageType.MessageOutput) and
+ (infoToggleOn or messageList[i].Type ~= Enum.MessageType.MessageInfo) and
+ (warningToggleOn or messageList[i].Type ~= Enum.MessageType.MessageWarning) and
+ (errorToggleOn or messageList[i].Type ~= Enum.MessageType.MessageError) then
+ message.TextWrapped = wordWrapToggleOn
+ message.Size = UDim2.new(0.98, 0, 0, 2000)
+ message.Parent = Dev_Container
+ message.Text = messageList[i].Time.." -- "..messageList[i].Message
+
+ message.Size = UDim2.new(0.98, 0, 0, message.TextBounds.Y)
+ message.Position = UDim2.new(0, 5, 0, posOffset)
+ message.Parent = Dev_TextHolder
+ posOffset = posOffset + message.TextBounds.Y
+
+ if movePosition then
+ if (currentConsole == LOCAL_CONSOLE and localOffset > 0) or (currentConsole == SERVER_CONSOLE and serverOffset > 0) then
+ changeOffset(message.TextBounds.Y)
+ end
+ end
+
+ message.Visible = true
+
+ if messageList[i].Type == Enum.MessageType.MessageError then
+ message.TextColor3 = Color3.new(1, 0, 0)
+ elseif messageList[i].Type == Enum.MessageType.MessageInfo then
+ message.TextColor3 = Color3.new(0.4, 0.5, 1)
+ elseif messageList[i].Type == Enum.MessageType.MessageWarning then
+ message.TextColor3 = Color3.new(1, 0.6, 0.4)
+ else
+ message.TextColor3 = Color3.new(1, 1, 1)
+ end
+ end
+
+
+ end
+
+ textHolderSize = posOffset
+
+ repositionList()
+
+ end
+
+ -- Refreshing the textholder every 0.1 (if needed) is good enough, surely fast enough
+ -- We don't want it to update 50x in a tick because there are 50 messages in that tick
+ -- (Whenever for one reason or another a lot of output comes in, it can lag
+ -- This will make it behave better in a situation of a lot of output comming in)
+ local refreshQueued = false
+ function refreshTextHolder()
+ if refreshQueued or currentConsole == SERVER_STATS then return end
+ Delay(0.1,function()
+ refreshQueued = false
+ refreshTextHolderForReal()
+ end) refreshQueued = true
+ end
+
+ --Handle Dev-Console Scrollbar
+
+ local inside = 0
+ function holdingUpButton()
+ if scrollUpIsDown then
+ return
+ end
+ scrollUpIsDown = true
+ wait(.6)
+ inside = inside + 1
+ while scrollUpIsDown and inside < 2 do
+ wait()
+ changeOffset(12)
+ end
+ inside = inside - 1
+ end
+
+ function holdingDownButton()
+ if scrollDownIsDown then
+ return
+ end
+ scrollDownIsDown = true
+ wait(.6)
+ inside = inside + 1
+ while scrollDownIsDown and inside < 2 do
+ wait()
+ changeOffset(-12)
+ end
+ inside = inside - 1
+ end
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Click:connect(function()
+ changeOffset(10)
+ end)
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Down:connect(function()
+ changeOffset(10)
+ holdingUpButton()
+ end)
+
+ Dev_Container.Body.ScrollBar.Up.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ Dev_Container.Body.ScrollBar.Down.MouseButton1Down:connect(function()
+ changeOffset(-10)
+ holdingDownButton()
+ end)
+
+ Dev_Container.Body.ScrollBar.Down.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ function handleScroll(x, y)
+ if not previousMousePosScroll then
+ return
+ end
+
+ local delta = (Vector2.new(x, y) - previousMousePosScroll).Y
+
+ local backRatio = 1 - (Dev_Container.Body.TextBox.AbsoluteSize.Y / Dev_TextHolder.AbsoluteSize.Y)
+
+ local movementSize = Dev_ScrollArea.AbsoluteSize.Y - Dev_ScrollArea.Handle.AbsoluteSize.Y
+ local normalDelta = math.max(math.min(delta, movementSize), 0 - movementSize)
+ local normalRatio = normalDelta / movementSize
+
+ local textMovementSize = (backRatio * Dev_TextHolder.AbsoluteSize.Y)
+ local offsetChange = textMovementSize * normalRatio
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = pOffset - offsetChange
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = pOffset - offsetChange
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = pOffset - offsetChange
+ end
+ end
+
+ Dev_ScrollArea.Handle.MouseButton1Down:connect(function(x, y)
+ previousMousePosScroll = Vector2.new(x, y)
+ pScrollHandle = Dev_ScrollArea.Handle.AbsolutePosition
+ if (currentConsole == LOCAL_CONSOLE) then
+ pOffset = localOffset
+ elseif (currentConsole == SERVER_CONSOLE) then
+ pOffset = serverOffset
+ elseif (currentConsole == SERVER_STATS) then
+ pOffset = serverStatsOffset
+ end
+
+ end)
+
+ Dev_ScrollArea.Handle.MouseButton1Up:connect(function(x, y)
+ clean()
+ end)
+
+ local function existsInsideContainer(container, x, y)
+ local pos = container.AbsolutePosition
+ local size = container.AbsoluteSize
+ if x < pos.X or x > pos.X + size.X or y < pos.y or y > pos.y + size.y then
+ return false
+ end
+ return true
+ end
+
+
+
+ --Refresh Dev-Console Message Positions
+ function repositionList()
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ localOffset = math.min(math.max(localOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ serverOffset = math.min(math.max(serverOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ elseif (currentConsole == SERVER_STATS) then
+ serverStatsOffset = math.min(math.max(serverStatsOffset, 0), textHolderSize - Dev_Container.Body.TextBox.AbsoluteSize.Y)
+ Dev_TextHolder.Size = UDim2.new(1, 0, 0, textHolderSize)
+ end
+
+ local ratio = Dev_Container.Body.TextBox.AbsoluteSize.Y / Dev_TextHolder.AbsoluteSize.Y
+
+ if ratio >= 1 then
+ Dev_Container.Body.ScrollBar.Visible = false
+ Dev_Container.Body.TextBox.Size = UDim2.new(1, -4, 1, -28 + getCommandBarOffset())
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize)
+ end
+
+
+ else
+ Dev_Container.Body.ScrollBar.Visible = true
+ Dev_Container.Body.TextBox.Size = UDim2.new(1, -25, 1, -28 + getCommandBarOffset())
+
+ local backRatio = 1 - ratio
+ local offsetRatio
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ offsetRatio = localOffset / Dev_TextHolder.AbsoluteSize.Y
+ elseif (currentConsole == SERVER_CONSOLE) then
+ offsetRatio = serverOffset / Dev_TextHolder.AbsoluteSize.Y
+ elseif (currentConsole == SERVER_STATS) then
+ offsetRatio = (serverStatsOffset / Dev_TextHolder.AbsoluteSize.Y)
+ end
+
+ local topRatio = math.max(0, backRatio - offsetRatio)
+ local scrollHandleSize = math.max((Dev_ScrollArea.AbsoluteSize.Y) * ratio, 21)
+
+ local scrollRatio = scrollHandleSize / Dev_ScrollArea.AbsoluteSize.Y
+ local ratioConversion = (1 - scrollRatio) / (1 - ratio)
+
+ local topScrollRatio = topRatio * ratioConversion
+
+ local sPos = math.min((Dev_ScrollArea.AbsoluteSize.Y) * topScrollRatio, Dev_ScrollArea.AbsoluteSize.Y - scrollHandleSize)
+
+ Dev_ScrollArea.Handle.Size = UDim2.new(1, 0, 0, scrollHandleSize)
+ Dev_ScrollArea.Handle.Position = UDim2.new(0, 0, 0, sPos)
+
+ if (currentConsole == LOCAL_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + localOffset)
+ elseif (currentConsole == SERVER_CONSOLE) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + serverOffset)
+ elseif (currentConsole == SERVER_STATS) then
+ Dev_TextHolder.Position = UDim2.new(0, 0, 1, 0 - textHolderSize + serverStatsOffset)
+ end
+
+ end
+ end
+
+ -- Easy, fast, and working nicely
+ local function numberWithZero(num)
+ return (num < 10 and "0" or "")..num
+ end
+
+ local str = "%s:%s:%s"
+
+ function ConvertTimeStamp(timeStamp)
+ local localTime = timeStamp - os.time() + math.floor(tick())
+ local dayTime = localTime % 86400
+
+ local hour = math.floor(dayTime/3600)
+
+ dayTime = dayTime - (hour * 3600)
+ local minute = math.floor(dayTime/60)
+
+ dayTime = dayTime - (minute * 60)
+ local second = dayTime
+
+ local h = numberWithZero(hour)
+ local m = numberWithZero(minute)
+ local s = numberWithZero(dayTime)
+
+ return str:format(h,m,s)
+ end
+
+ --Filter
+
+ Dev_OptionsBar.ErrorToggleButton.MouseButton1Down:connect(function(x, y)
+ errorToggleOn = not errorToggleOn
+ Dev_OptionsBar.ErrorToggleButton.CheckFrame.Visible = errorToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.WarningToggleButton.MouseButton1Down:connect(function(x, y)
+ warningToggleOn = not warningToggleOn
+ Dev_OptionsBar.WarningToggleButton.CheckFrame.Visible = warningToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.InfoToggleButton.MouseButton1Down:connect(function(x, y)
+ infoToggleOn = not infoToggleOn
+ Dev_OptionsBar.InfoToggleButton.CheckFrame.Visible = infoToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.OutputToggleButton.MouseButton1Down:connect(function(x, y)
+ outputToggleOn = not outputToggleOn
+ Dev_OptionsBar.OutputToggleButton.CheckFrame.Visible = outputToggleOn
+ refreshTextHolder()
+ end)
+
+ Dev_OptionsBar.WordWrapToggleButton.MouseButton1Down:connect(function(x, y)
+ wordWrapToggleOn = not wordWrapToggleOn
+ Dev_OptionsBar.WordWrapToggleButton.CheckFrame.Visible = wordWrapToggleOn
+ refreshTextHolder()
+ end)
+
+ ---Dev-Console Message Functionality
+ function AddLocalMessage(str, messageType, timeStamp)
+ localMessageList[#localMessageList+1] = {Message = str, Time = ConvertTimeStamp(timeStamp), Type = messageType}
+ while #localMessageList > MAX_LIST_SIZE do
+ table.remove(localMessageList, 1)
+ end
+
+ refreshTextHolder()
+ end
+
+ function AddServerMessage(str, messageType, timeStamp)
+ serverMessageList[#serverMessageList+1] = {Message = str, Time = ConvertTimeStamp(timeStamp), Type = messageType}
+ while #serverMessageList > MAX_LIST_SIZE do
+ table.remove(serverMessageList, 1)
+ end
+
+ refreshTextHolder()
+ end
+
+
+
+ --Handle Dev-Console Local/Server Buttons
+ Dev_Container.Body.LocalConsole.MouseButton1Click:connect(function(x, y)
+ if (currentConsole ~= LOCAL_CONSOLE) then
+
+ if (currentConsole == SERVER_STATS) then
+ removeStatsListener()
+ clearCharts()
+ end
+
+ Dev_Container.CommandBar.Visible = false
+
+ currentConsole = LOCAL_CONSOLE
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ localConsole.Size = UDim2.new(0, 90, 0, 20)
+ serverConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverStats.Size = UDim2.new(0, 90, 0, 17)
+ localConsole.BackgroundTransparency = 0.6
+ serverConsole.BackgroundTransparency = 0.8
+ serverStats.BackgroundTransparency = 0.8
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+ end
+
+ refreshTextHolder()
+ end
+ end)
+
+ Dev_Container.Body.LocalConsole.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ local serverHistoryRequested = false;
+
+ Dev_Container.Body.ServerConsole.MouseButton1Click:connect(function(x, y)
+
+ if not serverHistoryRequested then
+ serverHistoryRequested = true
+ game:GetService("LogService"):RequestServerOutput()
+ end
+
+ if (currentConsole ~= SERVER_CONSOLE) then
+
+ Dev_Container.CommandBar.Visible = shouldShowCommandBar()
+
+ if (currentConsole == SERVER_STATS) then
+ removeStatsListener()
+ clearCharts()
+ end
+
+ currentConsole = SERVER_CONSOLE
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ serverConsole.Size = UDim2.new(0, 90, 0, 20)
+ localConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverConsole.BackgroundTransparency = 0.6
+ localConsole.BackgroundTransparency = 0.8
+ serverStats.BackgroundTransparency = 0.8
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+ end
+
+ refreshTextHolder()
+ end
+ end)
+
+ ---Extra Mouse Handlers for Dev-Console
+ Dev_Container.Body.ServerConsole.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ Dev_Container.Body.ServerStats.MouseButton1Click:connect(function(x, y)
+ if (currentConsole ~= SERVER_STATS) then
+
+ Dev_Container.CommandBar.Visible = false
+
+ currentConsole = SERVER_STATS
+ local localConsole = Dev_Container.Body.LocalConsole
+ local serverConsole = Dev_Container.Body.ServerConsole
+ local serverStats = Dev_Container.Body.ServerStats
+
+ serverStats.Size = UDim2.new(0, 90, 0, 20)
+ serverConsole.Size = UDim2.new(0, 90, 0, 17)
+ localConsole.Size = UDim2.new(0, 90, 0, 17)
+ serverStats.BackgroundTransparency = 0.6
+ serverConsole.BackgroundTransparency = 0.8
+ localConsole.BackgroundTransparency = 0.8
+
+ -- clear holder of log entries
+ local messages = Dev_TextHolder:GetChildren()
+ for i = 1, #messages do
+ messages[i].Visible = false
+ end
+
+ pcall(function() initStatsListener() end)
+
+ end
+ end)
+
+ Dev_Container.Body.ServerStats.MouseButton1Up:connect(function()
+ clean()
+ end)
+
+ if game:FindFirstChild("Players") and game.Players["LocalPlayer"] then
+ local LocalMouse = game.Players.LocalPlayer:GetMouse()
+ LocalMouse.Move:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ local mouse = game.Players.LocalPlayer:GetMouse()
+ local mousePos = Vector2.new(mouse.X, mouse.Y)
+ refreshConsolePosition(mouse.X, mouse.Y)
+ refreshConsoleSize(mouse.X, mouse.Y)
+ handleScroll(mouse.X, mouse.Y)
+
+ refreshTextHolder()
+ repositionList()
+ end)
+
+ LocalMouse.Button1Up:connect(function()
+ clean()
+ end)
+
+ LocalMouse.WheelForward:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ if existsInsideContainer(Dev_Container, LocalMouse.X, LocalMouse.Y) then
+ changeOffset(10)
+ end
+ end)
+
+ LocalMouse.WheelBackward:connect(function()
+ if not Dev_Container.Visible then
+ return
+ end
+ if existsInsideContainer(Dev_Container, LocalMouse.X, LocalMouse.Y) then
+ changeOffset(-10)
+ end
+ end)
+
+ end
+
+ Dev_ScrollArea.Handle.MouseButton1Down:connect(function()
+ repositionList()
+ end)
+
+
+ ---Populate Dev-Console with dummy messages
+
+ local history = game:GetService("LogService"):GetLogHistory()
+
+ for i = 1, #history do
+ AddLocalMessage(history[i].message, history[i].messageType, history[i].timestamp)
+ end
+
+ game:GetService("LogService").MessageOut:connect(function(message, messageType)
+ AddLocalMessage(message, messageType, os.time())
+ end)
+
+ game:GetService("LogService").ServerMessageOut:connect(AddServerMessage)
+
+end
+
+local currentlyToggling = false
+function ToggleConsole.OnInvoke()
+ if currentlyToggling then
+ return
+ end
+
+ currentlyToggling = true
+ initializeDeveloperConsole()
+ Dev_Container.Visible = not Dev_Container.Visible
+ currentlyToggling = false
+
+ if not Dev_Container.Visible then
+ removeStatsListener()
+ clearCharts()
+ end
+
+end
diff --git a/asset/backup/9 b/asset/backup/9
new file mode 100644
index 0000000..617d1b4
--- /dev/null
+++ b/asset/backup/9
@@ -0,0 +1,73 @@
+%9%
+--build our gui
+
+local popupFrame = Instance.new("Frame")
+popupFrame.Position = UDim2.new(0.5,-165,0.5,-175)
+popupFrame.Size = UDim2.new(0,330,0,350)
+popupFrame.Style = Enum.FrameStyle.DropShadow
+popupFrame.ZIndex = 4
+popupFrame.Name = "Popup"
+popupFrame.Visible = false
+popupFrame.Parent = script.Parent
+
+local darken = popupFrame:clone()
+darken.Size = UDim2.new(1,16,1,16)
+darken.Position = UDim2.new(0,-8,0,-8)
+darken.Name = "Darken"
+darken.ZIndex = 1
+darken.Parent = popupFrame
+
+local acceptButton = Instance.new("TextButton")
+acceptButton.Position = UDim2.new(0,20,0,270)
+acceptButton.Size = UDim2.new(0,100,0,50)
+acceptButton.Font = Enum.Font.ArialBold
+acceptButton.FontSize = Enum.FontSize.Size24
+acceptButton.Style = Enum.ButtonStyle.RobloxRoundButton
+acceptButton.TextColor3 = Color3.new(248/255,248/255,248/255)
+acceptButton.Text = "Yes"
+acceptButton.ZIndex = 5
+acceptButton.Name = "AcceptButton"
+acceptButton.Parent = popupFrame
+
+local declineButton = acceptButton:clone()
+declineButton.Position = UDim2.new(1,-120,0,270)
+declineButton.Text = "No"
+declineButton.Name = "DeclineButton"
+declineButton.Parent = popupFrame
+
+local okButton = acceptButton:clone()
+okButton.Name = "OKButton"
+okButton.Text = "OK"
+okButton.Position = UDim2.new(0.5,-50,0,270)
+okButton.Visible = false
+okButton.Parent = popupFrame
+
+local popupImage = Instance.new("ImageLabel")
+popupImage.BackgroundTransparency = 1
+popupImage.Position = UDim2.new(0.5,-140,0,10)
+popupImage.Size = UDim2.new(0,280,0,280)
+popupImage.ZIndex = 3
+popupImage.Name = "PopupImage"
+popupImage.Parent = popupFrame
+
+local backing = Instance.new("ImageLabel")
+backing.BackgroundTransparency = 1
+backing.Size = UDim2.new(1,0,1,0)
+backing.Image = "http://www.roblox.com/asset/?id=47574181"
+backing.Name = "Backing"
+backing.ZIndex = 2
+backing.Parent = popupImage
+
+local popupText = Instance.new("TextLabel")
+popupText.Name = "PopupText"
+popupText.Size = UDim2.new(1,0,0.8,0)
+popupText.Font = Enum.Font.ArialBold
+popupText.FontSize = Enum.FontSize.Size36
+popupText.BackgroundTransparency = 1
+popupText.Text = "Hello I'm a popup"
+popupText.TextColor3 = Color3.new(248/255,248/255,248/255)
+popupText.TextWrap = true
+popupText.ZIndex = 5
+popupText.Parent = popupFrame
+
+script:remove()
\ No newline at end of file
diff --git a/asset/index.php b/asset/index.php
new file mode 100644
index 0000000..b5f0bb5
--- /dev/null
+++ b/asset/index.php
@@ -0,0 +1,14 @@
+ "Unable to process request."])));
+
+switch(file_exists($_SERVER["DOCUMENT_ROOT"] . "/asset/" . $id)){
+ case true:
+ $file = file_get_contents($_SERVER["DOCUMENT_ROOT"] . "/asset/" . $id);
+ echo $file;
+ break;
+ default:
+ header("Location: https://assetdelivery.roblox.com/v1/asset/?id=" . $id);
+ die();
+}
+?>
\ No newline at end of file
diff --git a/dashboard.php b/dashboard.php
new file mode 100644
index 0000000..a16bcd5
--- /dev/null
+++ b/dashboard.php
@@ -0,0 +1,27 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/GetAllowedMD5Hashes/index.php b/GetAllowedMD5Hashes/index.php
new file mode 100644
index 0000000..f5e9b9e
--- /dev/null
+++ b/GetAllowedMD5Hashes/index.php
@@ -0,0 +1 @@
+{"data":["0fb35a870ca24bea2a17020144335cd7","0fb35a870ca24bea2a17020144335cd7"]}
diff --git a/GetAllowedSecurityVersions/index.html b/GetAllowedSecurityVersions/index.html
new file mode 100644
index 0000000..56d0f3f
--- /dev/null
+++ b/GetAllowedSecurityVersions/index.html
@@ -0,0 +1 @@
+{"data":["0.206.0pcplayer"]}
\ No newline at end of file
diff --git a/Setting/QuietGet/ClientAppSettings/index.php b/Setting/QuietGet/ClientAppSettings/index.php
new file mode 100644
index 0000000..4465515
--- /dev/null
+++ b/Setting/QuietGet/ClientAppSettings/index.php
@@ -0,0 +1,4 @@
+
+DOCTYPE HTML
+{ "GoogleAnalyticsAccountPropertyID": "UA-43420590-3", "GoogleAnalyticsAccountPropertyIDPlayer": "UA-43420590-14", "DFFlagUseKeyframeHumanoidAnimations": "True", "AllowVideoPreRoll": true, "FFlagWaterEnabled": "True", "FFlagServerScriptProtection": "False", "FFlagTaskSchedulerUseSharedPtr": "True", "FFlagReparentingLockEnabled": "True", "FFlagDeprecateMeaninglessTerrainPropertiesAndMethods": "True", "FLogAsserts": "0", "NonScriptableAccessEnabled": "False", "FFlagNonScriptableAccessEnabled": "False", "FFlagUsesNewCameraFrustum": "False", "FLogCloseDataModel": "3", "FFlagImmediateYieldResultsEnabled": "True", "FFlagIsChangeHistoryRunAware": "True", "FFlagDisplayFPS": "False", "FFlagDE4411Fixed": "True", "FFlagAreSoundsFiltered": "True", "FFlagDE4510Fixed": "True", "FFlagDE4528Fixed": "False", "FFlagDE4508Fixed": "False", "FFlagFastClone": "False", "CaptureQTStudioCountersEnabled": "True", "CaptureMFCStudioCountersEnabled": "True", "CaptureCountersIntervalInMinutes": "5", "FFlagLoadingGuiEnabled": "False", "FLogServiceVectorResize": "4", "FLogServiceCreation": "4", "FFlagDMFeatherweightEnabled": "True", "FFlagRenderFeatherweightEnabled": "True", "FFlagRenderFeatherweightUseGeometryGenerator": "True", "FFlagRenderNoDMLock": "True", "FFlagFRMCullDebris": "True", "FFlagMouseMoveOptimization": "True", "FFlagDisableClickToWalk": "True", "FFlagSegregatedLuaEnvironments": "True", "FFlagInGamePurchases": "True", "FFlagOpenNativeBrowserWindowFromLua": "True", "FFlagRenderFlexClusterEnabled": "False", "ReorderGUI": "False", "FFlagRenderTextureCompositorUse32Bit": "True", "FFlagScriptAutoIndent": "True", "FFlagRenderShadowFadeout": "True", "FFlagDE3737Fixed": "True", "FFlagFRMUsePerformanceLockstepTable": "False", "FFlagD3D9UseSoftwareVertexShaders": "True", "FFlagRenderFastClusterParts": "True", "FFlagRenderFastClusterHumanoids": "True", "FFlagFRMForceShadingQualityIfShadowAll": "False", "FFlagNewRaknetTimestamp": "True", "FFlagUpdateTargetPointBeforeMouseDown": "True", "FFlagRenderFeatherweightForHighQuality": "False", "FFlagQtStudioHighlightAdornments": "True", "FFlagQtStudioToggleCollisionCheck": "True", "FFlagRobloxStudio2013MessageEnabled": "True", "FFlagDrawSelectionBoxLinesFarAway": "True", "FFlagThrottleIfNotFocus": "True", "AxisAdornmentGrabSize": "12", "FFlagProcessAllPacketsPerStep": "True", "FFlagImmediateCrashUploadEnabled": "True", "FFlagImmediateHangUploadEnabled": "True", "FFlagQTStudioDoNotDeleteWebDlg": "True", "FFlagQTStudioDoNotRedirect": "True", "FFlagFilterInvisibleNonCollidePartsInLadderRaycasts": "True", "FFlagScriptToggleFold": "True", "FFlagScriptCommentSelection": "True", "FFlagUS14116": "True", "FFlagRenderFastClusterForceSleepForFixed": "True", "FFlagFRMAdornSupport": "True", "FFlagEThrottleBumpUp": "True", "FFlagEditModeLaunchFromWebsiteEnabled": "True", "FFlagCameraJitterFix": "True", "FFlagShowSplashScreen": "True", "FFlagSkipBroadPhaseWhenThrottling": "True", "FFlagConsistentThrottlingIncrements": "True", "FFlagBlockBlockNarrowPhaseRefactor": "True", "FFlagClampEdgeEdgeConnectorPointsToEdges": "True", "FFlagPolyPolyFaceFacePairUsesAlternativeFace": "True", "FFlagFreeFallOptimization": "True", "FFlagImpulseSolverForContact": "True", "FFlagReduceToleranceToEdgeEdgeParallelism": "True", "FFlagEnableSixDigitDoublePrecision": "True", "FFlagQtStudioCreateJointsAutomatically": "True", "FFlagFriendlyErrorMsgOnStartGameFailure": "True", "FFlagQtStudioVideoRecordingEnabled": "True", "FFlagEnableRubberBandSelection": "True", "FFlagQtStudioScreenshotEnabled": "True", "FFlagClickDrillDown": "True", "FFlagFixNoPhysicsGlitchWithGyro": "True", "FFlagFixFirstPersonToolLag": "True", "FFlagUS14597": "True", "FFlagActOnUS14597": "True", "FFlagUseVirtualMethodForCellCallback": "True", "FFlagTurnOffUnthrottledLogs": "False", "FLogFullRenderObjects": "0", "FLogRenderFastCluster": "0", "PublishedProjectsPageHeight": "535", "PublishedProjectsPageUrl": "/ide/publish", "StartPageUrl": "/ide/welcome", "FFlagOpenNewWindowsInDefaultBrowser": "True", "FFlagOnScreenProfiler": "False", "FFlagUS14933": "True", "FFlagActOnUS14933": "True", "FFlagInitializeNewPlace": "True", "FFlagQtFileOpenCrashFix": "True", "FFlagWaitUntilSignalForJavascriptInit": "True", "FFlagQtStudioCrashCounters": "True", "PrizeAssetIDs": "0=110718551=Congratulations! Your success at publishing a place has earned you the Eggcellent Builder hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;1=110719580=Congratulations! Your exploration of ROBLOX Studio's models has led you to the Eggstreme Builder hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;2=110720049=Congratulations! Your contribution to ROBLOX's content catalog has earned you the Eggsultant Contributor hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;3=110790044=Congratulations! Your large experience in scripting has earned you the rare Eggscruciatingly Deviled Scripter hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;4=110790072=Congratulations! Your flexibility at finding eggs has led you to the Yolk's on Us hat! You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;5=110790103=Congratulations! You've found the Eggsplosion hat! You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!", "PrizeAwarderURL": "/ostara/boon", "MinNumberScriptExecutionsToGetPrize": 500, "FFlagUS15154": "True", "FFlagActOnUS15154": "True", "FFlagValidateAssetUrlEnabled": "True", "FFlagDebugCrashEnabled": "False", "FFlagRenderFastClusterHighQuality": "True", "FLogHangDetection": "3", "FFlagRenderFastClusterMergeDraws": "True", "FFlagRenderFastClusterMergeBuffers": "True", "FFlagVoxelGridInsideMegaCluster": "True", "FFlagRenderForceBevelsOff": "True", "FFlagRenderLightGridTerrainOccupancy": "False", "FFlagRenderOptimizedTextureUpload": "True", "FFlagCharAnimationStats": "False", "FFlagRenderOpenGLForcePOTTextures": "True", "FFlagUseNewCameraZoomPath": "True", "FFlagQTStudioPublishFailure": "True", "ExcludeContactWithInteriorTerrainMinusYFace": "True", "FFlagFixUphillClimb": "True", "FFlagUseAveragedFloorHeight": "True", "FFlagScaleExplosionLifetime": "True", "FFlagUS15300": "True", "PublishedProjectsPageWidth": "950", "FFlagRenderFastClusterEverywhere": "True", "FLogPlayerShutdownLuaTimeoutSeconds": "1", "FFlagUS15977": "True", "FFlagQtFixToolDragging": "True", "FFlagSelectPartOnUndoRedo": "True", "FFlagUS15884": "True", "FFlagStatusBarProgress": "True", "FFlagStudioCheckForUpgrade": "True", "FFlagStudioInsertModelCounterEnabled": "True", "FFlagStudioAuthenticationFailureCounterEnabled": "True", "FFlagRenderCheckTextureContentProvider": "True", "FFlagRenderLightGridEnabled": "True", "FFlagStudioLightGridAPIVisible": "True", "FFlagActOnUS15526": "False", "FFlagUS15526": "True", "FFlagBetterSleepingJobErrorComputation": "True", "FFlagActOnUS15977": "False", "FLogDXVideoMemory": "4", "FFlagRenderNoLegacy": "True", "FFlagStudioLightGridOnForNewPlaces": "True", "FFlagPhysicsSkipRedundantJoinAll": "True", "FFlagTerrainOptimizedLoad": "True", "FFlagTerrainOptimizedStorage": "True", "FFlagTerrainOptimizedCHS": "True", "FFlagRenderGLES2": "True", "FFlagStudioMacAddressValidationEnabled": "True", "FFlagDoNotPassSunkEventsToPlayerMouse": "True", "FFlagQtAutoSave": "True", "FFlagRenderLoopExplicit": "True", "FFlagStudioUseBinaryFormatForPlay": "True", "PhysicsRemoveWorldAssemble_US16512": "True", "FFlagNativeSafeChatRendering": "True", "FFlagUS17162": "True", "DFFlagUS17412": "True", "FFlagRenderNewMegaCluster": "True", "FFlagAutoJumpForTouchDevices": "True", "DFFlagUS17646": "True", "DFFlagUS17889": "True", "FLogOutlineBrightnessMin": "50", "FLogOutlineBrightnessMax": "160", "FLogOutlineThickness": "40", "FFlagDE5511FixEnabled": "True", "FFlagDE4423Fixed": "True", "FFlagSymmetricContact": "True", "FFlagLocalMD5": "True", "FFlagStudioCookieParsingDisabled": "False", "FFlagLastWakeTimeSleepingJobError": "True", "FFlagPhysicsAllowAutoJointsWithSmallParts_DE6056": "True", "FFlagPhysicsLockGroupDraggerHitPointOntoSurface_DE6174": "True", "FFlagOutlineControlEnabled": "True", "FFlagAllowCommentedScriptSigs": "True", "FFlagDataModelUseBinaryFormatForSave": "True", "FFlagStudioUseBinaryFormatForSave": "True", "FFlagDebugAdornableCrash": "True", "FFlagOverlayDataModelEnabled": "True", "DFFlagFixInstanceParentDesyncBug": "True", "FFlagPromoteAssemblyModifications": "False", "FFlagFontSourceSans": "True", "DFFlagCreateHumanoidRootNode": "True", "FFlagRenderNewFonts": "True", "FFlagStudioCookieDesegregation": "True", "FFlagResponsiveJump": "True", "FFlagGoogleAnalyticsTrackingEnabled": "True", "FFlagNoCollideLadderFilter": "True", "FFlagFlexibleTipping": "True", "FFlagUseStrongerBalancer": "True", "FFlagClampControllerVelocityMag": "True", "DFFlagUseSaferChatMetadataLoading": "True", "FFlagSinkActiveGuiObjectMouseEvents": "False", "FLogLuaBridge": "2", "DFFlagPromoteAssemblyModifications": "True", "FFlagDeferredContacts": "True", "FFlagFRMUse60FPSLockstepTable": "True", "FFlagFRMAdjustForMultiCore": "True", "FFlagPhysics60HZ": "True", "FFlagQtRightClickContextMenu": "True", "FFlagUseTopmostSettingToBringWindowToFront": "True", "FFlagNewLightAPI": "True", "FFlagRenderLightGridShadows": "True", "FFlagRenderLightGridShadowsSmooth": "True", "DFFlagSanitizeKeyframeUrl": "True", "DFFlagDisableGetKeyframeSequence": "False", "FFlagCreateServerScriptServiceInStudio": "True", "FFlagCreateServerStorageInStudio": "True", "FFlagCreateReplicatedStorageInStudio": "True", "FFlagFilterEmoteChat": "True", "DFFlagUseCharacterRootforCameraTarget": "True", "FFlagImageRectEnabled": "True", "FFlagNewWaterMaterialEnable": "True", "DFFlagUserHttpAPIEnabled": "True", "DFIntUserHttpAccessUserId0": "0", "FFlagUserHttpAPIVisible": "True", "FFlagCameraChangeHistory": "True", "FFlagDE4640Fixed": "True", "FFlagShowStreamingEnabledProp": "True", "FFlagOptimizedDragger": "True", "FFlagRenderNewMaterials": "True", "FFlagRenderAnisotropy": "True", "FFlagStudioInitializeViewOnPaint": "True", "DFFlagPartsStreamingEnabled": "True", "FFlagStudioLuaDebugger": "True", "FFlagStudioLocalSpaceDragger": "True", "FFlagGuiRotationEnabled": "True", "FFlagDataStoreEnabled": "True", "DFFlagDisableTeleportConfirmation": "True", "DFFlagAllowTeleportFromServer": "True", "DFFlagNonBlockingTeleport": "True", "FFlagD3D9CrashOnError": "False", "FFlagRibbonBarEnabled": "True", "SFFlagInfiniteTerrain": "True", "FFlagStudioScriptBlockAutocomplete": "True", "FFlagRenderFixAnchoredLag": "True", "DFFlagAllowAllUsersToUseHttpService": "True", "GoogleAnalyticsAccountPropertyIDClient": "", "FFlagSurfaceGuiVisible": "True", "FFlagStudioIntellesenseEnabled": "True", "FFlagAsyncPostMachineInfo": "True", "FFlagModuleScriptsVisible": "True", "FFlagModelPluginsEnabled": "True", "FFlagGetUserIdFromPluginEnabled": "True", "FFlagStudioPluginUIActionEnabled": "True", "DFFlagRemoveAdornFromBucketInDtor": "True", "FFlagRapidJSONEnabled": "True", "DFFlagDE6959Fixed": "True", "DFFlagScopedMutexOnJSONParser": "True", "FFlagSupressNavOnTextBoxFocus": "True", "DFFlagExplicitPostContentType": "True", "DFFlagAddPlaceIdToAnimationRequests": "True", "FFlagCreatePlaceEnabled": "True", "DFFlagClientAdditionalPOSTHeaders": "True", "FFlagEnableAnimationExport": "True", "DFFlagAnimationAllowProdUrls": "True", "FFlagGetUserIDFromPluginEnabled": "True", "FFlagStudioContextualHelpEnabled": "True", "FFlagLogServiceEnabled": "True", "FFlagQtPlaySoloOptimization": "True", "FFlagStudioBuildGui": "True", "DFFlagListenForZVectorChanges": "True", "DFFlagUserInputServiceProcessOnRender": "True", "FFlagDE7421Fixed": "True", "FFlagStudioExplorerActionsEnabledInScriptView": "True", "FFlagHumanoidNetworkOptEnabled": "True", "DFFlagEnableNPCServerAnimation": "True", "DFFlagDataStoreUseUForGlobalDataStore": "True", "DFFlagDataStoreAllowedForEveryone": "True", "DFFlagBadTypeOnConnectErrorEnabled": "True", "FFlagStudioRemoveUpdateUIThread": "True", "FFlagPhysicsSkipUnnecessaryContactCreation": "False", "FFlagUseNewHumanoidCache": "True", "FFlagSecureReceiptsBackendEnabled": "True", "FFlagOrderedDataStoreEnabled": "True", "FFlagStudioLuaDebuggerGA": "True", "FFlagNPSSetScriptDocsReadOnly": "True", "FFlagRDBGHashStringComparison": "True", "FFlagStudioDebuggerVisitDescendants": "True", "FFlagDeprecateScriptInfoService": "True", "FFlagIntellisenseScriptContextDatamodelSearchingEnabled": "True", "FFlagStudioCompareDatamodelHashOnClose": "True", "FFlagSecureReceiptsFrontendEnabled": "True", "DFFlagCreatePlaceEnabledForEveryone": "True", "FFlagCreatePlaceInPlayerInventoryEnabled": "True", "DFFlagAddRequestIdToDeveloperProductPurchases": "True", "DFFlagUseYPCallInsteadOfPCallEnabled": "True", "FFlagStudioMouseOffsetFixEnabled": "True", "DFFlagPlaceValidation": "True", "FFlagReconstructAssetUrl": "True", "FFlagUseNewSoundEngine": "True", "FIntMinMillisecondLengthForLongSoundChannel": "5000", "FFlagStudioHideInsertedServices": "True", "FFlagStudioAlwaysSetActionEnabledState": "True", "FFlagRenderNew": "True", "FIntRenderNewPercentWin": "100", "FIntRenderNewPercentMac": "100", "FLogGraphics": "6", "FFlagStudioInSyncWebKitAuthentication": "False", "DFFlagDisallowHopperServerScriptReplication": "True", "FFlagInterpolationFix": "False", "FFlagHeartbeatAt60Hz": "False", "DFFlagFixProcessReceiptValueTypes": "True", "DFFlagPhysicsSkipUnnecessaryContactCreation": "True", "FFlagStudioLiveCoding": "True", "FFlagPlayerHumanoidStep60Hz": "True", "DFFlagCrispFilteringEnabled": "False", "SFFlagProtocolSynchronization": "True", "FFlagUserInputServicePipelineStudio": "True", "FFlagUserInputServicePipelineWindowsClient": "True", "FFlagUserInputServicePipelineMacClient": "True", "FFlagStudioKeyboardMouseConfig": "True", "DFFlagLogServiceEnabled": "True", "DFFlagLoadAnimationsThroughInsertService": "True", "FFlagFRMFogEnabled": "True", "FLogBrowserActivity": "3", "DFFlagPhysicsPacketAlwaysUseCurrentTime": "True", "FFlagFixedStudioRotateTool": "True", "FFlagRibbonBarEnabledGA": "True", "FFlagRenderSafeChat": "False", "DFFlagPhysicsAllowSimRadiusToDecreaseToOne": "True", "DFFlagPhysicsAggressiveSimRadiusReduction": "True", "DFFlagLuaYieldErrorNoResumeEnabled": "True", "DFFlagEnableJointCache": "False", "DFFlagOnCloseTimeoutEnabled": "True", "FFlagStudioQuickInsertEnabled": "True", "FFlagStudioPropertiesRespectCollisionToggle": "True", "FFlagTweenServiceUsesRenderStep": "True", "FFlagUseNewSoundEngine3dFix": "True", "FFlagDebugUseDefaultGlobalSettings": "True", "FFlagStudioMiddleMouseTrackCamera": "False", "FFlagTurnOffiOSNativeControls": "True", "DFFlagUseNewHumanoidHealthGui": "True", "FFlagUS21919": "True", "DFFlagLoggingConsoleEnabled": "True", "DFFlagAllowModuleLoadingFromAssetId": "True", "FFlagStudioZoomExtentsExplorerFixEnabled": "True", "FFlagStudioExplorerFilterEnabled": "False", "FFlagStudioPropertySearchDisabled": "False", "FFlagLuaDebuggerBreakOnError": "True", "FFlagRetentionTrackingEnabled": "True", "FFlagShowAlmostAllItemsInExplorer": "True", "FFlagStudioFindInAllScriptsEnabled": "True", "FFlagImprovedNameOcclusion": "True", "FFlagHumanoidMoveToDefaultValueEnabled": "True", "FFlagEnableDisplayDistances": "True", "FFlagUseMinMaxZoomDistance": "True", "SFFlagAllowPhysicsPacketCompression": "False", "FFlagStudioOneClickColorPickerEnabled": "True", "DFFlagHumanoidMoveToDefaultValueEnabled": "True", "FFlagStudioFindContextFixEnabled": "False", "VideoPreRollWaitTimeSeconds": 45, "FFlagBalancingRateLimit": "True", "FFlagLadderCheckRate": "True", "FFlagStateSpecificAutoJump": "True", "SFFlagOneWaySimRadiusReplication": "True", "DFFlagApiDictionaryCompression": "True", "SFFlagPathBasedPartMovement": "True", "FFlagEnsureInputIsCorrectState": "False", "DFFlagLuaLoadStringStrictSecurity": "True", "DFFlagCrossPacketCompression": "True", "FFlagWorkspaceLoadStringEnabledHidden": "True", "FFlagStudioPasteAsSiblingEnabled": "True", "FFlagStudioDuplicateActionEnabled": "True", "FFlagPreventInterpolationOnCFrameChange": "True", "FLogNetworkPacketsReceive": 5, "FFlagPlayPauseFix": "True", "DFFlagCrashOnNetworkPacketError": "False", "FFlagHumanoidStateInterfaces": "True", "FFlagRenderDownloadAssets": "True", "FFlagBreakOnErrorConfirmationDialog": "True", "FFlagStudioAnalyticsEnabled": "True", "FFlagAutoRotateFlag": "True", "DFFlagUseImprovedLadderClimb": "True", "FFlagUseCameraOffset": "True", "FFlagRenderBlobShadows": "True", "DFFlagWebParserDisableInstances": "False", "FFlagStudioNewWiki": "True", "DFFlagLogPacketErrorDetails": "False", "FFlagStudioLiveColorProperty": "False", "FFlagLimitHorizontalDragForce": "True", "FFlagEnableNonleathalExplosions": "True", "DFFlagCreateSeatWeldOnServer": "True", "FFlagGraphicsUseRetina": "True", "FFlagDynamicEnvmapEnabled": "True", "DFFlagDeferredTouchReplication": true, "DFFlagCreatePlayerGuiEarlier": "True", "DFFlagProjectileOwnershipOptimization": "True", "DFFlagLoadSourceForCoreScriptsBeforeInserting": "False", "GoogleAnalyticsLoadStudio": 1, "DFFlagTaskSchedulerFindJobOpt": "True", "SFFlagPreventInterpolationOnCFrameChange": "True", "DFIntNumPhysicsPacketsPerStep": 2, "DFFlagDataStoreUrlEncodingEnabled": "True", "FFlagShowWebPlaceNameOnTabWhenOpeningFromWeb": "True", "DFFlagTrackTimesScriptLoadedFromLinkedSource": "True", "FFlagToggleDevConsoleThroughChatCommandEnabled": "True", "FFlagEnableFullMonitorsResolution": "True", "DFFlagAlwaysUseHumanoidMass": "True", "DFFlagUseStrongerGroundControl": "True", "DFFlagCorrectlyReportSpeedOnRunStart": "True", "FFlagLuaDebuggerImprovedToolTip": "True", "FFlagLuaDebuggerPopulateFuncName": "True", "FFlagLuaDebuggerNewCodeFlow": "True", "DFFlagValidateCharacterAppearanceUrl": "false", "FFlagStudioQuickAccessCustomization": "True", "DFFlagTaskSchedulerUpdateJobPriorityOnWake": "True", "DFFlagTaskSchedulerNotUpdateErrorOnPreStep": "True", "FFlagWikiSelectionSearch": "True", "DFIntTaskSchedularBatchErrorCalcFPS": 1200, "FFlagSuppressNavOnTextBoxFocus": "False", "FFlagEnabledMouseIconStack": "True", "DFFlagFastClone": "True", "DFFlagLuaNoTailCalls": "True", "DFFlagFilterStreamingProps": "True", "DFFlagNetworkOwnerOptEnabled": "True", "DFFlagPathfindingEnabled": "True", "FFlagEnableiOSSettingsLeave": "True", "FFlagUseFollowCamera": "True", "FFlagDefaultToFollowCameraOnTouch": "True", "DFFlagAllowMoveToInMouseLookMove": "True", "DFFlagAllowHumanoidDecalTransparency": "True", "DFFlagSupportCsrfHeaders": "True", "DFFlagConfigureInsertServiceFromSettings": "True", "FFlagPathfindingClientComputeEnabled": "True", "DFFlagLuaResumeSupportsCeeCalls": "True", "DFFlagPhysicsSenderErrorCalcOpt": "True", "DFFlagClearPlayerReceivingServerLogsOnLeave": "True", "DFFlagConsoleCodeExecutionEnabled": "True", "DFFlagCSGDictionaryReplication": "True", "FFlagCSGToolsEnabled": "True", "FFlagCSGDictionaryServiceEnabled": "True", "FFlagCSGMeshRenderEnable": "True", "FFlagCSGChangeHistory": "True", "FFlagCSGMeshColorEnable": "True", "FFlagCSGMeshColorToolsEnabled": "True", "FFlagCSGScaleEnabled": "True", "FFlagCylinderUsesConstantTessellation": "True", "FFlagStudioDraggersScaleFixes": "True", "FFlagCSGDecalsEnabled": "True", "FFlagCSGMigrateChildData": "True", "SFFlagBinaryStringReplicationFix": "True", "FFlagHummanoidScaleEnable": "True", "FFlagStudioDataModelIsStudioFix": "True", "DFFlagWebParserEnforceASCIIEnabled": "True", "DFFlagScriptDefaultSourceIsEmpty": "True", "FFlagFixCaptureFocusInput": "True", "FFlagFireUserInputServiceEventsAfterDMEvents": "True", "FFlagVectorErrorOnNilArithmetic": "True", "FFlagFontSmoothScalling": "True", "DFFlagUseImageColor": "True", "FFlagStopNoPhysicsStrafe": "True", "DFFlagDebugLogNetworkErrorToDB": "False", "FFlagLowQMaterialsEnable": "True", "FFLagEnableFullMonitorsResolution": "True", "FFlagStudioChildProcessCleanEnabled": "True", "DFFlagAllowFullModelsWhenLoadingModules": "True", "DFFlagRealWinInetHttpCacheBypassingEnabled": "True", "FFlagNewUniverseInfoEndpointEnabled": "True", "FFlagGameExplorerEnabled": "True", "FFlagStudioUseBinaryFormatForModelPublish": "True", "FFlagGraphicsFeatureLvlStatsEnable": "True", "FFlagStudioEnableWebKitPlugins": "True", "DFFlagSendHumanoidTouchedSignal": "True", "DFFlagReduceHumanoidBounce": "True", "DFFlagUseNewSounds": "True", "FFlagFixHumanoidRootPartCollision": "True", "FFlagEnableAndroidMenuLeave": "True", "FFlagOnlyProcessGestureEventsWhenSunk": "True", "FFlagAdServiceReportImpressions": "True", "FFlagStudioUseExtendedHTTPTimeout": "True", "FFlagStudioSeparateActionByActivationMethod": "False", "DFFlagPhysicsSenderThrottleBasedOnBufferHealth": "True", "FFlagCSGExportFailure": "False", "DFFlagGetGroupInfoEnabled": "True", "DFFlagGetGroupRelationsEnabled": "True", "FStringPlaceFilter_StateBasedAnimationReplication": "True;175953385;174810327;181219650", "SFFlagTopRepContSync": "True", "FFlagStudioUseBinaryFormatForModelSave": "True", "EnableFullMonitorsResolution": "True", "DFFlagRenderSteppedServerExceptionEnabled": "True", "FFlagUseWindowSizeFromGameSettings": "True", "DFFlagCheckStudioApiAccess": "True", "FFlagGameExplorerPublishEnabled": "True", "DFFlagKeepXmlIdsBetweenLoads": "True", "DFFlagReadXmlCDataEnabled": "True", "FFlagStudioRemoveToolSounds": "True", "FFlagStudioOneStudGridDefault": "True", "FFlagStudioPartSymmetricByDefault": "True", "FFlagStudioIncreasedBaseplateSize": "True", "FFlagSkipSilentAudioOps": "True", "SFFlagGuid64Bit": "False", "FIntValidateLauncherPercent": "100", "FFlagCSGDataLossFixEnabled": "True", "DFStringRobloxAnalyticsURL": "http://ecsv2.roblox.com/", "DFFlagRobloxAnalyticsTrackingEnabled": "True", "FFlagStudioOpenFirstPlace": "False", "FFlagStudioOpenLastSaved": "False", "FFlagStudioShowTutorialsByDefault": "True", "FFlagStudioForceToolboxSize": "True", "FFlagStudioExplorerDisabledByDefault": "True", "FFlagStudioDefaultWidgetSizeChangesEnabled": "True", "FFlagStudioUseScriptAnalyzer": "True", "FFlagNoClimbPeople": "True", "DFFlagAnimationFormatAssetId": "True", "FFlagStudioMobileCompanionEnabled": "True", "FFlagGetCorrectScreenResolutionFaster": "True", "DFFlagFixTouchEndedReporting": "False", "FFlagStudioOpenFirstPlaceBasePlate": "False", "FFlagStudioTeleportPlaySolo": "True", "FFlagCSGRemoveScriptScaleRestriction": "True", "FFlagStudioDE7928FixEnabled": "True", "FFlagDE8768FixEnabled": "True", "FFlagStudioDE9108FixEnabled": "True", "FFlagStudioPlaySoloMapDebuggerData": "True", "FFlagLuaDebuggerCloneDebugger": "True", "FFlagStudioCommandLineSaveEditText": "False", "FFlagRenderLightgridInPerformEnable": "True", "SFFlagStateBasedAnimationReplication": "True", "FFlagVolumeControlInGameEnabled": "True", "FFlagGameConfigurerUseStatsService": "True", "FFlagStudioUseHttpAuthentication": "True", "FFlagDetectTemplatesWhenSettingUpGameExplorerEnabled": "True", "FFlagEntityNameEditingEnabled": "True", "FFlagNewCreatePlaceFlowEnabled": "True", "FFlagFakePlayableDevices": "False", "FFlagMutePreRollSoundService": "True", "DFFlagBodyMoverParentingFix": "True", "DFFlagBroadcastServerOnAllInterfaces": "True", "HttpUseCurlPercentageWinClient": "100", "HttpUseCurlPercentageMacClient": "100", "HttpUseCurlPercentageWinStudio": "100", "HttpUseCurlPercentageMacStudio": "100", "SFFlagReplicatedFirstEnabled": "True", "DFFlagCSGShrinkForMargin": "True", "FFlagPhysicsBulletConnectorPointRecalc": "True", "DFIntBulletContactBreakThresholdPercent": "200", "DFIntBulletContactBreakOrthogonalThresholdPercent": "200", "FFlagPhysicsBulletConnectorMatching": "True", "FFlagPhysicsBulletUseProximityMatching": "False", "FFlagPhysicsCSGUsesBullet": "True", "DFFlagCSGPhysicsDeserializeRefactor": "True", "FFlagWedgeEnableDecalOnTop": "True", "FFlagFrustumTestGUI": "True", "FFlagFeatureLvlsDX11BeforeDeviceCreate": "True", "FFlagStudioPasteSyncEnabled": "True", "FFlagResetMouseCursorOnToolUnequip": "True", "DFFlagUpdateCameraTarget": "True", "DFFlagFixGhostClimb": "True", "DFFlagUseStarterPlayer": "True", "FFlagStudioMobileEmulatorEnabled": "True", "FFlagStudioFindCrashFixEnabled": "True", "FFlagFixPartOffset": "True", "DFFlagLuaCloseUpvalues": "True", "FFlagRenderTextureCompositorUseBudgetForSize": "True", "FFlagAllowOutOfBoxAssets": "False", "FFlagRemoveTintingWhenActiveIsFalseOnImageButton": "True", "FFlagStudioModuleScriptDefaultContents": "True", "FFlagStudioHomeKeyChangeEnabled": "True", "FFlagStudioOpenStartPageForLogin": "True", "FFlagStudioNativeKeepSavedChanges": "True", "FFlagSerializeCurrentlyOpenPlaceWhenPublishingGame": "True", "FFlagGameNameLabelEnabled": "True", "FFlagStudioValidateBootstrapper": true, "FFlagRakNetReadFast": "True", "DFFlagPhysicsSenderSleepingUpdate": "True", "FFlagUseShortShingles": "True", "FFlagKKTChecks": "False", "DFFlagUseApiProxyThrottling": "True", "DFFlagValidateSetCharacter": true, "DFFlagUpdateHumanoidSimBodyInComputeForce": "True", "DFFlagNetworkPendingItemsPreserveTimestamp": true, "FFlagStudioCSGRotationalFix": "True", "FFlagNewLoadingScreen": "True", "FFlagScrollingFrameOverridesButtonsOnTouch": "True", "DFFlagStreamLargeAudioFiles": "True", "DFFlagNewLuaChatScript": "True", "DFFlagLoopedDefaultHumanoidAnimation": "True", "FFlagSoundsRespectDelayedStop": "False", "DFFlagCSGPhysicsErrorCatchingEnabled": "True", "DFFlagFireStoppedAnimSignal": "True", "FFlagStudioFixToolboxReload": "True", "FFlagCSGDecalsV2": "True", "FFlagLocalOptimizer": "True", "DFFlagClearFailedUrlsWhenClearingCacheEnabled": "True", "DFFlagSupportNamedAssetsShortcutUrl": "True", "DFFlagUseW3CURIParser": "True", "DFFlagContentProviderHttpCaching": "True", "FFlagNoWallClimb": "False", "FFlagSmoothMouseLock": "False", "DFFlagCSGPhysicsNanPrevention": "True", "FFlagStudioDE9818FixEnabled": "True", "FFlagGameExplorerImagesEnabled": "True", "DFFlagUS24505": "True", "FFlagStudioInsertOrientationFix": "True", "FFlagStudioTabOrderingEnabled": "True", "FFlagFramerateDeviationDroppedReport": "True", "FFlagModuleScriptsPerVmEnabled": "False", "FFlagGameExplorerImagesInsertEnabled": "True", "FFlagTexturePropertyWidgetEnabled": "True", "FFlagReloadAllImagesOnDataReload": "True", "FFlagModuleScriptsPerVmEnabledFix2": "True", "DFFlagFixBufferZoneContainsCheck": "False", "FFlagStudioPlaceAssetFromToolbox": "True", "FFlagChannelMasterMuting": "True", "FFlagStudioUseDelayedSyntaxCheck": "True", "FFlagStudioCommandLineSaveEditText ": "True", "DFFlagLuaDetectCyclicTables": "True", "FFlagStudioAddHelpInContextMenu": "True", "DFIntHttpCacheCleanMinFilesRequired": "3000", "DFIntHttpCacheCleanMaxFilesToKeep": "1500", "FFlagCSGVoxelizer": "True", "DFFlagCheckApiAccessInTransactionProcessing": "True", "FFlagBindPurchaseValidateCallbackInMarketplaceService": "True", "FFlagSetDataModelUniverseIdAfterPublishing": "True", "FFlagOpenScriptWorksOnModulesEnabled": "True", "FFlagStudioRibbonBarNewLayout": "True", "FFlagStudioRibbonBarLayoutFixes": "True", "FFlagStudioPlaceOnlineIndicator": "True", "FFlagRenderWangTiles": "True", "FFlagDisableBadUrl": true, "FFlagPrimalSolverLogBarrierIP": true, "FFlagDualSolverSimplex": true, "FFlagPrimalSolverSimplex": true, "FIntNumSmoothingPasses": 3, "FFlagVerifyConnection": true, "FIntRegLambda": 1400, "FFlagScriptAnalyzerPlaceholder": "True", "FFlagStudioCSGAssets": "True", "FFlagCSGStripPublishedData": "True", "DFFlagRaycastReturnSurfaceNormal": "True", "FFlagMoveGameExplorerActionsIntoContextMenu": "True", "FFlagStudioAdvanceCookieExpirationBugFixEnabled": "True", "FFlagNewBackpackScript": "True", "FFlagNewPlayerListScript": "True", "FFlagGameNameAtTopOfExplorer": "True", "FFlagStudioActActionsAsTools": "True", "FFlagStudioInsertAtMouseClick": "True", "FFlagStopLoadingStockSounds": "True", "DFFlagFixTimePositionReplication": "True", "DFFlagHttpReportStatistics": "True", "DFFlagEnableChatTestingInStudio": "True", "DFIntHttpSendStatsEveryXSeconds": "300", "FLogStepAnimatedJoints": "5", "DFFlagLuaDisconnectFailingSlots": "False", "DFFlagEnsureSoundPosIsUpdated": "True", "DFFlagLoadStarterGearEarlier": "False", "DFFlagBlockUsersInLuaChat": "True", "FFlagRibbonPartInsertNotAllowedInModel": "True", "DFFlagUsePlayerScripts": "True", "DFFlagUserAccessUserSettings": "True", "DFFlagUseLuaCameraAndControl": "True", "DFFlagUseLuaPCInput": "True", "DFFlagFixLuaMoveDirection": "True", "DFFlagUseDecalLocalTransparencyModifier": "True", "DFFlagUseFolder": "True", "DFFlagUsePreferredSpawnInPlaySoloTeleport": "True", "DFFlagFilterAddSelectionToSameDataModel": "False", "FFlagGameExplorerAutofillImageNameFromFileName": "True", "FFlagGameExplorerBulkImageUpload": "True", "FFlagStudioAllowAudioSettings": "True", "DFFlagUsePlayerInGroupLuaChat": "True", "FFlagStudioDecalPasteFix": "True", "FFlagStudioCtrlTabDocSwitchEnabled": "True", "DFIntDraggerMaxMovePercent": 60, "FFlagUseUniverseGetInfoCallToDetermineUniverseAccess": "True", "FFlagMaxFriendsCount": "True", "DFIntPercentApiRequestsRecordGoogleAnalytics": 0, "FFlagSelectSpinlock": "True", "FFlagFastZlibPath": "True", "DFFlagWriteXmlCDataEnabled": "True", "DFFlagUseSpawnPointOrientation": "True", "DFFlagUsePlayerSpawnPoint": "True", "DFFlagCSGPhysicsRecalculateBadContactsInConnectors": "True", "FFlagStudioPartAlignmentChangeEnabled": "True", "FFlagStudioToolBoxModelDragFix": "True", "DFFlagOrder66": "False", "FFlagCloudIconFixEnabled": "True", "DFFlagFixHealthReplication": "True", "DFFlagReplicateAnimationSpeed": "True", "FFlagSurfaceLightEnabled": "True", "FFlagLuaFollowers": "True", "FFlagNewNotificationsScript": "True", "FFlagStudioSendMouseIdleToPluginMouse": "True", "DFFlagPhysicsOptimizeAssemblyHistory": "True", "DFFlagPhysicsOptimizeBallBallContact": "True", "DFFlagUseNewBubbleSkin": "True", "DFFlagUse9FrameBackgroundTransparency": "True", "DFFlagCheckForHeadHit": "False", "DFFlagUseHttpsForAllCalls": "True", "DFFlagLoadCoreModules": "True", "FFlagStudioRecentSavesEnabled": "True", "FFlagStudioToolBoxInsertUseRayTrace": "True", "FFlagInterpolationUseWightedDelay": "True", "FFlagUseInGameTopBar": "True", "FFlagNewPurchaseScript": "True", "FFlagStudioEnableGamepadSupport": "True", "FFlagStudioRemoveDuplicateParts": "True", "FFlagStudioLaunchDecalToolAfterDrag": "True", "DFFlagHumanoidFloorPVUpdateSignal": "True", "DFFlagHumanoidFloorDetectTeleport": "True", "DFFlagHumanoidFloorForceBufferZone": "False", "DFFlagHumanoidFloorManualDeltaUpdateManagment": "True", "DFFlagHumanoidFloorManualFrictionLimitation": "True", "FStringPlaceFilter_InterpolationTimingFix": "True;208770506", "DFFlagUpdateHumanoidNameAndHealth": "True", "DFFlagEnableHumanoidDisplayDistances": "True", "FFlagFixTouchInputEventStates": "False", "DFFlagInterpolationTimingFix": "True", "FIntRenderGBufferMinQLvl": "16", "FFlagResizeGuiOnStep": "True", "FFlagDontFireFakeMouseEventsOnUIS": "True", "FFlagCameraUseOwnViewport": "True", "FFlagStudioEnableDragMultiPartsAsSinglePart": "True", "FFlagGameExplorerMoveImagesUnderAssetsGroup": "True", "FFlagIgnoreBlankDataOnStore": "True", "DFFlagNetworkFilterAllowToolWelds": true, "FFlagStudioExplorerSlowSelectionFix": "False", "DFIntHttpInfluxHundredthsPercentage": 0, "DFStringHttpInfluxURL": "http://ec2-52-8-11-103.us-west-1.compute.amazonaws.com:8086", "DFStringHttpInfluxDatabase": "roblox", "DFStringHttpInfluxUser": "rob", "DFStringHttpInfluxPassword": "playfaster", "FFlagStudioSpawnLocationsDefaultValues": "True", "FFlagStudioDE11536FixEnabled": "True", "FFlagStudioRibbonGroupResizeFixEnabled": "True", "FFlagGradientStep": "True", "FFlagUseNewContentProvider": "False", "SFFlagEquipToolOnClient": "True", "FFlagStartWindowMaximizedDefault": "True", "FFlagUseNewKeyboardHandling": "True", "FFlagCameraZoomNoModifier": "True", "DFFlagRemoteValidateSubscribersError": "True", "FFlagNewMenuSettingsScript": "True", "FFlagStudioDE9790FixEnabled": "True", "DFFlagHttpCurlSanitizeUrl": "True", "FFlagPassBaseUrlIntoGameServerScript": "False", "DFFlagRemoveDataModelDependenceInWaitForChild": "True", "FFlagStudioUseCurlCookieSharing": "False", "FFlagFilterAddSelectionToSameDataModel": "True", "DFFlagUseCanManageApiToDetermineConsoleAccess": "True", "DFIntMoveInGameChatToTopPlaceId": 1, "FFlagStudioProgressIndicatorForInsertEnabled": "True", "FFlagTerrainLazyGrid": "True", "FFlagHintsRenderInUserGuiRect": "True", "DFFlagCustomEmitterInstanceEnabled": "True", "FFlagCustomEmitterRenderEnabled": "True", "FFlagCustomEmitterLuaTypesEnabled": "True", "FFlagCallSetFocusFromCorrectThread": true, "FFlagFastRevert": true, "FFlagSleepBeforeSpinlock": true, "FFlagSparseCheckFastFail": true, "FFlagStudioSmoothTerrainPlugin": "True", "FFlagStudioLoadPluginsLate": "True", "FFlagStudioInsertIntoStarterPack": "True", "FFlagStudioIgnoreSSLErrors": "True", "DFFlagFixJointReparentingDE11763": "True", "DFFlagPhysicsInvalidateContactCache": "True", "FFlagLuaMathNoise": "True", "FFlagArcHandlesBidirectional": "True", "FFlagChangeHistoryFixPendingChanges": "True", "DFFlagWorkspaceSkipTerrainRaycastForSurfaceGui": "True", "FFlagStudioBatchItemMapAddChild": "True", "FFlagRenderCameraFocusFix": "True", "DFFlagReplicatorWorkspaceProperties": "True", "FFlagDirectX11Enable": "True", "FFlagCheckDegenerateCases": true, "DFFlagUseServerCoreScripts": "True", "DFFlagCorrectFloorNormal": "True", "FFlagNewBadgeServiceUrlEnabled": "True", "FFlagBubbleChatbarDocksAtTop": "True", "FFlagSmoothTerrainClient": "True", "FFlagLuaUseBuiltinEqForEnum": "True", "FFlagPlaceLauncherThreadCheckDmClosed": "True", "DFFlagAppendTrackerIdToTeleportUrl": "True", "FFlagPlayerMouseRespectGuiOffset": "True", "DFFlagReportElevatedPhysicsFPSToGA": "True", "DFFlagPreventReturnOfElevatedPhysicsFPS": "True", "FFlagStudioIgnoreMouseMoveOnIdle": "True", "FFlagStudioDraggerFixes": "True", "FLogUseLuaMemoryPool": "0", "FFlagCSGNewTriangulate": "True", "DFFlagLuaFixResumeWaiting": "True", "FFlagFRMInStudio": "True", "DFFlagFixLadderClimbSpeed": "True", "DFFlagNoWalkAnimWeld": "False", "DFFlagImprovedKick": "True", "FFlagRenderFixLightGridDirty": "True", "FFlagLoadLinkedScriptsOnDataModelLoad": "True", "FFlagFixMeshOffset": "True", "FIntLaunchInfluxHundredthsPercentage": 0, "DFIntJoinInfluxHundredthsPercentage": 0, "FFlagSmoothTerrain": "True", "FFlagNewVehicleHud": "True", "DFFlagHumanoidStandOnSeatDestroyed": "True", "DFFlagGuiBase3dReplicateColor3WithBrickColor": "True", "FFlagTaskSchedulerCyclicExecutive": "True", "FFlagTaskSchedulerCyclicExecutiveStudio": "True", "DFIntElevatedPhysicsFPSReportThresholdTenths": "585", "DFIntExpireMarketPlaceServiceCacheSeconds": "60", "DFFlagEnableMarketPlaceServiceCaching": "True", "DFFlagUseNewAnalyticsApi": "True", "DFFlagHandleAdornmentEnabled": "True", "DFFlagGetTouchingPartsEnabled": "True", "DFFlagJoinUnjoinFromOthersEnabled": "True", "DFFlagSmoothTerrainDebounceUpdates": "True", "FFlagStudioAuthenticationCleanup": "True", "FFlagRenderFixGBufferLOD": "True", "FFlagStudioDraggerCrashFixEnabled": "True", "FFlagDraggerCrashFixEnabled": "True", "DFFlagEnableRapidJSONParser": "True", "DFFlagPushLuaWorldRayOriginToNearClipPlane": "True", "FFlagLoadTimeModificationTestFlag": "True", "DFFlagPhysicsFastSmoothTerrainUpdate": "True", "DFFlagSmoothTerrainPhysicsExpandPrimitiveOptimal": "True", "DFFlagFixBytesOnJoinReporting": "True", "FFlagRenderGBufferEverywhere": "False", "DFFlagSmoothTerrainPhysicsRayAabbExact": "True", "DFIntSmoothTerrainPhysicsRayAabbSlop": "1", "DFIntMaxClusterKBPerSecond": "300", "FStringPlaceFilter_UseNewAnalyticsApi": "True;192800", "FLogLuaAssert": "0", "FFlagSmoothTerrainCountCellVolume": "True", "DFFlagSmoothTerrainWorldToCellUseDiagonals": "True", "DFFlagAnalyticsUseEvtInsteadOfAction": "True", "FFlagTransformToolEnabled": "True", "FFlagStudioPluginDragEnterEventEnabled": "True", "DFFlagFireSelectionChangeOncePerChange": "False", "FIntLuaAssertCrash": "0", "FFlagAlternateFontKerning": "True", "FFlagRenderFixCameraFocus": "False", "DFFlagCSGPhysicsSphereRotationIdentity": "True", "DFFlagCSGPhysicsRefreshContactsManually": "True", "FFlagStudioUndoEnabledForEdit": "False", "FFlagLuaDebuggerCrashFixEnabled": "True", "DFIntLuaChatFloodCheckMessages": 7, "DFIntLuaChatFloodCheckInterval": 15, "FFlagLuaChatFiltering": "True", "FFlagMobileToggleChatVisibleIcon": "True", "FFlagLinkedScriptsBasicUIEnabled": "False", "FFlagGlowEnabled": "True", "FFlagStudioDE9132FixEnabled": "True", "DFFlagHttpCurlHandle301": "True", "FFlagSearchToolboxByDataModelSearchString": "True", "FFlagClientABTestingEnabled": "False", "FFlagStudioSmoothTerrainForNewPlaces": "True", "FFlagUsePGSSolver": "True", "FFlagSimplifyKeyboardInputPath": "False", "FFlagNewInGameDevConsole": "True" }
\ No newline at end of file
diff --git a/Setting/QuietGet/ClientAppSettings/indexbroken.php b/Setting/QuietGet/ClientAppSettings/indexbroken.php
new file mode 100644
index 0000000..3705290
--- /dev/null
+++ b/Setting/QuietGet/ClientAppSettings/indexbroken.php
@@ -0,0 +1 @@
+{ "GoogleAnalyticsAccountPropertyID": "UA-43420590-3", "GoogleAnalyticsAccountPropertyIDPlayer": "UA-43420590-14", "DFFlagUseKeyframeHumanoidAnimations": "True", "AllowVideoPreRoll": true, "FFlagWaterEnabled": "True", "FFlagServerScriptProtection": "False", "FFlagTaskSchedulerUseSharedPtr": "True", "FFlagReparentingLockEnabled": "True", "FFlagDeprecateMeaninglessTerrainPropertiesAndMethods": "True", "FLogAsserts": "0", "NonScriptableAccessEnabled": "False", "FFlagNonScriptableAccessEnabled": "False", "FFlagUsesNewCameraFrustum": "False", "FLogCloseDataModel": "3", "FFlagImmediateYieldResultsEnabled": "True", "FFlagIsChangeHistoryRunAware": "True", "FFlagDisplayFPS": "False", "FFlagDE4411Fixed": "True", "FFlagAreSoundsFiltered": "True", "FFlagDE4510Fixed": "True", "FFlagDE4528Fixed": "False", "FFlagDE4508Fixed": "False", "FFlagFastClone": "False", "CaptureQTStudioCountersEnabled": "True", "CaptureMFCStudioCountersEnabled": "True", "CaptureCountersIntervalInMinutes": "5", "FFlagLoadingGuiEnabled": "False", "FLogServiceVectorResize": "4", "FLogServiceCreation": "4", "FFlagDMFeatherweightEnabled": "True", "FFlagRenderFeatherweightEnabled": "True", "FFlagRenderFeatherweightUseGeometryGenerator": "True", "FFlagRenderNoDMLock": "True", "FFlagFRMCullDebris": "True", "FFlagMouseMoveOptimization": "True", "FFlagDisableClickToWalk": "True", "FFlagSegregatedLuaEnvironments": "True", "FFlagInGamePurchases": "True", "FFlagOpenNativeBrowserWindowFromLua": "True", "FFlagRenderFlexClusterEnabled": "False", "ReorderGUI": "False", "FFlagRenderTextureCompositorUse32Bit": "True", "FFlagScriptAutoIndent": "True", "FFlagRenderShadowFadeout": "True", "FFlagDE3737Fixed": "True", "FFlagFRMUsePerformanceLockstepTable": "False", "FFlagD3D9UseSoftwareVertexShaders": "True", "FFlagRenderFastClusterParts": "True", "FFlagRenderFastClusterHumanoids": "True", "FFlagFRMForceShadingQualityIfShadowAll": "False", "FFlagNewRaknetTimestamp": "True", "FFlagUpdateTargetPointBeforeMouseDown": "True", "FFlagRenderFeatherweightForHighQuality": "False", "FFlagQtStudioHighlightAdornments": "True", "FFlagQtStudioToggleCollisionCheck": "True", "FFlagRobloxStudio2013MessageEnabled": "True", "FFlagDrawSelectionBoxLinesFarAway": "True", "FFlagThrottleIfNotFocus": "True", "AxisAdornmentGrabSize": "12", "FFlagProcessAllPacketsPerStep": "True", "FFlagImmediateCrashUploadEnabled": "True", "FFlagImmediateHangUploadEnabled": "True", "FFlagQTStudioDoNotDeleteWebDlg": "True", "FFlagQTStudioDoNotRedirect": "True", "FFlagFilterInvisibleNonCollidePartsInLadderRaycasts": "True", "FFlagScriptToggleFold": "True", "FFlagScriptCommentSelection": "True", "FFlagUS14116": "True", "FFlagRenderFastClusterForceSleepForFixed": "True", "FFlagFRMAdornSupport": "True", "FFlagEThrottleBumpUp": "True", "FFlagEditModeLaunchFromWebsiteEnabled": "True", "FFlagCameraJitterFix": "True", "FFlagShowSplashScreen": "True", "FFlagSkipBroadPhaseWhenThrottling": "True", "FFlagConsistentThrottlingIncrements": "True", "FFlagBlockBlockNarrowPhaseRefactor": "True", "FFlagClampEdgeEdgeConnectorPointsToEdges": "True", "FFlagPolyPolyFaceFacePairUsesAlternativeFace": "True", "FFlagFreeFallOptimization": "True", "FFlagImpulseSolverForContact": "True", "FFlagReduceToleranceToEdgeEdgeParallelism": "True", "FFlagEnableSixDigitDoublePrecision": "True", "FFlagQtStudioCreateJointsAutomatically": "True", "FFlagFriendlyErrorMsgOnStartGameFailure": "True", "FFlagQtStudioVideoRecordingEnabled": "True", "FFlagEnableRubberBandSelection": "True", "FFlagQtStudioScreenshotEnabled": "True", "FFlagClickDrillDown": "True", "FFlagFixNoPhysicsGlitchWithGyro": "True", "FFlagFixFirstPersonToolLag": "True", "FFlagUS14597": "True", "FFlagActOnUS14597": "True", "FFlagUseVirtualMethodForCellCallback": "True", "FFlagTurnOffUnthrottledLogs": "False", "FLogFullRenderObjects": "0", "FLogRenderFastCluster": "0", "PublishedProjectsPageHeight": "535", "PublishedProjectsPageUrl": "/ide/publish", "StartPageUrl": "/ide/welcome", "FFlagOpenNewWindowsInDefaultBrowser": "True", "FFlagOnScreenProfiler": "False", "FFlagUS14933": "True", "FFlagActOnUS14933": "True", "FFlagInitializeNewPlace": "True", "FFlagQtFileOpenCrashFix": "True", "FFlagWaitUntilSignalForJavascriptInit": "True", "FFlagQtStudioCrashCounters": "True", "PrizeAssetIDs": "0=110718551=Congratulations! Your success at publishing a place has earned you the Eggcellent Builder hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;1=110719580=Congratulations! Your exploration of ROBLOX Studio's models has led you to the Eggstreme Builder hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;2=110720049=Congratulations! Your contribution to ROBLOX's content catalog has earned you the Eggsultant Contributor hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;3=110790044=Congratulations! Your large experience in scripting has earned you the rare Eggscruciatingly Deviled Scripter hat. You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;4=110790072=Congratulations! Your flexibility at finding eggs has led you to the Yolk's on Us hat! You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!;5=110790103=Congratulations! You've found the Eggsplosion hat! You can find this in your inventory on the website. Keep building to find more ROBLOX Studio Eggs!", "PrizeAwarderURL": "/ostara/boon", "MinNumberScriptExecutionsToGetPrize": 500, "FFlagUS15154": "True", "FFlagActOnUS15154": "True", "FFlagValidateAssetUrlEnabled": "True", "FFlagDebugCrashEnabled": "False", "FFlagRenderFastClusterHighQuality": "True", "FLogHangDetection": "3", "FFlagRenderFastClusterMergeDraws": "True", "FFlagRenderFastClusterMergeBuffers": "True", "FFlagVoxelGridInsideMegaCluster": "True", "FFlagRenderForceBevelsOff": "True", "FFlagRenderLightGridTerrainOccupancy": "False", "FFlagRenderOptimizedTextureUpload": "True", "FFlagCharAnimationStats": "False", "FFlagRenderOpenGLForcePOTTextures": "True", "FFlagUseNewCameraZoomPath": "True", "FFlagQTStudioPublishFailure": "True", "ExcludeContactWithInteriorTerrainMinusYFace": "True", "FFlagFixUphillClimb": "True", "FFlagUseAveragedFloorHeight": "True", "FFlagScaleExplosionLifetime": "True", "FFlagUS15300": "True", "PublishedProjectsPageWidth": "950", "FFlagRenderFastClusterEverywhere": "True", "FLogPlayerShutdownLuaTimeoutSeconds": "1", "FFlagUS15977": "True", "FFlagQtFixToolDragging": "True", "FFlagSelectPartOnUndoRedo": "True", "FFlagUS15884": "True", "FFlagStatusBarProgress": "True", "FFlagStudioCheckForUpgrade": "True", "FFlagStudioInsertModelCounterEnabled": "True", "FFlagStudioAuthenticationFailureCounterEnabled": "True", "FFlagRenderCheckTextureContentProvider": "True", "FFlagRenderLightGridEnabled": "True", "FFlagStudioLightGridAPIVisible": "True", "FFlagActOnUS15526": "False", "FFlagUS15526": "True", "FFlagBetterSleepingJobErrorComputation": "True", "FFlagActOnUS15977": "False", "FLogDXVideoMemory": "4", "FFlagRenderNoLegacy": "True", "FFlagStudioLightGridOnForNewPlaces": "True", "FFlagPhysicsSkipRedundantJoinAll": "True", "FFlagTerrainOptimizedLoad": "True", "FFlagTerrainOptimizedStorage": "True", "FFlagTerrainOptimizedCHS": "True", "FFlagRenderGLES2": "True", "FFlagStudioMacAddressValidationEnabled": "True", "FFlagDoNotPassSunkEventsToPlayerMouse": "True", "FFlagQtAutoSave": "True", "FFlagRenderLoopExplicit": "True", "FFlagStudioUseBinaryFormatForPlay": "True", "PhysicsRemoveWorldAssemble_US16512": "True", "FFlagNativeSafeChatRendering": "True", "FFlagUS17162": "True", "DFFlagUS17412": "True", "FFlagRenderNewMegaCluster": "True", "FFlagAutoJumpForTouchDevices": "True", "DFFlagUS17646": "True", "DFFlagUS17889": "True", "FLogOutlineBrightnessMin": "50", "FLogOutlineBrightnessMax": "160", "FLogOutlineThickness": "40", "FFlagDE5511FixEnabled": "True", "FFlagDE4423Fixed": "True", "FFlagSymmetricContact": "True", "FFlagLocalMD5": "True", "FFlagStudioCookieParsingDisabled": "False", "FFlagLastWakeTimeSleepingJobError": "True", "FFlagPhysicsAllowAutoJointsWithSmallParts_DE6056": "True", "FFlagPhysicsLockGroupDraggerHitPointOntoSurface_DE6174": "True", "FFlagOutlineControlEnabled": "True", "FFlagAllowCommentedScriptSigs": "True", "FFlagDataModelUseBinaryFormatForSave": "True", "FFlagStudioUseBinaryFormatForSave": "True", "FFlagDebugAdornableCrash": "True", "FFlagOverlayDataModelEnabled": "True", "DFFlagFixInstanceParentDesyncBug": "True", "FFlagPromoteAssemblyModifications": "False", "FFlagFontSourceSans": "True", "DFFlagCreateHumanoidRootNode": "True", "FFlagRenderNewFonts": "True", "FFlagStudioCookieDesegregation": "True", "FFlagResponsiveJump": "True", "FFlagGoogleAnalyticsTrackingEnabled": "True", "FFlagNoCollideLadderFilter": "True", "FFlagFlexibleTipping": "True", "FFlagUseStrongerBalancer": "True", "FFlagClampControllerVelocityMag": "True", "DFFlagUseSaferChatMetadataLoading": "True", "FFlagSinkActiveGuiObjectMouseEvents": "False", "FLogLuaBridge": "2", "DFFlagPromoteAssemblyModifications": "True", "FFlagDeferredContacts": "True", "FFlagFRMUse60FPSLockstepTable": "True", "FFlagFRMAdjustForMultiCore": "True", "FFlagPhysics60HZ": "True", "FFlagQtRightClickContextMenu": "True", "FFlagUseTopmostSettingToBringWindowToFront": "True", "FFlagNewLightAPI": "True", "FFlagRenderLightGridShadows": "True", "FFlagRenderLightGridShadowsSmooth": "True", "DFFlagSanitizeKeyframeUrl": "True", "DFFlagDisableGetKeyframeSequence": "False", "FFlagCreateServerScriptServiceInStudio": "True", "FFlagCreateServerStorageInStudio": "True", "FFlagCreateReplicatedStorageInStudio": "True", "FFlagFilterEmoteChat": "True", "DFFlagUseCharacterRootforCameraTarget": "True", "FFlagImageRectEnabled": "True", "FFlagNewWaterMaterialEnable": "True", "DFFlagUserHttpAPIEnabled": "True", "DFIntUserHttpAccessUserId0": "0", "FFlagUserHttpAPIVisible": "True", "FFlagCameraChangeHistory": "True", "FFlagDE4640Fixed": "True", "FFlagShowStreamingEnabledProp": "True", "FFlagOptimizedDragger": "True", "FFlagRenderNewMaterials": "True", "FFlagRenderAnisotropy": "True", "FFlagStudioInitializeViewOnPaint": "True", "DFFlagPartsStreamingEnabled": "True", "FFlagStudioLuaDebugger": "True", "FFlagStudioLocalSpaceDragger": "True", "FFlagGuiRotationEnabled": "True", "FFlagDataStoreEnabled": "True", "DFFlagDisableTeleportConfirmation": "True", "DFFlagAllowTeleportFromServer": "True", "DFFlagNonBlockingTeleport": "True", "FFlagD3D9CrashOnError": "False", "FFlagRibbonBarEnabled": "True", "SFFlagInfiniteTerrain": "True", "FFlagStudioScriptBlockAutocomplete": "True", "FFlagRenderFixAnchoredLag": "True", "DFFlagAllowAllUsersToUseHttpService": "True", "GoogleAnalyticsAccountPropertyIDClient": "", "FFlagSurfaceGuiVisible": "True", "FFlagStudioIntellesenseEnabled": "True", "FFlagAsyncPostMachineInfo": "True", "FFlagModuleScriptsVisible": "True", "FFlagModelPluginsEnabled": "True", "FFlagGetUserIdFromPluginEnabled": "True", "FFlagStudioPluginUIActionEnabled": "True", "DFFlagRemoveAdornFromBucketInDtor": "True", "FFlagRapidJSONEnabled": "True", "DFFlagDE6959Fixed": "True", "DFFlagScopedMutexOnJSONParser": "True", "FFlagSupressNavOnTextBoxFocus": "True", "DFFlagExplicitPostContentType": "True", "DFFlagAddPlaceIdToAnimationRequests": "True", "FFlagCreatePlaceEnabled": "True", "DFFlagClientAdditionalPOSTHeaders": "True", "FFlagEnableAnimationExport": "True", "DFFlagAnimationAllowProdUrls": "True", "FFlagGetUserIDFromPluginEnabled": "True", "FFlagStudioContextualHelpEnabled": "True", "FFlagLogServiceEnabled": "True", "FFlagQtPlaySoloOptimization": "True", "FFlagStudioBuildGui": "True", "DFFlagListenForZVectorChanges": "True", "DFFlagUserInputServiceProcessOnRender": "True", "FFlagDE7421Fixed": "True", "FFlagStudioExplorerActionsEnabledInScriptView": "True", "FFlagHumanoidNetworkOptEnabled": "True", "DFFlagEnableNPCServerAnimation": "True", "DFFlagDataStoreUseUForGlobalDataStore": "True", "DFFlagDataStoreAllowedForEveryone": "True", "DFFlagBadTypeOnConnectErrorEnabled": "True", "FFlagStudioRemoveUpdateUIThread": "True", "FFlagPhysicsSkipUnnecessaryContactCreation": "False", "FFlagUseNewHumanoidCache": "True", "FFlagSecureReceiptsBackendEnabled": "True", "FFlagOrderedDataStoreEnabled": "True", "FFlagStudioLuaDebuggerGA": "True", "FFlagNPSSetScriptDocsReadOnly": "True", "FFlagRDBGHashStringComparison": "True", "FFlagStudioDebuggerVisitDescendants": "True", "FFlagDeprecateScriptInfoService": "True", "FFlagIntellisenseScriptContextDatamodelSearchingEnabled": "True", "FFlagStudioCompareDatamodelHashOnClose": "True", "FFlagSecureReceiptsFrontendEnabled": "True", "DFFlagCreatePlaceEnabledForEveryone": "True", "FFlagCreatePlaceInPlayerInventoryEnabled": "True", "DFFlagAddRequestIdToDeveloperProductPurchases": "True", "DFFlagUseYPCallInsteadOfPCallEnabled": "True", "FFlagStudioMouseOffsetFixEnabled": "True", "DFFlagPlaceValidation": "True", "FFlagReconstructAssetUrl": "True", "FFlagUseNewSoundEngine": "True", "FIntMinMillisecondLengthForLongSoundChannel": "5000", "FFlagStudioHideInsertedServices": "True", "FFlagStudioAlwaysSetActionEnabledState": "True", "FFlagRenderNew": "True", "FIntRenderNewPercentWin": "100", "FIntRenderNewPercentMac": "100", "FLogGraphics": "6", "FFlagStudioInSyncWebKitAuthentication": "False", "DFFlagDisallowHopperServerScriptReplication": "True", "FFlagInterpolationFix": "False", "FFlagHeartbeatAt60Hz": "False", "DFFlagFixProcessReceiptValueTypes": "True", "DFFlagPhysicsSkipUnnecessaryContactCreation": "True", "FFlagStudioLiveCoding": "True", "FFlagPlayerHumanoidStep60Hz": "True", "DFFlagCrispFilteringEnabled": "False", "SFFlagProtocolSynchronization": "True", "FFlagUserInputServicePipelineStudio": "True", "FFlagUserInputServicePipelineWindowsClient": "True", "FFlagUserInputServicePipelineMacClient": "True", "FFlagStudioKeyboardMouseConfig": "True", "DFFlagLogServiceEnabled": "True", "DFFlagLoadAnimationsThroughInsertService": "True", "FFlagFRMFogEnabled": "True", "FLogBrowserActivity": "3", "DFFlagPhysicsPacketAlwaysUseCurrentTime": "True", "FFlagFixedStudioRotateTool": "True", "FFlagRibbonBarEnabledGA": "True", "FFlagRenderSafeChat": "False", "DFFlagPhysicsAllowSimRadiusToDecreaseToOne": "True", "DFFlagPhysicsAggressiveSimRadiusReduction": "True", "DFFlagLuaYieldErrorNoResumeEnabled": "True", "DFFlagEnableJointCache": "False", "DFFlagOnCloseTimeoutEnabled": "True", "FFlagStudioQuickInsertEnabled": "True", "FFlagStudioPropertiesRespectCollisionToggle": "True", "FFlagTweenServiceUsesRenderStep": "True", "FFlagUseNewSoundEngine3dFix": "True", "FFlagDebugUseDefaultGlobalSettings": "True", "FFlagStudioMiddleMouseTrackCamera": "False", "FFlagTurnOffiOSNativeControls": "True", "DFFlagUseNewHumanoidHealthGui": "True", "FFlagUS21919": "True", "DFFlagLoggingConsoleEnabled": "True", "DFFlagAllowModuleLoadingFromAssetId": "True", "FFlagStudioZoomExtentsExplorerFixEnabled": "True", "FFlagStudioExplorerFilterEnabled": "False", "FFlagStudioPropertySearchDisabled": "False", "FFlagLuaDebuggerBreakOnError": "True", "FFlagRetentionTrackingEnabled": "True", "FFlagShowAlmostAllItemsInExplorer": "True", "FFlagStudioFindInAllScriptsEnabled": "True", "FFlagImprovedNameOcclusion": "True", "FFlagHumanoidMoveToDefaultValueEnabled": "True", "FFlagEnableDisplayDistances": "True", "FFlagUseMinMaxZoomDistance": "True", "SFFlagAllowPhysicsPacketCompression": "False", "FFlagStudioOneClickColorPickerEnabled": "True", "DFFlagHumanoidMoveToDefaultValueEnabled": "True", "FFlagStudioFindContextFixEnabled": "False", "VideoPreRollWaitTimeSeconds": 45, "FFlagBalancingRateLimit": "True", "FFlagLadderCheckRate": "True", "FFlagStateSpecificAutoJump": "True", "SFFlagOneWaySimRadiusReplication": "True", "DFFlagApiDictionaryCompression": "True", "SFFlagPathBasedPartMovement": "True", "FFlagEnsureInputIsCorrectState": "False", "DFFlagLuaLoadStringStrictSecurity": "True", "DFFlagCrossPacketCompression": "True", "FFlagWorkspaceLoadStringEnabledHidden": "True", "FFlagStudioPasteAsSiblingEnabled": "True", "FFlagStudioDuplicateActionEnabled": "True", "FFlagPreventInterpolationOnCFrameChange": "True", "FLogNetworkPacketsReceive": 5, "FFlagPlayPauseFix": "True", "DFFlagCrashOnNetworkPacketError": "False", "FFlagHumanoidStateInterfaces": "True", "FFlagRenderDownloadAssets": "True", "FFlagBreakOnErrorConfirmationDialog": "True", "FFlagStudioAnalyticsEnabled": "True", "FFlagAutoRotateFlag": "True", "DFFlagUseImprovedLadderClimb": "True", "FFlagUseCameraOffset": "True", "FFlagRenderBlobShadows": "True", "DFFlagWebParserDisableInstances": "False", "FFlagStudioNewWiki": "True", "DFFlagLogPacketErrorDetails": "False", "FFlagStudioLiveColorProperty": "False", "FFlagLimitHorizontalDragForce": "True", "FFlagEnableNonleathalExplosions": "True", "DFFlagCreateSeatWeldOnServer": "True", "FFlagGraphicsUseRetina": "True", "FFlagDynamicEnvmapEnabled": "True", "DFFlagDeferredTouchReplication": true, "DFFlagCreatePlayerGuiEarlier": "True", "DFFlagProjectileOwnershipOptimization": "True", "DFFlagLoadSourceForCoreScriptsBeforeInserting": "False", "GoogleAnalyticsLoadStudio": 1, "DFFlagTaskSchedulerFindJobOpt": "True", "SFFlagPreventInterpolationOnCFrameChange": "True", "DFIntNumPhysicsPacketsPerStep": 2, "DFFlagDataStoreUrlEncodingEnabled": "True", "FFlagShowWebPlaceNameOnTabWhenOpeningFromWeb": "True", "DFFlagTrackTimesScriptLoadedFromLinkedSource": "True", "FFlagToggleDevConsoleThroughChatCommandEnabled": "True", "FFlagEnableFullMonitorsResolution": "True", "DFFlagAlwaysUseHumanoidMass": "True", "DFFlagUseStrongerGroundControl": "True", "DFFlagCorrectlyReportSpeedOnRunStart": "True", "FFlagLuaDebuggerImprovedToolTip": "True", "FFlagLuaDebuggerPopulateFuncName": "True", "FFlagLuaDebuggerNewCodeFlow": "True", "DFFlagValidateCharacterAppearanceUrl": "false", "FFlagStudioQuickAccessCustomization": "True", "DFFlagTaskSchedulerUpdateJobPriorityOnWake": "True", "DFFlagTaskSchedulerNotUpdateErrorOnPreStep": "True", "FFlagWikiSelectionSearch": "True", "DFIntTaskSchedularBatchErrorCalcFPS": 1200, "FFlagSuppressNavOnTextBoxFocus": "False", "FFlagEnabledMouseIconStack": "True", "DFFlagFastClone": "True", "DFFlagLuaNoTailCalls": "True", "DFFlagFilterStreamingProps": "True", "DFFlagNetworkOwnerOptEnabled": "True", "DFFlagPathfindingEnabled": "True", "FFlagEnableiOSSettingsLeave": "True", "FFlagUseFollowCamera": "True", "FFlagDefaultToFollowCameraOnTouch": "True", "DFFlagAllowMoveToInMouseLookMove": "True", "DFFlagAllowHumanoidDecalTransparency": "True", "DFFlagSupportCsrfHeaders": "True", "DFFlagConfigureInsertServiceFromSettings": "True", "FFlagPathfindingClientComputeEnabled": "True", "DFFlagLuaResumeSupportsCeeCalls": "True", "DFFlagPhysicsSenderErrorCalcOpt": "True", "DFFlagClearPlayerReceivingServerLogsOnLeave": "True", "DFFlagConsoleCodeExecutionEnabled": "True", "DFFlagCSGDictionaryReplication": "True", "FFlagCSGToolsEnabled": "True", "FFlagCSGDictionaryServiceEnabled": "True", "FFlagCSGMeshRenderEnable": "True", "FFlagCSGChangeHistory": "True", "FFlagCSGMeshColorEnable": "True", "FFlagCSGMeshColorToolsEnabled": "True", "FFlagCSGScaleEnabled": "True", "FFlagCylinderUsesConstantTessellation": "True", "FFlagStudioDraggersScaleFixes": "True", "FFlagCSGDecalsEnabled": "True", "FFlagCSGMigrateChildData": "True", "SFFlagBinaryStringReplicationFix": "True", "FFlagHummanoidScaleEnable": "True", "FFlagStudioDataModelIsStudioFix": "True", "DFFlagWebParserEnforceASCIIEnabled": "True", "DFFlagScriptDefaultSourceIsEmpty": "True", "FFlagFixCaptureFocusInput": "True", "FFlagFireUserInputServiceEventsAfterDMEvents": "True", "FFlagVectorErrorOnNilArithmetic": "True", "FFlagFontSmoothScalling": "True", "DFFlagUseImageColor": "True", "FFlagStopNoPhysicsStrafe": "True", "DFFlagDebugLogNetworkErrorToDB": "False", "FFlagLowQMaterialsEnable": "True", "FFLagEnableFullMonitorsResolution": "True", "FFlagStudioChildProcessCleanEnabled": "True", "DFFlagAllowFullModelsWhenLoadingModules": "True", "DFFlagRealWinInetHttpCacheBypassingEnabled": "True", "FFlagNewUniverseInfoEndpointEnabled": "True", "FFlagGameExplorerEnabled": "True", "FFlagStudioUseBinaryFormatForModelPublish": "True", "FFlagGraphicsFeatureLvlStatsEnable": "True", "FFlagStudioEnableWebKitPlugins": "True", "DFFlagSendHumanoidTouchedSignal": "True", "DFFlagReduceHumanoidBounce": "True", "DFFlagUseNewSounds": "True", "FFlagFixHumanoidRootPartCollision": "True", "FFlagEnableAndroidMenuLeave": "True", "FFlagOnlyProcessGestureEventsWhenSunk": "True", "FFlagAdServiceReportImpressions": "True", "FFlagStudioUseExtendedHTTPTimeout": "True", "FFlagStudioSeparateActionByActivationMethod": "False", "DFFlagPhysicsSenderThrottleBasedOnBufferHealth": "True", "FFlagCSGExportFailure": "False", "DFFlagGetGroupInfoEnabled": "True", "DFFlagGetGroupRelationsEnabled": "True", "FStringPlaceFilter_StateBasedAnimationReplication": "True;175953385;174810327;181219650", "SFFlagTopRepContSync": "True", "FFlagStudioUseBinaryFormatForModelSave": "True", "EnableFullMonitorsResolution": "True", "DFFlagRenderSteppedServerExceptionEnabled": "True", "FFlagUseWindowSizeFromGameSettings": "True", "DFFlagCheckStudioApiAccess": "True", "FFlagGameExplorerPublishEnabled": "True", "DFFlagKeepXmlIdsBetweenLoads": "True", "DFFlagReadXmlCDataEnabled": "True", "FFlagStudioRemoveToolSounds": "True", "FFlagStudioOneStudGridDefault": "True", "FFlagStudioPartSymmetricByDefault": "True", "FFlagStudioIncreasedBaseplateSize": "True", "FFlagSkipSilentAudioOps": "True", "SFFlagGuid64Bit": "False", "FIntValidateLauncherPercent": "100", "FFlagCSGDataLossFixEnabled": "True", "DFStringRobloxAnalyticsURL": "http://ecsv2.roblox.com/", "DFFlagRobloxAnalyticsTrackingEnabled": "True", "FFlagStudioOpenFirstPlace": "False", "FFlagStudioOpenLastSaved": "False", "FFlagStudioShowTutorialsByDefault": "True", "FFlagStudioForceToolboxSize": "True", "FFlagStudioExplorerDisabledByDefault": "True", "FFlagStudioDefaultWidgetSizeChangesEnabled": "True", "FFlagStudioUseScriptAnalyzer": "True", "FFlagNoClimbPeople": "True", "DFFlagAnimationFormatAssetId": "True", "FFlagStudioMobileCompanionEnabled": "True", "FFlagGetCorrectScreenResolutionFaster": "True", "DFFlagFixTouchEndedReporting": "False", "FFlagStudioOpenFirstPlaceBasePlate": "False", "FFlagStudioTeleportPlaySolo": "True", "FFlagCSGRemoveScriptScaleRestriction": "True", "FFlagStudioDE7928FixEnabled": "True", "FFlagDE8768FixEnabled": "True", "FFlagStudioDE9108FixEnabled": "True", "FFlagStudioPlaySoloMapDebuggerData": "True", "FFlagLuaDebuggerCloneDebugger": "True", "FFlagStudioCommandLineSaveEditText": "False", "FFlagRenderLightgridInPerformEnable": "True", "SFFlagStateBasedAnimationReplication": "True", "FFlagVolumeControlInGameEnabled": "True", "FFlagGameConfigurerUseStatsService": "True", "FFlagStudioUseHttpAuthentication": "True", "FFlagDetectTemplatesWhenSettingUpGameExplorerEnabled": "True", "FFlagEntityNameEditingEnabled": "True", "FFlagNewCreatePlaceFlowEnabled": "True", "FFlagFakePlayableDevices": "False", "FFlagMutePreRollSoundService": "True", "DFFlagBodyMoverParentingFix": "True", "DFFlagBroadcastServerOnAllInterfaces": "True", "HttpUseCurlPercentageWinClient": "100", "HttpUseCurlPercentageMacClient": "100", "HttpUseCurlPercentageWinStudio": "100", "HttpUseCurlPercentageMacStudio": "100", "SFFlagReplicatedFirstEnabled": "True", "DFFlagCSGShrinkForMargin": "True", "FFlagPhysicsBulletConnectorPointRecalc": "True", "DFIntBulletContactBreakThresholdPercent": "200", "DFIntBulletContactBreakOrthogonalThresholdPercent": "200", "FFlagPhysicsBulletConnectorMatching": "True", "FFlagPhysicsBulletUseProximityMatching": "False", "FFlagPhysicsCSGUsesBullet": "True", "DFFlagCSGPhysicsDeserializeRefactor": "True", "FFlagWedgeEnableDecalOnTop": "True", "FFlagFrustumTestGUI": "True", "FFlagFeatureLvlsDX11BeforeDeviceCreate": "True", "FFlagStudioPasteSyncEnabled": "True", "FFlagResetMouseCursorOnToolUnequip": "True", "DFFlagUpdateCameraTarget": "True", "DFFlagFixGhostClimb": "True", "DFFlagUseStarterPlayer": "True", "FFlagStudioMobileEmulatorEnabled": "True", "FFlagStudioFindCrashFixEnabled": "True", "FFlagFixPartOffset": "True", "DFFlagLuaCloseUpvalues": "True", "FFlagRenderTextureCompositorUseBudgetForSize": "True", "FFlagAllowOutOfBoxAssets": "False", "FFlagRemoveTintingWhenActiveIsFalseOnImageButton": "True", "FFlagStudioModuleScriptDefaultContents": "True", "FFlagStudioHomeKeyChangeEnabled": "True", "FFlagStudioOpenStartPageForLogin": "True", "FFlagStudioNativeKeepSavedChanges": "True", "FFlagSerializeCurrentlyOpenPlaceWhenPublishingGame": "True", "FFlagGameNameLabelEnabled": "True", "FFlagStudioValidateBootstrapper": true, "FFlagRakNetReadFast": "True", "DFFlagPhysicsSenderSleepingUpdate": "True", "FFlagUseShortShingles": "True", "FFlagKKTChecks": "False", "DFFlagUseApiProxyThrottling": "True", "DFFlagValidateSetCharacter": true, "DFFlagUpdateHumanoidSimBodyInComputeForce": "True", "DFFlagNetworkPendingItemsPreserveTimestamp": true, "FFlagStudioCSGRotationalFix": "True", "FFlagNewLoadingScreen": "True", "FFlagScrollingFrameOverridesButtonsOnTouch": "True", "DFFlagStreamLargeAudioFiles": "True", "DFFlagNewLuaChatScript": "True", "DFFlagLoopedDefaultHumanoidAnimation": "True", "FFlagSoundsRespectDelayedStop": "False", "DFFlagCSGPhysicsErrorCatchingEnabled": "True", "DFFlagFireStoppedAnimSignal": "True", "FFlagStudioFixToolboxReload": "True", "FFlagCSGDecalsV2": "True", "FFlagLocalOptimizer": "True", "DFFlagClearFailedUrlsWhenClearingCacheEnabled": "True", "DFFlagSupportNamedAssetsShortcutUrl": "True", "DFFlagUseW3CURIParser": "True", "DFFlagContentProviderHttpCaching": "True", "FFlagNoWallClimb": "False", "FFlagSmoothMouseLock": "False", "DFFlagCSGPhysicsNanPrevention": "True", "FFlagStudioDE9818FixEnabled": "True", "FFlagGameExplorerImagesEnabled": "True", "DFFlagUS24505": "True", "FFlagStudioInsertOrientationFix": "True", "FFlagStudioTabOrderingEnabled": "True", "FFlagFramerateDeviationDroppedReport": "True", "FFlagModuleScriptsPerVmEnabled": "False", "FFlagGameExplorerImagesInsertEnabled": "True", "FFlagTexturePropertyWidgetEnabled": "True", "FFlagReloadAllImagesOnDataReload": "True", "FFlagModuleScriptsPerVmEnabledFix2": "True", "DFFlagFixBufferZoneContainsCheck": "False", "FFlagStudioPlaceAssetFromToolbox": "True", "FFlagChannelMasterMuting": "True", "FFlagStudioUseDelayedSyntaxCheck": "True", "FFlagStudioCommandLineSaveEditText ": "True", "DFFlagLuaDetectCyclicTables": "True", "FFlagStudioAddHelpInContextMenu": "True", "DFIntHttpCacheCleanMinFilesRequired": "3000", "DFIntHttpCacheCleanMaxFilesToKeep": "1500", "FFlagCSGVoxelizer": "True", "DFFlagCheckApiAccessInTransactionProcessing": "True", "FFlagBindPurchaseValidateCallbackInMarketplaceService": "True", "FFlagSetDataModelUniverseIdAfterPublishing": "True", "FFlagOpenScriptWorksOnModulesEnabled": "True", "FFlagStudioRibbonBarNewLayout": "True", "FFlagStudioRibbonBarLayoutFixes": "True", "FFlagStudioPlaceOnlineIndicator": "True", "FFlagRenderWangTiles": "True", "FFlagDisableBadUrl": true, "FFlagPrimalSolverLogBarrierIP": true, "FFlagDualSolverSimplex": true, "FFlagPrimalSolverSimplex": true, "FIntNumSmoothingPasses": 3, "FFlagVerifyConnection": true, "FIntRegLambda": 1400, "FFlagScriptAnalyzerPlaceholder": "True", "FFlagStudioCSGAssets": "True", "FFlagCSGStripPublishedData": "True", "DFFlagRaycastReturnSurfaceNormal": "True", "FFlagMoveGameExplorerActionsIntoContextMenu": "True", "FFlagStudioAdvanceCookieExpirationBugFixEnabled": "True", "FFlagNewBackpackScript": "True", "FFlagNewPlayerListScript": "True", "FFlagGameNameAtTopOfExplorer": "True", "FFlagStudioActActionsAsTools": "True", "FFlagStudioInsertAtMouseClick": "True", "FFlagStopLoadingStockSounds": "True", "DFFlagFixTimePositionReplication": "True", "DFFlagHttpReportStatistics": "True", "DFFlagEnableChatTestingInStudio": "True", "DFIntHttpSendStatsEveryXSeconds": "300", "FLogStepAnimatedJoints": "5", "DFFlagLuaDisconnectFailingSlots": "False", "DFFlagEnsureSoundPosIsUpdated": "True", "DFFlagLoadStarterGearEarlier": "False", "DFFlagBlockUsersInLuaChat": "True", "FFlagRibbonPartInsertNotAllowedInModel": "True", "DFFlagUsePlayerScripts": "True", "DFFlagUserAccessUserSettings": "True", "DFFlagUseLuaCameraAndControl": "True", "DFFlagUseLuaPCInput": "True", "DFFlagFixLuaMoveDirection": "True", "DFFlagUseDecalLocalTransparencyModifier": "True", "DFFlagUseFolder": "True", "DFFlagUsePreferredSpawnInPlaySoloTeleport": "True", "DFFlagFilterAddSelectionToSameDataModel": "False", "FFlagGameExplorerAutofillImageNameFromFileName": "True", "FFlagGameExplorerBulkImageUpload": "True", "FFlagStudioAllowAudioSettings": "True", "DFFlagUsePlayerInGroupLuaChat": "True", "FFlagStudioDecalPasteFix": "True", "FFlagStudioCtrlTabDocSwitchEnabled": "True", "DFIntDraggerMaxMovePercent": 60, "FFlagUseUniverseGetInfoCallToDetermineUniverseAccess": "True", "FFlagMaxFriendsCount": "True", "DFIntPercentApiRequestsRecordGoogleAnalytics": 0, "FFlagSelectSpinlock": "True", "FFlagFastZlibPath": "True", "DFFlagWriteXmlCDataEnabled": "True", "DFFlagUseSpawnPointOrientation": "True", "DFFlagUsePlayerSpawnPoint": "True", "DFFlagCSGPhysicsRecalculateBadContactsInConnectors": "True", "FFlagStudioPartAlignmentChangeEnabled": "True", "FFlagStudioToolBoxModelDragFix": "True", "DFFlagOrder66": "False", "FFlagCloudIconFixEnabled": "True", "DFFlagFixHealthReplication": "True", "DFFlagReplicateAnimationSpeed": "True", "FFlagSurfaceLightEnabled": "True", "FFlagLuaFollowers": "True", "FFlagNewNotificationsScript": "True", "FFlagStudioSendMouseIdleToPluginMouse": "True", "DFFlagPhysicsOptimizeAssemblyHistory": "True", "DFFlagPhysicsOptimizeBallBallContact": "True", "DFFlagUseNewBubbleSkin": "True", "DFFlagUse9FrameBackgroundTransparency": "True", "DFFlagCheckForHeadHit": "False", "DFFlagUseHttpsForAllCalls": "True", "DFFlagLoadCoreModules": "True", "FFlagStudioRecentSavesEnabled": "True", "FFlagStudioToolBoxInsertUseRayTrace": "True", "FFlagInterpolationUseWightedDelay": "True", "FFlagUseInGameTopBar": "True", "FFlagNewPurchaseScript": "True", "FFlagStudioEnableGamepadSupport": "True", "FFlagStudioRemoveDuplicateParts": "True", "FFlagStudioLaunchDecalToolAfterDrag": "True", "DFFlagHumanoidFloorPVUpdateSignal": "True", "DFFlagHumanoidFloorDetectTeleport": "True", "DFFlagHumanoidFloorForceBufferZone": "False", "DFFlagHumanoidFloorManualDeltaUpdateManagment": "True", "DFFlagHumanoidFloorManualFrictionLimitation": "True", "FStringPlaceFilter_InterpolationTimingFix": "True;208770506", "DFFlagUpdateHumanoidNameAndHealth": "True", "DFFlagEnableHumanoidDisplayDistances": "True", "FFlagFixTouchInputEventStates": "False", "DFFlagInterpolationTimingFix": "True", "FIntRenderGBufferMinQLvl": "16", "FFlagResizeGuiOnStep": "True", "FFlagDontFireFakeMouseEventsOnUIS": "True", "FFlagCameraUseOwnViewport": "True", "FFlagStudioEnableDragMultiPartsAsSinglePart": "True", "FFlagGameExplorerMoveImagesUnderAssetsGroup": "True", "FFlagIgnoreBlankDataOnStore": "True", "DFFlagNetworkFilterAllowToolWelds": true, "FFlagStudioExplorerSlowSelectionFix": "False", "DFIntHttpInfluxHundredthsPercentage": 0, "DFStringHttpInfluxURL": "http://ec2-52-8-11-103.us-west-1.compute.amazonaws.com:8086", "DFStringHttpInfluxDatabase": "roblox", "DFStringHttpInfluxUser": "rob", "DFStringHttpInfluxPassword": "playfaster", "FFlagStudioSpawnLocationsDefaultValues": "True", "FFlagStudioDE11536FixEnabled": "True", "FFlagStudioRibbonGroupResizeFixEnabled": "True", "FFlagGradientStep": "True", "FFlagUseNewContentProvider": "False", "SFFlagEquipToolOnClient": "True", "FFlagStartWindowMaximizedDefault": "True", "FFlagUseNewKeyboardHandling": "True", "FFlagCameraZoomNoModifier": "True", "DFFlagRemoteValidateSubscribersError": "True", "FFlagNewMenuSettingsScript": "True", "FFlagStudioDE9790FixEnabled": "True", "DFFlagHttpCurlSanitizeUrl": "True", "FFlagPassBaseUrlIntoGameServerScript": "False", "DFFlagRemoveDataModelDependenceInWaitForChild": "True", "FFlagStudioUseCurlCookieSharing": "False", "FFlagFilterAddSelectionToSameDataModel": "True", "DFFlagUseCanManageApiToDetermineConsoleAccess": "True", "DFIntMoveInGameChatToTopPlaceId": 1, "FFlagStudioProgressIndicatorForInsertEnabled": "True", "FFlagTerrainLazyGrid": "True", "FFlagHintsRenderInUserGuiRect": "True", "DFFlagCustomEmitterInstanceEnabled": "True", "FFlagCustomEmitterRenderEnabled": "True", "FFlagCustomEmitterLuaTypesEnabled": "True", "FFlagCallSetFocusFromCorrectThread": true, "FFlagFastRevert": true, "FFlagSleepBeforeSpinlock": true, "FFlagSparseCheckFastFail": true, "FFlagStudioSmoothTerrainPlugin": "True", "FFlagStudioLoadPluginsLate": "True", "FFlagStudioInsertIntoStarterPack": "True", "FFlagStudioIgnoreSSLErrors": "True", "DFFlagFixJointReparentingDE11763": "True", "DFFlagPhysicsInvalidateContactCache": "True", "FFlagLuaMathNoise": "True", "FFlagArcHandlesBidirectional": "True", "FFlagChangeHistoryFixPendingChanges": "True", "DFFlagWorkspaceSkipTerrainRaycastForSurfaceGui": "True", "FFlagStudioBatchItemMapAddChild": "True", "FFlagRenderCameraFocusFix": "True", "DFFlagReplicatorWorkspaceProperties": "True", "FFlagDirectX11Enable": "True", "FFlagCheckDegenerateCases": true, "DFFlagUseServerCoreScripts": "True", "DFFlagCorrectFloorNormal": "True", "FFlagNewBadgeServiceUrlEnabled": "True", "FFlagBubbleChatbarDocksAtTop": "True", "FFlagSmoothTerrainClient": "True", "FFlagLuaUseBuiltinEqForEnum": "True", "FFlagPlaceLauncherThreadCheckDmClosed": "True", "DFFlagAppendTrackerIdToTeleportUrl": "True", "FFlagPlayerMouseRespectGuiOffset": "True", "DFFlagReportElevatedPhysicsFPSToGA": "True", "DFFlagPreventReturnOfElevatedPhysicsFPS": "True", "FFlagStudioIgnoreMouseMoveOnIdle": "True", "FFlagStudioDraggerFixes": "True", "FLogUseLuaMemoryPool": "0", "FFlagCSGNewTriangulate": "True", "DFFlagLuaFixResumeWaiting": "True", "FFlagFRMInStudio": "True", "DFFlagFixLadderClimbSpeed": "True", "DFFlagNoWalkAnimWeld": "False", "DFFlagImprovedKick": "True", "FFlagRenderFixLightGridDirty": "True", "FFlagLoadLinkedScriptsOnDataModelLoad": "True", "FFlagFixMeshOffset": "True", "FIntLaunchInfluxHundredthsPercentage": 0, "DFIntJoinInfluxHundredthsPercentage": 0, "FFlagSmoothTerrain": "True", "FFlagNewVehicleHud": "True", "DFFlagHumanoidStandOnSeatDestroyed": "True", "DFFlagGuiBase3dReplicateColor3WithBrickColor": "True", "FFlagTaskSchedulerCyclicExecutive": "True", "FFlagTaskSchedulerCyclicExecutiveStudio": "True", "DFIntElevatedPhysicsFPSReportThresholdTenths": "585", "DFIntExpireMarketPlaceServiceCacheSeconds": "60", "DFFlagEnableMarketPlaceServiceCaching": "True", "DFFlagUseNewAnalyticsApi": "True", "DFFlagHandleAdornmentEnabled": "True", "DFFlagGetTouchingPartsEnabled": "True", "DFFlagJoinUnjoinFromOthersEnabled": "True", "DFFlagSmoothTerrainDebounceUpdates": "True", "FFlagStudioAuthenticationCleanup": "True", "FFlagRenderFixGBufferLOD": "True", "FFlagStudioDraggerCrashFixEnabled": "True", "FFlagDraggerCrashFixEnabled": "True", "DFFlagEnableRapidJSONParser": "True", "DFFlagPushLuaWorldRayOriginToNearClipPlane": "True", "FFlagLoadTimeModificationTestFlag": "True", "DFFlagPhysicsFastSmoothTerrainUpdate": "True", "DFFlagSmoothTerrainPhysicsExpandPrimitiveOptimal": "True", "DFFlagFixBytesOnJoinReporting": "True", "FFlagRenderGBufferEverywhere": "False", "DFFlagSmoothTerrainPhysicsRayAabbExact": "True", "DFIntSmoothTerrainPhysicsRayAabbSlop": "1", "DFIntMaxClusterKBPerSecond": "300", "FStringPlaceFilter_UseNewAnalyticsApi": "True;192800", "FLogLuaAssert": "0", "FFlagSmoothTerrainCountCellVolume": "True", "DFFlagSmoothTerrainWorldToCellUseDiagonals": "True", "DFFlagAnalyticsUseEvtInsteadOfAction": "True", "FFlagTransformToolEnabled": "True", "FFlagStudioPluginDragEnterEventEnabled": "True", "DFFlagFireSelectionChangeOncePerChange": "False", "FIntLuaAssertCrash": "0", "FFlagAlternateFontKerning": "True", "FFlagRenderFixCameraFocus": "False", "DFFlagCSGPhysicsSphereRotationIdentity": "True", "DFFlagCSGPhysicsRefreshContactsManually": "True", "FFlagStudioUndoEnabledForEdit": "False", "FFlagLuaDebuggerCrashFixEnabled": "True", "DFIntLuaChatFloodCheckMessages": 7, "DFIntLuaChatFloodCheckInterval": 15, "FFlagLuaChatFiltering": "True", "FFlagMobileToggleChatVisibleIcon": "True", "FFlagLinkedScriptsBasicUIEnabled": "False", "FFlagGlowEnabled": "True", "FFlagStudioDE9132FixEnabled": "True", "DFFlagHttpCurlHandle301": "True", "FFlagSearchToolboxByDataModelSearchString": "True", "FFlagClientABTestingEnabled": "False", "FFlagStudioSmoothTerrainForNewPlaces": "True", "FFlagUsePGSSolver": "True", "FFlagSimplifyKeyboardInputPath": "False", "FFlagNewInGameDevConsole": "True" }
\ No newline at end of file
diff --git a/Setting/QuietGet/ClientSharedSettings/index.html b/Setting/QuietGet/ClientSharedSettings/index.html
new file mode 100644
index 0000000..9e26dfe
--- /dev/null
+++ b/Setting/QuietGet/ClientSharedSettings/index.html
@@ -0,0 +1 @@
+{}
\ No newline at end of file
diff --git a/asset/1 b/asset/1
new file mode 100644
index 0000000..c835472
--- /dev/null
+++ b/asset/1
@@ -0,0 +1,94 @@
+--rbxassetid%1%
+-- Creates all neccessary scripts for the gui on initial load, everything except build tools
+-- Created by Ben T. 10/29/10
+-- Please note that these are loaded in a specific order to diminish errors/perceived load time by user
+
+local scriptContext = game:GetService("ScriptContext")
+local touchEnabled = false
+pcall(function() touchEnabled = game:GetService("UserInputService").TouchEnabled end)
+
+-- library registration
+scriptContext:AddCoreScript(2, scriptContext,"/Libraries/LibraryRegistration/LibraryRegistration")
+
+local function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+local function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+
+-- Responsible for tracking logging items
+local scriptContext = game:GetService("ScriptContext")
+scriptContext:AddCoreScript(3, scriptContext, "CoreScripts/Sections")
+
+waitForChild(game:GetService("CoreGui"),"RobloxGui")
+local screenGui = game:GetService("CoreGui"):FindFirstChild("RobloxGui")
+
+-- SettingsScript
+scriptContext:AddCoreScript(4,screenGui,"CoreScripts/Settings")
+
+if not touchEnabled then
+ -- ToolTipper (creates tool tips for gui)
+ scriptContext:AddCoreScript(5,screenGui,"CoreScripts/ToolTip")
+else
+ -- no
+end
+
+-- MainBotChatScript
+scriptContext:AddCoreScript(7,screenGui,"CoreScripts/MainBotChatScript")
+
+-- Developer Console Script
+scriptContext:AddCoreScript(8,screenGui,"CoreScripts/DeveloperConsole")
+
+-- Popup Script
+scriptContext:AddCoreScript(9,screenGui,"CoreScripts/PopupScript")
+-- Friend Notification Script (probably can use this script to expand out to other notifications)
+scriptContext:AddCoreScript(10,screenGui,"CoreScripts/NotificationScript")
+-- Chat script
+scriptContext:AddCoreScript(11, screenGui, "CoreScripts/ChatScript2")
+-- Purchase Prompt Script
+scriptContext:AddCoreScript(12, screenGui, "CoreScripts/PurchasePromptScript")
+-- Health Script
+scriptContext:AddCoreScript(13, screenGui, "CoreScripts/HealthScript")
+
+if not touchEnabled then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+elseif screenGui.AbsoluteSize.Y >= 500 then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+else
+ delay(5, function()
+ if screenGui.AbsoluteSize.Y >= 500 then
+ -- New Player List
+ scriptContext:AddCoreScript(14,screenGui,"CoreScripts/PlayerListScript")
+ end
+ end)
+end
+
+if game.CoreGui.Version >= 3 then
+ -- Backpack Builder, creates most of the backpack gui
+ scriptContext:AddCoreScript(15,screenGui,"CoreScripts/BackpackScripts/BackpackBuilder")
+
+ waitForChild(screenGui,"CurrentLoadout")
+ waitForChild(screenGui,"Backpack")
+ local Backpack = screenGui.Backpack
+
+ -- Manager handles all big backpack state changes, other scripts subscribe to this and do things accordingly
+ if game.CoreGui.Version >= 7 then
+ scriptContext:AddCoreScript(16,Backpack,"CoreScripts/BackpackScripts/BackpackManager")
+ end
+
+ -- Backpack Gear (handles all backpack gear tab stuff)
+ game:GetService("ScriptContext"):AddCoreScript(17,Backpack,"CoreScripts/BackpackScripts/BackpackGear")
+ -- Loadout Script, used for gear hotkeys
+ scriptContext:AddCoreScript(18,screenGui.CurrentLoadout,"CoreScripts/BackpackScripts/LoadoutScript")
+ if game.CoreGui.Version >= 8 then
+ -- Wardrobe script handles all character dressing operations
+ scriptContext:AddCoreScript(-1,Backpack,"CoreScripts/BackpackScripts/BackpackWardrobe")
+ end
+end
\ No newline at end of file
diff --git a/asset/10 b/asset/10
new file mode 100644
index 0000000..4eb2ef3
--- /dev/null
+++ b/asset/10
@@ -0,0 +1,329 @@
+--rbxassetid%10%
+function waitForProperty(instance, property)
+ while not instance[property] do
+ instance.Changed:wait()
+ end
+end
+function waitForChild(instance, name)
+ while not instance:FindFirstChild(name) do
+ instance.ChildAdded:wait()
+ end
+end
+
+waitForProperty(game.Players,"LocalPlayer")
+waitForChild(script.Parent,"Popup")
+waitForChild(script.Parent.Popup,"AcceptButton")
+script.Parent.Popup.AcceptButton.Modal = true
+
+local localPlayer = game.Players.LocalPlayer
+local teleportUI = nil
+
+local acceptedTeleport = Instance.new("IntValue")
+
+local friendRequestBlacklist = {}
+
+local teleportEnabled = true
+
+local makePopupInvisible = function()
+ if script.Parent.Popup then script.Parent.Popup.Visible = false end
+end
+
+function makeFriend(fromPlayer,toPlayer)
+
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup == nil then return end -- there is no popup!
+ if popup.Visible then return end -- currently popping something, abort!
+ if friendRequestBlacklist[fromPlayer] then return end -- previously cancelled friend request, we don't want it!
+
+ popup.PopupText.Text = "Accept Friend Request from " .. tostring(fromPlayer.Name) .. "?"
+ popup.PopupImage.Image = "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=352&y=352"
+
+ showTwoButtons()
+ popup.Visible = true
+ popup.AcceptButton.Text = "Accept"
+ popup.DeclineButton.Text = "Decline"
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+
+ local yesCon, noCon
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ popup.Visible = false
+ toPlayer:RequestFriendship(fromPlayer)
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ popup.Visible = false
+ toPlayer:RevokeFriendship(fromPlayer)
+ friendRequestBlacklist[fromPlayer] = true
+
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+end
+
+
+game.Players.FriendRequestEvent:connect(function(fromPlayer,toPlayer,event)
+
+ -- if this doesn't involve me, then do nothing
+ if fromPlayer ~= localPlayer and toPlayer ~= localPlayer then return end
+
+ if fromPlayer == localPlayer then
+ if event == Enum.FriendRequestEvent.Accept then
+ game:GetService("GuiService"):SendNotification("You are Friends",
+ "With " .. toPlayer.Name .. "!",
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(toPlayer.userId).."&x=48&y=48",
+ 5,
+ function()
+
+ end)
+ end
+ elseif toPlayer == localPlayer then
+ if event == Enum.FriendRequestEvent.Issue then
+ if friendRequestBlacklist[fromPlayer] then return end -- previously cancelled friend request, we don't want it!
+ game:GetService("GuiService"):SendNotification("Friend Request",
+ "From " .. fromPlayer.Name,
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=48&y=48",
+ 8,
+ function()
+ makeFriend(fromPlayer,toPlayer)
+ end)
+ elseif event == Enum.FriendRequestEvent.Accept then
+ game:GetService("GuiService"):SendNotification("You are Friends",
+ "With " .. fromPlayer.Name .. "!",
+ "http://www.roblox.com/thumbs/avatar.ashx?userId="..tostring(fromPlayer.userId).."&x=48&y=48",
+ 5,
+ function()
+
+ end)
+ end
+ end
+end)
+
+function showOneButton()
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup then
+ popup.OKButton.Visible = true
+ popup.DeclineButton.Visible = false
+ popup.AcceptButton.Visible = false
+ end
+end
+
+function showTwoButtons()
+ local popup = script.Parent:FindFirstChild("Popup")
+ if popup then
+ popup.OKButton.Visible = false
+ popup.DeclineButton.Visible = true
+ popup.AcceptButton.Visible = true
+ end
+end
+
+function onTeleport(teleportState, placeId, spawnName)
+ if game:GetService("TeleportService").CustomizedTeleportUI == false then
+ if teleportState == Enum.TeleportState.Started then
+ showTeleportUI("Teleport started...", 0)
+ elseif teleportState == Enum.TeleportState.WaitingForServer then
+ showTeleportUI("Requesting server...", 0)
+ elseif teleportState == Enum.TeleportState.InProgress then
+ showTeleportUI("Teleporting...", 0)
+ elseif teleportState == Enum.TeleportState.Failed then
+ showTeleportUI("Teleport failed. Insufficient privileges or target place does not exist.", 3)
+ end
+ end
+end
+
+function showTeleportUI(message, timer)
+ if teleportUI ~= nil then
+ teleportUI:Remove()
+ end
+ waitForChild(localPlayer, "PlayerGui")
+ teleportUI = Instance.new("Message", localPlayer.PlayerGui)
+ teleportUI.Text = message
+ if timer > 0 then
+ wait(timer)
+ teleportUI:Remove()
+ end
+end
+
+if teleportEnabled then
+
+ localPlayer.OnTeleport:connect(onTeleport)
+
+ game:GetService("TeleportService").ErrorCallback = function(message)
+ local popup = script.Parent:FindFirstChild("Popup")
+ showOneButton()
+ popup.PopupText.Text = message
+ local clickCon
+ clickCon = popup.OKButton.MouseButton1Click:connect(function()
+ game:GetService("TeleportService"):TeleportCancel()
+ if clickCon then clickCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showOneButton()
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+
+ end
+ game:GetService("TeleportService").ConfirmationCallback = function(message, placeId, spawnName)
+ local popup = script.Parent:FindFirstChild("Popup")
+ popup.PopupText.Text = message
+ popup.PopupImage.Image = ""
+
+ local yesCon, noCon
+
+ local function killCons()
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ killCons()
+ local success, err = pcall(function() game:GetService("TeleportService"):TeleportImpl(placeId,spawnName) end)
+ if not success then
+ showOneButton()
+ popup.PopupText.Text = err
+ local clickCon
+ clickCon = popup.OKButton.MouseButton1Click:connect(function()
+ if clickCon then clickCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showOneButton()
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ killCons()
+ local success = pcall(function() game:GetService("TeleportService"):TeleportCancel() end)
+ end)
+
+ local centerDialogSuccess = pcall(function() game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ --ShowFunction
+ function()
+ showTwoButtons()
+ popup.AcceptButton.Text = "Leave"
+ popup.DeclineButton.Text = "Stay"
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ --HideFunction
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end)
+
+ if centerDialogSuccess == false then
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup.AcceptButton.Text = "Leave"
+ popup.DeclineButton.Text = "Stay"
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end
+ return true
+
+ end
+end
+
+game:GetService("MarketplaceService").ClientLuaDialogRequested:connect(function(message, accept, decline)
+ local popup = script.Parent:FindFirstChild("Popup")
+ popup.PopupText.Text = message
+ popup.PopupImage.Image = ""
+
+ local yesCon, noCon
+
+ local function killCons()
+ if yesCon then yesCon:disconnect() end
+ if noCon then noCon:disconnect() end
+ game.GuiService:RemoveCenterDialog(script.Parent:FindFirstChild("Popup"))
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end
+
+ yesCon = popup.AcceptButton.MouseButton1Click:connect(function()
+ killCons()
+ game:GetService("MarketplaceService"):SignalServerLuaDialogClosed(true);
+ end)
+
+ noCon = popup.DeclineButton.MouseButton1Click:connect(function()
+ killCons()
+ game:GetService("MarketplaceService"):SignalServerLuaDialogClosed(false);
+ end)
+
+ local centerDialogSuccess = pcall(function() game.GuiService:AddCenterDialog(script.Parent:FindFirstChild("Popup"), Enum.CenterDialogType.QuitDialog,
+ function()
+ showTwoButtons()
+ popup.AcceptButton.Text = accept
+ popup.DeclineButton.Text = decline
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end,
+ function()
+ popup:TweenSize(UDim2.new(0,0,0,0),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true,makePopupInvisible())
+ end)
+ end)
+
+ if centerDialogSuccess == false then
+ script.Parent:FindFirstChild("Popup").Visible = true
+ popup.AcceptButton.Text = accept
+ popup.DeclineButton.Text = decline
+ popup:TweenSize(UDim2.new(0,330,0,350),Enum.EasingDirection.Out,Enum.EasingStyle.Quart,1,true)
+ end
+
+ return true
+
+end)
+
+local noOptFunc = function ()
+ -- do nothing
+end
+
+Game:GetService("PointsService").PointsAwarded:connect( function(userId, pointsAwarded, userBalanceInGame, userTotalBalance)
+ if userId == Game.Players.LocalPlayer.userId then
+ if pointsAwarded > 0 then
+ game:GetService("GuiService"):SendNotification("Points Awarded!",
+ "You received " ..tostring(pointsAwarded) .. " points!",
+ "http://www.roblox.com/asset?id=155363793",
+ 5,
+ noOptFunc)
+ elseif pointsAwarded < 0 then
+ game:GetService("GuiService"):SendNotification("Points Lost!",
+ "You lost " ..tostring(-pointsAwarded) .. " points!",
+ "http://www.roblox.com/asset?id=155363793",
+ 5,
+ noOptFunc)
+ end
+ end
+end)
+
+-- Since we can't get the image right, let's just use a nice notification icon
+Game:GetService("BadgeService").BadgeAwarded:connect( function(message, userId, badgeId)
+ if userId == Game.Players.LocalPlayer.userId then
+ game:GetService("GuiService"):SendNotification("Badge Awarded!",
+ message,
+ "http://www.roblox.com/asset?id=177200377",
+ 5,
+ noOptFunc)
+ end
+end)
diff --git a/asset/11 b/asset/11
new file mode 100644
index 0000000..4fa79fb
--- /dev/null
+++ b/asset/11
@@ -0,0 +1,1756 @@
+--rbxassetid%11%
+--[[
+ // FileName: ChatScript.lua
+ // Written by: SolarCrane
+ // Description: Code for lua side chat on ROBLOX.
+]]
+
+--[[ CONSTANTS ]]
+local FORCE_CHAT_GUI = false
+local USE_PLAYER_GUI_TESTING = false
+
+local ADMIN_LIST = {
+ ['68465808'] = true, -- IMightBeLying
+ ['32345429'] = true, -- Rbadam
+ ['48453004'] = true, -- Adamintygum
+ ['57705391'] = true, -- androidtest
+ ['58491921'] = true, -- RobloxFrenchie
+ ['29341155'] = true, -- JacksSmirkingRevenge
+ ['60629145'] = true, -- Mandaari
+ ['6729993'] = true, -- vaiobot
+ ['9804369'] = true, -- Goddessnoob
+ ['67906358'] = true, -- Thr33pakShak3r
+ ['41101356'] = true, -- effward
+ ['29667843'] = true, -- Blockhaak
+ ['26076267'] = true, -- Drewbda
+ ['65171466'] = true, -- triptych999
+ ['264635'] = true, -- Tone
+ ['59257875'] = true, -- fasterbuilder19
+ ['30068452'] = true, -- Zeuxcg
+ ['53627251'] = true, -- concol2
+ ['56449'] = true, -- ReeseMcBlox
+ ['7210880'] = true, -- Jeditkacheff
+ ['35187797'] = true, -- ChiefJustus
+ ['21964644'] = true, -- Ellissar
+ ['63971416'] = true, -- geekndestroy
+ ['111627'] = true, -- Noob007
+ ['482238'] = true, -- Limon
+ ['39861325'] = true, -- hawkington
+ ['32580099'] = true, -- Tabemono
+ ['504316'] = true, -- BrightEyes
+ ['35825637'] = true, -- Monsterinc3D
+ ['55311255'] = true, -- IsolatedEvent
+ ['48988254'] = true, -- CountOnConnor
+ ['357346'] = true, -- Scubasomething
+ ['28969907'] = true, -- OnlyTwentyCharacters
+ ['17707636'] = true, -- LordRugdumph
+ ['26714811'] = true, -- bellavour
+ ['24941'] = true, -- david.baszucki
+ ['13057592'] = true, -- ibanez2189
+ ['66766775'] = true, -- ConvexHero
+ ['13268404'] = true, -- Sorcus
+ ['26065068'] = true, -- DeeAna00
+ ['4108667'] = true, -- TheLorekt
+ ['605367'] = true, -- MSE6
+ ['28350010'] = true, -- CorgiParade
+ ['1636196'] = true, -- Varia
+ ['27861308'] = true, -- 4runningwolves
+ ['26699190'] = true, -- pulmoesflor
+ ['9733258'] = true, -- Olive71
+ ['2284059'] = true, -- groundcontroll2
+ ['28080592'] = true, -- GuruKrish
+ ['28137935'] = true, -- Countvelcro
+ ['25964666'] = true, -- IltaLumi
+ ['31221099'] = true, -- juanjuan23
+ ['13965343'] = true, -- OstrichSized
+ ['541489'] = true, -- jackintheblox
+ ['38324232'] = true, -- SlingshotJunkie
+ ['146569'] = true, -- gordonrox24
+ ['61666252'] = true, -- sharpnine
+ ['25540124'] = true, -- Motornerve
+ ['29044576'] = true, -- watchmedogood
+ ['49626068'] = true, -- jmargh
+ ['57352126'] = true, -- JayKorean
+ ['25682044'] = true, -- Foyle
+ ['1113299'] = true, -- MajorTom4321
+ ['30598693'] = true, -- supernovacaine
+ ['1311'] = true, -- FFJosh
+ ['23603273'] = true, -- Sickenedmonkey
+ ['28568151'] = true, -- Doughtless
+ ['8298697'] = true, -- KBUX
+ ['39871898'] = true, -- totallynothere
+ ['57708043'] = true, -- ErzaStar
+ ['22'] = true, -- Keith
+ ['2430782'] = true, -- Chro
+ ['29373363'] = true, -- SolarCrane
+ ['29116915'] = true, -- GloriousSalt
+ ['6783205'] = true, -- UristMcSparks
+ ['62155769'] = true, -- ITOlaurEN
+ ['24162607'] = true, -- Malcomso
+ ['66692187'] = true, -- HeySeptember
+ ['80254'] = true, -- Stickmasterluke
+ ['66093461'] = true, -- chefdeletat
+ ['62968051'] = true, -- windlight13
+ ['80119'] = true, -- Stravant
+ ['61890000'] = true, -- imaginationsensation
+ ['916'] = true, -- Matt Dusek
+ ['4550725'] = true, -- CrimmsonGhost
+ ['59737068'] = true, -- Mcrtest
+ ['5600283'] = true, -- Seranok
+ ['48656806'] = true, -- maxvee
+ ['48656806'] = true, -- Coatp0cketninja
+ ['35231885'] = true, -- Screenme
+ ['55958416'] = true, -- b1tsh1ft
+ ['51763936'] = true, -- ConvexRumbler
+ ['59638684'] = true, -- mpliner476
+ ['44231609'] = true, -- Totbl
+ ['16906083'] = true, -- Aquabot8
+ ['23984372'] = true, -- grossinger
+ ['13416513'] = true, -- Merely
+ ['27416429'] = true, -- CDakkar
+ ['46526337'] = true, -- logitek00
+ ['21969613'] = true, -- Siekiera
+ ['39488230'] = true, -- Robloxkidsaccount
+ ['60425210'] = true, -- flotsamthespork
+ ['16732061'] = true, -- Soggoth
+ ['33904052'] = true, -- Phil
+ ['39882028'] = true, -- OrcaSparkles
+ ['62060462'] = true, -- skullgoblin
+ ['29044708'] = true, -- RickROSStheB0SS
+ ['15782010'] = true, -- ArgonPirate
+ ['6949935'] = true, -- NobleDragon
+ ['41256555'] = true, -- Squidcod
+ ['16150324'] = true, -- Raeglyn
+ ['24419770'] = true, -- Xerolayne
+ ['20396599'] = true, -- Robloxsai
+ ['55579189'] = true, -- Briarroze
+ ['21641566'] = true, -- hawkeyebandit
+ ['39871292'] = true, -- DapperBuffalo
+ ['48725400'] = true, -- Vukota
+ ['60880618'] = true, -- swiftstone
+ ['8736269'] = true, -- Gemlocker
+ ['17199995'] = true, -- Tarabyte
+ ['6983145'] = true, -- Timobius
+ ['20048521'] = true, -- Tobotrobot
+ ['1644345'] = true, -- Foster008
+ ['33067469'] = true, -- Twberg
+ ['57741156'] = true, -- DarthVaden
+ ['51164101'] = true, -- Khanovich
+ ['61380399'] = true, -- oLEFTo
+ ['39876101'] = true, -- CodeWriter
+ ['23598967'] = true, -- VladTheFirst
+ ['39299049'] = true, -- Phaedre
+ ['39855185'] = true, -- gorroth
+ ['61004766'] = true, -- jynj1984
+ ['10261020'] = true, -- RoboYZ
+ ['44564747'] = true, -- ZodiacZak
+}
+
+local CHAT_COLORS =
+{
+ BrickColor.new("Bright red"),
+ BrickColor.new("Bright blue"),
+ BrickColor.new("Earth green"),
+ BrickColor.new("Bright violet"),
+ BrickColor.new("Bright orange"),
+ BrickColor.new("Bright yellow"),
+ BrickColor.new("Light reddish violet"),
+ BrickColor.new("Brick yellow"),
+}
+-- These emotes are copy-pastad from the humanoidLocalAnimateKeyframe script
+local EMOTE_NAMES = {wave = true, point = true, dance = true, dance2 = true, dance3 = true, laugh = true, cheer = true}
+local MESSAGES_FADE_OUT_TIME = 30
+--[[ END OF CONSTANTS ]]
+
+--[[ SERVICES ]]
+local RunService = game:GetService('RunService')
+local CoreGuiService = game:GetService('CoreGui')
+local PlayersService = game:GetService('Players')
+local DebrisService = game:GetService('Debris')
+local GuiService = game:GetService('GuiService')
+local InputService = game:GetService('UserInputService')
+local StarterGui = game:GetService('StarterGui')
+--[[ END OF SERVICES ]]
+
+--[[ SCRIPT VARIABLES ]]
+
+-- I am not fond of waiting at the top of the script here...
+while PlayersService.LocalPlayer == nil do PlayersService.ChildAdded:wait() end
+local Player = PlayersService.LocalPlayer
+-- GuiRoot will act as the top-node for parenting GUIs
+local GuiRoot = nil
+if USE_PLAYER_GUI_TESTING then
+ GuiRoot = Instance.new("ScreenGui")
+ GuiRoot.Name = "RobloxGui"
+ GuiRoot.Parent = Player:WaitForChild('PlayerGui')
+else
+ GuiRoot = CoreGuiService:WaitForChild('RobloxGui')
+end
+--[[ END OF SCRIPT VARIABLES ]]
+
+local Util = {}
+do
+ -- Check if we are running on a touch device
+ function Util.IsTouchDevice()
+ local touchEnabled = false
+ pcall(function() touchEnabled = InputService.TouchEnabled end)
+ return touchEnabled
+ end
+
+ function Util.Create(instanceType)
+ return function(data)
+ local obj = Instance.new(instanceType)
+ for k, v in pairs(data) do
+ if type(k) == 'number' then
+ v.Parent = obj
+ else
+ obj[k] = v
+ end
+ end
+ return obj
+ end
+ end
+
+ function Util.Clamp(low, high, input)
+ return math.max(low, math.min(high, input))
+ end
+
+ function Util.Linear(t, b, c, d)
+ if t >= d then return b + c end
+
+ return c*t/d + b
+ end
+
+ function Util.EaseOutQuad(t, b, c, d)
+ if t >= d then return b + c end
+
+ t = t/d;
+ return -c * t*(t-2) + b
+ end
+
+ function Util.EaseInOutQuad(t, b, c, d)
+ if t >= d then return b + c end
+
+ t = t / (d/2);
+ if (t < 1) then return c/2*t*t + b end;
+ t = t - 1;
+ return -c/2 * (t*(t-2) - 1) + b;
+ end
+
+ function Util.PropertyTweener(instance, prop, start, final, duration, easingFunc, cbFunc)
+ local this = {}
+ this.StartTime = tick()
+ this.EndTime = this.StartTime + duration
+ this.Cancelled = false
+
+ local finished = false
+ local percentComplete = 0
+ spawn(function()
+ local now = tick()
+ while now < this.EndTime and instance do
+ if this.Cancelled then
+ return
+ end
+ instance[prop] = easingFunc(now - this.StartTime, start, final - start, duration)
+ percentComplete = Util.Clamp(0, 1, (now - this.StartTime) / duration)
+ RunService.RenderStepped:wait()
+ now = tick()
+ end
+ if this.Cancelled == false and instance then
+ instance[prop] = final
+ finished = true
+ percentComplete = 1
+ if cbFunc then
+ cbFunc()
+ end
+ end
+ end)
+
+ function this:GetPercentComplete()
+ return percentComplete
+ end
+
+ function this:IsFinished()
+ return finished
+ end
+
+ function this:Cancel()
+ this.Cancelled = true
+ end
+
+ return this
+ end
+
+ function Util.Signal()
+ local sig = {}
+
+ local mSignaler = Instance.new('BindableEvent')
+
+ local mArgData = nil
+ local mArgDataCount = nil
+
+ function sig:fire(...)
+ mArgData = {...}
+ mArgDataCount = select('#', ...)
+ mSignaler:Fire()
+ end
+
+ function sig:connect(f)
+ if not f then error("connect(nil)", 2) end
+ return mSignaler.Event:connect(function()
+ f(unpack(mArgData, 1, mArgDataCount))
+ end)
+ end
+
+ function sig:wait()
+ mSignaler.Event:wait()
+ assert(mArgData, "Missing arg data, likely due to :TweenSize/Position corrupting threadrefs.")
+ return unpack(mArgData, 1, mArgDataCount)
+ end
+
+ return sig
+ end
+
+ function Util.DisconnectEvent(conn)
+ if conn then
+ conn:disconnect()
+ end
+ return nil
+ end
+
+ function Util.SetGUIInsetBounds(x, y)
+ local success, _ = pcall(function() GuiService:SetGlobalGuiInset(0, x, 0, y) end)
+ if not success then
+ pcall(function() GuiService:SetGlobalSizeOffsetPixel(-x, -y) end) -- Legacy GUI-offset function
+ end
+ end
+
+ local baseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+ baseUrl = string.gsub(baseUrl,"/m.","/www.") --mobile site does not work for this stuff!
+ function Util.GetSecureApiBaseUrl()
+ local secureApiUrl = baseUrl
+ secureApiUrl = string.gsub(secureApiUrl,"http","https")
+ secureApiUrl = string.gsub(secureApiUrl,"www","api")
+ return secureApiUrl
+ end
+
+ function Util.GetPlayerByName(playerName)
+ -- O(n), may be faster if I store a reverse hash from the players list; can't trust FindFirstChild in PlayersService because anything can be parented to there.
+ local lowerName = string.lower(playerName)
+ for _, player in pairs(PlayersService:GetPlayers()) do
+ if string.lower(player.Name) == lowerName then
+ return player
+ end
+ end
+ return nil -- Found no player
+ end
+
+ local function GetNameValue(pName)
+ local value = 0
+ for index = 1, #pName do
+ local cValue = string.byte(string.sub(pName, index, index))
+ local reverseIndex = #pName - index + 1
+ if #pName%2 == 1 then
+ reverseIndex = reverseIndex - 1
+ end
+ if reverseIndex%4 >= 2 then
+ cValue = -cValue
+ end
+ value = value + cValue
+ end
+ return value%8
+ end
+
+ function Util.ComputeChatColor(pName)
+ return CHAT_COLORS[GetNameValue(pName) + 1].Color
+ end
+
+ -- This is a memo-izing function
+ local testLabel = Instance.new('TextLabel')
+ testLabel.TextWrapped = true;
+ testLabel.Position = UDim2.new(1,0,1,0)
+ testLabel.Parent = GuiRoot -- Note: We have to parent it to check TextBounds
+ -- The TextSizeCache table looks like this Text->Font->sizeBounds->FontSize
+ local TextSizeCache = {}
+ function Util.GetStringTextBounds(text, font, fontSize, sizeBounds)
+ -- If no sizeBounds are specified use some huge number
+ sizeBounds = sizeBounds or false
+ if not TextSizeCache[text] then
+ TextSizeCache[text] = {}
+ end
+ if not TextSizeCache[text][font] then
+ TextSizeCache[text][font] = {}
+ end
+ if not TextSizeCache[text][font][sizeBounds] then
+ TextSizeCache[text][font][sizeBounds] = {}
+ end
+ if not TextSizeCache[text][font][sizeBounds][fontSize] then
+ testLabel.Text = text
+ testLabel.Font = font
+ testLabel.FontSize = fontSize
+ if sizeBounds then
+ testLabel.TextWrapped = true;
+ testLabel.Size = sizeBounds
+ else
+ testLabel.TextWrapped = false;
+ end
+ TextSizeCache[text][font][sizeBounds][fontSize] = testLabel.TextBounds
+ end
+ return TextSizeCache[text][font][sizeBounds][fontSize]
+ end
+end
+
+local SelectChatModeEvent = Util.Signal()
+local SelectPlayerEvent = Util.Signal()
+
+local function CreateChatMessage()
+ local this = {}
+
+ this.Settings =
+ {
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size14;
+ }
+
+ function this:OnResize()
+ -- Nothing!
+ end
+
+ function this:FadeIn()
+ local gui = this:GetGui()
+ if gui then
+ --Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ gui.Visible = true
+ end
+ end
+
+ function this:FadeOut()
+ local gui = this:GetGui()
+ if gui then
+ --Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ gui.Visible = false
+ end
+ end
+
+ function this:GetGui()
+ return this.Container
+ end
+
+ function this:Destroy()
+ if this.Container ~= nil then
+ this.Container:Destroy()
+ this.Container = nil
+ end
+ end
+
+ return this
+end
+
+local function CreateSystemChatMessage(chattedMessage)
+ local this = CreateChatMessage()
+
+ this.chatMessage = chattedMessage
+
+ function this:OnResize(containerSize)
+ if this.Container and this.ChatMessage then
+ this.Container.Size = UDim2.new(1,0,0,1000)
+ local textHeight = this.ChatMessage.TextBounds.Y
+ this.Container.Size = UDim2.new(1,0,0,textHeight)
+ return textHeight
+ end
+ end
+
+ local function CreateMessageGuiElement()
+ local systemMesasgeDisplayText = this.chatMessage or ""
+ local systemMessageSize = Util.GetStringTextBounds(systemMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize, UDim2.new(0, 400, 0, 1000))
+
+ local container = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Position = UDim2.new(0, 0, 0, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+
+ local chatMessage = Util.Create'TextLabel'
+ {
+ Name = 'SystemChatMessage';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(1, 0, 1, 0);
+ Text = systemMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+
+ container.Size = UDim2.new(1, 0, 0, systemMessageSize.Y);
+ this.Container = container
+ this.ChatMessage = chatMessage
+ end
+
+ CreateMessageGuiElement()
+
+ return this
+end
+
+local function CreatePlayerChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ local this = CreateChatMessage()
+
+ this.PlayerChatType = playerChatType
+ this.SendingPlayer = sendingPlayer
+ this.RawMessageContent = chattedMessage
+ this.ReceivingPlayer = receivingPlayer
+ this.ReceivedTime = tick()
+
+ this.Neutral = this.SendingPlayer and this.SendingPlayer.Neutral or true
+ this.TeamColor = this.SendingPlayer and this.SendingPlayer.TeamColor or BrickColor.new("White")
+
+ function this:OnResize(containerSize)
+ if this.Container and this.ChatMessage then
+ this.Container.Size = UDim2.new(1,0,0,1000)
+ local textHeight = this.ChatMessage.TextBounds.Y
+ this.Container.Size = UDim2.new(1,0,0,textHeight)
+ return textHeight
+ end
+ end
+
+ function this:FormatMessage()
+ local result = ""
+ if this.RawMessageContent then
+ local message = this.RawMessageContent
+
+ if string.sub(message, 1, 3) == '/e ' or string.sub(message, 1, 7) == '/emote ' then
+ if this.SendingPlayer then
+ result = this.SendingPlayer.Name .. " emotes."
+ end
+ else
+ result = message
+ end
+ end
+ return result
+ end
+
+ function this:FormatChatType()
+ if this.PlayerChatType then
+ if this.PlayerChatType == Enum.PlayerChatType.All then
+ --return "[All]"
+ elseif this.PlayerChatType == Enum.PlayerChatType.Team then
+ return "[Team]"
+ elseif this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ -- nothing!
+ end
+ end
+ end
+
+ function this:FormatPlayerNameText()
+ local playerName = ""
+ -- If we are sending a whisper to someone, then we should show their name
+ if this.PlayerChatType == Enum.PlayerChatType.Whisper and this.SendingPlayer and this.SendingPlayer == Player then
+ playerName = (this.ReceivingPlayer and this.ReceivingPlayer.Name or "")
+ else
+ playerName = (this.SendingPlayer and this.SendingPlayer.Name or "")
+ end
+ return "[" .. playerName .. "]"
+ end
+
+ function this:Destroy()
+ if this.Container ~= nil then
+ this.Container:Destroy()
+ this.Container = nil
+ end
+ this.ClickedOnModeConn = Util.DisconnectEvent(this.ClickedOnModeConn)
+ this.ClickedOnPlayerConn = Util.DisconnectEvent(this.ClickedOnPlayerConn)
+ end
+
+ local function CreateMessageGuiElement()
+ local toMesasgeDisplayText = "To: "
+ local toMessageSize = Util.GetStringTextBounds(toMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize)
+ local fromMesasgeDisplayText = "From: "
+ local fromMessageSize = Util.GetStringTextBounds(fromMesasgeDisplayText, this.Settings.Font, this.Settings.FontSize)
+ local chatTypeDisplayText = this:FormatChatType()
+ local chatTypeSize = chatTypeDisplayText and Util.GetStringTextBounds(chatTypeDisplayText, this.Settings.Font, this.Settings.FontSize) or Vector2.new(0,0)
+ local playerNameDisplayText = this:FormatPlayerNameText()
+ local playerNameSize = Util.GetStringTextBounds(playerNameDisplayText, this.Settings.Font, this.Settings.FontSize)
+
+ local singleSpaceSize = Util.GetStringTextBounds(" ", this.Settings.Font, this.Settings.FontSize)
+ local numNeededSpaces = math.ceil(playerNameSize.X / singleSpaceSize.X) + 1
+ local chatMessageDisplayText = string.rep(" ", numNeededSpaces) .. this:FormatMessage()
+ local chatMessageSize = Util.GetStringTextBounds(chatMessageDisplayText, this.Settings.Font, this.Settings.FontSize, UDim2.new(0, 400 - 5 - playerNameSize.X, 0, 1000))
+
+
+ local playerColor = Color3.new(1,1,1)
+ if this.SendingPlayer then
+ if this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ if this.SendingPlayer == Player and this.ReceivingPlayer then
+ playerColor = Util.ComputeChatColor(this.ReceivingPlayer.Name)
+ else
+ playerColor = Util.ComputeChatColor(this.SendingPlayer.Name)
+ end
+ else
+ if this.SendingPlayer.Neutral then
+ playerColor = Util.ComputeChatColor(this.SendingPlayer.Name)
+ else
+ playerColor = this.SendingPlayer.TeamColor.Color
+ end
+ end
+ end
+
+ local container = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Position = UDim2.new(0, 0, 0, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+ local xOffset = 0
+
+ if this.SendingPlayer and this.SendingPlayer == Player and this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ local whisperToText = Util.Create'TextLabel'
+ {
+ Name = 'WhisperTo';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, toMessageSize.X, 0, toMessageSize.Y);
+ Text = toMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ xOffset = xOffset + toMessageSize.X
+ elseif this.SendingPlayer and this.SendingPlayer ~= Player and this.PlayerChatType == Enum.PlayerChatType.Whisper then
+ local whisperFromText = Util.Create'TextLabel'
+ {
+ Name = 'whisperFromText';
+ Position = UDim2.new(0, 0, 0, 0);
+ Size = UDim2.new(0, fromMessageSize.X, 0, fromMessageSize.Y);
+ Text = fromMesasgeDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(1, 1, 1);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ xOffset = xOffset + fromMessageSize.X
+ else
+ local userNameDot = Util.Create'ImageLabel'
+ {
+ Name = "UserNameDot";
+ Size = UDim2.new(0, 14, 0, 14);
+ BackgroundTransparency = 1;
+ Position = UDim2.new(0, 0, 0, 2);
+ BorderSizePixel = 0;
+ Image = "rbxasset://textures/ui/chat_teamButton.png";
+ ImageColor3 = playerColor;
+ Parent = container;
+ }
+ xOffset = xOffset + 14 + 3
+ end
+ if chatTypeDisplayText then
+ local chatModeButton = Util.Create(Util.IsTouchDevice() and 'TextLabel' or 'TextButton')
+ {
+ Name = 'ChatMode';
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = chatTypeDisplayText;
+ TextColor3 = Color3.new(255/255, 255/255, 243/255);
+ Position = UDim2.new(0, xOffset, 0, 0);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ Size = UDim2.new(0, chatTypeSize.X, 0, chatTypeSize.Y);
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container
+ }
+ if chatModeButton:IsA('TextButton') then
+ this.ClickedOnModeConn = chatModeButton.MouseButton1Click:connect(function()
+ SelectChatModeEvent:fire(this.PlayerChatType)
+ end)
+ end
+ if this.PlayerChatType == Enum.PlayerChatType.Team then
+ chatModeButton.TextColor3 = playerColor
+ end
+ xOffset = xOffset + chatTypeSize.X + 1
+ end
+ local userNameButton = Util.Create(Util.IsTouchDevice() and 'TextLabel' or 'TextButton')
+ {
+ Name = 'PlayerName';
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = playerNameDisplayText;
+ TextColor3 = playerColor;
+ Position = UDim2.new(0, xOffset, 0, 0);
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ Size = UDim2.new(0, playerNameSize.X, 0, playerNameSize.Y);
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container
+ }
+ if userNameButton:IsA('TextButton') then
+ this.ClickedOnPlayerConn = userNameButton.MouseButton1Click:connect(function()
+ SelectPlayerEvent:fire(this.SendingPlayer)
+ end)
+ end
+
+ local chatMessage = Util.Create'TextLabel'
+ {
+ Name = 'ChatMessage';
+ Position = UDim2.new(0, xOffset, 0, 0);
+ Size = UDim2.new(1, -xOffset, 1, 0);
+ Text = chatMessageDisplayText;
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextWrapped = true;
+ TextColor3 = Color3.new(255/255, 255/255, 243/255);
+ FontSize = this.Settings.FontSize;
+ Font = this.Settings.Font;
+ TextStrokeColor3 = Color3.new(34/255, 34/255, 34/255);
+ TextStrokeTransparency = 0.3;
+ Parent = container;
+ };
+ -- Check if they got moderated and put up a real message instead of Label
+ if chatMessage.Text == 'Label' and chatMessageDisplayText ~= 'Label' then
+ chatMessage.Text = string.rep(" ", numNeededSpaces) .. '[Content Deleted]'
+ end
+ if this.SendingPlayer and ADMIN_LIST[tostring(this.SendingPlayer.userId)] then
+ chatMessage.TextColor3 = Color3.new(1, 215/255, 0)
+ end
+ chatMessage.Size = chatMessage.Size + UDim2.new(0, 0, 0, chatMessage.TextBounds.Y);
+
+ container.Size = UDim2.new(1, 0, 0, math.max(chatMessageSize.Y, userNameButton.Size.Y.Offset));
+ this.Container = container
+ this.ChatMessage = chatMessage
+ end
+
+ CreateMessageGuiElement()
+
+ return this
+end
+
+local function CreateChatBarWidget(settings)
+ local this = {}
+
+ -- MessageModes: {All, Team, Whisper}
+ this.MessageMode = "All"
+ this.TargetWhisperPlayer = nil
+ this.Settings = settings
+
+ this.ChatBarGainedFocusEvent = Util.Signal()
+ this.ChatBarLostFocusEvent = Util.Signal()
+ this.ChatCommandEvent = Util.Signal() -- success, actionType, captures
+ this.ChatErrorEvent = Util.Signal() -- success, actionType, captures
+
+ this.ChatMatchingRegex =
+ {
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/w (%w+)") end] = "Whisper";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/whisper (%w+)") end] = "Whisper";
+
+ [function(chatBarText) return string.find(chatBarText, "^%%") end] = "Team";
+ [function(chatBarText) return string.find(chatBarText, "^(TEAM)") end] = "Team";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/t") end] = "Team";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/team") end] = "Team";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/a") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/all") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/s") end] = "All";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/say") end] = "All";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/e") end] = "Emote";
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/emote") end] = "Emote";
+
+ [function(chatBarText) return string.find(string.lower(chatBarText), "^/%?") end] = "Help";
+ }
+
+ local ChatModesDict =
+ {
+ ['Whisper'] = 'Whisper';
+ ['Team'] = 'Team';
+ ['All'] = 'All';
+ [Enum.PlayerChatType.Whisper] = 'Whisper';
+ [Enum.PlayerChatType.Team] = 'Team';
+ [Enum.PlayerChatType.All] = 'All';
+ }
+
+ local function TearDownEvents()
+ -- Note: This is a new api so we need to pcall it
+ pcall(function() GuiService:RemoveSpecialKey(Enum.SpecialKey.ChatHotkey) end)
+ this.SpecialKeyPressedConn = Util.DisconnectEvent(this.SpecialKeyPressedConn)
+ this.ClickToChatButtonConn = Util.DisconnectEvent(this.ClickToChatButtonConn)
+ this.ChatBarFocusLostConn = Util.DisconnectEvent(this.ChatBarFocusLostConn)
+ this.ChatBarLostFocusConn = Util.DisconnectEvent(this.ChatBarLostFocusConn)
+ this.SelectChatModeConn = Util.DisconnectEvent(this.SelectChatModeConn)
+ this.SelectPlayerConn = Util.DisconnectEvent(this.SelectPlayerConn)
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ end
+
+ local function HookUpEvents()
+ TearDownEvents() -- Cleanup old events
+
+ -- ChatHotKey is '/'
+ GuiService:AddSpecialKey(Enum.SpecialKey.ChatHotkey)
+ this.SpecialKeyPressedConn = GuiService.SpecialKeyPressed:connect(function(key)
+ if key == Enum.SpecialKey.ChatHotkey then
+ this:FocusChatBar()
+ end
+ end)
+
+ if this.ClickToChatButton then this.ClickToChatButtonConn = this.ClickToChatButton.MouseButton1Click:connect(function() this:FocusChatBar() end) end
+
+ if this.ChatBar then this.ChatBarFocusLostConn = this.ChatBar.FocusLost:connect(function(...) this.ChatBarLostFocusEvent:fire(...) end) end
+
+ if this.ChatBarLostFocusEvent then this.ChatBarLostFocusConn = this.ChatBarLostFocusEvent:connect(function(...) this:OnChatBarFocusLost(...) end) end
+
+ this.SelectChatModeConn = SelectChatModeEvent:connect(function(chatType)
+ this:SetMessageMode(chatType)
+ this:FocusChatBar()
+ end)
+
+ this.SelectPlayerConn = SelectPlayerEvent:connect(function(chatPlayer)
+ this.TargetWhisperPlayer = chatPlayer
+ this:SetMessageMode("Whisper")
+ this:FocusChatBar()
+ end)
+ end
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if enabled then
+ HookUpEvents()
+ else
+ TearDownEvents()
+ end
+ if this.ChatBarContainer then
+ this.ChatBarContainer.Visible = enabled
+ end
+ end
+ end
+
+ function this:IsAChatMode(mode)
+ return ChatModesDict[mode] ~= nil
+ end
+
+ function this:IsAnEmoteMode(mode)
+ return mode == "Emote"
+ end
+
+ function this:ProcessChatBarModes(requireWhitespaceAfterChatMode)
+ local matchedAChatCommand = false
+ if this.ChatBar then
+ local chatBarText = this:SanitizeInput(this:GetChatBarText())
+ for regexFunc, actionType in pairs(this.ChatMatchingRegex) do
+ local start, finish, capture = regexFunc(chatBarText)
+ if start and finish then
+ -- The following line is for whether or not to try setting the chatmode as-you-type
+ -- versus when you press enter.
+ local whitespaceAfterSlashCommand = string.find(string.sub(chatBarText, finish+1, finish+1), "%s")
+ if (not requireWhitespaceAfterChatMode and finish == #chatBarText) or whitespaceAfterSlashCommand then
+ if this:IsAChatMode(actionType) then
+ if actionType == "Whisper" then
+ local targetPlayer = capture and Util.GetPlayerByName(capture)
+ if targetPlayer then --and targetPlayer ~= Player then
+ this.TargetWhisperPlayer = targetPlayer
+ -- start from two over to eat the space or tab character after the slash command
+ this:SetChatBarText(string.sub(chatBarText, finish + 2))
+ this:SetMessageMode(actionType)
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ else
+ this:SetChatBarText("")
+ this.ChatCommandEvent:fire(false, actionType, capture)
+ end
+ else
+ -- start from two over to eat the space or tab character after the slash command
+ this:SetChatBarText(string.sub(chatBarText, finish + 2))
+ this:SetMessageMode(actionType)
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ end
+ elseif actionType == "Emote" then
+ -- You can only emote to everyone.
+ this:SetMessageMode('All')
+ elseif not requireWhitespaceAfterChatMode then -- Some non-chat related command
+ if actionType == "Help" then
+ this:SetChatBarText("") -- Clear the chat so we don't send /? to everyone
+ end
+ this.ChatCommandEvent:fire(true, actionType, capture)
+ end
+ -- should we break here since we already matched a slash command or keep going?
+ matchedAChatCommand = true
+ end
+ end
+ end
+ end
+ return matchedAChatCommand
+ end
+
+ local previousText = ""
+ function this:OnChatBarTextChanged()
+ if not Util.IsTouchDevice() then
+ this:ProcessChatBarModes(true)
+ local newText = this:GetChatBarText()
+ if #newText > this.Settings.MaxCharactersInMessage then
+ local fixedText = ""
+ -- This is a hack to deal with the bug that holding down a key for repeated input doesn't trigger the textChanged event
+ if #newText == #previousText + 1 then
+ fixedText = string.sub(previousText, 1, this.Settings.MaxCharactersInMessage)
+ else
+ fixedText = string.sub(newText, 1, this.Settings.MaxCharactersInMessage)
+ end
+ this:SetChatBarText(fixedText)
+ previousText = fixedText
+ -- TODO: Flash Max Characters Feedback
+ else
+ previousText = newText
+ end
+ end
+ end
+
+ function this:GetChatBarText()
+ return this.ChatBar and this.ChatBar.Text or ""
+ end
+
+ function this:SetChatBarText(newText)
+ if this.ChatBar then
+ this.ChatBar.Text = newText
+ end
+ end
+
+ function this:GetMessageMode()
+ return this.MessageMode
+ end
+
+ function this:SetMessageMode(newMessageMode)
+ newMessageMode = ChatModesDict[newMessageMode]
+ if this.MessageMode ~= newMessageMode then
+ this.MessageMode = newMessageMode
+ if this.ChatModeText then
+ if newMessageMode == 'Whisper' then
+ -- TODO: also update this when they change players to whisper to
+ local chatRecipientText = "[" .. (this.TargetWhisperPlayer and this.TargetWhisperPlayer.Name or "") .. "]"
+ local chatRecipientTextBounds = Util.GetStringTextBounds(chatRecipientText, this.ChatModeText.Font, this.ChatModeText.FontSize)
+
+ this.ChatModeText.TextColor3 = this.Settings.WhisperTextColor
+ this.ChatModeText.Text = chatRecipientText
+ this.ChatModeText.Size = UDim2.new(0, chatRecipientTextBounds.X, 1, 0)
+ elseif newMessageMode == 'Team' then
+ local chatTeamText = '[Team]'
+ local chatTeamTextBounds = Util.GetStringTextBounds(chatTeamText, this.ChatModeText.Font, this.ChatModeText.FontSize)
+
+ this.ChatModeText.TextColor3 = this.Settings.TeamTextColor
+ this.ChatModeText.Text = "[Team]"
+ this.ChatModeText.Size = UDim2.new(0, chatTeamTextBounds.X, 1, 0)
+ else
+ this.ChatModeText.Text = ""
+ this.ChatModeText.Size = UDim2.new(0, 0, 1, 0)
+ end
+ if this.ChatBar then
+ local offset = this.ChatModeText.Size.X.Offset + this.ChatModeText.Position.X.Offset
+ this.ChatBar.Size = UDim2.new(1, -offset - 5, 1, 0)
+ this.ChatBar.Position = UDim2.new(0, offset + 5, 0, 0)
+ end
+ end
+ end
+ end
+
+ function this:FocusChatBar()
+ if this.ChatBar then
+ this.ChatBar:CaptureFocus()
+ if self.ClickToChatButton then
+ self.ClickToChatButton.Visible = false
+ end
+ if this.ChatModeText then
+ this.ChatModeText.Visible = true
+ end
+ this.ChatBarChangedConn = Util.DisconnectEvent(this.ChatBarChangedConn)
+ this.ChatBarChangedConn = this.ChatBar.Changed:connect(function(prop)
+ if prop == "Text" then
+ this:OnChatBarTextChanged()
+ end
+ end)
+ if Util.IsTouchDevice() then
+ this.ChatBar.Visible = true
+ this:SetMessageMode('All') -- Don't remember message mode on mobile devices
+ else
+ -- Use a count to make sure you double backspace out of a chatmode; less likely to accidently do it.
+ local count = 0
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ this.FocusChatBarInputBeganConn = InputService.InputBegan:connect(function(inputObj)
+ if inputObj.KeyCode == Enum.KeyCode.Backspace and this:GetChatBarText() == "" then
+ if count == 0 then
+ count = count + 1
+ else
+ this:SetMessageMode('All')
+ end
+ else
+ count = 0
+ end
+ end)
+ end
+ this.ChatBarGainedFocusEvent:fire()
+ end
+ end
+
+ function this:SanitizeInput(input)
+ local sanitizedInput = input
+ -- Chomp the whitespace at the front and end of the string
+ -- TODO: maybe only chop off the front space if there are more than a few?
+ local _, _, capture = string.find(sanitizedInput, "^%s*(.*)%s*$")
+ sanitizedInput = capture or ""
+
+ return sanitizedInput
+ end
+
+ function this:OnChatBarFocusLost(enterPressed)
+ if self.ChatBar then
+ if Util.IsTouchDevice() then
+ self.ChatBar.Visible = false
+ end
+ if enterPressed then
+ local didMatchSlashCommand = this:ProcessChatBarModes(false)
+ local cText = this:SanitizeInput(this:GetChatBarText())
+ if cText ~= "" then
+ if not didMatchSlashCommand and string.sub(cText,1,1) == "/" then
+ this.ChatCommandEvent:fire(false, "Unknown", cText)
+ else
+ local currentMessageMode = this:GetMessageMode()
+ -- {All, Team, Whisper}
+ if currentMessageMode == 'Team' then
+ if Player and Player.Neutral == true then
+ this.ChatErrorEvent:fire("You are not in any team.")
+ else
+ pcall(function() PlayersService:TeamChat(cText) end)
+ end
+ elseif currentMessageMode == 'Whisper' then
+ if this.TargetWhisperPlayer then
+ if this.TargetWhisperPlayer == Player then
+ this.ChatErrorEvent:fire("You cannot send a whisper to yourself.")
+ else
+ pcall(function() PlayersService:WhisperChat(cText, this.TargetWhisperPlayer) end)
+ end
+ else
+ this.ChatErrorEvent:fire("Invalid whisper target.")
+ end
+ elseif currentMessageMode == 'All' then
+ pcall(function() PlayersService:Chat(cText) end)
+ else
+ spawn(function() error("ChatScript: Unknown Message Mode of " .. tostring(currentMessageMode)) end)
+ end
+ end
+ end
+ this:SetChatBarText("")
+ end
+ end
+ if self.ClickToChatButton then
+ self.ClickToChatButton.Visible = true
+ end
+ if this.ChatModeText then
+ this.ChatModeText.Visible = false
+ end
+ this.ChatBarChangedConn = Util.DisconnectEvent(this.ChatBarChangedConn)
+ this.FocusChatBarInputBeganConn = Util.DisconnectEvent(this.FocusChatBarInputBeganConn)
+ end
+
+ local function CreateChatBar()
+ local chatBarContainer = Util.Create'Frame'
+ {
+ Name = 'ChatBarContainer';
+ Position = UDim2.new(0, 0, 1, 0);
+ Size = UDim2.new(1, 0, 0, 20);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 0.25;
+ };
+ local clickToChatButton = Util.Create'TextButton'
+ {
+ Name = 'ClickToChat';
+ Position = UDim2.new(0,9,0,0);
+ Size = UDim2.new(1, -9, 1, 0);
+ BackgroundTransparency = 1;
+ ZIndex = 3;
+ Text = 'To chat click here or press "/" key';
+ TextColor3 = this.Settings.GlobalTextColor;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ Parent = chatBarContainer;
+ }
+ local chatBar = Util.Create'TextBox'
+ {
+ Name = 'ChatBar';
+ Position = UDim2.new(0, 9, 0, 0);
+ Size = UDim2.new(1, -9, 1, 0);
+ Text = "";
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ TextColor3 = this.Settings.GlobalTextColor;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ ClearTextOnFocus = false;
+ Visible = not Util.IsTouchDevice();
+ Parent = chatBarContainer;
+ }
+ local chatModeText = Util.Create'TextButton'
+ {
+ Name = 'ChatModeText';
+ Position = UDim2.new(0, 9, 0, 0);
+ Size = UDim2.new(1, -9, 1, 0);
+ BackgroundTransparency = 1;
+ ZIndex = 2;
+ Text = '';
+ TextColor3 = this.Settings.WhisperTextColor;
+ TextXAlignment = Enum.TextXAlignment.Left;
+ TextYAlignment = Enum.TextYAlignment.Top;
+ Font = Enum.Font.SourceSansBold;
+ FontSize = Enum.FontSize.Size18;
+ Parent = chatBarContainer;
+ }
+
+ this.ChatBarContainer = chatBarContainer
+ this.ClickToChatButton = clickToChatButton
+ this.ChatBar = chatBar
+ this.ChatModeText = chatModeText
+ this.ChatBarContainer.Parent = GuiRoot
+ end
+
+ CreateChatBar()
+ return this
+end
+
+local function CreateChatWindowWidget(settings)
+ local this = {}
+ this.Settings = settings
+ this.Chats = {}
+ this.BackgroundVisible = false
+
+ this.ChatWindowPagingConn = nil
+
+ local lastMoveTime = tick()
+ local lastEnterTime = tick()
+ local lastLeaveTime = tick()
+
+ local lastFadeOutTime = 0
+ local lastFadeInTime = 0
+
+ local FadeLock = false
+
+ local function PointInChatWindow(pt)
+ local point0 = this.ChatContainer.AbsolutePosition
+ local point1 = point0 + this.ChatContainer.AbsoluteSize
+ return point0.X <= pt.X and point1.X >= pt.X and
+ point0.Y <= pt.Y and point1.Y >= pt.Y
+ end
+
+ function this:IsHovering()
+ --return lastEnterTime > lastLeaveTime
+ if this.ChatContainer and this.LastMousePosition then
+ return PointInChatWindow(this.LastMousePosition)
+ end
+ return false
+ end
+
+ function this:SetFadeLock(lock)
+ FadeLock = lock
+ end
+
+ function this:GetFadeLock()
+ return FadeLock
+ end
+
+ function this:FadeIn(duration, lockFade)
+ if not FadeLock then
+ duration = duration or 0.75
+ -- fade in
+ if this.BackgroundTweener then
+ this.BackgroundTweener:Cancel()
+ end
+ lastFadeInTime = tick()
+ this.ScrollingFrame.ScrollingEnabled = true
+ this.BackgroundTweener = Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 0.7, duration, Util.Linear)
+ this.BackgroundVisible = true
+ this:FadeInChats()
+
+ this.ChatWindowPagingConn = Util.DisconnectEvent(this.ChatWindowPagingConn)
+ this.ChatWindowPagingConn = InputService.InputBegan:connect(function(inputObject)
+ local key = inputObject.KeyCode
+ if key == Enum.KeyCode.PageUp then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasPosition.Y - this.ScrollingFrame.AbsoluteSize.Y))
+ elseif key == Enum.KeyCode.PageDown then
+ this.ScrollingFrame.CanvasPosition =
+ Vector2.new(0, Util.Clamp(0, --min
+ this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y, --max
+ this.ScrollingFrame.CanvasPosition.Y + this.ScrollingFrame.AbsoluteSize.Y))
+ elseif key == Enum.KeyCode.Home then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, 0)
+ elseif key == Enum.KeyCode.End then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y)
+ end
+ end)
+ end
+ end
+ function this:FadeOut(duration, unlockFade)
+ if not FadeLock then
+ duration = duration or 0.75
+ -- fade out
+ if this.BackgroundTweener then
+ this.BackgroundTweener:Cancel()
+ end
+ lastFadeOutTime = tick()
+ this.ScrollingFrame.ScrollingEnabled = false
+ this.BackgroundTweener = Util.PropertyTweener(this.ChatContainer, 'BackgroundTransparency', this.ChatContainer.BackgroundTransparency, 1, duration, Util.Linear)
+ this.BackgroundVisible = false
+
+ this.ChatWindowPagingConn = Util.DisconnectEvent(this.ChatWindowPagingConn)
+
+ local now = lastFadeOutTime
+ delay(MESSAGES_FADE_OUT_TIME, function()
+ if lastFadeOutTime > lastFadeInTime and now == lastFadeOutTime then
+ this:FadeOutChats()
+ end
+ end)
+ end
+ end
+
+ function this:FadeInChats()
+ -- TODO: only bother with this loop if we know chats have been faded out, could be quicker than this
+ for index, message in pairs(this.Chats) do
+ message:FadeIn()
+ end
+ end
+
+ function this:FadeOutChats()
+ for index, message in pairs(this.Chats) do
+ message:FadeOut()
+ end
+ end
+
+ function this:OnResize()
+ local isScrolledDown = this:IsScrolledDown()
+
+ local ySize = 0
+
+ if this.ScrollingFrame then
+ for index, message in pairs(this.Chats) do
+ local newHeight = message:OnResize(this.ScrollingFrame.AbsoluteSize)
+ if newHeight then
+ local chatMessageElement = message:GetGui()
+ if chatMessageElement then
+ local chatMessageElementYSize = chatMessageElement.Size.Y.Offset
+ chatMessageElement.Position = UDim2.new(0, 0, 0, ySize)
+ ySize = ySize + chatMessageElementYSize
+ end
+ end
+ end
+ end
+ if this.MessageContainer and this.ScrollingFrame then
+ this.MessageContainer .Size = UDim2.new(
+ 1,
+ this.ScrollingFrame.Size.X.Offset - this.ScrollingFrame.ScrollBarThickness - this.ScrollingFrame.Position.X.Offset,
+ 0,
+ ySize)
+
+ this.ScrollingFrame.CanvasSize = UDim2.new(this.ScrollingFrame.CanvasSize.X.Scale, this.ScrollingFrame.CanvasSize.X.Offset, this.ScrollingFrame.CanvasSize.Y.Scale, ySize)
+ if isScrolledDown then
+ local function UpdateScrollDown()
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasSize.Y.Offset - math.max(0, this.ScrollingFrame.AbsoluteSize.Y)))
+ end
+ UpdateScrollDown()
+ -- Have to do it after a delay as well because when you resize not all of the absolutesize have been updated yet
+ delay(0, UpdateScrollDown)
+ end
+ end
+ end
+
+ function this:PushMessageIntoQueue(chatMessage)
+ table.insert(this.Chats, chatMessage)
+
+ local isScrolledDown = this:IsScrolledDown()
+
+ local chatMessageElement = chatMessage:GetGui()
+
+ chatMessageElement.Parent = this.MessageContainer
+ chatMessage:OnResize()
+ local ySize = this.MessageContainer.Size.Y.Offset
+ local chatMessageElementYSize = UDim2.new(0, 0, 0, chatMessageElement.Size.Y.Offset)
+
+ chatMessageElement.Position = chatMessageElement.Position + UDim2.new(0, 0, 0, ySize)
+ this.MessageContainer.Size = this.MessageContainer.Size + chatMessageElementYSize
+ this.ScrollingFrame.CanvasSize = this.ScrollingFrame.CanvasSize + chatMessageElementYSize
+
+ if this.Settings.MaxWindowChatMessages < #this.Chats then
+ this:RemoveOldestMessage()
+ end
+ if isScrolledDown then
+ this.ScrollingFrame.CanvasPosition = Vector2.new(0, math.max(0, this.ScrollingFrame.CanvasSize.Y.Offset - this.ScrollingFrame.AbsoluteSize.Y))
+ else
+ -- Raise unread message alert!
+ end
+ this:FadeInChats()
+ end
+
+ function this:AddSystemChatMessage(chattedMessage)
+ local chatMessage = CreateSystemChatMessage(chattedMessage)
+ this:PushMessageIntoQueue(chatMessage)
+ end
+
+ function this:AddChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ local chatMessage = CreatePlayerChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ this:PushMessageIntoQueue(chatMessage)
+ end
+
+ function this:RemoveOldestMessage()
+ local oldestChat = this.Chats[1]
+ if oldestChat then
+ return this:RemoveChatMessage(oldestChat)
+ end
+ end
+
+ function this:RemoveChatMessage(chatMessage)
+ if chatMessage then
+ for index, message in pairs(this.Chats) do
+ if chatMessage == message then
+ local guiObj = chatMessage:GetGui()
+ if guiObj then
+ local ySize = guiObj.Size.Y.Offset
+ this.ScrollingFrame.CanvasSize = this.ScrollingFrame.CanvasSize - UDim2.new(0,0,0,ySize)
+ guiObj.Parent = nil
+ end
+ message:Destroy()
+ return table.remove(this.Chats, index)
+ end
+ end
+ end
+ end
+
+ function this:IsScrolledDown()
+ local yCanvasSize = this.ScrollingFrame.CanvasSize.Y.Offset
+ local yContainerSize = this.ScrollingFrame.AbsoluteSize.Y
+ local yScrolledPosition = this.ScrollingFrame.CanvasPosition.Y
+ -- Check if the messages are at the bottom
+ return yCanvasSize < yContainerSize or
+ yCanvasSize - yScrolledPosition >= yContainerSize - 2 -- Fuzzy equals here
+ end
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if this.ChatContainer then
+ this.ChatContainer.Visible = enabled
+ end
+ end
+ -- If we are using bubble-chat then do not show chat window
+ if this.ChatContainer and not PlayersService.ClassicChat then
+ this.ChatContainer.Visible = false
+ end
+ end
+
+ local function CreateChatWindow()
+ local container = Util.Create'Frame'
+ {
+ Name = 'ChatWindowContainer';
+ -- Height is a multiple of chat message height, maybe keep this value at 150 and move that padding into the messageContainer
+ Size = UDim2.new(0.33, 0, 0.25, 0);
+ Position = UDim2.new(0, 20, 0, 50);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ };
+ local scrollingFrame = Util.Create'ScrollingFrame'
+ {
+ Name = 'ChatWindow';
+ Size = UDim2.new(1, -4 - 10, 1, -20);
+ CanvasSize = UDim2.new(1, -4 - 10, 0, 0);
+ Position = UDim2.new(0, 10, 0, 10);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ BottomImage = "rbxasset://textures/ui/scroll-bottom.png";
+ MidImage = "rbxasset://textures/ui/scroll-middle.png";
+ TopImage = "rbxasset://textures/ui/scroll-top.png";
+ ScrollBarThickness = 7;
+ BorderSizePixel = 0;
+ ScrollingEnabled = false;
+ Parent = container;
+ };
+ local messageContainer = Util.Create'Frame'
+ {
+ Name = 'MessageContainer';
+ Size = UDim2.new(1, 0, 0, 0);
+ Position = UDim2.new(0, 0, 1, 0);
+ ZIndex = 1;
+ BackgroundColor3 = Color3.new(0, 0, 0);
+ BackgroundTransparency = 1;
+ Parent = scrollingFrame
+ };
+
+ -- This is some trickery we are doing to make the first chat messages appear at the bottom and go towards the top.
+ local function OnChatWindowResize(prop)
+ if prop == 'AbsoluteSize' then
+ messageContainer.Position = UDim2.new(0, 0, 1, -messageContainer.Size.Y.Offset)
+ elseif prop == 'ScrollBarThickness' then
+ messageContainer.Size = UDim2.new(
+ messageContainer.Size.X.Scale,
+ scrollingFrame.Size.X.Offset - scrollingFrame.ScrollBarThickness - scrollingFrame.Position.X.Offset,
+ messageContainer.Size.Y.Scale,
+ messageContainer.Size.Y.Offset)
+ end
+ end
+ container.Changed:connect(function(prop) if prop == 'AbsoluteSize' then this:OnResize() end end)
+
+ local function RobloxClientScreenSizeChanged(newSize)
+ if container then
+ -- Phone
+ if newSize.X <= 640 then
+ container.Size = UDim2.new(0.5,0,0.5,0) - container.Position
+ -- Tablet
+ elseif newSize.X <= 1024 then
+ container.Size = UDim2.new(0.4,0,0.3,0) - container.Position
+ -- Desktop
+ else
+ container.Size = UDim2.new(0.33,0,0.25,0) - container.Position
+ end
+ end
+ end
+
+ GuiRoot.Changed:connect(function(prop) if prop == "AbsoluteSize" then RobloxClientScreenSizeChanged(GuiRoot.AbsoluteSize) end end)
+ RobloxClientScreenSizeChanged(GuiRoot.AbsoluteSize)
+
+ messageContainer.Changed:connect(OnChatWindowResize)
+ scrollingFrame.Changed:connect(OnChatWindowResize)
+
+ this.ChatContainer = container
+ this.ScrollingFrame = scrollingFrame
+ this.MessageContainer = messageContainer
+ this.ChatContainer.Parent = GuiRoot
+
+ --- BACKGROUND FADING CODE ---
+ -- This is so we don't accidentally fade out when we are scrolling and mess with the scrollbar.
+ local dontFadeOutOnMouseLeave = false
+
+ if Util:IsTouchDevice() then
+ local touchCount = 0
+ this.InputBeganConn = InputService.InputBegan:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.Touch and inputObject.UserInputState == Enum.UserInputState.Begin then
+ if PointInChatWindow(Vector2.new(inputObject.Position.X, inputObject.Position.Y)) then
+ touchCount = touchCount + 1
+ dontFadeOutOnMouseLeave = true
+ end
+ end
+ end)
+
+ this.InputEndedConn = InputService.InputEnded:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.Touch and inputObject.UserInputState == Enum.UserInputState.End then
+ local endedCount = touchCount
+ wait(2)
+ if touchCount == endedCount then
+ dontFadeOutOnMouseLeave = false
+ end
+ end
+ end)
+
+ spawn(function()
+ while true do
+ wait()
+ if this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut(0.25)
+ end
+ end
+ end
+ end)
+ else
+ this.LastMousePosition = Vector2.new()
+
+ this.MouseEnterFrameConn = this.ChatContainer.MouseEnter:connect(function()
+ lastEnterTime = tick()
+ if this.BackgroundTweener and not this.BackgroundTweener:IsFinished() and not this.BackgroundVisible then
+ this:FadeIn()
+ end
+ end)
+
+ this.MouseMoveConn = InputService.InputChanged:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseMovement then
+ lastMoveTime = tick()
+ this.LastMousePosition = Vector2.new(inputObject.Position.X, inputObject.Position.Y)
+ if this.BackgroundTweener and this.BackgroundTweener:GetPercentComplete() < 0.5 and this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut()
+ end
+ end
+ end
+ end)
+
+ local clickCount = 0
+ this.InputBeganConn = InputService.InputBegan:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseButton1 and inputObject.UserInputState == Enum.UserInputState.Begin then
+ if PointInChatWindow(Vector2.new(inputObject.Position.X, inputObject.Position.Y)) then
+ clickCount = clickCount + 1
+ dontFadeOutOnMouseLeave = true
+ end
+ end
+ end)
+
+ this.InputEndedConn = InputService.InputEnded:connect(function(inputObject)
+ if inputObject.UserInputType == Enum.UserInputType.MouseButton1 and inputObject.UserInputState == Enum.UserInputState.End then
+ local nowCount = clickCount
+ wait(2)
+ if nowCount == clickCount then
+ dontFadeOutOnMouseLeave = false
+ end
+ end
+ end)
+
+ this.MouseLeaveFrameConn = this.ChatContainer.MouseLeave:connect(function()
+ lastLeaveTime = tick()
+ if this.BackgroundTweener and not this.BackgroundTweener:IsFinished() and this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut()
+ end
+ end
+ end)
+
+ spawn(function()
+ while true do
+ wait()
+ if this:IsHovering() then
+ if tick() - lastMoveTime > 2 and not this.BackgroundVisible then
+ this:FadeIn()
+ end
+ else -- not this:IsHovering()
+ if this.BackgroundVisible then
+ if not dontFadeOutOnMouseLeave then
+ this:FadeOut(0.25)
+ end
+ end
+ end
+ end
+ end)
+ end
+ --- END OF BACKGROUND FADING CODE ---
+ end
+
+ CreateChatWindow()
+
+ return this
+end
+
+
+local function CreateChat()
+ local this = {}
+
+ this.Settings =
+ {
+ GlobalTextColor = Color3.new(255/255, 255/255, 243/255);
+ WhisperTextColor = Color3.new(77/255, 139/255, 255/255);
+ TeamTextColor = Color3.new(230/255, 207/255, 0);
+ MaxWindowChatMessages = 100;
+ MaxCharactersInMessage = 140; -- Same as a tweet :D
+ }
+
+
+ function this:CoreGuiChanged(coreGuiType, enabled)
+ if coreGuiType == Enum.CoreGuiType.Chat or coreGuiType == Enum.CoreGuiType.All then
+ if Util:IsTouchDevice() then
+ Util.SetGUIInsetBounds(0, 0)
+ else
+ if enabled then
+ -- Reserve bottom 20 pixels for our chat bar
+ Util.SetGUIInsetBounds(0, 20)
+ else
+ Util.SetGUIInsetBounds(0, 0)
+ end
+ end
+ end
+ if this.ChatWindowWidget then
+ this.ChatWindowWidget:CoreGuiChanged(coreGuiType, enabled)
+ end
+ if this.ChatBarWidget then
+ this.ChatBarWidget:CoreGuiChanged(coreGuiType, enabled)
+ end
+ end
+
+ -- This event has 4 callback arguments
+ -- Enum.PlayerChatType.{All|Team|Whisper}, chatPlayer, message, targetPlayer
+ function this:OnPlayerChatted(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ if this.ChatWindowWidget then
+ this.ChatWindowWidget:AddChatMessage(playerChatType, sendingPlayer, chattedMessage, receivingPlayer)
+ end
+ end
+
+ function this:OnPlayerAdded()
+ this.PlayerChattedConn = Util.DisconnectEvent(this.PlayerChattedConn)
+ this.PlayerChattedConn = PlayersService.PlayerChatted:connect(function(...)
+ this:OnPlayerChatted(...)
+ end)
+ end
+
+ function this:GetBlockedPlayersAsync()
+ local secureBaseUrl = Util.GetSecureApiBaseUrl()
+ local url = secureBaseUrl .. "userblock/getblockedusers" .. "?" .. "userId=" .. tostring(Player.userId) .. "&" .. "page=" .. "1"
+ local blockList = nil
+ local success, msg = ypcall(function()
+ local request = game:HttpGetAsync(url)
+ blockList = request and game:GetService('HttpService'):DecodeJSON(request)
+ end)
+ if blockList and blockList['success'] == true then
+ return blockList['userList']
+ end
+ end
+
+ function this:CreateTouchDeviceChatButton()
+ return Util.Create'ImageButton'
+ {
+ Name = 'TouchDeviceChatButton';
+ Size = UDim2.new(0, 128, 0, 32);
+ Position = UDim2.new(0, 88, 0, 0);
+ BackgroundTransparency = 1.0;
+ Image = 'http://www.roblox.com/asset/?id=97078724';
+ };
+ end
+
+ function this:PrintWelcome()
+ this.ChatWindowWidget:AddSystemChatMessage("Welcome to Roblox")
+ this.ChatWindowWidget:AddSystemChatMessage("Please type /? for a list of commands")
+ end
+
+ function this:PrintHelp()
+ this.ChatWindowWidget:AddSystemChatMessage("Help Menu")
+ this.ChatWindowWidget:AddSystemChatMessage("Chat Commands:")
+ this.ChatWindowWidget:AddSystemChatMessage("/w [PlayerName] or /whisper [PlayerName] - Whisper Chat")
+ this.ChatWindowWidget:AddSystemChatMessage("/t or /team - Team Chat")
+ this.ChatWindowWidget:AddSystemChatMessage("/a or /all - All Chat")
+ end
+
+ function this:CreateGUI()
+ if Player.ChatMode == Enum.ChatMode.TextAndMenu or FORCE_CHAT_GUI then
+ -- NOTE: eventually we will make multiple chat window frames
+ -- Settings is a table, which makes it a pointing and is kosher to pass by reference
+ this.ChatWindowWidget = CreateChatWindowWidget(this.Settings)
+ this.ChatBarWidget = CreateChatBarWidget(this.Settings)
+
+ local focusCount = 0
+ this.ChatBarWidget.ChatBarGainedFocusEvent:connect(function()
+ focusCount = focusCount + 1
+ this.ChatWindowWidget:FadeIn(0.25)
+ this.ChatWindowWidget:SetFadeLock(true)
+ end)
+ this.ChatBarWidget.ChatBarLostFocusEvent:connect(function()
+ local focusNow = focusCount
+ if Util:IsTouchDevice() then
+ wait(2)
+ if focusNow == focusCount then
+ this.ChatWindowWidget:SetFadeLock(false)
+ end
+ else
+ this.ChatWindowWidget:SetFadeLock(false)
+ end
+ end)
+
+ this.ChatBarWidget.ChatErrorEvent:connect(function(msg)
+ if msg then
+ this.ChatWindowWidget:AddSystemChatMessage(msg)
+ end
+ end)
+
+ this.ChatBarWidget.ChatCommandEvent:connect(function(success, actionType, capture)
+ if actionType == "Help" then
+ this:PrintHelp()
+ elseif actionType == "Whisper" then
+ if success == false then
+ local playerName = capture and tostring(capture) or "Unknown"
+ this.ChatWindowWidget:AddSystemChatMessage("Unable to Send a Whisper to Player: " .. playerName)
+ end
+ elseif actionType == "Unknown" then
+ if success == false then
+ local commandText = capture and tostring(capture) or "Unknown"
+ this.ChatWindowWidget:AddSystemChatMessage("Invalid Slash Command: " .. commandText)
+ end
+ end
+ end)
+
+ if Util.IsTouchDevice() then
+ local mobileChatButton = this:CreateTouchDeviceChatButton()
+ mobileChatButton.Parent = GuiRoot
+
+ mobileChatButton.TouchTap:connect(function()
+ mobileChatButton.Visible = false
+ if this.ChatBarWidget then
+ this.ChatBarWidget:FocusChatBar()
+ end
+ end)
+
+ this.ChatBarWidget.ChatBarLostFocusEvent:connect(function()
+ mobileChatButton.Visible = true
+ end)
+ end
+ end
+ end
+
+ function this:Initialize()
+ --spawn(function()
+ -- this:GetBlockedPlayersAsync()
+ --end)
+
+ this:OnPlayerAdded()
+ -- Upsettingly, it seems everytime a player is added, you have to redo the connection
+ -- NOTE: PlayerAdded only fires on the server, hence ChildAdded is used here
+ PlayersService.ChildAdded:connect(function()
+ this:OnPlayerAdded()
+ end)
+
+ this:CreateGUI()
+
+ pcall(function()
+ this:CoreGuiChanged(Enum.CoreGuiType.Chat, StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Chat))
+ this.CoreGuiChangedConn = Util.DisconnectEvent(this.CoreGuiChangedConn)
+ this.CoreGuiChangedConn = StarterGui.CoreGuiChangedSignal:connect(
+ function(coreGuiType,enabled)
+ this:CoreGuiChanged(coreGuiType, enabled)
+ end)
+ end)
+
+ this:PrintWelcome()
+ end
+
+ return this
+end
+
+
+-- Run the script
+do
+ local ChatInstance = CreateChat()
+ ChatInstance:Initialize()
+end
diff --git a/asset/12 b/asset/12
new file mode 100644
index 0000000..f05538f
--- /dev/null
+++ b/asset/12
@@ -0,0 +1,1295 @@
+--rbxassetid%12%
+-- this script creates the gui and sends the web requests for in game purchase prompts
+
+-- wait for important items to appear
+while not Game do
+ wait(0.1)
+end
+while not game:GetService("MarketplaceService") do
+ wait(0.1)
+end
+while not game:FindFirstChild("CoreGui") do
+ wait(0.1)
+end
+while not game.CoreGui:FindFirstChild("RobloxGui") do
+ wait(0.1)
+end
+
+-------------------------------- Global Variables ----------------------------------------
+-- utility variables
+local RbxUtility = nil
+local baseUrl = game:GetService("ContentProvider").BaseUrl:lower()
+baseUrl = string.gsub(baseUrl,"/m.","/www.") --mobile site does not work for this stuff!
+
+local doNativePurchasing = true
+
+-- data variables
+local currentProductInfo, currentAssetId, currentCurrencyType, currentCurrencyAmount, currentEquipOnPurchase, currentProductId, currentServerResponseTable, thirdPartyProductName
+local checkingPlayerFunds = false
+local purchasingConsumable = false
+
+-- gui variables
+local currentlyPrompting = false
+local currentlyPurchasing = false
+local purchaseDialog, errorDialog = nil
+local tweenTime = 0.3
+local showPosition = UDim2.new(0.5,-217,0.5,-146)
+local hidePosition = UDim2.new(0.5,-217,1,25)
+local isSmallScreen = nil
+local spinning = false
+local spinnerIcons = nil
+local smallScreenThreshold = 450
+local renderSteppedConnection = nil
+
+-- user facing images
+local assetUrls = {}
+local assetUrl = "http://www.roblox.com/Asset/?id="
+local errorImageUrl = assetUrl .. "42557901" table.insert(assetUrls, errorImageUrl)
+local buyImageUrl = assetUrl .. "142494143" table.insert(assetUrls,buyImageUrl)
+local cancelButtonImageUrl = assetUrl .. "142494219" table.insert(assetUrls, cancelButtonImageUrl)
+local freeButtonImageDownUrl = assetUrl .. "104651761" table.insert(assetUrls, freeButtonImageDownUrl)
+local loadingImage = assetUrl .. "143116791" table.insert(assetUrls,loadingImage)
+
+-- user facing string
+local buyHeaderText = "Buy Item"
+local takeHeaderText = "Take Item"
+local buyFailedHeaderText = "An Error Occurred"
+
+local errorPurchasesDisabledText = "In-game purchases are disabled"
+local errorPurchasesBuyRobuxText = "your account does not have enough Robux"
+local errorPurchasesUnknownText = "Roblox is performing maintenance"
+
+local purchaseSucceededText = "Your purchase of itemName succeeded!"
+local purchaseFailedText = "Your purchase of itemName failed because errorReason. Your account has not been charged. Please try again soon."
+local productPurchaseText = "Would you like to buy the itemName assetType for currencyTypecurrencyAmount?"
+local productPurchaseTixOnlyText = "Would you like to buy the itemName assetType for currencyAmount currencyType?"
+local freeItemPurchaseText = "Would you like to take the assetType itemName for FREE?"
+local freeItemBalanceText = "Your balance of Robux or Tix will not be affected by this transaction."
+local upgradeBCText = "You require an upgrade to your Builders Club membership to purchase this item. Click 'Buy Builders Club' to upgrade."
+local productPurchaseWithMoreRobuxText = "Buy robuxToBuyAmount$R to get itemName assetType."
+local productPurchaseWithMoreRobuxRemainderText = "The remaining purchaseRemainder$R will be credited to your ROBUX balance."
+local balanceFutureTenseText = "Your balance after this transaction will be "
+local balanceCurrentTenseText = "Your balance is now "
+
+-- robux product arrays
+local bcRobuxProducts = {90, 180, 270, 360, 450, 1000, 2750}
+local nonBcRobuxProducts = {80, 160, 240, 320, 400, 800, 2000}
+-------------------------------- End Global Variables ----------------------------------------
+
+
+----------------------------- Util Functions ---------------------------------------------
+function getSecureApiBaseUrl()
+ local secureApiUrl = baseUrl
+ secureApiUrl = string.gsub(secureApiUrl,"http","https")
+ secureApiUrl = string.gsub(secureApiUrl,"www","api")
+ return secureApiUrl
+end
+
+function getRbxUtility()
+ if not RbxUtility then
+ RbxUtility = LoadLibrary("RbxUtility")
+ end
+ return RbxUtility
+end
+
+function preloadAssets()
+ for i = 1, #assetUrls do
+ game:GetService("ContentProvider"):Preload(assetUrls[i])
+ end
+end
+----------------------------- End Util Functions ---------------------------------------------
+
+
+-------------------------------- Accept/Decline Functions --------------------------------------
+function removeCurrentPurchaseInfo()
+ currentAssetId = nil
+ currentCurrencyType = nil
+ currentCurrencyAmount = nil
+ currentEquipOnPurchase = nil
+ currentProductId = nil
+ currentProductInfo = nil
+ currentServerResponseTable = nil
+
+ checkingPlayerFunds = false
+end
+
+function userPurchaseActionsEnded(isSuccess)
+ checkingPlayerFunds = false
+
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = false
+
+ if isSuccess then -- show the user we bought the item successfully, when they close this dialog we will call signalPromptEnded
+ local newPurchasedSucceededText = string.gsub( purchaseSucceededText,"itemName", tostring(currentProductInfo["Name"]))
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedSucceededText
+
+ local playerBalance = getPlayerBalance()
+ local keyWord = "robux"
+ if currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ local afterBalanceNumber = playerBalance[keyWord]
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balanceCurrentTenseText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkPurchasedButton)
+ hidePurchasing()
+ else -- otherwise we didn't purchase, no need to show anything, just signal and close dialog
+ signalPromptEnded(isSuccess)
+ end
+end
+
+function signalPromptEnded(isSuccess)
+ closePurchasePrompt()
+ if purchasingConsumable then
+ game:GetService("MarketplaceService"):SignalPromptProductPurchaseFinished(game.Players.LocalPlayer.userId, currentProductId, isSuccess)
+ else
+ game:GetService("MarketplaceService"):SignalPromptPurchaseFinished(game.Players.LocalPlayer, currentAssetId, isSuccess)
+ end
+ removeCurrentPurchaseInfo()
+end
+
+function getClosestRobuxProduct(amountNeededToBuy, robuxProductArray)
+ local closest = robuxProductArray[1];
+ local closestIndex = 1
+
+ for i = 1, #robuxProductArray do
+ if ( math.abs(robuxProductArray[i] - amountNeededToBuy) < math.abs(closest - amountNeededToBuy) ) then
+ closest = robuxProductArray[i]
+ closestIndex = i
+ end
+ end
+
+ if closest < amountNeededToBuy then
+ closest = robuxProductArray[1 + closestIndex]
+ end
+
+ return closest
+end
+
+--todo: get productIds from server instead of embedding values
+function getMinimumProductNeededForPurchase(amountNeededToBuy)
+ local isBcMember = (Game.Players.LocalPlayer.MembershipType ~= Enum.MembershipType.None)
+ local productAmount = nil
+
+ if isBcMember then
+ productAmount = getClosestRobuxProduct(amountNeededToBuy, bcRobuxProducts)
+ else
+ productAmount = getClosestRobuxProduct(amountNeededToBuy, nonBcRobuxProducts)
+ end
+
+ local isAndroid = false
+ pcall(function() isAndroid = (Game:GetService("UserInputService"):GetPlatform() == Enum.Platform.Android) end)
+
+ local prependString = ""
+ local appendString = ""
+ local appPrefix = ""
+
+ if isAndroid then
+ prependString = "robux"
+ if isBcMember then
+ appendString = "bc"
+ end
+ appPrefix = "com.roblox.client."
+ else
+ if isBcMember then
+ appendString = "RobuxBC"
+ else
+ appendString = "RobuxNonBC"
+ end
+
+ appPrefix = "com.roblox.robloxmobile."
+ end
+
+ local productString = appPrefix .. prependString .. tostring(productAmount) .. appendString
+
+ return productAmount, productString
+end
+
+function getClosestRobuxProductToBuyItem(productAmount, playerBalanceInRobux)
+ local amountNeededToBuy = productAmount - playerBalanceInRobux
+ local amountToBuy, productName = getMinimumProductNeededForPurchase(amountNeededToBuy)
+ local remainderAfterPurchase = amountToBuy - productAmount
+
+ return amountToBuy, remainderAfterPurchase, productName
+end
+
+function canUseNewRobuxToProductFlow()
+ return (Game:GetService("UserInputService").TouchEnabled and doNativePurchasing)
+end
+
+-- make sure our gui displays the proper purchase data, and set the productid we will try and buy if use specifies a buy action
+function updatePurchasePromptData(insufficientFunds)
+ local newItemDescription = ""
+
+ -- id to use when we request a purchase
+ if not currentProductId then
+ currentProductId = currentProductInfo["ProductId"]
+ end
+
+ if isFreeItem() then
+ newItemDescription = string.gsub( freeItemPurchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ setHeaderText(takeHeaderText)
+ elseif insufficientFunds and canUseNewRobuxToProductFlow() then
+ local purchaseText = productPurchaseWithMoreRobuxText
+
+ local playerBalance = getPlayerBalance()
+ if not playerBalance then
+ newItemDescription = "Could not retrieve your balance. Please try again later."
+ elseif canUseNewRobuxToProductFlow() then
+ local amountToBuy, remainderAfterPurchase, productName = getClosestRobuxProductToBuyItem(currentCurrencyAmount, playerBalance["robux"])
+ thirdPartyProductName = productName
+
+ newItemDescription = string.gsub( purchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ newItemDescription = string.gsub( newItemDescription,"robuxToBuyAmount", tostring(amountToBuy))
+
+ if remainderAfterPurchase > 0 then
+ newItemDescription = newItemDescription .. " " .. string.gsub( productPurchaseWithMoreRobuxRemainderText,"purchaseRemainder", tostring(remainderAfterPurchase))
+ end
+ end
+ setHeaderText(buyHeaderText)
+ else
+ local purchaseText = productPurchaseText
+ if currentProductIsTixOnly() then
+ purchaseText = productPurchaseTixOnlyText
+ end
+
+ newItemDescription = string.gsub( purchaseText,"itemName", tostring(currentProductInfo["Name"]))
+ newItemDescription = string.gsub( newItemDescription,"assetType", tostring(assetTypeToString(currentProductInfo["AssetTypeId"])) )
+ newItemDescription = string.gsub( newItemDescription,"currencyType", tostring(currencyTypeToString(currentCurrencyType)) )
+ newItemDescription = string.gsub( newItemDescription,"currencyAmount", tostring(currentCurrencyAmount))
+ setHeaderText(buyHeaderText)
+ end
+
+ purchaseDialog.BodyFrame.ItemDescription.Text = newItemDescription
+
+ if purchasingConsumable then
+ purchaseDialog.BodyFrame.ItemPreview.Image = baseUrl .. "thumbs/asset.ashx?assetid=" .. tostring(currentProductInfo["IconImageAssetId"]) .. '&x=100&y=100&format=png'
+ else
+ purchaseDialog.BodyFrame.ItemPreview.Image = baseUrl .. "thumbs/asset.ashx?assetid=" .. tostring(currentAssetId) .. '&x=100&y=100&format=png'
+ end
+end
+
+function checkIfCanPurchase()
+ if checkingPlayerFunds then
+ local canPurchase, insufficientFunds, notRightBC = canPurchaseItem() -- check again to see if we can buy item
+ if not canPurchase or (insufficientFunds or notRightBC) then -- wait a bit and try a few more times
+ local retries = 20
+ while retries > 0 and (insufficientFunds or notRightBC) and checkingPlayerFunds and canPurchase do
+ wait(0.5)
+ canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ retries = retries - 1
+ end
+ end
+ if canPurchase and not insufficientFunds then
+ -- we can buy item! set our buttons up and we will exit this loop
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyButton,purchaseDialog.BodyFrame.CancelButton, purchaseDialog.BodyFrame.AfterBalanceText)
+ end
+ end
+end
+
+function closePurchasePrompt()
+ purchaseDialog:TweenPosition(hidePosition, Enum.EasingDirection.Out, Enum.EasingStyle.Quad, tweenTime, true, function()
+ game.GuiService:RemoveCenterDialog(purchaseDialog)
+ hidePurchasing()
+
+ purchaseDialog.Visible = false
+ currentlyPrompting = false
+ currentlyPurchasing = false
+
+ Game:GetService("UserInputService").ModalEnabled = false
+ end)
+end
+
+function showPurchasePrompt()
+ local canPurchase, insufficientFunds, notRightBC, override, descText = canPurchaseItem()
+
+ if canPurchase then
+ updatePurchasePromptData(insufficientFunds)
+
+ if override and descText then
+ purchaseDialog.BodyFrame.ItemDescription.Text = descText
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = false
+ end
+ game.GuiService:AddCenterDialog(purchaseDialog, Enum.CenterDialogType.ModalDialog,
+ --ShowFunction
+ function()
+ -- set the state for our buttons
+ purchaseDialog.Visible = true
+
+ if not currentlyPurchasing then
+ if isFreeItem() then
+ setButtonsVisible(purchaseDialog.BodyFrame.FreeButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif notRightBC then
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyBCButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif insufficientFunds then
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyRobuxButton, purchaseDialog.BodyFrame.CancelButton)
+ elseif override then
+ if currentProductIsTixOnly() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+ end
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyDisabledButton, purchaseDialog.BodyFrame.CancelButton)
+ else
+ setButtonsVisible(purchaseDialog.BodyFrame.BuyButton, purchaseDialog.BodyFrame.CancelButton)
+ end
+ end
+
+ Game:GetService("UserInputService").ModalEnabled = true
+
+ purchaseDialog:TweenPosition(showPosition, Enum.EasingDirection.Out, Enum.EasingStyle.Quad, tweenTime, true)
+ end,
+ --HideFunction
+ function()
+ Game:GetService("UserInputService").ModalEnabled = false
+ purchaseDialog.Visible = false
+ end)
+ else -- we failed in prompting a purchase, do a decline
+ doDeclinePurchase()
+ end
+end
+
+-- given an asset id, this function will grab that asset from the website, and return the first "Tool" object found inside it
+function getToolAssetID(assetID)
+ local newTool = game:GetService("InsertService"):LoadAsset(assetID)
+ if not newTool then return nil end
+
+ if newTool:IsA("Tool") then
+ return newTool
+ end
+
+ local toolChildren = newTool:GetChildren()
+ for i = 1, #toolChildren do
+ if toolChildren[i]:IsA("Tool") then
+ return toolChildren[i]
+ end
+ end
+ return nil
+end
+
+-- the user tried to purchase by clicking the purchase button, but something went wrong.
+-- let them know their account was not charged, and that they do not own the item yet.
+function purchaseFailed(errorType)
+ local name = "Item"
+ if currentProductInfo then name = currentProductInfo["Name"] end
+
+ local newPurchasedFailedText = string.gsub( purchaseFailedText,"itemName", tostring(name))
+
+ if errorType == "inGamePurchasesDisabled" then
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesDisabledText) )
+ elseif errorType == "didNotBuyRobux" then
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesBuyRobuxText) )
+ else
+ newPurchasedFailedText = string.gsub( newPurchasedFailedText,"errorReason", tostring(errorPurchasesUnknownText) )
+ end
+
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedFailedText
+ purchaseDialog.BodyFrame.ItemPreview.Image = errorImageUrl
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = ""
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkButton)
+
+ setHeaderText(buyFailedHeaderText)
+
+ hidePurchasing()
+end
+
+-- user has specified they want to buy an item, now try to attempt to buy it for them
+function doAcceptPurchase(currencyPreferredByUser)
+ if currentlyPurchasing then return end
+ currentlyPurchasing = true
+
+ showPurchasing() -- shows a purchasing ui (shows spinner)
+
+ local startTime = tick()
+
+ -- http call to do the purchase
+ local response = "none"
+ local url = nil
+
+ local flagExists, flagValue = pcall(function() return settings():GetFFlag("AddRequestIdToDeveloperProductPurchases") end)
+ local reliableDevProductEnabled = flagExists and flagValue
+ -- consumables need to use a different url
+ if purchasingConsumable then
+ url = getSecureApiBaseUrl() .. "marketplace/submitpurchase?productId=" .. tostring(currentProductId) ..
+ "¤cyTypeId=" .. tostring(currencyEnumToInt(currentCurrencyType)) ..
+ "&expectedUnitPrice=" .. tostring(currentCurrencyAmount) ..
+ "&placeId=" .. tostring(Game.PlaceId)
+ if reliableDevProductEnabled then
+ local h = game:GetService("HttpService")
+ url = url .. "&requestId=" .. h:UrlEncode(h:GenerateGUID(false))
+ end
+ else
+ url = getSecureApiBaseUrl() .. "marketplace/purchase?productId=" .. tostring(currentProductId) ..
+ "¤cyTypeId=" .. tostring(currencyEnumToInt(currentCurrencyType)) ..
+ "&purchasePrice=" .. tostring(currentCurrencyAmount) ..
+ "&locationType=Game" .. "&locationId=" .. Game.PlaceId
+ end
+
+ local success, reason = ypcall(function()
+ response = game:HttpPostAsync(url, "RobloxPurchaseRequest")
+ end)
+
+ if reliableDevProductEnabled and purchasingConsumable then
+ local retriesLeft = 3
+ local gotGoodResponse = success and response ~= "none" and response ~= nil and response ~= ''
+ while retriesLeft > 0 and (not gotGoodResponse) do
+ wait(1)
+ retriesLeft = retriesLeft - 1
+ success, reason = ypcall(function()
+ response = game:HttpPostAsync(url, "RobloxPurchaseRequest")
+ end)
+ gotGoodResponse = success and response ~= "none" and response ~= nil and response ~= ''
+ end
+
+ game:ReportInGoogleAnalytics("Developer Product", "Purchase",
+ gotGoodResponse and ("success. Retries = " .. (3 - retriesLeft)) or ("failure: " .. tostring(reason)), 1)
+ end
+
+ -- debug output for us (found in the logs from local)
+ print("doAcceptPurchase success from ypcall is ",success,"reason is",reason)
+
+ if (tick() - startTime) < 1 then
+ wait(1) -- allow the purchasing waiting dialog to at least be readable (otherwise it might flash, looks bad)...
+ end
+
+ -- check to make sure purchase actually happened on the web end
+ if response == "none" or response == nil or response == '' then
+ print("did not get a proper response from web on purchase of",currentAssetId,currentProductId)
+ purchaseFailed()
+ return
+ end
+
+ -- parse our response, decide how to react
+ response = getRbxUtility().DecodeJSON(response)
+
+ if response then
+ if response["success"] == false then
+ if response["status"] ~= "AlreadyOwned" then
+ print("web return response of fail on purchase of",currentAssetId,currentProductId)
+ if (response["status"] == "EconomyDisabled") then
+ purchaseFailed("inGamePurchasesDisabled")
+ else
+ purchaseFailed()
+ end
+ return
+ end
+ end
+ else
+ print("web return response of non parsable JSON on purchase of",currentAssetId)
+ purchaseFailed()
+ return
+ end
+
+ -- check to see if this item was bought, and if we want to equip it (also need to make sure the asset type was gear)
+ if currentEquipOnPurchase and success and currentAssetId and tonumber(currentProductInfo["AssetTypeId"]) == 19 then
+ local tool = getToolAssetID(tonumber(currentAssetId))
+ if tool then
+ tool.Parent = game.Players.LocalPlayer.Backpack
+ end
+ end
+
+ if purchasingConsumable then
+ if not response["receipt"] then
+ print("tried to buy productId, but no receipt returned. productId was",currentProductId)
+ purchaseFailed()
+ return
+ end
+ Game:GetService("MarketplaceService"):SignalClientPurchaseSuccess( tostring(response["receipt"]), game.Players.LocalPlayer.userId, currentProductId )
+ else
+ userPurchaseActionsEnded(success)
+ end
+end
+
+-- user pressed the cancel button, just remove all purchasing prompts
+function doDeclinePurchase()
+ if currentlyPurchasing then return end
+ userPurchaseActionsEnded(false)
+end
+-------------------------------- End Accept/Decline Functions --------------------------------------
+
+
+---------------------------------------------- Currency Functions ---------------------------------------------
+-- enums have no implicit conversion to numbers in lua, has to have a function to do this
+function currencyEnumToInt(currencyEnum)
+ if currencyEnum == Enum.CurrencyType.Robux or currencyEnum == Enum.CurrencyType.Default then
+ return 1
+ elseif currencyEnum == Enum.CurrencyType.Tix then
+ return 2
+ end
+end
+
+-- oi, this isn't so ugly anymore
+function assetTypeToString(assetType)
+ local assetTypes = {
+ [1] = "Image";
+ [2] = "T-Shirt";
+ [3] = "Audio";
+ [4] = "Mesh";
+ [5] = "Lua";
+ [6] = "HTML";
+ [7] = "Text";
+ [8] = "Hat";
+ [9] = "Place";
+ [10] = "Model";
+ [11] = "Shirt";
+ [12] = "Pants";
+ [13] = "Decal";
+ [16] = "Avatar";
+ [17] = "Head";
+ [18] = "Face";
+ [19] = "Gear";
+ [21] = "Badge";
+ [22] = "Group Emblem";
+ [24] = "Animation";
+ [25] = "Arms";
+ [26] = "Legs";
+ [27] = "Torso";
+ [28] = "Right Arm";
+ [29] = "Left Arm";
+ [30] = "Left Leg";
+ [31] = "Right Leg";
+ [32] = "Package";
+ [33] = "YouTube Video";
+ [34] = "Game Pass";
+ [0] = "Product";
+ }
+ return assetTypes[assetType] or ""
+end
+
+function currencyTypeToString(currencyType)
+ if currencyType == Enum.CurrencyType.Tix then
+ return "Tix"
+ else
+ return "R$"
+ end
+end
+
+-- figure out what currency to use based on the currency you can actually sell the item in and what the script specified
+function setCurrencyAmountAndType(priceInRobux, priceInTix)
+ if currentCurrencyType == Enum.CurrencyType.Default or currentCurrencyType == Enum.CurrencyType.Robux then -- sell for default (user doesn't care) or robux
+ if priceInRobux ~= nil and priceInRobux ~= 0 then -- we can sell for robux
+ currentCurrencyAmount = priceInRobux
+ currentCurrencyType = Enum.CurrencyType.Robux
+ else -- have to use tix
+ currentCurrencyAmount = priceInTix
+ currentCurrencyType = Enum.CurrencyType.Tix
+ end
+ elseif currentCurrencyType == Enum.CurrencyType.Tix then -- we want to sell for tix
+ if priceInTix ~= nil and priceInTix ~= 0 then -- we can sell for tix
+ currentCurrencyAmount = priceInTix
+ currentCurrencyType = Enum.CurrencyType.Tix
+ else -- have to use robux
+ currentCurrencyAmount = priceInRobux
+ currentCurrencyType = Enum.CurrencyType.Robux
+ end
+ else
+ return false
+ end
+
+ if currentCurrencyAmount == nil then
+ return false
+ end
+
+ return true
+end
+
+-- will get the player's balance of robux and tix, return in a table
+function getPlayerBalance()
+ local playerBalance = nil
+ local success, errorCode = ypcall(function() playerBalance = game:HttpGetAsync(getSecureApiBaseUrl() .. "currency/balance") end)
+ if not success then
+ print("Get player balance failed because",errorCode)
+ return nil
+ end
+
+ if playerBalance == '' then
+ return nil
+ end
+
+ playerBalance = getRbxUtility().DecodeJSON(playerBalance)
+
+ return playerBalance
+end
+
+-- should open an external default browser window to this url
+function openBuyCurrencyWindow()
+ checkingPlayerFunds = true
+ game:GetService("GuiService"):OpenBrowserWindow(baseUrl .. "Upgrades/Robux.aspx")
+end
+
+function buyEnoughCurrencyForProduct()
+ showPurchasing()
+ Game.MarketplaceService:PromptNativePurchase(Game.Players.LocalPlayer, thirdPartyProductName)
+end
+
+function openBCUpSellWindow()
+ checkingPlayerFunds = true
+ Game:GetService('GuiService'):OpenBrowserWindow(baseUrl .. "Upgrades/BuildersClubMemberships.aspx")
+end
+
+-- set up the gui text at the bottom of the prompt (alerts user to how much money they will have left, or if they need to buy more to buy the item)
+function updateAfterBalanceText(playerBalance, notRightBc, balancePreText)
+ if isFreeItem() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = freeItemBalanceText
+ return true, false
+ end
+
+ local keyWord = nil
+ if currentCurrencyType == Enum.CurrencyType.Robux then
+ keyWord = "robux"
+ elseif currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ if not keyWord then
+ return false
+ end
+
+ local playerBalanceNumber = tonumber(playerBalance[keyWord])
+ if not playerBalanceNumber then
+ return false
+ end
+
+ local afterBalanceNumber = playerBalanceNumber - currentCurrencyAmount
+
+ -- check to see if we have enough of the desired currency to allow a purchase, if not we need to prompt user to buy robux
+ if not notRightBc then
+ if afterBalanceNumber < 0 and keyWord == "robux" then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = ""
+ return true, true
+ elseif afterBalanceNumber < 0 and keyWord == "tickets" then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = "You need " .. tostring(-afterBalanceNumber) .. " " .. currencyTypeToString(currentCurrencyType) .. " more to buy this item."
+ return true, true -- user can't buy more tickets, so we say fail the transaction (maybe instead we can prompt them to trade currency???)
+ end
+ else
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = upgradeBCText
+ return true, false
+ end
+
+ if currentProductIsTixOnly() then
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balancePreText) .. tostring(afterBalanceNumber) .. " " .. currencyTypeToString(currentCurrencyType) .. "."
+ else
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balancePreText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+ end
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+ return true, false
+end
+
+function isFreeItem()
+ -- Apparently free items have 'IsForSale' set to false, but 'IsPublicDomain' set to true
+ -- Example: https://api.roblox.com/marketplace/productinfo?assetid=163811695
+ -- I've tested it, if you take it off the public domain, 'IsPublicDomain' is of course false
+ return currentProductInfo and currentProductInfo["IsPublicDomain"] == true
+end
+---------------------------------------------- End Currency Functions ---------------------------------------------
+
+
+---------------------------------------------- Data Functions -----------------------------------------------------
+
+-- more enum to int fun!
+function membershipTypeToNumber(membership)
+ if membership == Enum.MembershipType.None then
+ return 0
+ elseif membership == Enum.MembershipType.BuildersClub then
+ return 1
+ elseif membership == Enum.MembershipType.TurboBuildersClub then
+ return 2
+ elseif membership == Enum.MembershipType.OutrageousBuildersClub then
+ return 3
+ end
+
+ return -1
+end
+
+function currentProductIsTixOnly()
+ local priceInRobux = currentProductInfo["PriceInRobux"]
+ local priceInTix = currentProductInfo["PriceInTickets"]
+
+ if priceInRobux == nil then return true end
+ priceInRobux = tonumber(priceInRobux)
+ if priceInRobux == nil then return true end
+
+ if priceInTix == nil then return false end
+ priceInTix = tonumber(priceInTix)
+ if priceInTix == nil then return false end
+
+ return (priceInRobux <= 0 and priceInTix > 0)
+end
+
+-- This functions checks to make sure the purchase is even possible, if not it returns false and we don't prompt user (some situations require user feedback when we won't prompt)
+function canPurchaseItem()
+
+ -- first we see if player already owns the asset/get the productinfo
+ local playerOwnsAsset = false
+ local notRightBc = false
+ local descText = nil
+ local getProductSuccess = false
+ local getProductErrorReason = ""
+
+ if purchasingConsumable then
+ getProductSuccess, getProductErrorReason = pcall(function() currentProductInfo = game:GetService("MarketplaceService"):GetProductInfo(currentProductId, Enum.InfoType.Product) end)
+ else
+ getProductSuccess, getProductErrorReason = pcall(function() currentProductInfo = game:GetService("MarketplaceService"):GetProductInfo(currentAssetId) end)
+ end
+
+ if getProductSuccess == false or currentProductInfo == nil then
+ print("could not get product info because",getProductErrorReason)
+ descText = "In-game sales are temporarily disabled. Please try again later."
+ return false, nil, nil, true, descText
+ end
+
+ if not purchasingConsumable then
+ if not currentAssetId then
+ return false
+ end
+ if currentAssetId <= 0 then
+ return false
+ end
+
+ local success, errorCode = ypcall(function() playerOwnsAsset = game:HttpGetAsync(getSecureApiBaseUrl()
+ .. "ownership/hasAsset?userId="
+ .. tostring(game.Players.LocalPlayer.userId)
+ .. "&assetId=" .. tostring(currentAssetId))
+ end)
+
+ if not success then
+ return false
+ end
+
+ if playerOwnsAsset == true or playerOwnsAsset == "true" then
+ descText = "You already own this item."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ -- For public models, as there is still the freeButton, indicating it should be
+ -- available, while this function (canPurchaseItem) doesn't count on free stuff
+ if isFreeItem() then
+ return true
+ end
+
+ purchaseDialog.BodyFrame.AfterBalanceText.Visible = true
+
+ -- next we parse through product info and see if we can purchase
+
+ if type(currentProductInfo) ~= "table" then
+ currentProductInfo = getRbxUtility().DecodeJSON(currentProductInfo)
+ end
+
+ if not currentProductInfo then
+ descText = "Could not get product info. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ if currentProductInfo["IsForSale"] == false and currentProductInfo["IsPublicDomain"] == false then
+ descText = "This item is no longer for sale."
+ return true, nil, nil, true, descText
+ end
+
+ -- now we start talking money, making sure we are going to be able to purchase this
+ if not setCurrencyAmountAndType(tonumber(currentProductInfo["PriceInRobux"]), tonumber(currentProductInfo["PriceInTickets"])) then
+ descText = "We couldn't retrieve the price of the item correctly. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ local playerBalance = getPlayerBalance()
+ if not playerBalance then
+ descText = "Could not retrieve your balance. Please try again later."
+ return true, nil, nil, true, descText
+ end
+
+ if tonumber(currentProductInfo["MinimumMembershipLevel"]) > membershipTypeToNumber(game.Players.LocalPlayer.MembershipType) then
+ notRightBc = true
+ end
+
+ local updatedBalance, insufficientFunds = updateAfterBalanceText(playerBalance, notRightBc, balanceFutureTenseText)
+
+ if notRightBc then
+ purchaseDialog.BodyFrame.AfterBalanceText.Active = true
+ return true, insufficientFunds, notRightBc, false
+ end
+
+ if currentProductInfo["ContentRatingTypeId"] == 1 then
+ if game.Players.LocalPlayer:GetUnder13() then
+ descText = "Your account is under 13 so purchase of this item is not allowed."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ if (currentProductInfo["IsLimited"] == true or currentProductInfo["IsLimitedUnique"] == true) and
+ (currentProductInfo["Remaining"] == "" or currentProductInfo["Remaining"] == 0 or currentProductInfo["Remaining"] == nil) then
+ descText = "All copies of this item have been sold out! Try buying from other users on www.roblox.com."
+ return true, nil, nil, true, descText
+ end
+
+ if not updatedBalance then
+ descText = 'Could not update your balance. Please check back after some time.'
+ return true, nil, nil, true, descText
+ end
+
+ if insufficientFunds then
+ -- if this is a ticket only time and we don't have enough, tell the user to get more tix
+ if currentProductIsTixOnly() then
+ descText = "This item costs more tickets than you currently have! Try trading currency on www.roblox.com to get more tickets."
+ return true, nil, nil, true, descText
+ end
+ end
+
+ -- we use insufficient funds to display a prompt to buy more robux
+ return true, insufficientFunds
+end
+
+---------------------------------------------- End Data Functions -----------------------------------------------------
+
+
+---------------------------------------------- Gui Functions ----------------------------------------------
+function startSpinner()
+ if purchaseDialog.PurchasingFrame.Visible then return end
+ purchaseDialog.PurchasingFrame.Visible = true
+
+ renderSteppedConnection = Game:GetService("RunService").RenderStepped:connect(function()
+ purchaseDialog.PurchasingFrame.PurchasingSpinnerOuter.Rotation = purchaseDialog.PurchasingFrame.PurchasingSpinnerOuter.Rotation + 7
+ purchaseDialog.PurchasingFrame.PurchasingSpinnerInner.Rotation = purchaseDialog.PurchasingFrame.PurchasingSpinnerInner.Rotation - 9
+ end)
+end
+
+function stopSpinner()
+ if renderSteppedConnection then
+ renderSteppedConnection:disconnect()
+ renderSteppedConnection = nil
+ purchaseDialog.PurchasingFrame.Visible = false
+ end
+end
+
+-- next two functions control the "Purchasing..." overlay
+function showPurchasing()
+ startSpinner()
+end
+
+function hidePurchasing()
+ stopSpinner()
+end
+
+-- convenience method to say exactly what buttons should be visible (all others are not!)
+function setButtonsVisible(...)
+ local args = {...}
+ local argCount = select('#', ...)
+
+ local bodyFrameChildren = purchaseDialog.BodyFrame:GetChildren()
+ for i = 1, #bodyFrameChildren do
+ if bodyFrameChildren[i]:IsA("GuiButton") then
+ bodyFrameChildren[i].Visible = false
+ for j = 1, argCount do
+ if bodyFrameChildren[i] == args[j] then
+ bodyFrameChildren[i].Visible = true
+ break
+ end
+ end
+ end
+ end
+end
+
+-- all the gui init. Would be nice if this didn't have to be a script
+function createPurchasePromptGui()
+ purchaseDialog = Instance.new("Frame")
+ purchaseDialog.Name = "PurchaseFrame"
+ purchaseDialog.Size = UDim2.new(0,435,0,292)
+ purchaseDialog.Position = hidePosition
+ purchaseDialog.Active = true
+ purchaseDialog.Visible = false
+ purchaseDialog.BackgroundColor3 = Color3.new(225/255,225/255,225/255)
+ purchaseDialog.BorderSizePixel = 0
+ purchaseDialog.ZIndex = 8
+ purchaseDialog.Parent = game.CoreGui.RobloxGui
+
+ local bodyFrame = Instance.new("Frame")
+ bodyFrame.Name = "BodyFrame"
+ bodyFrame.Active = true
+ bodyFrame.Size = UDim2.new(1,-10,1,-55)
+ bodyFrame.Position = UDim2.new(0,5,0,50)
+ bodyFrame.BackgroundColor3 = Color3.new(1, 1, 1)
+ bodyFrame.BorderSizePixel = 0
+ bodyFrame.ZIndex = 8
+ bodyFrame.Parent = purchaseDialog
+
+ local titleLabel = createTextObject("TitleLabel", "Buy Item", "TextLabel", Enum.FontSize.Size36)
+ titleLabel.Active = true
+ titleLabel.Font = Enum.Font.SourceSansBold
+ titleLabel.TextColor3 = Color3.new(54/255,54/255,54/255)
+ titleLabel.ZIndex = 8
+ titleLabel.Size = UDim2.new(1,0,0,50)
+ titleLabel.Parent = purchaseDialog
+
+ local distanceBetweenButtons = 20
+
+ local cancelButton = createImageButton("CancelButton")
+ cancelButton.Position = UDim2.new(0.5,(distanceBetweenButtons/2),1,-100)
+ cancelButton.BorderColor3 = Color3.new(86/255,86/255,86/255)
+ cancelButton.Parent = bodyFrame
+ cancelButton.Modal = true
+ cancelButton.ZIndex = 8
+ cancelButton.Image = cancelButtonImageUrl
+ cancelButton.MouseButton1Up:connect(function( )
+ cancelButton.Image = cancelButtonImageUrl
+ end)
+ cancelButton.MouseLeave:connect(function( )
+ cancelButton.Image = cancelButtonImageUrl
+ end)
+ cancelButton.MouseButton1Click:connect(doDeclinePurchase)
+
+ local cancelText = createTextObject("CancelText","Cancel","TextLabel",Enum.FontSize.Size24)
+ cancelText.TextColor3 = Color3.new(1,1,1)
+ cancelText.Size = UDim2.new(1,0,1,0)
+ cancelText.ZIndex = 8
+ cancelText.Parent = cancelButton
+
+ local cancelHoverFrame = Instance.new("Frame")
+ cancelHoverFrame.Name = "HoverFrame"
+ cancelHoverFrame.Size = UDim2.new(1,0,1,0)
+ cancelHoverFrame.BackgroundColor3 = Color3.new(1,1,1)
+ cancelHoverFrame.BackgroundTransparency = 0.7
+ cancelHoverFrame.BorderSizePixel = 0
+ cancelHoverFrame.Visible = false
+ cancelHoverFrame.ZIndex = 8
+ cancelHoverFrame.Parent = cancelButton
+ cancelButton.MouseEnter:connect(function()
+ cancelHoverFrame.Visible = true
+ end)
+ cancelButton.MouseLeave:connect(function( )
+ cancelHoverFrame.Visible = false
+ end)
+ cancelButton.MouseButton1Click:connect(function( )
+ cancelHoverFrame.Visible = false
+ end)
+
+ local buyButton = createImageButton("BuyButton")
+ buyButton.Position = UDim2.new(0.5,-117-(distanceBetweenButtons/2),1,-100)
+ buyButton.BorderColor3 = Color3.new(0,112/255,1/255)
+ buyButton.Image = buyImageUrl
+ buyButton.ZIndex = 8
+ buyButton.Parent = bodyFrame
+
+ local buyText = createTextObject("BuyText","Buy Now","TextLabel",Enum.FontSize.Size24)
+ buyText.ZIndex = 8
+ buyText.TextColor3 = Color3.new(1,1,1)
+ buyText.Size = UDim2.new(1,0,1,0)
+ buyText.Parent = buyButton
+
+ local buyHoverFrame = cancelHoverFrame:Clone()
+ buyButton.MouseEnter:connect(function()
+ buyHoverFrame.Visible = true
+ end)
+ buyButton.MouseLeave:connect(function( )
+ buyHoverFrame.Visible = false
+ end)
+ buyButton.MouseButton1Click:connect(function( )
+ buyHoverFrame.Visible = false
+ end)
+ buyHoverFrame.Parent = buyButton
+
+ local buyDisabledButton = buyButton:Clone()
+ buyDisabledButton.Name = "BuyDisabledButton"
+ buyDisabledButton.AutoButtonColor = false
+ buyDisabledButton.Visible = false
+ buyDisabledButton.Active = false
+ buyDisabledButton.Parent = bodyFrame
+
+ local buyRobux = buyButton:Clone()
+ buyRobux.Name = "BuyRobuxButton"
+ buyRobux.AutoButtonColor = false
+ buyRobux.Visible = false
+ buyRobux.ZIndex = 8
+
+ if canUseNewRobuxToProductFlow() then
+ buyRobux.BuyText.Text = "Buy"
+ else
+ buyRobux.BuyText.Text = "Buy R$"
+ end
+
+ buyRobux.MouseEnter:connect(function()
+ buyRobux.HoverFrame.Visible = true
+ end)
+ buyRobux.MouseLeave:connect(function( )
+ buyRobux.HoverFrame.Visible = false
+ end)
+ buyRobux.MouseButton1Click:connect(function( )
+ buyRobux.HoverFrame.Visible = false
+
+ if canUseNewRobuxToProductFlow() then
+ buyEnoughCurrencyForProduct()
+ else
+ openBuyCurrencyWindow()
+ end
+ end)
+ buyRobux.Parent = bodyFrame
+
+ local buyBC = buyRobux:Clone()
+ buyBC.Name = "BuyBCButton"
+ buyBC.BuyText.Text = "Buy Builders Club"
+ buyBC.MouseEnter:connect(function()
+ buyBC.HoverFrame.Visible = true
+ end)
+ buyBC.MouseLeave:connect(function( )
+ buyBC.HoverFrame.Visible = false
+ end)
+ buyBC.MouseButton1Click:connect(function( )
+ buyBC.HoverFrame.Visible = false
+ openBCUpSellWindow()
+ end)
+ buyBC.Parent = bodyFrame
+
+ local freeButton = buyButton:Clone()
+ freeButton.BuyText.Text = "Take Free"
+ freeButton.BackgroundTransparency = 1
+ freeButton.Name = "FreeButton"
+ freeButton.Visible = false
+ freeButton.MouseEnter:connect(function()
+ freeButton.HoverFrame.Visible = true
+ end)
+ freeButton.MouseButton1Click:connect(function( )
+ freeButton.HoverFrame.Visible = false
+ end)
+ freeButton.MouseLeave:connect(function( )
+ freeButton.HoverFrame.Visible = false
+ end)
+ freeButton.Parent = bodyFrame
+
+ local okButton = buyButton:Clone()
+ okButton.BuyText.Text = "Ok"
+ okButton.Name = "OkButton"
+ okButton.Visible = false
+ okButton.Position = UDim2.new(0.5,-okButton.Size.X.Offset/2,1,-100)
+ okButton.Modal = true
+ okButton.MouseEnter:connect(function()
+ okButton.HoverFrame.Visible = true
+ end)
+ okButton.MouseButton1Click:connect(function( )
+ okButton.HoverFrame.Visible = false
+ signalPromptEnded(false)
+ end)
+ okButton.MouseLeave:connect(function( )
+ okButton.HoverFrame.Visible = false
+ end)
+ okButton.Parent = bodyFrame
+
+ local okPurchasedButton = okButton:Clone()
+ okPurchasedButton.Name = "OkPurchasedButton"
+ okPurchasedButton.MouseEnter:connect(function()
+ okPurchasedButton.HoverFrame.Visible = true
+ end)
+ okPurchasedButton.MouseLeave:connect(function( )
+ okPurchasedButton.HoverFrame.Visible = false
+ end)
+ okPurchasedButton.MouseButton1Click:connect(function()
+ okPurchasedButton.HoverFrame.Visible = false
+ if purchasingConsumable then
+ userPurchaseProductActionsEnded(true)
+ else
+ signalPromptEnded(true)
+ end
+ end)
+ okPurchasedButton.Parent = bodyFrame
+
+ buyButton.MouseButton1Click:connect(function() doAcceptPurchase(Enum.CurrencyType.Robux) end)
+ freeButton.MouseButton1Click:connect(function() doAcceptPurchase(false) end)
+
+ local itemPreview = Instance.new("ImageLabel")
+ itemPreview.Name = "ItemPreview"
+ itemPreview.BackgroundTransparency = 1
+ itemPreview.BorderSizePixel = 0
+ itemPreview.Position = UDim2.new(0,20,0,20)
+ itemPreview.Size = UDim2.new(0,100,0,100)
+ itemPreview.ZIndex = 9
+ itemPreview.Parent = bodyFrame
+
+ local itemDescription = createTextObject("ItemDescription","","TextLabel",Enum.FontSize.Size18)
+ itemDescription.TextXAlignment = Enum.TextXAlignment.Left
+ itemDescription.Position = UDim2.new(0.5, -70, 0, 10)
+ itemDescription.Size = UDim2.new(0,245,0,115)
+ itemDescription.TextColor3 = Color3.new(54/255,54/255,54/255)
+ itemDescription.ZIndex = 8
+ itemDescription.Parent = bodyFrame
+
+ local afterBalanceText = createTextObject("AfterBalanceText","","TextLabel",Enum.FontSize.Size14)
+ afterBalanceText.BackgroundTransparency = 1
+ afterBalanceText.TextColor3 = Color3.new(102/255,102/255,102/255)
+ afterBalanceText.Position = UDim2.new(0,5,1,-33)
+ afterBalanceText.Size = UDim2.new(1,-10,0,28)
+ afterBalanceText.ZIndex = 8
+ afterBalanceText.Parent = bodyFrame
+
+ local purchasingFrame = Instance.new("Frame")
+ purchasingFrame.Name = "PurchasingFrame"
+ purchasingFrame.Size = UDim2.new(1,0,1,0)
+ purchasingFrame.BackgroundColor3 = Color3.new(0,0,0)
+ purchasingFrame.BackgroundTransparency = 0.05
+ purchasingFrame.BorderSizePixel = 0
+ purchasingFrame.ZIndex = 9
+ purchasingFrame.Visible = false
+ purchasingFrame.Active = true
+ purchasingFrame.Parent = purchaseDialog
+
+ local purchasingLabel = createTextObject("PurchasingLabel","Purchasing","TextLabel",Enum.FontSize.Size48)
+ purchasingLabel.Size = UDim2.new(1,0,1,0)
+ purchasingLabel.Position = UDim2.new(0,0,0,-24)
+ purchasingLabel.ZIndex = 10
+ purchasingLabel.Parent = purchasingFrame
+
+ local purchasingSpinner = Instance.new("ImageLabel")
+ purchasingSpinner.Name = "PurchasingSpinnerOuter"
+ purchasingSpinner.Image = loadingImage
+ purchasingSpinner.BackgroundTransparency = 1
+ purchasingSpinner.BorderSizePixel = 0
+ purchasingSpinner.Size = UDim2.new(0,64,0,64)
+ purchasingSpinner.Position = UDim2.new(0.5,-32,0.5,32)
+ purchasingSpinner.ZIndex = 10
+ purchasingSpinner.Parent = purchasingFrame
+
+ local purchasingSpinnerInner = purchasingSpinner:Clone()
+ purchasingSpinnerInner.BackgroundTransparency = 1
+ purchasingSpinnerInner.Name = "PurchasingSpinnerInner"
+ purchasingSpinnerInner.Size = UDim2.new(0,32,0,32)
+ purchasingSpinnerInner.Position = UDim2.new(0.5,-16,0.5,48)
+ purchasingSpinnerInner.Parent = purchasingFrame
+end
+
+-- next 2 functions are convenienvce creation functions for guis
+function createTextObject(name, text, type, size)
+ local textLabel = Instance.new(type)
+ textLabel.Font = Enum.Font.SourceSans
+ textLabel.TextColor3 = Color3.new(217/255, 217/255, 217/255)
+ textLabel.TextWrapped = true
+ textLabel.Name = name
+ textLabel.Text = text
+ textLabel.BackgroundTransparency = 1
+ textLabel.BorderSizePixel = 0
+ textLabel.FontSize = size
+
+ return textLabel
+end
+
+function createImageButton(name)
+ local imageButton = Instance.new("ImageButton")
+ imageButton.Size = UDim2.new(0,117,0,60)
+ imageButton.Name = name
+ return imageButton
+end
+
+function setHeaderText(text)
+ purchaseDialog.TitleLabel.Text = text
+end
+
+function doPurchasePrompt(player, assetId, equipIfPurchased, currencyType, productId)
+ if not purchaseDialog then
+ createPurchasePromptGui()
+ end
+
+ if player == game.Players.LocalPlayer then
+ if currentlyPrompting then return end
+
+ currentlyPrompting = true
+
+ currentAssetId = assetId
+ currentProductId = productId
+ currentCurrencyType = currencyType
+ currentEquipOnPurchase = equipIfPurchased
+
+ purchasingConsumable = (currentProductId ~= nil)
+
+ showPurchasePrompt()
+ end
+end
+
+function userPurchaseProductActionsEnded(userIsClosingDialog)
+ checkingPlayerFunds = false
+
+ if userIsClosingDialog then
+ closePurchasePrompt()
+ if currentServerResponseTable then
+ local isPurchased = false
+ if tostring(currentServerResponseTable["isValid"]):lower() == "true" then
+ isPurchased = true
+ end
+
+ Game:GetService("MarketplaceService"):SignalPromptProductPurchaseFinished(tonumber(currentServerResponseTable["playerId"]), tonumber(currentServerResponseTable["productId"]), isPurchased)
+ end
+ removeCurrentPurchaseInfo()
+ else
+ if tostring(currentServerResponseTable["isValid"]):lower() == "true" then
+ local newPurchasedSucceededText = string.gsub( purchaseSucceededText,"itemName", tostring(currentProductInfo["Name"]))
+ purchaseDialog.BodyFrame.ItemDescription.Text = newPurchasedSucceededText
+
+ local playerBalance = getPlayerBalance()
+ local keyWord = "robux"
+ if currentCurrencyType == Enum.CurrencyType.Tix then
+ keyWord = "tickets"
+ end
+
+ local afterBalanceNumber = playerBalance[keyWord]
+ purchaseDialog.BodyFrame.AfterBalanceText.Text = tostring(balanceCurrentTenseText) .. currencyTypeToString(currentCurrencyType) .. tostring(afterBalanceNumber) .. "."
+
+ setButtonsVisible(purchaseDialog.BodyFrame.OkPurchasedButton)
+ hidePurchasing()
+ else
+ purchaseFailed()
+ end
+ end
+end
+
+function doProcessServerPurchaseResponse(serverResponseTable)
+ if not serverResponseTable then
+ purchaseFailed()
+ return
+ end
+
+ if serverResponseTable["playerId"] and tonumber(serverResponseTable["playerId"]) == game.Players.LocalPlayer.userId then
+ currentServerResponseTable = serverResponseTable
+ userPurchaseProductActionsEnded(false)
+ end
+end
+
+---------------------------------------------- End Gui Functions ----------------------------------------------
+
+
+---------------------------------------------- Script Event start/initialization ----------------------------------------------
+preloadAssets()
+
+game:GetService("MarketplaceService").PromptProductPurchaseRequested:connect(function(player, productId, equipIfPurchased, currencyType)
+ doPurchasePrompt(player, nil, equipIfPurchased, currencyType, productId)
+end)
+
+Game:GetService("MarketplaceService").PromptPurchaseRequested:connect(function(player, assetId, equipIfPurchased, currencyType)
+ doPurchasePrompt(player, assetId, equipIfPurchased, currencyType, nil)
+end)
+
+Game:GetService("MarketplaceService").ServerPurchaseVerification:connect(function(serverResponseTable)
+ doProcessServerPurchaseResponse(serverResponseTable)
+end)
+
+Game:GetService("GuiService").BrowserWindowClosed:connect(checkIfCanPurchase)
+
+if not canUseNewRobuxToProductFlow() then return end
+
+Game.MarketplaceService.NativePurchaseFinished:connect(function(player, productId, wasPurchased)
+ if wasPurchased then
+
+ -- try for 20 seconds to see if we get the funds if we purchased something
+ local retriesLeft = 40
+ local canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ while canPurchase and insufficientFunds and retriesLeft > 0 do
+ wait(0.5)
+ canPurchase, insufficientFunds, notRightBC = canPurchaseItem()
+ retriesLeft = retriesLeft - 1
+ end
+
+ if canPurchase and not insufficientFunds and not notRightBC then
+ doAcceptPurchase(Enum.CurrencyType.Robux)
+ else
+ purchaseFailed("didNotBuyRobux")
+ end
+ else
+ purchaseFailed("didNotBuyRobux")
+ end
+end)
diff --git a/asset/13 b/asset/13
new file mode 100644
index 0000000..f0f4f49
--- /dev/null
+++ b/asset/13
@@ -0,0 +1,317 @@
+--rbxassetid%13%
+--[[
+ This script controls the gui the player sees in regards to his or her health.
+ Can be turned with Game.StarterGui:SetCoreGuiEnabled(Enum.CoreGuiType.Health,false)
+ Copyright ROBLOX 2014. Written by Ben Tkacheff.
+--]]
+
+---------------------------------------------------------------------
+-- Initialize/Variables
+while not Game do
+ wait(1/60)
+end
+while not Game.Players do
+ wait(1/60)
+end
+
+local useCoreHealthBar = false
+local success = pcall(function() useCoreHealthBar = Game.Players:GetUseCoreScriptHealthBar() end)
+if not success or not useCoreHealthBar then
+ return
+end
+
+local currentHumanoid = nil
+
+local HealthGui = nil
+local lastHealth = 100
+local HealthPercentageForOverlay = 5
+local maxBarTweenTime = 0.3
+local greenColor = Color3.new(0.2, 1, 0.2)
+local redColor = Color3.new(1, 0.2, 0.2)
+local yellowColor = Color3.new(1, 1, 0.2)
+
+local guiEnabled = false
+local healthChangedConnection = nil
+local humanoidDiedConnection = nil
+local characterAddedConnection = nil
+
+local greenBarImage = "rbxasset://textures/ui/Health-BKG-Center.png"
+local greenBarImageLeft = "rbxasset://textures/ui/Health-BKG-Left-Cap.png"
+local greenBarImageRight = "rbxasset://textures/ui/Health-BKG-Right-Cap.png"
+local hurtOverlayImage = "http://www.roblox.com/asset/?id=34854607"
+
+Game:GetService("ContentProvider"):Preload(greenBarImage)
+Game:GetService("ContentProvider"):Preload(hurtOverlayImage)
+
+while not Game.Players.LocalPlayer do
+ wait(1/60)
+end
+
+---------------------------------------------------------------------
+-- Functions
+
+local capHeight = 15
+local capWidth = 7
+
+function CreateGui()
+ if HealthGui and #HealthGui:GetChildren() > 0 then
+ HealthGui.Parent = Game.CoreGui.RobloxGui
+ return
+ end
+
+ local hurtOverlay = Instance.new("ImageLabel")
+ hurtOverlay.Name = "HurtOverlay"
+ hurtOverlay.BackgroundTransparency = 1
+ hurtOverlay.Image = hurtOverlayImage
+ hurtOverlay.Position = UDim2.new(-10,0,-10,0)
+ hurtOverlay.Size = UDim2.new(20,0,20,0)
+ hurtOverlay.Visible = false
+ hurtOverlay.Parent = HealthGui
+
+ local healthFrame = Instance.new("Frame")
+ healthFrame.Name = "HealthFrame"
+ healthFrame.BackgroundTransparency = 1
+ healthFrame.BackgroundColor3 = Color3.new(1,1,1)
+ healthFrame.BorderColor3 = Color3.new(0,0,0)
+ healthFrame.BorderSizePixel = 0
+ healthFrame.Position = UDim2.new(0.5,-85,1,-20)
+ healthFrame.Size = UDim2.new(0,170,0,capHeight)
+ healthFrame.Parent = HealthGui
+
+
+ local healthBarBackCenter = Instance.new("ImageLabel")
+ healthBarBackCenter.Name = "healthBarBackCenter"
+ healthBarBackCenter.BackgroundTransparency = 1
+ healthBarBackCenter.Image = greenBarImage
+ healthBarBackCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBarBackCenter.Position = UDim2.new(0,capWidth,0,0)
+ healthBarBackCenter.Parent = healthFrame
+ healthBarBackCenter.ImageColor3 = Color3.new(1,1,1)
+
+ local healthBarBackLeft = Instance.new("ImageLabel")
+ healthBarBackLeft.Name = "healthBarBackLeft"
+ healthBarBackLeft.BackgroundTransparency = 1
+ healthBarBackLeft.Image = greenBarImageLeft
+ healthBarBackLeft.Size = UDim2.new(0,capWidth,1,0)
+ healthBarBackLeft.Position = UDim2.new(0,0,0,0)
+ healthBarBackLeft.Parent = healthFrame
+ healthBarBackLeft.ImageColor3 = Color3.new(1,1,1)
+
+ local healthBarBackRight = Instance.new("ImageLabel")
+ healthBarBackRight.Name = "healthBarBackRight"
+ healthBarBackRight.BackgroundTransparency = 1
+ healthBarBackRight.Image = greenBarImageRight
+ healthBarBackRight.Size = UDim2.new(0,capWidth,1,0)
+ healthBarBackRight.Position = UDim2.new(1,-capWidth,0,0)
+ healthBarBackRight.Parent = healthFrame
+ healthBarBackRight.ImageColor3 = Color3.new(1,1,1)
+
+
+ local healthBar = Instance.new("Frame")
+ healthBar.Name = "HealthBar"
+ healthBar.BackgroundTransparency = 1
+ healthBar.BackgroundColor3 = Color3.new(1,1,1)
+ healthBar.BorderColor3 = Color3.new(0,0,0)
+ healthBar.BorderSizePixel = 0
+ healthBar.ClipsDescendants = true
+ healthBar.Position = UDim2.new(0, 0, 0, 0)
+ healthBar.Size = UDim2.new(1,0,1,0)
+ healthBar.Parent = healthFrame
+
+
+ local healthBarCenter = Instance.new("ImageLabel")
+ healthBarCenter.Name = "healthBarCenter"
+ healthBarCenter.BackgroundTransparency = 1
+ healthBarCenter.Image = greenBarImage
+ healthBarCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBarCenter.Position = UDim2.new(0,capWidth,0,0)
+ healthBarCenter.Parent = healthBar
+ healthBarCenter.ImageColor3 = greenColor
+
+ local healthBarLeft = Instance.new("ImageLabel")
+ healthBarLeft.Name = "healthBarLeft"
+ healthBarLeft.BackgroundTransparency = 1
+ healthBarLeft.Image = greenBarImageLeft
+ healthBarLeft.Size = UDim2.new(0,capWidth,1,0)
+ healthBarLeft.Position = UDim2.new(0,0,0,0)
+ healthBarLeft.Parent = healthBar
+ healthBarLeft.ImageColor3 = greenColor
+
+ local healthBarRight = Instance.new("ImageLabel")
+ healthBarRight.Name = "healthBarRight"
+ healthBarRight.BackgroundTransparency = 1
+ healthBarRight.Image = greenBarImageRight
+ healthBarRight.Size = UDim2.new(0,capWidth,1,0)
+ healthBarRight.Position = UDim2.new(1,-capWidth,0,0)
+ healthBarRight.Parent = healthBar
+ healthBarRight.ImageColor3 = greenColor
+
+ HealthGui.Parent = Game.CoreGui.RobloxGui
+end
+
+function UpdateGui(health)
+ if not HealthGui then return end
+
+ local healthFrame = HealthGui:FindFirstChild("HealthFrame")
+ if not healthFrame then return end
+
+ local healthBar = healthFrame:FindFirstChild("HealthBar")
+ if not healthBar then return end
+
+ -- If more than 1/4 health, bar = green. Else, bar = red.
+ local percentHealth = (health/currentHumanoid.MaxHealth)
+ if percentHealth ~= percentHealth then
+ percentHealth = 1
+ healthBar.healthBarCenter.ImageColor3 = yellowColor
+ healthBar.healthBarRight.ImageColor3 = yellowColor
+ healthBar.healthBarLeft.ImageColor3 = yellowColor
+ elseif percentHealth > 0.25 then
+ healthBar.healthBarCenter.ImageColor3 = greenColor
+ healthBar.healthBarRight.ImageColor3 = greenColor
+ healthBar.healthBarLeft.ImageColor3 = greenColor
+ else
+ healthBar.healthBarCenter.ImageColor3 = redColor
+ healthBar.healthBarRight.ImageColor3 = redColor
+ healthBar.healthBarLeft.ImageColor3 = redColor
+ end
+
+ local width = (health / currentHumanoid.MaxHealth)
+ width = math.max(math.min(width,1),0) -- make sure width is between 0 and 1
+ if width ~= width then width = 1 end
+
+ local healthDelta = lastHealth - health
+ lastHealth = health
+
+ local percentOfTotalHealth = math.abs(healthDelta/currentHumanoid.MaxHealth)
+ percentOfTotalHealth = math.max(math.min(percentOfTotalHealth,1),0) -- make sure percentOfTotalHealth is between 0 and 1
+ if percentOfTotalHealth ~= percentOfTotalHealth then percentOfTotalHealth = 1 end
+
+ local newHealthSize = UDim2.new(width,0,1,0)
+
+ healthBar.Size = newHealthSize
+
+ local sizeX = healthBar.AbsoluteSize.X
+ if sizeX < capWidth then
+ healthBar.healthBarCenter.Visible = false
+ healthBar.healthBarRight.Visible = false
+ elseif sizeX < (2*capWidth + 1) then
+ healthBar.healthBarCenter.Visible = true
+ healthBar.healthBarCenter.Size = UDim2.new(0,sizeX - capWidth,1,0)
+ healthBar.healthBarRight.Visible = false
+ else
+ healthBar.healthBarCenter.Visible = true
+ healthBar.healthBarCenter.Size = UDim2.new(1,-capWidth*2,1,0)
+ healthBar.healthBarRight.Visible = true
+ end
+
+ local thresholdForHurtOverlay = currentHumanoid.MaxHealth * (HealthPercentageForOverlay/100)
+
+ if healthDelta >= thresholdForHurtOverlay then
+ AnimateHurtOverlay()
+ end
+
+end
+
+function AnimateHurtOverlay()
+ if not HealthGui then return end
+
+ local overlay = HealthGui:FindFirstChild("HurtOverlay")
+ if not overlay then return end
+
+ local newSize = UDim2.new(20, 0, 20, 0)
+ local newPos = UDim2.new(-10, 0, -10, 0)
+
+ if overlay:IsDescendantOf(Game) then
+ -- stop any tweens on overlay
+ overlay:TweenSizeAndPosition(newSize,newPos,Enum.EasingDirection.Out,Enum.EasingStyle.Linear,0,true,function()
+
+ -- show the gui
+ overlay.Size = UDim2.new(1,0,1,0)
+ overlay.Position = UDim2.new(0,0,0,0)
+ overlay.Visible = true
+
+ -- now tween the hide
+ if overlay:IsDescendantOf(Game) then
+ overlay:TweenSizeAndPosition(newSize,newPos,Enum.EasingDirection.Out,Enum.EasingStyle.Quad,10,false,function()
+ overlay.Visible = false
+ end)
+ else
+ overlay.Size = newSize
+ overlay.Position = newPos
+ end
+ end)
+ else
+ overlay.Size = newSize
+ overlay.Position = newPos
+ end
+
+end
+
+function humanoidDied()
+ UpdateGui(0)
+end
+
+function disconnectPlayerConnections()
+ if characterAddedConnection then characterAddedConnection:disconnect() end
+ if humanoidDiedConnection then humanoidDiedConnection:disconnect() end
+ if healthChangedConnection then healthChangedConnection:disconnect() end
+end
+
+function newPlayerCharacter()
+ disconnectPlayerConnections()
+ startGui()
+end
+
+function startGui()
+ characterAddedConnection = Game.Players.LocalPlayer.CharacterAdded:connect(newPlayerCharacter)
+
+ local character = Game.Players.LocalPlayer.Character
+ if not character then
+ return
+ end
+
+ currentHumanoid = character:WaitForChild("Humanoid")
+ if not currentHumanoid then
+ return
+ end
+
+ if not Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health) then
+ return
+ end
+
+ healthChangedConnection = currentHumanoid.HealthChanged:connect(UpdateGui)
+ humanoidDiedConnection = currentHumanoid.Died:connect(humanoidDied)
+ UpdateGui(currentHumanoid.Health)
+
+ CreateGui()
+end
+
+
+
+---------------------------------------------------------------------
+-- Start Script
+
+HealthGui = Instance.new("Frame")
+HealthGui.Name = "HealthGui"
+HealthGui.BackgroundTransparency = 1
+HealthGui.Size = UDim2.new(1,0,1,0)
+
+Game.StarterGui.CoreGuiChangedSignal:connect(function(coreGuiType,enabled)
+ if coreGuiType == Enum.CoreGuiType.Health or coreGuiType == Enum.CoreGuiType.All then
+ if guiEnabled and not enabled then
+ if HealthGui then
+ HealthGui.Parent = nil
+ end
+ disconnectPlayerConnections()
+ elseif not guiEnabled and enabled then
+ startGui()
+ end
+
+ guiEnabled = enabled
+ end
+end)
+
+if Game.StarterGui:GetCoreGuiEnabled(Enum.CoreGuiType.Health) then
+ guiEnabled = true
+ startGui()
+end
\ No newline at end of file
diff --git a/asset/14 b/asset/14
new file mode 100644
index 0000000..ac2c46f
--- /dev/null
+++ b/asset/14
@@ -0,0 +1,3056 @@
+--rbxassetid%14%
+--------------------
+-- Super Util
+--------------------
+
+local ADMINS =
+{
+ MAO = 1,
+ adamintygum = 1,
+ androidtest = 1,
+ robloxfrenchie = 1,
+ jackssmirkingrevenge = 1,
+ mandaari = 1,
+ vaiobot = 1,
+ goddessnoob = 1,
+ thr33pakshak3r = 1,
+ effward = 1,
+ blockhaak = 1,
+ drewbda = 1,
+ triptych999 = 1,
+ tone = 1,
+ fasterbuilder19 = 1,
+ zeuxcg = 1,
+ concol2 = 1,
+ reesemcblox = 1,
+ jeditkacheff = 'http://www.roblox.com/asset/?id=134032333',
+ chiefjustus = 1,
+ ellissar = 1,
+ geekndestroy = 1,
+ noob007 = 1,
+ limon = 1,
+ hawkington = 1,
+ tabemono = 1,
+ autoconfig = 1,
+ brighteyes = 1,
+ monsterinc3d = 1,
+ isolatedevent = 1,
+ countonconnor = 1,
+ scubasomething = 1,
+ onlytwentycharacters = 1,
+ lordrugdumph = 1,
+ bellavour = 1,
+ ['david.baszucki'] = 1,
+ ibanez2189 = 1,
+ convexhero = 1,
+ sorcus = 'http://www.roblox.com/asset/?id=113059239',
+ deeana00 = 1,
+ thelorekt = 1,
+ ['mse6'] = 1,
+ corgiparade = 1,
+ varia = 1,
+ ['4runningwolves'] = 1,
+ pulmoesflor = 1,
+ olive71 = 1,
+ groundcontroll2 = 1,
+ gurukrish = 1,
+ countvelcro = 1,
+ iltalumi = 1,
+ juanjuan23 = 1,
+ ostrichsized = 1,
+ jackintheblox = 1,
+ slingshotjunkie = 1,
+ gordonrox24 = 1,
+ sharpnine = 1,
+ motornerve = 1,
+ watchmedogood = 1,
+ jmargh = 1,
+ jaykorean = 1,
+ foyle = 1,
+ majortom4321 = 1,
+ shedletsky = 'http://www.roblox.com/asset/?id=105897927',
+ supernovacaine = 1,
+ ffjosh = 1,
+ sickenedmonkey = 1,
+ doughtless = 1,
+ kbux = 1,
+ totallynothere = 1,
+ erzastar = 1,
+ keith = 1,
+ chro = 1,
+ solarcrane = 1,
+ glorioussalt = 1,
+ imightbelying = 1,
+ uristmcsparks = 1,
+ itolauren = 1,
+ malcomso = 1,
+ heyseptember = 1,
+ stickmasterluke = 1,
+ windlight13 = 1,
+ stravant = 1,
+ imaginationsensation = 1,
+ ['matt.dusek'] = 1,
+ crimmsonghost = 1,
+ mcrtest = 1,
+ maxvee = 1,
+ coatp0cketninja = 1,
+ screenme = 1,
+ b1tsh1ft = 1,
+ convexrumbler = 1,
+ mpliner476 = 1,
+ totbl = 1,
+ aquabot8 = 1,
+ grossinger = 1,
+ merely = 1,
+ cdakkar = 1,
+ siekiera = 1,
+ robloxkidsaccount = 1,
+ flotsamthespork = 1,
+ soggoth = 1,
+ phil = 1,
+ orcasparkles = 1,
+ skullgoblin = 1,
+ rickrosstheb0ss = 1,
+ argonpirate = 1,
+ nobledragon = 1,
+ squidcod = 1,
+ raeglyn = 1,
+ xerolayne = 1,
+ robloxsai = 'http://www.roblox.com/asset/?id=161078086',
+ briarroze = 1,
+ hawkeyebandit = 1,
+ dapperbuffalo = 1,
+ vukota = 1,
+ swiftstone = 1,
+ gemlocker = 1,
+ tarabyte = 1,
+ timobius = 1,
+ tobotrobot = 1,
+ foster008 = 1,
+ twberg = 1,
+ darthvaden = 1,
+ khanovich = 1,
+ codewriter = 1,
+ olefto = 1,
+ vladthefirst = 1,
+ phaedre = 1,
+ gorroth = 1,
+ jynj1984 = 1,
+ roboyz = 1,
+ zodiaczak = 1,
+}
+
+
+local Images = {
+ bottomDark = '94691904',
+ bottomLight = '94691940',
+ midDark = '94691980',
+ midLight = '94692025',
+ LargeDark = '96098866',
+ LargeLight = '96098920',
+ LargeHeader = '96097470',
+ NormalHeader = '94692054',
+ LargeBottom = '96397271',
+ NormalBottom = '94754966',
+ DarkBluePopupMid = '97114905',
+ LightBluePopupMid = '97114905',
+ DarkPopupMid = '97112126',
+ LightPopupMid = '97109338',
+ DarkBluePopupTop = '97114838',
+ DarkBluePopupBottom = '97114758',
+ DarkPopupBottom = '100869219',
+ LightPopupBottom = '97109175',
+}
+
+local BASE_TWEEN = .25
+
+local MOUSE_HOLD_TIME = .15
+local MOUSE_DRAG_DISTANCE = 15
+
+local BACKGROUND_TRANSPARENCY = 0.7
+--[[
+ Generic object Create function, which I am using to create Gui's
+ Thanks to Stravant!
+--]]
+local Obj = {}
+function Obj.Create(guiType)
+ return function(data)
+ local obj = Instance.new(guiType)
+ for k, v in pairs(data) do
+ if type(k) == 'number' then
+ v.Parent = obj
+ else
+ obj[k] = v
+ end
+ end
+ return obj
+ end
+end
+
+--[[
+ makes a full sized background for a guiobject
+ @Args:
+ imgName asset name of image to fill background
+ @Return: background gui object
+--]]
+function MakeBackgroundGuiObjOld(imgName)
+ return Obj.Create'ImageLabel'
+ {
+ Name = 'Background',
+ BackgroundTransparency = 1,
+ Image = imgName,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ }
+end
+
+function MakeBackgroundGuiObj(imgName)
+ return Obj.Create'Frame'
+ {
+ Name = 'Background',
+ BackgroundTransparency = BACKGROUND_TRANSPARENCY,
+ BackgroundColor3 = Color3.new(0,0,0),
+ BorderSizePixel = 0,
+ Position = UDim2.new(0, 1, 0, 1),
+ Size = UDim2.new(1,-2,1,-2),
+ }
+end
+
+
+--[[ turns 255 integer color value to a color3 --]]
+function Color3I(r,g,b)
+ return Color3.new(r/255,g/255,b/255)
+end
+
+--[[
+ Gets correct icon for builder's club status to display by name
+ @Args:
+ membershipType Enum of membership status
+ @Return: string of image asset
+--]]
+function getMembershipTypeIcon(membershipType,playerName)
+ if ADMINS[string.lower(playerName)]~=nil then
+ if ADMINS[string.lower(playerName)] == 1 then
+ return "http://www.roblox.com/asset/?id=99727663"
+ else
+ return ADMINS[string.lower(playerName)]
+ end
+ elseif membershipType == Enum.MembershipType.None then
+ return ""
+ elseif membershipType == Enum.MembershipType.BuildersClub then
+ return "rbxasset://textures/ui/TinyBcIcon.png"
+ elseif membershipType == Enum.MembershipType.TurboBuildersClub then
+ return "rbxasset://textures/ui/TinyTbcIcon.png"
+ elseif membershipType == Enum.MembershipType.OutrageousBuildersClub then
+ return "rbxasset://textures/ui/TinyObcIcon.png"
+ else
+ error("Unknown membershipType" .. membershipType)
+ end
+end
+
+local function getFriendStatusIcon(friendStatus)
+ if friendStatus == Enum.FriendStatus.Unknown or friendStatus == Enum.FriendStatus.NotFriend then
+ return ""
+ elseif friendStatus == Enum.FriendStatus.Friend then
+ return "http://www.roblox.com/asset/?id=99749771"
+ elseif friendStatus == Enum.FriendStatus.FriendRequestSent then
+ return "http://www.roblox.com/asset/?id=99776888"
+ elseif friendStatus == Enum.FriendStatus.FriendRequestReceived then
+ return "http://www.roblox.com/asset/?id=99776838"
+ else
+ error("Unknown FriendStatus: " .. friendStatus)
+ end
+end
+
+
+--[[
+ Utility function to create buttons for the popup menus
+ @Args:
+ nparent what to parent this button to
+ ntext text to put on this button
+ index number index of this entry in menu
+ last is this the last element of the popup menu
+ @Return: a popup menu button
+--]]
+function MakePopupButton(nparent,ntext,index,last)
+ local tobj = Obj.Create"ImageButton"
+ {
+ Name = 'ReportButton',
+ BackgroundTransparency = 1,
+ BackgroundColor3 = Color3.new(0, 0, 0),
+ Position = UDim2.new(0,0,1*index,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ ZIndex=7,
+ Obj.Create'TextLabel'
+ {
+ Name = 'ButtonText',
+ BackgroundTransparency = 0.6,
+ BackgroundColor3 = Color3.new(0, 0, 0),
+ Position = UDim2.new(.07, 0, .07, 0),
+ Size = UDim2.new(.86,0,.86,0),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = ntext,
+ FontSize = 'Size14',
+ TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeTransparency = 1,
+ ZIndex=7,
+ },
+ Parent = nparent,
+ }
+
+ return tobj
+end
+
+
+--[[
+ obligatory wait for child function
+ @Args:
+ parent Parent object to look for child in
+ child name of child object to look for
+ @Return: object waited for
+--]]
+function WaitForChild(parent,child)
+ while not parent:FindFirstChild(child) do
+ wait() debugprint(" child "..parent.Name.." waiting for "..child)
+ end
+ return parent[child]
+end
+
+ ---------------------------
+ -- Workspace Objects
+ ---------------------------
+
+-- might want to move all this to an init function, wait for localplayer elsewhere
+local Players = game:GetService('Players')
+-- make sure this doesn't run on the server(it will if you dont do this)
+while not Players.LocalPlayer do
+ Players.Changed:wait()
+end
+
+local LocalPlayer = Players.LocalPlayer
+local Mouse = LocalPlayer:GetMouse()
+
+local ScreenGui = Obj.Create"Frame"
+{
+ Name = 'PlayerListScreen',
+ Size = UDim2.new(1, 0, 1, 0),
+ BackgroundTransparency = 1,
+ Parent = script.Parent
+}
+local MainFrame = Obj.Create"Frame"
+{
+ Name = 'LeaderBoardFrame',
+ Position = UDim2.new(1, -150, 0.005, 0),
+ Size = UDim2.new(0, 150, 0, 800),
+ BackgroundTransparency = 1,
+ Parent = ScreenGui,
+}
+
+--frame used for expanding leaderstats when frame is 'focused'
+local FocusFrame = Obj.Create"Frame"
+{
+ Name = 'FocusFrame',
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1, 0, 0, 100),
+ BackgroundTransparency = 1,
+ Active = true,
+ Parent = MainFrame,
+}
+
+local TemplateFrameYSize = 0.670000017
+
+ -- HEADER
+local HeaderFrame = Obj.Create"Frame"
+{
+ Name = 'Header',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,0,0),
+ Size = UDim2.new(1, 0, .07, 0),
+ Parent = MainFrame,
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=94692054'),
+}
+ local HeaderFrameHeight = HeaderFrame.Size.Y.Scale
+ local MaximizeButton = Obj.Create"ImageButton"
+ {
+ Name = 'MaximizeButton',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ Parent = HeaderFrame,
+ }
+ local HeaderName = Obj.Create"TextLabel"
+ {
+ Name = 'PlayerName',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, .05, 0),
+ Size = UDim2.new(.98,0,.38,0),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = LocalPlayer.Name,
+ FontSize='Size24',
+ --TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+ local HeaderScore = Obj.Create"TextLabel"
+ {
+ Name = 'PlayerScore',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, .4, 0),
+ Size = UDim2.new(.98,0,0,30),
+ Parent = HeaderFrame,
+ Font = 'ArialBold',
+ Text = '',
+ FontSize='Size24',
+ TextYAlignment = 'Top',
+ --TextScaled = true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeTransparency = 1,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Top',
+ }
+ -- BOTTOM
+ --used for shifting bottom frame for mouse over effects
+local BottomShiftFrame = Obj.Create"Frame"
+{
+ Name= 'BottomShiftFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,HeaderFrameHeight,0),
+ Size = UDim2.new(1,0,1,0),
+ Parent=MainFrame,
+}
+ local BottomFrame = Obj.Create"Frame"
+ {
+ Name = 'Bottom',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,.07,0),
+ Size = UDim2.new(1, 0, .03, 0),
+ Parent = BottomShiftFrame,
+ }
+ local ExtendButton = Obj.Create"ImageButton"
+ {
+ Name = 'bigbutton',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1.5,0),
+ ZIndex = 3,
+ Parent = BottomFrame,
+ }
+ local ExtendTab = Obj.Create"ImageButton"
+ {
+ Name = 'extendTab',
+ Active = true,
+ BackgroundTransparency = 1,
+ Image = 'rbxasset://textures/ui/expandPlayerList.png',
+ Position = UDim2.new(.608, 0, .3, 0),
+ Size = UDim2.new(0,27,0,11),
+ Parent = BottomFrame,
+ }
+local TopClipFrame = Obj.Create"Frame"
+{
+ Name = 'ListFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(-1,0,.07,0),
+ Size = UDim2.new(2, 0, 1, 0),
+ Parent = MainFrame,
+ ClipsDescendants = true,
+}
+ local BottomClipFrame = Obj.Create"Frame"
+ {
+ Name = 'BottomFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0, - .8,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ Parent = TopClipFrame,
+ ClipsDescendants = true,
+ }
+ local ScrollBarFrame = Obj.Create"Frame"
+ {
+ Name = 'ScrollBarFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.987,0,.8,0),
+ Size = UDim2.new(.01, 0, .2, 0),
+ Parent = BottomClipFrame,
+ }
+ local ScrollBar = Obj.Create"Frame"
+ {
+ Name = 'ScrollBar',
+ BackgroundTransparency = 0,
+ BackgroundColor3 = Color3.new(.2,.2,.2),
+ Position = UDim2.new(0,0,0,0),
+ Size = UDim2.new(1, 0, .5, 0),
+ ZIndex = 5,
+ Parent = ScrollBarFrame,
+
+ }
+ local ListFrame = Obj.Create"Frame"
+ {
+ Name = 'SubFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,.8,0),
+ Size = UDim2.new(1, 0, 1, 0),
+ Parent = BottomClipFrame,
+ }
+local PopUpClipFrame = Obj.Create"Frame"
+{
+ Name = 'PopUpFrame',
+ BackgroundTransparency = 1,
+ SizeConstraint='RelativeXX',
+ Position = MainFrame.Position + UDim2.new( 0,-150,0,0),
+ Size = UDim2.new(0,150,0,800),
+ Parent = MainFrame,
+ ClipsDescendants = true,
+ ZIndex=7,
+}
+local PopUpPanel = nil
+ local PopUpPanelTemplate = Obj.Create"Frame"
+ {
+ Name = 'Panel',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(1,0,0,0),
+ Size = UDim2.new(1,0,.032,0),
+ Parent = PopUpClipFrame,
+ }
+
+local StatTitles = Obj.Create"Frame"
+{
+ Name = 'StatTitles',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0,0,1,-10),
+ Size = UDim2.new(1, 0, 0, 0),
+ Parent = HeaderFrame,
+}
+
+local IsMinimized = Instance.new('BoolValue')
+local IsMaximized = Instance.new('BoolValue')
+local IsTabified = Instance.new('BoolValue')
+local AreNamesExpanded = Instance.new('BoolValue')
+
+
+local MiddleTemplate = Obj.Create"Frame"
+{
+ Name = 'MidTemplate',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(100,0,.07,0),
+ Size = UDim2.new(.5, 0, .025, 0),--UDim2.new(1, 0, .03, 0),
+ Obj.Create'ImageLabel'
+ {
+ Name = 'BCLabel',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.005, 5, .20, -2),
+ Size = UDim2.new(0,16,0,16),
+ SizeConstraint = 'RelativeYY',
+ Image = "",
+ ZIndex = 4,
+ },
+ Obj.Create'ImageLabel'
+ {
+ Name = 'FriendLabel',
+ Active = true,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.005, 5, .15, 0),
+ Size = UDim2.new(0,16,0,16),
+ SizeConstraint = 'RelativeYY',
+ Image = "",
+ ZIndex = 4,
+ },
+ Obj.Create"ImageButton"
+ {
+ Name = 'ClickListener',
+ Active = true,
+ BackgroundTransparency = 1,
+ BorderSizePixel = 0,
+ Position = UDim2.new(0, 1, 0, 1),
+ Size = UDim2.new(1, -2,1,-2),
+ ZIndex = 3,
+ },
+ Obj.Create"Frame"
+ {
+ Name = 'TitleFrame',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.01, 0, 0, 0),
+ Size = UDim2.new(0,140,1,0),
+ BorderSizePixel = 0,
+ ClipsDescendants=true,
+ Obj.Create"TextLabel"
+ {
+ Name = 'Title',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 5, 0, 0),
+ Size = UDim2.new(100,0,1,0),
+ Font = 'Arial',
+ FontSize='Size14',
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = 'Left',
+ TextYAlignment = 'Center',
+ ZIndex = 3,
+ },
+ },
+
+ Obj.Create"TextLabel"
+ {
+ Name = 'PlayerScore',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(1,0,1,0),
+ Font = 'ArialBold',
+ Text = '',
+ FontSize='Size14',
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ ZIndex = 3,
+ },
+ --Obj.Create'IntValue'{Name = 'ID'},
+ --Obj.Create'ObjectValue'{Name = 'Player'},
+ --Obj.Create'IntValue'{Name = 'Score'},
+ ZIndex = 3,
+}
+local MiddleBGTemplate = Obj.Create"Frame"
+{
+ Name = 'MidBGTemplate',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(100,0,.07,0),
+ Size = UDim2.new(.5, 0, .025, 0),--UDim2.new(1, 0, .03, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=94692025'),
+
+}
+
+ -- REPORT ABUSE OBJECTS
+
+local ReportAbuseShield = Obj.Create"TextButton"
+{
+ Name = "ReportAbuseShield",
+ Text = "",
+ AutoButtonColor = false,
+ Active = true,
+ Visible = true,
+ Size = UDim2.new(1,0,1,0),
+ BackgroundColor3 = Color3I(51,51,51),
+ BorderColor3 = Color3I(27,42,53),
+ BackgroundTransparency = 1,
+}
+
+local ReportAbuseFrame = Obj.Create "Frame"
+{
+ Name = "Settings",
+ Position = UDim2.new(0.5, - 250, 0.5, - 200),
+ Size = UDim2.new(0.0, 500, 0.0, 400),
+ BackgroundTransparency = 1,
+ Active = true,
+ Parent = ReportAbuseShield,
+}
+
+local AbuseSettingsFrame = Obj.Create"Frame"
+{
+ Name = "ReportAbuseStyle",
+ Size = UDim2.new(1, 0, 1, 0),
+ Active = true,
+ BackgroundTransparency = 1,
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96488767'), -- 96480351'),
+ Obj.Create"TextLabel"
+ {
+ Name = "Title",
+ Text = "Report Abuse",
+ TextColor3 = Color3I(221,221,221),
+ Position = UDim2.new(0.5, 0, 0, 30),
+ Font = Enum.Font.ArialBold,
+ FontSize = Enum.FontSize.Size36,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "Description",
+ Text = "This will send a complete report to a moderator. The moderator will review the chat log and take appropriate action.",
+ TextColor3 = Color3I(221,221,221),
+ Position = UDim2.new(.01, 0, 0, 55),
+ Size = UDim2.new(.99, 0, 0, 40),
+ BackgroundTransparency = 1,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ TextWrap = true,
+ TextXAlignment = Enum.TextXAlignment.Left,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "AbuseLabel",
+ Text = "What did they do?",
+ Font = Enum.Font.Arial,
+ BackgroundTransparency = 1,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,140),
+ Size = UDim2.new(0.4,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "ShortDescriptionLabel",
+ Text = "Short Description: (optional)",
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,180),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ BackgroundTransparency = 1,
+ },
+ Obj.Create"TextLabel"
+ {
+ Name = "ReportingPlayerLabel",
+ Text = "Reporting Player",
+ BackgroundTransparency = 1,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,100),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ Parent = AbuseSettingsFrame
+ },
+
+ Parent = ReportAbuseFrame,
+}
+
+local AbusePlayerLabel = Obj.Create"TextLabel"
+{
+ Name = "PlayerLabel",
+ Text = "",
+ BackgroundTransparency = 1,
+ Font = Enum.Font.ArialBold,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0.025,0,0,100),
+ Size = UDim2.new(0.95,0,0,36),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Right,
+ Parent = AbuseSettingsFrame
+}
+
+local SubmitReportButton = Obj.Create"ImageButton"
+{
+ Name = "SubmitReportBtn",
+ Active = false,
+ BackgroundTransparency = 1,
+ Position = UDim2.new(.5, - 200, 1, - 80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = false,
+ Image = 'http://www.roblox.com/asset/?id=96502438', -- 96501119',
+ Parent = AbuseSettingsFrame,
+}
+
+local CancelReportButton = Obj.Create"ImageButton"
+{
+ Name = "CancelBtn",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, 50, 1, - 80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96500683',
+ Parent = AbuseSettingsFrame,
+}
+
+local AbuseDescriptionWrapper = Obj.Create"Frame"
+{
+ Name = "AbuseDescriptionWrapper",
+ Position = UDim2.new(0.025,0,0,220),
+ Size = UDim2.new(0.95,0,1, - 310),
+ BackgroundColor3 = Color3I(0,0,0),
+ BorderSizePixel = 0,
+ Parent = AbuseSettingsFrame,
+}
+
+local AbuseDescriptionBox
+
+local OriginalAbuseDescriptionBox = Obj.Create"TextBox"
+{
+ Name = "TextBox",
+ Text = "",
+ ClearTextOnFocus = false,
+ Font = Enum.Font.Arial,
+ FontSize = Enum.FontSize.Size18,
+ Position = UDim2.new(0,3,0,3),
+ Size = UDim2.new(1, - 6,1, - 6),
+ TextColor3 = Color3I(255,255,255),
+ TextXAlignment = Enum.TextXAlignment.Left,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ TextWrap = true,
+ BackgroundColor3 = Color3I(0,0,0),
+ BorderSizePixel = 0,
+}
+
+local CalmingAbuseBox = Obj.Create'Frame'
+{
+ Name = 'AbuseFeedbackBox',
+ BackgroundTransparency = 1,
+ Position=UDim2.new(0.25, 0, 0.300000012, 0),
+ Size=UDim2.new(0.5, 0, 0.370000005, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96506233'),
+ Obj.Create'TextLabel'
+ {
+ Name = 'Header',
+ Position=UDim2.new(0,10,.05,0),
+ Size=UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextXAlignment = Enum.TextXAlignment.Center,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ Text = 'Thanks for your report!',
+ TextColor3 = Color3.new(1,1,1),
+ FontSize = Enum.FontSize.Size48,
+ Font = 'ArialBold',
+ },
+ Obj.Create'TextLabel'
+ {
+ Name = 'content',
+ Position = UDim2.new(0,10,.20,0),
+ Size = UDim2.new(1, -30, .40, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ Text = 'Our moderators will review the chat logs and determine what happened. The other user is probably just trying to make you mad.\n\nIf anyone used swear words, inappropriate language, or threatened you in real life, please report them for Bad Words or Threats',
+ TextWrapped = true,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ FontSize = Enum.FontSize.Size24,
+ Font = 'Arial',
+ },
+ Obj.Create'ImageButton'
+ {
+ Name = "OkButton",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, -75, 1, -80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96507959',
+ }
+}
+local NormalAbuseBox = Obj.Create'Frame'
+{
+ Name = 'AbuseFeedbackBox',
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.25, 0, 0.300000012, 0),
+ Size = UDim2.new(0.5, 0, 0.370000005, 0),
+ MakeBackgroundGuiObj('http://www.roblox.com/asset/?id=96506233'),
+ Obj.Create'TextLabel'
+ {
+ Name = 'Header',
+ Position = UDim2.new(0,10,.05,0),
+ Size = UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ TextXAlignment = Enum.TextXAlignment.Center,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ Text = 'Thanks for your report!',
+ FontSize = Enum.FontSize.Size48,
+ Font ='ArialBold'
+ },
+ Obj.Create'TextLabel'
+ {
+ Name = 'content',
+ Position = UDim2.new(0,10,.20,0),
+ Size = UDim2.new(1, -30, .15, 0),
+ TextScaled = true,
+ BackgroundTransparency = 1,
+ TextColor3 = Color3.new(1,1,1),
+ Text = "Our moderators will review the chat logs and determine what happened.",
+ TextWrapped = true,
+ TextYAlignment = Enum.TextYAlignment.Top,
+ FontSize = Enum.FontSize.Size24,
+ Font = 'Arial',
+ },
+ Obj.Create'ImageButton'
+ {
+ Name = "OkButton",
+ BackgroundTransparency = 1,
+ Position = UDim2.new(0.5, -75, 1, -80),
+ Size = UDim2.new(0,150,0,50),
+ AutoButtonColor = true,
+ Image = 'http://www.roblox.com/asset/?id=96507959',
+ },
+}
+
+local BigButton=Instance.new('ImageButton')
+ BigButton.Size=UDim2.new(1,0,1,0)
+ BigButton.BackgroundTransparency=1
+ BigButton.ZIndex=8
+ BigButton.Visible=false
+ --BigButton.Active=false
+ BigButton.Parent=ScreenGui
+
+
+ local debugFrame = Obj.Create"Frame"
+ {
+ Name = 'debugframe',
+ Position = UDim2.new(0, 0, 0, 0),
+ Size = UDim2.new(0, 150, 0, 800),--0.99000001
+ BackgroundTransparency = 1,
+
+ }
+ local debugplayers = Obj.Create"TextLabel"
+ {
+ BackgroundTransparency = .8,
+ Position = UDim2.new(0, 0, .01, 0),
+ Size = UDim2.new(1,0,.5,0),
+ Parent = debugFrame,
+ Font = 'ArialBold',
+ Text = '--',
+ FontSize='Size14',
+ TextWrapped=true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+ local debugOutput = Obj.Create"TextLabel"
+ {
+ BackgroundTransparency = .8,
+ Position = UDim2.new(0, 0, .5, 0),
+ Size = UDim2.new(1,0,.5,0),
+ Parent = debugFrame,
+ Font = 'ArialBold',
+ Text = '--',
+ FontSize='Size14',
+ TextWrapped=true,
+ TextColor3 = Color3.new(1,1,1),
+ TextStrokeColor3 = Color3.new(0,0,0),
+ TextStrokeTransparency = 0,
+ TextXAlignment = 'Right',
+ TextYAlignment = 'Center',
+ }
+
+
+--[[
+ simple function to toggle the display of debug output
+--]]
+local DebugPrintEnabled=true
+function debugprint(str)
+ --print(str)
+ if DebugPrintEnabled then
+ debugOutput.Text=str
+ end
+end
+
+
+ -------------------------
+ -- Script objects
+ -------------------------
+local RbxGui = assert(LoadLibrary('RbxGui'))
+
+ -- number of entries to show if you click minimize
+local DefaultEntriesOnScreen = 8
+
+
+
+
+
+for _,i in pairs(Images) do
+ Game:GetService("ContentProvider"):Preload("http://www.roblox.com/asset/?id="..i)
+end
+
+ -- ordered array of 'score data', each entry has:
+ -- Name(String)
+ -- Priority(number)
+ -- IsPrimary (bool, should it be shown in upper right)
+ -- MaxLength (integer, of the length of the longest element for this column)
+local ScoreNames = {}
+ -- prevents flipping in playerlist panels
+local AddId = 0
+ -- intermediate table form of all player entries in format of:
+ -- Frame
+ -- Player
+ -- Score
+ -- ID
+ -- MyTeam (team ENRTY(not actual team) I am currently on)
+local PlayerFrames = {}
+ -- intermediate ordered frame array, composed of Entrys of
+ -- Frame
+ -- MyTeam (my team object)
+ -- MyPlayers ( an ordered array of all player frames in team )
+ -- AutoHide (bool saying whether it should be hidden)
+ -- IsHidden (bool)
+ -- ID (int to prevent flipping out of leaderboard, fun times)
+local TeamFrames = {}
+ -- one special entry from teamFrames, for unaffiliated players, only shown if players non - empty
+local NeutralTeam = nil
+
+ -- final 'to be displayed' list of frames
+local MiddleFrames = {}
+local MiddleFrameBackgrounds = {}
+local MiddleFrameHeight = .03
+ -- time of last click
+local LastClick = 0
+local ButtonCooldown = .25
+
+local OnIos = false
+pcall(function() OnIos = Game:GetService('UserInputService').TouchEnabled end)
+
+
+ -- you get 200 of x screen space per stat added, start width 16%
+local BaseScreenXSize = 150
+local SpacingPerStat = 10 --spacing between stats
+
+
+local MaximizedBounds = UDim2.new(.5,0,1,0)
+local MaximizedPosition = UDim2.new(.25,0,.1,0)
+local NormalBounds = UDim2.new(0,BaseScreenXSize, 0, 800)
+local NormalPosition = UDim2.new(1 , - BaseScreenXSize, 0.005, 0)
+
+local MinimizedBounds = UDim2.new(0, BaseScreenXSize, 0.99000001, 0)
+
+--free space to give last stat on the right
+local RightEdgeSpace = -.04
+
+ -- where the scroll par currently is positioned
+local ScrollPosition = 0.75999999
+local IsDragging = false -- am I dragging the player list
+
+local DefaultBottomClipPos = BottomClipFrame.Position.Y.Scale
+
+local LastSelectedPlayerEntry = nil
+local SelectedPlayerEntry = nil
+local SelectedPlayer = nil
+
+ -- locks(semaphores) for stopping race conditions
+local AddingFrameLock = false
+local ChangingOrderLock = false
+local AddingStatLock = false
+local BaseUpdateLock = false
+local WaitForClickLock = false
+local InPopupWaitForClick=false
+local PlayerChangedLock = false
+local NeutralTeamLock = false
+
+local ScrollWheelConnections = {}
+
+
+local DefaultListSize = 15
+if not OnIos then DefaultListSize = 24 end
+local DidMinimizeDrag = false
+
+--local PlaceCreatorId=game.CreatorId
+
+ -- report abuse objects
+local AbuseName
+local Abuses = {
+ "Bad Words or Threats",
+ "Bad Username",
+ "Talking about Dating",
+ "Account Trading or Sharing",
+ "Asking Personal Questions",
+ "Rude or Mean Behavior",
+ "False Reporting Me"
+}
+local UpdateAbuseFunction
+local AbuseDropDown, UpdateAbuseSelection
+
+local PrivilegeLevel =
+{
+ Owner = 255,
+ Admin = 240,
+ Member = 128,
+ Visitor = 10,
+ Banned = 0,
+}
+
+
+local IsPersonalServer = not not game.Workspace:FindFirstChild("PSVariable")
+
+game.Workspace.ChildAdded:connect(function(nchild)
+ if nchild.Name=='PSVariable' and nchild:IsA('BoolValue') then
+ IsPersonalServer=true
+ end
+end)
+ -------------------------------
+ -- Static Functions
+ -------------------------------
+function GetTotalEntries()
+ return math.min(#MiddleFrameBackgrounds,DefaultEntriesOnScreen)
+end
+
+function GetEntryListLength()
+ local numEnts=#PlayerFrames+#TeamFrames
+ if NeutralTeam then
+ numEnts=numEnts+1
+ end
+ return numEnts
+end
+
+function AreAllEntriesOnScreen()
+ return #MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale <= 1 + DefaultBottomClipPos
+end
+
+function GetLengthOfVisbleScroll()
+ return 1 + DefaultBottomClipPos
+end
+
+function GetMaxScroll()
+ return DefaultBottomClipPos * - 1
+end
+ -- can be optimized by caching when this varible changes
+function GetMinScroll()
+ if AreAllEntriesOnScreen() then
+ return GetMaxScroll()
+ else
+ return (GetMaxScroll() - (#MiddleFrameBackgrounds * MiddleTemplate.Size.Y.Scale)) + (1 + DefaultBottomClipPos)
+ end
+end
+
+function AbsoluteToPercent(x,y)
+ return Vector2.new(x,y)/ScreenGui.AbsoluteSize
+end
+--[[
+ tweens property of element from starta to enda over length of time
+ Warning: should be put in a Spawn call
+ @Args:
+ element textobject to tween transparency on
+ propName
+ starta alpha to start tweening
+ enda alpha to end tweening on
+ length how many seconds to spend tweening
+--]]
+function TweenProperty(obj, propName, inita, enda, length)
+ local startTime = tick()
+ while tick()-startTime
+ >>0;h--;)l[h]=c[h];return l}function Ac(c){return c.classList?bc(c.classList):(c.getAttribute("class")||"").split(" ").filter(function(c){return c})}function gc(c,l){var h,a=l.split("-"),z=a[0],v=a.slice(1).join("-");return z!==c||""===v||(h=v,~T.indexOf(h))?null:v}function Sc(c){return"".concat(c).replace(/&/g,"&").replace(/"/g,""").replace(/'/g,"'").replace(//g,">")}function yc(h){return Object.keys(h||{}).reduce(function(c,l){return c+"".concat(l,": ").concat(h[l],";")},"")}function wc(c){return c.size!==Lc.size||c.x!==Lc.x||c.y!==Lc.y||c.rotate!==Lc.rotate||c.flipX||c.flipY}function Zc(c){var l=c.transform,h=c.containerWidth,a=c.iconWidth,z={transform:"translate(".concat(h/2," 256)")},v="translate(".concat(32*l.x,", ").concat(32*l.y,") "),m="scale(".concat(l.size/16*(l.flipX?-1:1),", ").concat(l.size/16*(l.flipY?-1:1),") "),e="rotate(".concat(l.rotate," 0 0)");return{outer:z,inner:{transform:"".concat(v," ").concat(m," ").concat(e)},path:{transform:"translate(".concat(a/2*-1," -256)")}}}var kc={x:0,y:0,width:"100%",height:"100%"};function xc(c){var l=!(1").concat(m.map(Jc).join(""),"").concat(l,">")}var $c=function(){};function cl(c){return"string"==typeof(c.getAttribute?c.getAttribute(cc):null)}var ll={replace:function(c){var l=c[0],h=c[1].map(function(c){return Jc(c)}).join("\n");if(l.parentNode&&l.outerHTML)l.outerHTML=h+(lc.keepOriginalSource&&"svg"!==l.tagName.toLowerCase()?"\x3c!-- ".concat(l.outerHTML," Font Awesome fontawesome.com --\x3e"):"");else if(l.parentNode){var a=document.createElement("span");l.parentNode.replaceChild(a,l),a.outerHTML=h}},nest:function(c){var l=c[0],h=c[1];if(~Ac(l).indexOf(lc.replacementClass))return ll.replace(c);var a=new RegExp("".concat(lc.familyPrefix,"-.*"));delete h[0].attributes.style,delete h[0].attributes.id;var z=h[0].attributes.class.split(" ").reduce(function(c,l){return l===lc.replacementClass||l.match(a)?c.toSvg.push(l):c.toNode.push(l),c},{toNode:[],toSvg:[]});h[0].attributes.class=z.toSvg.join(" ");var v=h.map(function(c){return Jc(c)}).join("\n");l.setAttribute("class",z.toNode.join(" ")),l.setAttribute(cc,""),l.innerHTML=v}};function hl(c){c()}function al(h,c){var a="function"==typeof c?c:$c;if(0===h.length)a();else{var l=hl;lc.mutateApproach===y&&(l=o.requestAnimationFrame||hl),l(function(){var c=!0===lc.autoReplaceSvg?ll.replace:ll[lc.autoReplaceSvg]||ll.replace,l=_c.begin("mutate");h.map(c),l(),a()})}}var zl=!1;function vl(){zl=!1}var ml=null;function el(c){if(t&&lc.observeMutations){var z=c.treeCallback,v=c.nodeCallback,m=c.pseudoElementsCallback,l=c.observeMutationsRoot,h=void 0===l?C:l;ml=new t(function(c){zl||bc(c).forEach(function(c){if("childList"===c.type&&0 2 && arguments[2] !== undefined ? arguments[2] : {};
+ var _params$skipHooks = params.skipHooks,
+ skipHooks = _params$skipHooks === void 0 ? false : _params$skipHooks;
+ var normalized = Object.keys(icons).reduce(function (acc, iconName) {
+ var icon = icons[iconName];
+ var expanded = !!icon.icon;
+
+ if (expanded) {
+ acc[icon.iconName] = icon.icon;
+ } else {
+ acc[iconName] = icon;
+ }
+
+ return acc;
+ }, {});
+
+ if (typeof namespace.hooks.addPack === 'function' && !skipHooks) {
+ namespace.hooks.addPack(prefix, normalized);
+ } else {
+ namespace.styles[prefix] = _objectSpread({}, namespace.styles[prefix] || {}, normalized);
+ }
+ /**
+ * Font Awesome 4 used the prefix of `fa` for all icons. With the introduction
+ * of new styles we needed to differentiate between them. Prefix `fa` is now an alias
+ * for `fas` so we'll easy the upgrade process for our users by automatically defining
+ * this as well.
+ */
+
+
+ if (prefix === 'fas') {
+ defineIcons('fa', icons);
+ }
+ }
+
+ var icons = {
+ "500px": [448, 512, [], "f26e", "M103.3 344.3c-6.5-14.2-6.9-18.3 7.4-23.1 25.6-8 8 9.2 43.2 49.2h.3v-93.9c1.2-50.2 44-92.2 97.7-92.2 53.9 0 97.7 43.5 97.7 96.8 0 63.4-60.8 113.2-128.5 93.3-10.5-4.2-2.1-31.7 8.5-28.6 53 0 89.4-10.1 89.4-64.4 0-61-77.1-89.6-116.9-44.6-23.5 26.4-17.6 42.1-17.6 157.6 50.7 31 118.3 22 160.4-20.1 24.8-24.8 38.5-58 38.5-93 0-35.2-13.8-68.2-38.8-93.3-24.8-24.8-57.8-38.5-93.3-38.5s-68.8 13.8-93.5 38.5c-.3.3-16 16.5-21.2 23.9l-.5.6c-3.3 4.7-6.3 9.1-20.1 6.1-6.9-1.7-14.3-5.8-14.3-11.8V20c0-5 3.9-10.5 10.5-10.5h241.3c8.3 0 8.3 11.6 8.3 15.1 0 3.9 0 15.1-8.3 15.1H130.3v132.9h.3c104.2-109.8 282.8-36 282.8 108.9 0 178.1-244.8 220.3-310.1 62.8zm63.3-260.8c-.5 4.2 4.6 24.5 14.6 20.6C306 56.6 384 144.5 390.6 144.5c4.8 0 22.8-15.3 14.3-22.8-93.2-89-234.5-57-238.3-38.2zM393 414.7C283 524.6 94 475.5 61 310.5c0-12.2-30.4-7.4-28.9 3.3 24 173.4 246 256.9 381.6 121.3 6.9-7.8-12.6-28.4-20.7-20.4zM213.6 306.6c0 4 4.3 7.3 5.5 8.5 3 3 6.1 4.4 8.5 4.4 3.8 0 2.6.2 22.3-19.5 19.6 19.3 19.1 19.5 22.3 19.5 5.4 0 18.5-10.4 10.7-18.2L265.6 284l18.2-18.2c6.3-6.8-10.1-21.8-16.2-15.7L249.7 268c-18.6-18.8-18.4-19.5-21.5-19.5-5 0-18 11.7-12.4 17.3L234 284c-18.1 17.9-20.4 19.2-20.4 22.6z"],
+ "accessible-icon": [448, 512, [], "f368", "M423.9 255.8L411 413.1c-3.3 40.7-63.9 35.1-60.6-4.9l10-122.5-41.1 2.3c10.1 20.7 15.8 43.9 15.8 68.5 0 41.2-16.1 78.7-42.3 106.5l-39.3-39.3c57.9-63.7 13.1-167.2-74-167.2-25.9 0-49.5 9.9-67.2 26L73 243.2c22-20.7 50.1-35.1 81.4-40.2l75.3-85.7-42.6-24.8-51.6 46c-30 26.8-70.6-18.5-40.5-45.4l68-60.7c9.8-8.8 24.1-10.2 35.5-3.6 0 0 139.3 80.9 139.5 81.1 16.2 10.1 20.7 36 6.1 52.6L285.7 229l106.1-5.9c18.5-1.1 33.6 14.4 32.1 32.7zm-64.9-154c28.1 0 50.9-22.8 50.9-50.9C409.9 22.8 387.1 0 359 0c-28.1 0-50.9 22.8-50.9 50.9 0 28.1 22.8 50.9 50.9 50.9zM179.6 456.5c-80.6 0-127.4-90.6-82.7-156.1l-39.7-39.7C36.4 287 24 320.3 24 356.4c0 130.7 150.7 201.4 251.4 122.5l-39.7-39.7c-16 10.9-35.3 17.3-56.1 17.3z"],
+ "accusoft": [640, 512, [], "f369", "M322.1 252v-1l-51.2-65.8s-12 1.6-25 15.1c-9 9.3-242.1 239.1-243.4 240.9-7 10 1.6 6.8 15.7 1.7.8 0 114.5-36.6 114.5-36.6.5-.6-.1-.1.6-.6-.4-5.1-.8-26.2-1-27.7-.6-5.2 2.2-6.9 7-8.9l92.6-33.8c.6-.8 88.5-81.7 90.2-83.3zm160.1 120.1c13.3 16.1 20.7 13.3 30.8 9.3 3.2-1.2 115.4-47.6 117.8-48.9 8-4.3-1.7-16.7-7.2-23.4-2.1-2.5-205.1-245.6-207.2-248.3-9.7-12.2-14.3-12.9-38.4-12.8-10.2 0-106.8.5-116.5.6-19.2.1-32.9-.3-19.2 16.9C250 75 476.5 365.2 482.2 372.1zm152.7 1.6c-2.3-.3-24.6-4.7-38-7.2 0 0-115 50.4-117.5 51.6-16 7.3-26.9-3.2-36.7-14.6l-57.1-74c-5.4-.9-60.4-9.6-65.3-9.3-3.1.2-9.6.8-14.4 2.9-4.9 2.1-145.2 52.8-150.2 54.7-5.1 2-11.4 3.6-11.1 7.6.2 2.5 2 2.6 4.6 3.5 2.7.8 300.9 67.6 308 69.1 15.6 3.3 38.5 10.5 53.6 1.7 2.1-1.2 123.8-76.4 125.8-77.8 5.4-4 4.3-6.8-1.7-8.2z"],
+ "acquisitions-incorporated": [384, 512, [], "f6af", "M357.45 468.2c-1.2-7.7-1.3-7.6-9.6-7.6-99.8.2-111.8-2.4-112.7-2.6-12.3-1.7-20.6-10.5-21-23.1-.1-1.6-.2-71.6-1-129.1-.1-4.7 1.6-6.4 5.9-7.5 12.5-3 24.9-6.1 37.3-9.7 4.3-1.3 6.8-.2 8.4 3.5 4.5 10.3 8.8 20.6 13.2 30.9 1.6 3.7.1 4.4-3.4 4.4-10-.2-20-.1-30.4-.1v27h116c-1.4-9.5-2.7-18.1-4-27.5-7 0-13.8.4-20.4-.1-22.6-1.6-18.3-4.4-84-158.6-8.8-20.1-27.9-62.1-36.5-89.2-4.4-14 5.5-25.4 18.9-26.6 18.6-1.7 37.5-1.6 56.2-2 20.6-.4 41.2-.4 61.8-.5 3.1 0 4-1.4 4.3-4.3 1.2-9.8 2.7-19.5 4-29.2.8-5.3 1.6-10.7 2.4-16.1L23.75 0c-3.6 0-5.3 1.1-4.6 5.3 2.2 13.2-.8.8 6.4 45.3 63.4 0 71.8.9 101.8.5 12.3-.2 37 3.5 37.7 22.1.4 11.4-1.1 11.3-32.6 87.4-53.8 129.8-50.7 120.3-67.3 161-1.7 4.1-3.6 5.2-7.6 5.2-8.5-.2-17-.3-25.4.1-1.9.1-5.2 1.8-5.5 3.2-1.5 8.1-2.2 16.3-3.2 24.9h114.3v-27.6c-6.9 0-33.5.4-35.3-2.9 5.3-12.3 10.4-24.4 15.7-36.7 16.3 4 31.9 7.8 47.6 11.7 3.4.9 4.6 3 4.6 6.8-.1 42.9.1 85.9.2 128.8 0 10.2-5.5 19.1-14.9 23.1-6.5 2.7-3.3 3.4-121.4 2.4-5.3 0-7.1 2-7.6 6.8-1.5 12.9-2.9 25.9-5 38.8-.8 5 1.3 5.7 5.3 5.7 183.2.6-30.7 0 337.1 0-2.5-15-4.4-29.4-6.6-43.7zm-174.9-205.7c-13.3-4.2-26.6-8.2-39.9-12.5a44.53 44.53 0 0 1-5.8-2.9c17.2-44.3 34.2-88.1 51.3-132.1 7.5 2.4 7.9-.8 9.4 0 9.3 22.5 18.1 60.1 27 82.8 6.6 16.7 13 33.5 19.7 50.9a35.78 35.78 0 0 1-3.9 2.1c-13.1 3.9-26.4 7.5-39.4 11.7a27.66 27.66 0 0 1-18.4 0z"],
+ "adn": [496, 512, [], "f170", "M248 167.5l64.9 98.8H183.1l64.9-98.8zM496 256c0 136.9-111.1 248-248 248S0 392.9 0 256 111.1 8 248 8s248 111.1 248 248zm-99.8 82.7L248 115.5 99.8 338.7h30.4l33.6-51.7h168.6l33.6 51.7h30.2z"],
+ "adversal": [512, 512, [], "f36a", "M482.1 32H28.7C5.8 32 0 37.9 0 60.9v390.2C0 474.4 5.8 480 28.7 480h453.4c24.4 0 29.9-5.2 29.9-29.7V62.2c0-24.6-5.4-30.2-29.9-30.2zM178.4 220.3c-27.5-20.2-72.1-8.7-84.2 23.4-4.3 11.1-9.3 9.5-17.5 8.3-9.7-1.5-17.2-3.2-22.5-5.5-28.8-11.4 8.6-55.3 24.9-64.3 41.1-21.4 83.4-22.2 125.3-4.8 40.9 16.8 34.5 59.2 34.5 128.5 2.7 25.8-4.3 58.3 9.3 88.8 1.9 4.4.4 7.9-2.7 10.7-8.4 6.7-39.3 2.2-46.6-7.4-1.9-2.2-1.8-3.6-3.9-6.2-3.6-3.9-7.3-2.2-11.9 1-57.4 36.4-140.3 21.4-147-43.3-3.1-29.3 12.4-57.1 39.6-71 38.2-19.5 112.2-11.8 114-30.9 1.1-10.2-1.9-20.1-11.3-27.3zm286.7 222c0 15.1-11.1 9.9-17.8 9.9H52.4c-7.4 0-18.2 4.8-17.8-10.7.4-13.9 10.5-9.1 17.1-9.1 132.3-.4 264.5-.4 396.8 0 6.8 0 16.6-4.4 16.6 9.9zm3.8-340.5v291c0 5.7-.7 13.9-8.1 13.9-12.4-.4-27.5 7.1-36.1-5.6-5.8-8.7-7.8-4-12.4-1.2-53.4 29.7-128.1 7.1-144.4-85.2-6.1-33.4-.7-67.1 15.7-100 11.8-23.9 56.9-76.1 136.1-30.5v-71c0-26.2-.1-26.2 26-26.2 3.1 0 6.6.4 9.7 0 10.1-.8 13.6 4.4 13.6 14.3-.1.2-.1.3-.1.5zm-51.5 232.3c-19.5 47.6-72.9 43.3-90 5.2-15.1-33.3-15.5-68.2.4-101.5 16.3-34.1 59.7-35.7 81.5-4.8 20.6 28.8 14.9 84.6 8.1 101.1zm-294.8 35.3c-7.5-1.3-33-3.3-33.7-27.8-.4-13.9 7.8-23 19.8-25.8 24.4-5.9 49.3-9.9 73.7-14.7 8.9-2 7.4 4.4 7.8 9.5 1.4 33-26.1 59.2-67.6 58.8z"],
+ "affiliatetheme": [512, 512, [], "f36b", "M159.7 237.4C108.4 308.3 43.1 348.2 14 326.6-15.2 304.9 2.8 230 54.2 159.1c51.3-70.9 116.6-110.8 145.7-89.2 29.1 21.6 11.1 96.6-40.2 167.5zm351.2-57.3C437.1 303.5 319 367.8 246.4 323.7c-25-15.2-41.3-41.2-49-73.8-33.6 64.8-92.8 113.8-164.1 133.2 49.8 59.3 124.1 96.9 207 96.9 150 0 271.6-123.1 271.6-274.9.1-8.5-.3-16.8-1-25z"],
+ "airbnb": [448, 512, [], "f834", "M224 373.12c-25.24-31.67-40.08-59.43-45-83.18-22.55-88 112.61-88 90.06 0-5.45 24.25-20.29 52-45 83.18zm138.15 73.23c-42.06 18.31-83.67-10.88-119.3-50.47 103.9-130.07 46.11-200-18.85-200-54.92 0-85.16 46.51-73.28 100.5 6.93 29.19 25.23 62.39 54.43 99.5-32.53 36.05-60.55 52.69-85.15 54.92-50 7.43-89.11-41.06-71.3-91.09 15.1-39.16 111.72-231.18 115.87-241.56 15.75-30.07 25.56-57.4 59.38-57.4 32.34 0 43.4 25.94 60.37 59.87 36 70.62 89.35 177.48 114.84 239.09 13.17 33.07-1.37 71.29-37.01 86.64zm47-136.12C280.27 35.93 273.13 32 224 32c-45.52 0-64.87 31.67-84.66 72.79C33.18 317.1 22.89 347.19 22 349.81-3.22 419.14 48.74 480 111.63 480c21.71 0 60.61-6.06 112.37-62.4 58.68 63.78 101.26 62.4 112.37 62.4 62.89.05 114.85-60.86 89.61-130.19.02-3.89-16.82-38.9-16.82-39.58z"],
+ "algolia": [448, 512, [], "f36c", "M229.3 182.6c-49.3 0-89.2 39.9-89.2 89.2 0 49.3 39.9 89.2 89.2 89.2s89.2-39.9 89.2-89.2c0-49.3-40-89.2-89.2-89.2zm62.7 56.6l-58.9 30.6c-1.8.9-3.8-.4-3.8-2.3V201c0-1.5 1.3-2.7 2.7-2.6 26.2 1 48.9 15.7 61.1 37.1.7 1.3.2 3-1.1 3.7zM389.1 32H58.9C26.4 32 0 58.4 0 90.9V421c0 32.6 26.4 59 58.9 59H389c32.6 0 58.9-26.4 58.9-58.9V90.9C448 58.4 421.6 32 389.1 32zm-202.6 84.7c0-10.8 8.7-19.5 19.5-19.5h45.3c10.8 0 19.5 8.7 19.5 19.5v15.4c0 1.8-1.7 3-3.3 2.5-12.3-3.4-25.1-5.1-38.1-5.1-13.5 0-26.7 1.8-39.4 5.5-1.7.5-3.4-.8-3.4-2.5v-15.8zm-84.4 37l9.2-9.2c7.6-7.6 19.9-7.6 27.5 0l7.7 7.7c1.1 1.1 1 3-.3 4-6.2 4.5-12.1 9.4-17.6 14.9-5.4 5.4-10.4 11.3-14.8 17.4-1 1.3-2.9 1.5-4 .3l-7.7-7.7c-7.6-7.5-7.6-19.8 0-27.4zm127.2 244.8c-70 0-126.6-56.7-126.6-126.6s56.7-126.6 126.6-126.6c70 0 126.6 56.6 126.6 126.6 0 69.8-56.7 126.6-126.6 126.6z"],
+ "alipay": [448, 512, [], "f642", "M377.74 32H70.26C31.41 32 0 63.41 0 102.26v307.48C0 448.59 31.41 480 70.26 480h307.48c38.52 0 69.76-31.08 70.26-69.6-45.96-25.62-110.59-60.34-171.6-88.44-32.07 43.97-84.14 81-148.62 81-70.59 0-93.73-45.3-97.04-76.37-3.97-39.01 14.88-81.5 99.52-81.5 35.38 0 79.35 10.25 127.13 24.96 16.53-30.09 26.45-60.34 26.45-60.34h-178.2v-16.7h92.08v-31.24H88.28v-19.01h109.44V92.34h50.92v50.42h109.44v19.01H248.63v31.24h88.77s-15.21 46.62-38.35 90.92c48.93 16.7 100.01 36.04 148.62 52.74V102.26C447.83 63.57 416.43 32 377.74 32zM47.28 322.95c.99 20.17 10.25 53.73 69.93 53.73 52.07 0 92.58-39.68 117.87-72.9-44.63-18.68-84.48-31.41-109.44-31.41-67.45 0-79.35 33.06-78.36 50.58z"],
+ "amazon": [448, 512, [], "f270", "M257.2 162.7c-48.7 1.8-169.5 15.5-169.5 117.5 0 109.5 138.3 114 183.5 43.2 6.5 10.2 35.4 37.5 45.3 46.8l56.8-56S341 288.9 341 261.4V114.3C341 89 316.5 32 228.7 32 140.7 32 94 87 94 136.3l73.5 6.8c16.3-49.5 54.2-49.5 54.2-49.5 40.7-.1 35.5 29.8 35.5 69.1zm0 86.8c0 80-84.2 68-84.2 17.2 0-47.2 50.5-56.7 84.2-57.8v40.6zm136 163.5c-7.7 10-70 67-174.5 67S34.2 408.5 9.7 379c-6.8-7.7 1-11.3 5.5-8.3C88.5 415.2 203 488.5 387.7 401c7.5-3.7 13.3 2 5.5 12zm39.8 2.2c-6.5 15.8-16 26.8-21.2 31-5.5 4.5-9.5 2.7-6.5-3.8s19.3-46.5 12.7-55c-6.5-8.3-37-4.3-48-3.2-10.8 1-13 2-14-.3-2.3-5.7 21.7-15.5 37.5-17.5 15.7-1.8 41-.8 46 5.7 3.7 5.1 0 27.1-6.5 43.1z"],
+ "amazon-pay": [640, 512, [], "f42c", "M14 325.3c2.3-4.2 5.2-4.9 9.7-2.5 10.4 5.6 20.6 11.4 31.2 16.7a595.88 595.88 0 0 0 127.4 46.3 616.61 616.61 0 0 0 63.2 11.8 603.33 603.33 0 0 0 95 5.2c17.4-.4 34.8-1.8 52.1-3.8a603.66 603.66 0 0 0 163.3-42.8c2.9-1.2 5.9-2 9.1-1.2 6.7 1.8 9 9 4.1 13.9a70 70 0 0 1-9.6 7.4c-30.7 21.1-64.2 36.4-99.6 47.9a473.31 473.31 0 0 1-75.1 17.6 431 431 0 0 1-53.2 4.8 21.3 21.3 0 0 0-2.5.3H308a21.3 21.3 0 0 0-2.5-.3c-3.6-.2-7.2-.3-10.7-.4a426.3 426.3 0 0 1-50.4-5.3A448.4 448.4 0 0 1 164 420a443.33 443.33 0 0 1-145.6-87c-1.8-1.6-3-3.8-4.4-5.7zM172 65.1l-4.3.6a80.92 80.92 0 0 0-38 15.1c-2.4 1.7-4.6 3.5-7.1 5.4a4.29 4.29 0 0 1-.4-1.4c-.4-2.7-.8-5.5-1.3-8.2-.7-4.6-3-6.6-7.6-6.6h-11.5c-6.9 0-8.2 1.3-8.2 8.2v209.3c0 1 0 2 .1 3 .2 3 2 4.9 4.9 5 7 .1 14.1.1 21.1 0 2.9 0 4.7-2 5-5 .1-1 .1-2 .1-3v-72.4c1.1.9 1.7 1.4 2.2 1.9 17.9 14.9 38.5 19.8 61 15.4 20.4-4 34.6-16.5 43.8-34.9 7-13.9 9.9-28.7 10.3-44.1.5-17.1-1.2-33.9-8.1-49.8-8.5-19.6-22.6-32.5-43.9-36.9-3.2-.7-6.5-1-9.8-1.5-2.8-.1-5.5-.1-8.3-.1zM124.6 107a3.48 3.48 0 0 1 1.7-3.3c13.7-9.5 28.8-14.5 45.6-13.2 14.9 1.1 27.1 8.4 33.5 25.9 3.9 10.7 4.9 21.8 4.9 33 0 10.4-.8 20.6-4 30.6-6.8 21.3-22.4 29.4-42.6 28.5-14-.6-26.2-6-37.4-13.9a3.57 3.57 0 0 1-1.7-3.3c.1-14.1 0-28.1 0-42.2s.1-28 0-42.1zm205.7-41.9c-1 .1-2 .3-2.9.4a148 148 0 0 0-28.9 4.1c-6.1 1.6-12 3.8-17.9 5.8-3.6 1.2-5.4 3.8-5.3 7.7.1 3.3-.1 6.6 0 9.9.1 4.8 2.1 6.1 6.8 4.9 7.8-2 15.6-4.2 23.5-5.7 12.3-2.3 24.7-3.3 37.2-1.4 6.5 1 12.6 2.9 16.8 8.4 3.7 4.8 5.1 10.5 5.3 16.4.3 8.3.2 16.6.3 24.9a7.84 7.84 0 0 1-.2 1.4c-.5-.1-.9 0-1.3-.1a180.56 180.56 0 0 0-32-4.9c-11.3-.6-22.5.1-33.3 3.9-12.9 4.5-23.3 12.3-29.4 24.9-4.7 9.8-5.4 20.2-3.9 30.7 2 14 9 24.8 21.4 31.7 11.9 6.6 24.8 7.4 37.9 5.4 15.1-2.3 28.5-8.7 40.3-18.4a7.36 7.36 0 0 1 1.6-1.1c.6 3.8 1.1 7.4 1.8 11 .6 3.1 2.5 5.1 5.4 5.2 5.4.1 10.9.1 16.3 0a4.84 4.84 0 0 0 4.8-4.7 26.2 26.2 0 0 0 .1-2.8v-106a80 80 0 0 0-.9-12.9c-1.9-12.9-7.4-23.5-19-30.4-6.7-4-14.1-6-21.8-7.1-3.6-.5-7.2-.8-10.8-1.3-3.9.1-7.9.1-11.9.1zm35 127.7a3.33 3.33 0 0 1-1.5 3c-11.2 8.1-23.5 13.5-37.4 14.9-5.7.6-11.4.4-16.8-1.8a20.08 20.08 0 0 1-12.4-13.3 32.9 32.9 0 0 1-.1-19.4c2.5-8.3 8.4-13 16.4-15.6a61.33 61.33 0 0 1 24.8-2.2c8.4.7 16.6 2.3 25 3.4 1.6.2 2.1 1 2.1 2.6-.1 4.8 0 9.5 0 14.3s-.2 9.4-.1 14.1zm259.9 129.4c-1-5-4.8-6.9-9.1-8.3a88.42 88.42 0 0 0-21-3.9 147.32 147.32 0 0 0-39.2 1.9c-14.3 2.7-27.9 7.3-40 15.6a13.75 13.75 0 0 0-3.7 3.5 5.11 5.11 0 0 0-.5 4c.4 1.5 2.1 1.9 3.6 1.8a16.2 16.2 0 0 0 2.2-.1c7.8-.8 15.5-1.7 23.3-2.5 11.4-1.1 22.9-1.8 34.3-.9a71.64 71.64 0 0 1 14.4 2.7c5.1 1.4 7.4 5.2 7.6 10.4.4 8-1.4 15.7-3.5 23.3-4.1 15.4-10 30.3-15.8 45.1a17.6 17.6 0 0 0-1 3c-.5 2.9 1.2 4.8 4.1 4.1a10.56 10.56 0 0 0 4.8-2.5 145.91 145.91 0 0 0 12.7-13.4c12.8-16.4 20.3-35.3 24.7-55.6.8-3.6 1.4-7.3 2.1-10.9v-17.3zM493.1 199q-19.35-53.55-38.7-107.2c-2-5.7-4.2-11.3-6.3-16.9-1.1-2.9-3.2-4.8-6.4-4.8-7.6-.1-15.2-.2-22.9-.1-2.5 0-3.7 2-3.2 4.5a43.1 43.1 0 0 0 1.9 6.1q29.4 72.75 59.1 145.5c1.7 4.1 2.1 7.6.2 11.8-3.3 7.3-5.9 15-9.3 22.3-3 6.5-8 11.4-15.2 13.3a42.13 42.13 0 0 1-15.4 1.1c-2.5-.2-5-.8-7.5-1-3.4-.2-5.1 1.3-5.2 4.8q-.15 5 0 9.9c.1 5.5 2 8 7.4 8.9a108.18 108.18 0 0 0 16.9 2c17.1.4 30.7-6.5 39.5-21.4a131.63 131.63 0 0 0 9.2-18.4q35.55-89.7 70.6-179.6a26.62 26.62 0 0 0 1.6-5.5c.4-2.8-.9-4.4-3.7-4.4-6.6-.1-13.3 0-19.9 0a7.54 7.54 0 0 0-7.7 5.2c-.5 1.4-1.1 2.7-1.6 4.1l-34.8 100c-2.5 7.2-5.1 14.5-7.7 22.2-.4-1.1-.6-1.7-.9-2.4z"],
+ "amilia": [448, 512, [], "f36d", "M240.1 32c-61.9 0-131.5 16.9-184.2 55.4-5.1 3.1-9.1 9.2-7.2 19.4 1.1 5.1 5.1 27.4 10.2 39.6 4.1 10.2 14.2 10.2 20.3 6.1 32.5-22.3 96.5-47.7 152.3-47.7 57.9 0 58.9 28.4 58.9 73.1v38.5C203 227.7 78.2 251 46.7 264.2 11.2 280.5 16.3 357.7 16.3 376s15.2 104 124.9 104c47.8 0 113.7-20.7 153.3-42.1v25.4c0 3 2.1 8.2 6.1 9.1 3.1 1 50.7 2 59.9 2s62.5.3 66.5-.7c4.1-1 5.1-6.1 5.1-9.1V168c-.1-80.3-57.9-136-192-136zm50.2 348c-21.4 13.2-48.7 24.4-79.1 24.4-52.8 0-58.9-33.5-59-44.7 0-12.2-3-42.7 18.3-52.9 24.3-13.2 75.1-29.4 119.8-33.5z"],
+ "android": [576, 512, [], "f17b", "M420.55,301.93a24,24,0,1,1,24-24,24,24,0,0,1-24,24m-265.1,0a24,24,0,1,1,24-24,24,24,0,0,1-24,24m273.7-144.48,47.94-83a10,10,0,1,0-17.27-10h0l-48.54,84.07a301.25,301.25,0,0,0-246.56,0L116.18,64.45a10,10,0,1,0-17.27,10h0l47.94,83C64.53,202.22,8.24,285.55,0,384H576c-8.24-98.45-64.54-181.78-146.85-226.55"],
+ "angellist": [448, 512, [], "f209", "M347.1 215.4c11.7-32.6 45.4-126.9 45.4-157.1 0-26.6-15.7-48.9-43.7-48.9-44.6 0-84.6 131.7-97.1 163.1C242 144 196.6 0 156.6 0c-31.1 0-45.7 22.9-45.7 51.7 0 35.3 34.2 126.8 46.6 162-6.3-2.3-13.1-4.3-20-4.3-23.4 0-48.3 29.1-48.3 52.6 0 8.9 4.9 21.4 8 29.7-36.9 10-51.1 34.6-51.1 71.7C46 435.6 114.4 512 210.6 512c118 0 191.4-88.6 191.4-202.9 0-43.1-6.9-82-54.9-93.7zM311.7 108c4-12.3 21.1-64.3 37.1-64.3 8.6 0 10.9 8.9 10.9 16 0 19.1-38.6 124.6-47.1 148l-34-6 33.1-93.7zM142.3 48.3c0-11.9 14.5-45.7 46.3 47.1l34.6 100.3c-15.6-1.3-27.7-3-35.4 1.4-10.9-28.8-45.5-119.7-45.5-148.8zM140 244c29.3 0 67.1 94.6 67.1 107.4 0 5.1-4.9 11.4-10.6 11.4-20.9 0-76.9-76.9-76.9-97.7.1-7.7 12.7-21.1 20.4-21.1zm184.3 186.3c-29.1 32-66.3 48.6-109.7 48.6-59.4 0-106.3-32.6-128.9-88.3-17.1-43.4 3.8-68.3 20.6-68.3 11.4 0 54.3 60.3 54.3 73.1 0 4.9-7.7 8.3-11.7 8.3-16.1 0-22.4-15.5-51.1-51.4-29.7 29.7 20.5 86.9 58.3 86.9 26.1 0 43.1-24.2 38-42 3.7 0 8.3.3 11.7-.6 1.1 27.1 9.1 59.4 41.7 61.7 0-.9 2-7.1 2-7.4 0-17.4-10.6-32.6-10.6-50.3 0-28.3 21.7-55.7 43.7-71.7 8-6 17.7-9.7 27.1-13.1 9.7-3.7 20-8 27.4-15.4-1.1-11.2-5.7-21.1-16.9-21.1-27.7 0-120.6 4-120.6-39.7 0-6.7.1-13.1 17.4-13.1 32.3 0 114.3 8 138.3 29.1 18.1 16.1 24.3 113.2-31 174.7zm-98.6-126c9.7 3.1 19.7 4 29.7 6-7.4 5.4-14 12-20.3 19.1-2.8-8.5-6.2-16.8-9.4-25.1z"],
+ "angrycreative": [640, 512, [], "f36e", "M640 238.2l-3.2 28.2-34.5 2.3-2 18.1 34.5-2.3-3.2 28.2-34.4 2.2-2.3 20.1 34.4-2.2-3 26.1-64.7 4.1 12.7-113.2L527 365.2l-31.9 2-23.8-117.8 30.3-2 13.6 79.4 31.7-82.4 93.1-6.2zM426.8 371.5l28.3-1.8L468 249.6l-28.4 1.9-12.8 120zM162 388.1l-19.4-36-3.5 37.4-28.2 1.7 2.7-29.1c-11 18-32 34.3-56.9 35.8C23.9 399.9-3 377 .3 339.7c2.6-29.3 26.7-62.8 67.5-65.4 37.7-2.4 47.6 23.2 51.3 28.8l2.8-30.8 38.9-2.5c20.1-1.3 38.7 3.7 42.5 23.7l2.6-26.6 64.8-4.2-2.7 27.9-36.4 2.4-1.7 17.9 36.4-2.3-2.7 27.9-36.4 2.3-1.9 19.9 36.3-2.3-2.1 20.8 55-117.2 23.8-1.6L370.4 369l8.9-85.6-22.3 1.4 2.9-27.9 75-4.9-3 28-24.3 1.6-9.7 91.9-58 3.7-4.3-15.6-39.4 2.5-8 16.3-126.2 7.7zm-44.3-70.2l-26.4 1.7C84.6 307.2 76.9 303 65 303.8c-19 1.2-33.3 17.5-34.6 33.3-1.4 16 7.3 32.5 28.7 31.2 12.8-.8 21.3-8.6 28.9-18.9l27-1.7 2.7-29.8zm56.1-7.7c1.2-12.9-7.6-13.6-26.1-12.4l-2.7 28.5c14.2-.9 27.5-2.1 28.8-16.1zm21.1 70.8l5.8-60c-5 13.5-14.7 21.1-27.9 26.6l22.1 33.4zm135.4-45l-7.9-37.8-15.8 39.3 23.7-1.5zm-170.1-74.6l-4.3-17.5-39.6 2.6-8.1 18.2-31.9 2.1 57-121.9 23.9-1.6 30.7 102 9.9-104.7 27-1.8 37.8 63.6 6.5-66.6 28.5-1.9-4 41.2c7.4-13.5 22.9-44.7 63.6-47.5 40.5-2.8 52.4 29.3 53.4 30.3l3.3-32 39.3-2.7c12.7-.9 27.8.3 36.3 9.7l-4.4-11.9 32.2-2.2 12.9 43.2 23-45.7 31-2.2-43.6 78.4-4.8 44.3-28.4 1.9 4.8-44.3-15.8-43c1 22.3-9.2 40.1-32 49.6l25.2 38.8-36.4 2.4-19.2-36.8-4 38.3-28.4 1.9 3.3-31.5c-6.7 9.3-19.7 35.4-59.6 38-26.2 1.7-45.6-10.3-55.4-39.2l-4 40.3-25 1.6-37.6-63.3-6.3 66.2-56.8 3.7zm276.6-82.1c10.2-.7 17.5-2.1 21.6-4.3 4.5-2.4 7-6.4 7.6-12.1.6-5.3-.6-8.8-3.4-10.4-3.6-2.1-10.6-2.8-22.9-2l-2.9 28.8zM327.7 214c5.6 5.9 12.7 8.5 21.3 7.9 4.7-.3 9.1-1.8 13.3-4.1 5.5-3 10.6-8 15.1-14.3l-34.2 2.3 2.4-23.9 63.1-4.3 1.2-12-31.2 2.1c-4.1-3.7-7.8-6.6-11.1-8.1-4-1.7-8.1-2.8-12.2-2.5-8 .5-15.3 3.6-22 9.2-7.7 6.4-12 14.5-12.9 24.4-1.1 9.6 1.4 17.3 7.2 23.3zm-201.3 8.2l23.8-1.6-8.3-37.6-15.5 39.2z"],
+ "angular": [448, 512, [], "f420", "M185.7 268.1h76.2l-38.1-91.6-38.1 91.6zM223.8 32L16 106.4l31.8 275.7 176 97.9 176-97.9 31.8-275.7zM354 373.8h-48.6l-26.2-65.4H168.6l-26.2 65.4H93.7L223.8 81.5z"],
+ "app-store": [512, 512, [], "f36f", "M255.9 120.9l9.1-15.7c5.6-9.8 18.1-13.1 27.9-7.5 9.8 5.6 13.1 18.1 7.5 27.9l-87.5 151.5h63.3c20.5 0 32 24.1 23.1 40.8H113.8c-11.3 0-20.4-9.1-20.4-20.4 0-11.3 9.1-20.4 20.4-20.4h52l66.6-115.4-20.8-36.1c-5.6-9.8-2.3-22.2 7.5-27.9 9.8-5.6 22.2-2.3 27.9 7.5l8.9 15.7zm-78.7 218l-19.6 34c-5.6 9.8-18.1 13.1-27.9 7.5-9.8-5.6-13.1-18.1-7.5-27.9l14.6-25.2c16.4-5.1 29.8-1.2 40.4 11.6zm168.9-61.7h53.1c11.3 0 20.4 9.1 20.4 20.4 0 11.3-9.1 20.4-20.4 20.4h-29.5l19.9 34.5c5.6 9.8 2.3 22.2-7.5 27.9-9.8 5.6-22.2 2.3-27.9-7.5-33.5-58.1-58.7-101.6-75.4-130.6-17.1-29.5-4.9-59.1 7.2-69.1 13.4 23 33.4 57.7 60.1 104zM256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm216 248c0 118.7-96.1 216-216 216-118.7 0-216-96.1-216-216 0-118.7 96.1-216 216-216 118.7 0 216 96.1 216 216z"],
+ "app-store-ios": [448, 512, [], "f370", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM127 384.5c-5.5 9.6-17.8 12.8-27.3 7.3-9.6-5.5-12.8-17.8-7.3-27.3l14.3-24.7c16.1-4.9 29.3-1.1 39.6 11.4L127 384.5zm138.9-53.9H84c-11 0-20-9-20-20s9-20 20-20h51l65.4-113.2-20.5-35.4c-5.5-9.6-2.2-21.8 7.3-27.3 9.6-5.5 21.8-2.2 27.3 7.3l8.9 15.4 8.9-15.4c5.5-9.6 17.8-12.8 27.3-7.3 9.6 5.5 12.8 17.8 7.3 27.3l-85.8 148.6h62.1c20.2 0 31.5 23.7 22.7 40zm98.1 0h-29l19.6 33.9c5.5 9.6 2.2 21.8-7.3 27.3-9.6 5.5-21.8 2.2-27.3-7.3-32.9-56.9-57.5-99.7-74-128.1-16.7-29-4.8-58 7.1-67.8 13.1 22.7 32.7 56.7 58.9 102h52c11 0 20 9 20 20 0 11.1-9 20-20 20z"],
+ "apper": [640, 512, [], "f371", "M42.1 239.1c22.2 0 29 2.8 33.5 14.6h.8v-22.9c0-11.3-4.8-15.4-17.9-15.4-11.3 0-14.4 2.5-15.1 12.8H4.8c.3-13.9 1.5-19.1 5.8-24.4C17.9 195 29.5 192 56.7 192c33 0 47.1 5 53.9 18.9 2 4.3 4 15.6 4 23.7v76.3H76.3l1.3-19.1h-1c-5.3 15.6-13.6 20.4-35.5 20.4-30.3 0-41.1-10.1-41.1-37.3 0-25.2 12.3-35.8 42.1-35.8zm17.1 48.1c13.1 0 16.9-3 16.9-13.4 0-9.1-4.3-11.6-19.6-11.6-13.1 0-17.9 3-17.9 12.1-.1 10.4 3.7 12.9 20.6 12.9zm77.8-94.9h38.3l-1.5 20.6h.8c9.1-17.1 15.9-20.9 37.5-20.9 14.4 0 24.7 3 31.5 9.1 9.8 8.6 12.8 20.4 12.8 48.1 0 30-3 43.1-12.1 52.9-6.8 7.3-16.4 10.1-33.2 10.1-20.4 0-29.2-5.5-33.8-21.2h-.8v70.3H137v-169zm80.9 60.7c0-27.5-3.3-32.5-20.7-32.5-16.9 0-20.7 5-20.7 28.7 0 28 3.5 33.5 21.2 33.5 16.4 0 20.2-5.6 20.2-29.7zm57.9-60.7h38.3l-1.5 20.6h.8c9.1-17.1 15.9-20.9 37.5-20.9 14.4 0 24.7 3 31.5 9.1 9.8 8.6 12.8 20.4 12.8 48.1 0 30-3 43.1-12.1 52.9-6.8 7.3-16.4 10.1-33.3 10.1-20.4 0-29.2-5.5-33.8-21.2h-.8v70.3h-39.5v-169zm80.9 60.7c0-27.5-3.3-32.5-20.7-32.5-16.9 0-20.7 5-20.7 28.7 0 28 3.5 33.5 21.2 33.5 16.4 0 20.2-5.6 20.2-29.7zm53.8-3.8c0-25.4 3.3-37.8 12.3-45.8 8.8-8.1 22.2-11.3 45.1-11.3 42.8 0 55.7 12.8 55.7 55.7v11.1h-75.3c-.3 2-.3 4-.3 4.8 0 16.9 4.5 21.9 20.1 21.9 13.9 0 17.9-3 17.9-13.9h37.5v2.3c0 9.8-2.5 18.9-6.8 24.7-7.3 9.8-19.6 13.6-44.3 13.6-27.5 0-41.6-3.3-50.6-12.3-8.5-8.5-11.3-21.3-11.3-50.8zm76.4-11.6c-.3-1.8-.3-3.3-.3-3.8 0-12.3-3.3-14.6-19.6-14.6-14.4 0-17.1 3-18.1 15.1l-.3 3.3h38.3zm55.6-45.3h38.3l-1.8 19.9h.7c6.8-14.9 14.4-20.2 29.7-20.2 10.8 0 19.1 3.3 23.4 9.3 5.3 7.3 6.8 14.4 6.8 34 0 1.5 0 5 .2 9.3h-35c.3-1.8.3-3.3.3-4 0-15.4-2-19.4-10.3-19.4-6.3 0-10.8 3.3-13.1 9.3-1 3-1 4.3-1 12.3v68h-38.3V192.3z"],
+ "apple": [384, 512, [], "f179", "M318.7 268.7c-.2-36.7 16.4-64.4 50-84.8-18.8-26.9-47.2-41.7-84.7-44.6-35.5-2.8-74.3 20.7-88.5 20.7-15 0-49.4-19.7-76.4-19.7C63.3 141.2 4 184.8 4 273.5q0 39.3 14.4 81.2c12.8 36.7 59 126.7 107.2 125.2 25.2-.6 43-17.9 75.8-17.9 31.8 0 48.3 17.9 76.4 17.9 48.6-.7 90.4-82.5 102.6-119.3-65.2-30.7-61.7-90-61.7-91.9zm-56.6-164.2c27.3-32.4 24.8-61.9 24-72.5-24.1 1.4-52 16.4-67.9 34.9-17.5 19.8-27.8 44.3-25.6 71.9 26.1 2 49.9-11.4 69.5-34.3z"],
+ "apple-pay": [640, 512, [], "f415", "M116.9 158.5c-7.5 8.9-19.5 15.9-31.5 14.9-1.5-12 4.4-24.8 11.3-32.6 7.5-9.1 20.6-15.6 31.3-16.1 1.2 12.4-3.7 24.7-11.1 33.8m10.9 17.2c-17.4-1-32.3 9.9-40.5 9.9-8.4 0-21-9.4-34.8-9.1-17.9.3-34.5 10.4-43.6 26.5-18.8 32.3-4.9 80 13.3 106.3 8.9 13 19.5 27.3 33.5 26.8 13.3-.5 18.5-8.6 34.5-8.6 16.1 0 20.8 8.6 34.8 8.4 14.5-.3 23.6-13 32.5-26 10.1-14.8 14.3-29.1 14.5-29.9-.3-.3-28-10.9-28.3-42.9-.3-26.8 21.9-39.5 22.9-40.3-12.5-18.6-32-20.6-38.8-21.1m100.4-36.2v194.9h30.3v-66.6h41.9c38.3 0 65.1-26.3 65.1-64.3s-26.4-64-64.1-64h-73.2zm30.3 25.5h34.9c26.3 0 41.3 14 41.3 38.6s-15 38.8-41.4 38.8h-34.8V165zm162.2 170.9c19 0 36.6-9.6 44.6-24.9h.6v23.4h28v-97c0-28.1-22.5-46.3-57.1-46.3-32.1 0-55.9 18.4-56.8 43.6h27.3c2.3-12 13.4-19.9 28.6-19.9 18.5 0 28.9 8.6 28.9 24.5v10.8l-37.8 2.3c-35.1 2.1-54.1 16.5-54.1 41.5.1 25.2 19.7 42 47.8 42zm8.2-23.1c-16.1 0-26.4-7.8-26.4-19.6 0-12.3 9.9-19.4 28.8-20.5l33.6-2.1v11c0 18.2-15.5 31.2-36 31.2zm102.5 74.6c29.5 0 43.4-11.3 55.5-45.4L640 193h-30.8l-35.6 115.1h-.6L537.4 193h-31.6L557 334.9l-2.8 8.6c-4.6 14.6-12.1 20.3-25.5 20.3-2.4 0-7-.3-8.9-.5v23.4c1.8.4 9.3.7 11.6.7z"],
+ "artstation": [512, 512, [], "f77a", "M2 377.4l43 74.3A51.35 51.35 0 0 0 90.9 480h285.4l-59.2-102.6zM501.8 350L335.6 59.3A51.38 51.38 0 0 0 290.2 32h-88.4l257.3 447.6 40.7-70.5c1.9-3.2 21-29.7 2-59.1zM275 304.5l-115.5-200L44 304.5z"],
+ "asymmetrik": [576, 512, [], "f372", "M517.5 309.2c38.8-40 58.1-80 58.5-116.1.8-65.5-59.4-118.2-169.4-135C277.9 38.4 118.1 73.6 0 140.5 52 114 110.6 92.3 170.7 82.3c74.5-20.5 153-25.4 221.3-14.8C544.5 91.3 588.8 195 490.8 299.2c-10.2 10.8-22 21.1-35 30.6L304.9 103.4 114.7 388.9c-65.6-29.4-76.5-90.2-19.1-151.2 20.8-22.2 48.3-41.9 79.5-58.1 20-12.2 39.7-22.6 62-30.7-65.1 20.3-122.7 52.9-161.6 92.9-27.7 28.6-41.4 57.1-41.7 82.9-.5 35.1 23.4 65.1 68.4 83l-34.5 51.7h101.6l22-34.4c22.2 1 45.3 0 68.6-2.7l-22.8 37.1h135.5L340 406.3c18.6-5.3 36.9-11.5 54.5-18.7l45.9 71.8H542L468.6 349c18.5-12.1 35-25.5 48.9-39.8zm-187.6 80.5l-25-40.6-32.7 53.3c-23.4 3.5-46.7 5.1-69.2 4.4l101.9-159.3 78.7 123c-17.2 7.4-35.3 13.9-53.7 19.2z"],
+ "atlassian": [512, 512, [], "f77b", "M152.2 236.4c-7.7-8.2-19.7-7.7-24.8 2.8L1.6 490.2c-5 10 2.4 21.7 13.4 21.7h175c5.8.1 11-3.2 13.4-8.4 37.9-77.8 15.1-196.3-51.2-267.1zM244.4 8.1c-122.3 193.4-8.5 348.6 65 495.5 2.5 5.1 7.7 8.4 13.4 8.4H497c11.2 0 18.4-11.8 13.4-21.7 0 0-234.5-470.6-240.4-482.3-5.3-10.6-18.8-10.8-25.6.1z"],
+ "audible": [640, 512, [], "f373", "M640 199.9v54l-320 200L0 254v-54l320 200 320-200.1zm-194.5 72l47.1-29.4c-37.2-55.8-100.7-92.6-172.7-92.6-72 0-135.5 36.7-172.6 92.4h.3c2.5-2.3 5.1-4.5 7.7-6.7 89.7-74.4 219.4-58.1 290.2 36.3zm-220.1 18.8c16.9-11.9 36.5-18.7 57.4-18.7 34.4 0 65.2 18.4 86.4 47.6l45.4-28.4c-20.9-29.9-55.6-49.5-94.8-49.5-38.9 0-73.4 19.4-94.4 49zM103.6 161.1c131.8-104.3 318.2-76.4 417.5 62.1l.7 1 48.8-30.4C517.1 112.1 424.8 58.1 319.9 58.1c-103.5 0-196.6 53.5-250.5 135.6 9.9-10.5 22.7-23.5 34.2-32.6zm467 32.7z"],
+ "autoprefixer": [640, 512, [], "f41c", "M318.4 16l-161 480h77.5l25.4-81.4h119.5L405 496h77.5L318.4 16zm-40.3 341.9l41.2-130.4h1.5l40.9 130.4h-83.6zM640 405l-10-31.4L462.1 358l19.4 56.5L640 405zm-462.1-47L10 373.7 0 405l158.5 9.4 19.4-56.4z"],
+ "avianex": [512, 512, [], "f374", "M453.1 32h-312c-38.9 0-76.2 31.2-83.3 69.7L1.2 410.3C-5.9 448.8 19.9 480 58.9 480h312c38.9 0 76.2-31.2 83.3-69.7l56.7-308.5c7-38.6-18.8-69.8-57.8-69.8zm-58.2 347.3l-32 13.5-115.4-110c-14.7 10-29.2 19.5-41.7 27.1l22.1 64.2-17.9 12.7-40.6-61-52.4-48.1 15.7-15.4 58 31.1c9.3-10.5 20.8-22.6 32.8-34.9L203 228.9l-68.8-99.8 18.8-28.9 8.9-4.8L265 207.8l4.9 4.5c19.4-18.8 33.8-32.4 33.8-32.4 7.7-6.5 21.5-2.9 30.7 7.9 9 10.5 10.6 24.7 2.7 31.3-1.8 1.3-15.5 11.4-35.3 25.6l4.5 7.3 94.9 119.4-6.3 7.9z"],
+ "aviato": [640, 512, [], "f421", "M107.2 283.5l-19-41.8H36.1l-19 41.8H0l62.2-131.4 62.2 131.4h-17.2zm-45-98.1l-19.6 42.5h39.2l-19.6-42.5zm112.7 102.4l-62.2-131.4h17.1l45.1 96 45.1-96h17l-62.1 131.4zm80.6-4.3V156.4H271v127.1h-15.5zm209.1-115.6v115.6h-17.3V167.9h-41.2v-11.5h99.6v11.5h-41.1zM640 218.8c0 9.2-1.7 17.8-5.1 25.8-3.4 8-8.2 15.1-14.2 21.1-6 6-13.1 10.8-21.1 14.2-8 3.4-16.6 5.1-25.8 5.1s-17.8-1.7-25.8-5.1c-8-3.4-15.1-8.2-21.1-14.2-6-6-10.8-13-14.2-21.1-3.4-8-5.1-16.6-5.1-25.8s1.7-17.8 5.1-25.8c3.4-8 8.2-15.1 14.2-21.1 6-6 13-8.4 21.1-11.9 8-3.4 16.6-5.1 25.8-5.1s17.8 1.7 25.8 5.1c8 3.4 15.1 5.8 21.1 11.9 6 6 10.7 13.1 14.2 21.1 3.4 8 5.1 16.6 5.1 25.8zm-15.5 0c0-7.3-1.3-14-3.9-20.3-2.6-6.3-6.2-11.7-10.8-16.3-4.6-4.6-10-8.2-16.2-10.9-6.2-2.7-12.8-4-19.8-4s-13.6 1.3-19.8 4c-6.2 2.7-11.6 6.3-16.2 10.9-4.6 4.6-8.2 10-10.8 16.3-2.6 6.3-3.9 13.1-3.9 20.3 0 7.3 1.3 14 3.9 20.3 2.6 6.3 6.2 11.7 10.8 16.3 4.6 4.6 10 8.2 16.2 10.9 6.2 2.7 12.8 4 19.8 4s13.6-1.3 19.8-4c6.2-2.7 11.6-6.3 16.2-10.9 4.6-4.6 8.2-10 10.8-16.3 2.6-6.3 3.9-13.1 3.9-20.3zm-94.8 96.7v-6.3l88.9-10-242.9 13.4c.6-2.2 1.1-4.6 1.4-7.2.3-2 .5-4.2.6-6.5l64.8-8.1-64.9 1.9c0-.4-.1-.7-.1-1.1-2.8-17.2-25.5-23.7-25.5-23.7l-1.1-26.3h23.8l19 41.8h17.1L348.6 152l-62.2 131.4h17.1l19-41.8h23.6L345 268s-22.7 6.5-25.5 23.7c-.1.3-.1.7-.1 1.1l-64.9-1.9 64.8 8.1c.1 2.3.3 4.4.6 6.5.3 2.6.8 5 1.4 7.2L78.4 299.2l88.9 10v6.3c-5.9.9-10.5 6-10.5 12.2 0 6.8 5.6 12.4 12.4 12.4 6.8 0 12.4-5.6 12.4-12.4 0-6.2-4.6-11.3-10.5-12.2v-5.8l80.3 9v5.4c-5.7 1.1-9.9 6.2-9.9 12.1 0 6.8 5.6 10.2 12.4 10.2 6.8 0 12.4-3.4 12.4-10.2 0-6-4.3-11-9.9-12.1v-4.9l28.4 3.2v23.7h-5.9V360h5.9v-6.6h5v6.6h5.9v-13.8h-5.9V323l38.3 4.3c8.1 11.4 19 13.6 19 13.6l-.1 6.7-5.1.2-.1 12.1h4.1l.1-5h5.2l.1 5h4.1l-.1-12.1-5.1-.2-.1-6.7s10.9-2.1 19-13.6l38.3-4.3v23.2h-5.9V360h5.9v-6.6h5v6.6h5.9v-13.8h-5.9v-23.7l28.4-3.2v4.9c-5.7 1.1-9.9 6.2-9.9 12.1 0 6.8 5.6 10.2 12.4 10.2 6.8 0 12.4-3.4 12.4-10.2 0-6-4.3-11-9.9-12.1v-5.4l80.3-9v5.8c-5.9.9-10.5 6-10.5 12.2 0 6.8 5.6 12.4 12.4 12.4 6.8 0 12.4-5.6 12.4-12.4-.2-6.3-4.7-11.4-10.7-12.3zm-200.8-87.6l19.6-42.5 19.6 42.5h-17.9l-1.7-40.3-1.7 40.3h-17.9z"],
+ "aws": [640, 512, [], "f375", "M180.41 203.01c-.72 22.65 10.6 32.68 10.88 39.05a8.164 8.164 0 0 1-4.1 6.27l-12.8 8.96a10.66 10.66 0 0 1-5.63 1.92c-.43-.02-8.19 1.83-20.48-25.61a78.608 78.608 0 0 1-62.61 29.45c-16.28.89-60.4-9.24-58.13-56.21-1.59-38.28 34.06-62.06 70.93-60.05 7.1.02 21.6.37 46.99 6.27v-15.62c2.69-26.46-14.7-46.99-44.81-43.91-2.4.01-19.4-.5-45.84 10.11-7.36 3.38-8.3 2.82-10.75 2.82-7.41 0-4.36-21.48-2.94-24.2 5.21-6.4 35.86-18.35 65.94-18.18a76.857 76.857 0 0 1 55.69 17.28 70.285 70.285 0 0 1 17.67 52.36l-.01 69.29zM93.99 235.4c32.43-.47 46.16-19.97 49.29-30.47 2.46-10.05 2.05-16.41 2.05-27.4-9.67-2.32-23.59-4.85-39.56-4.87-15.15-1.14-42.82 5.63-41.74 32.26-1.24 16.79 11.12 31.4 29.96 30.48zm170.92 23.05c-7.86.72-11.52-4.86-12.68-10.37l-49.8-164.65c-.97-2.78-1.61-5.65-1.92-8.58a4.61 4.61 0 0 1 3.86-5.25c.24-.04-2.13 0 22.25 0 8.78-.88 11.64 6.03 12.55 10.37l35.72 140.83 33.16-140.83c.53-3.22 2.94-11.07 12.8-10.24h17.16c2.17-.18 11.11-.5 12.68 10.37l33.42 142.63L420.98 80.1c.48-2.18 2.72-11.37 12.68-10.37h19.72c.85-.13 6.15-.81 5.25 8.58-.43 1.85 3.41-10.66-52.75 169.9-1.15 5.51-4.82 11.09-12.68 10.37h-18.69c-10.94 1.15-12.51-9.66-12.68-10.75L328.67 110.7l-32.78 136.99c-.16 1.09-1.73 11.9-12.68 10.75h-18.3zm273.48 5.63c-5.88.01-33.92-.3-57.36-12.29a12.802 12.802 0 0 1-7.81-11.91v-10.75c0-8.45 6.2-6.9 8.83-5.89 10.04 4.06 16.48 7.14 28.81 9.6 36.65 7.53 52.77-2.3 56.72-4.48 13.15-7.81 14.19-25.68 5.25-34.95-10.48-8.79-15.48-9.12-53.13-21-4.64-1.29-43.7-13.61-43.79-52.36-.61-28.24 25.05-56.18 69.52-55.95 12.67-.01 46.43 4.13 55.57 15.62 1.35 2.09 2.02 4.55 1.92 7.04v10.11c0 4.44-1.62 6.66-4.87 6.66-7.71-.86-21.39-11.17-49.16-10.75-6.89-.36-39.89.91-38.41 24.97-.43 18.96 26.61 26.07 29.7 26.89 36.46 10.97 48.65 12.79 63.12 29.58 17.14 22.25 7.9 48.3 4.35 55.44-19.08 37.49-68.42 34.44-69.26 34.42zm40.2 104.86c-70.03 51.72-171.69 79.25-258.49 79.25A469.127 469.127 0 0 1 2.83 327.46c-6.53-5.89-.77-13.96 7.17-9.47a637.37 637.37 0 0 0 316.88 84.12 630.22 630.22 0 0 0 241.59-49.55c11.78-5 21.77 7.8 10.12 16.38zm29.19-33.29c-8.96-11.52-59.28-5.38-81.81-2.69-6.79.77-7.94-5.12-1.79-9.47 40.07-28.17 105.88-20.1 113.44-10.63 7.55 9.47-2.05 75.41-39.56 106.91-5.76 4.87-11.27 2.3-8.71-4.1 8.44-21.25 27.39-68.49 18.43-80.02z"],
+ "bandcamp": [512, 512, [], "f2d5", "M256,8C119,8,8,119,8,256S119,504,256,504,504,393,504,256,393,8,256,8Zm48.2,326.1h-181L207.9,178h181Z"],
+ "battle-net": [512, 512, [], "f835", "M448.61 225.62c26.87.18 35.57-7.43 38.92-12.37 12.47-16.32-7.06-47.6-52.85-71.33 17.76-33.58 30.11-63.68 36.34-85.3 3.38-11.83 1.09-19 .45-20.25-1.72 10.52-15.85 48.46-48.2 100.05-25-11.22-56.52-20.1-93.77-23.8-8.94-16.94-34.88-63.86-60.48-88.93C252.18 7.14 238.7 1.07 228.18.22h-.05c-13.83-1.55-22.67 5.85-27.4 11-17.2 18.53-24.33 48.87-25 84.07-7.24-12.35-17.17-24.63-28.5-25.93h-.18c-20.66-3.48-38.39 29.22-36 81.29-38.36 1.38-71 5.75-93 11.23-9.9 2.45-16.22 7.27-17.76 9.72 1-.38 22.4-9.22 111.56-9.22 5.22 53 29.75 101.82 26 93.19-9.73 15.4-38.24 62.36-47.31 97.7-5.87 22.88-4.37 37.61.15 47.14 5.57 12.75 16.41 16.72 23.2 18.26 25 5.71 55.38-3.63 86.7-21.14-7.53 12.84-13.9 28.51-9.06 39.34 7.31 19.65 44.49 18.66 88.44-9.45 20.18 32.18 40.07 57.94 55.7 74.12a39.79 39.79 0 0 0 8.75 7.09c5.14 3.21 8.58 3.37 8.58 3.37-8.24-6.75-34-38-62.54-91.78 22.22-16 45.65-38.87 67.47-69.27 122.82 4.6 143.29-24.76 148-31.64 14.67-19.88 3.43-57.44-57.32-93.69zm-77.85 106.22c23.81-37.71 30.34-67.77 29.45-92.33 27.86 17.57 47.18 37.58 49.06 58.83 1.14 12.93-8.1 29.12-78.51 33.5zM216.9 387.69c9.76-6.23 19.53-13.12 29.2-20.49 6.68 13.33 13.6 26.1 20.6 38.19-40.6 21.86-68.84 12.76-49.8-17.7zm215-171.35c-10.29-5.34-21.16-10.34-32.38-15.05a722.459 722.459 0 0 0 22.74-36.9c39.06 24.1 45.9 53.18 9.64 51.95zM279.18 398c-5.51-11.35-11-23.5-16.5-36.44 43.25 1.27 62.42-18.73 63.28-20.41 0 .07-25 15.64-62.53 12.25a718.78 718.78 0 0 0 85.06-84q13.06-15.31 24.93-31.11c-.36-.29-1.54-3-16.51-12-51.7 60.27-102.34 98-132.75 115.92-20.59-11.18-40.84-31.78-55.71-61.49-20-39.92-30-82.39-31.57-116.07 12.3.91 25.27 2.17 38.85 3.88-22.29 36.8-14.39 63-13.47 64.23 0-.07-.95-29.17 20.14-59.57a695.23 695.23 0 0 0 44.67 152.84c.93-.38 1.84.88 18.67-8.25-26.33-74.47-33.76-138.17-34-173.43 20-12.42 48.18-19.8 81.63-17.81 44.57 2.67 86.36 15.25 116.32 30.71q-10.69 15.66-23.33 32.47C365.63 152 339.1 145.84 337.5 146c.11 0 25.9 14.07 41.52 47.22a717.63 717.63 0 0 0-115.34-31.71 646.608 646.608 0 0 0-39.39-6.05c-.07.45-1.81 1.85-2.16 20.33C300 190.28 358.78 215.68 389.36 233c.74 23.55-6.95 51.61-25.41 79.57-24.6 37.31-56.39 67.23-84.77 85.43zm27.4-287c-44.56-1.66-73.58 7.43-94.69 20.67 2-52.3 21.31-76.38 38.21-75.28C267 52.15 305 108.55 306.58 111zm-130.65 3.1c.48 12.11 1.59 24.62 3.21 37.28-14.55-.85-28.74-1.25-42.4-1.26-.08 3.24-.12-51 24.67-49.59h.09c5.76 1.09 10.63 6.88 14.43 13.57zm-28.06 162c20.76 39.7 43.3 60.57 65.25 72.31-46.79 24.76-77.53 20-84.92 4.51-.2-.21-11.13-15.3 19.67-76.81zm210.06 74.8"],
+ "behance": [576, 512, [], "f1b4", "M232 237.2c31.8-15.2 48.4-38.2 48.4-74 0-70.6-52.6-87.8-113.3-87.8H0v354.4h171.8c64.4 0 124.9-30.9 124.9-102.9 0-44.5-21.1-77.4-64.7-89.7zM77.9 135.9H151c28.1 0 53.4 7.9 53.4 40.5 0 30.1-19.7 42.2-47.5 42.2h-79v-82.7zm83.3 233.7H77.9V272h84.9c34.3 0 56 14.3 56 50.6 0 35.8-25.9 47-57.6 47zm358.5-240.7H376V94h143.7v34.9zM576 305.2c0-75.9-44.4-139.2-124.9-139.2-78.2 0-131.3 58.8-131.3 135.8 0 79.9 50.3 134.7 131.3 134.7 61.3 0 101-27.6 120.1-86.3H509c-6.7 21.9-34.3 33.5-55.7 33.5-41.3 0-63-24.2-63-65.3h185.1c.3-4.2.6-8.7.6-13.2zM390.4 274c2.3-33.7 24.7-54.8 58.5-54.8 35.4 0 53.2 20.8 56.2 54.8H390.4z"],
+ "behance-square": [448, 512, [], "f1b5", "M186.5 293c0 19.3-14 25.4-31.2 25.4h-45.1v-52.9h46c18.6.1 30.3 7.8 30.3 27.5zm-7.7-82.3c0-17.7-13.7-21.9-28.9-21.9h-39.6v44.8H153c15.1 0 25.8-6.6 25.8-22.9zm132.3 23.2c-18.3 0-30.5 11.4-31.7 29.7h62.2c-1.7-18.5-11.3-29.7-30.5-29.7zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zM271.7 185h77.8v-18.9h-77.8V185zm-43 110.3c0-24.1-11.4-44.9-35-51.6 17.2-8.2 26.2-17.7 26.2-37 0-38.2-28.5-47.5-61.4-47.5H68v192h93.1c34.9-.2 67.6-16.9 67.6-55.9zM380 280.5c0-41.1-24.1-75.4-67.6-75.4-42.4 0-71.1 31.8-71.1 73.6 0 43.3 27.3 73 71.1 73 33.2 0 54.7-14.9 65.1-46.8h-33.7c-3.7 11.9-18.6 18.1-30.2 18.1-22.4 0-34.1-13.1-34.1-35.3h100.2c.1-2.3.3-4.8.3-7.2z"],
+ "bimobject": [448, 512, [], "f378", "M416 32H32C14.4 32 0 46.4 0 64v384c0 17.6 14.4 32 32 32h384c17.6 0 32-14.4 32-32V64c0-17.6-14.4-32-32-32zm-64 257.4c0 49.4-11.4 82.6-103.8 82.6h-16.9c-44.1 0-62.4-14.9-70.4-38.8h-.9V368H96V136h64v74.7h1.1c4.6-30.5 39.7-38.8 69.7-38.8h17.3c92.4 0 103.8 33.1 103.8 82.5v35zm-64-28.9v22.9c0 21.7-3.4 33.8-38.4 33.8h-45.3c-28.9 0-44.1-6.5-44.1-35.7v-19c0-29.3 15.2-35.7 44.1-35.7h45.3c35-.2 38.4 12 38.4 33.7z"],
+ "bitbucket": [512, 512, [], "f171", "M22.2 32A16 16 0 0 0 6 47.8a26.35 26.35 0 0 0 .2 2.8l67.9 412.1a21.77 21.77 0 0 0 21.3 18.2h325.7a16 16 0 0 0 16-13.4L505 50.7a16 16 0 0 0-13.2-18.3 24.58 24.58 0 0 0-2.8-.2L22.2 32zm285.9 297.8h-104l-28.1-147h157.3l-25.2 147z"],
+ "bitcoin": [512, 512, [], "f379", "M504 256c0 136.967-111.033 248-248 248S8 392.967 8 256 119.033 8 256 8s248 111.033 248 248zm-141.651-35.33c4.937-32.999-20.191-50.739-54.55-62.573l11.146-44.702-27.213-6.781-10.851 43.524c-7.154-1.783-14.502-3.464-21.803-5.13l10.929-43.81-27.198-6.781-11.153 44.686c-5.922-1.349-11.735-2.682-17.377-4.084l.031-.14-37.53-9.37-7.239 29.062s20.191 4.627 19.765 4.913c11.022 2.751 13.014 10.044 12.68 15.825l-12.696 50.925c.76.194 1.744.473 2.829.907-.907-.225-1.876-.473-2.876-.713l-17.796 71.338c-1.349 3.348-4.767 8.37-12.471 6.464.271.395-19.78-4.937-19.78-4.937l-13.51 31.147 35.414 8.827c6.588 1.651 13.045 3.379 19.4 5.006l-11.262 45.213 27.182 6.781 11.153-44.733a1038.209 1038.209 0 0 0 21.687 5.627l-11.115 44.523 27.213 6.781 11.262-45.128c46.404 8.781 81.299 5.239 95.986-36.727 11.836-33.79-.589-53.281-25.004-65.991 17.78-4.098 31.174-15.792 34.747-39.949zm-62.177 87.179c-8.41 33.79-65.308 15.523-83.755 10.943l14.944-59.899c18.446 4.603 77.6 13.717 68.811 48.956zm8.417-87.667c-7.673 30.736-55.031 15.12-70.393 11.292l13.548-54.327c15.363 3.828 64.836 10.973 56.845 43.035z"],
+ "bity": [496, 512, [], "f37a", "M78.4 67.2C173.8-22 324.5-24 421.5 71c14.3 14.1-6.4 37.1-22.4 21.5-84.8-82.4-215.8-80.3-298.9-3.2-16.3 15.1-36.5-8.3-21.8-22.1zm98.9 418.6c19.3 5.7 29.3-23.6 7.9-30C73 421.9 9.4 306.1 37.7 194.8c5-19.6-24.9-28.1-30.2-7.1-32.1 127.4 41.1 259.8 169.8 298.1zm148.1-2c121.9-40.2 192.9-166.9 164.4-291-4.5-19.7-34.9-13.8-30 7.9 24.2 107.7-37.1 217.9-143.2 253.4-21.2 7-10.4 36 8.8 29.7zm-62.9-79l.2-71.8c0-8.2-6.6-14.8-14.8-14.8-8.2 0-14.8 6.7-14.8 14.8l-.2 71.8c0 8.2 6.6 14.8 14.8 14.8s14.8-6.6 14.8-14.8zm71-269c2.1 90.9 4.7 131.9-85.5 132.5-92.5-.7-86.9-44.3-85.5-132.5 0-21.8-32.5-19.6-32.5 0v71.6c0 69.3 60.7 90.9 118 90.1 57.3.8 118-20.8 118-90.1v-71.6c0-19.6-32.5-21.8-32.5 0z"],
+ "black-tie": [448, 512, [], "f27e", "M0 32v448h448V32H0zm316.5 325.2L224 445.9l-92.5-88.7 64.5-184-64.5-86.6h184.9L252 173.2l64.5 184z"],
+ "blackberry": [512, 512, [], "f37b", "M166 116.9c0 23.4-16.4 49.1-72.5 49.1H23.4l21-88.8h67.8c42.1 0 53.8 23.3 53.8 39.7zm126.2-39.7h-67.8L205.7 166h70.1c53.8 0 70.1-25.7 70.1-49.1.1-16.4-11.6-39.7-53.7-39.7zM88.8 208.1H21L0 296.9h70.1c56.1 0 72.5-23.4 72.5-49.1 0-16.3-11.7-39.7-53.8-39.7zm180.1 0h-67.8l-18.7 88.8h70.1c53.8 0 70.1-23.4 70.1-49.1 0-16.3-11.7-39.7-53.7-39.7zm189.3-53.8h-67.8l-18.7 88.8h70.1c53.8 0 70.1-23.4 70.1-49.1.1-16.3-11.6-39.7-53.7-39.7zm-28 137.9h-67.8L343.7 381h70.1c56.1 0 70.1-23.4 70.1-49.1 0-16.3-11.6-39.7-53.7-39.7zM240.8 346H173l-18.7 88.8h70.1c56.1 0 70.1-25.7 70.1-49.1.1-16.3-11.6-39.7-53.7-39.7z"],
+ "blogger": [448, 512, [], "f37c", "M162.4 196c4.8-4.9 6.2-5.1 36.4-5.1 27.2 0 28.1.1 32.1 2.1 5.8 2.9 8.3 7 8.3 13.6 0 5.9-2.4 10-7.6 13.4-2.8 1.8-4.5 1.9-31.1 2.1-16.4.1-29.5-.2-31.5-.8-10.3-2.9-14.1-17.7-6.6-25.3zm61.4 94.5c-53.9 0-55.8.2-60.2 4.1-3.5 3.1-5.7 9.4-5.1 13.9.7 4.7 4.8 10.1 9.2 12 2.2 1 14.1 1.7 56.3 1.2l47.9-.6 9.2-1.5c9-5.1 10.5-17.4 3.1-24.4-5.3-4.7-5-4.7-60.4-4.7zm223.4 130.1c-3.5 28.4-23 50.4-51.1 57.5-7.2 1.8-9.7 1.9-172.9 1.8-157.8 0-165.9-.1-172-1.8-8.4-2.2-15.6-5.5-22.3-10-5.6-3.8-13.9-11.8-17-16.4-3.8-5.6-8.2-15.3-10-22C.1 423 0 420.3 0 256.3 0 93.2 0 89.7 1.8 82.6 8.1 57.9 27.7 39 53 33.4c7.3-1.6 332.1-1.9 340-.3 21.2 4.3 37.9 17.1 47.6 36.4 7.7 15.3 7-1.5 7.3 180.6.2 115.8 0 164.5-.7 170.5zm-85.4-185.2c-1.1-5-4.2-9.6-7.7-11.5-1.1-.6-8-1.3-15.5-1.7-12.4-.6-13.8-.8-17.8-3.1-6.2-3.6-7.9-7.6-8-18.3 0-20.4-8.5-39.4-25.3-56.5-12-12.2-25.3-20.5-40.6-25.1-3.6-1.1-11.8-1.5-39.2-1.8-42.9-.5-52.5.4-67.1 6.2-27 10.7-46.3 33.4-53.4 62.4-1.3 5.4-1.6 14.2-1.9 64.3-.4 62.8 0 72.1 4 84.5 9.7 30.7 37.1 53.4 64.6 58.4 9.2 1.7 122.2 2.1 133.7.5 20.1-2.7 35.9-10.8 50.7-25.9 10.7-10.9 17.4-22.8 21.8-38.5 3.2-10.9 2.9-88.4 1.7-93.9z"],
+ "blogger-b": [448, 512, [], "f37d", "M446.6 222.7c-1.8-8-6.8-15.4-12.5-18.5-1.8-1-13-2.2-25-2.7-20.1-.9-22.3-1.3-28.7-5-10.1-5.9-12.8-12.3-12.9-29.5-.1-33-13.8-63.7-40.9-91.3-19.3-19.7-40.9-33-65.5-40.5-5.9-1.8-19.1-2.4-63.3-2.9-69.4-.8-84.8.6-108.4 10C45.9 59.5 14.7 96.1 3.3 142.9 1.2 151.7.7 165.8.2 246.8c-.6 101.5.1 116.4 6.4 136.5 15.6 49.6 59.9 86.3 104.4 94.3 14.8 2.7 197.3 3.3 216 .8 32.5-4.4 58-17.5 81.9-41.9 17.3-17.7 28.1-36.8 35.2-62.1 4.9-17.6 4.5-142.8 2.5-151.7zm-322.1-63.6c7.8-7.9 10-8.2 58.8-8.2 43.9 0 45.4.1 51.8 3.4 9.3 4.7 13.4 11.3 13.4 21.9 0 9.5-3.8 16.2-12.3 21.6-4.6 2.9-7.3 3.1-50.3 3.3-26.5.2-47.7-.4-50.8-1.2-16.6-4.7-22.8-28.5-10.6-40.8zm191.8 199.8l-14.9 2.4-77.5.9c-68.1.8-87.3-.4-90.9-2-7.1-3.1-13.8-11.7-14.9-19.4-1.1-7.3 2.6-17.3 8.2-22.4 7.1-6.4 10.2-6.6 97.3-6.7 89.6-.1 89.1-.1 97.6 7.8 12.1 11.3 9.5 31.2-4.9 39.4z"],
+ "bluetooth": [448, 512, [], "f293", "M292.6 171.1L249.7 214l-.3-86 43.2 43.1m-43.2 219.8l43.1-43.1-42.9-42.9-.2 86zM416 259.4C416 465 344.1 512 230.9 512S32 465 32 259.4 115.4 0 228.6 0 416 53.9 416 259.4zm-158.5 0l79.4-88.6L211.8 36.5v176.9L138 139.6l-27 26.9 92.7 93-92.7 93 26.9 26.9 73.8-73.8 2.3 170 127.4-127.5-83.9-88.7z"],
+ "bluetooth-b": [320, 512, [], "f294", "M196.48 260.023l92.626-103.333L143.125 0v206.33l-86.111-86.111-31.406 31.405 108.061 108.399L25.608 368.422l31.406 31.405 86.111-86.111L145.84 512l148.552-148.644-97.912-103.333zm40.86-102.996l-49.977 49.978-.338-100.295 50.315 50.317zM187.363 313.04l49.977 49.978-50.315 50.316.338-100.294z"],
+ "bootstrap": [576, 512, [], "f836", "M333.5,201.4c0-22.1-15.6-34.3-43-34.3h-50.4v71.2h42.5C315.4,238.2,333.5,225,333.5,201.4z M517,188.6 c-9.5-30.9-10.9-68.8-9.8-98.1c1.1-30.5-22.7-58.5-54.7-58.5H123.7c-32.1,0-55.8,28.1-54.7,58.5c1,29.3-0.3,67.2-9.8,98.1 c-9.6,31-25.7,50.6-52.2,53.1v28.5c26.4,2.5,42.6,22.1,52.2,53.1c9.5,30.9,10.9,68.8,9.8,98.1c-1.1,30.5,22.7,58.5,54.7,58.5h328.7 c32.1,0,55.8-28.1,54.7-58.5c-1-29.3,0.3-67.2,9.8-98.1c9.6-31,25.7-50.6,52.1-53.1v-28.5C542.7,239.2,526.5,219.6,517,188.6z M300.2,375.1h-97.9V136.8h97.4c43.3,0,71.7,23.4,71.7,59.4c0,25.3-19.1,47.9-43.5,51.8v1.3c33.2,3.6,55.5,26.6,55.5,58.3 C383.4,349.7,352.1,375.1,300.2,375.1z M290.2,266.4h-50.1v78.4h52.3c34.2,0,52.3-13.7,52.3-39.5 C344.7,279.6,326.1,266.4,290.2,266.4z"],
+ "btc": [384, 512, [], "f15a", "M310.204 242.638c27.73-14.18 45.377-39.39 41.28-81.3-5.358-57.351-52.458-76.573-114.85-81.929V0h-48.528v77.203c-12.605 0-25.525.315-38.444.63V0h-48.528v79.409c-17.842.539-38.622.276-97.37 0v51.678c38.314-.678 58.417-3.14 63.023 21.427v217.429c-2.925 19.492-18.524 16.685-53.255 16.071L3.765 443.68c88.481 0 97.37.315 97.37.315V512h48.528v-67.06c13.234.315 26.154.315 38.444.315V512h48.528v-68.005c81.299-4.412 135.647-24.894 142.895-101.467 5.671-61.446-23.32-88.862-69.326-99.89zM150.608 134.553c27.415 0 113.126-8.507 113.126 48.528 0 54.515-85.71 48.212-113.126 48.212v-96.74zm0 251.776V279.821c32.772 0 133.127-9.138 133.127 53.255-.001 60.186-100.355 53.253-133.127 53.253z"],
+ "buffer": [448, 512, [], "f837", "M427.84 380.67l-196.5 97.82a18.6 18.6 0 0 1-14.67 0L20.16 380.67c-4-2-4-5.28 0-7.29L67.22 350a18.65 18.65 0 0 1 14.69 0l134.76 67a18.51 18.51 0 0 0 14.67 0l134.76-67a18.62 18.62 0 0 1 14.68 0l47.06 23.43c4.05 1.96 4.05 5.24 0 7.24zm0-136.53l-47.06-23.43a18.62 18.62 0 0 0-14.68 0l-134.76 67.08a18.68 18.68 0 0 1-14.67 0L81.91 220.71a18.65 18.65 0 0 0-14.69 0l-47.06 23.43c-4 2-4 5.29 0 7.31l196.51 97.8a18.6 18.6 0 0 0 14.67 0l196.5-97.8c4.05-2.02 4.05-5.3 0-7.31zM20.16 130.42l196.5 90.29a20.08 20.08 0 0 0 14.67 0l196.51-90.29c4-1.86 4-4.89 0-6.74L231.33 33.4a19.88 19.88 0 0 0-14.67 0l-196.5 90.28c-4.05 1.85-4.05 4.88 0 6.74z"],
+ "buromobelexperte": [448, 512, [], "f37f", "M0 32v128h128V32H0zm120 120H8V40h112v112zm40-120v128h128V32H160zm120 120H168V40h112v112zm40-120v128h128V32H320zm120 120H328V40h112v112zM0 192v128h128V192H0zm120 120H8V200h112v112zm40-120v128h128V192H160zm120 120H168V200h112v112zm40-120v128h128V192H320zm120 120H328V200h112v112zM0 352v128h128V352H0zm120 120H8V360h112v112zm40-120v128h128V352H160zm120 120H168V360h112v112zm40-120v128h128V352H320z"],
+ "buy-n-large": [576, 512, [], "f8a6", "M288 32C133.27 32 7.79 132.32 7.79 256S133.27 480 288 480s280.21-100.32 280.21-224S442.73 32 288 32zm-85.39 357.19L64.1 390.55l77.25-290.74h133.44c63.15 0 84.93 28.65 78 72.84a60.24 60.24 0 0 1-1.5 6.85 77.39 77.39 0 0 0-17.21-1.93c-42.35 0-76.69 33.88-76.69 75.65 0 37.14 27.14 68 62.93 74.45-18.24 37.16-56.16 60.92-117.71 61.52zM358 207.11h32l-22.16 90.31h-35.41l-11.19-35.63-7.83 35.63h-37.83l26.63-90.31h31.34l15 36.75zm145.86 182.08H306.79L322.63 328a78.8 78.8 0 0 0 11.47.83c42.34 0 76.69-33.87 76.69-75.65 0-32.65-21-60.46-50.38-71.06l21.33-82.35h92.5l-53.05 205.36h103.87zM211.7 269.39H187l-13.8 56.47h24.7c16.14 0 32.11-3.18 37.94-26.65 5.56-22.31-7.99-29.82-24.14-29.82zM233 170h-21.34L200 217.71h21.37c18 0 35.38-14.64 39.21-30.14C265.23 168.71 251.07 170 233 170z"],
+ "buysellads": [448, 512, [], "f20d", "M224 150.7l42.9 160.7h-85.8L224 150.7zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-65.3 325.3l-94.5-298.7H159.8L65.3 405.3H156l111.7-91.6 24.2 91.6h90.8z"],
+ "canadian-maple-leaf": [512, 512, [], "f785", "M383.8 351.7c2.5-2.5 105.2-92.4 105.2-92.4l-17.5-7.5c-10-4.9-7.4-11.5-5-17.4 2.4-7.6 20.1-67.3 20.1-67.3s-47.7 10-57.7 12.5c-7.5 2.4-10-2.5-12.5-7.5s-15-32.4-15-32.4-52.6 59.9-55.1 62.3c-10 7.5-20.1 0-17.6-10 0-10 27.6-129.6 27.6-129.6s-30.1 17.4-40.1 22.4c-7.5 5-12.6 5-17.6-5C293.5 72.3 255.9 0 255.9 0s-37.5 72.3-42.5 79.8c-5 10-10 10-17.6 5-10-5-40.1-22.4-40.1-22.4S183.3 182 183.3 192c2.5 10-7.5 17.5-17.6 10-2.5-2.5-55.1-62.3-55.1-62.3S98.1 167 95.6 172s-5 9.9-12.5 7.5C73 177 25.4 167 25.4 167s17.6 59.7 20.1 67.3c2.4 6 5 12.5-5 17.4L23 259.3s102.6 89.9 105.2 92.4c5.1 5 10 7.5 5.1 22.5-5.1 15-10.1 35.1-10.1 35.1s95.2-20.1 105.3-22.6c8.7-.9 18.3 2.5 18.3 12.5S241 512 241 512h30s-5.8-102.7-5.8-112.8 9.5-13.4 18.4-12.5c10 2.5 105.2 22.6 105.2 22.6s-5-20.1-10-35.1 0-17.5 5-22.5z"],
+ "cc-amazon-pay": [576, 512, [], "f42d", "M124.7 201.8c.1-11.8 0-23.5 0-35.3v-35.3c0-1.3.4-2 1.4-2.7 11.5-8 24.1-12.1 38.2-11.1 12.5.9 22.7 7 28.1 21.7 3.3 8.9 4.1 18.2 4.1 27.7 0 8.7-.7 17.3-3.4 25.6-5.7 17.8-18.7 24.7-35.7 23.9-11.7-.5-21.9-5-31.4-11.7-.9-.8-1.4-1.6-1.3-2.8zm154.9 14.6c4.6 1.8 9.3 2 14.1 1.5 11.6-1.2 21.9-5.7 31.3-12.5.9-.6 1.3-1.3 1.3-2.5-.1-3.9 0-7.9 0-11.8 0-4-.1-8 0-12 0-1.4-.4-2-1.8-2.2-7-.9-13.9-2.2-20.9-2.9-7-.6-14-.3-20.8 1.9-6.7 2.2-11.7 6.2-13.7 13.1-1.6 5.4-1.6 10.8.1 16.2 1.6 5.5 5.2 9.2 10.4 11.2zM576 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zm-207.5 23.9c.4 1.7.9 3.4 1.6 5.1 16.5 40.6 32.9 81.3 49.5 121.9 1.4 3.5 1.7 6.4.2 9.9-2.8 6.2-4.9 12.6-7.8 18.7-2.6 5.5-6.7 9.5-12.7 11.2-4.2 1.1-8.5 1.3-12.9.9-2.1-.2-4.2-.7-6.3-.8-2.8-.2-4.2 1.1-4.3 4-.1 2.8-.1 5.6 0 8.3.1 4.6 1.6 6.7 6.2 7.5 4.7.8 9.4 1.6 14.2 1.7 14.3.3 25.7-5.4 33.1-17.9 2.9-4.9 5.6-10.1 7.7-15.4 19.8-50.1 39.5-100.3 59.2-150.5.6-1.5 1.1-3 1.3-4.6.4-2.4-.7-3.6-3.1-3.7-5.6-.1-11.1 0-16.7 0-3.1 0-5.3 1.4-6.4 4.3-.4 1.1-.9 2.3-1.3 3.4l-29.1 83.7c-2.1 6.1-4.2 12.1-6.5 18.6-.4-.9-.6-1.4-.8-1.9-10.8-29.9-21.6-59.9-32.4-89.8-1.7-4.7-3.5-9.5-5.3-14.2-.9-2.5-2.7-4-5.4-4-6.4-.1-12.8-.2-19.2-.1-2.2 0-3.3 1.6-2.8 3.7zM242.4 206c1.7 11.7 7.6 20.8 18 26.6 9.9 5.5 20.7 6.2 31.7 4.6 12.7-1.9 23.9-7.3 33.8-15.5.4-.3.8-.6 1.4-1 .5 3.2.9 6.2 1.5 9.2.5 2.6 2.1 4.3 4.5 4.4 4.6.1 9.1.1 13.7 0 2.3-.1 3.8-1.6 4-3.9.1-.8.1-1.6.1-2.3v-88.8c0-3.6-.2-7.2-.7-10.8-1.6-10.8-6.2-19.7-15.9-25.4-5.6-3.3-11.8-5-18.2-5.9-3-.4-6-.7-9.1-1.1h-10c-.8.1-1.6.3-2.5.3-8.2.4-16.3 1.4-24.2 3.5-5.1 1.3-10 3.2-15 4.9-3 1-4.5 3.2-4.4 6.5.1 2.8-.1 5.6 0 8.3.1 4.1 1.8 5.2 5.7 4.1 6.5-1.7 13.1-3.5 19.7-4.8 10.3-1.9 20.7-2.7 31.1-1.2 5.4.8 10.5 2.4 14.1 7 3.1 4 4.2 8.8 4.4 13.7.3 6.9.2 13.9.3 20.8 0 .4-.1.7-.2 1.2-.4 0-.8 0-1.1-.1-8.8-2.1-17.7-3.6-26.8-4.1-9.5-.5-18.9.1-27.9 3.2-10.8 3.8-19.5 10.3-24.6 20.8-4.1 8.3-4.6 17-3.4 25.8zM98.7 106.9v175.3c0 .8 0 1.7.1 2.5.2 2.5 1.7 4.1 4.1 4.2 5.9.1 11.8.1 17.7 0 2.5 0 4-1.7 4.1-4.1.1-.8.1-1.7.1-2.5v-60.7c.9.7 1.4 1.2 1.9 1.6 15 12.5 32.2 16.6 51.1 12.9 17.1-3.4 28.9-13.9 36.7-29.2 5.8-11.6 8.3-24.1 8.7-37 .5-14.3-1-28.4-6.8-41.7-7.1-16.4-18.9-27.3-36.7-30.9-2.7-.6-5.5-.8-8.2-1.2h-7c-1.2.2-2.4.3-3.6.5-11.7 1.4-22.3 5.8-31.8 12.7-2 1.4-3.9 3-5.9 4.5-.1-.5-.3-.8-.4-1.2-.4-2.3-.7-4.6-1.1-6.9-.6-3.9-2.5-5.5-6.4-5.6h-9.7c-5.9-.1-6.9 1-6.9 6.8zM493.6 339c-2.7-.7-5.1 0-7.6 1-43.9 18.4-89.5 30.2-136.8 35.8-14.5 1.7-29.1 2.8-43.7 3.2-26.6.7-53.2-.8-79.6-4.3-17.8-2.4-35.5-5.7-53-9.9-37-8.9-72.7-21.7-106.7-38.8-8.8-4.4-17.4-9.3-26.1-14-3.8-2.1-6.2-1.5-8.2 2.1v1.7c1.2 1.6 2.2 3.4 3.7 4.8 36 32.2 76.6 56.5 122 72.9 21.9 7.9 44.4 13.7 67.3 17.5 14 2.3 28 3.8 42.2 4.5 3 .1 6 .2 9 .4.7 0 1.4.2 2.1.3h17.7c.7-.1 1.4-.3 2.1-.3 14.9-.4 29.8-1.8 44.6-4 21.4-3.2 42.4-8.1 62.9-14.7 29.6-9.6 57.7-22.4 83.4-40.1 2.8-1.9 5.7-3.8 8-6.2 4.3-4.4 2.3-10.4-3.3-11.9zm50.4-27.7c-.8-4.2-4-5.8-7.6-7-5.7-1.9-11.6-2.8-17.6-3.3-11-.9-22-.4-32.8 1.6-12 2.2-23.4 6.1-33.5 13.1-1.2.8-2.4 1.8-3.1 3-.6.9-.7 2.3-.5 3.4.3 1.3 1.7 1.6 3 1.5.6 0 1.2 0 1.8-.1l19.5-2.1c9.6-.9 19.2-1.5 28.8-.8 4.1.3 8.1 1.2 12 2.2 4.3 1.1 6.2 4.4 6.4 8.7.3 6.7-1.2 13.1-2.9 19.5-3.5 12.9-8.3 25.4-13.3 37.8-.3.8-.7 1.7-.8 2.5-.4 2.5 1 4 3.4 3.5 1.4-.3 3-1.1 4-2.1 3.7-3.6 7.5-7.2 10.6-11.2 10.7-13.8 17-29.6 20.7-46.6.7-3 1.2-6.1 1.7-9.1.2-4.7.2-9.6.2-14.5z"],
+ "cc-amex": [576, 512, [], "f1f3", "M325.1 167.8c0-16.4-14.1-18.4-27.4-18.4l-39.1-.3v69.3H275v-25.1h18c18.4 0 14.5 10.3 14.8 25.1h16.6v-13.5c0-9.2-1.5-15.1-11-18.4 7.4-3 11.8-10.7 11.7-18.7zm-29.4 11.3H275v-15.3h21c5.1 0 10.7 1 10.7 7.4 0 6.6-5.3 7.9-11 7.9zM279 268.6h-52.7l-21 22.8-20.5-22.8h-66.5l-.1 69.3h65.4l21.3-23 20.4 23h32.2l.1-23.3c18.9 0 49.3 4.6 49.3-23.3 0-17.3-12.3-22.7-27.9-22.7zm-103.8 54.7h-40.6v-13.8h36.3v-14.1h-36.3v-12.5h41.7l17.9 20.2zm65.8 8.2l-25.3-28.1L241 276zm37.8-31h-21.2v-17.6h21.5c5.6 0 10.2 2.3 10.2 8.4 0 6.4-4.6 9.2-10.5 9.2zm-31.6-136.7v-14.6h-55.5v69.3h55.5v-14.3h-38.9v-13.8h37.8v-14.1h-37.8v-12.5zM576 255.4h-.2zm-194.6 31.9c0-16.4-14.1-18.7-27.1-18.7h-39.4l-.1 69.3h16.6l.1-25.3h17.6c11 0 14.8 2 14.8 13.8l-.1 11.5h16.6l.1-13.8c0-8.9-1.8-15.1-11-18.4 7.7-3.1 11.8-10.8 11.9-18.4zm-29.2 11.2h-20.7v-15.6h21c5.1 0 10.7 1 10.7 7.4 0 6.9-5.4 8.2-11 8.2zm-172.8-80v-69.3h-27.6l-19.7 47-21.7-47H83.3v65.7l-28.1-65.7H30.7L1 218.5h17.9l6.4-15.3h34.5l6.4 15.3H100v-54.2l24 54.2h14.6l24-54.2v54.2zM31.2 188.8l11.2-27.6 11.5 27.6zm477.4 158.9v-4.5c-10.8 5.6-3.9 4.5-156.7 4.5 0-25.2.1-23.9 0-25.2-1.7-.1-3.2-.1-9.4-.1 0 17.9-.1 6.8-.1 25.3h-39.6c0-12.1.1-15.3.1-29.2-10 6-22.8 6.4-34.3 6.2 0 14.7-.1 8.3-.1 23h-48.9c-5.1-5.7-2.7-3.1-15.4-17.4-3.2 3.5-12.8 13.9-16.1 17.4h-82v-92.3h83.1c5 5.6 2.8 3.1 15.5 17.2 3.2-3.5 12.2-13.4 15.7-17.2h58c9.8 0 18 1.9 24.3 5.6v-5.6c54.3 0 64.3-1.4 75.7 5.1v-5.1h78.2v5.2c11.4-6.9 19.6-5.2 64.9-5.2v5c10.3-5.9 16.6-5.2 54.3-5V80c0-26.5-21.5-48-48-48h-480c-26.5 0-48 21.5-48 48v109.8c9.4-21.9 19.7-46 23.1-53.9h39.7c4.3 10.1 1.6 3.7 9 21.1v-21.1h46c2.9 6.2 11.1 24 13.9 30 5.8-13.6 10.1-23.9 12.6-30h103c0-.1 11.5 0 11.6 0 43.7.2 53.6-.8 64.4 5.3v-5.3H363v9.3c7.6-6.1 17.9-9.3 30.7-9.3h27.6c0 .5 1.9.3 2.3.3H456c4.2 9.8 2.6 6 8.8 20.6v-20.6h43.3c4.9 8-1-1.8 11.2 18.4v-18.4h39.9v92h-41.6c-5.4-9-1.4-2.2-13.2-21.9v21.9h-52.8c-6.4-14.8-.1-.3-6.6-15.3h-19c-4.2 10-2.2 5.2-6.4 15.3h-26.8c-12.3 0-22.3-3-29.7-8.9v8.9h-66.5c-.3-13.9-.1-24.8-.1-24.8-1.8-.3-3.4-.2-9.8-.2v25.1H151.2v-11.4c-2.5 5.6-2.7 5.9-5.1 11.4h-29.5c-4-8.9-2.9-6.4-5.1-11.4v11.4H58.6c-4.2-10.1-2.2-5.3-6.4-15.3H33c-4.2 10-2.2 5.2-6.4 15.3H0V432c0 26.5 21.5 48 48 48h480.1c26.5 0 48-21.5 48-48v-90.4c-12.7 8.3-32.7 6.1-67.5 6.1zm36.3-64.5H575v-14.6h-32.9c-12.8 0-23.8 6.6-23.8 20.7 0 33 42.7 12.8 42.7 27.4 0 5.1-4.3 6.4-8.4 6.4h-32l-.1 14.8h32c8.4 0 17.6-1.8 22.5-8.9v-25.8c-10.5-13.8-39.3-1.3-39.3-13.5 0-5.8 4.6-6.5 9.2-6.5zm-57 39.8h-32.2l-.1 14.8h32.2c14.8 0 26.2-5.6 26.2-22 0-33.2-42.9-11.2-42.9-26.3 0-5.6 4.9-6.4 9.2-6.4h30.4v-14.6h-33.2c-12.8 0-23.5 6.6-23.5 20.7 0 33 42.7 12.5 42.7 27.4-.1 5.4-4.7 6.4-8.8 6.4zm-42.2-40.1v-14.3h-55.2l-.1 69.3h55.2l.1-14.3-38.6-.3v-13.8H445v-14.1h-37.8v-12.5zm-56.3-108.1c-.3.2-1.4 2.2-1.4 7.6 0 6 .9 7.7 1.1 7.9.2.1 1.1.5 3.4.5l7.3-16.9c-1.1 0-2.1-.1-3.1-.1-5.6 0-7 .7-7.3 1zm20.4-10.5h-.1zm-16.2-15.2c-23.5 0-34 12-34 35.3 0 22.2 10.2 34 33 34h19.2l6.4-15.3h34.3l6.6 15.3h33.7v-51.9l31.2 51.9h23.6v-69h-16.9v48.1l-29.1-48.1h-25.3v65.4l-27.9-65.4h-24.8l-23.5 54.5h-7.4c-13.3 0-16.1-8.1-16.1-19.9 0-23.8 15.7-20 33.1-19.7v-15.2zm42.1 12.1l11.2 27.6h-22.8zm-101.1-12v69.3h16.9v-69.3z"],
+ "cc-apple-pay": [576, 512, [], "f416", "M302.2 218.4c0 17.2-10.5 27.1-29 27.1h-24.3v-54.2h24.4c18.4 0 28.9 9.8 28.9 27.1zm47.5 62.6c0 8.3 7.2 13.7 18.5 13.7 14.4 0 25.2-9.1 25.2-21.9v-7.7l-23.5 1.5c-13.3.9-20.2 5.8-20.2 14.4zM576 79v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V79c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zM127.8 197.2c8.4.7 16.8-4.2 22.1-10.4 5.2-6.4 8.6-15 7.7-23.7-7.4.3-16.6 4.9-21.9 11.3-4.8 5.5-8.9 14.4-7.9 22.8zm60.6 74.5c-.2-.2-19.6-7.6-19.8-30-.2-18.7 15.3-27.7 16-28.2-8.8-13-22.4-14.4-27.1-14.7-12.2-.7-22.6 6.9-28.4 6.9-5.9 0-14.7-6.6-24.3-6.4-12.5.2-24.2 7.3-30.5 18.6-13.1 22.6-3.4 56 9.3 74.4 6.2 9.1 13.7 19.1 23.5 18.7 9.3-.4 13-6 24.2-6 11.3 0 14.5 6 24.3 5.9 10.2-.2 16.5-9.1 22.8-18.2 6.9-10.4 9.8-20.4 10-21zm135.4-53.4c0-26.6-18.5-44.8-44.9-44.8h-51.2v136.4h21.2v-46.6h29.3c26.8 0 45.6-18.4 45.6-45zm90 23.7c0-19.7-15.8-32.4-40-32.4-22.5 0-39.1 12.9-39.7 30.5h19.1c1.6-8.4 9.4-13.9 20-13.9 13 0 20.2 6 20.2 17.2v7.5l-26.4 1.6c-24.6 1.5-37.9 11.6-37.9 29.1 0 17.7 13.7 29.4 33.4 29.4 13.3 0 25.6-6.7 31.2-17.4h.4V310h19.6v-68zM516 210.9h-21.5l-24.9 80.6h-.4l-24.9-80.6H422l35.9 99.3-1.9 6c-3.2 10.2-8.5 14.2-17.9 14.2-1.7 0-4.9-.2-6.2-.3v16.4c1.2.4 6.5.5 8.1.5 20.7 0 30.4-7.9 38.9-31.8L516 210.9z"],
+ "cc-diners-club": [576, 512, [], "f24c", "M239.7 79.9c-96.9 0-175.8 78.6-175.8 175.8 0 96.9 78.9 175.8 175.8 175.8 97.2 0 175.8-78.9 175.8-175.8 0-97.2-78.6-175.8-175.8-175.8zm-39.9 279.6c-41.7-15.9-71.4-56.4-71.4-103.8s29.7-87.9 71.4-104.1v207.9zm79.8.3V151.6c41.7 16.2 71.4 56.7 71.4 104.1s-29.7 87.9-71.4 104.1zM528 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h480c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM329.7 448h-90.3c-106.2 0-193.8-85.5-193.8-190.2C45.6 143.2 133.2 64 239.4 64h90.3c105 0 200.7 79.2 200.7 193.8 0 104.7-95.7 190.2-200.7 190.2z"],
+ "cc-discover": [576, 512, [], "f1f2", "M520.4 196.1c0-7.9-5.5-12.1-15.6-12.1h-4.9v24.9h4.7c10.3 0 15.8-4.4 15.8-12.8zM528 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h480c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-44.1 138.9c22.6 0 52.9-4.1 52.9 24.4 0 12.6-6.6 20.7-18.7 23.2l25.8 34.4h-19.6l-22.2-32.8h-2.2v32.8h-16zm-55.9.1h45.3v14H444v18.2h28.3V217H444v22.2h29.3V253H428zm-68.7 0l21.9 55.2 22.2-55.2h17.5l-35.5 84.2h-8.6l-35-84.2zm-55.9-3c24.7 0 44.6 20 44.6 44.6 0 24.7-20 44.6-44.6 44.6-24.7 0-44.6-20-44.6-44.6 0-24.7 20-44.6 44.6-44.6zm-49.3 6.1v19c-20.1-20.1-46.8-4.7-46.8 19 0 25 27.5 38.5 46.8 19.2v19c-29.7 14.3-63.3-5.7-63.3-38.2 0-31.2 33.1-53 63.3-38zm-97.2 66.3c11.4 0 22.4-15.3-3.3-24.4-15-5.5-20.2-11.4-20.2-22.7 0-23.2 30.6-31.4 49.7-14.3l-8.4 10.8c-10.4-11.6-24.9-6.2-24.9 2.5 0 4.4 2.7 6.9 12.3 10.3 18.2 6.6 23.6 12.5 23.6 25.6 0 29.5-38.8 37.4-56.6 11.3l10.3-9.9c3.7 7.1 9.9 10.8 17.5 10.8zM55.4 253H32v-82h23.4c26.1 0 44.1 17 44.1 41.1 0 18.5-13.2 40.9-44.1 40.9zm67.5 0h-16v-82h16zM544 433c0 8.2-6.8 15-15 15H128c189.6-35.6 382.7-139.2 416-160zM74.1 191.6c-5.2-4.9-11.6-6.6-21.9-6.6H48v54.2h4.2c10.3 0 17-2 21.9-6.4 5.7-5.2 8.9-12.8 8.9-20.7s-3.2-15.5-8.9-20.5z"],
+ "cc-jcb": [576, 512, [], "f24b", "M431.5 244.3V212c41.2 0 38.5.2 38.5.2 7.3 1.3 13.3 7.3 13.3 16 0 8.8-6 14.5-13.3 15.8-1.2.4-3.3.3-38.5.3zm42.8 20.2c-2.8-.7-3.3-.5-42.8-.5v35c39.6 0 40 .2 42.8-.5 7.5-1.5 13.5-8 13.5-17 0-8.7-6-15.5-13.5-17zM576 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zM182 192.3h-57c0 67.1 10.7 109.7-35.8 109.7-19.5 0-38.8-5.7-57.2-14.8v28c30 8.3 68 8.3 68 8.3 97.9 0 82-47.7 82-131.2zm178.5 4.5c-63.4-16-165-14.9-165 59.3 0 77.1 108.2 73.6 165 59.2V287C312.9 311.7 253 309 253 256s59.8-55.6 107.5-31.2v-28zM544 286.5c0-18.5-16.5-30.5-38-32v-.8c19.5-2.7 30.3-15.5 30.3-30.2 0-19-15.7-30-37-31 0 0 6.3-.3-120.3-.3v127.5h122.7c24.3.1 42.3-12.9 42.3-33.2z"],
+ "cc-mastercard": [576, 512, [], "f1f1", "M482.9 410.3c0 6.8-4.6 11.7-11.2 11.7-6.8 0-11.2-5.2-11.2-11.7 0-6.5 4.4-11.7 11.2-11.7 6.6 0 11.2 5.2 11.2 11.7zm-310.8-11.7c-7.1 0-11.2 5.2-11.2 11.7 0 6.5 4.1 11.7 11.2 11.7 6.5 0 10.9-4.9 10.9-11.7-.1-6.5-4.4-11.7-10.9-11.7zm117.5-.3c-5.4 0-8.7 3.5-9.5 8.7h19.1c-.9-5.7-4.4-8.7-9.6-8.7zm107.8.3c-6.8 0-10.9 5.2-10.9 11.7 0 6.5 4.1 11.7 10.9 11.7 6.8 0 11.2-4.9 11.2-11.7 0-6.5-4.4-11.7-11.2-11.7zm105.9 26.1c0 .3.3.5.3 1.1 0 .3-.3.5-.3 1.1-.3.3-.3.5-.5.8-.3.3-.5.5-1.1.5-.3.3-.5.3-1.1.3-.3 0-.5 0-1.1-.3-.3 0-.5-.3-.8-.5-.3-.3-.5-.5-.5-.8-.3-.5-.3-.8-.3-1.1 0-.5 0-.8.3-1.1 0-.5.3-.8.5-1.1.3-.3.5-.3.8-.5.5-.3.8-.3 1.1-.3.5 0 .8 0 1.1.3.5.3.8.3 1.1.5s.2.6.5 1.1zm-2.2 1.4c.5 0 .5-.3.8-.3.3-.3.3-.5.3-.8 0-.3 0-.5-.3-.8-.3 0-.5-.3-1.1-.3h-1.6v3.5h.8V426h.3l1.1 1.4h.8l-1.1-1.3zM576 81v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V81c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zM64 220.6c0 76.5 62.1 138.5 138.5 138.5 27.2 0 53.9-8.2 76.5-23.1-72.9-59.3-72.4-171.2 0-230.5-22.6-15-49.3-23.1-76.5-23.1-76.4-.1-138.5 62-138.5 138.2zm224 108.8c70.5-55 70.2-162.2 0-217.5-70.2 55.3-70.5 162.6 0 217.5zm-142.3 76.3c0-8.7-5.7-14.4-14.7-14.7-4.6 0-9.5 1.4-12.8 6.5-2.4-4.1-6.5-6.5-12.2-6.5-3.8 0-7.6 1.4-10.6 5.4V392h-8.2v36.7h8.2c0-18.9-2.5-30.2 9-30.2 10.2 0 8.2 10.2 8.2 30.2h7.9c0-18.3-2.5-30.2 9-30.2 10.2 0 8.2 10 8.2 30.2h8.2v-23zm44.9-13.7h-7.9v4.4c-2.7-3.3-6.5-5.4-11.7-5.4-10.3 0-18.2 8.2-18.2 19.3 0 11.2 7.9 19.3 18.2 19.3 5.2 0 9-1.9 11.7-5.4v4.6h7.9V392zm40.5 25.6c0-15-22.9-8.2-22.9-15.2 0-5.7 11.9-4.8 18.5-1.1l3.3-6.5c-9.4-6.1-30.2-6-30.2 8.2 0 14.3 22.9 8.3 22.9 15 0 6.3-13.5 5.8-20.7.8l-3.5 6.3c11.2 7.6 32.6 6 32.6-7.5zm35.4 9.3l-2.2-6.8c-3.8 2.1-12.2 4.4-12.2-4.1v-16.6h13.1V392h-13.1v-11.2h-8.2V392h-7.6v7.3h7.6V416c0 17.6 17.3 14.4 22.6 10.9zm13.3-13.4h27.5c0-16.2-7.4-22.6-17.4-22.6-10.6 0-18.2 7.9-18.2 19.3 0 20.5 22.6 23.9 33.8 14.2l-3.8-6c-7.8 6.4-19.6 5.8-21.9-4.9zm59.1-21.5c-4.6-2-11.6-1.8-15.2 4.4V392h-8.2v36.7h8.2V408c0-11.6 9.5-10.1 12.8-8.4l2.4-7.6zm10.6 18.3c0-11.4 11.6-15.1 20.7-8.4l3.8-6.5c-11.6-9.1-32.7-4.1-32.7 15 0 19.8 22.4 23.8 32.7 15l-3.8-6.5c-9.2 6.5-20.7 2.6-20.7-8.6zm66.7-18.3H408v4.4c-8.3-11-29.9-4.8-29.9 13.9 0 19.2 22.4 24.7 29.9 13.9v4.6h8.2V392zm33.7 0c-2.4-1.2-11-2.9-15.2 4.4V392h-7.9v36.7h7.9V408c0-11 9-10.3 12.8-8.4l2.4-7.6zm40.3-14.9h-7.9v19.3c-8.2-10.9-29.9-5.1-29.9 13.9 0 19.4 22.5 24.6 29.9 13.9v4.6h7.9v-51.7zm7.6-75.1v4.6h.8V302h1.9v-.8h-4.6v.8h1.9zm6.6 123.8c0-.5 0-1.1-.3-1.6-.3-.3-.5-.8-.8-1.1-.3-.3-.8-.5-1.1-.8-.5 0-1.1-.3-1.6-.3-.3 0-.8.3-1.4.3-.5.3-.8.5-1.1.8-.5.3-.8.8-.8 1.1-.3.5-.3 1.1-.3 1.6 0 .3 0 .8.3 1.4 0 .3.3.8.8 1.1.3.3.5.5 1.1.8.5.3 1.1.3 1.4.3.5 0 1.1 0 1.6-.3.3-.3.8-.5 1.1-.8.3-.3.5-.8.8-1.1.3-.6.3-1.1.3-1.4zm3.2-124.7h-1.4l-1.6 3.5-1.6-3.5h-1.4v5.4h.8v-4.1l1.6 3.5h1.1l1.4-3.5v4.1h1.1v-5.4zm4.4-80.5c0-76.2-62.1-138.3-138.5-138.3-27.2 0-53.9 8.2-76.5 23.1 72.1 59.3 73.2 171.5 0 230.5 22.6 15 49.5 23.1 76.5 23.1 76.4.1 138.5-61.9 138.5-138.4z"],
+ "cc-paypal": [576, 512, [], "f1f4", "M186.3 258.2c0 12.2-9.7 21.5-22 21.5-9.2 0-16-5.2-16-15 0-12.2 9.5-22 21.7-22 9.3 0 16.3 5.7 16.3 15.5zM80.5 209.7h-4.7c-1.5 0-3 1-3.2 2.7l-4.3 26.7 8.2-.3c11 0 19.5-1.5 21.5-14.2 2.3-13.4-6.2-14.9-17.5-14.9zm284 0H360c-1.8 0-3 1-3.2 2.7l-4.2 26.7 8-.3c13 0 22-3 22-18-.1-10.6-9.6-11.1-18.1-11.1zM576 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zM128.3 215.4c0-21-16.2-28-34.7-28h-40c-2.5 0-5 2-5.2 4.7L32 294.2c-.3 2 1.2 4 3.2 4h19c2.7 0 5.2-2.9 5.5-5.7l4.5-26.6c1-7.2 13.2-4.7 18-4.7 28.6 0 46.1-17 46.1-45.8zm84.2 8.8h-19c-3.8 0-4 5.5-4.2 8.2-5.8-8.5-14.2-10-23.7-10-24.5 0-43.2 21.5-43.2 45.2 0 19.5 12.2 32.2 31.7 32.2 9 0 20.2-4.9 26.5-11.9-.5 1.5-1 4.7-1 6.2 0 2.3 1 4 3.2 4H200c2.7 0 5-2.9 5.5-5.7l10.2-64.3c.3-1.9-1.2-3.9-3.2-3.9zm40.5 97.9l63.7-92.6c.5-.5.5-1 .5-1.7 0-1.7-1.5-3.5-3.2-3.5h-19.2c-1.7 0-3.5 1-4.5 2.5l-26.5 39-11-37.5c-.8-2.2-3-4-5.5-4h-18.7c-1.7 0-3.2 1.8-3.2 3.5 0 1.2 19.5 56.8 21.2 62.1-2.7 3.8-20.5 28.6-20.5 31.6 0 1.8 1.5 3.2 3.2 3.2h19.2c1.8-.1 3.5-1.1 4.5-2.6zm159.3-106.7c0-21-16.2-28-34.7-28h-39.7c-2.7 0-5.2 2-5.5 4.7l-16.2 102c-.2 2 1.3 4 3.2 4h20.5c2 0 3.5-1.5 4-3.2l4.5-29c1-7.2 13.2-4.7 18-4.7 28.4 0 45.9-17 45.9-45.8zm84.2 8.8h-19c-3.8 0-4 5.5-4.3 8.2-5.5-8.5-14-10-23.7-10-24.5 0-43.2 21.5-43.2 45.2 0 19.5 12.2 32.2 31.7 32.2 9.3 0 20.5-4.9 26.5-11.9-.3 1.5-1 4.7-1 6.2 0 2.3 1 4 3.2 4H484c2.7 0 5-2.9 5.5-5.7l10.2-64.3c.3-1.9-1.2-3.9-3.2-3.9zm47.5-33.3c0-2-1.5-3.5-3.2-3.5h-18.5c-1.5 0-3 1.2-3.2 2.7l-16.2 104-.3.5c0 1.8 1.5 3.5 3.5 3.5h16.5c2.5 0 5-2.9 5.2-5.7L544 191.2v-.3zm-90 51.8c-12.2 0-21.7 9.7-21.7 22 0 9.7 7 15 16.2 15 12 0 21.7-9.2 21.7-21.5.1-9.8-6.9-15.5-16.2-15.5z"],
+ "cc-stripe": [576, 512, [], "f1f5", "M492.4 220.8c-8.9 0-18.7 6.7-18.7 22.7h36.7c0-16-9.3-22.7-18-22.7zM375 223.4c-8.2 0-13.3 2.9-17 7l.2 52.8c3.5 3.7 8.5 6.7 16.8 6.7 13.1 0 21.9-14.3 21.9-33.4 0-18.6-9-33.2-21.9-33.1zM528 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h480c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM122.2 281.1c0 25.6-20.3 40.1-49.9 40.3-12.2 0-25.6-2.4-38.8-8.1v-33.9c12 6.4 27.1 11.3 38.9 11.3 7.9 0 13.6-2.1 13.6-8.7 0-17-54-10.6-54-49.9 0-25.2 19.2-40.2 48-40.2 11.8 0 23.5 1.8 35.3 6.5v33.4c-10.8-5.8-24.5-9.1-35.3-9.1-7.5 0-12.1 2.2-12.1 7.7 0 16 54.3 8.4 54.3 50.7zm68.8-56.6h-27V275c0 20.9 22.5 14.4 27 12.6v28.9c-4.7 2.6-13.3 4.7-24.9 4.7-21.1 0-36.9-15.5-36.9-36.5l.2-113.9 34.7-7.4v30.8H191zm74 2.4c-4.5-1.5-18.7-3.6-27.1 7.4v84.4h-35.5V194.2h30.7l2.2 10.5c8.3-15.3 24.9-12.2 29.6-10.5h.1zm44.1 91.8h-35.7V194.2h35.7zm0-142.9l-35.7 7.6v-28.9l35.7-7.6zm74.1 145.5c-12.4 0-20-5.3-25.1-9l-.1 40.2-35.5 7.5V194.2h31.3l1.8 8.8c4.9-4.5 13.9-11.1 27.8-11.1 24.9 0 48.4 22.5 48.4 63.8 0 45.1-23.2 65.5-48.6 65.6zm160.4-51.5h-69.5c1.6 16.6 13.8 21.5 27.6 21.5 14.1 0 25.2-3 34.9-7.9V312c-9.7 5.3-22.4 9.2-39.4 9.2-34.6 0-58.8-21.7-58.8-64.5 0-36.2 20.5-64.9 54.3-64.9 33.7 0 51.3 28.7 51.3 65.1 0 3.5-.3 10.9-.4 12.9z"],
+ "cc-visa": [576, 512, [], "f1f0", "M470.1 231.3s7.6 37.2 9.3 45H446c3.3-8.9 16-43.5 16-43.5-.2.3 3.3-9.1 5.3-14.9l2.8 13.4zM576 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h480c26.5 0 48 21.5 48 48zM152.5 331.2L215.7 176h-42.5l-39.3 106-4.3-21.5-14-71.4c-2.3-9.9-9.4-12.7-18.2-13.1H32.7l-.7 3.1c15.8 4 29.9 9.8 42.2 17.1l35.8 135h42.5zm94.4.2L272.1 176h-40.2l-25.1 155.4h40.1zm139.9-50.8c.2-17.7-10.6-31.2-33.7-42.3-14.1-7.1-22.7-11.9-22.7-19.2.2-6.6 7.3-13.4 23.1-13.4 13.1-.3 22.7 2.8 29.9 5.9l3.6 1.7 5.5-33.6c-7.9-3.1-20.5-6.6-36-6.6-39.7 0-67.6 21.2-67.8 51.4-.3 22.3 20 34.7 35.2 42.2 15.5 7.6 20.8 12.6 20.8 19.3-.2 10.4-12.6 15.2-24.1 15.2-16 0-24.6-2.5-37.7-8.3l-5.3-2.5-5.6 34.9c9.4 4.3 26.8 8.1 44.8 8.3 42.2.1 69.7-20.8 70-53zM528 331.4L495.6 176h-31.1c-9.6 0-16.9 2.8-21 12.9l-59.7 142.5H426s6.9-19.2 8.4-23.3H486c1.2 5.5 4.8 23.3 4.8 23.3H528z"],
+ "centercode": [512, 512, [], "f380", "M329.2 268.6c-3.8 35.2-35.4 60.6-70.6 56.8-35.2-3.8-60.6-35.4-56.8-70.6 3.8-35.2 35.4-60.6 70.6-56.8 35.1 3.8 60.6 35.4 56.8 70.6zm-85.8 235.1C96.7 496-8.2 365.5 10.1 224.3c11.2-86.6 65.8-156.9 139.1-192 161-77.1 349.7 37.4 354.7 216.6 4.1 147-118.4 262.2-260.5 254.8zm179.9-180c27.9-118-160.5-205.9-237.2-234.2-57.5 56.3-69.1 188.6-33.8 344.4 68.8 15.8 169.1-26.4 271-110.2z"],
+ "centos": [448, 512, [], "f789", "M289.6 97.5l31.6 31.7-76.3 76.5V97.5zm-162.4 31.7l76.3 76.5V97.5h-44.7zm41.5-41.6h44.7v127.9l10.8 10.8 10.8-10.8V87.6h44.7L224.2 32zm26.2 168.1l-10.8-10.8H55.5v-44.8L0 255.7l55.5 55.6v-44.8h128.6l10.8-10.8zm79.3-20.7h107.9v-44.8l-31.6-31.7zm173.3 20.7L392 200.1v44.8H264.3l-10.8 10.8 10.8 10.8H392v44.8l55.5-55.6zM65.4 176.2l32.5-31.7 90.3 90.5h15.3v-15.3l-90.3-90.5 31.6-31.7H65.4zm316.7-78.7h-78.5l31.6 31.7-90.3 90.5V235h15.3l90.3-90.5 31.6 31.7zM203.5 413.9V305.8l-76.3 76.5 31.6 31.7h44.7zM65.4 235h108.8l-76.3-76.5-32.5 31.7zm316.7 100.2l-31.6 31.7-90.3-90.5h-15.3v15.3l90.3 90.5-31.6 31.7h78.5zm0-58.8H274.2l76.3 76.5 31.6-31.7zm-60.9 105.8l-76.3-76.5v108.1h44.7zM97.9 352.9l76.3-76.5H65.4v44.8zm181.8 70.9H235V295.9l-10.8-10.8-10.8 10.8v127.9h-44.7l55.5 55.6zm-166.5-41.6l90.3-90.5v-15.3h-15.3l-90.3 90.5-32.5-31.7v78.7h79.4z"],
+ "chrome": [496, 512, [], "f268", "M131.5 217.5L55.1 100.1c47.6-59.2 119-91.8 192-92.1 42.3-.3 85.5 10.5 124.8 33.2 43.4 25.2 76.4 61.4 97.4 103L264 133.4c-58.1-3.4-113.4 29.3-132.5 84.1zm32.9 38.5c0 46.2 37.4 83.6 83.6 83.6s83.6-37.4 83.6-83.6-37.4-83.6-83.6-83.6-83.6 37.3-83.6 83.6zm314.9-89.2L339.6 174c37.9 44.3 38.5 108.2 6.6 157.2L234.1 503.6c46.5 2.5 94.4-7.7 137.8-32.9 107.4-62 150.9-192 107.4-303.9zM133.7 303.6L40.4 120.1C14.9 159.1 0 205.9 0 256c0 124 90.8 226.7 209.5 244.9l63.7-124.8c-57.6 10.8-113.2-20.8-139.5-72.5z"],
+ "chromecast": [512, 512, [], "f838", "M447.8,64H64c-23.6,0-42.7,19.1-42.7,42.7v63.9H64v-63.9h383.8v298.6H298.6V448H448c23.6,0,42.7-19.1,42.7-42.7V106.7 C490.7,83.1,471.4,64,447.8,64z M21.3,383.6L21.3,383.6l0,63.9h63.9C85.2,412.2,56.6,383.6,21.3,383.6L21.3,383.6z M21.3,298.6V341 c58.9,0,106.6,48.1,106.6,107h42.7C170.7,365.6,103.7,298.7,21.3,298.6z M213.4,448h42.7c-0.5-129.5-105.3-234.3-234.8-234.6l0,42.4 C127.3,255.6,213.3,342,213.4,448z"],
+ "cloudflare": [640, 512, [], "e07d", "M407.906,319.913l-230.8-2.928a4.58,4.58,0,0,1-3.632-1.926,4.648,4.648,0,0,1-.494-4.147,6.143,6.143,0,0,1,5.361-4.076L411.281,303.9c27.631-1.26,57.546-23.574,68.022-50.784l13.286-34.542a7.944,7.944,0,0,0,.524-2.936,7.735,7.735,0,0,0-.164-1.631A151.91,151.91,0,0,0,201.257,198.4,68.12,68.12,0,0,0,94.2,269.59C41.924,271.106,0,313.728,0,366.12a96.054,96.054,0,0,0,1.029,13.958,4.508,4.508,0,0,0,4.445,3.871l426.1.051c.043,0,.08-.019.122-.02a5.606,5.606,0,0,0,5.271-4l3.273-11.265c3.9-13.4,2.448-25.8-4.1-34.9C430.124,325.423,420.09,320.487,407.906,319.913ZM513.856,221.1c-2.141,0-4.271.062-6.391.164a3.771,3.771,0,0,0-3.324,2.653l-9.077,31.193c-3.9,13.4-2.449,25.786,4.1,34.89,6.02,8.4,16.054,13.323,28.238,13.9l49.2,2.939a4.491,4.491,0,0,1,3.51,1.894,4.64,4.64,0,0,1,.514,4.169,6.153,6.153,0,0,1-5.351,4.075l-51.125,2.939c-27.754,1.27-57.669,23.574-68.145,50.784l-3.695,9.606a2.716,2.716,0,0,0,2.427,3.68c.046,0,.088.017.136.017h175.91a4.69,4.69,0,0,0,4.539-3.37,124.807,124.807,0,0,0,4.682-34C640,277.3,583.524,221.1,513.856,221.1Z"],
+ "cloudscale": [448, 512, [], "f383", "M318.1 154l-9.4 7.6c-22.5-19.3-51.5-33.6-83.3-33.6C153.8 128 96 188.8 96 260.3c0 6.6.4 13.1 1.4 19.4-2-56 41.8-97.4 92.6-97.4 24.2 0 46.2 9.4 62.6 24.7l-25.2 20.4c-8.3-.9-16.8 1.8-23.1 8.1-11.1 11-11.1 28.9 0 40 11.1 11 28.9 11 40 0 6.3-6.3 9-14.9 8.1-23.1l75.2-88.8c6.3-6.5-3.3-15.9-9.5-9.6zm-83.8 111.5c-5.6 5.5-14.6 5.5-20.2 0-5.6-5.6-5.6-14.6 0-20.2s14.6-5.6 20.2 0 5.6 14.7 0 20.2zM224 32C100.5 32 0 132.5 0 256s100.5 224 224 224 224-100.5 224-224S347.5 32 224 32zm0 384c-88.2 0-160-71.8-160-160S135.8 96 224 96s160 71.8 160 160-71.8 160-160 160z"],
+ "cloudsmith": [332, 512, [], "f384", "M332.5 419.9c0 46.4-37.6 84.1-84 84.1s-84-37.7-84-84.1 37.6-84 84-84 84 37.6 84 84zm-84-243.9c46.4 0 80-37.6 80-84s-33.6-84-80-84-88 37.6-88 84-29.6 76-76 76-84 41.6-84 88 37.6 80 84 80 84-33.6 84-80 33.6-80 80-80z"],
+ "cloudversify": [616, 512, [], "f385", "M148.6 304c8.2 68.5 67.4 115.5 146 111.3 51.2 43.3 136.8 45.8 186.4-5.6 69.2 1.1 118.5-44.6 131.5-99.5 14.8-62.5-18.2-132.5-92.1-155.1-33-88.1-131.4-101.5-186.5-85-57.3 17.3-84.3 53.2-99.3 109.7-7.8 2.7-26.5 8.9-45 24.1 11.7 0 15.2 8.9 15.2 19.5v20.4c0 10.7-8.7 19.5-19.5 19.5h-20.2c-10.7 0-19.5-6-19.5-16.7V240H98.8C95 240 88 244.3 88 251.9v40.4c0 6.4 5.3 11.8 11.7 11.8h48.9zm227.4 8c-10.7 46.3 21.7 72.4 55.3 86.8C324.1 432.6 259.7 348 296 288c-33.2 21.6-33.7 71.2-29.2 92.9-17.9-12.4-53.8-32.4-57.4-79.8-3-39.9 21.5-75.7 57-93.9C297 191.4 369.9 198.7 400 248c-14.1-48-53.8-70.1-101.8-74.8 30.9-30.7 64.4-50.3 114.2-43.7 69.8 9.3 133.2 82.8 67.7 150.5 35-16.3 48.7-54.4 47.5-76.9l10.5 19.6c11.8 22 15.2 47.6 9.4 72-9.2 39-40.6 68.8-79.7 76.5-32.1 6.3-83.1-5.1-91.8-59.2zM128 208H88.2c-8.9 0-16.2-7.3-16.2-16.2v-39.6c0-8.9 7.3-16.2 16.2-16.2H128c8.9 0 16.2 7.3 16.2 16.2v39.6c0 8.9-7.3 16.2-16.2 16.2zM10.1 168C4.5 168 0 163.5 0 157.9v-27.8c0-5.6 4.5-10.1 10.1-10.1h27.7c5.5 0 10.1 4.5 10.1 10.1v27.8c0 5.6-4.5 10.1-10.1 10.1H10.1zM168 142.7v-21.4c0-5.1 4.2-9.3 9.3-9.3h21.4c5.1 0 9.3 4.2 9.3 9.3v21.4c0 5.1-4.2 9.3-9.3 9.3h-21.4c-5.1 0-9.3-4.2-9.3-9.3zM56 235.5v25c0 6.3-5.1 11.5-11.4 11.5H19.4C13.1 272 8 266.8 8 260.5v-25c0-6.3 5.1-11.5 11.4-11.5h25.1c6.4 0 11.5 5.2 11.5 11.5z"],
+ "codepen": [512, 512, [], "f1cb", "M502.285 159.704l-234-156c-7.987-4.915-16.511-4.96-24.571 0l-234 156C3.714 163.703 0 170.847 0 177.989v155.999c0 7.143 3.714 14.286 9.715 18.286l234 156.022c7.987 4.915 16.511 4.96 24.571 0l234-156.022c6-3.999 9.715-11.143 9.715-18.286V177.989c-.001-7.142-3.715-14.286-9.716-18.285zM278 63.131l172.286 114.858-76.857 51.429L278 165.703V63.131zm-44 0v102.572l-95.429 63.715-76.857-51.429L234 63.131zM44 219.132l55.143 36.857L44 292.846v-73.714zm190 229.715L61.714 333.989l76.857-51.429L234 346.275v102.572zm22-140.858l-77.715-52 77.715-52 77.715 52-77.715 52zm22 140.858V346.275l95.429-63.715 76.857 51.429L278 448.847zm190-156.001l-55.143-36.857L468 219.132v73.714z"],
+ "codiepie": [472, 512, [], "f284", "M422.5 202.9c30.7 0 33.5 53.1-.3 53.1h-10.8v44.3h-26.6v-97.4h37.7zM472 352.6C429.9 444.5 350.4 504 248 504 111 504 0 393 0 256S111 8 248 8c97.4 0 172.8 53.7 218.2 138.4l-186 108.8L472 352.6zm-38.5 12.5l-60.3-30.7c-27.1 44.3-70.4 71.4-122.4 71.4-82.5 0-149.2-66.7-149.2-148.9 0-82.5 66.7-149.2 149.2-149.2 48.4 0 88.9 23.5 116.9 63.4l59.5-34.6c-40.7-62.6-104.7-100-179.2-100-121.2 0-219.5 98.3-219.5 219.5S126.8 475.5 248 475.5c78.6 0 146.5-42.1 185.5-110.4z"],
+ "confluence": [512, 512, [], "f78d", "M2.3 412.2c-4.5 7.6-2.1 17.5 5.5 22.2l105.9 65.2c7.7 4.7 17.7 2.4 22.4-5.3 0-.1.1-.2.1-.2 67.1-112.2 80.5-95.9 280.9-.7 8.1 3.9 17.8.4 21.7-7.7.1-.1.1-.3.2-.4l50.4-114.1c3.6-8.1-.1-17.6-8.1-21.3-22.2-10.4-66.2-31.2-105.9-50.3C127.5 179 44.6 345.3 2.3 412.2zm507.4-312.1c4.5-7.6 2.1-17.5-5.5-22.2L398.4 12.8c-7.5-5-17.6-3.1-22.6 4.4-.2.3-.4.6-.6 1-67.3 112.6-81.1 95.6-280.6.9-8.1-3.9-17.8-.4-21.7 7.7-.1.1-.1.3-.2.4L22.2 141.3c-3.6 8.1.1 17.6 8.1 21.3 22.2 10.4 66.3 31.2 106 50.4 248 120 330.8-45.4 373.4-112.9z"],
+ "connectdevelop": [576, 512, [], "f20e", "M550.5 241l-50.089-86.786c1.071-2.142 1.875-4.553 1.875-7.232 0-8.036-6.696-14.733-14.732-15.001l-55.447-95.893c.536-1.607 1.071-3.214 1.071-4.821 0-8.571-6.964-15.268-15.268-15.268-4.821 0-8.839 2.143-11.786 5.625H299.518C296.839 18.143 292.821 16 288 16s-8.839 2.143-11.518 5.625H170.411C167.464 18.143 163.447 16 158.625 16c-8.303 0-15.268 6.696-15.268 15.268 0 1.607.536 3.482 1.072 4.821l-55.983 97.233c-5.356 2.41-9.107 7.5-9.107 13.661 0 .535.268 1.071.268 1.607l-53.304 92.143c-7.232 1.339-12.59 7.5-12.59 15 0 7.232 5.089 13.393 12.054 15l55.179 95.358c-.536 1.607-.804 2.946-.804 4.821 0 7.232 5.089 13.393 12.054 14.732l51.697 89.732c-.536 1.607-1.071 3.482-1.071 5.357 0 8.571 6.964 15.268 15.268 15.268 4.821 0 8.839-2.143 11.518-5.357h106.875C279.161 493.857 283.447 496 288 496s8.839-2.143 11.518-5.357h107.143c2.678 2.946 6.696 4.821 10.982 4.821 8.571 0 15.268-6.964 15.268-15.268 0-1.607-.267-2.946-.803-4.285l51.697-90.268c6.964-1.339 12.054-7.5 12.054-14.732 0-1.607-.268-3.214-.804-4.821l54.911-95.358c6.964-1.339 12.322-7.5 12.322-15-.002-7.232-5.092-13.393-11.788-14.732zM153.535 450.732l-43.66-75.803h43.66v75.803zm0-83.839h-43.66c-.268-1.071-.804-2.142-1.339-3.214l44.999-47.41v50.624zm0-62.411l-50.357 53.304c-1.339-.536-2.679-1.34-4.018-1.607L43.447 259.75c.535-1.339.535-2.679.535-4.018s0-2.41-.268-3.482l51.965-90c2.679-.268 5.357-1.072 7.768-2.679l50.089 51.965v92.946zm0-102.322l-45.803-47.41c1.339-2.143 2.143-4.821 2.143-7.767 0-.268-.268-.804-.268-1.072l43.928-15.804v72.053zm0-80.625l-43.66 15.804 43.66-75.536v59.732zm326.519 39.108l.804 1.339L445.5 329.125l-63.75-67.232 98.036-101.518.268.268zM291.75 355.107l11.518 11.786H280.5l11.25-11.786zm-.268-11.25l-83.303-85.446 79.553-84.375 83.036 87.589-79.286 82.232zm5.357 5.893l79.286-82.232 67.5 71.25-5.892 28.125H313.714l-16.875-17.143zM410.411 44.393c1.071.536 2.142 1.072 3.482 1.34l57.857 100.714v.536c0 2.946.803 5.624 2.143 7.767L376.393 256l-83.035-87.589L410.411 44.393zm-9.107-2.143L287.732 162.518l-57.054-60.268 166.339-60h4.287zm-123.483 0c2.678 2.678 6.16 4.285 10.179 4.285s7.5-1.607 10.179-4.285h75L224.786 95.821 173.893 42.25h103.928zm-116.249 5.625l1.071-2.142a33.834 33.834 0 0 0 2.679-.804l51.161 53.84-54.911 19.821V47.875zm0 79.286l60.803-21.964 59.732 63.214-79.553 84.107-40.982-42.053v-83.304zm0 92.678L198 257.607l-36.428 38.304v-76.072zm0 87.858l42.053-44.464 82.768 85.982-17.143 17.678H161.572v-59.196zm6.964 162.053c-1.607-1.607-3.482-2.678-5.893-3.482l-1.071-1.607v-89.732h99.91l-91.607 94.821h-1.339zm129.911 0c-2.679-2.41-6.428-4.285-10.447-4.285s-7.767 1.875-10.447 4.285h-96.429l91.607-94.821h38.304l91.607 94.821H298.447zm120-11.786l-4.286 7.5c-1.339.268-2.41.803-3.482 1.339l-89.196-91.875h114.376l-17.412 83.036zm12.856-22.232l12.858-60.803h21.964l-34.822 60.803zm34.822-68.839h-20.357l4.553-21.16 17.143 18.214c-.535.803-1.071 1.874-1.339 2.946zm66.161-107.411l-55.447 96.697c-1.339.535-2.679 1.071-4.018 1.874l-20.625-21.964 34.554-163.928 45.803 79.286c-.267 1.339-.803 2.678-.803 4.285 0 1.339.268 2.411.536 3.75z"],
+ "contao": [512, 512, [], "f26d", "M45.4 305c14.4 67.1 26.4 129 68.2 175H34c-18.7 0-34-15.2-34-34V66c0-18.7 15.2-34 34-34h57.7C77.9 44.6 65.6 59.2 54.8 75.6c-45.4 70-27 146.8-9.4 229.4zM478 32h-90.2c21.4 21.4 39.2 49.5 52.7 84.1l-137.1 29.3c-14.9-29-37.8-53.3-82.6-43.9-24.6 5.3-41 19.3-48.3 34.6-8.8 18.7-13.2 39.8 8.2 140.3 21.1 100.2 33.7 117.7 49.5 131.2 12.9 11.1 33.4 17 58.3 11.7 44.5-9.4 55.7-40.7 57.4-73.2l137.4-29.6c3.2 71.5-18.7 125.2-57.4 163.6H478c18.7 0 34-15.2 34-34V66c0-18.8-15.2-34-34-34z"],
+ "cotton-bureau": [512, 512, [], "f89e", "M474.31 330.41c-23.66 91.85-94.23 144.59-201.9 148.35V429.6c0-48 26.41-74.39 74.39-74.39 62 0 99.2-37.2 99.2-99.21 0-61.37-36.53-98.28-97.38-99.06-33-69.32-146.5-64.65-177.24 0C110.52 157.72 74 194.63 74 256c0 62.13 37.27 99.41 99.4 99.41 48 0 74.55 26.23 74.55 74.39V479c-134.43-5-211.1-85.07-211.1-223 0-141.82 81.35-223.2 223.2-223.2 114.77 0 189.84 53.2 214.69 148.81H500C473.88 71.51 388.22 8 259.82 8 105 8 12 101.19 12 255.82 12 411.14 105.19 504.34 259.82 504c128.27 0 213.87-63.81 239.67-173.59zM357 182.33c41.37 3.45 64.2 29 64.2 73.67 0 48-26.43 74.41-74.4 74.41-28.61 0-49.33-9.59-61.59-27.33 83.06-16.55 75.59-99.67 71.79-120.75zm-81.68 97.36c-2.46-10.34-16.33-87 56.23-97 2.27 10.09 16.52 87.11-56.26 97zM260 132c28.61 0 49 9.67 61.44 27.61-28.36 5.48-49.36 20.59-61.59 43.45-12.23-22.86-33.23-38-61.6-43.45 12.41-17.69 33.27-27.35 61.57-27.35zm-71.52 50.72c73.17 10.57 58.91 86.81 56.49 97-72.41-9.84-59-86.95-56.25-97zM173.2 330.41c-48 0-74.4-26.4-74.4-74.41 0-44.36 22.86-70 64.22-73.67-6.75 37.2-1.38 106.53 71.65 120.75-12.14 17.63-32.84 27.3-61.14 27.3zm53.21 12.39A80.8 80.8 0 0 0 260 309.25c7.77 14.49 19.33 25.54 33.82 33.55a80.28 80.28 0 0 0-33.58 33.83c-8-14.5-19.07-26.23-33.56-33.83z"],
+ "cpanel": [640, 512, [], "f388", "M210.3 220.2c-5.6-24.8-26.9-41.2-51-41.2h-37c-7.1 0-12.5 4.5-14.3 10.9L73.1 320l24.7-.1c6.8 0 12.3-4.5 14.2-10.7l25.8-95.7h19.8c8.4 0 16.2 5.6 18.3 14.8 2.5 10.9-5.9 22.6-18.3 22.6h-10.3c-7 0-12.5 4.6-14.3 10.8l-6.4 23.8h32c37.2 0 58.3-36.2 51.7-65.3zm-156.5 28h18.6c6.9 0 12.4-4.4 14.3-10.9l6.2-23.6h-40C30 213.7 9 227.8 1.7 254.8-7 288.6 18.5 320 52 320h12.4l7.1-26.1c1.2-4.4-2.2-8.3-6.4-8.3H53.8c-24.7 0-24.9-37.4 0-37.4zm247.5-34.8h-77.9l-3.5 13.4c-2.4 9.6 4.5 18.5 14.2 18.5h57.5c4 0 2.4 4.3 2.1 5.3l-8.6 31.8c-.4 1.4-.9 5.3-5.5 5.3h-34.9c-5.3 0-5.3-7.9 0-7.9h21.6c6.8 0 12.3-4.6 14.2-10.8l3.5-13.2h-48.4c-39.2 0-43.6 63.8-.7 63.8l57.5.2c11.2 0 20.6-7.2 23.4-17.8l14-51.8c4.8-19.2-9.7-36.8-28.5-36.8zM633.1 179h-18.9c-4.9 0-9.2 3.2-10.4 7.9L568.2 320c20.7 0 39.8-13.8 44.9-34.5l26.5-98.2c1.2-4.3-2-8.3-6.5-8.3zm-236.3 34.7v.1h-48.3l-26.2 98c-1.2 4.4 2.2 8.3 6.4 8.3h18.9c4.8 0 9.2-3 10.4-7.8l17.2-64H395c12.5 0 21.4 11.8 18.1 23.4l-10.6 40c-1.2 4.3 1.9 8.3 6.4 8.3H428c4.6 0 9.1-2.9 10.3-7.8l8.8-33.1c9-33.1-15.9-65.4-50.3-65.4zm98.3 74.6c-3.6 0-6-3.4-5.1-6.7l8-30c.9-3.9 3.7-6 7.8-6h32.9c2.6 0 4.6 2.4 3.9 5.1l-.7 2.6c-.6 2-1.9 3-3.9 3h-21.6c-7 0-12.6 4.6-14.2 10.8l-3.5 13h53.4c10.5 0 20.3-6.6 23.2-17.6l3.2-12c4.9-19.1-9.3-36.8-28.3-36.8h-47.3c-17.9 0-33.8 12-38.6 29.6l-10.8 40c-5 17.7 8.3 36.7 28.3 36.7h66.7c6.8 0 12.3-4.5 14.2-10.7l5.7-21z"],
+ "creative-commons": [496, 512, [], "f25e", "M245.83 214.87l-33.22 17.28c-9.43-19.58-25.24-19.93-27.46-19.93-22.13 0-33.22 14.61-33.22 43.84 0 23.57 9.21 43.84 33.22 43.84 14.47 0 24.65-7.09 30.57-21.26l30.55 15.5c-6.17 11.51-25.69 38.98-65.1 38.98-22.6 0-73.96-10.32-73.96-77.05 0-58.69 43-77.06 72.63-77.06 30.72-.01 52.7 11.95 65.99 35.86zm143.05 0l-32.78 17.28c-9.5-19.77-25.72-19.93-27.9-19.93-22.14 0-33.22 14.61-33.22 43.84 0 23.55 9.23 43.84 33.22 43.84 14.45 0 24.65-7.09 30.54-21.26l31 15.5c-2.1 3.75-21.39 38.98-65.09 38.98-22.69 0-73.96-9.87-73.96-77.05 0-58.67 42.97-77.06 72.63-77.06 30.71-.01 52.58 11.95 65.56 35.86zM247.56 8.05C104.74 8.05 0 123.11 0 256.05c0 138.49 113.6 248 247.56 248 129.93 0 248.44-100.87 248.44-248 0-137.87-106.62-248-248.44-248zm.87 450.81c-112.54 0-203.7-93.04-203.7-202.81 0-105.42 85.43-203.27 203.72-203.27 112.53 0 202.82 89.46 202.82 203.26-.01 121.69-99.68 202.82-202.84 202.82z"],
+ "creative-commons-by": [496, 512, [], "f4e7", "M314.9 194.4v101.4h-28.3v120.5h-77.1V295.9h-28.3V194.4c0-4.4 1.6-8.2 4.6-11.3 3.1-3.1 6.9-4.7 11.3-4.7H299c4.1 0 7.8 1.6 11.1 4.7 3.1 3.2 4.8 6.9 4.8 11.3zm-101.5-63.7c0-23.3 11.5-35 34.5-35s34.5 11.7 34.5 35c0 23-11.5 34.5-34.5 34.5s-34.5-11.5-34.5-34.5zM247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3z"],
+ "creative-commons-nc": [496, 512, [], "f4e8", "M247.6 8C387.4 8 496 115.9 496 256c0 147.2-118.5 248-248.4 248C113.1 504 0 393.2 0 256 0 123.1 104.7 8 247.6 8zM55.8 189.1c-7.4 20.4-11.1 42.7-11.1 66.9 0 110.9 92.1 202.4 203.7 202.4 122.4 0 177.2-101.8 178.5-104.1l-93.4-41.6c-7.7 37.1-41.2 53-68.2 55.4v38.1h-28.8V368c-27.5-.3-52.6-10.2-75.3-29.7l34.1-34.5c31.7 29.4 86.4 31.8 86.4-2.2 0-6.2-2.2-11.2-6.6-15.1-14.2-6-1.8-.1-219.3-97.4zM248.4 52.3c-38.4 0-112.4 8.7-170.5 93l94.8 42.5c10-31.3 40.4-42.9 63.8-44.3v-38.1h28.8v38.1c22.7 1.2 43.4 8.9 62 23L295 199.7c-42.7-29.9-83.5-8-70 11.1 53.4 24.1 43.8 19.8 93 41.6l127.1 56.7c4.1-17.4 6.2-35.1 6.2-53.1 0-57-19.8-105-59.3-143.9-39.3-39.9-87.2-59.8-143.6-59.8z"],
+ "creative-commons-nc-eu": [496, 512, [], "f4e9", "M247.7 8C103.6 8 0 124.8 0 256c0 136.3 111.7 248 247.7 248C377.9 504 496 403.1 496 256 496 117 388.4 8 247.7 8zm.6 450.7c-112 0-203.6-92.5-203.6-202.7 0-23.2 3.7-45.2 10.9-66l65.7 29.1h-4.7v29.5h23.3c0 6.2-.4 3.2-.4 19.5h-22.8v29.5h27c11.4 67 67.2 101.3 124.6 101.3 26.6 0 50.6-7.9 64.8-15.8l-10-46.1c-8.7 4.6-28.2 10.8-47.3 10.8-28.2 0-58.1-10.9-67.3-50.2h90.3l128.3 56.8c-1.5 2.1-56.2 104.3-178.8 104.3zm-16.7-190.6l-.5-.4.9.4h-.4zm77.2-19.5h3.7v-29.5h-70.3l-28.6-12.6c2.5-5.5 5.4-10.5 8.8-14.3 12.9-15.8 31.1-22.4 51.1-22.4 18.3 0 35.3 5.4 46.1 10l11.6-47.3c-15-6.6-37-12.4-62.3-12.4-39 0-72.2 15.8-95.9 42.3-5.3 6.1-9.8 12.9-13.9 20.1l-81.6-36.1c64.6-96.8 157.7-93.6 170.7-93.6 113 0 203 90.2 203 203.4 0 18.7-2.1 36.3-6.3 52.9l-136.1-60.5z"],
+ "creative-commons-nc-jp": [496, 512, [], "f4ea", "M247.7 8C103.6 8 0 124.8 0 256c0 136.4 111.8 248 247.7 248C377.9 504 496 403.2 496 256 496 117.2 388.5 8 247.7 8zm.6 450.7c-112 0-203.6-92.5-203.6-202.7 0-21.1 3-41.2 9-60.3l127 56.5h-27.9v38.6h58.1l5.7 11.8v18.7h-63.8V360h63.8v56h61.7v-56h64.2v-35.7l81 36.1c-1.5 2.2-57.1 98.3-175.2 98.3zm87.6-137.3h-57.6v-18.7l2.9-5.6 54.7 24.3zm6.5-51.4v-17.8h-38.6l63-116H301l-43.4 96-23-10.2-39.6-85.7h-65.8l27.3 51-81.9-36.5c27.8-44.1 82.6-98.1 173.7-98.1 112.8 0 203 90 203 203.4 0 21-2.7 40.6-7.9 59l-101-45.1z"],
+ "creative-commons-nd": [496, 512, [], "f4eb", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm94 144.3v42.5H162.1V197h180.3zm0 79.8v42.5H162.1v-42.5h180.3z"],
+ "creative-commons-pd": [496, 512, [], "f4ec", "M248 8C111 8 0 119.1 0 256c0 137 111 248 248 248s248-111 248-248C496 119.1 385 8 248 8zm0 449.5c-139.2 0-235.8-138-190.2-267.9l78.8 35.1c-2.1 10.5-3.3 21.5-3.3 32.9 0 99 73.9 126.9 120.4 126.9 22.9 0 53.5-6.7 79.4-29.5L297 311.1c-5.5 6.3-17.6 16.7-36.3 16.7-37.8 0-53.7-39.9-53.9-71.9 230.4 102.6 216.5 96.5 217.9 96.8-34.3 62.4-100.6 104.8-176.7 104.8zm194.2-150l-224-100c18.8-34 54.9-30.7 74.7-11l40.4-41.6c-27.1-23.3-58-27.5-78.1-27.5-47.4 0-80.9 20.5-100.7 51.6l-74.9-33.4c36.1-54.9 98.1-91.2 168.5-91.2 111.1 0 201.5 90.4 201.5 201.5 0 18-2.4 35.4-6.8 52-.3-.1-.4-.2-.6-.4z"],
+ "creative-commons-pd-alt": [496, 512, [], "f4ed", "M247.6 8C104.7 8 0 123.1 0 256c0 138.5 113.6 248 247.6 248C377.5 504 496 403.1 496 256 496 118.1 389.4 8 247.6 8zm.8 450.8c-112.5 0-203.7-93-203.7-202.8 0-105.4 85.5-203.3 203.7-203.3 112.6 0 202.9 89.5 202.8 203.3 0 121.7-99.6 202.8-202.8 202.8zM316.7 186h-53.2v137.2h53.2c21.4 0 70-5.1 70-68.6 0-63.4-48.6-68.6-70-68.6zm.8 108.5h-19.9v-79.7l19.4-.1c3.8 0 35-2.1 35 39.9 0 24.6-10.5 39.9-34.5 39.9zM203.7 186h-68.2v137.3h34.6V279h27c54.1 0 57.1-37.5 57.1-46.5 0-31-16.8-46.5-50.5-46.5zm-4.9 67.3h-29.2v-41.6h28.3c30.9 0 28.8 41.6.9 41.6z"],
+ "creative-commons-remix": [496, 512, [], "f4ee", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm161.7 207.7l4.9 2.2v70c-7.2 3.6-63.4 27.5-67.3 28.8-6.5-1.8-113.7-46.8-137.3-56.2l-64.2 26.6-63.3-27.5v-63.8l59.3-24.8c-.7-.7-.4 5-.4-70.4l67.3-29.7L361 178.5v61.6l49.1 20.3zm-70.4 81.5v-43.8h-.4v-1.8l-113.8-46.5V295l113.8 46.9v-.4l.4.4zm7.5-57.6l39.9-16.4-36.8-15.5-39 16.4 35.9 15.5zm52.3 38.1v-43L355.2 298v43.4l44.3-19z"],
+ "creative-commons-sa": [496, 512, [], "f4ef", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zM137.7 221c13-83.9 80.5-95.7 108.9-95.7 99.8 0 127.5 82.5 127.5 134.2 0 63.6-41 132.9-128.9 132.9-38.9 0-99.1-20-109.4-97h62.5c1.5 30.1 19.6 45.2 54.5 45.2 23.3 0 58-18.2 58-82.8 0-82.5-49.1-80.6-56.7-80.6-33.1 0-51.7 14.6-55.8 43.8h18.2l-49.2 49.2-49-49.2h19.4z"],
+ "creative-commons-sampling": [496, 512, [], "f4f0", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm3.6 53.2c2.8-.3 11.5 1 11.5 11.5l6.6 107.2 4.9-59.3c0-6 4.7-10.6 10.6-10.6 5.9 0 10.6 4.7 10.6 10.6 0 2.5-.5-5.7 5.7 81.5l5.8-64.2c.3-2.9 2.9-9.3 10.2-9.3 3.8 0 9.9 2.3 10.6 8.9l11.5 96.5 5.3-12.8c1.8-4.4 5.2-6.6 10.2-6.6h58v21.3h-50.9l-18.2 44.3c-3.9 9.9-19.5 9.1-20.8-3.1l-4-31.9-7.5 92.6c-.3 3-3 9.3-10.2 9.3-3 0-9.8-2.1-10.6-9.3 0-1.9.6 5.8-6.2-77.9l-5.3 72.2c-1.1 4.8-4.8 9.3-10.6 9.3-2.9 0-9.8-2-10.6-9.3 0-1.9.5 6.7-5.8-87.7l-5.8 94.8c0 6.3-3.6 12.4-10.6 12.4-5.2 0-10.6-4.1-10.6-12l-5.8-87.7c-5.8 92.5-5.3 84-5.3 85.9-1.1 4.8-4.8 9.3-10.6 9.3-3 0-9.8-2.1-10.6-9.3 0-.7-.4-1.1-.4-2.6l-6.2-88.6L182 348c-.7 6.5-6.7 9.3-10.6 9.3-5.8 0-9.6-4.1-10.6-8.9L149.7 272c-2 4-3.5 8.4-11.1 8.4H87.2v-21.3H132l13.7-27.9c4.4-9.9 18.2-7.2 19.9 2.7l3.1 20.4 8.4-97.9c0-6 4.8-10.6 10.6-10.6.5 0 10.6-.2 10.6 12.4l4.9 69.1 6.6-92.6c0-10.1 9.5-10.6 10.2-10.6.6 0 10.6.7 10.6 10.6l5.3 80.6 6.2-97.9c.1-1.1-.6-10.3 9.9-11.5z"],
+ "creative-commons-sampling-plus": [496, 512, [], "f4f1", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm107 205.6c-4.7 0-9 2.8-10.7 7.2l-4 9.5-11-92.8c-1.7-13.9-22-13.4-23.1.4l-4.3 51.4-5.2-68.8c-1.1-14.3-22.1-14.2-23.2 0l-3.5 44.9-5.9-94.3c-.9-14.5-22.3-14.4-23.2 0l-5.1 83.7-4.3-66.3c-.9-14.4-22.2-14.4-23.2 0l-5.3 80.2-4.1-57c-1.1-14.3-22-14.3-23.2-.2l-7.7 89.8-1.8-12.2c-1.7-11.4-17.1-13.6-22-3.3l-13.2 27.7H87.5v23.2h51.3c4.4 0 8.4-2.5 10.4-6.4l10.7 73.1c2 13.5 21.9 13 23.1-.7l3.8-43.6 5.7 78.3c1.1 14.4 22.3 14.2 23.2-.1l4.6-70.4 4.8 73.3c.9 14.4 22.3 14.4 23.2-.1l4.9-80.5 4.5 71.8c.9 14.3 22.1 14.5 23.2.2l4.6-58.6 4.9 64.4c1.1 14.3 22 14.2 23.1.1l6.8-83 2.7 22.3c1.4 11.8 17.7 14.1 22.3 3.1l18-43.4h50.5V258l-58.4.3zm-78 5.2h-21.9v21.9c0 4.1-3.3 7.5-7.5 7.5-4.1 0-7.5-3.3-7.5-7.5v-21.9h-21.9c-4.1 0-7.5-3.3-7.5-7.5 0-4.1 3.4-7.5 7.5-7.5h21.9v-21.9c0-4.1 3.4-7.5 7.5-7.5s7.5 3.3 7.5 7.5v21.9h21.9c4.1 0 7.5 3.3 7.5 7.5 0 4.1-3.4 7.5-7.5 7.5z"],
+ "creative-commons-share": [496, 512, [], "f4f2", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm101 132.4c7.8 0 13.7 6.1 13.7 13.7v182.5c0 7.7-6.1 13.7-13.7 13.7H214.3c-7.7 0-13.7-6-13.7-13.7v-54h-54c-7.8 0-13.7-6-13.7-13.7V131.1c0-8.2 6.6-12.7 12.4-13.7h136.4c7.7 0 13.7 6 13.7 13.7v54h54zM159.9 300.3h40.7V198.9c0-7.4 5.8-12.6 12-13.7h55.8v-40.3H159.9v155.4zm176.2-88.1H227.6v155.4h108.5V212.2z"],
+ "creative-commons-zero": [496, 512, [], "f4f3", "M247.6 8C389.4 8 496 118.1 496 256c0 147.1-118.5 248-248.4 248C113.6 504 0 394.5 0 256 0 123.1 104.7 8 247.6 8zm.8 44.7C130.2 52.7 44.7 150.6 44.7 256c0 109.8 91.2 202.8 203.7 202.8 103.2 0 202.8-81.1 202.8-202.8.1-113.8-90.2-203.3-202.8-203.3zm-.4 60.5c-81.9 0-102.5 77.3-102.5 142.8 0 65.5 20.6 142.8 102.5 142.8S350.5 321.5 350.5 256c0-65.5-20.6-142.8-102.5-142.8zm0 53.9c3.3 0 6.4.5 9.2 1.2 5.9 5.1 8.8 12.1 3.1 21.9l-54.5 100.2c-1.7-12.7-1.9-25.1-1.9-34.4 0-28.8 2-88.9 44.1-88.9zm40.8 46.2c2.9 15.4 3.3 31.4 3.3 42.7 0 28.9-2 88.9-44.1 88.9-13.5 0-32.6-7.7-20.1-26.4l60.9-105.2z"],
+ "critical-role": [448, 512, [], "f6c9", "M225.82 0c.26.15 216.57 124.51 217.12 124.72 3 1.18 3.7 3.46 3.7 6.56q-.11 125.17 0 250.36a5.88 5.88 0 0 1-3.38 5.78c-21.37 12-207.86 118.29-218.93 124.58h-3C142 466.34 3.08 386.56 2.93 386.48a3.29 3.29 0 0 1-1.88-3.24c0-.87 0-225.94-.05-253.1a5 5 0 0 1 2.93-4.93C27.19 112.11 213.2 6 224.07 0zM215.4 20.42l-.22-.16Q118.06 75.55 21 130.87c0 .12.08.23.13.35l30.86 11.64c-7.71 6-8.32 6-10.65 5.13-.1 0-24.17-9.28-26.8-10v230.43c.88-1.41 64.07-110.91 64.13-111 1.62-2.82 3-1.92 9.12-1.52 1.4.09 1.48.22.78 1.42-41.19 71.33-36.4 63-67.48 116.94-.81 1.4-.61 1.13 1.25 1.13h186.5c1.44 0 1.69-.23 1.7-1.64v-8.88c0-1.34 2.36-.81-18.37-1-7.46-.07-14.14-3.22-21.38-12.7-7.38-9.66-14.62-19.43-21.85-29.21-2.28-3.08-3.45-2.38-16.76-2.38-1.75 0-1.78 0-1.76 1.82.29 26.21.15 25.27 1 32.66.52 4.37 2.16 4.2 9.69 4.81 3.14.26 3.88 4.08.52 4.92-1.57.39-31.6.51-33.67-.1a2.42 2.42 0 0 1 .3-4.73c3.29-.76 6.16.81 6.66-4.44 1.3-13.66 1.17-9 1.1-79.42 0-10.82-.35-12.58-5.36-13.55-1.22-.24-3.54-.16-4.69-.55-2.88-1-2-4.84 1.77-4.85 33.67 0 46.08-1.07 56.06 4.86 7.74 4.61 12 11.48 12.51 20.4.88 14.59-6.51 22.35-15 32.59a1.46 1.46 0 0 0 0 2.22c2.6 3.25 5 6.63 7.71 9.83 27.56 33.23 24.11 30.54 41.28 33.06.89.13 1-.42 1-1.15v-11c0-1 .32-1.43 1.41-1.26a72.37 72.37 0 0 0 23.58-.3c1.08-.15 1.5.2 1.48 1.33 0 .11.88 26.69.87 26.8-.05 1.52.67 1.62 1.89 1.62h186.71Q386.51 304.6 346 234.33c2.26-.66-.4 0 6.69-1.39 2-.39 2.05-.41 3.11 1.44 7.31 12.64 77.31 134 77.37 134.06V138c-1.72.5-103.3 38.72-105.76 39.68-1.08.42-1.55.2-1.91-.88-.63-1.9-1.34-3.76-2.09-5.62-.32-.79-.09-1.13.65-1.39.1 0 95.53-35.85 103-38.77-65.42-37.57-130.56-75-196-112.6l86.82 150.39-.28.33c-9.57-.9-10.46-1.6-11.8-3.94-1-1.69-73.5-127.71-82-142.16-9.1 14.67-83.56 146.21-85.37 146.32-2.93.17-5.88.08-9.25.08q43.25-74.74 86.18-149zm51.93 129.92a37.68 37.68 0 0 0 5.54-.85c1.69-.3 2.53.2 2.6 1.92 0 .11.07 19.06-.86 20.45s-1.88 1.22-2.6-.19c-5-9.69 6.22-9.66-39.12-12-.7 0-1 .23-1 .93 0 .13 3.72 122 3.73 122.11 0 .89.52 1.2 1.21 1.51a83.92 83.92 0 0 1 8.7 4.05c7.31 4.33 11.38 10.84 12.41 19.31 1.44 11.8-2.77 35.77-32.21 37.14-2.75.13-28.26 1.08-34.14-23.25-4.66-19.26 8.26-32.7 19.89-36.4a2.45 2.45 0 0 0 2-2.66c.1-5.63 3-107.1 3.71-121.35.05-1.08-.62-1.16-1.35-1.15-32.35.52-36.75-.34-40.22 8.52-2.42 6.18-4.14 1.32-3.95.23q1.59-9 3.31-18c.4-2.11 1.43-2.61 3.43-1.86 5.59 2.11 6.72 1.7 37.25 1.92 1.73 0 1.78-.08 1.82-1.85.68-27.49.58-22.59 1-29.55a2.69 2.69 0 0 0-1.63-2.8c-5.6-2.91-8.75-7.55-8.9-13.87-.35-14.81 17.72-21.67 27.38-11.51 6.84 7.19 5.8 18.91-2.45 24.15a4.35 4.35 0 0 0-2.22 4.34c0 .59-.11-4.31 1 30.05 0 .9.43 1.12 1.24 1.11.1 0 23-.09 34.47-.37zM68.27 141.7c19.84-4.51 32.68-.56 52.49 1.69 2.76.31 3.74 1.22 3.62 4-.21 5-1.16 22.33-1.24 23.15a2.65 2.65 0 0 1-1.63 2.34c-4.06 1.7-3.61-4.45-4-7.29-3.13-22.43-73.87-32.7-74.63 25.4-.31 23.92 17 53.63 54.08 50.88 27.24-2 19-20.19 24.84-20.47a2.72 2.72 0 0 1 3 3.36c-1.83 10.85-3.42 18.95-3.45 19.15-1.54 9.17-86.7 22.09-93.35-42.06-2.71-25.85 10.44-53.37 40.27-60.15zm80 87.67h-19.49a2.57 2.57 0 0 1-2.66-1.79c2.38-3.75 5.89.92 5.86-6.14-.08-25.75.21-38 .23-40.1 0-3.42-.53-4.65-3.32-4.94-7-.72-3.11-3.37-1.11-3.38 11.84-.1 22.62-.18 30.05.72 8.77 1.07 16.71 12.63 7.93 22.62-2 2.25-4 4.42-6.14 6.73.95 1.15 6.9 8.82 17.28 19.68 2.66 2.78 6.15 3.51 9.88 3.13a2.21 2.21 0 0 0 2.23-2.12c.3-3.42.26 4.73.45-40.58 0-5.65-.34-6.58-3.23-6.83-3.95-.35-4-2.26-.69-3.37l19.09-.09c.32 0 4.49.53 1 3.38 0 .05-.16 0-.24 0-3.61.26-3.94 1-4 4.62-.27 43.93.07 40.23.41 42.82.11.84.27 2.23 5.1 2.14 2.49 0 3.86 3.37 0 3.4-10.37.08-20.74 0-31.11.07-10.67 0-13.47-6.2-24.21-20.82-1.6-2.18-8.31-2.36-8.2-.37.88 16.47 0 17.78 4 17.67 4.75-.1 4.73 3.57.83 3.55zm275-10.15c-1.21 7.13.17 10.38-5.3 10.34-61.55-.42-47.82-.22-50.72-.31a18.4 18.4 0 0 1-3.63-.73c-2.53-.6 1.48-1.23-.38-5.6-1.43-3.37-2.78-6.78-4.11-10.19a1.94 1.94 0 0 0-2-1.44 138 138 0 0 0-14.58.07 2.23 2.23 0 0 0-1.62 1.06c-1.58 3.62-3.07 7.29-4.51 11-1.27 3.23 7.86 1.32 12.19 2.16 3 .57 4.53 3.72.66 3.73H322.9c-2.92 0-3.09-3.15-.74-3.21a6.3 6.3 0 0 0 5.92-3.47c1.5-3 2.8-6 4.11-9.09 18.18-42.14 17.06-40.17 18.42-41.61a1.83 1.83 0 0 1 3 0c2.93 3.34 18.4 44.71 23.62 51.92 2 2.7 5.74 2 6.36 2 3.61.13 4-1.11 4.13-4.29.09-1.87.08 1.17.07-41.24 0-4.46-2.36-3.74-5.55-4.27-.26 0-2.56-.63-.08-3.06.21-.2-.89-.24 21.7-.15 2.32 0 5.32 2.75-1.21 3.45a2.56 2.56 0 0 0-2.66 2.83c-.07 1.63-.19 38.89.29 41.21a3.06 3.06 0 0 0 3.23 2.43c13.25.43 14.92.44 16-3.41 1.67-5.78 4.13-2.52 3.73-.19zm-104.72 64.37c-4.24 0-4.42-3.39-.61-3.41 35.91-.16 28.11.38 37.19-.65 1.68-.19 2.38.24 2.25 1.89-.26 3.39-.64 6.78-1 10.16-.25 2.16-3.2 2.61-3.4-.15-.38-5.31-2.15-4.45-15.63-5.08-1.58-.07-1.64 0-1.64 1.52V304c0 1.65 0 1.6 1.62 1.47 3.12-.25 10.31.34 15.69-1.52.47-.16 3.3-1.79 3.07 1.76 0 .21-.76 10.35-1.18 11.39-.53 1.29-1.88 1.51-2.58.32-1.17-2 0-5.08-3.71-5.3-15.42-.9-12.91-2.55-12.91 6 0 12.25-.76 16.11 3.89 16.24 16.64.48 14.4 0 16.43-5.71.84-2.37 3.5-1.77 3.18.58-.44 3.21-.85 6.43-1.23 9.64 0 .36-.16 2.4-4.66 2.39-37.16-.08-34.54-.19-35.21-.31-2.72-.51-2.2-3 .22-3.45 1.1-.19 4 .54 4.16-2.56 2.44-56.22-.07-51.34-3.91-51.33zm-.41-109.52c2.46.61 3.13 1.76 2.95 4.65-.33 5.3-.34 9-.55 9.69-.66 2.23-3.15 2.12-3.34-.27-.38-4.81-3.05-7.82-7.57-9.15-26.28-7.73-32.81 15.46-27.17 30.22 5.88 15.41 22 15.92 28.86 13.78 5.92-1.85 5.88-6.5 6.91-7.58 1.23-1.3 2.25-1.84 3.12 1.1 0 .1.57 11.89-6 12.75-1.6.21-19.38 3.69-32.68-3.39-21-11.19-16.74-35.47-6.88-45.33 14-14.06 39.91-7.06 42.32-6.47zM289.8 280.14c3.28 0 3.66 3 .16 3.43-2.61.32-5-.42-5 5.46 0 2-.19 29.05.4 41.45.11 2.29 1.15 3.52 3.44 3.65 22 1.21 14.95-1.65 18.79-6.34 1.83-2.24 2.76.84 2.76 1.08.35 13.62-4 12.39-5.19 12.4l-38.16-.19c-1.93-.23-2.06-3-.42-3.38 2-.48 4.94.4 5.13-2.8 1-15.87.57-44.65.34-47.81-.27-3.77-2.8-3.27-5.68-3.71-2.47-.38-2-3.22.34-3.22 1.45-.02 17.97-.03 23.09-.02zm-31.63-57.79c.07 4.08 2.86 3.46 6 3.58 2.61.1 2.53 3.41-.07 3.43-6.48 0-13.7 0-21.61-.06-3.84 0-3.38-3.35 0-3.37 4.49 0 3.24 1.61 3.41-45.54 0-5.08-3.27-3.54-4.72-4.23-2.58-1.23-1.36-3.09.41-3.15 1.29 0 20.19-.41 21.17.21s1.87 1.65-.42 2.86c-1 .52-3.86-.28-4.15 2.47 0 .21-.82 1.63-.07 43.8zm-36.91 274.27a2.93 2.93 0 0 0 3.26 0c17-9.79 182-103.57 197.42-112.51-.14-.43 11.26-.18-181.52-.27-1.22 0-1.57.37-1.53 1.56 0 .1 1.25 44.51 1.22 50.38a28.33 28.33 0 0 1-1.36 7.71c-.55 1.83.38-.5-13.5 32.23-.73 1.72-1 2.21-2-.08-4.19-10.34-8.28-20.72-12.57-31a23.6 23.6 0 0 1-2-10.79c.16-2.46.8-16.12 1.51-48 0-1.95 0-2-2-2h-183c2.58 1.63 178.32 102.57 196 112.76zm-90.9-188.75c0 2.4.36 2.79 2.76 3 11.54 1.17 21 3.74 25.64-7.32 6-14.46 2.66-34.41-12.48-38.84-2-.59-16-2.76-15.94 1.51.05 8.04.01 11.61.02 41.65zm105.75-15.05c0 2.13 1.07 38.68 1.09 39.13.34 9.94-25.58 5.77-25.23-2.59.08-2 1.37-37.42 1.1-39.43-14.1 7.44-14.42 40.21 6.44 48.8a17.9 17.9 0 0 0 22.39-7.07c4.91-7.76 6.84-29.47-5.43-39a2.53 2.53 0 0 1-.36.12zm-12.28-198c-9.83 0-9.73 14.75-.07 14.87s10.1-14.88.07-14.91zm-80.15 103.83c0 1.8.41 2.4 2.17 2.58 13.62 1.39 12.51-11 12.16-13.36-1.69-11.22-14.38-10.2-14.35-7.81.05 4.5-.03 13.68.02 18.59zm212.32 6.4l-6.1-15.84c-2.16 5.48-4.16 10.57-6.23 15.84z"],
+ "css3": [512, 512, [], "f13c", "M480 32l-64 368-223.3 80L0 400l19.6-94.8h82l-8 40.6L210 390.2l134.1-44.4 18.8-97.1H29.5l16-82h333.7l10.5-52.7H56.3l16.3-82H480z"],
+ "css3-alt": [384, 512, [], "f38b", "M0 32l34.9 395.8L192 480l157.1-52.2L384 32H0zm313.1 80l-4.8 47.3L193 208.6l-.3.1h111.5l-12.8 146.6-98.2 28.7-98.8-29.2-6.4-73.9h48.9l3.2 38.3 52.6 13.3 54.7-15.4 3.7-61.6-166.3-.5v-.1l-.2.1-3.6-46.3L193.1 162l6.5-2.7H76.7L70.9 112h242.2z"],
+ "cuttlefish": [440, 512, [], "f38c", "M344 305.5c-17.5 31.6-57.4 54.5-96 54.5-56.6 0-104-47.4-104-104s47.4-104 104-104c38.6 0 78.5 22.9 96 54.5 13.7-50.9 41.7-93.3 87-117.8C385.7 39.1 320.5 8 248 8 111 8 0 119 0 256s111 248 248 248c72.5 0 137.7-31.1 183-80.7-45.3-24.5-73.3-66.9-87-117.8z"],
+ "d-and-d": [576, 512, [], "f38d", "M82.5 98.9c-.6-17.2 2-33.8 12.7-48.2.3 7.4 1.2 14.5 4.2 21.6 5.9-27.5 19.7-49.3 42.3-65.5-1.9 5.9-3.5 11.8-3 17.7 8.7-7.4 18.8-17.8 44.4-22.7 14.7-2.8 29.7-2 42.1 1 38.5 9.3 61 34.3 69.7 72.3 5.3 23.1.7 45-8.3 66.4-5.2 12.4-12 24.4-20.7 35.1-2-1.9-3.9-3.8-5.8-5.6-42.8-40.8-26.8-25.2-37.4-37.4-1.1-1.2-1-2.2-.1-3.6 8.3-13.5 11.8-28.2 10-44-1.1-9.8-4.3-18.9-11.3-26.2-14.5-15.3-39.2-15-53.5.6-11.4 12.5-14.1 27.4-10.9 43.6.2 1.3.4 2.7 0 3.9-3.4 13.7-4.6 27.6-2.5 41.6.1.5.1 1.1.1 1.6 0 .3-.1.5-.2 1.1-21.8-11-36-28.3-43.2-52.2-8.3 17.8-11.1 35.5-6.6 54.1-15.6-15.2-21.3-34.3-22-55.2zm469.6 123.2c-11.6-11.6-25-20.4-40.1-26.6-12.8-5.2-26-7.9-39.9-7.1-10 .6-19.6 3.1-29 6.4-2.5.9-5.1 1.6-7.7 2.2-4.9 1.2-7.3-3.1-4.7-6.8 3.2-4.6 3.4-4.2 15-12 .6-.4 1.2-.8 2.2-1.5h-2.5c-.6 0-1.2.2-1.9.3-19.3 3.3-30.7 15.5-48.9 29.6-10.4 8.1-13.8 3.8-12-.5 1.4-3.5 3.3-6.7 5.1-10 1-1.8 2.3-3.4 3.5-5.1-.2-.2-.5-.3-.7-.5-27 18.3-46.7 42.4-57.7 73.3.3.3.7.6 1 .9.3-.6.5-1.2.9-1.7 10.4-12.1 22.8-21.8 36.6-29.8 18.2-10.6 37.5-18.3 58.7-20.2 4.3-.4 8.7-.1 13.1-.1-1.8.7-3.5.9-5.3 1.1-18.5 2.4-35.5 9-51.5 18.5-30.2 17.9-54.5 42.2-75.1 70.4-.3.4-.4.9-.7 1.3 14.5 5.3 24 17.3 36.1 25.6.2-.1.3-.2.4-.4l1.2-2.7c12.2-26.9 27-52.3 46.7-74.5 16.7-18.8 38-25.3 62.5-20 5.9 1.3 11.4 4.4 17.2 6.8 2.3-1.4 5.1-3.2 8-4.7 8.4-4.3 17.4-7 26.7-9 14.7-3.1 29.5-4.9 44.5-1.3v-.5c-.5-.4-1.2-.8-1.7-1.4zM316.7 397.6c-39.4-33-22.8-19.5-42.7-35.6-.8.9 0-.2-1.9 3-11.2 19.1-25.5 35.3-44 47.6-10.3 6.8-21.5 11.8-34.1 11.8-21.6 0-38.2-9.5-49.4-27.8-12-19.5-13.3-40.7-8.2-62.6 7.8-33.8 30.1-55.2 38.6-64.3-18.7-6.2-33 1.7-46.4 13.9.8-13.9 4.3-26.2 11.8-37.3-24.3 10.6-45.9 25-64.8 43.9-.3-5.8 5.4-43.7 5.6-44.7.3-2.7-.6-5.3-3-7.4-24.2 24.7-44.5 51.8-56.1 84.6 7.4-5.9 14.9-11.4 23.6-16.2-8.3 22.3-19.6 52.8-7.8 101.1 4.6 19 11.9 36.8 24.1 52.3 2.9 3.7 6.3 6.9 9.5 10.3.2-.2.4-.3.6-.5-1.4-7-2.2-14.1-1.5-21.9 2.2 3.2 3.9 6 5.9 8.6 12.6 16 28.7 27.4 47.2 35.6 25 11.3 51.1 13.3 77.9 8.6 54.9-9.7 90.7-48.6 116-98.8 1-1.8.6-2.9-.9-4.2zm172-46.4c-9.5-3.1-22.2-4.2-28.7-2.9 9.9 4 14.1 6.6 18.8 12 12.6 14.4 10.4 34.7-5.4 45.6-11.7 8.1-24.9 10.5-38.9 9.1-1.2-.1-2.3-.4-3-.6 2.8-3.7 6-7 8.1-10.8 9.4-16.8 5.4-42.1-8.7-56.1-2.1-2.1-4.6-3.9-7-5.9-.3 1.3-.1 2.1.1 2.8 4.2 16.6-8.1 32.4-24.8 31.8-7.6-.3-13.9-3.8-19.6-8.5-19.5-16.1-39.1-32.1-58.5-48.3-5.9-4.9-12.5-8.1-20.1-8.7-4.6-.4-9.3-.6-13.9-.9-5.9-.4-8.8-2.8-10.4-8.4-.9-3.4-1.5-6.8-2.2-10.2-1.5-8.1-6.2-13-14.3-14.2-4.4-.7-8.9-1-13.3-1.5-13-1.4-19.8-7.4-22.6-20.3-5 11-1.6 22.4 7.3 29.9 4.5 3.8 9.3 7.3 13.8 11.2 4.6 3.8 7.4 8.7 7.9 14.8.4 4.7.8 9.5 1.8 14.1 2.2 10.6 8.9 18.4 17 25.1 16.5 13.7 33 27.3 49.5 41.1 17.9 15 13.9 32.8 13 56-.9 22.9 12.2 42.9 33.5 51.2 1 .4 2 .6 3.6 1.1-15.7-18.2-10.1-44.1.7-52.3.3 2.2.4 4.3.9 6.4 9.4 44.1 45.4 64.2 85 56.9 16-2.9 30.6-8.9 42.9-19.8 2-1.8 3.7-4.1 5.9-6.5-19.3 4.6-35.8.1-50.9-10.6.7-.3 1.3-.3 1.9-.3 21.3 1.8 40.6-3.4 57-17.4 19.5-16.6 26.6-42.9 17.4-66-8.3-20.1-23.6-32.3-43.8-38.9zM99.4 179.3c-5.3-9.2-13.2-15.6-22.1-21.3 13.7-.5 26.6.2 39.6 3.7-7-12.2-8.5-24.7-5-38.7 5.3 11.9 13.7 20.1 23.6 26.8 19.7 13.2 35.7 19.6 46.7 30.2 3.4 3.3 6.3 7.1 9.6 10.9-.8-2.1-1.4-4.1-2.2-6-5-10.6-13-18.6-22.6-25-1.8-1.2-2.8-2.5-3.4-4.5-3.3-12.5-3-25.1-.7-37.6 1-5.5 2.8-10.9 4.5-16.3.8-2.4 2.3-4.6 4-6.6.6 6.9 0 25.5 19.6 46 10.8 11.3 22.4 21.9 33.9 32.7 9 8.5 18.3 16.7 25.5 26.8 1.1 1.6 2.2 3.3 3.8 4.7-5-13-14.2-24.1-24.2-33.8-9.6-9.3-19.4-18.4-29.2-27.4-3.3-3-4.6-6.7-5.1-10.9-1.2-10.4 0-20.6 4.3-30.2.5-1 1.1-2 1.9-3.3.5 4.2.6 7.9 1.4 11.6 4.8 23.1 20.4 36.3 49.3 63.5 10 9.4 19.3 19.2 25.6 31.6 4.8 9.3 7.3 19 5.7 29.6-.1.6.5 1.7 1.1 2 6.2 2.6 10 6.9 9.7 14.3 7.7-2.6 12.5-8 16.4-14.5 4.2 20.2-9.1 50.3-27.2 58.7.4-4.5 5-23.4-16.5-27.7-6.8-1.3-12.8-1.3-22.9-2.1 4.7-9 10.4-20.6.5-22.4-24.9-4.6-52.8 1.9-57.8 4.6 8.2.4 16.3 1 23.5 3.3-2 6.5-4 12.7-5.8 18.9-1.9 6.5 2.1 14.6 9.3 9.6 1.2-.9 2.3-1.9 3.3-2.7-3.1 17.9-2.9 15.9-2.8 18.3.3 10.2 9.5 7.8 15.7 7.3-2.5 11.8-29.5 27.3-45.4 25.8 7-4.7 12.7-10.3 15.9-17.9-6.5.8-12.9 1.6-19.2 2.4l-.3-.9c4.7-3.4 8-7.8 10.2-13.1 8.7-21.1-3.6-38-25-39.9-9.1-.8-17.8.8-25.9 5.5 6.2-15.6 17.2-26.6 32.6-34.5-15.2-4.3-8.9-2.7-24.6-6.3 14.6-9.3 30.2-13.2 46.5-14.6-5.2-3.2-48.1-3.6-70.2 20.9 7.9 1.4 15.5 2.8 23.2 4.2-23.8 7-44 19.7-62.4 35.6 1.1-4.8 2.7-9.5 3.3-14.3.6-4.5.8-9.2.1-13.6-1.5-9.4-8.9-15.1-19.7-16.3-7.9-.9-15.6.1-23.3 1.3-.9.1-1.7.3-2.9 0 15.8-14.8 36-21.7 53.1-33.5 6-4.5 6.8-8.2 3-14.9zm128.4 26.8c3.3 16 12.6 25.5 23.8 24.3-4.6-11.3-12.1-19.5-23.8-24.3z"],
+ "d-and-d-beyond": [640, 512, [], "f6ca", "M313.8 241.5c13.8 0 21-10.1 24.8-17.9-1-1.1-5-4.2-7.4-6.6-2.4 4.3-8.2 10.7-13.9 10.7-10.2 0-15.4-14.7-3.2-26.6-.5-.2-4.3-1.8-8 2.4 0-3 1-5.1 2.1-6.6-3.5 1.3-9.8 5.6-11.4 7.9.2-5.8 1.6-7.5.6-9l-.2-.2s-8.5 5.6-9.3 14.7c0 0 1.1-1.6 2.1-1.9.6-.3 1.3 0 .6 1.9-.2.6-5.8 15.7 5.1 26-.6-1.6-1.9-7.6 2.4-1.9-.3.1 5.8 7.1 15.7 7.1zm52.4-21.1c0-4-4.9-4.4-5.6-4.5 2 3.9.9 7.5.2 9 2.5-.4 5.4-1.6 5.4-4.5zm10.3 5.2c0-6.4-6.2-11.4-13.5-10.7 8 1.3 5.6 13.8-5 11.4 3.7-2.6 3.2-9.9-1.3-12.5 1.4 4.2-3 8.2-7.4 4.6-2.4-1.9-8-6.6-10.6-8.6-2.4-2.1-5.5-1-6.6-1.8-1.3-1.1-.5-3.8-2.2-5-1.6-.8-3-.3-4.8-1-1.6-.6-2.7-1.9-2.6-3.5-2.5 4.4 3.4 6.3 4.5 8.5 1 1.9-.8 4.8 4 8.5 14.8 11.6 9.1 8 10.4 18.1.6 4.3 4.2 6.7 6.4 7.4-2.1-1.9-2.9-6.4 0-9.3 0 13.9 19.2 13.3 23.1 6.4-2.4 1.1-7-.2-9-1.9 7.7 1 14.2-4.1 14.6-10.6zm-39.4-18.4c2 .8 1.6.7 6.4 4.5 10.2-24.5 21.7-15.7 22-15.5 2.2-1.9 9.8-3.8 13.8-2.7-2.4-2.7-7.5-6.2-13.3-6.2-4.7 0-7.4 2.2-8 1.3-.8-1.4 3.2-3.4 3.2-3.4-5.4.2-9.6 6.7-11.2 5.9-1.1-.5 1.4-3.7 1.4-3.7-5.1 2.9-9.3 9.1-10.2 13 4.6-5.8 13.8-9.8 19.7-9-10.5.5-19.5 9.7-23.8 15.8zm242.5 51.9c-20.7 0-40 1.3-50.3 2.1l7.4 8.2v77.2l-7.4 8.2c10.4.8 30.9 2.1 51.6 2.1 42.1 0 59.1-20.7 59.1-48.9 0-29.3-23.2-48.9-60.4-48.9zm-15.1 75.6v-53.3c30.1-3.3 46.8 3.8 46.8 26.3 0 25.6-21.4 30.2-46.8 27zM301.6 181c-1-3.4-.2-6.9 1.1-9.4 1 3 2.6 6.4 7.5 9-.5-2.4-.2-5.6.5-8-1.4-5.4 2.1-9.9 6.4-9.9 6.9 0 8.5 8.8 4.7 14.4 2.1 3.2 5.5 5.6 7.7 7.8 3.2-3.7 5.5-9.5 5.5-13.8 0-8.2-5.5-15.9-16.7-16.5-20-.9-20.2 16.6-20 18.9.5 5.2 3.4 7.8 3.3 7.5zm-.4 6c-.5 1.8-7 3.7-10.2 6.9 4.8-1 7-.2 7.8 1.8.5 1.4-.2 3.4-.5 5.6 1.6-1.8 7-5.5 11-6.2-1-.3-3.4-.8-4.3-.8 2.9-3.4 9.3-4.5 12.8-3.7-2.2-.2-6.7 1.1-8.5 2.6 1.6.3 3 .6 4.3 1.1-2.1.8-4.8 3.4-5.8 6.1 7-5 13.1 5.2 7 8.2.8.2 2.7 0 3.5-.5-.3 1.1-1.9 3-3 3.4 2.9 0 7-1.9 8.2-4.6 0 0-1.8.6-2.6-.2s.3-4.3.3-4.3c-2.3 2.9-3.4-1.3-1.3-4.2-1-.3-3.5-.6-4.6-.5 3.2-1.1 10.4-1.8 11.2-.3.6 1.1-1 3.4-1 3.4 4-.5 8.3 1.1 6.7 5.1 2.9-1.4 5.5-5.9 4.8-10.4-.3 1-1.6 2.4-2.9 2.7.2-1.4-1-2.2-1.9-2.6 1.7-9.6-14.6-14.2-14.1-23.9-1 1.3-1.8 5-.8 7.1 2.7 3.2 8.7 6.7 10.1 12.2-2.6-6.4-15.1-11.4-14.6-20.2-1.6 1.6-2.6 7.8-1.3 11 2.4 1.4 4.5 3.8 4.8 6.1-2.2-5.1-11.4-6.1-13.9-12.2-.6 2.2-.3 5 1 6.7 0 0-2.2-.8-7-.6 1.7.6 5.1 3.5 4.8 5.2zm25.9 7.4c-2.7 0-3.5-2.1-4.2-4.3 3.3 1.3 4.2 4.3 4.2 4.3zm38.9 3.7l-1-.6c-1.1-1-2.9-1.4-4.7-1.4-2.9 0-5.8 1.3-7.5 3.4-.8.8-1.4 1.8-2.1 2.6v15.7c3.5 2.6 7.1-2.9 3-7.2 1.5.3 4.6 2.7 5.1 3.2 0 0 2.6-.5 5-.5 2.1 0 3.9.3 5.6 1.1V196c-1.1.5-2.2 1-2.7 1.4zM79.9 305.9c17.2-4.6 16.2-18 16.2-19.9 0-20.6-24.1-25-37-25H3l8.3 8.6v29.5H0l11.4 14.6V346L3 354.6c61.7 0 73.8 1.5 86.4-5.9 6.7-4 9.9-9.8 9.9-17.6 0-5.1 2.6-18.8-19.4-25.2zm-41.3-27.5c20 0 29.6-.8 29.6 9.1v3c0 12.1-19 8.8-29.6 8.8zm0 59.2V315c12.2 0 32.7-2.3 32.7 8.8v4.5h.2c0 11.2-12.5 9.3-32.9 9.3zm101.2-19.3l23.1.2v-.2l14.1-21.2h-37.2v-14.9h52.4l-14.1-21v-.2l-73.5.2 7.4 8.2v77.1l-7.4 8.2h81.2l14.1-21.2-60.1.2zm214.7-60.1c-73.9 0-77.5 99.3-.3 99.3 77.9 0 74.1-99.3.3-99.3zm-.3 77.5c-37.4 0-36.9-55.3.2-55.3 36.8.1 38.8 55.3-.2 55.3zm-91.3-8.3l44.1-66.2h-41.7l6.1 7.2-20.5 37.2h-.3l-21-37.2 6.4-7.2h-44.9l44.1 65.8.2 19.4-7.7 8.2h42.6l-7.2-8.2zm-28.4-151.3c1.6 1.3 2.9 2.4 2.9 6.6v38.8c0 4.2-.8 5.3-2.7 6.4-.1.1-7.5 4.5-7.9 4.6h35.1c10 0 17.4-1.5 26-8.6-.6-5 .2-9.5.8-12 0-.2-1.8 1.4-2.7 3.5 0-5.7 1.6-15.4 9.6-20.5-.1 0-3.7-.8-9 1.1 2-3.1 10-7.9 10.4-7.9-8.2-26-38-22.9-32.2-22.9-30.9 0-32.6.3-39.9-4 .1.8.5 8.2 9.6 14.9zm21.5 5.5c4.6 0 23.1-3.3 23.1 17.3 0 20.7-18.4 17.3-23.1 17.3zm228.9 79.6l7 8.3V312h-.3c-5.4-14.4-42.3-41.5-45.2-50.9h-31.6l7.4 8.5v76.9l-7.2 8.3h39l-7.4-8.2v-47.4h.3c3.7 10.6 44.5 42.9 48.5 55.6h21.3v-85.2l7.4-8.3zm-106.7-96.1c-32.2 0-32.8.2-39.9-4 .1.7.5 8.3 9.6 14.9 3.1 2 2.9 4.3 2.9 9.5 1.8-1.1 3.8-2.2 6.1-3-1.1 1.1-2.7 2.7-3.5 4.5 1-1.1 7.5-5.1 14.6-3.5-1.6.3-4 1.1-6.1 2.9.1 0 2.1-1.1 7.5-.3v-4.3c4.7 0 23.1-3.4 23.1 17.3 0 20.5-18.5 17.3-19.7 17.3 5.7 4.4 5.8 12 2.2 16.3h.3c33.4 0 36.7-27.3 36.7-34 0-3.8-1.1-32-33.8-33.6z"],
+ "dailymotion": [448, 512, [], "e052", "M298.93,267a48.4,48.4,0,0,0-24.36-6.21q-19.83,0-33.44,13.27t-13.61,33.42q0,21.16,13.28,34.6t33.43,13.44q20.5,0,34.11-13.78T322,307.47A47.13,47.13,0,0,0,315.9,284,44.13,44.13,0,0,0,298.93,267ZM0,32V480H448V32ZM374.71,405.26h-53.1V381.37h-.67q-15.79,26.2-55.78,26.2-27.56,0-48.89-13.1a88.29,88.29,0,0,1-32.94-35.77q-11.6-22.68-11.59-50.89,0-27.56,11.76-50.22a89.9,89.9,0,0,1,32.93-35.78q21.18-13.09,47.72-13.1a80.87,80.87,0,0,1,29.74,5.21q13.28,5.21,25,17V153l55.79-12.09Z"],
+ "dashcube": [448, 512, [], "f210", "M326.6 104H110.4c-51.1 0-91.2 43.3-91.2 93.5V427c0 50.5 40.1 85 91.2 85h227.2c51.1 0 91.2-34.5 91.2-85V0L326.6 104zM153.9 416.5c-17.7 0-32.4-15.1-32.4-32.8V240.8c0-17.7 14.7-32.5 32.4-32.5h140.7c17.7 0 32 14.8 32 32.5v123.5l51.1 52.3H153.9z"],
+ "deezer": [576, 512, [], "e077", "M451.46,244.71H576V172H451.46Zm0-173.89v72.67H576V70.82Zm0,275.06H576V273.2H451.46ZM0,447.09H124.54V374.42H0Zm150.47,0H275V374.42H150.47Zm150.52,0H425.53V374.42H301Zm150.47,0H576V374.42H451.46ZM301,345.88H425.53V273.2H301Zm-150.52,0H275V273.2H150.47Zm0-101.17H275V172H150.47Z"],
+ "delicious": [448, 512, [], "f1a5", "M446.5 68c-.4-1.5-.9-3-1.4-4.5-.9-2.5-2-4.8-3.3-7.1-1.4-2.4-3-4.8-4.7-6.9-2.1-2.5-4.4-4.8-6.9-6.8-1.1-.9-2.2-1.7-3.3-2.5-1.3-.9-2.6-1.7-4-2.4-1.8-1-3.6-1.8-5.5-2.5-1.7-.7-3.5-1.3-5.4-1.7-3.8-1-7.9-1.5-12-1.5H48C21.5 32 0 53.5 0 80v352c0 4.1.5 8.2 1.5 12 2 7.7 5.8 14.6 11 20.3 1 1.1 2.1 2.2 3.3 3.3 5.7 5.2 12.6 9 20.3 11 3.8 1 7.9 1.5 12 1.5h352c26.5 0 48-21.5 48-48V80c-.1-4.1-.6-8.2-1.6-12zM416 432c0 8.8-7.2 16-16 16H224V256H32V80c0-8.8 7.2-16 16-16h176v192h192z"],
+ "deploydog": [512, 512, [], "f38e", "M382.2 136h51.7v239.6h-51.7v-20.7c-19.8 24.8-52.8 24.1-73.8 14.7-26.2-11.7-44.3-38.1-44.3-71.8 0-29.8 14.8-57.9 43.3-70.8 20.2-9.1 52.7-10.6 74.8 12.9V136zm-64.7 161.8c0 18.2 13.6 33.5 33.2 33.5 19.8 0 33.2-16.4 33.2-32.9 0-17.1-13.7-33.2-33.2-33.2-19.6 0-33.2 16.4-33.2 32.6zM188.5 136h51.7v239.6h-51.7v-20.7c-19.8 24.8-52.8 24.1-73.8 14.7-26.2-11.7-44.3-38.1-44.3-71.8 0-29.8 14.8-57.9 43.3-70.8 20.2-9.1 52.7-10.6 74.8 12.9V136zm-64.7 161.8c0 18.2 13.6 33.5 33.2 33.5 19.8 0 33.2-16.4 33.2-32.9 0-17.1-13.7-33.2-33.2-33.2-19.7 0-33.2 16.4-33.2 32.6zM448 96c17.5 0 32 14.4 32 32v256c0 17.5-14.4 32-32 32H64c-17.5 0-32-14.4-32-32V128c0-17.5 14.4-32 32-32h384m0-32H64C28.8 64 0 92.8 0 128v256c0 35.2 28.8 64 64 64h384c35.2 0 64-28.8 64-64V128c0-35.2-28.8-64-64-64z"],
+ "deskpro": [480, 512, [], "f38f", "M205.9 512l31.1-38.4c12.3-.2 25.6-1.4 36.5-6.6 38.9-18.6 38.4-61.9 38.3-63.8-.1-5-.8-4.4-28.9-37.4H362c-.2 50.1-7.3 68.5-10.2 75.7-9.4 23.7-43.9 62.8-95.2 69.4-8.7 1.1-32.8 1.2-50.7 1.1zm200.4-167.7c38.6 0 58.5-13.6 73.7-30.9l-175.5-.3-17.4 31.3 119.2-.1zm-43.6-223.9v168.3h-73.5l-32.7 55.5H250c-52.3 0-58.1-56.5-58.3-58.9-1.2-13.2-21.3-11.6-20.1 1.8 1.4 15.8 8.8 40 26.4 57.1h-91c-25.5 0-110.8-26.8-107-114V16.9C0 .9 9.7.3 15 .1h82c.2 0 .3.1.5.1 4.3-.4 50.1-2.1 50.1 43.7 0 13.3 20.2 13.4 20.2 0 0-18.2-5.5-32.8-15.8-43.7h84.2c108.7-.4 126.5 79.4 126.5 120.2zm-132.5 56l64 29.3c13.3-45.5-42.2-71.7-64-29.3z"],
+ "dev": [448, 512, [], "f6cc", "M120.12 208.29c-3.88-2.9-7.77-4.35-11.65-4.35H91.03v104.47h17.45c3.88 0 7.77-1.45 11.65-4.35 3.88-2.9 5.82-7.25 5.82-13.06v-69.65c-.01-5.8-1.96-10.16-5.83-13.06zM404.1 32H43.9C19.7 32 .06 51.59 0 75.8v360.4C.06 460.41 19.7 480 43.9 480h360.2c24.21 0 43.84-19.59 43.9-43.8V75.8c-.06-24.21-19.7-43.8-43.9-43.8zM154.2 291.19c0 18.81-11.61 47.31-48.36 47.25h-46.4V172.98h47.38c35.44 0 47.36 28.46 47.37 47.28l.01 70.93zm100.68-88.66H201.6v38.42h32.57v29.57H201.6v38.41h53.29v29.57h-62.18c-11.16.29-20.44-8.53-20.72-19.69V193.7c-.27-11.15 8.56-20.41 19.71-20.69h63.19l-.01 29.52zm103.64 115.29c-13.2 30.75-36.85 24.63-47.44 0l-38.53-144.8h32.57l29.71 113.72 29.57-113.72h32.58l-38.46 144.8z"],
+ "deviantart": [320, 512, [], "f1bd", "M320 93.2l-98.2 179.1 7.4 9.5H320v127.7H159.1l-13.5 9.2-43.7 84c-.3 0-8.6 8.6-9.2 9.2H0v-93.2l93.2-179.4-7.4-9.2H0V102.5h156l13.5-9.2 43.7-84c.3 0 8.6-8.6 9.2-9.2H320v93.1z"],
+ "dhl": [640, 512, [], "f790", "M238 301.2h58.7L319 271h-58.7L238 301.2zM0 282.9v6.4h81.8l4.7-6.4H0zM172.9 271c-8.7 0-6-3.6-4.6-5.5 2.8-3.8 7.6-10.4 10.4-14.1 2.8-3.7 2.8-5.9-2.8-5.9h-51l-41.1 55.8h100.1c33.1 0 51.5-22.5 57.2-30.3h-68.2zm317.5-6.9l39.3-53.4h-62.2l-39.3 53.4h62.2zM95.3 271H0v6.4h90.6l4.7-6.4zm111-26.6c-2.8 3.8-7.5 10.4-10.3 14.2-1.4 2-4.1 5.5 4.6 5.5h45.6s7.3-10 13.5-18.4c8.4-11.4.7-35-29.2-35H112.6l-20.4 27.8h111.4c5.6 0 5.5 2.2 2.7 5.9zM0 301.2h73.1l4.7-6.4H0v6.4zm323 0h58.7L404 271h-58.7c-.1 0-22.3 30.2-22.3 30.2zm222 .1h95v-6.4h-90.3l-4.7 6.4zm22.3-30.3l-4.7 6.4H640V271h-72.7zm-13.5 18.3H640v-6.4h-81.5l-4.7 6.4zm-164.2-78.6l-22.5 30.6h-26.2l22.5-30.6h-58.7l-39.3 53.4H409l39.3-53.4h-58.7zm33.5 60.3s-4.3 5.9-6.4 8.7c-7.4 10-.9 21.6 23.2 21.6h94.3l22.3-30.3H423.1z"],
+ "diaspora": [512, 512, [], "f791", "M251.64 354.55c-1.4 0-88 119.9-88.7 119.9S76.34 414 76 413.25s86.6-125.7 86.6-127.4c0-2.2-129.6-44-137.6-47.1-1.3-.5 31.4-101.8 31.7-102.1.6-.7 144.4 47 145.5 47 .4 0 .9-.6 1-1.3.4-2 1-148.6 1.7-149.6.8-1.2 104.5-.7 105.1-.3 1.5 1 3.5 156.1 6.1 156.1 1.4 0 138.7-47 139.3-46.3.8.9 31.9 102.2 31.5 102.6-.9.9-140.2 47.1-140.6 48.8-.3 1.4 82.8 122.1 82.5 122.9s-85.5 63.5-86.3 63.5c-1-.2-89-125.5-90.9-125.5z"],
+ "digg": [512, 512, [], "f1a6", "M81.7 172.3H0v174.4h132.7V96h-51v76.3zm0 133.4H50.9v-92.3h30.8v92.3zm297.2-133.4v174.4h81.8v28.5h-81.8V416H512V172.3H378.9zm81.8 133.4h-30.8v-92.3h30.8v92.3zm-235.6 41h82.1v28.5h-82.1V416h133.3V172.3H225.1v174.4zm51.2-133.3h30.8v92.3h-30.8v-92.3zM153.3 96h51.3v51h-51.3V96zm0 76.3h51.3v174.4h-51.3V172.3z"],
+ "digital-ocean": [512, 512, [], "f391", "M87 481.8h73.7v-73.6H87zM25.4 346.6v61.6H87v-61.6zm466.2-169.7c-23-74.2-82.4-133.3-156.6-156.6C164.9-32.8 8 93.7 8 255.9h95.8c0-101.8 101-180.5 208.1-141.7 39.7 14.3 71.5 46.1 85.8 85.7 39.1 107-39.7 207.8-141.4 208v.3h-.3V504c162.6 0 288.8-156.8 235.6-327.1zm-235.3 231v-95.3h-95.6v95.6H256v-.3z"],
+ "discord": [640, 512, [], "f392", "M524.531,69.836a1.5,1.5,0,0,0-.764-.7A485.065,485.065,0,0,0,404.081,32.03a1.816,1.816,0,0,0-1.923.91,337.461,337.461,0,0,0-14.9,30.6,447.848,447.848,0,0,0-134.426,0,309.541,309.541,0,0,0-15.135-30.6,1.89,1.89,0,0,0-1.924-.91A483.689,483.689,0,0,0,116.085,69.137a1.712,1.712,0,0,0-.788.676C39.068,183.651,18.186,294.69,28.43,404.354a2.016,2.016,0,0,0,.765,1.375A487.666,487.666,0,0,0,176.02,479.918a1.9,1.9,0,0,0,2.063-.676A348.2,348.2,0,0,0,208.12,430.4a1.86,1.86,0,0,0-1.019-2.588,321.173,321.173,0,0,1-45.868-21.853,1.885,1.885,0,0,1-.185-3.126c3.082-2.309,6.166-4.711,9.109-7.137a1.819,1.819,0,0,1,1.9-.256c96.229,43.917,200.41,43.917,295.5,0a1.812,1.812,0,0,1,1.924.233c2.944,2.426,6.027,4.851,9.132,7.16a1.884,1.884,0,0,1-.162,3.126,301.407,301.407,0,0,1-45.89,21.83,1.875,1.875,0,0,0-1,2.611,391.055,391.055,0,0,0,30.014,48.815,1.864,1.864,0,0,0,2.063.7A486.048,486.048,0,0,0,610.7,405.729a1.882,1.882,0,0,0,.765-1.352C623.729,277.594,590.933,167.465,524.531,69.836ZM222.491,337.58c-28.972,0-52.844-26.587-52.844-59.239S193.056,219.1,222.491,219.1c29.665,0,53.306,26.82,52.843,59.239C275.334,310.993,251.924,337.58,222.491,337.58Zm195.38,0c-28.971,0-52.843-26.587-52.843-59.239S388.437,219.1,417.871,219.1c29.667,0,53.307,26.82,52.844,59.239C470.715,310.993,447.538,337.58,417.871,337.58Z"],
+ "discourse": [448, 512, [], "f393", "M225.9 32C103.3 32 0 130.5 0 252.1 0 256 .1 480 .1 480l225.8-.2c122.7 0 222.1-102.3 222.1-223.9C448 134.3 348.6 32 225.9 32zM224 384c-19.4 0-37.9-4.3-54.4-12.1L88.5 392l22.9-75c-9.8-18.1-15.4-38.9-15.4-61 0-70.7 57.3-128 128-128s128 57.3 128 128-57.3 128-128 128z"],
+ "dochub": [416, 512, [], "f394", "M397.9 160H256V19.6L397.9 160zM304 192v130c0 66.8-36.5 100.1-113.3 100.1H96V84.8h94.7c12 0 23.1.8 33.1 2.5v-84C212.9 1.1 201.4 0 189.2 0H0v512h189.2C329.7 512 400 447.4 400 318.1V192h-96z"],
+ "docker": [640, 512, [], "f395", "M349.9 236.3h-66.1v-59.4h66.1v59.4zm0-204.3h-66.1v60.7h66.1V32zm78.2 144.8H362v59.4h66.1v-59.4zm-156.3-72.1h-66.1v60.1h66.1v-60.1zm78.1 0h-66.1v60.1h66.1v-60.1zm276.8 100c-14.4-9.7-47.6-13.2-73.1-8.4-3.3-24-16.7-44.9-41.1-63.7l-14-9.3-9.3 14c-18.4 27.8-23.4 73.6-3.7 103.8-8.7 4.7-25.8 11.1-48.4 10.7H2.4c-8.7 50.8 5.8 116.8 44 162.1 37.1 43.9 92.7 66.2 165.4 66.2 157.4 0 273.9-72.5 328.4-204.2 21.4.4 67.6.1 91.3-45.2 1.5-2.5 6.6-13.2 8.5-17.1l-13.3-8.9zm-511.1-27.9h-66v59.4h66.1v-59.4zm78.1 0h-66.1v59.4h66.1v-59.4zm78.1 0h-66.1v59.4h66.1v-59.4zm-78.1-72.1h-66.1v60.1h66.1v-60.1z"],
+ "draft2digital": [480, 512, [], "f396", "M480 398.1l-144-82.2v64.7h-91.3c30.8-35 81.8-95.9 111.8-149.3 35.2-62.6 16.1-123.4-12.8-153.3-4.4-4.6-62.2-62.9-166-41.2-59.1 12.4-89.4 43.4-104.3 67.3-13.1 20.9-17 39.8-18.2 47.7-5.5 33 19.4 67.1 56.7 67.1 31.7 0 57.3-25.7 57.3-57.4 0-27.1-19.7-52.1-48-56.8 1.8-7.3 17.7-21.1 26.3-24.7 41.1-17.3 78 5.2 83.3 33.5 8.3 44.3-37.1 90.4-69.7 127.6C84.5 328.1 18.3 396.8 0 415.9l336-.1V480zM369.9 371l47.1 27.2-47.1 27.2zM134.2 161.4c0 12.4-10 22.4-22.4 22.4s-22.4-10-22.4-22.4 10-22.4 22.4-22.4 22.4 10.1 22.4 22.4zM82.5 380.5c25.6-27.4 97.7-104.7 150.8-169.9 35.1-43.1 40.3-82.4 28.4-112.7-7.4-18.8-17.5-30.2-24.3-35.7 45.3 2.1 68 23.4 82.2 38.3 0 0 42.4 48.2 5.8 113.3-37 65.9-110.9 147.5-128.5 166.7z"],
+ "dribbble": [512, 512, [], "f17d", "M256 8C119.252 8 8 119.252 8 256s111.252 248 248 248 248-111.252 248-248S392.748 8 256 8zm163.97 114.366c29.503 36.046 47.369 81.957 47.835 131.955-6.984-1.477-77.018-15.682-147.502-6.818-5.752-14.041-11.181-26.393-18.617-41.614 78.321-31.977 113.818-77.482 118.284-83.523zM396.421 97.87c-3.81 5.427-35.697 48.286-111.021 76.519-34.712-63.776-73.185-116.168-79.04-124.008 67.176-16.193 137.966 1.27 190.061 47.489zm-230.48-33.25c5.585 7.659 43.438 60.116 78.537 122.509-99.087 26.313-186.36 25.934-195.834 25.809C62.38 147.205 106.678 92.573 165.941 64.62zM44.17 256.323c0-2.166.043-4.322.108-6.473 9.268.19 111.92 1.513 217.706-30.146 6.064 11.868 11.857 23.915 17.174 35.949-76.599 21.575-146.194 83.527-180.531 142.306C64.794 360.405 44.17 310.73 44.17 256.323zm81.807 167.113c22.127-45.233 82.178-103.622 167.579-132.756 29.74 77.283 42.039 142.053 45.189 160.638-68.112 29.013-150.015 21.053-212.768-27.882zm248.38 8.489c-2.171-12.886-13.446-74.897-41.152-151.033 66.38-10.626 124.7 6.768 131.947 9.055-9.442 58.941-43.273 109.844-90.795 141.978z"],
+ "dribbble-square": [448, 512, [], "f397", "M90.2 228.2c8.9-42.4 37.4-77.7 75.7-95.7 3.6 4.9 28 38.8 50.7 79-64 17-120.3 16.8-126.4 16.7zM314.6 154c-33.6-29.8-79.3-41.1-122.6-30.6 3.8 5.1 28.6 38.9 51 80 48.6-18.3 69.1-45.9 71.6-49.4zM140.1 364c40.5 31.6 93.3 36.7 137.3 18-2-12-10-53.8-29.2-103.6-55.1 18.8-93.8 56.4-108.1 85.6zm98.8-108.2c-3.4-7.8-7.2-15.5-11.1-23.2C159.6 253 93.4 252.2 87.4 252c0 1.4-.1 2.8-.1 4.2 0 35.1 13.3 67.1 35.1 91.4 22.2-37.9 67.1-77.9 116.5-91.8zm34.9 16.3c17.9 49.1 25.1 89.1 26.5 97.4 30.7-20.7 52.5-53.6 58.6-91.6-4.6-1.5-42.3-12.7-85.1-5.8zm-20.3-48.4c4.8 9.8 8.3 17.8 12 26.8 45.5-5.7 90.7 3.4 95.2 4.4-.3-32.3-11.8-61.9-30.9-85.1-2.9 3.9-25.8 33.2-76.3 53.9zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-64 176c0-88.2-71.8-160-160-160S64 167.8 64 256s71.8 160 160 160 160-71.8 160-160z"],
+ "dropbox": [528, 512, [], "f16b", "M264.4 116.3l-132 84.3 132 84.3-132 84.3L0 284.1l132.3-84.3L0 116.3 132.3 32l132.1 84.3zM131.6 395.7l132-84.3 132 84.3-132 84.3-132-84.3zm132.8-111.6l132-84.3-132-83.6L395.7 32 528 116.3l-132.3 84.3L528 284.8l-132.3 84.3-131.3-85z"],
+ "drupal": [448, 512, [], "f1a9", "M319.5 114.7c-22.2-14-43.5-19.5-64.7-33.5-13-8.8-31.3-30-46.5-48.3-2.7 29.3-11.5 41.2-22 49.5-21.3 17-34.8 22.2-53.5 32.3C117 123 32 181.5 32 290.5 32 399.7 123.8 480 225.8 480 327.5 480 416 406 416 294c0-112.3-83-171-96.5-179.3zm2.5 325.6c-20.1 20.1-90.1 28.7-116.7 4.2-4.8-4.8.3-12 6.5-12 0 0 17 13.3 51.5 13.3 27 0 46-7.7 54.5-14 6.1-4.6 8.4 4.3 4.2 8.5zm-54.5-52.6c8.7-3.6 29-3.8 36.8 1.3 4.1 2.8 16.1 18.8 6.2 23.7-8.4 4.2-1.2-15.7-26.5-15.7-14.7 0-19.5 5.2-26.7 11-7 6-9.8 8-12.2 4.7-6-8.2 15.9-22.3 22.4-25zM360 405c-15.2-1-45.5-48.8-65-49.5-30.9-.9-104.1 80.7-161.3 42-38.8-26.6-14.6-104.8 51.8-105.2 49.5-.5 83.8 49 108.5 48.5 21.3-.3 61.8-41.8 81.8-41.8 48.7 0 23.3 109.3-15.8 106z"],
+ "dyalog": [416, 512, [], "f399", "M0 32v119.2h64V96h107.2C284.6 96 352 176.2 352 255.9 352 332 293.4 416 171.2 416H0v64h171.2C331.9 480 416 367.3 416 255.9c0-58.7-22.1-113.4-62.3-154.3C308.9 56 245.7 32 171.2 32H0z"],
+ "earlybirds": [480, 512, [], "f39a", "M313.2 47.5c1.2-13 21.3-14 36.6-8.7.9.3 26.2 9.7 19 15.2-27.9-7.4-56.4 18.2-55.6-6.5zm-201 6.9c30.7-8.1 62 20 61.1-7.1-1.3-14.2-23.4-15.3-40.2-9.6-1 .3-28.7 10.5-20.9 16.7zM319.4 160c-8.8 0-16 7.2-16 16s7.2 16 16 16 16-7.2 16-16-7.2-16-16-16zm-159.7 0c-8.8 0-16 7.2-16 16s7.2 16 16 16 16-7.2 16-16-7.2-16-16-16zm318.5 163.2c-9.9 24-40.7 11-63.9-1.2-13.5 69.1-58.1 111.4-126.3 124.2.3.9-2-.1 24 1 33.6 1.4 63.8-3.1 97.4-8-19.8-13.8-11.4-37.1-9.8-38.1 1.4-.9 14.7 1.7 21.6 11.5 8.6-12.5 28.4-14.8 30.2-13.6 1.6 1.1 6.6 20.9-6.9 34.6 4.7-.9 8.2-1.6 9.8-2.1 2.6-.8 17.7 11.3 3.1 13.3-14.3 2.3-22.6 5.1-47.1 10.8-45.9 10.7-85.9 11.8-117.7 12.8l1 11.6c3.8 18.1-23.4 24.3-27.6 6.2.8 17.9-27.1 21.8-28.4-1l-.5 5.3c-.7 18.4-28.4 17.9-28.3-.6-7.5 13.5-28.1 6.8-26.4-8.5l1.2-12.4c-36.7.9-59.7 3.1-61.8 3.1-20.9 0-20.9-31.6 0-31.6 2.4 0 27.7 1.3 63.2 2.8-61.1-15.5-103.7-55-114.9-118.2-25 12.8-57.5 26.8-68.2.8-10.5-25.4 21.5-42.6 66.8-73.4.7-6.6 1.6-13.3 2.7-19.8-14.4-19.6-11.6-36.3-16.1-60.4-16.8 2.4-23.2-9.1-23.6-23.1.3-7.3 2.1-14.9 2.4-15.4 1.1-1.8 10.1-2 12.7-2.6 6-31.7 50.6-33.2 90.9-34.5 19.7-21.8 45.2-41.5 80.9-48.3C203.3 29 215.2 8.5 216.2 8c1.7-.8 21.2 4.3 26.3 23.2 5.2-8.8 18.3-11.4 19.6-10.7 1.1.6 6.4 15-4.9 25.9 40.3 3.5 72.2 24.7 96 50.7 36.1 1.5 71.8 5.9 77.1 34 2.7.6 11.6.8 12.7 2.6.3.5 2.1 8.1 2.4 15.4-.5 13.9-6.8 25.4-23.6 23.1-3.2 17.3-2.7 32.9-8.7 47.7 2.4 11.7 4 23.8 4.8 36.4 37 25.4 70.3 42.5 60.3 66.9zM207.4 159.9c.9-44-37.9-42.2-78.6-40.3-21.7 1-38.9 1.9-45.5 13.9-11.4 20.9 5.9 92.9 23.2 101.2 9.8 4.7 73.4 7.9 86.3-7.1 8.2-9.4 15-49.4 14.6-67.7zm52 58.3c-4.3-12.4-6-30.1-15.3-32.7-2-.5-9-.5-11 0-10 2.8-10.8 22.1-17 37.2 15.4 0 19.3 9.7 23.7 9.7 4.3 0 6.3-11.3 19.6-14.2zm135.7-84.7c-6.6-12.1-24.8-12.9-46.5-13.9-40.2-1.9-78.2-3.8-77.3 40.3-.5 18.3 5 58.3 13.2 67.8 13 14.9 76.6 11.8 86.3 7.1 15.8-7.6 36.5-78.9 24.3-101.3z"],
+ "ebay": [640, 512, [], "f4f4", "M606 189.5l-54.8 109.9-54.9-109.9h-37.5l10.9 20.6c-11.5-19-35.9-26-63.3-26-31.8 0-67.9 8.7-71.5 43.1h33.7c1.4-13.8 15.7-21.8 35-21.8 26 0 41 9.6 41 33v3.4c-12.7 0-28 .1-41.7.4-42.4.9-69.6 10-76.7 34.4 1-5.2 1.5-10.6 1.5-16.2 0-52.1-39.7-76.2-75.4-76.2-21.3 0-43 5.5-58.7 24.2v-80.6h-32.1v169.5c0 10.3-.6 22.9-1.1 33.1h31.5c.7-6.3 1.1-12.9 1.1-19.5 13.6 16.6 35.4 24.9 58.7 24.9 36.9 0 64.9-21.9 73.3-54.2-.5 2.8-.7 5.8-.7 9 0 24.1 21.1 45 60.6 45 26.6 0 45.8-5.7 61.9-25.5 0 6.6.3 13.3 1.1 20.2h29.8c-.7-8.2-1-17.5-1-26.8v-65.6c0-9.3-1.7-17.2-4.8-23.8l61.5 116.1-28.5 54.1h35.9L640 189.5zM243.7 313.8c-29.6 0-50.2-21.5-50.2-53.8 0-32.4 20.6-53.8 50.2-53.8 29.8 0 50.2 21.4 50.2 53.8 0 32.3-20.4 53.8-50.2 53.8zm200.9-47.3c0 30-17.9 48.4-51.6 48.4-25.1 0-35-13.4-35-25.8 0-19.1 18.1-24.4 47.2-25.3 13.1-.5 27.6-.6 39.4-.6zm-411.9 1.6h128.8v-8.5c0-51.7-33.1-75.4-78.4-75.4-56.8 0-83 30.8-83 77.6 0 42.5 25.3 74 82.5 74 31.4 0 68-11.7 74.4-46.1h-33.1c-12 35.8-87.7 36.7-91.2-21.6zm95-21.4H33.3c6.9-56.6 92.1-54.7 94.4 0z"],
+ "edge": [512, 512, [], "f282", "M481.92,134.48C440.87,54.18,352.26,8,255.91,8,137.05,8,37.51,91.68,13.47,203.66c26-46.49,86.22-79.14,149.46-79.14,79.27,0,121.09,48.93,122.25,50.18,22,23.8,33,50.39,33,83.1,0,10.4-5.31,25.82-15.11,38.57-1.57,2-6.39,4.84-6.39,11,0,5.06,3.29,9.92,9.14,14,27.86,19.37,80.37,16.81,80.51,16.81A115.39,115.39,0,0,0,444.94,322a118.92,118.92,0,0,0,58.95-102.44C504.39,176.13,488.39,147.26,481.92,134.48ZM212.77,475.67a154.88,154.88,0,0,1-46.64-45c-32.94-47.42-34.24-95.6-20.1-136A155.5,155.5,0,0,1,203,215.75c59-45.2,94.84-5.65,99.06-1a80,80,0,0,0-4.89-10.14c-9.24-15.93-24-36.41-56.56-53.51-33.72-17.69-70.59-18.59-77.64-18.59-38.71,0-77.9,13-107.53,35.69C35.68,183.3,12.77,208.72,8.6,243c-1.08,12.31-2.75,62.8,23,118.27a248,248,0,0,0,248.3,141.61C241.78,496.26,214.05,476.24,212.77,475.67Zm250.72-98.33a7.76,7.76,0,0,0-7.92-.23,181.66,181.66,0,0,1-20.41,9.12,197.54,197.54,0,0,1-69.55,12.52c-91.67,0-171.52-63.06-171.52-144A61.12,61.12,0,0,1,200.61,228,168.72,168.72,0,0,0,161.85,278c-14.92,29.37-33,88.13,13.33,151.66,6.51,8.91,23,30,56,47.67,23.57,12.65,49,19.61,71.7,19.61,35.14,0,115.43-33.44,163-108.87A7.75,7.75,0,0,0,463.49,377.34Z"],
+ "edge-legacy": [512, 512, [], "e078", "M25.71,228.16l.35-.48c0,.16,0,.32-.07.48Zm460.58,15.51c0-44-7.76-84.46-28.81-122.4C416.5,47.88,343.91,8,258.89,8,119,7.72,40.62,113.21,26.06,227.68c42.42-61.31,117.07-121.38,220.37-125,0,0,109.67,0,99.42,105H170c6.37-37.39,18.55-59,34.34-78.93-75.05,34.9-121.85,96.1-120.75,188.32.83,71.45,50.13,144.84,120.75,172,83.35,31.84,192.77,7.2,240.13-21.33V363.31C363.6,419.8,173.6,424.23,172.21,295.74H486.29V243.67Z"],
+ "elementor": [448, 512, [], "f430", "M425.6 32H22.4C10 32 0 42 0 54.4v403.2C0 470 10 480 22.4 480h403.2c12.4 0 22.4-10 22.4-22.4V54.4C448 42 438 32 425.6 32M164.3 355.5h-39.8v-199h39.8v199zm159.3 0H204.1v-39.8h119.5v39.8zm0-79.6H204.1v-39.8h119.5v39.8zm0-79.7H204.1v-39.8h119.5v39.8z"],
+ "ello": [496, 512, [], "f5f1", "M248 8C111.03 8 0 119.03 0 256s111.03 248 248 248 248-111.03 248-248S384.97 8 248 8zm143.84 285.2C375.31 358.51 315.79 404.8 248 404.8s-127.31-46.29-143.84-111.6c-1.65-7.44 2.48-15.71 9.92-17.36 7.44-1.65 15.71 2.48 17.36 9.92 14.05 52.91 62 90.11 116.56 90.11s102.51-37.2 116.56-90.11c1.65-7.44 9.92-12.4 17.36-9.92 7.44 1.65 12.4 9.92 9.92 17.36z"],
+ "ember": [640, 512, [], "f423", "M639.9 254.6c-1.1-10.7-10.7-6.8-10.7-6.8s-15.6 12.1-29.3 10.7c-13.7-1.3-9.4-32-9.4-32s3-28.1-5.1-30.4c-8.1-2.4-18 7.3-18 7.3s-12.4 13.7-18.3 31.2l-1.6.5s1.9-30.6-.3-37.6c-1.6-3.5-16.4-3.2-18.8 3s-14.2 49.2-15 67.2c0 0-23.1 19.6-43.3 22.8s-25-9.4-25-9.4 54.8-15.3 52.9-59.1-44.2-27.6-49-24c-4.6 3.5-29.4 18.4-36.6 59.7-.2 1.4-.7 7.5-.7 7.5s-21.2 14.2-33 18c0 0 33-55.6-7.3-80.9-11.4-6.8-21.3-.5-27.2 5.3 13.6-17.3 46.4-64.2 36.9-105.2-5.8-24.4-18-27.1-29.2-23.1-17 6.7-23.5 16.7-23.5 16.7s-22 32-27.1 79.5-12.6 105.1-12.6 105.1-10.5 10.2-20.2 10.7-5.4-28.7-5.4-28.7 7.5-44.6 7-52.1-1.1-11.6-9.9-14.2c-8.9-2.7-18.5 8.6-18.5 8.6s-25.5 38.7-27.7 44.6l-1.3 2.4-1.3-1.6s18-52.7.8-53.5-28.5 18.8-28.5 18.8-19.6 32.8-20.4 36.5l-1.3-1.6s8.1-38.2 6.4-47.6c-1.6-9.4-10.5-7.5-10.5-7.5s-11.3-1.3-14.2 5.9-13.7 55.3-15 70.7c0 0-28.2 20.2-46.8 20.4-18.5.3-16.7-11.8-16.7-11.8s68-23.3 49.4-69.2c-8.3-11.8-18-15.5-31.7-15.3-13.7.3-30.3 8.6-41.3 33.3-5.3 11.8-6.8 23-7.8 31.5 0 0-12.3 2.4-18.8-2.9s-10 0-10 0-11.2 14-.1 18.3 28.1 6.1 28.1 6.1c1.6 7.5 6.2 19.5 19.6 29.7 20.2 15.3 58.8-1.3 58.8-1.3l15.9-8.8s.5 14.6 12.1 16.7 16.4 1 36.5-47.9c11.8-25 12.6-23.6 12.6-23.6l1.3-.3s-9.1 46.8-5.6 59.7C187.7 319.4 203 318 203 318s8.3 2.4 15-21.2 19.6-49.9 19.6-49.9h1.6s-5.6 48.1 3 63.7 30.9 5.3 30.9 5.3 15.6-7.8 18-10.2c0 0 18.5 15.8 44.6 12.9 58.3-11.5 79.1-25.9 79.1-25.9s10 24.4 41.1 26.7c35.5 2.7 54.8-18.6 54.8-18.6s-.3 13.5 12.1 18.6 20.7-22.8 20.7-22.8l20.7-57.2h1.9s1.1 37.3 21.5 43.2 47-13.7 47-13.7 6.4-3.5 5.3-14.3zm-578 5.3c.8-32 21.8-45.9 29-39 7.3 7 4.6 22-9.1 31.4-13.7 9.5-19.9 7.6-19.9 7.6zm272.8-123.8s19.1-49.7 23.6-25.5-40 96.2-40 96.2c.5-16.2 16.4-70.7 16.4-70.7zm22.8 138.4c-12.6 33-43.3 19.6-43.3 19.6s-3.5-11.8 6.4-44.9 33.3-20.2 33.3-20.2 16.2 12.4 3.6 45.5zm84.6-14.6s-3-10.5 8.1-30.6c11-20.2 19.6-9.1 19.6-9.1s9.4 10.2-1.3 25.5-26.4 14.2-26.4 14.2z"],
+ "empire": [496, 512, [], "f1d1", "M287.6 54.2c-10.8-2.2-22.1-3.3-33.5-3.6V32.4c78.1 2.2 146.1 44 184.6 106.6l-15.8 9.1c-6.1-9.7-12.7-18.8-20.2-27.1l-18 15.5c-26-29.6-61.4-50.7-101.9-58.4l4.8-23.9zM53.4 322.4l23-7.7c-6.4-18.3-10-38.2-10-58.7s3.3-40.4 9.7-58.7l-22.7-7.7c3.6-10.8 8.3-21.3 13.6-31l-15.8-9.1C34 181 24.1 217.5 24.1 256s10 75 27.1 106.6l15.8-9.1c-5.3-10-9.7-20.3-13.6-31.1zM213.1 434c-40.4-8-75.8-29.1-101.9-58.7l-18 15.8c-7.5-8.6-14.4-17.7-20.2-27.4l-16 9.4c38.5 62.3 106.8 104.3 184.9 106.6v-18.3c-11.3-.3-22.7-1.7-33.5-3.6l4.7-23.8zM93.3 120.9l18 15.5c26-29.6 61.4-50.7 101.9-58.4l-4.7-23.8c10.8-2.2 22.1-3.3 33.5-3.6V32.4C163.9 34.6 95.9 76.4 57.4 139l15.8 9.1c6-9.7 12.6-18.9 20.1-27.2zm309.4 270.2l-18-15.8c-26 29.6-61.4 50.7-101.9 58.7l4.7 23.8c-10.8 1.9-22.1 3.3-33.5 3.6v18.3c78.1-2.2 146.4-44.3 184.9-106.6l-16.1-9.4c-5.7 9.7-12.6 18.8-20.1 27.4zM496 256c0 137-111 248-248 248S0 393 0 256 111 8 248 8s248 111 248 248zm-12.2 0c0-130.1-105.7-235.8-235.8-235.8S12.2 125.9 12.2 256 117.9 491.8 248 491.8 483.8 386.1 483.8 256zm-39-106.6l-15.8 9.1c5.3 9.7 10 20.2 13.6 31l-22.7 7.7c6.4 18.3 9.7 38.2 9.7 58.7s-3.6 40.4-10 58.7l23 7.7c-3.9 10.8-8.3 21-13.6 31l15.8 9.1C462 331 471.9 294.5 471.9 256s-9.9-75-27.1-106.6zm-183 177.7c16.3-3.3 30.4-11.6 40.7-23.5l51.2 44.8c11.9-13.6 21.3-29.3 27.1-46.8l-64.2-22.1c2.5-7.5 3.9-15.2 3.9-23.5s-1.4-16.1-3.9-23.5l64.5-22.1c-6.1-17.4-15.5-33.2-27.4-46.8l-51.2 44.8c-10.2-11.9-24.4-20.5-40.7-23.8l13.3-66.4c-8.6-1.9-17.7-2.8-27.1-2.8-9.4 0-18.5.8-27.1 2.8l13.3 66.4c-16.3 3.3-30.4 11.9-40.7 23.8l-51.2-44.8c-11.9 13.6-21.3 29.3-27.4 46.8l64.5 22.1c-2.5 7.5-3.9 15.2-3.9 23.5s1.4 16.1 3.9 23.5l-64.2 22.1c5.8 17.4 15.2 33.2 27.1 46.8l51.2-44.8c10.2 11.9 24.4 20.2 40.7 23.5l-13.3 66.7c8.6 1.7 17.7 2.8 27.1 2.8 9.4 0 18.5-1.1 27.1-2.8l-13.3-66.7z"],
+ "envira": [448, 512, [], "f299", "M0 32c477.6 0 366.6 317.3 367.1 366.3L448 480h-26l-70.4-71.2c-39 4.2-124.4 34.5-214.4-37C47 300.3 52 214.7 0 32zm79.7 46c-49.7-23.5-5.2 9.2-5.2 9.2 45.2 31.2 66 73.7 90.2 119.9 31.5 60.2 79 139.7 144.2 167.7 65 28 34.2 12.5 6-8.5-28.2-21.2-68.2-87-91-130.2-31.7-60-61-118.6-144.2-158.1z"],
+ "erlang": [640, 512, [], "f39d", "M87.2 53.5H0v405h100.4c-49.7-52.6-78.8-125.3-78.7-212.1-.1-76.7 24-142.7 65.5-192.9zm238.2 9.7c-45.9.1-85.1 33.5-89.2 83.2h169.9c-1.1-49.7-34.5-83.1-80.7-83.2zm230.7-9.6h.3l-.1-.1zm.3 0c31.4 42.7 48.7 97.5 46.2 162.7.5 6 .5 11.7 0 24.1H230.2c-.2 109.7 38.9 194.9 138.6 195.3 68.5-.3 118-51 151.9-106.1l96.4 48.2c-17.4 30.9-36.5 57.8-57.9 80.8H640v-405z"],
+ "ethereum": [320, 512, [], "f42e", "M311.9 260.8L160 353.6 8 260.8 160 0l151.9 260.8zM160 383.4L8 290.6 160 512l152-221.4-152 92.8z"],
+ "etsy": [384, 512, [], "f2d7", "M384 348c-1.75 10.75-13.75 110-15.5 132-117.879-4.299-219.895-4.743-368.5 0v-25.5c45.457-8.948 60.627-8.019 61-35.25 1.793-72.322 3.524-244.143 0-322-1.029-28.46-12.13-26.765-61-36v-25.5c73.886 2.358 255.933 8.551 362.999-3.75-3.5 38.25-7.75 126.5-7.75 126.5H332C320.947 115.665 313.241 68 277.25 68h-137c-10.25 0-10.75 3.5-10.75 9.75V241.5c58 .5 88.5-2.5 88.5-2.5 29.77-.951 27.56-8.502 40.75-65.251h25.75c-4.407 101.351-3.91 61.829-1.75 160.25H257c-9.155-40.086-9.065-61.045-39.501-61.5 0 0-21.5-2-88-2v139c0 26 14.25 38.25 44.25 38.25H263c63.636 0 66.564-24.996 98.751-99.75H384z"],
+ "evernote": [384, 512, [], "f839", "M120.82 132.21c1.6 22.31-17.55 21.59-21.61 21.59-68.93 0-73.64-1-83.58 3.34-.56.22-.74 0-.37-.37L123.79 46.45c.38-.37.6-.22.38.37-4.35 9.99-3.35 15.09-3.35 85.39zm79 308c-14.68-37.08 13-76.93 52.52-76.62 17.49 0 22.6 23.21 7.95 31.42-6.19 3.3-24.95 1.74-25.14 19.2-.05 17.09 19.67 25 31.2 24.89A45.64 45.64 0 0 0 312 393.45v-.08c0-11.63-7.79-47.22-47.54-55.34-7.72-1.54-65-6.35-68.35-50.52-3.74 16.93-17.4 63.49-43.11 69.09-8.74 1.94-69.68 7.64-112.92-36.77 0 0-18.57-15.23-28.23-57.95-3.38-15.75-9.28-39.7-11.14-62 0-18 11.14-30.45 25.07-32.2 81 0 90 2.32 101-7.8 9.82-9.24 7.8-15.5 7.8-102.78 1-8.3 7.79-30.81 53.41-24.14 6 .86 31.91 4.18 37.48 30.64l64.26 11.15c20.43 3.71 70.94 7 80.6 57.94 22.66 121.09 8.91 238.46 7.8 238.46C362.15 485.53 267.06 480 267.06 480c-18.95-.23-54.25-9.4-67.27-39.83zm80.94-204.84c-1 1.92-2.2 6 .85 7 14.09 4.93 39.75 6.84 45.88 5.53 3.11-.25 3.05-4.43 2.48-6.65-3.53-21.85-40.83-26.5-49.24-5.92z"],
+ "expeditedssl": [496, 512, [], "f23e", "M248 43.4C130.6 43.4 35.4 138.6 35.4 256S130.6 468.6 248 468.6 460.6 373.4 460.6 256 365.4 43.4 248 43.4zm-97.4 132.9c0-53.7 43.7-97.4 97.4-97.4s97.4 43.7 97.4 97.4v26.6c0 5-3.9 8.9-8.9 8.9h-17.7c-5 0-8.9-3.9-8.9-8.9v-26.6c0-82.1-124-82.1-124 0v26.6c0 5-3.9 8.9-8.9 8.9h-17.7c-5 0-8.9-3.9-8.9-8.9v-26.6zM389.7 380c0 9.7-8 17.7-17.7 17.7H124c-9.7 0-17.7-8-17.7-17.7V238.3c0-9.7 8-17.7 17.7-17.7h248c9.7 0 17.7 8 17.7 17.7V380zm-248-137.3v132.9c0 2.5-1.9 4.4-4.4 4.4h-8.9c-2.5 0-4.4-1.9-4.4-4.4V242.7c0-2.5 1.9-4.4 4.4-4.4h8.9c2.5 0 4.4 1.9 4.4 4.4zm141.7 48.7c0 13-7.2 24.4-17.7 30.4v31.6c0 5-3.9 8.9-8.9 8.9h-17.7c-5 0-8.9-3.9-8.9-8.9v-31.6c-10.5-6.1-17.7-17.4-17.7-30.4 0-19.7 15.8-35.4 35.4-35.4s35.5 15.8 35.5 35.4zM248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm0 478.3C121 486.3 17.7 383 17.7 256S121 25.7 248 25.7 478.3 129 478.3 256 375 486.3 248 486.3z"],
+ "facebook": [512, 512, [], "f09a", "M504 256C504 119 393 8 256 8S8 119 8 256c0 123.78 90.69 226.38 209.25 245V327.69h-63V256h63v-54.64c0-62.15 37-96.48 93.67-96.48 27.14 0 55.52 4.84 55.52 4.84v61h-31.28c-30.8 0-40.41 19.12-40.41 38.73V256h68.78l-11 71.69h-57.78V501C413.31 482.38 504 379.78 504 256z"],
+ "facebook-f": [320, 512, [], "f39e", "M279.14 288l14.22-92.66h-88.91v-60.13c0-25.35 12.42-50.06 52.24-50.06h40.42V6.26S260.43 0 225.36 0c-73.22 0-121.08 44.38-121.08 124.72v70.62H22.89V288h81.39v224h100.17V288z"],
+ "facebook-messenger": [512, 512, [], "f39f", "M256.55 8C116.52 8 8 110.34 8 248.57c0 72.3 29.71 134.78 78.07 177.94 8.35 7.51 6.63 11.86 8.05 58.23A19.92 19.92 0 0 0 122 502.31c52.91-23.3 53.59-25.14 62.56-22.7C337.85 521.8 504 423.7 504 248.57 504 110.34 396.59 8 256.55 8zm149.24 185.13l-73 115.57a37.37 37.37 0 0 1-53.91 9.93l-58.08-43.47a15 15 0 0 0-18 0l-78.37 59.44c-10.46 7.93-24.16-4.6-17.11-15.67l73-115.57a37.36 37.36 0 0 1 53.91-9.93l58.06 43.46a15 15 0 0 0 18 0l78.41-59.38c10.44-7.98 24.14 4.54 17.09 15.62z"],
+ "facebook-square": [448, 512, [], "f082", "M400 32H48A48 48 0 0 0 0 80v352a48 48 0 0 0 48 48h137.25V327.69h-63V256h63v-54.64c0-62.15 37-96.48 93.67-96.48 27.14 0 55.52 4.84 55.52 4.84v61h-31.27c-30.81 0-40.42 19.12-40.42 38.73V256h68.78l-11 71.69h-57.78V480H400a48 48 0 0 0 48-48V80a48 48 0 0 0-48-48z"],
+ "fantasy-flight-games": [512, 512, [], "f6dc", "M256 32.86L32.86 256 256 479.14 479.14 256 256 32.86zM88.34 255.83c1.96-2 11.92-12.3 96.49-97.48 41.45-41.75 86.19-43.77 119.77-18.69 24.63 18.4 62.06 58.9 62.15 59 .68.74 1.07 2.86.58 3.38-11.27 11.84-22.68 23.54-33.5 34.69-34.21-32.31-40.52-38.24-48.51-43.95-17.77-12.69-41.4-10.13-56.98 5.1-2.17 2.13-1.79 3.43.12 5.35 2.94 2.95 28.1 28.33 35.09 35.78-11.95 11.6-23.66 22.97-35.69 34.66-12.02-12.54-24.48-25.53-36.54-38.11-21.39 21.09-41.69 41.11-61.85 60.99a42569.01 42569.01 0 0 1-41.13-40.72zm234.82 101.6c-35.49 35.43-78.09 38.14-106.99 20.47-22.08-13.5-39.38-32.08-72.93-66.84 12.05-12.37 23.79-24.42 35.37-36.31 33.02 31.91 37.06 36.01 44.68 42.09 18.48 14.74 42.52 13.67 59.32-1.8 3.68-3.39 3.69-3.64.14-7.24-10.59-10.73-21.19-21.44-31.77-32.18-1.32-1.34-3.03-2.48-.8-4.69 10.79-10.71 21.48-21.52 32.21-32.29.26-.26.65-.38 1.91-1.07 12.37 12.87 24.92 25.92 37.25 38.75 21.01-20.73 41.24-40.68 61.25-60.42 13.68 13.4 27.13 26.58 40.86 40.03-20.17 20.86-81.68 82.71-100.5 101.5zM256 0L0 256l256 256 256-256L256 0zM16 256L256 16l240 240-240 240L16 256z"],
+ "fedex": [640, 512, [], "f797", "M586 284.5l53.3-59.9h-62.4l-21.7 24.8-22.5-24.8H414v-16h56.1v-48.1H318.9V236h-.5c-9.6-11-21.5-14.8-35.4-14.8-28.4 0-49.8 19.4-57.3 44.9-18-59.4-97.4-57.6-121.9-14v-24.2H49v-26.2h60v-41.1H0V345h49v-77.5h48.9c-1.5 5.7-2.3 11.8-2.3 18.2 0 73.1 102.6 91.4 130.2 23.7h-42c-14.7 20.9-45.8 8.9-45.8-14.6h85.5c3.7 30.5 27.4 56.9 60.1 56.9 14.1 0 27-6.9 34.9-18.6h.5V345h212.2l22.1-25 22.3 25H640l-54-60.5zm-446.7-16.6c6.1-26.3 41.7-25.6 46.5 0h-46.5zm153.4 48.9c-34.6 0-34-62.8 0-62.8 32.6 0 34.5 62.8 0 62.8zm167.8 19.1h-94.4V169.4h95v30.2H405v33.9h55.5v28.1h-56.1v44.7h56.1v29.6zm-45.9-39.8v-24.4h56.1v-44l50.7 57-50.7 57v-45.6h-56.1zm138.6 10.3l-26.1 29.5H489l45.6-51.2-45.6-51.2h39.7l26.6 29.3 25.6-29.3h38.5l-45.4 51 46 51.4h-40.5l-26.3-29.5z"],
+ "fedora": [448, 512, [], "f798", "M225 32C101.3 31.7.8 131.7.4 255.4L0 425.7a53.6 53.6 0 0 0 53.6 53.9l170.2.4c123.7.3 224.3-99.7 224.6-223.4S348.7 32.3 225 32zm169.8 157.2L333 126.6c2.3-4.7 3.8-9.2 3.8-14.3v-1.6l55.2 56.1a101 101 0 0 1 2.8 22.4zM331 94.3a106.06 106.06 0 0 1 58.5 63.8l-54.3-54.6a26.48 26.48 0 0 0-4.2-9.2zM118.1 247.2a49.66 49.66 0 0 0-7.7 11.4l-8.5-8.5a85.78 85.78 0 0 1 16.2-2.9zM97 251.4l11.8 11.9-.9 8a34.74 34.74 0 0 0 2.4 12.5l-27-27.2a80.6 80.6 0 0 1 13.7-5.2zm-18.2 7.4l38.2 38.4a53.17 53.17 0 0 0-14.1 4.7L67.6 266a107 107 0 0 1 11.2-7.2zm-15.2 9.8l35.3 35.5a67.25 67.25 0 0 0-10.5 8.5L53.5 278a64.33 64.33 0 0 1 10.1-9.4zm-13.3 12.3l34.9 35a56.84 56.84 0 0 0-7.7 11.4l-35.8-35.9c2.8-3.8 5.7-7.2 8.6-10.5zm-11 14.3l36.4 36.6a48.29 48.29 0 0 0-3.6 15.2l-39.5-39.8a99.81 99.81 0 0 1 6.7-12zm-8.8 16.3l41.3 41.8a63.47 63.47 0 0 0 6.7 26.2L25.8 326c1.4-4.9 2.9-9.6 4.7-14.5zm-7.9 43l61.9 62.2a31.24 31.24 0 0 0-3.6 14.3v1.1l-55.4-55.7a88.27 88.27 0 0 1-2.9-21.9zm5.3 30.7l54.3 54.6a28.44 28.44 0 0 0 4.2 9.2 106.32 106.32 0 0 1-58.5-63.8zm-5.3-37a80.69 80.69 0 0 1 2.1-17l72.2 72.5a37.59 37.59 0 0 0-9.9 8.7zm253.3-51.8l-42.6-.1-.1 56c-.2 69.3-64.4 115.8-125.7 102.9-5.7 0-19.9-8.7-19.9-24.2a24.89 24.89 0 0 1 24.5-24.6c6.3 0 6.3 1.6 15.7 1.6a55.91 55.91 0 0 0 56.1-55.9l.1-47c0-4.5-4.5-9-8.9-9l-33.6-.1c-32.6-.1-32.5-49.4.1-49.3l42.6.1.1-56a105.18 105.18 0 0 1 105.6-105 86.35 86.35 0 0 1 20.2 2.3c11.2 1.8 19.9 11.9 19.9 24 0 15.5-14.9 27.8-30.3 23.9-27.4-5.9-65.9 14.4-66 54.9l-.1 47a8.94 8.94 0 0 0 8.9 9l33.6.1c32.5.2 32.4 49.5-.2 49.4zm23.5-.3a35.58 35.58 0 0 0 7.6-11.4l8.5 8.5a102 102 0 0 1-16.1 2.9zm21-4.2L308.6 280l.9-8.1a34.74 34.74 0 0 0-2.4-12.5l27 27.2a74.89 74.89 0 0 1-13.7 5.3zm18-7.4l-38-38.4c4.9-1.1 9.6-2.4 13.7-4.7l36.2 35.9c-3.8 2.5-7.9 5-11.9 7.2zm15.5-9.8l-35.3-35.5a61.06 61.06 0 0 0 10.5-8.5l34.9 35a124.56 124.56 0 0 1-10.1 9zm13.2-12.3l-34.9-35a63.18 63.18 0 0 0 7.7-11.4l35.8 35.9a130.28 130.28 0 0 1-8.6 10.5zm11-14.3l-36.4-36.6a48.29 48.29 0 0 0 3.6-15.2l39.5 39.8a87.72 87.72 0 0 1-6.7 12zm13.5-30.9a140.63 140.63 0 0 1-4.7 14.3L345.6 190a58.19 58.19 0 0 0-7.1-26.2zm1-5.6l-71.9-72.1a32 32 0 0 0 9.9-9.2l64.3 64.7a90.93 90.93 0 0 1-2.3 16.6z"],
+ "figma": [384, 512, [], "f799", "M14 95.7924C14 42.8877 56.8878 0 109.793 0H274.161C327.066 0 369.954 42.8877 369.954 95.7924C369.954 129.292 352.758 158.776 326.711 175.897C352.758 193.019 369.954 222.502 369.954 256.002C369.954 308.907 327.066 351.795 274.161 351.795H272.081C247.279 351.795 224.678 342.369 207.666 326.904V415.167C207.666 468.777 163.657 512 110.309 512C57.5361 512 14 469.243 14 416.207C14 382.709 31.1945 353.227 57.2392 336.105C31.1945 318.983 14 289.5 14 256.002C14 222.502 31.196 193.019 57.2425 175.897C31.196 158.776 14 129.292 14 95.7924ZM176.288 191.587H109.793C74.2172 191.587 45.3778 220.427 45.3778 256.002C45.3778 291.44 73.9948 320.194 109.381 320.416C109.518 320.415 109.655 320.415 109.793 320.415H176.288V191.587ZM207.666 256.002C207.666 291.577 236.505 320.417 272.081 320.417H274.161C309.737 320.417 338.576 291.577 338.576 256.002C338.576 220.427 309.737 191.587 274.161 191.587H272.081C236.505 191.587 207.666 220.427 207.666 256.002ZM109.793 351.795C109.655 351.795 109.518 351.794 109.381 351.794C73.9948 352.015 45.3778 380.769 45.3778 416.207C45.3778 451.652 74.6025 480.622 110.309 480.622C146.591 480.622 176.288 451.186 176.288 415.167V351.795H109.793ZM109.793 31.3778C74.2172 31.3778 45.3778 60.2173 45.3778 95.7924C45.3778 131.368 74.2172 160.207 109.793 160.207H176.288V31.3778H109.793ZM207.666 160.207H274.161C309.737 160.207 338.576 131.368 338.576 95.7924C338.576 60.2173 309.737 31.3778 274.161 31.3778H207.666V160.207Z"],
+ "firefox": [512, 512, [], "f269", "M503.52,241.48c-.12-1.56-.24-3.12-.24-4.68v-.12l-.36-4.68v-.12a245.86,245.86,0,0,0-7.32-41.15c0-.12,0-.12-.12-.24l-1.08-4c-.12-.24-.12-.48-.24-.6-.36-1.2-.72-2.52-1.08-3.72-.12-.24-.12-.6-.24-.84-.36-1.2-.72-2.4-1.08-3.48-.12-.36-.24-.6-.36-1-.36-1.2-.72-2.28-1.2-3.48l-.36-1.08c-.36-1.08-.84-2.28-1.2-3.36a8.27,8.27,0,0,0-.36-1c-.48-1.08-.84-2.28-1.32-3.36-.12-.24-.24-.6-.36-.84-.48-1.2-1-2.28-1.44-3.48,0-.12-.12-.24-.12-.36-1.56-3.84-3.24-7.68-5-11.4l-.36-.72c-.48-1-.84-1.8-1.32-2.64-.24-.48-.48-1.08-.72-1.56-.36-.84-.84-1.56-1.2-2.4-.36-.6-.6-1.2-1-1.8s-.84-1.44-1.2-2.28c-.36-.6-.72-1.32-1.08-1.92s-.84-1.44-1.2-2.16a18.07,18.07,0,0,0-1.2-2c-.36-.72-.84-1.32-1.2-2s-.84-1.32-1.2-2-.84-1.32-1.2-1.92-.84-1.44-1.32-2.16a15.63,15.63,0,0,0-1.2-1.8L463.2,119a15.63,15.63,0,0,0-1.2-1.8c-.48-.72-1.08-1.56-1.56-2.28-.36-.48-.72-1.08-1.08-1.56l-1.8-2.52c-.36-.48-.6-.84-1-1.32-1-1.32-1.8-2.52-2.76-3.72a248.76,248.76,0,0,0-23.51-26.64A186.82,186.82,0,0,0,412,62.46c-4-3.48-8.16-6.72-12.48-9.84a162.49,162.49,0,0,0-24.6-15.12c-2.4-1.32-4.8-2.52-7.2-3.72a254,254,0,0,0-55.43-19.56c-1.92-.36-3.84-.84-5.64-1.2h-.12c-1-.12-1.8-.36-2.76-.48a236.35,236.35,0,0,0-38-4H255.14a234.62,234.62,0,0,0-45.48,5c-33.59,7.08-63.23,21.24-82.91,39-1.08,1-1.92,1.68-2.4,2.16l-.48.48H124l-.12.12.12-.12a.12.12,0,0,0,.12-.12l-.12.12a.42.42,0,0,1,.24-.12c14.64-8.76,34.92-16,49.44-19.56l5.88-1.44c.36-.12.84-.12,1.2-.24,1.68-.36,3.36-.72,5.16-1.08.24,0,.6-.12.84-.12C250.94,20.94,319.34,40.14,367,85.61a171.49,171.49,0,0,1,26.88,32.76c30.36,49.2,27.48,111.11,3.84,147.59-34.44,53-111.35,71.27-159,24.84a84.19,84.19,0,0,1-25.56-59,74.05,74.05,0,0,1,6.24-31c1.68-3.84,13.08-25.67,18.24-24.59-13.08-2.76-37.55,2.64-54.71,28.19-15.36,22.92-14.52,58.2-5,83.28a132.85,132.85,0,0,1-12.12-39.24c-12.24-82.55,43.31-153,94.31-170.51-27.48-24-96.47-22.31-147.71,15.36-29.88,22-51.23,53.16-62.51,90.36,1.68-20.88,9.6-52.08,25.8-83.88-17.16,8.88-39,37-49.8,62.88-15.6,37.43-21,82.19-16.08,124.79.36,3.24.72,6.36,1.08,9.6,19.92,117.11,122,206.38,244.78,206.38C392.77,503.42,504,392.19,504,255,503.88,250.48,503.76,245.92,503.52,241.48Z"],
+ "firefox-browser": [512, 512, [], "e007", "M189.37,152.86Zm-58.74-29.37C130.79,123.5,130.71,123.5,130.63,123.49Zm351.42,45.35c-10.61-25.5-32.08-53-48.94-61.73,13.72,26.89,21.67,53.88,24.7,74,0,0,0,.14.05.41-27.58-68.75-74.35-96.47-112.55-156.83-1.93-3.05-3.86-6.11-5.74-9.33-1-1.65-1.86-3.34-2.69-5.05A44.88,44.88,0,0,1,333.24.69a.63.63,0,0,0-.55-.66.9.9,0,0,0-.46,0l-.12.07-.18.1.1-.14c-54.23,31.77-76.72,87.38-82.5,122.78a130,130,0,0,0-48.33,12.33,6.25,6.25,0,0,0-3.09,7.75,6.13,6.13,0,0,0,7.79,3.79l.52-.21a117.84,117.84,0,0,1,42.11-11l1.42-.1c2-.12,4-.2,6-.22A122.61,122.61,0,0,1,291,140c.67.2,1.32.42,2,.63,1.89.57,3.76,1.2,5.62,1.87,1.36.5,2.71,1,4.05,1.58,1.09.44,2.18.88,3.25,1.35q2.52,1.13,5,2.35c.75.37,1.5.74,2.25,1.13q2.4,1.26,4.74,2.63,1.51.87,3,1.8a124.89,124.89,0,0,1,42.66,44.13c-13-9.15-36.35-18.19-58.82-14.28,87.74,43.86,64.18,194.9-57.39,189.2a108.43,108.43,0,0,1-31.74-6.12c-2.42-.91-4.8-1.89-7.16-2.93-1.38-.63-2.76-1.27-4.12-2C174.5,346,149.9,316.92,146.83,281.59c0,0,11.25-41.95,80.62-41.95,7.5,0,28.93-20.92,29.33-27-.09-2-42.54-18.87-59.09-35.18-8.85-8.71-13.05-12.91-16.77-16.06a69.58,69.58,0,0,0-6.31-4.77A113.05,113.05,0,0,1,173.92,97c-25.06,11.41-44.55,29.45-58.71,45.37h-.12c-9.67-12.25-9-52.65-8.43-61.08-.12-.53-7.22,3.68-8.15,4.31a178.54,178.54,0,0,0-23.84,20.43A214,214,0,0,0,51.9,133.36l0,0a.08.08,0,0,1,0,0,205.84,205.84,0,0,0-32.73,73.9c-.06.27-2.33,10.21-4,22.48q-.42,2.87-.78,5.74c-.57,3.69-1,7.71-1.44,14,0,.24,0,.48-.05.72-.18,2.71-.34,5.41-.49,8.12,0,.41,0,.82,0,1.24,0,134.7,109.21,243.89,243.92,243.89,120.64,0,220.82-87.58,240.43-202.62.41-3.12.74-6.26,1.11-9.41,4.85-41.83-.54-85.79-15.82-122.55Z"],
+ "first-order": [448, 512, [], "f2b0", "M12.9 229.2c.1-.1.2-.3.3-.4 0 .1 0 .3-.1.4h-.2zM224 96.6c-7.1 0-14.6.6-21.4 1.7l3.7 67.4-22-64c-14.3 3.7-27.7 9.4-40 16.6l29.4 61.4-45.1-50.9c-11.4 8.9-21.7 19.1-30.6 30.9l50.6 45.4-61.1-29.7c-7.1 12.3-12.9 25.7-16.6 40l64.3 22.6-68-4c-.9 7.1-1.4 14.6-1.4 22s.6 14.6 1.4 21.7l67.7-4-64 22.6c3.7 14.3 9.4 27.7 16.6 40.3l61.1-29.7L97.7 352c8.9 11.7 19.1 22.3 30.9 30.9l44.9-50.9-29.5 61.4c12.3 7.4 25.7 13.1 40 16.9l22.3-64.6-4 68c7.1 1.1 14.6 1.7 21.7 1.7 7.4 0 14.6-.6 21.7-1.7l-4-68.6 22.6 65.1c14.3-4 27.7-9.4 40-16.9L274.9 332l44.9 50.9c11.7-8.9 22-19.1 30.6-30.9l-50.6-45.1 61.1 29.4c7.1-12.3 12.9-25.7 16.6-40.3l-64-22.3 67.4 4c1.1-7.1 1.4-14.3 1.4-21.7s-.3-14.9-1.4-22l-67.7 4 64-22.3c-3.7-14.3-9.1-28-16.6-40.3l-60.9 29.7 50.6-45.4c-8.9-11.7-19.1-22-30.6-30.9l-45.1 50.9 29.4-61.1c-12.3-7.4-25.7-13.1-40-16.9L241.7 166l4-67.7c-7.1-1.2-14.3-1.7-21.7-1.7zM443.4 128v256L224 512 4.6 384V128L224 0l219.4 128zm-17.1 10.3L224 20.9 21.7 138.3v235.1L224 491.1l202.3-117.7V138.3zM224 37.1l187.7 109.4v218.9L224 474.9 36.3 365.4V146.6L224 37.1zm0 50.9c-92.3 0-166.9 75.1-166.9 168 0 92.6 74.6 167.7 166.9 167.7 92 0 166.9-75.1 166.9-167.7 0-92.9-74.9-168-166.9-168z"],
+ "first-order-alt": [496, 512, [], "f50a", "M248 8C111.03 8 0 119.03 0 256s111.03 248 248 248 248-111.03 248-248S384.97 8 248 8zm0 488.21C115.34 496.21 7.79 388.66 7.79 256S115.34 15.79 248 15.79 488.21 123.34 488.21 256 380.66 496.21 248 496.21zm0-459.92C126.66 36.29 28.29 134.66 28.29 256S126.66 475.71 248 475.71 467.71 377.34 467.71 256 369.34 36.29 248 36.29zm0 431.22c-116.81 0-211.51-94.69-211.51-211.51S131.19 44.49 248 44.49 459.51 139.19 459.51 256 364.81 467.51 248 467.51zm186.23-162.98a191.613 191.613 0 0 1-20.13 48.69l-74.13-35.88 61.48 54.82a193.515 193.515 0 0 1-37.2 37.29l-54.8-61.57 35.88 74.27a190.944 190.944 0 0 1-48.63 20.23l-27.29-78.47 4.79 82.93c-8.61 1.18-17.4 1.8-26.33 1.8s-17.72-.62-26.33-1.8l4.76-82.46-27.15 78.03a191.365 191.365 0 0 1-48.65-20.2l35.93-74.34-54.87 61.64a193.85 193.85 0 0 1-37.22-37.28l61.59-54.9-74.26 35.93a191.638 191.638 0 0 1-20.14-48.69l77.84-27.11-82.23 4.76c-1.16-8.57-1.78-17.32-1.78-26.21 0-9 .63-17.84 1.82-26.51l82.38 4.77-77.94-27.16a191.726 191.726 0 0 1 20.23-48.67l74.22 35.92-61.52-54.86a193.85 193.85 0 0 1 37.28-37.22l54.76 61.53-35.83-74.17a191.49 191.49 0 0 1 48.65-20.13l26.87 77.25-4.71-81.61c8.61-1.18 17.39-1.8 26.32-1.8s17.71.62 26.32 1.8l-4.74 82.16 27.05-77.76c17.27 4.5 33.6 11.35 48.63 20.17l-35.82 74.12 54.72-61.47a193.13 193.13 0 0 1 37.24 37.23l-61.45 54.77 74.12-35.86a191.515 191.515 0 0 1 20.2 48.65l-77.81 27.1 82.24-4.75c1.19 8.66 1.82 17.5 1.82 26.49 0 8.88-.61 17.63-1.78 26.19l-82.12-4.75 77.72 27.09z"],
+ "firstdraft": [384, 512, [], "f3a1", "M384 192h-64v128H192v128H0v-25.6h166.4v-128h128v-128H384V192zm-25.6 38.4v128h-128v128H64V512h192V384h128V230.4h-25.6zm25.6 192h-89.6V512H320v-64h64v-25.6zM0 0v384h128V256h128V128h128V0H0z"],
+ "flickr": [448, 512, [], "f16e", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM144.5 319c-35.1 0-63.5-28.4-63.5-63.5s28.4-63.5 63.5-63.5 63.5 28.4 63.5 63.5-28.4 63.5-63.5 63.5zm159 0c-35.1 0-63.5-28.4-63.5-63.5s28.4-63.5 63.5-63.5 63.5 28.4 63.5 63.5-28.4 63.5-63.5 63.5z"],
+ "flipboard": [448, 512, [], "f44d", "M0 32v448h448V32H0zm358.4 179.2h-89.6v89.6h-89.6v89.6H89.6V121.6h268.8v89.6z"],
+ "fly": [384, 512, [], "f417", "M197.8 427.8c12.9 11.7 33.7 33.3 33.2 50.7 0 .8-.1 1.6-.1 2.5-1.8 19.8-18.8 31.1-39.1 31-25-.1-39.9-16.8-38.7-35.8 1-16.2 20.5-36.7 32.4-47.6 2.3-2.1 2.7-2.7 5.6-3.6 3.4 0 3.9.3 6.7 2.8zM331.9 67.3c-16.3-25.7-38.6-40.6-63.3-52.1C243.1 4.5 214-.2 192 0c-44.1 0-71.2 13.2-81.1 17.3C57.3 45.2 26.5 87.2 28 158.6c7.1 82.2 97 176 155.8 233.8 1.7 1.6 4.5 4.5 6.2 5.1l3.3.1c2.1-.7 1.8-.5 3.5-2.1 52.3-49.2 140.7-145.8 155.9-215.7 7-39.2 3.1-72.5-20.8-112.5zM186.8 351.9c-28-51.1-65.2-130.7-69.3-189-3.4-47.5 11.4-131.2 69.3-136.7v325.7zM328.7 180c-16.4 56.8-77.3 128-118.9 170.3C237.6 298.4 275 217 277 158.4c1.6-45.9-9.8-105.8-48-131.4 88.8 18.3 115.5 98.1 99.7 153z"],
+ "font-awesome": [448, 512, [], "f2b4", "M400 32H48A48 48 0 0 0 0 80V432a48 48 0 0 0 48 48H400a48 48 0 0 0 48-48V80A48 48 0 0 0 400 32ZM336 312c-31.6 11.2-41.2 16-59.8 16-31.4 0-43.2-16-74.6-16a80 80 0 0 0-25.6 4V284a85.9 85.9 0 0 1 25.6-4c31.2 0 43.2 16 74.6 16 10.2 0 17.8-1.4 27.8-4.6v-96c-10 3.2-17.6 4.6-27.8 4.6-31.4 0-43.2-16-74.6-16-25.4 0-37.4 10.4-57.6 14.4V352a16 16 0 0 1-32 0V160a16 16 0 0 1 32 0v6.4c20.2-4 32.2-14.4 57.6-14.4 31.2 0 43.2 16 74.6 16 18.6 0 28.2-4.8 59.8-16Z"],
+ "font-awesome-alt": [448, 512, [], "f35c", "M400 32H48A48 48 0 0 0 0 80V432a48 48 0 0 0 48 48H400a48 48 0 0 0 48-48V80A48 48 0 0 0 400 32Zm16 400a16 16 0 0 1-16 16H48a16 16 0 0 1-16-16V80A16 16 0 0 1 48 64H400a16 16 0 0 1 16 16ZM201.6 152c-25.4 0-37.4 10.4-57.6 14.4V160a16 16 0 0 0-32 0V352a16 16 0 0 0 32 0V198.4c20.2-4 32.2-14.4 57.6-14.4 31.4 0 43.2 16 74.6 16 10.2 0 17.8-1.4 27.8-4.6v96c-10 3.2-17.6 4.6-27.8 4.6-31.4 0-43.4-16-74.6-16a85.9 85.9 0 0 0-25.6 4v32a80 80 0 0 1 25.6-4c31.4 0 43.2 16 74.6 16 18.6 0 28.2-4.8 59.8-16V152c-31.6 11.2-41.2 16-59.8 16C244.8 168 232.8 152 201.6 152Z"],
+ "font-awesome-flag": [448, 512, [], "f425", "M448 48V384c-63 23-82 32-119 32-63 0-87-32-150-32-20 0-36 4-51 8V328c15-4 31-8 51-8 63 0 87 32 150 32 20 0 35-3 55-9V135c-20 6-35 9-55 9-63 0-87-32-150-32-51 0-75 21-115 29V448a31.6 31.6 0 0 1-32 32A31.6 31.6 0 0 1 0 448V64A31.6 31.6 0 0 1 32 32 31.6 31.6 0 0 1 64 64V77c40-8 64-29 115-29 63 0 87 32 150 32C366 80 385 71 448 48Z"],
+ "font-awesome-logo-full": [3992, 512, ["Font Awesome"], "f4e6", "M1209.7 156.5c-57.8 0-102 43.9-102 99.1 0 56 44.6 99.1 102 99.1 57.4 0 102-43.1 102-99.1C1311.7 200.4 1267.5 156.5 1209.7 156.5Zm0 152.7c-35.1 0-51.8-27.4-51.8-53.2 0-25.8 16.7-53.2 51.8-53.2 35.1 0 51.8 27.8 51.8 53.2C1261.1 281.8 1244.8 309.2 1209.7 309.2Zm962.1-136.1c-4.4-10.9-12.3-16.5-23.5-16.5s-19.1 5.6-23.5 16.5l-59.4 145.8c-7.2 17.7 2.8 27.4 4.4 29a24.6 24.6 0 0 0 17.5 6.8c10.8 0 18.7-6 23.1-18.1l4-10.1h67.7l4 10.1c4.8 12.1 12.3 18.1 23.1 18.1a24.6 24.6 0 0 0 17.5-6.8c10-10.1 6.8-22.6 4.4-29Zm-43 113.6 19.1-56 19.1 56Zm-574.5-130.1c-14.3 0-24.7 10.9-24.7 25.4v76.5l-68.5-85.8c-4.4-5.6-11.6-16.1-25.5-16.1-19.1 0-24.3 17.7-24.3 25.4V329.7c0 14.1 10.4 25.4 24.7 25.4 14.3 0 24.7-10.9 24.7-25.4V252.8l68.9 86.2c4.8 5.6 11.6 16.1 25.5 16.1 19.1 0 23.9-17.3 23.9-25.4V181.9C1579 167.4 1568.6 156.5 1554.3 156.5Zm-554.1 1.6H916.5c-19.9 0-25.1 17.3-25.1 25.4V328.1c0 19.7 16.7 25.4 24.7 25.4 8 0 24.7-5.2 24.7-25.4V285h44.6c12.8 0 22.7-9.3 22.7-22.6 0-17.7-15.5-22.1-22.7-22.1H940.8V203.6h59.4c12.8 0 22.7-9.3 22.7-22.6C1022.9 163 1007.3 158.1 1000.2 158.1Zm815.1 0H1691.7c-7.2 0-22.7 4.4-22.7 22.2 0 13.3 10 22.6 22.7 22.6h37V327.7c0 14.1 10.4 25.4 24.7 25.4 14.3 0 24.7-10.9 24.7-25.4V202.8h37c12.7 0 22.7-9.3 22.7-22.6C1837.9 163 1822.4 158.1 1815.2 158.1Zm1789.5-1.6c-9.6 0-17.5 6-25.1 18.1l-46.6 76.1L3486.4 174.6q-10.8-18.1-25.1-18.1c-19.5 0-24.7 18.1-24.7 25.8V329.7c0 14.1 10.4 25.4 24.7 25.4s24.7-10.9 24.7-25.4V262.8L3510.7 302.7c6.4 10.1 13.9 15.3 22.3 15.3 8.8 0 15.9-5.2 22.3-15.3l24.7-39.9v66.9c0 14.1 10.3 25.4 24.7 25.4 14.3 0 24.7-10.9 24.7-25.4V182.3C3629.4 174.2 3624.6 156.5 3604.7 156.5Zm248.6 149.8h-65.7V272.9h39.4c11.9 0 21.1-8.9 21.1-20.9 0-12.1-9.2-20.9-21.1-20.9h-39.4V204.8h62.1c12.8 0 22.7-9.3 22.7-22.6 0-17.7-15.6-22.2-22.7-22.2h-86.4c-19.9 0-25.1 17.3-25.1 25.4V326.5c0 8.1 5.2 25.4 25.1 25.4h90c12.8 0 22.7-9.3 22.7-22.6C3876 311.2 3860.5 306.3 3853.3 306.3ZM3235 156.5c-57.8 0-102 43.9-102 99.1 0 56 44.6 99.1 102 99.1 57.4 0 102-43.1 102-99.1C3337 200.4 3292.8 156.5 3235 156.5Zm0 152.7c-35.1 0-51.8-27.4-51.8-53.2 0-25.8 16.7-53.2 51.8-53.2 35.1 0 51.8 27.8 51.8 53.2C3286.8 281.8 3270.1 309.2 3235 309.2ZM2550.2 156.5c-11.2 0-19.1 5.6-23.1 16.5l-34.3 94.7-31.5-92.2c-4.4-12.5-12.3-18.9-24.3-18.9-11.9 0-19.9 6.4-24.3 18.9l-31.5 92.2-34.3-95.5q-5.4-15.7-22.7-15.7c-6.8 0-12.3 2.4-17.5 7.3-5.2 5.2-10.8 14.5-4.8 28.6l55.8 145.8c4 11.3 11.6 16.9 23.1 16.9q16.7 0 22.7-16.9l33.5-91.8 33.5 91.8q6 16.9 22.7 16.9c11.2 0 19.1-5.6 23.1-16.9l55.8-145.8c3.6-9.3 4.4-19.3-4.8-28.6A23 23 0 0 0 2550.2 156.5Zm444.2 81-21.9-9.3c-11.9-4.8-16.3-8.5-16.3-15.7q0-12.1 16.7-12.1c12.7 0 19.5 7.7 24.3 10.9 7.2 5.2 18.3 6.8 27.9-2 10.8-10.5 6.8-23.8 1.2-30.6-12.3-14.9-30.3-22.2-53.8-22.2-19.1 0-35.1 5.2-47.4 15.7-12.3 10.5-18.7 24.2-18.7 41.1 0 24.2 15.9 43.5 47.8 57.6l19.5 8.9c15.9 6.8 19.1 9.7 19.1 17.7 0 9.3-6.4 14.1-19.5 14.1-19.1 0-34.7-14.9-36.3-16.1-10.8-7.3-21.5-2-26.3 2.8-6.8 6.4-12.7 20.9 3.2 36.2 6.8 6.4 15.5 11.7 26.7 15.3a94.6 94.6 0 0 0 32.7 5.6c19.9 0 36.7-5.2 49.8-16.1 13.1-10.9 19.5-25.4 19.5-43.5q0-20.5-12-33.8C3022.7 253.2 3010.7 244.3 2994.4 237.5Zm-206.4 68.9h-65.7V272.9h39.4c12 0 21.1-8.9 21.1-20.9 0-12.1-9.2-20.9-21.1-20.9h-39.4V204.8h62.1c12.8 0 22.7-9.3 22.7-22.6 0-17.7-15.5-22.2-22.7-22.2h-86.4c-19.9 0-25.1 17.3-25.1 25.4V326.5c0 8.1 5.2 25.4 25.1 25.4h90c12.7 0 22.7-9.3 22.7-22.6C2810.8 311.2 2795.2 306.3 2788 306.3ZM178.3 49.1c-50.5 0-74.4 20.7-114.6 28.7V65A31.8 31.8 0 1 0 0 65V447a31.8 31.8 0 0 0 63.7 0V141.4c40.2-8 64.1-28.7 114.6-28.7 62.5 0 86 31.8 148.4 31.8 20.3 0 35.4-2.8 55.3-9.2v191c-19.9 6.4-35 9.2-55.3 9.2-62.5 0-86.4-31.8-148.4-31.8-20.3 0-36.2 3.6-50.9 8V375.4a159.1 159.1 0 0 1 50.9-8c62.5 0 86 31.8 148.4 31.8 37 0 56.1-9.6 119-31.8V49.1C382.8 71.4 363.7 80.9 326.7 80.9 264.2 80.9 240.4 49.1 178.3 49.1Z"],
+ "fonticons": [448, 512, [], "f280", "M0 32v448h448V32zm187 140.9c-18.4 0-19 9.9-19 27.4v23.3c0 2.4-3.5 4.4-.6 4.4h67.4l-11.1 37.3H168v112.9c0 5.8-2 6.7 3.2 7.3l43.5 4.1v25.1H84V389l21.3-2c5.2-.6 6.7-2.3 6.7-7.9V267.7c0-2.3-2.9-2.3-5.8-2.3H84V228h28v-21c0-49.6 26.5-70 77.3-70 34.1 0 64.7 8.2 64.7 52.8l-50.7 6.1c.3-18.7-4.4-23-16.3-23zm74.3 241.8v-25.1l20.4-2.6c5.2-.6 7.6-1.7 7.6-7.3V271.8c0-4.1-2.9-6.7-6.7-7.9l-24.2-6.4 6.7-29.5h80.2v151.7c0 5.8-2.6 6.4 2.9 7.3l15.7 2.6v25.1zm80.8-255.5l9 33.2-7.3 7.3-31.2-16.6-31.2 16.6-7.3-7.3 9-33.2-21.8-24.2 3.5-9.6h27.7l15.5-28h9.3l15.5 28h27.7l3.5 9.6z"],
+ "fonticons-fi": [384, 512, [], "f3a2", "M114.4 224h92.4l-15.2 51.2h-76.4V433c0 8-2.8 9.2 4.4 10l59.6 5.6V483H0v-35.2l29.2-2.8c7.2-.8 9.2-3.2 9.2-10.8V278.4c0-3.2-4-3.2-8-3.2H0V224h38.4v-28.8c0-68 36.4-96 106-96 46.8 0 88.8 11.2 88.8 72.4l-69.6 8.4c.4-25.6-6-31.6-22.4-31.6-25.2 0-26 13.6-26 37.6v32c0 3.2-4.8 6-.8 6zM384 483H243.2v-34.4l28-3.6c7.2-.8 10.4-2.4 10.4-10V287c0-5.6-4-9.2-9.2-10.8l-33.2-8.8 9.2-40.4h110v208c0 8-3.6 8.8 4 10l21.6 3.6V483zm-30-347.2l12.4 45.6-10 10-42.8-22.8-42.8 22.8-10-10 12.4-45.6-30-36.4 4.8-10h38L307.2 51H320l21.2 38.4h38l4.8 13.2-30 33.2z"],
+ "fort-awesome": [512, 512, [], "f286", "M489.2 287.9h-27.4c-2.6 0-4.6 2-4.6 4.6v32h-36.6V146.2c0-2.6-2-4.6-4.6-4.6h-27.4c-2.6 0-4.6 2-4.6 4.6v32h-36.6v-32c0-2.6-2-4.6-4.6-4.6h-27.4c-2.6 0-4.6 2-4.6 4.6v32h-36.6v-32c0-6-8-4.6-11.7-4.6v-38c8.3-2 17.1-3.4 25.7-3.4 10.9 0 20.9 4.3 31.4 4.3 4.6 0 27.7-1.1 27.7-8v-60c0-2.6-2-4.6-4.6-4.6-5.1 0-15.1 4.3-24 4.3-9.7 0-20.9-4.3-32.6-4.3-8 0-16 1.1-23.7 2.9v-4.9c5.4-2.6 9.1-8.3 9.1-14.3 0-20.7-31.4-20.8-31.4 0 0 6 3.7 11.7 9.1 14.3v111.7c-3.7 0-11.7-1.4-11.7 4.6v32h-36.6v-32c0-2.6-2-4.6-4.6-4.6h-27.4c-2.6 0-4.6 2-4.6 4.6v32H128v-32c0-2.6-2-4.6-4.6-4.6H96c-2.6 0-4.6 2-4.6 4.6v178.3H54.8v-32c0-2.6-2-4.6-4.6-4.6H22.8c-2.6 0-4.6 2-4.6 4.6V512h182.9v-96c0-72.6 109.7-72.6 109.7 0v96h182.9V292.5c.1-2.6-1.9-4.6-4.5-4.6zm-288.1-4.5c0 2.6-2 4.6-4.6 4.6h-27.4c-2.6 0-4.6-2-4.6-4.6v-64c0-2.6 2-4.6 4.6-4.6h27.4c2.6 0 4.6 2 4.6 4.6v64zm146.4 0c0 2.6-2 4.6-4.6 4.6h-27.4c-2.6 0-4.6-2-4.6-4.6v-64c0-2.6 2-4.6 4.6-4.6h27.4c2.6 0 4.6 2 4.6 4.6v64z"],
+ "fort-awesome-alt": [512, 512, [], "f3a3", "M208 237.4h-22.2c-2.1 0-3.7 1.6-3.7 3.7v51.7c0 2.1 1.6 3.7 3.7 3.7H208c2.1 0 3.7-1.6 3.7-3.7v-51.7c0-2.1-1.6-3.7-3.7-3.7zm118.2 0H304c-2.1 0-3.7 1.6-3.7 3.7v51.7c0 2.1 1.6 3.7 3.7 3.7h22.2c2.1 0 3.7-1.6 3.7-3.7v-51.7c-.1-2.1-1.7-3.7-3.7-3.7zm132-125.1c-2.3-3.2-4.6-6.4-7.1-9.5-9.8-12.5-20.8-24-32.8-34.4-4.5-3.9-9.1-7.6-13.9-11.2-1.6-1.2-3.2-2.3-4.8-3.5C372 34.1 340.3 20 306 13c-16.2-3.3-32.9-5-50-5s-33.9 1.7-50 5c-34.3 7.1-66 21.2-93.3 40.8-1.6 1.1-3.2 2.3-4.8 3.5-4.8 3.6-9.4 7.3-13.9 11.2-3 2.6-5.9 5.3-8.8 8s-5.7 5.5-8.4 8.4c-5.5 5.7-10.7 11.8-15.6 18-2.4 3.1-4.8 6.3-7.1 9.5C25.2 153 8.3 202.5 8.3 256c0 2 .1 4 .1 6 .1.7.1 1.3.1 2 .1 1.3.1 2.7.2 4 0 .8.1 1.5.1 2.3 0 1.3.1 2.5.2 3.7.1.8.1 1.6.2 2.4.1 1.1.2 2.3.3 3.5 0 .8.1 1.6.2 2.4.1 1.2.3 2.4.4 3.6.1.8.2 1.5.3 2.3.1 1.3.3 2.6.5 3.9.1.6.2 1.3.3 1.9l.9 5.7c.1.6.2 1.1.3 1.7.3 1.3.5 2.7.8 4 .2.8.3 1.6.5 2.4.2 1 .5 2.1.7 3.2.2.9.4 1.7.6 2.6.2 1 .4 2 .7 3 .2.9.5 1.8.7 2.7.3 1 .5 1.9.8 2.9.3.9.5 1.8.8 2.7.2.9.5 1.9.8 2.8s.5 1.8.8 2.7c.3 1 .6 1.9.9 2.8.6 1.6 1.1 3.3 1.7 4.9.4 1 .7 1.9 1 2.8.3 1 .7 2 1.1 3 .3.8.6 1.5.9 2.3l1.2 3c.3.7.6 1.5.9 2.2.4 1 .9 2 1.3 3l.9 2.1c.5 1 .9 2 1.4 3 .3.7.6 1.3.9 2 .5 1 1 2.1 1.5 3.1.2.6.5 1.1.8 1.7.6 1.1 1.1 2.2 1.7 3.3.1.2.2.3.3.5 2.2 4.1 4.4 8.2 6.8 12.2.2.4.5.8.7 1.2.7 1.1 1.3 2.2 2 3.3.3.5.6.9.9 1.4.6 1.1 1.3 2.1 2 3.2.3.5.6.9.9 1.4.7 1.1 1.4 2.1 2.1 3.2.2.4.5.8.8 1.2.7 1.1 1.5 2.2 2.3 3.3.2.2.3.5.5.7 37.5 51.7 94.4 88.5 160 99.4.9.1 1.7.3 2.6.4 1 .2 2.1.4 3.1.5s1.9.3 2.8.4c1 .2 2 .3 3 .4.9.1 1.9.2 2.9.3s1.9.2 2.9.3 2.1.2 3.1.3c.9.1 1.8.1 2.7.2 1.1.1 2.3.1 3.4.2.8 0 1.7.1 2.5.1 1.3 0 2.6.1 3.9.1.7.1 1.4.1 2.1.1 2 .1 4 .1 6 .1s4-.1 6-.1c.7 0 1.4-.1 2.1-.1 1.3 0 2.6 0 3.9-.1.8 0 1.7-.1 2.5-.1 1.1-.1 2.3-.1 3.4-.2.9 0 1.8-.1 2.7-.2 1-.1 2.1-.2 3.1-.3s1.9-.2 2.9-.3c.9-.1 1.9-.2 2.9-.3s2-.3 3-.4 1.9-.3 2.8-.4c1-.2 2.1-.3 3.1-.5.9-.1 1.7-.3 2.6-.4 65.6-11 122.5-47.7 160.1-102.4.2-.2.3-.5.5-.7.8-1.1 1.5-2.2 2.3-3.3.2-.4.5-.8.8-1.2.7-1.1 1.4-2.1 2.1-3.2.3-.5.6-.9.9-1.4.6-1.1 1.3-2.1 2-3.2.3-.5.6-.9.9-1.4.7-1.1 1.3-2.2 2-3.3.2-.4.5-.8.7-1.2 2.4-4 4.6-8.1 6.8-12.2.1-.2.2-.3.3-.5.6-1.1 1.1-2.2 1.7-3.3.2-.6.5-1.1.8-1.7.5-1 1-2.1 1.5-3.1.3-.7.6-1.3.9-2 .5-1 1-2 1.4-3l.9-2.1c.5-1 .9-2 1.3-3 .3-.7.6-1.5.9-2.2l1.2-3c.3-.8.6-1.5.9-2.3.4-1 .7-2 1.1-3s.7-1.9 1-2.8c.6-1.6 1.2-3.3 1.7-4.9.3-1 .6-1.9.9-2.8s.5-1.8.8-2.7c.2-.9.5-1.9.8-2.8s.6-1.8.8-2.7c.3-1 .5-1.9.8-2.9.2-.9.5-1.8.7-2.7.2-1 .5-2 .7-3 .2-.9.4-1.7.6-2.6.2-1 .5-2.1.7-3.2.2-.8.3-1.6.5-2.4.3-1.3.6-2.7.8-4 .1-.6.2-1.1.3-1.7l.9-5.7c.1-.6.2-1.3.3-1.9.1-1.3.3-2.6.5-3.9.1-.8.2-1.5.3-2.3.1-1.2.3-2.4.4-3.6 0-.8.1-1.6.2-2.4.1-1.1.2-2.3.3-3.5.1-.8.1-1.6.2-2.4.1 1.7.1.5.2-.7 0-.8.1-1.5.1-2.3.1-1.3.2-2.7.2-4 .1-.7.1-1.3.1-2 .1-2 .1-4 .1-6 0-53.5-16.9-103-45.8-143.7zM448 371.5c-9.4 15.5-20.6 29.9-33.6 42.9-20.6 20.6-44.5 36.7-71.2 48-13.9 5.8-28.2 10.3-42.9 13.2v-75.8c0-58.6-88.6-58.6-88.6 0v75.8c-14.7-2.9-29-7.3-42.9-13.2-26.7-11.3-50.6-27.4-71.2-48-13-13-24.2-27.4-33.6-42.9v-71.3c0-2.1 1.6-3.7 3.7-3.7h22.1c2.1 0 3.7 1.6 3.7 3.7V326h29.6V182c0-2.1 1.6-3.7 3.7-3.7h22.1c2.1 0 3.7 1.6 3.7 3.7v25.9h29.5V182c0-2.1 1.6-3.7 3.7-3.7H208c2.1 0 3.7 1.6 3.7 3.7v25.9h29.5V182c0-4.8 6.5-3.7 9.5-3.7V88.1c-4.4-2-7.4-6.7-7.4-11.5 0-16.8 25.4-16.8 25.4 0 0 4.8-3 9.4-7.4 11.5V92c6.3-1.4 12.7-2.3 19.2-2.3 9.4 0 18.4 3.5 26.3 3.5 7.2 0 15.2-3.5 19.4-3.5 2.1 0 3.7 1.6 3.7 3.7v48.4c0 5.6-18.7 6.5-22.4 6.5-8.6 0-16.6-3.5-25.4-3.5-7 0-14.1 1.2-20.8 2.8v30.7c3 0 9.5-1.1 9.5 3.7v25.9h29.5V182c0-2.1 1.6-3.7 3.7-3.7h22.2c2.1 0 3.7 1.6 3.7 3.7v25.9h29.5V182c0-2.1 1.6-3.7 3.7-3.7h22.1c2.1 0 3.7 1.6 3.7 3.7v144h29.5v-25.8c0-2.1 1.6-3.7 3.7-3.7h22.2c2.1 0 3.7 1.6 3.7 3.7z"],
+ "forumbee": [448, 512, [], "f211", "M5.8 309.7C2 292.7 0 275.5 0 258.3 0 135 99.8 35 223.1 35c16.6 0 33.3 2 49.3 5.5C149 87.5 51.9 186 5.8 309.7zm392.9-189.2C385 103 369 87.8 350.9 75.2c-149.6 44.3-266.3 162.1-309.7 312 12.5 18.1 28 35.6 45.2 49 43.1-151.3 161.2-271.7 312.3-315.7zm15.8 252.7c15.2-25.1 25.4-53.7 29.5-82.8-79.4 42.9-145 110.6-187.6 190.3 30-4.4 58.9-15.3 84.6-31.3 35 13.1 70.9 24.3 107 33.6-9.3-36.5-20.4-74.5-33.5-109.8zm29.7-145.5c-2.6-19.5-7.9-38.7-15.8-56.8C290.5 216.7 182 327.5 137.1 466c18.1 7.6 37 12.5 56.6 15.2C240 367.1 330.5 274.4 444.2 227.7z"],
+ "foursquare": [368, 512, [], "f180", "M323.1 3H49.9C12.4 3 0 31.3 0 49.1v433.8c0 20.3 12.1 27.7 18.2 30.1 6.2 2.5 22.8 4.6 32.9-7.1C180 356.5 182.2 354 182.2 354c3.1-3.4 3.4-3.1 6.8-3.1h83.4c35.1 0 40.6-25.2 44.3-39.7l48.6-243C373.8 25.8 363.1 3 323.1 3zm-16.3 73.8l-11.4 59.7c-1.2 6.5-9.5 13.2-16.9 13.2H172.1c-12 0-20.6 8.3-20.6 20.3v13c0 12 8.6 20.6 20.6 20.6h90.4c8.3 0 16.6 9.2 14.8 18.2-1.8 8.9-10.5 53.8-11.4 58.8-.9 4.9-6.8 13.5-16.9 13.5h-73.5c-13.5 0-17.2 1.8-26.5 12.6 0 0-8.9 11.4-89.5 108.3-.9.9-1.8.6-1.8-.3V75.9c0-7.7 6.8-16.6 16.6-16.6h219c8.2 0 15.6 7.7 13.5 17.5z"],
+ "free-code-camp": [576, 512, [], "f2c5", "M97.22,96.21c10.36-10.65,16-17.12,16-21.9,0-2.76-1.92-5.51-3.83-7.42A14.81,14.81,0,0,0,101,64.05c-8.48,0-20.92,8.79-35.84,25.69C23.68,137,2.51,182.81,3.37,250.34s17.47,117,54.06,161.87C76.22,435.86,90.62,448,100.9,448a13.55,13.55,0,0,0,8.37-3.84c1.91-2.76,3.81-5.63,3.81-8.38,0-5.63-3.86-12.2-13.2-20.55-44.45-42.33-67.32-97-67.48-165C32.25,188.8,54,137.83,97.22,96.21ZM239.47,420.07c.58.37.91.55.91.55Zm93.79.55.17-.13C333.24,420.62,333.17,420.67,333.26,420.62Zm3.13-158.18c-16.24-4.15,50.41-82.89-68.05-177.17,0,0,15.54,49.38-62.83,159.57-74.27,104.35,23.46,168.73,34,175.23-6.73-4.35-47.4-35.7,9.55-128.64,11-18.3,25.53-34.87,43.5-72.16,0,0,15.91,22.45,7.6,71.13C287.7,364,354,342.91,355,343.94c22.75,26.78-17.72,73.51-21.58,76.55,5.49-3.65,117.71-78,33-188.1C360.43,238.4,352.62,266.59,336.39,262.44ZM510.88,89.69C496,72.79,483.52,64,475,64a14.81,14.81,0,0,0-8.39,2.84c-1.91,1.91-3.83,4.66-3.83,7.42,0,4.78,5.6,11.26,16,21.9,43.23,41.61,65,92.59,64.82,154.06-.16,68-23,122.63-67.48,165-9.34,8.35-13.18,14.92-13.2,20.55,0,2.75,1.9,5.62,3.81,8.38A13.61,13.61,0,0,0,475.1,448c10.28,0,24.68-12.13,43.47-35.79,36.59-44.85,53.14-94.38,54.06-161.87S552.32,137,510.88,89.69Z"],
+ "freebsd": [448, 512, [], "f3a4", "M303.7 96.2c11.1-11.1 115.5-77 139.2-53.2 23.7 23.7-42.1 128.1-53.2 139.2-11.1 11.1-39.4.9-63.1-22.9-23.8-23.7-34.1-52-22.9-63.1zM109.9 68.1C73.6 47.5 22 24.6 5.6 41.1c-16.6 16.6 7.1 69.4 27.9 105.7 18.5-32.2 44.8-59.3 76.4-78.7zM406.7 174c3.3 11.3 2.7 20.7-2.7 26.1-20.3 20.3-87.5-27-109.3-70.1-18-32.3-11.1-53.4 14.9-48.7 5.7-3.6 12.3-7.6 19.6-11.6-29.8-15.5-63.6-24.3-99.5-24.3-119.1 0-215.6 96.5-215.6 215.6 0 119 96.5 215.6 215.6 215.6S445.3 380.1 445.3 261c0-38.4-10.1-74.5-27.7-105.8-3.9 7-7.6 13.3-10.9 18.8z"],
+ "fulcrum": [320, 512, [], "f50b", "M95.75 164.14l-35.38 43.55L25 164.14l35.38-43.55zM144.23 0l-20.54 198.18L72.72 256l51 57.82L144.23 512V300.89L103.15 256l41.08-44.89zm79.67 164.14l35.38 43.55 35.38-43.55-35.38-43.55zm-48.48 47L216.5 256l-41.08 44.89V512L196 313.82 247 256l-51-57.82L175.42 0z"],
+ "galactic-republic": [496, 512, [], "f50c", "M248 504C111.25 504 0 392.75 0 256S111.25 8 248 8s248 111.25 248 248-111.25 248-248 248zm0-479.47C120.37 24.53 16.53 128.37 16.53 256S120.37 487.47 248 487.47 479.47 383.63 479.47 256 375.63 24.53 248 24.53zm27.62 21.81v24.62a185.933 185.933 0 0 1 83.57 34.54l17.39-17.36c-28.75-22.06-63.3-36.89-100.96-41.8zm-55.37.07c-37.64 4.94-72.16 19.8-100.88 41.85l17.28 17.36h.08c24.07-17.84 52.55-30.06 83.52-34.67V46.41zm12.25 50.17v82.87c-10.04 2.03-19.42 5.94-27.67 11.42l-58.62-58.59-21.93 21.93 58.67 58.67c-5.47 8.23-9.45 17.59-11.47 27.62h-82.9v31h82.9c2.02 10.02 6.01 19.31 11.47 27.54l-58.67 58.69 21.93 21.93 58.62-58.62a77.873 77.873 0 0 0 27.67 11.47v82.9h31v-82.9c10.05-2.03 19.37-6.06 27.62-11.55l58.67 58.69 21.93-21.93-58.67-58.69c5.46-8.23 9.47-17.52 11.5-27.54h82.87v-31h-82.87c-2.02-10.02-6.03-19.38-11.5-27.62l58.67-58.67-21.93-21.93-58.67 58.67c-8.25-5.49-17.57-9.47-27.62-11.5V96.58h-31zm183.24 30.72l-17.36 17.36a186.337 186.337 0 0 1 34.67 83.67h24.62c-4.95-37.69-19.83-72.29-41.93-101.03zm-335.55.13c-22.06 28.72-36.91 63.26-41.85 100.91h24.65c4.6-30.96 16.76-59.45 34.59-83.52l-17.39-17.39zM38.34 283.67c4.92 37.64 19.75 72.18 41.8 100.9l17.36-17.39c-17.81-24.07-29.92-52.57-34.51-83.52H38.34zm394.7 0c-4.61 30.99-16.8 59.5-34.67 83.6l17.36 17.36c22.08-28.74 36.98-63.29 41.93-100.96h-24.62zM136.66 406.38l-17.36 17.36c28.73 22.09 63.3 36.98 100.96 41.93v-24.64c-30.99-4.63-59.53-16.79-83.6-34.65zm222.53.05c-24.09 17.84-52.58 30.08-83.57 34.67v24.57c37.67-4.92 72.21-19.79 100.96-41.85l-17.31-17.39h-.08z"],
+ "galactic-senate": [512, 512, [], "f50d", "M249.86 33.48v26.07C236.28 80.17 226 168.14 225.39 274.9c11.74-15.62 19.13-33.33 19.13-48.24v-16.88c-.03-5.32.75-10.53 2.19-15.65.65-2.14 1.39-4.08 2.62-5.82 1.23-1.75 3.43-3.79 6.68-3.79 3.24 0 5.45 2.05 6.68 3.79 1.23 1.75 1.97 3.68 2.62 5.82 1.44 5.12 2.22 10.33 2.19 15.65v16.88c0 14.91 7.39 32.62 19.13 48.24-.63-106.76-10.91-194.73-24.49-215.35V33.48h-12.28zm-26.34 147.77c-9.52 2.15-18.7 5.19-27.46 9.08 8.9 16.12 9.76 32.64 1.71 37.29-8 4.62-21.85-4.23-31.36-19.82-11.58 8.79-21.88 19.32-30.56 31.09 14.73 9.62 22.89 22.92 18.32 30.66-4.54 7.7-20.03 7.14-35.47-.96-5.78 13.25-9.75 27.51-11.65 42.42 9.68.18 18.67 2.38 26.18 6.04 17.78-.3 32.77-1.96 40.49-4.22 5.55-26.35 23.02-48.23 46.32-59.51.73-25.55 1.88-49.67 3.48-72.07zm64.96 0c1.59 22.4 2.75 46.52 3.47 72.07 23.29 11.28 40.77 33.16 46.32 59.51 7.72 2.26 22.71 3.92 40.49 4.22 7.51-3.66 16.5-5.85 26.18-6.04-1.9-14.91-5.86-29.17-11.65-42.42-15.44 8.1-30.93 8.66-35.47.96-4.57-7.74 3.6-21.05 18.32-30.66-8.68-11.77-18.98-22.3-30.56-31.09-9.51 15.59-23.36 24.44-31.36 19.82-8.05-4.65-7.19-21.16 1.71-37.29a147.49 147.49 0 0 0-27.45-9.08zm-32.48 8.6c-3.23 0-5.86 8.81-6.09 19.93h-.05v16.88c0 41.42-49.01 95.04-93.49 95.04-52 0-122.75-1.45-156.37 29.17v2.51c9.42 17.12 20.58 33.17 33.18 47.97C45.7 380.26 84.77 360.4 141.2 360c45.68 1.02 79.03 20.33 90.76 40.87.01.01-.01.04 0 .05 7.67 2.14 15.85 3.23 24.04 3.21 8.19.02 16.37-1.07 24.04-3.21.01-.01-.01-.04 0-.05 11.74-20.54 45.08-39.85 90.76-40.87 56.43.39 95.49 20.26 108.02 41.35 12.6-14.8 23.76-30.86 33.18-47.97v-2.51c-33.61-30.62-104.37-29.17-156.37-29.17-44.48 0-93.49-53.62-93.49-95.04v-16.88h-.05c-.23-11.12-2.86-19.93-6.09-19.93zm0 96.59c22.42 0 40.6 18.18 40.6 40.6s-18.18 40.65-40.6 40.65-40.6-18.23-40.6-40.65c0-22.42 18.18-40.6 40.6-40.6zm0 7.64c-18.19 0-32.96 14.77-32.96 32.96S237.81 360 256 360s32.96-14.77 32.96-32.96-14.77-32.96-32.96-32.96zm0 6.14c14.81 0 26.82 12.01 26.82 26.82s-12.01 26.82-26.82 26.82-26.82-12.01-26.82-26.82 12.01-26.82 26.82-26.82zm-114.8 66.67c-10.19.07-21.6.36-30.5 1.66.43 4.42 1.51 18.63 7.11 29.76 9.11-2.56 18.36-3.9 27.62-3.9 41.28.94 71.48 34.35 78.26 74.47l.11 4.7c10.4 1.91 21.19 2.94 32.21 2.94 11.03 0 21.81-1.02 32.21-2.94l.11-4.7c6.78-40.12 36.98-73.53 78.26-74.47 9.26 0 18.51 1.34 27.62 3.9 5.6-11.13 6.68-25.34 7.11-29.76-8.9-1.3-20.32-1.58-30.5-1.66-18.76.42-35.19 4.17-48.61 9.67-12.54 16.03-29.16 30.03-49.58 33.07-.09.02-.17.04-.27.05-.05.01-.11.04-.16.05-5.24 1.07-10.63 1.6-16.19 1.6-5.55 0-10.95-.53-16.19-1.6-.05-.01-.11-.04-.16-.05-.1-.02-.17-.04-.27-.05-20.42-3.03-37.03-17.04-49.58-33.07-13.42-5.49-29.86-9.25-48.61-9.67z"],
+ "get-pocket": [448, 512, [], "f265", "M407.6 64h-367C18.5 64 0 82.5 0 104.6v135.2C0 364.5 99.7 464 224.2 464c124 0 223.8-99.5 223.8-224.2V104.6c0-22.4-17.7-40.6-40.4-40.6zm-162 268.5c-12.4 11.8-31.4 11.1-42.4 0C89.5 223.6 88.3 227.4 88.3 209.3c0-16.9 13.8-30.7 30.7-30.7 17 0 16.1 3.8 105.2 89.3 90.6-86.9 88.6-89.3 105.5-89.3 16.9 0 30.7 13.8 30.7 30.7 0 17.8-2.9 15.7-114.8 123.2z"],
+ "gg": [512, 512, [], "f260", "M179.2 230.4l102.4 102.4-102.4 102.4L0 256 179.2 76.8l44.8 44.8-25.6 25.6-19.2-19.2-128 128 128 128 51.5-51.5-77.1-76.5 25.6-25.6zM332.8 76.8L230.4 179.2l102.4 102.4 25.6-25.6-77.1-76.5 51.5-51.5 128 128-128 128-19.2-19.2-25.6 25.6 44.8 44.8L512 256 332.8 76.8z"],
+ "gg-circle": [512, 512, [], "f261", "M257 8C120 8 9 119 9 256s111 248 248 248 248-111 248-248S394 8 257 8zm-49.5 374.8L81.8 257.1l125.7-125.7 35.2 35.4-24.2 24.2-11.1-11.1-77.2 77.2 77.2 77.2 26.6-26.6-53.1-52.9 24.4-24.4 77.2 77.2-75 75.2zm99-2.2l-35.2-35.2 24.1-24.4 11.1 11.1 77.2-77.2-77.2-77.2-26.5 26.5 53.1 52.9-24.4 24.4-77.2-77.2 75-75L432.2 255 306.5 380.6z"],
+ "git": [512, 512, [], "f1d3", "M216.29 158.39H137C97 147.9 6.51 150.63 6.51 233.18c0 30.09 15 51.23 35 61-25.1 23-37 33.85-37 49.21 0 11 4.47 21.14 17.89 26.81C8.13 383.61 0 393.35 0 411.65c0 32.11 28.05 50.82 101.63 50.82 70.75 0 111.79-26.42 111.79-73.18 0-58.66-45.16-56.5-151.63-63l13.43-21.55c27.27 7.58 118.7 10 118.7-67.89 0-18.7-7.73-31.71-15-41.07l37.41-2.84zm-63.42 241.9c0 32.06-104.89 32.1-104.89 2.43 0-8.14 5.27-15 10.57-21.54 77.71 5.3 94.32 3.37 94.32 19.11zm-50.81-134.58c-52.8 0-50.46-71.16 1.2-71.16 49.54 0 50.82 71.16-1.2 71.16zm133.3 100.51v-32.1c26.75-3.66 27.24-2 27.24-11V203.61c0-8.5-2.05-7.38-27.24-16.26l4.47-32.92H324v168.71c0 6.51.4 7.32 6.51 8.14l20.73 2.84v32.1zm52.45-244.31c-23.17 0-36.59-13.43-36.59-36.61s13.42-35.77 36.59-35.77c23.58 0 37 12.62 37 35.77s-13.42 36.61-37 36.61zM512 350.46c-17.49 8.53-43.1 16.26-66.28 16.26-48.38 0-66.67-19.5-66.67-65.46V194.75c0-5.42 1.05-4.06-31.71-4.06V154.5c35.78-4.07 50-22 54.47-66.27h38.63c0 65.83-1.34 61.81 3.26 61.81H501v40.65h-60.56v97.15c0 6.92-4.92 51.41 60.57 26.84z"],
+ "git-alt": [448, 512, [], "f841", "M439.55 236.05L244 40.45a28.87 28.87 0 0 0-40.81 0l-40.66 40.63 51.52 51.52c27.06-9.14 52.68 16.77 43.39 43.68l49.66 49.66c34.23-11.8 61.18 31 35.47 56.69-26.49 26.49-70.21-2.87-56-37.34L240.22 199v121.85c25.3 12.54 22.26 41.85 9.08 55a34.34 34.34 0 0 1-48.55 0c-17.57-17.6-11.07-46.91 11.25-56v-123c-20.8-8.51-24.6-30.74-18.64-45L142.57 101 8.45 235.14a28.86 28.86 0 0 0 0 40.81l195.61 195.6a28.86 28.86 0 0 0 40.8 0l194.69-194.69a28.86 28.86 0 0 0 0-40.81z"],
+ "git-square": [448, 512, [], "f1d2", "M100.59 334.24c48.57 3.31 58.95 2.11 58.95 11.94 0 20-65.55 20.06-65.55 1.52.01-5.09 3.29-9.4 6.6-13.46zm27.95-116.64c-32.29 0-33.75 44.47-.75 44.47 32.51 0 31.71-44.47.75-44.47zM448 80v352a48 48 0 0 1-48 48H48a48 48 0 0 1-48-48V80a48 48 0 0 1 48-48h352a48 48 0 0 1 48 48zm-227 69.31c0 14.49 8.38 22.88 22.86 22.88 14.74 0 23.13-8.39 23.13-22.88S258.62 127 243.88 127c-14.48 0-22.88 7.84-22.88 22.31zM199.18 195h-49.55c-25-6.55-81.56-4.85-81.56 46.75 0 18.8 9.4 32 21.85 38.11C74.23 294.23 66.8 301 66.8 310.6c0 6.87 2.79 13.22 11.18 16.76-8.9 8.4-14 14.48-14 25.92C64 373.35 81.53 385 127.52 385c44.22 0 69.87-16.51 69.87-45.73 0-36.67-28.23-35.32-94.77-39.38l8.38-13.43c17 4.74 74.19 6.23 74.19-42.43 0-11.69-4.83-19.82-9.4-25.67l23.38-1.78zm84.34 109.84l-13-1.78c-3.82-.51-4.07-1-4.07-5.09V192.52h-52.6l-2.79 20.57c15.75 5.55 17 4.86 17 10.17V298c0 5.62-.31 4.58-17 6.87v20.06h72.42zM384 315l-6.87-22.37c-40.93 15.37-37.85-12.41-37.85-16.73v-60.72h37.85v-25.41h-35.82c-2.87 0-2 2.52-2-38.63h-24.18c-2.79 27.7-11.68 38.88-34 41.42v22.62c20.47 0 19.82-.85 19.82 2.54v66.57c0 28.72 11.43 40.91 41.67 40.91 14.45 0 30.45-4.83 41.38-10.2z"],
+ "github": [496, 512, [], "f09b", "M165.9 397.4c0 2-2.3 3.6-5.2 3.6-3.3.3-5.6-1.3-5.6-3.6 0-2 2.3-3.6 5.2-3.6 3-.3 5.6 1.3 5.6 3.6zm-31.1-4.5c-.7 2 1.3 4.3 4.3 4.9 2.6 1 5.6 0 6.2-2s-1.3-4.3-4.3-5.2c-2.6-.7-5.5.3-6.2 2.3zm44.2-1.7c-2.9.7-4.9 2.6-4.6 4.9.3 2 2.9 3.3 5.9 2.6 2.9-.7 4.9-2.6 4.6-4.6-.3-1.9-3-3.2-5.9-2.9zM244.8 8C106.1 8 0 113.3 0 252c0 110.9 69.8 205.8 169.5 239.2 12.8 2.3 17.3-5.6 17.3-12.1 0-6.2-.3-40.4-.3-61.4 0 0-70 15-84.7-29.8 0 0-11.4-29.1-27.8-36.6 0 0-22.9-15.7 1.6-15.4 0 0 24.9 2 38.6 25.8 21.9 38.6 58.6 27.5 72.9 20.9 2.3-16 8.8-27.1 16-33.7-55.9-6.2-112.3-14.3-112.3-110.5 0-27.5 7.6-41.3 23.6-58.9-2.6-6.5-11.1-33.3 2.6-67.9 20.9-6.5 69 27 69 27 20-5.6 41.5-8.5 62.8-8.5s42.8 2.9 62.8 8.5c0 0 48.1-33.6 69-27 13.7 34.7 5.2 61.4 2.6 67.9 16 17.7 25.8 31.5 25.8 58.9 0 96.5-58.9 104.2-114.8 110.5 9.2 7.9 17 22.9 17 46.4 0 33.7-.3 75.4-.3 83.6 0 6.5 4.6 14.4 17.3 12.1C428.2 457.8 496 362.9 496 252 496 113.3 383.5 8 244.8 8zM97.2 352.9c-1.3 1-1 3.3.7 5.2 1.6 1.6 3.9 2.3 5.2 1 1.3-1 1-3.3-.7-5.2-1.6-1.6-3.9-2.3-5.2-1zm-10.8-8.1c-.7 1.3.3 2.9 2.3 3.9 1.6 1 3.6.7 4.3-.7.7-1.3-.3-2.9-2.3-3.9-2-.6-3.6-.3-4.3.7zm32.4 35.6c-1.6 1.3-1 4.3 1.3 6.2 2.3 2.3 5.2 2.6 6.5 1 1.3-1.3.7-4.3-1.3-6.2-2.2-2.3-5.2-2.6-6.5-1zm-11.4-14.7c-1.6 1-1.6 3.6 0 5.9 1.6 2.3 4.3 3.3 5.6 2.3 1.6-1.3 1.6-3.9 0-6.2-1.4-2.3-4-3.3-5.6-2z"],
+ "github-alt": [480, 512, [], "f113", "M186.1 328.7c0 20.9-10.9 55.1-36.7 55.1s-36.7-34.2-36.7-55.1 10.9-55.1 36.7-55.1 36.7 34.2 36.7 55.1zM480 278.2c0 31.9-3.2 65.7-17.5 95-37.9 76.6-142.1 74.8-216.7 74.8-75.8 0-186.2 2.7-225.6-74.8-14.6-29-20.2-63.1-20.2-95 0-41.9 13.9-81.5 41.5-113.6-5.2-15.8-7.7-32.4-7.7-48.8 0-21.5 4.9-32.3 14.6-51.8 45.3 0 74.3 9 108.8 36 29-6.9 58.8-10 88.7-10 27 0 54.2 2.9 80.4 9.2 34-26.7 63-35.2 107.8-35.2 9.8 19.5 14.6 30.3 14.6 51.8 0 16.4-2.6 32.7-7.7 48.2 27.5 32.4 39 72.3 39 114.2zm-64.3 50.5c0-43.9-26.7-82.6-73.5-82.6-18.9 0-37 3.4-56 6-14.9 2.3-29.8 3.2-45.1 3.2-15.2 0-30.1-.9-45.1-3.2-18.7-2.6-37-6-56-6-46.8 0-73.5 38.7-73.5 82.6 0 87.8 80.4 101.3 150.4 101.3h48.2c70.3 0 150.6-13.4 150.6-101.3zm-82.6-55.1c-25.8 0-36.7 34.2-36.7 55.1s10.9 55.1 36.7 55.1 36.7-34.2 36.7-55.1-10.9-55.1-36.7-55.1z"],
+ "github-square": [448, 512, [], "f092", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM277.3 415.7c-8.4 1.5-11.5-3.7-11.5-8 0-5.4.2-33 .2-55.3 0-15.6-5.2-25.5-11.3-30.7 37-4.1 76-9.2 76-73.1 0-18.2-6.5-27.3-17.1-39 1.7-4.3 7.4-22-1.7-45-13.9-4.3-45.7 17.9-45.7 17.9-13.2-3.7-27.5-5.6-41.6-5.6-14.1 0-28.4 1.9-41.6 5.6 0 0-31.8-22.2-45.7-17.9-9.1 22.9-3.5 40.6-1.7 45-10.6 11.7-15.6 20.8-15.6 39 0 63.6 37.3 69 74.3 73.1-4.8 4.3-9.1 11.7-10.6 22.3-9.5 4.3-33.8 11.7-48.3-13.9-9.1-15.8-25.5-17.1-25.5-17.1-16.2-.2-1.1 10.2-1.1 10.2 10.8 5 18.4 24.2 18.4 24.2 9.7 29.7 56.1 19.7 56.1 19.7 0 13.9.2 36.5.2 40.6 0 4.3-3 9.5-11.5 8-66-22.1-112.2-84.9-112.2-158.3 0-91.8 70.2-161.5 162-161.5S388 165.6 388 257.4c.1 73.4-44.7 136.3-110.7 158.3zm-98.1-61.1c-1.9.4-3.7-.4-3.9-1.7-.2-1.5 1.1-2.8 3-3.2 1.9-.2 3.7.6 3.9 1.9.3 1.3-1 2.6-3 3zm-9.5-.9c0 1.3-1.5 2.4-3.5 2.4-2.2.2-3.7-.9-3.7-2.4 0-1.3 1.5-2.4 3.5-2.4 1.9-.2 3.7.9 3.7 2.4zm-13.7-1.1c-.4 1.3-2.4 1.9-4.1 1.3-1.9-.4-3.2-1.9-2.8-3.2.4-1.3 2.4-1.9 4.1-1.5 2 .6 3.3 2.1 2.8 3.4zm-12.3-5.4c-.9 1.1-2.8.9-4.3-.6-1.5-1.3-1.9-3.2-.9-4.1.9-1.1 2.8-.9 4.3.6 1.3 1.3 1.8 3.3.9 4.1zm-9.1-9.1c-.9.6-2.6 0-3.7-1.5s-1.1-3.2 0-3.9c1.1-.9 2.8-.2 3.7 1.3 1.1 1.5 1.1 3.3 0 4.1zm-6.5-9.7c-.9.9-2.4.4-3.5-.6-1.1-1.3-1.3-2.8-.4-3.5.9-.9 2.4-.4 3.5.6 1.1 1.3 1.3 2.8.4 3.5zm-6.7-7.4c-.4.9-1.7 1.1-2.8.4-1.3-.6-1.9-1.7-1.5-2.6.4-.6 1.5-.9 2.8-.4 1.3.7 1.9 1.8 1.5 2.6z"],
+ "gitkraken": [592, 512, [], "f3a6", "M565.7 118.1c-2.3-6.1-9.3-9.2-15.3-6.6-5.7 2.4-8.5 8.9-6.3 14.6 10.9 29 16.9 60.5 16.9 93.3 0 134.6-100.3 245.7-230.2 262.7V358.4c7.9-1.5 15.5-3.6 23-6.2v104c106.7-25.9 185.9-122.1 185.9-236.8 0-91.8-50.8-171.8-125.8-213.3-5.7-3.2-13-.9-15.9 5-2.7 5.5-.6 12.2 4.7 15.1 67.9 37.6 113.9 110 113.9 193.2 0 93.3-57.9 173.1-139.8 205.4v-92.2c14.2-4.5 24.9-17.7 24.9-33.5 0-13.1-6.8-24.4-17.3-30.5 8.3-79.5 44.5-58.6 44.5-83.9V170c0-38-87.9-161.8-129-164.7-2.5-.2-5-.2-7.6 0C251.1 8.3 163.2 132 163.2 170v14.8c0 25.3 36.3 4.3 44.5 83.9-10.6 6.1-17.3 17.4-17.3 30.5 0 15.8 10.6 29 24.8 33.5v92.2c-81.9-32.2-139.8-112-139.8-205.4 0-83.1 46-155.5 113.9-193.2 5.4-3 7.4-9.6 4.7-15.1-2.9-5.9-10.1-8.2-15.9-5-75 41.5-125.8 121.5-125.8 213.3 0 114.7 79.2 210.8 185.9 236.8v-104c7.6 2.5 15.1 4.6 23 6.2v123.7C131.4 465.2 31 354.1 31 219.5c0-32.8 6-64.3 16.9-93.3 2.2-5.8-.6-12.2-6.3-14.6-6-2.6-13 .4-15.3 6.6C14.5 149.7 8 183.8 8 219.5c0 155.1 122.6 281.6 276.3 287.8V361.4c6.8.4 15 .5 23.4 0v145.8C461.4 501.1 584 374.6 584 219.5c0-35.7-6.5-69.8-18.3-101.4zM365.9 275.5c13 0 23.7 10.5 23.7 23.7 0 13.1-10.6 23.7-23.7 23.7-13 0-23.7-10.5-23.7-23.7 0-13.1 10.6-23.7 23.7-23.7zm-139.8 47.3c-13.2 0-23.7-10.7-23.7-23.7s10.5-23.7 23.7-23.7c13.1 0 23.7 10.6 23.7 23.7 0 13-10.5 23.7-23.7 23.7z"],
+ "gitlab": [512, 512, [], "f296", "M105.2 24.9c-3.1-8.9-15.7-8.9-18.9 0L29.8 199.7h132c-.1 0-56.6-174.8-56.6-174.8zM.9 287.7c-2.6 8 .3 16.9 7.1 22l247.9 184-226.2-294zm160.8-88l94.3 294 94.3-294zm349.4 88l-28.8-88-226.3 294 247.9-184c6.9-5.1 9.7-14 7.2-22zM425.7 24.9c-3.1-8.9-15.7-8.9-18.9 0l-56.6 174.8h132z"],
+ "gitter": [384, 512, [], "f426", "M66.4 322.5H16V0h50.4v322.5zM166.9 76.1h-50.4V512h50.4V76.1zm100.6 0h-50.4V512h50.4V76.1zM368 76h-50.4v247H368V76z"],
+ "glide": [448, 512, [], "f2a5", "M252.8 148.6c0 8.8-1.6 17.7-3.4 26.4-5.8 27.8-11.6 55.8-17.3 83.6-1.4 6.3-8.3 4.9-13.7 4.9-23.8 0-30.5-26-30.5-45.5 0-29.3 11.2-68.1 38.5-83.1 4.3-2.5 9.2-4.2 14.1-4.2 11.4 0 12.3 8.3 12.3 17.9zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-64 187c0-5.1-20.8-37.7-25.5-39.5-2.2-.9-7.2-2.3-9.6-2.3-23.1 0-38.7 10.5-58.2 21.5l-.5-.5c4.3-29.4 14.6-57.2 14.6-87.4 0-44.6-23.8-62.7-67.5-62.7-71.7 0-108 70.8-108 123.5 0 54.7 32 85 86.3 85 7.5 0 6.9-.6 6.9 2.3-10.5 80.3-56.5 82.9-56.5 58.9 0-24.4 28-36.5 28.3-38-.2-7.6-29.3-17.2-36.7-17.2-21.1 0-32.7 33-32.7 50.6 0 32.3 20.4 54.7 53.3 54.7 48.2 0 83.4-49.7 94.3-91.7 9.4-37.7 7-39.4 12.3-42.1 20-10.1 35.8-16.8 58.4-16.8 11.1 0 19 2.3 36.7 5.2 1.8.1 4.1-1.7 4.1-3.5z"],
+ "glide-g": [448, 512, [], "f2a6", "M407.1 211.2c-3.5-1.4-11.6-3.8-15.4-3.8-37.1 0-62.2 16.8-93.5 34.5l-.9-.9c7-47.3 23.5-91.9 23.5-140.4C320.8 29.1 282.6 0 212.4 0 97.3 0 39 113.7 39 198.4 39 286.3 90.3 335 177.6 335c12 0 11-1 11 3.8-16.9 128.9-90.8 133.1-90.8 94.6 0-39.2 45-58.6 45.5-61-.3-12.2-47-27.6-58.9-27.6-33.9.1-52.4 51.2-52.4 79.3C32 476 64.8 512 117.5 512c77.4 0 134-77.8 151.4-145.4 15.1-60.5 11.2-63.3 19.7-67.6 32.2-16.2 57.5-27 93.8-27 17.8 0 30.5 3.7 58.9 8.4 2.9 0 6.7-2.9 6.7-5.8 0-8-33.4-60.5-40.9-63.4zm-175.3-84.4c-9.3 44.7-18.6 89.6-27.8 134.3-2.3 10.2-13.3 7.8-22 7.8-38.3 0-49-41.8-49-73.1 0-47 18-109.3 61.8-133.4 7-4.1 14.8-6.7 22.6-6.7 18.6 0 20 13.3 20 28.7-.1 14.3-2.7 28.5-5.6 42.4z"],
+ "gofore": [400, 512, [], "f3a7", "M324 319.8h-13.2v34.7c-24.5 23.1-56.3 35.8-89.9 35.8-73.2 0-132.4-60.2-132.4-134.4 0-74.1 59.2-134.4 132.4-134.4 35.3 0 68.6 14 93.6 39.4l62.3-63.3C335 55.3 279.7 32 220.7 32 98 32 0 132.6 0 256c0 122.5 97 224 220.7 224 63.2 0 124.5-26.2 171-82.5-2-27.6-13.4-77.7-67.7-77.7zm-12.1-112.5H205.6v89H324c33.5 0 60.5 15.1 76 41.8v-30.6c0-65.2-40.4-100.2-88.1-100.2z"],
+ "goodreads": [448, 512, [], "f3a8", "M299.9 191.2c5.1 37.3-4.7 79-35.9 100.7-22.3 15.5-52.8 14.1-70.8 5.7-37.1-17.3-49.5-58.6-46.8-97.2 4.3-60.9 40.9-87.9 75.3-87.5 46.9-.2 71.8 31.8 78.2 78.3zM448 88v336c0 30.9-25.1 56-56 56H56c-30.9 0-56-25.1-56-56V88c0-30.9 25.1-56 56-56h336c30.9 0 56 25.1 56 56zM330 313.2s-.1-34-.1-217.3h-29v40.3c-.8.3-1.2-.5-1.6-1.2-9.6-20.7-35.9-46.3-76-46-51.9.4-87.2 31.2-100.6 77.8-4.3 14.9-5.8 30.1-5.5 45.6 1.7 77.9 45.1 117.8 112.4 115.2 28.9-1.1 54.5-17 69-45.2.5-1 1.1-1.9 1.7-2.9.2.1.4.1.6.2.3 3.8.2 30.7.1 34.5-.2 14.8-2 29.5-7.2 43.5-7.8 21-22.3 34.7-44.5 39.5-17.8 3.9-35.6 3.8-53.2-1.2-21.5-6.1-36.5-19-41.1-41.8-.3-1.6-1.3-1.3-2.3-1.3h-26.8c.8 10.6 3.2 20.3 8.5 29.2 24.2 40.5 82.7 48.5 128.2 37.4 49.9-12.3 67.3-54.9 67.4-106.3z"],
+ "goodreads-g": [384, 512, [], "f3a9", "M42.6 403.3h2.8c12.7 0 25.5 0 38.2.1 1.6 0 3.1-.4 3.6 2.1 7.1 34.9 30 54.6 62.9 63.9 26.9 7.6 54.1 7.8 81.3 1.8 33.8-7.4 56-28.3 68-60.4 8-21.5 10.7-43.8 11-66.5.1-5.8.3-47-.2-52.8l-.9-.3c-.8 1.5-1.7 2.9-2.5 4.4-22.1 43.1-61.3 67.4-105.4 69.1-103 4-169.4-57-172-176.2-.5-23.7 1.8-46.9 8.3-69.7C58.3 47.7 112.3.6 191.6 0c61.3-.4 101.5 38.7 116.2 70.3.5 1.1 1.3 2.3 2.4 1.9V10.6h44.3c0 280.3.1 332.2.1 332.2-.1 78.5-26.7 143.7-103 162.2-69.5 16.9-159 4.8-196-57.2-8-13.5-11.8-28.3-13-44.5zM188.9 36.5c-52.5-.5-108.5 40.7-115 133.8-4.1 59 14.8 122.2 71.5 148.6 27.6 12.9 74.3 15 108.3-8.7 47.6-33.2 62.7-97 54.8-154-9.7-71.1-47.8-120-119.6-119.7z"],
+ "google": [488, 512, [], "f1a0", "M488 261.8C488 403.3 391.1 504 248 504 110.8 504 0 393.2 0 256S110.8 8 248 8c66.8 0 123 24.5 166.3 64.9l-67.5 64.9C258.5 52.6 94.3 116.6 94.3 256c0 86.5 69.1 156.6 153.7 156.6 98.2 0 135-70.4 140.8-106.9H248v-85.3h236.1c2.3 12.7 3.9 24.9 3.9 41.4z"],
+ "google-drive": [512, 512, [], "f3aa", "M339 314.9L175.4 32h161.2l163.6 282.9H339zm-137.5 23.6L120.9 480h310.5L512 338.5H201.5zM154.1 67.4L0 338.5 80.6 480 237 208.8 154.1 67.4z"],
+ "google-pay": [640, 512, [], "e079", "M105.72,215v41.25h57.1a49.66,49.66,0,0,1-21.14,32.6c-9.54,6.55-21.72,10.28-36,10.28-27.6,0-50.93-18.91-59.3-44.22a65.61,65.61,0,0,1,0-41l0,0c8.37-25.46,31.7-44.37,59.3-44.37a56.43,56.43,0,0,1,40.51,16.08L176.47,155a101.24,101.24,0,0,0-70.75-27.84,105.55,105.55,0,0,0-94.38,59.11,107.64,107.64,0,0,0,0,96.18v.15a105.41,105.41,0,0,0,94.38,59c28.47,0,52.55-9.53,70-25.91,20-18.61,31.41-46.15,31.41-78.91A133.76,133.76,0,0,0,205.38,215Zm389.41-4c-10.13-9.38-23.93-14.14-41.39-14.14-22.46,0-39.34,8.34-50.5,24.86l20.85,13.26q11.45-17,31.26-17a34.05,34.05,0,0,1,22.75,8.79A28.14,28.14,0,0,1,487.79,248v5.51c-9.1-5.07-20.55-7.75-34.64-7.75-16.44,0-29.65,3.88-39.49,11.77s-14.82,18.31-14.82,31.56a39.74,39.74,0,0,0,13.94,31.27c9.25,8.34,21,12.51,34.79,12.51,16.29,0,29.21-7.3,39-21.89h1v17.72h22.61V250C510.25,233.45,505.26,220.34,495.13,211ZM475.9,300.3a37.32,37.32,0,0,1-26.57,11.16A28.61,28.61,0,0,1,431,305.21a19.41,19.41,0,0,1-7.77-15.63c0-7,3.22-12.81,9.54-17.42s14.53-7,24.07-7C470,265,480.3,268,487.64,273.94,487.64,284.07,483.68,292.85,475.9,300.3Zm-93.65-142A55.71,55.71,0,0,0,341.74,142H279.07V328.74H302.7V253.1h39c16,0,29.5-5.36,40.51-15.93.88-.89,1.76-1.79,2.65-2.68A54.45,54.45,0,0,0,382.25,158.26Zm-16.58,62.23a30.65,30.65,0,0,1-23.34,9.68H302.7V165h39.63a32,32,0,0,1,22.6,9.23A33.18,33.18,0,0,1,365.67,220.49ZM614.31,201,577.77,292.7h-.45L539.9,201H514.21L566,320.55l-29.35,64.32H561L640,201Z"],
+ "google-play": [512, 512, [], "f3ab", "M325.3 234.3L104.6 13l280.8 161.2-60.1 60.1zM47 0C34 6.8 25.3 19.2 25.3 35.3v441.3c0 16.1 8.7 28.5 21.7 35.3l256.6-256L47 0zm425.2 225.6l-58.9-34.1-65.7 64.5 65.7 64.5 60.1-34.1c18-14.3 18-46.5-1.2-60.8zM104.6 499l280.8-161.2-60.1-60.1L104.6 499z"],
+ "google-plus": [512, 512, [], "f2b3", "M256,8C119.1,8,8,119.1,8,256S119.1,504,256,504,504,392.9,504,256,392.9,8,256,8ZM185.3,380a124,124,0,0,1,0-248c31.3,0,60.1,11,83,32.3l-33.6,32.6c-13.2-12.9-31.3-19.1-49.4-19.1-42.9,0-77.2,35.5-77.2,78.1S142.3,334,185.3,334c32.6,0,64.9-19.1,70.1-53.3H185.3V238.1H302.2a109.2,109.2,0,0,1,1.9,20.7c0,70.8-47.5,121.2-118.8,121.2ZM415.5,273.8v35.5H380V273.8H344.5V238.3H380V202.8h35.5v35.5h35.2v35.5Z"],
+ "google-plus-g": [640, 512, [], "f0d5", "M386.061 228.496c1.834 9.692 3.143 19.384 3.143 31.956C389.204 370.205 315.599 448 204.8 448c-106.084 0-192-85.915-192-192s85.916-192 192-192c51.864 0 95.083 18.859 128.611 50.292l-52.126 50.03c-14.145-13.621-39.028-29.599-76.485-29.599-65.484 0-118.92 54.221-118.92 121.277 0 67.056 53.436 121.277 118.92 121.277 75.961 0 104.513-54.745 108.965-82.773H204.8v-66.009h181.261zm185.406 6.437V179.2h-56.001v55.733h-55.733v56.001h55.733v55.733h56.001v-55.733H627.2v-56.001h-55.733z"],
+ "google-plus-square": [448, 512, [], "f0d4", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM164 356c-55.3 0-100-44.7-100-100s44.7-100 100-100c27 0 49.5 9.8 67 26.2l-27.1 26.1c-7.4-7.1-20.3-15.4-39.8-15.4-34.1 0-61.9 28.2-61.9 63.2 0 34.9 27.8 63.2 61.9 63.2 39.6 0 54.4-28.5 56.8-43.1H164v-34.4h94.4c1 5 1.6 10.1 1.6 16.6 0 57.1-38.3 97.6-96 97.6zm220-81.8h-29v29h-29.2v-29h-29V245h29v-29H355v29h29v29.2z"],
+ "google-wallet": [448, 512, [], "f1ee", "M156.8 126.8c37.6 60.6 64.2 113.1 84.3 162.5-8.3 33.8-18.8 66.5-31.3 98.3-13.2-52.3-26.5-101.3-56-148.5 6.5-36.4 2.3-73.6 3-112.3zM109.3 200H16.1c-6.5 0-10.5 7.5-6.5 12.7C51.8 267 81.3 330.5 101.3 400h103.5c-16.2-69.7-38.7-133.7-82.5-193.5-3-4-8-6.5-13-6.5zm47.8-88c68.5 108 130 234.5 138.2 368H409c-12-138-68.4-265-143.2-368H157.1zm251.8-68.5c-1.8-6.8-8.2-11.5-15.2-11.5h-88.3c-5.3 0-9 5-7.8 10.3 13.2 46.5 22.3 95.5 26.5 146 48.2 86.2 79.7 178.3 90.6 270.8 15.8-60.5 25.3-133.5 25.3-203 0-73.6-12.1-145.1-31.1-212.6z"],
+ "gratipay": [496, 512, [], "f184", "M248 8C111.1 8 0 119.1 0 256s111.1 248 248 248 248-111.1 248-248S384.9 8 248 8zm114.6 226.4l-113 152.7-112.7-152.7c-8.7-11.9-19.1-50.4 13.6-72 28.1-18.1 54.6-4.2 68.5 11.9 15.9 17.9 46.6 16.9 61.7 0 13.9-16.1 40.4-30 68.1-11.9 32.9 21.6 22.6 60 13.8 72z"],
+ "grav": [512, 512, [], "f2d6", "M301.1 212c4.4 4.4 4.4 11.9 0 16.3l-9.7 9.7c-4.4 4.7-11.9 4.7-16.6 0l-10.5-10.5c-4.4-4.7-4.4-11.9 0-16.6l9.7-9.7c4.4-4.4 11.9-4.4 16.6 0l10.5 10.8zm-30.2-19.7c3-3 3-7.8 0-10.5-2.8-3-7.5-3-10.5 0-2.8 2.8-2.8 7.5 0 10.5 3.1 2.8 7.8 2.8 10.5 0zm-26 5.3c-3 2.8-3 7.5 0 10.2 2.8 3 7.5 3 10.5 0 2.8-2.8 2.8-7.5 0-10.2-3-3-7.7-3-10.5 0zm72.5-13.3c-19.9-14.4-33.8-43.2-11.9-68.1 21.6-24.9 40.7-17.2 59.8.8 11.9 11.3 29.3 24.9 17.2 48.2-12.5 23.5-45.1 33.2-65.1 19.1zm47.7-44.5c-8.9-10-23.3 6.9-15.5 16.1 7.4 9 32.1 2.4 15.5-16.1zM504 256c0 137-111 248-248 248S8 393 8 256 119 8 256 8s248 111 248 248zm-66.2 42.6c2.5-16.1-20.2-16.6-25.2-25.7-13.6-24.1-27.7-36.8-54.5-30.4 11.6-8 23.5-6.1 23.5-6.1.3-6.4 0-13-9.4-24.9 3.9-12.5.3-22.4.3-22.4 15.5-8.6 26.8-24.4 29.1-43.2 3.6-31-18.8-59.2-49.8-62.8-22.1-2.5-43.7 7.7-54.3 25.7-23.2 40.1 1.4 70.9 22.4 81.4-14.4-1.4-34.3-11.9-40.1-34.3-6.6-25.7 2.8-49.8 8.9-61.4 0 0-4.4-5.8-8-8.9 0 0-13.8 0-24.6 5.3 11.9-15.2 25.2-14.4 25.2-14.4 0-6.4-.6-14.9-3.6-21.6-5.4-11-23.8-12.9-31.7 2.8.1-.2.3-.4.4-.5-5 11.9-1.1 55.9 16.9 87.2-2.5 1.4-9.1 6.1-13 10-21.6 9.7-56.2 60.3-56.2 60.3-28.2 10.8-77.2 50.9-70.6 79.7.3 3 1.4 5.5 3 7.5-2.8 2.2-5.5 5-8.3 8.3-11.9 13.8-5.3 35.2 17.7 24.4 15.8-7.2 29.6-20.2 36.3-30.4 0 0-5.5-5-16.3-4.4 27.7-6.6 34.3-9.4 46.2-9.1 8 3.9 8-34.3 8-34.3 0-14.7-2.2-31-11.1-41.5 12.5 12.2 29.1 32.7 28 60.6-.8 18.3-15.2 23-15.2 23-9.1 16.6-43.2 65.9-30.4 106 0 0-9.7-14.9-10.2-22.1-17.4 19.4-46.5 52.3-24.6 64.5 26.6 14.7 108.8-88.6 126.2-142.3 34.6-20.8 55.4-47.3 63.9-65 22 43.5 95.3 94.5 101.1 59z"],
+ "gripfire": [384, 512, [], "f3ac", "M112.5 301.4c0-73.8 105.1-122.5 105.1-203 0-47.1-34-88-39.1-90.4.4 3.3.6 6.7.6 10C179.1 110.1 32 171.9 32 286.6c0 49.8 32.2 79.2 66.5 108.3 65.1 46.7 78.1 71.4 78.1 86.6 0 10.1-4.8 17-4.8 22.3 13.1-16.7 17.4-31.9 17.5-46.4 0-29.6-21.7-56.3-44.2-86.5-16-22.3-32.6-42.6-32.6-69.5zm205.3-39c-12.1-66.8-78-124.4-94.7-130.9l4 7.2c2.4 5.1 3.4 10.9 3.4 17.1 0 44.7-54.2 111.2-56.6 116.7-2.2 5.1-3.2 10.5-3.2 15.8 0 20.1 15.2 42.1 17.9 42.1 2.4 0 56.6-55.4 58.1-87.7 6.4 11.7 9.1 22.6 9.1 33.4 0 41.2-41.8 96.9-41.8 96.9 0 11.6 31.9 53.2 35.5 53.2 1 0 2.2-1.4 3.2-2.4 37.9-39.3 67.3-85 67.3-136.8 0-8-.7-16.2-2.2-24.6z"],
+ "grunt": [384, 512, [], "f3ad", "M61.3 189.3c-1.1 10 5.2 19.1 5.2 19.1.7-7.5 2.2-12.8 4-16.6.4 10.3 3.2 23.5 12.8 34.1 6.9 7.6 35.6 23.3 54.9 6.1 1 2.4 2.1 5.3 3 8.5 2.9 10.3-2.7 25.3-2.7 25.3s15.1-17.1 13.9-32.5c10.8-.5 21.4-8.4 21.1-19.5 0 0-18.9 10.4-35.5-8.8-9.7-11.2-40.9-42-83.1-31.8 4.3 1 8.9 2.4 13.5 4.1h-.1c-4.2 2-6.5 7.1-7 12zm28.3-1.8c19.5 11 37.4 25.7 44.9 37-5.7 3.3-21.7 10.4-38-1.7-10.3-7.6-9.8-26.2-6.9-35.3zm142.1 45.8c-1.2 15.5 13.9 32.5 13.9 32.5s-5.6-15-2.7-25.3c.9-3.2 2-6 3-8.5 19.3 17.3 48 1.5 54.8-6.1 9.6-10.6 12.3-23.8 12.8-34.1 1.8 3.8 3.4 9.1 4 16.6 0 0 6.4-9.1 5.2-19.1-.6-5-2.9-10-7-11.8h-.1c4.6-1.8 9.2-3.2 13.5-4.1-42.3-10.2-73.4 20.6-83.1 31.8-16.7 19.2-35.5 8.8-35.5 8.8-.2 10.9 10.4 18.9 21.2 19.3zm62.7-45.8c3 9.1 3.4 27.7-7 35.4-16.3 12.1-32.2 5-37.9 1.6 7.5-11.4 25.4-26 44.9-37zM160 418.5h-29.4c-5.5 0-8.2 1.6-9.5 2.9-1.9 2-2.2 4.7-.9 8.1 3.5 9.1 11.4 16.5 13.7 18.6 3.1 2.7 7.5 4.3 11.8 4.3 4.4 0 8.3-1.7 11-4.6 7.5-8.2 11.9-17.1 13-19.8.6-1.5 1.3-4.5-.9-6.8-1.8-1.8-4.7-2.7-8.8-2.7zm189.2-101.2c-2.4 17.9-13 33.8-24.6 43.7-3.1-22.7-3.7-55.5-3.7-62.4 0-14.7 9.5-24.5 12.2-26.1 2.5-1.5 5.4-3 8.3-4.6 18-9.6 40.4-21.6 40.4-43.7 0-16.2-9.3-23.2-15.4-27.8-.8-.6-1.5-1.1-2.2-1.7-2.1-1.7-3.7-3-4.3-4.4-4.4-9.8-3.6-34.2-1.7-37.6.6-.6 16.7-20.9 11.8-39.2-2-7.4-6.9-13.3-14.1-17-5.3-2.7-11.9-4.2-19.5-4.5-.1-2-.5-3.9-.9-5.9-.6-2.6-1.1-5.3-.9-8.1.4-4.7.8-9 2.2-11.3 8.4-13.3 28.8-17.6 29-17.6l12.3-2.4-8.1-9.5c-.1-.2-17.3-17.5-46.3-17.5-7.9 0-16 1.3-24.1 3.9-24.2 7.8-42.9 30.5-49.4 39.3-3.1-1-6.3-1.9-9.6-2.7-4.2-15.8 9-38.5 9-38.5s-13.6-3-33.7 15.2c-2.6-6.5-8.1-20.5-1.8-37.2C184.6 10.1 177.2 26 175 40.4c-7.6-5.4-6.7-23.1-7.2-27.6-7.5.9-29.2 21.9-28.2 48.3-2 .5-3.9 1.1-5.9 1.7-6.5-8.8-25.1-31.5-49.4-39.3-7.9-2.2-16-3.5-23.9-3.5-29 0-46.1 17.3-46.3 17.5L6 46.9l12.3 2.4c.2 0 20.6 4.3 29 17.6 1.4 2.2 1.8 6.6 2.2 11.3.2 2.8-.4 5.5-.9 8.1-.4 1.9-.8 3.9-.9 5.9-7.7.3-14.2 1.8-19.5 4.5-7.2 3.7-12.1 9.6-14.1 17-5 18.2 11.2 38.5 11.8 39.2 1.9 3.4 2.7 27.8-1.7 37.6-.6 1.4-2.2 2.7-4.3 4.4-.7.5-1.4 1.1-2.2 1.7-6.1 4.6-15.4 11.7-15.4 27.8 0 22.1 22.4 34.1 40.4 43.7 3 1.6 5.8 3.1 8.3 4.6 2.7 1.6 12.2 11.4 12.2 26.1 0 6.9-.6 39.7-3.7 62.4-11.6-9.9-22.2-25.9-24.6-43.8 0 0-29.2 22.6-20.6 70.8 5.2 29.5 23.2 46.1 47 54.7 8.8 19.1 29.4 45.7 67.3 49.6C143 504.3 163 512 192.2 512h.2c29.1 0 49.1-7.7 63.6-19.5 37.9-3.9 58.5-30.5 67.3-49.6 23.8-8.7 41.7-25.2 47-54.7 8.2-48.4-21.1-70.9-21.1-70.9zM305.7 37.7c5.6-1.8 11.6-2.7 17.7-2.7 11 0 19.9 3 24.7 5-3.1 1.4-6.4 3.2-9.7 5.3-2.4-.4-5.6-.8-9.2-.8-10.5 0-20.5 3.1-28.7 8.9-12.3 8.7-18 16.9-20.7 22.4-2.2-1.3-4.5-2.5-7.1-3.7-1.6-.8-3.1-1.5-4.7-2.2 6.1-9.1 19.9-26.5 37.7-32.2zm21 18.2c-.8 1-1.6 2.1-2.3 3.2-3.3 5.2-3.9 11.6-4.4 17.8-.5 6.4-1.1 12.5-4.4 17-4.2.8-8.1 1.7-11.5 2.7-2.3-3.1-5.6-7-10.5-11.2 1.4-4.8 5.5-16.1 13.5-22.5 5.6-4.3 12.2-6.7 19.6-7zM45.6 45.3c-3.3-2.2-6.6-4-9.7-5.3 4.8-2 13.7-5 24.7-5 6.1 0 12 .9 17.7 2.7 17.8 5.8 31.6 23.2 37.7 32.1-1.6.7-3.2 1.4-4.8 2.2-2.5 1.2-4.9 2.5-7.1 3.7-2.6-5.4-8.3-13.7-20.7-22.4-8.3-5.8-18.2-8.9-28.8-8.9-3.4.1-6.6.5-9 .9zm44.7 40.1c-4.9 4.2-8.3 8-10.5 11.2-3.4-.9-7.3-1.9-11.5-2.7C65 89.5 64.5 83.4 64 77c-.5-6.2-1.1-12.6-4.4-17.8-.7-1.1-1.5-2.2-2.3-3.2 7.4.3 14 2.6 19.5 7 8 6.3 12.1 17.6 13.5 22.4zM58.1 259.9c-2.7-1.6-5.6-3.1-8.4-4.6-14.9-8-30.2-16.3-30.2-30.5 0-11.1 4.3-14.6 8.9-18.2l.5-.4c.7-.6 1.4-1.2 2.2-1.8-.9 7.2-1.9 13.3-2.7 14.9 0 0 12.1-15 15.7-44.3 1.4-11.5-1.1-34.3-5.1-43 .2 4.9 0 9.8-.3 14.4-.4-.8-.8-1.6-1.3-2.2-3.2-4-11.8-17.5-9.4-26.6.9-3.5 3.1-6 6.7-7.8 3.8-1.9 8.8-2.9 15.1-2.9 12.3 0 25.9 3.7 32.9 6 25.1 8 55.4 30.9 64.1 37.7.2.2.4.3.4.3l5.6 3.9-3.5-5.8c-.2-.3-19.1-31.4-53.2-46.5 2-2.9 7.4-8.1 21.6-15.1 21.4-10.5 46.5-15.8 74.3-15.8 27.9 0 52.9 5.3 74.3 15.8 14.2 6.9 19.6 12.2 21.6 15.1-34 15.1-52.9 46.2-53.1 46.5l-3.5 5.8 5.6-3.9s.2-.1.4-.3c8.7-6.8 39-29.8 64.1-37.7 7-2.2 20.6-6 32.9-6 6.3 0 11.3 1 15.1 2.9 3.5 1.8 5.7 4.4 6.7 7.8 2.5 9.1-6.1 22.6-9.4 26.6-.5.6-.9 1.3-1.3 2.2-.3-4.6-.5-9.5-.3-14.4-4 8.8-6.5 31.5-5.1 43 3.6 29.3 15.7 44.3 15.7 44.3-.8-1.6-1.8-7.7-2.7-14.9.7.6 1.5 1.2 2.2 1.8l.5.4c4.6 3.7 8.9 7.1 8.9 18.2 0 14.2-15.4 22.5-30.2 30.5-2.9 1.5-5.7 3.1-8.4 4.6-8.7 5-18 16.7-19.1 34.2-.9 14.6.9 49.9 3.4 75.9-12.4 4.8-26.7 6.4-39.7 6.8-2-4.1-3.9-8.5-5.5-13.1-.7-2-19.6-51.1-26.4-62.2 5.5 39 17.5 73.7 23.5 89.6-3.5-.5-7.3-.7-11.7-.7h-117c-4.4 0-8.3.3-11.7.7 6-15.9 18.1-50.6 23.5-89.6-6.8 11.2-25.7 60.3-26.4 62.2-1.6 4.6-3.5 9-5.5 13.1-13-.4-27.2-2-39.7-6.8 2.5-26 4.3-61.2 3.4-75.9-.9-17.4-10.3-29.2-19-34.2zM34.8 404.6c-12.1-20-8.7-54.1-3.7-59.1 10.9 34.4 47.2 44.3 74.4 45.4-2.7 4.2-5.2 7.6-7 10l-1.4 1.4c-7.2 7.8-8.6 18.5-4.1 31.8-22.7-.1-46.3-9.8-58.2-29.5zm45.7 43.5c6 1.1 12.2 1.9 18.6 2.4 3.5 8 7.4 15.9 12.3 23.1-14.4-5.9-24.4-16-30.9-25.5zM192 498.2c-60.6-.1-78.3-45.8-84.9-64.7-3.7-10.5-3.4-18.2.9-23.1 2.9-3.3 9.5-7.2 24.6-7.2h118.8c15.1 0 21.8 3.9 24.6 7.2 4.2 4.8 4.5 12.6.9 23.1-6.6 18.8-24.3 64.6-84.9 64.7zm80.6-24.6c4.9-7.2 8.8-15.1 12.3-23.1 6.4-.5 12.6-1.3 18.6-2.4-6.5 9.5-16.5 19.6-30.9 25.5zm76.6-69c-12 19.7-35.6 29.3-58.1 29.7 4.5-13.3 3.1-24.1-4.1-31.8-.4-.5-.9-1-1.4-1.5-1.8-2.4-4.3-5.8-7-10 27.2-1.2 63.5-11 74.4-45.4 5 5 8.4 39.1-3.8 59zM191.9 187.7h.2c12.7-.1 27.2-17.8 27.2-17.8-9.9 6-18.8 8.1-27.3 8.3-8.5-.2-17.4-2.3-27.3-8.3 0 0 14.5 17.6 27.2 17.8zm61.7 230.7h-29.4c-4.2 0-7.2.9-8.9 2.7-2.2 2.3-1.5 5.2-.9 6.7 1 2.6 5.5 11.3 13 19.3 2.7 2.9 6.6 4.5 11 4.5s8.7-1.6 11.8-4.2c2.3-2 10.2-9.2 13.7-18.1 1.3-3.3 1-6-.9-7.9-1.3-1.3-4-2.9-9.4-3z"],
+ "guilded": [448, 512, [], "e07e", "M443.427,64H4.571c0,103.26,22.192,180.06,43.418,222.358C112.046,414.135,224,448,225.256,448a312.824,312.824,0,0,0,140.55-103.477c25.907-33.923,53.1-87.19,65.916-145.761H171.833c4.14,36.429,22.177,67.946,45.1,86.944h88.589c-17.012,28.213-48.186,54.4-80.456,69.482-31.232-13.259-69.09-46.544-96.548-98.362-26.726-53.833-27.092-105.883-27.092-105.883H437.573A625.91,625.91,0,0,0,443.427,64Z"],
+ "gulp": [256, 512, [], "f3ae", "M209.8 391.1l-14.1 24.6-4.6 80.2c0 8.9-28.3 16.1-63.1 16.1s-63.1-7.2-63.1-16.1l-5.8-79.4-14.9-25.4c41.2 17.3 126 16.7 165.6 0zm-196-253.3l13.6 125.5c5.9-20 20.8-47 40-55.2 6.3-2.7 12.7-2.7 18.7.9 5.2 3 9.6 9.3 10.1 11.8 1.2 6.5-2 9.1-4.5 9.1-3 0-5.3-4.6-6.8-7.3-4.1-7.3-10.3-7.6-16.9-2.8-6.9 5-12.9 13.4-17.1 20.7-5.1 8.8-9.4 18.5-12 28.2-1.5 5.6-2.9 14.6-.6 19.9 1 2.2 2.5 3.6 4.9 3.6 5 0 12.3-6.6 15.8-10.1 4.5-4.5 10.3-11.5 12.5-16l5.2-15.5c2.6-6.8 9.9-5.6 9.9 0 0 10.2-3.7 13.6-10 34.7-5.8 19.5-7.6 25.8-7.6 25.8-.7 2.8-3.4 7.5-6.3 7.5-1.2 0-2.1-.4-2.6-1.2-1-1.4-.9-5.3-.8-6.3.2-3.2 6.3-22.2 7.3-25.2-2 2.2-4.1 4.4-6.4 6.6-5.4 5.1-14.1 11.8-21.5 11.8-3.4 0-5.6-.9-7.7-2.4l7.6 79.6c2 5 39.2 17.1 88.2 17.1 49.1 0 86.3-12.2 88.2-17.1l10.9-94.6c-5.7 5.2-12.3 11.6-19.6 14.8-5.4 2.3-17.4 3.8-17.4-5.7 0-5.2 9.1-14.8 14.4-21.5 1.4-1.7 4.7-5.9 4.7-8.1 0-2.9-6-2.2-11.7 2.5-3.2 2.7-6.2 6.3-8.7 9.7-4.3 6-6.6 11.2-8.5 15.5-6.2 14.2-4.1 8.6-9.1 22-5 13.3-4.2 11.8-5.2 14-.9 1.9-2.2 3.5-4 4.5-1.9 1-4.5.9-6.1-.3-.9-.6-1.3-1.9-1.3-3.7 0-.9.1-1.8.3-2.7 1.5-6.1 7.8-18.1 15-34.3 1.6-3.7 1-2.6.8-2.3-6.2 6-10.9 8.9-14.4 10.5-5.8 2.6-13 2.6-14.5-4.1-.1-.4-.1-.8-.2-1.2-11.8 9.2-24.3 11.7-20-8.1-4.6 8.2-12.6 14.9-22.4 14.9-4.1 0-7.1-1.4-8.6-5.1-2.3-5.5 1.3-14.9 4.6-23.8 1.7-4.5 4-9.9 7.1-16.2 1.6-3.4 4.2-5.4 7.6-4.5.6.2 1.1.4 1.6.7 2.6 1.8 1.6 4.5.3 7.2-3.8 7.5-7.1 13-9.3 20.8-.9 3.3-2 9 1.5 9 2.4 0 4.7-.8 6.9-2.4 4.6-3.4 8.3-8.5 11.1-13.5 2-3.6 4.4-8.3 5.6-12.3.5-1.7 1.1-3.3 1.8-4.8 1.1-2.5 2.6-5.1 5.2-5.1 1.3 0 2.4.5 3.2 1.5 1.7 2.2 1.3 4.5.4 6.9-2 5.6-4.7 10.6-6.9 16.7-1.3 3.5-2.7 8-2.7 11.7 0 3.4 3.7 2.6 6.8 1.2 2.4-1.1 4.8-2.8 6.8-4.5 1.2-4.9.9-3.8 26.4-68.2 1.3-3.3 3.7-4.7 6.1-4.7 1.2 0 2.2.4 3.2 1.1 1.7 1.3 1.7 4.1 1 6.2-.7 1.9-.6 1.3-4.5 10.5-5.2 12.1-8.6 20.8-13.2 31.9-1.9 4.6-7.7 18.9-8.7 22.3-.6 2.2-1.3 5.8 1 5.8 5.4 0 19.3-13.1 23.1-17 .2-.3.5-.4.9-.6.6-1.9 1.2-3.7 1.7-5.5 1.4-3.8 2.7-8.2 5.3-11.3.8-1 1.7-1.6 2.7-1.6 2.8 0 4.2 1.2 4.2 4 0 1.1-.7 5.1-1.1 6.2 1.4-1.5 2.9-3 4.5-4.5 15-13.9 25.7-6.8 25.7.2 0 7.4-8.9 17.7-13.8 23.4-1.6 1.9-4.9 5.4-5 6.4 0 1.3.9 1.8 2.2 1.8 2 0 6.4-3.5 8-4.7 5-3.9 11.8-9.9 16.6-14.1l14.8-136.8c-30.5 17.1-197.6 17.2-228.3.2zm229.7-8.5c0 21-231.2 21-231.2 0 0-8.8 51.8-15.9 115.6-15.9 9 0 17.8.1 26.3.4l12.6-48.7L228.1.6c1.4-1.4 5.8-.2 9.9 3.5s6.6 7.9 5.3 9.3l-.1.1L185.9 74l-10 40.7c39.9 2.6 67.6 8.1 67.6 14.6zm-69.4 4.6c0-.8-.9-1.5-2.5-2.1l-.2.8c0 1.3-5 2.4-11.1 2.4s-11.1-1.1-11.1-2.4c0-.1 0-.2.1-.3l.2-.7c-1.8.6-3 1.4-3 2.3 0 2.1 6.2 3.7 13.7 3.7 7.7.1 13.9-1.6 13.9-3.7z"],
+ "hacker-news": [448, 512, [], "f1d4", "M0 32v448h448V32H0zm21.2 197.2H21c.1-.1.2-.3.3-.4 0 .1 0 .3-.1.4zm218 53.9V384h-31.4V281.3L128 128h37.3c52.5 98.3 49.2 101.2 59.3 125.6 12.3-27 5.8-24.4 60.6-125.6H320l-80.8 155.1z"],
+ "hacker-news-square": [448, 512, [], "f3af", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM21.2 229.2H21c.1-.1.2-.3.3-.4 0 .1 0 .3-.1.4zm218 53.9V384h-31.4V281.3L128 128h37.3c52.5 98.3 49.2 101.2 59.3 125.6 12.3-27 5.8-24.4 60.6-125.6H320l-80.8 155.1z"],
+ "hackerrank": [512, 512, [], "f5f7", "M477.5 128C463 103.05 285.13 0 256.16 0S49.25 102.79 34.84 128s-14.49 230.8 0 256 192.38 128 221.32 128S463 409.08 477.49 384s14.51-231 .01-256zM316.13 414.22c-4 0-40.91-35.77-38-38.69.87-.87 6.26-1.48 17.55-1.83 0-26.23.59-68.59.94-86.32 0-2-.44-3.43-.44-5.85h-79.93c0 7.1-.46 36.2 1.37 72.88.23 4.54-1.58 6-5.74 5.94-10.13 0-20.27-.11-30.41-.08-4.1 0-5.87-1.53-5.74-6.11.92-33.44 3-84-.15-212.67v-3.17c-9.67-.35-16.38-1-17.26-1.84-2.92-2.92 34.54-38.69 38.49-38.69s41.17 35.78 38.27 38.69c-.87.87-7.9 1.49-16.77 1.84v3.16c-2.42 25.75-2 79.59-2.63 105.39h80.26c0-4.55.39-34.74-1.2-83.64-.1-3.39.95-5.17 4.21-5.2 11.07-.08 22.15-.13 33.23-.06 3.46 0 4.57 1.72 4.5 5.38C333 354.64 336 341.29 336 373.69c8.87.35 16.82 1 17.69 1.84 2.88 2.91-33.62 38.69-37.58 38.69z"],
+ "hips": [640, 512, [], "f452", "M251.6 157.6c0-1.9-.9-2.8-2.8-2.8h-40.9c-1.6 0-2.7 1.4-2.7 2.8v201.8c0 1.4 1.1 2.8 2.7 2.8h40.9c1.9 0 2.8-.9 2.8-2.8zM156.5 168c-16.1-11.8-36.3-17.9-60.3-18-18.1-.1-34.6 3.7-49.8 11.4V80.2c0-1.8-.9-2.7-2.8-2.7H2.7c-1.8 0-2.7.9-2.7 2.7v279.2c0 1.9.9 2.8 2.7 2.8h41c1.9 0 2.8-.9 2.8-2.8V223.3c0-.8-2.8-27 45.8-27 48.5 0 45.8 26.1 45.8 27v122.6c0 9 7.3 16.3 16.4 16.3h27.3c1.8 0 2.7-.9 2.7-2.8V223.3c0-23.4-9.3-41.8-28-55.3zm478.4 110.1c-6.8-15.7-18.4-27-34.9-34.1l-57.6-25.3c-8.6-3.6-9.2-11.2-2.6-16.1 7.4-5.5 44.3-13.9 84 6.8 1.7 1 4-.3 4-2.4v-44.7c0-1.3-.6-2.1-1.9-2.6-17.7-6.6-36.1-9.9-55.1-9.9-26.5 0-45.3 5.8-58.5 15.4-.5.4-28.4 20-22.7 53.7 3.4 19.6 15.8 34.2 37.2 43.6l53.6 23.5c11.6 5.1 15.2 13.3 12.2 21.2-3.7 9.1-13.2 13.6-36.5 13.6-24.3 0-44.7-8.9-58.4-19.1-2.1-1.4-4.4.2-4.4 2.3v34.4c0 10.4 4.9 17.3 14.6 20.7 15.6 5.5 31.6 8.2 48.2 8.2 12.7 0 25.8-1.2 36.3-4.3.7-.3 36-8.9 45.6-45.8 3.5-13.5 2.4-26.5-3.1-39.1zM376.2 149.8c-31.7 0-104.2 20.1-104.2 103.5v183.5c0 .8.6 2.7 2.7 2.7h40.9c1.9 0 2.8-.9 2.8-2.7V348c16.5 12.7 35.8 19.1 57.7 19.1 60.5 0 108.7-48.5 108.7-108.7.1-60.3-48.2-108.6-108.6-108.6zm0 170.9c-17.2 0-31.9-6.1-44-18.2-12.2-12.2-18.2-26.8-18.2-44 0-34.5 27.6-62.2 62.2-62.2 34.5 0 62.2 27.6 62.2 62.2.1 34.3-27.3 62.2-62.2 62.2zM228.3 72.5c-15.9 0-28.8 12.9-28.9 28.9 0 15.6 12.7 28.9 28.9 28.9s28.9-13.1 28.9-28.9c0-16.2-13-28.9-28.9-28.9z"],
+ "hire-a-helper": [512, 512, [], "f3b0", "M443.1 0H71.9C67.9 37.3 37.4 67.8 0 71.7v371.5c37.4 4.9 66 32.4 71.9 68.8h372.2c3-36.4 32.5-65.8 67.9-69.8V71.7c-36.4-5.9-65-35.3-68.9-71.7zm-37 404.9c-36.3 0-18.8-2-55.1-2-35.8 0-21 2-56.1 2-5.9 0-4.9-8.2 0-9.8 22.8-7.6 22.9-10.2 24.6-12.8 10.4-15.6 5.9-83 5.9-113 0-5.3-6.4-12.8-13.8-12.8H200.4c-7.4 0-13.8 7.5-13.8 12.8 0 30-4.5 97.4 5.9 113 1.7 2.5 1.8 5.2 24.6 12.8 4.9 1.6 6 9.8 0 9.8-35.1 0-20.3-2-56.1-2-36.3 0-18.8 2-55.1 2-7.9 0-5.8-10.8 0-10.8 10.2-3.4 13.5-3.5 21.7-13.8 7.7-12.9 7.9-44.4 7.9-127.8V151.3c0-22.2-12.2-28.3-28.6-32.4-8.8-2.2-4-11.8 1-11.8 36.5 0 20.6 2 57.1 2 32.7 0 16.5-2 49.2-2 3.3 0 8.5 8.3 1 10.8-4.9 1.6-27.6 3.7-27.6 39.3 0 45.6-.2 55.8 1 68.8 0 1.3 2.3 12.8 12.8 12.8h109.2c10.5 0 12.8-11.5 12.8-12.8 1.2-13 1-23.2 1-68.8 0-35.6-22.7-37.7-27.6-39.3-7.5-2.5-2.3-10.8 1-10.8 32.7 0 16.5 2 49.2 2 36.5 0 20.6-2 57.1-2 4.9 0 9.9 9.6 1 11.8-16.4 4.1-28.6 10.3-28.6 32.4v101.2c0 83.4.1 114.9 7.9 127.8 8.2 10.2 11.4 10.4 21.7 13.8 5.8 0 7.8 10.8 0 10.8z"],
+ "hive": [512, 512, [], "e07f", "M260.353,254.878,131.538,33.1a2.208,2.208,0,0,0-3.829.009L.3,254.887A2.234,2.234,0,0,0,.3,257.122L129.116,478.9a2.208,2.208,0,0,0,3.83-.009L260.358,257.113A2.239,2.239,0,0,0,260.353,254.878Zm39.078-25.713a2.19,2.19,0,0,0,1.9,1.111h66.509a2.226,2.226,0,0,0,1.9-3.341L259.115,33.111a2.187,2.187,0,0,0-1.9-1.111H190.707a2.226,2.226,0,0,0-1.9,3.341ZM511.7,254.886,384.9,33.112A2.2,2.2,0,0,0,382.99,32h-66.6a2.226,2.226,0,0,0-1.906,3.34L440.652,256,314.481,476.66a2.226,2.226,0,0,0,1.906,3.34h66.6a2.2,2.2,0,0,0,1.906-1.112L511.7,257.114A2.243,2.243,0,0,0,511.7,254.886ZM366.016,284.917H299.508a2.187,2.187,0,0,0-1.9,1.111l-108.8,190.631a2.226,2.226,0,0,0,1.9,3.341h66.509a2.187,2.187,0,0,0,1.9-1.111l108.8-190.631A2.226,2.226,0,0,0,366.016,284.917Z"],
+ "hooli": [640, 512, [], "f427", "M144.5 352l38.3.8c-13.2-4.6-26-10.2-38.3-16.8zm57.7-5.3v5.3l-19.4.8c36.5 12.5 69.9 14.2 94.7 7.2-19.9.2-45.8-2.6-75.3-13.3zm408.9-115.2c15.9 0 28.9-12.9 28.9-28.9s-12.9-24.5-28.9-24.5c-15.9 0-28.9 8.6-28.9 24.5s12.9 28.9 28.9 28.9zm-29 120.5H640V241.5h-57.9zm-73.7 0h57.9V156.7L508.4 184zm-31-119.4c-18.2-18.2-50.4-17.1-50.4-17.1s-32.3-1.1-50.4 17.1c-18.2 18.2-16.8 33.9-16.8 52.6s-1.4 34.3 16.8 52.5 50.4 17.1 50.4 17.1 32.3 1.1 50.4-17.1c18.2-18.2 16.8-33.8 16.8-52.5-.1-18.8 1.3-34.5-16.8-52.6zm-39.8 71.9c0 3.6-1.8 12.5-10.7 12.5s-10.7-8.9-10.7-12.5v-40.4c0-8.7 7.3-10.9 10.7-10.9s10.7 2.1 10.7 10.9zm-106.2-71.9c-18.2-18.2-50.4-17.1-50.4-17.1s-32.2-1.1-50.4 17.1c-1.9 1.9-3.7 3.9-5.3 6-38.2-29.6-72.5-46.5-102.1-61.1v-20.7l-22.5 10.6c-54.4-22.1-89-18.2-97.3.1 0 0-24.9 32.8 61.8 110.8V352h57.9v-28.6c-6.5-4.2-13-8.7-19.4-13.6-14.8-11.2-27.4-21.6-38.4-31.4v-31c13.1 14.7 30.5 31.4 53.4 50.3l4.5 3.6v-29.8c0-6.9 1.7-18.2 10.8-18.2s10.6 6.9 10.6 15V317c18 12.2 37.3 22.1 57.7 29.6v-93.9c0-18.7-13.4-37.4-40.6-37.4-15.8-.1-30.5 8.2-38.5 21.9v-54.3c41.9 20.9 83.9 46.5 99.9 58.3-10.2 14.6-9.3 28.1-9.3 43.7 0 18.7-1.4 34.3 16.8 52.5s50.4 17.1 50.4 17.1 32.3 1.1 50.4-17.1c18.2-18.2 16.7-33.8 16.7-52.5 0-18.5 1.5-34.2-16.7-52.3zM65.2 184v63.3c-48.7-54.5-38.9-76-35.2-79.1 13.5-11.4 37.5-8 64.4 2.1zm226.5 120.5c0 3.6-1.8 12.5-10.7 12.5s-10.7-8.9-10.7-12.5v-40.4c0-8.7 7.3-10.9 10.7-10.9s10.7 2.1 10.7 10.9z"],
+ "hornbill": [512, 512, [], "f592", "M76.38 370.3a37.8 37.8 0 1 1-32.07-32.42c-78.28-111.35 52-190.53 52-190.53-5.86 43-8.24 91.16-8.24 91.16-67.31 41.49.93 64.06 39.81 72.87a140.38 140.38 0 0 0 131.66 91.94c1.92 0 3.77-.21 5.67-.28l.11 18.86c-99.22 1.39-158.7-29.14-188.94-51.6zm108-327.7A37.57 37.57 0 0 0 181 21.45a37.95 37.95 0 1 0-31.17 54.22c-22.55 29.91-53.83 89.57-52.42 190l21.84-.15c0-.9-.14-1.77-.14-2.68A140.42 140.42 0 0 1 207 132.71c8-37.71 30.7-114.3 73.8-44.29 0 0 48.14 2.38 91.18 8.24 0 0-77.84-128-187.59-54.06zm304.19 134.17a37.94 37.94 0 1 0-53.84-28.7C403 126.13 344.89 99 251.28 100.33l.14 22.5c2.7-.15 5.39-.41 8.14-.41a140.37 140.37 0 0 1 130.49 88.76c39.1 9 105.06 31.58 38.46 72.54 0 0-2.34 48.13-8.21 91.16 0 0 133.45-81.16 49-194.61a37.45 37.45 0 0 0 19.31-3.5zM374.06 436.24c21.43-32.46 46.42-89.69 45.14-179.66l-19.52.14c.08 2.06.3 4.07.3 6.15a140.34 140.34 0 0 1-91.39 131.45c-8.85 38.95-31.44 106.66-72.77 39.49 0 0-48.12-2.34-91.19-8.22 0 0 79.92 131.34 191.9 51a37.5 37.5 0 0 0 3.64 14 37.93 37.93 0 1 0 33.89-54.29z"],
+ "hotjar": [448, 512, [], "f3b1", "M414.9 161.5C340.2 29 121.1 0 121.1 0S222.2 110.4 93 197.7C11.3 252.8-21 324.4 14 402.6c26.8 59.9 83.5 84.3 144.6 93.4-29.2-55.1-6.6-122.4-4.1-129.6 57.1 86.4 165 0 110.8-93.9 71 15.4 81.6 138.6 27.1 215.5 80.5-25.3 134.1-88.9 148.8-145.6 15.5-59.3 3.7-127.9-26.3-180.9z"],
+ "houzz": [448, 512, [], "f27c", "M275.9 330.7H171.3V480H17V32h109.5v104.5l305.1 85.6V480H275.9z"],
+ "html5": [384, 512, [], "f13b", "M0 32l34.9 395.8L191.5 480l157.6-52.2L384 32H0zm308.2 127.9H124.4l4.1 49.4h175.6l-13.6 148.4-97.9 27v.3h-1.1l-98.7-27.3-6-75.8h47.7L138 320l53.5 14.5 53.7-14.5 6-62.2H84.3L71.5 112.2h241.1l-4.4 47.7z"],
+ "hubspot": [512, 512, [], "f3b2", "M267.4 211.6c-25.1 23.7-40.8 57.3-40.8 94.6 0 29.3 9.7 56.3 26 78L203.1 434c-4.4-1.6-9.1-2.5-14-2.5-10.8 0-20.9 4.2-28.5 11.8-7.6 7.6-11.8 17.8-11.8 28.6s4.2 20.9 11.8 28.5c7.6 7.6 17.8 11.6 28.5 11.6 10.8 0 20.9-3.9 28.6-11.6 7.6-7.6 11.8-17.8 11.8-28.5 0-4.2-.6-8.2-1.9-12.1l50-50.2c22 16.9 49.4 26.9 79.3 26.9 71.9 0 130-58.3 130-130.2 0-65.2-47.7-119.2-110.2-128.7V116c17.5-7.4 28.2-23.8 28.2-42.9 0-26.1-20.9-47.9-47-47.9S311.2 47 311.2 73.1c0 19.1 10.7 35.5 28.2 42.9v61.2c-15.2 2.1-29.6 6.7-42.7 13.6-27.6-20.9-117.5-85.7-168.9-124.8 1.2-4.4 2-9 2-13.8C129.8 23.4 106.3 0 77.4 0 48.6 0 25.2 23.4 25.2 52.2c0 28.9 23.4 52.3 52.2 52.3 9.8 0 18.9-2.9 26.8-7.6l163.2 114.7zm89.5 163.6c-38.1 0-69-30.9-69-69s30.9-69 69-69 69 30.9 69 69-30.9 69-69 69z"],
+ "ideal": [576, 512, [], "e013", "M125.61,165.48a49.07,49.07,0,1,0,49.06,49.06A49.08,49.08,0,0,0,125.61,165.48ZM86.15,425.84h78.94V285.32H86.15Zm151.46-211.6c0-20-10-22.53-18.74-22.53H204.82V237.5h14.05C228.62,237.5,237.61,234.69,237.61,214.24Zm201.69,46V168.93h22.75V237.5h33.69C486.5,113.08,388.61,86.19,299.67,86.19H204.84V169h14c25.6,0,41.5,17.35,41.5,45.26,0,28.81-15.52,46-41.5,46h-14V425.88h94.83c144.61,0,194.94-67.16,196.72-165.64Zm-109.75,0H273.3V169h54.43v22.73H296v10.58h30V225H296V237.5h33.51Zm74.66,0-5.16-17.67H369.31l-5.18,17.67H340.47L368,168.92h32.35l27.53,91.34ZM299.65,32H32V480H299.65c161.85,0,251-79.73,251-224.52C550.62,172,518,32,299.65,32Zm0,426.92H53.07V53.07H299.65c142.1,0,229.9,64.61,229.9,202.41C529.55,389.57,448.55,458.92,299.65,458.92Zm83.86-264.85L376,219.88H392.4l-7.52-25.81Z"],
+ "imdb": [448, 512, [], "f2d8", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM21.3 229.2H21c.1-.1.2-.3.3-.4zM97 319.8H64V192h33zm113.2 0h-28.7v-86.4l-11.6 86.4h-20.6l-12.2-84.5v84.5h-29V192h42.8c3.3 19.8 6 39.9 8.7 59.9l7.6-59.9h43zm11.4 0V192h24.6c17.6 0 44.7-1.6 49 20.9 1.7 7.6 1.4 16.3 1.4 24.4 0 88.5 11.1 82.6-75 82.5zm160.9-29.2c0 15.7-2.4 30.9-22.2 30.9-9 0-15.2-3-20.9-9.8l-1.9 8.1h-29.8V192h31.7v41.7c6-6.5 12-9.2 20.9-9.2 21.4 0 22.2 12.8 22.2 30.1zM265 229.9c0-9.7 1.6-16-10.3-16v83.7c12.2.3 10.3-8.7 10.3-18.4zm85.5 26.1c0-5.4 1.1-12.7-6.2-12.7-6 0-4.9 8.9-4.9 12.7 0 .6-1.1 39.6 1.1 44.7.8 1.6 2.2 2.4 3.8 2.4 7.8 0 6.2-9 6.2-14.4z"],
+ "innosoft": [448, 512, [], "e080", "M422.559,159.71a27.379,27.379,0,0,0-13.866-23.337,26.42,26.42,0,0,0-26.211.133L73.943,314.647V176.261a11.955,11.955,0,0,1,6.047-10.34L218.066,86.208a12.153,12.153,0,0,1,11.922.025l32.656,18.853L112.581,191.723v56L359.642,105.086,241.129,36.679c-10.992-6.129-22.3-6.255-33.8-.27l-164.6,95.026c-10.634,6.12-16.771,16.39-17.29,29.124l0,191.5c.17,10.135,5.08,18.672,13.474,23.428a27.037,27.037,0,0,0,26.736-.045L374.057,197.376V335.657a11.976,11.976,0,0,1-5.92,10.368L230.025,425.77a12.175,12.175,0,0,1-11.937.062l-32.723-18.9,150.051-86.627v-56L88.367,406.932l118.794,68.583a33.88,33.88,0,0,0,34.25-.327l164.527-94.995c10.746-6.631,16.649-17.118,16.624-29.528Z"],
+ "instagram": [448, 512, [], "f16d", "M224.1 141c-63.6 0-114.9 51.3-114.9 114.9s51.3 114.9 114.9 114.9S339 319.5 339 255.9 287.7 141 224.1 141zm0 189.6c-41.1 0-74.7-33.5-74.7-74.7s33.5-74.7 74.7-74.7 74.7 33.5 74.7 74.7-33.6 74.7-74.7 74.7zm146.4-194.3c0 14.9-12 26.8-26.8 26.8-14.9 0-26.8-12-26.8-26.8s12-26.8 26.8-26.8 26.8 12 26.8 26.8zm76.1 27.2c-1.7-35.9-9.9-67.7-36.2-93.9-26.2-26.2-58-34.4-93.9-36.2-37-2.1-147.9-2.1-184.9 0-35.8 1.7-67.6 9.9-93.9 36.1s-34.4 58-36.2 93.9c-2.1 37-2.1 147.9 0 184.9 1.7 35.9 9.9 67.7 36.2 93.9s58 34.4 93.9 36.2c37 2.1 147.9 2.1 184.9 0 35.9-1.7 67.7-9.9 93.9-36.2 26.2-26.2 34.4-58 36.2-93.9 2.1-37 2.1-147.8 0-184.8zM398.8 388c-7.8 19.6-22.9 34.7-42.6 42.6-29.5 11.7-99.5 9-132.1 9s-102.7 2.6-132.1-9c-19.6-7.8-34.7-22.9-42.6-42.6-11.7-29.5-9-99.5-9-132.1s-2.6-102.7 9-132.1c7.8-19.6 22.9-34.7 42.6-42.6 29.5-11.7 99.5-9 132.1-9s102.7-2.6 132.1 9c19.6 7.8 34.7 22.9 42.6 42.6 11.7 29.5 9 99.5 9 132.1s2.7 102.7-9 132.1z"],
+ "instagram-square": [448, 512, [], "e055", "M224,202.66A53.34,53.34,0,1,0,277.36,256,53.38,53.38,0,0,0,224,202.66Zm124.71-41a54,54,0,0,0-30.41-30.41c-21-8.29-71-6.43-94.3-6.43s-73.25-1.93-94.31,6.43a54,54,0,0,0-30.41,30.41c-8.28,21-6.43,71.05-6.43,94.33S91,329.26,99.32,350.33a54,54,0,0,0,30.41,30.41c21,8.29,71,6.43,94.31,6.43s73.24,1.93,94.3-6.43a54,54,0,0,0,30.41-30.41c8.35-21,6.43-71.05,6.43-94.33S357.1,182.74,348.75,161.67ZM224,338a82,82,0,1,1,82-82A81.9,81.9,0,0,1,224,338Zm85.38-148.3a19.14,19.14,0,1,1,19.13-19.14A19.1,19.1,0,0,1,309.42,189.74ZM400,32H48A48,48,0,0,0,0,80V432a48,48,0,0,0,48,48H400a48,48,0,0,0,48-48V80A48,48,0,0,0,400,32ZM382.88,322c-1.29,25.63-7.14,48.34-25.85,67s-41.4,24.63-67,25.85c-26.41,1.49-105.59,1.49-132,0-25.63-1.29-48.26-7.15-67-25.85s-24.63-41.42-25.85-67c-1.49-26.42-1.49-105.61,0-132,1.29-25.63,7.07-48.34,25.85-67s41.47-24.56,67-25.78c26.41-1.49,105.59-1.49,132,0,25.63,1.29,48.33,7.15,67,25.85s24.63,41.42,25.85,67.05C384.37,216.44,384.37,295.56,382.88,322Z"],
+ "instalod": [512, 512, [], "e081", "M153.384,480H387.113L502.554,275.765,204.229,333.211ZM504.726,240.078,387.113,32H155.669L360.23,267.9ZM124.386,48.809,7.274,256,123.236,461.154,225.627,165.561Z"],
+ "intercom": [448, 512, [], "f7af", "M392 32H56C25.1 32 0 57.1 0 88v336c0 30.9 25.1 56 56 56h336c30.9 0 56-25.1 56-56V88c0-30.9-25.1-56-56-56zm-108.3 82.1c0-19.8 29.9-19.8 29.9 0v199.5c0 19.8-29.9 19.8-29.9 0V114.1zm-74.6-7.5c0-19.8 29.9-19.8 29.9 0v216.5c0 19.8-29.9 19.8-29.9 0V106.6zm-74.7 7.5c0-19.8 29.9-19.8 29.9 0v199.5c0 19.8-29.9 19.8-29.9 0V114.1zM59.7 144c0-19.8 29.9-19.8 29.9 0v134.3c0 19.8-29.9 19.8-29.9 0V144zm323.4 227.8c-72.8 63-241.7 65.4-318.1 0-15-12.8 4.4-35.5 19.4-22.7 65.9 55.3 216.1 53.9 279.3 0 14.9-12.9 34.3 9.8 19.4 22.7zm5.2-93.5c0 19.8-29.9 19.8-29.9 0V144c0-19.8 29.9-19.8 29.9 0v134.3z"],
+ "internet-explorer": [512, 512, [], "f26b", "M483.049 159.706c10.855-24.575 21.424-60.438 21.424-87.871 0-72.722-79.641-98.371-209.673-38.577-107.632-7.181-211.221 73.67-237.098 186.457 30.852-34.862 78.271-82.298 121.977-101.158C125.404 166.85 79.128 228.002 43.992 291.725 23.246 329.651 0 390.94 0 436.747c0 98.575 92.854 86.5 180.251 42.006 31.423 15.43 66.559 15.573 101.695 15.573 97.124 0 184.249-54.294 216.814-146.022H377.927c-52.509 88.593-196.819 52.996-196.819-47.436H509.9c6.407-43.581-1.655-95.715-26.851-141.162zM64.559 346.877c17.711 51.15 53.703 95.871 100.266 123.304-88.741 48.94-173.267 29.096-100.266-123.304zm115.977-108.873c2-55.151 50.276-94.871 103.98-94.871 53.418 0 101.981 39.72 103.981 94.871H180.536zm184.536-187.6c21.425-10.287 48.563-22.003 72.558-22.003 31.422 0 54.274 21.717 54.274 53.722 0 20.003-7.427 49.007-14.569 67.867-26.28-42.292-65.986-81.584-112.263-99.586z"],
+ "invision": [448, 512, [], "f7b0", "M407.4 32H40.6C18.2 32 0 50.2 0 72.6v366.8C0 461.8 18.2 480 40.6 480h366.8c22.4 0 40.6-18.2 40.6-40.6V72.6c0-22.4-18.2-40.6-40.6-40.6zM176.1 145.6c.4 23.4-22.4 27.3-26.6 27.4-14.9 0-27.1-12-27.1-27 .1-35.2 53.1-35.5 53.7-.4zM332.8 377c-65.6 0-34.1-74-25-106.6 14.1-46.4-45.2-59-59.9.7l-25.8 103.3H177l8.1-32.5c-31.5 51.8-94.6 44.4-94.6-4.3.1-14.3.9-14 23-104.1H81.7l9.7-35.6h76.4c-33.6 133.7-32.6 126.9-32.9 138.2 0 20.9 40.9 13.5 57.4-23.2l19.8-79.4h-32.3l9.7-35.6h68.8l-8.9 40.5c40.5-75.5 127.9-47.8 101.8 38-14.2 51.1-14.6 50.7-14.9 58.8 0 15.5 17.5 22.6 31.8-16.9L386 325c-10.5 36.7-29.4 52-53.2 52z"],
+ "ioxhost": [640, 512, [], "f208", "M616 160h-67.3C511.2 70.7 422.9 8 320 8 183 8 72 119 72 256c0 16.4 1.6 32.5 4.7 48H24c-13.3 0-24 10.8-24 24 0 13.3 10.7 24 24 24h67.3c37.5 89.3 125.8 152 228.7 152 137 0 248-111 248-248 0-16.4-1.6-32.5-4.7-48H616c13.3 0 24-10.8 24-24 0-13.3-10.7-24-24-24zm-96 96c0 110.5-89.5 200-200 200-75.7 0-141.6-42-175.5-104H424c13.3 0 24-10.8 24-24 0-13.3-10.7-24-24-24H125.8c-3.8-15.4-5.8-31.4-5.8-48 0-110.5 89.5-200 200-200 75.7 0 141.6 42 175.5 104H216c-13.3 0-24 10.8-24 24 0 13.3 10.7 24 24 24h298.2c3.8 15.4 5.8 31.4 5.8 48zm-304-24h208c13.3 0 24 10.7 24 24 0 13.2-10.7 24-24 24H216c-13.3 0-24-10.7-24-24 0-13.2 10.7-24 24-24z"],
+ "itch-io": [512, 512, [], "f83a", "M71.92 34.77C50.2 47.67 7.4 96.84 7 109.73v21.34c0 27.06 25.29 50.84 48.25 50.84 27.57 0 50.54-22.85 50.54-50 0 27.12 22.18 50 49.76 50s49-22.85 49-50c0 27.12 23.59 50 51.16 50h.5c27.57 0 51.16-22.85 51.16-50 0 27.12 21.47 50 49 50s49.76-22.85 49.76-50c0 27.12 23 50 50.54 50 23 0 48.25-23.78 48.25-50.84v-21.34c-.4-12.9-43.2-62.07-64.92-75C372.56 32.4 325.76 32 256 32S91.14 33.1 71.92 34.77zm132.32 134.39c-22 38.4-77.9 38.71-99.85.25-13.17 23.14-43.17 32.07-56 27.66-3.87 40.15-13.67 237.13 17.73 269.15 80 18.67 302.08 18.12 379.76 0 31.65-32.27 21.32-232 17.75-269.15-12.92 4.44-42.88-4.6-56-27.66-22 38.52-77.85 38.1-99.85-.24-7.1 12.49-23.05 28.94-51.76 28.94a57.54 57.54 0 0 1-51.75-28.94zm-41.58 53.77c16.47 0 31.09 0 49.22 19.78a436.91 436.91 0 0 1 88.18 0C318.22 223 332.85 223 349.31 223c52.33 0 65.22 77.53 83.87 144.45 17.26 62.15-5.52 63.67-33.95 63.73-42.15-1.57-65.49-32.18-65.49-62.79-39.25 6.43-101.93 8.79-155.55 0 0 30.61-23.34 61.22-65.49 62.79-28.42-.06-51.2-1.58-33.94-63.73 18.67-67 31.56-144.45 83.88-144.45zM256 270.79s-44.38 40.77-52.35 55.21l29-1.17v25.32c0 1.55 21.34.16 23.33.16 11.65.54 23.31 1 23.31-.16v-25.28l29 1.17c-8-14.48-52.35-55.24-52.35-55.24z"],
+ "itunes": [448, 512, [], "f3b4", "M223.6 80.3C129 80.3 52.5 157 52.5 251.5S129 422.8 223.6 422.8s171.2-76.7 171.2-171.2c0-94.6-76.7-171.3-171.2-171.3zm79.4 240c-3.2 13.6-13.5 21.2-27.3 23.8-12.1 2.2-22.2 2.8-31.9-5-11.8-10-12-26.4-1.4-36.8 8.4-8 20.3-9.6 38-12.8 3-.5 5.6-1.2 7.7-3.7 3.2-3.6 2.2-2 2.2-80.8 0-5.6-2.7-7.1-8.4-6.1-4 .7-91.9 17.1-91.9 17.1-5 1.1-6.7 2.6-6.7 8.3 0 116.1.5 110.8-1.2 118.5-2.1 9-7.6 15.8-14.9 19.6-8.3 4.6-23.4 6.6-31.4 5.2-21.4-4-28.9-28.7-14.4-42.9 8.4-8 20.3-9.6 38-12.8 3-.5 5.6-1.2 7.7-3.7 5-5.7.9-127 2.6-133.7.4-2.6 1.5-4.8 3.5-6.4 2.1-1.7 5.8-2.7 6.7-2.7 101-19 113.3-21.4 115.1-21.4 5.7-.4 9 3 9 8.7-.1 170.6.4 161.4-1 167.6zM345.2 32H102.8C45.9 32 0 77.9 0 134.8v242.4C0 434.1 45.9 480 102.8 480h242.4c57 0 102.8-45.9 102.8-102.8V134.8C448 77.9 402.1 32 345.2 32zM223.6 444c-106.3 0-192.5-86.2-192.5-192.5S117.3 59 223.6 59s192.5 86.2 192.5 192.5S329.9 444 223.6 444z"],
+ "itunes-note": [384, 512, [], "f3b5", "M381.9 388.2c-6.4 27.4-27.2 42.8-55.1 48-24.5 4.5-44.9 5.6-64.5-10.2-23.9-20.1-24.2-53.4-2.7-74.4 17-16.2 40.9-19.5 76.8-25.8 6-1.1 11.2-2.5 15.6-7.4 6.4-7.2 4.4-4.1 4.4-163.2 0-11.2-5.5-14.3-17-12.3-8.2 1.4-185.7 34.6-185.7 34.6-10.2 2.2-13.4 5.2-13.4 16.7 0 234.7 1.1 223.9-2.5 239.5-4.2 18.2-15.4 31.9-30.2 39.5-16.8 9.3-47.2 13.4-63.4 10.4-43.2-8.1-58.4-58-29.1-86.6 17-16.2 40.9-19.5 76.8-25.8 6-1.1 11.2-2.5 15.6-7.4 10.1-11.5 1.8-256.6 5.2-270.2.8-5.2 3-9.6 7.1-12.9 4.2-3.5 11.8-5.5 13.4-5.5 204-38.2 228.9-43.1 232.4-43.1 11.5-.8 18.1 6 18.1 17.6.2 344.5 1.1 326-1.8 338.5z"],
+ "java": [384, 512, [], "f4e4", "M277.74 312.9c9.8-6.7 23.4-12.5 23.4-12.5s-38.7 7-77.2 10.2c-47.1 3.9-97.7 4.7-123.1 1.3-60.1-8 33-30.1 33-30.1s-36.1-2.4-80.6 19c-52.5 25.4 130 37 224.5 12.1zm-85.4-32.1c-19-42.7-83.1-80.2 0-145.8C296 53.2 242.84 0 242.84 0c21.5 84.5-75.6 110.1-110.7 162.6-23.9 35.9 11.7 74.4 60.2 118.2zm114.6-176.2c.1 0-175.2 43.8-91.5 140.2 24.7 28.4-6.5 54-6.5 54s62.7-32.4 33.9-72.9c-26.9-37.8-47.5-56.6 64.1-121.3zm-6.1 270.5a12.19 12.19 0 0 1-2 2.6c128.3-33.7 81.1-118.9 19.8-97.3a17.33 17.33 0 0 0-8.2 6.3 70.45 70.45 0 0 1 11-3c31-6.5 75.5 41.5-20.6 91.4zM348 437.4s14.5 11.9-15.9 21.2c-57.9 17.5-240.8 22.8-291.6.7-18.3-7.9 16-19 26.8-21.3 11.2-2.4 17.7-2 17.7-2-20.3-14.3-131.3 28.1-56.4 40.2C232.84 509.4 401 461.3 348 437.4zM124.44 396c-78.7 22 47.9 67.4 148.1 24.5a185.89 185.89 0 0 1-28.2-13.8c-44.7 8.5-65.4 9.1-106 4.5-33.5-3.8-13.9-15.2-13.9-15.2zm179.8 97.2c-78.7 14.8-175.8 13.1-233.3 3.6 0-.1 11.8 9.7 72.4 13.6 92.2 5.9 233.8-3.3 237.1-46.9 0 0-6.4 16.5-76.2 29.7zM260.64 353c-59.2 11.4-93.5 11.1-136.8 6.6-33.5-3.5-11.6-19.7-11.6-19.7-86.8 28.8 48.2 61.4 169.5 25.9a60.37 60.37 0 0 1-21.1-12.8z"],
+ "jedi-order": [448, 512, [], "f50e", "M398.5 373.6c95.9-122.1 17.2-233.1 17.2-233.1 45.4 85.8-41.4 170.5-41.4 170.5 105-171.5-60.5-271.5-60.5-271.5 96.9 72.7-10.1 190.7-10.1 190.7 85.8 158.4-68.6 230.1-68.6 230.1s-.4-16.9-2.2-85.7c4.3 4.5 34.5 36.2 34.5 36.2l-24.2-47.4 62.6-9.1-62.6-9.1 20.2-55.5-31.4 45.9c-2.2-87.7-7.8-305.1-7.9-306.9v-2.4 1-1 2.4c0 1-5.6 219-7.9 306.9l-31.4-45.9 20.2 55.5-62.6 9.1 62.6 9.1-24.2 47.4 34.5-36.2c-1.8 68.8-2.2 85.7-2.2 85.7s-154.4-71.7-68.6-230.1c0 0-107-118.1-10.1-190.7 0 0-165.5 99.9-60.5 271.5 0 0-86.8-84.8-41.4-170.5 0 0-78.7 111 17.2 233.1 0 0-26.2-16.1-49.4-77.7 0 0 16.9 183.3 222 185.7h4.1c205-2.4 222-185.7 222-185.7-23.6 61.5-49.9 77.7-49.9 77.7z"],
+ "jenkins": [512, 512, [], "f3b6", "M487.1 425c-1.4-11.2-19-23.1-28.2-31.9-5.1-5-29-23.1-30.4-29.9-1.4-6.6 9.7-21.5 13.3-28.9 5.1-10.7 8.8-23.7 11.3-32.6 18.8-66.1 20.7-156.9-6.2-211.2-10.2-20.6-38.6-49-56.4-62.5-42-31.7-119.6-35.3-170.1-16.6-14.1 5.2-27.8 9.8-40.1 17.1-33.1 19.4-68.3 32.5-78.1 71.6-24.2 10.8-31.5 41.8-30.3 77.8.2 7 4.1 15.8 2.7 22.4-.7 3.3-5.2 7.6-6.1 9.8-11.6 27.7-2.3 64 11.1 83.7 8.1 11.9 21.5 22.4 39.2 25.2.7 10.6 3.3 19.7 8.2 30.4 3.1 6.8 14.7 19 10.4 27.7-2.2 4.4-21 13.8-27.3 17.6C89 407.2 73.7 415 54.2 429c-12.6 9-32.3 10.2-29.2 31.1 2.1 14.1 10.1 31.6 14.7 45.8.7 2 1.4 4.1 2.1 6h422c4.9-15.3 9.7-30.9 14.6-47.2 3.4-11.4 10.2-27.8 8.7-39.7zM205.9 33.7c1.8-.5 3.4.7 4.9 2.4-.2 5.2-5.4 5.1-8.9 6.8-5.4 6.7-13.4 9.8-20 17.2-6.8 7.5-14.4 27.7-23.4 30-4.5 1.1-9.7-.8-13.6-.5-10.4.7-17.7 6-28.3 7.5 13.6-29.9 56.1-54 89.3-63.4zm-104.8 93.6c13.5-14.9 32.1-24.1 54.8-25.9 11.7 29.7-8.4 65-.9 97.6 2.3 9.9 10.2 25.4-2.4 25.7.3-28.3-34.8-46.3-61.3-29.6-1.8-21.5-4.9-51.7 9.8-67.8zm36.7 200.2c-1-4.1-2.7-12.9-2.3-15.1 1.6-8.7 17.1-12.5 11-24.7-11.3-.1-13.8 10.2-24.1 11.3-26.7 2.6-45.6-35.4-44.4-58.4 1-19.5 17.6-38.2 40.1-35.8 16 1.8 21.4 19.2 24.5 34.7 9.2.5 22.5-.4 26.9-7.6-.6-17.5-8.8-31.6-8.2-47.7 1-30.3 17.5-57.6 4.8-87.4 13.6-30.9 53.5-55.3 83.1-70 36.6-18.3 94.9-3.7 129.3 15.8 19.7 11.1 34.4 32.7 48.3 50.7-19.5-5.8-36.1 4.2-33.1 20.3 16.3-14.9 44.2-.2 52.5 16.4 7.9 15.8 7.8 39.3 9 62.8 2.9 57-10.4 115.9-39.1 157.1-7.7 11-14.1 23-24.9 30.6-26 18.2-65.4 34.7-99.2 23.4-44.7-15-65-44.8-89.5-78.8.7 18.7 13.8 34.1 26.8 48.4 11.3 12.5 25 26.6 39.7 32.4-12.3-2.9-31.1-3.8-36.2 7.2-28.6-1.9-55.1-4.8-68.7-24.2-10.6-15.4-21.4-41.4-26.3-61.4zm222 124.1c4.1-3 11.1-2.9 17.4-3.6-5.4-2.7-13-3.7-19.3-2.2-.1-4.2-2-6.8-3.2-10.2 10.6-3.8 35.5-28.5 49.6-20.3 6.7 3.9 9.5 26.2 10.1 37 .4 9-.8 18-4.5 22.8-18.8-.6-35.8-2.8-50.7-7 .9-6.1-1-12.1.6-16.5zm-17.2-20c-16.8.8-26-1.2-38.3-10.8.2-.8 1.4-.5 1.5-1.4 18 8 40.8-3.3 59-4.9-7.9 5.1-14.6 11.6-22.2 17.1zm-12.1 33.2c-1.6-9.4-3.5-12-2.8-20.2 25-16.6 29.7 28.6 2.8 20.2zM226 438.6c-11.6-.7-48.1-14-38.5-23.7 9.4 6.5 27.5 4.9 41.3 7.3.8 4.4-2.8 10.2-2.8 16.4zM57.7 497.1c-4.3-12.7-9.2-25.1-14.8-36.9 30.8-23.8 65.3-48.9 102.2-63.5 2.8-1.1 23.2 25.4 26.2 27.6 16.5 11.7 37 21 56.2 30.2 1.2 8.8 3.9 20.2 8.7 35.5.7 2.3 1.4 4.7 2.2 7.2H57.7zm240.6 5.7h-.8c.3-.2.5-.4.8-.5v.5zm7.5-5.7c2.1-1.4 4.3-2.8 6.4-4.3 1.1 1.4 2.2 2.8 3.2 4.3h-9.6zm15.1-24.7c-10.8 7.3-20.6 18.3-33.3 25.2-6 3.3-27 11.7-33.4 10.2-3.6-.8-3.9-5.3-5.4-9.5-3.1-9-10.1-23.4-10.8-37-.8-17.2-2.5-46 16-42.4 14.9 2.9 32.3 9.7 43.9 16.1 7.1 3.9 11.1 8.6 21.9 9.5-.1 1.4-.1 2.8-.2 4.3-5.9 3.9-15.3 3.8-21.8 7.1 9.5.4 17 2.7 23.5 5.9-.1 3.4-.3 7-.4 10.6zm53.4 24.7h-14c-.1-3.2-2.8-5.8-6.1-5.8s-5.9 2.6-6.1 5.8h-17.4c-2.8-4.4-5.7-8.6-8.9-12.5 2.1-2.2 4-4.7 6-6.9 9 3.7 14.8-4.9 21.7-4.2 7.9.8 14.2 11.7 25.4 11l-.6 12.6zm8.7 0c.2-4 .4-7.8.6-11.5 15.6-7.3 29 1.3 35.7 11.5H383zm83.4-37c-2.3 11.2-5.8 24-9.9 37.1-.2-.1-.4-.1-.6-.1H428c.6-1.1 1.2-2.2 1.9-3.3-2.6-6.1-9-8.7-10.9-15.5 12.1-22.7 6.5-93.4-24.2-78.5 4.3-6.3 15.6-11.5 20.8-19.3 13 10.4 20.8 20.3 33.2 31.4 6.8 6 20 13.3 21.4 23.1.8 5.5-2.6 18.9-3.8 25.1zM222.2 130.5c5.4-14.9 27.2-34.7 45-32 7.7 1.2 18 8.2 12.2 17.7-30.2-7-45.2 12.6-54.4 33.1-8.1-2-4.9-13.1-2.8-18.8zm184.1 63.1c8.2-3.6 22.4-.7 29.6-5.3-4.2-11.5-10.3-21.4-9.3-37.7.5 0 1 0 1.4.1 6.8 14.2 12.7 29.2 21.4 41.7-5.7 13.5-43.6 25.4-43.1 1.2zm20.4-43zm-117.2 45.7c-6.8-10.9-19-32.5-14.5-45.3 6.5 11.9 8.6 24.4 17.8 33.3 4.1 4 12.2 9 8.2 20.2-.9 2.7-7.8 8.6-11.7 9.7-14.4 4.3-47.9.9-36.6-17.1 11.9.7 27.9 7.8 36.8-.8zm27.3 70c3.8 6.6 1.4 18.7 12.1 20.6 20.2 3.4 43.6-12.3 58.1-17.8 9-15.2-.8-20.7-8.9-30.5-16.6-20-38.8-44.8-38-74.7 6.7-4.9 7.3 7.4 8.2 9.7 8.7 20.3 30.4 46.2 46.3 63.5 3.9 4.3 10.3 8.4 11 11.2 2.1 8.2-5.4 18-4.5 23.5-21.7 13.9-45.8 29.1-81.4 25.6-7.4-6.7-10.3-21.4-2.9-31.1zm-201.3-9.2c-6.8-3.9-8.4-21-16.4-21.4-11.4-.7-9.3 22.2-9.3 35.5-7.8-7.1-9.2-29.1-3.5-40.3-6.6-3.2-9.5 3.6-13.1 5.9 4.7-34.1 49.8-15.8 42.3 20.3zm299.6 28.8c-10.1 19.2-24.4 40.4-54 41-.6-6.2-1.1-15.6 0-19.4 22.7-2.2 36.6-13.7 54-21.6zm-141.9 12.4c18.9 9.9 53.6 11 79.3 10.2 1.4 5.6 1.3 12.6 1.4 19.4-33 1.8-72-6.4-80.7-29.6zm92.2 46.7c-1.7 4.3-5.3 9.3-9.8 11.1-12.1 4.9-45.6 8.7-62.4-.3-10.7-5.7-17.5-18.5-23.4-26-2.8-3.6-16.9-12.9-.2-12.9 13.1 32.7 58 29 95.8 28.1z"],
+ "jira": [496, 512, [], "f7b1", "M490 241.7C417.1 169 320.6 71.8 248.5 0 83 164.9 6 241.7 6 241.7c-7.9 7.9-7.9 20.7 0 28.7C138.8 402.7 67.8 331.9 248.5 512c379.4-378 15.7-16.7 241.5-241.7 8-7.9 8-20.7 0-28.6zm-241.5 90l-76-75.7 76-75.7 76 75.7-76 75.7z"],
+ "joget": [496, 512, [], "f3b7", "M378.1 45C337.6 19.9 292.6 8 248.2 8 165 8 83.8 49.9 36.9 125.9c-71.9 116.6-35.6 269.3 81 341.2s269.3 35.6 341.2-80.9c71.9-116.6 35.6-269.4-81-341.2zm51.8 323.2c-40.4 65.5-110.4 101.5-182 101.5-6.8 0-13.6-.4-20.4-1-9-13.6-19.9-33.3-23.7-42.4-5.7-13.7-27.2-45.6 31.2-67.1 51.7-19.1 176.7-16.5 208.8-17.6-4 9-8.6 17.9-13.9 26.6zm-200.8-86.3c-55.5-1.4-81.7-20.8-58.5-48.2s51.1-40.7 68.9-51.2c17.9-10.5 27.3-33.7-23.6-29.7C87.3 161.5 48.6 252.1 37.6 293c-8.8-49.7-.1-102.7 28.5-149.1C128 43.4 259.6 12.2 360.1 74.1c74.8 46.1 111.2 130.9 99.3 212.7-24.9-.5-179.3-3.6-230.3-4.9zm183.8-54.8c-22.7-6-57 11.3-86.7 27.2-29.7 15.8-31.1 8.2-31.1 8.2s40.2-28.1 50.7-34.5 31.9-14 13.4-24.6c-3.2-1.8-6.7-2.7-10.4-2.7-17.8 0-41.5 18.7-67.5 35.6-31.5 20.5-65.3 31.3-65.3 31.3l169.5-1.6 46.5-23.4s3.6-9.5-19.1-15.5z"],
+ "joomla": [448, 512, [], "f1aa", "M.6 92.1C.6 58.8 27.4 32 60.4 32c30 0 54.5 21.9 59.2 50.2 32.6-7.6 67.1.6 96.5 30l-44.3 44.3c-20.5-20.5-42.6-16.3-55.4-3.5-14.3 14.3-14.3 37.9 0 52.2l99.5 99.5-44 44.3c-87.7-87.2-49.7-49.7-99.8-99.7-26.8-26.5-35-64.8-24.8-98.9C20.4 144.6.6 120.7.6 92.1zm129.5 116.4l44.3 44.3c10-10 89.7-89.7 99.7-99.8 14.3-14.3 37.6-14.3 51.9 0 12.8 12.8 17 35-3.5 55.4l44 44.3c31.2-31.2 38.5-67.6 28.9-101.2 29.2-4.1 51.9-29.2 51.9-59.5 0-33.2-26.8-60.1-59.8-60.1-30.3 0-55.4 22.5-59.5 51.6-33.8-9.9-71.7-1.5-98.3 25.1-18.3 19.1-71.1 71.5-99.6 99.9zm266.3 152.2c8.2-32.7-.9-68.5-26.3-93.9-11.8-12.2 5 4.7-99.5-99.7l-44.3 44.3 99.7 99.7c14.3 14.3 14.3 37.6 0 51.9-12.8 12.8-35 17-55.4-3.5l-44 44.3c27.6 30.2 68 38.8 102.7 28 5.5 27.4 29.7 48.1 58.9 48.1 33 0 59.8-26.8 59.8-60.1 0-30.2-22.5-55-51.6-59.1zm-84.3-53.1l-44-44.3c-87 86.4-50.4 50.4-99.7 99.8-14.3 14.3-37.6 14.3-51.9 0-13.1-13.4-16.9-35.3 3.2-55.4l-44-44.3c-30.2 30.2-38 65.2-29.5 98.3-26.7 6-46.2 29.9-46.2 58.2C0 453.2 26.8 480 59.8 480c28.6 0 52.5-19.8 58.6-46.7 32.7 8.2 68.5-.6 94.2-26 32.1-32 12.2-12.4 99.5-99.7z"],
+ "js": [448, 512, [], "f3b8", "M0 32v448h448V32H0zm243.8 349.4c0 43.6-25.6 63.5-62.9 63.5-33.7 0-53.2-17.4-63.2-38.5l34.3-20.7c6.6 11.7 12.6 21.6 27.1 21.6 13.8 0 22.6-5.4 22.6-26.5V237.7h42.1v143.7zm99.6 63.5c-39.1 0-64.4-18.6-76.7-43l34.3-19.8c9 14.7 20.8 25.6 41.5 25.6 17.4 0 28.6-8.7 28.6-20.8 0-14.4-11.4-19.5-30.7-28l-10.5-4.5c-30.4-12.9-50.5-29.2-50.5-63.5 0-31.6 24.1-55.6 61.6-55.6 26.8 0 46 9.3 59.8 33.7L368 290c-7.2-12.9-15-18-27.1-18-12.3 0-20.1 7.8-20.1 18 0 12.6 7.8 17.7 25.9 25.6l10.5 4.5c35.8 15.3 55.9 31 55.9 66.2 0 37.8-29.8 58.6-69.7 58.6z"],
+ "js-square": [448, 512, [], "f3b9", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM243.8 381.4c0 43.6-25.6 63.5-62.9 63.5-33.7 0-53.2-17.4-63.2-38.5l34.3-20.7c6.6 11.7 12.6 21.6 27.1 21.6 13.8 0 22.6-5.4 22.6-26.5V237.7h42.1v143.7zm99.6 63.5c-39.1 0-64.4-18.6-76.7-43l34.3-19.8c9 14.7 20.8 25.6 41.5 25.6 17.4 0 28.6-8.7 28.6-20.8 0-14.4-11.4-19.5-30.7-28l-10.5-4.5c-30.4-12.9-50.5-29.2-50.5-63.5 0-31.6 24.1-55.6 61.6-55.6 26.8 0 46 9.3 59.8 33.7L368 290c-7.2-12.9-15-18-27.1-18-12.3 0-20.1 7.8-20.1 18 0 12.6 7.8 17.7 25.9 25.6l10.5 4.5c35.8 15.3 55.9 31 55.9 66.2 0 37.8-29.8 58.6-69.7 58.6z"],
+ "jsfiddle": [576, 512, [], "f1cc", "M510.634 237.462c-4.727-2.621-5.664-5.748-6.381-10.776-2.352-16.488-3.539-33.619-9.097-49.095-35.895-99.957-153.99-143.386-246.849-91.646-27.37 15.25-48.971 36.369-65.493 63.903-3.184-1.508-5.458-2.71-7.824-3.686-30.102-12.421-59.049-10.121-85.331 9.167-25.531 18.737-36.422 44.548-32.676 76.408.355 3.025-1.967 7.621-4.514 9.545-39.712 29.992-56.031 78.065-41.902 124.615 13.831 45.569 57.514 79.796 105.608 81.433 30.291 1.031 60.637.546 90.959.539 84.041-.021 168.09.531 252.12-.48 52.664-.634 96.108-36.873 108.212-87.293 11.54-48.074-11.144-97.3-56.832-122.634zm21.107 156.88c-18.23 22.432-42.343 35.253-71.28 35.65-56.874.781-113.767.23-170.652.23 0 .7-163.028.159-163.728.154-43.861-.332-76.739-19.766-95.175-59.995-18.902-41.245-4.004-90.848 34.186-116.106 9.182-6.073 12.505-11.566 10.096-23.136-5.49-26.361 4.453-47.956 26.42-62.981 22.987-15.723 47.422-16.146 72.034-3.083 10.269 5.45 14.607 11.564 22.198-2.527 14.222-26.399 34.557-46.727 60.671-61.294 97.46-54.366 228.37 7.568 230.24 132.697.122 8.15 2.412 12.428 9.848 15.894 57.56 26.829 74.456 96.122 35.142 144.497zm-87.789-80.499c-5.848 31.157-34.622 55.096-66.666 55.095-16.953-.001-32.058-6.545-44.079-17.705-27.697-25.713-71.141-74.98-95.937-93.387-20.056-14.888-41.99-12.333-60.272 3.782-49.996 44.071 15.859 121.775 67.063 77.188 4.548-3.96 7.84-9.543 12.744-12.844 8.184-5.509 20.766-.884 13.168 10.622-17.358 26.284-49.33 38.197-78.863 29.301-28.897-8.704-48.84-35.968-48.626-70.179 1.225-22.485 12.364-43.06 35.414-55.965 22.575-12.638 46.369-13.146 66.991 2.474C295.68 280.7 320.467 323.97 352.185 343.47c24.558 15.099 54.254 7.363 68.823-17.506 28.83-49.209-34.592-105.016-78.868-63.46-3.989 3.744-6.917 8.932-11.41 11.72-10.975 6.811-17.333-4.113-12.809-10.353 20.703-28.554 50.464-40.44 83.271-28.214 31.429 11.714 49.108 44.366 42.76 78.186z"],
+ "kaggle": [320, 512, [], "f5fa", "M304.2 501.5L158.4 320.3 298.2 185c2.6-2.7 1.7-10.5-5.3-10.5h-69.2c-3.5 0-7 1.8-10.5 5.3L80.9 313.5V7.5q0-7.5-7.5-7.5H21.5Q14 0 14 7.5v497q0 7.5 7.5 7.5h51.9q7.5 0 7.5-7.5v-109l30.8-29.3 110.5 140.6c3 3.5 6.5 5.3 10.5 5.3h66.9q5.25 0 6-3z"],
+ "keybase": [448, 512, [], "f4f5", "M286.17 419a18 18 0 1 0 18 18 18 18 0 0 0-18-18zm111.92-147.6c-9.5-14.62-39.37-52.45-87.26-73.71q-9.1-4.06-18.38-7.27a78.43 78.43 0 0 0-47.88-104.13c-12.41-4.1-23.33-6-32.41-5.77-.6-2-1.89-11 9.4-35L198.66 32l-5.48 7.56c-8.69 12.06-16.92 23.55-24.34 34.89a51 51 0 0 0-8.29-1.25c-41.53-2.45-39-2.33-41.06-2.33-50.61 0-50.75 52.12-50.75 45.88l-2.36 36.68c-1.61 27 19.75 50.21 47.63 51.85l8.93.54a214 214 0 0 0-46.29 35.54C14 304.66 14 374 14 429.77v33.64l23.32-29.8a148.6 148.6 0 0 0 14.56 37.56c5.78 10.13 14.87 9.45 19.64 7.33 4.21-1.87 10-6.92 3.75-20.11a178.29 178.29 0 0 1-15.76-53.13l46.82-59.83-24.66 74.11c58.23-42.4 157.38-61.76 236.25-38.59 34.2 10.05 67.45.69 84.74-23.84.72-1 1.2-2.16 1.85-3.22a156.09 156.09 0 0 1 2.8 28.43c0 23.3-3.69 52.93-14.88 81.64-2.52 6.46 1.76 14.5 8.6 15.74 7.42 1.57 15.33-3.1 18.37-11.15C429 443 434 414 434 382.32c0-38.58-13-77.46-35.91-110.92zM142.37 128.58l-15.7-.93-1.39 21.79 13.13.78a93 93 0 0 0 .32 19.57l-22.38-1.34a12.28 12.28 0 0 1-11.76-12.79L107 119c1-12.17 13.87-11.27 13.26-11.32l29.11 1.73a144.35 144.35 0 0 0-7 19.17zm148.42 172.18a10.51 10.51 0 0 1-14.35-1.39l-9.68-11.49-34.42 27a8.09 8.09 0 0 1-11.13-1.08l-15.78-18.64a7.38 7.38 0 0 1 1.34-10.34l34.57-27.18-14.14-16.74-17.09 13.45a7.75 7.75 0 0 1-10.59-1s-3.72-4.42-3.8-4.53a7.38 7.38 0 0 1 1.37-10.34L214 225.19s-18.51-22-18.6-22.14a9.56 9.56 0 0 1 1.74-13.42 10.38 10.38 0 0 1 14.3 1.37l81.09 96.32a9.58 9.58 0 0 1-1.74 13.44zM187.44 419a18 18 0 1 0 18 18 18 18 0 0 0-18-18z"],
+ "keycdn": [512, 512, [], "f3ba", "M63.8 409.3l60.5-59c32.1 42.8 71.1 66 126.6 67.4 30.5.7 60.3-7 86.4-22.4 5.1 5.3 18.5 19.5 20.9 22-32.2 20.7-69.6 31.1-108.1 30.2-43.3-1.1-84.6-16.7-117.7-44.4.3-.6-38.2 37.5-38.6 37.9 9.5 29.8-13.1 62.4-46.3 62.4C20.7 503.3 0 481.7 0 454.9c0-34.3 33.1-56.6 63.8-45.6zm354.9-252.4c19.1 31.3 29.6 67.4 28.7 104-1.1 44.8-19 87.5-48.6 121 .3.3 23.8 25.2 24.1 25.5 9.6-1.3 19.2 2 25.9 9.1 11.3 12 10.9 30.9-1.1 42.4-12 11.3-30.9 10.9-42.4-1.1-6.7-7-9.4-16.8-7.6-26.3-24.9-26.6-44.4-47.2-44.4-47.2 42.7-34.1 63.3-79.6 64.4-124.2.7-28.9-7.2-57.2-21.1-82.2l22.1-21zM104 53.1c6.7 7 9.4 16.8 7.6 26.3l45.9 48.1c-4.7 3.8-13.3 10.4-22.8 21.3-25.4 28.5-39.6 64.8-40.7 102.9-.7 28.9 6.1 57.2 20 82.4l-22 21.5C72.7 324 63.1 287.9 64.2 250.9c1-44.6 18.3-87.6 47.5-121.1l-25.3-26.4c-9.6 1.3-19.2-2-25.9-9.1-11.3-12-10.9-30.9 1.1-42.4C73.5 40.7 92.2 41 104 53.1zM464.9 8c26 0 47.1 22.4 47.1 48.3S490.9 104 464.9 104c-6.3.1-14-1.1-15.9-1.8l-62.9 59.7c-32.7-43.6-76.7-65.9-126.9-67.2-30.5-.7-60.3 6.8-86.2 22.4l-21.1-22C184.1 74.3 221.5 64 260 64.9c43.3 1.1 84.6 16.7 117.7 44.6l41.1-38.6c-1.5-4.7-2.2-9.6-2.2-14.5C416.5 29.7 438.9 8 464.9 8zM256.7 113.4c5.5 0 10.9.4 16.4 1.1 78.1 9.8 133.4 81.1 123.8 159.1-9.8 78.1-81.1 133.4-159.1 123.8-78.1-9.8-133.4-81.1-123.8-159.2 9.3-72.4 70.1-124.6 142.7-124.8zm-59 119.4c.6 22.7 12.2 41.8 32.4 52.2l-11 51.7h73.7l-11-51.7c20.1-10.9 32.1-29 32.4-52.2-.4-32.8-25.8-57.5-58.3-58.3-32.1.8-57.3 24.8-58.2 58.3zM256 160"],
+ "kickstarter": [448, 512, [], "f3bb", "M400 480H48c-26.4 0-48-21.6-48-48V80c0-26.4 21.6-48 48-48h352c26.4 0 48 21.6 48 48v352c0 26.4-21.6 48-48 48zM199.6 178.5c0-30.7-17.6-45.1-39.7-45.1-25.8 0-40 19.8-40 44.5v154.8c0 25.8 13.7 45.6 40.5 45.6 21.5 0 39.2-14 39.2-45.6v-41.8l60.6 75.7c12.3 14.9 39 16.8 55.8 0 14.6-15.1 14.8-36.8 4-50.4l-49.1-62.8 40.5-58.7c9.4-13.5 9.5-34.5-5.6-49.1-16.4-15.9-44.6-17.3-61.4 7l-44.8 64.7v-38.8z"],
+ "kickstarter-k": [384, 512, [], "f3bc", "M147.3 114.4c0-56.2-32.5-82.4-73.4-82.4C26.2 32 0 68.2 0 113.4v283c0 47.3 25.3 83.4 74.9 83.4 39.8 0 72.4-25.6 72.4-83.4v-76.5l112.1 138.3c22.7 27.2 72.1 30.7 103.2 0 27-27.6 27.3-67.4 7.4-92.2l-90.8-114.8 74.9-107.4c17.4-24.7 17.5-63.1-10.4-89.8-30.3-29-82.4-31.6-113.6 12.8L147.3 185v-70.6z"],
+ "korvue": [446, 512, [], "f42f", "M386.5 34h-327C26.8 34 0 60.8 0 93.5v327.1C0 453.2 26.8 480 59.5 480h327.1c33 0 59.5-26.8 59.5-59.5v-327C446 60.8 419.2 34 386.5 34zM87.1 120.8h96v116l61.8-116h110.9l-81.2 132H87.1v-132zm161.8 272.1l-65.7-113.6v113.6h-96V262.1h191.5l88.6 130.8H248.9z"],
+ "laravel": [512, 512, [], "f3bd", "M504.4,115.83a5.72,5.72,0,0,0-.28-.68,8.52,8.52,0,0,0-.53-1.25,6,6,0,0,0-.54-.71,9.36,9.36,0,0,0-.72-.94c-.23-.22-.52-.4-.77-.6a8.84,8.84,0,0,0-.9-.68L404.4,55.55a8,8,0,0,0-8,0L300.12,111h0a8.07,8.07,0,0,0-.88.69,7.68,7.68,0,0,0-.78.6,8.23,8.23,0,0,0-.72.93c-.17.24-.39.45-.54.71a9.7,9.7,0,0,0-.52,1.25c-.08.23-.21.44-.28.68a8.08,8.08,0,0,0-.28,2.08V223.18l-80.22,46.19V63.44a7.8,7.8,0,0,0-.28-2.09c-.06-.24-.2-.45-.28-.68a8.35,8.35,0,0,0-.52-1.24c-.14-.26-.37-.47-.54-.72a9.36,9.36,0,0,0-.72-.94,9.46,9.46,0,0,0-.78-.6,9.8,9.8,0,0,0-.88-.68h0L115.61,1.07a8,8,0,0,0-8,0L11.34,56.49h0a6.52,6.52,0,0,0-.88.69,7.81,7.81,0,0,0-.79.6,8.15,8.15,0,0,0-.71.93c-.18.25-.4.46-.55.72a7.88,7.88,0,0,0-.51,1.24,6.46,6.46,0,0,0-.29.67,8.18,8.18,0,0,0-.28,2.1v329.7a8,8,0,0,0,4,6.95l192.5,110.84a8.83,8.83,0,0,0,1.33.54c.21.08.41.2.63.26a7.92,7.92,0,0,0,4.1,0c.2-.05.37-.16.55-.22a8.6,8.6,0,0,0,1.4-.58L404.4,400.09a8,8,0,0,0,4-6.95V287.88l92.24-53.11a8,8,0,0,0,4-7V117.92A8.63,8.63,0,0,0,504.4,115.83ZM111.6,17.28h0l80.19,46.15-80.2,46.18L31.41,63.44Zm88.25,60V278.6l-46.53,26.79-33.69,19.4V123.5l46.53-26.79Zm0,412.78L23.37,388.5V77.32L57.06,96.7l46.52,26.8V338.68a6.94,6.94,0,0,0,.12.9,8,8,0,0,0,.16,1.18h0a5.92,5.92,0,0,0,.38.9,6.38,6.38,0,0,0,.42,1v0a8.54,8.54,0,0,0,.6.78,7.62,7.62,0,0,0,.66.84l0,0c.23.22.52.38.77.58a8.93,8.93,0,0,0,.86.66l0,0,0,0,92.19,52.18Zm8-106.17-80.06-45.32,84.09-48.41,92.26-53.11,80.13,46.13-58.8,33.56Zm184.52,4.57L215.88,490.11V397.8L346.6,323.2l45.77-26.15Zm0-119.13L358.68,250l-46.53-26.79V131.79l33.69,19.4L392.37,178Zm8-105.28-80.2-46.17,80.2-46.16,80.18,46.15Zm8,105.28V178L455,151.19l33.68-19.4v91.39h0Z"],
+ "lastfm": [512, 512, [], "f202", "M225.8 367.1l-18.8-51s-30.5 34-76.2 34c-40.5 0-69.2-35.2-69.2-91.5 0-72.1 36.4-97.9 72.1-97.9 66.5 0 74.8 53.3 100.9 134.9 18.8 56.9 54 102.6 155.4 102.6 72.7 0 122-22.3 122-80.9 0-72.9-62.7-80.6-115-92.1-25.8-5.9-33.4-16.4-33.4-34 0-19.9 15.8-31.7 41.6-31.7 28.2 0 43.4 10.6 45.7 35.8l58.6-7c-4.7-52.8-41.1-74.5-100.9-74.5-52.8 0-104.4 19.9-104.4 83.9 0 39.9 19.4 65.1 68 76.8 44.9 10.6 79.8 13.8 79.8 45.7 0 21.7-21.1 30.5-61 30.5-59.2 0-83.9-31.1-97.9-73.9-32-96.8-43.6-163-161.3-163C45.7 113.8 0 168.3 0 261c0 89.1 45.7 137.2 127.9 137.2 66.2 0 97.9-31.1 97.9-31.1z"],
+ "lastfm-square": [448, 512, [], "f203", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-92.2 312.9c-63.4 0-85.4-28.6-97.1-64.1-16.3-51-21.5-84.3-63-84.3-22.4 0-45.1 16.1-45.1 61.2 0 35.2 18 57.2 43.3 57.2 28.6 0 47.6-21.3 47.6-21.3l11.7 31.9s-19.8 19.4-61.2 19.4c-51.3 0-79.9-30.1-79.9-85.8 0-57.9 28.6-92 82.5-92 73.5 0 80.8 41.4 100.8 101.9 8.8 26.8 24.2 46.2 61.2 46.2 24.9 0 38.1-5.5 38.1-19.1 0-19.9-21.8-22-49.9-28.6-30.4-7.3-42.5-23.1-42.5-48 0-40 32.3-52.4 65.2-52.4 37.4 0 60.1 13.6 63 46.6l-36.7 4.4c-1.5-15.8-11-22.4-28.6-22.4-16.1 0-26 7.3-26 19.8 0 11 4.8 17.6 20.9 21.3 32.7 7.1 71.8 12 71.8 57.5.1 36.7-30.7 50.6-76.1 50.6z"],
+ "leanpub": [576, 512, [], "f212", "M386.539 111.485l15.096 248.955-10.979-.275c-36.232-.824-71.64 8.783-102.657 27.997-31.016-19.214-66.424-27.997-102.657-27.997-45.564 0-82.07 10.705-123.516 27.723L93.117 129.6c28.546-11.803 61.484-18.115 92.226-18.115 41.173 0 73.836 13.175 102.657 42.544 27.723-28.271 59.013-41.721 98.539-42.544zM569.07 448c-25.526 0-47.485-5.215-70.542-15.645-34.31-15.645-69.993-24.978-107.871-24.978-38.977 0-74.934 12.901-102.657 40.623-27.723-27.723-63.68-40.623-102.657-40.623-37.878 0-73.561 9.333-107.871 24.978C55.239 442.236 32.731 448 8.303 448H6.93L49.475 98.859C88.726 76.626 136.486 64 181.775 64 218.83 64 256.984 71.685 288 93.095 319.016 71.685 357.17 64 394.225 64c45.289 0 93.049 12.626 132.3 34.859L569.07 448zm-43.368-44.741l-34.036-280.246c-30.742-13.999-67.248-21.41-101.009-21.41-38.428 0-74.385 12.077-102.657 38.702-28.272-26.625-64.228-38.702-102.657-38.702-33.761 0-70.267 7.411-101.009 21.41L50.298 403.259c47.211-19.487 82.894-33.486 135.045-33.486 37.604 0 70.817 9.606 102.657 29.644 31.84-20.038 65.052-29.644 102.657-29.644 52.151 0 87.834 13.999 135.045 33.486z"],
+ "less": [640, 512, [], "f41d", "M612.7 219c0-20.5 3.2-32.6 3.2-54.6 0-34.2-12.6-45.2-40.5-45.2h-20.5v24.2h6.3c14.2 0 17.3 4.7 17.3 22.1 0 16.3-1.6 32.6-1.6 51.5 0 24.2 7.9 33.6 23.6 37.3v1.6c-15.8 3.7-23.6 13.1-23.6 37.3 0 18.9 1.6 34.2 1.6 51.5 0 17.9-3.7 22.6-17.3 22.6v.5h-6.3V393h20.5c27.8 0 40.5-11 40.5-45.2 0-22.6-3.2-34.2-3.2-54.6 0-11 6.8-22.6 27.3-23.6v-27.3c-20.5-.7-27.3-12.3-27.3-23.3zm-105.6 32c-15.8-6.3-30.5-10-30.5-20.5 0-7.9 6.3-12.6 17.9-12.6s22.1 4.7 33.6 13.1l21-27.8c-13.1-10-31-20.5-55.2-20.5-35.7 0-59.9 20.5-59.9 49.4 0 25.7 22.6 38.9 41.5 46.2 16.3 6.3 32.1 11.6 32.1 22.1 0 7.9-6.3 13.1-20.5 13.1-13.1 0-26.3-5.3-40.5-16.3l-21 30.5c15.8 13.1 39.9 22.1 59.9 22.1 42 0 64.6-22.1 64.6-51s-22.5-41-43-47.8zm-358.9 59.4c-3.7 0-8.4-3.2-8.4-13.1V119.1H65.2c-28.4 0-41 11-41 45.2 0 22.6 3.2 35.2 3.2 54.6 0 11-6.8 22.6-27.3 23.6v27.3c20.5.5 27.3 12.1 27.3 23.1 0 19.4-3.2 31-3.2 53.6 0 34.2 12.6 45.2 40.5 45.2h20.5v-24.2h-6.3c-13.1 0-17.3-5.3-17.3-22.6s1.6-32.1 1.6-51.5c0-24.2-7.9-33.6-23.6-37.3v-1.6c15.8-3.7 23.6-13.1 23.6-37.3 0-18.9-1.6-34.2-1.6-51.5s3.7-22.1 17.3-22.1H93v150.8c0 32.1 11 53.1 43.1 53.1 10 0 17.9-1.6 23.6-3.7l-5.3-34.2c-3.1.8-4.6.8-6.2.8zM379.9 251c-16.3-6.3-31-10-31-20.5 0-7.9 6.3-12.6 17.9-12.6 11.6 0 22.1 4.7 33.6 13.1l21-27.8c-13.1-10-31-20.5-55.2-20.5-35.7 0-59.9 20.5-59.9 49.4 0 25.7 22.6 38.9 41.5 46.2 16.3 6.3 32.1 11.6 32.1 22.1 0 7.9-6.3 13.1-20.5 13.1-13.1 0-26.3-5.3-40.5-16.3l-20.5 30.5c15.8 13.1 39.9 22.1 59.9 22.1 42 0 64.6-22.1 64.6-51 .1-28.9-22.5-41-43-47.8zm-155-68.8c-38.4 0-75.1 32.1-74.1 82.5 0 52 34.2 82.5 79.3 82.5 18.9 0 39.9-6.8 56.2-17.9l-15.8-27.8c-11.6 6.8-22.6 10-34.2 10-21 0-37.3-10-41.5-34.2H290c.5-3.7 1.6-11 1.6-19.4.6-42.6-22.6-75.7-66.7-75.7zm-30 66.2c3.2-21 15.8-31 30.5-31 18.9 0 26.3 13.1 26.3 31h-56.8z"],
+ "line": [448, 512, [], "f3c0", "M272.1 204.2v71.1c0 1.8-1.4 3.2-3.2 3.2h-11.4c-1.1 0-2.1-.6-2.6-1.3l-32.6-44v42.2c0 1.8-1.4 3.2-3.2 3.2h-11.4c-1.8 0-3.2-1.4-3.2-3.2v-71.1c0-1.8 1.4-3.2 3.2-3.2H219c1 0 2.1.5 2.6 1.4l32.6 44v-42.2c0-1.8 1.4-3.2 3.2-3.2h11.4c1.8-.1 3.3 1.4 3.3 3.1zm-82-3.2h-11.4c-1.8 0-3.2 1.4-3.2 3.2v71.1c0 1.8 1.4 3.2 3.2 3.2h11.4c1.8 0 3.2-1.4 3.2-3.2v-71.1c0-1.7-1.4-3.2-3.2-3.2zm-27.5 59.6h-31.1v-56.4c0-1.8-1.4-3.2-3.2-3.2h-11.4c-1.8 0-3.2 1.4-3.2 3.2v71.1c0 .9.3 1.6.9 2.2.6.5 1.3.9 2.2.9h45.7c1.8 0 3.2-1.4 3.2-3.2v-11.4c0-1.7-1.4-3.2-3.1-3.2zM332.1 201h-45.7c-1.7 0-3.2 1.4-3.2 3.2v71.1c0 1.7 1.4 3.2 3.2 3.2h45.7c1.8 0 3.2-1.4 3.2-3.2v-11.4c0-1.8-1.4-3.2-3.2-3.2H301v-12h31.1c1.8 0 3.2-1.4 3.2-3.2V234c0-1.8-1.4-3.2-3.2-3.2H301v-12h31.1c1.8 0 3.2-1.4 3.2-3.2v-11.4c-.1-1.7-1.5-3.2-3.2-3.2zM448 113.7V399c-.1 44.8-36.8 81.1-81.7 81H81c-44.8-.1-81.1-36.9-81-81.7V113c.1-44.8 36.9-81.1 81.7-81H367c44.8.1 81.1 36.8 81 81.7zm-61.6 122.6c0-73-73.2-132.4-163.1-132.4-89.9 0-163.1 59.4-163.1 132.4 0 65.4 58 120.2 136.4 130.6 19.1 4.1 16.9 11.1 12.6 36.8-.7 4.1-3.3 16.1 14.1 8.8 17.4-7.3 93.9-55.3 128.2-94.7 23.6-26 34.9-52.3 34.9-81.5z"],
+ "linkedin": [448, 512, [], "f08c", "M416 32H31.9C14.3 32 0 46.5 0 64.3v383.4C0 465.5 14.3 480 31.9 480H416c17.6 0 32-14.5 32-32.3V64.3c0-17.8-14.4-32.3-32-32.3zM135.4 416H69V202.2h66.5V416zm-33.2-243c-21.3 0-38.5-17.3-38.5-38.5S80.9 96 102.2 96c21.2 0 38.5 17.3 38.5 38.5 0 21.3-17.2 38.5-38.5 38.5zm282.1 243h-66.4V312c0-24.8-.5-56.7-34.5-56.7-34.6 0-39.9 27-39.9 54.9V416h-66.4V202.2h63.7v29.2h.9c8.9-16.8 30.6-34.5 62.9-34.5 67.2 0 79.7 44.3 79.7 101.9V416z"],
+ "linkedin-in": [448, 512, [], "f0e1", "M100.28 448H7.4V148.9h92.88zM53.79 108.1C24.09 108.1 0 83.5 0 53.8a53.79 53.79 0 0 1 107.58 0c0 29.7-24.1 54.3-53.79 54.3zM447.9 448h-92.68V302.4c0-34.7-.7-79.2-48.29-79.2-48.29 0-55.69 37.7-55.69 76.7V448h-92.78V148.9h89.08v40.8h1.3c12.4-23.5 42.69-48.3 87.88-48.3 94 0 111.28 61.9 111.28 142.3V448z"],
+ "linode": [448, 512, [], "f2b8", "M437.4 226.3c-.3-.9-.9-1.4-1.4-2l-70-38.6c-.9-.6-2-.6-3.1 0l-58.9 36c-.9.6-1.4 1.7-1.4 2.6l-.9 31.4-24-16c-.9-.6-2.3-.6-3.1 0L240 260.9l-1.4-35.1c0-.9-.6-2-1.4-2.3l-36-24.3 33.7-17.4c1.1-.6 1.7-1.7 1.7-2.9l-5.7-132.3c0-.9-.9-2-1.7-2.6L138.6.3c-.9-.3-1.7-.3-2.3-.3L12.6 38.6c-1.4.6-2.3 2-2 3.7L38 175.4c.9 3.4 34 27.4 38.6 30.9l-26.9 12.9c-1.4.9-2 2.3-1.7 3.4l20.6 100.3c.6 2.9 23.7 23.1 27.1 26.3l-17.4 10.6c-.9.6-1.7 2-1.4 3.1 1.4 7.1 15.4 77.7 16.9 79.1l65.1 69.1c.6.6 1.4.6 2.3.9.6 0 1.1-.3 1.7-.6l83.7-66.9c.9-.6 1.1-1.4 1.1-2.3l-2-46 28 23.7c1.1.9 2.9.9 4 0l66.9-53.4c.9-.6 1.1-1.4 1.1-2.3l2.3-33.4 20.3 14c1.1.9 2.6.9 3.7 0l54.6-43.7c.6-.3 1.1-1.1 1.1-2 .9-6.5 10.3-70.8 9.7-72.8zm-204.8 4.8l4 92.6-90.6 61.2-14-96.6 100.6-57.2zm-7.7-180l5.4 126-106.6 55.4L104 97.7l120.9-46.6zM44 173.1L18 48l79.7 49.4 19.4 132.9L44 173.1zm30.6 147.8L55.7 230l70 58.3 13.7 93.4-64.8-60.8zm24.3 117.7l-13.7-67.1 61.7 60.9 9.7 67.4-57.7-61.2zm64.5 64.5l-10.6-70.9 85.7-61.4 3.1 70-78.2 62.3zm82-115.1c0-3.4.9-22.9-2-25.1l-24.3-20 22.3-14.9c2.3-1.7 1.1-5.7 1.1-8l29.4 22.6.6 68.3-27.1-22.9zm94.3-25.4l-60.9 48.6-.6-68.6 65.7-46.9-4.2 66.9zm27.7-25.7l-19.1-13.4 2-34c.3-.9-.3-2-1.1-2.6L308 259.7l.6-30 64.6 40.6-5.8 66.6zm54.6-39.8l-48.3 38.3 5.7-65.1 51.1-36.6-8.5 63.4z"],
+ "linux": [448, 512, [], "f17c", "M220.8 123.3c1 .5 1.8 1.7 3 1.7 1.1 0 2.8-.4 2.9-1.5.2-1.4-1.9-2.3-3.2-2.9-1.7-.7-3.9-1-5.5-.1-.4.2-.8.7-.6 1.1.3 1.3 2.3 1.1 3.4 1.7zm-21.9 1.7c1.2 0 2-1.2 3-1.7 1.1-.6 3.1-.4 3.5-1.6.2-.4-.2-.9-.6-1.1-1.6-.9-3.8-.6-5.5.1-1.3.6-3.4 1.5-3.2 2.9.1 1 1.8 1.5 2.8 1.4zM420 403.8c-3.6-4-5.3-11.6-7.2-19.7-1.8-8.1-3.9-16.8-10.5-22.4-1.3-1.1-2.6-2.1-4-2.9-1.3-.8-2.7-1.5-4.1-2 9.2-27.3 5.6-54.5-3.7-79.1-11.4-30.1-31.3-56.4-46.5-74.4-17.1-21.5-33.7-41.9-33.4-72C311.1 85.4 315.7.1 234.8 0 132.4-.2 158 103.4 156.9 135.2c-1.7 23.4-6.4 41.8-22.5 64.7-18.9 22.5-45.5 58.8-58.1 96.7-6 17.9-8.8 36.1-6.2 53.3-6.5 5.8-11.4 14.7-16.6 20.2-4.2 4.3-10.3 5.9-17 8.3s-14 6-18.5 14.5c-2.1 3.9-2.8 8.1-2.8 12.4 0 3.9.6 7.9 1.2 11.8 1.2 8.1 2.5 15.7.8 20.8-5.2 14.4-5.9 24.4-2.2 31.7 3.8 7.3 11.4 10.5 20.1 12.3 17.3 3.6 40.8 2.7 59.3 12.5 19.8 10.4 39.9 14.1 55.9 10.4 11.6-2.6 21.1-9.6 25.9-20.2 12.5-.1 26.3-5.4 48.3-6.6 14.9-1.2 33.6 5.3 55.1 4.1.6 2.3 1.4 4.6 2.5 6.7v.1c8.3 16.7 23.8 24.3 40.3 23 16.6-1.3 34.1-11 48.3-27.9 13.6-16.4 36-23.2 50.9-32.2 7.4-4.5 13.4-10.1 13.9-18.3.4-8.2-4.4-17.3-15.5-29.7zM223.7 87.3c9.8-22.2 34.2-21.8 44-.4 6.5 14.2 3.6 30.9-4.3 40.4-1.6-.8-5.9-2.6-12.6-4.9 1.1-1.2 3.1-2.7 3.9-4.6 4.8-11.8-.2-27-9.1-27.3-7.3-.5-13.9 10.8-11.8 23-4.1-2-9.4-3.5-13-4.4-1-6.9-.3-14.6 2.9-21.8zM183 75.8c10.1 0 20.8 14.2 19.1 33.5-3.5 1-7.1 2.5-10.2 4.6 1.2-8.9-3.3-20.1-9.6-19.6-8.4.7-9.8 21.2-1.8 28.1 1 .8 1.9-.2-5.9 5.5-15.6-14.6-10.5-52.1 8.4-52.1zm-13.6 60.7c6.2-4.6 13.6-10 14.1-10.5 4.7-4.4 13.5-14.2 27.9-14.2 7.1 0 15.6 2.3 25.9 8.9 6.3 4.1 11.3 4.4 22.6 9.3 8.4 3.5 13.7 9.7 10.5 18.2-2.6 7.1-11 14.4-22.7 18.1-11.1 3.6-19.8 16-38.2 14.9-3.9-.2-7-1-9.6-2.1-8-3.5-12.2-10.4-20-15-8.6-4.8-13.2-10.4-14.7-15.3-1.4-4.9 0-9 4.2-12.3zm3.3 334c-2.7 35.1-43.9 34.4-75.3 18-29.9-15.8-68.6-6.5-76.5-21.9-2.4-4.7-2.4-12.7 2.6-26.4v-.2c2.4-7.6.6-16-.6-23.9-1.2-7.8-1.8-15 .9-20 3.5-6.7 8.5-9.1 14.8-11.3 10.3-3.7 11.8-3.4 19.6-9.9 5.5-5.7 9.5-12.9 14.3-18 5.1-5.5 10-8.1 17.7-6.9 8.1 1.2 15.1 6.8 21.9 16l19.6 35.6c9.5 19.9 43.1 48.4 41 68.9zm-1.4-25.9c-4.1-6.6-9.6-13.6-14.4-19.6 7.1 0 14.2-2.2 16.7-8.9 2.3-6.2 0-14.9-7.4-24.9-13.5-18.2-38.3-32.5-38.3-32.5-13.5-8.4-21.1-18.7-24.6-29.9s-3-23.3-.3-35.2c5.2-22.9 18.6-45.2 27.2-59.2 2.3-1.7.8 3.2-8.7 20.8-8.5 16.1-24.4 53.3-2.6 82.4.6-20.7 5.5-41.8 13.8-61.5 12-27.4 37.3-74.9 39.3-112.7 1.1.8 4.6 3.2 6.2 4.1 4.6 2.7 8.1 6.7 12.6 10.3 12.4 10 28.5 9.2 42.4 1.2 6.2-3.5 11.2-7.5 15.9-9 9.9-3.1 17.8-8.6 22.3-15 7.7 30.4 25.7 74.3 37.2 95.7 6.1 11.4 18.3 35.5 23.6 64.6 3.3-.1 7 .4 10.9 1.4 13.8-35.7-11.7-74.2-23.3-84.9-4.7-4.6-4.9-6.6-2.6-6.5 12.6 11.2 29.2 33.7 35.2 59 2.8 11.6 3.3 23.7.4 35.7 16.4 6.8 35.9 17.9 30.7 34.8-2.2-.1-3.2 0-4.2 0 3.2-10.1-3.9-17.6-22.8-26.1-19.6-8.6-36-8.6-38.3 12.5-12.1 4.2-18.3 14.7-21.4 27.3-2.8 11.2-3.6 24.7-4.4 39.9-.5 7.7-3.6 18-6.8 29-32.1 22.9-76.7 32.9-114.3 7.2zm257.4-11.5c-.9 16.8-41.2 19.9-63.2 46.5-13.2 15.7-29.4 24.4-43.6 25.5s-26.5-4.8-33.7-19.3c-4.7-11.1-2.4-23.1 1.1-36.3 3.7-14.2 9.2-28.8 9.9-40.6.8-15.2 1.7-28.5 4.2-38.7 2.6-10.3 6.6-17.2 13.7-21.1.3-.2.7-.3 1-.5.8 13.2 7.3 26.6 18.8 29.5 12.6 3.3 30.7-7.5 38.4-16.3 9-.3 15.7-.9 22.6 5.1 9.9 8.5 7.1 30.3 17.1 41.6 10.6 11.6 14 19.5 13.7 24.6zM173.3 148.7c2 1.9 4.7 4.5 8 7.1 6.6 5.2 15.8 10.6 27.3 10.6 11.6 0 22.5-5.9 31.8-10.8 4.9-2.6 10.9-7 14.8-10.4s5.9-6.3 3.1-6.6-2.6 2.6-6 5.1c-4.4 3.2-9.7 7.4-13.9 9.8-7.4 4.2-19.5 10.2-29.9 10.2s-18.7-4.8-24.9-9.7c-3.1-2.5-5.7-5-7.7-6.9-1.5-1.4-1.9-4.6-4.3-4.9-1.4-.1-1.8 3.7 1.7 6.5z"],
+ "lyft": [512, 512, [], "f3c3", "M0 81.1h77.8v208.7c0 33.1 15 52.8 27.2 61-12.7 11.1-51.2 20.9-80.2-2.8C7.8 334 0 310.7 0 289V81.1zm485.9 173.5v-22h23.8v-76.8h-26.1c-10.1-46.3-51.2-80.7-100.3-80.7-56.6 0-102.7 46-102.7 102.7V357c16 2.3 35.4-.3 51.7-14 17.1-14 24.8-37.2 24.8-59v-6.7h38.8v-76.8h-38.8v-23.3c0-34.6 52.2-34.6 52.2 0v77.1c0 56.6 46 102.7 102.7 102.7v-76.5c-14.5 0-26.1-11.7-26.1-25.9zm-294.3-99v113c0 15.4-23.8 15.4-23.8 0v-113H91v132.7c0 23.8 8 54 45 63.9 37 9.8 58.2-10.6 58.2-10.6-2.1 13.4-14.5 23.3-34.9 25.3-15.5 1.6-35.2-3.6-45-7.8v70.3c25.1 7.5 51.5 9.8 77.6 4.7 47.1-9.1 76.8-48.4 76.8-100.8V155.1h-77.1v.5z"],
+ "magento": [448, 512, [], "f3c4", "M445.7 127.9V384l-63.4 36.5V164.7L223.8 73.1 65.2 164.7l.4 255.9L2.3 384V128.1L224.2 0l221.5 127.9zM255.6 420.5L224 438.9l-31.8-18.2v-256l-63.3 36.6.1 255.9 94.9 54.9 95.1-54.9v-256l-63.4-36.6v255.9z"],
+ "mailchimp": [448, 512, [], "f59e", "M330.61 243.52a36.15 36.15 0 0 1 9.3 0c1.66-3.83 1.95-10.43.45-17.61-2.23-10.67-5.25-17.14-11.48-16.13s-6.47 8.74-4.24 19.42c1.26 6 3.49 11.14 6 14.32zM277.05 252c4.47 2 7.2 3.26 8.28 2.13 1.89-1.94-3.48-9.39-12.12-13.09a31.44 31.44 0 0 0-30.61 3.68c-3 2.18-5.81 5.22-5.41 7.06.85 3.74 10-2.71 22.6-3.48 7-.44 12.8 1.75 17.26 3.71zm-9 5.13c-9.07 1.42-15 6.53-13.47 10.1.9.34 1.17.81 5.21-.81a37 37 0 0 1 18.72-1.95c2.92.34 4.31.52 4.94-.49 1.46-2.22-5.71-8-15.39-6.85zm54.17 17.1c3.38-6.87-10.9-13.93-14.3-7s10.92 13.88 14.32 6.97zm15.66-20.47c-7.66-.13-7.95 15.8-.26 15.93s7.98-15.81.28-15.96zm-218.79 78.9c-1.32.31-6 1.45-8.47-2.35-5.2-8 11.11-20.38 3-35.77-9.1-17.47-27.82-13.54-35.05-5.54-8.71 9.6-8.72 23.54-5 24.08 4.27.57 4.08-6.47 7.38-11.63a12.83 12.83 0 0 1 17.85-3.72c11.59 7.59 1.37 17.76 2.28 28.62 1.39 16.68 18.42 16.37 21.58 9a2.08 2.08 0 0 0-.2-2.33c.03.89.68-1.3-3.35-.39zm299.72-17.07c-3.35-11.73-2.57-9.22-6.78-20.52 2.45-3.67 15.29-24-3.07-43.25-10.4-10.92-33.9-16.54-41.1-18.54-1.5-11.39 4.65-58.7-21.52-83 20.79-21.55 33.76-45.29 33.73-65.65-.06-39.16-48.15-51-107.42-26.47l-12.55 5.33c-.06-.05-22.71-22.27-23.05-22.57C169.5-18-41.77 216.81 25.78 273.85l14.76 12.51a72.49 72.49 0 0 0-4.1 33.5c3.36 33.4 36 60.42 67.53 60.38 57.73 133.06 267.9 133.28 322.29 3 1.74-4.47 9.11-24.61 9.11-42.38s-10.09-25.27-16.53-25.27zm-316 48.16c-22.82-.61-47.46-21.15-49.91-45.51-6.17-61.31 74.26-75.27 84-12.33 4.54 29.64-4.67 58.49-34.12 57.81zM84.3 249.55C69.14 252.5 55.78 261.09 47.6 273c-4.88-4.07-14-12-15.59-15-13.01-24.85 14.24-73 33.3-100.21C112.42 90.56 186.19 39.68 220.36 48.91c5.55 1.57 23.94 22.89 23.94 22.89s-34.15 18.94-65.8 45.35c-42.66 32.85-74.89 80.59-94.2 132.4zM323.18 350.7s-35.74 5.3-69.51-7.07c6.21-20.16 27 6.1 96.4-13.81 15.29-4.38 35.37-13 51-25.35a102.85 102.85 0 0 1 7.12 24.28c3.66-.66 14.25-.52 11.44 18.1-3.29 19.87-11.73 36-25.93 50.84A106.86 106.86 0 0 1 362.55 421a132.45 132.45 0 0 1-20.34 8.58c-53.51 17.48-108.3-1.74-126-43a66.33 66.33 0 0 1-3.55-9.74c-7.53-27.2-1.14-59.83 18.84-80.37 1.23-1.31 2.48-2.85 2.48-4.79a8.45 8.45 0 0 0-1.92-4.54c-7-10.13-31.19-27.4-26.33-60.83 3.5-24 24.49-40.91 44.07-39.91l5 .29c8.48.5 15.89 1.59 22.88 1.88 11.69.5 22.2-1.19 34.64-11.56 4.2-3.5 7.57-6.54 13.26-7.51a17.45 17.45 0 0 1 13.6 2.24c10 6.64 11.4 22.73 11.92 34.49.29 6.72 1.1 23 1.38 27.63.63 10.67 3.43 12.17 9.11 14 3.19 1.05 6.15 1.83 10.51 3.06 13.21 3.71 21 7.48 26 12.31a16.38 16.38 0 0 1 4.74 9.29c1.56 11.37-8.82 25.4-36.31 38.16-46.71 21.68-93.68 14.45-100.48 13.68-20.15-2.71-31.63 23.32-19.55 41.15 22.64 33.41 122.4 20 151.37-21.35.69-1 .12-1.59-.73-1-41.77 28.58-97.06 38.21-128.46 26-4.77-1.85-14.73-6.44-15.94-16.67 43.6 13.49 71 .74 71 .74s2.03-2.79-.56-2.53zm-68.47-5.7zm-83.4-187.5c16.74-19.35 37.36-36.18 55.83-45.63a.73.73 0 0 1 1 1c-1.46 2.66-4.29 8.34-5.19 12.65a.75.75 0 0 0 1.16.79c11.49-7.83 31.48-16.22 49-17.3a.77.77 0 0 1 .52 1.38 41.86 41.86 0 0 0-7.71 7.74.75.75 0 0 0 .59 1.19c12.31.09 29.66 4.4 41 10.74.76.43.22 1.91-.64 1.72-69.55-15.94-123.08 18.53-134.5 26.83a.76.76 0 0 1-1-1.12z"],
+ "mandalorian": [448, 512, [], "f50f", "M232.27 511.89c-1-3.26-1.69-15.83-1.39-24.58.55-15.89 1-24.72 1.4-28.76.64-6.2 2.87-20.72 3.28-21.38.6-1 .4-27.87-.24-33.13-.31-2.58-.63-11.9-.69-20.73-.13-16.47-.53-20.12-2.73-24.76-1.1-2.32-1.23-3.84-1-11.43a92.38 92.38 0 0 0-.34-12.71c-2-13-3.46-27.7-3.25-33.9s.43-7.15 2.06-9.67c3.05-4.71 6.51-14 8.62-23.27 2.26-9.86 3.88-17.18 4.59-20.74a109.54 109.54 0 0 1 4.42-15.05c2.27-6.25 2.49-15.39.37-15.39-.3 0-1.38 1.22-2.41 2.71s-4.76 4.8-8.29 7.36c-8.37 6.08-11.7 9.39-12.66 12.58s-1 7.23-.16 7.76c.34.21 1.29 2.4 2.11 4.88a28.83 28.83 0 0 1 .72 15.36c-.39 1.77-1 5.47-1.46 8.23s-1 6.46-1.25 8.22a9.85 9.85 0 0 1-1.55 4.26c-1 1-1.14.91-2.05-.53a14.87 14.87 0 0 1-1.44-4.75c-.25-1.74-1.63-7.11-3.08-11.93-3.28-10.9-3.52-16.15-1-21a14.24 14.24 0 0 0 1.67-4.61c0-2.39-2.2-5.32-7.41-9.89-7-6.18-8.63-7.92-10.23-11.3-1.71-3.6-3.06-4.06-4.54-1.54-1.78 3-2.6 9.11-3 22l-.34 12.19 2 2.25c3.21 3.7 12.07 16.45 13.78 19.83 3.41 6.74 4.34 11.69 4.41 23.56s.95 22.75 2 24.71c.36.66.51 1.35.34 1.52s.41 2.09 1.29 4.27a38.14 38.14 0 0 1 2.06 9 91 91 0 0 0 1.71 10.37c2.23 9.56 2.77 14.08 2.39 20.14-.2 3.27-.53 11.07-.73 17.32-1.31 41.76-1.85 58-2 61.21-.12 2-.39 11.51-.6 21.07-.36 16.3-1.3 27.37-2.42 28.65-.64.73-8.07-4.91-12.52-9.49-3.75-3.87-4-4.79-2.83-9.95.7-3 2.26-18.29 3.33-32.62.36-4.78.81-10.5 1-12.71.83-9.37 1.66-20.35 2.61-34.78.56-8.46 1.33-16.44 1.72-17.73s.89-9.89 1.13-19.11l.43-16.77-2.26-4.3c-1.72-3.28-4.87-6.94-13.22-15.34-6-6.07-11.84-12.3-12.91-13.85l-1.95-2.81.75-10.9c1.09-15.71 1.1-48.57 0-59.06l-.89-8.7-3.28-4.52c-5.86-8.08-5.8-7.75-6.22-33.27-.1-6.07-.38-11.5-.63-12.06-.83-1.87-3.05-2.66-8.54-3.05-8.86-.62-11-1.9-23.85-14.55-6.15-6-12.34-12-13.75-13.19-2.81-2.42-2.79-2-.56-9.63l1.35-4.65-1.69-3a32.22 32.22 0 0 0-2.59-4.07c-1.33-1.51-5.5-10.89-6-13.49a4.24 4.24 0 0 1 .87-3.9c2.23-2.86 3.4-5.68 4.45-10.73 2.33-11.19 7.74-26.09 10.6-29.22 3.18-3.47 7.7-1 9.41 5 1.34 4.79 1.37 9.79.1 18.55a101.2 101.2 0 0 0-1 11.11c0 4 .19 4.69 2.25 7.39 3.33 4.37 7.73 7.41 15.2 10.52a18.67 18.67 0 0 1 4.72 2.85c11.17 10.72 18.62 16.18 22.95 16.85 5.18.8 8 4.54 10 13.39 1.31 5.65 4 11.14 5.46 11.14a9.38 9.38 0 0 0 3.33-1.39c2-1.22 2.25-1.73 2.25-4.18a132.88 132.88 0 0 0-2-17.84c-.37-1.66-.78-4.06-.93-5.35s-.61-3.85-1-5.69c-2.55-11.16-3.65-15.46-4.1-16-1.55-2-4.08-10.2-4.93-15.92-1.64-11.11-4-14.23-12.91-17.39A43.15 43.15 0 0 1 165.24 78c-1.15-1-4-3.22-6.35-5.06s-4.41-3.53-4.6-3.76a22.7 22.7 0 0 0-2.69-2c-6.24-4.22-8.84-7-11.26-12l-2.44-5-.22-13-.22-13 6.91-6.55c3.95-3.75 8.48-7.35 10.59-8.43 3.31-1.69 4.45-1.89 11.37-2 8.53-.19 10.12 0 11.66 1.56s1.36 6.4-.29 8.5a6.66 6.66 0 0 0-1.34 2.32c0 .58-2.61 4.91-5.42 9a30.39 30.39 0 0 0-2.37 6.82c20.44 13.39 21.55 3.77 14.07 29L194 66.92c3.11-8.66 6.47-17.26 8.61-26.22.29-7.63-12-4.19-15.4-8.68-2.33-5.93 3.13-14.18 6.06-19.2 1.6-2.34 6.62-4.7 8.82-4.15.88.22 4.16-.35 7.37-1.28a45.3 45.3 0 0 1 7.55-1.68 29.57 29.57 0 0 0 6-1.29c3.65-1.11 4.5-1.17 6.35-.4a29.54 29.54 0 0 0 5.82 1.36 18.18 18.18 0 0 1 6 1.91 22.67 22.67 0 0 0 5 2.17c2.51.68 3 .57 7.05-1.67l4.35-2.4L268.32 5c10.44-.4 10.81-.47 15.26-2.68L288.16 0l2.46 1.43c1.76 1 3.14 2.73 4.85 6 2.36 4.51 2.38 4.58 1.37 7.37-.88 2.44-.89 3.3-.1 6.39a35.76 35.76 0 0 0 2.1 5.91 13.55 13.55 0 0 1 1.31 4c.31 4.33 0 5.3-2.41 6.92-2.17 1.47-7 7.91-7 9.34a14.77 14.77 0 0 1-1.07 3c-5 11.51-6.76 13.56-14.26 17-9.2 4.2-12.3 5.19-16.21 5.19-3.1 0-4 .25-4.54 1.26a18.33 18.33 0 0 1-4.09 3.71 13.62 13.62 0 0 0-4.38 4.78 5.89 5.89 0 0 1-2.49 2.91 6.88 6.88 0 0 0-2.45 1.71 67.62 67.62 0 0 1-7 5.38c-3.33 2.34-6.87 5-7.87 6A7.27 7.27 0 0 1 224 100a5.76 5.76 0 0 0-2.13 1.65c-1.31 1.39-1.49 2.11-1.14 4.6a36.45 36.45 0 0 0 1.42 5.88c1.32 3.8 1.31 7.86 0 10.57s-.89 6.65 1.35 9.59c2 2.63 2.16 4.56.71 8.84a33.45 33.45 0 0 0-1.06 8.91c0 4.88.22 6.28 1.46 8.38s1.82 2.48 3.24 2.32c2-.23 2.3-1.05 4.71-12.12 2.18-10 3.71-11.92 13.76-17.08 2.94-1.51 7.46-4 10-5.44s6.79-3.69 9.37-4.91a40.09 40.09 0 0 0 15.22-11.67c7.11-8.79 10-16.22 12.85-33.3a18.37 18.37 0 0 1 2.86-7.73 20.39 20.39 0 0 0 2.89-7.31c1-5.3 2.85-9.08 5.58-11.51 4.7-4.18 6-1.09 4.59 10.87-.46 3.86-1.1 10.33-1.44 14.38l-.61 7.36 4.45 4.09 4.45 4.09.11 8.42c.06 4.63.47 9.53.92 10.89l.82 2.47-6.43 6.28c-8.54 8.33-12.88 13.93-16.76 21.61-1.77 3.49-3.74 7.11-4.38 8-2.18 3.11-6.46 13-8.76 20.26l-2.29 7.22-7 6.49c-3.83 3.57-8 7.25-9.17 8.17-3.05 2.32-4.26 5.15-4.26 10a14.62 14.62 0 0 0 1.59 7.26 42 42 0 0 1 2.09 4.83 9.28 9.28 0 0 0 1.57 2.89c1.4 1.59 1.92 16.12.83 23.22-.68 4.48-3.63 12-4.7 12-1.79 0-4.06 9.27-5.07 20.74-.18 2-.62 5.94-1 8.7s-1 10-1.35 16.05c-.77 12.22-.19 18.77 2 23.15 3.41 6.69.52 12.69-11 22.84l-4 3.49.07 5.19a40.81 40.81 0 0 0 1.14 8.87c4.61 16 4.73 16.92 4.38 37.13-.46 26.4-.26 40.27.63 44.15a61.31 61.31 0 0 1 1.08 7c.17 2 .66 5.33 1.08 7.36.47 2.26.78 11 .79 22.74v19.06l-1.81 2.63c-2.71 3.91-15.11 13.54-15.49 12.29zm29.53-45.11c-.18-.3-.33-6.87-.33-14.59 0-14.06-.89-27.54-2.26-34.45-.4-2-.81-9.7-.9-17.06-.15-11.93-1.4-24.37-2.64-26.38-.66-1.07-3-17.66-3-21.3 0-4.23 1-6 5.28-9.13s4.86-3.14 5.48-.72c.28 1.1 1.45 5.62 2.6 10 3.93 15.12 4.14 16.27 4.05 21.74-.1 5.78-.13 6.13-1.74 17.73-1 7.07-1.17 12.39-1 28.43.17 19.4-.64 35.73-2 41.27-.71 2.78-2.8 5.48-3.43 4.43zm-71-37.58a101 101 0 0 1-1.73-10.79 100.5 100.5 0 0 0-1.73-10.79 37.53 37.53 0 0 1-1-6.49c-.31-3.19-.91-7.46-1.33-9.48-1-4.79-3.35-19.35-3.42-21.07 0-.74-.34-4.05-.7-7.36-.67-6.21-.84-27.67-.22-28.29 1-1 6.63 2.76 11.33 7.43l5.28 5.25-.45 6.47c-.25 3.56-.6 10.23-.78 14.83s-.49 9.87-.67 11.71-.61 9.36-.94 16.72c-.79 17.41-1.94 31.29-2.65 32a.62.62 0 0 1-1-.14zm-87.18-266.59c21.07 12.79 17.84 14.15 28.49 17.66 13 4.29 18.87 7.13 23.15 16.87C111.6 233.28 86.25 255 78.55 268c-31 52-6 101.59 62.75 87.21-14.18 29.23-78 28.63-98.68-4.9-24.68-39.95-22.09-118.3 61-187.66zm210.79 179c56.66 6.88 82.32-37.74 46.54-89.23 0 0-26.87-29.34-64.28-68 3-15.45 9.49-32.12 30.57-53.82 89.2 63.51 92 141.61 92.46 149.36 4.3 70.64-78.7 91.18-105.29 61.71z"],
+ "markdown": [640, 512, [], "f60f", "M593.8 59.1H46.2C20.7 59.1 0 79.8 0 105.2v301.5c0 25.5 20.7 46.2 46.2 46.2h547.7c25.5 0 46.2-20.7 46.1-46.1V105.2c0-25.4-20.7-46.1-46.2-46.1zM338.5 360.6H277v-120l-61.5 76.9-61.5-76.9v120H92.3V151.4h61.5l61.5 76.9 61.5-76.9h61.5v209.2zm135.3 3.1L381.5 256H443V151.4h61.5V256H566z"],
+ "mastodon": [448, 512, [], "f4f6", "M433 179.11c0-97.2-63.71-125.7-63.71-125.7-62.52-28.7-228.56-28.4-290.48 0 0 0-63.72 28.5-63.72 125.7 0 115.7-6.6 259.4 105.63 289.1 40.51 10.7 75.32 13 103.33 11.4 50.81-2.8 79.32-18.1 79.32-18.1l-1.7-36.9s-36.31 11.4-77.12 10.1c-40.41-1.4-83-4.4-89.63-54a102.54 102.54 0 0 1-.9-13.9c85.63 20.9 158.65 9.1 178.75 6.7 56.12-6.7 105-41.3 111.23-72.9 9.8-49.8 9-121.5 9-121.5zm-75.12 125.2h-46.63v-114.2c0-49.7-64-51.6-64 6.9v62.5h-46.33V197c0-58.5-64-56.6-64-6.9v114.2H90.19c0-122.1-5.2-147.9 18.41-175 25.9-28.9 79.82-30.8 103.83 6.1l11.6 19.5 11.6-19.5c24.11-37.1 78.12-34.8 103.83-6.1 23.71 27.3 18.4 53 18.4 175z"],
+ "maxcdn": [512, 512, [], "f136", "M461.1 442.7h-97.4L415.6 200c2.3-10.2.9-19.5-4.4-25.7-5-6.1-13.7-9.6-24.2-9.6h-49.3l-59.5 278h-97.4l59.5-278h-83.4l-59.5 278H0l59.5-278-44.6-95.4H387c39.4 0 75.3 16.3 98.3 44.9 23.3 28.6 31.8 67.4 23.6 105.9l-47.8 222.6z"],
+ "mdb": [576, 512, [], "f8ca", "M17.37 160.41L7 352h43.91l5.59-79.83L84.43 352h44.71l25.54-77.43 4.79 77.43H205l-12.79-191.59H146.7L106 277.74 63.67 160.41zm281 0h-47.9V352h47.9s95 .8 94.2-95.79c-.78-94.21-94.18-95.78-94.18-95.78zm-1.2 146.46V204.78s46 4.27 46.8 50.57-46.78 51.54-46.78 51.54zm238.29-74.24a56.16 56.16 0 0 0 8-38.31c-5.34-35.76-55.08-34.32-55.08-34.32h-51.9v191.58H482s87 4.79 87-63.85c0-43.14-33.52-55.08-33.52-55.08zm-51.9-31.94s13.57-1.59 16 9.59c1.43 6.66-4 12-4 12h-12v-21.57zm-.1 109.46l.1-24.92V267h.08s41.58-4.73 41.19 22.43c-.33 25.65-41.35 20.74-41.35 20.74z"],
+ "medapps": [320, 512, [], "f3c6", "M118.3 238.4c3.5-12.5 6.9-33.6 13.2-33.6 8.3 1.8 9.6 23.4 18.6 36.6 4.6-23.5 5.3-85.1 14.1-86.7 9-.7 19.7 66.5 22 77.5 9.9 4.1 48.9 6.6 48.9 6.6 1.9 7.3-24 7.6-40 7.8-4.6 14.8-5.4 27.7-11.4 28-4.7.2-8.2-28.8-17.5-49.6l-9.4 65.5c-4.4 13-15.5-22.5-21.9-39.3-3.3-.1-62.4-1.6-47.6-7.8l31-5zM228 448c21.2 0 21.2-32 0-32H92c-21.2 0-21.2 32 0 32h136zm-24 64c21.2 0 21.2-32 0-32h-88c-21.2 0-21.2 32 0 32h88zm34.2-141.5c3.2-18.9 5.2-36.4 11.9-48.8 7.9-14.7 16.1-28.1 24-41 24.6-40.4 45.9-75.2 45.9-125.5C320 69.6 248.2 0 160 0S0 69.6 0 155.2c0 50.2 21.3 85.1 45.9 125.5 7.9 12.9 16 26.3 24 41 6.7 12.5 8.7 29.8 11.9 48.9 3.5 21 36.1 15.7 32.6-5.1-3.6-21.7-5.6-40.7-15.3-58.6C66.5 246.5 33 211.3 33 155.2 33 87.3 90 32 160 32s127 55.3 127 123.2c0 56.1-33.5 91.3-66.1 151.6-9.7 18-11.7 37.4-15.3 58.6-3.4 20.6 29 26.4 32.6 5.1z"],
+ "medium": [448, 512, [], "f23a", "M0 32v448h448V32H0zm372.2 106.1l-24 23c-2.1 1.6-3.1 4.2-2.7 6.7v169.3c-.4 2.6.6 5.2 2.7 6.7l23.5 23v5.1h-118V367l24.3-23.6c2.4-2.4 2.4-3.1 2.4-6.7V199.8l-67.6 171.6h-9.1L125 199.8v115c-.7 4.8 1 9.7 4.4 13.2l31.6 38.3v5.1H71.2v-5.1l31.6-38.3c3.4-3.5 4.9-8.4 4.1-13.2v-133c.4-3.7-1-7.3-3.8-9.8L75 138.1V133h87.3l67.4 148L289 133.1h83.2v5z"],
+ "medium-m": [512, 512, [], "f3c7", "M71.5 142.3c.6-5.9-1.7-11.8-6.1-15.8L20.3 72.1V64h140.2l108.4 237.7L364.2 64h133.7v8.1l-38.6 37c-3.3 2.5-5 6.7-4.3 10.8v272c-.7 4.1 1 8.3 4.3 10.8l37.7 37v8.1H307.3v-8.1l39.1-37.9c3.8-3.8 3.8-5 3.8-10.8V171.2L241.5 447.1h-14.7L100.4 171.2v184.9c-1.1 7.8 1.5 15.6 7 21.2l50.8 61.6v8.1h-144v-8L65 377.3c5.4-5.6 7.9-13.5 6.5-21.2V142.3z"],
+ "medrt": [544, 512, [], "f3c8", "M113.7 256c0 121.8 83.9 222.8 193.5 241.1-18.7 4.5-38.2 6.9-58.2 6.9C111.4 504 0 393 0 256S111.4 8 248.9 8c20.1 0 39.6 2.4 58.2 6.9C197.5 33.2 113.7 134.2 113.7 256m297.4 100.3c-77.7 55.4-179.6 47.5-240.4-14.6 5.5 14.1 12.7 27.7 21.7 40.5 61.6 88.2 182.4 109.3 269.7 47 87.3-62.3 108.1-184.3 46.5-272.6-9-12.9-19.3-24.3-30.5-34.2 37.4 78.8 10.7 178.5-67 233.9m-218.8-244c-1.4 1-2.7 2.1-4 3.1 64.3-17.8 135.9 4 178.9 60.5 35.7 47 42.9 106.6 24.4 158 56.7-56.2 67.6-142.1 22.3-201.8-50-65.5-149.1-74.4-221.6-19.8M296 224c-4.4 0-8-3.6-8-8v-40c0-4.4-3.6-8-8-8h-48c-4.4 0-8 3.6-8 8v40c0 4.4-3.6 8-8 8h-40c-4.4 0-8 3.6-8 8v48c0 4.4 3.6 8 8 8h40c4.4 0 8 3.6 8 8v40c0 4.4 3.6 8 8 8h48c4.4 0 8-3.6 8-8v-40c0-4.4 3.6-8 8-8h40c4.4 0 8-3.6 8-8v-48c0-4.4-3.6-8-8-8h-40z"],
+ "meetup": [512, 512, [], "f2e0", "M99 414.3c1.1 5.7-2.3 11.1-8 12.3-5.4 1.1-10.9-2.3-12-8-1.1-5.4 2.3-11.1 7.7-12.3 5.4-1.2 11.1 2.3 12.3 8zm143.1 71.4c-6.3 4.6-8 13.4-3.7 20 4.6 6.6 13.4 8.3 20 3.7 6.3-4.6 8-13.4 3.4-20-4.2-6.5-13.1-8.3-19.7-3.7zm-86-462.3c6.3-1.4 10.3-7.7 8.9-14-1.1-6.6-7.4-10.6-13.7-9.1-6.3 1.4-10.3 7.7-9.1 14 1.4 6.6 7.6 10.6 13.9 9.1zM34.4 226.3c-10-6.9-23.7-4.3-30.6 6-6.9 10-4.3 24 5.7 30.9 10 7.1 23.7 4.6 30.6-5.7 6.9-10.4 4.3-24.1-5.7-31.2zm272-170.9c10.6-6.3 13.7-20 7.7-30.3-6.3-10.6-19.7-14-30-7.7s-13.7 20-7.4 30.6c6 10.3 19.4 13.7 29.7 7.4zm-191.1 58c7.7-5.4 9.4-16 4.3-23.7s-15.7-9.4-23.1-4.3c-7.7 5.4-9.4 16-4.3 23.7 5.1 7.8 15.6 9.5 23.1 4.3zm372.3 156c-7.4 1.7-12.3 9.1-10.6 16.9 1.4 7.4 8.9 12.3 16.3 10.6 7.4-1.4 12.3-8.9 10.6-16.6-1.5-7.4-8.9-12.3-16.3-10.9zm39.7-56.8c-1.1-5.7-6.6-9.1-12-8-5.7 1.1-9.1 6.9-8 12.6 1.1 5.4 6.6 9.1 12.3 8 5.4-1.5 9.1-6.9 7.7-12.6zM447 138.9c-8.6 6-10.6 17.7-4.9 26.3 5.7 8.6 17.4 10.6 26 4.9 8.3-6 10.3-17.7 4.6-26.3-5.7-8.7-17.4-10.9-25.7-4.9zm-6.3 139.4c26.3 43.1 15.1 100-26.3 129.1-17.4 12.3-37.1 17.7-56.9 17.1-12 47.1-69.4 64.6-105.1 32.6-1.1.9-2.6 1.7-3.7 2.9-39.1 27.1-92.3 17.4-119.4-22.3-9.7-14.3-14.6-30.6-15.1-46.9-65.4-10.9-90-94-41.1-139.7-28.3-46.9.6-107.4 53.4-114.9C151.6 70 234.1 38.6 290.1 82c67.4-22.3 136.3 29.4 130.9 101.1 41.1 12.6 52.8 66.9 19.7 95.2zm-70 74.3c-3.1-20.6-40.9-4.6-43.1-27.1-3.1-32 43.7-101.1 40-128-3.4-24-19.4-29.1-33.4-29.4-13.4-.3-16.9 2-21.4 4.6-2.9 1.7-6.6 4.9-11.7-.3-6.3-6-11.1-11.7-19.4-12.9-12.3-2-17.7 2-26.6 9.7-3.4 2.9-12 12.9-20 9.1-3.4-1.7-15.4-7.7-24-11.4-16.3-7.1-40 4.6-48.6 20-12.9 22.9-38 113.1-41.7 125.1-8.6 26.6 10.9 48.6 36.9 47.1 11.1-.6 18.3-4.6 25.4-17.4 4-7.4 41.7-107.7 44.6-112.6 2-3.4 8.9-8 14.6-5.1 5.7 3.1 6.9 9.4 6 15.1-1.1 9.7-28 70.9-28.9 77.7-3.4 22.9 26.9 26.6 38.6 4 3.7-7.1 45.7-92.6 49.4-98.3 4.3-6.3 7.4-8.3 11.7-8 3.1 0 8.3.9 7.1 10.9-1.4 9.4-35.1 72.3-38.9 87.7-4.6 20.6 6.6 41.4 24.9 50.6 11.4 5.7 62.5 15.7 58.5-11.1zm5.7 92.3c-10.3 7.4-12.9 22-5.7 32.6 7.1 10.6 21.4 13.1 32 6 10.6-7.4 13.1-22 6-32.6-7.4-10.6-21.7-13.5-32.3-6z"],
+ "megaport": [496, 512, [], "f5a3", "M214.5 209.6v66.2l33.5 33.5 33.3-33.3v-66.4l-33.4-33.4zM248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm145.1 414.4L367 441.6l-26-19.2v-65.5l-33.4-33.4-33.4 33.4v65.5L248 441.6l-26.1-19.2v-65.5l-33.4-33.4-33.5 33.4v65.5l-26.1 19.2-26.1-19.2v-87l59.5-59.5V188l59.5-59.5V52.9l26.1-19.2L274 52.9v75.6l59.5 59.5v87.6l59.7 59.7v87.1z"],
+ "mendeley": [640, 512, [], "f7b3", "M624.6 325.2c-12.3-12.4-29.7-19.2-48.4-17.2-43.3-1-49.7-34.9-37.5-98.8 22.8-57.5-14.9-131.5-87.4-130.8-77.4.7-81.7 82-130.9 82-48.1 0-54-81.3-130.9-82-72.9-.8-110.1 73.3-87.4 130.8 12.2 63.9 5.8 97.8-37.5 98.8-21.2-2.3-37 6.5-53 22.5-19.9 19.7-19.3 94.8 42.6 102.6 47.1 5.9 81.6-42.9 61.2-87.8-47.3-103.7 185.9-106.1 146.5-8.2-.1.1-.2.2-.3.4-26.8 42.8 6.8 97.4 58.8 95.2 52.1 2.1 85.4-52.6 58.8-95.2-.1-.2-.2-.3-.3-.4-39.4-97.9 193.8-95.5 146.5 8.2-4.6 10-6.7 21.3-5.7 33 4.9 53.4 68.7 74.1 104.9 35.2 17.8-14.8 23.1-65.6 0-88.3zm-303.9-19.1h-.6c-43.4 0-62.8-37.5-62.8-62.8 0-34.7 28.2-62.8 62.8-62.8h.6c34.7 0 62.8 28.1 62.8 62.8 0 25-19.2 62.8-62.8 62.8z"],
+ "microblog": [448, 512, [], "e01a", "M399.36,362.23c29.49-34.69,47.1-78.34,47.1-125.79C446.46,123.49,346.86,32,224,32S1.54,123.49,1.54,236.44,101.14,440.87,224,440.87a239.28,239.28,0,0,0,79.44-13.44,7.18,7.18,0,0,1,8.12,2.56c18.58,25.09,47.61,42.74,79.89,49.92a4.42,4.42,0,0,0,5.22-3.43,4.37,4.37,0,0,0-.85-3.62,87,87,0,0,1,3.69-110.69ZM329.52,212.4l-57.3,43.49L293,324.75a6.5,6.5,0,0,1-9.94,7.22L224,290.92,164.94,332a6.51,6.51,0,0,1-9.95-7.22l20.79-68.86-57.3-43.49a6.5,6.5,0,0,1,3.8-11.68l71.88-1.51,23.66-67.92a6.5,6.5,0,0,1,12.28,0l23.66,67.92,71.88,1.51a6.5,6.5,0,0,1,3.88,11.68Z"],
+ "microsoft": [448, 512, [], "f3ca", "M0 32h214.6v214.6H0V32zm233.4 0H448v214.6H233.4V32zM0 265.4h214.6V480H0V265.4zm233.4 0H448V480H233.4V265.4z"],
+ "mix": [448, 512, [], "f3cb", "M0 64v348.9c0 56.2 88 58.1 88 0V174.3c7.9-52.9 88-50.4 88 6.5v175.3c0 57.9 96 58 96 0V240c5.3-54.7 88-52.5 88 4.3v23.8c0 59.9 88 56.6 88 0V64H0z"],
+ "mixcloud": [640, 512, [], "f289", "M424.43 219.729C416.124 134.727 344.135 68 256.919 68c-72.266 0-136.224 46.516-159.205 114.074-54.545 8.029-96.63 54.822-96.63 111.582 0 62.298 50.668 112.966 113.243 112.966h289.614c52.329 0 94.969-42.362 94.969-94.693 0-45.131-32.118-83.063-74.48-92.2zm-20.489 144.53H114.327c-39.04 0-70.881-31.564-70.881-70.604s31.841-70.604 70.881-70.604c18.827 0 36.548 7.475 49.838 20.766 19.963 19.963 50.133-10.227 30.18-30.18-14.675-14.398-32.672-24.365-52.053-29.349 19.935-44.3 64.79-73.926 114.628-73.926 69.496 0 125.979 56.483 125.979 125.702 0 13.568-2.215 26.857-6.369 39.594-8.943 27.517 32.133 38.939 40.147 13.29 2.769-8.306 4.984-16.889 6.369-25.472 19.381 7.476 33.502 26.303 33.502 48.453 0 28.795-23.535 52.33-52.607 52.33zm235.069-52.33c0 44.024-12.737 86.386-37.102 122.657-4.153 6.092-10.798 9.414-17.72 9.414-16.317 0-27.127-18.826-17.443-32.949 19.381-29.349 29.903-63.682 29.903-99.122s-10.521-69.773-29.903-98.845c-15.655-22.831 19.361-47.24 35.163-23.534 24.366 35.993 37.102 78.356 37.102 122.379zm-70.88 0c0 31.565-9.137 62.021-26.857 88.325-4.153 6.091-10.798 9.136-17.72 9.136-17.201 0-27.022-18.979-17.443-32.948 13.013-19.104 19.658-41.255 19.658-64.513 0-22.981-6.645-45.408-19.658-64.512-15.761-22.986 19.008-47.095 35.163-23.535 17.719 26.026 26.857 56.483 26.857 88.047z"],
+ "mixer": [512, 512, [], "e056", "M114.57,76.07a45.71,45.71,0,0,0-67.51-6.41c-17.58,16.18-19,43.52-4.75,62.77l91.78,123L41.76,379.58c-14.23,19.25-13.11,46.59,4.74,62.77A45.71,45.71,0,0,0,114,435.94L242.89,262.7a12.14,12.14,0,0,0,0-14.23ZM470.24,379.58,377.91,255.45l91.78-123c14.22-19.25,12.83-46.59-4.75-62.77a45.71,45.71,0,0,0-67.51,6.41l-128,172.12a12.14,12.14,0,0,0,0,14.23L398,435.94a45.71,45.71,0,0,0,67.51,6.41C483.35,426.17,484.47,398.83,470.24,379.58Z"],
+ "mizuni": [496, 512, [], "f3cc", "M248 8C111 8 0 119.1 0 256c0 137 111 248 248 248s248-111 248-248C496 119.1 385 8 248 8zm-80 351.9c-31.4 10.6-58.8 27.3-80 48.2V136c0-22.1 17.9-40 40-40s40 17.9 40 40v223.9zm120-9.9c-12.9-2-26.2-3.1-39.8-3.1-13.8 0-27.2 1.1-40.2 3.1V136c0-22.1 17.9-40 40-40s40 17.9 40 40v214zm120 57.7c-21.2-20.8-48.6-37.4-80-48V136c0-22.1 17.9-40 40-40s40 17.9 40 40v271.7z"],
+ "modx": [448, 512, [], "f285", "M356 241.8l36.7 23.7V480l-133-83.8L356 241.8zM440 75H226.3l-23 37.8 153.5 96.5L440 75zm-89 142.8L55.2 32v214.5l46 29L351 217.8zM97 294.2L8 437h213.7l125-200.5L97 294.2z"],
+ "monero": [496, 512, [], "f3d0", "M352 384h108.4C417 455.9 338.1 504 248 504S79 455.9 35.6 384H144V256.2L248 361l104-105v128zM88 336V128l159.4 159.4L408 128v208h74.8c8.5-25.1 13.2-52 13.2-80C496 119 385 8 248 8S0 119 0 256c0 28 4.6 54.9 13.2 80H88z"],
+ "napster": [496, 512, [], "f3d2", "M298.3 373.6c-14.2 13.6-31.3 24.1-50.4 30.5-19-6.4-36.2-16.9-50.3-30.5h100.7zm44-199.6c20-16.9 43.6-29.2 69.6-36.2V299c0 219.4-328 217.6-328 .3V137.7c25.9 6.9 49.6 19.6 69.5 36.4 56.8-40 132.5-39.9 188.9-.1zm-208.8-58.5c64.4-60 164.3-60.1 228.9-.2-7.1 3.5-13.9 7.3-20.6 11.5-58.7-30.5-129.2-30.4-187.9.1-6.3-4-13.9-8.2-20.4-11.4zM43.8 93.2v69.3c-58.4 36.5-58.4 121.1.1 158.3 26.4 245.1 381.7 240.3 407.6 1.5l.3-1.7c58.7-36.3 58.9-121.7.2-158.2V93.2c-17.3.5-34 3-50.1 7.4-82-91.5-225.5-91.5-307.5.1-16.3-4.4-33.1-7-50.6-7.5zM259.2 352s36-.3 61.3-1.5c10.2-.5 21.1-4 25.5-6.5 26.3-15.1 25.4-39.2 26.2-47.4-79.5-.6-99.9-3.9-113 55.4zm-135.5-55.3c.8 8.2-.1 32.3 26.2 47.4 4.4 2.5 15.2 6 25.5 6.5 25.3 1.1 61.3 1.5 61.3 1.5-13.2-59.4-33.7-56.1-113-55.4zm169.1 123.4c-3.2-5.3-6.9-7.3-6.9-7.3-24.8 7.3-52.2 6.9-75.9 0 0 0-2.9 1.5-6.4 6.6-2.8 4.1-3.7 9.6-3.7 9.6 29.1 17.6 67.1 17.6 96.2 0-.1-.1-.3-4-3.3-8.9z"],
+ "neos": [512, 512, [], "f612", "M415.44 512h-95.11L212.12 357.46v91.1L125.69 512H28V29.82L68.47 0h108.05l123.74 176.13V63.45L386.69 0h97.69v461.5zM38.77 35.27V496l72-52.88V194l215.5 307.64h84.79l52.35-38.17h-78.27L69 13zm82.54 466.61l80-58.78v-101l-79.76-114.4v220.94L49 501.89h72.34zM80.63 10.77l310.6 442.57h82.37V10.77h-79.75v317.56L170.91 10.77zM311 191.65l72 102.81V15.93l-72 53v122.72z"],
+ "nimblr": [384, 512, [], "f5a8", "M246.6 299.29c15.57 0 27.15 11.46 27.15 27s-11.62 27-27.15 27c-15.7 0-27.15-11.57-27.15-27s11.55-27 27.15-27zM113 326.25c0-15.61 11.68-27 27.15-27s27.15 11.46 27.15 27-11.47 27-27.15 27c-15.44 0-27.15-11.31-27.15-27M191.76 159C157 159 89.45 178.77 59.25 227L14 0v335.48C14 433.13 93.61 512 191.76 512s177.76-78.95 177.76-176.52S290.13 159 191.76 159zm0 308.12c-73.27 0-132.51-58.9-132.51-131.59s59.24-131.59 132.51-131.59 132.51 58.86 132.51 131.54S265 467.07 191.76 467.07z"],
+ "node": [640, 512, [], "f419", "M316.3 452c-2.1 0-4.2-.6-6.1-1.6L291 439c-2.9-1.6-1.5-2.2-.5-2.5 3.8-1.3 4.6-1.6 8.7-4 .4-.2 1-.1 1.4.1l14.8 8.8c.5.3 1.3.3 1.8 0L375 408c.5-.3.9-.9.9-1.6v-66.7c0-.7-.3-1.3-.9-1.6l-57.8-33.3c-.5-.3-1.2-.3-1.8 0l-57.8 33.3c-.6.3-.9 1-.9 1.6v66.7c0 .6.4 1.2.9 1.5l15.8 9.1c8.6 4.3 13.9-.8 13.9-5.8v-65.9c0-.9.7-1.7 1.7-1.7h7.3c.9 0 1.7.7 1.7 1.7v65.9c0 11.5-6.2 18-17.1 18-3.3 0-6 0-13.3-3.6l-15.2-8.7c-3.7-2.2-6.1-6.2-6.1-10.5v-66.7c0-4.3 2.3-8.4 6.1-10.5l57.8-33.4c3.7-2.1 8.5-2.1 12.1 0l57.8 33.4c3.7 2.2 6.1 6.2 6.1 10.5v66.7c0 4.3-2.3 8.4-6.1 10.5l-57.8 33.4c-1.7 1.1-3.8 1.7-6 1.7zm46.7-65.8c0-12.5-8.4-15.8-26.2-18.2-18-2.4-19.8-3.6-19.8-7.8 0-3.5 1.5-8.1 14.8-8.1 11.9 0 16.3 2.6 18.1 10.6.2.8.8 1.3 1.6 1.3h7.5c.5 0 .9-.2 1.2-.5.3-.4.5-.8.4-1.3-1.2-13.8-10.3-20.2-28.8-20.2-16.5 0-26.3 7-26.3 18.6 0 12.7 9.8 16.1 25.6 17.7 18.9 1.9 20.4 4.6 20.4 8.3 0 6.5-5.2 9.2-17.4 9.2-15.3 0-18.7-3.8-19.8-11.4-.1-.8-.8-1.4-1.7-1.4h-7.5c-.9 0-1.7.7-1.7 1.7 0 9.7 5.3 21.3 30.6 21.3 18.5 0 29-7.2 29-19.8zm54.5-50.1c0 6.1-5 11.1-11.1 11.1s-11.1-5-11.1-11.1c0-6.3 5.2-11.1 11.1-11.1 6-.1 11.1 4.8 11.1 11.1zm-1.8 0c0-5.2-4.2-9.3-9.4-9.3-5.1 0-9.3 4.1-9.3 9.3 0 5.2 4.2 9.4 9.3 9.4 5.2-.1 9.4-4.3 9.4-9.4zm-4.5 6.2h-2.6c-.1-.6-.5-3.8-.5-3.9-.2-.7-.4-1.1-1.3-1.1h-2.2v5h-2.4v-12.5h4.3c1.5 0 4.4 0 4.4 3.3 0 2.3-1.5 2.8-2.4 3.1 1.7.1 1.8 1.2 2.1 2.8.1 1 .3 2.7.6 3.3zm-2.8-8.8c0-1.7-1.2-1.7-1.8-1.7h-2v3.5h1.9c1.6 0 1.9-1.1 1.9-1.8zM137.3 191c0-2.7-1.4-5.1-3.7-6.4l-61.3-35.3c-1-.6-2.2-.9-3.4-1h-.6c-1.2 0-2.3.4-3.4 1L3.7 184.6C1.4 185.9 0 188.4 0 191l.1 95c0 1.3.7 2.5 1.8 3.2 1.1.7 2.5.7 3.7 0L42 268.3c2.3-1.4 3.7-3.8 3.7-6.4v-44.4c0-2.6 1.4-5.1 3.7-6.4l15.5-8.9c1.2-.7 2.4-1 3.7-1 1.3 0 2.6.3 3.7 1l15.5 8.9c2.3 1.3 3.7 3.8 3.7 6.4v44.4c0 2.6 1.4 5.1 3.7 6.4l36.4 20.9c1.1.7 2.6.7 3.7 0 1.1-.6 1.8-1.9 1.8-3.2l.2-95zM472.5 87.3v176.4c0 2.6-1.4 5.1-3.7 6.4l-61.3 35.4c-2.3 1.3-5.1 1.3-7.4 0l-61.3-35.4c-2.3-1.3-3.7-3.8-3.7-6.4v-70.8c0-2.6 1.4-5.1 3.7-6.4l61.3-35.4c2.3-1.3 5.1-1.3 7.4 0l15.3 8.8c1.7 1 3.9-.3 3.9-2.2v-94c0-2.8 3-4.6 5.5-3.2l36.5 20.4c2.3 1.2 3.8 3.7 3.8 6.4zm-46 128.9c0-.7-.4-1.3-.9-1.6l-21-12.2c-.6-.3-1.3-.3-1.9 0l-21 12.2c-.6.3-.9.9-.9 1.6v24.3c0 .7.4 1.3.9 1.6l21 12.1c.6.3 1.3.3 1.8 0l21-12.1c.6-.3.9-.9.9-1.6v-24.3zm209.8-.7c2.3-1.3 3.7-3.8 3.7-6.4V192c0-2.6-1.4-5.1-3.7-6.4l-60.9-35.4c-2.3-1.3-5.1-1.3-7.4 0l-61.3 35.4c-2.3 1.3-3.7 3.8-3.7 6.4v70.8c0 2.7 1.4 5.1 3.7 6.4l60.9 34.7c2.2 1.3 5 1.3 7.3 0l36.8-20.5c2.5-1.4 2.5-5 0-6.4L550 241.6c-1.2-.7-1.9-1.9-1.9-3.2v-22.2c0-1.3.7-2.5 1.9-3.2l19.2-11.1c1.1-.7 2.6-.7 3.7 0l19.2 11.1c1.1.7 1.9 1.9 1.9 3.2v17.4c0 2.8 3.1 4.6 5.6 3.2l36.7-21.3zM559 219c-.4.3-.7.7-.7 1.2v13.6c0 .5.3 1 .7 1.2l11.8 6.8c.4.3 1 .3 1.4 0L584 235c.4-.3.7-.7.7-1.2v-13.6c0-.5-.3-1-.7-1.2l-11.8-6.8c-.4-.3-1-.3-1.4 0L559 219zm-254.2 43.5v-70.4c0-2.6-1.6-5.1-3.9-6.4l-61.1-35.2c-2.1-1.2-5-1.4-7.4 0l-61.1 35.2c-2.3 1.3-3.9 3.7-3.9 6.4v70.4c0 2.8 1.9 5.2 4 6.4l61.2 35.2c2.4 1.4 5.2 1.3 7.4 0l61-35.2c1.8-1 3.1-2.7 3.6-4.7.1-.5.2-1.1.2-1.7zm-74.3-124.9l-.8.5h1.1l-.3-.5zm76.2 130.2l-.4-.7v.9l.4-.2z"],
+ "node-js": [448, 512, [], "f3d3", "M224 508c-6.7 0-13.5-1.8-19.4-5.2l-61.7-36.5c-9.2-5.2-4.7-7-1.7-8 12.3-4.3 14.8-5.2 27.9-12.7 1.4-.8 3.2-.5 4.6.4l47.4 28.1c1.7 1 4.1 1 5.7 0l184.7-106.6c1.7-1 2.8-3 2.8-5V149.3c0-2.1-1.1-4-2.9-5.1L226.8 37.7c-1.7-1-4-1-5.7 0L36.6 144.3c-1.8 1-2.9 3-2.9 5.1v213.1c0 2 1.1 4 2.9 4.9l50.6 29.2c27.5 13.7 44.3-2.4 44.3-18.7V167.5c0-3 2.4-5.3 5.4-5.3h23.4c2.9 0 5.4 2.3 5.4 5.3V378c0 36.6-20 57.6-54.7 57.6-10.7 0-19.1 0-42.5-11.6l-48.4-27.9C8.1 389.2.7 376.3.7 362.4V149.3c0-13.8 7.4-26.8 19.4-33.7L204.6 9c11.7-6.6 27.2-6.6 38.8 0l184.7 106.7c12 6.9 19.4 19.8 19.4 33.7v213.1c0 13.8-7.4 26.7-19.4 33.7L243.4 502.8c-5.9 3.4-12.6 5.2-19.4 5.2zm149.1-210.1c0-39.9-27-50.5-83.7-58-57.4-7.6-63.2-11.5-63.2-24.9 0-11.1 4.9-25.9 47.4-25.9 37.9 0 51.9 8.2 57.7 33.8.5 2.4 2.7 4.2 5.2 4.2h24c1.5 0 2.9-.6 3.9-1.7s1.5-2.6 1.4-4.1c-3.7-44.1-33-64.6-92.2-64.6-52.7 0-84.1 22.2-84.1 59.5 0 40.4 31.3 51.6 81.8 56.6 60.5 5.9 65.2 14.8 65.2 26.7 0 20.6-16.6 29.4-55.5 29.4-48.9 0-59.6-12.3-63.2-36.6-.4-2.6-2.6-4.5-5.3-4.5h-23.9c-3 0-5.3 2.4-5.3 5.3 0 31.1 16.9 68.2 97.8 68.2 58.4-.1 92-23.2 92-63.4z"],
+ "npm": [576, 512, [], "f3d4", "M288 288h-32v-64h32v64zm288-128v192H288v32H160v-32H0V160h576zm-416 32H32v128h64v-96h32v96h32V192zm160 0H192v160h64v-32h64V192zm224 0H352v128h64v-96h32v96h32v-96h32v96h32V192z"],
+ "ns8": [640, 512, [], "f3d5", "M104.324,269.172h26.067V242.994H104.324Zm52.466-26.178-.055-26.178v-.941a39.325,39.325,0,0,0-78.644.941v.166h26.4v-.166a12.98,12.98,0,0,1,25.956,0v26.178Zm52.356,25.846a91.1,91.1,0,0,1-91.1,91.1h-.609a91.1,91.1,0,0,1-91.1-91.1H0v.166A117.33,117.33,0,0,0,117.44,386.28h.775A117.331,117.331,0,0,0,235.49,268.84V242.828H209.146Zm-157.233,0a65.362,65.362,0,0,0,130.723,0H156.292a39.023,39.023,0,0,1-78.035,0V242.883H51.968v-26.62A65.42,65.42,0,0,1,182.8,217.48v25.293h26.344V217.48a91.761,91.761,0,0,0-183.522,0v25.4H51.913Zm418.4-71.173c13.67,0,24.573,6.642,30.052,18.264l.719,1.549,23.245-11.511-.609-1.439c-8.025-19.26-28.5-31.27-53.407-31.27-23.134,0-43.611,11.4-50.972,28.447-.123,26.876-.158,23.9,0,24.85,4.7,11.013,14.555,19.37,28.668,24.241a102.033,102.033,0,0,0,19.813,3.984c5.479.72,10.626,1.384,15.829,3.1,6.364,2.1,10.46,5.257,12.84,9.851v9.851c-3.708,7.527-13.781,12.342-25.791,12.342-14.334,0-25.956-6.918-31.933-19.039l-.72-1.494L415.026,280.9l.553,1.439c7.915,19.426,29.609,32.044,55.289,32.044,23.632,0,44.608-11.4,52.3-28.447l.166-25.9-.166-.664c-4.87-11.014-15.219-19.647-28.944-24.241-7.693-2.712-14.335-3.6-20.7-4.427a83.777,83.777,0,0,1-14.832-2.878c-6.31-1.937-10.4-5.092-12.619-9.63v-8.412C449.45,202.427,458.969,197.667,470.315,197.667ZM287.568,311.344h26.067v-68.4H287.568Zm352.266-53.3c-2.933-6.254-8.3-12.01-15.441-16.714A37.99,37.99,0,0,0,637.4,226l.166-25.347-.166-.664C630.038,184,610.667,173.26,589.25,173.26S548.461,184,541.1,199.992l-.166,25.347.166.664a39.643,39.643,0,0,0,13.006,15.331c-7.2,4.7-12.508,10.46-15.441,16.714l-.166,28.889.166.72c7.582,15.994,27.893,26.731,50.585,26.731s43.057-10.737,50.584-26.731l.166-28.89Zm-73.22-50.806c3.6-6.31,12.563-10.516,22.58-10.516s19.038,4.206,22.636,10.516v13.725c-3.542,6.2-12.563,10.349-22.636,10.349s-19.094-4.15-22.58-10.349Zm47.319,72.169c-3.764,6.641-13.338,10.9-24.683,10.9-11.125,0-20.976-4.372-24.684-10.9V263.25c3.708-6.309,13.5-10.515,24.684-10.515,11.345,0,20.919,4.15,24.683,10.515ZM376.4,265.962l-59.827-89.713h-29v40.623h26.51v.387l62.539,94.085H402.3V176.249H376.4Z"],
+ "nutritionix": [400, 512, [], "f3d6", "M88 8.1S221.4-.1 209 112.5c0 0 19.1-74.9 103-40.6 0 0-17.7 74-88 56 0 0 14.6-54.6 66.1-56.6 0 0-39.9-10.3-82.1 48.8 0 0-19.8-94.5-93.6-99.7 0 0 75.2 19.4 77.6 107.5 0 .1-106.4 7-104-119.8zm312 315.6c0 48.5-9.7 95.3-32 132.3-42.2 30.9-105 48-168 48-62.9 0-125.8-17.1-168-48C9.7 419 0 372.2 0 323.7 0 275.3 17.7 229 40 192c42.2-30.9 97.1-48.6 160-48.6 63 0 117.8 17.6 160 48.6 22.3 37 40 83.3 40 131.7zM120 428c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zM192 428c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zM264 428c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zM336 428c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm0-66.2c0-15.5-12.5-28-28-28s-28 12.5-28 28 12.5 28 28 28 28-12.5 28-28zm24-39.6c-4.8-22.3-7.4-36.9-16-56-38.8-19.9-90.5-32-144-32S94.8 180.1 56 200c-8.8 19.5-11.2 33.9-16 56 42.2-7.9 98.7-14.8 160-14.8s117.8 6.9 160 14.8z"],
+ "octopus-deploy": [512, 512, [], "e082", "M455.6,349.2c-45.891-39.09-36.67-77.877-16.095-128.11C475.16,134.04,415.967,34.14,329.93,8.3,237.04-19.6,134.252,24.341,99.677,117.147a180.862,180.862,0,0,0-10.988,73.544c1.733,29.543,14.717,52.97,24.09,80.3,17.2,50.161-28.1,92.743-66.662,117.582-46.806,30.2-36.319,39.857-8.428,41.858,23.378,1.68,44.478-4.548,65.265-15.045,9.2-4.647,40.687-18.931,45.13-28.588C135.9,413.388,111.122,459.5,126.621,488.9c19.1,36.229,67.112-31.77,76.709-45.812,8.591-12.572,42.963-81.279,63.627-46.926,18.865,31.361,8.6,76.391,35.738,104.622,32.854,34.2,51.155-18.312,51.412-44.221.163-16.411-6.1-95.852,29.9-59.944C405.428,418,436.912,467.8,472.568,463.642c38.736-4.516-22.123-67.967-28.262-78.695,5.393,4.279,53.665,34.128,53.818,9.52C498.234,375.678,468.039,359.8,455.6,349.2Z"],
+ "odnoklassniki": [320, 512, [], "f263", "M275.1 334c-27.4 17.4-65.1 24.3-90 26.9l20.9 20.6 76.3 76.3c27.9 28.6-17.5 73.3-45.7 45.7-19.1-19.4-47.1-47.4-76.3-76.6L84 503.4c-28.2 27.5-73.6-17.6-45.4-45.7 19.4-19.4 47.1-47.4 76.3-76.3l20.6-20.6c-24.6-2.6-62.9-9.1-90.6-26.9-32.6-21-46.9-33.3-34.3-59 7.4-14.6 27.7-26.9 54.6-5.7 0 0 36.3 28.9 94.9 28.9s94.9-28.9 94.9-28.9c26.9-21.1 47.1-8.9 54.6 5.7 12.4 25.7-1.9 38-34.5 59.1zM30.3 129.7C30.3 58 88.6 0 160 0s129.7 58 129.7 129.7c0 71.4-58.3 129.4-129.7 129.4s-129.7-58-129.7-129.4zm66 0c0 35.1 28.6 63.7 63.7 63.7s63.7-28.6 63.7-63.7c0-35.4-28.6-64-63.7-64s-63.7 28.6-63.7 64z"],
+ "odnoklassniki-square": [448, 512, [], "f264", "M184.2 177.1c0-22.1 17.9-40 39.8-40s39.8 17.9 39.8 40c0 22-17.9 39.8-39.8 39.8s-39.8-17.9-39.8-39.8zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-305.1 97.1c0 44.6 36.4 80.9 81.1 80.9s81.1-36.2 81.1-80.9c0-44.8-36.4-81.1-81.1-81.1s-81.1 36.2-81.1 81.1zm174.5 90.7c-4.6-9.1-17.3-16.8-34.1-3.6 0 0-22.7 18-59.3 18s-59.3-18-59.3-18c-16.8-13.2-29.5-5.5-34.1 3.6-7.9 16.1 1.1 23.7 21.4 37 17.3 11.1 41.2 15.2 56.6 16.8l-12.9 12.9c-18.2 18-35.5 35.5-47.7 47.7-17.6 17.6 10.7 45.8 28.4 28.6l47.7-47.9c18.2 18.2 35.7 35.7 47.7 47.9 17.6 17.2 46-10.7 28.6-28.6l-47.7-47.7-13-12.9c15.5-1.6 39.1-5.9 56.2-16.8 20.4-13.3 29.3-21 21.5-37z"],
+ "old-republic": [496, 512, [], "f510", "M235.76 10.23c7.5-.31 15-.28 22.5-.09 3.61.14 7.2.4 10.79.73 4.92.27 9.79 1.03 14.67 1.62 2.93.43 5.83.98 8.75 1.46 7.9 1.33 15.67 3.28 23.39 5.4 12.24 3.47 24.19 7.92 35.76 13.21 26.56 12.24 50.94 29.21 71.63 49.88 20.03 20.09 36.72 43.55 48.89 69.19 1.13 2.59 2.44 5.1 3.47 7.74 2.81 6.43 5.39 12.97 7.58 19.63 4.14 12.33 7.34 24.99 9.42 37.83.57 3.14 1.04 6.3 1.4 9.47.55 3.83.94 7.69 1.18 11.56.83 8.34.84 16.73.77 25.1-.07 4.97-.26 9.94-.75 14.89-.24 3.38-.51 6.76-.98 10.12-.39 2.72-.63 5.46-1.11 8.17-.9 5.15-1.7 10.31-2.87 15.41-4.1 18.5-10.3 36.55-18.51 53.63-15.77 32.83-38.83 62.17-67.12 85.12a246.503 246.503 0 0 1-56.91 34.86c-6.21 2.68-12.46 5.25-18.87 7.41-3.51 1.16-7.01 2.38-10.57 3.39-6.62 1.88-13.29 3.64-20.04 5-4.66.91-9.34 1.73-14.03 2.48-5.25.66-10.5 1.44-15.79 1.74-6.69.66-13.41.84-20.12.81-6.82.03-13.65-.12-20.45-.79-3.29-.23-6.57-.5-9.83-.95-2.72-.39-5.46-.63-8.17-1.11-4.12-.72-8.25-1.37-12.35-2.22-4.25-.94-8.49-1.89-12.69-3.02-8.63-2.17-17.08-5.01-25.41-8.13-10.49-4.12-20.79-8.75-30.64-14.25-2.14-1.15-4.28-2.29-6.35-3.57-11.22-6.58-21.86-14.1-31.92-22.34-34.68-28.41-61.41-66.43-76.35-108.7-3.09-8.74-5.71-17.65-7.8-26.68-1.48-6.16-2.52-12.42-3.58-18.66-.4-2.35-.61-4.73-.95-7.09-.6-3.96-.75-7.96-1.17-11.94-.8-9.47-.71-18.99-.51-28.49.14-3.51.34-7.01.7-10.51.31-3.17.46-6.37.92-9.52.41-2.81.65-5.65 1.16-8.44.7-3.94 1.3-7.9 2.12-11.82 3.43-16.52 8.47-32.73 15.26-48.18 1.15-2.92 2.59-5.72 3.86-8.59 8.05-16.71 17.9-32.56 29.49-47.06 20-25.38 45.1-46.68 73.27-62.47 7.5-4.15 15.16-8.05 23.07-11.37 15.82-6.88 32.41-11.95 49.31-15.38 3.51-.67 7.04-1.24 10.56-1.85 2.62-.47 5.28-.7 7.91-1.08 3.53-.53 7.1-.68 10.65-1.04 2.46-.24 4.91-.36 7.36-.51m8.64 24.41c-9.23.1-18.43.99-27.57 2.23-7.3 1.08-14.53 2.6-21.71 4.3-13.91 3.5-27.48 8.34-40.46 14.42-10.46 4.99-20.59 10.7-30.18 17.22-4.18 2.92-8.4 5.8-12.34 9.03-5.08 3.97-9.98 8.17-14.68 12.59-2.51 2.24-4.81 4.7-7.22 7.06-28.22 28.79-48.44 65.39-57.5 104.69-2.04 8.44-3.54 17.02-4.44 25.65-1.1 8.89-1.44 17.85-1.41 26.8.11 7.14.38 14.28 1.22 21.37.62 7.12 1.87 14.16 3.2 21.18 1.07 4.65 2.03 9.32 3.33 13.91 6.29 23.38 16.5 45.7 30.07 65.75 8.64 12.98 18.78 24.93 29.98 35.77 16.28 15.82 35.05 29.04 55.34 39.22 7.28 3.52 14.66 6.87 22.27 9.63 5.04 1.76 10.06 3.57 15.22 4.98 11.26 3.23 22.77 5.6 34.39 7.06 2.91.29 5.81.61 8.72.9 13.82 1.08 27.74 1 41.54-.43 4.45-.6 8.92-.99 13.35-1.78 3.63-.67 7.28-1.25 10.87-2.1 4.13-.98 8.28-1.91 12.36-3.07 26.5-7.34 51.58-19.71 73.58-36.2 15.78-11.82 29.96-25.76 42.12-41.28 3.26-4.02 6.17-8.31 9.13-12.55 3.39-5.06 6.58-10.25 9.6-15.54 2.4-4.44 4.74-8.91 6.95-13.45 5.69-12.05 10.28-24.62 13.75-37.49 2.59-10.01 4.75-20.16 5.9-30.45 1.77-13.47 1.94-27.1 1.29-40.65-.29-3.89-.67-7.77-1-11.66-2.23-19.08-6.79-37.91-13.82-55.8-5.95-15.13-13.53-29.63-22.61-43.13-12.69-18.8-28.24-35.68-45.97-49.83-25.05-20-54.47-34.55-85.65-42.08-7.78-1.93-15.69-3.34-23.63-4.45-3.91-.59-7.85-.82-11.77-1.24-7.39-.57-14.81-.72-22.22-.58zM139.26 83.53c13.3-8.89 28.08-15.38 43.3-20.18-3.17 1.77-6.44 3.38-9.53 5.29-11.21 6.68-21.52 14.9-30.38 24.49-6.8 7.43-12.76 15.73-17.01 24.89-3.29 6.86-5.64 14.19-6.86 21.71-.93 4.85-1.3 9.81-1.17 14.75.13 13.66 4.44 27.08 11.29 38.82 5.92 10.22 13.63 19.33 22.36 27.26 4.85 4.36 10.24 8.09 14.95 12.6 2.26 2.19 4.49 4.42 6.43 6.91 2.62 3.31 4.89 6.99 5.99 11.1.9 3.02.66 6.2.69 9.31.02 4.1-.04 8.2.03 12.3.14 3.54-.02 7.09.11 10.63.08 2.38.02 4.76.05 7.14.16 5.77.06 11.53.15 17.3.11 2.91.02 5.82.13 8.74.03 1.63.13 3.28-.03 4.91-.91.12-1.82.18-2.73.16-10.99 0-21.88-2.63-31.95-6.93-6-2.7-11.81-5.89-17.09-9.83-5.75-4.19-11.09-8.96-15.79-14.31-6.53-7.24-11.98-15.39-16.62-23.95-1.07-2.03-2.24-4.02-3.18-6.12-1.16-2.64-2.62-5.14-3.67-7.82-4.05-9.68-6.57-19.94-8.08-30.31-.49-4.44-1.09-8.88-1.2-13.35-.7-15.73.84-31.55 4.67-46.82 2.12-8.15 4.77-16.18 8.31-23.83 6.32-14.2 15.34-27.18 26.3-38.19 6.28-6.2 13.13-11.84 20.53-16.67zm175.37-20.12c2.74.74 5.41 1.74 8.09 2.68 6.36 2.33 12.68 4.84 18.71 7.96 13.11 6.44 25.31 14.81 35.82 24.97 10.2 9.95 18.74 21.6 25.14 34.34 1.28 2.75 2.64 5.46 3.81 8.26 6.31 15.1 10 31.26 11.23 47.57.41 4.54.44 9.09.45 13.64.07 11.64-1.49 23.25-4.3 34.53-1.97 7.27-4.35 14.49-7.86 21.18-3.18 6.64-6.68 13.16-10.84 19.24-6.94 10.47-15.6 19.87-25.82 27.22-10.48 7.64-22.64 13.02-35.4 15.38-3.51.69-7.08 1.08-10.66 1.21-1.85.06-3.72.16-5.56-.1-.28-2.15 0-4.31-.01-6.46-.03-3.73.14-7.45.1-11.17.19-7.02.02-14.05.21-21.07.03-2.38-.03-4.76.03-7.14.17-5.07-.04-10.14.14-15.21.1-2.99-.24-6.04.51-8.96.66-2.5 1.78-4.86 3.09-7.08 4.46-7.31 11.06-12.96 17.68-18.26 5.38-4.18 10.47-8.77 15.02-13.84 7.68-8.37 14.17-17.88 18.78-28.27 2.5-5.93 4.52-12.1 5.55-18.46.86-4.37 1.06-8.83 1.01-13.27-.02-7.85-1.4-15.65-3.64-23.17-1.75-5.73-4.27-11.18-7.09-16.45-3.87-6.93-8.65-13.31-13.96-19.2-9.94-10.85-21.75-19.94-34.6-27.1-1.85-1.02-3.84-1.82-5.63-2.97zm-100.8 58.45c.98-1.18 1.99-2.33 3.12-3.38-.61.93-1.27 1.81-1.95 2.68-3.1 3.88-5.54 8.31-7.03 13.06-.87 3.27-1.68 6.6-1.73 10-.07 2.52-.08 5.07.32 7.57 1.13 7.63 4.33 14.85 8.77 21.12 2 2.7 4.25 5.27 6.92 7.33 1.62 1.27 3.53 2.09 5.34 3.05 3.11 1.68 6.32 3.23 9.07 5.48 2.67 2.09 4.55 5.33 4.4 8.79-.01 73.67 0 147.34-.01 221.02 0 1.35-.08 2.7.04 4.04.13 1.48.82 2.83 1.47 4.15.86 1.66 1.78 3.34 3.18 4.62.85.77 1.97 1.4 3.15 1.24 1.5-.2 2.66-1.35 3.45-2.57.96-1.51 1.68-3.16 2.28-4.85.76-2.13.44-4.42.54-6.63.14-4.03-.02-8.06.14-12.09.03-5.89.03-11.77.06-17.66.14-3.62.03-7.24.11-10.86.15-4.03-.02-8.06.14-12.09.03-5.99.03-11.98.07-17.97.14-3.62.02-7.24.11-10.86.14-3.93-.02-7.86.14-11.78.03-5.99.03-11.98.06-17.97.16-3.94-.01-7.88.19-11.82.29 1.44.13 2.92.22 4.38.19 3.61.42 7.23.76 10.84.32 3.44.44 6.89.86 10.32.37 3.1.51 6.22.95 9.31.57 4.09.87 8.21 1.54 12.29 1.46 9.04 2.83 18.11 5.09 26.99 1.13 4.82 2.4 9.61 4 14.3 2.54 7.9 5.72 15.67 10.31 22.62 1.73 2.64 3.87 4.98 6.1 7.21.27.25.55.51.88.71.6.25 1.31-.07 1.7-.57.71-.88 1.17-1.94 1.7-2.93 4.05-7.8 8.18-15.56 12.34-23.31.7-1.31 1.44-2.62 2.56-3.61 1.75-1.57 3.84-2.69 5.98-3.63 2.88-1.22 5.9-2.19 9.03-2.42 6.58-.62 13.11.75 19.56 1.85 3.69.58 7.4 1.17 11.13 1.41 3.74.1 7.48.05 11.21-.28 8.55-.92 16.99-2.96 24.94-6.25 5.3-2.24 10.46-4.83 15.31-7.93 11.46-7.21 21.46-16.57 30.04-27.01 1.17-1.42 2.25-2.9 3.46-4.28-1.2 3.24-2.67 6.37-4.16 9.48-1.25 2.9-2.84 5.61-4.27 8.42-5.16 9.63-11.02 18.91-17.75 27.52-4.03 5.21-8.53 10.05-13.33 14.57-6.64 6.05-14.07 11.37-22.43 14.76-8.21 3.37-17.31 4.63-26.09 3.29-3.56-.58-7.01-1.69-10.41-2.88-2.79-.97-5.39-2.38-8.03-3.69-3.43-1.71-6.64-3.81-9.71-6.08 2.71 3.06 5.69 5.86 8.7 8.61 4.27 3.76 8.74 7.31 13.63 10.23 3.98 2.45 8.29 4.4 12.84 5.51 1.46.37 2.96.46 4.45.6-1.25 1.1-2.63 2.04-3.99 2.98-9.61 6.54-20.01 11.86-30.69 16.43-20.86 8.7-43.17 13.97-65.74 15.34-4.66.24-9.32.36-13.98.36-4.98-.11-9.97-.13-14.92-.65-11.2-.76-22.29-2.73-33.17-5.43-10.35-2.71-20.55-6.12-30.3-10.55-8.71-3.86-17.12-8.42-24.99-13.79-1.83-1.31-3.74-2.53-5.37-4.08 6.6-1.19 13.03-3.39 18.99-6.48 5.74-2.86 10.99-6.66 15.63-11.07 2.24-2.19 4.29-4.59 6.19-7.09-3.43 2.13-6.93 4.15-10.62 5.78-4.41 2.16-9.07 3.77-13.81 5.02-5.73 1.52-11.74 1.73-17.61 1.14-8.13-.95-15.86-4.27-22.51-8.98-4.32-2.94-8.22-6.43-11.96-10.06-9.93-10.16-18.2-21.81-25.66-33.86-3.94-6.27-7.53-12.75-11.12-19.22-1.05-2.04-2.15-4.05-3.18-6.1 2.85 2.92 5.57 5.97 8.43 8.88 8.99 8.97 18.56 17.44 29.16 24.48 7.55 4.9 15.67 9.23 24.56 11.03 3.11.73 6.32.47 9.47.81 2.77.28 5.56.2 8.34.3 5.05.06 10.11.04 15.16-.16 3.65-.16 7.27-.66 10.89-1.09 2.07-.25 4.11-.71 6.14-1.2 3.88-.95 8.11-.96 11.83.61 4.76 1.85 8.44 5.64 11.38 9.71 2.16 3.02 4.06 6.22 5.66 9.58 1.16 2.43 2.46 4.79 3.55 7.26 1 2.24 2.15 4.42 3.42 6.52.67 1.02 1.4 2.15 2.62 2.55 1.06-.75 1.71-1.91 2.28-3.03 2.1-4.16 3.42-8.65 4.89-13.05 2.02-6.59 3.78-13.27 5.19-20.02 2.21-9.25 3.25-18.72 4.54-28.13.56-3.98.83-7.99 1.31-11.97.87-10.64 1.9-21.27 2.24-31.94.08-1.86.24-3.71.25-5.57.01-4.35.25-8.69.22-13.03-.01-2.38-.01-4.76 0-7.13.05-5.07-.2-10.14-.22-15.21-.2-6.61-.71-13.2-1.29-19.78-.73-5.88-1.55-11.78-3.12-17.51-2.05-7.75-5.59-15.03-9.8-21.82-3.16-5.07-6.79-9.88-11.09-14.03-3.88-3.86-8.58-7.08-13.94-8.45-1.5-.41-3.06-.45-4.59-.64.07-2.99.7-5.93 1.26-8.85 1.59-7.71 3.8-15.3 6.76-22.6 1.52-4.03 3.41-7.9 5.39-11.72 3.45-6.56 7.62-12.79 12.46-18.46zm31.27 1.7c.35-.06.71-.12 1.07-.19.19 1.79.09 3.58.1 5.37v38.13c-.01 1.74.13 3.49-.15 5.22-.36-.03-.71-.05-1.06-.05-.95-3.75-1.72-7.55-2.62-11.31-.38-1.53-.58-3.09-1.07-4.59-1.7-.24-3.43-.17-5.15-.2-5.06-.01-10.13 0-15.19-.01-1.66-.01-3.32.09-4.98-.03-.03-.39-.26-.91.16-1.18 1.28-.65 2.72-.88 4.06-1.35 3.43-1.14 6.88-2.16 10.31-3.31 1.39-.48 2.9-.72 4.16-1.54.04-.56.02-1.13-.05-1.68-1.23-.55-2.53-.87-3.81-1.28-3.13-1.03-6.29-1.96-9.41-3.02-1.79-.62-3.67-1-5.41-1.79-.03-.37-.07-.73-.11-1.09 5.09-.19 10.2.06 15.3-.12 3.36-.13 6.73.08 10.09-.07.12-.39.26-.77.37-1.16 1.08-4.94 2.33-9.83 3.39-14.75zm5.97-.2c.36.05.72.12 1.08.2.98 3.85 1.73 7.76 2.71 11.61.36 1.42.56 2.88 1.03 4.27 2.53.18 5.07-.01 7.61.05 5.16.12 10.33.12 15.49.07.76-.01 1.52.03 2.28.08-.04.36-.07.72-.1 1.08-1.82.83-3.78 1.25-5.67 1.89-3.73 1.23-7.48 2.39-11.22 3.57-.57.17-1.12.42-1.67.64-.15.55-.18 1.12-.12 1.69.87.48 1.82.81 2.77 1.09 4.88 1.52 9.73 3.14 14.63 4.6.38.13.78.27 1.13.49.4.27.23.79.15 1.18-1.66.13-3.31.03-4.97.04-5.17.01-10.33-.01-15.5.01-1.61.03-3.22-.02-4.82.21-.52 1.67-.72 3.42-1.17 5.11-.94 3.57-1.52 7.24-2.54 10.78-.36.01-.71.02-1.06.06-.29-1.73-.15-3.48-.15-5.22v-38.13c.02-1.78-.08-3.58.11-5.37zM65.05 168.33c1.12-2.15 2.08-4.4 3.37-6.46-1.82 7.56-2.91 15.27-3.62 23-.8 7.71-.85 15.49-.54 23.23 1.05 19.94 5.54 39.83 14.23 57.88 2.99 5.99 6.35 11.83 10.5 17.11 6.12 7.47 12.53 14.76 19.84 21.09 4.8 4.1 9.99 7.78 15.54 10.8 3.27 1.65 6.51 3.39 9.94 4.68 5.01 2.03 10.19 3.61 15.42 4.94 3.83.96 7.78 1.41 11.52 2.71 5 1.57 9.47 4.61 13.03 8.43 4.93 5.23 8.09 11.87 10.2 18.67.99 2.9 1.59 5.91 2.17 8.92.15.75.22 1.52.16 2.29-6.5 2.78-13.26 5.06-20.26 6.18-4.11.78-8.29.99-12.46 1.08-10.25.24-20.47-1.76-30.12-5.12-3.74-1.42-7.49-2.85-11.03-4.72-8.06-3.84-15.64-8.7-22.46-14.46-2.92-2.55-5.83-5.13-8.4-8.03-9.16-9.83-16.3-21.41-21.79-33.65-2.39-5.55-4.61-11.18-6.37-16.96-1.17-3.94-2.36-7.89-3.26-11.91-.75-2.94-1.22-5.95-1.87-8.92-.46-2.14-.69-4.32-1.03-6.48-.85-5.43-1.28-10.93-1.33-16.43.11-6.18.25-12.37 1.07-18.5.4-2.86.67-5.74 1.15-8.6.98-5.7 2.14-11.37 3.71-16.93 3.09-11.65 7.48-22.95 12.69-33.84zm363.73-6.44c1.1 1.66 1.91 3.48 2.78 5.26 2.1 4.45 4.24 8.9 6.02 13.49 7.61 18.76 12.3 38.79 13.04 59.05.02 1.76.07 3.52.11 5.29.13 9.57-1.27 19.09-3.18 28.45-.73 3.59-1.54 7.17-2.58 10.69-4.04 14.72-10 29-18.41 41.78-8.21 12.57-19.01 23.55-31.84 31.41-5.73 3.59-11.79 6.64-18.05 9.19-5.78 2.19-11.71 4.03-17.8 5.11-6.4 1.05-12.91 1.52-19.4 1.23-7.92-.48-15.78-2.07-23.21-4.85-1.94-.8-3.94-1.46-5.84-2.33-.21-1.51.25-2.99.53-4.46 1.16-5.74 3.03-11.36 5.7-16.58 2.37-4.51 5.52-8.65 9.46-11.9 2.43-2.05 5.24-3.61 8.16-4.83 3.58-1.5 7.47-1.97 11.24-2.83 7.23-1.71 14.37-3.93 21.15-7 10.35-4.65 19.71-11.38 27.65-19.46 1.59-1.61 3.23-3.18 4.74-4.87 3.37-3.76 6.71-7.57 9.85-11.53 7.48-10.07 12.82-21.59 16.71-33.48 1.58-5.3 3.21-10.6 4.21-16.05.63-2.87 1.04-5.78 1.52-8.68.87-6.09 1.59-12.22 1.68-18.38.12-6.65.14-13.32-.53-19.94-.73-7.99-1.87-15.96-3.71-23.78z"],
+ "opencart": [640, 512, [], "f23d", "M423.3 440.7c0 25.3-20.3 45.6-45.6 45.6s-45.8-20.3-45.8-45.6 20.6-45.8 45.8-45.8c25.4 0 45.6 20.5 45.6 45.8zm-253.9-45.8c-25.3 0-45.6 20.6-45.6 45.8s20.3 45.6 45.6 45.6 45.8-20.3 45.8-45.6-20.5-45.8-45.8-45.8zm291.7-270C158.9 124.9 81.9 112.1 0 25.7c34.4 51.7 53.3 148.9 373.1 144.2 333.3-5 130 86.1 70.8 188.9 186.7-166.7 319.4-233.9 17.2-233.9z"],
+ "openid": [448, 512, [], "f19b", "M271.5 432l-68 32C88.5 453.7 0 392.5 0 318.2c0-71.5 82.5-131 191.7-144.3v43c-71.5 12.5-124 53-124 101.3 0 51 58.5 93.3 135.7 103v-340l68-33.2v384zM448 291l-131.3-28.5 36.8-20.7c-19.5-11.5-43.5-20-70-24.8v-43c46.2 5.5 87.7 19.5 120.3 39.3l35-19.8L448 291z"],
+ "opera": [496, 512, [], "f26a", "M313.9 32.7c-170.2 0-252.6 223.8-147.5 355.1 36.5 45.4 88.6 75.6 147.5 75.6 36.3 0 70.3-11.1 99.4-30.4-43.8 39.2-101.9 63-165.3 63-3.9 0-8 0-11.9-.3C104.6 489.6 0 381.1 0 248 0 111 111 0 248 0h.8c63.1.3 120.7 24.1 164.4 63.1-29-19.4-63.1-30.4-99.3-30.4zm101.8 397.7c-40.9 24.7-90.7 23.6-132-5.8 56.2-20.5 97.7-91.6 97.7-176.6 0-84.7-41.2-155.8-97.4-176.6 41.8-29.2 91.2-30.3 132.9-5 105.9 98.7 105.5 265.7-1.2 364z"],
+ "optin-monster": [576, 512, [], "f23c", "M572.6 421.4c5.6-9.5 4.7-15.2-5.4-11.6-3-4.9-7-9.5-11.1-13.8 2.9-9.7-.7-14.2-10.8-9.2-4.6-3.2-10.3-6.5-15.9-9.2 0-15.1-11.6-11.6-17.6-5.7-10.4-1.5-18.7-.3-26.8 5.7.3-6.5.3-13 .3-19.7 12.6 0 40.2-11 45.9-36.2 1.4-6.8 1.6-13.8-.3-21.9-3-13.5-14.3-21.3-25.1-25.7-.8-5.9-7.6-14.3-14.9-15.9s-12.4 4.9-14.1 10.3c-8.5 0-19.2 2.8-21.1 8.4-5.4-.5-11.1-1.4-16.8-1.9 2.7-1.9 5.4-3.5 8.4-4.6 5.4-9.2 14.6-11.4 25.7-11.6V256c19.5-.5 43-5.9 53.8-18.1 12.7-13.8 14.6-37.3 12.4-55.1-2.4-17.3-9.7-37.6-24.6-48.1-8.4-5.9-21.6-.8-22.7 9.5-2.2 19.6 1.2 30-38.6 25.1-10.3-23.8-24.6-44.6-42.7-60C341 49.6 242.9 55.5 166.4 71.7c19.7 4.6 41.1 8.6 59.7 16.5-26.2 2.4-52.7 11.3-76.2 23.2-32.8 17-44 29.9-56.7 42.4 14.9-2.2 28.9-5.1 43.8-3.8-9.7 5.4-18.4 12.2-26.5 20-25.8.9-23.8-5.3-26.2-25.9-1.1-10.5-14.3-15.4-22.7-9.7-28.1 19.9-33.5 79.9-12.2 103.5 10.8 12.2 35.1 17.3 54.9 17.8-.3 1.1-.3 1.9-.3 2.7 10.8.5 19.5 2.7 24.6 11.6 3 1.1 5.7 2.7 8.1 4.6-5.4.5-11.1 1.4-16.5 1.9-3.3-6.6-13.7-8.1-21.1-8.1-1.6-5.7-6.5-12.2-14.1-10.3-6.8 1.9-14.1 10-14.9 15.9-22.5 9.5-30.1 26.8-25.1 47.6 5.3 24.8 33 36.2 45.9 36.2v19.7c-6.6-5-14.3-7.5-26.8-5.7-5.5-5.5-17.3-10.1-17.3 5.7-5.9 2.7-11.4 5.9-15.9 9.2-9.8-4.9-13.6-1.7-11.1 9.2-4.1 4.3-7.8 8.6-11.1 13.8-10.2-3.7-11 2.2-5.4 11.6-1.1 3.5-1.6 7-1.9 10.8-.5 31.6 44.6 64 73.5 65.1 17.3.5 34.6-8.4 43-23.5 113.2 4.9 226.7 4.1 340.2 0 8.1 15.1 25.4 24.3 42.7 23.5 29.2-1.1 74.3-33.5 73.5-65.1.2-3.7-.7-7.2-1.7-10.7zm-73.8-254c1.1-3 2.4-8.4 2.4-14.6 0-5.9 6.8-8.1 14.1-.8 11.1 11.6 14.9 40.5 13.8 51.1-4.1-13.6-13-29-30.3-35.7zm-4.6 6.7c19.5 6.2 28.6 27.6 29.7 48.9-1.1 2.7-3 5.4-4.9 7.6-5.7 5.9-15.4 10-26.2 12.2 4.3-21.3.3-47.3-12.7-63 4.9-.8 10.9-2.4 14.1-5.7zm-24.1 6.8c13.8 11.9 20 39.2 14.1 63.5-4.1.5-8.1.8-11.6.8-1.9-21.9-6.8-44-14.3-64.6 3.7.3 8.1.3 11.8.3zM47.5 203c-1.1-10.5 2.4-39.5 13.8-51.1 7-7.3 14.1-5.1 14.1.8 0 6.2 1.4 11.6 2.4 14.6-17.3 6.8-26.2 22.2-30.3 35.7zm9.7 27.6c-1.9-2.2-3.5-4.9-4.9-7.6 1.4-21.3 10.3-42.7 29.7-48.9 3.2 3.2 9.2 4.9 14.1 5.7-13 15.7-17 41.6-12.7 63-10.8-2.2-20.5-6-26.2-12.2zm47.9 14.6c-4.1 0-8.1-.3-12.7-.8-4.6-18.6-1.9-38.9 5.4-53v.3l12.2-5.1c4.9-1.9 9.7-3.8 14.9-4.9-10.7 19.7-17.4 41.3-19.8 63.5zm184-162.7c41.9 0 76.2 34 76.2 75.9 0 42.2-34.3 76.2-76.2 76.2s-76.2-34-76.2-76.2c0-41.8 34.3-75.9 76.2-75.9zm115.6 174.3c-.3 17.8-7 48.9-23 57-13.2 6.6-6.5-7.5-16.5-58.1 13.3.3 26.6.3 39.5 1.1zm-54-1.6c.8 4.9 3.8 40.3-1.6 41.9-11.6 3.5-40 4.3-51.1-1.1-4.1-3-4.6-35.9-4.3-41.1v.3c18.9-.3 38.1-.3 57 0zM278.3 309c-13 3.5-41.6 4.1-54.6-1.6-6.5-2.7-3.8-42.4-1.9-51.6 19.2-.5 38.4-.5 57.8-.8v.3c1.1 8.3 3.3 51.2-1.3 53.7zm-106.5-51.1c12.2-.8 24.6-1.4 36.8-1.6-2.4 15.4-3 43.5-4.9 52.2-1.1 6.8-4.3 6.8-9.7 4.3-21.9-9.8-27.6-35.2-22.2-54.9zm-35.4 31.3c7.8-1.1 15.7-1.9 23.5-2.7 1.6 6.2 3.8 11.9 7 17.6 10 17 44 35.7 45.1 7 6.2 14.9 40.8 12.2 54.9 10.8 15.7-1.4 23.8-1.4 26.8-14.3 12.4 4.3 30.8 4.1 44 3 11.3-.8 20.8-.5 24.6-8.9 1.1 5.1 1.9 11.6 4.6 16.8 10.8 21.3 37.3 1.4 46.8-31.6 8.6.8 17.6 1.9 26.5 2.7-.4 1.3-3.8 7.3 7.3 11.6-47.6 47-95.7 87.8-163.2 107-63.2-20.8-112.1-59.5-155.9-106.5 9.6-3.4 10.4-8.8 8-12.5zm-21.6 172.5c-3.8 17.8-21.9 29.7-39.7 28.9-19.2-.8-46.5-17-59.2-36.5-2.7-31.1 43.8-61.3 66.2-54.6 14.9 4.3 27.8 30.8 33.5 54 0 3-.3 5.7-.8 8.2zm-8.7-66c-.5-13.5-.5-27-.3-40.5h.3c2.7-1.6 5.7-3.8 7.8-6.5 6.5-1.6 13-5.1 15.1-9.2 3.3-7.1-7-7.5-5.4-12.4 2.7-1.1 5.7-2.2 7.8-3.5 29.2 29.2 58.6 56.5 97.3 77-36.8 11.3-72.4 27.6-105.9 47-1.2-18.6-7.7-35.9-16.7-51.9zm337.6 64.6c-103 3.5-206.2 4.1-309.4 0 0 .3 0 .3-.3.3v-.3h.3c35.1-21.6 72.2-39.2 112.4-50.8 11.6 5.1 23 9.5 34.9 13.2 2.2.8 2.2.8 4.3 0 14.3-4.1 28.4-9.2 42.2-15.4 41.5 11.7 78.8 31.7 115.6 53zm10.5-12.4c-35.9-19.5-73-35.9-111.9-47.6 38.1-20 71.9-47.3 103.5-76.7 2.2 1.4 4.6 2.4 7.6 3.2 0 .8.3 1.9.5 2.4-4.6 2.7-7.8 6.2-5.9 10.3 2.2 3.8 8.6 7.6 15.1 8.9 2.4 2.7 5.1 5.1 8.1 6.8 0 13.8-.3 27.6-.8 41.3l.3-.3c-9.3 15.9-15.5 37-16.5 51.7zm105.9 6.2c-12.7 19.5-40 35.7-59.2 36.5-19.3.9-40.5-13.2-40.5-37 5.7-23.2 18.9-49.7 33.5-54 22.7-6.9 69.2 23.4 66.2 54.5zM372.9 75.2c-3.8-72.1-100.8-79.7-126-23.5 44.6-24.3 90.3-15.7 126 23.5zM74.8 407.1c-15.7 1.6-49.5 25.4-49.5 43.2 0 11.6 15.7 19.5 32.2 14.9 12.2-3.2 31.1-17.6 35.9-27.3 6-11.6-3.7-32.7-18.6-30.8zm215.9-176.2c28.6 0 51.9-21.6 51.9-48.4 0-36.1-40.5-58.1-72.2-44.3 9.5 3 16.5 11.6 16.5 21.6 0 23.3-33.3 32-46.5 11.3-7.3 34.1 19.4 59.8 50.3 59.8zM68 474.1c.5 6.5 12.2 12.7 21.6 9.5 6.8-2.7 14.6-10.5 17.3-16.2 3-7-1.1-20-9.7-18.4-8.9 1.6-29.7 16.7-29.2 25.1zm433.2-67c-14.9-1.9-24.6 19.2-18.9 30.8 4.9 9.7 24.1 24.1 36.2 27.3 16.5 4.6 32.2-3.2 32.2-14.9 0-17.8-33.8-41.6-49.5-43.2zM478.8 449c-8.4-1.6-12.4 11.3-9.5 18.4 2.4 5.7 10.3 13.5 17.3 16.2 9.2 3.2 21.1-3 21.3-9.5.9-8.4-20.2-23.5-29.1-25.1z"],
+ "orcid": [512, 512, [], "f8d2", "M294.75 188.19h-45.92V342h47.47c67.62 0 83.12-51.34 83.12-76.91 0-41.64-26.54-76.9-84.67-76.9zM256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm-80.79 360.76h-29.84v-207.5h29.84zm-14.92-231.14a19.57 19.57 0 1 1 19.57-19.57 19.64 19.64 0 0 1-19.57 19.57zM300 369h-81V161.26h80.6c76.73 0 110.44 54.83 110.44 103.85C410 318.39 368.38 369 300 369z"],
+ "osi": [512, 512, [], "f41a", "M8 266.44C10.3 130.64 105.4 34 221.8 18.34c138.8-18.6 255.6 75.8 278 201.1 21.3 118.8-44 230-151.6 274-9.3 3.8-14.4 1.7-18-7.7q-26.7-69.45-53.4-139c-3.1-8.1-1-13.2 7-16.8 24.2-11 39.3-29.4 43.3-55.8a71.47 71.47 0 0 0-64.5-82.2c-39-3.4-71.8 23.7-77.5 59.7-5.2 33 11.1 63.7 41.9 77.7 9.6 4.4 11.5 8.6 7.8 18.4q-26.85 69.9-53.7 139.9c-2.6 6.9-8.3 9.3-15.5 6.5-52.6-20.3-101.4-61-130.8-119-24.9-49.2-25.2-87.7-26.8-108.7zm20.9-1.9c.4 6.6.6 14.3 1.3 22.1 6.3 71.9 49.6 143.5 131 183.1 3.2 1.5 4.4.8 5.6-2.3q22.35-58.65 45-117.3c1.3-3.3.6-4.8-2.4-6.7-31.6-19.9-47.3-48.5-45.6-86 1-21.6 9.3-40.5 23.8-56.3 30-32.7 77-39.8 115.5-17.6a91.64 91.64 0 0 1 45.2 90.4c-3.6 30.6-19.3 53.9-45.7 69.8-2.7 1.6-3.5 2.9-2.3 6q22.8 58.8 45.2 117.7c1.2 3.1 2.4 3.8 5.6 2.3 35.5-16.6 65.2-40.3 88.1-72 34.8-48.2 49.1-101.9 42.3-161-13.7-117.5-119.4-214.8-255.5-198-106.1 13-195.3 102.5-197.1 225.8z"],
+ "page4": [496, 512, [], "f3d7", "M248 504C111 504 0 393 0 256S111 8 248 8c20.9 0 41.3 2.6 60.7 7.5L42.3 392H248v112zm0-143.6V146.8L98.6 360.4H248zm96 31.6v92.7c45.7-19.2 84.5-51.7 111.4-92.7H344zm57.4-138.2l-21.2 8.4 21.2 8.3v-16.7zm-20.3 54.5c-6.7 0-8 6.3-8 12.9v7.7h16.2v-10c0-5.9-2.3-10.6-8.2-10.6zM496 256c0 37.3-8.2 72.7-23 104.4H344V27.3C433.3 64.8 496 153.1 496 256zM360.4 143.6h68.2V96h-13.9v32.6h-13.9V99h-13.9v29.6h-12.7V96h-13.9v47.6zm68.1 185.3H402v-11c0-15.4-5.6-25.2-20.9-25.2-15.4 0-20.7 10.6-20.7 25.9v25.3h68.2v-15zm0-103l-68.2 29.7V268l68.2 29.5v-16.6l-14.4-5.7v-26.5l14.4-5.9v-16.9zm-4.8-68.5h-35.6V184H402v-12.2h11c8.6 15.8 1.3 35.3-18.6 35.3-22.5 0-28.3-25.3-15.5-37.7l-11.6-10.6c-16.2 17.5-12.2 63.9 27.1 63.9 34 0 44.7-35.9 29.3-65.3z"],
+ "pagelines": [384, 512, [], "f18c", "M384 312.7c-55.1 136.7-187.1 54-187.1 54-40.5 81.8-107.4 134.4-184.6 134.7-16.1 0-16.6-24.4 0-24.4 64.4-.3 120.5-42.7 157.2-110.1-41.1 15.9-118.6 27.9-161.6-82.2 109-44.9 159.1 11.2 178.3 45.5 9.9-24.4 17-50.9 21.6-79.7 0 0-139.7 21.9-149.5-98.1 119.1-47.9 152.6 76.7 152.6 76.7 1.6-16.7 3.3-52.6 3.3-53.4 0 0-106.3-73.7-38.1-165.2 124.6 43 61.4 162.4 61.4 162.4.5 1.6.5 23.8 0 33.4 0 0 45.2-89 136.4-57.5-4.2 134-141.9 106.4-141.9 106.4-4.4 27.4-11.2 53.4-20 77.5 0 0 83-91.8 172-20z"],
+ "palfed": [576, 512, [], "f3d8", "M384.9 193.9c0-47.4-55.2-44.2-95.4-29.8-1.3 39.4-2.5 80.7-3 119.8.7 2.8 2.6 6.2 15.1 6.2 36.8 0 83.4-42.8 83.3-96.2zm-194.5 72.2c.2 0 6.5-2.7 11.2-2.7 26.6 0 20.7 44.1-14.4 44.1-21.5 0-37.1-18.1-37.1-43 0-42 42.9-95.6 100.7-126.5 1-12.4 3-22 10.5-28.2 11.2-9 26.6-3.5 29.5 11.1 72.2-22.2 135.2 1 135.2 72 0 77.9-79.3 152.6-140.1 138.2-.1 39.4.9 74.4 2.7 100v.2c.2 3.4.6 12.5-5.3 19.1-9.6 10.6-33.4 10-36.4-22.3-4.1-44.4.2-206.1 1.4-242.5-21.5 15-58.5 50.3-58.5 75.9.2 2.5.4 4 .6 4.6zM8 181.1s-.1 37.4 38.4 37.4h30l22.4 217.2s0 44.3 44.7 44.3h288.9s44.7-.4 44.7-44.3l22.4-217.2h30s38.4 1.2 38.4-37.4c0 0 .1-37.4-38.4-37.4h-30.1c-7.3-25.6-30.2-74.3-119.4-74.3h-28V50.3s-2.7-18.4-21.1-18.4h-85.8s-21.1 0-21.1 18.4v19.1h-28.1s-105 4.2-120.5 74.3h-29S8 142.5 8 181.1z"],
+ "patreon": [512, 512, [], "f3d9", "M512 194.8c0 101.3-82.4 183.8-183.8 183.8-101.7 0-184.4-82.4-184.4-183.8 0-101.6 82.7-184.3 184.4-184.3C429.6 10.5 512 93.2 512 194.8zM0 501.5h90v-491H0v491z"],
+ "paypal": [384, 512, [], "f1ed", "M111.4 295.9c-3.5 19.2-17.4 108.7-21.5 134-.3 1.8-1 2.5-3 2.5H12.3c-7.6 0-13.1-6.6-12.1-13.9L58.8 46.6c1.5-9.6 10.1-16.9 20-16.9 152.3 0 165.1-3.7 204 11.4 60.1 23.3 65.6 79.5 44 140.3-21.5 62.6-72.5 89.5-140.1 90.3-43.4.7-69.5-7-75.3 24.2zM357.1 152c-1.8-1.3-2.5-1.8-3 1.3-2 11.4-5.1 22.5-8.8 33.6-39.9 113.8-150.5 103.9-204.5 103.9-6.1 0-10.1 3.3-10.9 9.4-22.6 140.4-27.1 169.7-27.1 169.7-1 7.1 3.5 12.9 10.6 12.9h63.5c8.6 0 15.7-6.3 17.4-14.9.7-5.4-1.1 6.1 14.4-91.3 4.6-22 14.3-19.7 29.3-19.7 71 0 126.4-28.8 142.9-112.3 6.5-34.8 4.6-71.4-23.8-92.6z"],
+ "penny-arcade": [640, 512, [], "f704", "M421.91 164.27c-4.49 19.45-1.4 6.06-15.1 65.29l39.73-10.61c-22.34-49.61-17.29-38.41-24.63-54.68zm-206.09 51.11c-20.19 5.4-11.31 3.03-39.63 10.58l4.46 46.19c28.17-7.59 20.62-5.57 34.82-9.34 42.3-9.79 32.85-56.42.35-47.43zm326.16-26.19l-45.47-99.2c-5.69-12.37-19.46-18.84-32.62-15.33-70.27 18.75-38.72 10.32-135.59 36.23a27.618 27.618 0 0 0-18.89 17.41C144.26 113.27 0 153.75 0 226.67c0 33.5 30.67 67.11 80.9 95.37l1.74 17.88a27.891 27.891 0 0 0-17.77 28.67l4.3 44.48c1.39 14.31 13.43 25.21 27.8 25.2 5.18-.01-3.01 1.78 122.53-31.76 12.57-3.37 21.12-15.02 20.58-28.02 216.59 45.5 401.99-5.98 399.89-84.83.01-28.15-22.19-66.56-97.99-104.47zM255.14 298.3l-21.91 5.88-48.44 12.91 2.46 23.55 20.53-5.51 4.51 44.51-115.31 30.78-4.3-44.52 20.02-5.35-11.11-114.64-20.12 5.39-4.35-44.5c178.15-47.54 170.18-46.42 186.22-46.65 56.66-1.13 64.15 71.84 42.55 104.43a86.7 86.7 0 0 1-50.75 33.72zm199.18 16.62l-3.89-39.49 14.9-3.98-6.61-14.68-57.76 15.42-4.1 17.54 19.2-5.12 4.05 39.54-112.85 30.07-4.46-44.43 20.99-5.59 33.08-126.47-17.15 4.56-4.2-44.48c93.36-24.99 65.01-17.41 135.59-36.24l66.67 145.47 20.79-5.56 4.3 44.48-108.55 28.96z"],
+ "perbyte": [448, 512, [], "e083", "M305.314,284.578H246.6V383.3h58.711q24.423,0,38.193-13.77t13.77-36.11q0-21.826-14.032-35.335T305.314,284.578ZM149.435,128.7H90.724v98.723h58.711q24.42,0,38.19-13.773t13.77-36.107q0-21.826-14.029-35.338T149.435,128.7ZM366.647,32H81.353A81.445,81.445,0,0,0,0,113.352V398.647A81.445,81.445,0,0,0,81.353,480H366.647A81.445,81.445,0,0,0,448,398.647V113.352A81.445,81.445,0,0,0,366.647,32Zm63.635,366.647a63.706,63.706,0,0,1-63.635,63.635H81.353a63.706,63.706,0,0,1-63.635-63.635V113.352A63.706,63.706,0,0,1,81.353,49.718H366.647a63.706,63.706,0,0,1,63.635,63.634ZM305.314,128.7H246.6v98.723h58.711q24.423,0,38.193-13.773t13.77-36.107q0-21.826-14.032-35.338T305.314,128.7Z"],
+ "periscope": [448, 512, [], "f3da", "M370 63.6C331.4 22.6 280.5 0 226.6 0 111.9 0 18.5 96.2 18.5 214.4c0 75.1 57.8 159.8 82.7 192.7C137.8 455.5 192.6 512 226.6 512c41.6 0 112.9-94.2 120.9-105 24.6-33.1 82-118.3 82-192.6 0-56.5-21.1-110.1-59.5-150.8zM226.6 493.9c-42.5 0-190-167.3-190-279.4 0-107.4 83.9-196.3 190-196.3 100.8 0 184.7 89 184.7 196.3.1 112.1-147.4 279.4-184.7 279.4zM338 206.8c0 59.1-51.1 109.7-110.8 109.7-100.6 0-150.7-108.2-92.9-181.8v.4c0 24.5 20.1 44.4 44.8 44.4 24.7 0 44.8-19.9 44.8-44.4 0-18.2-11.1-33.8-26.9-40.7 76.6-19.2 141 39.3 141 112.4z"],
+ "phabricator": [496, 512, [], "f3db", "M323 262.1l-.1-13s21.7-19.8 21.1-21.2l-9.5-20c-.6-1.4-29.5-.5-29.5-.5l-9.4-9.3s.2-28.5-1.2-29.1l-20.1-9.2c-1.4-.6-20.7 21-20.7 21l-13.1-.2s-20.5-21.4-21.9-20.8l-20 8.3c-1.4.5.2 28.9.2 28.9l-9.1 9.1s-29.2-.9-29.7.4l-8.1 19.8c-.6 1.4 21 21 21 21l.1 12.9s-21.7 19.8-21.1 21.2l9.5 20c.6 1.4 29.5.5 29.5.5l9.4 9.3s-.2 31.8 1.2 32.3l20.1 8.3c1.4.6 20.7-23.5 20.7-23.5l13.1.2s20.5 23.8 21.8 23.3l20-7.5c1.4-.6-.2-32.1-.2-32.1l9.1-9.1s29.2.9 29.7-.5l8.1-19.8c.7-1.1-20.9-20.7-20.9-20.7zm-44.9-8.7c.7 17.1-12.8 31.6-30.1 32.4-17.3.8-32.1-12.5-32.8-29.6-.7-17.1 12.8-31.6 30.1-32.3 17.3-.8 32.1 12.5 32.8 29.5zm201.2-37.9l-97-97-.1.1c-75.1-73.3-195.4-72.8-269.8 1.6-50.9 51-27.8 27.9-95.7 95.3-22.3 22.3-22.3 58.7 0 81 69.9 69.4 46.4 46 97.4 97l.1-.1c75.1 73.3 195.4 72.9 269.8-1.6 51-50.9 27.9-27.9 95.3-95.3 22.3-22.3 22.3-58.7 0-81zM140.4 363.8c-59.6-59.5-59.6-156 0-215.5 59.5-59.6 156-59.5 215.6 0 59.5 59.5 59.6 156 0 215.6-59.6 59.5-156 59.4-215.6-.1z"],
+ "phoenix-framework": [640, 512, [], "f3dc", "M212.9 344.3c3.8-.1 22.8-1.4 25.6-2.2-2.4-2.6-43.6-1-68-49.6-4.3-8.6-7.5-17.6-6.4-27.6 2.9-25.5 32.9-30 52-18.5 36 21.6 63.3 91.3 113.7 97.5 37 4.5 84.6-17 108.2-45.4-.6-.1-.8-.2-1-.1-.4.1-.8.2-1.1.3-33.3 12.1-94.3 9.7-134.7-14.8-37.6-22.8-53.1-58.7-51.8-74.6 1.8-21.3 22.9-23.2 35.9-19.6 14.4 3.9 24.4 17.6 38.9 27.4 15.6 10.4 32.9 13.7 51.3 10.3 14.9-2.7 34.4-12.3 36.5-14.5-1.1-.1-1.8-.1-2.5-.2-6.2-.6-12.4-.8-18.5-1.7C279.8 194.5 262.1 47.4 138.5 37.9 94.2 34.5 39.1 46 2.2 72.9c-.8.6-1.5 1.2-2.2 1.8.1.2.1.3.2.5.8 0 1.6-.1 2.4-.2 6.3-1 12.5-.8 18.7.3 23.8 4.3 47.7 23.1 55.9 76.5 5.3 34.3-.7 50.8 8 86.1 19 77.1 91 107.6 127.7 106.4zM75.3 64.9c-.9-1-.9-1.2-1.3-2 12.1-2.6 24.2-4.1 36.6-4.8-1.1 14.7-22.2 21.3-35.3 6.8zm196.9 350.5c-42.8 1.2-92-26.7-123.5-61.4-4.6-5-16.8-20.2-18.6-23.4l.4-.4c6.6 4.1 25.7 18.6 54.8 27 24.2 7 48.1 6.3 71.6-3.3 22.7-9.3 41-.5 43.1 2.9-18.5 3.8-20.1 4.4-24 7.9-5.1 4.4-4.6 11.7 7 17.2 26.2 12.4 63-2.8 97.2 25.4 2.4 2 8.1 7.8 10.1 10.7-.1.2-.3.3-.4.5-4.8-1.5-16.4-7.5-40.2-9.3-24.7-2-46.3 5.3-77.5 6.2zm174.8-252c16.4-5.2 41.3-13.4 66.5-3.3 16.1 6.5 26.2 18.7 32.1 34.6 3.5 9.4 5.1 19.7 5.1 28.7-.2 0-.4 0-.6.1-.2-.4-.4-.9-.5-1.3-5-22-29.9-43.8-67.6-29.9-50.2 18.6-130.4 9.7-176.9-48-.7-.9-2.4-1.7-1.3-3.2.1-.2 2.1.6 3 1.3 18.1 13.4 38.3 21.9 60.3 26.2 30.5 6.1 54.6 2.9 79.9-5.2zm102.7 117.5c-32.4.2-33.8 50.1-103.6 64.4-18.2 3.7-38.7 4.6-44.9 4.2v-.4c2.8-1.5 14.7-2.6 29.7-16.6 7.9-7.3 15.3-15.1 22.8-22.9 19.5-20.2 41.4-42.2 81.9-39 23.1 1.8 29.3 8.2 36.1 12.7.3.2.4.5.7.9-.5 0-.7.1-.9 0-7-2.7-14.3-3.3-21.8-3.3zm-12.3-24.1c-.1.2-.1.4-.2.6-28.9-4.4-48-7.9-68.5 4-17 9.9-31.4 20.5-62 24.4-27.1 3.4-45.1 2.4-66.1-8-.3-.2-.6-.4-1-.6 0-.2.1-.3.1-.5 24.9 3.8 36.4 5.1 55.5-5.8 22.3-12.9 40.1-26.6 71.3-31 29.6-4.1 51.3 2.5 70.9 16.9zM268.6 97.3c-.6-.6-1.1-1.2-2.1-2.3 7.6 0 29.7-1.2 53.4 8.4 19.7 8 32.2 21 50.2 32.9 11.1 7.3 23.4 9.3 36.4 8.1 4.3-.4 8.5-1.2 12.8-1.7.4-.1.9 0 1.5.3-.6.4-1.2.9-1.8 1.2-8.1 4-16.7 6.3-25.6 7.1-26.1 2.6-50.3-3.7-73.4-15.4-19.3-9.9-36.4-22.9-51.4-38.6zM640 335.7c-3.5 3.1-22.7 11.6-42.7 5.3-12.3-3.9-19.5-14.9-31.6-24.1-10-7.6-20.9-7.9-28.1-8.4.6-.8.9-1.2 1.2-1.4 14.8-9.2 30.5-12.2 47.3-6.5 12.5 4.2 19.2 13.5 30.4 24.2 10.8 10.4 21 9.9 23.1 10.5.1-.1.2 0 .4.4zm-212.5 137c2.2 1.2 1.6 1.5 1.5 2-18.5-1.4-33.9-7.6-46.8-22.2-21.8-24.7-41.7-27.9-48.6-29.7.5-.2.8-.4 1.1-.4 13.1.1 26.1.7 38.9 3.9 25.3 6.4 35 25.4 41.6 35.3 3.2 4.8 7.3 8.3 12.3 11.1z"],
+ "phoenix-squadron": [512, 512, [], "f511", "M96 63.38C142.49 27.25 201.55 7.31 260.51 8.81c29.58-.38 59.11 5.37 86.91 15.33-24.13-4.63-49-6.34-73.38-2.45C231.17 27 191 48.84 162.21 80.87c5.67-1 10.78-3.67 16-5.86 18.14-7.87 37.49-13.26 57.23-14.83 19.74-2.13 39.64-.43 59.28 1.92-14.42 2.79-29.12 4.57-43 9.59-34.43 11.07-65.27 33.16-86.3 62.63-13.8 19.71-23.63 42.86-24.67 67.13-.35 16.49 5.22 34.81 19.83 44a53.27 53.27 0 0 0 37.52 6.74c15.45-2.46 30.07-8.64 43.6-16.33 11.52-6.82 22.67-14.55 32-24.25 3.79-3.22 2.53-8.45 2.62-12.79-2.12-.34-4.38-1.11-6.3.3a203 203 0 0 1-35.82 15.37c-20 6.17-42.16 8.46-62.1.78 12.79 1.73 26.06.31 37.74-5.44 20.23-9.72 36.81-25.2 54.44-38.77a526.57 526.57 0 0 1 88.9-55.31c25.71-12 52.94-22.78 81.57-24.12-15.63 13.72-32.15 26.52-46.78 41.38-14.51 14-27.46 29.5-40.11 45.18-3.52 4.6-8.95 6.94-13.58 10.16a150.7 150.7 0 0 0-51.89 60.1c-9.33 19.68-14.5 41.85-11.77 63.65 1.94 13.69 8.71 27.59 20.9 34.91 12.9 8 29.05 8.07 43.48 5.1 32.8-7.45 61.43-28.89 81-55.84 20.44-27.52 30.52-62.2 29.16-96.35-.52-7.5-1.57-15-1.66-22.49 8 19.48 14.82 39.71 16.65 60.83 2 14.28.75 28.76-1.62 42.9-1.91 11-5.67 21.51-7.78 32.43a165 165 0 0 0 39.34-81.07 183.64 183.64 0 0 0-14.21-104.64c20.78 32 32.34 69.58 35.71 107.48.49 12.73.49 25.51 0 38.23A243.21 243.21 0 0 1 482 371.34c-26.12 47.34-68 85.63-117.19 108-78.29 36.23-174.68 31.32-248-14.68A248.34 248.34 0 0 1 25.36 366 238.34 238.34 0 0 1 0 273.08v-31.34C3.93 172 40.87 105.82 96 63.38m222 80.33a79.13 79.13 0 0 0 16-4.48c5-1.77 9.24-5.94 10.32-11.22-8.96 4.99-17.98 9.92-26.32 15.7z"],
+ "php": [640, 512, [], "f457", "M320 104.5c171.4 0 303.2 72.2 303.2 151.5S491.3 407.5 320 407.5c-171.4 0-303.2-72.2-303.2-151.5S148.7 104.5 320 104.5m0-16.8C143.3 87.7 0 163 0 256s143.3 168.3 320 168.3S640 349 640 256 496.7 87.7 320 87.7zM218.2 242.5c-7.9 40.5-35.8 36.3-70.1 36.3l13.7-70.6c38 0 63.8-4.1 56.4 34.3zM97.4 350.3h36.7l8.7-44.8c41.1 0 66.6 3 90.2-19.1 26.1-24 32.9-66.7 14.3-88.1-9.7-11.2-25.3-16.7-46.5-16.7h-70.7L97.4 350.3zm185.7-213.6h36.5l-8.7 44.8c31.5 0 60.7-2.3 74.8 10.7 14.8 13.6 7.7 31-8.3 113.1h-37c15.4-79.4 18.3-86 12.7-92-5.4-5.8-17.7-4.6-47.4-4.6l-18.8 96.6h-36.5l32.7-168.6zM505 242.5c-8 41.1-36.7 36.3-70.1 36.3l13.7-70.6c38.2 0 63.8-4.1 56.4 34.3zM384.2 350.3H421l8.7-44.8c43.2 0 67.1 2.5 90.2-19.1 26.1-24 32.9-66.7 14.3-88.1-9.7-11.2-25.3-16.7-46.5-16.7H417l-32.8 168.7z"],
+ "pied-piper": [480, 512, [], "f2ae", "M455.93,23.2C429.23,30,387.79,51.69,341.35,90.66A206,206,0,0,0,240,64C125.13,64,32,157.12,32,272s93.13,208,208,208,208-93.13,208-208a207.25,207.25,0,0,0-58.75-144.81,155.35,155.35,0,0,0-17,27.4A176.16,176.16,0,0,1,417.1,272c0,97.66-79.44,177.11-177.09,177.11a175.81,175.81,0,0,1-87.63-23.4c82.94-107.33,150.79-37.77,184.31-226.65,5.79-32.62,28-94.26,126.23-160.18C471,33.45,465.35,20.8,455.93,23.2ZM125,406.4A176.66,176.66,0,0,1,62.9,272C62.9,174.34,142.35,94.9,240,94.9a174,174,0,0,1,76.63,17.75C250.64,174.76,189.77,265.52,125,406.4Z"],
+ "pied-piper-alt": [576, 512, [], "f1a8", "M244 246c-3.2-2-6.3-2.9-10.1-2.9-6.6 0-12.6 3.2-19.3 3.7l1.7 4.9zm135.9 197.9c-19 0-64.1 9.5-79.9 19.8l6.9 45.1c35.7 6.1 70.1 3.6 106-9.8-4.8-10-23.5-55.1-33-55.1zM340.8 177c6.6 2.8 11.5 9.2 22.7 22.1 2-1.4 7.5-5.2 7.5-8.6 0-4.9-11.8-13.2-13.2-23 11.2-5.7 25.2-6 37.6-8.9 68.1-16.4 116.3-52.9 146.8-116.7C548.3 29.3 554 16.1 554.6 2l-2 2.6c-28.4 50-33 63.2-81.3 100-31.9 24.4-69.2 40.2-106.6 54.6l-6.3-.3v-21.8c-19.6 1.6-19.7-14.6-31.6-23-18.7 20.6-31.6 40.8-58.9 51.1-12.7 4.8-19.6 10-25.9 21.8 34.9-16.4 91.2-13.5 98.8-10zM555.5 0l-.6 1.1-.3.9.6-.6zm-59.2 382.1c-33.9-56.9-75.3-118.4-150-115.5l-.3-6c-1.1-13.5 32.8 3.2 35.1-31l-14.4 7.2c-19.8-45.7-8.6-54.3-65.5-54.3-14.7 0-26.7 1.7-41.4 4.6 2.9 18.6 2.2 36.7-10.9 50.3l19.5 5.5c-1.7 3.2-2.9 6.3-2.9 9.8 0 21 42.8 2.9 42.8 33.6 0 18.4-36.8 60.1-54.9 60.1-8 0-53.7-50-53.4-60.1l.3-4.6 52.3-11.5c13-2.6 12.3-22.7-2.9-22.7-3.7 0-43.1 9.2-49.4 10.6-2-5.2-7.5-14.1-13.8-14.1-3.2 0-6.3 3.2-9.5 4-9.2 2.6-31 2.9-21.5 20.1L15.9 298.5c-5.5 1.1-8.9 6.3-8.9 11.8 0 6 5.5 10.9 11.5 10.9 8 0 131.3-28.4 147.4-32.2 2.6 3.2 4.6 6.3 7.8 8.6 20.1 14.4 59.8 85.9 76.4 85.9 24.1 0 58-22.4 71.3-41.9 3.2-4.3 6.9-7.5 12.4-6.9.6 13.8-31.6 34.2-33 43.7-1.4 10.2-1 35.2-.3 41.1 26.7 8.1 52-3.6 77.9-2.9 4.3-21 10.6-41.9 9.8-63.5l-.3-9.5c-1.4-34.2-10.9-38.5-34.8-58.6-1.1-1.1-2.6-2.6-3.7-4 2.2-1.4 1.1-1 4.6-1.7 88.5 0 56.3 183.6 111.5 229.9 33.1-15 72.5-27.9 103.5-47.2-29-25.6-52.6-45.7-72.7-79.9zm-196.2 46.1v27.2l11.8-3.4-2.9-23.8zm-68.7-150.4l24.1 61.2 21-13.8-31.3-50.9zm84.4 154.9l2 12.4c9-1.5 58.4-6.6 58.4-14.1 0-1.4-.6-3.2-.9-4.6-26.8 0-36.9 3.8-59.5 6.3z"],
+ "pied-piper-hat": [640, 512, [], "f4e5", "M640 24.9c-80.8 53.6-89.4 92.5-96.4 104.4-6.7 12.2-11.7 60.3-23.3 83.6-11.7 23.6-54.2 42.2-66.1 50-11.7 7.8-28.3 38.1-41.9 64.2-108.1-4.4-167.4 38.8-259.2 93.6 29.4-9.7 43.3-16.7 43.3-16.7 94.2-36 139.3-68.3 281.1-49.2 1.1 0 1.9.6 2.8.8 3.9 2.2 5.3 6.9 3.1 10.8l-53.9 95.8c-2.5 4.7-7.8 7.2-13.1 6.1-126.8-23.8-226.9 17.3-318.9 18.6C24.1 488 0 453.4 0 451.8c0-1.1.6-1.7 1.7-1.7 0 0 38.3 0 103.1-15.3C178.4 294.5 244 245.4 315.4 245.4c0 0 71.7 0 90.6 61.9 22.8-39.7 28.3-49.2 28.3-49.2 5.3-9.4 35-77.2 86.4-141.4 51.5-64 90.4-79.9 119.3-91.8z"],
+ "pied-piper-pp": [448, 512, [], "f1a7", "M205.3 174.6c0 21.1-14.2 38.1-31.7 38.1-7.1 0-12.8-1.2-17.2-3.7v-68c4.4-2.7 10.1-4.2 17.2-4.2 17.5 0 31.7 16.9 31.7 37.8zm52.6 67c-7.1 0-12.8 1.5-17.2 4.2v68c4.4 2.5 10.1 3.7 17.2 3.7 17.4 0 31.7-16.9 31.7-37.8 0-21.1-14.3-38.1-31.7-38.1zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zM185 255.1c41 0 74.2-35.6 74.2-79.6 0-44-33.2-79.6-74.2-79.6-12 0-24.1 3.2-34.6 8.8h-45.7V311l51.8-10.1v-50.6c8.6 3.1 18.1 4.8 28.5 4.8zm158.4 25.3c0-44-33.2-79.6-73.9-79.6-3.2 0-6.4.2-9.6.7-3.7 12.5-10.1 23.8-19.2 33.4-13.8 15-32.2 23.8-51.8 24.8V416l51.8-10.1v-50.6c8.6 3.2 18.2 4.7 28.7 4.7 40.8 0 74-35.6 74-79.6z"],
+ "pied-piper-square": [448, 512, [], "e01e", "M32 419L0 479.2l.8-328C.8 85.3 54 32 120 32h327.2c-93 28.9-189.9 94.2-253.9 168.6C122.7 282 82.6 338 32 419M448 32S305.2 98.8 261.6 199.1c-23.2 53.6-28.9 118.1-71 158.6-28.9 27.8-69.8 38.2-105.3 56.3-23.2 12-66.4 40.5-84.9 66h328.4c66 0 119.3-53.3 119.3-119.2-.1 0-.1-328.8-.1-328.8z"],
+ "pinterest": [496, 512, [], "f0d2", "M496 256c0 137-111 248-248 248-25.6 0-50.2-3.9-73.4-11.1 10.1-16.5 25.2-43.5 30.8-65 3-11.6 15.4-59 15.4-59 8.1 15.4 31.7 28.5 56.8 28.5 74.8 0 128.7-68.8 128.7-154.3 0-81.9-66.9-143.2-152.9-143.2-107 0-163.9 71.8-163.9 150.1 0 36.4 19.4 81.7 50.3 96.1 4.7 2.2 7.2 1.2 8.3-3.3.8-3.4 5-20.3 6.9-28.1.6-2.5.3-4.7-1.7-7.1-10.1-12.5-18.3-35.3-18.3-56.6 0-54.7 41.4-107.6 112-107.6 60.9 0 103.6 41.5 103.6 100.9 0 67.1-33.9 113.6-78 113.6-24.3 0-42.6-20.1-36.7-44.8 7-29.5 20.5-61.3 20.5-82.6 0-19-10.2-34.9-31.4-34.9-24.9 0-44.9 25.7-44.9 60.2 0 22 7.4 36.8 7.4 36.8s-24.5 103.8-29 123.2c-5 21.4-3 51.6-.9 71.2C65.4 450.9 0 361.1 0 256 0 119 111 8 248 8s248 111 248 248z"],
+ "pinterest-p": [384, 512, [], "f231", "M204 6.5C101.4 6.5 0 74.9 0 185.6 0 256 39.6 296 63.6 296c9.9 0 15.6-27.6 15.6-35.4 0-9.3-23.7-29.1-23.7-67.8 0-80.4 61.2-137.4 140.4-137.4 68.1 0 118.5 38.7 118.5 109.8 0 53.1-21.3 152.7-90.3 152.7-24.9 0-46.2-18-46.2-43.8 0-37.8 26.4-74.4 26.4-113.4 0-66.2-93.9-54.2-93.9 25.8 0 16.8 2.1 35.4 9.6 50.7-13.8 59.4-42 147.9-42 209.1 0 18.9 2.7 37.5 4.5 56.4 3.4 3.8 1.7 3.4 6.9 1.5 50.4-69 48.6-82.5 71.4-172.8 12.3 23.4 44.1 36 69.3 36 106.2 0 153.9-103.5 153.9-196.8C384 71.3 298.2 6.5 204 6.5z"],
+ "pinterest-square": [448, 512, [], "f0d3", "M448 80v352c0 26.5-21.5 48-48 48H154.4c9.8-16.4 22.4-40 27.4-59.3 3-11.5 15.3-58.4 15.3-58.4 8 15.3 31.4 28.2 56.3 28.2 74.1 0 127.4-68.1 127.4-152.7 0-81.1-66.2-141.8-151.4-141.8-106 0-162.2 71.1-162.2 148.6 0 36 19.2 80.8 49.8 95.1 4.7 2.2 7.1 1.2 8.2-3.3.8-3.4 5-20.1 6.8-27.8.6-2.5.3-4.6-1.7-7-10.1-12.3-18.3-34.9-18.3-56 0-54.2 41-106.6 110.9-106.6 60.3 0 102.6 41.1 102.6 99.9 0 66.4-33.5 112.4-77.2 112.4-24.1 0-42.1-19.9-36.4-44.4 6.9-29.2 20.3-60.7 20.3-81.8 0-53-75.5-45.7-75.5 25 0 21.7 7.3 36.5 7.3 36.5-31.4 132.8-36.1 134.5-29.6 192.6l2.2.8H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48z"],
+ "playstation": [576, 512, [], "f3df", "M570.9 372.3c-11.3 14.2-38.8 24.3-38.8 24.3L327 470.2v-54.3l150.9-53.8c17.1-6.1 19.8-14.8 5.8-19.4-13.9-4.6-39.1-3.3-56.2 2.9L327 381.1v-56.4c23.2-7.8 47.1-13.6 75.7-16.8 40.9-4.5 90.9.6 130.2 15.5 44.2 14 49.2 34.7 38 48.9zm-224.4-92.5v-139c0-16.3-3-31.3-18.3-35.6-11.7-3.8-19 7.1-19 23.4v347.9l-93.8-29.8V32c39.9 7.4 98 24.9 129.2 35.4C424.1 94.7 451 128.7 451 205.2c0 74.5-46 102.8-104.5 74.6zM43.2 410.2c-45.4-12.8-53-39.5-32.3-54.8 19.1-14.2 51.7-24.9 51.7-24.9l134.5-47.8v54.5l-96.8 34.6c-17.1 6.1-19.7 14.8-5.8 19.4 13.9 4.6 39.1 3.3 56.2-2.9l46.4-16.9v48.8c-51.6 9.3-101.4 7.3-153.9-10z"],
+ "product-hunt": [512, 512, [], "f288", "M326.3 218.8c0 20.5-16.7 37.2-37.2 37.2h-70.3v-74.4h70.3c20.5 0 37.2 16.7 37.2 37.2zM504 256c0 137-111 248-248 248S8 393 8 256 119 8 256 8s248 111 248 248zm-128.1-37.2c0-47.9-38.9-86.8-86.8-86.8H169.2v248h49.6v-74.4h70.3c47.9 0 86.8-38.9 86.8-86.8z"],
+ "pushed": [432, 512, [], "f3e1", "M407 111.9l-98.5-9 14-33.4c10.4-23.5-10.8-40.4-28.7-37L22.5 76.9c-15.1 2.7-26 18.3-21.4 36.6l105.1 348.3c6.5 21.3 36.7 24.2 47.7 7l35.3-80.8 235.2-231.3c16.4-16.8 4.3-42.9-17.4-44.8zM297.6 53.6c5.1-.7 7.5 2.5 5.2 7.4L286 100.9 108.6 84.6l189-31zM22.7 107.9c-3.1-5.1 1-10 6.1-9.1l248.7 22.7-96.9 230.7L22.7 107.9zM136 456.4c-2.6 4-7.9 3.1-9.4-1.2L43.5 179.7l127.7 197.6c-7 15-35.2 79.1-35.2 79.1zm272.8-314.5L210.1 337.3l89.7-213.7 106.4 9.7c4 1.1 5.7 5.3 2.6 8.6z"],
+ "python": [448, 512, [], "f3e2", "M439.8 200.5c-7.7-30.9-22.3-54.2-53.4-54.2h-40.1v47.4c0 36.8-31.2 67.8-66.8 67.8H172.7c-29.2 0-53.4 25-53.4 54.3v101.8c0 29 25.2 46 53.4 54.3 33.8 9.9 66.3 11.7 106.8 0 26.9-7.8 53.4-23.5 53.4-54.3v-40.7H226.2v-13.6h160.2c31.1 0 42.6-21.7 53.4-54.2 11.2-33.5 10.7-65.7 0-108.6zM286.2 404c11.1 0 20.1 9.1 20.1 20.3 0 11.3-9 20.4-20.1 20.4-11 0-20.1-9.2-20.1-20.4.1-11.3 9.1-20.3 20.1-20.3zM167.8 248.1h106.8c29.7 0 53.4-24.5 53.4-54.3V91.9c0-29-24.4-50.7-53.4-55.6-35.8-5.9-74.7-5.6-106.8.1-45.2 8-53.4 24.7-53.4 55.6v40.7h106.9v13.6h-147c-31.1 0-58.3 18.7-66.8 54.2-9.8 40.7-10.2 66.1 0 108.6 7.6 31.6 25.7 54.2 56.8 54.2H101v-48.8c0-35.3 30.5-66.4 66.8-66.4zm-6.7-142.6c-11.1 0-20.1-9.1-20.1-20.3.1-11.3 9-20.4 20.1-20.4 11 0 20.1 9.2 20.1 20.4s-9 20.3-20.1 20.3z"],
+ "qq": [448, 512, [], "f1d6", "M433.754 420.445c-11.526 1.393-44.86-52.741-44.86-52.741 0 31.345-16.136 72.247-51.051 101.786 16.842 5.192 54.843 19.167 45.803 34.421-7.316 12.343-125.51 7.881-159.632 4.037-34.122 3.844-152.316 8.306-159.632-4.037-9.045-15.25 28.918-29.214 45.783-34.415-34.92-29.539-51.059-70.445-51.059-101.792 0 0-33.334 54.134-44.859 52.741-5.37-.65-12.424-29.644 9.347-99.704 10.261-33.024 21.995-60.478 40.144-105.779C60.683 98.063 108.982.006 224 0c113.737.006 163.156 96.133 160.264 214.963 18.118 45.223 29.912 72.85 40.144 105.778 21.768 70.06 14.716 99.053 9.346 99.704z"],
+ "quinscape": [512, 512, [], "f459", "M313.6 474.6h-1a158.1 158.1 0 0 1 0-316.2c94.9 0 168.2 83.1 157 176.6 4 5.1 8.2 9.6 11.2 15.3 13.4-30.3 20.3-62.4 20.3-97.7C501.1 117.5 391.6 8 256.5 8S12 117.5 12 252.6s109.5 244.6 244.5 244.6a237.36 237.36 0 0 0 70.4-10.1c-5.2-3.5-8.9-8.1-13.3-12.5zm-.1-.1l.4.1zm78.4-168.9a99.2 99.2 0 1 0 99.2 99.2 99.18 99.18 0 0 0-99.2-99.2z"],
+ "quora": [448, 512, [], "f2c4", "M440.5 386.7h-29.3c-1.5 13.5-10.5 30.8-33 30.8-20.5 0-35.3-14.2-49.5-35.8 44.2-34.2 74.7-87.5 74.7-153C403.5 111.2 306.8 32 205 32 105.3 32 7.3 111.7 7.3 228.7c0 134.1 131.3 221.6 249 189C276 451.3 302 480 351.5 480c81.8 0 90.8-75.3 89-93.3zM297 329.2C277.5 300 253.3 277 205.5 277c-30.5 0-54.3 10-69 22.8l12.2 24.3c6.2-3 13-4 19.8-4 35.5 0 53.7 30.8 69.2 61.3-10 3-20.7 4.2-32.7 4.2-75 0-107.5-53-107.5-156.7C97.5 124.5 130 71 205 71c76.2 0 108.7 53.5 108.7 157.7.1 41.8-5.4 75.6-16.7 100.5z"],
+ "r-project": [581, 512, [], "f4f7", "M581 226.6C581 119.1 450.9 32 290.5 32S0 119.1 0 226.6C0 322.4 103.3 402 239.4 418.1V480h99.1v-61.5c24.3-2.7 47.6-7.4 69.4-13.9L448 480h112l-67.4-113.7c54.5-35.4 88.4-84.9 88.4-139.7zm-466.8 14.5c0-73.5 98.9-133 220.8-133s211.9 40.7 211.9 133c0 50.1-26.5 85-70.3 106.4-2.4-1.6-4.7-2.9-6.4-3.7-10.2-5.2-27.8-10.5-27.8-10.5s86.6-6.4 86.6-92.7-90.6-87.9-90.6-87.9h-199V361c-74.1-21.5-125.2-67.1-125.2-119.9zm225.1 38.3v-55.6c57.8 0 87.8-6.8 87.8 27.3 0 36.5-38.2 28.3-87.8 28.3zm-.9 72.5H365c10.8 0 18.9 11.7 24 19.2-16.1 1.9-33 2.8-50.6 2.9v-22.1z"],
+ "raspberry-pi": [407, 512, [], "f7bb", "M372 232.5l-3.7-6.5c.1-46.4-21.4-65.3-46.5-79.7 7.6-2 15.4-3.6 17.6-13.2 13.1-3.3 15.8-9.4 17.1-15.8 3.4-2.3 14.8-8.7 13.6-19.7 6.4-4.4 10-10.1 8.1-18.1 6.9-7.5 8.7-13.7 5.8-19.4 8.3-10.3 4.6-15.6 1.1-20.9 6.2-11.2.7-23.2-16.6-21.2-6.9-10.1-21.9-7.8-24.2-7.8-2.6-3.2-6-6-16.5-4.7-6.8-6.1-14.4-5-22.3-2.1-9.3-7.3-15.5-1.4-22.6.8C271.6.6 269 5.5 263.5 7.6c-12.3-2.6-16.1 3-22 8.9l-6.9-.1c-18.6 10.8-27.8 32.8-31.1 44.1-3.3-11.3-12.5-33.3-31.1-44.1l-6.9.1c-5.9-5.9-9.7-11.5-22-8.9-5.6-2-8.1-7-19.4-3.4-4.6-1.4-8.9-4.4-13.9-4.3-2.6.1-5.5 1-8.7 3.5-7.9-3-15.5-4-22.3 2.1-10.5-1.3-14 1.4-16.5 4.7-2.3 0-17.3-2.3-24.2 7.8C21.2 16 15.8 28 22 39.2c-3.5 5.4-7.2 10.7 1.1 20.9-2.9 5.7-1.1 11.9 5.8 19.4-1.8 8 1.8 13.7 8.1 18.1-1.2 11 10.2 17.4 13.6 19.7 1.3 6.4 4 12.4 17.1 15.8 2.2 9.5 10 11.2 17.6 13.2-25.1 14.4-46.6 33.3-46.5 79.7l-3.7 6.5c-28.8 17.2-54.7 72.7-14.2 117.7 2.6 14.1 7.1 24.2 11 35.4 5.9 45.2 44.5 66.3 54.6 68.8 14.9 11.2 30.8 21.8 52.2 29.2C159 504.2 181 512 203 512h1c22.1 0 44-7.8 64.2-28.4 21.5-7.4 37.3-18 52.2-29.2 10.2-2.5 48.7-23.6 54.6-68.8 3.9-11.2 8.4-21.3 11-35.4 40.6-45.1 14.7-100.5-14-117.7zm-22.2-8c-1.5 18.7-98.9-65.1-82.1-67.9 45.7-7.5 83.6 19.2 82.1 67.9zm-43 93.1c-24.5 15.8-59.8 5.6-78.8-22.8s-14.6-64.2 9.9-80c24.5-15.8 59.8-5.6 78.8 22.8s14.6 64.2-9.9 80zM238.9 29.3c.8 4.2 1.8 6.8 2.9 7.6 5.4-5.8 9.8-11.7 16.8-17.3 0 3.3-1.7 6.8 2.5 9.4 3.7-5 8.8-9.5 15.5-13.3-3.2 5.6-.6 7.3 1.2 9.6 5.1-4.4 10-8.8 19.4-12.3-2.6 3.1-6.2 6.2-2.4 9.8 5.3-3.3 10.6-6.6 23.1-8.9-2.8 3.1-8.7 6.3-5.1 9.4 6.6-2.5 14-4.4 22.1-5.4-3.9 3.2-7.1 6.3-3.9 8.8 7.1-2.2 16.9-5.1 26.4-2.6l-6 6.1c-.7.8 14.1.6 23.9.8-3.6 5-7.2 9.7-9.3 18.2 1 1 5.8.4 10.4 0-4.7 9.9-12.8 12.3-14.7 16.6 2.9 2.2 6.8 1.6 11.2.1-3.4 6.9-10.4 11.7-16 17.3 1.4 1 3.9 1.6 9.7.9-5.2 5.5-11.4 10.5-18.8 15 1.3 1.5 5.8 1.5 10 1.6-6.7 6.5-15.3 9.9-23.4 14.2 4 2.7 6.9 2.1 10 2.1-5.7 4.7-15.4 7.1-24.4 10 1.7 2.7 3.4 3.4 7.1 4.1-9.5 5.3-23.2 2.9-27 5.6.9 2.7 3.6 4.4 6.7 5.8-15.4.9-57.3-.6-65.4-32.3 15.7-17.3 44.4-37.5 93.7-62.6-38.4 12.8-73 30-102 53.5-34.3-15.9-10.8-55.9 5.8-71.8zm-34.4 114.6c24.2-.3 54.1 17.8 54 34.7-.1 15-21 27.1-53.8 26.9-32.1-.4-53.7-15.2-53.6-29.8 0-11.9 26.2-32.5 53.4-31.8zm-123-12.8c3.7-.7 5.4-1.5 7.1-4.1-9-2.8-18.7-5.3-24.4-10 3.1 0 6 .7 10-2.1-8.1-4.3-16.7-7.7-23.4-14.2 4.2-.1 8.7 0 10-1.6-7.4-4.5-13.6-9.5-18.8-15 5.8.7 8.3.1 9.7-.9-5.6-5.6-12.7-10.4-16-17.3 4.3 1.5 8.3 2 11.2-.1-1.9-4.2-10-6.7-14.7-16.6 4.6.4 9.4 1 10.4 0-2.1-8.5-5.8-13.3-9.3-18.2 9.8-.1 24.6 0 23.9-.8l-6-6.1c9.5-2.5 19.3.4 26.4 2.6 3.2-2.5-.1-5.6-3.9-8.8 8.1 1.1 15.4 2.9 22.1 5.4 3.5-3.1-2.3-6.3-5.1-9.4 12.5 2.3 17.8 5.6 23.1 8.9 3.8-3.6.2-6.7-2.4-9.8 9.4 3.4 14.3 7.9 19.4 12.3 1.7-2.3 4.4-4 1.2-9.6 6.7 3.8 11.8 8.3 15.5 13.3 4.1-2.6 2.5-6.2 2.5-9.4 7 5.6 11.4 11.5 16.8 17.3 1.1-.8 2-3.4 2.9-7.6 16.6 15.9 40.1 55.9 6 71.8-29-23.5-63.6-40.7-102-53.5 49.3 25 78 45.3 93.7 62.6-8 31.8-50 33.2-65.4 32.3 3.1-1.4 5.8-3.2 6.7-5.8-4-2.8-17.6-.4-27.2-5.6zm60.1 24.1c16.8 2.8-80.6 86.5-82.1 67.9-1.5-48.7 36.5-75.5 82.1-67.9zM38.2 342c-23.7-18.8-31.3-73.7 12.6-98.3 26.5-7 9 107.8-12.6 98.3zm91 98.2c-13.3 7.9-45.8 4.7-68.8-27.9-15.5-27.4-13.5-55.2-2.6-63.4 16.3-9.8 41.5 3.4 60.9 25.6 16.9 20 24.6 55.3 10.5 65.7zm-26.4-119.7c-24.5-15.8-28.9-51.6-9.9-80s54.3-38.6 78.8-22.8 28.9 51.6 9.9 80c-19.1 28.4-54.4 38.6-78.8 22.8zM205 496c-29.4 1.2-58.2-23.7-57.8-32.3-.4-12.7 35.8-22.6 59.3-22 23.7-1 55.6 7.5 55.7 18.9.5 11-28.8 35.9-57.2 35.4zm58.9-124.9c.2 29.7-26.2 53.8-58.8 54-32.6.2-59.2-23.8-59.4-53.4v-.6c-.2-29.7 26.2-53.8 58.8-54 32.6-.2 59.2 23.8 59.4 53.4v.6zm82.2 42.7c-25.3 34.6-59.6 35.9-72.3 26.3-13.3-12.4-3.2-50.9 15.1-72 20.9-23.3 43.3-38.5 58.9-26.6 10.5 10.3 16.7 49.1-1.7 72.3zm22.9-73.2c-21.5 9.4-39-105.3-12.6-98.3 43.9 24.7 36.3 79.6 12.6 98.3z"],
+ "ravelry": [512, 512, [], "f2d9", "M498.252,234.223c-1.208-10.34-1.7-20.826-3.746-31a310.306,310.306,0,0,0-9.622-36.6,184.068,184.068,0,0,0-30.874-57.5,251.154,251.154,0,0,0-18.818-21.689,237.362,237.362,0,0,0-47.113-36.116A240.8,240.8,0,0,0,331.356,26.65c-11.018-3.1-22.272-5.431-33.515-7.615-6.78-1.314-13.749-1.667-20.627-2.482-.316-.036-.6-.358-.9-.553q-16.143.009-32.288.006c-2.41.389-4.808.925-7.236,1.15a179.331,179.331,0,0,0-34.256,7.1,221.5,221.5,0,0,0-39.768,16.355,281.385,281.385,0,0,0-38.08,24.158c-6.167,4.61-12.268,9.36-17.974,14.518C96.539,88.494,86.34,97.72,76.785,107.555a243.878,243.878,0,0,0-33.648,43.95,206.488,206.488,0,0,0-20.494,44.6,198.2,198.2,0,0,0-7.691,34.759A201.13,201.13,0,0,0,13.4,266.385a299.716,299.716,0,0,0,4.425,40.24,226.865,226.865,0,0,0,16.73,53.3,210.543,210.543,0,0,0,24,39.528,213.589,213.589,0,0,0,26.358,28.416A251.313,251.313,0,0,0,126.7,458.455a287.831,287.831,0,0,0,55.9,25.277,269.5,269.5,0,0,0,40.641,9.835c6.071,1.01,12.275,1.253,18.412,1.873a4.149,4.149,0,0,1,1.19.56h32.289c2.507-.389,5-.937,7.527-1.143,16.336-1.332,32.107-5.335,47.489-10.717A219.992,219.992,0,0,0,379.1,460.322c9.749-6.447,19.395-13.077,28.737-20.1,5.785-4.348,10.988-9.5,16.3-14.457,3.964-3.7,7.764-7.578,11.51-11.5a232.162,232.162,0,0,0,31.427-41.639c9.542-16.045,17.355-32.905,22.3-50.926,2.859-10.413,4.947-21.045,7.017-31.652,1.032-5.279,1.251-10.723,1.87-16.087.036-.317.358-.6.552-.9V236.005A9.757,9.757,0,0,1,498.252,234.223Zm-161.117-1.15s-16.572-2.98-28.47-2.98c-27.2,0-33.57,14.9-33.57,37.04V360.8H201.582V170.062H275.1v31.931c8.924-26.822,26.771-36.189,62.04-36.189Z"],
+ "react": [512, 512, [], "f41b", "M418.2 177.2c-5.4-1.8-10.8-3.5-16.2-5.1.9-3.7 1.7-7.4 2.5-11.1 12.3-59.6 4.2-107.5-23.1-123.3-26.3-15.1-69.2.6-112.6 38.4-4.3 3.7-8.5 7.6-12.5 11.5-2.7-2.6-5.5-5.2-8.3-7.7-45.5-40.4-91.1-57.4-118.4-41.5-26.2 15.2-34 60.3-23 116.7 1.1 5.6 2.3 11.1 3.7 16.7-6.4 1.8-12.7 3.8-18.6 5.9C38.3 196.2 0 225.4 0 255.6c0 31.2 40.8 62.5 96.3 81.5 4.5 1.5 9 3 13.6 4.3-1.5 6-2.8 11.9-4 18-10.5 55.5-2.3 99.5 23.9 114.6 27 15.6 72.4-.4 116.6-39.1 3.5-3.1 7-6.3 10.5-9.7 4.4 4.3 9 8.4 13.6 12.4 42.8 36.8 85.1 51.7 111.2 36.6 27-15.6 35.8-62.9 24.4-120.5-.9-4.4-1.9-8.9-3-13.5 3.2-.9 6.3-1.9 9.4-2.9 57.7-19.1 99.5-50 99.5-81.7 0-30.3-39.4-59.7-93.8-78.4zM282.9 92.3c37.2-32.4 71.9-45.1 87.7-36 16.9 9.7 23.4 48.9 12.8 100.4-.7 3.4-1.4 6.7-2.3 10-22.2-5-44.7-8.6-67.3-10.6-13-18.6-27.2-36.4-42.6-53.1 3.9-3.7 7.7-7.2 11.7-10.7zM167.2 307.5c5.1 8.7 10.3 17.4 15.8 25.9-15.6-1.7-31.1-4.2-46.4-7.5 4.4-14.4 9.9-29.3 16.3-44.5 4.6 8.8 9.3 17.5 14.3 26.1zm-30.3-120.3c14.4-3.2 29.7-5.8 45.6-7.8-5.3 8.3-10.5 16.8-15.4 25.4-4.9 8.5-9.7 17.2-14.2 26-6.3-14.9-11.6-29.5-16-43.6zm27.4 68.9c6.6-13.8 13.8-27.3 21.4-40.6s15.8-26.2 24.4-38.9c15-1.1 30.3-1.7 45.9-1.7s31 .6 45.9 1.7c8.5 12.6 16.6 25.5 24.3 38.7s14.9 26.7 21.7 40.4c-6.7 13.8-13.9 27.4-21.6 40.8-7.6 13.3-15.7 26.2-24.2 39-14.9 1.1-30.4 1.6-46.1 1.6s-30.9-.5-45.6-1.4c-8.7-12.7-16.9-25.7-24.6-39s-14.8-26.8-21.5-40.6zm180.6 51.2c5.1-8.8 9.9-17.7 14.6-26.7 6.4 14.5 12 29.2 16.9 44.3-15.5 3.5-31.2 6.2-47 8 5.4-8.4 10.5-17 15.5-25.6zm14.4-76.5c-4.7-8.8-9.5-17.6-14.5-26.2-4.9-8.5-10-16.9-15.3-25.2 16.1 2 31.5 4.7 45.9 8-4.6 14.8-10 29.2-16.1 43.4zM256.2 118.3c10.5 11.4 20.4 23.4 29.6 35.8-19.8-.9-39.7-.9-59.5 0 9.8-12.9 19.9-24.9 29.9-35.8zM140.2 57c16.8-9.8 54.1 4.2 93.4 39 2.5 2.2 5 4.6 7.6 7-15.5 16.7-29.8 34.5-42.9 53.1-22.6 2-45 5.5-67.2 10.4-1.3-5.1-2.4-10.3-3.5-15.5-9.4-48.4-3.2-84.9 12.6-94zm-24.5 263.6c-4.2-1.2-8.3-2.5-12.4-3.9-21.3-6.7-45.5-17.3-63-31.2-10.1-7-16.9-17.8-18.8-29.9 0-18.3 31.6-41.7 77.2-57.6 5.7-2 11.5-3.8 17.3-5.5 6.8 21.7 15 43 24.5 63.6-9.6 20.9-17.9 42.5-24.8 64.5zm116.6 98c-16.5 15.1-35.6 27.1-56.4 35.3-11.1 5.3-23.9 5.8-35.3 1.3-15.9-9.2-22.5-44.5-13.5-92 1.1-5.6 2.3-11.2 3.7-16.7 22.4 4.8 45 8.1 67.9 9.8 13.2 18.7 27.7 36.6 43.2 53.4-3.2 3.1-6.4 6.1-9.6 8.9zm24.5-24.3c-10.2-11-20.4-23.2-30.3-36.3 9.6.4 19.5.6 29.5.6 10.3 0 20.4-.2 30.4-.7-9.2 12.7-19.1 24.8-29.6 36.4zm130.7 30c-.9 12.2-6.9 23.6-16.5 31.3-15.9 9.2-49.8-2.8-86.4-34.2-4.2-3.6-8.4-7.5-12.7-11.5 15.3-16.9 29.4-34.8 42.2-53.6 22.9-1.9 45.7-5.4 68.2-10.5 1 4.1 1.9 8.2 2.7 12.2 4.9 21.6 5.7 44.1 2.5 66.3zm18.2-107.5c-2.8.9-5.6 1.8-8.5 2.6-7-21.8-15.6-43.1-25.5-63.8 9.6-20.4 17.7-41.4 24.5-62.9 5.2 1.5 10.2 3.1 15 4.7 46.6 16 79.3 39.8 79.3 58 0 19.6-34.9 44.9-84.8 61.4zm-149.7-15c25.3 0 45.8-20.5 45.8-45.8s-20.5-45.8-45.8-45.8c-25.3 0-45.8 20.5-45.8 45.8s20.5 45.8 45.8 45.8z"],
+ "reacteurope": [576, 512, [], "f75d", "M250.6 211.74l5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3-7.1-.1-2.3-6.8-2.3 6.8-7.2.1 5.7 4.3zm63.7 0l5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3-7.2-.1-2.3-6.8-2.3 6.8-7.2.1 5.7 4.3zm-91.3 50.5h-3.4c-4.8 0-3.8 4-3.8 12.1 0 4.7-2.3 6.1-5.8 6.1s-5.8-1.4-5.8-6.1v-36.6c0-4.7 2.3-6.1 5.8-6.1s5.8 1.4 5.8 6.1c0 7.2-.7 10.5 3.8 10.5h3.4c4.7-.1 3.8-3.9 3.8-12.3 0-9.9-6.7-14.1-16.8-14.1h-.2c-10.1 0-16.8 4.2-16.8 14.1V276c0 10.4 6.7 14.1 16.8 14.1h.2c10.1 0 16.8-3.8 16.8-14.1 0-9.86 1.1-13.76-3.8-13.76zm-80.7 17.4h-14.7v-19.3H139c2.5 0 3.8-1.3 3.8-3.8v-2.1c0-2.5-1.3-3.8-3.8-3.8h-11.4v-18.3H142c2.5 0 3.8-1.3 3.8-3.8v-2.1c0-2.5-1.3-3.8-3.8-3.8h-21.7c-2.4-.1-3.7 1.3-3.7 3.8v59.1c0 2.5 1.3 3.8 3.8 3.8h21.9c2.5 0 3.8-1.3 3.8-3.8v-2.1c0-2.5-1.3-3.8-3.8-3.8zm-42-18.5c4.6-2 7.3-6 7.3-12.4v-11.9c0-10.1-6.7-14.1-16.8-14.1H77.4c-2.5 0-3.8 1.3-3.8 3.8v59.1c0 2.5 1.3 3.8 3.8 3.8h3.4c2.5 0 3.8-1.3 3.8-3.8v-22.9h5.6l7.4 23.5a4.1 4.1 0 0 0 4.3 3.2h3.3c2.8 0 4-1.8 3.2-4.4zm-3.8-14c0 4.8-2.5 6.1-6.1 6.1h-5.8v-20.9h5.8c3.6 0 6.1 1.3 6.1 6.1zM176 226a3.82 3.82 0 0 0-4.2-3.4h-6.9a3.68 3.68 0 0 0-4 3.4l-11 59.2c-.5 2.7.9 4.1 3.4 4.1h3a3.74 3.74 0 0 0 4.1-3.5l1.8-11.3h12.2l1.8 11.3a3.74 3.74 0 0 0 4.1 3.5h3.5c2.6 0 3.9-1.4 3.4-4.1zm-12.3 39.3l4.7-29.7 4.7 29.7zm89.3 20.2v-53.2h7.5c2.5 0 3.8-1.3 3.8-3.8v-2.1c0-2.5-1.3-3.8-3.8-3.8h-25.8c-2.5 0-3.8 1.3-3.8 3.8v2.1c0 2.5 1.3 3.8 3.8 3.8h7.3v53.2c0 2.5 1.3 3.8 3.8 3.8h3.4c2.5.04 3.8-1.3 3.8-3.76zm248-.8h-19.4V258h16.1a1.89 1.89 0 0 0 2-2v-.8a1.89 1.89 0 0 0-2-2h-16.1v-25.8h19.1a1.89 1.89 0 0 0 2-2v-.8a1.77 1.77 0 0 0-2-1.9h-22.2a1.62 1.62 0 0 0-2 1.8v63a1.81 1.81 0 0 0 2 1.9H501a1.81 1.81 0 0 0 2-1.9v-.8a1.84 1.84 0 0 0-2-1.96zm-93.1-62.9h-.8c-10.1 0-15.3 4.7-15.3 14.1V276c0 9.3 5.2 14.1 15.3 14.1h.8c10.1 0 15.3-4.8 15.3-14.1v-40.1c0-9.36-5.2-14.06-15.3-14.06zm10.2 52.4c-.1 8-3 11.1-10.5 11.1s-10.5-3.1-10.5-11.1v-36.6c0-7.9 3-11.1 10.5-11.1s10.5 3.2 10.5 11.1zm-46.5-14.5c6.1-1.6 9.2-6.1 9.2-13.3v-9.7c0-9.4-5.2-14.1-15.3-14.1h-13.7a1.81 1.81 0 0 0-2 1.9v63a1.81 1.81 0 0 0 2 1.9h1.2a1.74 1.74 0 0 0 1.9-1.9v-26.9h11.6l10.4 27.2a2.32 2.32 0 0 0 2.3 1.5h1.5c1.4 0 2-1 1.5-2.3zm-6.4-3.9H355v-28.5h10.2c7.5 0 10.5 3.1 10.5 11.1v6.4c0 7.84-3 11.04-10.5 11.04zm85.9-33.1h-13.7a1.62 1.62 0 0 0-2 1.8v63a1.81 1.81 0 0 0 2 1.9h1.2a1.74 1.74 0 0 0 1.9-1.9v-26.1h10.6c10.1 0 15.3-4.8 15.3-14.1v-10.5c0-9.4-5.2-14.1-15.3-14.1zm10.2 22.8c0 7.9-3 11.1-10.5 11.1h-10.2v-29.2h10.2c7.5-.1 10.5 3.1 10.5 11zM259.5 308l-2.3-6.8-2.3 6.8-7.1.1 5.7 4.3-2.1 6.8 5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3zm227.6-136.1a364.42 364.42 0 0 0-35.6-11.3c19.6-78 11.6-134.7-22.3-153.9C394.7-12.66 343.3 11 291 61.94q5.1 4.95 10.2 10.2c82.5-80 119.6-53.5 120.9-52.8 22.4 12.7 36 55.8 15.5 137.8a587.83 587.83 0 0 0-84.6-13C281.1 43.64 212.4 2 170.8 2 140 2 127 23 123.2 29.74c-18.1 32-13.3 84.2.1 133.8-70.5 20.3-120.7 54.1-120.3 95 .5 59.6 103.2 87.8 122.1 92.8-20.5 81.9-10.1 135.6 22.3 153.9 28 15.8 75.1 6 138.2-55.2q-5.1-4.95-10.2-10.2c-82.5 80-119.7 53.5-120.9 52.8-22.3-12.6-36-55.6-15.5-137.9 12.4 2.9 41.8 9.5 84.6 13 71.9 100.4 140.6 142 182.1 142 30.8 0 43.8-21 47.6-27.7 18-31.9 13.3-84.1-.1-133.8 152.3-43.8 156.2-130.2 33.9-176.3zM135.9 36.84c2.9-5.1 11.9-20.3 34.9-20.3 36.8 0 98.8 39.6 163.3 126.2a714 714 0 0 0-93.9.9 547.76 547.76 0 0 1 42.2-52.4Q277.3 86 272.2 81a598.25 598.25 0 0 0-50.7 64.2 569.69 569.69 0 0 0-84.4 14.6c-.2-1.4-24.3-82.2-1.2-123zm304.8 438.3c-2.9 5.1-11.8 20.3-34.9 20.3-36.7 0-98.7-39.4-163.3-126.2a695.38 695.38 0 0 0 93.9-.9 547.76 547.76 0 0 1-42.2 52.4q5.1 5.25 10.2 10.2a588.47 588.47 0 0 0 50.7-64.2c47.3-4.7 80.3-13.5 84.4-14.6 22.7 84.4 4.5 117 1.2 123zm9.1-138.6c-3.6-11.9-7.7-24.1-12.4-36.4a12.67 12.67 0 0 1-10.7-5.7l-.1.1a19.61 19.61 0 0 1-5.4 3.6c5.7 14.3 10.6 28.4 14.7 42.2a535.3 535.3 0 0 1-72 13c3.5-5.3 17.2-26.2 32.2-54.2a24.6 24.6 0 0 1-6-3.2c-1.1 1.2-3.6 4.2-10.9 4.2-6.2 11.2-17.4 30.9-33.9 55.2a711.91 711.91 0 0 1-112.4 1c-7.9-11.2-21.5-31.1-36.8-57.8a21 21 0 0 1-3-1.5c-1.9 1.6-3.9 3.2-12.6 3.2 6.3 11.2 17.5 30.7 33.8 54.6a548.81 548.81 0 0 1-72.2-11.7q5.85-21 14.1-42.9c-3.2 0-5.4.2-8.4-1a17.58 17.58 0 0 1-6.9 1c-4.9 13.4-9.1 26.5-12.7 39.4C-31.7 297-12.1 216 126.7 175.64c3.6 11.9 7.7 24.1 12.4 36.4 10.4 0 12.9 3.4 14.4 5.3a12 12 0 0 1 2.3-2.2c-5.8-14.7-10.9-29.2-15.2-43.3 7-1.8 32.4-8.4 72-13-15.9 24.3-26.7 43.9-32.8 55.3a14.22 14.22 0 0 1 6.4 8 23.42 23.42 0 0 1 10.2-8.4c6.5-11.7 17.9-31.9 34.8-56.9a711.72 711.72 0 0 1 112.4-1c31.5 44.6 28.9 48.1 42.5 64.5a21.42 21.42 0 0 1 10.4-7.4c-6.4-11.4-17.6-31-34.3-55.5 40.4 4.1 65 10 72.2 11.7-4 14.4-8.9 29.2-14.6 44.2a20.74 20.74 0 0 1 6.8 4.3l.1.1a12.72 12.72 0 0 1 8.9-5.6c4.9-13.4 9.2-26.6 12.8-39.5a359.71 359.71 0 0 1 34.5 11c106.1 39.9 74 87.9 72.6 90.4-19.8 35.1-80.1 55.2-105.7 62.5zm-114.4-114h-1.2a1.74 1.74 0 0 0-1.9 1.9v49.8c0 7.9-2.6 11.1-10.1 11.1s-10.1-3.1-10.1-11.1v-49.8a1.69 1.69 0 0 0-1.9-1.9H309a1.81 1.81 0 0 0-2 1.9v51.5c0 9.6 5 14.1 15.1 14.1h.4c10.1 0 15.1-4.6 15.1-14.1v-51.5a2 2 0 0 0-2.2-1.9zM321.7 308l-2.3-6.8-2.3 6.8-7.1.1 5.7 4.3-2.1 6.8 5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3zm-31.1 7.4l-2.3-6.8-2.3 6.8-7.1.1 5.7 4.3-2.1 6.8 5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3zm5.1-30.8h-19.4v-26.7h16.1a1.89 1.89 0 0 0 2-2v-.8a1.89 1.89 0 0 0-2-2h-16.1v-25.8h19.1a1.89 1.89 0 0 0 2-2v-.8a1.77 1.77 0 0 0-2-1.9h-22.2a1.81 1.81 0 0 0-2 1.9v63a1.81 1.81 0 0 0 2 1.9h22.5a1.77 1.77 0 0 0 2-1.9v-.8a1.83 1.83 0 0 0-2-2.06zm-7.4-99.4L286 192l-7.1.1 5.7 4.3-2.1 6.8 5.8-4.1 5.8 4.1-2.1-6.8 5.7-4.3-7.1-.1z"],
+ "readme": [576, 512, [], "f4d5", "M528.3 46.5H388.5c-48.1 0-89.9 33.3-100.4 80.3-10.6-47-52.3-80.3-100.4-80.3H48c-26.5 0-48 21.5-48 48v245.8c0 26.5 21.5 48 48 48h89.7c102.2 0 132.7 24.4 147.3 75 .7 2.8 5.2 2.8 6 0 14.7-50.6 45.2-75 147.3-75H528c26.5 0 48-21.5 48-48V94.6c0-26.4-21.3-47.9-47.7-48.1zM242 311.9c0 1.9-1.5 3.5-3.5 3.5H78.2c-1.9 0-3.5-1.5-3.5-3.5V289c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5v22.9zm0-60.9c0 1.9-1.5 3.5-3.5 3.5H78.2c-1.9 0-3.5-1.5-3.5-3.5v-22.9c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5V251zm0-60.9c0 1.9-1.5 3.5-3.5 3.5H78.2c-1.9 0-3.5-1.5-3.5-3.5v-22.9c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5v22.9zm259.3 121.7c0 1.9-1.5 3.5-3.5 3.5H337.5c-1.9 0-3.5-1.5-3.5-3.5v-22.9c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5v22.9zm0-60.9c0 1.9-1.5 3.5-3.5 3.5H337.5c-1.9 0-3.5-1.5-3.5-3.5V228c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5v22.9zm0-60.9c0 1.9-1.5 3.5-3.5 3.5H337.5c-1.9 0-3.5-1.5-3.5-3.5v-22.8c0-1.9 1.5-3.5 3.5-3.5h160.4c1.9 0 3.5 1.5 3.5 3.5V190z"],
+ "rebel": [512, 512, [], "f1d0", "M256.5 504C117.2 504 9 387.8 13.2 249.9 16 170.7 56.4 97.7 129.7 49.5c.3 0 1.9-.6 1.1.8-5.8 5.5-111.3 129.8-14.1 226.4 49.8 49.5 90 2.5 90 2.5 38.5-50.1-.6-125.9-.6-125.9-10-24.9-45.7-40.1-45.7-40.1l28.8-31.8c24.4 10.5 43.2 38.7 43.2 38.7.8-29.6-21.9-61.4-21.9-61.4L255.1 8l44.3 50.1c-20.5 28.8-21.9 62.6-21.9 62.6 13.8-23 43.5-39.3 43.5-39.3l28.5 31.8c-27.4 8.9-45.4 39.9-45.4 39.9-15.8 28.5-27.1 89.4.6 127.3 32.4 44.6 87.7-2.8 87.7-2.8 102.7-91.9-10.5-225-10.5-225-6.1-5.5.8-2.8.8-2.8 50.1 36.5 114.6 84.4 116.2 204.8C500.9 400.2 399 504 256.5 504z"],
+ "red-river": [448, 512, [], "f3e3", "M353.2 32H94.8C42.4 32 0 74.4 0 126.8v258.4C0 437.6 42.4 480 94.8 480h258.4c52.4 0 94.8-42.4 94.8-94.8V126.8c0-52.4-42.4-94.8-94.8-94.8zM144.9 200.9v56.3c0 27-21.9 48.9-48.9 48.9V151.9c0-13.2 10.7-23.9 23.9-23.9h154.2c0 27-21.9 48.9-48.9 48.9h-56.3c-12.3-.6-24.6 11.6-24 24zm176.3 72h-56.3c-12.3-.6-24.6 11.6-24 24v56.3c0 27-21.9 48.9-48.9 48.9V247.9c0-13.2 10.7-23.9 23.9-23.9h154.2c0 27-21.9 48.9-48.9 48.9z"],
+ "reddit": [512, 512, [], "f1a1", "M201.5 305.5c-13.8 0-24.9-11.1-24.9-24.6 0-13.8 11.1-24.9 24.9-24.9 13.6 0 24.6 11.1 24.6 24.9 0 13.6-11.1 24.6-24.6 24.6zM504 256c0 137-111 248-248 248S8 393 8 256 119 8 256 8s248 111 248 248zm-132.3-41.2c-9.4 0-17.7 3.9-23.8 10-22.4-15.5-52.6-25.5-86.1-26.6l17.4-78.3 55.4 12.5c0 13.6 11.1 24.6 24.6 24.6 13.8 0 24.9-11.3 24.9-24.9s-11.1-24.9-24.9-24.9c-9.7 0-18 5.8-22.1 13.8l-61.2-13.6c-3-.8-6.1 1.4-6.9 4.4l-19.1 86.4c-33.2 1.4-63.1 11.3-85.5 26.8-6.1-6.4-14.7-10.2-24.1-10.2-34.9 0-46.3 46.9-14.4 62.8-1.1 5-1.7 10.2-1.7 15.5 0 52.6 59.2 95.2 132 95.2 73.1 0 132.3-42.6 132.3-95.2 0-5.3-.6-10.8-1.9-15.8 31.3-16 19.8-62.5-14.9-62.5zM302.8 331c-18.2 18.2-76.1 17.9-93.6 0-2.2-2.2-6.1-2.2-8.3 0-2.5 2.5-2.5 6.4 0 8.6 22.8 22.8 87.3 22.8 110.2 0 2.5-2.2 2.5-6.1 0-8.6-2.2-2.2-6.1-2.2-8.3 0zm7.7-75c-13.6 0-24.6 11.1-24.6 24.9 0 13.6 11.1 24.6 24.6 24.6 13.8 0 24.9-11.1 24.9-24.6 0-13.8-11-24.9-24.9-24.9z"],
+ "reddit-alien": [512, 512, [], "f281", "M440.3 203.5c-15 0-28.2 6.2-37.9 15.9-35.7-24.7-83.8-40.6-137.1-42.3L293 52.3l88.2 19.8c0 21.6 17.6 39.2 39.2 39.2 22 0 39.7-18.1 39.7-39.7s-17.6-39.7-39.7-39.7c-15.4 0-28.7 9.3-35.3 22l-97.4-21.6c-4.9-1.3-9.7 2.2-11 7.1L246.3 177c-52.9 2.2-100.5 18.1-136.3 42.8-9.7-10.1-23.4-16.3-38.4-16.3-55.6 0-73.8 74.6-22.9 100.1-1.8 7.9-2.6 16.3-2.6 24.7 0 83.8 94.4 151.7 210.3 151.7 116.4 0 210.8-67.9 210.8-151.7 0-8.4-.9-17.2-3.1-25.1 49.9-25.6 31.5-99.7-23.8-99.7zM129.4 308.9c0-22 17.6-39.7 39.7-39.7 21.6 0 39.2 17.6 39.2 39.7 0 21.6-17.6 39.2-39.2 39.2-22 .1-39.7-17.6-39.7-39.2zm214.3 93.5c-36.4 36.4-139.1 36.4-175.5 0-4-3.5-4-9.7 0-13.7 3.5-3.5 9.7-3.5 13.2 0 27.8 28.5 120 29 149 0 3.5-3.5 9.7-3.5 13.2 0 4.1 4 4.1 10.2.1 13.7zm-.8-54.2c-21.6 0-39.2-17.6-39.2-39.2 0-22 17.6-39.7 39.2-39.7 22 0 39.7 17.6 39.7 39.7-.1 21.5-17.7 39.2-39.7 39.2z"],
+ "reddit-square": [448, 512, [], "f1a2", "M283.2 345.5c2.7 2.7 2.7 6.8 0 9.2-24.5 24.5-93.8 24.6-118.4 0-2.7-2.4-2.7-6.5 0-9.2 2.4-2.4 6.5-2.4 8.9 0 18.7 19.2 81 19.6 100.5 0 2.4-2.3 6.6-2.3 9 0zm-91.3-53.8c0-14.9-11.9-26.8-26.5-26.8-14.9 0-26.8 11.9-26.8 26.8 0 14.6 11.9 26.5 26.8 26.5 14.6 0 26.5-11.9 26.5-26.5zm90.7-26.8c-14.6 0-26.5 11.9-26.5 26.8 0 14.6 11.9 26.5 26.5 26.5 14.9 0 26.8-11.9 26.8-26.5 0-14.9-11.9-26.8-26.8-26.8zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-99.7 140.6c-10.1 0-19 4.2-25.6 10.7-24.1-16.7-56.5-27.4-92.5-28.6l18.7-84.2 59.5 13.4c0 14.6 11.9 26.5 26.5 26.5 14.9 0 26.8-12.2 26.8-26.8 0-14.6-11.9-26.8-26.8-26.8-10.4 0-19.3 6.2-23.8 14.9l-65.7-14.6c-3.3-.9-6.5 1.5-7.4 4.8l-20.5 92.8c-35.7 1.5-67.8 12.2-91.9 28.9-6.5-6.8-15.8-11-25.9-11-37.5 0-49.8 50.4-15.5 67.5-1.2 5.4-1.8 11-1.8 16.7 0 56.5 63.7 102.3 141.9 102.3 78.5 0 142.2-45.8 142.2-102.3 0-5.7-.6-11.6-2.1-17 33.6-17.2 21.2-67.2-16.1-67.2z"],
+ "redhat": [512, 512, [], "f7bc", "M341.52 285.56c33.65 0 82.34-6.94 82.34-47 .22-6.74.86-1.82-20.88-96.24-4.62-19.15-8.68-27.84-42.31-44.65-26.09-13.34-82.92-35.37-99.73-35.37-15.66 0-20.2 20.17-38.87 20.17-18 0-31.31-15.06-48.12-15.06-16.14 0-26.66 11-34.78 33.62-27.5 77.55-26.28 74.27-26.12 78.27 0 24.8 97.64 106.11 228.47 106.11M429 254.84c4.65 22 4.65 24.35 4.65 27.25 0 37.66-42.33 58.56-98 58.56-125.74.08-235.91-73.65-235.91-122.33a49.55 49.55 0 0 1 4.06-19.72C58.56 200.86 0 208.93 0 260.63c0 84.67 200.63 189 359.49 189 121.79 0 152.51-55.08 152.51-98.58 0-34.21-29.59-73.05-82.93-96.24"],
+ "renren": [512, 512, [], "f18b", "M214 169.1c0 110.4-61 205.4-147.6 247.4C30 373.2 8 317.7 8 256.6 8 133.9 97.1 32.2 214 12.5v156.6zM255 504c-42.9 0-83.3-11-118.5-30.4C193.7 437.5 239.9 382.9 255 319c15.5 63.9 61.7 118.5 118.8 154.7C338.7 493 298.3 504 255 504zm190.6-87.5C359 374.5 298 279.6 298 169.1V12.5c116.9 19.7 206 121.4 206 244.1 0 61.1-22 116.6-58.4 159.9z"],
+ "replyd": [448, 512, [], "f3e6", "M320 480H128C57.6 480 0 422.4 0 352V160C0 89.6 57.6 32 128 32h192c70.4 0 128 57.6 128 128v192c0 70.4-57.6 128-128 128zM193.4 273.2c-6.1-2-11.6-3.1-16.4-3.1-7.2 0-13.5 1.9-18.9 5.6-5.4 3.7-9.6 9-12.8 15.8h-1.1l-4.2-18.3h-28v138.9h36.1v-89.7c1.5-5.4 4.4-9.8 8.7-13.2 4.3-3.4 9.8-5.1 16.2-5.1 4.6 0 9.8 1 15.6 3.1l4.8-34zm115.2 103.4c-3.2 2.4-7.7 4.8-13.7 7.1-6 2.3-12.8 3.5-20.4 3.5-12.2 0-21.1-3-26.5-8.9-5.5-5.9-8.5-14.7-9-26.4h83.3c.9-4.8 1.6-9.4 2.1-13.9.5-4.4.7-8.6.7-12.5 0-10.7-1.6-19.7-4.7-26.9-3.2-7.2-7.3-13-12.5-17.2-5.2-4.3-11.1-7.3-17.8-9.2-6.7-1.8-13.5-2.8-20.6-2.8-21.1 0-37.5 6.1-49.2 18.3s-17.5 30.5-17.5 55c0 22.8 5.2 40.7 15.6 53.7 10.4 13.1 26.8 19.6 49.2 19.6 10.7 0 20.9-1.5 30.4-4.6 9.5-3.1 17.1-6.8 22.6-11.2l-12-23.6zm-21.8-70.3c3.8 5.4 5.3 13.1 4.6 23.1h-51.7c.9-9.4 3.7-17 8.2-22.6 4.5-5.6 11.5-8.5 21-8.5 8.2-.1 14.1 2.6 17.9 8zm79.9 2.5c4.1 3.9 9.4 5.8 16.1 5.8 7 0 12.6-1.9 16.7-5.8s6.1-9.1 6.1-15.6-2-11.6-6.1-15.4c-4.1-3.8-9.6-5.7-16.7-5.7-6.7 0-12 1.9-16.1 5.7-4.1 3.8-6.1 8.9-6.1 15.4s2 11.7 6.1 15.6zm0 100.5c4.1 3.9 9.4 5.8 16.1 5.8 7 0 12.6-1.9 16.7-5.8s6.1-9.1 6.1-15.6-2-11.6-6.1-15.4c-4.1-3.8-9.6-5.7-16.7-5.7-6.7 0-12 1.9-16.1 5.7-4.1 3.8-6.1 8.9-6.1 15.4 0 6.6 2 11.7 6.1 15.6z"],
+ "researchgate": [448, 512, [], "f4f8", "M0 32v448h448V32H0zm262.2 334.4c-6.6 3-33.2 6-50-14.2-9.2-10.6-25.3-33.3-42.2-63.6-8.9 0-14.7 0-21.4-.6v46.4c0 23.5 6 21.2 25.8 23.9v8.1c-6.9-.3-23.1-.8-35.6-.8-13.1 0-26.1.6-33.6.8v-8.1c15.5-2.9 22-1.3 22-23.9V225c0-22.6-6.4-21-22-23.9V193c25.8 1 53.1-.6 70.9-.6 31.7 0 55.9 14.4 55.9 45.6 0 21.1-16.7 42.2-39.2 47.5 13.6 24.2 30 45.6 42.2 58.9 7.2 7.8 17.2 14.7 27.2 14.7v7.3zm22.9-135c-23.3 0-32.2-15.7-32.2-32.2V167c0-12.2 8.8-30.4 34-30.4s30.4 17.9 30.4 17.9l-10.7 7.2s-5.5-12.5-19.7-12.5c-7.9 0-19.7 7.3-19.7 19.7v26.8c0 13.4 6.6 23.3 17.9 23.3 14.1 0 21.5-10.9 21.5-26.8h-17.9v-10.7h30.4c0 20.5 4.7 49.9-34 49.9zm-116.5 44.7c-9.4 0-13.6-.3-20-.8v-69.7c6.4-.6 15-.6 22.5-.6 23.3 0 37.2 12.2 37.2 34.5 0 21.9-15 36.6-39.7 36.6z"],
+ "resolving": [496, 512, [], "f3e7", "M281.2 278.2c46-13.3 49.6-23.5 44-43.4L314 195.5c-6.1-20.9-18.4-28.1-71.1-12.8L54.7 236.8l28.6 98.6 197.9-57.2zM248.5 8C131.4 8 33.2 88.7 7.2 197.5l221.9-63.9c34.8-10.2 54.2-11.7 79.3-8.2 36.3 6.1 52.7 25 61.4 55.2l10.7 37.8c8.2 28.1 1 50.6-23.5 73.6-19.4 17.4-31.2 24.5-61.4 33.2L203 351.8l220.4 27.1 9.7 34.2-48.1 13.3-286.8-37.3 23 80.2c36.8 22 80.3 34.7 126.3 34.7 137 0 248.5-111.4 248.5-248.3C497 119.4 385.5 8 248.5 8zM38.3 388.6L0 256.8c0 48.5 14.3 93.4 38.3 131.8z"],
+ "rev": [448, 512, [], "f5b2", "M289.67 274.89a65.57 65.57 0 1 1-65.56-65.56 65.64 65.64 0 0 1 65.56 65.56zm139.55-5.05h-.13a204.69 204.69 0 0 0-74.32-153l-45.38 26.2a157.07 157.07 0 0 1 71.81 131.84C381.2 361.5 310.73 432 224.11 432S67 361.5 67 274.88c0-81.88 63-149.27 143-156.43v39.12l108.77-62.79L210 32v38.32c-106.7 7.25-191 96-191 204.57 0 111.59 89.12 202.29 200.06 205v.11h210.16V269.84z"],
+ "rocketchat": [576, 512, [], "f3e8", "M284.046,224.8a34.114,34.114,0,1,0,34.317,34.113A34.217,34.217,0,0,0,284.046,224.8Zm-110.45,0a34.114,34.114,0,1,0,34.317,34.113A34.217,34.217,0,0,0,173.6,224.8Zm220.923,0a34.114,34.114,0,1,0,34.317,34.113A34.215,34.215,0,0,0,394.519,224.8Zm153.807-55.319c-15.535-24.172-37.31-45.57-64.681-63.618-52.886-34.817-122.374-54-195.666-54a405.975,405.975,0,0,0-72.032,6.357,238.524,238.524,0,0,0-49.51-36.588C99.684-11.7,40.859.711,11.135,11.421A14.291,14.291,0,0,0,5.58,34.782C26.542,56.458,61.222,99.3,52.7,138.252c-33.142,33.9-51.112,74.776-51.112,117.337,0,43.372,17.97,84.248,51.112,118.148,8.526,38.956-26.154,81.816-47.116,103.491a14.284,14.284,0,0,0,5.555,23.34c29.724,10.709,88.549,23.147,155.324-10.2a238.679,238.679,0,0,0,49.51-36.589A405.972,405.972,0,0,0,288,460.14c73.313,0,142.8-19.159,195.667-53.975,27.371-18.049,49.145-39.426,64.679-63.619,17.309-26.923,26.07-55.916,26.07-86.125C574.394,225.4,565.634,196.43,548.326,169.485ZM284.987,409.9a345.65,345.65,0,0,1-89.446-11.5l-20.129,19.393a184.366,184.366,0,0,1-37.138,27.585,145.767,145.767,0,0,1-52.522,14.87c.983-1.771,1.881-3.563,2.842-5.356q30.258-55.68,16.325-100.078c-32.992-25.962-52.778-59.2-52.778-95.4,0-83.1,104.254-150.469,232.846-150.469s232.867,67.373,232.867,150.469C517.854,342.525,413.6,409.9,284.987,409.9Z"],
+ "rockrms": [496, 512, [], "f3e9", "M248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm157.4 419.5h-90l-112-131.3c-17.9-20.4-3.9-56.1 26.6-56.1h75.3l-84.6-99.3-84.3 98.9h-90L193.5 67.2c14.4-18.4 41.3-17.3 54.5 0l157.7 185.1c19 22.8 2 57.2-27.6 56.1-.6 0-74.2.2-74.2.2l101.5 118.9z"],
+ "rust": [512, 512, [], "e07a", "M508.52,249.75,486.7,236.24c-.17-2-.34-3.93-.55-5.88l18.72-17.5a7.35,7.35,0,0,0-2.44-12.25l-24-9c-.54-1.88-1.08-3.78-1.67-5.64l15-20.83a7.35,7.35,0,0,0-4.79-11.54l-25.42-4.15c-.9-1.73-1.79-3.45-2.73-5.15l10.68-23.42a7.35,7.35,0,0,0-6.95-10.39l-25.82.91q-1.79-2.22-3.61-4.4L439,81.84A7.36,7.36,0,0,0,430.16,73L405,78.93q-2.17-1.83-4.4-3.61l.91-25.82a7.35,7.35,0,0,0-10.39-7L367.7,53.23c-1.7-.94-3.43-1.84-5.15-2.73L358.4,25.08a7.35,7.35,0,0,0-11.54-4.79L326,35.26c-1.86-.59-3.75-1.13-5.64-1.67l-9-24a7.35,7.35,0,0,0-12.25-2.44l-17.5,18.72c-1.95-.21-3.91-.38-5.88-.55L262.25,3.48a7.35,7.35,0,0,0-12.5,0L236.24,25.3c-2,.17-3.93.34-5.88.55L212.86,7.13a7.35,7.35,0,0,0-12.25,2.44l-9,24c-1.89.55-3.79,1.08-5.66,1.68l-20.82-15a7.35,7.35,0,0,0-11.54,4.79l-4.15,25.41c-1.73.9-3.45,1.79-5.16,2.73L120.88,42.55a7.35,7.35,0,0,0-10.39,7l.92,25.81c-1.49,1.19-3,2.39-4.42,3.61L81.84,73A7.36,7.36,0,0,0,73,81.84L78.93,107c-1.23,1.45-2.43,2.93-3.62,4.41l-25.81-.91a7.42,7.42,0,0,0-6.37,3.26,7.35,7.35,0,0,0-.57,7.13l10.66,23.41c-.94,1.7-1.83,3.43-2.73,5.16L25.08,153.6a7.35,7.35,0,0,0-4.79,11.54l15,20.82c-.59,1.87-1.13,3.77-1.68,5.66l-24,9a7.35,7.35,0,0,0-2.44,12.25l18.72,17.5c-.21,1.95-.38,3.91-.55,5.88L3.48,249.75a7.35,7.35,0,0,0,0,12.5L25.3,275.76c.17,2,.34,3.92.55,5.87L7.13,299.13a7.35,7.35,0,0,0,2.44,12.25l24,9c.55,1.89,1.08,3.78,1.68,5.65l-15,20.83a7.35,7.35,0,0,0,4.79,11.54l25.42,4.15c.9,1.72,1.79,3.45,2.73,5.14L42.56,391.12a7.35,7.35,0,0,0,.57,7.13,7.13,7.13,0,0,0,6.37,3.26l25.83-.91q1.77,2.22,3.6,4.4L73,430.16A7.36,7.36,0,0,0,81.84,439L107,433.07q2.18,1.83,4.41,3.61l-.92,25.82a7.35,7.35,0,0,0,10.39,6.95l23.43-10.68c1.69.94,3.42,1.83,5.14,2.73l4.15,25.42a7.34,7.34,0,0,0,11.54,4.78l20.83-15c1.86.6,3.76,1.13,5.65,1.68l9,24a7.36,7.36,0,0,0,12.25,2.44l17.5-18.72c1.95.21,3.92.38,5.88.55l13.51,21.82a7.35,7.35,0,0,0,12.5,0l13.51-21.82c2-.17,3.93-.34,5.88-.56l17.5,18.73a7.36,7.36,0,0,0,12.25-2.44l9-24c1.89-.55,3.78-1.08,5.65-1.68l20.82,15a7.34,7.34,0,0,0,11.54-4.78l4.15-25.42c1.72-.9,3.45-1.79,5.15-2.73l23.42,10.68a7.35,7.35,0,0,0,10.39-6.95l-.91-25.82q2.22-1.79,4.4-3.61L430.16,439a7.36,7.36,0,0,0,8.84-8.84L433.07,405q1.83-2.17,3.61-4.4l25.82.91a7.23,7.23,0,0,0,6.37-3.26,7.35,7.35,0,0,0,.58-7.13L458.77,367.7c.94-1.7,1.83-3.43,2.73-5.15l25.42-4.15a7.35,7.35,0,0,0,4.79-11.54l-15-20.83c.59-1.87,1.13-3.76,1.67-5.65l24-9a7.35,7.35,0,0,0,2.44-12.25l-18.72-17.5c.21-1.95.38-3.91.55-5.87l21.82-13.51a7.35,7.35,0,0,0,0-12.5Zm-151,129.08A13.91,13.91,0,0,0,341,389.51l-7.64,35.67A187.51,187.51,0,0,1,177,424.44l-7.64-35.66a13.87,13.87,0,0,0-16.46-10.68l-31.51,6.76a187.38,187.38,0,0,1-16.26-19.21H258.3c1.72,0,2.89-.29,2.89-1.91V309.55c0-1.57-1.17-1.91-2.89-1.91H213.47l.05-34.35H262c4.41,0,23.66,1.28,29.79,25.87,1.91,7.55,6.17,32.14,9.06,40,2.89,8.82,14.6,26.46,27.1,26.46H407a187.3,187.3,0,0,1-17.34,20.09Zm25.77,34.49A15.24,15.24,0,1,1,368,398.08h.44A15.23,15.23,0,0,1,383.24,413.32Zm-225.62-.68a15.24,15.24,0,1,1-15.25-15.25h.45A15.25,15.25,0,0,1,157.62,412.64ZM69.57,234.15l32.83-14.6a13.88,13.88,0,0,0,7.06-18.33L102.69,186h26.56V305.73H75.65A187.65,187.65,0,0,1,69.57,234.15ZM58.31,198.09a15.24,15.24,0,0,1,15.23-15.25H74a15.24,15.24,0,1,1-15.67,15.24Zm155.16,24.49.05-35.32h63.26c3.28,0,23.07,3.77,23.07,18.62,0,12.29-15.19,16.7-27.68,16.7ZM399,306.71c-9.8,1.13-20.63-4.12-22-10.09-5.78-32.49-15.39-39.4-30.57-51.4,18.86-11.95,38.46-29.64,38.46-53.26,0-25.52-17.49-41.59-29.4-49.48-16.76-11-35.28-13.23-40.27-13.23H116.32A187.49,187.49,0,0,1,221.21,70.06l23.47,24.6a13.82,13.82,0,0,0,19.6.44l26.26-25a187.51,187.51,0,0,1,128.37,91.43l-18,40.57A14,14,0,0,0,408,220.43l34.59,15.33a187.12,187.12,0,0,1,.4,32.54H423.71c-1.91,0-2.69,1.27-2.69,3.13v8.82C421,301,409.31,305.58,399,306.71ZM240,60.21A15.24,15.24,0,0,1,255.21,45h.45A15.24,15.24,0,1,1,240,60.21ZM436.84,214a15.24,15.24,0,1,1,0-30.48h.44a15.24,15.24,0,0,1-.44,30.48Z"],
+ "safari": [512, 512, [], "f267", "M274.69,274.69l-37.38-37.38L166,346ZM256,8C119,8,8,119,8,256S119,504,256,504,504,393,504,256,393,8,256,8ZM411.85,182.79l14.78-6.13A8,8,0,0,1,437.08,181h0a8,8,0,0,1-4.33,10.46L418,197.57a8,8,0,0,1-10.45-4.33h0A8,8,0,0,1,411.85,182.79ZM314.43,94l6.12-14.78A8,8,0,0,1,331,74.92h0a8,8,0,0,1,4.33,10.45l-6.13,14.78a8,8,0,0,1-10.45,4.33h0A8,8,0,0,1,314.43,94ZM256,60h0a8,8,0,0,1,8,8V84a8,8,0,0,1-8,8h0a8,8,0,0,1-8-8V68A8,8,0,0,1,256,60ZM181,74.92a8,8,0,0,1,10.46,4.33L197.57,94a8,8,0,1,1-14.78,6.12l-6.13-14.78A8,8,0,0,1,181,74.92Zm-63.58,42.49h0a8,8,0,0,1,11.31,0L140,128.72A8,8,0,0,1,140,140h0a8,8,0,0,1-11.31,0l-11.31-11.31A8,8,0,0,1,117.41,117.41ZM60,256h0a8,8,0,0,1,8-8H84a8,8,0,0,1,8,8h0a8,8,0,0,1-8,8H68A8,8,0,0,1,60,256Zm40.15,73.21-14.78,6.13A8,8,0,0,1,74.92,331h0a8,8,0,0,1,4.33-10.46L94,314.43a8,8,0,0,1,10.45,4.33h0A8,8,0,0,1,100.15,329.21Zm4.33-136h0A8,8,0,0,1,94,197.57l-14.78-6.12A8,8,0,0,1,74.92,181h0a8,8,0,0,1,10.45-4.33l14.78,6.13A8,8,0,0,1,104.48,193.24ZM197.57,418l-6.12,14.78a8,8,0,0,1-14.79-6.12l6.13-14.78A8,8,0,1,1,197.57,418ZM264,444a8,8,0,0,1-8,8h0a8,8,0,0,1-8-8V428a8,8,0,0,1,8-8h0a8,8,0,0,1,8,8Zm67-6.92h0a8,8,0,0,1-10.46-4.33L314.43,418a8,8,0,0,1,4.33-10.45h0a8,8,0,0,1,10.45,4.33l6.13,14.78A8,8,0,0,1,331,437.08Zm63.58-42.49h0a8,8,0,0,1-11.31,0L372,383.28A8,8,0,0,1,372,372h0a8,8,0,0,1,11.31,0l11.31,11.31A8,8,0,0,1,394.59,394.59ZM286.25,286.25,110.34,401.66,225.75,225.75,401.66,110.34ZM437.08,331h0a8,8,0,0,1-10.45,4.33l-14.78-6.13a8,8,0,0,1-4.33-10.45h0A8,8,0,0,1,418,314.43l14.78,6.12A8,8,0,0,1,437.08,331ZM444,264H428a8,8,0,0,1-8-8h0a8,8,0,0,1,8-8h16a8,8,0,0,1,8,8h0A8,8,0,0,1,444,264Z"],
+ "salesforce": [640, 512, [], "f83b", "M248.89 245.64h-26.35c.69-5.16 3.32-14.12 13.64-14.12 6.75 0 11.97 3.82 12.71 14.12zm136.66-13.88c-.47 0-14.11-1.77-14.11 20s13.63 20 14.11 20c13 0 14.11-13.54 14.11-20 0-21.76-13.66-20-14.11-20zm-243.22 23.76a8.63 8.63 0 0 0-3.29 7.29c0 4.78 2.08 6.05 3.29 7.05 4.7 3.7 15.07 2.12 20.93.95v-16.94c-5.32-1.07-16.73-1.96-20.93 1.65zM640 232c0 87.58-80 154.39-165.36 136.43-18.37 33-70.73 70.75-132.2 41.63-41.16 96.05-177.89 92.18-213.81-5.17C8.91 428.78-50.19 266.52 53.36 205.61 18.61 126.18 76 32 167.67 32a124.24 124.24 0 0 1 98.56 48.7c20.7-21.4 49.4-34.81 81.15-34.81 42.34 0 79 23.52 98.8 58.57C539 63.78 640 132.69 640 232zm-519.55 31.8c0-11.76-11.69-15.17-17.87-17.17-5.27-2.11-13.41-3.51-13.41-8.94 0-9.46 17-6.66 25.17-2.12 0 0 1.17.71 1.64-.47.24-.7 2.36-6.58 2.59-7.29a1.13 1.13 0 0 0-.7-1.41c-12.33-7.63-40.7-8.51-40.7 12.7 0 12.46 11.49 15.44 17.88 17.17 4.72 1.58 13.17 3 13.17 8.7 0 4-3.53 7.06-9.17 7.06a31.76 31.76 0 0 1-19-6.35c-.47-.23-1.42-.71-1.65.71l-2.4 7.47c-.47.94.23 1.18.23 1.41 1.75 1.4 10.3 6.59 22.82 6.59 13.17 0 21.4-7.06 21.4-18.11zm32-42.58c-10.13 0-18.66 3.17-21.4 5.18a1 1 0 0 0-.24 1.41l2.59 7.06a1 1 0 0 0 1.18.7c.65 0 6.8-4 16.93-4 4 0 7.06.71 9.18 2.36 3.6 2.8 3.06 8.29 3.06 10.58-4.79-.3-19.11-3.44-29.41 3.76a16.92 16.92 0 0 0-7.34 14.54c0 5.9 1.51 10.4 6.59 14.35 12.24 8.16 36.28 2 38.1 1.41 1.58-.32 3.53-.66 3.53-1.88v-33.88c.04-4.61.32-21.64-22.78-21.64zM199 200.24a1.11 1.11 0 0 0-1.18-1.18H188a1.11 1.11 0 0 0-1.17 1.18v79a1.11 1.11 0 0 0 1.17 1.18h9.88a1.11 1.11 0 0 0 1.18-1.18zm55.75 28.93c-2.1-2.31-6.79-7.53-17.65-7.53-3.51 0-14.16.23-20.7 8.94-6.35 7.63-6.58 18.11-6.58 21.41 0 3.12.15 14.26 7.06 21.17 2.64 2.91 9.06 8.23 22.81 8.23 10.82 0 16.47-2.35 18.58-3.76.47-.24.71-.71.24-1.88l-2.35-6.83a1.26 1.26 0 0 0-1.41-.7c-2.59.94-6.35 2.82-15.29 2.82-17.42 0-16.85-14.74-16.94-16.7h37.17a1.23 1.23 0 0 0 1.17-.94c-.29 0 2.07-14.7-6.09-24.23zm36.69 52.69c13.17 0 21.41-7.06 21.41-18.11 0-11.76-11.7-15.17-17.88-17.17-4.14-1.66-13.41-3.38-13.41-8.94 0-3.76 3.29-6.35 8.47-6.35a38.11 38.11 0 0 1 16.7 4.23s1.18.71 1.65-.47c.23-.7 2.35-6.58 2.58-7.29a1.13 1.13 0 0 0-.7-1.41c-7.91-4.9-16.74-4.94-20.23-4.94-12 0-20.46 7.29-20.46 17.64 0 12.46 11.48 15.44 17.87 17.17 6.11 2 13.17 3.26 13.17 8.7 0 4-3.52 7.06-9.17 7.06a31.8 31.8 0 0 1-19-6.35 1 1 0 0 0-1.65.71l-2.35 7.52c-.47.94.23 1.18.23 1.41 1.72 1.4 10.33 6.59 22.79 6.59zM357.09 224c0-.71-.24-1.18-1.18-1.18h-11.76c0-.14.94-8.94 4.47-12.47 4.16-4.15 11.76-1.64 12-1.64 1.17.47 1.41 0 1.64-.47l2.83-7.77c.7-.94 0-1.17-.24-1.41-5.09-2-17.35-2.87-24.46 4.24-5.48 5.48-7 13.92-8 19.52h-8.47a1.28 1.28 0 0 0-1.17 1.18l-1.42 7.76c0 .7.24 1.17 1.18 1.17h8.23c-8.51 47.9-8.75 50.21-10.35 55.52-1.08 3.62-3.29 6.9-5.88 7.76-.09 0-3.88 1.68-9.64-.24 0 0-.94-.47-1.41.71-.24.71-2.59 6.82-2.83 7.53s0 1.41.47 1.41c5.11 2 13 1.77 17.88 0 6.28-2.28 9.72-7.89 11.53-12.94 2.75-7.71 2.81-9.79 11.76-59.74h12.23a1.29 1.29 0 0 0 1.18-1.18zm53.39 16c-.56-1.68-5.1-18.11-25.17-18.11-15.25 0-23 10-25.16 18.11-1 3-3.18 14 0 23.52.09.3 4.41 18.12 25.16 18.12 14.95 0 22.9-9.61 25.17-18.12 3.21-9.61 1.01-20.52 0-23.52zm45.4-16.7c-5-1.65-16.62-1.9-22.11 5.41v-4.47a1.11 1.11 0 0 0-1.18-1.17h-9.4a1.11 1.11 0 0 0-1.18 1.17v55.28a1.12 1.12 0 0 0 1.18 1.18h9.64a1.12 1.12 0 0 0 1.18-1.18v-27.77c0-2.91.05-11.37 4.46-15.05 4.9-4.9 12-3.36 13.41-3.06a1.57 1.57 0 0 0 1.41-.94 74 74 0 0 0 3.06-8 1.16 1.16 0 0 0-.47-1.41zm46.81 54.1l-2.12-7.29c-.47-1.18-1.41-.71-1.41-.71-4.23 1.82-10.15 1.89-11.29 1.89-4.64 0-17.17-1.13-17.17-19.76 0-6.23 1.85-19.76 16.47-19.76a34.85 34.85 0 0 1 11.52 1.65s.94.47 1.18-.71c.94-2.59 1.64-4.47 2.59-7.53.23-.94-.47-1.17-.71-1.17-11.59-3.87-22.34-2.53-27.76 0-1.59.74-16.23 6.49-16.23 27.52 0 2.9-.58 30.11 28.94 30.11a44.45 44.45 0 0 0 15.52-2.83 1.3 1.3 0 0 0 .47-1.42zm53.87-39.52c-.8-3-5.37-16.23-22.35-16.23-16 0-23.52 10.11-25.64 18.59a38.58 38.58 0 0 0-1.65 11.76c0 25.87 18.84 29.4 29.88 29.4 10.82 0 16.46-2.35 18.58-3.76.47-.24.71-.71.24-1.88l-2.36-6.83a1.26 1.26 0 0 0-1.41-.7c-2.59.94-6.35 2.82-15.29 2.82-17.42 0-16.85-14.74-16.93-16.7h37.16a1.25 1.25 0 0 0 1.18-.94c-.24-.01.94-7.07-1.41-15.54zm-23.29-6.35c-10.33 0-13 9-13.64 14.12H546c-.88-11.92-7.62-14.13-12.73-14.13z"],
+ "sass": [640, 512, [], "f41e", "M301.84 378.92c-.3.6-.6 1.08 0 0zm249.13-87a131.16 131.16 0 0 0-58 13.5c-5.9-11.9-12-22.3-13-30.1-1.2-9.1-2.5-14.5-1.1-25.3s7.7-26.1 7.6-27.2-1.4-6.6-14.3-6.7-24 2.5-25.29 5.9a122.83 122.83 0 0 0-5.3 19.1c-2.3 11.7-25.79 53.5-39.09 75.3-4.4-8.5-8.1-16-8.9-22-1.2-9.1-2.5-14.5-1.1-25.3s7.7-26.1 7.6-27.2-1.4-6.6-14.29-6.7-24 2.5-25.3 5.9-2.7 11.4-5.3 19.1-33.89 77.3-42.08 95.4c-4.2 9.2-7.8 16.6-10.4 21.6-.4.8-.7 1.3-.9 1.7.3-.5.5-1 .5-.8-2.2 4.3-3.5 6.7-3.5 6.7v.1c-1.7 3.2-3.6 6.1-4.5 6.1-.6 0-1.9-8.4.3-19.9 4.7-24.2 15.8-61.8 15.7-63.1-.1-.7 2.1-7.2-7.3-10.7-9.1-3.3-12.4 2.2-13.2 2.2s-1.4 2-1.4 2 10.1-42.4-19.39-42.4c-18.4 0-44 20.2-56.58 38.5-7.9 4.3-25 13.6-43 23.5-6.9 3.8-14 7.7-20.7 11.4-.5-.5-.9-1-1.4-1.5-35.79-38.2-101.87-65.2-99.07-116.5 1-18.7 7.5-67.8 127.07-127.4 98-48.8 176.35-35.4 189.84-5.6 19.4 42.5-41.89 121.6-143.66 133-38.79 4.3-59.18-10.7-64.28-16.3-5.3-5.9-6.1-6.2-8.1-5.1-3.3 1.8-1.2 7 0 10.1 3 7.9 15.5 21.9 36.79 28.9 18.7 6.1 64.18 9.5 119.17-11.8 61.78-23.8 109.87-90.1 95.77-145.6C386.52 18.32 293-.18 204.57 31.22c-52.69 18.7-109.67 48.1-150.66 86.4-48.69 45.6-56.48 85.3-53.28 101.9 11.39 58.9 92.57 97.3 125.06 125.7-1.6.9-3.1 1.7-4.5 2.5-16.29 8.1-78.18 40.5-93.67 74.7-17.5 38.8 2.9 66.6 16.29 70.4 41.79 11.6 84.58-9.3 107.57-43.6s20.2-79.1 9.6-99.5c-.1-.3-.3-.5-.4-.8 4.2-2.5 8.5-5 12.8-7.5 8.29-4.9 16.39-9.4 23.49-13.3-4 10.8-6.9 23.8-8.4 42.6-1.8 22 7.3 50.5 19.1 61.7 5.2 4.9 11.49 5 15.39 5 13.8 0 20-11.4 26.89-25 8.5-16.6 16-35.9 16-35.9s-9.4 52.2 16.3 52.2c9.39 0 18.79-12.1 23-18.3v.1s.2-.4.7-1.2c1-1.5 1.5-2.4 1.5-2.4v-.3c3.8-6.5 12.1-21.4 24.59-46 16.2-31.8 31.69-71.5 31.69-71.5a201.24 201.24 0 0 0 6.2 25.8c2.8 9.5 8.7 19.9 13.4 30-3.8 5.2-6.1 8.2-6.1 8.2a.31.31 0 0 0 .1.2c-3 4-6.4 8.3-9.9 12.5-12.79 15.2-28 32.6-30 37.6-2.4 5.9-1.8 10.3 2.8 13.7 3.4 2.6 9.4 3 15.69 2.5 11.5-.8 19.6-3.6 23.5-5.4a82.2 82.2 0 0 0 20.19-10.6c12.5-9.2 20.1-22.4 19.4-39.8-.4-9.6-3.5-19.2-7.3-28.2 1.1-1.6 2.3-3.3 3.4-5C434.8 301.72 450.1 270 450.1 270a201.24 201.24 0 0 0 6.2 25.8c2.4 8.1 7.09 17 11.39 25.7-18.59 15.1-30.09 32.6-34.09 44.1-7.4 21.3-1.6 30.9 9.3 33.1 4.9 1 11.9-1.3 17.1-3.5a79.46 79.46 0 0 0 21.59-11.1c12.5-9.2 24.59-22.1 23.79-39.6-.3-7.9-2.5-15.8-5.4-23.4 15.7-6.6 36.09-10.2 62.09-7.2 55.68 6.5 66.58 41.3 64.48 55.8s-13.8 22.6-17.7 25-5.1 3.3-4.8 5.1c.5 2.6 2.3 2.5 5.6 1.9 4.6-.8 29.19-11.8 30.29-38.7 1.6-34-31.09-71.4-89-71.1zm-429.18 144.7c-18.39 20.1-44.19 27.7-55.28 21.3C54.61 451 59.31 421.42 82 400c13.8-13 31.59-25 43.39-32.4 2.7-1.6 6.6-4 11.4-6.9.8-.5 1.2-.7 1.2-.7.9-.6 1.9-1.1 2.9-1.7 8.29 30.4.3 57.2-19.1 78.3zm134.36-91.4c-6.4 15.7-19.89 55.7-28.09 53.6-7-1.8-11.3-32.3-1.4-62.3 5-15.1 15.6-33.1 21.9-40.1 10.09-11.3 21.19-14.9 23.79-10.4 3.5 5.9-12.2 49.4-16.2 59.2zm111 53c-2.7 1.4-5.2 2.3-6.4 1.6-.9-.5 1.1-2.4 1.1-2.4s13.9-14.9 19.4-21.7c3.2-4 6.9-8.7 10.89-13.9 0 .5.1 1 .1 1.6-.13 17.9-17.32 30-25.12 34.8zm85.58-19.5c-2-1.4-1.7-6.1 5-20.7 2.6-5.7 8.59-15.3 19-24.5a36.18 36.18 0 0 1 1.9 10.8c-.1 22.5-16.2 30.9-25.89 34.4z"],
+ "schlix": [448, 512, [], "f3ea", "M350.5 157.7l-54.2-46.1 73.4-39 78.3 44.2-97.5 40.9zM192 122.1l45.7-28.2 34.7 34.6-55.4 29-25-35.4zm-65.1 6.6l31.9-22.1L176 135l-36.7 22.5-12.4-28.8zm-23.3 88.2l-8.8-34.8 29.6-18.3 13.1 35.3-33.9 17.8zm-21.2-83.7l23.9-18.1 8.9 24-26.7 18.3-6.1-24.2zM59 206.5l-3.6-28.4 22.3-15.5 6.1 28.7L59 206.5zm-30.6 16.6l20.8-12.8 3.3 33.4-22.9 12-1.2-32.6zM1.4 268l19.2-10.2.4 38.2-21 8.8L1.4 268zm59.1 59.3l-28.3 8.3-1.6-46.8 25.1-10.7 4.8 49.2zM99 263.2l-31.1 13-5.2-40.8L90.1 221l8.9 42.2zM123.2 377l-41.6 5.9-8.1-63.5 35.2-10.8 14.5 68.4zm28.5-139.9l21.2 57.1-46.2 13.6-13.7-54.1 38.7-16.6zm85.7 230.5l-70.9-3.3-24.3-95.8 55.2-8.6 40 107.7zm-84.9-279.7l42.2-22.4 28 45.9-50.8 21.3-19.4-44.8zm41 94.9l61.3-18.7 52.8 86.6-79.8 11.3-34.3-79.2zm51.4-85.6l67.3-28.8 65.5 65.4-88.6 26.2-44.2-62.8z"],
+ "scribd": [384, 512, [], "f28a", "M42.3 252.7c-16.1-19-24.7-45.9-24.8-79.9 0-100.4 75.2-153.1 167.2-153.1 98.6-1.6 156.8 49 184.3 70.6l-50.5 72.1-37.3-24.6 26.9-38.6c-36.5-24-79.4-36.5-123-35.8-50.7-.8-111.7 27.2-111.7 76.2 0 18.7 11.2 20.7 28.6 15.6 23.3-5.3 41.9.6 55.8 14 26.4 24.3 23.2 67.6-.7 91.9-29.2 29.5-85.2 27.3-114.8-8.4zm317.7 5.9c-15.5-18.8-38.9-29.4-63.2-28.6-38.1-2-71.1 28-70.5 67.2-.7 16.8 6 33 18.4 44.3 14.1 13.9 33 19.7 56.3 14.4 17.4-5.1 28.6-3.1 28.6 15.6 0 4.3-.5 8.5-1.4 12.7-16.7 40.9-59.5 64.4-121.4 64.4-51.9.2-102.4-16.4-144.1-47.3l33.7-39.4-35.6-27.4L0 406.3l15.4 13.8c52.5 46.8 120.4 72.5 190.7 72.2 51.4 0 94.4-10.5 133.6-44.1 57.1-51.4 54.2-149.2 20.3-189.6z"],
+ "searchengin": [460, 512, [], "f3eb", "M220.6 130.3l-67.2 28.2V43.2L98.7 233.5l54.7-24.2v130.3l67.2-209.3zm-83.2-96.7l-1.3 4.7-15.2 52.9C80.6 106.7 52 145.8 52 191.5c0 52.3 34.3 95.9 83.4 105.5v53.6C57.5 340.1 0 272.4 0 191.6c0-80.5 59.8-147.2 137.4-158zm311.4 447.2c-11.2 11.2-23.1 12.3-28.6 10.5-5.4-1.8-27.1-19.9-60.4-44.4-33.3-24.6-33.6-35.7-43-56.7-9.4-20.9-30.4-42.6-57.5-52.4l-9.7-14.7c-24.7 16.9-53 26.9-81.3 28.7l2.1-6.6 15.9-49.5c46.5-11.9 80.9-54 80.9-104.2 0-54.5-38.4-102.1-96-107.1V32.3C254.4 37.4 320 106.8 320 191.6c0 33.6-11.2 64.7-29 90.4l14.6 9.6c9.8 27.1 31.5 48 52.4 57.4s32.2 9.7 56.8 43c24.6 33.2 42.7 54.9 44.5 60.3s.7 17.3-10.5 28.5zm-9.9-17.9c0-4.4-3.6-8-8-8s-8 3.6-8 8 3.6 8 8 8 8-3.6 8-8z"],
+ "sellcast": [448, 512, [], "f2da", "M353.4 32H94.7C42.6 32 0 74.6 0 126.6v258.7C0 437.4 42.6 480 94.7 480h258.7c52.1 0 94.7-42.6 94.7-94.6V126.6c0-52-42.6-94.6-94.7-94.6zm-50 316.4c-27.9 48.2-89.9 64.9-138.2 37.2-22.9 39.8-54.9 8.6-42.3-13.2l15.7-27.2c5.9-10.3 19.2-13.9 29.5-7.9 18.6 10.8-.1-.1 18.5 10.7 27.6 15.9 63.4 6.3 79.4-21.3 15.9-27.6 6.3-63.4-21.3-79.4-17.8-10.2-.6-.4-18.6-10.6-24.6-14.2-3.4-51.9 21.6-37.5 18.6 10.8-.1-.1 18.5 10.7 48.4 28 65.1 90.3 37.2 138.5zm21.8-208.8c-17 29.5-16.3 28.8-19 31.5-6.5 6.5-16.3 8.7-26.5 3.6-18.6-10.8.1.1-18.5-10.7-27.6-15.9-63.4-6.3-79.4 21.3s-6.3 63.4 21.3 79.4c0 0 18.5 10.6 18.6 10.6 24.6 14.2 3.4 51.9-21.6 37.5-18.6-10.8.1.1-18.5-10.7-48.2-27.8-64.9-90.1-37.1-138.4 27.9-48.2 89.9-64.9 138.2-37.2l4.8-8.4c14.3-24.9 52-3.3 37.7 21.5z"],
+ "sellsy": [640, 512, [], "f213", "M539.71 237.308c3.064-12.257 4.29-24.821 4.29-37.384C544 107.382 468.618 32 376.076 32c-77.22 0-144.634 53.012-163.02 127.781-15.322-13.176-34.934-20.53-55.157-20.53-46.271 0-83.962 37.69-83.962 83.961 0 7.354.92 15.015 3.065 22.369-42.9 20.225-70.785 63.738-70.785 111.234C6.216 424.843 61.68 480 129.401 480h381.198c67.72 0 123.184-55.157 123.184-123.184.001-56.384-38.916-106.025-94.073-119.508zM199.88 401.554c0 8.274-7.048 15.321-15.321 15.321H153.61c-8.274 0-15.321-7.048-15.321-15.321V290.626c0-8.273 7.048-15.321 15.321-15.321h30.949c8.274 0 15.321 7.048 15.321 15.321v110.928zm89.477 0c0 8.274-7.048 15.321-15.322 15.321h-30.949c-8.274 0-15.321-7.048-15.321-15.321V270.096c0-8.274 7.048-15.321 15.321-15.321h30.949c8.274 0 15.322 7.048 15.322 15.321v131.458zm89.477 0c0 8.274-7.047 15.321-15.321 15.321h-30.949c-8.274 0-15.322-7.048-15.322-15.321V238.84c0-8.274 7.048-15.321 15.322-15.321h30.949c8.274 0 15.321 7.048 15.321 15.321v162.714zm87.027 0c0 8.274-7.048 15.321-15.322 15.321h-28.497c-8.274 0-15.321-7.048-15.321-15.321V176.941c0-8.579 7.047-15.628 15.321-15.628h28.497c8.274 0 15.322 7.048 15.322 15.628v224.613z"],
+ "servicestack": [496, 512, [], "f3ec", "M88 216c81.7 10.2 273.7 102.3 304 232H0c99.5-8.1 184.5-137 88-232zm32-152c32.3 35.6 47.7 83.9 46.4 133.6C249.3 231.3 373.7 321.3 400 448h96C455.3 231.9 222.8 79.5 120 64z"],
+ "shirtsinbulk": [448, 512, [], "f214", "M100 410.3l30.6 13.4 4.4-9.9-30.6-13.4zm39.4 17.5l30.6 13.4 4.4-9.9-30.6-13.4zm172.1-14l4.4 9.9 30.6-13.4-4.4-9.9zM179.1 445l30.3 13.7 4.4-9.9-30.3-13.4zM60.4 392.8L91 406.2l4.4-9.6-30.6-13.7zm211.4 38.5l4.4 9.9 30.6-13.4-4.4-9.9zm-39.3 17.5l4.4 9.9 30.6-13.7-4.4-9.6zm118.4-52.2l4.4 9.6 30.6-13.4-4.4-9.9zM170 46.6h-33.5v10.5H170zm-47.2 0H89.2v10.5h33.5zm-47.3 0H42.3v10.5h33.3zm141.5 0h-33.2v10.5H217zm94.5 0H278v10.5h33.5zm47.3 0h-33.5v10.5h33.5zm-94.6 0H231v10.5h33.2zm141.5 0h-33.3v10.5h33.3zM52.8 351.1H42v33.5h10.8zm70-215.9H89.2v10.5h33.5zm-70 10.6h22.8v-10.5H42v33.5h10.8zm168.9 228.6c50.5 0 91.3-40.8 91.3-91.3 0-50.2-40.8-91.3-91.3-91.3-50.2 0-91.3 41.1-91.3 91.3 0 50.5 41.1 91.3 91.3 91.3zm-48.2-111.1c0-25.4 29.5-31.8 49.6-31.8 16.9 0 29.2 5.8 44.3 12l-8.8 16.9h-.9c-6.4-9.9-24.8-13.1-35.6-13.1-9 0-29.8 1.8-29.8 14.9 0 21.6 78.5-10.2 78.5 37.9 0 25.4-31.5 31.2-51 31.2-18.1 0-32.4-2.9-47.2-12.2l9-18.4h.9c6.1 12.2 23.6 14.9 35.9 14.9 8.7 0 32.7-1.2 32.7-14.3 0-26.1-77.6 6.3-77.6-38zM52.8 178.4H42V212h10.8zm342.4 206.2H406v-33.5h-10.8zM52.8 307.9H42v33.5h10.8zM0 3.7v406l221.7 98.6L448 409.7V3.7zm418.8 387.1L222 476.5 29.2 390.8V120.7h389.7v270.1zm0-299.3H29.2V32.9h389.7v58.6zm-366 130.1H42v33.5h10.8zm0 43.2H42v33.5h10.8zM170 135.2h-33.5v10.5H170zm225.2 163.1H406v-33.5h-10.8zm0-43.2H406v-33.5h-10.8zM217 135.2h-33.2v10.5H217zM395.2 212H406v-33.5h-10.8zm0 129.5H406V308h-10.8zm-131-206.3H231v10.5h33.2zm47.3 0H278v10.5h33.5zm83.7 33.6H406v-33.5h-33.5v10.5h22.8zm-36.4-33.6h-33.5v10.5h33.5z"],
+ "shopify": [448, 512, [], "e057", "M388.32,104.1a4.66,4.66,0,0,0-4.4-4c-2,0-37.23-.8-37.23-.8s-21.61-20.82-29.62-28.83V503.2L442.76,472S388.72,106.5,388.32,104.1ZM288.65,70.47a116.67,116.67,0,0,0-7.21-17.61C271,32.85,255.42,22,237,22a15,15,0,0,0-4,.4c-.4-.8-1.2-1.2-1.6-2C223.4,11.63,213,7.63,200.58,8c-24,.8-48,18-67.25,48.83-13.61,21.62-24,48.84-26.82,70.06-27.62,8.4-46.83,14.41-47.23,14.81-14,4.4-14.41,4.8-16,18-1.2,10-38,291.82-38,291.82L307.86,504V65.67a41.66,41.66,0,0,0-4.4.4S297.86,67.67,288.65,70.47ZM233.41,87.69c-16,4.8-33.63,10.4-50.84,15.61,4.8-18.82,14.41-37.63,25.62-50,4.4-4.4,10.41-9.61,17.21-12.81C232.21,54.86,233.81,74.48,233.41,87.69ZM200.58,24.44A27.49,27.49,0,0,1,215,28c-6.4,3.2-12.81,8.41-18.81,14.41-15.21,16.42-26.82,42-31.62,66.45-14.42,4.41-28.83,8.81-42,12.81C131.33,83.28,163.75,25.24,200.58,24.44ZM154.15,244.61c1.6,25.61,69.25,31.22,73.25,91.66,2.8,47.64-25.22,80.06-65.65,82.47-48.83,3.2-75.65-25.62-75.65-25.62l10.4-44s26.82,20.42,48.44,18.82c14-.8,19.22-12.41,18.81-20.42-2-33.62-57.24-31.62-60.84-86.86-3.2-46.44,27.22-93.27,94.47-97.68,26-1.6,39.23,4.81,39.23,4.81L221.4,225.39s-17.21-8-37.63-6.4C154.15,221,153.75,239.8,154.15,244.61ZM249.42,82.88c0-12-1.6-29.22-7.21-43.63,18.42,3.6,27.22,24,31.23,36.43Q262.63,78.68,249.42,82.88Z"],
+ "shopware": [512, 512, [], "f5b5", "M403.5 455.41A246.17 246.17 0 0 1 256 504C118.81 504 8 393 8 256 8 118.81 119 8 256 8a247.39 247.39 0 0 1 165.7 63.5 3.57 3.57 0 0 1-2.86 6.18A418.62 418.62 0 0 0 362.13 74c-129.36 0-222.4 53.47-222.4 155.35 0 109 92.13 145.88 176.83 178.73 33.64 13 65.4 25.36 87 41.59a3.58 3.58 0 0 1 0 5.72zM503 233.09a3.64 3.64 0 0 0-1.27-2.44c-51.76-43-93.62-60.48-144.48-60.48-84.13 0-80.25 52.17-80.25 53.63 0 42.6 52.06 62 112.34 84.49 31.07 11.59 63.19 23.57 92.68 39.93a3.57 3.57 0 0 0 5-1.82A249 249 0 0 0 503 233.09z"],
+ "simplybuilt": [512, 512, [], "f215", "M481.2 64h-106c-14.5 0-26.6 11.8-26.6 26.3v39.6H163.3V90.3c0-14.5-12-26.3-26.6-26.3h-106C16.1 64 4.3 75.8 4.3 90.3v331.4c0 14.5 11.8 26.3 26.6 26.3h450.4c14.8 0 26.6-11.8 26.6-26.3V90.3c-.2-14.5-12-26.3-26.7-26.3zM149.8 355.8c-36.6 0-66.4-29.7-66.4-66.4 0-36.9 29.7-66.6 66.4-66.6 36.9 0 66.6 29.7 66.6 66.6 0 36.7-29.7 66.4-66.6 66.4zm212.4 0c-36.9 0-66.6-29.7-66.6-66.6 0-36.6 29.7-66.4 66.6-66.4 36.6 0 66.4 29.7 66.4 66.4 0 36.9-29.8 66.6-66.4 66.6z"],
+ "sistrix": [448, 512, [], "f3ee", "M448 449L301.2 300.2c20-27.9 31.9-62.2 31.9-99.2 0-93.1-74.7-168.9-166.5-168.9C74.7 32 0 107.8 0 200.9s74.7 168.9 166.5 168.9c39.8 0 76.3-14.2 105-37.9l146 148.1 30.5-31zM166.5 330.8c-70.6 0-128.1-58.3-128.1-129.9S95.9 71 166.5 71s128.1 58.3 128.1 129.9-57.4 129.9-128.1 129.9z"],
+ "sith": [448, 512, [], "f512", "M0 32l69.71 118.75-58.86-11.52 69.84 91.03a146.741 146.741 0 0 0 0 51.45l-69.84 91.03 58.86-11.52L0 480l118.75-69.71-11.52 58.86 91.03-69.84c17.02 3.04 34.47 3.04 51.48 0l91.03 69.84-11.52-58.86L448 480l-69.71-118.78 58.86 11.52-69.84-91.03c3.03-17.01 3.04-34.44 0-51.45l69.84-91.03-58.86 11.52L448 32l-118.75 69.71 11.52-58.9-91.06 69.87c-8.5-1.52-17.1-2.29-25.71-2.29s-17.21.78-25.71 2.29l-91.06-69.87 11.52 58.9L0 32zm224 99.78c31.8 0 63.6 12.12 87.85 36.37 48.5 48.5 48.49 127.21 0 175.7s-127.2 48.46-175.7-.03c-48.5-48.5-48.49-127.21 0-175.7 24.24-24.25 56.05-36.34 87.85-36.34zm0 36.66c-22.42 0-44.83 8.52-61.92 25.61-34.18 34.18-34.19 89.68 0 123.87s89.65 34.18 123.84 0c34.18-34.18 34.19-89.68 0-123.87-17.09-17.09-39.5-25.61-61.92-25.61z"],
+ "sketch": [512, 512, [], "f7c6", "M27.5 162.2L9 187.1h90.5l6.9-130.7-78.9 105.8zM396.3 45.7L267.7 32l135.7 147.2-7.1-133.5zM112.2 218.3l-11.2-22H9.9L234.8 458zm2-31.2h284l-81.5-88.5L256.3 33zm297.3 9.1L277.6 458l224.8-261.7h-90.9zM415.4 69L406 56.4l.9 17.3 6.1 113.4h90.3zM113.5 93.5l-4.6 85.6L244.7 32 116.1 45.7zm287.7 102.7h-290l42.4 82.9L256.3 480l144.9-283.8z"],
+ "skyatlas": [640, 512, [], "f216", "M640 329.3c0 65.9-52.5 114.4-117.5 114.4-165.9 0-196.6-249.7-359.7-249.7-146.9 0-147.1 212.2 5.6 212.2 42.5 0 90.9-17.8 125.3-42.5 5.6-4.1 16.9-16.3 22.8-16.3s10.9 5 10.9 10.9c0 7.8-13.1 19.1-18.7 24.1-40.9 35.6-100.3 61.2-154.7 61.2-83.4.1-154-59-154-144.9s67.5-149.1 152.8-149.1c185.3 0 222.5 245.9 361.9 245.9 99.9 0 94.8-139.7 3.4-139.7-17.5 0-35 11.6-46.9 11.6-8.4 0-15.9-7.2-15.9-15.6 0-11.6 5.3-23.7 5.3-36.3 0-66.6-50.9-114.7-116.9-114.7-53.1 0-80 36.9-88.8 36.9-6.2 0-11.2-5-11.2-11.2 0-5.6 4.1-10.3 7.8-14.4 25.3-28.8 64.7-43.7 102.8-43.7 79.4 0 139.1 58.4 139.1 137.8 0 6.9-.3 13.7-1.2 20.6 11.9-3.1 24.1-4.7 35.9-4.7 60.7 0 111.9 45.3 111.9 107.2z"],
+ "skype": [448, 512, [], "f17e", "M424.7 299.8c2.9-14 4.7-28.9 4.7-43.8 0-113.5-91.9-205.3-205.3-205.3-14.9 0-29.7 1.7-43.8 4.7C161.3 40.7 137.7 32 112 32 50.2 32 0 82.2 0 144c0 25.7 8.7 49.3 23.3 68.2-2.9 14-4.7 28.9-4.7 43.8 0 113.5 91.9 205.3 205.3 205.3 14.9 0 29.7-1.7 43.8-4.7 19 14.6 42.6 23.3 68.2 23.3 61.8 0 112-50.2 112-112 .1-25.6-8.6-49.2-23.2-68.1zm-194.6 91.5c-65.6 0-120.5-29.2-120.5-65 0-16 9-30.6 29.5-30.6 31.2 0 34.1 44.9 88.1 44.9 25.7 0 42.3-11.4 42.3-26.3 0-18.7-16-21.6-42-28-62.5-15.4-117.8-22-117.8-87.2 0-59.2 58.6-81.1 109.1-81.1 55.1 0 110.8 21.9 110.8 55.4 0 16.9-11.4 31.8-30.3 31.8-28.3 0-29.2-33.5-75-33.5-25.7 0-42 7-42 22.5 0 19.8 20.8 21.8 69.1 33 41.4 9.3 90.7 26.8 90.7 77.6 0 59.1-57.1 86.5-112 86.5z"],
+ "slack": [448, 512, [], "f198", "M94.12 315.1c0 25.9-21.16 47.06-47.06 47.06S0 341 0 315.1c0-25.9 21.16-47.06 47.06-47.06h47.06v47.06zm23.72 0c0-25.9 21.16-47.06 47.06-47.06s47.06 21.16 47.06 47.06v117.84c0 25.9-21.16 47.06-47.06 47.06s-47.06-21.16-47.06-47.06V315.1zm47.06-188.98c-25.9 0-47.06-21.16-47.06-47.06S139 32 164.9 32s47.06 21.16 47.06 47.06v47.06H164.9zm0 23.72c25.9 0 47.06 21.16 47.06 47.06s-21.16 47.06-47.06 47.06H47.06C21.16 243.96 0 222.8 0 196.9s21.16-47.06 47.06-47.06H164.9zm188.98 47.06c0-25.9 21.16-47.06 47.06-47.06 25.9 0 47.06 21.16 47.06 47.06s-21.16 47.06-47.06 47.06h-47.06V196.9zm-23.72 0c0 25.9-21.16 47.06-47.06 47.06-25.9 0-47.06-21.16-47.06-47.06V79.06c0-25.9 21.16-47.06 47.06-47.06 25.9 0 47.06 21.16 47.06 47.06V196.9zM283.1 385.88c25.9 0 47.06 21.16 47.06 47.06 0 25.9-21.16 47.06-47.06 47.06-25.9 0-47.06-21.16-47.06-47.06v-47.06h47.06zm0-23.72c-25.9 0-47.06-21.16-47.06-47.06 0-25.9 21.16-47.06 47.06-47.06h117.84c25.9 0 47.06 21.16 47.06 47.06 0 25.9-21.16 47.06-47.06 47.06H283.1z"],
+ "slack-hash": [448, 512, [], "f3ef", "M446.2 270.4c-6.2-19-26.9-29.1-46-22.9l-45.4 15.1-30.3-90 45.4-15.1c19.1-6.2 29.1-26.8 23-45.9-6.2-19-26.9-29.1-46-22.9l-45.4 15.1-15.7-47c-6.2-19-26.9-29.1-46-22.9-19.1 6.2-29.1 26.8-23 45.9l15.7 47-93.4 31.2-15.7-47c-6.2-19-26.9-29.1-46-22.9-19.1 6.2-29.1 26.8-23 45.9l15.7 47-45.3 15c-19.1 6.2-29.1 26.8-23 45.9 5 14.5 19.1 24 33.6 24.6 6.8 1 12-1.6 57.7-16.8l30.3 90L78 354.8c-19 6.2-29.1 26.9-23 45.9 5 14.5 19.1 24 33.6 24.6 6.8 1 12-1.6 57.7-16.8l15.7 47c5.9 16.9 24.7 29 46 22.9 19.1-6.2 29.1-26.8 23-45.9l-15.7-47 93.6-31.3 15.7 47c5.9 16.9 24.7 29 46 22.9 19.1-6.2 29.1-26.8 23-45.9l-15.7-47 45.4-15.1c19-6 29.1-26.7 22.9-45.7zm-254.1 47.2l-30.3-90.2 93.5-31.3 30.3 90.2-93.5 31.3z"],
+ "slideshare": [512, 512, [], "f1e7", "M187.7 153.7c-34 0-61.7 25.7-61.7 57.7 0 31.7 27.7 57.7 61.7 57.7s61.7-26 61.7-57.7c0-32-27.7-57.7-61.7-57.7zm143.4 0c-34 0-61.7 25.7-61.7 57.7 0 31.7 27.7 57.7 61.7 57.7 34.3 0 61.7-26 61.7-57.7.1-32-27.4-57.7-61.7-57.7zm156.6 90l-6 4.3V49.7c0-27.4-20.6-49.7-46-49.7H76.6c-25.4 0-46 22.3-46 49.7V248c-2-1.4-4.3-2.9-6.3-4.3-15.1-10.6-25.1 4-16 17.7 18.3 22.6 53.1 50.3 106.3 72C58.3 525.1 252 555.7 248.9 457.5c0-.7.3-56.6.3-96.6 5.1 1.1 9.4 2.3 13.7 3.1 0 39.7.3 92.8.3 93.5-3.1 98.3 190.6 67.7 134.3-124 53.1-21.7 88-49.4 106.3-72 9.1-13.8-.9-28.3-16.1-17.8zm-30.5 19.2c-68.9 37.4-128.3 31.1-160.6 29.7-23.7-.9-32.6 9.1-33.7 24.9-10.3-7.7-18.6-15.5-20.3-17.1-5.1-5.4-13.7-8-27.1-7.7-31.7 1.1-89.7 7.4-157.4-28V72.3c0-34.9 8.9-45.7 40.6-45.7h317.7c30.3 0 40.9 12.9 40.9 45.7v190.6z"],
+ "snapchat": [496, 512, [], "f2ab", "M248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm169.5 338.9c-3.5 8.1-18.1 14-44.8 18.2-1.4 1.9-2.5 9.8-4.3 15.9-1.1 3.7-3.7 5.9-8.1 5.9h-.2c-6.2 0-12.8-2.9-25.8-2.9-17.6 0-23.7 4-37.4 13.7-14.5 10.3-28.4 19.1-49.2 18.2-21 1.6-38.6-11.2-48.5-18.2-13.8-9.7-19.8-13.7-37.4-13.7-12.5 0-20.4 3.1-25.8 3.1-5.4 0-7.5-3.3-8.3-6-1.8-6.1-2.9-14.1-4.3-16-13.8-2.1-44.8-7.5-45.5-21.4-.2-3.6 2.3-6.8 5.9-7.4 46.3-7.6 67.1-55.1 68-57.1 0-.1.1-.2.2-.3 2.5-5 3-9.2 1.6-12.5-3.4-7.9-17.9-10.7-24-13.2-15.8-6.2-18-13.4-17-18.3 1.6-8.5 14.4-13.8 21.9-10.3 5.9 2.8 11.2 4.2 15.7 4.2 3.3 0 5.5-.8 6.6-1.4-1.4-23.9-4.7-58 3.8-77.1C183.1 100 230.7 96 244.7 96c.6 0 6.1-.1 6.7-.1 34.7 0 68 17.8 84.3 54.3 8.5 19.1 5.2 53.1 3.8 77.1 1.1.6 2.9 1.3 5.7 1.4 4.3-.2 9.2-1.6 14.7-4.2 4-1.9 9.6-1.6 13.6 0 6.3 2.3 10.3 6.8 10.4 11.9.1 6.5-5.7 12.1-17.2 16.6-1.4.6-3.1 1.1-4.9 1.7-6.5 2.1-16.4 5.2-19 11.5-1.4 3.3-.8 7.5 1.6 12.5.1.1.1.2.2.3.9 2 21.7 49.5 68 57.1 4 1 7.1 5.5 4.9 10.8z"],
+ "snapchat-ghost": [512, 512, [], "f2ac", "M510.846 392.673c-5.211 12.157-27.239 21.089-67.36 27.318-2.064 2.786-3.775 14.686-6.507 23.956-1.625 5.566-5.623 8.869-12.128 8.869l-.297-.005c-9.395 0-19.203-4.323-38.852-4.323-26.521 0-35.662 6.043-56.254 20.588-21.832 15.438-42.771 28.764-74.027 27.399-31.646 2.334-58.025-16.908-72.871-27.404-20.714-14.643-29.828-20.582-56.241-20.582-18.864 0-30.736 4.72-38.852 4.72-8.073 0-11.213-4.922-12.422-9.04-2.703-9.189-4.404-21.263-6.523-24.13-20.679-3.209-67.31-11.344-68.498-32.15a10.627 10.627 0 0 1 8.877-11.069c69.583-11.455 100.924-82.901 102.227-85.934.074-.176.155-.344.237-.515 3.713-7.537 4.544-13.849 2.463-18.753-5.05-11.896-26.872-16.164-36.053-19.796-23.715-9.366-27.015-20.128-25.612-27.504 2.437-12.836 21.725-20.735 33.002-15.453 8.919 4.181 16.843 6.297 23.547 6.297 5.022 0 8.212-1.204 9.96-2.171-2.043-35.936-7.101-87.29 5.687-115.969C158.122 21.304 229.705 15.42 250.826 15.42c.944 0 9.141-.089 10.11-.089 52.148 0 102.254 26.78 126.723 81.643 12.777 28.65 7.749 79.792 5.695 116.009 1.582.872 4.357 1.942 8.599 2.139 6.397-.286 13.815-2.389 22.069-6.257 6.085-2.846 14.406-2.461 20.48.058l.029.01c9.476 3.385 15.439 10.215 15.589 17.87.184 9.747-8.522 18.165-25.878 25.018-2.118.835-4.694 1.655-7.434 2.525-9.797 3.106-24.6 7.805-28.616 17.271-2.079 4.904-1.256 11.211 2.46 18.748.087.168.166.342.239.515 1.301 3.03 32.615 74.46 102.23 85.934 6.427 1.058 11.163 7.877 7.725 15.859z"],
+ "snapchat-square": [448, 512, [], "f2ad", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-6.5 314.9c-3.5 8.1-18.1 14-44.8 18.2-1.4 1.9-2.5 9.8-4.3 15.9-1.1 3.7-3.7 5.9-8.1 5.9h-.2c-6.2 0-12.8-2.9-25.8-2.9-17.6 0-23.7 4-37.4 13.7-14.5 10.3-28.4 19.1-49.2 18.2-21 1.6-38.6-11.2-48.5-18.2-13.8-9.7-19.8-13.7-37.4-13.7-12.5 0-20.4 3.1-25.8 3.1-5.4 0-7.5-3.3-8.3-6-1.8-6.1-2.9-14.1-4.3-16-13.8-2.1-44.8-7.5-45.5-21.4-.2-3.6 2.3-6.8 5.9-7.4 46.3-7.6 67.1-55.1 68-57.1 0-.1.1-.2.2-.3 2.5-5 3-9.2 1.6-12.5-3.4-7.9-17.9-10.7-24-13.2-15.8-6.2-18-13.4-17-18.3 1.6-8.5 14.4-13.8 21.9-10.3 5.9 2.8 11.2 4.2 15.7 4.2 3.3 0 5.5-.8 6.6-1.4-1.4-23.9-4.7-58 3.8-77.1C159.1 100 206.7 96 220.7 96c.6 0 6.1-.1 6.7-.1 34.7 0 68 17.8 84.3 54.3 8.5 19.1 5.2 53.1 3.8 77.1 1.1.6 2.9 1.3 5.7 1.4 4.3-.2 9.2-1.6 14.7-4.2 4-1.9 9.6-1.6 13.6 0 6.3 2.3 10.3 6.8 10.4 11.9.1 6.5-5.7 12.1-17.2 16.6-1.4.6-3.1 1.1-4.9 1.7-6.5 2.1-16.4 5.2-19 11.5-1.4 3.3-.8 7.5 1.6 12.5.1.1.1.2.2.3.9 2 21.7 49.5 68 57.1 4 1 7.1 5.5 4.9 10.8z"],
+ "soundcloud": [640, 512, [], "f1be", "M111.4 256.3l5.8 65-5.8 68.3c-.3 2.5-2.2 4.4-4.4 4.4s-4.2-1.9-4.2-4.4l-5.6-68.3 5.6-65c0-2.2 1.9-4.2 4.2-4.2 2.2 0 4.1 2 4.4 4.2zm21.4-45.6c-2.8 0-4.7 2.2-5 5l-5 105.6 5 68.3c.3 2.8 2.2 5 5 5 2.5 0 4.7-2.2 4.7-5l5.8-68.3-5.8-105.6c0-2.8-2.2-5-4.7-5zm25.5-24.1c-3.1 0-5.3 2.2-5.6 5.3l-4.4 130 4.4 67.8c.3 3.1 2.5 5.3 5.6 5.3 2.8 0 5.3-2.2 5.3-5.3l5.3-67.8-5.3-130c0-3.1-2.5-5.3-5.3-5.3zM7.2 283.2c-1.4 0-2.2 1.1-2.5 2.5L0 321.3l4.7 35c.3 1.4 1.1 2.5 2.5 2.5s2.2-1.1 2.5-2.5l5.6-35-5.6-35.6c-.3-1.4-1.1-2.5-2.5-2.5zm23.6-21.9c-1.4 0-2.5 1.1-2.5 2.5l-6.4 57.5 6.4 56.1c0 1.7 1.1 2.8 2.5 2.8s2.5-1.1 2.8-2.5l7.2-56.4-7.2-57.5c-.3-1.4-1.4-2.5-2.8-2.5zm25.3-11.4c-1.7 0-3.1 1.4-3.3 3.3L47 321.3l5.8 65.8c.3 1.7 1.7 3.1 3.3 3.1 1.7 0 3.1-1.4 3.1-3.1l6.9-65.8-6.9-68.1c0-1.9-1.4-3.3-3.1-3.3zm25.3-2.2c-1.9 0-3.6 1.4-3.6 3.6l-5.8 70 5.8 67.8c0 2.2 1.7 3.6 3.6 3.6s3.6-1.4 3.9-3.6l6.4-67.8-6.4-70c-.3-2.2-2-3.6-3.9-3.6zm241.4-110.9c-1.1-.8-2.8-1.4-4.2-1.4-2.2 0-4.2.8-5.6 1.9-1.9 1.7-3.1 4.2-3.3 6.7v.8l-3.3 176.7 1.7 32.5 1.7 31.7c.3 4.7 4.2 8.6 8.9 8.6s8.6-3.9 8.6-8.6l3.9-64.2-3.9-177.5c-.4-3-2-5.8-4.5-7.2zm-26.7 15.3c-1.4-.8-2.8-1.4-4.4-1.4s-3.1.6-4.4 1.4c-2.2 1.4-3.6 3.9-3.6 6.7l-.3 1.7-2.8 160.8s0 .3 3.1 65.6v.3c0 1.7.6 3.3 1.7 4.7 1.7 1.9 3.9 3.1 6.4 3.1 2.2 0 4.2-1.1 5.6-2.5 1.7-1.4 2.5-3.3 2.5-5.6l.3-6.7 3.1-58.6-3.3-162.8c-.3-2.8-1.7-5.3-3.9-6.7zm-111.4 22.5c-3.1 0-5.8 2.8-5.8 6.1l-4.4 140.6 4.4 67.2c.3 3.3 2.8 5.8 5.8 5.8 3.3 0 5.8-2.5 6.1-5.8l5-67.2-5-140.6c-.2-3.3-2.7-6.1-6.1-6.1zm376.7 62.8c-10.8 0-21.1 2.2-30.6 6.1-6.4-70.8-65.8-126.4-138.3-126.4-17.8 0-35 3.3-50.3 9.4-6.1 2.2-7.8 4.4-7.8 9.2v249.7c0 5 3.9 8.6 8.6 9.2h218.3c43.3 0 78.6-35 78.6-78.3.1-43.6-35.2-78.9-78.5-78.9zm-296.7-60.3c-4.2 0-7.5 3.3-7.8 7.8l-3.3 136.7 3.3 65.6c.3 4.2 3.6 7.5 7.8 7.5 4.2 0 7.5-3.3 7.5-7.5l3.9-65.6-3.9-136.7c-.3-4.5-3.3-7.8-7.5-7.8zm-53.6-7.8c-3.3 0-6.4 3.1-6.4 6.7l-3.9 145.3 3.9 66.9c.3 3.6 3.1 6.4 6.4 6.4 3.6 0 6.4-2.8 6.7-6.4l4.4-66.9-4.4-145.3c-.3-3.6-3.1-6.7-6.7-6.7zm26.7 3.4c-3.9 0-6.9 3.1-6.9 6.9L227 321.3l3.9 66.4c.3 3.9 3.1 6.9 6.9 6.9s6.9-3.1 6.9-6.9l4.2-66.4-4.2-141.7c0-3.9-3-6.9-6.9-6.9z"],
+ "sourcetree": [448, 512, [], "f7d3", "M427.2 203c0-112.1-90.9-203-203-203C112.1-.2 21.2 90.6 21 202.6A202.86 202.86 0 0 0 161.5 396v101.7a14.3 14.3 0 0 0 14.3 14.3h96.4a14.3 14.3 0 0 0 14.3-14.3V396.1A203.18 203.18 0 0 0 427.2 203zm-271.6 0c0-90.8 137.3-90.8 137.3 0-.1 89.9-137.3 91-137.3 0z"],
+ "speakap": [448, 512, [], "f3f3", "M64 391.78C-15.41 303.59-8 167.42 80.64 87.64s224.8-73 304.21 15.24 72 224.36-16.64 304.14c-18.74 16.87 64 43.09 42 52.26-82.06 34.21-253.91 35-346.23-67.5zm213.31-211.6l38.5-40.86c-9.61-8.89-32-26.83-76.17-27.6-52.33-.91-95.86 28.3-96.77 80-.2 11.33.29 36.72 29.42 54.83 34.46 21.42 86.52 21.51 86 52.26-.37 21.28-26.42 25.81-38.59 25.6-3-.05-30.23-.46-47.61-24.62l-40 42.61c28.16 27 59 32.62 83.49 33.05 10.23.18 96.42.33 97.84-81 .28-15.81-2.07-39.72-28.86-56.59-34.36-21.64-85-19.45-84.43-49.75.41-23.25 31-25.37 37.53-25.26.43 0 26.62.26 39.62 17.37z"],
+ "speaker-deck": [512, 512, [], "f83c", "M213.86 296H100a100 100 0 0 1 0-200h132.84a40 40 0 0 1 0 80H98c-26.47 0-26.45 40 0 40h113.82a100 100 0 0 1 0 200H40a40 40 0 0 1 0-80h173.86c26.48 0 26.46-40 0-40zM298 416a120.21 120.21 0 0 0 51.11-80h64.55a19.83 19.83 0 0 0 19.66-20V196a19.83 19.83 0 0 0-19.66-20H296.42a60.77 60.77 0 0 0 0-80h136.93c43.44 0 78.65 35.82 78.65 80v160c0 44.18-35.21 80-78.65 80z"],
+ "spotify": [496, 512, [], "f1bc", "M248 8C111.1 8 0 119.1 0 256s111.1 248 248 248 248-111.1 248-248S384.9 8 248 8zm100.7 364.9c-4.2 0-6.8-1.3-10.7-3.6-62.4-37.6-135-39.2-206.7-24.5-3.9 1-9 2.6-11.9 2.6-9.7 0-15.8-7.7-15.8-15.8 0-10.3 6.1-15.2 13.6-16.8 81.9-18.1 165.6-16.5 237 26.2 6.1 3.9 9.7 7.4 9.7 16.5s-7.1 15.4-15.2 15.4zm26.9-65.6c-5.2 0-8.7-2.3-12.3-4.2-62.5-37-155.7-51.9-238.6-29.4-4.8 1.3-7.4 2.6-11.9 2.6-10.7 0-19.4-8.7-19.4-19.4s5.2-17.8 15.5-20.7c27.8-7.8 56.2-13.6 97.8-13.6 64.9 0 127.6 16.1 177 45.5 8.1 4.8 11.3 11 11.3 19.7-.1 10.8-8.5 19.5-19.4 19.5zm31-76.2c-5.2 0-8.4-1.3-12.9-3.9-71.2-42.5-198.5-52.7-280.9-29.7-3.6 1-8.1 2.6-12.9 2.6-13.2 0-23.3-10.3-23.3-23.6 0-13.6 8.4-21.3 17.4-23.9 35.2-10.3 74.6-15.2 117.5-15.2 73 0 149.5 15.2 205.4 47.8 7.8 4.5 12.9 10.7 12.9 22.6 0 13.6-11 23.3-23.2 23.3z"],
+ "squarespace": [512, 512, [], "f5be", "M186.12 343.34c-9.65 9.65-9.65 25.29 0 34.94 9.65 9.65 25.29 9.65 34.94 0L378.24 221.1c19.29-19.29 50.57-19.29 69.86 0s19.29 50.57 0 69.86L293.95 445.1c19.27 19.29 50.53 19.31 69.82.04l.04-.04 119.25-119.24c38.59-38.59 38.59-101.14 0-139.72-38.59-38.59-101.15-38.59-139.72 0l-157.22 157.2zm244.53-104.8c-9.65-9.65-25.29-9.65-34.93 0l-157.2 157.18c-19.27 19.29-50.53 19.31-69.82.05l-.05-.05c-9.64-9.64-25.27-9.65-34.92-.01l-.01.01c-9.65 9.64-9.66 25.28-.02 34.93l.02.02c38.58 38.57 101.14 38.57 139.72 0l157.2-157.2c9.65-9.65 9.65-25.29.01-34.93zm-261.99 87.33l157.18-157.18c9.64-9.65 9.64-25.29 0-34.94-9.64-9.64-25.27-9.64-34.91 0L133.72 290.93c-19.28 19.29-50.56 19.3-69.85.01l-.01-.01c-19.29-19.28-19.31-50.54-.03-69.84l.03-.03L218.03 66.89c-19.28-19.29-50.55-19.3-69.85-.02l-.02.02L28.93 186.14c-38.58 38.59-38.58 101.14 0 139.72 38.6 38.59 101.13 38.59 139.73.01zm-87.33-52.4c9.64 9.64 25.27 9.64 34.91 0l157.21-157.19c19.28-19.29 50.55-19.3 69.84-.02l.02.02c9.65 9.65 25.29 9.65 34.93 0 9.65-9.65 9.65-25.29 0-34.93-38.59-38.59-101.13-38.59-139.72 0L81.33 238.54c-9.65 9.64-9.65 25.28-.01 34.93h.01z"],
+ "stack-exchange": [448, 512, [], "f18d", "M17.7 332.3h412.7v22c0 37.7-29.3 68-65.3 68h-19L259.3 512v-89.7H83c-36 0-65.3-30.3-65.3-68v-22zm0-23.6h412.7v-85H17.7v85zm0-109.4h412.7v-85H17.7v85zM365 0H83C47 0 17.7 30.3 17.7 67.7V90h412.7V67.7C430.3 30.3 401 0 365 0z"],
+ "stack-overflow": [384, 512, [], "f16c", "M290.7 311L95 269.7 86.8 309l195.7 41zm51-87L188.2 95.7l-25.5 30.8 153.5 128.3zm-31.2 39.7L129.2 179l-16.7 36.5L293.7 300zM262 32l-32 24 119.3 160.3 32-24zm20.5 328h-200v39.7h200zm39.7 80H42.7V320h-40v160h359.5V320h-40z"],
+ "stackpath": [448, 512, [], "f842", "M244.6 232.4c0 8.5-4.26 20.49-21.34 20.49h-19.61v-41.47h19.61c17.13 0 21.34 12.36 21.34 20.98zM448 32v448H0V32zM151.3 287.84c0-21.24-12.12-34.54-46.72-44.85-20.57-7.41-26-10.91-26-18.63s7-14.61 20.41-14.61c14.09 0 20.79 8.45 20.79 18.35h30.7l.19-.57c.5-19.57-15.06-41.65-51.12-41.65-23.37 0-52.55 10.75-52.55 38.29 0 19.4 9.25 31.29 50.74 44.37 17.26 6.15 21.91 10.4 21.91 19.48 0 15.2-19.13 14.23-19.47 14.23-20.4 0-25.65-9.1-25.65-21.9h-30.8l-.18.56c-.68 31.32 28.38 45.22 56.63 45.22 29.98 0 51.12-13.55 51.12-38.29zm125.38-55.63c0-25.3-18.43-45.46-53.42-45.46h-51.78v138.18h32.17v-47.36h19.61c30.25 0 53.42-15.95 53.42-45.36zM297.94 325L347 186.78h-31.09L268 325zm106.52-138.22h-31.09L325.46 325h29.94z"],
+ "staylinked": [440, 512, [], "f3f5", "M382.7 292.5l2.7 2.7-170-167.3c-3.5-3.5-9.7-3.7-13.8-.5L144.3 171c-4.2 3.2-4.6 8.7-1.1 12.2l68.1 64.3c3.6 3.5 9.9 3.7 14 .5l.1-.1c4.1-3.2 10.4-3 14 .5l84 81.3c3.6 3.5 3.2 9-.9 12.2l-93.2 74c-4.2 3.3-10.5 3.1-14.2-.4L63.2 268c-3.5-3.5-9.7-3.7-13.9-.5L3.5 302.4c-4.2 3.2-4.7 8.7-1.2 12.2L211 510.7s7.4 6.8 17.3-.8l198-163.9c4-3.2 4.4-8.7.7-12.2zm54.5-83.4L226.7 2.5c-1.5-1.2-8-5.5-16.3 1.1L3.6 165.7c-4.2 3.2-4.8 8.7-1.2 12.2l42.3 41.7 171.7 165.1c3.7 3.5 10.1 3.7 14.3.4l50.2-38.8-.3-.3 7.7-6c4.2-3.2 4.6-8.7.9-12.2l-57.1-54.4c-3.6-3.5-10-3.7-14.2-.5l-.1.1c-4.2 3.2-10.5 3.1-14.2-.4L109 180.8c-3.6-3.5-3.1-8.9 1.1-12.2l92.2-71.5c4.1-3.2 10.3-3 13.9.5l160.4 159c3.7 3.5 10 3.7 14.1.5l45.8-35.8c4.1-3.2 4.4-8.7.7-12.2z"],
+ "steam": [496, 512, [], "f1b6", "M496 256c0 137-111.2 248-248.4 248-113.8 0-209.6-76.3-239-180.4l95.2 39.3c6.4 32.1 34.9 56.4 68.9 56.4 39.2 0 71.9-32.4 70.2-73.5l84.5-60.2c52.1 1.3 95.8-40.9 95.8-93.5 0-51.6-42-93.5-93.7-93.5s-93.7 42-93.7 93.5v1.2L176.6 279c-15.5-.9-30.7 3.4-43.5 12.1L0 236.1C10.2 108.4 117.1 8 247.6 8 384.8 8 496 119 496 256zM155.7 384.3l-30.5-12.6a52.79 52.79 0 0 0 27.2 25.8c26.9 11.2 57.8-1.6 69-28.4 5.4-13 5.5-27.3.1-40.3-5.4-13-15.5-23.2-28.5-28.6-12.9-5.4-26.7-5.2-38.9-.6l31.5 13c19.8 8.2 29.2 30.9 20.9 50.7-8.3 19.9-31 29.2-50.8 21zm173.8-129.9c-34.4 0-62.4-28-62.4-62.3s28-62.3 62.4-62.3 62.4 28 62.4 62.3-27.9 62.3-62.4 62.3zm.1-15.6c25.9 0 46.9-21 46.9-46.8 0-25.9-21-46.8-46.9-46.8s-46.9 21-46.9 46.8c.1 25.8 21.1 46.8 46.9 46.8z"],
+ "steam-square": [448, 512, [], "f1b7", "M185.2 356.5c7.7-18.5-1-39.7-19.6-47.4l-29.5-12.2c11.4-4.3 24.3-4.5 36.4.5 12.2 5.1 21.6 14.6 26.7 26.7 5 12.2 5 25.6-.1 37.7-10.5 25.1-39.4 37-64.6 26.5-11.6-4.8-20.4-13.6-25.4-24.2l28.5 11.8c18.6 7.8 39.9-.9 47.6-19.4zM400 32H48C21.5 32 0 53.5 0 80v160.7l116.6 48.1c12-8.2 26.2-12.1 40.7-11.3l55.4-80.2v-1.1c0-48.2 39.3-87.5 87.6-87.5s87.6 39.3 87.6 87.5c0 49.2-40.9 88.7-89.6 87.5l-79 56.3c1.6 38.5-29.1 68.8-65.7 68.8-31.8 0-58.5-22.7-64.5-52.7L0 319.2V432c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-99.7 222.5c-32.2 0-58.4-26.1-58.4-58.3s26.2-58.3 58.4-58.3 58.4 26.2 58.4 58.3-26.2 58.3-58.4 58.3zm.1-14.6c24.2 0 43.9-19.6 43.9-43.8 0-24.2-19.6-43.8-43.9-43.8-24.2 0-43.9 19.6-43.9 43.8 0 24.2 19.7 43.8 43.9 43.8z"],
+ "steam-symbol": [448, 512, [], "f3f6", "M395.5 177.5c0 33.8-27.5 61-61 61-33.8 0-61-27.3-61-61s27.3-61 61-61c33.5 0 61 27.2 61 61zm52.5.2c0 63-51 113.8-113.7 113.8L225 371.3c-4 43-40.5 76.8-84.5 76.8-40.5 0-74.7-28.8-83-67L0 358V250.7L97.2 290c15.1-9.2 32.2-13.3 52-11.5l71-101.7c.5-62.3 51.5-112.8 114-112.8C397 64 448 115 448 177.7zM203 363c0-34.7-27.8-62.5-62.5-62.5-4.5 0-9 .5-13.5 1.5l26 10.5c25.5 10.2 38 39 27.7 64.5-10.2 25.5-39.2 38-64.7 27.5-10.2-4-20.5-8.3-30.7-12.2 10.5 19.7 31.2 33.2 55.2 33.2 34.7 0 62.5-27.8 62.5-62.5zm207.5-185.3c0-42-34.3-76.2-76.2-76.2-42.3 0-76.5 34.2-76.5 76.2 0 42.2 34.3 76.2 76.5 76.2 41.9.1 76.2-33.9 76.2-76.2z"],
+ "sticker-mule": [576, 512, [], "f3f7", "M561.7 199.6c-1.3.3.3 0 0 0zm-6.2-77.4c-7.7-22.3-5.1-7.2-13.4-36.9-1.6-6.5-3.6-14.5-6.2-20-4.4-8.7-4.6-7.5-4.6-9.5 0-5.3 30.7-45.3 19-46.9-5.7-.6-12.2 11.6-20.6 17-8.6 4.2-8 5-10.3 5-2.6 0-5.7-3-6.2-5-2-5.7 1.9-25.9-3.6-25.9-3.6 0-12.3 24.8-17 25.8-5.2 1.3-27.9-11.4-75.1 18-25.3 13.2-86.9 65.2-87 65.3-6.7 4.7-20 4.7-35.5 16-44.4 30.1-109.6 9.4-110.7 9-110.6-26.8-128-15.2-159 11.5-20.8 17.9-23.7 36.5-24.2 38.9-4.2 20.4 5.2 48.3 6.7 64.3 1.8 19.3-2.7 17.7 7.7 98.3.5 1 4.1 0 5.1 1.5 0 8.4-3.8 12.1-4.1 13-1.5 4.5-1.5 10.5 0 16 2.3 8.2 8.2 37.2 8.2 46.9 0 41.8.4 44 2.6 49.4 3.9 10 12.5 9.1 17 12 3.1 3.5-.5 8.5 1 12.5.5 2 3.6 4 6.2 5 9.2 3.6 27 .3 29.9-2.5 1.6-1.5.5-4.5 3.1-5 5.1 0 10.8-.5 14.4-2.5 5.1-2.5 4.1-6 1.5-10.5-.4-.8-7-13.3-9.8-16-2.1-2-5.1-3-7.2-4.5-5.8-4.9-10.3-19.4-10.3-19.5-4.6-19.4-10.3-46.3-4.1-66.8 4.6-17.2 39.5-87.7 39.6-87.8 4.1-6.5 17-11.5 27.3-7 6 1.9 19.3 22 65.4 30.9 47.9 8.7 97.4-2 112.2-2 2.8 2-1.9 13-.5 38.9 0 26.4-.4 13.7-4.1 29.9-2.2 9.7 3.4 23.2-1.5 46.9-1.4 9.8-9.9 32.7-8.2 43.4.5 1 1 2 1.5 3.5.5 4.5 1.5 8.5 4.6 10 7.3 3.6 12-3.5 9.8 11.5-.7 3.1-2.6 12 1.5 15 4.4 3.7 30.6 3.4 36.5.5 2.6-1.5 1.6-4.5 6.4-7.4 1.9-.9 11.3-.4 11.3-6.5.3-1.8-9.2-19.9-9.3-20-2.6-3.5-9.2-4.5-11.3-8-6.9-10.1-1.7-52.6.5-59.4 3-11 5.6-22.4 8.7-32.4 11-42.5 10.3-50.6 16.5-68.3.8-1.8 6.4-23.1 10.3-29.9 9.3-17 21.7-32.4 33.5-47.4 18-22.9 34-46.9 52-69.8 6.1-7 8.2-13.7 18-8 10.8 5.7 21.6 7 31.9 17 14.6 12.8 10.2 18.2 11.8 22.9 1.5 5 7.7 10.5 14.9 9.5 10.4-2 13-2.5 13.4-2.5 2.6-.5 5.7-5 7.2-8 3.1-5.5 7.2-9 7.2-16.5 0-7.7-.4-2.8-20.6-52.9z"],
+ "strava": [384, 512, [], "f428", "M158.4 0L7 292h89.2l62.2-116.1L220.1 292h88.5zm150.2 292l-43.9 88.2-44.6-88.2h-67.6l112.2 220 111.5-220z"],
+ "stripe": [640, 512, [], "f429", "M165 144.7l-43.3 9.2-.2 142.4c0 26.3 19.8 43.3 46.1 43.3 14.6 0 25.3-2.7 31.2-5.9v-33.8c-5.7 2.3-33.7 10.5-33.7-15.7V221h33.7v-37.8h-33.7zm89.1 51.6l-2.7-13.1H213v153.2h44.3V233.3c10.5-13.8 28.2-11.1 33.9-9.3v-40.8c-6-2.1-26.7-6-37.1 13.1zm92.3-72.3l-44.6 9.5v36.2l44.6-9.5zM44.9 228.3c0-6.9 5.8-9.6 15.1-9.7 13.5 0 30.7 4.1 44.2 11.4v-41.8c-14.7-5.8-29.4-8.1-44.1-8.1-36 0-60 18.8-60 50.2 0 49.2 67.5 41.2 67.5 62.4 0 8.2-7.1 10.9-17 10.9-14.7 0-33.7-6.1-48.6-14.2v40c16.5 7.1 33.2 10.1 48.5 10.1 36.9 0 62.3-15.8 62.3-47.8 0-52.9-67.9-43.4-67.9-63.4zM640 261.6c0-45.5-22-81.4-64.2-81.4s-67.9 35.9-67.9 81.1c0 53.5 30.3 78.2 73.5 78.2 21.2 0 37.1-4.8 49.2-11.5v-33.4c-12.1 6.1-26 9.8-43.6 9.8-17.3 0-32.5-6.1-34.5-26.9h86.9c.2-2.3.6-11.6.6-15.9zm-87.9-16.8c0-20 12.3-28.4 23.4-28.4 10.9 0 22.5 8.4 22.5 28.4zm-112.9-64.6c-17.4 0-28.6 8.2-34.8 13.9l-2.3-11H363v204.8l44.4-9.4.1-50.2c6.4 4.7 15.9 11.2 31.4 11.2 31.8 0 60.8-23.2 60.8-79.6.1-51.6-29.3-79.7-60.5-79.7zm-10.6 122.5c-10.4 0-16.6-3.8-20.9-8.4l-.3-66c4.6-5.1 11-8.8 21.2-8.8 16.2 0 27.4 18.2 27.4 41.4.1 23.9-10.9 41.8-27.4 41.8zm-126.7 33.7h44.6V183.2h-44.6z"],
+ "stripe-s": [384, 512, [], "f42a", "M155.3 154.6c0-22.3 18.6-30.9 48.4-30.9 43.4 0 98.5 13.3 141.9 36.7V26.1C298.3 7.2 251.1 0 203.8 0 88.1 0 11 60.4 11 161.4c0 157.9 216.8 132.3 216.8 200.4 0 26.4-22.9 34.9-54.7 34.9-47.2 0-108.2-19.5-156.1-45.5v128.5a396.09 396.09 0 0 0 156 32.4c118.6 0 200.3-51 200.3-153.6 0-170.2-218-139.7-218-203.9z"],
+ "studiovinari": [512, 512, [], "f3f8", "M480.3 187.7l4.2 28v28l-25.1 44.1-39.8 78.4-56.1 67.5-79.1 37.8-17.7 24.5-7.7 12-9.6 4s17.3-63.6 19.4-63.6c2.1 0 20.3.7 20.3.7l66.7-38.6-92.5 26.1-55.9 36.8-22.8 28-6.6 1.4 20.8-73.6 6.9-5.5 20.7 12.9 88.3-45.2 56.8-51.5 14.8-68.4-125.4 23.3 15.2-18.2-173.4-53.3 81.9-10.5-166-122.9L133.5 108 32.2 0l252.9 126.6-31.5-38L378 163 234.7 64l18.7 38.4-49.6-18.1L158.3 0l194.6 122L310 66.2l108 96.4 12-8.9-21-16.4 4.2-37.8L451 89.1l29.2 24.7 11.5 4.2-7 6.2 8.5 12-13.1 7.4-10.3 20.2 10.5 23.9z"],
+ "stumbleupon": [512, 512, [], "f1a4", "M502.9 266v69.7c0 62.1-50.3 112.4-112.4 112.4-61.8 0-112.4-49.8-112.4-111.3v-70.2l34.3 16 51.1-15.2V338c0 14.7 12 26.5 26.7 26.5S417 352.7 417 338v-72h85.9zm-224.7-58.2l34.3 16 51.1-15.2V173c0-60.5-51.1-109-112.1-109-60.8 0-112.1 48.2-112.1 108.2v162.4c0 14.9-12 26.7-26.7 26.7S86 349.5 86 334.6V266H0v69.7C0 397.7 50.3 448 112.4 448c61.6 0 112.4-49.5 112.4-110.8V176.9c0-14.7 12-26.7 26.7-26.7s26.7 12 26.7 26.7v30.9z"],
+ "stumbleupon-circle": [496, 512, [], "f1a3", "M256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm0 177.5c-9.8 0-17.8 8-17.8 17.8v106.9c0 40.9-33.9 73.9-74.9 73.9-41.4 0-74.9-33.5-74.9-74.9v-46.5h57.3v45.8c0 10 8 17.8 17.8 17.8s17.8-7.9 17.8-17.8V200.1c0-40 34.2-72.1 74.7-72.1 40.7 0 74.7 32.3 74.7 72.6v23.7l-34.1 10.1-22.9-10.7v-20.6c.1-9.6-7.9-17.6-17.7-17.6zm167.6 123.6c0 41.4-33.5 74.9-74.9 74.9-41.2 0-74.9-33.2-74.9-74.2V263l22.9 10.7 34.1-10.1v47.1c0 9.8 8 17.6 17.8 17.6s17.8-7.9 17.8-17.6v-48h57.3c-.1 45.9-.1 46.4-.1 46.4z"],
+ "superpowers": [448, 512, [], "f2dd", "M448 32c-83.3 11-166.8 22-250 33-92 12.5-163.3 86.7-169 180-3.3 55.5 18 109.5 57.8 148.2L0 480c83.3-11 166.5-22 249.8-33 91.8-12.5 163.3-86.8 168.7-179.8 3.5-55.5-18-109.5-57.7-148.2L448 32zm-79.7 232.3c-4.2 79.5-74 139.2-152.8 134.5-79.5-4.7-140.7-71-136.3-151 4.5-79.2 74.3-139.3 153-134.5 79.3 4.7 140.5 71 136.1 151z"],
+ "supple": [640, 512, [], "f3f9", "M640 262.5c0 64.1-109 116.1-243.5 116.1-24.8 0-48.6-1.8-71.1-5 7.7.4 15.5.6 23.4.6 134.5 0 243.5-56.9 243.5-127.1 0-29.4-19.1-56.4-51.2-78 60 21.1 98.9 55.1 98.9 93.4zM47.7 227.9c-.1-70.2 108.8-127.3 243.3-127.6 7.9 0 15.6.2 23.3.5-22.5-3.2-46.3-4.9-71-4.9C108.8 96.3-.1 148.5 0 212.6c.1 38.3 39.1 72.3 99.3 93.3-32.3-21.5-51.5-48.6-51.6-78zm60.2 39.9s10.5 13.2 29.3 13.2c17.9 0 28.4-11.5 28.4-25.1 0-28-40.2-25.1-40.2-39.7 0-5.4 5.3-9.1 12.5-9.1 5.7 0 11.3 2.6 11.3 6.6v3.9h14.2v-7.9c0-12.1-15.4-16.8-25.4-16.8-16.5 0-28.5 10.2-28.5 24.1 0 26.6 40.2 25.4 40.2 39.9 0 6.6-5.8 10.1-12.3 10.1-11.9 0-20.7-10.1-20.7-10.1l-8.8 10.9zm120.8-73.6v54.4c0 11.3-7.1 17.8-17.8 17.8-10.7 0-17.8-6.5-17.8-17.7v-54.5h-15.8v55c0 18.9 13.4 31.9 33.7 31.9 20.1 0 33.4-13 33.4-31.9v-55h-15.7zm34.4 85.4h15.8v-29.5h15.5c16 0 27.2-11.5 27.2-28.1s-11.2-27.8-27.2-27.8h-39.1v13.4h7.8v72zm15.8-43v-29.1h12.9c8.7 0 13.7 5.7 13.7 14.4 0 8.9-5.1 14.7-14 14.7h-12.6zm57 43h15.8v-29.5h15.5c16 0 27.2-11.5 27.2-28.1s-11.2-27.8-27.2-27.8h-39.1v13.4h7.8v72zm15.7-43v-29.1h12.9c8.7 0 13.7 5.7 13.7 14.4 0 8.9-5 14.7-14 14.7h-12.6zm57.1 34.8c0 5.8 2.4 8.2 8.2 8.2h37.6c5.8 0 8.2-2.4 8.2-8.2v-13h-14.3v5.2c0 1.7-1 2.6-2.6 2.6h-18.6c-1.7 0-2.6-1-2.6-2.6v-61.2c0-5.7-2.4-8.2-8.2-8.2H401v13.4h5.2c1.7 0 2.6 1 2.6 2.6v61.2zm63.4 0c0 5.8 2.4 8.2 8.2 8.2H519c5.7 0 8.2-2.4 8.2-8.2v-13h-14.3v5.2c0 1.7-1 2.6-2.6 2.6h-19.7c-1.7 0-2.6-1-2.6-2.6v-20.3h27.7v-13.4H488v-22.4h19.2c1.7 0 2.6 1 2.6 2.6v5.2H524v-13c0-5.7-2.5-8.2-8.2-8.2h-51.6v13.4h7.8v63.9zm58.9-76v5.9h1.6v-5.9h2.7v-1.2h-7v1.2h2.7zm5.7-1.2v7.1h1.5v-5.7l2.3 5.7h1.3l2.3-5.7v5.7h1.5v-7.1h-2.3l-2.1 5.1-2.1-5.1h-2.4z"],
+ "suse": [640, 512, [], "f7d6", "M471.08 102.66s-.3 18.3-.3 20.3c-9.1-3-74.4-24.1-135.7-26.3-51.9-1.8-122.8-4.3-223 57.3-19.4 12.4-73.9 46.1-99.6 109.7C7 277-.12 307 7 335.06a111 111 0 0 0 16.5 35.7c17.4 25 46.6 41.6 78.1 44.4 44.4 3.9 78.1-16 90-53.3 8.2-25.8 0-63.6-31.5-82.9-25.6-15.7-53.3-12.1-69.2-1.6-13.9 9.2-21.8 23.5-21.6 39.2.3 27.8 24.3 42.6 41.5 42.6a49 49 0 0 0 15.8-2.7c6.5-1.8 13.3-6.5 13.3-14.9 0-12.1-11.6-14.8-16.8-13.9-2.9.5-4.5 2-11.8 2.4-2-.2-12-3.1-12-14V316c.2-12.3 13.2-18 25.5-16.9 32.3 2.8 47.7 40.7 28.5 65.7-18.3 23.7-76.6 23.2-99.7-20.4-26-49.2 12.7-111.2 87-98.4 33.2 5.7 83.6 35.5 102.4 104.3h45.9c-5.7-17.6-8.9-68.3 42.7-68.3 56.7 0 63.9 39.9 79.8 68.3H460c-12.8-18.3-21.7-38.7-18.9-55.8 5.6-33.8 39.7-18.4 82.4-17.4 66.5.4 102.1-27 103.1-28 3.7-3.1 6.5-15.8 7-17.7 1.3-5.1-3.2-2.4-3.2-2.4-8.7 5.2-30.5 15.2-50.9 15.6-25.3.5-76.2-25.4-81.6-28.2-.3-.4.1 1.2-11-25.5 88.4 58.3 118.3 40.5 145.2 21.7.8-.6 4.3-2.9 3.6-5.7-13.8-48.1-22.4-62.7-34.5-69.6-37-21.6-125-34.7-129.2-35.3.1-.1-.9-.3-.9.7zm60.4 72.8a37.54 37.54 0 0 1 38.9-36.3c33.4 1.2 48.8 42.3 24.4 65.2-24.2 22.7-64.4 4.6-63.3-28.9zm38.6-25.3a26.27 26.27 0 1 0 25.4 27.2 26.19 26.19 0 0 0-25.4-27.2zm4.3 28.8c-15.4 0-15.4-15.6 0-15.6s15.4 15.64 0 15.64z"],
+ "swift": [448, 512, [], "f8e1", "M448 156.09c0-4.51-.08-9-.2-13.52a196.31 196.31 0 0 0-2.58-29.42 99.62 99.62 0 0 0-9.22-28A94.08 94.08 0 0 0 394.84 44a99.17 99.17 0 0 0-28-9.22 195 195 0 0 0-29.43-2.59c-4.51-.12-9-.17-13.52-.2H124.14c-4.51 0-9 .08-13.52.2-2.45.07-4.91.15-7.37.27a171.68 171.68 0 0 0-22.06 2.32 103.06 103.06 0 0 0-21.21 6.1q-3.46 1.45-6.81 3.12a94.66 94.66 0 0 0-18.39 12.32c-1.88 1.61-3.69 3.28-5.43 5A93.86 93.86 0 0 0 12 85.17a99.45 99.45 0 0 0-9.22 28 196.31 196.31 0 0 0-2.54 29.4c-.13 4.51-.18 9-.21 13.52v199.83c0 4.51.08 9 .21 13.51a196.08 196.08 0 0 0 2.58 29.42 99.3 99.3 0 0 0 9.22 28A94.31 94.31 0 0 0 53.17 468a99.47 99.47 0 0 0 28 9.21 195 195 0 0 0 29.43 2.59c4.5.12 9 .17 13.52.2H323.91c4.51 0 9-.08 13.52-.2a196.59 196.59 0 0 0 29.44-2.59 99.57 99.57 0 0 0 28-9.21A94.22 94.22 0 0 0 436 426.84a99.3 99.3 0 0 0 9.22-28 194.79 194.79 0 0 0 2.59-29.42c.12-4.5.17-9 .2-13.51V172.14c-.01-5.35-.01-10.7-.01-16.05zm-69.88 241c-20-38.93-57.23-29.27-76.31-19.47-1.72 1-3.48 2-5.25 3l-.42.25c-39.5 21-92.53 22.54-145.85-.38A234.64 234.64 0 0 1 45 290.12a230.63 230.63 0 0 0 39.17 23.37c56.36 26.4 113 24.49 153 0-57-43.85-104.6-101-141.09-147.22a197.09 197.09 0 0 1-18.78-25.9c43.7 40 112.7 90.22 137.48 104.12-52.57-55.49-98.89-123.94-96.72-121.74 82.79 83.42 159.18 130.59 159.18 130.59 2.88 1.58 5 2.85 6.73 4a127.44 127.44 0 0 0 4.16-12.47c13.22-48.33-1.66-103.58-35.31-149.2C329.61 141.75 375 229.34 356.4 303.42c-.44 1.73-.95 3.4-1.44 5.09 38.52 47.4 28.04 98.17 23.13 88.59z"],
+ "symfony": [512, 512, [], "f83d", "M256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm133.74 143.54c-11.47.41-19.4-6.45-19.77-16.87-.27-9.18 6.68-13.44 6.53-18.85-.23-6.55-10.16-6.82-12.87-6.67-39.78 1.29-48.59 57-58.89 113.85 21.43 3.15 36.65-.72 45.14-6.22 12-7.75-3.34-15.72-1.42-24.56 4-18.16 32.55-19 32 5.3-.36 17.86-25.92 41.81-77.6 35.7-10.76 59.52-18.35 115-58.2 161.72-29 34.46-58.4 39.82-71.58 40.26-24.65.85-41-12.31-41.58-29.84-.56-17 14.45-26.26 24.31-26.59 21.89-.75 30.12 25.67 14.88 34-12.09 9.71.11 12.61 2.05 12.55 10.42-.36 17.34-5.51 22.18-9 24-20 33.24-54.86 45.35-118.35 8.19-49.66 17-78 18.23-82-16.93-12.75-27.08-28.55-49.85-34.72-15.61-4.23-25.12-.63-31.81 7.83-7.92 10-5.29 23 2.37 30.7l12.63 14c15.51 17.93 24 31.87 20.8 50.62-5.06 29.93-40.72 52.9-82.88 39.94-36-11.11-42.7-36.56-38.38-50.62 7.51-24.15 42.36-11.72 34.62 13.6-2.79 8.6-4.92 8.68-6.28 13.07-4.56 14.77 41.85 28.4 51-1.39 4.47-14.52-5.3-21.71-22.25-39.85-28.47-31.75-16-65.49 2.95-79.67C204.23 140.13 251.94 197 262 205.29c37.17-109 100.53-105.46 102.43-105.53 25.16-.81 44.19 10.59 44.83 28.65.25 7.69-4.17 22.59-19.52 23.13z"],
+ "teamspeak": [512, 512, [], "f4f9", "M244.2 346.79c2.4-12.3-12-30-32.4-48.7-20.9-19.2-48.2-39.1-63.4-46.6-21.7-12-41.7-1.8-46.3 22.7-5 26.2 0 51.4 14.5 73.9 10.2 15.5 25.4 22.7 43.4 24 11.6.6 52.5 2.2 61.7-1 11.9-4.3 20.1-11.8 22.5-24.3zm205 20.8a5.22 5.22 0 0 0-8.3 2.4c-8 25.4-44.7 112.5-172.1 121.5-149.7 10.5 80.3 43.6 145.4-6.4 22.7-17.4 47.6-35 46.6-85.4-.4-10.1-4.9-26.69-11.6-32.1zm62-122.4c-.3-18.9-8.6-33.4-26-42.2-2.9-1.3-5-2.7-5.9-6.4A222.64 222.64 0 0 0 438.9 103c-1.1-1.5-3.5-3.2-2.2-5 8.5-11.5-.3-18-7-24.4Q321.4-31.11 177.4 13.09c-40.1 12.3-73.9 35.6-102 67.4-4 4.3-6.7 9.1-3 14.5 3 4 1.3 6.2-1 9.3C51.6 132 38.2 162.59 32.1 196c-.7 4.3-2.9 6-6.4 7.8-14.2 7-22.5 18.5-24.9 34L0 264.29v20.9c0 30.8 21 50.4 51.8 49 7.7-.3 11.7-4.3 12-11.5 2-77.5-2.4-95.4 3.7-125.8C92.1 72.39 234.3 5 345.3 65.39 411.4 102 445.7 159 447.6 234.79c.8 28.2 0 56.5 0 84.6 0 7 2.2 12.5 9.4 14.2 24.1 5 49.2-12 53.2-36.7 2.9-17.1 1-34.5 1-51.7zm-159.6 131.5c36.5 2.8 59.3-28.5 58.4-60.5-2.1-45.2-66.2-16.5-87.8-8-73.2 28.1-45 54.9-22.2 60.8z"],
+ "telegram": [496, 512, [], "f2c6", "M248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm121.8 169.9l-40.7 191.8c-3 13.6-11.1 16.9-22.4 10.5l-62-45.7-29.9 28.8c-3.3 3.3-6.1 6.1-12.5 6.1l4.4-63.1 114.9-103.8c5-4.4-1.1-6.9-7.7-2.5l-142 89.4-61.2-19.1c-13.3-4.2-13.6-13.3 2.8-19.7l239.1-92.2c11.1-4 20.8 2.7 17.2 19.5z"],
+ "telegram-plane": [448, 512, [], "f3fe", "M446.7 98.6l-67.6 318.8c-5.1 22.5-18.4 28.1-37.3 17.5l-103-75.9-49.7 47.8c-5.5 5.5-10.1 10.1-20.7 10.1l7.4-104.9 190.9-172.5c8.3-7.4-1.8-11.5-12.9-4.1L117.8 284 16.2 252.2c-22.1-6.9-22.5-22.1 4.6-32.7L418.2 66.4c18.4-6.9 34.5 4.1 28.5 32.2z"],
+ "tencent-weibo": [384, 512, [], "f1d5", "M72.3 495.8c1.4 19.9-27.6 22.2-29.7 2.9C31 368.8 73.7 259.2 144 185.5c-15.6-34 9.2-77.1 50.6-77.1 30.3 0 55.1 24.6 55.1 55.1 0 44-49.5 70.8-86.9 45.1-65.7 71.3-101.4 169.8-90.5 287.2zM192 .1C66.1.1-12.3 134.3 43.7 242.4 52.4 259.8 79 246.9 70 229 23.7 136.4 91 29.8 192 29.8c75.4 0 136.9 61.4 136.9 136.9 0 90.8-86.9 153.9-167.7 133.1-19.1-4.1-25.6 24.4-6.6 29.1 110.7 23.2 204-60 204-162.3C358.6 74.7 284 .1 192 .1z"],
+ "the-red-yeti": [512, 512, [], "f69d", "M488.23 241.7l20.7 7.1c-9.6-23.9-23.9-37-31.7-44.8l7.1-18.2c.2 0 12.3-27.8-2.5-30.7-.6-11.3-6.6-27-18.4-27-7.6-10.6-17.7-12.3-30.7-5.9a122.2 122.2 0 0 0-25.3 16.5c-5.3-6.4-3 .4-3-29.8-37.1-24.3-45.4-11.7-74.8 3l.5.5a239.36 239.36 0 0 0-68.4-13.3c-5.5-8.7-18.6-19.1-25.1-25.1l24.8 7.1c-5.5-5.5-26.8-12.9-34.2-15.2 18.2-4.1 29.8-20.8 42.5-33-34.9-10.1-67.9-5.9-97.9 11.8l12-44.2L182 0c-31.6 24.2-33 41.9-33.7 45.5-.9-2.4-6.3-19.6-15.2-27a35.12 35.12 0 0 0-.5 25.3c3 8.4 5.9 14.8 8.4 18.9-16-3.3-28.3-4.9-49.2 0h-3.7l33 14.3a194.26 194.26 0 0 0-46.7 67.4l-1.7 8.4 1.7 1.7 7.6-4.7c-3.3 11.6-5.3 19.4-6.6 25.8a200.18 200.18 0 0 0-27.8 40.3c-15 1-31.8 10.8-40.3 14.3l3 3.4 28.8 1c-.5 1-.7 2.2-1.2 3.2-7.3 6.4-39.8 37.7-33 80.7l20.2-22.4c.5 1.7.7 3.4 1.2 5.2 0 25.5.4 89.6 64.9 150.5 43.6 40 96 60.2 157.5 60.2 121.7 0 223-87.3 223-211.5 6.8-9.7-1.2 3 16.7-25.1l13 14.3 2.5-.5A181.84 181.84 0 0 0 495 255a44.74 44.74 0 0 0-6.8-13.3zM398 111.2l-.5 21.9c5.5 18.1 16.9 17.2 22.4 17.2l-3.4-4.7 22.4-5.4a242.44 242.44 0 0 1-27 0c12.8-2.1 33.3-29 43-11.3 3.4 7.6 6.4 17.2 9.3 27.8l1.7-5.9a56.38 56.38 0 0 1-1.7-15.2c5.4.5 8.8 3.4 9.3 10.1.5 6.4 1.7 14.8 3.4 25.3l4.7-11.3c4.6 0 4.5-3.6-2.5 20.7-20.9-8.7-35.1-8.4-46.5-8.4l18.2-16c-25.3 8.2-33 10.8-54.8 20.9-1.1-5.4-5-13.5-16-19.9-3.2 3.8-2.8.9-.7 14.8h-2.5a62.32 62.32 0 0 0-8.4-23.1l4.2-3.4c8.4-7.1 11.8-14.3 10.6-21.9-.5-6.4-5.4-13.5-13.5-20.7 5.6-3.4 15.2-.4 28.3 8.5zm-39.6-10.1c2.7 1.9 11.4 5.4 18.9 17.2 4.2 8.4 4 9.8 3.4 11.1-.5 2.4-.5 4.3-3 7.1-1.7 2.5-5.4 4.7-11.8 7.6-7.6-13-16.5-23.6-27.8-31.2zM91 143.1l1.2-1.7c1.2-2.9 4.2-7.6 9.3-15.2l2.5-3.4-13 12.3 5.4-4.7-10.1 9.3-4.2 1.2c12.3-24.1 23.1-41.3 32.5-50.2 9.3-9.3 16-16 20.2-19.4l-6.4 1.2c-11.3-4.2-19.4-7.1-24.8-8.4 2.5-.5 3.7-.5 3.2-.5 10.3 0 17.5.5 20.9 1.2a52.35 52.35 0 0 0 16 2.5l.5-1.7-8.4-35.8 13.5 29a42.89 42.89 0 0 0 5.9-14.3c1.7-6.4 5.4-13 10.1-19.4s7.6-10.6 9.3-11.3a234.68 234.68 0 0 0-6.4 25.3l-1.7 7.1-.5 4.7 2.5 2.5C190.4 39.9 214 34 239.8 34.5l21.1.5c-11.8 13.5-27.8 21.9-48.5 24.8a201.26 201.26 0 0 1-23.4 2.9l-.2-.5-2.5-1.2a20.75 20.75 0 0 0-14 2c-2.5-.2-4.9-.5-7.1-.7l-2.5 1.7.5 1.2c2 .2 3.9.5 6.2.7l-2 3.4 3.4-.5-10.6 11.3c-4.2 3-5.4 6.4-4.2 9.3l5.4-3.4h1.2a39.4 39.4 0 0 1 25.3-15.2v-3c6.4.5 13 1 19.4 1.2 6.4 0 8.4.5 5.4 1.2a189.6 189.6 0 0 1 20.7 13.5c13.5 10.1 23.6 21.9 30 35.4 8.8 18.2 13.5 37.1 13.5 56.6a141.13 141.13 0 0 1-3 28.3 209.91 209.91 0 0 1-16 46l2.5.5c18.2-19.7 41.9-16 49.2-16l-6.4 5.9 22.4 17.7-1.7 30.7c-5.4-12.3-16.5-21.1-33-27.8 16.5 14.8 23.6 21.1 21.9 20.2-4.8-2.8-3.5-1.9-10.8-3.7 4.1 4.1 17.5 18.8 18.2 20.7l.2.2-.2.2c0 1.8 1.6-1.2-14 22.9-75.2-15.3-106.27-42.7-141.2-63.2l11.8 1.2c-11.8-18.5-15.6-17.7-38.4-26.1L149 225c-8.8-3-18.2-3-28.3.5l7.6-10.6-1.2-1.7c-14.9 4.3-19.8 9.2-22.6 11.3-1.1-5.5-2.8-12.4-12.3-28.8l-1.2 27-13.2-5c1.5-25.2 5.4-50.5 13.2-74.6zm276.5 330c-49.9 25-56.1 22.4-59 23.9-29.8-11.8-50.9-31.7-63.5-58.8l30 16.5c-9.8-9.3-18.3-16.5-38.4-44.3l11.8 23.1-17.7-7.6c14.2 21.1 23.5 51.7 66.6 73.5-120.8 24.2-199-72.1-200.9-74.3a262.57 262.57 0 0 0 35.4 24.8c3.4 1.7 7.1 2.5 10.1 1.2l-16-20.7c9.2 4.2 9.5 4.5 69.1 29-42.5-20.7-73.8-40.8-93.2-60.2-.5 6.4-1.2 10.1-1.2 10.1a80.25 80.25 0 0 1 20.7 26.6c-39-18.9-57.6-47.6-71.3-82.6 49.9 55.1 118.9 37.5 120.5 37.1 34.8 16.4 69.9 23.6 113.9 10.6 3.3 0 20.3 17 25.3 39.1l4.2-3-2.5-23.6c9 9 24.9 22.6 34.4 13-15.6-5.3-23.5-9.5-29.5-31.7 4.6 4.2 7.6 9 27.8 15l1.2-1.2-10.5-14.2c11.7-4.8-3.5 1 32-10.8 4.3 34.3 9 49.2.7 89.5zm115.3-214.4l-2.5.5 3 9.3c-3.5 5.9-23.7 44.3-71.6 79.7-39.5 29.8-76.6 39.1-80.9 40.3l-7.6-7.1-1.2 3 14.3 16-7.1-4.7 3.4 4.2h-1.2l-21.9-13.5 9.3 26.6-19-27.9-1.2 2.5 7.6 29c-6.1-8.2-21-32.6-56.8-39.6l32.5 21.2a214.82 214.82 0 0 1-93.2-6.4c-4.2-1.2-8.9-2.5-13.5-4.2l1.2-3-44.8-22.4 26.1 22.4c-57.7 9.1-113-25.4-126.4-83.4l-2.5-16.4-22.27 22.3c19.5-57.5 25.6-57.9 51.4-70.1-9.1-5.3-1.6-3.3-38.4-9.3 15.8-5.8 33-15.4 73 5.2a18.5 18.5 0 0 1 3.7-1.7c.6-3.2.4-.8 1-11.8 3.9 10 3.6 8.7 3 9.3l1.7.5c12.7-6.5 8.9-4.5 17-8.9l-5.4 13.5 22.3-5.8-8.4 8.4 2.5 2.5c4.5-1.8 30.3 3.4 40.8 16l-23.6-2.5c39.4 23 51.5 54 55.8 69.6l1.7-1.2c-2.8-22.3-12.4-33.9-16-40.1 4.2 5 39.2 34.6 110.4 46-11.3-.5-23.1 5.4-34.9 18.9l46.7-20.2-9.3 21.9c7.6-10.1 14.8-23.6 21.2-39.6v-.5l1.2-3-1.2 16c13.5-41.8 25.3-78.5 35.4-109.7l13.5-27.8v-2l-5.4-4.2h10.1l5.9 4.2 2.5-1.2-3.4-16 12.3 18.9 41.8-20.2-14.8 13 .5 2.9 17.7-.5a184 184 0 0 1 33 4.2l-23.6 2.5-1.2 3 26.6 23.1a254.21 254.21 0 0 1 27 32c-11.2-3.3-10.3-3.4-21.2-3.4l12.3 32.5zm-6.1-71.3l-3.9 13-14.3-11.8zm-254.8 7.1c1.7 10.6 4.7 17.7 8.8 21.9-9.3 6.6-27.5 13.9-46.5 16l.5 1.2a50.22 50.22 0 0 0 24.8-2.5l-7.1 13c4.2-1.7 10.1-7.1 17.7-14.8 11.9-5.5 12.7-5.1 20.2-16-12.7-6.4-15.7-13.7-18.4-18.8zm3.7-102.3c-6.4-3.4-10.6 3-12.3 18.9s2.5 29.5 11.8 39.6 18.2 10.6 26.1 3 3.4-23.6-11.3-47.7a39.57 39.57 0 0 0-14.27-13.8zm-4.7 46.3c5.4 2.2 10.5 1.9 12.3-10.6v-4.7l-1.2.5c-4.3-3.1-2.5-4.5-1.7-6.2l.5-.5c-.9-1.2-5-8.1-12.5 4.7-.5-13.5.5-21.9 3-24.8 1.2-2.5 4.7-1.2 11.3 4.2 6.4 5.4 11.3 16 15.2 32.5 6.5 28-19.8 26.2-26.9 4.9zm-45-5.5c1.6.3 9.3-1.1 9.3-14.8h-.5c-5.4-1.1-2.2-5.5-.7-5.9-1.7-3-3.4-4.2-5.4-4.7-8.1 0-11.6 12.7-8.1 21.2a7.51 7.51 0 0 0 5.43 4.2zM216 82.9l-2.5.5.5 3a48.94 48.94 0 0 1 26.1 5.9c-2.5-5.5-10-14.3-28.3-14.3l.5 2.5zm-71.8 49.4c21.7 16.8 16.5 21.4 46.5 23.6l-2.9-4.7a42.67 42.67 0 0 0 14.8-28.3c1.7-16-1.2-29.5-8.8-41.3l13-7.6a2.26 2.26 0 0 0-.5-1.7 14.21 14.21 0 0 0-13.5 1.7c-12.7 6.7-28 20.9-29 22.4-1.7 1.7-3.4 5.9-5.4 13.5a99.61 99.61 0 0 0-2.9 23.6c-4.7-8-10.5-6.4-19.9-5.9l7.1 7.6c-16.5 0-23.3 15.4-23.6 16 6.8 0 4.6-7.6 30-12.3-4.3-6.3-3.3-5-4.9-6.6zm18.7-18.7c1.2-7.6 3.4-13 6.4-17.2 5.4-6.4 10.6-10.1 16-11.8 4.2-1.7 7.1 1.2 10.1 9.3a72.14 72.14 0 0 1 3 25.3c-.5 9.3-3.4 17.2-8.4 23.1-2.9 3.4-5.4 5.9-6.4 7.6a39.21 39.21 0 0 1-11.3-.5l-7.1-3.4-5.4-6.4c.8-10 1.3-18.8 3.1-26zm42 56.1c-34.8 14.4-34.7 14-36.1 14.3-20.8 4.7-19-24.4-18.9-24.8l5.9-1.2-.5-2.5c-20.2-2.6-31 4.2-32.5 4.9.5.5 3 3.4 5.9 9.3 4.2-6.4 8.8-10.1 15.2-10.6a83.47 83.47 0 0 0 1.7 33.7c.1.5 2.6 17.4 27.5 24.1 11.3 3 27 1.2 48.9-5.4l-9.2.5c-4.2-14.8-6.4-24.8-5.9-29.5 11.3-8.8 21.9-11.3 30.7-7.6h2.5l-11.8-7.6-7.1.5c-5.9 1.2-12.3 4.2-19.4 8.4z"],
+ "themeco": [448, 512, [], "f5c6", "M202.9 8.43c9.9-5.73 26-5.82 35.95-.21L430 115.85c10 5.6 18 19.44 18 30.86V364c0 11.44-8.06 25.29-18 31L238.81 503.74c-9.93 5.66-26 5.57-35.85-.21L17.86 395.12C8 389.34 0 375.38 0 364V146.71c0-11.44 8-25.36 17.91-31.08zm-77.4 199.83c-15.94 0-31.89.14-47.83.14v101.45H96.8V280h28.7c49.71 0 49.56-71.74 0-71.74zm140.14 100.29l-30.73-34.64c37-7.51 34.8-65.23-10.87-65.51-16.09 0-32.17-.14-48.26-.14v101.59h19.13v-33.91h18.41l29.56 33.91h22.76zm-41.59-82.32c23.34 0 23.26 32.46 0 32.46h-29.13v-32.46zm-95.56-1.6c21.18 0 21.11 38.85 0 38.85H96.18v-38.84zm192.65-18.25c-68.46 0-71 105.8 0 105.8 69.48-.01 69.41-105.8 0-105.8zm0 17.39c44.12 0 44.8 70.86 0 70.86s-44.43-70.86 0-70.86z"],
+ "themeisle": [512, 512, [], "f2b2", "M208 88.286c0-10 6.286-21.714 17.715-21.714 11.142 0 17.714 11.714 17.714 21.714 0 10.285-6.572 21.714-17.714 21.714C214.286 110 208 98.571 208 88.286zm304 160c0 36.001-11.429 102.286-36.286 129.714-22.858 24.858-87.428 61.143-120.857 70.572l-1.143.286v32.571c0 16.286-12.572 30.571-29.143 30.571-10 0-19.429-5.714-24.572-14.286-5.427 8.572-14.856 14.286-24.856 14.286-10 0-19.429-5.714-24.858-14.286-5.142 8.572-14.571 14.286-24.57 14.286-10.286 0-19.429-5.714-24.858-14.286-5.143 8.572-14.571 14.286-24.571 14.286-18.857 0-29.429-15.714-29.429-32.857-16.286 12.285-35.715 19.428-56.571 19.428-22 0-43.429-8.285-60.286-22.857 10.285-.286 20.571-2.286 30.285-5.714-20.857-5.714-39.428-18.857-52-36.286 21.37 4.645 46.209 1.673 67.143-11.143-22-22-56.571-58.857-68.572-87.428C1.143 321.714 0 303.714 0 289.429c0-49.714 20.286-160 86.286-160 10.571 0 18.857 4.858 23.143 14.857a158.792 158.792 0 0 1 12-15.428c2-2.572 5.714-5.429 7.143-8.286 7.999-12.571 11.714-21.142 21.714-34C182.571 45.428 232 17.143 285.143 17.143c6 0 12 .285 17.714 1.143C313.714 6.571 328.857 0 344.572 0c14.571 0 29.714 6 40 16.286.857.858 1.428 2.286 1.428 3.428 0 3.714-10.285 13.429-12.857 16.286 4.286 1.429 15.714 6.858 15.714 12 0 2.857-2.857 5.143-4.571 7.143 31.429 27.714 49.429 67.143 56.286 108 4.286-5.143 10.285-8.572 17.143-8.572 10.571 0 20.857 7.144 28.571 14.001C507.143 187.143 512 221.714 512 248.286zM188 89.428c0 18.286 12.571 37.143 32.286 37.143 19.714 0 32.285-18.857 32.285-37.143 0-18-12.571-36.857-32.285-36.857-19.715 0-32.286 18.858-32.286 36.857zM237.714 194c0-19.714 3.714-39.143 8.571-58.286-52.039 79.534-13.531 184.571 68.858 184.571 21.428 0 42.571-7.714 60-20 2-7.429 3.714-14.857 3.714-22.572 0-14.286-6.286-21.428-20.572-21.428-4.571 0-9.143.857-13.429 1.714-63.343 12.668-107.142 3.669-107.142-63.999zm-41.142 254.858c0-11.143-8.858-20.857-20.286-20.857-11.429 0-20 9.715-20 20.857v32.571c0 11.143 8.571 21.142 20 21.142 11.428 0 20.286-9.715 20.286-21.142v-32.571zm49.143 0c0-11.143-8.572-20.857-20-20.857-11.429 0-20.286 9.715-20.286 20.857v32.571c0 11.143 8.857 21.142 20.286 21.142 11.428 0 20-10 20-21.142v-32.571zm49.713 0c0-11.143-8.857-20.857-20.285-20.857-11.429 0-20.286 9.715-20.286 20.857v32.571c0 11.143 8.857 21.142 20.286 21.142 11.428 0 20.285-9.715 20.285-21.142v-32.571zm49.715 0c0-11.143-8.857-20.857-20.286-20.857-11.428 0-20.286 9.715-20.286 20.857v32.571c0 11.143 8.858 21.142 20.286 21.142 11.429 0 20.286-10 20.286-21.142v-32.571zM421.714 286c-30.857 59.142-90.285 102.572-158.571 102.572-96.571 0-160.571-84.572-160.571-176.572 0-16.857 2-33.429 6-49.714-20 33.715-29.714 72.572-29.714 111.429 0 60.286 24.857 121.715 71.429 160.857 5.143-9.714 14.857-16.286 26-16.286 10 0 19.428 5.714 24.571 14.286 5.429-8.571 14.571-14.286 24.858-14.286 10 0 19.428 5.714 24.571 14.286 5.429-8.571 14.857-14.286 24.858-14.286 10 0 19.428 5.714 24.857 14.286 5.143-8.571 14.571-14.286 24.572-14.286 10.857 0 20.857 6.572 25.714 16 43.427-36.286 68.569-92 71.426-148.286zm10.572-99.714c0-53.714-34.571-105.714-92.572-105.714-30.285 0-58.571 15.143-78.857 36.857C240.862 183.812 233.41 254 302.286 254c28.805 0 97.357-28.538 84.286 36.857 28.857-26 45.714-65.714 45.714-104.571z"],
+ "think-peaks": [576, 512, [], "f731", "M465.4 409.4l87.1-150.2-32-.3-55.1 95L259.2 0 23 407.4l32 .3L259.2 55.6zm-355.3-44.1h32.1l117.4-202.5L463 511.9l32.5.1-235.8-404.6z"],
+ "tiktok": [448, 512, [], "e07b", "M448,209.91a210.06,210.06,0,0,1-122.77-39.25V349.38A162.55,162.55,0,1,1,185,188.31V278.2a74.62,74.62,0,1,0,52.23,71.18V0l88,0a121.18,121.18,0,0,0,1.86,22.17h0A122.18,122.18,0,0,0,381,102.39a121.43,121.43,0,0,0,67,20.14Z"],
+ "trade-federation": [496, 512, [], "f513", "M248 8.8c-137 0-248 111-248 248s111 248 248 248 248-111 248-248-111-248-248-248zm0 482.8c-129.7 0-234.8-105.1-234.8-234.8S118.3 22 248 22s234.8 105.1 234.8 234.8S377.7 491.6 248 491.6zm155.1-328.5v-46.8H209.3V198H54.2l36.7 46h117.7v196.8h48.8V245h83.3v-47h-83.3v-34.8h145.7zm-73.3 45.1v23.9h-82.9v197.4h-26.8V232.1H96.3l-20.1-23.9h143.9v-80.6h171.8V152h-145v56.2zm-161.3-69l-12.4-20.7 2.1 23.8-23.5 5.4 23.3 5.4-2.1 24 12.3-20.5 22.2 9.5-15.7-18.1 15.8-18.1zm-29.6-19.7l9.3-11.5-12.7 5.9-8-12.4 1.7 13.9-14.3 3.8 13.7 2.7-.8 14.7 6.8-12.2 13.8 5.3zm165.4 145.2l-13.1 5.6-7.3-12.2 1.3 14.2-13.9 3.2 13.9 3.2-1.2 14.2 7.3-12.2 13.1 5.5-9.4-10.7zm106.9-77.2l-20.9 9.1-12-19.6 2.2 22.7-22.3 5.4 22.2 4.9-1.8 22.9 11.5-19.6 21.2 8.8-15.1-17zM248 29.9c-125.3 0-226.9 101.6-226.9 226.9S122.7 483.7 248 483.7s226.9-101.6 226.9-226.9S373.3 29.9 248 29.9zM342.6 196v51h-83.3v195.7h-52.7V245.9H89.9l-40-49.9h157.4v-81.6h197.8v50.7H259.4V196zM248 43.2c60.3 0 114.8 25 153.6 65.2H202.5V190H45.1C73.1 104.8 153.4 43.2 248 43.2zm0 427.1c-117.9 0-213.6-95.6-213.6-213.5 0-21.2 3.1-41.8 8.9-61.1L87.1 252h114.7v196.8h64.6V253h83.3v-62.7h-83.2v-19.2h145.6v-50.8c30.8 37 49.3 84.6 49.3 136.5.1 117.9-95.5 213.5-213.4 213.5zM178.8 275l-11-21.4 1.7 24.5-23.7 3.9 23.8 5.9-3.7 23.8 13-20.9 21.5 10.8-15.8-18.8 16.9-17.1z"],
+ "trello": [448, 512, [], "f181", "M392.3 32H56.1C25.1 32 0 57.1 0 88c-.1 0 0-4 0 336 0 30.9 25.1 56 56 56h336.2c30.8-.2 55.7-25.2 55.7-56V88c.1-30.8-24.8-55.8-55.6-56zM197 371.3c-.2 14.7-12.1 26.6-26.9 26.6H87.4c-14.8.1-26.9-11.8-27-26.6V117.1c0-14.8 12-26.9 26.9-26.9h82.9c14.8 0 26.9 12 26.9 26.9v254.2zm193.1-112c0 14.8-12 26.9-26.9 26.9h-81c-14.8 0-26.9-12-26.9-26.9V117.2c0-14.8 12-26.9 26.8-26.9h81.1c14.8 0 26.9 12 26.9 26.9v142.1z"],
+ "tumblr": [320, 512, [], "f173", "M309.8 480.3c-13.6 14.5-50 31.7-97.4 31.7-120.8 0-147-88.8-147-140.6v-144H17.9c-5.5 0-10-4.5-10-10v-68c0-7.2 4.5-13.6 11.3-16 62-21.8 81.5-76 84.3-117.1.8-11 6.5-16.3 16.1-16.3h70.9c5.5 0 10 4.5 10 10v115.2h83c5.5 0 10 4.4 10 9.9v81.7c0 5.5-4.5 10-10 10h-83.4V360c0 34.2 23.7 53.6 68 35.8 4.8-1.9 9-3.2 12.7-2.2 3.5.9 5.8 3.4 7.4 7.9l22 64.3c1.8 5 3.3 10.6-.4 14.5z"],
+ "tumblr-square": [448, 512, [], "f174", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-82.3 364.2c-8.5 9.1-31.2 19.8-60.9 19.8-75.5 0-91.9-55.5-91.9-87.9v-90h-29.7c-3.4 0-6.2-2.8-6.2-6.2v-42.5c0-4.5 2.8-8.5 7.1-10 38.8-13.7 50.9-47.5 52.7-73.2.5-6.9 4.1-10.2 10-10.2h44.3c3.4 0 6.2 2.8 6.2 6.2v72h51.9c3.4 0 6.2 2.8 6.2 6.2v51.1c0 3.4-2.8 6.2-6.2 6.2h-52.1V321c0 21.4 14.8 33.5 42.5 22.4 3-1.2 5.6-2 8-1.4 2.2.5 3.6 2.1 4.6 4.9l13.8 40.2c1 3.2 2 6.7-.3 9.1z"],
+ "twitch": [512, 512, [], "f1e8", "M391.17,103.47H352.54v109.7h38.63ZM285,103H246.37V212.75H285ZM120.83,0,24.31,91.42V420.58H140.14V512l96.53-91.42h77.25L487.69,256V0ZM449.07,237.75l-77.22,73.12H294.61l-67.6,64v-64H140.14V36.58H449.07Z"],
+ "twitter": [512, 512, [], "f099", "M459.37 151.716c.325 4.548.325 9.097.325 13.645 0 138.72-105.583 298.558-298.558 298.558-59.452 0-114.68-17.219-161.137-47.106 8.447.974 16.568 1.299 25.34 1.299 49.055 0 94.213-16.568 130.274-44.832-46.132-.975-84.792-31.188-98.112-72.772 6.498.974 12.995 1.624 19.818 1.624 9.421 0 18.843-1.3 27.614-3.573-48.081-9.747-84.143-51.98-84.143-102.985v-1.299c13.969 7.797 30.214 12.67 47.431 13.319-28.264-18.843-46.781-51.005-46.781-87.391 0-19.492 5.197-37.36 14.294-52.954 51.655 63.675 129.3 105.258 216.365 109.807-1.624-7.797-2.599-15.918-2.599-24.04 0-57.828 46.782-104.934 104.934-104.934 30.213 0 57.502 12.67 76.67 33.137 23.715-4.548 46.456-13.32 66.599-25.34-7.798 24.366-24.366 44.833-46.132 57.827 21.117-2.273 41.584-8.122 60.426-16.243-14.292 20.791-32.161 39.308-52.628 54.253z"],
+ "twitter-square": [448, 512, [], "f081", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-48.9 158.8c.2 2.8.2 5.7.2 8.5 0 86.7-66 186.6-186.6 186.6-37.2 0-71.7-10.8-100.7-29.4 5.3.6 10.4.8 15.8.8 30.7 0 58.9-10.4 81.4-28-28.8-.6-53-19.5-61.3-45.5 10.1 1.5 19.2 1.5 29.6-1.2-30-6.1-52.5-32.5-52.5-64.4v-.8c8.7 4.9 18.9 7.9 29.6 8.3a65.447 65.447 0 0 1-29.2-54.6c0-12.2 3.2-23.4 8.9-33.1 32.3 39.8 80.8 65.8 135.2 68.6-9.3-44.5 24-80.6 64-80.6 18.9 0 35.9 7.9 47.9 20.7 14.8-2.8 29-8.3 41.6-15.8-4.9 15.2-15.2 28-28.8 36.1 13.2-1.4 26-5.1 37.8-10.2-8.9 13.1-20.1 24.7-32.9 34z"],
+ "typo3": [448, 512, [], "f42b", "M178.7 78.4c0-24.7 5.4-32.4 13.9-39.4-69.5 8.5-149.3 34-176.3 66.4-5.4 7.7-9.3 20.8-9.3 37.1C7 246 113.8 480 191.1 480c36.3 0 97.3-59.5 146.7-139-7 2.3-11.6 2.3-18.5 2.3-57.2 0-140.6-198.5-140.6-264.9zM301.5 32c-30.1 0-41.7 5.4-41.7 36.3 0 66.4 53.8 198.5 101.7 198.5 26.3 0 78.8-99.7 78.8-182.3 0-40.9-67-52.5-138.8-52.5z"],
+ "uber": [448, 512, [], "f402", "M414.1 32H33.9C15.2 32 0 47.2 0 65.9V446c0 18.8 15.2 34 33.9 34H414c18.7 0 33.9-15.2 33.9-33.9V65.9C448 47.2 432.8 32 414.1 32zM237.6 391.1C163 398.6 96.4 344.2 88.9 269.6h94.4V290c0 3.7 3 6.8 6.8 6.8H258c3.7 0 6.8-3 6.8-6.8v-67.9c0-3.7-3-6.8-6.8-6.8h-67.9c-3.7 0-6.8 3-6.8 6.8v20.4H88.9c7-69.4 65.4-122.2 135.1-122.2 69.7 0 128.1 52.8 135.1 122.2 7.5 74.5-46.9 141.1-121.5 148.6z"],
+ "ubuntu": [496, 512, [], "f7df", "M248 8C111 8 0 119 0 256s111 248 248 248 248-111 248-248S385 8 248 8zm52.7 93c8.8-15.2 28.3-20.5 43.5-11.7 15.3 8.8 20.5 28.3 11.7 43.6-8.8 15.2-28.3 20.5-43.5 11.7-15.3-8.9-20.5-28.4-11.7-43.6zM87.4 287.9c-17.6 0-31.9-14.3-31.9-31.9 0-17.6 14.3-31.9 31.9-31.9 17.6 0 31.9 14.3 31.9 31.9 0 17.6-14.3 31.9-31.9 31.9zm28.1 3.1c22.3-17.9 22.4-51.9 0-69.9 8.6-32.8 29.1-60.7 56.5-79.1l23.7 39.6c-51.5 36.3-51.5 112.5 0 148.8L172 370c-27.4-18.3-47.8-46.3-56.5-79zm228.7 131.7c-15.3 8.8-34.7 3.6-43.5-11.7-8.8-15.3-3.6-34.8 11.7-43.6 15.2-8.8 34.7-3.6 43.5 11.7 8.8 15.3 3.6 34.8-11.7 43.6zm.3-69.5c-26.7-10.3-56.1 6.6-60.5 35-5.2 1.4-48.9 14.3-96.7-9.4l22.5-40.3c57 26.5 123.4-11.7 128.9-74.4l46.1.7c-2.3 34.5-17.3 65.5-40.3 88.4zm-5.9-105.3c-5.4-62-71.3-101.2-128.9-74.4l-22.5-40.3c47.9-23.7 91.5-10.8 96.7-9.4 4.4 28.3 33.8 45.3 60.5 35 23.1 22.9 38 53.9 40.2 88.5l-46 .6z"],
+ "uikit": [448, 512, [], "f403", "M443.9 128v256L218 512 0 384V169.7l87.6 45.1v117l133.5 75.5 135.8-75.5v-151l-101.1-57.6 87.6-53.1L443.9 128zM308.6 49.1L223.8 0l-88.6 54.8 86 47.3 87.4-53z"],
+ "umbraco": [510, 512, [], "f8e8", "M255.35 8C118.36 7.83 7.14 118.72 7 255.68c-.07 137 111 248.2 248 248.27 136.85 0 247.82-110.7 248-247.67S392.34 8.17 255.35 8zm145 266q-1.14 40.68-14 65t-43.51 35q-30.61 10.7-85.45 10.47h-4.6q-54.78.22-85.44-10.47t-43.52-35q-12.85-24.36-14-65a224.81 224.81 0 0 1 0-30.71 418.37 418.37 0 0 1 3.6-43.88c1.88-13.39 3.57-22.58 5.4-32 1-4.88 1.28-6.42 1.82-8.45a5.09 5.09 0 0 1 4.9-3.89h.69l32 5a5.07 5.07 0 0 1 4.16 5 5 5 0 0 1 0 .77l-1.7 8.78q-2.41 13.25-4.84 33.68a380.62 380.62 0 0 0-2.64 42.15q-.28 40.43 8.13 59.83a43.87 43.87 0 0 0 31.31 25.18A243 243 0 0 0 250 340.6h10.25a242.64 242.64 0 0 0 57.27-5.16 43.86 43.86 0 0 0 31.15-25.23q8.53-19.42 8.13-59.78a388 388 0 0 0-2.6-42.15q-2.48-20.38-4.89-33.68l-1.69-8.78a5 5 0 0 1 0-.77 5 5 0 0 1 4.2-5l32-5h.82a5 5 0 0 1 4.9 3.89c.55 2.05.81 3.57 1.83 8.45 1.82 9.62 3.52 18.78 5.39 32a415.71 415.71 0 0 1 3.61 43.88 228.06 228.06 0 0 1-.04 30.73z"],
+ "uncharted": [448, 512, [], "e084", "M171.73,232.813A5.381,5.381,0,0,0,176.7,229.5,48.081,48.081,0,0,1,191.6,204.244c1.243-.828,1.657-2.484,1.657-4.141a4.22,4.22,0,0,0-2.071-3.312L74.429,128.473,148.958,85a9.941,9.941,0,0,0,4.968-8.281,9.108,9.108,0,0,0-4.968-8.281L126.6,55.6a9.748,9.748,0,0,0-9.523,0l-100.2,57.966a9.943,9.943,0,0,0-4.969,8.281V236.954a9.109,9.109,0,0,0,4.969,8.281L39.235,258.07a8.829,8.829,0,0,0,4.968,1.242,9.4,9.4,0,0,0,6.625-2.484,10.8,10.8,0,0,0,2.9-7.039V164.5L169.66,232.4A4.5,4.5,0,0,0,171.73,232.813ZM323.272,377.73a12.478,12.478,0,0,0-4.969,1.242l-74.528,43.062V287.882c0-2.9-2.9-5.8-6.211-4.555a53.036,53.036,0,0,1-28.984.414,4.86,4.86,0,0,0-6.21,4.555V421.619l-74.529-43.061a8.83,8.83,0,0,0-4.969-1.242,9.631,9.631,0,0,0-9.523,9.523v26.085a9.107,9.107,0,0,0,4.969,8.281l100.2,57.553A8.829,8.829,0,0,0,223.486,480a11.027,11.027,0,0,0,4.969-1.242l100.2-57.553a9.941,9.941,0,0,0,4.968-8.281V386.839C332.8,382.285,328.24,377.73,323.272,377.73ZM286.007,78a23,23,0,1,0-23-23A23,23,0,0,0,286.007,78Zm63.627-10.086a23,23,0,1,0,23,23A23,23,0,0,0,349.634,67.914ZM412.816,151.6a23,23,0,1,0-23-23A23,23,0,0,0,412.816,151.6Zm-63.182-9.2a23,23,0,1,0,23,23A23,23,0,0,0,349.634,142.4Zm-63.627,83.244a23,23,0,1,0-23-23A23,23,0,0,0,286.007,225.648Zm-62.074,36.358a23,23,0,1,0-23-23A23,23,0,0,0,223.933,262.006Zm188.883-82.358a23,23,0,1,0,23,23A23,23,0,0,0,412.816,179.648Zm0,72.272a23,23,0,1,0,23,23A23,23,0,0,0,412.816,251.92Z"],
+ "uniregistry": [384, 512, [], "f404", "M192 480c39.5 0 76.2-11.8 106.8-32.2H85.3C115.8 468.2 152.5 480 192 480zm-89.1-193.1v-12.4H0v12.4c0 2.5 0 5 .1 7.4h103.1c-.2-2.4-.3-4.9-.3-7.4zm20.5 57H8.5c2.6 8.5 5.8 16.8 9.6 24.8h138.3c-12.9-5.7-24.1-14.2-33-24.8zm-17.7-34.7H1.3c.9 7.6 2.2 15 3.9 22.3h109.7c-4-6.9-7.2-14.4-9.2-22.3zm-2.8-69.3H0v17.3h102.9zm0-173.2H0v4.9h102.9zm0-34.7H0v2.5h102.9zm0 69.3H0v7.4h102.9zm0 104H0v14.8h102.9zm0-69.3H0v9.9h102.9zm0 34.6H0V183h102.9zm166.2 160.9h109.7c1.8-7.3 3.1-14.7 3.9-22.3H278.3c-2.1 7.9-5.2 15.4-9.2 22.3zm12-185.7H384V136H281.1zm0 37.2H384v-12.4H281.1zm0-74.3H384v-7.4H281.1zm0-76.7v2.5H384V32zm-203 410.9h227.7c11.8-8.7 22.7-18.6 32.2-29.7H44.9c9.6 11 21.4 21 33.2 29.7zm203-371.3H384v-4.9H281.1zm0 148.5H384v-14.8H281.1zM38.8 405.7h305.3c6.7-8.5 12.6-17.6 17.8-27.2H23c5.2 9.6 9.2 18.7 15.8 27.2zm188.8-37.1H367c3.7-8 5.8-16.2 8.5-24.8h-115c-8.8 10.7-20.1 19.2-32.9 24.8zm53.5-81.7c0 2.5-.1 5-.4 7.4h103.1c.1-2.5.2-4.9.2-7.4v-12.4H281.1zm0-29.7H384v-17.3H281.1z"],
+ "unity": [576, 512, [], "e049", "M498.11,206.4,445.31,14.72,248.2,66.08,219,116.14l-59.2-.43L15.54,256,159.82,396.32l59.17-.43,29.24,50,197.08,51.36,52.8-191.62-30-49.63ZM223.77,124.2,374.55,86.51,288,232.33H114.87Zm0,263.63L114.87,279.71H288l86.55,145.81Zm193,14L330.17,256l86.58-145.84L458.56,256Z"],
+ "unsplash": [448, 512, [], "e07c", "M448,230.17V480H0V230.17H141.13V355.09H306.87V230.17ZM306.87,32H141.13V156.91H306.87Z"],
+ "untappd": [640, 512, [], "f405", "M401.3 49.9c-79.8 160.1-84.6 152.5-87.9 173.2l-5.2 32.8c-1.9 12-6.6 23.5-13.7 33.4L145.6 497.1c-7.6 10.6-20.4 16.2-33.4 14.6-40.3-5-77.8-32.2-95.3-68.5-5.7-11.8-4.5-25.8 3.1-36.4l148.9-207.9c7.1-9.9 16.4-18 27.2-23.7l29.3-15.5c18.5-9.8 9.7-11.9 135.6-138.9 1-4.8 1-7.3 3.6-8 3-.7 6.6-1 6.3-4.6l-.4-4.6c-.2-1.9 1.3-3.6 3.2-3.6 4.5-.1 13.2 1.2 25.6 10 12.3 8.9 16.4 16.8 17.7 21.1.6 1.8-.6 3.7-2.4 4.2l-4.5 1.1c-3.4.9-2.5 4.4-2.3 7.4.1 2.8-2.3 3.6-6.5 6.1zM230.1 36.4c3.4.9 2.5 4.4 2.3 7.4-.2 2.7 2.1 3.5 6.4 6 7.9 15.9 15.3 30.5 22.2 44 .7 1.3 2.3 1.5 3.3.5 11.2-12 24.6-26.2 40.5-42.6 1.3-1.4 1.4-3.5.1-4.9-8-8.2-16.5-16.9-25.6-26.1-1-4.7-1-7.3-3.6-8-3-.8-6.6-1-6.3-4.6.3-3.3 1.4-8.1-2.8-8.2-4.5-.1-13.2 1.1-25.6 10-12.3 8.9-16.4 16.8-17.7 21.1-1.4 4.2 3.6 4.6 6.8 5.4zM620 406.7L471.2 198.8c-13.2-18.5-26.6-23.4-56.4-39.1-11.2-5.9-14.2-10.9-30.5-28.9-1-1.1-2.9-.9-3.6.5-46.3 88.8-47.1 82.8-49 94.8-1.7 10.7-1.3 20 .3 29.8 1.9 12 6.6 23.5 13.7 33.4l148.9 207.9c7.6 10.6 20.2 16.2 33.1 14.7 40.3-4.9 78-32 95.7-68.6 5.4-11.9 4.3-25.9-3.4-36.6z"],
+ "ups": [384, 512, [], "f7e0", "M103.2 303c-5.2 3.6-32.6 13.1-32.6-19V180H37.9v102.6c0 74.9 80.2 51.1 97.9 39V180h-32.6zM4 74.82v220.9c0 103.7 74.9 135.2 187.7 184.1 112.4-48.9 187.7-80.2 187.7-184.1V74.82c-116.3-61.6-281.8-49.6-375.4 0zm358.1 220.9c0 86.6-53.2 113.6-170.4 165.3-117.5-51.8-170.5-78.7-170.5-165.3v-126.4c102.3-93.8 231.6-100 340.9-89.8zm-209.6-107.4v212.8h32.7v-68.7c24.4 7.3 71.7-2.6 71.7-78.5 0-97.4-80.7-80.92-104.4-65.6zm32.7 117.3v-100.3c8.4-4.2 38.4-12.7 38.4 49.3 0 67.9-36.4 51.8-38.4 51zm79.1-86.4c.1 47.3 51.6 42.5 52.2 70.4.6 23.5-30.4 23-50.8 4.9v30.1c36.2 21.5 81.9 8.1 83.2-33.5 1.7-51.5-54.1-46.6-53.4-73.2.6-20.3 30.6-20.5 48.5-2.2v-28.4c-28.5-22-79.9-9.2-79.7 31.9z"],
+ "usb": [640, 512, [], "f287", "M641.5 256c0 3.1-1.7 6.1-4.5 7.5L547.9 317c-1.4.8-2.8 1.4-4.5 1.4-1.4 0-3.1-.3-4.5-1.1-2.8-1.7-4.5-4.5-4.5-7.8v-35.6H295.7c25.3 39.6 40.5 106.9 69.6 106.9H392V354c0-5 3.9-8.9 8.9-8.9H490c5 0 8.9 3.9 8.9 8.9v89.1c0 5-3.9 8.9-8.9 8.9h-89.1c-5 0-8.9-3.9-8.9-8.9v-26.7h-26.7c-75.4 0-81.1-142.5-124.7-142.5H140.3c-8.1 30.6-35.9 53.5-69 53.5C32 327.3 0 295.3 0 256s32-71.3 71.3-71.3c33.1 0 61 22.8 69 53.5 39.1 0 43.9 9.5 74.6-60.4C255 88.7 273 95.7 323.8 95.7c7.5-20.9 27-35.6 50.4-35.6 29.5 0 53.5 23.9 53.5 53.5s-23.9 53.5-53.5 53.5c-23.4 0-42.9-14.8-50.4-35.6H294c-29.1 0-44.3 67.4-69.6 106.9h310.1v-35.6c0-3.3 1.7-6.1 4.5-7.8 2.8-1.7 6.4-1.4 8.9.3l89.1 53.5c2.8 1.1 4.5 4.1 4.5 7.2z"],
+ "usps": [576, 512, [], "f7e1", "M460.3 241.7c25.8-41.3 15.2-48.8-11.7-48.8h-27c-.1 0-1.5-1.4-10.9 8-11.2 5.6-37.9 6.3-37.9 8.7 0 4.5 70.3-3.1 88.1 0 9.5 1.5-1.5 20.4-4.4 32-.5 4.5 2.4 2.3 3.8.1zm-112.1 22.6c64-21.3 97.3-23.9 102-26.2 4.4-2.9-4.4-6.6-26.2-5.8-51.7 2.2-137.6 37.1-172.6 53.9l-30.7-93.3h196.6c-2.7-28.2-152.9-22.6-337.9-22.6L27 415.8c196.4-97.3 258.9-130.3 321.2-151.5zM94.7 96c253.3 53.7 330 65.7 332.1 85.2 36.4 0 45.9 0 52.4 6.6 21.1 19.7-14.6 67.7-14.6 67.7-4.4 2.9-406.4 160.2-406.4 160.2h423.1L549 96z"],
+ "ussunnah": [512, 512, [], "f407", "M156.8 285.1l5.7 14.4h-8.2c-1.3-3.2-3.1-7.7-3.8-9.5-2.5-6.3-1.1-8.4 0-10 1.9-2.7 3.2-4.4 3.6-5.2 0 2.2.8 5.7 2.7 10.3zm297.3 18.8c-2.1 13.8-5.7 27.1-10.5 39.7l43 23.4-44.8-18.8c-5.3 13.2-12 25.6-19.9 37.2l34.2 30.2-36.8-26.4c-8.4 11.8-18 22.6-28.7 32.3l24.9 34.7-28.1-31.8c-11 9.6-23.1 18-36.1 25.1l15.7 37.2-19.3-35.3c-13.1 6.8-27 12.1-41.6 15.9l6.7 38.4-10.5-37.4c-14.3 3.4-29.2 5.3-44.5 5.4L256 512l-1.9-38.4c-15.3-.1-30.2-2-44.5-5.3L199 505.6l6.7-38.2c-14.6-3.7-28.6-9.1-41.7-15.8l-19.2 35.1 15.6-37c-13-7-25.2-15.4-36.2-25.1l-27.9 31.6 24.7-34.4c-10.7-9.7-20.4-20.5-28.8-32.3l-36.5 26.2 33.9-29.9c-7.9-11.6-14.6-24.1-20-37.3l-44.4 18.7L67.8 344c-4.8-12.7-8.4-26.1-10.5-39.9l-51 9 50.3-14.2c-1.1-8.5-1.7-17.1-1.7-25.9 0-4.7.2-9.4.5-14.1L0 256l56-2.8c1.3-13.1 3.8-25.8 7.5-38.1L6.4 199l58.9 10.4c4-12 9.1-23.5 15.2-34.4l-55.1-30 58.3 24.6C90 159 97.2 149.2 105.3 140L55.8 96.4l53.9 38.7c8.1-8.6 17-16.5 26.6-23.6l-40-55.6 45.6 51.6c9.5-6.6 19.7-12.3 30.3-17.2l-27.3-64.9 33.8 62.1c10.5-4.4 21.4-7.9 32.7-10.4L199 6.4l19.5 69.2c11-2.1 22.3-3.2 33.8-3.4L256 0l3.6 72.2c11.5.2 22.8 1.4 33.8 3.5L313 6.4l-12.4 70.7c11.3 2.6 22.2 6.1 32.6 10.5l33.9-62.2-27.4 65.1c10.6 4.9 20.7 10.7 30.2 17.2l45.8-51.8-40.1 55.9c9.5 7.1 18.4 15 26.5 23.6l54.2-38.9-49.7 43.9c8 9.1 15.2 18.9 21.5 29.4l58.7-24.7-55.5 30.2c6.1 10.9 11.1 22.3 15.1 34.3l59.3-10.4-57.5 16.2c3.7 12.2 6.2 24.9 7.5 37.9L512 256l-56 2.8c.3 4.6.5 9.3.5 14.1 0 8.7-.6 17.3-1.6 25.8l50.7 14.3-51.5-9.1zm-21.8-31c0-97.5-79-176.5-176.5-176.5s-176.5 79-176.5 176.5 79 176.5 176.5 176.5 176.5-79 176.5-176.5zm-24 0c0 84.3-68.3 152.6-152.6 152.6s-152.6-68.3-152.6-152.6 68.3-152.6 152.6-152.6 152.6 68.3 152.6 152.6zM195 241c0 2.1 1.3 3.8 3.6 5.1 3.3 1.9 6.2 4.6 8.2 8.2 2.8-5.7 4.3-9.5 4.3-11.2 0-2.2-1.1-4.4-3.2-7-2.1-2.5-3.2-5.2-3.3-7.7-6.5 6.8-9.6 10.9-9.6 12.6zm-40.7-19c0 2.1 1.3 3.8 3.6 5.1 3.5 1.9 6.2 4.6 8.2 8.2 2.8-5.7 4.3-9.5 4.3-11.2 0-2.2-1.1-4.4-3.2-7-2.1-2.5-3.2-5.2-3.3-7.7-6.5 6.8-9.6 10.9-9.6 12.6zm-19 0c0 2.1 1.3 3.8 3.6 5.1 3.3 1.9 6.2 4.6 8.2 8.2 2.8-5.7 4.3-9.5 4.3-11.2 0-2.2-1.1-4.4-3.2-7-2.1-2.5-3.2-5.2-3.3-7.7-6.4 6.8-9.6 10.9-9.6 12.6zm204.9 87.9c-8.4-3-8.7-6.8-8.7-15.6V182c-8.2 12.5-14.2 18.6-18 18.6 6.3 14.4 9.5 23.9 9.5 28.3v64.3c0 2.2-2.2 6.5-4.7 6.5h-18c-2.8-7.5-10.2-26.9-15.3-40.3-2 2.5-7.2 9.2-10.7 13.7 2.4 1.6 4.1 3.6 5.2 6.3 2.6 6.7 6.4 16.5 7.9 20.2h-9.2c-3.9-10.4-9.6-25.4-11.8-31.1-2 2.5-7.2 9.2-10.7 13.7 2.4 1.6 4.1 3.6 5.2 6.3.8 2 2.8 7.3 4.3 10.9H256c-1.5-4.1-5.6-14.6-8.4-22-2 2.5-7.2 9.2-10.7 13.7 2.5 1.6 4.3 3.6 5.2 6.3.2.6.5 1.4.6 1.7H225c-4.6-13.9-11.4-27.7-11.4-34.1 0-2.2.3-5.1 1.1-8.2-8.8 10.8-14 15.9-14 25 0 7.5 10.4 28.3 10.4 33.3 0 1.7-.5 3.3-1.4 4.9-9.6-12.7-15.5-20.7-18.8-20.7h-12l-11.2-28c-3.8-9.6-5.7-16-5.7-18.8 0-3.8.5-7.7 1.7-12.2-1 1.3-3.7 4.7-5.5 7.1-.8-2.1-3.1-7.7-4.6-11.5-2.1 2.5-7.5 9.1-11.2 13.6.9 2.3 3.3 8.1 4.9 12.2-2.5 3.3-9.1 11.8-13.6 17.7-4 5.3-5.8 13.3-2.7 21.8 2.5 6.7 2 7.9-1.7 14.1H191c5.5 0 14.3 14 15.5 22 13.2-16 15.4-19.6 16.8-21.6h107c3.9 0 7.2-1.9 9.9-5.8zm20.1-26.6V181.7c-9 12.5-15.9 18.6-20.7 18.6 7.1 14.4 10.7 23.9 10.7 28.3v66.3c0 17.5 8.6 20.4 24 20.4 8.1 0 12.5-.8 13.7-2.7-4.3-1.6-7.6-2.5-9.9-3.3-8.1-3.2-17.8-7.4-17.8-26z"],
+ "vaadin": [448, 512, [], "f408", "M224.5 140.7c1.5-17.6 4.9-52.7 49.8-52.7h98.6c20.7 0 32.1-7.8 32.1-21.6V54.1c0-12.2 9.3-22.1 21.5-22.1S448 41.9 448 54.1v36.5c0 42.9-21.5 62-66.8 62H280.7c-30.1 0-33 14.7-33 27.1 0 1.3-.1 2.5-.2 3.7-.7 12.3-10.9 22.2-23.4 22.2s-22.7-9.8-23.4-22.2c-.1-1.2-.2-2.4-.2-3.7 0-12.3-3-27.1-33-27.1H66.8c-45.3 0-66.8-19.1-66.8-62V54.1C0 41.9 9.4 32 21.6 32s21.5 9.9 21.5 22.1v12.3C43.1 80.2 54.5 88 75.2 88h98.6c44.8 0 48.3 35.1 49.8 52.7h.9zM224 456c11.5 0 21.4-7 25.7-16.3 1.1-1.8 97.1-169.6 98.2-171.4 11.9-19.6-3.2-44.3-27.2-44.3-13.9 0-23.3 6.4-29.8 20.3L224 362l-66.9-117.7c-6.4-13.9-15.9-20.3-29.8-20.3-24 0-39.1 24.6-27.2 44.3 1.1 1.9 97.1 169.6 98.2 171.4 4.3 9.3 14.2 16.3 25.7 16.3z"],
+ "viacoin": [384, 512, [], "f237", "M384 32h-64l-80.7 192h-94.5L64 32H0l48 112H0v48h68.5l13.8 32H0v48h102.8L192 480l89.2-208H384v-48h-82.3l13.8-32H384v-48h-48l48-112zM192 336l-27-64h54l-27 64z"],
+ "viadeo": [448, 512, [], "f2a9", "M276.2 150.5v.7C258.3 98.6 233.6 47.8 205.4 0c43.3 29.2 67 100 70.8 150.5zm32.7 121.7c7.6 18.2 11 37.5 11 57 0 77.7-57.8 141-137.8 139.4l3.8-.3c74.2-46.7 109.3-118.6 109.3-205.1 0-38.1-6.5-75.9-18.9-112 1 11.7 1 23.7 1 35.4 0 91.8-18.1 241.6-116.6 280C95 455.2 49.4 398 49.4 329.2c0-75.6 57.4-142.3 135.4-142.3 16.8 0 33.7 3.1 49.1 9.6 1.7-15.1 6.5-29.9 13.4-43.3-19.9-7.2-41.2-10.7-62.5-10.7-161.5 0-238.7 195.9-129.9 313.7 67.9 74.6 192 73.9 259.8 0 56.6-61.3 60.9-142.4 36.4-201-12.7 8-27.1 13.9-42.2 17zM418.1 11.7c-31 66.5-81.3 47.2-115.8 80.1-12.4 12-20.6 34-20.6 50.5 0 14.1 4.5 27.1 12 38.8 47.4-11 98.3-46 118.2-90.7-.7 5.5-4.8 14.4-7.2 19.2-20.3 35.7-64.6 65.6-99.7 84.9 14.8 14.4 33.7 25.8 55 25.8 79 0 110.1-134.6 58.1-208.6z"],
+ "viadeo-square": [448, 512, [], "f2aa", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM280.7 381.2c-42.4 46.2-120 46.6-162.4 0-68-73.6-19.8-196.1 81.2-196.1 13.3 0 26.6 2.1 39.1 6.7-4.3 8.4-7.3 17.6-8.4 27.1-9.7-4.1-20.2-6-30.7-6-48.8 0-84.6 41.7-84.6 88.9 0 43 28.5 78.7 69.5 85.9 61.5-24 72.9-117.6 72.9-175 0-7.3 0-14.8-.6-22.1-11.2-32.9-26.6-64.6-44.2-94.5 27.1 18.3 41.9 62.5 44.2 94.1v.4c7.7 22.5 11.8 46.2 11.8 70 0 54.1-21.9 99-68.3 128.2l-2.4.2c50 1 86.2-38.6 86.2-87.2 0-12.2-2.1-24.3-6.9-35.7 9.5-1.9 18.5-5.6 26.4-10.5 15.3 36.6 12.6 87.3-22.8 125.6zM309 233.7c-13.3 0-25.1-7.1-34.4-16.1 21.9-12 49.6-30.7 62.3-53 1.5-3 4.1-8.6 4.5-12-12.5 27.9-44.2 49.8-73.9 56.7-4.7-7.3-7.5-15.5-7.5-24.3 0-10.3 5.2-24.1 12.9-31.6 21.6-20.5 53-8.5 72.4-50 32.5 46.2 13.1 130.3-36.3 130.3z"],
+ "viber": [512, 512, [], "f409", "M444 49.9C431.3 38.2 379.9.9 265.3.4c0 0-135.1-8.1-200.9 52.3C27.8 89.3 14.9 143 13.5 209.5c-1.4 66.5-3.1 191.1 117 224.9h.1l-.1 51.6s-.8 20.9 13 25.1c16.6 5.2 26.4-10.7 42.3-27.8 8.7-9.4 20.7-23.2 29.8-33.7 82.2 6.9 145.3-8.9 152.5-11.2 16.6-5.4 110.5-17.4 125.7-142 15.8-128.6-7.6-209.8-49.8-246.5zM457.9 287c-12.9 104-89 110.6-103 115.1-6 1.9-61.5 15.7-131.2 11.2 0 0-52 62.7-68.2 79-5.3 5.3-11.1 4.8-11-5.7 0-6.9.4-85.7.4-85.7-.1 0-.1 0 0 0-101.8-28.2-95.8-134.3-94.7-189.8 1.1-55.5 11.6-101 42.6-131.6 55.7-50.5 170.4-43 170.4-43 96.9.4 143.3 29.6 154.1 39.4 35.7 30.6 53.9 103.8 40.6 211.1zm-139-80.8c.4 8.6-12.5 9.2-12.9.6-1.1-22-11.4-32.7-32.6-33.9-8.6-.5-7.8-13.4.7-12.9 27.9 1.5 43.4 17.5 44.8 46.2zm20.3 11.3c1-42.4-25.5-75.6-75.8-79.3-8.5-.6-7.6-13.5.9-12.9 58 4.2 88.9 44.1 87.8 92.5-.1 8.6-13.1 8.2-12.9-.3zm47 13.4c.1 8.6-12.9 8.7-12.9.1-.6-81.5-54.9-125.9-120.8-126.4-8.5-.1-8.5-12.9 0-12.9 73.7.5 133 51.4 133.7 139.2zM374.9 329v.2c-10.8 19-31 40-51.8 33.3l-.2-.3c-21.1-5.9-70.8-31.5-102.2-56.5-16.2-12.8-31-27.9-42.4-42.4-10.3-12.9-20.7-28.2-30.8-46.6-21.3-38.5-26-55.7-26-55.7-6.7-20.8 14.2-41 33.3-51.8h.2c9.2-4.8 18-3.2 23.9 3.9 0 0 12.4 14.8 17.7 22.1 5 6.8 11.7 17.7 15.2 23.8 6.1 10.9 2.3 22-3.7 26.6l-12 9.6c-6.1 4.9-5.3 14-5.3 14s17.8 67.3 84.3 84.3c0 0 9.1.8 14-5.3l9.6-12c4.6-6 15.7-9.8 26.6-3.7 14.7 8.3 33.4 21.2 45.8 32.9 7 5.7 8.6 14.4 3.8 23.6z"],
+ "vimeo": [448, 512, [], "f40a", "M403.2 32H44.8C20.1 32 0 52.1 0 76.8v358.4C0 459.9 20.1 480 44.8 480h358.4c24.7 0 44.8-20.1 44.8-44.8V76.8c0-24.7-20.1-44.8-44.8-44.8zM377 180.8c-1.4 31.5-23.4 74.7-66 129.4-44 57.2-81.3 85.8-111.7 85.8-18.9 0-34.8-17.4-47.9-52.3-25.5-93.3-36.4-148-57.4-148-2.4 0-10.9 5.1-25.4 15.2l-15.2-19.6c37.3-32.8 72.9-69.2 95.2-71.2 25.2-2.4 40.7 14.8 46.5 51.7 20.7 131.2 29.9 151 67.6 91.6 13.5-21.4 20.8-37.7 21.8-48.9 3.5-33.2-25.9-30.9-45.8-22.4 15.9-52.1 46.3-77.4 91.2-76 33.3.9 49 22.5 47.1 64.7z"],
+ "vimeo-square": [448, 512, [], "f194", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zm-16.2 149.6c-1.4 31.1-23.2 73.8-65.3 127.9-43.5 56.5-80.3 84.8-110.4 84.8-18.7 0-34.4-17.2-47.3-51.6-25.2-92.3-35.9-146.4-56.7-146.4-2.4 0-10.8 5-25.1 15.1L64 192c36.9-32.4 72.1-68.4 94.1-70.4 24.9-2.4 40.2 14.6 46 51.1 20.5 129.6 29.6 149.2 66.8 90.5 13.4-21.2 20.6-37.2 21.5-48.3 3.4-32.8-25.6-30.6-45.2-22.2 15.7-51.5 45.8-76.5 90.1-75.1 32.9 1 48.4 22.4 46.5 64z"],
+ "vimeo-v": [448, 512, [], "f27d", "M447.8 153.6c-2 43.6-32.4 103.3-91.4 179.1-60.9 79.2-112.4 118.8-154.6 118.8-26.1 0-48.2-24.1-66.3-72.3C100.3 250 85.3 174.3 56.2 174.3c-3.4 0-15.1 7.1-35.2 21.1L0 168.2c51.6-45.3 100.9-95.7 131.8-98.5 34.9-3.4 56.3 20.5 64.4 71.5 28.7 181.5 41.4 208.9 93.6 126.7 18.7-29.6 28.8-52.1 30.2-67.6 4.8-45.9-35.8-42.8-63.3-31 22-72.1 64.1-107.1 126.2-105.1 45.8 1.2 67.5 31.1 64.9 89.4z"],
+ "vine": [384, 512, [], "f1ca", "M384 254.7v52.1c-18.4 4.2-36.9 6.1-52.1 6.1-36.9 77.4-103 143.8-125.1 156.2-14 7.9-27.1 8.4-42.7-.8C137 452 34.2 367.7 0 102.7h74.5C93.2 261.8 139 343.4 189.3 404.5c27.9-27.9 54.8-65.1 75.6-106.9-49.8-25.3-80.1-80.9-80.1-145.6 0-65.6 37.7-115.1 102.2-115.1 114.9 0 106.2 127.9 81.6 181.5 0 0-46.4 9.2-63.5-20.5 3.4-11.3 8.2-30.8 8.2-48.5 0-31.3-11.3-46.6-28.4-46.6-18.2 0-30.8 17.1-30.8 50 .1 79.2 59.4 118.7 129.9 101.9z"],
+ "vk": [576, 512, [], "f189", "M545 117.7c3.7-12.5 0-21.7-17.8-21.7h-58.9c-15 0-21.9 7.9-25.6 16.7 0 0-30 73.1-72.4 120.5-13.7 13.7-20 18.1-27.5 18.1-3.7 0-9.4-4.4-9.4-16.9V117.7c0-15-4.2-21.7-16.6-21.7h-92.6c-9.4 0-15 7-15 13.5 0 14.2 21.2 17.5 23.4 57.5v86.8c0 19-3.4 22.5-10.9 22.5-20 0-68.6-73.4-97.4-157.4-5.8-16.3-11.5-22.9-26.6-22.9H38.8c-16.8 0-20.2 7.9-20.2 16.7 0 15.6 20 93.1 93.1 195.5C160.4 378.1 229 416 291.4 416c37.5 0 42.1-8.4 42.1-22.9 0-66.8-3.4-73.1 15.4-73.1 8.7 0 23.7 4.4 58.7 38.1 40 40 46.6 57.9 69 57.9h58.9c16.8 0 25.3-8.4 20.4-25-11.2-34.9-86.9-106.7-90.3-111.5-8.7-11.2-6.2-16.2 0-26.2.1-.1 72-101.3 79.4-135.6z"],
+ "vnv": [640, 512, [], "f40b", "M104.9 352c-34.1 0-46.4-30.4-46.4-30.4L2.6 210.1S-7.8 192 13 192h32.8c10.4 0 13.2 8.7 18.8 18.1l36.7 74.5s5.2 13.1 21.1 13.1 21.1-13.1 21.1-13.1l36.7-74.5c5.6-9.5 8.4-18.1 18.8-18.1h32.8c20.8 0 10.4 18.1 10.4 18.1l-55.8 111.5S174.2 352 140 352h-35.1zm395 0c-34.1 0-46.4-30.4-46.4-30.4l-55.9-111.5S387.2 192 408 192h32.8c10.4 0 13.2 8.7 18.8 18.1l36.7 74.5s5.2 13.1 21.1 13.1 21.1-13.1 21.1-13.1l36.8-74.5c5.6-9.5 8.4-18.1 18.8-18.1H627c20.8 0 10.4 18.1 10.4 18.1l-55.9 111.5S569.3 352 535.1 352h-35.2zM337.6 192c34.1 0 46.4 30.4 46.4 30.4l55.9 111.5s10.4 18.1-10.4 18.1h-32.8c-10.4 0-13.2-8.7-18.8-18.1l-36.7-74.5s-5.2-13.1-21.1-13.1c-15.9 0-21.1 13.1-21.1 13.1l-36.7 74.5c-5.6 9.4-8.4 18.1-18.8 18.1h-32.9c-20.8 0-10.4-18.1-10.4-18.1l55.9-111.5s12.2-30.4 46.4-30.4h35.1z"],
+ "vuejs": [448, 512, [], "f41f", "M356.9 64.3H280l-56 88.6-48-88.6H0L224 448 448 64.3h-91.1zm-301.2 32h53.8L224 294.5 338.4 96.3h53.8L224 384.5 55.7 96.3z"],
+ "watchman-monitoring": [512, 512, [], "e087", "M256,16C123.452,16,16,123.452,16,256S123.452,496,256,496,496,388.548,496,256,388.548,16,256,16ZM121.69,429.122C70.056,388.972,36.741,326.322,36.741,256a218.519,218.519,0,0,1,9.587-64.122l102.9-17.895-.121,10.967-13.943,2.013s-.144,12.5-.144,19.549a12.778,12.778,0,0,0,4.887,10.349l9.468,7.4Zm105.692-283.27,8.48-7.618s6.934-5.38-.143-9.344c-7.188-4.024-39.53-34.5-39.53-34.5-5.348-5.477-8.257-7.347-15.46,0,0,0-32.342,30.474-39.529,34.5-7.078,3.964-.144,9.344-.144,9.344l8.481,7.618-.048,4.369L75.982,131.045c39.644-56.938,105.532-94.3,180.018-94.3A218.754,218.754,0,0,1,420.934,111.77l-193.512,37.7Zm34.063,329.269-33.9-250.857,9.467-7.4a12.778,12.778,0,0,0,4.888-10.349c0-7.044-.144-19.549-.144-19.549l-13.943-2.013-.116-10.474,241.711,31.391A218.872,218.872,0,0,1,475.259,256C475.259,375.074,379.831,472.212,261.445,475.121Z"],
+ "waze": [512, 512, [], "f83f", "M502.17 201.67C516.69 287.53 471.23 369.59 389 409.8c13 34.1-12.4 70.2-48.32 70.2a51.68 51.68 0 0 1-51.57-49c-6.44.19-64.2 0-76.33-.64A51.69 51.69 0 0 1 159 479.92c-33.86-1.36-57.95-34.84-47-67.92-37.21-13.11-72.54-34.87-99.62-70.8-13-17.28-.48-41.8 20.84-41.8 46.31 0 32.22-54.17 43.15-110.26C94.8 95.2 193.12 32 288.09 32c102.48 0 197.15 70.67 214.08 169.67zM373.51 388.28c42-19.18 81.33-56.71 96.29-102.14 40.48-123.09-64.15-228-181.71-228-83.45 0-170.32 55.42-186.07 136-9.53 48.91 5 131.35-68.75 131.35C58.21 358.6 91.6 378.11 127 389.54c24.66-21.8 63.87-15.47 79.83 14.34 14.22 1 79.19 1.18 87.9.82a51.69 51.69 0 0 1 78.78-16.42zM205.12 187.13c0-34.74 50.84-34.75 50.84 0s-50.84 34.74-50.84 0zm116.57 0c0-34.74 50.86-34.75 50.86 0s-50.86 34.75-50.86 0zm-122.61 70.69c-3.44-16.94 22.18-22.18 25.62-5.21l.06.28c4.14 21.42 29.85 44 64.12 43.07 35.68-.94 59.25-22.21 64.11-42.77 4.46-16.05 28.6-10.36 25.47 6-5.23 22.18-31.21 62-91.46 62.9-42.55 0-80.88-27.84-87.9-64.25z"],
+ "weebly": [512, 512, [], "f5cc", "M425.09 65.83c-39.88 0-73.28 25.73-83.66 64.33-18.16-58.06-65.5-64.33-84.95-64.33-19.78 0-66.8 6.28-85.28 64.33-10.38-38.6-43.45-64.33-83.66-64.33C38.59 65.83 0 99.72 0 143.03c0 28.96 4.18 33.27 77.17 233.48 22.37 60.57 67.77 69.35 92.74 69.35 39.23 0 70.04-19.46 85.93-53.98 15.89 34.83 46.69 54.29 85.93 54.29 24.97 0 70.36-9.1 92.74-69.67 76.55-208.65 77.5-205.58 77.5-227.2.63-48.32-36.01-83.47-86.92-83.47zm26.34 114.81l-65.57 176.44c-7.92 21.49-21.22 37.22-46.24 37.22-23.44 0-37.38-12.41-44.03-33.9l-39.28-117.42h-.95L216.08 360.4c-6.96 21.5-20.9 33.6-44.02 33.6-25.02 0-38.33-15.74-46.24-37.22L60.88 181.55c-5.38-14.83-7.92-23.91-7.92-34.5 0-16.34 15.84-29.36 38.33-29.36 18.69 0 31.99 11.8 36.11 29.05l44.03 139.82h.95l44.66-136.79c6.02-19.67 16.47-32.08 38.96-32.08s32.94 12.11 38.96 32.08l44.66 136.79h.95l44.03-139.82c4.12-17.25 17.42-29.05 36.11-29.05 22.17 0 38.33 13.32 38.33 35.71-.32 7.87-4.12 16.04-7.61 27.24z"],
+ "weibo": [512, 512, [], "f18a", "M407 177.6c7.6-24-13.4-46.8-37.4-41.7-22 4.8-28.8-28.1-7.1-32.8 50.1-10.9 92.3 37.1 76.5 84.8-6.8 21.2-38.8 10.8-32-10.3zM214.8 446.7C108.5 446.7 0 395.3 0 310.4c0-44.3 28-95.4 76.3-143.7C176 67 279.5 65.8 249.9 161c-4 13.1 12.3 5.7 12.3 6 79.5-33.6 140.5-16.8 114 51.4-3.7 9.4 1.1 10.9 8.3 13.1 135.7 42.3 34.8 215.2-169.7 215.2zm143.7-146.3c-5.4-55.7-78.5-94-163.4-85.7-84.8 8.6-148.8 60.3-143.4 116s78.5 94 163.4 85.7c84.8-8.6 148.8-60.3 143.4-116zM347.9 35.1c-25.9 5.6-16.8 43.7 8.3 38.3 72.3-15.2 134.8 52.8 111.7 124-7.4 24.2 29.1 37 37.4 12 31.9-99.8-55.1-195.9-157.4-174.3zm-78.5 311c-17.1 38.8-66.8 60-109.1 46.3-40.8-13.1-58-53.4-40.3-89.7 17.7-35.4 63.1-55.4 103.4-45.1 42 10.8 63.1 50.2 46 88.5zm-86.3-30c-12.9-5.4-30 .3-38 12.9-8.3 12.9-4.3 28 8.6 34 13.1 6 30.8.3 39.1-12.9 8-13.1 3.7-28.3-9.7-34zm32.6-13.4c-5.1-1.7-11.4.6-14.3 5.4-2.9 5.1-1.4 10.6 3.7 12.9 5.1 2 11.7-.3 14.6-5.4 2.8-5.2 1.1-10.9-4-12.9z"],
+ "weixin": [576, 512, [], "f1d7", "M385.2 167.6c6.4 0 12.6.3 18.8 1.1C387.4 90.3 303.3 32 207.7 32 100.5 32 13 104.8 13 197.4c0 53.4 29.3 97.5 77.9 131.6l-19.3 58.6 68-34.1c24.4 4.8 43.8 9.7 68.2 9.7 6.2 0 12.1-.3 18.3-.8-4-12.9-6.2-26.6-6.2-40.8-.1-84.9 72.9-154 165.3-154zm-104.5-52.9c14.5 0 24.2 9.7 24.2 24.4 0 14.5-9.7 24.2-24.2 24.2-14.8 0-29.3-9.7-29.3-24.2.1-14.7 14.6-24.4 29.3-24.4zm-136.4 48.6c-14.5 0-29.3-9.7-29.3-24.2 0-14.8 14.8-24.4 29.3-24.4 14.8 0 24.4 9.7 24.4 24.4 0 14.6-9.6 24.2-24.4 24.2zM563 319.4c0-77.9-77.9-141.3-165.4-141.3-92.7 0-165.4 63.4-165.4 141.3S305 460.7 397.6 460.7c19.3 0 38.9-5.1 58.6-9.9l53.4 29.3-14.8-48.6C534 402.1 563 363.2 563 319.4zm-219.1-24.5c-9.7 0-19.3-9.7-19.3-19.6 0-9.7 9.7-19.3 19.3-19.3 14.8 0 24.4 9.7 24.4 19.3 0 10-9.7 19.6-24.4 19.6zm107.1 0c-9.7 0-19.3-9.7-19.3-19.6 0-9.7 9.7-19.3 19.3-19.3 14.5 0 24.4 9.7 24.4 19.3.1 10-9.9 19.6-24.4 19.6z"],
+ "whatsapp": [448, 512, [], "f232", "M380.9 97.1C339 55.1 283.2 32 223.9 32c-122.4 0-222 99.6-222 222 0 39.1 10.2 77.3 29.6 111L0 480l117.7-30.9c32.4 17.7 68.9 27 106.1 27h.1c122.3 0 224.1-99.6 224.1-222 0-59.3-25.2-115-67.1-157zm-157 341.6c-33.2 0-65.7-8.9-94-25.7l-6.7-4-69.8 18.3L72 359.2l-4.4-7c-18.5-29.4-28.2-63.3-28.2-98.2 0-101.7 82.8-184.5 184.6-184.5 49.3 0 95.6 19.2 130.4 54.1 34.8 34.9 56.2 81.2 56.1 130.5 0 101.8-84.9 184.6-186.6 184.6zm101.2-138.2c-5.5-2.8-32.8-16.2-37.9-18-5.1-1.9-8.8-2.8-12.5 2.8-3.7 5.6-14.3 18-17.6 21.8-3.2 3.7-6.5 4.2-12 1.4-32.6-16.3-54-29.1-75.5-66-5.7-9.8 5.7-9.1 16.3-30.3 1.8-3.7.9-6.9-.5-9.7-1.4-2.8-12.5-30.1-17.1-41.2-4.5-10.8-9.1-9.3-12.5-9.5-3.2-.2-6.9-.2-10.6-.2-3.7 0-9.7 1.4-14.8 6.9-5.1 5.6-19.4 19-19.4 46.3 0 27.3 19.9 53.7 22.6 57.4 2.8 3.7 39.1 59.7 94.8 83.8 35.2 15.2 49 16.5 66.6 13.9 10.7-1.6 32.8-13.4 37.4-26.4 4.6-13 4.6-24.1 3.2-26.4-1.3-2.5-5-3.9-10.5-6.6z"],
+ "whatsapp-square": [448, 512, [], "f40c", "M224 122.8c-72.7 0-131.8 59.1-131.9 131.8 0 24.9 7 49.2 20.2 70.1l3.1 5-13.3 48.6 49.9-13.1 4.8 2.9c20.2 12 43.4 18.4 67.1 18.4h.1c72.6 0 133.3-59.1 133.3-131.8 0-35.2-15.2-68.3-40.1-93.2-25-25-58-38.7-93.2-38.7zm77.5 188.4c-3.3 9.3-19.1 17.7-26.7 18.8-12.6 1.9-22.4.9-47.5-9.9-39.7-17.2-65.7-57.2-67.7-59.8-2-2.6-16.2-21.5-16.2-41s10.2-29.1 13.9-33.1c3.6-4 7.9-5 10.6-5 2.6 0 5.3 0 7.6.1 2.4.1 5.7-.9 8.9 6.8 3.3 7.9 11.2 27.4 12.2 29.4s1.7 4.3.3 6.9c-7.6 15.2-15.7 14.6-11.6 21.6 15.3 26.3 30.6 35.4 53.9 47.1 4 2 6.3 1.7 8.6-1 2.3-2.6 9.9-11.6 12.5-15.5 2.6-4 5.3-3.3 8.9-2 3.6 1.3 23.1 10.9 27.1 12.9s6.6 3 7.6 4.6c.9 1.9.9 9.9-2.4 19.1zM400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM223.9 413.2c-26.6 0-52.7-6.7-75.8-19.3L64 416l22.5-82.2c-13.9-24-21.2-51.3-21.2-79.3C65.4 167.1 136.5 96 223.9 96c42.4 0 82.2 16.5 112.2 46.5 29.9 30 47.9 69.8 47.9 112.2 0 87.4-72.7 158.5-160.1 158.5z"],
+ "whmcs": [448, 512, [], "f40d", "M448 161v-21.3l-28.5-8.8-2.2-10.4 20.1-20.7L427 80.4l-29 7.5-7.2-7.5 7.5-28.2-19.1-11.6-21.3 21-10.7-3.2-7-26.4h-22.6l-6.2 26.4-12.1 3.2-19.7-21-19.4 11 8.1 27.7-8.1 8.4-28.5-7.5-11 19.1 20.7 21-2.9 10.4-28.5 7.8-.3 21.7 28.8 7.5 2.4 12.1-20.1 19.9 10.4 18.5 29.6-7.5 7.2 8.6-8.1 26.9 19.9 11.6 19.4-20.4 11.6 2.9 6.7 28.5 22.6.3 6.7-28.8 11.6-3.5 20.7 21.6 20.4-12.1-8.8-28 7.8-8.1 28.8 8.8 10.3-20.1-20.9-18.8 2.2-12.1 29.1-7zm-119.2 45.2c-31.3 0-56.8-25.4-56.8-56.8s25.4-56.8 56.8-56.8 56.8 25.4 56.8 56.8c0 31.5-25.4 56.8-56.8 56.8zm72.3 16.4l46.9 14.5V277l-55.1 13.4-4.1 22.7 38.9 35.3-19.2 37.9-54-16.7-14.6 15.2 16.7 52.5-38.3 22.7-38.9-40.5-21.7 6.6-12.6 54-42.4-.5-12.6-53.6-21.7-5.6-36.4 38.4-37.4-21.7 15.2-50.5-13.7-16.1-55.5 14.1-19.7-34.8 37.9-37.4-4.8-22.8-54-14.1.5-40.9L54 219.9l5.7-19.7-38.9-39.4L41.5 125l53.6 14.1 15.2-15.7-15.2-52 36.4-20.7 36.8 39.4L191 84l11.6-52H245l11.6 45.9L234 72l-6.3-1.7-3.3 5.7-11 19.1-3.3 5.6 4.6 4.6 17.2 17.4-.3 1-23.8 6.5-6.2 1.7-.1 6.4-.2 12.9C153.8 161.6 118 204 118 254.7c0 58.3 47.3 105.7 105.7 105.7 50.5 0 92.7-35.4 103.2-82.8l13.2.2 6.9.1 1.6-6.7 5.6-24 1.9-.6 17.1 17.8 4.7 4.9 5.8-3.4 20.4-12.1 5.8-3.5-2-6.5-6.8-21.2z"],
+ "wikipedia-w": [640, 512, [], "f266", "M640 51.2l-.3 12.2c-28.1.8-45 15.8-55.8 40.3-25 57.8-103.3 240-155.3 358.6H415l-81.9-193.1c-32.5 63.6-68.3 130-99.2 193.1-.3.3-15 0-15-.3C172 352.3 122.8 243.4 75.8 133.4 64.4 106.7 26.4 63.4.2 63.7c0-3.1-.3-10-.3-14.2h161.9v13.9c-19.2 1.1-52.8 13.3-43.3 34.2 21.9 49.7 103.6 240.3 125.6 288.6 15-29.7 57.8-109.2 75.3-142.8-13.9-28.3-58.6-133.9-72.8-160-9.7-17.8-36.1-19.4-55.8-19.7V49.8l142.5.3v13.1c-19.4.6-38.1 7.8-29.4 26.1 18.9 40 30.6 68.1 48.1 104.7 5.6-10.8 34.7-69.4 48.1-100.8 8.9-20.6-3.9-28.6-38.6-29.4.3-3.6 0-10.3.3-13.6 44.4-.3 111.1-.3 123.1-.6v13.6c-22.5.8-45.8 12.8-58.1 31.7l-59.2 122.8c6.4 16.1 63.3 142.8 69.2 156.7L559.2 91.8c-8.6-23.1-36.4-28.1-47.2-28.3V49.6l127.8 1.1.2.5z"],
+ "windows": [448, 512, [], "f17a", "M0 93.7l183.6-25.3v177.4H0V93.7zm0 324.6l183.6 25.3V268.4H0v149.9zm203.8 28L448 480V268.4H203.8v177.9zm0-380.6v180.1H448V32L203.8 65.7z"],
+ "wix": [640, 512, [], "f5cf", "M393.38 131.69c0 13.03 2.08 32.69-28.68 43.83-9.52 3.45-15.95 9.66-15.95 9.66 0-31 4.72-42.22 17.4-48.86 9.75-5.11 27.23-4.63 27.23-4.63zm-115.8 35.54l-34.24 132.66-28.48-108.57c-7.69-31.99-20.81-48.53-48.43-48.53-27.37 0-40.66 16.18-48.43 48.53L89.52 299.89 55.28 167.23C49.73 140.51 23.86 128.96 0 131.96l65.57 247.93s21.63 1.56 32.46-3.96c14.22-7.25 20.98-12.84 29.59-46.57 7.67-30.07 29.11-118.41 31.12-124.7 4.76-14.94 11.09-13.81 15.4 0 1.97 6.3 23.45 94.63 31.12 124.7 8.6 33.73 15.37 39.32 29.59 46.57 10.82 5.52 32.46 3.96 32.46 3.96l65.57-247.93c-24.42-3.07-49.82 8.93-55.3 35.27zm115.78 5.21s-4.1 6.34-13.46 11.57c-6.01 3.36-11.78 5.64-17.97 8.61-15.14 7.26-13.18 13.95-13.18 35.2v152.07s16.55 2.09 27.37-3.43c13.93-7.1 17.13-13.95 17.26-44.78V181.41l-.02.01v-8.98zm163.44 84.08L640 132.78s-35.11-5.98-52.5 9.85c-13.3 12.1-24.41 29.55-54.18 72.47-.47.73-6.25 10.54-13.07 0-29.29-42.23-40.8-60.29-54.18-72.47-17.39-15.83-52.5-9.85-52.5-9.85l83.2 123.74-82.97 123.36s36.57 4.62 53.95-11.21c11.49-10.46 17.58-20.37 52.51-70.72 6.81-10.52 12.57-.77 13.07 0 29.4 42.38 39.23 58.06 53.14 70.72 17.39 15.83 53.32 11.21 53.32 11.21L556.8 256.52z"],
+ "wizards-of-the-coast": [640, 512, [], "f730", "M219.19 345.69c-1.9 1.38-11.07 8.44-.26 23.57 4.64 6.42 14.11 12.79 21.73 6.55 6.5-4.88 7.35-12.92.26-23.04-5.47-7.76-14.28-12.88-21.73-7.08zm336.75 75.94c-.34 1.7-.55 1.67.79 0 2.09-4.19 4.19-10.21 4.98-19.9 3.14-38.49-40.33-71.49-101.34-78.03-54.73-6.02-124.38 9.17-188.8 60.49l-.26 1.57c2.62 4.98 4.98 10.74 3.4 21.21l.79.26c63.89-58.4 131.19-77.25 184.35-73.85 58.4 3.67 100.03 34.04 100.03 68.08-.01 9.96-2.63 15.72-3.94 20.17zM392.28 240.42c.79 7.07 4.19 10.21 9.17 10.47 5.5.26 9.43-2.62 10.47-6.55.79-3.4 2.09-29.85 2.09-29.85s-11.26 6.55-14.93 10.47c-3.66 3.68-7.33 8.39-6.8 15.46zm-50.02-151.1C137.75 89.32 13.1 226.8.79 241.2c-1.05.52-1.31.79.79 1.31 60.49 16.5 155.81 81.18 196.13 202.16l1.05.26c55.25-69.92 140.88-128.05 236.99-128.05 80.92 0 130.15 42.16 130.15 80.39 0 18.33-6.55 33.52-22.26 46.35 0 .96-.2.79.79.79 14.66-10.74 27.5-28.8 27.5-48.18 0-22.78-12.05-38.23-12.05-38.23 7.07 7.07 10.74 16.24 10.74 16.24 5.76-40.85 26.97-62.32 26.97-62.32-2.36-9.69-6.81-17.81-6.81-17.81 7.59 8.12 14.4 27.5 14.4 41.37 0 10.47-3.4 22.78-12.57 31.95l.26.52c8.12-4.98 16.5-16.76 16.5-37.97 0-15.71-4.71-25.92-4.71-25.92 5.76-5.24 11.26-9.17 15.97-11.78.79 3.4 2.09 9.69 2.36 14.93 0 1.05.79 1.83 1.05 0 .79-5.76-.26-16.24-.26-16.5 6.02-3.14 9.69-4.45 9.69-4.45C617.74 176 489.43 89.32 342.26 89.32zm-99.24 289.62c-11.06 8.99-24.2 4.08-30.64-4.19-7.45-9.58-6.76-24.09 4.19-32.47 14.85-11.35 27.08-.49 31.16 5.5.28.39 12.13 16.57-4.71 31.16zm2.09-136.43l9.43-17.81 11.78 70.96-12.57 6.02-24.62-28.8 14.14-26.71 3.67 4.45-1.83-8.11zm18.59 117.58l-.26-.26c2.05-4.1-2.5-6.61-17.54-31.69-1.31-2.36-3.14-2.88-4.45-2.62l-.26-.52c7.86-5.76 15.45-10.21 25.4-15.71l.52.26c1.31 1.83 2.09 2.88 3.4 4.71l-.26.52c-1.05-.26-2.36-.79-5.24.26-2.09.79-7.86 3.67-12.31 7.59v1.31c1.57 2.36 3.93 6.55 5.76 9.69h.26c10.05-6.28 7.56-4.55 11.52-7.86h.26c.52 1.83.52 1.83 1.83 5.5l-.26.26c-3.06.61-4.65.34-11.52 5.5v.26c9.46 17.02 11.01 16.75 12.57 15.97l.26.26c-2.34 1.59-6.27 4.21-9.68 6.57zm55.26-32.47c-3.14 1.57-6.02 2.88-9.95 4.98l-.26-.26c1.29-2.59 1.16-2.71-11.78-32.47l-.26-.26c-.15 0-8.9 3.65-9.95 7.33h-.52l-1.05-5.76.26-.52c7.29-4.56 25.53-11.64 27.76-12.57l.52.26 3.14 4.98-.26.52c-3.53-1.76-7.35.76-12.31 2.62v.26c12.31 32.01 12.67 30.64 14.66 30.64v.25zm44.77-16.5c-4.19 1.05-5.24 1.31-9.69 2.88l-.26-.26.52-4.45c-1.05-3.4-3.14-11.52-3.67-13.62l-.26-.26c-3.4.79-8.9 2.62-12.83 3.93l-.26.26c.79 2.62 3.14 9.95 4.19 13.88.79 2.36 1.83 2.88 2.88 3.14v.52c-3.67 1.05-7.07 2.62-10.21 3.93l-.26-.26c1.05-1.31 1.05-2.88.26-4.98-1.05-3.14-8.12-23.83-9.17-27.23-.52-1.83-1.57-3.14-2.62-3.14v-.52c3.14-1.05 6.02-2.09 10.74-3.4l.26.26-.26 4.71c1.31 3.93 2.36 7.59 3.14 9.69h.26c3.93-1.31 9.43-2.88 12.83-3.93l.26-.26-2.62-9.43c-.52-1.83-1.05-3.4-2.62-3.93v-.26c4.45-1.05 7.33-1.83 10.74-2.36l.26.26c-1.05 1.31-1.05 2.88-.52 4.45 1.57 6.28 4.71 20.43 6.28 26.45.54 2.62 1.85 3.41 2.63 3.93zm32.21-6.81l-.26.26c-4.71.52-14.14 2.36-22.52 4.19l-.26-.26.79-4.19c-1.57-7.86-3.4-18.59-4.98-26.19-.26-1.83-.79-2.88-2.62-3.67l.79-.52c9.17-1.57 20.16-2.36 24.88-2.62l.26.26c.52 2.36.79 3.14 1.57 5.5l-.26.26c-1.14-1.14-3.34-3.2-16.24-.79l-.26.26c.26 1.57 1.05 6.55 1.57 9.95l.26.26c9.52-1.68 4.76-.06 10.74-2.36h.26c0 1.57-.26 1.83-.26 5.24h-.26c-4.81-1.03-2.15-.9-10.21 0l-.26.26c.26 2.09 1.57 9.43 2.09 12.57l.26.26c1.15.38 14.21-.65 16.24-4.71h.26c-.53 2.38-1.05 4.21-1.58 6.04zm10.74-44.51c-4.45 2.36-8.12 2.88-11 2.88-.25.02-11.41 1.09-17.54-9.95-6.74-10.79-.98-25.2 5.5-31.69 8.8-8.12 23.35-10.1 28.54-17.02 8.03-10.33-13.04-22.31-29.59-5.76l-2.62-2.88 5.24-16.24c25.59-1.57 45.2-3.04 50.02 16.24.79 3.14 0 9.43-.26 12.05 0 2.62-1.83 18.85-2.09 23.04-.52 4.19-.79 18.33-.79 20.69.26 2.36.52 4.19 1.57 5.5 1.57 1.83 5.76 1.83 5.76 1.83l-.79 4.71c-11.82-1.07-10.28-.59-20.43-1.05-3.22-5.15-2.23-3.28-4.19-7.86 0 .01-4.19 3.94-7.33 5.51zm37.18 21.21c-6.35-10.58-19.82-7.16-21.73 5.5-2.63 17.08 14.3 19.79 20.69 10.21l.26.26c-.52 1.83-1.83 6.02-1.83 6.28l-.52.52c-10.3 6.87-28.5-2.5-25.66-18.59 1.94-10.87 14.44-18.93 28.8-9.95l.26.52c0 1.06-.27 3.41-.27 5.25zm5.77-87.73v-6.55c.69 0 19.65 3.28 27.76 7.33l-1.57 17.54s10.21-9.43 15.45-10.74c5.24-1.57 14.93 7.33 14.93 7.33l-11.26 11.26c-12.07-6.35-19.59-.08-20.69.79-5.29 38.72-8.6 42.17 4.45 46.09l-.52 4.71c-17.55-4.29-18.53-4.5-36.92-7.33l.79-4.71c7.25 0 7.48-5.32 7.59-6.81 0 0 4.98-53.16 4.98-55.25-.02-2.87-4.99-3.66-4.99-3.66zm10.99 114.44c-8.12-2.09-14.14-11-10.74-20.69 3.14-9.43 12.31-12.31 18.85-10.21 9.17 2.62 12.83 11.78 10.74 19.38-2.61 8.9-9.42 13.87-18.85 11.52zm42.16 9.69c-2.36-.52-7.07-2.36-8.64-2.88v-.26l1.57-1.83c.59-8.24.59-7.27.26-7.59-4.82-1.81-6.66-2.36-7.07-2.36-1.31 1.83-2.88 4.45-3.67 5.5l-.79 3.4v.26c-1.31-.26-3.93-1.31-6.02-1.57v-.26l2.62-1.83c3.4-4.71 9.95-14.14 13.88-20.16v-2.09l.52-.26c2.09.79 5.5 2.09 7.59 2.88.48.48.18-1.87-1.05 25.14-.24 1.81.02 2.6.8 3.91zm-4.71-89.82c11.25-18.27 30.76-16.19 34.04-3.4L539.7 198c2.34-6.25-2.82-9.9-4.45-11.26l1.83-3.67c12.22 10.37 16.38 13.97 22.52 20.43-25.91 73.07-30.76 80.81-24.62 84.32l-1.83 4.45c-6.37-3.35-8.9-4.42-17.81-8.64l2.09-6.81c-.26-.26-3.93 3.93-9.69 3.67-19.06-1.3-22.89-31.75-9.67-52.9zm29.33 79.34c0-5.71-6.34-7.89-7.86-5.24-1.31 2.09 1.05 4.98 2.88 8.38 1.57 2.62 2.62 6.28 1.05 9.43-2.64 6.34-12.4 5.31-15.45-.79 0-.7-.27.09 1.83-4.71l.79-.26c-.57 5.66 6.06 9.61 8.38 4.98 1.05-2.09-.52-5.5-2.09-8.38-1.57-2.62-3.67-6.28-1.83-9.69 2.72-5.06 11.25-4.47 14.66 2.36v.52l-2.36 3.4zm21.21 13.36c-1.96-3.27-.91-2.14-4.45-4.71h-.26c-2.36 4.19-5.76 10.47-8.64 16.24-1.31 2.36-1.05 3.4-.79 3.93l-.26.26-5.76-4.45.26-.26 2.09-1.31c3.14-5.76 6.55-12.05 9.17-17.02v-.26c-2.64-1.98-1.22-1.51-6.02-1.83v-.26l3.14-3.4h.26c3.67 2.36 9.95 6.81 12.31 8.9l.26.26-1.31 3.91zm27.23-44.26l-2.88-2.88c.79-2.36 1.83-4.98 2.09-7.59.75-9.74-11.52-11.84-11.52-4.98 0 4.98 7.86 19.38 7.86 27.76 0 10.21-5.76 15.71-13.88 16.5-8.38.79-20.16-10.47-20.16-10.47l4.98-14.4 2.88 2.09c-2.97 17.8 17.68 20.37 13.35 5.24-1.06-4.02-18.75-34.2 2.09-38.23 13.62-2.36 23.04 16.5 23.04 16.5l-7.85 10.46zm35.62-10.21c-11-30.38-60.49-127.53-191.95-129.62-53.42-1.05-94.27 15.45-132.76 37.97l85.63-9.17-91.39 20.69 25.14 19.64-3.93-16.5c7.5-1.71 39.15-8.45 66.77-8.9l-22.26 80.39c13.61-.7 18.97-8.98 19.64-22.78l4.98-1.05.26 26.71c-22.46 3.21-37.3 6.69-49.49 9.95l13.09-43.21-61.54-36.66 2.36 8.12 10.21 4.98c6.28 18.59 19.38 56.56 20.43 58.66 1.95 4.28 3.16 5.78 12.05 4.45l1.05 4.98c-16.08 4.86-23.66 7.61-39.02 14.4l-2.36-4.71c4.4-2.94 8.73-3.94 5.5-12.83-23.7-62.5-21.48-58.14-22.78-59.44l2.36-4.45 33.52 67.3c-3.84-11.87 1.68 1.69-32.99-78.82l-41.9 88.51 4.71-13.88-35.88-42.16 27.76 93.48-11.78 8.38C95 228.58 101.05 231.87 93.23 231.52c-5.5-.26-13.62 5.5-13.62 5.5L74.63 231c30.56-23.53 31.62-24.33 58.4-42.68l4.19 7.07s-5.76 4.19-7.86 7.07c-5.9 9.28 1.67 13.28 61.8 75.68l-18.85-58.92 39.8-10.21 25.66 30.64 4.45-12.31-4.98-24.62 13.09-3.4.52 3.14 3.67-10.47-94.27 29.33 11.26-4.98-13.62-42.42 17.28-9.17 30.11 36.14 28.54-13.09c-1.41-7.47-2.47-14.5-4.71-19.64l17.28 13.88 4.71-2.09-59.18-42.68 23.08 11.5c18.98-6.07 25.23-7.47 32.21-9.69l2.62 11c-12.55 12.55 1.43 16.82 6.55 19.38l-13.62-61.01 12.05 28.28c4.19-1.31 7.33-2.09 7.33-2.09l2.62 8.64s-3.14 1.05-6.28 2.09l8.9 20.95 33.78-65.73-20.69 61.01c42.42-24.09 81.44-36.66 131.98-35.88 67.04 1.05 167.33 40.85 199.8 139.83.78 2.1-.01 2.63-.79.27zM203.48 152.43s1.83-.52 4.19-1.31l9.43 7.59c-.4 0-3.44-.25-11.26 2.36l-2.36-8.64zm143.76 38.5c-1.57-.6-26.46-4.81-33.26 20.69l21.73 17.02 11.53-37.71zM318.43 67.07c-58.4 0-106.05 12.05-114.96 14.4v.79c8.38 2.09 14.4 4.19 21.21 11.78l1.57.26c6.55-1.83 48.97-13.88 110.24-13.88 180.16 0 301.67 116.79 301.67 223.37v9.95c0 1.31.79 2.62 1.05.52.52-2.09.79-8.64.79-19.64.26-83.79-96.63-227.55-321.57-227.55zm211.06 169.68c1.31-5.76 0-12.31-7.33-13.09-9.62-1.13-16.14 23.79-17.02 33.52-.79 5.5-1.31 14.93 6.02 14.93 4.68-.01 9.72-.91 18.33-35.36zm-61.53 42.95c-2.62-.79-9.43-.79-12.57 10.47-1.83 6.81.52 13.35 6.02 14.66 3.67 1.05 8.9.52 11.78-10.74 2.62-9.94-1.83-13.61-5.23-14.39zM491 300.65c1.83.52 3.14 1.05 5.76 1.83 0-1.83.52-8.38.79-12.05-1.05 1.31-5.5 8.12-6.55 9.95v.27z"],
+ "wodu": [640, 512, [], "e088", "M178.414 339.706H141.1L112.166 223.475h-.478L83.228 339.706H45.2L0 168.946H37.548L64.574 285.177h.478L94.707 168.946h35.157l29.178 117.667h.479L187.5 168.946h36.831zM271.4 212.713c38.984 0 64.1 25.828 64.1 65.291 0 39.222-25.111 65.05-64.1 65.05-38.743 0-63.855-25.828-63.855-65.05C207.547 238.541 232.659 212.713 271.4 212.713zm0 104.753c23.2 0 30.133-19.852 30.133-39.462 0-19.852-6.934-39.7-30.133-39.7-27.7 0-29.894 19.85-29.894 39.7C241.508 297.614 248.443 317.466 271.4 317.466zM435.084 323.922h-.478c-7.893 13.392-21.765 19.132-37.548 19.132-37.31 0-55.485-32.045-55.485-66.246 0-33.243 18.415-64.095 54.767-64.095 14.589 0 28.938 6.218 36.831 18.416h.24V168.946h33.96v170.76H435.084zM405.428 238.3c-22.24 0-29.894 19.134-29.894 39.463 0 19.371 8.848 39.7 29.894 39.7 22.482 0 29.178-19.613 29.178-39.94C434.606 257.436 427.432 238.3 405.428 238.3zM592.96 339.706H560.673V322.487h-.718c-8.609 13.87-23.436 20.567-37.786 20.567-36.113 0-45.2-20.328-45.2-50.941V216.061h33.959V285.9c0 20.329 5.979 30.372 21.765 30.372 18.415 0 26.306-10.283 26.306-35.393V216.061H592.96zM602.453 302.876H640v36.83H602.453z"],
+ "wolf-pack-battalion": [512, 512, [], "f514", "M267.73 471.53l10.56 15.84 5.28-12.32 5.28 7V512c21.06-7.92 21.11-66.86 25.51-97.21 4.62-31.89-.88-92.81 81.37-149.11-8.88-23.61-12-49.43-2.64-80.05C421 189 447 196.21 456.43 239.73l-30.35 8.36c11.15 23 17 46.76 13.2 72.14L412 313.18l-6.16 33.43-18.47-7-8.8 33.39-19.35-7 26.39 21.11 8.8-28.15L419 364.2l7-35.63 26.39 14.52c.25-20 7-58.06-8.8-84.45l26.39 5.28c4-22.07-2.38-39.21-7.92-56.74l22.43 9.68c-.44-25.07-29.94-56.79-61.58-58.5-20.22-1.09-56.74-25.17-54.1-51.9 2-19.87 17.45-42.62 43.11-49.7-44 36.51-9.68 67.3 5.28 73.46 4.4-11.44 17.54-69.08 0-130.2-40.39 22.87-89.65 65.1-93.2 147.79l-58 38.71-3.52 93.25L369.78 220l7 7-17.59 3.52-44 38.71-15.84-5.28-28.1 49.25-3.52 119.64 21.11 15.84-32.55 15.84-32.55-15.84 21.11-15.84-3.52-119.64-28.15-49.26-15.84 5.28-44-38.71-17.58-3.51 7-7 107.33 59.82-3.52-93.25-58.06-38.71C185 65.1 135.77 22.87 95.3 0c-17.54 61.12-4.4 118.76 0 130.2 15-6.16 49.26-36.95 5.28-73.46 25.66 7.08 41.15 29.83 43.11 49.7 2.63 26.74-33.88 50.81-54.1 51.9-31.65 1.72-61.15 33.44-61.59 58.51l22.43-9.68c-5.54 17.53-11.91 34.67-7.92 56.74l26.39-5.28c-15.76 26.39-9.05 64.43-8.8 84.45l26.39-14.52 7 35.63 24.63-5.28 8.8 28.15L153.35 366 134 373l-8.8-33.43-18.47 7-6.16-33.43-27.27 7c-3.82-25.38 2-49.1 13.2-72.14l-30.35-8.36c9.4-43.52 35.47-50.77 63.34-54.1 9.36 30.62 6.24 56.45-2.64 80.05 82.25 56.3 76.75 117.23 81.37 149.11 4.4 30.35 4.45 89.29 25.51 97.21v-29.83l5.28-7 5.28 12.32 10.56-15.84 11.44 21.11 11.43-21.1zm79.17-95L331.06 366c7.47-4.36 13.76-8.42 19.35-12.32-.6 7.22-.27 13.84-3.51 22.84zm28.15-49.26c-.4 10.94-.9 21.66-1.76 31.67-7.85-1.86-15.57-3.8-21.11-7 8.24-7.94 15.55-16.32 22.87-24.68zm24.63 5.28c0-13.43-2.05-24.21-5.28-33.43a235 235 0 0 1-18.47 27.27zm3.52-80.94c19.44 12.81 27.8 33.66 29.91 56.3-12.32-4.53-24.63-9.31-36.95-10.56 5.06-12 6.65-28.14 7-45.74zm-1.76-45.74c.81 14.3 1.84 28.82 1.76 42.23 19.22-8.11 29.78-9.72 44-14.08-10.61-18.96-27.2-25.53-45.76-28.16zM165.68 376.52L181.52 366c-7.47-4.36-13.76-8.42-19.35-12.32.6 7.26.27 13.88 3.51 22.88zm-28.15-49.26c.4 10.94.9 21.66 1.76 31.67 7.85-1.86 15.57-3.8 21.11-7-8.24-7.93-15.55-16.31-22.87-24.67zm-24.64 5.28c0-13.43 2-24.21 5.28-33.43a235 235 0 0 0 18.47 27.27zm-3.52-80.94c-19.44 12.81-27.8 33.66-29.91 56.3 12.32-4.53 24.63-9.31 37-10.56-5-12-6.65-28.14-7-45.74zm1.76-45.74c-.81 14.3-1.84 28.82-1.76 42.23-19.22-8.11-29.78-9.72-44-14.08 10.63-18.95 27.23-25.52 45.76-28.15z"],
+ "wordpress": [512, 512, [], "f19a", "M61.7 169.4l101.5 278C92.2 413 43.3 340.2 43.3 256c0-30.9 6.6-60.1 18.4-86.6zm337.9 75.9c0-26.3-9.4-44.5-17.5-58.7-10.8-17.5-20.9-32.4-20.9-49.9 0-19.6 14.8-37.8 35.7-37.8.9 0 1.8.1 2.8.2-37.9-34.7-88.3-55.9-143.7-55.9-74.3 0-139.7 38.1-177.8 95.9 5 .2 9.7.3 13.7.3 22.2 0 56.7-2.7 56.7-2.7 11.5-.7 12.8 16.2 1.4 17.5 0 0-11.5 1.3-24.3 2l77.5 230.4L249.8 247l-33.1-90.8c-11.5-.7-22.3-2-22.3-2-11.5-.7-10.1-18.2 1.3-17.5 0 0 35.1 2.7 56 2.7 22.2 0 56.7-2.7 56.7-2.7 11.5-.7 12.8 16.2 1.4 17.5 0 0-11.5 1.3-24.3 2l76.9 228.7 21.2-70.9c9-29.4 16-50.5 16-68.7zm-139.9 29.3l-63.8 185.5c19.1 5.6 39.2 8.7 60.1 8.7 24.8 0 48.5-4.3 70.6-12.1-.6-.9-1.1-1.9-1.5-2.9l-65.4-179.2zm183-120.7c.9 6.8 1.4 14 1.4 21.9 0 21.6-4 45.8-16.2 76.2l-65 187.9C426.2 403 468.7 334.5 468.7 256c0-37-9.4-71.8-26-102.1zM504 256c0 136.8-111.3 248-248 248C119.2 504 8 392.7 8 256 8 119.2 119.2 8 256 8c136.7 0 248 111.2 248 248zm-11.4 0c0-130.5-106.2-236.6-236.6-236.6C125.5 19.4 19.4 125.5 19.4 256S125.6 492.6 256 492.6c130.5 0 236.6-106.1 236.6-236.6z"],
+ "wordpress-simple": [512, 512, [], "f411", "M256 8C119.3 8 8 119.2 8 256c0 136.7 111.3 248 248 248s248-111.3 248-248C504 119.2 392.7 8 256 8zM33 256c0-32.3 6.9-63 19.3-90.7l106.4 291.4C84.3 420.5 33 344.2 33 256zm223 223c-21.9 0-43-3.2-63-9.1l66.9-194.4 68.5 187.8c.5 1.1 1 2.1 1.6 3.1-23.1 8.1-48 12.6-74 12.6zm30.7-327.5c13.4-.7 25.5-2.1 25.5-2.1 12-1.4 10.6-19.1-1.4-18.4 0 0-36.1 2.8-59.4 2.8-21.9 0-58.7-2.8-58.7-2.8-12-.7-13.4 17.7-1.4 18.4 0 0 11.4 1.4 23.4 2.1l34.7 95.2L200.6 393l-81.2-241.5c13.4-.7 25.5-2.1 25.5-2.1 12-1.4 10.6-19.1-1.4-18.4 0 0-36.1 2.8-59.4 2.8-4.2 0-9.1-.1-14.4-.3C109.6 73 178.1 33 256 33c58 0 110.9 22.2 150.6 58.5-1-.1-1.9-.2-2.9-.2-21.9 0-37.4 19.1-37.4 39.6 0 18.4 10.6 33.9 21.9 52.3 8.5 14.8 18.4 33.9 18.4 61.5 0 19.1-7.3 41.2-17 72.1l-22.2 74.3-80.7-239.6zm81.4 297.2l68.1-196.9c12.7-31.8 17-57.2 17-79.9 0-8.2-.5-15.8-1.5-22.9 17.4 31.8 27.3 68.2 27.3 107 0 82.3-44.6 154.1-110.9 192.7z"],
+ "wpbeginner": [512, 512, [], "f297", "M462.799 322.374C519.01 386.682 466.961 480 370.944 480c-39.602 0-78.824-17.687-100.142-50.04-6.887.356-22.702.356-29.59 0C219.848 462.381 180.588 480 141.069 480c-95.49 0-148.348-92.996-91.855-157.626C-29.925 190.523 80.479 32 256.006 32c175.632 0 285.87 158.626 206.793 290.374zm-339.647-82.972h41.529v-58.075h-41.529v58.075zm217.18 86.072v-23.839c-60.506 20.915-132.355 9.198-187.589-33.971l.246 24.897c51.101 46.367 131.746 57.875 187.343 32.913zm-150.753-86.072h166.058v-58.075H189.579v58.075z"],
+ "wpexplorer": [512, 512, [], "f2de", "M512 256c0 141.2-114.7 256-256 256C114.8 512 0 397.3 0 256S114.7 0 256 0s256 114.7 256 256zm-32 0c0-123.2-100.3-224-224-224C132.5 32 32 132.5 32 256s100.5 224 224 224 224-100.5 224-224zM160.9 124.6l86.9 37.1-37.1 86.9-86.9-37.1 37.1-86.9zm110 169.1l46.6 94h-14.6l-50-100-48.9 100h-14l51.1-106.9-22.3-9.4 6-14 68.6 29.1-6 14.3-16.5-7.1zm-11.8-116.3l68.6 29.4-29.4 68.3L230 246l29.1-68.6zm80.3 42.9l54.6 23.1-23.4 54.3-54.3-23.1 23.1-54.3z"],
+ "wpforms": [448, 512, [], "f298", "M448 75.2v361.7c0 24.3-19 43.2-43.2 43.2H43.2C19.3 480 0 461.4 0 436.8V75.2C0 51.1 18.8 32 43.2 32h361.7c24 0 43.1 18.8 43.1 43.2zm-37.3 361.6V75.2c0-3-2.6-5.8-5.8-5.8h-9.3L285.3 144 224 94.1 162.8 144 52.5 69.3h-9.3c-3.2 0-5.8 2.8-5.8 5.8v361.7c0 3 2.6 5.8 5.8 5.8h361.7c3.2.1 5.8-2.7 5.8-5.8zM150.2 186v37H76.7v-37h73.5zm0 74.4v37.3H76.7v-37.3h73.5zm11.1-147.3l54-43.7H96.8l64.5 43.7zm210 72.9v37h-196v-37h196zm0 74.4v37.3h-196v-37.3h196zm-84.6-147.3l64.5-43.7H232.8l53.9 43.7zM371.3 335v37.3h-99.4V335h99.4z"],
+ "wpressr": [496, 512, [], "f3e4", "M248 8C111.03 8 0 119.03 0 256s111.03 248 248 248 248-111.03 248-248S384.97 8 248 8zm171.33 158.6c-15.18 34.51-30.37 69.02-45.63 103.5-2.44 5.51-6.89 8.24-12.97 8.24-23.02-.01-46.03.06-69.05-.05-5.12-.03-8.25 1.89-10.34 6.72-10.19 23.56-20.63 47-30.95 70.5-1.54 3.51-4.06 5.29-7.92 5.29-45.94-.01-91.87-.02-137.81 0-3.13 0-5.63-1.15-7.72-3.45-11.21-12.33-22.46-24.63-33.68-36.94-2.69-2.95-2.79-6.18-1.21-9.73 8.66-19.54 17.27-39.1 25.89-58.66 12.93-29.35 25.89-58.69 38.75-88.08 1.7-3.88 4.28-5.68 8.54-5.65 14.24.1 28.48.02 42.72.05 6.24.01 9.2 4.84 6.66 10.59-13.6 30.77-27.17 61.55-40.74 92.33-5.72 12.99-11.42 25.99-17.09 39-3.91 8.95 7.08 11.97 10.95 5.6.23-.37-1.42 4.18 30.01-67.69 1.36-3.1 3.41-4.4 6.77-4.39 15.21.08 30.43.02 45.64.04 5.56.01 7.91 3.64 5.66 8.75-8.33 18.96-16.71 37.9-24.98 56.89-4.98 11.43 8.08 12.49 11.28 5.33.04-.08 27.89-63.33 32.19-73.16 2.02-4.61 5.44-6.51 10.35-6.5 26.43.05 52.86 0 79.29.05 12.44.02 13.93-13.65 3.9-13.64-25.26.03-50.52.02-75.78.02-6.27 0-7.84-2.47-5.27-8.27 5.78-13.06 11.59-26.11 17.3-39.21 1.73-3.96 4.52-5.79 8.84-5.78 23.09.06 25.98.02 130.78.03 6.08-.01 8.03 2.79 5.62 8.27z"],
+ "xbox": [512, 512, [], "f412", "M369.9 318.2c44.3 54.3 64.7 98.8 54.4 118.7-7.9 15.1-56.7 44.6-92.6 55.9-29.6 9.3-68.4 13.3-100.4 10.2-38.2-3.7-76.9-17.4-110.1-39C93.3 445.8 87 438.3 87 423.4c0-29.9 32.9-82.3 89.2-142.1 32-33.9 76.5-73.7 81.4-72.6 9.4 2.1 84.3 75.1 112.3 109.5zM188.6 143.8c-29.7-26.9-58.1-53.9-86.4-63.4-15.2-5.1-16.3-4.8-28.7 8.1-29.2 30.4-53.5 79.7-60.3 122.4-5.4 34.2-6.1 43.8-4.2 60.5 5.6 50.5 17.3 85.4 40.5 120.9 9.5 14.6 12.1 17.3 9.3 9.9-4.2-11-.3-37.5 9.5-64 14.3-39 53.9-112.9 120.3-194.4zm311.6 63.5C483.3 127.3 432.7 77 425.6 77c-7.3 0-24.2 6.5-36 13.9-23.3 14.5-41 31.4-64.3 52.8C367.7 197 427.5 283.1 448.2 346c6.8 20.7 9.7 41.1 7.4 52.3-1.7 8.5-1.7 8.5 1.4 4.6 6.1-7.7 19.9-31.3 25.4-43.5 7.4-16.2 15-40.2 18.6-58.7 4.3-22.5 3.9-70.8-.8-93.4zM141.3 43C189 40.5 251 77.5 255.6 78.4c.7.1 10.4-4.2 21.6-9.7 63.9-31.1 94-25.8 107.4-25.2-63.9-39.3-152.7-50-233.9-11.7-23.4 11.1-24 11.9-9.4 11.2z"],
+ "xing": [384, 512, [], "f168", "M162.7 210c-1.8 3.3-25.2 44.4-70.1 123.5-4.9 8.3-10.8 12.5-17.7 12.5H9.8c-7.7 0-12.1-7.5-8.5-14.4l69-121.3c.2 0 .2-.1 0-.3l-43.9-75.6c-4.3-7.8.3-14.1 8.5-14.1H100c7.3 0 13.3 4.1 18 12.2l44.7 77.5zM382.6 46.1l-144 253v.3L330.2 466c3.9 7.1.2 14.1-8.5 14.1h-65.2c-7.6 0-13.6-4-18-12.2l-92.4-168.5c3.3-5.8 51.5-90.8 144.8-255.2 4.6-8.1 10.4-12.2 17.5-12.2h65.7c8 0 12.3 6.7 8.5 14.1z"],
+ "xing-square": [448, 512, [], "f169", "M400 32H48C21.5 32 0 53.5 0 80v352c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48V80c0-26.5-21.5-48-48-48zM140.4 320.2H93.8c-5.5 0-8.7-5.3-6-10.3l49.3-86.7c.1 0 .1-.1 0-.2l-31.4-54c-3-5.6.2-10.1 6-10.1h46.6c5.2 0 9.5 2.9 12.9 8.7l31.9 55.3c-1.3 2.3-18 31.7-50.1 88.2-3.5 6.2-7.7 9.1-12.6 9.1zm219.7-214.1L257.3 286.8v.2l65.5 119c2.8 5.1.1 10.1-6 10.1h-46.6c-5.5 0-9.7-2.9-12.9-8.7l-66-120.3c2.3-4.1 36.8-64.9 103.4-182.3 3.3-5.8 7.4-8.7 12.5-8.7h46.9c5.7-.1 8.8 4.7 6 10z"],
+ "y-combinator": [448, 512, [], "f23b", "M448 32v448H0V32h448zM236 287.5L313.5 142h-32.7L235 233c-4.7 9.3-9 18.3-12.8 26.8L210 233l-45.2-91h-35l76.7 143.8v94.5H236v-92.8z"],
+ "yahoo": [512, 512, [], "f19e", "M223.69,141.06,167,284.23,111,141.06H14.93L120.76,390.19,82.19,480h94.17L317.27,141.06Zm105.4,135.79a58.22,58.22,0,1,0,58.22,58.22A58.22,58.22,0,0,0,329.09,276.85ZM394.65,32l-93,223.47H406.44L499.07,32Z"],
+ "yammer": [512, 512, [], "f840", "M421.78 152.17A23.06 23.06 0 0 0 400.9 112c-.83.43-1.71.9-2.63 1.4-15.25 8.4-118.33 80.62-106.69 88.77s82.04-23.61 130.2-50zm0 217.17c-48.16-26.38-118.64-58.1-130.2-50s91.42 80.35 106.69 88.74c.92.51 1.8 1 2.63 1.41a23.07 23.07 0 0 0 20.88-40.15zM464.21 237c-.95 0-1.95-.06-3-.06-17.4 0-142.52 13.76-136.24 26.51s83.3 18.74 138.21 18.76a23 23 0 0 0 1-45.21zM31 96.65a24.88 24.88 0 0 1 46.14-18.4l81 205.06h1.21l77-203.53a23.52 23.52 0 0 1 44.45 15.27L171.2 368.44C152.65 415.66 134.08 448 77.91 448a139.67 139.67 0 0 1-23.81-1.95 21.31 21.31 0 0 1 6.9-41.77c.66.06 10.91.66 13.86.66 30.47 0 43.74-18.94 58.07-59.41z"],
+ "yandex": [256, 512, [], "f413", "M153.1 315.8L65.7 512H2l96-209.8c-45.1-22.9-75.2-64.4-75.2-141.1C22.7 53.7 90.8 0 171.7 0H254v512h-55.1V315.8h-45.8zm45.8-269.3h-29.4c-44.4 0-87.4 29.4-87.4 114.6 0 82.3 39.4 108.8 87.4 108.8h29.4V46.5z"],
+ "yandex-international": [320, 512, [], "f414", "M129.5 512V345.9L18.5 48h55.8l81.8 229.7L250.2 0h51.3L180.8 347.8V512h-51.3z"],
+ "yarn": [496, 512, [], "f7e3", "M393.9 345.2c-39 9.3-48.4 32.1-104 47.4 0 0-2.7 4-10.4 5.8-13.4 3.3-63.9 6-68.5 6.1-12.4.1-19.9-3.2-22-8.2-6.4-15.3 9.2-22 9.2-22-8.1-5-9-9.9-9.8-8.1-2.4 5.8-3.6 20.1-10.1 26.5-8.8 8.9-25.5 5.9-35.3.8-10.8-5.7.8-19.2.8-19.2s-5.8 3.4-10.5-3.6c-6-9.3-17.1-37.3 11.5-62-1.3-10.1-4.6-53.7 40.6-85.6 0 0-20.6-22.8-12.9-43.3 5-13.4 7-13.3 8.6-13.9 5.7-2.2 11.3-4.6 15.4-9.1 20.6-22.2 46.8-18 46.8-18s12.4-37.8 23.9-30.4c3.5 2.3 16.3 30.6 16.3 30.6s13.6-7.9 15.1-5c8.2 16 9.2 46.5 5.6 65.1-6.1 30.6-21.4 47.1-27.6 57.5-1.4 2.4 16.5 10 27.8 41.3 10.4 28.6 1.1 52.7 2.8 55.3.8 1.4 13.7.8 36.4-13.2 12.8-7.9 28.1-16.9 45.4-17 16.7-.5 17.6 19.2 4.9 22.2zM496 256c0 136.9-111.1 248-248 248S0 392.9 0 256 111.1 8 248 8s248 111.1 248 248zm-79.3 75.2c-1.7-13.6-13.2-23-28-22.8-22 .3-40.5 11.7-52.8 19.2-4.8 3-8.9 5.2-12.4 6.8 3.1-44.5-22.5-73.1-28.7-79.4 7.8-11.3 18.4-27.8 23.4-53.2 4.3-21.7 3-55.5-6.9-74.5-1.6-3.1-7.4-11.2-21-7.4-9.7-20-13-22.1-15.6-23.8-1.1-.7-23.6-16.4-41.4 28-12.2.9-31.3 5.3-47.5 22.8-2 2.2-5.9 3.8-10.1 5.4h.1c-8.4 3-12.3 9.9-16.9 22.3-6.5 17.4.2 34.6 6.8 45.7-17.8 15.9-37 39.8-35.7 82.5-34 36-11.8 73-5.6 79.6-1.6 11.1 3.7 19.4 12 23.8 12.6 6.7 30.3 9.6 43.9 2.8 4.9 5.2 13.8 10.1 30 10.1 6.8 0 58-2.9 72.6-6.5 6.8-1.6 11.5-4.5 14.6-7.1 9.8-3.1 36.8-12.3 62.2-28.7 18-11.7 24.2-14.2 37.6-17.4 12.9-3.2 21-15.1 19.4-28.2z"],
+ "yelp": [384, 512, [], "f1e9", "M42.9 240.32l99.62 48.61c19.2 9.4 16.2 37.51-4.5 42.71L30.5 358.45a22.79 22.79 0 0 1-28.21-19.6 197.16 197.16 0 0 1 9-85.32 22.8 22.8 0 0 1 31.61-13.21zm44 239.25a199.45 199.45 0 0 0 79.42 32.11A22.78 22.78 0 0 0 192.94 490l3.9-110.82c.7-21.3-25.5-31.91-39.81-16.1l-74.21 82.4a22.82 22.82 0 0 0 4.09 34.09zm145.34-109.92l58.81 94a22.93 22.93 0 0 0 34 5.5 198.36 198.36 0 0 0 52.71-67.61A23 23 0 0 0 364.17 370l-105.42-34.26c-20.31-6.5-37.81 15.8-26.51 33.91zm148.33-132.23a197.44 197.44 0 0 0-50.41-69.31 22.85 22.85 0 0 0-34 4.4l-62 91.92c-11.9 17.7 4.7 40.61 25.2 34.71L366 268.63a23 23 0 0 0 14.61-31.21zM62.11 30.18a22.86 22.86 0 0 0-9.9 32l104.12 180.44c11.7 20.2 42.61 11.9 42.61-11.4V22.88a22.67 22.67 0 0 0-24.5-22.8 320.37 320.37 0 0 0-112.33 30.1z"],
+ "yoast": [448, 512, [], "f2b1", "M91.3 76h186l-7 18.9h-179c-39.7 0-71.9 31.6-71.9 70.3v205.4c0 35.4 24.9 70.3 84 70.3V460H91.3C41.2 460 0 419.8 0 370.5V165.2C0 115.9 40.7 76 91.3 76zm229.1-56h66.5C243.1 398.1 241.2 418.9 202.2 459.3c-20.8 21.6-49.3 31.7-78.3 32.7v-51.1c49.2-7.7 64.6-49.9 64.6-75.3 0-20.1.6-12.6-82.1-223.2h61.4L218.2 299 320.4 20zM448 161.5V460H234c6.6-9.6 10.7-16.3 12.1-19.4h182.5V161.5c0-32.5-17.1-51.9-48.2-62.9l6.7-17.6c41.7 13.6 60.9 43.1 60.9 80.5z"],
+ "youtube": [576, 512, [], "f167", "M549.655 124.083c-6.281-23.65-24.787-42.276-48.284-48.597C458.781 64 288 64 288 64S117.22 64 74.629 75.486c-23.497 6.322-42.003 24.947-48.284 48.597-11.412 42.867-11.412 132.305-11.412 132.305s0 89.438 11.412 132.305c6.281 23.65 24.787 41.5 48.284 47.821C117.22 448 288 448 288 448s170.78 0 213.371-11.486c23.497-6.321 42.003-24.171 48.284-47.821 11.412-42.867 11.412-132.305 11.412-132.305s0-89.438-11.412-132.305zm-317.51 213.508V175.185l142.739 81.205-142.739 81.201z"],
+ "youtube-square": [448, 512, [], "f431", "M186.8 202.1l95.2 54.1-95.2 54.1V202.1zM448 80v352c0 26.5-21.5 48-48 48H48c-26.5 0-48-21.5-48-48V80c0-26.5 21.5-48 48-48h352c26.5 0 48 21.5 48 48zm-42 176.3s0-59.6-7.6-88.2c-4.2-15.8-16.5-28.2-32.2-32.4C337.9 128 224 128 224 128s-113.9 0-142.2 7.7c-15.7 4.2-28 16.6-32.2 32.4-7.6 28.5-7.6 88.2-7.6 88.2s0 59.6 7.6 88.2c4.2 15.8 16.5 27.7 32.2 31.9C110.1 384 224 384 224 384s113.9 0 142.2-7.7c15.7-4.2 28-16.1 32.2-31.9 7.6-28.5 7.6-88.1 7.6-88.1z"],
+ "zhihu": [640, 512, [], "f63f", "M170.54 148.13v217.54l23.43.01 7.71 26.37 42.01-26.37h49.53V148.13H170.54zm97.75 193.93h-27.94l-27.9 17.51-5.08-17.47-11.9-.04V171.75h72.82v170.31zm-118.46-94.39H97.5c1.74-27.1 2.2-51.59 2.2-73.46h51.16s1.97-22.56-8.58-22.31h-88.5c3.49-13.12 7.87-26.66 13.12-40.67 0 0-24.07 0-32.27 21.57-3.39 8.9-13.21 43.14-30.7 78.12 5.89-.64 25.37-1.18 36.84-22.21 2.11-5.89 2.51-6.66 5.14-14.53h28.87c0 10.5-1.2 66.88-1.68 73.44H20.83c-11.74 0-15.56 23.62-15.56 23.62h65.58C66.45 321.1 42.83 363.12 0 396.34c20.49 5.85 40.91-.93 51-9.9 0 0 22.98-20.9 35.59-69.25l53.96 64.94s7.91-26.89-1.24-39.99c-7.58-8.92-28.06-33.06-36.79-41.81L87.9 311.95c4.36-13.98 6.99-27.55 7.87-40.67h61.65s-.09-23.62-7.59-23.62v.01zm412.02-1.6c20.83-25.64 44.98-58.57 44.98-58.57s-18.65-14.8-27.38-4.06c-6 8.15-36.83 48.2-36.83 48.2l19.23 14.43zm-150.09-59.09c-9.01-8.25-25.91 2.13-25.91 2.13s39.52 55.04 41.12 57.45l19.46-13.73s-25.67-37.61-34.66-45.86h-.01zM640 258.35c-19.78 0-130.91.93-131.06.93v-101c4.81 0 12.42-.4 22.85-1.2 40.88-2.41 70.13-4 87.77-4.81 0 0 12.22-27.19-.59-33.44-3.07-1.18-23.17 4.58-23.17 4.58s-165.22 16.49-232.36 18.05c1.6 8.82 7.62 17.08 15.78 19.55 13.31 3.48 22.69 1.7 49.15.89 24.83-1.6 43.68-2.43 56.51-2.43v99.81H351.41s2.82 22.31 25.51 22.85h107.94v70.92c0 13.97-11.19 21.99-24.48 21.12-14.08.11-26.08-1.15-41.69-1.81 1.99 3.97 6.33 14.39 19.31 21.84 9.88 4.81 16.17 6.57 26.02 6.57 29.56 0 45.67-17.28 44.89-45.31v-73.32h122.36c9.68 0 8.7-23.78 8.7-23.78l.03-.01z"]
+ };
+
+ bunker(function () {
+ defineIcons('fab', icons);
+ });
+
+}());
diff --git a/fontawesomelib/js/brands.min.js b/fontawesomelib/js/brands.min.js
new file mode 100644
index 0000000..83c3c1c
--- /dev/null
+++ b/fontawesomelib/js/brands.min.js
@@ -0,0 +1,5 @@
+/*!
+ * Font Awesome Free 5.15.4 by @fontawesome - https://fontawesome.com
+ * License - https://fontawesome.com/license/free (Icons: CC BY 4.0, Fonts: SIL OFL 1.1, Code: MIT License)
+ */
+!function(){"use strict";var c={},l={};try{"undefined"!=typeof window&&(c=window),"undefined"!=typeof document&&(l=document)}catch(c){}var z=(c.navigator||{}).userAgent,h=void 0===z?"":z,m=c,v=l,a=(m.document,!!v.documentElement&&!!v.head&&"function"==typeof v.addEventListener&&v.createElement,~h.indexOf("MSIE")||h.indexOf("Trident/"),"___FONT_AWESOME___"),M=function(){try{return!0}catch(c){return!1}}();var s=m||{};s[a]||(s[a]={}),s[a].styles||(s[a].styles={}),s[a].hooks||(s[a].hooks={}),s[a].shims||(s[a].shims=[]);var H=s[a];function V(c,h){var l=(2 0) {
+ console.info("%cConflict".concat(conflictsCount > 1 ? 's' : '', " found:"), 'color: darkred; font-size: large');
+ var data = {};
+
+ for (var _key in nodesTested.conflict) {
+ var item = nodesTested.conflict[_key];
+ data[_key] = {
+ 'tagName': item.tagName,
+ 'src/href': item.src || item.href || 'n/a',
+ 'innerText excerpt': item.innerText && item.innerText !== '' ? item.innerText.slice(0, 200) + '...' : '(empty)'
+ };
+ }
+
+ console.table(data);
+ }
+
+ var noConflictsCount = Object.keys(nodesTested.noConflict).length;
+
+ if (noConflictsCount > 0) {
+ console.info("%cNo conflict".concat(noConflictsCount > 1 ? 's' : '', " found with ").concat(noConflictsCount == 1 ? 'this' : 'these', ":"), 'color: green; font-size: large');
+ var _data = {};
+
+ for (var _key2 in nodesTested.noConflict) {
+ var _item = nodesTested.noConflict[_key2];
+ _data[_key2] = {
+ 'tagName': _item.tagName,
+ 'src/href': _item.src || _item.href || 'n/a',
+ 'innerText excerpt': _item.innerText && _item.innerText !== '' ? _item.innerText.slice(0, 200) + '...' : '(empty)'
+ };
+ }
+
+ console.table(_data);
+ }
+
+ var timeOutCount = Object.keys(timedOutTests).length;
+
+ if (timeOutCount > 0) {
+ console.info("%cLeftovers--we timed out before collecting test results for ".concat(timeOutCount == 1 ? 'this' : 'these', ":"), 'color: blue; font-size: large');
+ var _data2 = {};
+
+ for (var _key3 in timedOutTests) {
+ var _item2 = timedOutTests[_key3];
+ _data2[_key3] = {
+ 'tagName': _item2.tagName,
+ 'src/href': _item2.src || _item2.href || 'n/a',
+ 'innerText excerpt': _item2.innerText && _item2.innerText !== '' ? _item2.innerText.slice(0, 200) + '...' : '(empty)'
+ };
+ }
+
+ console.table(_data2);
+ }
+ }
+
+ var commonjsGlobal = typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
+
+ function createCommonjsModule(fn, module) {
+ return module = { exports: {} }, fn(module, module.exports), module.exports;
+ }
+
+ var md5 = createCommonjsModule(function (module) {
+
+ (function ($) {
+ /**
+ * Add integers, wrapping at 2^32.
+ * This uses 16-bit operations internally to work around bugs in interpreters.
+ *
+ * @param {number} x First integer
+ * @param {number} y Second integer
+ * @returns {number} Sum
+ */
+
+ function safeAdd(x, y) {
+ var lsw = (x & 0xffff) + (y & 0xffff);
+ var msw = (x >> 16) + (y >> 16) + (lsw >> 16);
+ return msw << 16 | lsw & 0xffff;
+ }
+ /**
+ * Bitwise rotate a 32-bit number to the left.
+ *
+ * @param {number} num 32-bit number
+ * @param {number} cnt Rotation count
+ * @returns {number} Rotated number
+ */
+
+
+ function bitRotateLeft(num, cnt) {
+ return num << cnt | num >>> 32 - cnt;
+ }
+ /**
+ * Basic operation the algorithm uses.
+ *
+ * @param {number} q q
+ * @param {number} a a
+ * @param {number} b b
+ * @param {number} x x
+ * @param {number} s s
+ * @param {number} t t
+ * @returns {number} Result
+ */
+
+
+ function md5cmn(q, a, b, x, s, t) {
+ return safeAdd(bitRotateLeft(safeAdd(safeAdd(a, q), safeAdd(x, t)), s), b);
+ }
+ /**
+ * Basic operation the algorithm uses.
+ *
+ * @param {number} a a
+ * @param {number} b b
+ * @param {number} c c
+ * @param {number} d d
+ * @param {number} x x
+ * @param {number} s s
+ * @param {number} t t
+ * @returns {number} Result
+ */
+
+
+ function md5ff(a, b, c, d, x, s, t) {
+ return md5cmn(b & c | ~b & d, a, b, x, s, t);
+ }
+ /**
+ * Basic operation the algorithm uses.
+ *
+ * @param {number} a a
+ * @param {number} b b
+ * @param {number} c c
+ * @param {number} d d
+ * @param {number} x x
+ * @param {number} s s
+ * @param {number} t t
+ * @returns {number} Result
+ */
+
+
+ function md5gg(a, b, c, d, x, s, t) {
+ return md5cmn(b & d | c & ~d, a, b, x, s, t);
+ }
+ /**
+ * Basic operation the algorithm uses.
+ *
+ * @param {number} a a
+ * @param {number} b b
+ * @param {number} c c
+ * @param {number} d d
+ * @param {number} x x
+ * @param {number} s s
+ * @param {number} t t
+ * @returns {number} Result
+ */
+
+
+ function md5hh(a, b, c, d, x, s, t) {
+ return md5cmn(b ^ c ^ d, a, b, x, s, t);
+ }
+ /**
+ * Basic operation the algorithm uses.
+ *
+ * @param {number} a a
+ * @param {number} b b
+ * @param {number} c c
+ * @param {number} d d
+ * @param {number} x x
+ * @param {number} s s
+ * @param {number} t t
+ * @returns {number} Result
+ */
+
+
+ function md5ii(a, b, c, d, x, s, t) {
+ return md5cmn(c ^ (b | ~d), a, b, x, s, t);
+ }
+ /**
+ * Calculate the MD5 of an array of little-endian words, and a bit length.
+ *
+ * @param {Array} x Array of little-endian words
+ * @param {number} len Bit length
+ * @returns {Array} MD5 Array
+ */
+
+
+ function binlMD5(x, len) {
+ /* append padding */
+ x[len >> 5] |= 0x80 << len % 32;
+ x[(len + 64 >>> 9 << 4) + 14] = len;
+ var i;
+ var olda;
+ var oldb;
+ var oldc;
+ var oldd;
+ var a = 1732584193;
+ var b = -271733879;
+ var c = -1732584194;
+ var d = 271733878;
+
+ for (i = 0; i < x.length; i += 16) {
+ olda = a;
+ oldb = b;
+ oldc = c;
+ oldd = d;
+ a = md5ff(a, b, c, d, x[i], 7, -680876936);
+ d = md5ff(d, a, b, c, x[i + 1], 12, -389564586);
+ c = md5ff(c, d, a, b, x[i + 2], 17, 606105819);
+ b = md5ff(b, c, d, a, x[i + 3], 22, -1044525330);
+ a = md5ff(a, b, c, d, x[i + 4], 7, -176418897);
+ d = md5ff(d, a, b, c, x[i + 5], 12, 1200080426);
+ c = md5ff(c, d, a, b, x[i + 6], 17, -1473231341);
+ b = md5ff(b, c, d, a, x[i + 7], 22, -45705983);
+ a = md5ff(a, b, c, d, x[i + 8], 7, 1770035416);
+ d = md5ff(d, a, b, c, x[i + 9], 12, -1958414417);
+ c = md5ff(c, d, a, b, x[i + 10], 17, -42063);
+ b = md5ff(b, c, d, a, x[i + 11], 22, -1990404162);
+ a = md5ff(a, b, c, d, x[i + 12], 7, 1804603682);
+ d = md5ff(d, a, b, c, x[i + 13], 12, -40341101);
+ c = md5ff(c, d, a, b, x[i + 14], 17, -1502002290);
+ b = md5ff(b, c, d, a, x[i + 15], 22, 1236535329);
+ a = md5gg(a, b, c, d, x[i + 1], 5, -165796510);
+ d = md5gg(d, a, b, c, x[i + 6], 9, -1069501632);
+ c = md5gg(c, d, a, b, x[i + 11], 14, 643717713);
+ b = md5gg(b, c, d, a, x[i], 20, -373897302);
+ a = md5gg(a, b, c, d, x[i + 5], 5, -701558691);
+ d = md5gg(d, a, b, c, x[i + 10], 9, 38016083);
+ c = md5gg(c, d, a, b, x[i + 15], 14, -660478335);
+ b = md5gg(b, c, d, a, x[i + 4], 20, -405537848);
+ a = md5gg(a, b, c, d, x[i + 9], 5, 568446438);
+ d = md5gg(d, a, b, c, x[i + 14], 9, -1019803690);
+ c = md5gg(c, d, a, b, x[i + 3], 14, -187363961);
+ b = md5gg(b, c, d, a, x[i + 8], 20, 1163531501);
+ a = md5gg(a, b, c, d, x[i + 13], 5, -1444681467);
+ d = md5gg(d, a, b, c, x[i + 2], 9, -51403784);
+ c = md5gg(c, d, a, b, x[i + 7], 14, 1735328473);
+ b = md5gg(b, c, d, a, x[i + 12], 20, -1926607734);
+ a = md5hh(a, b, c, d, x[i + 5], 4, -378558);
+ d = md5hh(d, a, b, c, x[i + 8], 11, -2022574463);
+ c = md5hh(c, d, a, b, x[i + 11], 16, 1839030562);
+ b = md5hh(b, c, d, a, x[i + 14], 23, -35309556);
+ a = md5hh(a, b, c, d, x[i + 1], 4, -1530992060);
+ d = md5hh(d, a, b, c, x[i + 4], 11, 1272893353);
+ c = md5hh(c, d, a, b, x[i + 7], 16, -155497632);
+ b = md5hh(b, c, d, a, x[i + 10], 23, -1094730640);
+ a = md5hh(a, b, c, d, x[i + 13], 4, 681279174);
+ d = md5hh(d, a, b, c, x[i], 11, -358537222);
+ c = md5hh(c, d, a, b, x[i + 3], 16, -722521979);
+ b = md5hh(b, c, d, a, x[i + 6], 23, 76029189);
+ a = md5hh(a, b, c, d, x[i + 9], 4, -640364487);
+ d = md5hh(d, a, b, c, x[i + 12], 11, -421815835);
+ c = md5hh(c, d, a, b, x[i + 15], 16, 530742520);
+ b = md5hh(b, c, d, a, x[i + 2], 23, -995338651);
+ a = md5ii(a, b, c, d, x[i], 6, -198630844);
+ d = md5ii(d, a, b, c, x[i + 7], 10, 1126891415);
+ c = md5ii(c, d, a, b, x[i + 14], 15, -1416354905);
+ b = md5ii(b, c, d, a, x[i + 5], 21, -57434055);
+ a = md5ii(a, b, c, d, x[i + 12], 6, 1700485571);
+ d = md5ii(d, a, b, c, x[i + 3], 10, -1894986606);
+ c = md5ii(c, d, a, b, x[i + 10], 15, -1051523);
+ b = md5ii(b, c, d, a, x[i + 1], 21, -2054922799);
+ a = md5ii(a, b, c, d, x[i + 8], 6, 1873313359);
+ d = md5ii(d, a, b, c, x[i + 15], 10, -30611744);
+ c = md5ii(c, d, a, b, x[i + 6], 15, -1560198380);
+ b = md5ii(b, c, d, a, x[i + 13], 21, 1309151649);
+ a = md5ii(a, b, c, d, x[i + 4], 6, -145523070);
+ d = md5ii(d, a, b, c, x[i + 11], 10, -1120210379);
+ c = md5ii(c, d, a, b, x[i + 2], 15, 718787259);
+ b = md5ii(b, c, d, a, x[i + 9], 21, -343485551);
+ a = safeAdd(a, olda);
+ b = safeAdd(b, oldb);
+ c = safeAdd(c, oldc);
+ d = safeAdd(d, oldd);
+ }
+
+ return [a, b, c, d];
+ }
+ /**
+ * Convert an array of little-endian words to a string
+ *
+ * @param {Array} input MD5 Array
+ * @returns {string} MD5 string
+ */
+
+
+ function binl2rstr(input) {
+ var i;
+ var output = '';
+ var length32 = input.length * 32;
+
+ for (i = 0; i < length32; i += 8) {
+ output += String.fromCharCode(input[i >> 5] >>> i % 32 & 0xff);
+ }
+
+ return output;
+ }
+ /**
+ * Convert a raw string to an array of little-endian words
+ * Characters >255 have their high-byte silently ignored.
+ *
+ * @param {string} input Raw input string
+ * @returns {Array} Array of little-endian words
+ */
+
+
+ function rstr2binl(input) {
+ var i;
+ var output = [];
+ output[(input.length >> 2) - 1] = undefined;
+
+ for (i = 0; i < output.length; i += 1) {
+ output[i] = 0;
+ }
+
+ var length8 = input.length * 8;
+
+ for (i = 0; i < length8; i += 8) {
+ output[i >> 5] |= (input.charCodeAt(i / 8) & 0xff) << i % 32;
+ }
+
+ return output;
+ }
+ /**
+ * Calculate the MD5 of a raw string
+ *
+ * @param {string} s Input string
+ * @returns {string} Raw MD5 string
+ */
+
+
+ function rstrMD5(s) {
+ return binl2rstr(binlMD5(rstr2binl(s), s.length * 8));
+ }
+ /**
+ * Calculates the HMAC-MD5 of a key and some data (raw strings)
+ *
+ * @param {string} key HMAC key
+ * @param {string} data Raw input string
+ * @returns {string} Raw MD5 string
+ */
+
+
+ function rstrHMACMD5(key, data) {
+ var i;
+ var bkey = rstr2binl(key);
+ var ipad = [];
+ var opad = [];
+ var hash;
+ ipad[15] = opad[15] = undefined;
+
+ if (bkey.length > 16) {
+ bkey = binlMD5(bkey, key.length * 8);
+ }
+
+ for (i = 0; i < 16; i += 1) {
+ ipad[i] = bkey[i] ^ 0x36363636;
+ opad[i] = bkey[i] ^ 0x5c5c5c5c;
+ }
+
+ hash = binlMD5(ipad.concat(rstr2binl(data)), 512 + data.length * 8);
+ return binl2rstr(binlMD5(opad.concat(hash), 512 + 128));
+ }
+ /**
+ * Convert a raw string to a hex string
+ *
+ * @param {string} input Raw input string
+ * @returns {string} Hex encoded string
+ */
+
+
+ function rstr2hex(input) {
+ var hexTab = '0123456789abcdef';
+ var output = '';
+ var x;
+ var i;
+
+ for (i = 0; i < input.length; i += 1) {
+ x = input.charCodeAt(i);
+ output += hexTab.charAt(x >>> 4 & 0x0f) + hexTab.charAt(x & 0x0f);
+ }
+
+ return output;
+ }
+ /**
+ * Encode a string as UTF-8
+ *
+ * @param {string} input Input string
+ * @returns {string} UTF8 string
+ */
+
+
+ function str2rstrUTF8(input) {
+ return unescape(encodeURIComponent(input));
+ }
+ /**
+ * Encodes input string as raw MD5 string
+ *
+ * @param {string} s Input string
+ * @returns {string} Raw MD5 string
+ */
+
+
+ function rawMD5(s) {
+ return rstrMD5(str2rstrUTF8(s));
+ }
+ /**
+ * Encodes input string as Hex encoded string
+ *
+ * @param {string} s Input string
+ * @returns {string} Hex encoded string
+ */
+
+
+ function hexMD5(s) {
+ return rstr2hex(rawMD5(s));
+ }
+ /**
+ * Calculates the raw HMAC-MD5 for the given key and data
+ *
+ * @param {string} k HMAC key
+ * @param {string} d Input string
+ * @returns {string} Raw MD5 string
+ */
+
+
+ function rawHMACMD5(k, d) {
+ return rstrHMACMD5(str2rstrUTF8(k), str2rstrUTF8(d));
+ }
+ /**
+ * Calculates the Hex encoded HMAC-MD5 for the given key and data
+ *
+ * @param {string} k HMAC key
+ * @param {string} d Input string
+ * @returns {string} Raw MD5 string
+ */
+
+
+ function hexHMACMD5(k, d) {
+ return rstr2hex(rawHMACMD5(k, d));
+ }
+ /**
+ * Calculates MD5 value for a given string.
+ * If a key is provided, calculates the HMAC-MD5 value.
+ * Returns a Hex encoded string unless the raw argument is given.
+ *
+ * @param {string} string Input string
+ * @param {string} [key] HMAC key
+ * @param {boolean} raw Raw oytput switch
+ * @returns {string} MD5 output
+ */
+
+
+ function md5(string, key, raw) {
+ if (!key) {
+ if (!raw) {
+ return hexMD5(string);
+ }
+
+ return rawMD5(string);
+ }
+
+ if (!raw) {
+ return hexHMACMD5(key, string);
+ }
+
+ return rawHMACMD5(key, string);
+ }
+
+ if (module.exports) {
+ module.exports = md5;
+ } else {
+ $.md5 = md5;
+ }
+ })(commonjsGlobal);
+ });
+
+ function md5ForNode(node) {
+ if (null === node || 'object' !== _typeof(node)) return undefined;
+
+ if (node.src) {
+ return md5(node.src);
+ } else if (node.href) {
+ return md5(node.href);
+ } else if (node.innerText && '' !== node.innerText) {
+ // eslint-disable-line yoda
+ return md5(node.innerText);
+ } else {
+ return undefined;
+ }
+ }
+
+ var diagScriptId = 'fa-kits-diag';
+ var nodeUnderTestId = 'fa-kits-node-under-test';
+ var md5Attr = 'data-md5';
+ var detectionIgnoreAttr = 'data-fa-detection-ignore';
+ var timeoutAttr = 'data-fa-detection-timeout';
+ var resultsCollectionMaxWaitAttr = 'data-fa-detection-results-collection-max-wait';
+
+ var silenceErrors = function silenceErrors(e) {
+ e.preventDefault();
+ e.stopPropagation();
+ };
+
+ function pollUntil(_ref) {
+ var _ref$fn = _ref.fn,
+ fn = _ref$fn === void 0 ? function () {
+ return true;
+ } : _ref$fn,
+ _ref$initialDuration = _ref.initialDuration,
+ initialDuration = _ref$initialDuration === void 0 ? 1 : _ref$initialDuration,
+ _ref$maxDuration = _ref.maxDuration,
+ maxDuration = _ref$maxDuration === void 0 ? WINDOW.FontAwesomeDetection.timeout : _ref$maxDuration,
+ _ref$showProgress = _ref.showProgress,
+ showProgress = _ref$showProgress === void 0 ? false : _ref$showProgress,
+ progressIndicator = _ref.progressIndicator;
+ return new Promise(function (resolve, reject) {
+ // eslint-disable-line compat/compat
+ function poll(duration, cumulativeDuration) {
+ setTimeout(function () {
+ var result = fn();
+
+ if (showProgress) {
+ console.info(progressIndicator);
+ }
+
+ if (!!result) {
+ // eslint-disable-line no-extra-boolean-cast
+ resolve(result);
+ } else {
+ var nextDuration = 250;
+ var nextCumulativeDuration = nextDuration + cumulativeDuration;
+
+ if (nextCumulativeDuration <= maxDuration) {
+ poll(nextDuration, nextCumulativeDuration);
+ } else {
+ reject('timeout'); // eslint-disable-line prefer-promise-reject-errors
+ }
+ }
+ }, duration);
+ }
+
+ poll(initialDuration, 0);
+ });
+ }
+
+ function detectWebfontConflicts() {
+ var linkTags = Array.from(DOCUMENT.getElementsByTagName('link')).filter(function (t) {
+ return !t.hasAttribute(detectionIgnoreAttr);
+ });
+ var styleTags = Array.from(DOCUMENT.getElementsByTagName('style')).filter(function (t) {
+ if (t.hasAttribute(detectionIgnoreAttr)) {
+ return false;
+ } // If the browser has loaded the FA5 CSS, let's not test that
+
+
+
+
+
+
+
+