internal void UpdateStarDifficultyDisplay(bool instant) { if (!IsLoaded || Beatmap == null || state < TreeItemState.ExtrasVisible) { return; } double stars = Math.Min(Beatmap.StarDisplay, 10.0); // We don't want to deal with more than 10 stars in this display if (currentlyVisibleStars == stars) { return; } double previouslyVisibleStars = currentlyVisibleStars; currentlyVisibleStars = stars; UpdateDifficultyText(); // We want the -1 placeholder for "inexistant difficulty" to be treated like 0 stars here if (stars < 0) { stars = 0; int BackgroundStarSpritesEndIndex = starSpritesBeginIndex + AMOUNT_STARS; for (int i = starSpritesBeginIndex; i < BackgroundStarSpritesEndIndex; ++i) { pDrawable starSprite = SpriteCollection[i]; starSprite.FadeOut(instant ? 0 : (OldLayout ? 1000 : 600)); } } // ... with the exception of the background stars appearing. We want these to only appear once difficulty has been computed. (for looking good!) else { int BackgroundStarSpritesEndIndex = starSpritesBeginIndex + AMOUNT_STARS; for (int i = starSpritesBeginIndex; i < BackgroundStarSpritesEndIndex; ++i) { pDrawable starSprite = SpriteCollection[i]; starSprite.FadeIn(instant ? 0 : (OldLayout ? 1000 : 600)); } } int StarSpritesEndIndex = starSpritesBeginIndex + AMOUNT_STARS * 2; for (int i = starSpritesBeginIndex + AMOUNT_STARS; i < StarSpritesEndIndex; ++i) { int starIndex = i - (starSpritesBeginIndex + AMOUNT_STARS); double starsLeft = stars - starIndex; pSprite starSprite = SpriteCollection[i] as pSprite; starSprite.Transformations.Clear(); if (OldLayout) { int targetWidth = (int)(starSprite.Width * starsLeft); // It is important to also clip the width to negative values so the animation is delayed when the stars potentially appear again after the difficulty has been computed. // Don't optimize this and set to 0! starSprite.ClipWidthTo(targetWidth, instant ? 0 : 500, EasingTypes.OutCubic); } else { float newScale = starsLeft <= 0 ? 0 : star_scale * (float)Math.Max(0.5f, Math.Min(1, starsLeft) + starIndex * 0.04f); int amountStarsScaled = (int)Math.Floor(starIndex - Math.Min(stars, previouslyVisibleStars)); if (instant) { starSprite.ScaleTo(newScale, 0); } else { int timeAddition = previouslyVisibleStars <= stars ? amountStarsScaled : (int)Math.Floor(previouslyVisibleStars - stars) - amountStarsScaled - 1; int startTime = GameBase.Time + timeAddition * 80 + 50; starSprite.Transformations.Add(new Transformation(TransformationType.Scale, starSprite.Scale, newScale, startTime, startTime + 500, EasingTypes.OutBack)); } } } }
private void AddControls(NotificationStyle style) { const int button_height = 95; switch (style) { case NotificationStyle.Okay: { pDrawable additiveButton = null; okayButton = new pSprite(TextureManager.Load(OsuTexture.notification_button_ok), new Vector2(0, button_height)) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true, DrawDepth = 0.99f, HandleClickOnUp = true }; okayButton.OnHover += delegate { additiveButton = okayButton.AdditiveFlash(10000, 0.4f); }; okayButton.OnHoverLost += delegate { if (additiveButton != null) { additiveButton.FadeOut(100); } }; okayButton.OnClick += delegate { dismiss(true); }; Add(okayButton); pText okayText = new pText(LocalisationManager.GetString(OsuString.Okay), 24, new Vector2(0, button_height), Vector2.Zero, 1, true, Color4.White, true) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true }; Add(okayText); } break; case NotificationStyle.YesNo: { pDrawable additiveButton = null; okayButton = new pSprite(TextureManager.Load(OsuTexture.notification_button_yes), new Vector2(-140, button_height)) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true, DrawDepth = 0.99f, HandleClickOnUp = true }; okayButton.OnHover += delegate { additiveButton = okayButton.AdditiveFlash(10000, 0.4f); }; okayButton.OnHoverLost += delegate { if (additiveButton != null) { additiveButton.FadeOut(100); } }; okayButton.OnClick += delegate { dismiss(true); }; Add(okayButton); pText okayText = new pText(LocalisationManager.GetString(OsuString.Yes), 24, new Vector2(-140, button_height), Vector2.Zero, 1, true, Color4.White, true) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true }; Add(okayText); } { pDrawable additiveButton = null; cancelButton = new pSprite(TextureManager.Load(OsuTexture.notification_button_no), new Vector2(140, button_height)) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true, DrawDepth = 0.99f, HandleClickOnUp = true }; cancelButton.OnHover += delegate { additiveButton = cancelButton.AdditiveFlash(10000, 0.4f); }; cancelButton.OnHoverLost += delegate { if (additiveButton != null) { additiveButton.FadeOut(100); } }; cancelButton.OnClick += delegate { dismiss(false); }; Add(cancelButton); pText cancelText = new pText(LocalisationManager.GetString(OsuString.No), 24, new Vector2(140, button_height), Vector2.Zero, 1, true, Color4.White, true) { Field = FieldTypes.StandardSnapCentre, Origin = OriginTypes.Centre, Clocking = ClockTypes.Game, DimImmune = true }; Add(cancelText); } break; } }