using System.Windows; using OneClickRun.Helpers; using Xunit; namespace OneClickRun.Tests; /// 滑动选择:按方向角选取最近扇形的行为测试 public class WheelGeometrySwipeTests { private const double InnerR = 70; private static readonly Point Center = new(300, 300); private static Point At(double angleDeg, double radius) => WheelGeometry.PointOnCircle(Center, radius, angleDeg * Math.PI / 180); [Theory] [InlineData(4, -90, 0)] // 上 → 扇形0 [InlineData(4, 0, 1)] // 右 → 扇形1 [InlineData(4, 90, 2)] // 下 → 扇形2 [InlineData(4, 180, 3)] // 左 → 扇形3 [InlineData(3, -90, 0)] // 上 → 扇形0 [InlineData(3, 0, 0)] // 右 → 扇形0(3:00 位于扇形0 区域内) [InlineData(3, 90, 1)] // 下 → 扇形1 [InlineData(3, 180, 2)] // 左 → 扇形2 [InlineData(12, 15, 3)] // 12 扇区:15° 方向 → rel=105°,span=30° → 扇形3 public void PicksSectorByDirection(int count, double angleDeg, int expected) { var point = At(angleDeg, (InnerR + 220) / 2); Assert.Equal(expected, WheelGeometry.PickSectorByAngle(point, Center, InnerR, count)); } [Fact] public void CenterHubReturnsNull() { Assert.Null(WheelGeometry.PickSectorByAngle(Center, Center, InnerR, 4)); Assert.Null(WheelGeometry.PickSectorByAngle(At(45, InnerR - 5), Center, InnerR, 4)); } [Fact] public void BeyondOuterRadiusStillPicksByDirection() { // 快速滑动滑出圆环外:仍按方向命中 Assert.Equal(0, WheelGeometry.PickSectorByAngle(At(-45, 800), Center, InnerR, 4)); Assert.Equal(2, WheelGeometry.PickSectorByAngle(At(135, 2000), Center, InnerR, 4)); } [Fact] public void GapAndBoundaryPickNearestSector() { // 4 扇区:89°/91° 位于 90° 边界两侧的间隙内,应就近归属扇形1/扇形2 Assert.Equal(1, WheelGeometry.PickSectorByAngle(At(89, 145), Center, InnerR, 4)); Assert.Equal(2, WheelGeometry.PickSectorByAngle(At(91, 145), Center, InnerR, 4)); // 恰好正下方:边界平局 → 扇形2 Assert.Equal(2, WheelGeometry.PickSectorByAngle(At(90, 145), Center, InnerR, 4)); } [Fact] public void SingleSectorPicksAnyDirection() { Assert.Equal(0, WheelGeometry.PickSectorByAngle(At(0, 300), Center, InnerR, 1)); Assert.Equal(0, WheelGeometry.PickSectorByAngle(At(213, 300), Center, InnerR, 1)); Assert.Null(WheelGeometry.PickSectorByAngle(Center, Center, InnerR, 1)); } }