Building a Settings Menu with Unity 2021 URP
In this article we’ll setup a basic “Settings” menu to be configured when the game is paused.
Initial Scene Setup
Let’s quickly go over our scene starting point.
We’ve got a Canvas with the usual Image element background, Image Element title background and associated Text element, two sliders and their associated Text elements.
We’ve customized the sprites used with the sprite sheet from previous articles.
We’ve also set the values of both slider to be .5 or 50% full.
Let’s go ahead and create a new script and assign it to our Canvas element.
Before we forget, we also need to add a Cancel Button element.
We’ll demonstrate using the pause menu to actually pause the game state while we are at it.
But first, we’ll need something to pause!
Add a stretched cube or plane and rename it to “Ground” or “Floor”.
Add a spawn point to your scene by creating an empty game object, renaming it to “SpawnPoint”, and then setting it’s Transform position to 0, 20, 0.
The PauseSettings Class/Script
We’ll put together the class variables we know we’ll need to have for our “gameplay” and UI elements and a rudimentary physics interaction where a ball spawns, drops to the ground, and is destroyed repeatedly.
This will allow us to see that the game state is in fact paused.
Next, let’s go ahead and assign to our script component a prefab for our Ball Prefab and the UI elements we’ll need later.
I ended up bumping up the spawn delay to 5 seconds.
If we hit play, we should see something similar to the above.
I’ll add a scale up size to the prefab in my script.
I also need to add a couple class variables for the UI.
I’ll need to toggle the visibility of the menu, so a reference to the parent element background and I’ll need to know when the menu is active or not so a Boolean value for that.
And we’ll need to assign that to our script component in the Inspector window.
Now we’ll need to add the overall logic for our open/close menu while pausing/unpausing the game.
We’ll else check in the Update() method for when the escape key is pressed.
Now that we have a method setup to act when our Cancel button is clicked, let’s hook it up with Unity Event system marked as “On Click ()” on the btnCancel element.
Now if we run the game, we should be able to hit escape and see the game pause.
Hitting the Cancel button starts it again.
Turn Up The Volume
We’ll add Music in a time-efficient manner for this project.
In a production project we’d add an Audio Manager first and go from there, but here we’ll just create a new empty game object and call it “Music”.
Add the “Audio Source” component to it assign it an mp3 you like.
Set the volume to .5 so as to match our default volume slider value and Play on Awake to enabled.
Now create an Audio Mixer in your Audio folder.
Open the Audio Mixer by going to Window > Audio > Audio Mixer and dock it where you like.
Now create a “BG_Music” group to create a separate mixer for our Music.
Now set the “Output” to your newly created “BG_Music” group.
On the sliderVolume element, change the Min max values to match the decibel settings shown in the Audio Mixer.
-80 decibels being the minimum and 20 decibels being the maximum.
Also, set the default Value to 0 to match our current 0 decibel level.
Note that this is a modifier value in decibels, not the actual decibels at which the volume will be set.
We need to select our BG_Music group in the Audio Mixer window, right click the “Volume” field in the Inspector, and select “Expose ‘Volume (of BG_Music)’ to script”.
We need to add an Audio Mixer reference to our class variables in the PauseSettings class and use it in a new method to tie the volume to the volume slider.
NOTE: Not shown but important, there needs to be “using UnityEngine.Audio” and “using UnityEngine.InputSystem” statements.
Jetbrains Rider IDE auto adds these for me, so sometimes I forget to mention them!
Assign the Audio Mixer from the Project window to the script component.
Now assign the newly created method to the Unity Event “On Value Changed (Single)” field on the sliderVolume element.
If you are getting an “Exposed name does not exist:” error, that is because the parameter name does not match what we typed in our script.
In the Audio Mixer window, open the Exposed Paramters tab and rename the parameter to “BG_Music”.
Now if we hit play, we should see (and hear) that the volume mixer is tied to the volume slider in the Pause menu screen.
Turn Down the Sun
There are a couple of ways to adjust the screen brightness.
We won’t touch post processing for now, we’ll use an overlay method.
Create a new Image element as a child of the Background element and rename it “BlackOverlay”.
Change the Color to pure black, the resolution to match your current resolution, and set the alignment to stretch vertically and horizontally.
Now, let’s set the alpha value of the overlay to 0 for now.
EDIT: Originally set sliderBrightness max value to 255 here, needs to be 1.
We need to add an Image class variable to reference our BlackOverlay Image element and a method to adjust the alpha value of it based on the sliderBrightness.
Assign the BlackOverlay Image element to the script component.
We also need to assign the newly created AdjustBrightness() method to the Unity Event, “On Value Changed (Single)” on the sliderBrightness element.
Our Black Overlay occupies the entire screen and still has “Raycast Target” enabled.
That means every click will be intercepted by this invisible element!
Let’s disable it as shown above.
The BlackOverlay is not stretching beyond the background Image size so we’ll move that in the hierarchy as a direct child of canvas and manually set the boundaries in the scene view to be larger than the Canvas.
Since Color.a is normalized to expect a value between 0 and 1 rather than the entire 0 to 255, we need to change our min/max values on the sliderBrightness element to match.
Set the current value to 0 and the Direction as “Right To Left”.
Hit play and enjoy your pause menu!
See you in the next article!