mirror of
https://github.com/FunkinCrew/Funkin.git
synced 2024-11-23 16:17:53 -05:00
New refactor to VoicesGroup to make multiple vocal tracks actually work
This commit is contained in:
parent
317c127730
commit
2f10de3594
6 changed files with 183 additions and 378 deletions
|
@ -119,16 +119,21 @@ class SongLoad
|
||||||
switch (diff)
|
switch (diff)
|
||||||
{
|
{
|
||||||
case 'easy':
|
case 'easy':
|
||||||
speedShit = songData.speed.easy;
|
speedShit = songData?.speed?.easy ?? 1.0;
|
||||||
case 'normal':
|
case 'normal':
|
||||||
speedShit = songData.speed.normal;
|
speedShit = songData?.speed?.normal ?? 1.0;
|
||||||
case 'hard':
|
case 'hard':
|
||||||
speedShit = songData.speed.hard;
|
speedShit = songData?.speed?.hard ?? 1.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (songData.speedMap[diff] == null) songData.speedMap[diff] = 1;
|
if (songData?.speedMap == null || songData?.speedMap[diff] == null)
|
||||||
|
{
|
||||||
|
speedShit = 1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
speedShit = songData.speedMap[diff];
|
speedShit = songData.speedMap[diff];
|
||||||
|
}
|
||||||
|
|
||||||
return speedShit;
|
return speedShit;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,194 +0,0 @@
|
||||||
package funkin.audio;
|
|
||||||
|
|
||||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
|
||||||
import flixel.system.FlxSound;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A group of FlxSounds which can be controlled as a whole.
|
|
||||||
*
|
|
||||||
* Add sounds to the group using `add()`, and then control them
|
|
||||||
* as a whole using the properties and methods of this class.
|
|
||||||
*
|
|
||||||
* It is assumed that all the sounds will play at the same time,
|
|
||||||
* and have the same duration.
|
|
||||||
*/
|
|
||||||
class FlxAudioGroup extends FlxTypedGroup<FlxSound>
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* The position in time of the sounds in the group.
|
|
||||||
* Measured in milliseconds.
|
|
||||||
*/
|
|
||||||
public var time(get, set):Float;
|
|
||||||
|
|
||||||
function get_time():Float
|
|
||||||
{
|
|
||||||
if (getFirstAlive() != null) return getFirstAlive().time;
|
|
||||||
else
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
function set_time(time:Float):Float
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
// account for different offsets per sound?
|
|
||||||
sound.time = time;
|
|
||||||
});
|
|
||||||
|
|
||||||
return time;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The volume of the sounds in the group.
|
|
||||||
*/
|
|
||||||
public var volume(get, set):Float;
|
|
||||||
|
|
||||||
function get_volume():Float
|
|
||||||
{
|
|
||||||
if (getFirstAlive() != null) return getFirstAlive().volume;
|
|
||||||
else
|
|
||||||
return 1.0;
|
|
||||||
}
|
|
||||||
|
|
||||||
function set_volume(volume:Float):Float
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.volume = volume;
|
|
||||||
});
|
|
||||||
|
|
||||||
return volume;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The pitch of the sounds in the group, as a multiplier of 1.0x.
|
|
||||||
* `2.0` would play the audio twice as fast with a higher pitch,
|
|
||||||
* and `0.5` would play the audio at half speed with a lower pitch.
|
|
||||||
*/
|
|
||||||
public var pitch(get, set):Float;
|
|
||||||
|
|
||||||
function get_pitch():Float
|
|
||||||
{
|
|
||||||
#if FLX_PITCH
|
|
||||||
if (getFirstAlive() != null) return getFirstAlive().pitch;
|
|
||||||
else
|
|
||||||
#end
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
function set_pitch(val:Float):Float
|
|
||||||
{
|
|
||||||
#if FLX_PITCH
|
|
||||||
trace('Setting audio pitch to ' + val);
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.pitch = val;
|
|
||||||
});
|
|
||||||
#end
|
|
||||||
return val;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Whether members of the group should be destroyed when they finish playing.
|
|
||||||
*/
|
|
||||||
public var autoDestroyMembers(default, set):Bool = false;
|
|
||||||
|
|
||||||
function set_autoDestroyMembers(value:Bool):Bool
|
|
||||||
{
|
|
||||||
autoDestroyMembers = value;
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.autoDestroy = value;
|
|
||||||
});
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Add a sound to the group.
|
|
||||||
*/
|
|
||||||
public override function add(sound:FlxSound):FlxSound
|
|
||||||
{
|
|
||||||
var result:FlxSound = super.add(sound);
|
|
||||||
|
|
||||||
if (result == null) return null;
|
|
||||||
|
|
||||||
// Apply parameters to the new sound.
|
|
||||||
result.autoDestroy = this.autoDestroyMembers;
|
|
||||||
result.pitch = this.pitch;
|
|
||||||
result.volume = this.volume;
|
|
||||||
|
|
||||||
// We have to play, then pause the sound to set the time,
|
|
||||||
// else the sound will restart immediately when played.
|
|
||||||
result.play(true, 0.0);
|
|
||||||
result.pause();
|
|
||||||
result.time = this.time;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Pause all the sounds in the group.
|
|
||||||
*/
|
|
||||||
public function pause()
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.pause();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Play all the sounds in the group.
|
|
||||||
*/
|
|
||||||
public function play(forceRestart:Bool = false, startTime:Float = 0.0, ?endTime:Float)
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.play(forceRestart, startTime, endTime);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Resume all the sounds in the group.
|
|
||||||
*/
|
|
||||||
public function resume()
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.resume();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stop all the sounds in the group.
|
|
||||||
*/
|
|
||||||
public function stop()
|
|
||||||
{
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
sound.stop();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public override function clear():Void
|
|
||||||
{
|
|
||||||
this.stop();
|
|
||||||
|
|
||||||
super.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Calculates the deviation of the sounds in the group from the target time.
|
|
||||||
*
|
|
||||||
* @param targetTime The time to compare the sounds to.
|
|
||||||
* If null, the current time of the first sound in the group is used.
|
|
||||||
* @return The largest deviation of the sounds in the group from the target time.
|
|
||||||
*/
|
|
||||||
public function calcDeviation(?targetTime:Float):Float
|
|
||||||
{
|
|
||||||
var deviation:Float = 0;
|
|
||||||
|
|
||||||
forEachAlive(function(sound:FlxSound) {
|
|
||||||
if (targetTime == null) targetTime = sound.time;
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var diff:Float = sound.time - targetTime;
|
|
||||||
if (Math.abs(diff) > Math.abs(deviation)) deviation = diff;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
return deviation;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,11 +1,13 @@
|
||||||
package funkin;
|
package funkin.audio;
|
||||||
|
|
||||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||||
import flixel.system.FlxSound;
|
import flixel.sound.FlxSound;
|
||||||
|
|
||||||
// different than FlxSoundGroup cuz this can control all the sounds time and shit
|
/**
|
||||||
// when needed
|
* A group of FlxSounds that are all synced together.
|
||||||
class VoicesGroup extends FlxTypedGroup<FlxSound>
|
* Unlike FlxSoundGroup, you cann also control their time and pitch.
|
||||||
|
*/
|
||||||
|
class SoundGroup extends FlxTypedGroup<FlxSound>
|
||||||
{
|
{
|
||||||
public var time(get, set):Float;
|
public var time(get, set):Float;
|
||||||
|
|
||||||
|
@ -13,16 +15,15 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
|
|
||||||
public var pitch(get, set):Float;
|
public var pitch(get, set):Float;
|
||||||
|
|
||||||
// make it a group that you add to?
|
|
||||||
public function new()
|
public function new()
|
||||||
{
|
{
|
||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Remove this.
|
@:deprecated("Create sound files and call add() instead")
|
||||||
public static function build(song:String, ?files:Array<String> = null):VoicesGroup
|
public static function build(song:String, ?files:Array<String> = null):SoundGroup
|
||||||
{
|
{
|
||||||
var result = new VoicesGroup();
|
var result = new SoundGroup();
|
||||||
|
|
||||||
if (files == null)
|
if (files == null)
|
||||||
{
|
{
|
||||||
|
@ -42,18 +43,17 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Finds the largest deviation from the desired time inside this VoicesGroup.
|
* Finds the largest deviation from the desired time inside this SoundGroup.
|
||||||
*
|
*
|
||||||
* @param targetTime The time to check against.
|
* @param targetTime The time to check against.
|
||||||
* If none is provided, it checks the time of all members against the first member of this VoicesGroup.
|
* If none is provided, it checks the time of all members against the first member of this SoundGroup.
|
||||||
* @return The largest deviation from the target time found.
|
* @return The largest deviation from the target time found.
|
||||||
*/
|
*/
|
||||||
public function checkSyncError(?targetTime:Float):Float
|
public function checkSyncError(?targetTime:Float):Float
|
||||||
{
|
{
|
||||||
var error:Float = 0;
|
var error:Float = 0;
|
||||||
|
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(snd) {
|
||||||
{
|
|
||||||
if (targetTime == null) targetTime = snd.time;
|
if (targetTime == null) targetTime = snd.time;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -64,31 +64,78 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
return error;
|
return error;
|
||||||
}
|
}
|
||||||
|
|
||||||
// prob a better / cleaner way to do all these forEach stuff?
|
/**
|
||||||
|
* Add a sound to the group.
|
||||||
|
*/
|
||||||
|
public override function add(sound:FlxSound):FlxSound
|
||||||
|
{
|
||||||
|
var result:FlxSound = super.add(sound);
|
||||||
|
|
||||||
|
if (result == null) return null;
|
||||||
|
|
||||||
|
// We have to play, then pause the sound to set the time,
|
||||||
|
// else the sound will restart immediately when played.
|
||||||
|
result.play(true, 0.0);
|
||||||
|
result.pause();
|
||||||
|
result.time = this.time;
|
||||||
|
|
||||||
|
// Apply parameters to the new sound.
|
||||||
|
result.pitch = this.pitch;
|
||||||
|
result.volume = this.volume;
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pause all the sounds in the group.
|
||||||
|
*/
|
||||||
public function pause()
|
public function pause()
|
||||||
{
|
{
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(sound:FlxSound) {
|
||||||
{
|
sound.pause();
|
||||||
snd.pause();
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public function play()
|
/**
|
||||||
|
* Play all the sounds in the group.
|
||||||
|
*/
|
||||||
|
public function play(forceRestart:Bool = false, startTime:Float = 0.0, ?endTime:Float)
|
||||||
{
|
{
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(sound:FlxSound) {
|
||||||
{
|
sound.play(forceRestart, startTime, endTime);
|
||||||
snd.play();
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resume all the sounds in the group.
|
||||||
|
*/
|
||||||
|
public function resume()
|
||||||
|
{
|
||||||
|
forEachAlive(function(sound:FlxSound) {
|
||||||
|
sound.resume();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Stop all the sounds in the group.
|
||||||
|
*/
|
||||||
public function stop()
|
public function stop()
|
||||||
{
|
{
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(sound:FlxSound) {
|
||||||
{
|
sound.stop();
|
||||||
snd.stop();
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove all sounds from the group.
|
||||||
|
*/
|
||||||
|
public override function clear():Void
|
||||||
|
{
|
||||||
|
this.stop();
|
||||||
|
|
||||||
|
super.clear();
|
||||||
|
}
|
||||||
|
|
||||||
function get_time():Float
|
function get_time():Float
|
||||||
{
|
{
|
||||||
if (getFirstAlive() != null) return getFirstAlive().time;
|
if (getFirstAlive() != null) return getFirstAlive().time;
|
||||||
|
@ -98,8 +145,7 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
|
|
||||||
function set_time(time:Float):Float
|
function set_time(time:Float):Float
|
||||||
{
|
{
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(snd) {
|
||||||
{
|
|
||||||
// account for different offsets per sound?
|
// account for different offsets per sound?
|
||||||
snd.time = time;
|
snd.time = time;
|
||||||
});
|
});
|
||||||
|
@ -117,8 +163,7 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
// in PlayState, adjust the code so that it only mutes the player1 vocal tracks?
|
// in PlayState, adjust the code so that it only mutes the player1 vocal tracks?
|
||||||
function set_volume(volume:Float):Float
|
function set_volume(volume:Float):Float
|
||||||
{
|
{
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(snd) {
|
||||||
{
|
|
||||||
snd.volume = volume;
|
snd.volume = volume;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -138,8 +183,7 @@ class VoicesGroup extends FlxTypedGroup<FlxSound>
|
||||||
{
|
{
|
||||||
#if FLX_PITCH
|
#if FLX_PITCH
|
||||||
trace('Setting audio pitch to ' + val);
|
trace('Setting audio pitch to ' + val);
|
||||||
forEachAlive(function(snd)
|
forEachAlive(function(snd) {
|
||||||
{
|
|
||||||
snd.pitch = val;
|
snd.pitch = val;
|
||||||
});
|
});
|
||||||
#end
|
#end
|
|
@ -1,119 +0,0 @@
|
||||||
package funkin.audio;
|
|
||||||
|
|
||||||
import flixel.system.FlxSound;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* An audio group that allows for specific control of vocal tracks.
|
|
||||||
*/
|
|
||||||
class VocalGroup extends FlxAudioGroup
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* The player's vocal track.
|
|
||||||
*/
|
|
||||||
var playerVocals:FlxSound;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The opponent's vocal track.
|
|
||||||
*/
|
|
||||||
var opponentVocals:FlxSound;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The volume of the player's vocal track.
|
|
||||||
* Nore that this value is multiplied by the overall volume of the group.
|
|
||||||
*/
|
|
||||||
public var playerVolume(default, set):Float;
|
|
||||||
|
|
||||||
function set_playerVolume(value:Float):Float
|
|
||||||
{
|
|
||||||
playerVolume = value;
|
|
||||||
if (playerVocals != null)
|
|
||||||
{
|
|
||||||
// Make sure volume is capped at 1.0.
|
|
||||||
playerVocals.volume = Math.min(playerVolume * this.volume, 1.0);
|
|
||||||
}
|
|
||||||
return playerVolume;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The volume of the opponent's vocal track.
|
|
||||||
* Nore that this value is multiplied by the overall volume of the group.
|
|
||||||
*/
|
|
||||||
public var opponentVolume(default, set):Float;
|
|
||||||
|
|
||||||
function set_opponentVolume(value:Float):Float
|
|
||||||
{
|
|
||||||
opponentVolume = value;
|
|
||||||
if (opponentVocals != null)
|
|
||||||
{
|
|
||||||
// Make sure volume is capped at 1.0.
|
|
||||||
opponentVocals.volume = opponentVolume * this.volume;
|
|
||||||
}
|
|
||||||
return opponentVolume;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets up the player's vocal track.
|
|
||||||
* Stops and removes the existing player track if one exists.
|
|
||||||
*/
|
|
||||||
public function setPlayerVocals(sound:FlxSound):FlxSound
|
|
||||||
{
|
|
||||||
if (playerVocals != null)
|
|
||||||
{
|
|
||||||
playerVocals.stop();
|
|
||||||
remove(playerVocals);
|
|
||||||
playerVocals = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
playerVocals = add(sound);
|
|
||||||
playerVocals.volume = this.playerVolume * this.volume;
|
|
||||||
|
|
||||||
return playerVocals;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets up the opponent's vocal track.
|
|
||||||
* Stops and removes the existing player track if one exists.
|
|
||||||
*/
|
|
||||||
public function setOpponentVocals(sound:FlxSound):FlxSound
|
|
||||||
{
|
|
||||||
if (opponentVocals != null)
|
|
||||||
{
|
|
||||||
opponentVocals.stop();
|
|
||||||
remove(opponentVocals);
|
|
||||||
opponentVocals = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
opponentVocals = add(sound);
|
|
||||||
opponentVocals.volume = this.opponentVolume * this.volume;
|
|
||||||
|
|
||||||
return opponentVocals;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* In this extension of FlxAudioGroup, there is a separate overall volume
|
|
||||||
* which affects all the members of the group.
|
|
||||||
*/
|
|
||||||
var _volume = 1.0;
|
|
||||||
|
|
||||||
override function get_volume():Float
|
|
||||||
{
|
|
||||||
return _volume;
|
|
||||||
}
|
|
||||||
|
|
||||||
override function set_volume(value:Float):Float
|
|
||||||
{
|
|
||||||
_volume = super.set_volume(value);
|
|
||||||
|
|
||||||
if (playerVocals != null)
|
|
||||||
{
|
|
||||||
playerVocals.volume = playerVolume * _volume;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (opponentVocals != null)
|
|
||||||
{
|
|
||||||
opponentVocals.volume = opponentVolume * _volume;
|
|
||||||
}
|
|
||||||
|
|
||||||
return _volume;
|
|
||||||
}
|
|
||||||
}
|
|
68
source/funkin/audio/VoicesGroup.hx
Normal file
68
source/funkin/audio/VoicesGroup.hx
Normal file
|
@ -0,0 +1,68 @@
|
||||||
|
package funkin.audio;
|
||||||
|
|
||||||
|
import flixel.sound.FlxSound;
|
||||||
|
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||||
|
|
||||||
|
class VoicesGroup extends SoundGroup
|
||||||
|
{
|
||||||
|
var playerVoices:FlxTypedGroup<FlxSound>;
|
||||||
|
var opponentVoices:FlxTypedGroup<FlxSound>;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Control the volume of only the sounds in the player group.
|
||||||
|
*/
|
||||||
|
public var playerVolume(default, set):Float;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Control the volume of only the sounds in the opponent group.
|
||||||
|
*/
|
||||||
|
public var opponentVolume(default, set):Float;
|
||||||
|
|
||||||
|
public function new()
|
||||||
|
{
|
||||||
|
super();
|
||||||
|
playerVoices = new FlxTypedGroup<FlxSound>();
|
||||||
|
opponentVoices = new FlxTypedGroup<FlxSound>();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a voice to the player group.
|
||||||
|
*/
|
||||||
|
public function addPlayerVoice(sound:FlxSound):Void
|
||||||
|
{
|
||||||
|
super.add(sound);
|
||||||
|
playerVoices.add(sound);
|
||||||
|
}
|
||||||
|
|
||||||
|
function set_playerVolume(volume:Float):Float
|
||||||
|
{
|
||||||
|
playerVoices.forEachAlive(function(voice:FlxSound) {
|
||||||
|
voice.volume = volume;
|
||||||
|
});
|
||||||
|
return playerVolume = volume;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a voice to the opponent group.
|
||||||
|
*/
|
||||||
|
public function addOpponentVoice(sound:FlxSound):Void
|
||||||
|
{
|
||||||
|
super.add(sound);
|
||||||
|
opponentVoices.add(sound);
|
||||||
|
}
|
||||||
|
|
||||||
|
function set_opponentVolume(volume:Float):Float
|
||||||
|
{
|
||||||
|
opponentVoices.forEachAlive(function(voice:FlxSound) {
|
||||||
|
voice.volume = volume;
|
||||||
|
});
|
||||||
|
return opponentVolume = volume;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override function clear():Void
|
||||||
|
{
|
||||||
|
playerVoices.clear();
|
||||||
|
opponentVoices.clear();
|
||||||
|
super.clear();
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,11 +1,13 @@
|
||||||
package funkin.play;
|
package funkin.play;
|
||||||
|
|
||||||
|
import funkin.play.song.SongData.SongDataParser;
|
||||||
|
import flixel.sound.FlxSound;
|
||||||
|
import flixel.addons.transition.FlxTransitionableState;
|
||||||
import flixel.FlxCamera;
|
import flixel.FlxCamera;
|
||||||
import flixel.FlxObject;
|
import flixel.FlxObject;
|
||||||
import flixel.FlxSprite;
|
import flixel.FlxSprite;
|
||||||
import flixel.FlxState;
|
import flixel.FlxState;
|
||||||
import flixel.FlxSubState;
|
import flixel.FlxSubState;
|
||||||
import flixel.addons.transition.FlxTransitionableState;
|
|
||||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||||
import flixel.input.keyboard.FlxKey;
|
import flixel.input.keyboard.FlxKey;
|
||||||
import flixel.math.FlxMath;
|
import flixel.math.FlxMath;
|
||||||
|
@ -17,18 +19,14 @@ import flixel.ui.FlxBar;
|
||||||
import flixel.util.FlxColor;
|
import flixel.util.FlxColor;
|
||||||
import flixel.util.FlxSort;
|
import flixel.util.FlxSort;
|
||||||
import flixel.util.FlxTimer;
|
import flixel.util.FlxTimer;
|
||||||
import funkin.Highscore.Tallies;
|
|
||||||
import funkin.Note;
|
|
||||||
import funkin.Section.SwagSection;
|
|
||||||
import funkin.SongLoad.SwagSong;
|
|
||||||
import funkin.charting.ChartingState;
|
import funkin.charting.ChartingState;
|
||||||
|
import funkin.Highscore.Tallies;
|
||||||
import funkin.modding.events.ScriptEvent;
|
import funkin.modding.events.ScriptEvent;
|
||||||
import funkin.modding.events.ScriptEventDispatcher;
|
import funkin.modding.events.ScriptEventDispatcher;
|
||||||
import funkin.play.Strumline.StrumlineArrow;
|
import funkin.Note;
|
||||||
import funkin.play.Strumline.StrumlineStyle;
|
|
||||||
import funkin.play.character.BaseCharacter;
|
import funkin.play.character.BaseCharacter;
|
||||||
import funkin.play.character.CharacterData.CharacterDataParser;
|
|
||||||
import funkin.play.character.CharacterData;
|
import funkin.play.character.CharacterData;
|
||||||
|
import funkin.play.character.CharacterData.CharacterDataParser;
|
||||||
import funkin.play.cutscene.VanillaCutscenes;
|
import funkin.play.cutscene.VanillaCutscenes;
|
||||||
import funkin.play.event.SongEvent.SongEventParser;
|
import funkin.play.event.SongEvent.SongEventParser;
|
||||||
import funkin.play.scoring.Scoring;
|
import funkin.play.scoring.Scoring;
|
||||||
|
@ -39,6 +37,11 @@ import funkin.play.song.SongData.SongPlayableChar;
|
||||||
import funkin.play.song.SongValidator;
|
import funkin.play.song.SongValidator;
|
||||||
import funkin.play.stage.Stage;
|
import funkin.play.stage.Stage;
|
||||||
import funkin.play.stage.StageData.StageDataParser;
|
import funkin.play.stage.StageData.StageDataParser;
|
||||||
|
import funkin.play.Strumline.StrumlineArrow;
|
||||||
|
import funkin.play.Strumline.StrumlineStyle;
|
||||||
|
import funkin.Section.SwagSection;
|
||||||
|
import funkin.SongLoad.SwagSong;
|
||||||
|
import funkin.audio.VoicesGroup;
|
||||||
import funkin.ui.PopUpStuff;
|
import funkin.ui.PopUpStuff;
|
||||||
import funkin.ui.PreferencesMenu;
|
import funkin.ui.PreferencesMenu;
|
||||||
import funkin.ui.stageBuildShit.StageOffsetSubstate;
|
import funkin.ui.stageBuildShit.StageOffsetSubstate;
|
||||||
|
@ -359,7 +362,7 @@ class PlayState extends MusicBeatState
|
||||||
if (currentChart != null)
|
if (currentChart != null)
|
||||||
{
|
{
|
||||||
currentChart.cacheInst();
|
currentChart.cacheInst();
|
||||||
currentChart.cacheVocals();
|
currentChart.cacheVocals('bf');
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1059,9 +1062,11 @@ class PlayState extends MusicBeatState
|
||||||
|
|
||||||
currentSong.song = currentSong.song;
|
currentSong.song = currentSong.song;
|
||||||
|
|
||||||
if (currentSong.needsVoices) vocals = VoicesGroup.build(currentSong.song, currentSong.voiceList);
|
vocals = new VoicesGroup();
|
||||||
else
|
var playerVocals:FlxSound = FlxG.sound.load(Paths.voices(currentSong.song, 'bf'), 1.0, false);
|
||||||
vocals = VoicesGroup.build(currentSong.song, null);
|
vocals.addPlayerVoice(playerVocals);
|
||||||
|
var opponentVocals:FlxSound = FlxG.sound.load(Paths.voices(currentSong.song, 'dad'), 1.0, false);
|
||||||
|
vocals.addOpponentVoice(opponentVocals);
|
||||||
|
|
||||||
vocals.members[0].onComplete = function() {
|
vocals.members[0].onComplete = function() {
|
||||||
vocalsFinished = true;
|
vocalsFinished = true;
|
||||||
|
@ -1427,6 +1432,8 @@ class PlayState extends MusicBeatState
|
||||||
|
|
||||||
FlxG.sound.music.volume = 1;
|
FlxG.sound.music.volume = 1;
|
||||||
vocals.volume = 1;
|
vocals.volume = 1;
|
||||||
|
vocals.playerVolume = 1;
|
||||||
|
vocals.opponentVolume = 1;
|
||||||
|
|
||||||
currentStage.resetStage();
|
currentStage.resetStage();
|
||||||
|
|
||||||
|
@ -1719,7 +1726,7 @@ class PlayState extends MusicBeatState
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Volume of DAD.
|
// Volume of DAD.
|
||||||
if (currentSong != null && currentSong.needsVoices) vocals.volume = 1;
|
if (currentSong != null && currentSong.needsVoices) vocals.opponentVolume = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1903,7 +1910,7 @@ class PlayState extends MusicBeatState
|
||||||
// if ()
|
// if ()
|
||||||
StoryMenuState.weekUnlocked[Std.int(Math.min(storyWeek + 1, StoryMenuState.weekUnlocked.length - 1))] = true;
|
StoryMenuState.weekUnlocked[Std.int(Math.min(storyWeek + 1, StoryMenuState.weekUnlocked.length - 1))] = true;
|
||||||
|
|
||||||
if (currentSong.validScore)
|
if (currentSong?.validScore)
|
||||||
{
|
{
|
||||||
NGio.unlockMedal(60961);
|
NGio.unlockMedal(60961);
|
||||||
Highscore.saveWeekScore(storyWeek, campaignScore, storyDifficulty);
|
Highscore.saveWeekScore(storyWeek, campaignScore, storyDifficulty);
|
||||||
|
@ -1929,7 +1936,7 @@ class PlayState extends MusicBeatState
|
||||||
FlxG.sound.music.stop();
|
FlxG.sound.music.stop();
|
||||||
vocals.stop();
|
vocals.stop();
|
||||||
|
|
||||||
if (currentSong.song.toLowerCase() == 'eggnog')
|
if ((currentSong?.song ?? '').toLowerCase() == 'eggnog')
|
||||||
{
|
{
|
||||||
var blackShit:FlxSprite = new FlxSprite(-FlxG.width * FlxG.camera.zoom,
|
var blackShit:FlxSprite = new FlxSprite(-FlxG.width * FlxG.camera.zoom,
|
||||||
-FlxG.height * FlxG.camera.zoom).makeGraphic(FlxG.width * 3, FlxG.height * 3, FlxColor.BLACK);
|
-FlxG.height * FlxG.camera.zoom).makeGraphic(FlxG.width * 3, FlxG.height * 3, FlxColor.BLACK);
|
||||||
|
@ -1948,7 +1955,7 @@ class PlayState extends MusicBeatState
|
||||||
{
|
{
|
||||||
previousCameraFollowPoint = cameraFollowPoint;
|
previousCameraFollowPoint = cameraFollowPoint;
|
||||||
|
|
||||||
currentSong = SongLoad.loadFromJson(storyPlaylist[0].toLowerCase() + difficulty, storyPlaylist[0]);
|
currentSong_NEW = SongDataParser.fetchSong(PlayState.storyPlaylist[0].toLowerCase());
|
||||||
LoadingState.loadAndSwitchState(new PlayState());
|
LoadingState.loadAndSwitchState(new PlayState());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1992,7 +1999,7 @@ class PlayState extends MusicBeatState
|
||||||
{
|
{
|
||||||
var noteDiff:Float = Math.abs(strumtime - Conductor.songPosition);
|
var noteDiff:Float = Math.abs(strumtime - Conductor.songPosition);
|
||||||
// boyfriend.playAnimation('hey');
|
// boyfriend.playAnimation('hey');
|
||||||
vocals.volume = 1;
|
vocals.playerVolume = 1;
|
||||||
|
|
||||||
var isSick:Bool = false;
|
var isSick:Bool = false;
|
||||||
var score = Scoring.scoreNote(noteDiff, PBOT1);
|
var score = Scoring.scoreNote(noteDiff, PBOT1);
|
||||||
|
@ -2124,7 +2131,6 @@ class PlayState extends MusicBeatState
|
||||||
// TODO: Un-hardcode this stuff.
|
// TODO: Un-hardcode this stuff.
|
||||||
if (currentStage.getDad().characterId == 'mom')
|
if (currentStage.getDad().characterId == 'mom')
|
||||||
{
|
{
|
||||||
vocals.volume = 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (currentSong.song.toLowerCase() == 'tutorial')
|
if (currentSong.song.toLowerCase() == 'tutorial')
|
||||||
|
@ -2312,7 +2318,7 @@ class PlayState extends MusicBeatState
|
||||||
|
|
||||||
if (event.playSound)
|
if (event.playSound)
|
||||||
{
|
{
|
||||||
vocals.volume = 0;
|
vocals.playerVolume = 0;
|
||||||
FlxG.sound.play(Paths.soundRandom('missnote', 1, 3), FlxG.random.float(0.1, 0.2));
|
FlxG.sound.play(Paths.soundRandom('missnote', 1, 3), FlxG.random.float(0.1, 0.2));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2367,7 +2373,7 @@ class PlayState extends MusicBeatState
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
vocals.volume = 0;
|
vocals.playerVolume = 0;
|
||||||
|
|
||||||
if (Highscore.tallies.combo != 0)
|
if (Highscore.tallies.combo != 0)
|
||||||
{
|
{
|
||||||
|
@ -2405,7 +2411,7 @@ class PlayState extends MusicBeatState
|
||||||
playerStrumline.getArrow(note.data.noteData).playAnimation('confirm', true);
|
playerStrumline.getArrow(note.data.noteData).playAnimation('confirm', true);
|
||||||
|
|
||||||
note.wasGoodHit = true;
|
note.wasGoodHit = true;
|
||||||
vocals.volume = 1;
|
vocals.playerVolume = 1;
|
||||||
|
|
||||||
if (!note.isSustainNote)
|
if (!note.isSustainNote)
|
||||||
{
|
{
|
||||||
|
@ -2742,15 +2748,10 @@ class PlayState extends MusicBeatState
|
||||||
* This function is called whenever Flixel switches switching to a new FlxState.
|
* This function is called whenever Flixel switches switching to a new FlxState.
|
||||||
* @return Whether to actually switch to the new state.
|
* @return Whether to actually switch to the new state.
|
||||||
*/
|
*/
|
||||||
override function switchTo(nextState:FlxState):Bool
|
override function startOutro(onComplete:() -> Void):Void
|
||||||
{
|
|
||||||
var result = super.switchTo(nextState);
|
|
||||||
|
|
||||||
if (result)
|
|
||||||
{
|
{
|
||||||
performCleanup();
|
performCleanup();
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
onComplete();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue