using XFEEDToolBox.Core.Navigation; using XFEEDToolBox.Core.Rendering; using XFEExtension.NetCore.XUnit.Attributes; namespace XFEEDToolBox.Test; [TestFixture] public sealed class LocalSystemViewLockTests { private static CurrentSystemSnapshot Binary() { var a=new SystemLocation(1,11,"Star A","",1,SystemLocationCategory.Star,null,new(1e12,0,0),null,false,"a"); var b=new SystemLocation(2,22,"Star B","",1,SystemLocationCategory.Star,null,new(-2e12,0,0),null,false,"b"); SystemOrbit Orbit(SystemLocation child,double major,Vector3d x,Vector3d z)=>new(){SystemAddress=1,ChildWorldAddress=child.WorldAddress,ChildIdentity=child.Identity, ParentWorldAddress=33,ParentIdentity="AB",ParentPosition=new(0,0,0),ParentName="A/B barycentre",SemiMajorAxisMetres=major,Eccentricity=0, PeriapsisDirection=x,TransverseDirection=z,Source="isolated binary regression fixture",Quality=SystemOrbitQuality.NativeVerified}; return new(1,"Binary",1,1,DateTimeOffset.UtcNow,[a,b]){Orbits=[Orbit(a,1e12,new(1,0,0),new(0,0,1)),Orbit(b,2e12,new(-1,0,0),new(0,0,-1))],PlayerPosition=new(1e12,0,1e6),PlayerForward=new(0,0,1),PlayerReferenceWorld=11}; } [Test]public void BinaryOrbitsRemainCompleteCirclesAroundTheirCommonBarycentre() { var scene=new LocalSystemScene(Binary());Check.That(scene.HierarchicalOrbitScale);Check.Equal(2,scene.Orbits.Count); foreach(var path in scene.Orbits) { Check.Equal(path.Points[0],path.Points[^1]);var centre=(path.Points[0]+path.Points[64])/2; Check.That(centre.Length<1e-9);var radius=(path.Points[0]-centre).Length; Check.That(path.Points.All(point=>Math.Abs((point-centre).Length-radius)<1e-9)); Check.Equal(scene.Nodes.Single(node=>node.Location.Identity==path.Child.Identity).Position,path.Points[0]); Check.That(path.Points.Any(point=>point.X>0)&&path.Points.Any(point=>point.X<0)&&path.Points.Any(point=>point.Z>0)&&path.Points.Any(point=>point.Z<0)); } } [Test]public void ReferenceRotationDoesNotRotateBodiesOrOrbitsButRealPositionChangesRemainVisible() { var first=Binary();var frame=new LocalSystemViewLock();Check.That(frame.Observe(first));var before=new LocalSystemScene(first,null,frame.Orientation); Vector3d R(Vector3d p)=>new(-p.Z,p.Y,p.X); var rotated=first with{Locations=first.Locations.Select(row=>row with{Position=R(row.Position!.Value)}).ToArray(), Orbits=first.Orbits.Select(orbit=>orbit with{ParentPosition=R(orbit.ParentPosition!.Value),PeriapsisDirection=R(orbit.PeriapsisDirection!.Value),TransverseDirection=R(orbit.TransverseDirection!.Value)}).ToArray(), PlayerPosition=R(first.PlayerPosition!.Value),PlayerForward=R(first.PlayerForward!.Value)}; Check.That(frame.Observe(rotated));var after=new LocalSystemScene(rotated,null,frame.Orientation); foreach(var pair in before.Nodes.Zip(after.Nodes))Check.That((pair.First.Position-pair.Second.Position).Length<1e-9); foreach(var pair in before.Orbits.Zip(after.Orbits))Check.That(pair.First.Points.Zip(pair.Second.Points).All(points=>(points.First-points.Second).Length<1e-9)); Check.That((before.PlayerPosition!.Value-after.PlayerPosition!.Value).Length<1e-9);Check.Equal(before.PlayerForward,after.PlayerForward); var moved=rotated with{PlayerPosition=rotated.PlayerPosition+new Vector3d(0,0,1e9)}; Check.That((new LocalSystemScene(moved,null,frame.Orientation).PlayerPosition!.Value-after.PlayerPosition.Value).Length>1e-5); } [Test]public void MissingAnchorKeepsTheLastVerifiedFrameAndChangingSystemResetsIt() { var frame=new LocalSystemViewLock();var snapshot=Binary();frame.Observe(snapshot);var before=frame.Orientation; Check.That(!frame.Observe(snapshot with{Orbits=[]}));Check.Equal(before,frame.Orientation); Check.That(frame.Observe(snapshot with{SystemAddress=2,Orbits=[]}));Check.That(!frame.Locked);Check.Equal(LocalSystemOrientation.Identity,frame.Orientation); } [Test]public void NativeSpectralClassesDoNotAllBecomeOrangeStars() { var f=LocalSystemStellarStyle.Colour(3);var m=LocalSystemStellarStyle.Colour(6);var o=LocalSystemStellarStyle.Colour(0); Check.That(f.B>m.B&&o.B>o.R&&m.R>m.B);Check.That(LocalSystemStellarStyle.Colour(null)!=m); } }