using System.Text.Json;
using System.Collections.Specialized;
using XFEEDToolBox.Core.Presentation;
using XFEEDToolBox.Core.Navigation;
using XFEEDToolBox.Views;
namespace XFEEDToolBox;
public partial class App
{
private static async Task RunCurrentSystemProbeAsync(string path)
{
var directory=Path.GetDirectoryName(Path.GetFullPath(path))!;Directory.CreateDirectory(directory);
string? failure=null;object? result=null;
static void Require(bool value,string message){if(!value)throw new InvalidOperationException(message);}
try
{
Require(ViewModel.OfflinePreview,"Current-system fixture requires --offline-preview and an isolated data directory.");
Require(Runtime.FlightDriver is null&&Runtime.Journal.Sequence==0,"Offline fixture must not bind a game or read the live Journal.");
MainWindow.AppWindow.Move(new(-30000,-30000));MainWindow.AppWindow.Resize(new(1680,1080));MainWindow.AppWindow.Show(false);
AppShellPage.Current!.Navigate(typeof(CurrentSystemPage));await Task.Delay(350);
Require(!ViewModel.CurrentSystemReading,"Offline fixture started a live catalogue read.");
var page=(CurrentSystemPage)AppShellPage.Current.CurrentPage!;
var categories=new[]{SystemLocationCategory.Signal,SystemLocationCategory.Asteroid,SystemLocationCategory.Signal,SystemLocationCategory.Carrier,SystemLocationCategory.Signal,
SystemLocationCategory.Station,SystemLocationCategory.PointOfInterest,SystemLocationCategory.Star,SystemLocationCategory.Settlement,SystemLocationCategory.Planet,SystemLocationCategory.LandablePlanet};
var names=new[]{"$USS_DegradedEmissions;","HIP 12099 A Belt Cluster 2","$USS_EncodedEmissions;","SPACEBALL1 | L1NK","$USS_HighGradeEmissions;",
"Ray Enterprise","$MULTIPLAYER_SCENARIO42_TITLE;","HIP 12099","Jameson Crash Site","HIP 12099 1","HIP 12099 1 b"};
var rows=Enumerable.Range(0,149).Select(i=>
{
var kind=i<categories.Length?categories[i]:SystemLocationCategory.Station;
return new SystemLocation(i+1,(ulong)i+100,i<names.Length?names[i]:$"离线测试地点 {i+1:000}","",i,kind,
kind is SystemLocationCategory.Station or SystemLocationCategory.Carrier or SystemLocationCategory.Settlement?70+i:null,
new(0,0,1000+i*1000),1000+i*1000,i==5,"interface-probe-"+i);
}).ToArray();
var snapshot=new CurrentSystemSnapshot(1,"HIP 12099",1,1,DateTimeOffset.UtcNow,rows);
ViewModel.ApplyCurrentSystemSnapshot(snapshot);await Task.Delay(150);page.UpdateLayout();
var list=Descendants(page).OfType<ListView>().Single();
var scroll=Descendants(list).OfType<ScrollViewer>().First();
Require(ViewModel.CurrentSystemLocations.Count==149,"Current system catalogue did not reach its real ListView.");
Require(ViewModel.CurrentSystemLocations[0].Name=="衰变信号"&&ViewModel.CurrentSystemLocations[1].Name=="HIP 12099 A 小行星带 2","Actual ListView did not use the built-in Chinese resource.");
var first=ViewModel.CurrentSystemLocations.ToArray();var actions=new List<NotifyCollectionChangedAction>();var properties=new List<string>();
ViewModel.CurrentSystemLocations.CollectionChanged+=(_,e)=>actions.Add(e.Action);
foreach(var row in first)row.PropertyChanged+=(_,e)=>properties.Add(e.PropertyName!);
var selected=first[12];ViewModel.SelectedSystemLocation=selected;
scroll.ChangeView(null,650,null,true);await Task.Delay(120);page.UpdateLayout();var offset=scroll.VerticalOffset;
var status=ViewModel.CurrentSystemStatus;
for(var sample=1;sample<=60;sample++)
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=sample+1,ObservedAt=snapshot.ObservedAt.AddSeconds(sample*3),
Locations=rows.Select(x=>x with{Position=new(1,sample,3),DistanceMetres=x.DistanceMetres+.001}).ToArray()});
await Task.Delay(100);page.UpdateLayout();
Require(actions.Count==0&&properties.Count==0,"Unchanged displayed values caused list/property notifications.");
Require(Math.Abs(scroll.VerticalOffset-offset)<.1&&ViewModel.CurrentSystemStatus==status&&!ViewModel.CurrentSystemReading,"Unchanged samples disturbed scrolling, the header or loading state.");
var stableProperties=properties.Count;var stableEvents=actions.Count;
var changed=rows.Select(x=>x.Key==selected.Record.Key?x with{DistanceMetres=60500}:x).ToArray();
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=62,Locations=changed});await Task.Delay(100);page.UpdateLayout();
Require(actions.Count==0&&properties.SequenceEqual(new[]{"Distance"}),"A distance change refreshed more than its displayed binding.");
Require(ReferenceEquals(selected,ViewModel.SelectedSystemLocation)&&first.Zip(ViewModel.CurrentSystemLocations).All(x=>ReferenceEquals(x.First,x.Second)),"Distance update recreated/reordered rows or reset selection.");
var container=list.ContainerFromItem(selected);
Require(container is not null&&Descendants(container).OfType<TextBlock>().Any(t=>t.Text=="60.5 km"),"The visible row's actual XAML distance binding did not update.");
var distanceProperties=properties.ToArray();
var anchor=first.First(x=>list.ContainerFromItem(x) is FrameworkElement element&&element.TransformToVisual(list).TransformPoint(new()).Y>=0);
double AnchorY()=>((FrameworkElement)list.ContainerFromItem(anchor)).TransformToVisual(list).TransformPoint(new()).Y;
var anchorY=AnchorY();
var signal=new SystemLocation(2000,9000,"$USS_DegradedEmissions;","",22,SystemLocationCategory.Signal,null,new(0,0,1500),1500,false,"new-signal");
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=63,Locations=changed.Append(signal).OrderBy(x=>x.DistanceMetres).ToArray()});await Task.Delay(100);page.UpdateLayout();var addedAnchorY=AnchorY();
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=64,Locations=changed.OrderBy(x=>x.DistanceMetres).ToArray()});await Task.Delay(100);page.UpdateLayout();var removedAnchorY=AnchorY();
Require(actions.SequenceEqual(new[]{NotifyCollectionChangedAction.Add,NotifyCollectionChangedAction.Remove}),"Signal arrival/removal caused a whole-list operation.");
Require(Math.Abs(anchorY-addedAnchorY)<2&&Math.Abs(anchorY-removedAnchorY)<2,"Adding/removing a signal moved the currently visible anchor.");
Require(ReferenceEquals(selected,ViewModel.SelectedSystemLocation),"Signal changes reset selection.");
await CapturePageAsync(page,Path.Combine(directory,"current-system-incremental.png"));
ViewModel.CurrentSystemSearch="高阶材料";Require(ViewModel.CurrentSystemLocations.Count==1,"Chinese navigation name search failed.");
ViewModel.CurrentSystemSearch="HighGradeEmissions";Require(ViewModel.CurrentSystemLocations.Count==1,"Original native name search failed.");
ViewModel.CurrentSystemSearch="";ViewModel.SelectedSystemLocation=ViewModel.CurrentSystemLocations.Single(x=>x.Name=="Ray Enterprise");
ViewModel.ShowSystemStations=false;Require(ViewModel.CurrentSystemLocations.All(x=>x.Record.Category!=SystemLocationCategory.Station)&&ViewModel.SelectedSystemLocation is null,"Station filter did not apply.");
ViewModel.ShowSystemStations=true;ViewModel.CurrentSystemSearch="Jameson";Require(ViewModel.CurrentSystemLocations.Count==1,"Proper name search failed.");
ViewModel.CurrentSystemSearch="";ViewModel.SelectedSystemLocation=ViewModel.CurrentSystemLocations.Single(x=>x.Name=="Ray Enterprise");
scroll.ChangeView(null,0,null,true);
Require(!ViewModel.StartSystemFlightCommand.CanExecute(null),"Unverified local flight controls must remain disabled.");
await Task.Delay(100);page.UpdateLayout();await CapturePageAsync(page,Path.Combine(directory,"current-system.png"));
result=new{visible=ViewModel.CurrentSystemLocations.Count,unchangedSamples=60,stableEvents,stableProperties,distanceProperties,signalEvents=actions.Select(x=>x.ToString()).Take(2).ToArray(),
scrollOffsetBefore=offset,anchorY,addedAnchorY,removedAnchorY,rowPreserved=true,selectionPreserved=true,searchPassed=true,localizedNames=first.Take(11).Select(x=>x.Name),
nativeLocalFlightReady=ViewModel.SystemFlightReady,gameFlightCommandsInvoked=false,gameRestartInvoked=false,gameChannelBound=Runtime.FlightDriver is not null,journalEvents=Runtime.Journal.Sequence,fixtureOnly=true};
}
catch(Exception error){failure=error.ToString();}
await File.WriteAllTextAsync(path,JsonSerializer.Serialize(new{result,failure,uiError=ViewModel.ErrorMessage},new JsonSerializerOptions{WriteIndented=true}));MainWindow.Close();
}
}
using System.Text.Json;
using System.Collections.Specialized;
using XFEEDToolBox.Core.Presentation;
using XFEEDToolBox.Core.Navigation;
using XFEEDToolBox.Views;
namespace XFEEDToolBox;
public partial class App
{
private static async Task RunCurrentSystemProbeAsync(string path)
{
var directory=Path.GetDirectoryName(Path.GetFullPath(path))!;Directory.CreateDirectory(directory);
string? failure=null;object? result=null;
static void Require(bool value,string message){if(!value)throw new InvalidOperationException(message);}
try
{
Require(ViewModel.OfflinePreview,"Current-system fixture requires --offline-preview and an isolated data directory.");
Require(Runtime.FlightDriver is null&&Runtime.Journal.Sequence==0,"Offline fixture must not bind a game or read the live Journal.");
MainWindow.AppWindow.Move(new(-30000,-30000));MainWindow.AppWindow.Resize(new(1680,1080));MainWindow.AppWindow.Show(false);
AppShellPage.Current!.Navigate(typeof(CurrentSystemPage));await Task.Delay(350);
Require(!ViewModel.CurrentSystemReading,"Offline fixture started a live catalogue read.");
var page=(CurrentSystemPage)AppShellPage.Current.CurrentPage!;
var categories=new[]{SystemLocationCategory.Signal,SystemLocationCategory.Asteroid,SystemLocationCategory.Signal,SystemLocationCategory.Carrier,SystemLocationCategory.Signal,
SystemLocationCategory.Station,SystemLocationCategory.PointOfInterest,SystemLocationCategory.Star,SystemLocationCategory.Settlement,SystemLocationCategory.Planet,SystemLocationCategory.LandablePlanet};
var names=new[]{"$USS_DegradedEmissions;","HIP 12099 A Belt Cluster 2","$USS_EncodedEmissions;","SPACEBALL1 | L1NK","$USS_HighGradeEmissions;",
"Ray Enterprise","$MULTIPLAYER_SCENARIO42_TITLE;","HIP 12099","Jameson Crash Site","HIP 12099 1","HIP 12099 1 b"};
var rows=Enumerable.Range(0,149).Select(i=>
{
var kind=i<categories.Length?categories[i]:SystemLocationCategory.Station;
return new SystemLocation(i+1,(ulong)i+100,i<names.Length?names[i]:$"离线测试地点 {i+1:000}","",i,kind,
kind is SystemLocationCategory.Station or SystemLocationCategory.Carrier or SystemLocationCategory.Settlement?70+i:null,
new(0,0,1000+i*1000),1000+i*1000,i==5,"interface-probe-"+i);
}).ToArray();
var snapshot=new CurrentSystemSnapshot(1,"HIP 12099",1,1,DateTimeOffset.UtcNow,rows);
ViewModel.ApplyCurrentSystemSnapshot(snapshot);await Task.Delay(150);page.UpdateLayout();
var list=Descendants(page).OfType<ListView>().Single();
var scroll=Descendants(list).OfType<ScrollViewer>().First();
Require(ViewModel.CurrentSystemLocations.Count==149,"Current system catalogue did not reach its real ListView.");
Require(ViewModel.CurrentSystemLocations[0].Name=="衰变信号"&&ViewModel.CurrentSystemLocations[1].Name=="HIP 12099 A 小行星带 2","Actual ListView did not use the built-in Chinese resource.");
var first=ViewModel.CurrentSystemLocations.ToArray();var actions=new List<NotifyCollectionChangedAction>();var properties=new List<string>();
ViewModel.CurrentSystemLocations.CollectionChanged+=(_,e)=>actions.Add(e.Action);
foreach(var row in first)row.PropertyChanged+=(_,e)=>properties.Add(e.PropertyName!);
var selected=first[12];ViewModel.SelectedSystemLocation=selected;
scroll.ChangeView(null,650,null,true);await Task.Delay(120);page.UpdateLayout();var offset=scroll.VerticalOffset;
var status=ViewModel.CurrentSystemStatus;
for(var sample=1;sample<=60;sample++)
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=sample+1,ObservedAt=snapshot.ObservedAt.AddSeconds(sample*3),
Locations=rows.Select(x=>x with{Position=new(1,sample,3),DistanceMetres=x.DistanceMetres+.001}).ToArray()});
await Task.Delay(100);page.UpdateLayout();
Require(actions.Count==0&&properties.Count==0,"Unchanged displayed values caused list/property notifications.");
Require(Math.Abs(scroll.VerticalOffset-offset)<.1&&ViewModel.CurrentSystemStatus==status&&!ViewModel.CurrentSystemReading,"Unchanged samples disturbed scrolling, the header or loading state.");
var stableProperties=properties.Count;var stableEvents=actions.Count;
var changed=rows.Select(x=>x.Key==selected.Record.Key?x with{DistanceMetres=60500}:x).ToArray();
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=62,Locations=changed});await Task.Delay(100);page.UpdateLayout();
Require(actions.Count==0&&properties.SequenceEqual(new[]{"Distance"}),"A distance change refreshed more than its displayed binding.");
Require(ReferenceEquals(selected,ViewModel.SelectedSystemLocation)&&first.Zip(ViewModel.CurrentSystemLocations).All(x=>ReferenceEquals(x.First,x.Second)),"Distance update recreated/reordered rows or reset selection.");
var container=list.ContainerFromItem(selected);
Require(container is not null&&Descendants(container).OfType<TextBlock>().Any(t=>t.Text=="60.5 km"),"The visible row's actual XAML distance binding did not update.");
var distanceProperties=properties.ToArray();
var anchor=first.First(x=>list.ContainerFromItem(x) is FrameworkElement element&&element.TransformToVisual(list).TransformPoint(new()).Y>=0);
double AnchorY()=>((FrameworkElement)list.ContainerFromItem(anchor)).TransformToVisual(list).TransformPoint(new()).Y;
var anchorY=AnchorY();
var signal=new SystemLocation(2000,9000,"$USS_DegradedEmissions;","",22,SystemLocationCategory.Signal,null,new(0,0,1500),1500,false,"new-signal");
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=63,Locations=changed.Append(signal).OrderBy(x=>x.DistanceMetres).ToArray()});await Task.Delay(100);page.UpdateLayout();var addedAnchorY=AnchorY();
ViewModel.ApplyCurrentSystemSnapshot(snapshot with{Sequence=64,Locations=changed.OrderBy(x=>x.DistanceMetres).ToArray()});await Task.Delay(100);page.UpdateLayout();var removedAnchorY=AnchorY();
Require(actions.SequenceEqual(new[]{NotifyCollectionChangedAction.Add,NotifyCollectionChangedAction.Remove}),"Signal arrival/removal caused a whole-list operation.");
Require(Math.Abs(anchorY-addedAnchorY)<2&&Math.Abs(anchorY-removedAnchorY)<2,"Adding/removing a signal moved the currently visible anchor.");
Require(ReferenceEquals(selected,ViewModel.SelectedSystemLocation),"Signal changes reset selection.");
await CapturePageAsync(page,Path.Combine(directory,"current-system-incremental.png"));
ViewModel.CurrentSystemSearch="高阶材料";Require(ViewModel.CurrentSystemLocations.Count==1,"Chinese navigation name search failed.");
ViewModel.CurrentSystemSearch="HighGradeEmissions";Require(ViewModel.CurrentSystemLocations.Count==1,"Original native name search failed.");
ViewModel.CurrentSystemSearch="";ViewModel.SelectedSystemLocation=ViewModel.CurrentSystemLocations.Single(x=>x.Name=="Ray Enterprise");
ViewModel.ShowSystemStations=false;Require(ViewModel.CurrentSystemLocations.All(x=>x.Record.Category!=SystemLocationCategory.Station)&&ViewModel.SelectedSystemLocation is null,"Station filter did not apply.");
ViewModel.ShowSystemStations=true;ViewModel.CurrentSystemSearch="Jameson";Require(ViewModel.CurrentSystemLocations.Count==1,"Proper name search failed.");
ViewModel.CurrentSystemSearch="";ViewModel.SelectedSystemLocation=ViewModel.CurrentSystemLocations.Single(x=>x.Name=="Ray Enterprise");
scroll.ChangeView(null,0,null,true);
Require(!ViewModel.StartSystemFlightCommand.CanExecute(null),"Unverified local flight controls must remain disabled.");
await Task.Delay(100);page.UpdateLayout();await CapturePageAsync(page,Path.Combine(directory,"current-system.png"));
result=new{visible=ViewModel.CurrentSystemLocations.Count,unchangedSamples=60,stableEvents,stableProperties,distanceProperties,signalEvents=actions.Select(x=>x.ToString()).Take(2).ToArray(),
scrollOffsetBefore=offset,anchorY,addedAnchorY,removedAnchorY,rowPreserved=true,selectionPreserved=true,searchPassed=true,localizedNames=first.Take(11).Select(x=>x.Name),
nativeLocalFlightReady=ViewModel.SystemFlightReady,gameFlightCommandsInvoked=false,gameRestartInvoked=false,gameChannelBound=Runtime.FlightDriver is not null,journalEvents=Runtime.Journal.Sequence,fixtureOnly=true};
}
catch(Exception error){failure=error.ToString();}
await File.WriteAllTextAsync(path,JsonSerializer.Serialize(new{result,failure,uiError=ViewModel.ErrorMessage},new JsonSerializerOptions{WriteIndented=true}));MainWindow.Close();
}
}