How to create a dynamic music script?

Hi,

I’ve been working on a JoJo’s Bizarre Adventure inspired game for quite a while, and the first gamemode available would be Steel Ball Run. Since it is inspired by Steel Ball Run, I asked myself if it would have been possible to include a dynamic music soundtrack, so the same theme won’t repeat over and over again. Of course the answer is yes, because Tunneler is a game that successfully did this.

But the issue here is that I don’t know where to start exactly. I want it to be very similar to how Zelda BOTW achieved this, like when nothing happens, a calm music plays, there’s a track suited for this playing, and then when fighting there’s another one suited for the fight playing (and since it is JoJo, that would be a theme that suits your character/stand).

I haven’t tried to figure out how I can possibly do it, and this is why I am here. But of course, I am not asking for someone to do it for me, I just need help on how I can possibly make something like that.

Best regards,

Ellie.

You could just change the sound track once its ended to prevent the same loop. For dofferent scenes you could change it when the event occurs. I dont watch anime so that’s the best I could infer from your post.

This is not a good solution. I really want to make a truly dynamic soundtrack where the music changes depending on the situation and the status of the player’s character.

Hello!

I am very sure that RPG-Games like Zelda: Breath of the Wild do this by registering Time Positions in every ambient theme, where a seamless transition to a next theme would be possible, like in soundless spaces in the soundtrack. When the music should change and one of those Time Positions is hit by the deprecated theme, they will stop the old music and replace it with the new one.

Alternatively, one could just fade the old song out. Both are I think possible in Roblox, but the upper one can cost a lot of time, since you have to register every point in every song you want that effect to apply for, for a possible transition point without having a hard cut.

This could be done in a Dictionary like this:

local TRANSITIONS = {
	songOne = { 
		-- time positions
	},
	
	songTwo = {
		-- time positions
	}
}

With two variables, one with the current song and one queue, you could check in a loop if something is in the queue, and if so, check when the next time position is hit by the old song and then stop or destroy it. Then place the queue song into the current song variable and play it.

You could then just easily place a theme into the queue and let everything happen by itself.

Hope I could help!

2 Likes

I think I might get somewhere.

The idea of using a table is great, and this is where I started. I do not know if what I have started is great or not, but is definitely worth trying.

local module = {
	Sounds = {
		Zone1 = {
			Calm = SoundService.DynamicMusics.Zone1.thankyougyro;
			Travelling = SoundService.DynamicMusics.Zone1.gyrozepelli;
			Fight = SoundService.DynamicMusics.Zone1
		}
	};
	EventSound = {
		["25thSembtember"] = SoundService.DynamicMusics.Events["25thseptember1890"]
	};
	PlayerData = {
		Player = game:GetService("Players").LocalPlayer;
		Zone = 1;
		CurrentTrack = SoundService;
	};
	Active = false
}

In this table, I have some data such as the currently playing song, and the song themselves. Since Steel Ball Run is quite long, and so is my game, I added variants to it.

But I think there would be a problem with the time positions idea where songs would not have a seamless transitions, so I would stick to a fade-in/fade-out system.

And yeah, that’s a module.

1 Like

Hello again!

I think this is a good start. A fading system is pretty simple and also can do a great job. I think the queue principle can also be applied here, with, as example, a variable called NextTrack which is nil by default. Then within a loop, it checks if NextTrack has a Sound inside it, and when it does, begins to fade out the current Track, maybe with a Tween draining its volume towards zero.

Then when the Tween.Completed Event is called, destroy the CurrentTrack, clone NextTrack into CurrentTrack and then destroy the sound inside NextTrack.

Afterward, put the volume of CurrentTrack instantly to zero before playing it, and then tween it up to the desired volume.

That way, it would be possible to just place a track inside NextTrack and do the job by itself, like I stated above. Maybe there is a better way, but that’s how I would do it in theory. Hope this answer could help further!

2 Likes