It documents the process of me smashing my head against the keyboard to build a game called LETSGO
It’s gotten long enough to break into several sections:
Pain: the True Development Environment
Every other time I open my Unreal project, I get the following error:
PAIN
If I click Yes I get:
PAIN
When I successfully load into the project, and open Visual Studio, I see the following:
The red lines mean PAIN.
I found I can get rid of the missing modules error if I delete the Source folder.
This is not a solution. This is PAIN
But it is a good example of the necessity of version control!
Always load last project on startup
selected on the Unreal Editor startup screen.
So like, don’t click that?
I feel you need to play the Curb Your Enthusiasm theme song while working with Unreal sometimes. I found I could work around the Visual Studio errors by simply not using Visual Studio.
That’s right: I am now a radicalized JetBrains convert and fully embracing the Rider train.
You will note the lack of squiggly red lines.
Unreal C++ Fundamental Types
So there’s C++, and then there is Unreal C++
// STRINGS
std::string foo = ""; // Not a thing in Unreal
FString foo = "bar"; // Unreal has implemented its own string type
foo + "wow"; // Concatenation, "barwow"
foo.Len(); // char length, 6
foo.IsEmpty(); // bool, false
foo += "wow"; // I assume `+` returns new string, += appends existing string: "barwowwow"
foo.Equals("wow"); // bool, false
foo.Left(3); // get substring from start of string to index. "bar"
foo.Find("wow"); // Return index of first found substring "wow" = 3
foo.RemoveAt(3); // Removes all characters at index = "bar"
// ARRAYS
int myArray[5]; // Oh no no
TArray<int32> myArray; // Unreal has customized dynamic arrays to be used
myArray.Add(10); // Has Add function to append to end of array
myArray.Num(); // Returns 1 - number of elements in the array
myArray.RemoveAt(0); // Remove by index
myArray.Empty(); // Remove all contents
I’m actually super glad to see this. I’ve stayed away from C++ in the past because how manual everything is.
I’m coming from a world where node/python/ruby just lets you add things to other stuff and let you deal with the consequences of your own lack of skill/clear design/time.
The C++ requirement to manually do the simplest things has been the highest prevention cost for me to learn it.
Anyways, cool I have some substring functions.
And dynamic arrays? Bruh.
Yo Dawg I Heard You Like Enums
Consider the following:
UENUM(BlueprintType)
enum EMusicScaleSteps : uint8 {
REST = 0, // Only here because compiler complains that it needs a 0th enum option
HALF = 1,
WHOLE = 2,
};
UENUM
is a macro that does a bunch of fancy-work to reflect an enum
into Unreal. Without it we won’t see the enum
in Unreal blueprints.
Compiler Highlander
There can only be one compiler. The true compiler is the one that makes both the IDE and Unreal happy that the thing has been compiled.
Unreal’s Live Coding
feature appears to be the one true compiler:
When you see this Live Coding
thing running, building the project seems to work reliably.
To make Live Coding appear reliably, update Editor Preferences
→ Live Coding
→ Enable Live Coding
Ctrl + Alt + F11
in Unreal.
Seriously it was like days of just getting IDE and Unreal to agree with each other.For me, I press Build in Rider, and log starts spewing in the Live Coding window:
There’s also log spew in Rider
via UnrealLink
, but that’s just the Unreal Editor Log.
Yo Theres Already EMusicalNoteName
Now this is the definition of excellent documentation:
Cool. Cool cool cool.
But it does link to the AudioMixer
engine, which is probably going to be important if someone was to be, I dunno, Designing Sound?
So the next step here is start stepping through the AudioMixer
module documentation.
Quick parse through to see what random things get my attention
Like yo there’s a USynthSound
:
In it there is OnGeneratePCMAudio
Heres Jippities take:
Big brain thought here is to wonder if I can connect Musio directly to Unreal.
Because then we’re cooking with the whole damn orchestra.
Cooking With Quartz: Some Actually Decent Unreal Docs?
Issues with Accurate Timing and Latency in Audio Rendering? Now this is some real shit.
Quartz provides a way of scheduling an audio call mid-buffer instead of having to delay the audio render until the beginning of the next buffer. This has many applications — from creating dynamic music systems, to controlling the playback of rhythmic and timing-dependent sounds such as sub-machine gunfire.
We’ve largely glossed over rhythm so far, but controlling when a note is played is just as important as what note to play.
Probably more important honestly.
Playing it on the grid:
When the game thread calls PlayQuantized()
, it requests that the sound be played on a given quantization boundary (such as the next quarter note), as calculated to the nearest audio output sample on the audio render thread.
Coming from a DAW world like Ableton, this makes a ton of sense. The majority of music made today is played “on the grid”- each notes placed precisely on a beat.
“Real music”, played by humans, are rarely ever precisely on the beat- so much so that playing “off-grid” can give your music a more “human feel”.
That we have quantization in Unreal via the Quartz Music System means we can stand on the shoulders of giants here- laying down four-on-the-floor with a kick drum on should be a (relative) walk in the park.
Terms
Quartz Subsystem
- Create, Get a
Clock
- Check if Clock exists
- Latency information
Quartz Clock
- Triggers sounds
- Created with Quartz Subsystem
- Exposed in Blueprints via
Clock Handles
Clock Handle
- Contains a Metronome
- Exposed in Blueprints
Metronome
- The actual audio render thread object
- Schedules audio commands
- Has understanding of BPM, time signatures, etc.
Getting Quartz into LETSGO
- When a Music Platform is stepped on, schedule the note to play using a Quartz Clock.
- In theory this will make the sound play on the grid.
- This means that regardless of when the physical object is hit, it will play in time.
- I think this will be the next System to build. Buuut that is after we finish the first requirements of Music Theory Engine - Spawn music platforms choosing notes of a real scale.