Client CoreScripts GitHub Repository & Semi-Comprehensive Overview

Foreword

I’ve noticed that I’ve been posting around the link for the CoreScripts repository many times, so I’ve decided to create a resource thread regarding it. This allows for link exposure and future usage, without the hassle of digging up a thread that references it.


Abstract

The following GitHub repository contains Roblox’s core client scripts. Here, you can view the source code for some of the CoreScripts that are inserted into the client at run time.

You may notice that you have some experience working with these scripts. For example, you may have forked the PlayerModule to access a CameraScript module in order to access the PopperCam to add a custom whitelist. In doing so, you’re forking a script that was inserted from this repository. Another example is using RemoveDefaultLoadingScreen. You’re not directly interacting with CoreScripts but you’re using a method exposed by them to modify something they made.

Note: The linked CoreScripts repository is fairly outdated and the last commit was around a year ago. CloneTrooper1019’s RobloxClientWatch repository holds an updated copy of the CoreScripts repository, which you can view here:

In addition, you are also able to view the files via your local file system. The path may look differently for some users, however I can provide the Windows path: %appdata%\..\Local\Roblox\Versions\{LATEST-STUDIO-VERSION}\content\scripts


Exploring

For veteran developers and those who can infer the meaning of various directories, exploring through this repository should be a breeze. For those who aren’t as experienced or need some guidance, I can provide a brief rundown of what you can expect to find and the purpose of each item.

Most or all CoreScripts are self explanatory, given their naming and brief documentation in comments around the script, especially the abstract at the top of each script.

The exploration section is written for the latest commit on the master branch (August 13th, 2018). Please keep in mind that this commit was made nearly a year ago and does not accurately reflect the current version of the CoreScripts at all - there are some very noticeable differences.

The point of showing the repository is allowing you to browse code.

Exploration Directory:


CoreScriptsRoot

CoreScriptsRoot is the first of the two top-level directories in the CoreScripts repository. This directory primarily contains the client CoreScripts you see for various controls, such as core UIs. You will never really find yourself having to access any of the code from this folder.

CoreScriptsRoot contains four code files:

  • LoadingScript.lua: Code for the default loading screen, notoriously known for being removed in favour of custom loading screens. For those curious, Lines 955 to 973 show the behaviour of removing the loading screen either when ReplicatedFirst has non-zero children or RemoveDefaultLoadingScreen is called.

  • MergeSort.lua: This is a module that returns the result of a call from the function mergesort. The mergesort function presents a way to quickly sort through a table, much like table.sort. It takes an array, reproduces a similar array and through a few reassignments of variables, returns a newly sorted table.

    • An engineer has noted that mergesort is intended to be used like a script in the command bar, rather than as an actual module (it cannot be used in its raw form unless you modify some parts of the code).
    • MergeSort is used as a sorter primarily for custom sorting order in a UI layout, such as UIPageLayout.
  • ServerStarterScript.lua: This script sets up the server-side logic for certain CoreScripts.

  • StarterScript.lua: Another script that sets up logic during initial load. This script is responsible for setting up various CoreGui-based elements.

Within CoreScriptsRoot, there are also four folders; CoreScripts, Libraries, Modules and ServerCoreScripts.

(back to directory) | (conclusion)

CoreScripts

Relatively self explanatory. The scripts in this folder contain code used as the contents of CoreScripts. Each of their functions are explained by the name of the script. There are two exceptions however, to which their name may not immediately explain their purpose:

  • MainBotChatScript2: This script is responsible for handling the ugly legacy dialog system. It has since been rewritten and replaced by a full Lua implementation with more features and a better framework, however it is not currently being maintained.

  • NotificationScript2: This script is responsible for the notifications you see in the bottom right corner of your screen (new badge, new friend, so on), as well as registering the SendNotification SetCore option that allows developers to send their own notifications.

    • Note that SetCore can only be called from LocalScripts once it has been registered. I typically set up my script in StarterPlayerScripts to connect to a remote.
    • You can have two buttons show up maximum. Having none of them with text hides them; having one of them with text shows only one button; having both with text shows both.

Example code for sending out a notification:

local StarterGui = game:GetService("StarterGui")

-- Called when the user selects an option of the notification
local function OnNotificationOptionSelected(OptionText)
    warn("Selected option:", OptionText)
end

local NotificationData = {
    Title = "Title", -- Required
    Text = "Body", -- Required
    Icon = "rbx(game)asset(id)://content", -- Optional, defaults to none
    Duration = 5, -- Optional, defaults to 5, dictates how long it stays for
    Callback = OnNotificationOptionSelected, -- Optional, defaults to nothing
    Button1 = "Yes", -- Optional, defaults to nothing
    Button2 = "No", -- Optional, defaults to nothing
}

(back to directory) | (conclusion)

Libraries

The libraries under here are used with the deprecated function LoadLibrary. You are still able to use LoadLibrary as well as the libraries without issue or error, though the libraries and their methods are recognised as deprecated. You’re encouraged to create your own libraries.

  • RbxGui: This library was used to create various Gui objects. Roblox has since provided better methods of accomplishing what RbxGui can do and developers can do the same. For example, ScrollingFrames replace the need to use RbxGui.CreateScrollingFrame.

  • RbxStamper: This library was used in Roblox’s legacy Stamper Building tool. Stampers were commonly used in free or plot-based building games such as the currently-closed Welcome to ROBLOX Building and Personal Servers (the Roblox Fandom page is unofficial, however it covers Personal Servers well enough without me needing to branch off and explain what they were).

  • RbxUtility: One of the most commonly used libraries. As the name suggests, it provided utilities for developers to use at their discretion. RbxUtility still has material that can be salvaged even now, despite the deprecation of LoadLibrary and the libraries.

    • EncodeJSON / DecodeJSON: Full Lua implementations of JSON encoding to and from the format respectively. These functions have since been superseded by their HttpService variants, JSONEncode and JSONDecode. It is more recommended that you use these as they are actively supported and handled in the backend.

      • Note: You do not need to use HttpEnabled to perform JSON (en/de)coding.
    • CreateSignal (and related): CreateSignal allows you to create pseudosignals that function similarly to a standard RBXScriptSignal via BindableEvents. There are still developers even now who favour creating signals like this, even to the point of making a signal pseudoclass - as a matter of fact, the Lua Chat System implements this for events as well, such as those listed under the Events section of the ChatService module.

    • Create: Create serves as a more powerful version of Instance.new. This allowed you to specify an object in the same format as Instance.new(ClassName) via RbxUtility.Create(ClassName), however you also got the option to specify properties.

      • Another powerful benefit to Create is that it defers (delays) setting the parent, regardless of what order you specify it in the dictionary of properties to set. This acts as a catcher for the bad practice of setting the parent first before the properties, which incurs performance issues.
      • Fun fact: the source code for RbxUtility.Create, despite RbxUtility being deprecated, still gets used in some areas internally. The code of RbxUtility.Create is still highly reusable for projects.

Code samples and difference between Instance.new and RbxUtility.Create

local Part = Instance.new("Part")
Part.Name = "NewPart"
Part.Parent = workspace

---

local RbxUtility = LoadLibrary("RbxUtility")
local Create = RbxUtility.Create

local Create = LoadLibrary("RbxUtility").Create -- Also valid as a shorthand

local Part = Create("Part")({
    Name = "NewPart",
    Parent = workspace,
})

local Part = Create("Part"){
    Name = "NewPart",
    Parent = workspace,
} -- Also valid. Using ["Name"] = "NewPart" is also valid.

(back to directory) | (conclusion)

Modules

The modules folder contains an assortment of modules with code that can be reused or expose various functionality to other CoreScripts. This is another folder that you won’t find really find yourself looking through. There’s of course inspiration, salvaging, getting inspiration for something you’re making or just out of curiosity.

This directory contains seven folders, each of which expand out into more modules or folders. Some folders may contain useful content (such as a handy BarGraph pseudoclass under Stats) for developers who know how to extract, modify and use these modules (it’s usually just as simple as copying the source code and posting it into a ModuleScript).

The Server folder, to note, does contain parts of the previously mentioned Lua Chat System, under the ClientChat and ServerChat modules. You’ll notice similar folders being mirrored while you fork the chat system through the Play Solo → Copy method.

Other than that, there are around 23 modules in this folder. I won’t be running through any of them as I haven’t had time to explore them myself, though the documentation and names of the scripts should suffice in helping you understand. If that doesn’t work, feel free to ask questions.

(back to directory) | (conclusion)

ServerCoreScripts

ServerCoreScripts is essentially the CoreScripts folder, however it relates to the server. There is only a single script within this folder, ServerSocialScript, which handles server-side logic for social interactions.

Social interactions are player-player interactions that can be the following:

  • Friends
  • Followers
  • Blocked users

(back to directory) | (conclusion)


PlayerScripts

PlayerScripts is the second top-level directory in the CoreScripts repository. This mainly pertains to scripts that you see inserted into each respective container under StarterPlayer. This is the directory you may find yourself searching through, directly on GitHub or indirectly by using the Play Solo → Copy fork method especially for the PlayerModule.

There are three folders here: StarterCharacterScripts, StarterPlayerScripts and StarterPlayerScripts_NewStructure.

(back to directory) | (conclusion)

StarterCharacterScripts

This directory matches the name of StarterPlayer.StarterCharacterScripts in the Studio Explorer menu, given the scripts here are placed inside that folder when the server starts initially. Currently, this folder only contains the script for character sounds.

(back to directory) | (conclusion)

StarterPlayerScripts

This directory contains the old modules used in StarterPlayerScripts, when CameraModule and ControlModule were separate. Although you can still salvage these items, it’s recommended that you use the new structure instead, as it is actively supported. It also has better, efficient and centralised features to use over the former two-branch structure.

(back to directory) | (conclusion)

StarterPlayerScripts_NewStructure

Note - this folder does NOT actually contain the new structure. The fork from a Play Solo session is more accurate. This one still uses two modules, while the current version uses one module to unify the two and act as a helper.

This folder contains the source code for the current PlayerScripts structure. PlayerModule is inserted into StarterPlayerScripts, which is a singleton that loads in both the camera and control modules under it respectively. It is initialised by a LocalScript that requires the module eagerly on start-up.

The PlayerModule is designed in a pseudoclass-like fashion, which exposes methods for allowing you to use certain exposed methods of the camera and control modules without directly trying to index them.

local Players = game:GetService("Players")

local LocalPlayer = Players.LocalPlayer
local PlayerScripts = LocalPlayer:WaitForChild("PlayerScripts")

local PlayerModule = require(PlayerScripts:WaitForChild("PlayerModule"))

local Cameras = PlayerModule:GetCameras()
local Controls = PlayerModule:GetControls()
local ClickToMoveController = PlayerModule:GetClickToMoveController()

Conclusion

That’s the end.

I’m not well-versed in this topic, I just happened to write this entire thread on a whim with several free hours after two exams. I don’t quite know if the information here is accurate or helpful and it drifted off towards the end particularly because there wasn’t much to say once all the important items were out of the way.

If there’s anything I’m misinformed of, have gotten incorrect, any questions or feedback in general, please do leave a response or drop me a direct message. I’ll try to address anything that’s dropped off within a timely manner, considering I’m hanging around here on a daily basis.

Thank you for reading if you did and good luck with your development.

26 Likes

It’s nice to have a place where I can quickly refer to the CoreScripts so I can enhance my programming/coding knowledge anytime.

Also, to add on, the MergeSort.lua module quickly (and efficiently) sorts an array and returns it.

EDIT: I do not think the return statement actually returns a function. There may be something wrong with it but I do not know.

Woah, this was a rich source of information. I have read this entire post without leaving a single line. Thank you very much and putting effort into this. Hope you have a wonderful day.

1 Like

I had a look into MergeSort. It does indeed seem to sort an array and return it, though the script itself (which is a module) does in fact return a function, the mergesort function. This way, when MergeSort is required, it can be called and return the sorted table.

-- Example of how it could be used

local MergeSort = require("MergeSort")
local Array = {}

local function ComparisonCallback(A, B)
    return FOOBAR -- Actually returns a boolean between A and B
end

local SortedArray = MergeSort(Array, ComparisonCallback)

I’d assume it works similarly to sort from the standard table library, though obviously different if there’s the need to create this module for later usage.

2 Likes

Hmm. Interesting.
By the way, the comparison argument/parameter (comp in the MergeSort module) works just like table.sort(). Try returning A < B in the comparison function, which causes an array of numbers to be sorted in ascending order.
Also, can you update the original post with this new info?

2 Likes

A quick note: this repo is not being kept up to date (the last commit was almost a year ago). If you want a more accurate picture of CoreScripts, you can go look at content/scripts in the most recent studio version folder on your harddrive or go to @Maximum_ADHD’s Client Tracker, which hosts an up-to-date version of that folder.

2 Likes

@starlebVerse I’ve updated the main post including this information now.

@Dekkonot Thanks for pointing that out! I will also include this link in the main thread, as well as the pointer towards the scripts folder on the local file system. When I get the chance, I’ll update the post to refer to an updated copy of the CoreScripts repository and it’s code.

I may just base the thread around commits made to that repository in general.

2 Likes

I’m extremely confused on what return mergesort(...) is doing. Is there even a difference between doing that and return mergesort?

That’s actually a good point to bring up, because there is a difference. return mergesort(...) would return the results of a mergesort call, whereas return mergesort would return the function. That’s another inaccuracy I’ll need to correct across posts, thanks for bringing it up.

I’m not quite sure why it’s structured this way, though I also don’t know if any CoreScripts currently use mergesort so it’s difficult to gain an understanding of how it’s used in code.

1 Like

I got an answer from @mrow_pizza.

this module is written like a command-line script; you can't use it in Roblox in this form it's used to implement the Custom sort order for UI layouts

1 Like

I’ve added this to the main post. Thank you for sharing this information. :slightly_smiling_face:

Where is the "Animate” local script that is normally found inside a players character?

The Animate LocalScript does not live in this repository. It is likely held somewhere else internally that is inaccessible to developers.

I don’t think this resource has much utility to developers and I can’t fully remember why I created it, maybe it was just to highlight where you could find the CoreScripts if you wanted to peek at something from it. I’ll think about revising or repurposing this.