diff --git a/osu.Game/Graphics/Carousel/Carousel.cs b/osu.Game/Graphics/Carousel/Carousel.cs index b605efc69d..a63fee6914 100644 --- a/osu.Game/Graphics/Carousel/Carousel.cs +++ b/osu.Game/Graphics/Carousel/Carousel.cs @@ -876,13 +876,18 @@ namespace osu.Game.Graphics.Carousel if (!scrollToSelection.IsValid) { - if (currentKeyboardSelection.YPosition != null) - Scroll.ScrollTo(currentKeyboardSelection.YPosition.Value - visibleHalfHeight + BleedTop); + if (GetScrollTarget() is double scrollTarget) + Scroll.ScrollTo(scrollTarget - visibleHalfHeight + BleedTop); scrollToSelection.Validate(); } } + /// + /// Returns the Y position to scroll to in order to show the most relevant carousel item(s). + /// + protected virtual double? GetScrollTarget() => currentKeyboardSelection.YPosition; + protected virtual float GetPanelXOffset(Drawable panel) { Vector2 posInScroll = Scroll.ToLocalSpace(panel.ScreenSpaceDrawQuad.Centre); diff --git a/osu.Game/Screens/SelectV2/BeatmapCarousel.cs b/osu.Game/Screens/SelectV2/BeatmapCarousel.cs index 780b5155fd..804987a6d0 100644 --- a/osu.Game/Screens/SelectV2/BeatmapCarousel.cs +++ b/osu.Game/Screens/SelectV2/BeatmapCarousel.cs @@ -661,6 +661,24 @@ namespace osu.Game.Screens.SelectV2 } } + protected override double? GetScrollTarget() + { + double? target = base.GetScrollTarget(); + + // if the base implementation returned null, it means that the keyboard selection has been filtered out and is no longer visible + // attempt a fallback to other possibly expanded panels (set first, then group) + if (target == null) + { + var items = GetCarouselItems(); + var targetItem = items?.FirstOrDefault(i => CheckModelEquality(i.Model, ExpandedBeatmapSet)) + ?? items?.FirstOrDefault(i => CheckModelEquality(i.Model, ExpandedGroup)); + + target = targetItem?.CarouselYPosition; + } + + return target; + } + #endregion #region Audio