Advertisement
okban

r

Jan 22nd, 2018
96
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 53.27 KB | None | 0 0
  1. function sandbox(var,func)
  2. local env = getfenv(func)
  3. local newenv = setmetatable({},{
  4. __index = function(self,k)
  5. if k=="script" then
  6. return var
  7. else
  8. return env[k]
  9. end
  10. end,
  11. })
  12. setfenv(func,newenv)
  13. return func
  14. end
  15. cors = {}
  16. mas = Instance.new("Model",game:GetService("Lighting"))
  17. ScreenGui0 = Instance.new("ScreenGui")
  18. Frame1 = Instance.new("Frame")
  19. LocalScript2 = Instance.new("LocalScript")
  20. BindableEvent3 = Instance.new("BindableEvent")
  21. BindableFunction4 = Instance.new("BindableFunction")
  22. BindableFunction5 = Instance.new("BindableFunction")
  23. BindableFunction6 = Instance.new("BindableFunction")
  24. BindableFunction7 = Instance.new("BindableFunction")
  25. ScreenGui0.Parent = mas
  26. Frame1.Name = "ExplorerPanel"
  27. Frame1.Parent = ScreenGui0
  28. Frame1.Transparency = 0.10000000149012
  29. Frame1.Size = UDim2.new(0, 300, 1, -168)
  30. Frame1.Position = UDim2.new(1, -308, 0, 160)
  31. Frame1.BackgroundColor3 = Color3.new(1, 1, 1)
  32. Frame1.BackgroundTransparency = 0.10000000149012
  33. Frame1.BorderColor3 = Color3.new(0.74902, 0.74902, 0.74902)
  34. LocalScript2.Parent = Frame1
  35. table.insert(cors,sandbox(LocalScript2,function()
  36. -- initial states
  37. local Option = {
  38. -- can modify objects
  39. Modifiable = true;
  40. -- can select objects
  41. Selectable = true;
  42. }
  43.  
  44. -- general size of GUI objects, in pixels
  45. local GUI_SIZE = 16
  46. -- padding between items within each entry
  47. local ENTRY_PADDING = 1
  48. -- padding between each entry
  49. local ENTRY_MARGIN = 1
  50.  
  51. --[[
  52.  
  53. # Explorer Panel
  54.  
  55. A GUI panel that displays the game hierarchy.
  56.  
  57.  
  58. ## Selection Bindables
  59.  
  60. - `Function GetSelection ( )`
  61.  
  62. Returns an array of objects representing the objects currently
  63. selected in the panel.
  64.  
  65. - `Function SetSelection ( Objects selection )`
  66.  
  67. Sets the objects that are selected in the panel. `selection` is an array
  68. of objects.
  69.  
  70. - `Event SelectionChanged ( )`
  71.  
  72. Fired after the selection changes.
  73.  
  74.  
  75. ## Option Bindables
  76.  
  77. - `Function GetOption ( string optionName )`
  78.  
  79. If `optionName` is given, returns the value of that option. Otherwise,
  80. returns a table of options and their current values.
  81.  
  82. - `Function SetOption ( string optionName, bool value )`
  83.  
  84. Sets `optionName` to `value`.
  85.  
  86. Options:
  87.  
  88. - Modifiable
  89.  
  90. Whether objects can be modified by the panel.
  91.  
  92. Note that modifying objects depends on being able to select them. If
  93. Selectable is false, then Actions will not be available. Reparenting
  94. is still possible, but only for the dragged object.
  95.  
  96. - Selectable
  97.  
  98. Whether objects can be selected.
  99.  
  100. If Modifiable is false, then left-clicking will perform a drag
  101. selection.
  102.  
  103. ## Updates
  104.  
  105. - 2013-09-18
  106. - Fixed explorer icons to match studio explorer.
  107.  
  108. - 2013-09-14
  109. - Added GetOption and SetOption bindables.
  110. - Option: Modifiable; sets whether objects can be modified by the panel.
  111. - Option: Selectable; sets whether objects can be selected.
  112. - Slight modification to left-click selection behavior.
  113. - Improved layout and scaling.
  114.  
  115. - 2013-09-13
  116. - Added drag to reparent objects.
  117. - Left-click to select/deselect object.
  118. - Left-click and drag unselected object to reparent single object.
  119. - Left-click and drag selected object to move reparent entire selection.
  120. - Right-click while dragging to cancel.
  121.  
  122. - 2013-09-11
  123. - Added explorer panel header with actions.
  124. - Added Cut action.
  125. - Added Copy action.
  126. - Added Paste action.
  127. - Added Delete action.
  128. - Added drag selection.
  129. - Left-click: Add to selection on drag.
  130. - Right-click: Add to or remove from selection on drag.
  131. - Ensured SelectionChanged fires only when the selection actually changes.
  132. - Added documentation and change log.
  133. - Fixed thread issue.
  134.  
  135. - 2013-09-09
  136. - Added basic multi-selection.
  137. - Left-click to set selection.
  138. - Right-click to add to or remove from selection.
  139. - Removed "Selection" ObjectValue.
  140. - Added GetSelection BindableFunction.
  141. - Added SetSelection BindableFunction.
  142. - Added SelectionChanged BindableEvent.
  143. - Changed font to SourceSans.
  144.  
  145. - 2013-08-31
  146. - Improved GUI sizing based off of `GUI_SIZE` constant.
  147. - Automatic font size detection.
  148.  
  149. - 2013-08-27
  150. - Initial explorer panel.
  151.  
  152.  
  153. ## Todo
  154.  
  155. - Sorting
  156. - by ExplorerOrder
  157. - by children
  158. - by name
  159. - Drag objects to reparent
  160.  
  161. ]]
  162.  
  163. local ENTRY_SIZE = GUI_SIZE + ENTRY_PADDING*2
  164. local ENTRY_BOUND = ENTRY_SIZE + ENTRY_MARGIN
  165. local HEADER_SIZE = ENTRY_SIZE
  166.  
  167. local FONT = 'SourceSans'
  168. local FONT_SIZE do
  169. local size = {8,9,10,11,12,14,18,24,36,48}
  170. local s
  171. local n = math.huge
  172. for i = 1,#size do
  173. if size[i] <= GUI_SIZE then
  174. FONT_SIZE = i - 1
  175. end
  176. end
  177. end
  178.  
  179. local GuiColor = {
  180. Background = Color3.new(233/255, 233/255, 233/255);
  181. Border = Color3.new(149/255, 149/255, 149/255);
  182. Selected = Color3.new( 96/255, 140/255, 211/255);
  183. BorderSelected = Color3.new( 86/255, 125/255, 188/255);
  184. Text = Color3.new( 0/255, 0/255, 0/255);
  185. TextDisabled = Color3.new(128/255, 128/255, 128/255);
  186. TextSelected = Color3.new(255/255, 255/255, 255/255);
  187. Button = Color3.new(221/255, 221/255, 221/255);
  188. ButtonBorder = Color3.new(149/255, 149/255, 149/255);
  189. ButtonSelected = Color3.new(255/255, 0/255, 0/255);
  190. Field = Color3.new(255/255, 255/255, 255/255);
  191. FieldBorder = Color3.new(191/255, 191/255, 191/255);
  192. TitleBackground = Color3.new(178/255, 178/255, 178/255);
  193. }
  194.  
  195. ----------------------------------------------------------------
  196. ----------------------------------------------------------------
  197. ----------------------------------------------------------------
  198. ----------------------------------------------------------------
  199. ---- Icon map constants
  200.  
  201. local MAP_ID = 129293660
  202.  
  203. -- Indices based on implementation of Icon function.
  204. local ACTION_CUT = 160
  205. local ACTION_COPY = 161
  206. local ACTION_PASTE = 162
  207. local ACTION_DELETE = 163
  208. local ACTION_SORT = 164
  209. local ACTION_CUT_OVER = 174
  210. local ACTION_COPY_OVER = 175
  211. local ACTION_PASTE_OVER = 176
  212. local ACTION_DELETE_OVER = 177
  213. local ACTION_SORT_OVER = 178
  214.  
  215. local NODE_COLLAPSED = 165
  216. local NODE_EXPANDED = 166
  217. local NODE_COLLAPSED_OVER = 179
  218. local NODE_EXPANDED_OVER = 180
  219.  
  220. local ExplorerIndex = {
  221. ["Accoutrement"] = 32;
  222. ["Animation"] = 60;
  223. ["AnimationTrack"] = 60;
  224. ["ArcHandles"] = 56;
  225. ["Backpack"] = 20;
  226. ["BillboardGui"] = 64;
  227. ["BindableEvent"] = 67;
  228. ["BindableFunction"] = 66;
  229. ["BlockMesh"] = 8;
  230. ["BodyAngularVelocity"] = 14;
  231. ["BodyForce"] = 14;
  232. ["BodyGyro"] = 14;
  233. ["BodyPosition"] = 14;
  234. ["BodyThrust"] = 14;
  235. ["BodyVelocity"] = 14;
  236. ["BoolValue"] = 4;
  237. ["BrickColorValue"] = 4;
  238. ["Camera"] = 5;
  239. ["CFrameValue"] = 4;
  240. ["CharacterMesh"] = 60;
  241. ["ClickDetector"] = 41;
  242. ["Color3Value"] = 4;
  243. ["Configuration"] = 58;
  244. ["CoreGui"] = 46;
  245. ["CornerWedgePart"] = 1;
  246. ["CustomEvent"] = 4;
  247. ["CustomEventReceiver"] = 4;
  248. ["CylinderMesh"] = 8;
  249. ["Debris"] = 30;
  250. ["Decal"] = 7;
  251. ["Dialog"] = 62;
  252. ["DialogChoice"] = 63;
  253. ["DoubleConstrainedValue"] = 4;
  254. ["Explosion"] = 36;
  255. ["Fire"] = 61;
  256. ["Flag"] = 38;
  257. ["FlagStand"] = 39;
  258. ["FloorWire"] = 4;
  259. ["ForceField"] = 37;
  260. ["Frame"] = 48;
  261. ["GuiButton"] = 52;
  262. ["GuiMain"] = 47;
  263. ["Handles"] = 53;
  264. ["Hat"] = 45;
  265. ["Hint"] = 33;
  266. ["HopperBin"] = 22;
  267. ["Humanoid"] = 9;
  268. ["ImageButton"] = 52;
  269. ["ImageLabel"] = 49;
  270. ["IntConstrainedValue"] = 4;
  271. ["IntValue"] = 4;
  272. ["JointInstance"] = 34;
  273. ["Keyframe"] = 60;
  274. ["Lighting"] = 13;
  275. ["LocalScript"] = 18;
  276. ["MarketplaceService"] = 46;
  277. ["Message"] = 33;
  278. ["Model"] = 2;
  279. ["NetworkClient"] = 16;
  280. ["NetworkReplicator"] = 29;
  281. ["NetworkServer"] = 15;
  282. ["NumberValue"] = 4;
  283. ["ObjectValue"] = 4;
  284. ["Pants"] = 44;
  285. ["ParallelRampPart"] = 1;
  286. ["Part"] = 1;
  287. ["PartPairLasso"] = 57;
  288. ["Platform"] = 35;
  289. ["Player"] = 12;
  290. ["PlayerGui"] = 46;
  291. ["Players"] = 21;
  292. ["PointLight"] = 13;
  293. ["Pose"] = 60;
  294. ["PrismPart"] = 1;
  295. ["PyramidPart"] = 1;
  296. ["RayValue"] = 4;
  297. ["ReplicatedStorage"] = 0;
  298. ["RightAngleRampPart"] = 1;
  299. ["RocketPropulsion"] = 14;
  300. ["ScreenGui"] = 47;
  301. ["Script"] = 6;
  302. ["Seat"] = 35;
  303. ["SelectionBox"] = 54;
  304. ["SelectionPartLasso"] = 57;
  305. ["SelectionPointLasso"] = 57;
  306. ["ServerScriptService"] = 0;
  307. ["ServerStorage"] = 0;
  308. ["Shirt"] = 43;
  309. ["ShirtGraphic"] = 40;
  310. ["SkateboardPlatform"] = 35;
  311. ["Sky"] = 28;
  312. ["Smoke"] = 59;
  313. ["Sound"] = 11;
  314. ["SoundService"] = 31;
  315. ["Sparkles"] = 42;
  316. ["SpawnLocation"] = 25;
  317. ["SpecialMesh"] = 8;
  318. ["SpotLight"] = 13;
  319. ["StarterGear"] = 20;
  320. ["StarterGui"] = 46;
  321. ["StarterPack"] = 20;
  322. ["Status"] = 2;
  323. ["StringValue"] = 4;
  324. ["SurfaceSelection"] = 55;
  325. ["Team"] = 24;
  326. ["Teams"] = 23;
  327. ["Terrain"] = 65;
  328. ["TestService"] = 68;
  329. ["TextBox"] = 51;
  330. ["TextButton"] = 51;
  331. ["TextLabel"] = 50;
  332. ["Texture"] = 10;
  333. ["TextureTrail"] = 4;
  334. ["Tool"] = 17;
  335. ["TouchTransmitter"] = 37;
  336. ["TrussPart"] = 1;
  337. ["Vector3Value"] = 4;
  338. ["VehicleSeat"] = 35;
  339. ["WedgePart"] = 1;
  340. ["Weld"] = 34;
  341. ["Workspace"] = 19;
  342. }
  343.  
  344. ----------------------------------------------------------------
  345. ----------------------------------------------------------------
  346. ----------------------------------------------------------------
  347. ----------------------------------------------------------------
  348. ----------------------------------------------------------------
  349.  
  350. function Create(ty,data)
  351. local obj
  352. if type(ty) == 'string' then
  353. obj = Instance.new(ty)
  354. else
  355. obj = ty
  356. end
  357. for k, v in pairs(data) do
  358. if type(k) == 'number' then
  359. v.Parent = obj
  360. else
  361. obj[k] = v
  362. end
  363. end
  364. return obj
  365. end
  366.  
  367. -- Connects a function to an event such that it fires asynchronously
  368. function Connect(event,func)
  369. return event:connect(function(...)
  370. local a = {...}
  371. Spawn(function() func(unpack(a)) end)
  372. end)
  373. end
  374.  
  375. -- returns the ascendant ScreenGui of an object
  376. function GetScreen(screen)
  377. if screen == nil then return nil end
  378. while not screen:IsA("ScreenGui") do
  379. screen = screen.Parent
  380. if screen == nil then return nil end
  381. end
  382. return screen
  383. end
  384.  
  385. do
  386. local ZIndexLock = {}
  387. -- Sets the ZIndex of an object and its descendants. Objects are locked so
  388. -- that SetZIndexOnChanged doesn't spawn multiple threads that set the
  389. -- ZIndex of the same object.
  390. function SetZIndex(object,z)
  391. if not ZIndexLock[object] then
  392. ZIndexLock[object] = true
  393. if object:IsA'GuiObject' then
  394. object.ZIndex = z
  395. end
  396. local children = object:GetChildren()
  397. for i = 1,#children do
  398. SetZIndex(children[i],z)
  399. end
  400. ZIndexLock[object] = nil
  401. end
  402. end
  403.  
  404. function SetZIndexOnChanged(object)
  405. return object.Changed:connect(function(p)
  406. if p == "ZIndex" then
  407. SetZIndex(object,object.ZIndex)
  408. end
  409. end)
  410. end
  411. end
  412.  
  413. ---- IconMap ----
  414. -- Image size: 256px x 256px
  415. -- Icon size: 16px x 16px
  416. -- Padding between each icon: 2px
  417. -- Padding around image edge: 1px
  418. -- Total icons: 14 x 14 (196)
  419. local Icon do
  420. local iconMap = 'http://www.roblox.com/asset/?id=' .. MAP_ID
  421. Game:GetService('ContentProvider'):Preload(iconMap)
  422. local iconDehash do
  423. -- 14 x 14, 0-based input, 0-based output
  424. local f=math.floor
  425. function iconDehash(h)
  426. return f(h/14%14),f(h%14)
  427. end
  428. end
  429.  
  430. function Icon(IconFrame,index)
  431. local row,col = iconDehash(index)
  432. local mapSize = Vector2.new(256,256)
  433. local pad,border = 2,1
  434. local iconSize = 16
  435.  
  436. local class = 'Frame'
  437. if type(IconFrame) == 'string' then
  438. class = IconFrame
  439. IconFrame = nil
  440. end
  441.  
  442. if not IconFrame then
  443. IconFrame = Create(class,{
  444. Name = "Icon";
  445. BackgroundTransparency = 1;
  446. ClipsDescendants = true;
  447. Create('ImageLabel',{
  448. Name = "IconMap";
  449. Active = false;
  450. BackgroundTransparency = 1;
  451. Image = iconMap;
  452. Size = UDim2.new(mapSize.x/iconSize,0,mapSize.y/iconSize,0);
  453. });
  454. })
  455. end
  456.  
  457. IconFrame.IconMap.Position = UDim2.new(-col - (pad*(col+1) + border)/iconSize,0,-row - (pad*(row+1) + border)/iconSize,0)
  458. return IconFrame
  459. end
  460. end
  461.  
  462. ----------------------------------------------------------------
  463. ----------------------------------------------------------------
  464. ----------------------------------------------------------------
  465. ----------------------------------------------------------------
  466. ---- ScrollBar
  467. do
  468. -- AutoButtonColor doesn't always reset properly
  469. local function ResetButtonColor(button)
  470. local active = button.Active
  471. button.Active = not active
  472. button.Active = active
  473. end
  474.  
  475. local function ArrowGraphic(size,dir,scaled,template)
  476. local Frame = Create('Frame',{
  477. Name = "Arrow Graphic";
  478. BorderSizePixel = 0;
  479. Size = UDim2.new(0,size,0,size);
  480. Transparency = 1;
  481. })
  482. if not template then
  483. template = Instance.new("Frame")
  484. template.BorderSizePixel = 0
  485. end
  486.  
  487. local transform
  488. if dir == nil or dir == 'Up' then
  489. function transform(p,s) return p,s end
  490. elseif dir == 'Down' then
  491. function transform(p,s) return UDim2.new(0,p.X.Offset,0,size-p.Y.Offset-1),s end
  492. elseif dir == 'Left' then
  493. function transform(p,s) return UDim2.new(0,p.Y.Offset,0,p.X.Offset),UDim2.new(0,s.Y.Offset,0,s.X.Offset) end
  494. elseif dir == 'Right' then
  495. function transform(p,s) return UDim2.new(0,size-p.Y.Offset-1,0,p.X.Offset),UDim2.new(0,s.Y.Offset,0,s.X.Offset) end
  496. end
  497.  
  498. local scale
  499. if scaled then
  500. function scale(p,s) return UDim2.new(p.X.Offset/size,0,p.Y.Offset/size,0),UDim2.new(s.X.Offset/size,0,s.Y.Offset/size,0) end
  501. else
  502. function scale(p,s) return p,s end
  503. end
  504.  
  505. local o = math.floor(size/4)
  506. if size%2 == 0 then
  507. local n = size/2-1
  508. for i = 0,n do
  509. local t = template:Clone()
  510. local p,s = scale(transform(
  511. UDim2.new(0,n-i,0,o+i),
  512. UDim2.new(0,(i+1)*2,0,1)
  513. ))
  514. t.Position = p
  515. t.Size = s
  516. t.Parent = Frame
  517. end
  518. else
  519. local n = (size-1)/2
  520. for i = 0,n do
  521. local t = template:Clone()
  522. local p,s = scale(transform(
  523. UDim2.new(0,n-i,0,o+i),
  524. UDim2.new(0,i*2+1,0,1)
  525. ))
  526. t.Position = p
  527. t.Size = s
  528. t.Parent = Frame
  529. end
  530. end
  531. if size%4 > 1 then
  532. local t = template:Clone()
  533. local p,s = scale(transform(
  534. UDim2.new(0,0,0,size-o-1),
  535. UDim2.new(0,size,0,1)
  536. ))
  537. t.Position = p
  538. t.Size = s
  539. t.Parent = Frame
  540. end
  541. return Frame
  542. end
  543.  
  544.  
  545. local function GripGraphic(size,dir,spacing,scaled,template)
  546. local Frame = Create('Frame',{
  547. Name = "Grip Graphic";
  548. BorderSizePixel = 0;
  549. Size = UDim2.new(0,size.x,0,size.y);
  550. Transparency = 1;
  551. })
  552. if not template then
  553. template = Instance.new("Frame")
  554. template.BorderSizePixel = 0
  555. end
  556.  
  557. spacing = spacing or 2
  558.  
  559. local scale
  560. if scaled then
  561. function scale(p) return UDim2.new(p.X.Offset/size.x,0,p.Y.Offset/size.y,0) end
  562. else
  563. function scale(p) return p end
  564. end
  565.  
  566. if dir == 'Vertical' then
  567. for i=0,size.x-1,spacing do
  568. local t = template:Clone()
  569. t.Size = scale(UDim2.new(0,1,0,size.y))
  570. t.Position = scale(UDim2.new(0,i,0,0))
  571. t.Parent = Frame
  572. end
  573. elseif dir == nil or dir == 'Horizontal' then
  574. for i=0,size.y-1,spacing do
  575. local t = template:Clone()
  576. t.Size = scale(UDim2.new(0,size.x,0,1))
  577. t.Position = scale(UDim2.new(0,0,0,i))
  578. t.Parent = Frame
  579. end
  580. end
  581.  
  582. return Frame
  583. end
  584.  
  585. local mt = {
  586. __index = {
  587. GetScrollPercent = function(self)
  588. return self.ScrollIndex/(self.TotalSpace-self.VisibleSpace)
  589. end;
  590. CanScrollDown = function(self)
  591. return self.ScrollIndex + self.VisibleSpace < self.TotalSpace
  592. end;
  593. CanScrollUp = function(self)
  594. return self.ScrollIndex > 0
  595. end;
  596. ScrollDown = function(self)
  597. self.ScrollIndex = self.ScrollIndex + self.PageIncrement
  598. self:Update()
  599. end;
  600. ScrollUp = function(self)
  601. self.ScrollIndex = self.ScrollIndex - self.PageIncrement
  602. self:Update()
  603. end;
  604. ScrollTo = function(self,index)
  605. self.ScrollIndex = index
  606. self:Update()
  607. end;
  608. SetScrollPercent = function(self,percent)
  609. self.ScrollIndex = math.floor((self.TotalSpace - self.VisibleSpace)*percent + 0.5)
  610. self:Update()
  611. end;
  612. };
  613. }
  614. mt.__index.CanScrollRight = mt.__index.CanScrollDown
  615. mt.__index.CanScrollLeft = mt.__index.CanScrollUp
  616. mt.__index.ScrollLeft = mt.__index.ScrollUp
  617. mt.__index.ScrollRight = mt.__index.ScrollDown
  618.  
  619. function ScrollBar(horizontal)
  620. -- create row scroll bar
  621. local ScrollFrame = Create('Frame',{
  622. Name = "ScrollFrame";
  623. Position = horizontal and UDim2.new(0,0,1,-GUI_SIZE) or UDim2.new(1,-GUI_SIZE,0,0);
  624. Size = horizontal and UDim2.new(1,0,0,GUI_SIZE) or UDim2.new(0,GUI_SIZE,1,0);
  625. BackgroundTransparency = 1;
  626. Create('ImageButton',{
  627. Name = "ScrollDown";
  628. Position = horizontal and UDim2.new(1,-GUI_SIZE,0,0) or UDim2.new(0,0,1,-GUI_SIZE);
  629. Size = UDim2.new(0, GUI_SIZE, 0, GUI_SIZE);
  630. BackgroundColor3 = GuiColor.Button;
  631. BorderColor3 = GuiColor.Border;
  632. --BorderSizePixel = 0;
  633. });
  634. Create('ImageButton',{
  635. Name = "ScrollUp";
  636. Size = UDim2.new(0, GUI_SIZE, 0, GUI_SIZE);
  637. BackgroundColor3 = GuiColor.Button;
  638. BorderColor3 = GuiColor.Border;
  639. --BorderSizePixel = 0;
  640. });
  641. Create('ImageButton',{
  642. Name = "ScrollBar";
  643. Size = horizontal and UDim2.new(1,-GUI_SIZE*2,1,0) or UDim2.new(1,0,1,-GUI_SIZE*2);
  644. Position = horizontal and UDim2.new(0,GUI_SIZE,0,0) or UDim2.new(0,0,0,GUI_SIZE);
  645. AutoButtonColor = false;
  646. BackgroundColor3 = Color3.new(0.94902, 0.94902, 0.94902);
  647. BorderColor3 = GuiColor.Border;
  648. --BorderSizePixel = 0;
  649. Create('ImageButton',{
  650. Name = "ScrollThumb";
  651. AutoButtonColor = false;
  652. Size = UDim2.new(0, GUI_SIZE, 0, GUI_SIZE);
  653. BackgroundColor3 = GuiColor.Button;
  654. BorderColor3 = GuiColor.Border;
  655. --BorderSizePixel = 0;
  656. });
  657. });
  658. })
  659.  
  660. local graphicTemplate = Create('Frame',{
  661. Name="Graphic";
  662. BorderSizePixel = 0;
  663. BackgroundColor3 = GuiColor.Border;
  664. })
  665. local graphicSize = GUI_SIZE/2
  666.  
  667. local ScrollDownFrame = ScrollFrame.ScrollDown
  668. local ScrollDownGraphic = ArrowGraphic(graphicSize,horizontal and 'Right' or 'Down',true,graphicTemplate)
  669. ScrollDownGraphic.Position = UDim2.new(0.5,-graphicSize/2,0.5,-graphicSize/2)
  670. ScrollDownGraphic.Parent = ScrollDownFrame
  671. local ScrollUpFrame = ScrollFrame.ScrollUp
  672. local ScrollUpGraphic = ArrowGraphic(graphicSize,horizontal and 'Left' or 'Up',true,graphicTemplate)
  673. ScrollUpGraphic.Position = UDim2.new(0.5,-graphicSize/2,0.5,-graphicSize/2)
  674. ScrollUpGraphic.Parent = ScrollUpFrame
  675. local ScrollBarFrame = ScrollFrame.ScrollBar
  676. local ScrollThumbFrame = ScrollBarFrame.ScrollThumb
  677. do
  678. local size = GUI_SIZE*3/8
  679. local Decal = GripGraphic(Vector2.new(size,size),horizontal and 'Vertical' or 'Horizontal',2,graphicTemplate)
  680. Decal.Position = UDim2.new(0.5,-size/2,0.5,-size/2)
  681. Decal.Parent = ScrollThumbFrame
  682. end
  683.  
  684. local Class = setmetatable({
  685. GUI = ScrollFrame;
  686. ScrollIndex = 0;
  687. VisibleSpace = 0;
  688. TotalSpace = 0;
  689. PageIncrement = 1;
  690. },mt)
  691.  
  692. local UpdateScrollThumb
  693. if horizontal then
  694. function UpdateScrollThumb()
  695. ScrollThumbFrame.Size = UDim2.new(Class.VisibleSpace/Class.TotalSpace,0,0,GUI_SIZE)
  696. if ScrollThumbFrame.AbsoluteSize.x < GUI_SIZE then
  697. ScrollThumbFrame.Size = UDim2.new(0,GUI_SIZE,0,GUI_SIZE)
  698. end
  699. local barSize = ScrollBarFrame.AbsoluteSize.x
  700. ScrollThumbFrame.Position = UDim2.new(Class:GetScrollPercent()*(barSize - ScrollThumbFrame.AbsoluteSize.x)/barSize,0,0,0)
  701. end
  702. else
  703. function UpdateScrollThumb()
  704. ScrollThumbFrame.Size = UDim2.new(0,GUI_SIZE,Class.VisibleSpace/Class.TotalSpace,0)
  705. if ScrollThumbFrame.AbsoluteSize.y < GUI_SIZE then
  706. ScrollThumbFrame.Size = UDim2.new(0,GUI_SIZE,0,GUI_SIZE)
  707. end
  708. local barSize = ScrollBarFrame.AbsoluteSize.y
  709. ScrollThumbFrame.Position = UDim2.new(0,0,Class:GetScrollPercent()*(barSize - ScrollThumbFrame.AbsoluteSize.y)/barSize,0)
  710. end
  711. end
  712.  
  713. local lastDown
  714. local lastUp
  715. local scrollStyle = {BackgroundColor3=GuiColor.Border,BackgroundTransparency=0}
  716. local scrollStyle_ds = {BackgroundColor3=GuiColor.Border,BackgroundTransparency=0.7}
  717.  
  718. local function Update()
  719. local t = Class.TotalSpace
  720. local v = Class.VisibleSpace
  721. local s = Class.ScrollIndex
  722. if v <= t then
  723. if s > 0 then
  724. if s + v > t then
  725. Class.ScrollIndex = t - v
  726. end
  727. else
  728. Class.ScrollIndex = 0
  729. end
  730. else
  731. Class.ScrollIndex = 0
  732. end
  733.  
  734. if Class.UpdateCallback then
  735. if Class.UpdateCallback(Class) == false then
  736. return
  737. end
  738. end
  739.  
  740. local down = Class:CanScrollDown()
  741. local up = Class:CanScrollUp()
  742. if down ~= lastDown then
  743. lastDown = down
  744. ScrollDownFrame.Active = down
  745. ScrollDownFrame.AutoButtonColor = down
  746. local children = ScrollDownGraphic:GetChildren()
  747. local style = down and scrollStyle or scrollStyle_ds
  748. for i = 1,#children do
  749. Create(children[i],style)
  750. end
  751. end
  752. if up ~= lastUp then
  753. lastUp = up
  754. ScrollUpFrame.Active = up
  755. ScrollUpFrame.AutoButtonColor = up
  756. local children = ScrollUpGraphic:GetChildren()
  757. local style = up and scrollStyle or scrollStyle_ds
  758. for i = 1,#children do
  759. Create(children[i],style)
  760. end
  761. end
  762. ScrollThumbFrame.Visible = down or up
  763. UpdateScrollThumb()
  764. end
  765. Class.Update = Update
  766.  
  767. SetZIndexOnChanged(ScrollFrame)
  768.  
  769. local MouseDrag = Create('ImageButton',{
  770. Name = "MouseDrag";
  771. Position = UDim2.new(-0.25,0,-0.25,0);
  772. Size = UDim2.new(1.5,0,1.5,0);
  773. Transparency = 1;
  774. AutoButtonColor = false;
  775. Active = true;
  776. ZIndex = 10;
  777. })
  778.  
  779. local scrollEventID = 0
  780. ScrollDownFrame.MouseButton1Down:connect(function()
  781. scrollEventID = tick()
  782. local current = scrollEventID
  783. local up_con
  784. up_con = MouseDrag.MouseButton1Up:connect(function()
  785. scrollEventID = tick()
  786. MouseDrag.Parent = nil
  787. ResetButtonColor(ScrollDownFrame)
  788. up_con:disconnect(); drag = nil
  789. end)
  790. MouseDrag.Parent = GetScreen(ScrollFrame)
  791. Class:ScrollDown()
  792. wait(0.2) -- delay before auto scroll
  793. while scrollEventID == current do
  794. Class:ScrollDown()
  795. if not Class:CanScrollDown() then break end
  796. wait()
  797. end
  798. end)
  799.  
  800. ScrollDownFrame.MouseButton1Up:connect(function()
  801. scrollEventID = tick()
  802. end)
  803.  
  804. ScrollUpFrame.MouseButton1Down:connect(function()
  805. scrollEventID = tick()
  806. local current = scrollEventID
  807. local up_con
  808. up_con = MouseDrag.MouseButton1Up:connect(function()
  809. scrollEventID = tick()
  810. MouseDrag.Parent = nil
  811. ResetButtonColor(ScrollUpFrame)
  812. up_con:disconnect(); drag = nil
  813. end)
  814. MouseDrag.Parent = GetScreen(ScrollFrame)
  815. Class:ScrollUp()
  816. wait(0.2)
  817. while scrollEventID == current do
  818. Class:ScrollUp()
  819. if not Class:CanScrollUp() then break end
  820. wait()
  821. end
  822. end)
  823.  
  824. ScrollUpFrame.MouseButton1Up:connect(function()
  825. scrollEventID = tick()
  826. end)
  827.  
  828. if horizontal then
  829. ScrollBarFrame.MouseButton1Down:connect(function(x,y)
  830. scrollEventID = tick()
  831. local current = scrollEventID
  832. local up_con
  833. up_con = MouseDrag.MouseButton1Up:connect(function()
  834. scrollEventID = tick()
  835. MouseDrag.Parent = nil
  836. ResetButtonColor(ScrollUpFrame)
  837. up_con:disconnect(); drag = nil
  838. end)
  839. MouseDrag.Parent = GetScreen(ScrollFrame)
  840. if x > ScrollThumbFrame.AbsolutePosition.x then
  841. Class:ScrollTo(Class.ScrollIndex + Class.VisibleSpace)
  842. wait(0.2)
  843. while scrollEventID == current do
  844. if x < ScrollThumbFrame.AbsolutePosition.x + ScrollThumbFrame.AbsoluteSize.x then break end
  845. Class:ScrollTo(Class.ScrollIndex + Class.VisibleSpace)
  846. wait()
  847. end
  848. else
  849. Class:ScrollTo(Class.ScrollIndex - Class.VisibleSpace)
  850. wait(0.2)
  851. while scrollEventID == current do
  852. if x > ScrollThumbFrame.AbsolutePosition.x then break end
  853. Class:ScrollTo(Class.ScrollIndex - Class.VisibleSpace)
  854. wait()
  855. end
  856. end
  857. end)
  858. else
  859. ScrollBarFrame.MouseButton1Down:connect(function(x,y)
  860. scrollEventID = tick()
  861. local current = scrollEventID
  862. local up_con
  863. up_con = MouseDrag.MouseButton1Up:connect(function()
  864. scrollEventID = tick()
  865. MouseDrag.Parent = nil
  866. ResetButtonColor(ScrollUpFrame)
  867. up_con:disconnect(); drag = nil
  868. end)
  869. MouseDrag.Parent = GetScreen(ScrollFrame)
  870. if y > ScrollThumbFrame.AbsolutePosition.y then
  871. Class:ScrollTo(Class.ScrollIndex + Class.VisibleSpace)
  872. wait(0.2)
  873. while scrollEventID == current do
  874. if y < ScrollThumbFrame.AbsolutePosition.y + ScrollThumbFrame.AbsoluteSize.y then break end
  875. Class:ScrollTo(Class.ScrollIndex + Class.VisibleSpace)
  876. wait()
  877. end
  878. else
  879. Class:ScrollTo(Class.ScrollIndex - Class.VisibleSpace)
  880. wait(0.2)
  881. while scrollEventID == current do
  882. if y > ScrollThumbFrame.AbsolutePosition.y then break end
  883. Class:ScrollTo(Class.ScrollIndex - Class.VisibleSpace)
  884. wait()
  885. end
  886. end
  887. end)
  888. end
  889.  
  890. if horizontal then
  891. ScrollThumbFrame.MouseButton1Down:connect(function(x,y)
  892. scrollEventID = tick()
  893. local mouse_offset = x - ScrollThumbFrame.AbsolutePosition.x
  894. local drag_con
  895. local up_con
  896. drag_con = MouseDrag.MouseMoved:connect(function(x,y)
  897. local bar_abs_pos = ScrollBarFrame.AbsolutePosition.x
  898. local bar_drag = ScrollBarFrame.AbsoluteSize.x - ScrollThumbFrame.AbsoluteSize.x
  899. local bar_abs_one = bar_abs_pos + bar_drag
  900. x = x - mouse_offset
  901. x = x < bar_abs_pos and bar_abs_pos or x > bar_abs_one and bar_abs_one or x
  902. x = x - bar_abs_pos
  903. Class:SetScrollPercent(x/(bar_drag))
  904. end)
  905. up_con = MouseDrag.MouseButton1Up:connect(function()
  906. scrollEventID = tick()
  907. MouseDrag.Parent = nil
  908. ResetButtonColor(ScrollThumbFrame)
  909. drag_con:disconnect(); drag_con = nil
  910. up_con:disconnect(); drag = nil
  911. end)
  912. MouseDrag.Parent = GetScreen(ScrollFrame)
  913. end)
  914. else
  915. ScrollThumbFrame.MouseButton1Down:connect(function(x,y)
  916. scrollEventID = tick()
  917. local mouse_offset = y - ScrollThumbFrame.AbsolutePosition.y
  918. local drag_con
  919. local up_con
  920. drag_con = MouseDrag.MouseMoved:connect(function(x,y)
  921. local bar_abs_pos = ScrollBarFrame.AbsolutePosition.y
  922. local bar_drag = ScrollBarFrame.AbsoluteSize.y - ScrollThumbFrame.AbsoluteSize.y
  923. local bar_abs_one = bar_abs_pos + bar_drag
  924. y = y - mouse_offset
  925. y = y < bar_abs_pos and bar_abs_pos or y > bar_abs_one and bar_abs_one or y
  926. y = y - bar_abs_pos
  927. Class:SetScrollPercent(y/(bar_drag))
  928. end)
  929. up_con = MouseDrag.MouseButton1Up:connect(function()
  930. scrollEventID = tick()
  931. MouseDrag.Parent = nil
  932. ResetButtonColor(ScrollThumbFrame)
  933. drag_con:disconnect(); drag_con = nil
  934. up_con:disconnect(); drag = nil
  935. end)
  936. MouseDrag.Parent = GetScreen(ScrollFrame)
  937. end)
  938. end
  939.  
  940. function Class:Destroy()
  941. ScrollFrame:Destroy()
  942. MouseDrag:Destroy()
  943. for k in pairs(Class) do
  944. Class[k] = nil
  945. end
  946. setmetatable(Class,nil)
  947. end
  948.  
  949. Update()
  950.  
  951. return Class
  952. end
  953. end
  954.  
  955. ----------------------------------------------------------------
  956. ----------------------------------------------------------------
  957. ----------------------------------------------------------------
  958. ----------------------------------------------------------------
  959. ---- Explorer panel
  960.  
  961. local explorerPanel = script.Parent
  962. Create(explorerPanel,{
  963. BackgroundColor3 = GuiColor.Field;
  964. BorderColor3 = GuiColor.Border;
  965. Active = true;
  966. })
  967.  
  968. local listFrame = Create('Frame',{
  969. Name = "List";
  970. BackgroundTransparency = 1;
  971. ClipsDescendants = true;
  972. Position = UDim2.new(0,0,0,HEADER_SIZE);
  973. Size = UDim2.new(1,-GUI_SIZE,1,-HEADER_SIZE);
  974. Parent = explorerPanel;
  975. })
  976.  
  977. local scrollBar = ScrollBar(false)
  978. scrollBar.PageIncrement = 1
  979. Create(scrollBar.GUI,{
  980. Position = UDim2.new(1,-GUI_SIZE,0,HEADER_SIZE);
  981. Size = UDim2.new(0,GUI_SIZE,1,-HEADER_SIZE);
  982. Parent = explorerPanel;
  983. })
  984.  
  985. local scrollBarH = ScrollBar(true)
  986. scrollBarH.PageIncrement = GUI_SIZE
  987. Create(scrollBarH.GUI,{
  988. Position = UDim2.new(0,0,1,-GUI_SIZE);
  989. Size = UDim2.new(1,-GUI_SIZE,0,GUI_SIZE);
  990. Visible = false;
  991. Parent = explorerPanel;
  992. })
  993.  
  994. local headerFrame = Create('Frame',{
  995. Name = "Header";
  996. BackgroundColor3 = GuiColor.Background;
  997. BorderColor3 = GuiColor.Border;
  998. Position = UDim2.new(0,0,0,0);
  999. Size = UDim2.new(1,0,0,HEADER_SIZE);
  1000. Parent = explorerPanel;
  1001. Create('TextLabel',{
  1002. Text = "Explorer";
  1003. BackgroundTransparency = 1;
  1004. TextColor3 = GuiColor.Text;
  1005. TextXAlignment = 'Left';
  1006. Font = FONT;
  1007. FontSize = FONT_SIZE;
  1008. Position = UDim2.new(0,4,0,0);
  1009. Size = UDim2.new(1,-4,1,0);
  1010. });
  1011. })
  1012.  
  1013. SetZIndexOnChanged(explorerPanel)
  1014.  
  1015. local getTextWidth do
  1016. local text = Create('TextLabel',{
  1017. Name = "TextWidth";
  1018. TextXAlignment = 'Left';
  1019. TextYAlignment = 'Center';
  1020. Font = FONT;
  1021. FontSize = FONT_SIZE;
  1022. Text = "";
  1023. Position = UDim2.new(0,0,0,0);
  1024. Size = UDim2.new(1,0,1,0);
  1025. Visible = false;
  1026. Parent = explorerPanel;
  1027. })
  1028. function getTextWidth(s)
  1029. text.Text = s
  1030. return text.TextBounds.x
  1031. end
  1032. end
  1033.  
  1034. -- Holds the game tree converted to a list.
  1035. local TreeList = {}
  1036. -- Matches objects to their tree node representation.
  1037. local NodeLookup = {}
  1038.  
  1039. local nodeWidth = 0
  1040.  
  1041. local updateList,rawUpdateList,updateScroll,rawUpdateSize do
  1042. local function r(t)
  1043. for i = 1,#t do
  1044. TreeList[#TreeList+1] = t[i]
  1045.  
  1046. local w = (t[i].Depth)*(2+ENTRY_PADDING+GUI_SIZE) + 2 + ENTRY_SIZE + 4 + getTextWidth(t[i].Object.Name) + 4
  1047. if w > nodeWidth then
  1048. nodeWidth = w
  1049. end
  1050. if t[i].Expanded then
  1051. r(t[i])
  1052. end
  1053. end
  1054. end
  1055.  
  1056. function rawUpdateSize()
  1057. scrollBarH.TotalSpace = nodeWidth
  1058. scrollBarH.VisibleSpace = listFrame.AbsoluteSize.x
  1059. scrollBarH:Update()
  1060. local visible = scrollBarH:CanScrollDown() or scrollBarH:CanScrollUp()
  1061. scrollBarH.GUI.Visible = visible
  1062.  
  1063. listFrame.Size = UDim2.new(1,-GUI_SIZE,1,-GUI_SIZE*(visible and 1 or 0) - HEADER_SIZE)
  1064.  
  1065. scrollBar.VisibleSpace = math.ceil(listFrame.AbsoluteSize.y/ENTRY_BOUND)
  1066. scrollBar.GUI.Size = UDim2.new(0,GUI_SIZE,1,-GUI_SIZE*(visible and 1 or 0) - HEADER_SIZE)
  1067.  
  1068. scrollBar.TotalSpace = #TreeList+1
  1069. scrollBar:Update()
  1070. end
  1071.  
  1072. function rawUpdateList()
  1073. -- Clear then repopulate the entire list. It appears to be fast enough.
  1074. TreeList = {}
  1075. nodeWidth = 0
  1076. r(NodeLookup[Game])
  1077. rawUpdateSize()
  1078. end
  1079.  
  1080. -- Adding or removing large models will cause many updates to occur. We
  1081. -- can reduce the number of updates by creating a delay, then dropping any
  1082. -- updates that occur during the delay.
  1083. local updatingList = false
  1084. function updateList()
  1085. if updatingList then return end
  1086. updatingList = true
  1087. wait(0.25)
  1088. updatingList = false
  1089. rawUpdateList()
  1090. end
  1091.  
  1092. local updatingScroll = false
  1093. function updateScroll()
  1094. if updatingScroll then return end
  1095. updatingScroll = true
  1096. wait(0.25)
  1097. updatingScroll = false
  1098. scrollBar:Update()
  1099. end
  1100. end
  1101.  
  1102. local Selection do
  1103. local bindGetSelection = script.Parent:FindFirstChild("GetSelection")
  1104. if not bindGetSelection then
  1105. bindGetSelection = Create('BindableFunction',{Name = "GetSelection"})
  1106. bindGetSelection.Parent = script.Parent
  1107. end
  1108.  
  1109. local bindSetSelection = script.Parent:FindFirstChild("SetSelection")
  1110. if not bindSetSelection then
  1111. bindSetSelection = Create('BindableFunction',{Name = "SetSelection"})
  1112. bindSetSelection.Parent = script.Parent
  1113. end
  1114.  
  1115. local bindSelectionChanged = script.Parent:FindFirstChild("SelectionChanged")
  1116. if not bindSelectionChanged then
  1117. bindSelectionChanged = Create('BindableEvent',{Name = "SelectionChanged"})
  1118. bindSelectionChanged.Parent = script.Parent
  1119. end
  1120.  
  1121. local SelectionList = {}
  1122. local SelectionSet = {}
  1123. Selection = {
  1124. Selected = SelectionSet;
  1125. List = SelectionList;
  1126. }
  1127.  
  1128. local function addObject(object)
  1129. -- list update
  1130. local lupdate = false
  1131. -- scroll update
  1132. local supdate = false
  1133.  
  1134. if not SelectionSet[object] then
  1135. local node = NodeLookup[object]
  1136. if node then
  1137. table.insert(SelectionList,object)
  1138. SelectionSet[object] = true
  1139. node.Selected = true
  1140.  
  1141. -- expand all ancestors so that selected node becomes visible
  1142. node = node.Parent
  1143. while node do
  1144. if not node.Expanded then
  1145. node.Expanded = true
  1146. lupdate = true
  1147. end
  1148. node = node.Parent
  1149. end
  1150. supdate = true
  1151. end
  1152. end
  1153. return lupdate,supdate
  1154. end
  1155.  
  1156. function Selection:Set(objects)
  1157. local lupdate = false
  1158. local supdate = false
  1159.  
  1160. if #SelectionList > 0 then
  1161. for i = 1,#SelectionList do
  1162. local object = SelectionList[i]
  1163. local node = NodeLookup[object]
  1164. if node then
  1165. node.Selected = false
  1166. SelectionSet[object] = nil
  1167. end
  1168. end
  1169.  
  1170. SelectionList = {}
  1171. Selection.List = SelectionList
  1172. supdate = true
  1173. end
  1174.  
  1175. for i = 1,#objects do
  1176. local l,s = addObject(objects[i])
  1177. lupdate = l or lupdate
  1178. supdate = s or supdate
  1179. end
  1180.  
  1181. if lupdate then
  1182. rawUpdateList()
  1183. supdate = true
  1184. elseif supdate then
  1185. scrollBar:Update()
  1186. end
  1187.  
  1188. if supdate then
  1189. bindSelectionChanged:Fire()
  1190. end
  1191. end
  1192.  
  1193. function Selection:Add(object)
  1194. local l,s = addObject(object)
  1195. if l then
  1196. rawUpdateList()
  1197. bindSelectionChanged:Fire()
  1198. elseif s then
  1199. scrollBar:Update()
  1200. bindSelectionChanged:Fire()
  1201. end
  1202. end
  1203.  
  1204. function Selection:Remove(object,noupdate)
  1205. if SelectionSet[object] then
  1206. local node = NodeLookup[object]
  1207. if node then
  1208. node.Selected = false
  1209. SelectionSet[object] = nil
  1210. for i = 1,#SelectionList do
  1211. if SelectionList[i] == object then
  1212. table.remove(SelectionList,i)
  1213. break
  1214. end
  1215. end
  1216.  
  1217. if not noupdate then
  1218. scrollBar:Update()
  1219. end
  1220. bindSelectionChanged:Fire()
  1221. end
  1222. end
  1223. end
  1224.  
  1225. function Selection:Get()
  1226. local list = {}
  1227. for i = 1,#SelectionList do
  1228. list[i] = SelectionList[i]
  1229. end
  1230. return list
  1231. end
  1232.  
  1233. bindSetSelection.OnInvoke = function(...)
  1234. Selection:Set(...)
  1235. end
  1236.  
  1237. bindGetSelection.OnInvoke = function()
  1238. return Selection:Get()
  1239. end
  1240. end
  1241.  
  1242. local function cancelReparentDrag()end
  1243. local function cancelSelectDrag()end
  1244. do
  1245. local listEntries = {}
  1246. local nameConnLookup = {}
  1247.  
  1248. local mouseDrag = Create('ImageButton',{
  1249. Name = "MouseDrag";
  1250. Position = UDim2.new(-0.25,0,-0.25,0);
  1251. Size = UDim2.new(1.5,0,1.5,0);
  1252. Transparency = 1;
  1253. AutoButtonColor = false;
  1254. Active = true;
  1255. ZIndex = 10;
  1256. })
  1257. local function dragSelect(last,add,button)
  1258. local connDrag
  1259. local conUp
  1260.  
  1261. conDrag = mouseDrag.MouseMoved:connect(function(x,y)
  1262. local pos = Vector2.new(x,y) - listFrame.AbsolutePosition
  1263. local size = listFrame.AbsoluteSize
  1264. if pos.x < 0 or pos.x > size.x or pos.y < 0 or pos.y > size.y then return end
  1265.  
  1266. local i = math.ceil(pos.y/ENTRY_BOUND) + scrollBar.ScrollIndex
  1267. -- Mouse may have made a large step, so interpolate between the
  1268. -- last index and the current.
  1269. for n = i<last and i or last, i>last and i or last do
  1270. local node = TreeList[n]
  1271. if node then
  1272. if add then
  1273. Selection:Add(node.Object)
  1274. else
  1275. Selection:Remove(node.Object)
  1276. end
  1277. end
  1278. end
  1279. last = i
  1280. end)
  1281.  
  1282. function cancelSelectDrag()
  1283. mouseDrag.Parent = nil
  1284. conDrag:disconnect()
  1285. conUp:disconnect()
  1286. function cancelSelectDrag()end
  1287. end
  1288.  
  1289. conUp = mouseDrag[button]:connect(cancelSelectDrag)
  1290.  
  1291. mouseDrag.Parent = GetScreen(listFrame)
  1292. end
  1293.  
  1294. local function dragReparent(object,dragGhost,clickPos,ghostOffset)
  1295. local connDrag
  1296. local conUp
  1297. local conUp2
  1298.  
  1299. local parentIndex = nil
  1300. local dragged = false
  1301.  
  1302. local parentHighlight = Create('Frame',{
  1303. Transparency = 1;
  1304. Visible = false;
  1305. Create('Frame',{
  1306. BorderSizePixel = 0;
  1307. BackgroundColor3 = Color3.new(0,0,0);
  1308. BackgroundTransparency = 0.1;
  1309. Position = UDim2.new(0,0,0,0);
  1310. Size = UDim2.new(1,0,0,1);
  1311. });
  1312. Create('Frame',{
  1313. BorderSizePixel = 0;
  1314. BackgroundColor3 = Color3.new(0,0,0);
  1315. BackgroundTransparency = 0.1;
  1316. Position = UDim2.new(1,0,0,0);
  1317. Size = UDim2.new(0,1,1,0);
  1318. });
  1319. Create('Frame',{
  1320. BorderSizePixel = 0;
  1321. BackgroundColor3 = Color3.new(0,0,0);
  1322. BackgroundTransparency = 0.1;
  1323. Position = UDim2.new(0,0,1,0);
  1324. Size = UDim2.new(1,0,0,1);
  1325. });
  1326. Create('Frame',{
  1327. BorderSizePixel = 0;
  1328. BackgroundColor3 = Color3.new(0,0,0);
  1329. BackgroundTransparency = 0.1;
  1330. Position = UDim2.new(0,0,0,0);
  1331. Size = UDim2.new(0,1,1,0);
  1332. });
  1333. })
  1334. SetZIndex(parentHighlight,9)
  1335.  
  1336. conDrag = mouseDrag.MouseMoved:connect(function(x,y)
  1337. local dragPos = Vector2.new(x,y)
  1338. if dragged then
  1339. local pos = dragPos - listFrame.AbsolutePosition
  1340. local size = listFrame.AbsoluteSize
  1341.  
  1342. parentIndex = nil
  1343. parentHighlight.Visible = false
  1344. if pos.x >= 0 and pos.x <= size.x and pos.y >= 0 and pos.y <= size.y then
  1345. local i = math.ceil(pos.y/ENTRY_BOUND)
  1346. local node = TreeList[i + scrollBar.ScrollIndex]
  1347. if node and node.Object ~= object and not object:IsAncestorOf(node.Object) then
  1348. parentIndex = i
  1349. local entry = listEntries[i]
  1350. if entry then
  1351. parentHighlight.Visible = true
  1352. parentHighlight.Position = UDim2.new(0,1,0,entry.AbsolutePosition.y-listFrame.AbsolutePosition.y)
  1353. parentHighlight.Size = UDim2.new(0,size.x-4,0,entry.AbsoluteSize.y)
  1354. end
  1355. end
  1356. end
  1357.  
  1358. dragGhost.Position = UDim2.new(0,dragPos.x+ghostOffset.x,0,dragPos.y+ghostOffset.y)
  1359. elseif (clickPos-dragPos).magnitude > 8 then
  1360. dragged = true
  1361. SetZIndex(dragGhost,9)
  1362. dragGhost.IndentFrame.Transparency = 0.25
  1363. dragGhost.IndentFrame.EntryText.TextColor3 = GuiColor.TextSelected
  1364. dragGhost.Position = UDim2.new(0,dragPos.x+ghostOffset.x,0,dragPos.y+ghostOffset.y)
  1365. dragGhost.Parent = GetScreen(listFrame)
  1366. parentHighlight.Parent = listFrame
  1367. end
  1368. end)
  1369.  
  1370. function cancelReparentDrag()
  1371. mouseDrag.Parent = nil
  1372. conDrag:disconnect()
  1373. conUp:disconnect()
  1374. conUp2:disconnect()
  1375. dragGhost:Destroy()
  1376. parentHighlight:Destroy()
  1377. function cancelReparentDrag()end
  1378. end
  1379.  
  1380. local wasSelected = Selection.Selected[object]
  1381. if not wasSelected and Option.Selectable then
  1382. Selection:Set({object})
  1383. end
  1384.  
  1385. conUp = mouseDrag.MouseButton1Up:connect(function()
  1386. cancelReparentDrag()
  1387. if dragged then
  1388. if parentIndex then
  1389. local parentNode = TreeList[parentIndex + scrollBar.ScrollIndex]
  1390. if parentNode then
  1391. parentNode.Expanded = true
  1392.  
  1393. local parentObj = parentNode.Object
  1394. local function parent(a,b)
  1395. a.Parent = b
  1396. end
  1397. if Option.Selectable then
  1398. local list = Selection.List
  1399. for i = 1,#list do
  1400. pcall(parent,list[i],parentObj)
  1401. end
  1402. else
  1403. pcall(parent,object,parentObj)
  1404. end
  1405. end
  1406. end
  1407. else
  1408. -- do selection click
  1409. if wasSelected and Option.Selectable then
  1410. Selection:Set({})
  1411. end
  1412. end
  1413. end)
  1414. conUp2 = mouseDrag.MouseButton2Down:connect(function()
  1415. cancelReparentDrag()
  1416. end)
  1417.  
  1418. mouseDrag.Parent = GetScreen(listFrame)
  1419. end
  1420.  
  1421. local entryTemplate = Create('ImageButton',{
  1422. Name = "Entry";
  1423. Transparency = 1;
  1424. AutoButtonColor = false;
  1425. Position = UDim2.new(0,0,0,0);
  1426. Size = UDim2.new(1,0,0,ENTRY_SIZE);
  1427. Create('Frame',{
  1428. Name = "IndentFrame";
  1429. BackgroundTransparency = 1;
  1430. BackgroundColor3 = GuiColor.Selected;
  1431. BorderColor3 = GuiColor.BorderSelected;
  1432. Position = UDim2.new(0,0,0,0);
  1433. Size = UDim2.new(1,0,1,0);
  1434. Create(Icon('ImageButton',0),{
  1435. Name = "Expand";
  1436. AutoButtonColor = false;
  1437. Position = UDim2.new(0,-GUI_SIZE,0.5,-GUI_SIZE/2);
  1438. Size = UDim2.new(0,GUI_SIZE,0,GUI_SIZE);
  1439. });
  1440. Create(Icon(nil,0),{
  1441. Name = "ExplorerIcon";
  1442. Position = UDim2.new(0,2+ENTRY_PADDING,0.5,-GUI_SIZE/2);
  1443. Size = UDim2.new(0,GUI_SIZE,0,GUI_SIZE);
  1444. });
  1445. Create('TextLabel',{
  1446. Name = "EntryText";
  1447. BackgroundTransparency = 1;
  1448. TextColor3 = GuiColor.Text;
  1449. TextXAlignment = 'Left';
  1450. TextYAlignment = 'Center';
  1451. Font = FONT;
  1452. FontSize = FONT_SIZE;
  1453. Text = "";
  1454. Position = UDim2.new(0,2+ENTRY_SIZE+4,0,0);
  1455. Size = UDim2.new(1,-2,1,0);
  1456. });
  1457. });
  1458. })
  1459.  
  1460. function scrollBar.UpdateCallback(self)
  1461. for i = 1,self.VisibleSpace do
  1462. local node = TreeList[i + self.ScrollIndex]
  1463. if node then
  1464. local entry = listEntries[i]
  1465. if not entry then
  1466. entry = Create(entryTemplate:Clone(),{
  1467. Position = UDim2.new(0,2,0,ENTRY_BOUND*(i-1)+2);
  1468. Size = UDim2.new(0,nodeWidth,0,ENTRY_SIZE);
  1469. ZIndex = listFrame.ZIndex;
  1470. })
  1471. listEntries[i] = entry
  1472.  
  1473. local expand = entry.IndentFrame.Expand
  1474. expand.MouseEnter:connect(function()
  1475. local node = TreeList[i + self.ScrollIndex]
  1476. if #node > 0 then
  1477. if node.Expanded then
  1478. Icon(expand,NODE_EXPANDED_OVER)
  1479. else
  1480. Icon(expand,NODE_COLLAPSED_OVER)
  1481. end
  1482. end
  1483. end)
  1484. expand.MouseLeave:connect(function()
  1485. local node = TreeList[i + self.ScrollIndex]
  1486. if #node > 0 then
  1487. if node.Expanded then
  1488. Icon(expand,NODE_EXPANDED)
  1489. else
  1490. Icon(expand,NODE_COLLAPSED)
  1491. end
  1492. end
  1493. end)
  1494. expand.MouseButton1Down:connect(function()
  1495. local node = TreeList[i + self.ScrollIndex]
  1496. if #node > 0 then
  1497. node.Expanded = not node.Expanded
  1498. -- use raw update so the list updates instantly
  1499. rawUpdateList()
  1500. end
  1501. end)
  1502.  
  1503. entry.MouseButton1Down:connect(function(x,y)
  1504. local node = TreeList[i + self.ScrollIndex]
  1505. if Option.Modifiable then
  1506. local pos = Vector2.new(x,y)
  1507. dragReparent(node.Object,entry:Clone(),pos,entry.AbsolutePosition-pos)
  1508. elseif Option.Selectable then
  1509. if Selection.Selected[node.Object] then
  1510. Selection:Set({})
  1511. else
  1512. Selection:Set({node.Object})
  1513. end
  1514. dragSelect(i+self.ScrollIndex,true,'MouseButton1Up')
  1515. end
  1516. end)
  1517.  
  1518. entry.MouseButton2Down:connect(function()
  1519. if not Option.Selectable then return end
  1520.  
  1521. local node = TreeList[i + self.ScrollIndex]
  1522. if Selection.Selected[node.Object] then
  1523. Selection:Remove(node.Object)
  1524. dragSelect(i+self.ScrollIndex,false,'MouseButton2Up')
  1525. else
  1526. Selection:Add(node.Object)
  1527. dragSelect(i+self.ScrollIndex,true,'MouseButton2Up')
  1528. end
  1529. end)
  1530.  
  1531. entry.Parent = listFrame
  1532. end
  1533.  
  1534. entry.Visible = true
  1535.  
  1536. local object = node.Object
  1537.  
  1538. -- update expand icon
  1539. if #node == 0 then
  1540. entry.IndentFrame.Expand.Visible = false
  1541. elseif node.Expanded then
  1542. Icon(entry.IndentFrame.Expand,NODE_EXPANDED)
  1543. entry.IndentFrame.Expand.Visible = true
  1544. else
  1545. Icon(entry.IndentFrame.Expand,NODE_COLLAPSED)
  1546. entry.IndentFrame.Expand.Visible = true
  1547. end
  1548.  
  1549. -- update explorer icon
  1550. Icon(entry.IndentFrame.ExplorerIcon,ExplorerIndex[object.ClassName] or 0)
  1551.  
  1552. -- update indentation
  1553. local w = (node.Depth)*(2+ENTRY_PADDING+GUI_SIZE)
  1554. entry.IndentFrame.Position = UDim2.new(0,w,0,0)
  1555. entry.IndentFrame.Size = UDim2.new(1,-w,1,0)
  1556.  
  1557. -- update name change detection
  1558. if nameConnLookup[entry] then
  1559. nameConnLookup[entry]:disconnect()
  1560. end
  1561. local text = entry.IndentFrame.EntryText
  1562. text.Text = object.Name
  1563. nameConnLookup[entry] = node.Object.Changed:connect(function(p)
  1564. if p == 'Name' then
  1565. text.Text = object.Name
  1566. end
  1567. end)
  1568.  
  1569. -- update selection
  1570. entry.IndentFrame.Transparency = node.Selected and 0 or 1
  1571. text.TextColor3 = GuiColor[node.Selected and 'TextSelected' or 'Text']
  1572.  
  1573. entry.Size = UDim2.new(0,nodeWidth,0,ENTRY_SIZE)
  1574. elseif listEntries[i] then
  1575. listEntries[i].Visible = false
  1576. end
  1577. end
  1578. for i = self.VisibleSpace+1,self.TotalSpace do
  1579. local entry = listEntries[i]
  1580. if entry then
  1581. listEntries[i] = nil
  1582. entry:Destroy()
  1583. end
  1584. end
  1585. end
  1586.  
  1587. function scrollBarH.UpdateCallback(self)
  1588. for i = 1,scrollBar.VisibleSpace do
  1589. local node = TreeList[i + scrollBar.ScrollIndex]
  1590. if node then
  1591. local entry = listEntries[i]
  1592. if entry then
  1593. entry.Position = UDim2.new(0,2 - scrollBarH.ScrollIndex,0,ENTRY_BOUND*(i-1)+2)
  1594. end
  1595. end
  1596. end
  1597. end
  1598.  
  1599. Connect(listFrame.Changed,function(p)
  1600. if p == 'AbsoluteSize' then
  1601. rawUpdateSize()
  1602. end
  1603. end)
  1604.  
  1605. local wheelAmount = 6
  1606. explorerPanel.MouseWheelForward:connect(function()
  1607. if scrollBar.VisibleSpace - 1 > wheelAmount then
  1608. scrollBar:ScrollTo(scrollBar.ScrollIndex - wheelAmount)
  1609. else
  1610. scrollBar:ScrollTo(scrollBar.ScrollIndex - scrollBar.VisibleSpace)
  1611. end
  1612. end)
  1613. explorerPanel.MouseWheelBackward:connect(function()
  1614. if scrollBar.VisibleSpace - 1 > wheelAmount then
  1615. scrollBar:ScrollTo(scrollBar.ScrollIndex + wheelAmount)
  1616. else
  1617. scrollBar:ScrollTo(scrollBar.ScrollIndex + scrollBar.VisibleSpace)
  1618. end
  1619. end)
  1620. end
  1621.  
  1622. ----------------------------------------------------------------
  1623. ----------------------------------------------------------------
  1624. ----------------------------------------------------------------
  1625. ----------------------------------------------------------------
  1626. ---- Object detection
  1627.  
  1628. -- Inserts `v` into `t` at `i`. Also sets `Index` field in `v`.
  1629. local function insert(t,i,v)
  1630. for n = #t,i,-1 do
  1631. local v = t[n]
  1632. v.Index = n+1
  1633. t[n+1] = v
  1634. end
  1635. v.Index = i
  1636. t[i] = v
  1637. end
  1638.  
  1639. -- Removes `i` from `t`. Also sets `Index` field in removed value.
  1640. local function remove(t,i)
  1641. local v = t[i]
  1642. for n = i+1,#t do
  1643. local v = t[n]
  1644. v.Index = n-1
  1645. t[n-1] = v
  1646. end
  1647. t[#t] = nil
  1648. v.Index = 0
  1649. return v
  1650. end
  1651.  
  1652. -- Returns how deep `o` is in the tree.
  1653. local function depth(o)
  1654. local d = -1
  1655. while o do
  1656. o = o.Parent
  1657. d = d + 1
  1658. end
  1659. return d
  1660. end
  1661.  
  1662.  
  1663. local connLookup = {}
  1664.  
  1665. -- Returns whether a node would be present in the tree list
  1666. local function nodeIsVisible(node)
  1667. local visible = true
  1668. node = node.Parent
  1669. while node and visible do
  1670. visible = visible and node.Expanded
  1671. node = node.Parent
  1672. end
  1673. return visible
  1674. end
  1675.  
  1676. -- Removes an object's tree node. Called when the object stops existing in the
  1677. -- game tree.
  1678. local function removeObject(object)
  1679. local objectNode = NodeLookup[object]
  1680. if not objectNode then
  1681. return
  1682. end
  1683.  
  1684. local visible = nodeIsVisible(objectNode)
  1685.  
  1686. Selection:Remove(object,true)
  1687.  
  1688. local parent = objectNode.Parent
  1689. remove(parent,objectNode.Index)
  1690. NodeLookup[object] = nil
  1691. connLookup[object]:disconnect()
  1692. connLookup[object] = nil
  1693.  
  1694. if visible then
  1695. updateList()
  1696. elseif nodeIsVisible(parent) then
  1697. updateScroll()
  1698. end
  1699. end
  1700.  
  1701. -- Moves a tree node to a new parent. Called when an existing object's parent
  1702. -- changes.
  1703. local function moveObject(object,parent)
  1704. local objectNode = NodeLookup[object]
  1705. if not objectNode then
  1706. return
  1707. end
  1708.  
  1709. local parentNode = NodeLookup[parent]
  1710. if not parentNode then
  1711. return
  1712. end
  1713.  
  1714. local visible = nodeIsVisible(objectNode)
  1715.  
  1716. remove(objectNode.Parent,objectNode.Index)
  1717. objectNode.Parent = parentNode
  1718.  
  1719. objectNode.Depth = depth(object)
  1720. local function r(node,d)
  1721. for i = 1,#node do
  1722. node[i].Depth = d
  1723. r(node[i],d+1)
  1724. end
  1725. end
  1726. r(objectNode,objectNode.Depth+1)
  1727.  
  1728. insert(parentNode,#parentNode+1,objectNode)
  1729.  
  1730. if visible or nodeIsVisible(objectNode) then
  1731. updateList()
  1732. elseif nodeIsVisible(objectNode.Parent) then
  1733. updateScroll()
  1734. end
  1735. end
  1736.  
  1737. -- ScriptContext['/Libraries/LibraryRegistration/LibraryRegistration']
  1738. -- This RobloxLocked object lets me index its properties for some reason
  1739.  
  1740. local function check(object)
  1741. return object.AncestryChanged
  1742. end
  1743.  
  1744. -- Creates a new tree node from an object. Called when an object starts
  1745. -- existing in the game tree.
  1746. local function addObject(object,noupdate)
  1747. if script then
  1748. -- protect against naughty RobloxLocked objects
  1749. local s = pcall(check,object)
  1750. if not s then
  1751. return
  1752. end
  1753. end
  1754.  
  1755. local parentNode = NodeLookup[object.Parent]
  1756. if not parentNode then
  1757. return
  1758. end
  1759.  
  1760. local objectNode = {
  1761. Object = object;
  1762. Parent = parentNode;
  1763. Index = 0;
  1764. Expanded = false;
  1765. Selected = false;
  1766. Depth = depth(object);
  1767. }
  1768.  
  1769. connLookup[object] = Connect(object.AncestryChanged,function(c,p)
  1770. if c == object then
  1771. if p == nil then
  1772. removeObject(c)
  1773. else
  1774. moveObject(c,p)
  1775. end
  1776. end
  1777. end)
  1778.  
  1779. NodeLookup[object] = objectNode
  1780. insert(parentNode,#parentNode+1,objectNode)
  1781.  
  1782. if not noupdate then
  1783. if nodeIsVisible(objectNode) then
  1784. updateList()
  1785. elseif nodeIsVisible(objectNode.Parent) then
  1786. updateScroll()
  1787. end
  1788. end
  1789. end
  1790.  
  1791. do
  1792. NodeLookup[Game] = {
  1793. Object = Game;
  1794. Parent = nil;
  1795. Index = 0;
  1796. Expanded = true;
  1797. }
  1798.  
  1799. Connect(Game.DescendantAdded,addObject)
  1800. Connect(Game.DescendantRemoving,removeObject)
  1801.  
  1802. local function get(o)
  1803. return o:GetChildren()
  1804. end
  1805.  
  1806. local function r(o)
  1807. local s,children = pcall(get,o)
  1808. if s then
  1809. for i = 1,#children do
  1810. addObject(children[i],true)
  1811. r(children[i])
  1812. end
  1813. end
  1814. end
  1815.  
  1816. r(Game)
  1817.  
  1818. scrollBar.VisibleSpace = math.ceil(listFrame.AbsoluteSize.y/ENTRY_BOUND)
  1819. updateList()
  1820. end
  1821.  
  1822. ----------------------------------------------------------------
  1823. ----------------------------------------------------------------
  1824. ----------------------------------------------------------------
  1825. ----------------------------------------------------------------
  1826. ---- Actions
  1827.  
  1828. local actionButtons do
  1829. actionButtons = {}
  1830.  
  1831. local totalActions = (4) + 1
  1832. local currentActions = totalActions
  1833. local function makeButton(icon,over,name)
  1834. local button = Create(Icon('ImageButton',icon),{
  1835. Name = name .. "Button";
  1836. Visible = Option.Modifiable and Option.Selectable;
  1837. Position = UDim2.new(1,-(GUI_SIZE+2)*currentActions+2,0.5,-GUI_SIZE/2);
  1838. Size = UDim2.new(0,GUI_SIZE,0,GUI_SIZE);
  1839. Parent = headerFrame;
  1840. })
  1841.  
  1842. local tipText = Create('TextLabel',{
  1843. Name = name .. "Text";
  1844. Text = name;
  1845. Visible = false;
  1846. BackgroundTransparency = 1;
  1847. TextXAlignment = 'Right';
  1848. Font = FONT;
  1849. FontSize = FONT_SIZE;
  1850. Position = UDim2.new(0,0,0,0);
  1851. Size = UDim2.new(1,-(GUI_SIZE+2)*totalActions,1,0);
  1852. Parent = headerFrame;
  1853. })
  1854.  
  1855.  
  1856. button.MouseEnter:connect(function()
  1857. Icon(button,over)
  1858. tipText.Visible = true
  1859. end)
  1860. button.MouseLeave:connect(function()
  1861. Icon(button,icon)
  1862. tipText.Visible = false
  1863. end)
  1864.  
  1865. currentActions = currentActions - 1
  1866. actionButtons[#actionButtons+1] = button
  1867. return button
  1868. end
  1869.  
  1870. local clipboard = {}
  1871. local function delete(o)
  1872. o.Parent = nil
  1873. end
  1874.  
  1875. -- CUT
  1876. makeButton(ACTION_CUT,ACTION_CUT_OVER,"Cut").MouseButton1Click:connect(function()
  1877. if not Option.Modifiable then return end
  1878. clipboard = {}
  1879. local list = Selection.List
  1880. local cut = {}
  1881. for i = 1,#list do
  1882. local obj = list[i]:Clone()
  1883. if obj then
  1884. table.insert(clipboard,obj)
  1885. table.insert(cut,list[i])
  1886. end
  1887. end
  1888. for i = 1,#cut do
  1889. pcall(delete,cut[i])
  1890. end
  1891. end)
  1892.  
  1893. -- COPY
  1894. makeButton(ACTION_COPY,ACTION_COPY_OVER,"Copy").MouseButton1Click:connect(function()
  1895. if not Option.Modifiable then return end
  1896. clipboard = {}
  1897. local list = Selection.List
  1898. for i = 1,#list do
  1899. table.insert(clipboard,list[i]:Clone())
  1900. end
  1901. end)
  1902.  
  1903. -- PASTE
  1904. makeButton(ACTION_PASTE,ACTION_PASTE_OVER,"Paste").MouseButton1Click:connect(function()
  1905. if not Option.Modifiable then return end
  1906. local parent = Selection.List[1] or Workspace
  1907. for i = 1,#clipboard do
  1908. clipboard[i]:Clone().Parent = parent
  1909. end
  1910. end)
  1911.  
  1912. -- DELETE
  1913. makeButton(ACTION_DELETE,ACTION_DELETE_OVER,"Delete").MouseButton1Click:connect(function()
  1914. if not Option.Modifiable then return end
  1915. local list = Selection:Get()
  1916. for i = 1,#list do
  1917. pcall(delete,list[i])
  1918. end
  1919. Selection:Set({})
  1920. end)
  1921.  
  1922. -- SORT
  1923. -- local actionSort = makeButton(ACTION_SORT,ACTION_SORT_OVER,"Sort")
  1924. end
  1925.  
  1926. ----------------------------------------------------------------
  1927. ----------------------------------------------------------------
  1928. ----------------------------------------------------------------
  1929. ----------------------------------------------------------------
  1930. ---- Option Bindables
  1931.  
  1932. do
  1933. local optionCallback = {
  1934. Modifiable = function(value)
  1935. for i = 1,#actionButtons do
  1936. actionButtons[i].Visible = value and Option.Selectable
  1937. end
  1938. cancelReparentDrag()
  1939. end;
  1940. Selectable = function(value)
  1941. for i = 1,#actionButtons do
  1942. actionButtons[i].Visible = value and Option.Modifiable
  1943. end
  1944. cancelSelectDrag()
  1945. Selection:Set({})
  1946. end;
  1947. }
  1948.  
  1949. local bindSetOption = script.Parent:FindFirstChild("SetOption")
  1950. if not bindSetOption then
  1951. bindSetOption = Create('BindableFunction',{Name = "SetOption"})
  1952. bindSetOption.Parent = script.Parent
  1953. end
  1954.  
  1955. bindSetOption.OnInvoke = function(optionName,value)
  1956. if optionCallback[optionName] then
  1957. Option[optionName] = value
  1958. optionCallback[optionName](value)
  1959. end
  1960. end
  1961.  
  1962. local bindGetOption = script.Parent:FindFirstChild("GetOption")
  1963. if not bindGetOption then
  1964. bindGetOption = Create('BindableFunction',{Name = "GetOption"})
  1965. bindGetOption.Parent = script.Parent
  1966. end
  1967.  
  1968. bindGetOption.OnInvoke = function(optionName)
  1969. if optionName then
  1970. return Option[optionName]
  1971. else
  1972. local options = {}
  1973. for k,v in pairs(Option) do
  1974. options[k] = v
  1975. end
  1976. return options
  1977. end
  1978. end
  1979. end
  1980.  
  1981. end))
  1982. BindableEvent3.Name = "SelectionChanged"
  1983. BindableEvent3.Parent = Frame1
  1984. BindableFunction4.Name = "SetOption"
  1985. BindableFunction4.Parent = Frame1
  1986. BindableFunction5.Name = "SetSelection"
  1987. BindableFunction5.Parent = Frame1
  1988. BindableFunction6.Name = "GetOption"
  1989. BindableFunction6.Parent = Frame1
  1990. BindableFunction7.Name = "GetSelection"
  1991. BindableFunction7.Parent = Frame1
  1992. for i,v in pairs(mas:GetChildren()) do
  1993. v.Parent = game:GetService("Players").LocalPlayer.PlayerGui
  1994. pcall(function() v:MakeJoints() end)
  1995. end
  1996. mas:Destroy()
  1997. for i,v in pairs(cors) do
  1998. spawn(function()
  1999. pcall(v)
  2000. end)
  2001. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement