Important: To use the templates feature in WebGLA JavaScript API that renders 2D and 3D graphics in a web browser. The Unity WebGL build option allows Unity to publish content as JavaScript programs which use HTML5 technologies and the WebGL rendering API to run Unity content in a web browser. More info
See in Glossary, you need prior knowledge of JavaScript concepts and terminology.
When you build a WebGL project, Unity embeds the Player in a HTML page such that a browser can open it. A WebGL template is a configuration setting that lets you control the appearance of this HTML page, so that you can: test, demonstrate, and preview your WebGL application in a browser.
To access WebGL templates:
By default, the WebGL Template setting has the following options:
These built-in HTML pages are useful for testing and demonstrating a minimal Player.
You can also use JavaScript to build and supply your own WebGL templates to host the Player. This is useful for production purposes, so that you can preview the Player hosted in the page where it’s eventually deployed. For example, if the Unity Player content interacts with other elements in the page via the external call interface, you should test it with a page that contains those interacting elements.
To add custom templates to your project, navigate to your Project’s Assets
folder and create a folder called WebGLTemplates
. Each template is a subfolder within the WebGLTemplates
folder. Each template subfolder contains an index.html
file along with any other resources the page needs, such as images or stylesheets.
The easiest way to create a new custom WebGL template is to make a copy of the built-in Default or Minimal templates, which are stored in corresponding subfolders under <Unity Installation>/PlaybackEngines/WebGLSupport/BuildTools/WebGLTemplates/
. Every Unity Project includes these templates by default. Copy a template and place it in your own Project/Assets/WebGLTemplates
folder, and rename it to something meaningful so you can identify your template later.
Note: On Mac, you can locate the Unity Installation folder in the Applications folder.
Templates in your Project’s WebGLTemplates
folder appear in the Unity Player Settings’ WebGL Template setting. The name of the template is the same as its folder. To give this option a thumbnail image for easy reference, add a 128x128-pixel
image to the template folder and name it thumbnail.png
.
During the build process, Unity pre-processes template files and evaluates all macros and conditional directives included in those files. As part of this process, Unity finds and replaces all macro declarations with the values the Editor supplies. Unity automatically pre-processes all .html, .php, .css, .js and .json files in the template folder.
The following internal preprocessor variables refer to data in the Project, and Unity assigns value to them at build time according to the values the Editor supplies. Javascript macros and conditional directives can use these internal preprocessor variables.
Variable | Type | Description |
---|---|---|
COMPANY_NAME | String | The Company Name defined in the Player Settings. |
PRODUCT_NAME | String | The Product Name defined in the Player Settings. |
PRODUCT_VERSION | String | The Version defined in the Player Settings. |
WIDTH | Integer | The Default Canvas Width defined in the Player Settings > Resolution and Presentation. |
HEIGHT | Integer | The Default Canvas Height in the Player Settings > Resolution and Presentation. |
SPLASH_SCREEN_STYLE | String | This’s set to the “Dark” value when Splash Style Player Settings > Splash Image is set to Light on Dark, otherwise it’s set to the “Light” value. |
BACKGROUND_COLOR | String | Represents the Background Color defined in a form of a hex triplet. |
UNITY_VERSION | String | The Unity version. |
DEVELOPMENT_PLAYER | Boolean | This’s set to true if the Development BuildA development build includes debug symbols and enables the Profiler. More info See in Glossary option is enabled. |
DECOMPRESSION_FALLBACK | String | This’s set to Gzip or Brotli , depending on the compressionA method of storing data that reduces the amount of storage space it requires. See Texture Compression, Animation Compression, Audio Compression, Build Compression.See in Glossary method you use and the type of decompressor included in the build. If neither is included, the variable is set to an empty string. |
INITIAL_MEMORY | Integer | The initial size of the WASM memory heap in megabytes (MB). |
USE_WASM | Boolean | This is set to true if the current build is a WebAssembly build. |
USE_THREADS | Boolean | This is set to true if the current build uses threads. |
USE_WEBGL_1_0 | Boolean | This is set to true if the current build supports the WebGL1.0 graphics API. |
USE_WEBGL_2_0 | Boolean | This is set to true if the current build supports the WebGL2.0 graphics API. |
USE_DATA_CACHING | Boolean | This is set to true if the current build uses indexedDB caching for the downloaded files. |
LOADER_FILENAME | String | This is set to the filename of the build loader script. |
DATA_FILENAME | String | This is set to the filename of the main data file. |
FRAMEWORK_FILENAME | String | This is set to the filename of the build framework script. |
CODE_FILENAME | String | This is set to the filename of the WebAssembly module when the current build is a WebAssembly build, otherwise it’s set to the filename of the asm.js module. |
MEMORY_FILENAME | String | This is set to the filename of the memory file when memory is stored in an external file, otherwise it’s set to an empty string. |
SYMBOLS_FILENAME | String | This is set to the filename of the JSON file containing debug symbols when the current build is using debug symbols, otherwise it’s set to an empty string. |
BACKGROUND_FILENAME | String | This is set to the filename of the background image when the background image is selected in the Player Settings > Splash Image, otherwise it’s set to an empty string. |
JavaScript macros are blocks of JavaScript code in template files, surrounded by three sets of curly brackets. This JavaScript code can use the internal preprocessor variables listed above. These variables are assigned at build time according to the values the Editor supplies. During the build, the preprocessor evaluates all macros and replaces them with the output of the variable.
You can use JavaScript macros to preprocess values supplied by the Editor. These macros can be as complex as you like. They can include multiple operators, loops, functions, and any other JavaScript constructs.
The following example line is from the index.html
file used in the Default template:
<div id="unity-build-title">{{{ PRODUCT_NAME }}}</div>
If the value of the Product Name in the Player Settings is set to My WebGL Game
, the internal preprocessor variable PRODUCT_NAME
has the value My WebGL Game
. In the output index.html
file, the line appears as:
<div id="unity-build-title">My WebGL Game</div>
Below is a more complex example from the same index.html
template file:
canvas.style.background = "url('" + buildUrl + "/{{{ BACKGROUND_FILENAME.replace(/'/g, '%27') }}}') center / cover";
If the target build folder is called Let’s try WebGL
, and if you select a background image in the Player Settings, the internal preprocessor variable BACKGROUND_FILENAME
has the value Let’s try WebGL.jpg
. In the output index.html
file, the line changes into:
canvas.style.background = "url('" + buildUrl + "/Let%27s try WebGL.jpg') center / cover";
Conditional directives #if, #else, and #endif control whether Unity includes a specific portion of the preprocessed file in the output file, or discards it for the current build.
Code that starts with an #if directive and ends with an #endif directive is called a conditional group. Conditional groups can also include #else directives. Unity evaluates the expression written after the #if as a JavaScript expression. If this expression has a truthy value that translates to true when evaluated in a Boolean context, then Unity keeps the line group immediately following the #if directive in the output file. If the #if expression is false, and an #else directive is included in the conditional group, Unity keeps the line group immediately following the #else directive in the output. An example of a conditional group is as follows:
#if EXPRESSION
// this block is included in the output if EXPRESSION has a truthy value
#else
// this block is included in the output otherwise
#endif
Evaluated JavaScript expressions can include brackets, logical operators and other JavaScript constructs. Conditional directives can be nested.
When you select a WebGL template, Unity parses the template and looks for Javascript macros and conditional directives. JavaScript variables are treated as custom user variables if they’re:
Unity automatically adds these custom user variables to the Resolution and Presentation section in the Player Settings window.
As an example, if you want to control the title of the generated index.html
page directly from the Player Settings window, you first need to modify the <title>
line of the index.html
in your custom template, like this:
<title>{{{ PAGE_TITLE }}}</title>
After you’ve done this, re-select your custom template. This parses the template again, and you should find a Page Title field in the Resolution and Presentation > WebGL Template section of the Player Settings window.
When you enter text into this field and build your Project, the custom variable PAGE_TITLE used in the template macro automatically becomes the text in the Page Title field.
If you would like to use custom integer or float variables in your macros, use parseInt()
or parseFloat()
JavaScript functions in your macros to preprocess string values supplied by the Editor. This is because custom user variables are always assigned a string value.
Note: Underscore characters in variable names display as spaces inside the field to improve readability.
The index.html
contains the code necessary to load the build and should include the following:
<canvas>
element. Unity runtime uses the <canvas>
element to render the application.var buildUrl = "Build";
var loaderUrl = buildUrl + "/{{{ LOADER_FILENAME }}}";
var script = document.createElement("script");
script.src = loaderUrl;
script.onload = () => {
// code for instantiating the build
};
document.body.appendChild(script);`
In this example, {{{ LOADER_FILENAME }}}
is automatically resolved by the template preprocessor when the build is generated.
Alternatively, you can download the build loader using a script tag, for example:
lang-js
<script src="Build/{{{ LOADER_FILENAME }}}"></script>
createUnityInstance()
function, which is defined in the build loader script.The createUnityInstance()
function creates a new instance of your content. You can use it like this:
createUnityInstance(canvas, config, onProgress).then(onSuccess).catch(onError);
This function returns a Promise object, where:
Object | Use |
---|---|
canvas |
Unity runtime uses the canvas object to render the game. |
config |
The config object contains the build configuration, such as the code and data URLs, product and company name, and version. For more information on config definition, see the Build Configuration section on this page. |
onProgress(progress) {...} |
The WebGL loader calls the onProgress callback object every time the download progress updates. The progress argument that comes with the onProgress callback determines the loading progress as a value between 0.0 and 1.0. |
onSuccess(unityInstance) {...} |
The onSuccess callback is called after the build has successfully instantiated. The created Unity instance object is provided as an argument. This object can be used for interaction with the build. |
onError(message) {...} |
The onError callback is called if an error occurs during build instantiation. An error message is provided as an argument. |
The createUnityInstance()
function is defined in the build loader script and is specific to the instantiated build. Therefore, if you are embedding two or more builds in the same HTML document, make sure that the createUnityInstance()
function is called from an onload
callback of the corresponding build loader script. For more information about the Unity WebGL Loader, see Building and Running a WebGL Project.
The configuration object contains the build configuration, which consists of code and data URLs, product name, company name, and version. You can define it using the following code:
var buildUrl = "Build";
var config = {
dataUrl: buildUrl + "/{{{ DATA_FILENAME }}}",
frameworkUrl: buildUrl + "/{{{ FRAMEWORK_FILENAME }}}",
codeUrl: buildUrl + "/{{{ CODE_FILENAME }}}",
#if MEMORY_FILENAME
memoryUrl: buildUrl + "/{{{ MEMORY_FILENAME }}}",
#endif
#if SYMBOLS_FILENAME
symbolsUrl: buildUrl + "/{{{ SYMBOLS_FILENAME }}}",
#endif
streamingAssetsUrl: "StreamingAssets",
companyName: "{{{ COMPANY_NAME }}}",
productName: "{{{ PRODUCT_NAME }}}",
productVersion: "{{{ PRODUCT_VERSION }}}",
// additional options can go here, see below
};
In the example above, the build folder URL is stored as a separate variable called buildUrl
. This is useful in cases where you don’t know the relationship between the embedding page and build folder on the hosting server. It enables you to reuse the embedding code in other HTML documents. An example of when to use this is if you move the Build
folder to another location on your server. You can adjust the value of the buildUrl
variable on the embedding page, and you can use the same embedding code. This also applies to the StreamingAssets
folder (streamingAssetsUrl
).
In addition to setting the above URL and field names on the build, you can set the following properties on the config
object.
Property | Use |
---|---|
matchWebGLToCanvasSize: false |
By default (if set to true or unset), Unity synchronizes the WebGL canvas render target size with the Document Object Model (DOM) size of the canvas element (scaled by window.devicePixelRatio ). Set this to false if you want to set the canvas DOM size and WebGL render target sizes manually. |
devicePixelRatio: <number> |
This field enables forcing the DPI scaling ratio for the rendered page. Set to 1 to force rendering to “standard DPI” (or non-Retina DPI), which can help performance on lower-end mobile devices. By default, this field is unset, meaning the rendered page uses the browser DPR scaling ratio, resulting in High DPI rendering. |
autoSyncPersistentDataPath: true |
If set to true, all file writes inside the Unity Application.persistentDataPath directory automatically persist so that the contents are remembered when the user revisits the site the next time. If unset (or set to false), you must manually sync file modifications inside the Application.persistentDataPath directory by calling the JS_FileSystem_Sync() JavaScript function. |
After the build has successfully instantiated, the fulfilment handler callback of the Promise object receives the newly created Unity instance object as an argument. To interact with the build, call the following methods of the Unity instance:
Method | Use |
---|---|
unityInstance.SetFullscreen(fullscreen) |
The SetFullscreen method toggles full screen mode. This method doesn’t return a value. Note: You need to use a user interaction like a button or key press to activate fullscreen mode. You can’t activate fullscreen mode on startup. - To activate Full screen mode, set the fullscreen argument to 1. - To exit Full screen mode, set the fullscreen argument to 0. |
unityInstance.SendMessage(objectName, methodName, value) |
The SendMessage method sends messages to the GameObjects. This method doesn’t return a value. - objectName is the name of an object in your Scene. - methodName is the name of a method in the script, currently attached to that object. - value can be a string, a number, or it can be empty. |
unityInstance.Quit().then(onQuit) |
Use the Quit() method to quit the runtime and clean up the memory used by the Unity instance. This method returns a Promise object.- onQuit callback is called after the build runtime has quit. |