half of multiple vocals support

This commit is contained in:
Frakist
2023-11-03 00:39:07 +03:00
parent 25b213cccb
commit 398b61a824
12 changed files with 94 additions and 34 deletions
-3
View File
@@ -1,3 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
}
-3
View File
@@ -1,3 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
}
-3
View File
@@ -1,3 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
}
-3
View File
@@ -1,3 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
}
-3
View File
@@ -1,3 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
}
-4
View File
@@ -1,4 +0,0 @@
function onPlayerHit(event) {
trace(event.noteType);
trace(SONG.noteTypes);
}
+6 -6
View File
@@ -78,16 +78,16 @@ class Paths
inline static public function music(key:String, ?library:String)
return getPath('music/$key.$SOUND_EXT', library);
inline static public function voices(song:String, difficulty:String = "normal")
inline static public function voices(song:String, difficulty:String = "normal", ?prefix:String = "")
{
var diff = getPath('songs/${song.toLowerCase()}/song/Voices-${difficulty.toLowerCase()}.$SOUND_EXT', null);
return OpenFlAssets.exists(diff) ? diff : getPath('songs/${song.toLowerCase()}/song/Voices.$SOUND_EXT', null);
var diff = getPath('songs/${song.toLowerCase()}/song/Voices$prefix-${difficulty.toLowerCase()}.$SOUND_EXT', null);
return OpenFlAssets.exists(diff) ? diff : getPath('songs/${song.toLowerCase()}/song/Voices$prefix.$SOUND_EXT', null);
}
inline static public function inst(song:String, difficulty:String = "normal")
inline static public function inst(song:String, difficulty:String = "normal", ?prefix:String = "")
{
var diff = getPath('songs/${song.toLowerCase()}/song/Inst-${difficulty.toLowerCase()}.$SOUND_EXT', null);
return OpenFlAssets.exists(diff) ? diff : getPath('songs/${song.toLowerCase()}/song/Inst.$SOUND_EXT', null);
var diff = getPath('songs/${song.toLowerCase()}/song/Inst$prefix-${difficulty.toLowerCase()}.$SOUND_EXT', null);
return OpenFlAssets.exists(diff) ? diff : getPath('songs/${song.toLowerCase()}/song/Inst$prefix.$SOUND_EXT', null);
}
static public function image(key:String, ?library:String, checkForAtlas:Bool = false)
+1
View File
@@ -40,6 +40,7 @@ typedef ChartStrumLine = {
var ?strumPos:Array<Float>;
var ?strumScale:Float;
var ?scrollSpeed:Float;
var ?vocalsSuffix:String;
var ?strumLinePos:Float; // Backwards compatability
}
+20 -2
View File
@@ -21,7 +21,7 @@ import funkin.editors.ui.UIState;
import openfl.net.FileReference;
class Charter extends UIState {
static var __song:String;
public static var __song:String;
static var __diff:String;
static var __reload:Bool;
@@ -1444,6 +1444,8 @@ typedef SelectionDragChange = {
class CharterNoteTypeButton extends UIButton {
public var theType:String;
public var textBox:UIAutoCompleteTextBox;
public var deleteButton:UIButton;
public var deleteIcon:FlxSprite;
public function new(type:String, parent:UIButtonList<CharterNoteTypeButton>, state:Charter, suggestList:Array<String>) {
theType = type;
super(0,0,"" ,function() {
@@ -1452,7 +1454,7 @@ class CharterNoteTypeButton extends UIButton {
i.alpha = i == this ? 1 : 0.25;
},296,30);
if (suggestList != null && suggestList.length > 0) {
members.push(textBox = new UIAutoCompleteTextBox((bWidth - 200) / 2, y + 4, theType, 200, bHeight - 8));
members.push(textBox = new UIAutoCompleteTextBox((bWidth - 218) / 2, y + 4, theType, 200, bHeight - 8));
textBox.suggestItems = suggestList;
textBox.antialiasing = true;
textBox.onChange = function(typer:String) {
@@ -1464,13 +1466,29 @@ class CharterNoteTypeButton extends UIButton {
if (state.curNoteType == theType) state.curNoteType = typer;
theType = typer;
}
deleteButton = new UIButton(textBox.x + 204, bHeight/2 - (28/2), "", function () {
parent.remove(this);
}, 28, 28);
deleteButton.color = 0xFFFF0000;
deleteButton.autoAlpha = false;
members.push(deleteButton);
deleteIcon = new FlxSprite(deleteButton.x + (14/2), deleteButton.y + 5).loadGraphic(Paths.image('editors/character/delete-button'));
deleteIcon.antialiasing = false;
members.push(deleteIcon);
}
else field.text = type;
autoAlpha = false;
}
override function update(elapsed) {
super.update(elapsed);
if (textBox != null) textBox.y = y + 4;
if (deleteButton != null) {
deleteButton.y = y + bHeight / 2 - deleteButton.bHeight / 2;
deleteIcon.x = deleteButton.x + (14/2); deleteIcon.y = deleteButton.y + 5;
}
//x = alpha == 0.25 ? -50 : 10;
}
}
@@ -12,6 +12,7 @@ class CharterStrumlineScreen extends UISubstateWindow {
public var charactersList:UIButtonList<CharacterButton>;
public var typeDropdown:UIDropDown;
public var vocalsSuffixDropDown:UIDropDown;
public var stagePositionDropdown:UIDropDown;
public var hudScaleStepper:UINumericStepper;
public var hudXStepper:UINumericStepper;
@@ -135,6 +136,25 @@ class CharterStrumlineScreen extends UISubstateWindow {
}, 125);
add(closeButton);
closeButton.color = 0xFFFF0000;
var suffixlist = ["NONE"];
for (i in Paths.getFolderContent('songs/${Charter.__song.toLowerCase()}/song'))
if (i.startsWith("Voices")) {
i = haxe.io.Path.withoutExtension(i.substr("Voices".length));
if (i == "") continue;
for (j in PlayState.SONG.meta.difficulties) {
if (i.endsWith('-${j.toLowerCase()}')) {
if (suffixlist.contains(i.substring(0, i.length - j.length))) continue;
else suffixlist.push(i.substring(0, i.length - j.length));
}
else if (!suffixlist.contains(i)) suffixlist.push(i);
}
}
vocalsSuffixDropDown = new UIDropDown(typeDropdown.x, hudScaleStepper.y + 128, 200, 32, suffixlist, suffixlist.indexOf(strumLine.vocalsSuffix));
add(vocalsSuffixDropDown);
addLabelOn(vocalsSuffixDropDown, "Vocal Suffix");
}
function saveStrumline() {
@@ -152,7 +172,8 @@ class CharterStrumlineScreen extends UISubstateWindow {
visible: strumLine.visible,
strumPos: [0, hudYStepper.value],
strumLinePos: hudXStepper.value,
strumScale: hudScaleStepper.value
strumScale: hudScaleStepper.value,
vocalsSuffix: vocalsSuffixDropDown.options[vocalsSuffixDropDown.index] != "NONE" ? vocalsSuffixDropDown.options[vocalsSuffixDropDown.index] : ""
};
if(!usesChartscrollSpeed.checked) newStrumLine.scrollSpeed = scrollSpeedStepper.value;
if (onSave != null) onSave(newStrumLine);
+37 -5
View File
@@ -633,16 +633,17 @@ class PlayState extends MusicBeatState
var startingPos:FlxPoint = strumLine.strumPos == null ?
FlxPoint.get((FlxG.width * strOffset) - ((Note.swagWidth * (strumLine.strumScale == null ? 1 : strumLine.strumScale)) * 2), this.strumLine.y) :
FlxPoint.get(strumLine.strumPos[0] == 0 ? ((FlxG.width * strOffset) - ((Note.swagWidth * (strumLine.strumScale == null ? 1 : strumLine.strumScale)) * 2)) : strumLine.strumPos[0], strumLine.strumPos[1]);
var strLine = new StrumLine(chars,
startingPos,
strumLine.strumScale == null ? 1 : strumLine.strumScale,
strumLine.type == 2 || (!coopMode && !((strumLine.type == 1 && !opponentMode) || (strumLine.type == 0 && opponentMode))),
strumLine.type != 1, coopMode ? (strumLine.type == 1 ? controlsP1 : controlsP2) : controls
strumLine.type != 1, coopMode ? (strumLine.type == 1 ? controlsP1 : controlsP2) : controls,
strumLine.vocalsSuffix
);
strLine.cameras = [camHUD];
strLine.data = strumLine;
strLine.visible = (strumLine.visible != false);
strLine.vocals.group = FlxG.sound.defaultMusicGroup;
strLine.ID = i;
strumLines.add(strLine);
}
@@ -890,7 +891,15 @@ class PlayState extends MusicBeatState
vocals.pause();
inst.pause();
for (strumLine in strumLines.members) {
strumLine.vocals.play();
strumLine.vocals.pause();
}
inst.time = vocals.time = (chartingMode && Charter.startHere) ? Charter.startTime : 0;
for (strumLine in strumLines.members) {
strumLine.vocals.time = vocals.time;
strumLine.vocals.play();
}
vocals.play();
inst.play();
@@ -903,6 +912,9 @@ class PlayState extends MusicBeatState
scripts.call("destroy");
for(g in __cachedGraphics)
g.useCount--;
@:privateAccess
for (strumLine in strumLines.members)
FlxG.sound.destroySound(strumLine.vocals);
super.destroy();
scripts = FlxDestroyUtil.destroy(scripts);
@:privateAccess {
@@ -973,6 +985,7 @@ class PlayState extends MusicBeatState
{
if (FlxG.sound.music != null)
{
for (strumLine in strumLines.members) strumLine.vocals.pause();
FlxG.sound.music.pause();
vocals.pause();
}
@@ -1031,6 +1044,7 @@ class PlayState extends MusicBeatState
override public function onFocusLost():Void
{
if (!paused && FlxG.autoPause) {
for (strumLine in strumLines.members) strumLine.vocals.pause();
inst.pause();
vocals.pause();
}
@@ -1043,10 +1057,15 @@ class PlayState extends MusicBeatState
function resyncVocals():Void
{
vocals.pause();
for (strumLine in strumLines.members) strumLine.vocals.pause();
FlxG.sound.music.play();
Conductor.songPosition = FlxG.sound.music.time;
vocals.time = Conductor.songPosition + Conductor.songOffset;
for (strumLine in strumLines.members) {
strumLine.vocals.time = vocals.time;
strumLine.vocals.play();
}
vocals.play();
scripts.call("onVocalsResync");
}
@@ -1139,7 +1158,9 @@ class PlayState extends MusicBeatState
startSong();
}
} else {
__vocalOffsetViolation = Math.max(0, __vocalOffsetViolation + (FlxG.sound.music.time != vocals.time ? elapsed : -elapsed / 2));
var instTime = FlxG.sound.music.time;
var isOffsync = vocals.time != instTime || [for(strumLine in strumLines.members) strumLine.vocals.time != instTime].contains(true);
__vocalOffsetViolation = Math.max(0, __vocalOffsetViolation + (isOffsync ? elapsed : -elapsed / 2));
if (__vocalOffsetViolation > 25) {
resyncVocals();
__vocalOffsetViolation = 0;
@@ -1267,6 +1288,7 @@ class PlayState extends MusicBeatState
vocals.stop();
if (FlxG.sound.music != null)
FlxG.sound.music.stop();
for (strumLine in strumLines.members) strumLine.vocals.stop();
openSubState(new GameOverSubstate(event.x, event.y, event.deathCharID, event.isPlayer, event.gameOverSong, event.lossSFX, event.retrySFX));
@@ -1282,6 +1304,10 @@ class PlayState extends MusicBeatState
canPause = false;
inst.volume = 0;
vocals.volume = 0;
for (strumLine in strumLines.members) {
strumLine.vocals.volume = 0;
strumLine.vocals.pause();
}
inst.pause();
vocals.pause();
@@ -1409,7 +1435,10 @@ class PlayState extends MusicBeatState
if (event.playMissSound) FlxG.sound.play(event.missSound, event.missVolume);
if (event.muteVocals) vocals.volume = 0;
if (event.muteVocals) {
vocals.volume = 0;
strumLine.vocals.volume = 0;
}
if (event.accuracy != null) {
accuracyPressedNotes++;
@@ -1512,7 +1541,10 @@ class PlayState extends MusicBeatState
}
}
if (event.unmuteVocals) vocals.volume = 1;
if (event.unmuteVocals) {
vocals.volume = 1;
strumLine.vocals.volume = 1;
}
if (event.enableCamZooming) camZooming = true;
if (event.autoHitLastSustain) {
if (note.nextSustain != null && note.nextSustain.nextSustain == null) {
+8 -1
View File
@@ -8,6 +8,7 @@ import funkin.backend.system.Conductor;
import funkin.backend.chart.ChartData;
import funkin.backend.system.Controls;
import flixel.tweens.FlxTween;
import flixel.sound.FlxSound;
class StrumLine extends FlxTypedGroup<Strum> {
/**
@@ -74,6 +75,10 @@ class StrumLine extends FlxTypedGroup<Strum> {
* TODO: Write documention about this being a variable that can help when making multi key
*/
public var strumAnimPrefix = ["left", "down", "up", "right"];
/**
* Vocals sound (Vocals.ogg). Used for individual vocals per strumline.
*/
public var vocals:FlxSound;
public var extra:Map<String, Dynamic> = [];
@@ -89,7 +94,7 @@ class StrumLine extends FlxTypedGroup<Strum> {
private var startingPos:FlxPoint = FlxPoint.get(0,0);
private var strumScale:Float = 1;
public function new(characters:Array<Character>, startingPos:FlxPoint, strumScale:Float, cpu:Bool = false, opponentSide:Bool = true, ?controls:Controls) {
public function new(characters:Array<Character>, startingPos:FlxPoint, strumScale:Float, cpu:Bool = false, opponentSide:Bool = true, ?controls:Controls, ?vocalPrefix:String = "") {
super();
this.characters = characters;
this.startingPos = startingPos;
@@ -98,6 +103,8 @@ class StrumLine extends FlxTypedGroup<Strum> {
this.opponentSide = opponentSide;
this.controls = controls;
this.notes = new NoteGroup();
vocals = vocalPrefix != "" ? FlxG.sound.load(Paths.voices(PlayState.SONG.meta.name, PlayState.difficulty, vocalPrefix)) : new FlxSound();
vocals.persist = false;
}
public function generate(strumLine:ChartStrumLine, ?startTime:Float) {