diff --git a/TJAPlayer3/Helpers/HEasingMethods.cs b/TJAPlayer3/Helpers/HEasingMethods.cs new file mode 100644 index 00000000..4698c6cd --- /dev/null +++ b/TJAPlayer3/Helpers/HEasingMethods.cs @@ -0,0 +1,273 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Web.Security; + +namespace TJAPlayer3 +{ + internal class HEasingMethods + { + public enum EEaseType + { + IN = 0, + OUT, + INOUT, + OUTIN + } + + public enum EEaseFunction + { + LINEAR = 0, + SINE, + QUAD, + CUBIC, + QUART, + QUINT, + EXPO, + CIRC, + ELASTIC, + BACK, + BOUNCE + } + + private static readonly Dictionary> _easeMethods = new Dictionary>() + { + [EEaseFunction.LINEAR] = _easeLinear, + [EEaseFunction.SINE] = _easeSine, + [EEaseFunction.QUAD] = _easeQuad, + [EEaseFunction.CUBIC] = _easeCubic, + [EEaseFunction.QUART] = _easeQuart, + [EEaseFunction.QUINT] = _easeQuint, + [EEaseFunction.EXPO] = _easeExpo, + [EEaseFunction.CIRC] = _easeCirc, + [EEaseFunction.ELASTIC] = _easeElastic, + [EEaseFunction.BACK] = _easeBack, + [EEaseFunction.BOUNCE] = _easeBounce, + }; + + private static double _easeLinear(EEaseType type, double x) + { + return x; + } + + private static double _easeSine(EEaseType type, double x) + { + switch (type) { + case EEaseType.IN: + default: + return 1 - Math.Cos((x * Math.PI) / 2.0); + case EEaseType.OUT: + return Math.Sin((x * Math.PI) / 2.0); + case EEaseType.INOUT: + return -(Math.Cos(x * Math.PI) - 1) / 2.0; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeQuad(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return x * x; + case EEaseType.OUT: + return 1 - (1 - x) * (1 - x); + case EEaseType.INOUT: + return x < 0.5 ? 2 * x * x : 1 - Math.Pow(-2 * x + 2, 2) / 2.0; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeCubic(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return x * x * x; + case EEaseType.OUT: + return 1 - Math.Pow(1 - x, 3); + case EEaseType.INOUT: + return x < 0.5 ? 4 * x * x * x : 1 - Math.Pow(-2 * x + 2, 3) / 2.0; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeQuart(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return x * x * x * x; + case EEaseType.OUT: + return 1 - Math.Pow(1 - x, 4); + case EEaseType.INOUT: + return x < 0.5 ? 8 * x * x * x * x : 1 - Math.Pow(-2 * x + 2, 4) / 2.0; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeQuint(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return x * x * x * x * x; + case EEaseType.OUT: + return 1 - Math.Pow(1 - x, 5); + case EEaseType.INOUT: + return x < 0.5 ? 16 * x * x * x * x * x : 1 - Math.Pow(-2 * x + 2, 5) / 2.0; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeExpo(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return x == 0 ? 0 : Math.Pow(2, 10 * x - 10); + case EEaseType.OUT: + return x == 1 ? 1 : 1 - Math.Pow(2, -10 * x); + case EEaseType.INOUT: + return x == 0 + ? 0 + : x == 1 + ? 1 + : x < 0.5 + ? Math.Pow(2, 20 * x - 10) / 2 + : (2 - Math.Pow(2, -20 * x + 10)) / 2; ; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeCirc(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return 1 - Math.Sqrt(1 - Math.Pow(x, 2)); + case EEaseType.OUT: + return Math.Sqrt(1 - Math.Pow(x - 1, 2)); + case EEaseType.INOUT: + return x < 0.5 + ? (1 - Math.Sqrt(1 - Math.Pow(2 * x, 2))) / 2 + : (Math.Sqrt(1 - Math.Pow(-2 * x + 2, 2)) + 1) / 2; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeBack(EEaseType type, double x) + { + const double c1 = 1.70158; + const double c2 = c1 * 1.525; + const double c3 = c1 + 1; + switch (type) + { + case EEaseType.IN: + default: + return c3 * x * x * x - c1 * x * x; + case EEaseType.OUT: + return 1 + c3 * Math.Pow(x - 1, 3) + c1 * Math.Pow(x - 1, 2); + case EEaseType.INOUT: + return x < 0.5 + ? (Math.Pow(2 * x, 2) * ((c2 + 1) * 2 * x - c2)) / 2 + : (Math.Pow(2 * x - 2, 2) * ((c2 + 1) * (x * 2 - 2) + c2) + 2) / 2; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeElastic(EEaseType type, double x) + { + const double c4 = (2 * Math.PI) / 3; + const double c5 = (2 * Math.PI) / 4.5; + switch (type) + { + case EEaseType.IN: + default: + return x == 0 + ? 0 + : x == 1 + ? 1 + : -Math.Pow(2, 10 * x - 10) * Math.Sin((x * 10 - 10.75) * c4); + case EEaseType.OUT: + return x == 0 + ? 0 + : x == 1 + ? 1 + : Math.Pow(2, -10 * x) * Math.Sin((x * 10 - 0.75) * c4) + 1; + case EEaseType.INOUT: + return x == 0 + ? 0 + : x == 1 + ? 1 + : x < 0.5 + ? -(Math.Pow(2, 20 * x - 10) * Math.Sin((20 * x - 11.125) * c5)) / 2 + : (Math.Pow(2, -20 * x + 10) * Math.Sin((20 * x - 11.125) * c5)) / 2 + 1; + case EEaseType.OUTIN: + return x; + } + } + + private static double _easeOutBounce(double x) + { + const double n1 = 7.5625; + const double d1 = 2.75; + + if (x < 1 / d1) + return n1 * x * x; + else if (x < 2 / d1) + return n1 * (x -= 1.5 / d1) * x + 0.75; + else if (x < 2.5 / d1) + return n1 * (x -= 2.25 / d1) * x + 0.9375; + else + return n1 * (x -= 2.625 / d1) * x + 0.984375; + } + + private static double _easeBounce(EEaseType type, double x) + { + switch (type) + { + case EEaseType.IN: + default: + return 1 - _easeOutBounce(1 - x); + case EEaseType.OUT: + return _easeOutBounce(x); + case EEaseType.INOUT: + return x < 0.5 + ? (1 - _easeOutBounce(1 - 2 * x)) / 2 + : (1 + _easeOutBounce(2 * x - 1)) / 2; + case EEaseType.OUTIN: + return x; + } + } + + public static double tCalculateEaseNorm(EEaseType type, EEaseFunction function, double ratio) + { + return _easeMethods[function](type, ratio); + } + + public static double tCalculateEase(EEaseType type, EEaseFunction function, double timeStart, double timeEnd, double timeCurrent, double valueStart, double valueEnd) + { + if (timeStart == timeEnd) return valueEnd; + double ratio = (timeCurrent - timeStart) / (timeEnd - timeStart); + double ratio_eased = _easeMethods[function](type, ratio); + return valueStart + ratio_eased * (valueEnd - valueStart); + } + } +} diff --git a/TJAPlayer3/Stages/05.SongSelect/CActSelectPresound.cs b/TJAPlayer3/Stages/05.SongSelect/CActSelectPresound.cs index ef1064dd..fdc2724b 100644 --- a/TJAPlayer3/Stages/05.SongSelect/CActSelectPresound.cs +++ b/TJAPlayer3/Stages/05.SongSelect/CActSelectPresound.cs @@ -109,8 +109,10 @@ namespace TJAPlayer3 if (long再生位置 == -1) { this.long再生開始時のシステム時刻 = CSound管理.rc演奏用タイマ.nシステム時刻ms; - this.long再生位置 = cスコア.譜面情報.nデモBGMオフセット; + this.long再生位置 = cスコア.譜面情報.nデモBGMオフセット; + this.sound.t再生位置を変更する(cスコア.譜面情報.nデモBGMオフセット); + } else { @@ -170,7 +172,8 @@ namespace TJAPlayer3 strPreviewFilename = cスコア.ファイル情報.フォルダの絶対パス + cスコア.譜面情報.strBGMファイル名; if(TJAPlayer3.ConfigIni.bBGM音を発声する) this.sound = TJAPlayer3.Sound管理.tサウンドを生成する( strPreviewFilename, ESoundGroup.SongPreview ); - if (this.sound == null) return; + if (this.sound == null) return; + //this.sound.db再生速度 = ((double)TJAPlayer3.ConfigIni.n演奏速度) / 20.0; // 2018-08-27 twopointzero - DO attempt to load (or queue scanning) loudness metadata here. // Initialization, song enumeration, and/or interactions may have @@ -189,7 +192,7 @@ namespace TJAPlayer3 { this.long再生開始時のシステム時刻 = CSound管理.rc演奏用タイマ.nシステム時刻ms; this.long再生位置 = cスコア.譜面情報.nデモBGMオフセット; - this.sound.t再生位置を変更する( cスコア.譜面情報.nデモBGMオフセット ); + this.sound.t再生位置を変更する(cスコア.譜面情報.nデモBGMオフセット); this.long再生位置 = CSound管理.rc演奏用タイマ.nシステム時刻ms - this.long再生開始時のシステム時刻; } //if( long再生位置 == this.sound.n総演奏時間ms - 10 ) @@ -198,13 +201,7 @@ namespace TJAPlayer3 this.str現在のファイル名 = strPreviewFilename; this.tBGMフェードアウト開始(); Trace.TraceInformation( "プレビューサウンドを生成しました。({0})", strPreviewFilename ); - #region[ DTXMania(コメントアウト) ] - //this.sound = CDTXMania.Sound管理.tサウンドを生成する( strPreviewFilename ); - //this.sound.t再生を開始する( true ); - //this.str現在のファイル名 = strPreviewFilename; - //this.tBGMフェードアウト開始(); - //Trace.TraceInformation( "プレビューサウンドを生成しました。({0})", strPreviewFilename ); - #endregion + } catch (Exception e) { diff --git a/TJAPlayer3/Stages/05.SongSelect/CActSelect曲リスト.cs b/TJAPlayer3/Stages/05.SongSelect/CActSelect曲リスト.cs index 44ff0c6e..b850c499 100644 --- a/TJAPlayer3/Stages/05.SongSelect/CActSelect曲リスト.cs +++ b/TJAPlayer3/Stages/05.SongSelect/CActSelect曲リスト.cs @@ -3122,18 +3122,25 @@ namespace TJAPlayer3 private TitleTextureKey ttkGenerateBPMTexture(C曲リストノード node, Color forecolor, Color backcolor) { var _score = node.arスコア[tFetchDifficulty(node)].譜面情報; + var _speed = ((double)TJAPlayer3.ConfigIni.n演奏速度) / 20.0; double[] bpms = new double[3] { - _score.BaseBpm, - _score.MinBpm, - _score.MaxBpm + _score.BaseBpm * _speed, + _score.MinBpm * _speed, + _score.MaxBpm * _speed }; string bpm_str = "BPM: " + bpms[0].ToString(); if (bpms[1] != bpms[0] || bpms[2] != bpms[0]) bpm_str += " (" + bpms[1].ToString() + "-" + bpms[2].ToString() + ")"; - - return new TitleTextureKey(bpm_str, pfBPM, forecolor, backcolor, TJAPlayer3.Skin.SongSelect_BPM_Text_MaxSize); + + var _color = forecolor; + if (_speed > 1) + _color = Color.Red; + else if (_speed < 1) + _color = Color.LightBlue; + + return new TitleTextureKey(bpm_str, pfBPM, _color, backcolor, TJAPlayer3.Skin.SongSelect_BPM_Text_MaxSize); } public CTexture ResolveTitleTexture(TitleTextureKey titleTextureKey) diff --git a/TJAPlayer3/TJAPlayer3.csproj b/TJAPlayer3/TJAPlayer3.csproj index 1855838d..f10e62f4 100644 --- a/TJAPlayer3/TJAPlayer3.csproj +++ b/TJAPlayer3/TJAPlayer3.csproj @@ -144,6 +144,7 @@ +