506 lines
18 KiB
C#
506 lines
18 KiB
C#
using NaughtyBezierCurves;
|
|
using HeavenStudio.Common;
|
|
using HeavenStudio.Util;
|
|
using HeavenStudio.InputSystem;
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using UnityEngine;
|
|
using TMPro;
|
|
|
|
namespace HeavenStudio.Games.Loaders
|
|
{
|
|
using static Minigames;
|
|
using Jukebox;
|
|
public static class CtrChargingChickenLoader
|
|
{
|
|
public static Minigame AddGame(EventCaller eventCaller)
|
|
{
|
|
return new Minigame("chargingChicken", "Charging Chicken", "FFFFFF", false, false, new List<GameAction>()
|
|
{
|
|
new GameAction("input", "Charge")
|
|
{
|
|
preFunction = delegate {
|
|
var e = eventCaller.currentEntity;
|
|
if (eventCaller.gameManager.minigameObj.TryGetComponent(out ChargingChicken instance)) {
|
|
instance.ChargeUp(e.beat, e.length, e["drumbeat"]);
|
|
}
|
|
ChargingChicken.CountIn(e.beat);
|
|
},
|
|
parameters = new List<Param>()
|
|
{
|
|
new Param("drumbeat", ChargingChicken.DrumLoopList.Straight, "Drum Beat", "REPLACE THIS"),
|
|
},
|
|
defaultLength = 8,
|
|
resizable = true,
|
|
preFunctionLength = 4,
|
|
},
|
|
new GameAction("changeBgColor", "Background Appearance")
|
|
{
|
|
function = delegate {
|
|
var e = eventCaller.currentEntity;
|
|
if (eventCaller.gameManager.minigameObj.TryGetComponent(out ChargingChicken instance)) {
|
|
instance.ChangeColor(e.beat, e.length, e["colorFrom"], e["colorTo"], e["colorFrom2"], e["colorTo2"], e["ease"]);
|
|
}
|
|
},
|
|
defaultLength = 4f,
|
|
resizable = true,
|
|
parameters = new List<Param>()
|
|
{
|
|
new Param("colorFrom", ChargingChicken.defaultBGColor, "Color A Start", "Set the top-most color of the background gradient at the start of the event."),
|
|
new Param("colorTo", ChargingChicken.defaultBGColor, "Color A End", "Set the top-most color of the background gradient at the end of the event."),
|
|
new Param("colorFrom2", ChargingChicken.defaultBGColorBottom, "Color B Start", "Set the bottom-most color of the background gradient at the start of the event."),
|
|
new Param("colorTo2", ChargingChicken.defaultBGColorBottom, "Color B End", "Set the bottom-most color of the background gradient at the end of the event."),
|
|
new Param("ease", Util.EasingFunction.Ease.Linear, "Ease", "Set the easing of the action.", new() {
|
|
new Param.CollapseParam((x, _) => (int)x != (int)Util.EasingFunction.Ease.Instant, new[] { "colorFrom", "colorFrom2" }),
|
|
}),
|
|
}
|
|
},
|
|
},
|
|
new List<string>() { "ctr", "aim" },
|
|
"ctrChargingChicken", "en",
|
|
new List<string>() { "en" }
|
|
);
|
|
}
|
|
}
|
|
}
|
|
|
|
namespace HeavenStudio.Games
|
|
{
|
|
public class ChargingChicken : Minigame
|
|
{
|
|
//definitions
|
|
#region Definitions
|
|
|
|
[SerializeField] SpriteRenderer gradient;
|
|
[SerializeField] SpriteRenderer bgLow;
|
|
[SerializeField] SpriteRenderer bgHigh;
|
|
[SerializeField] Transform sea;
|
|
|
|
bool isInputting = false;
|
|
|
|
double bgColorStartBeat = -1;
|
|
float bgColorLength = 0;
|
|
Util.EasingFunction.Ease lastEase;
|
|
Color colorFrom;
|
|
Color colorTo;
|
|
Color colorFrom2;
|
|
Color colorTo2;
|
|
|
|
float seaPos = 0;
|
|
|
|
public enum DrumLoopList
|
|
{
|
|
None,
|
|
Straight,
|
|
SwungSixteenth,
|
|
SwungEighth,
|
|
Triplet,
|
|
}
|
|
|
|
private static Color _defaultBGColor;
|
|
public static Color defaultBGColor
|
|
{
|
|
get
|
|
{
|
|
ColorUtility.TryParseHtmlString("#6ED6FF", out _defaultBGColor);
|
|
return _defaultBGColor;
|
|
}
|
|
}
|
|
private static Color _defaultBGColorBottom;
|
|
public static Color defaultBGColorBottom
|
|
{
|
|
get
|
|
{
|
|
ColorUtility.TryParseHtmlString("#FFFFFF", out _defaultBGColorBottom);
|
|
return _defaultBGColorBottom;
|
|
}
|
|
}
|
|
|
|
//drum loops
|
|
#region DrumLoops
|
|
|
|
private struct DrumLoop : IComparable<DrumLoop>
|
|
{
|
|
// override object.Equals
|
|
public override bool Equals(object obj)
|
|
{
|
|
//
|
|
// See the full list of guidelines at
|
|
// http://go.microsoft.com/fwlink/?LinkID=85237
|
|
// and also the guidance for operator== at
|
|
// http://go.microsoft.com/fwlink/?LinkId=85238
|
|
//
|
|
|
|
if (obj == null || GetType() != obj.GetType())
|
|
{
|
|
return false;
|
|
}
|
|
|
|
// TODO: write your implementation of Equals() here
|
|
throw new System.NotImplementedException();
|
|
}
|
|
|
|
// override object.GetHashCode
|
|
public override int GetHashCode()
|
|
{
|
|
// TODO: write your implementation of GetHashCode() here
|
|
throw new System.NotImplementedException();
|
|
}
|
|
public int CompareTo(DrumLoop other)
|
|
{
|
|
if (other == null) return 1;
|
|
|
|
return timing.CompareTo(other.timing);
|
|
}
|
|
|
|
public static bool operator > (DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) > 0;
|
|
}
|
|
|
|
public static bool operator < (DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) < 0;
|
|
}
|
|
|
|
public static bool operator >=(DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) >= 0;
|
|
}
|
|
|
|
public static bool operator <=(DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) <= 0;
|
|
}
|
|
|
|
public static bool operator ==(DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) == 0;
|
|
}
|
|
|
|
public static bool operator !=(DrumLoop operand1, DrumLoop operand2)
|
|
{
|
|
return operand1.CompareTo(operand2) != 0;
|
|
}
|
|
public int drumType;
|
|
public double timing;
|
|
public float volume;
|
|
|
|
public DrumLoop(double timing, int drumType, float volume = 1)
|
|
{
|
|
this.drumType = drumType;
|
|
this.timing = timing;
|
|
this.volume = volume;
|
|
}
|
|
}
|
|
|
|
private DrumLoop[][] drumLoops = new DrumLoop[][] {
|
|
|
|
new DrumLoop[] {}, //silent
|
|
|
|
new DrumLoop[] { //straight
|
|
//kick
|
|
new(4.00, 0),
|
|
new(0.50, 0),
|
|
new(1.75, 0),
|
|
new(2.50, 0),
|
|
//snare
|
|
new(1.00, 1),
|
|
new(3.00, 1),
|
|
//loud hihat
|
|
new(4.00, 2),
|
|
new(1.00, 2),
|
|
new(2.00, 2),
|
|
new(3.00, 2),
|
|
//quiet hihat
|
|
new(0.50, 2, 0.7f),
|
|
new(1.50, 2, 0.7f),
|
|
new(2.50, 2, 0.7f),
|
|
new(3.50, 2, 0.7f),
|
|
},
|
|
|
|
new DrumLoop[] { //swungsixteenth
|
|
//kick
|
|
new(4.00, 0),
|
|
new(0.50, 0),
|
|
new((double)20/6, 0),
|
|
new(2.50, 0),
|
|
//snare
|
|
new(1.00, 1),
|
|
new(3.00, 1),
|
|
//loud hihat
|
|
new(4.00, 2),
|
|
new(1.00, 2),
|
|
new(2.00, 2),
|
|
new(3.00, 2),
|
|
//quiet hihat
|
|
new(0.50, 2, 0.7f),
|
|
new(1.50, 2, 0.7f),
|
|
new(2.50, 2, 0.7f),
|
|
new(3.50, 2, 0.7f),
|
|
//silent hihat
|
|
new((double) 2/6, 2, 0.5f),
|
|
new((double) 5/6, 2, 0.5f),
|
|
new((double) 8/6, 2, 0.5f),
|
|
new((double)11/6, 2, 0.5f),
|
|
new((double)14/6, 2, 0.5f),
|
|
new((double)17/6, 2, 0.5f),
|
|
new((double)20/6, 2, 0.5f),
|
|
new((double)23/6, 2, 0.5f),
|
|
},
|
|
|
|
new DrumLoop[] { //swungeighth
|
|
//kick
|
|
new(4.00, 0),
|
|
new((double)2/3, 0),
|
|
new((double)5/3, 0),
|
|
new((double)8/3, 0),
|
|
//snare
|
|
new(1.00, 1),
|
|
new(3.00, 1),
|
|
//loud hihat
|
|
new(4.00, 2),
|
|
new(1.00, 2),
|
|
new(2.00, 2),
|
|
new(3.00, 2),
|
|
//quiet hihat
|
|
new((double) 2/3, 2, 0.7f),
|
|
new((double) 5/3, 2, 0.7f),
|
|
new((double) 8/3, 2, 0.7f),
|
|
new((double)11/3, 2, 0.7f),
|
|
},
|
|
|
|
new DrumLoop[] { //triplet
|
|
//kick
|
|
new(4.00, 0),
|
|
new((double) 2/3, 0),
|
|
new((double) 5/3, 0),
|
|
new(2.00, 0),
|
|
new((double) 8/3, 0),
|
|
//snare
|
|
new((double) 4/3, 1),
|
|
new(3.00, 1),
|
|
//loud hihat
|
|
new(4.00, 2),
|
|
new((double) 4/3, 2),
|
|
new(2.00, 2),
|
|
new(3.00, 2),
|
|
//quiet hihat
|
|
new((double) 1/3, 2, 0.7f),
|
|
new(1.00, 2, 0.7f),
|
|
new((double) 5/3, 2, 0.7f),
|
|
new((double) 7/3, 2, 0.7f),
|
|
new((double) 8/3, 2, 0.7f),
|
|
new((double)11/3, 2, 0.7f),
|
|
},
|
|
};
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
//global methods
|
|
#region Global Methods
|
|
|
|
public void Update()
|
|
{
|
|
//update background color
|
|
BackgroundColorUpdate(Conductor.instance);
|
|
|
|
if (PlayerInput.GetIsAction(InputAction_BasicPress) && !IsExpectingInputNow(InputAction_BasicPress))
|
|
//player whiffs (press)
|
|
{
|
|
isInputting = false; //stops the drums (just in case)
|
|
}
|
|
|
|
if (PlayerInput.GetIsAction(InputAction_BasicRelease) && !IsExpectingInputNow(InputAction_BasicRelease))
|
|
//player whiffs (press)
|
|
{
|
|
if (isInputting)
|
|
//if the player was doing well
|
|
{
|
|
SoundByte.PlayOneShotGame("chargingChicken/blastoff"); //TO DO: replace with proper takeoff function
|
|
}
|
|
|
|
isInputting = false; //stops the drums
|
|
}
|
|
}
|
|
|
|
public override void OnPlay(double beat)
|
|
{
|
|
PersistColor(beat);
|
|
}
|
|
|
|
public override void OnGameSwitch(double beat)
|
|
{
|
|
PersistColor(beat);
|
|
}
|
|
|
|
private void Awake()
|
|
{
|
|
colorFrom = defaultBGColor;
|
|
colorTo = defaultBGColor;
|
|
colorFrom2 = defaultBGColorBottom;
|
|
colorTo2 = defaultBGColorBottom;
|
|
}
|
|
|
|
#endregion
|
|
|
|
//chicken methods
|
|
#region Chicken Methods
|
|
|
|
public static void CountIn(double beat)
|
|
{
|
|
//cowbell count in
|
|
MultiSound.Play(new MultiSound.Sound[]
|
|
{
|
|
new MultiSound.Sound("chargingChicken/cowbell", beat - 4),
|
|
new MultiSound.Sound("chargingChicken/cowbell", beat - 3),
|
|
new MultiSound.Sound("chargingChicken/cowbell", beat - 2),
|
|
new MultiSound.Sound("chargingChicken/cowbell", beat - 1)
|
|
}, forcePlay: true);
|
|
}
|
|
|
|
public void ChargeUp(double beat, double length, int whichDrum) //TO DO: make this inactive
|
|
{
|
|
//TO DO: GET RID OF THIS THIS IS JUST FOR DEMO PURPOSES, IT PLAYS THE LITTLE "COLLAPSE" NOISE BUT IT NEEDS TO BE REPLACED WITH A PROPER DISTANCE CHECK
|
|
BeatAction.New(GameManager.instance, new List<BeatAction.Action>()
|
|
{
|
|
new BeatAction.Action(beat + (length * 2) - 1, delegate {
|
|
SoundByte.PlayOneShotGame("chargingChicken/complete");
|
|
}),
|
|
});
|
|
|
|
//animation
|
|
//STUFF GOES HERE
|
|
|
|
//input
|
|
ScheduleInput(beat - 1, 1, InputAction_BasicPress, whichDrum == 0 ? StartChargingJust : StartChargingJustMusic, StartChargingMiss, Nothing);
|
|
ScheduleInput(beat, length, InputAction_BasicRelease, EndChargingJust, EndChargingMiss, Nothing);
|
|
|
|
while ( length >= 0 )
|
|
{
|
|
//create the beat action
|
|
var actions = PlayDrumLoop(beat, whichDrum, length);
|
|
|
|
//execute the list of actions from PlayDrumLoop
|
|
BeatAction.New(GameManager.instance, actions);
|
|
|
|
//start the next drum loop
|
|
beat += 4;
|
|
length -= 4;
|
|
}
|
|
}
|
|
|
|
public void StartChargingJust(PlayerActionEvent caller, float state)
|
|
{
|
|
//sound
|
|
isInputting = true; //starts the drums
|
|
}
|
|
|
|
public void StartChargingJustMusic(PlayerActionEvent caller, float state)
|
|
{
|
|
//sound
|
|
isInputting = true; //starts the drums
|
|
SoundByte.PlayOneShotGame("chargingChicken/kick");
|
|
SoundByte.PlayOneShotGame("chargingChicken/hihat");
|
|
}
|
|
|
|
public void StartChargingMiss(PlayerActionEvent caller)
|
|
{
|
|
//sound
|
|
isInputting = false; //ends the drums (just in case)
|
|
}
|
|
|
|
public void EndChargingJust(PlayerActionEvent caller, float state)
|
|
{
|
|
//sound
|
|
isInputting = false; //ends the drums
|
|
SoundByte.PlayOneShotGame("chargingChicken/blastoff");
|
|
}
|
|
|
|
public void EndChargingMiss(PlayerActionEvent caller)
|
|
{
|
|
//sound
|
|
isInputting = false; //ends the drums
|
|
}
|
|
|
|
public void Nothing(PlayerActionEvent caller) { }
|
|
|
|
public List<BeatAction.Action> PlayDrumLoop(double beat, int whichDrum, double length)
|
|
{
|
|
//create the beat action
|
|
var actions = new List<BeatAction.Action>();
|
|
|
|
//sort drums by timing
|
|
Array.Sort(drumLoops[whichDrum]);
|
|
|
|
//fill the beat action
|
|
foreach (var drumLoop in drumLoops[whichDrum]) {
|
|
string drumTypeInterpreted = drumLoop.drumType switch {
|
|
0 => "chargingChicken/kick",
|
|
1 => "chargingChicken/snare",
|
|
2 => "chargingChicken/hihat"
|
|
};
|
|
if (length > drumLoop.timing)
|
|
{
|
|
actions.Add(new(beat + drumLoop.timing, delegate {
|
|
PlayDrum(drumTypeInterpreted, drumLoop.volume);
|
|
}));
|
|
}
|
|
}
|
|
|
|
//return the list of actions
|
|
return actions;
|
|
}
|
|
|
|
public void PlayDrum(string whichDrum, float drumVolume)
|
|
{
|
|
if (isInputting) SoundByte.PlayOneShotGame(whichDrum, volume: drumVolume);
|
|
}
|
|
|
|
#region ColorShit
|
|
|
|
public void ChangeColor(double beat, float length, Color color1, Color color2, Color color3, Color color4, int ease)
|
|
{
|
|
bgColorStartBeat = beat;
|
|
bgColorLength = length;
|
|
colorFrom = color1;
|
|
colorTo = color2;
|
|
colorFrom2 = color3;
|
|
colorTo2 = color4;
|
|
lastEase = (Util.EasingFunction.Ease)ease;
|
|
}
|
|
|
|
private void PersistColor(double beat)
|
|
{
|
|
var allEventsBeforeBeat = EventCaller.GetAllInGameManagerList("chargingChicken", new string[] { "changeBgColor" }).FindAll(x => x.beat < beat);
|
|
if (allEventsBeforeBeat.Count > 0)
|
|
{
|
|
allEventsBeforeBeat.Sort((x, y) => x.beat.CompareTo(y.beat)); //just in case
|
|
var lastEvent = allEventsBeforeBeat[^1];
|
|
ChangeColor(lastEvent.beat, lastEvent.length, lastEvent["colorFrom"], lastEvent["colorTo"], lastEvent["colorFrom2"], lastEvent["colorTo2"], lastEvent["ease"]);
|
|
}
|
|
}
|
|
|
|
private void BackgroundColorUpdate(Conductor cond)
|
|
{
|
|
float normalizedBeat = Mathf.Clamp01(cond.GetPositionFromBeat(bgColorStartBeat, bgColorLength));
|
|
Util.EasingFunction.Function func = Util.EasingFunction.GetEasingFunction(lastEase);
|
|
float newColorR = func(colorFrom.r, colorTo.r, normalizedBeat);
|
|
float newColorG = func(colorFrom.g, colorTo.g, normalizedBeat);
|
|
float newColorB = func(colorFrom.b, colorTo.b, normalizedBeat);
|
|
bgHigh.color = new Color(newColorR, newColorG, newColorB);
|
|
gradient.color = new Color(newColorR, newColorG, newColorB);
|
|
newColorR = func(colorFrom2.r, colorTo2.r, normalizedBeat);
|
|
newColorG = func(colorFrom2.g, colorTo2.g, normalizedBeat);
|
|
newColorB = func(colorFrom2.b, colorTo2.b, normalizedBeat);
|
|
bgLow.color = new Color(newColorR, newColorG, newColorB);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
}
|
|
}
|