mirror of
https://github.com/ppy/osu.git
synced 2025-02-12 21:52:56 +08:00
added density aim multiplier
This commit is contained in:
parent
9e6ae3587a
commit
5d4c78239b
@ -18,8 +18,9 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Evaluators
|
||||
|
||||
private const double overlap_multiplier = 0.8;
|
||||
|
||||
public static double CalculateDenstityOf(OsuDifficultyHitObject currObj)
|
||||
public static double EvaluateDenstityOf(DifficultyHitObject current)
|
||||
{
|
||||
var currObj = (OsuDifficultyHitObject)current;
|
||||
double density = 0;
|
||||
double densityAnglesNerf = -2; // we have threshold of 2, so 2 or same angles won't be punished
|
||||
|
||||
@ -34,8 +35,7 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Evaluators
|
||||
double loopDifficulty = currObj.OpacityAt(loopObj.BaseObject.StartTime, false);
|
||||
|
||||
// Small distances means objects may be cheesed, so it doesn't matter whether they are arranged confusingly.
|
||||
// For HD: it's not subtracting anything cuz it's multiplied by the aim difficulty anyways.
|
||||
loopDifficulty *= logistic((loopObj.MinimumJumpDistance - 60) / 10);
|
||||
loopDifficulty *= logistic((loopObj.MinimumJumpDistance - 30) / 10);
|
||||
|
||||
// Reduce density bonus for this object if they're too apart in time
|
||||
// Nerf starts on 1500ms and reaches maximum (*=0) on 3000ms
|
||||
@ -123,14 +123,14 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Evaluators
|
||||
|
||||
return screenOverlapDifficulty;
|
||||
}
|
||||
public static double EvaluateDensityDifficultyOf(DifficultyHitObject current)
|
||||
public static double EvaluateDifficultyOf(DifficultyHitObject current)
|
||||
{
|
||||
if (current.BaseObject is Spinner || current.Index == 0)
|
||||
return 0;
|
||||
|
||||
var currObj = (OsuDifficultyHitObject)current;
|
||||
|
||||
double pastObjectDifficultyInfluence = CalculateDenstityOf(currObj);
|
||||
double pastObjectDifficultyInfluence = EvaluateDenstityOf(current);
|
||||
double screenOverlapDifficulty = CalculateOverlapDifficultyOf(currObj);
|
||||
|
||||
double difficulty = Math.Pow(4 * Math.Log(Math.Max(1, pastObjectDifficultyInfluence)), 2.3);
|
||||
|
@ -123,28 +123,11 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Evaluators
|
||||
// https://www.desmos.com/calculator/hbj7swzlth
|
||||
public static double GetDifficulty(double preempt)
|
||||
{
|
||||
double value = Math.Pow(3, 3 - 0.01 * preempt); // 1 for 300ms, 0.25 for 400ms, 0.0625 for 500ms
|
||||
double value = Math.Pow(3.5, 3 - 0.01 * preempt); // 1 for 300ms, 0.25 for 400ms, 0.0625 for 500ms
|
||||
value = softmin(value, 2, 1.7); // use softmin to achieve full-memory cap, 2 times more than AR11 (300ms)
|
||||
return value;
|
||||
}
|
||||
|
||||
// This is very accurate on preempt > 300ms, breaking starting somewhere around 120ms
|
||||
public static double GetPreempt(double difficulty)
|
||||
{
|
||||
double fixCoef = difficulty / GetDifficulty(highArCurveReversed(difficulty));
|
||||
return highArCurveReversed(difficulty * fixCoef);
|
||||
}
|
||||
|
||||
// This is an approximation cuz high AR curve is unsolvable
|
||||
// https://www.desmos.com/calculator/n9vk18bcyh
|
||||
private static double highArCurveReversed(double value)
|
||||
{
|
||||
double helperValue = value / Math.Pow(1 - Math.Pow(1.7, value - 2), 0.45);
|
||||
double preempt = -(Math.Log(helperValue, 3) - 3) / 0.01;
|
||||
|
||||
return preempt;
|
||||
}
|
||||
|
||||
// We are using mutiply and divide instead of add and subtract, so values won't be negative
|
||||
// https://www.desmos.com/calculator/fv5xerwpd2
|
||||
private static double softmin(double a, double b, double power = Math.E) => a * b / Math.Log(Math.Pow(power, a) + Math.Pow(power, b), power);
|
||||
|
@ -71,7 +71,7 @@ namespace osu.Game.Rulesets.Osu.Difficulty
|
||||
if (mods.Any(h => h is OsuModFlashlight))
|
||||
baseFlashlightPerformance = Math.Pow(flashlightRating, 2.0) * 25.0;
|
||||
|
||||
double baseReadingLowARPerformance = Math.Pow(readingLowARRating, 2.5) * 17.0;
|
||||
double baseReadingLowARPerformance = ReadingLowAR.DifficultyToPerformance(readingLowARRating);
|
||||
double baseReadingHighARPerformance = OsuStrainSkill.DifficultyToPerformance(readingHighARRating);
|
||||
double baseReadingARPerformance = Math.Pow(Math.Pow(baseReadingLowARPerformance, SUM_POWER) + Math.Pow(baseReadingHighARPerformance, SUM_POWER), 1.0 / SUM_POWER);
|
||||
|
||||
|
@ -261,7 +261,7 @@ namespace osu.Game.Rulesets.Osu.Difficulty
|
||||
if (score.Mods.Any(m => m is OsuModTouchDevice))
|
||||
rawReading = Math.Pow(rawReading, 0.8);
|
||||
|
||||
double readingValue = Math.Pow(rawReading, 2.5) * 17.0;
|
||||
double readingValue = ReadingLowAR.DifficultyToPerformance(rawReading);
|
||||
|
||||
// Penalize misses by assessing # of misses relative to the total # of objects. Default a 3% reduction for any # of misses.
|
||||
if (effectiveMissCount > 0)
|
||||
|
@ -35,6 +35,10 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
/// </summary>
|
||||
protected virtual double DifficultyMultiplier => DEFAULT_DIFFICULTY_MULTIPLIER;
|
||||
|
||||
protected virtual double StrainDecayBase => 0.15;
|
||||
|
||||
protected double StrainDecay(double ms) => Math.Pow(StrainDecayBase, ms / 1000);
|
||||
|
||||
protected OsuStrainSkill(Mod[] mods)
|
||||
: base(mods)
|
||||
{
|
||||
|
@ -16,18 +16,31 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
public class ReadingLowAR : GraphSkill
|
||||
{
|
||||
private readonly List<double> difficulties = new List<double>();
|
||||
private double skillMultiplier => 2;
|
||||
private double skillMultiplier => 1.3;
|
||||
private double aimComponentMultiplier => 0.7;
|
||||
//private double skillMultiplier => 2;
|
||||
|
||||
public ReadingLowAR(Mod[] mods)
|
||||
: base(mods)
|
||||
{
|
||||
}
|
||||
|
||||
private double strainDecayBase => 0.15;
|
||||
private double strainDecay(double ms) => Math.Pow(strainDecayBase, ms / 1000);
|
||||
|
||||
private double currentDensityAimStrain = 0;
|
||||
|
||||
public override void Process(DifficultyHitObject current)
|
||||
{
|
||||
double currentDifficulty = ReadingEvaluator.EvaluateDensityDifficultyOf(current) * skillMultiplier;
|
||||
double densityFactor = Math.Max(0, Math.Pow(ReadingEvaluator.EvaluateDenstityOf(current), 1.5) - 1);
|
||||
// double density = Math.Max(0, ReadingEvaluator.EvaluateDenstityOf(current));
|
||||
currentDensityAimStrain *= strainDecay(current.DeltaTime);
|
||||
currentDensityAimStrain += densityFactor * AimEvaluator.EvaluateDifficultyOf(current, false) * aimComponentMultiplier;
|
||||
|
||||
difficulties.Add(currentDifficulty);
|
||||
double densityReadingDifficulty = ReadingEvaluator.EvaluateDifficultyOf(current);
|
||||
double totalDensityDifficulty = (currentDensityAimStrain + densityReadingDifficulty) * skillMultiplier;
|
||||
|
||||
difficulties.Add(totalDensityDifficulty);
|
||||
|
||||
if (current.Index == 0)
|
||||
CurrentSectionEnd = Math.Ceiling(current.StartTime / SectionLength) * SectionLength;
|
||||
@ -39,7 +52,7 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
CurrentSectionEnd += SectionLength;
|
||||
}
|
||||
|
||||
CurrentSectionPeak = Math.Max(currentDifficulty, CurrentSectionPeak);
|
||||
CurrentSectionPeak = Math.Max(totalDensityDifficulty, CurrentSectionPeak);
|
||||
}
|
||||
|
||||
private double reducedNoteCount => 5;
|
||||
@ -71,6 +84,8 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
|
||||
return difficulty;
|
||||
}
|
||||
|
||||
public static double DifficultyToPerformance(double difficulty) => Math.Pow(difficulty, 3) * 10.0;
|
||||
}
|
||||
|
||||
public class ReadingHidden : OsuStrainSkill
|
||||
@ -82,15 +97,12 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
|
||||
private double currentStrain;
|
||||
private double skillMultiplier => 5;
|
||||
private double strainDecayBase => 0.15;
|
||||
|
||||
private double strainDecay(double ms) => Math.Pow(strainDecayBase, ms / 1000);
|
||||
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => currentStrain * strainDecay(time - current.Previous(0).StartTime);
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => currentStrain * StrainDecay(time - current.Previous(0).StartTime);
|
||||
|
||||
protected override double StrainValueAt(DifficultyHitObject current)
|
||||
{
|
||||
currentStrain *= strainDecay(current.DeltaTime);
|
||||
currentStrain *= StrainDecay(current.DeltaTime);
|
||||
|
||||
// We're not using slider aim because we assuming that HD doesn't makes sliders harder (what is not true, but we will ignore this for now)
|
||||
double hiddenDifficulty = AimEvaluator.EvaluateDifficultyOf(current, false);
|
||||
|
@ -29,12 +29,9 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
|
||||
private readonly List<double> difficulties = new List<double>();
|
||||
private int objectsCount = 0;
|
||||
private double preempt = -1;
|
||||
|
||||
public override void Process(DifficultyHitObject current)
|
||||
{
|
||||
if (preempt < 0) preempt = ((OsuDifficultyHitObject)current).Preempt;
|
||||
|
||||
aimComponent.Process(current);
|
||||
speedComponent.Process(current);
|
||||
|
||||
@ -97,17 +94,14 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
private bool adjustHighAR;
|
||||
private double currentStrain;
|
||||
|
||||
private double skillMultiplier => 17.8;
|
||||
private double defaultValueMultiplier => 30;
|
||||
private double strainDecayBase => 0.15;
|
||||
private double skillMultiplier => 17;
|
||||
private double defaultValueMultiplier => 50;
|
||||
|
||||
private double strainDecay(double ms) => Math.Pow(strainDecayBase, ms / 1000);
|
||||
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => currentStrain * strainDecay(time - current.Previous(0).StartTime);
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => currentStrain * StrainDecay(time - current.Previous(0).StartTime);
|
||||
|
||||
protected override double StrainValueAt(DifficultyHitObject current)
|
||||
{
|
||||
currentStrain *= strainDecay(current.DeltaTime);
|
||||
currentStrain *= StrainDecay(current.DeltaTime);
|
||||
|
||||
double aimDifficulty = AimEvaluator.EvaluateDifficultyOf(current, true);
|
||||
double readingDifficulty = ReadingHighAREvaluator.EvaluateDifficultyOf(current, adjustHighAR);
|
||||
@ -122,8 +116,8 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
|
||||
public class HighARSpeedComponent : OsuStrainSkill
|
||||
{
|
||||
private double skillMultiplier => 850;
|
||||
private double strainDecayBase => 0.3;
|
||||
private double skillMultiplier => 820;
|
||||
protected override double StrainDecayBase => 0.3;
|
||||
|
||||
private double currentStrain;
|
||||
private double currentRhythm;
|
||||
@ -133,15 +127,13 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
{
|
||||
}
|
||||
|
||||
private double strainDecay(double ms) => Math.Pow(strainDecayBase, ms / 1000);
|
||||
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => (currentStrain * currentRhythm) * strainDecay(time - current.Previous(0).StartTime);
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => (currentStrain * currentRhythm) * StrainDecay(time - current.Previous(0).StartTime);
|
||||
|
||||
protected override double StrainValueAt(DifficultyHitObject current)
|
||||
{
|
||||
OsuDifficultyHitObject currODHO = (OsuDifficultyHitObject)current;
|
||||
|
||||
currentStrain *= strainDecay(currODHO.StrainTime);
|
||||
currentStrain *= StrainDecay(currODHO.StrainTime);
|
||||
|
||||
double speedDifficulty = SpeedEvaluator.EvaluateDifficultyOf(current) * skillMultiplier;
|
||||
speedDifficulty *= Math.Pow(ReadingHighAREvaluator.EvaluateDifficultyOf(current, false), 2);
|
||||
|
@ -17,7 +17,7 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
public class Speed : OsuStrainSkill
|
||||
{
|
||||
private double skillMultiplier => 1375;
|
||||
private double strainDecayBase => 0.3;
|
||||
protected override double StrainDecayBase => 0.3;
|
||||
|
||||
private double currentStrain;
|
||||
private double currentRhythm;
|
||||
@ -32,15 +32,13 @@ namespace osu.Game.Rulesets.Osu.Difficulty.Skills
|
||||
{
|
||||
}
|
||||
|
||||
private double strainDecay(double ms) => Math.Pow(strainDecayBase, ms / 1000);
|
||||
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => (currentStrain * currentRhythm) * strainDecay(time - current.Previous(0).StartTime);
|
||||
protected override double CalculateInitialStrain(double time, DifficultyHitObject current) => (currentStrain * currentRhythm) * StrainDecay(time - current.Previous(0).StartTime);
|
||||
|
||||
protected override double StrainValueAt(DifficultyHitObject current)
|
||||
{
|
||||
OsuDifficultyHitObject currODHO = (OsuDifficultyHitObject)current;
|
||||
|
||||
currentStrain *= strainDecay(currODHO.StrainTime);
|
||||
currentStrain *= StrainDecay(currODHO.StrainTime);
|
||||
currentStrain += SpeedEvaluator.EvaluateDifficultyOf(current) * skillMultiplier;
|
||||
|
||||
currentRhythm = currODHO.RhythmDifficulty;
|
||||
|
Loading…
Reference in New Issue
Block a user