From 7fa72db0704904ee48c1959ec7c2a23c7cc081da Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 2 Nov 2023 23:59:09 +0900
Subject: [PATCH 01/29] Add TRViS.LocationService project to solution
---
TRViS.LocationService/TRViS.LocationService.csproj | 10 ++++++++++
TRViS.sln | 8 +++++++-
2 files changed, 17 insertions(+), 1 deletion(-)
create mode 100644 TRViS.LocationService/TRViS.LocationService.csproj
diff --git a/TRViS.LocationService/TRViS.LocationService.csproj b/TRViS.LocationService/TRViS.LocationService.csproj
new file mode 100644
index 00000000..5625b3af
--- /dev/null
+++ b/TRViS.LocationService/TRViS.LocationService.csproj
@@ -0,0 +1,10 @@
+
+
+
+ netstandard2.1
+ 11.0
+ enable
+ enable
+
+
+
diff --git a/TRViS.sln b/TRViS.sln
index 3928c350..02be5a96 100644
--- a/TRViS.sln
+++ b/TRViS.sln
@@ -1,4 +1,4 @@
-
+
Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 16
VisualStudioVersion = 17.0.31611.283
@@ -9,6 +9,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.IO", "TRViS.IO\TRViS.
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.IO.Tests", "TRViS.IO.Tests\TRViS.IO.Tests.csproj", "{39F34DB6-F6A8-4830-A2A0-A3F18C81C225}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.LocationService", "TRViS.LocationService\TRViS.LocationService.csproj", "{7B07663D-D68A-4CFD-823B-EE07644FEA8F}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -29,6 +31,10 @@ Global
{39F34DB6-F6A8-4830-A2A0-A3F18C81C225}.Debug|Any CPU.Build.0 = Debug|Any CPU
{39F34DB6-F6A8-4830-A2A0-A3F18C81C225}.Release|Any CPU.ActiveCfg = Release|Any CPU
{39F34DB6-F6A8-4830-A2A0-A3F18C81C225}.Release|Any CPU.Build.0 = Release|Any CPU
+ {7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
From a56cd036e602f93f8ec09e77fe4ce22cad7e10fd Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Sun, 12 Nov 2023 22:58:27 +0900
Subject: [PATCH 02/29] change line ending from CRLF to LF
---
.../TRViS.LocationService.csproj | 20 +++++++++----------
1 file changed, 10 insertions(+), 10 deletions(-)
diff --git a/TRViS.LocationService/TRViS.LocationService.csproj b/TRViS.LocationService/TRViS.LocationService.csproj
index 5625b3af..559307bf 100644
--- a/TRViS.LocationService/TRViS.LocationService.csproj
+++ b/TRViS.LocationService/TRViS.LocationService.csproj
@@ -1,10 +1,10 @@
-
-
-
- netstandard2.1
- 11.0
- enable
- enable
-
-
-
+
+
+
+ netstandard2.1
+ 11.0
+ enable
+ enable
+
+
+
From f993a48fac227aa2d9f366feb23b16e1f9e131d6 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Sun, 12 Nov 2023 23:03:37 +0900
Subject: [PATCH 03/29] Create CalculateDistance.cs
---
.../Utils/CalculateDistance.cs | 26 +++++++++++++++++++
1 file changed, 26 insertions(+)
create mode 100644 TRViS.LocationService/Utils/CalculateDistance.cs
diff --git a/TRViS.LocationService/Utils/CalculateDistance.cs b/TRViS.LocationService/Utils/CalculateDistance.cs
new file mode 100644
index 00000000..0d1d2763
--- /dev/null
+++ b/TRViS.LocationService/Utils/CalculateDistance.cs
@@ -0,0 +1,26 @@
+namespace TRViS.Services.LocationService;
+
+internal static partial class Utils
+{
+ const double EARTH_RADIUS_m = 6378137;
+
+ public static double DegToRad(in double deg)
+ => deg * Math.PI / 180.0;
+
+ // Haversine Formula
+ public static double CalculateDistance_m(in double lon1_deg, in double lat1_deg, in double lon2_deg, in double lat2_deg)
+ {
+ double lon1_rad = DegToRad(lon1_deg);
+ double lat1_rad = DegToRad(lat1_deg);
+ double lon2_rad = DegToRad(lon2_deg);
+ double lat2_rad = DegToRad(lat2_deg);
+
+ return EARTH_RADIUS_m * Math.Acos(
+ Math.Sin(lat1_rad) * Math.Sin(lat2_rad) +
+ Math.Cos(lat1_rad) * Math.Cos(lat2_rad) * Math.Cos(lon2_rad - lon1_rad)
+ );
+ }
+
+ public static double CalculateDistance_m(in ILocationLonLat_deg value1, in ILocationLonLat_deg value2)
+ => CalculateDistance_m(value1.Location_lon_deg, value1.Location_lat_deg, value2.Location_lon_deg, value2.Location_lat_deg);
+}
From 8fcc6115668daf81ec904634d09090c733db52b0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Sun, 12 Nov 2023 23:05:26 +0900
Subject: [PATCH 04/29] Create IsNearBy.cs
---
TRViS.LocationService/Utils/IsNearBy.cs | 9 +++++++++
1 file changed, 9 insertions(+)
create mode 100644 TRViS.LocationService/Utils/IsNearBy.cs
diff --git a/TRViS.LocationService/Utils/IsNearBy.cs b/TRViS.LocationService/Utils/IsNearBy.cs
new file mode 100644
index 00000000..72c2f255
--- /dev/null
+++ b/TRViS.LocationService/Utils/IsNearBy.cs
@@ -0,0 +1,9 @@
+namespace TRViS.Services.LocationService;
+
+internal static partial class Utils
+{
+ public static bool IsNearBy(StaLocationInfo target, ILocationLonLat_deg currentLocation)
+ => IsNearBy(target, CalculateDistance_m(target, currentLocation));
+ public static bool IsNearBy(StaLocationInfo target, double currentDistance_m)
+ => currentDistance_m <= target.NearbyRadius_m;
+}
From c4fd06b574d52c702395d014652e69e651ddba9e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Sun, 12 Nov 2023 23:06:49 +0900
Subject: [PATCH 05/29] add test project for TRViS.LocationService
---
TRViS.LocationService.Tests/GlobalUsings.cs | 1 +
.../TRViS.LocationService.Tests.csproj | 24 +++++++++++++++++++
TRViS.sln | 6 +++++
3 files changed, 31 insertions(+)
create mode 100644 TRViS.LocationService.Tests/GlobalUsings.cs
create mode 100644 TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
diff --git a/TRViS.LocationService.Tests/GlobalUsings.cs b/TRViS.LocationService.Tests/GlobalUsings.cs
new file mode 100644
index 00000000..32445676
--- /dev/null
+++ b/TRViS.LocationService.Tests/GlobalUsings.cs
@@ -0,0 +1 @@
+global using NUnit.Framework;
diff --git a/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj b/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
new file mode 100644
index 00000000..b9451058
--- /dev/null
+++ b/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
@@ -0,0 +1,24 @@
+
+
+
+ net8.0
+ enable
+ enable
+
+ false
+ true
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/TRViS.sln b/TRViS.sln
index 02be5a96..c5944145 100644
--- a/TRViS.sln
+++ b/TRViS.sln
@@ -11,6 +11,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.IO.Tests", "TRViS.IO.
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.LocationService", "TRViS.LocationService\TRViS.LocationService.csproj", "{7B07663D-D68A-4CFD-823B-EE07644FEA8F}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TRViS.LocationService.Tests", "TRViS.LocationService.Tests\TRViS.LocationService.Tests.csproj", "{9E965886-84FE-499E-9C30-D17F707D5EF5}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -35,6 +37,10 @@ Global
{7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Debug|Any CPU.Build.0 = Debug|Any CPU
{7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Release|Any CPU.ActiveCfg = Release|Any CPU
{7B07663D-D68A-4CFD-823B-EE07644FEA8F}.Release|Any CPU.Build.0 = Release|Any CPU
+ {9E965886-84FE-499E-9C30-D17F707D5EF5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {9E965886-84FE-499E-9C30-D17F707D5EF5}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {9E965886-84FE-499E-9C30-D17F707D5EF5}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {9E965886-84FE-499E-9C30-D17F707D5EF5}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
From 849edc514735500dff837f79d2e5c36b4b061e05 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 21:21:19 +0900
Subject: [PATCH 06/29] =?UTF-8?q?Leave=E5=88=A4=E5=AE=9A=E7=94=A8=E3=81=AE?=
=?UTF-8?q?=E9=96=A2=E6=95=B0=E3=82=82=E8=BF=BD=E5=8A=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS.LocationService/Utils/IsNearBy.cs | 12 +++++++++++-
1 file changed, 11 insertions(+), 1 deletion(-)
diff --git a/TRViS.LocationService/Utils/IsNearBy.cs b/TRViS.LocationService/Utils/IsNearBy.cs
index 72c2f255..8d22555f 100644
--- a/TRViS.LocationService/Utils/IsNearBy.cs
+++ b/TRViS.LocationService/Utils/IsNearBy.cs
@@ -5,5 +5,15 @@ internal static partial class Utils
public static bool IsNearBy(StaLocationInfo target, ILocationLonLat_deg currentLocation)
=> IsNearBy(target, CalculateDistance_m(target, currentLocation));
public static bool IsNearBy(StaLocationInfo target, double currentDistance_m)
- => currentDistance_m <= target.NearbyRadius_m;
+ => IsNearBy(target.NearbyRadius_m, currentDistance_m);
+
+ public static bool IsNearBy(double NearbyRadius_m, double currentDistance_m)
+ => currentDistance_m <= NearbyRadius_m;
+
+ public static bool IsLeaved(StaLocationInfo target, ILocationLonLat_deg currentLocation)
+ => IsLeaved(target, CalculateDistance_m(target, currentLocation));
+ public static bool IsLeaved(StaLocationInfo target, double currentDistance_m)
+ => IsLeaved(target.NearbyRadius_m, currentDistance_m);
+ public static bool IsLeaved(double NearbyRadius_m, double currentDistance_m)
+ => !IsNearBy(NearbyRadius_m * 1.1, currentDistance_m);
}
From 0fa965905b0fb93fd56dbd479ce6784ee9281eaa Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 22:07:35 +0900
Subject: [PATCH 07/29] Create ILocationService.cs
---
TRViS.LocationService/ILocationService.cs | 52 +++++++++++++++++++++++
1 file changed, 52 insertions(+)
create mode 100644 TRViS.LocationService/ILocationService.cs
diff --git a/TRViS.LocationService/ILocationService.cs b/TRViS.LocationService/ILocationService.cs
new file mode 100644
index 00000000..921bfb5f
--- /dev/null
+++ b/TRViS.LocationService/ILocationService.cs
@@ -0,0 +1,52 @@
+namespace TRViS.Services;
+
+public class LocationStateChangedEventArgs : EventArgs, IEquatable
+{
+ public int NewStationIndex { get; }
+ public bool IsRunningToNextStation { get; }
+
+ public LocationStateChangedEventArgs(int newStationIndex, bool isRunningToNextStation)
+ {
+ NewStationIndex = newStationIndex;
+ IsRunningToNextStation = isRunningToNextStation;
+ }
+
+ public bool Equals(LocationStateChangedEventArgs? other)
+ {
+ if (other is null)
+ return false;
+
+ if (ReferenceEquals(this, other))
+ return true;
+
+ return
+ NewStationIndex == other.NewStationIndex
+ &&
+ IsRunningToNextStation == other.IsRunningToNextStation
+ ;
+ }
+
+ public override bool Equals(object obj)
+ => Equals(obj as LocationStateChangedEventArgs);
+
+ public override int GetHashCode()
+ => HashCode.Combine(NewStationIndex, IsRunningToNextStation);
+
+ public override string ToString()
+ {
+ return $"{nameof(LocationStateChangedEventArgs)} {{ {nameof(NewStationIndex)}: {NewStationIndex}, {nameof(IsRunningToNextStation)}: {IsRunningToNextStation} }}";
+ }
+}
+
+public interface ILocationService
+{
+ event EventHandler? LocationStateChanged;
+
+ StaLocationInfo[]? StaLocationInfo { get; set; }
+
+ int CurrentStationIndex { get; }
+
+ bool IsRunningToNextStation { get; }
+
+ void ResetLocationInfo();
+}
From a81e85fa7079085cc424d3faf7832bf6243faec9 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 22:08:27 +0900
Subject: [PATCH 08/29] Create StaLocationInfo.cs
---
TRViS.LocationService/StaLocationInfo.cs | 53 ++++++++++++++++++++++++
1 file changed, 53 insertions(+)
create mode 100644 TRViS.LocationService/StaLocationInfo.cs
diff --git a/TRViS.LocationService/StaLocationInfo.cs b/TRViS.LocationService/StaLocationInfo.cs
new file mode 100644
index 00000000..23a9b164
--- /dev/null
+++ b/TRViS.LocationService/StaLocationInfo.cs
@@ -0,0 +1,53 @@
+namespace TRViS.Services;
+
+public interface ILocationLonLat_deg
+{
+ double Location_lon_deg { get; }
+ double Location_lat_deg { get; }
+}
+
+public class StaLocationInfo : ILocationLonLat_deg
+{
+ public double Location_m { get; }
+ public double Location_lon_deg { get; }
+ public double Location_lat_deg { get; }
+ public double NearbyRadius_m { get; }
+
+ public StaLocationInfo(double location_m, double location_lon_deg, double location_lat_deg, double nearbyRadius_m)
+ {
+ Location_m = location_m;
+ Location_lon_deg = location_lon_deg;
+ Location_lat_deg = location_lat_deg;
+ NearbyRadius_m = nearbyRadius_m;
+ }
+
+ public bool Equals(StaLocationInfo? other)
+ {
+ if (other is null)
+ return false;
+
+ if (ReferenceEquals(this, other))
+ return true;
+
+ return
+ Location_m == other.Location_m
+ &&
+ Location_lon_deg == other.Location_lon_deg
+ &&
+ Location_lat_deg == other.Location_lat_deg
+ &&
+ NearbyRadius_m == other.NearbyRadius_m
+ ;
+ }
+
+ public override bool Equals(object obj)
+ => Equals(obj as StaLocationInfo);
+
+ public override int GetHashCode()
+ => HashCode.Combine(Location_m, Location_lon_deg, Location_lat_deg, NearbyRadius_m);
+
+ public override string ToString()
+ {
+ return $"{nameof(StaLocationInfo)} {{ {nameof(Location_m)}: {Location_m}, {nameof(Location_lon_deg)}: {Location_lon_deg}, {nameof(Location_lat_deg)}: {Location_lat_deg}, {nameof(NearbyRadius_m)}: {NearbyRadius_m} }}";
+ }
+}
From 64c11f22297b8673ac57c2f18d9bbf9d83c9dfa4 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 22:08:34 +0900
Subject: [PATCH 09/29] Create LonLatLocationService.cs
---
.../LonLatLocationService.cs | 163 ++++++++++++++++++
1 file changed, 163 insertions(+)
create mode 100644 TRViS.LocationService/LonLatLocationService.cs
diff --git a/TRViS.LocationService/LonLatLocationService.cs b/TRViS.LocationService/LonLatLocationService.cs
new file mode 100644
index 00000000..b8a0f532
--- /dev/null
+++ b/TRViS.LocationService/LonLatLocationService.cs
@@ -0,0 +1,163 @@
+
+using TRViS.Services.LocationService;
+
+namespace TRViS.Services;
+
+public class LonLatLocationService : ILocationService
+{
+ public event EventHandler? LocationStateChanged;
+
+ const int CURRENT_STATION_INDEX_NOT_SET = -1;
+ const int DISTANCE_HISTORY_QUEUE_SIZE = 3;
+ readonly Queue DistanceHistoryQueue = new(DISTANCE_HISTORY_QUEUE_SIZE);
+
+ private StaLocationInfo[]? _staLocationInfo;
+ public StaLocationInfo[]? StaLocationInfo
+ {
+ get => _staLocationInfo;
+ set
+ {
+ if (value == _staLocationInfo)
+ return;
+
+ _staLocationInfo = value;
+ ResetLocationInfo();
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+ }
+
+ public int CurrentStationIndex { get; private set; } = CURRENT_STATION_INDEX_NOT_SET;
+
+ public bool IsRunningToNextStation { get; private set; }
+
+ public void ResetLocationInfo()
+ => ResetLocationInfo(true);
+ void ResetLocationInfo(bool invokeEvent)
+ {
+ CurrentStationIndex = StaLocationInfo is null ? CURRENT_STATION_INDEX_NOT_SET : 0;
+ IsRunningToNextStation = false;
+ DistanceHistoryQueue.Clear();
+
+ if (invokeEvent)
+ {
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+ }
+
+ public void ForceSetLocationInfo(double lon_deg, double lat_deg)
+ {
+ ResetLocationInfo(false);
+ if (StaLocationInfo is null)
+ return;
+
+ if (StaLocationInfo.Length <= 1)
+ {
+ CurrentStationIndex = StaLocationInfo.Length - 1;
+ IsRunningToNextStation = false;
+ return;
+ }
+
+ double[] distanceArray = StaLocationInfo.Select(v => Utils.CalculateDistance_m(lon_deg, lat_deg, v.Location_lon_deg, v.Location_lat_deg)).ToArray();
+
+ int nearestStationIndex = -1;
+ double nearestDistance = double.MaxValue;
+ for (int i = 0; i < distanceArray.Length; i++)
+ {
+ if (distanceArray[i] < nearestDistance)
+ {
+ nearestStationIndex = i;
+ nearestDistance = distanceArray[i];
+ }
+ }
+
+ if (nearestStationIndex == 0)
+ {
+ // 最初の駅が一番近い場合
+ CurrentStationIndex = 0;
+ IsRunningToNextStation = Utils.IsLeaved(StaLocationInfo[nearestStationIndex], distanceArray[nearestStationIndex]);
+ }
+ else if (nearestStationIndex == StaLocationInfo.Length - 1)
+ {
+ // 最後の駅が一番近い場合
+ if (Utils.IsNearBy(StaLocationInfo[nearestStationIndex], distanceArray[nearestStationIndex]))
+ {
+ CurrentStationIndex = nearestStationIndex;
+ IsRunningToNextStation = false;
+ }
+ else
+ {
+ CurrentStationIndex = nearestStationIndex - 1;
+ IsRunningToNextStation = true;
+ }
+ }
+ else
+ {
+ // 途中の駅が一番近い場合
+ if (Utils.IsNearBy(StaLocationInfo[nearestStationIndex], distanceArray[nearestStationIndex]))
+ {
+ CurrentStationIndex = nearestStationIndex;
+ IsRunningToNextStation = false;
+ }
+ else
+ {
+ IsRunningToNextStation = true;
+ CurrentStationIndex = nearestStationIndex;
+ // 次の駅よりも前の駅の方が近い場合、おそらく前の駅からこの駅に向かっているところである
+ if (distanceArray[nearestStationIndex - 1] < distanceArray[nearestStationIndex + 1])
+ {
+ CurrentStationIndex = nearestStationIndex - 1;
+ }
+ }
+ }
+
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+
+ double GetDistanceToStationAverage(in StaLocationInfo staLocationInfo, double lon_deg, double lat_deg)
+ {
+ double distanceToStation = Utils.CalculateDistance_m(lon_deg, lat_deg, staLocationInfo.Location_lon_deg, staLocationInfo.Location_lat_deg);
+
+ if (DistanceHistoryQueue.Count == DISTANCE_HISTORY_QUEUE_SIZE)
+ DistanceHistoryQueue.Dequeue();
+ DistanceHistoryQueue.Enqueue(distanceToStation);
+
+ if (DistanceHistoryQueue.Count < DISTANCE_HISTORY_QUEUE_SIZE)
+ return double.NaN;
+
+ return DistanceHistoryQueue.Average();
+ }
+
+ public void SetCurrentLocation(double lon_deg, double lat_deg)
+ {
+ if (StaLocationInfo is null || CurrentStationIndex < 0 || StaLocationInfo.Length <= CurrentStationIndex)
+ return;
+
+ if (IsRunningToNextStation)
+ {
+ StaLocationInfo nextStation = StaLocationInfo[CurrentStationIndex + 1];
+ double distanceToNextStationAverage = GetDistanceToStationAverage(nextStation, lon_deg, lat_deg);
+
+ if (!double.IsNaN(distanceToNextStationAverage)
+ && Utils.IsNearBy(nextStation, distanceToNextStationAverage))
+ {
+ DistanceHistoryQueue.Clear();
+ CurrentStationIndex++;
+ IsRunningToNextStation = false;
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+ }
+ else if (CurrentStationIndex < StaLocationInfo.Length - 1)
+ {
+ StaLocationInfo currentStation = StaLocationInfo[CurrentStationIndex];
+
+ double distanceFromCurrentStationAverage = GetDistanceToStationAverage(currentStation, lon_deg, lat_deg);
+ if (!double.IsNaN(distanceFromCurrentStationAverage)
+ && Utils.IsLeaved(currentStation, distanceFromCurrentStationAverage))
+ {
+ DistanceHistoryQueue.Clear();
+ IsRunningToNextStation = true;
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+ }
+ }
+}
From b7709ecd2ecc0af670e3be4611711d0694818d66 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 22:08:58 +0900
Subject: [PATCH 10/29] Create LonLatLocationService.Tests.cs
---
.../LonLatLocationService.Tests.cs | 102 ++++++++++++++++++
1 file changed, 102 insertions(+)
create mode 100644 TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
diff --git a/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
new file mode 100644
index 00000000..5f973d3f
--- /dev/null
+++ b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
@@ -0,0 +1,102 @@
+using TRViS.Services;
+
+namespace TRViS.LocationService.Tests;
+
+public class Tests
+{
+ [Test]
+ public void InitializeTest()
+ {
+ LonLatLocationService service = new();
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.StaLocationInfo, Is.Null);
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(-1));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+ }
+
+ [Test]
+ public void MoveTest()
+ {
+ LonLatLocationService service = new()
+ {
+ StaLocationInfo =
+ [
+ new(0, 0, 0, 200),
+ new(1, 1, 1, 200),
+ new(2, 2, 2, 200),
+ ]
+ };
+
+ // 初期状態は、駅0にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.SetCurrentLocation(0.1, 0.1);
+
+ // (平均値を取るために、3回以上の移動が必要)
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.SetCurrentLocation(0.1, 0.1);
+ service.SetCurrentLocation(0.1, 0.1);
+
+ // 駅0を離れ、駅1に向かっている
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+
+ service.SetCurrentLocation(1, 1);
+ service.SetCurrentLocation(1, 1);
+ service.SetCurrentLocation(1, 1);
+
+ // ちょうど駅1にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.SetCurrentLocation(2, 2);
+ service.SetCurrentLocation(2, 2);
+ service.SetCurrentLocation(2, 2);
+
+ // 駅1を離れ、駅2に向かっている
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+
+ service.SetCurrentLocation(2, 2);
+ service.SetCurrentLocation(2, 2);
+ service.SetCurrentLocation(2, 2);
+
+ // ちょうど駅2にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(2));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.SetCurrentLocation(3, 3);
+ service.SetCurrentLocation(3, 3);
+ service.SetCurrentLocation(3, 3);
+
+ // 駅2から先には進まない
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(2));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+ }
+}
From 011ee09760a3d283315a72a0d97760005da61bd0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Wed, 15 Nov 2023 22:09:58 +0900
Subject: [PATCH 11/29] =?UTF-8?q?=E3=82=A4=E3=83=B3=E3=83=87=E3=83=B3?=
=?UTF-8?q?=E3=83=88=E3=82=92=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj b/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
index b9451058..db4ce0f5 100644
--- a/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
+++ b/TRViS.LocationService.Tests/TRViS.LocationService.Tests.csproj
@@ -18,7 +18,7 @@
-
+
From e0a7f0280c14e14c366d7ee10a3f705a653877d4 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 00:09:46 +0900
Subject: [PATCH 12/29] =?UTF-8?q?InfoRow=E7=AD=89=E3=81=AE=E3=80=8C?=
=?UTF-8?q?=E7=B7=AF=E5=BA=A6=E7=B5=8C=E5=BA=A6=E3=81=8C=E8=A8=AD=E5=AE=9A?=
=?UTF-8?q?=E3=81=95=E3=82=8C=E3=81=A6=E3=81=84=E3=81=AA=E3=81=84=E9=A7=85?=
=?UTF-8?q?=E3=80=8D=E3=81=AF=E7=84=A1=E8=A6=96=E3=81=99=E3=82=8B=E3=82=88?=
=?UTF-8?q?=E3=81=86=E3=81=AB=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.../LonLatLocationService.cs | 91 ++++++++++++++++---
TRViS.LocationService/StaLocationInfo.cs | 39 +++++++-
2 files changed, 112 insertions(+), 18 deletions(-)
diff --git a/TRViS.LocationService/LonLatLocationService.cs b/TRViS.LocationService/LonLatLocationService.cs
index b8a0f532..899d72de 100644
--- a/TRViS.LocationService/LonLatLocationService.cs
+++ b/TRViS.LocationService/LonLatLocationService.cs
@@ -34,7 +34,7 @@ public void ResetLocationInfo()
=> ResetLocationInfo(true);
void ResetLocationInfo(bool invokeEvent)
{
- CurrentStationIndex = StaLocationInfo is null ? CURRENT_STATION_INDEX_NOT_SET : 0;
+ CurrentStationIndex = GetNextStationIndex(StaLocationInfo ?? Array.Empty(), CURRENT_STATION_INDEX_NOT_SET);
IsRunningToNextStation = false;
DistanceHistoryQueue.Clear();
@@ -44,25 +44,67 @@ void ResetLocationInfo(bool invokeEvent)
}
}
+ static int GetPastStationIndex(in StaLocationInfo[] staLocationInfo, int currentStationIndex)
+ {
+ for (int i = currentStationIndex - 1; i >= 0; i--)
+ {
+ if (staLocationInfo[i].HasLonLatLocation)
+ return i;
+ }
+
+ return CURRENT_STATION_INDEX_NOT_SET;
+ }
+ static int GetNextStationIndex(in StaLocationInfo[] staLocationInfo, int currentStationIndex)
+ {
+ for (int i = currentStationIndex + 1; i < staLocationInfo.Length; i++)
+ {
+ if (staLocationInfo[i].HasLonLatLocation)
+ return i;
+ }
+
+ return CURRENT_STATION_INDEX_NOT_SET;
+ }
public void ForceSetLocationInfo(double lon_deg, double lat_deg)
{
ResetLocationInfo(false);
if (StaLocationInfo is null)
+ {
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
return;
+ }
+ CurrentStationIndex = CURRENT_STATION_INDEX_NOT_SET;
if (StaLocationInfo.Length <= 1)
{
- CurrentStationIndex = StaLocationInfo.Length - 1;
- IsRunningToNextStation = false;
+ if (StaLocationInfo.Length == 1 && StaLocationInfo[0].HasLonLatLocation)
+ {
+ CurrentStationIndex = 0;
+ }
+
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
return;
}
- double[] distanceArray = StaLocationInfo.Select(v => Utils.CalculateDistance_m(lon_deg, lat_deg, v.Location_lon_deg, v.Location_lat_deg)).ToArray();
+ double[] distanceArray = StaLocationInfo.Select(
+ v =>
+ v.HasLonLatLocation
+ ? Utils.CalculateDistance_m(lon_deg, lat_deg, v.Location_lon_deg, v.Location_lat_deg)
+ : double.NaN
+ ).ToArray();
- int nearestStationIndex = -1;
+ int nearestStationIndex = CURRENT_STATION_INDEX_NOT_SET;
+ int firstStationIndex = CURRENT_STATION_INDEX_NOT_SET;
+ int lastStationIndex = CURRENT_STATION_INDEX_NOT_SET;
double nearestDistance = double.MaxValue;
for (int i = 0; i < distanceArray.Length; i++)
{
+ if (double.IsNaN(distanceArray[i]))
+ continue;
+
+ if (firstStationIndex < 0)
+ firstStationIndex = i;
+ lastStationIndex = i;
+
if (distanceArray[i] < nearestDistance)
{
nearestStationIndex = i;
@@ -70,13 +112,29 @@ public void ForceSetLocationInfo(double lon_deg, double lat_deg)
}
}
- if (nearestStationIndex == 0)
+ // 全ての駅で位置情報が設定されていない場合
+ if (nearestStationIndex < 0)
+ {
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ return;
+ }
+
+ // 有効な駅が1つしかない場合
+ if (firstStationIndex == lastStationIndex)
+ {
+ CurrentStationIndex = firstStationIndex;
+ IsRunningToNextStation = false;
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ return;
+ }
+
+ if (nearestStationIndex == firstStationIndex)
{
// 最初の駅が一番近い場合
- CurrentStationIndex = 0;
+ CurrentStationIndex = firstStationIndex;
IsRunningToNextStation = Utils.IsLeaved(StaLocationInfo[nearestStationIndex], distanceArray[nearestStationIndex]);
}
- else if (nearestStationIndex == StaLocationInfo.Length - 1)
+ else if (nearestStationIndex == lastStationIndex)
{
// 最後の駅が一番近い場合
if (Utils.IsNearBy(StaLocationInfo[nearestStationIndex], distanceArray[nearestStationIndex]))
@@ -86,7 +144,7 @@ public void ForceSetLocationInfo(double lon_deg, double lat_deg)
}
else
{
- CurrentStationIndex = nearestStationIndex - 1;
+ CurrentStationIndex = GetPastStationIndex(StaLocationInfo, nearestStationIndex);
IsRunningToNextStation = true;
}
}
@@ -102,10 +160,12 @@ public void ForceSetLocationInfo(double lon_deg, double lat_deg)
{
IsRunningToNextStation = true;
CurrentStationIndex = nearestStationIndex;
+ int pastStationIndex = GetPastStationIndex(StaLocationInfo, nearestStationIndex);
+ int nextStationIndex = GetNextStationIndex(StaLocationInfo, nearestStationIndex);
// 次の駅よりも前の駅の方が近い場合、おそらく前の駅からこの駅に向かっているところである
- if (distanceArray[nearestStationIndex - 1] < distanceArray[nearestStationIndex + 1])
+ if (distanceArray[pastStationIndex] < distanceArray[nextStationIndex])
{
- CurrentStationIndex = nearestStationIndex - 1;
+ CurrentStationIndex = pastStationIndex;
}
}
}
@@ -134,19 +194,22 @@ public void SetCurrentLocation(double lon_deg, double lat_deg)
if (IsRunningToNextStation)
{
- StaLocationInfo nextStation = StaLocationInfo[CurrentStationIndex + 1];
+ // LastStationであれば、RunningToNextStationはfalseであるはずである。
+ // -> 次の駅は必ず存在する
+ int nextStationIndex = GetNextStationIndex(StaLocationInfo, CurrentStationIndex);
+ StaLocationInfo nextStation = StaLocationInfo[nextStationIndex];
double distanceToNextStationAverage = GetDistanceToStationAverage(nextStation, lon_deg, lat_deg);
if (!double.IsNaN(distanceToNextStationAverage)
&& Utils.IsNearBy(nextStation, distanceToNextStationAverage))
{
DistanceHistoryQueue.Clear();
- CurrentStationIndex++;
+ CurrentStationIndex = nextStationIndex;
IsRunningToNextStation = false;
LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
}
}
- else if (CurrentStationIndex < StaLocationInfo.Length - 1)
+ else if (0 <= GetNextStationIndex(StaLocationInfo, CurrentStationIndex))
{
StaLocationInfo currentStation = StaLocationInfo[CurrentStationIndex];
diff --git a/TRViS.LocationService/StaLocationInfo.cs b/TRViS.LocationService/StaLocationInfo.cs
index 23a9b164..4ffe2305 100644
--- a/TRViS.LocationService/StaLocationInfo.cs
+++ b/TRViS.LocationService/StaLocationInfo.cs
@@ -2,23 +2,54 @@ namespace TRViS.Services;
public interface ILocationLonLat_deg
{
+ bool HasLonLatLocation { get; }
double Location_lon_deg { get; }
double Location_lat_deg { get; }
}
public class StaLocationInfo : ILocationLonLat_deg
{
+ public const double DefaultNearbyRadius_m = 200;
+
+ public bool HasLonLatLocation { get; }
public double Location_m { get; }
public double Location_lon_deg { get; }
public double Location_lat_deg { get; }
public double NearbyRadius_m { get; }
- public StaLocationInfo(double location_m, double location_lon_deg, double location_lat_deg, double nearbyRadius_m)
+ public StaLocationInfo(
+ double location_m,
+ double? location_lon_deg,
+ double? location_lat_deg,
+ double? nearbyRadius_m
+ )
{
Location_m = location_m;
- Location_lon_deg = location_lon_deg;
- Location_lat_deg = location_lat_deg;
- NearbyRadius_m = nearbyRadius_m;
+ NearbyRadius_m = nearbyRadius_m ?? DefaultNearbyRadius_m;
+ if (location_lon_deg is double lon && location_lat_deg is double lat)
+ {
+ Location_lon_deg = lon;
+ Location_lat_deg = lat;
+ HasLonLatLocation = true;
+ }
+ else
+ {
+ Location_lon_deg = 0;
+ Location_lat_deg = 0;
+ HasLonLatLocation = false;
+ }
+ }
+
+ public StaLocationInfo(
+ double location_m,
+ double? nearbyRadius_m
+ ) : this(
+ location_m,
+ null,
+ null,
+ nearbyRadius_m
+ )
+ {
}
public bool Equals(StaLocationInfo? other)
From f9c06f0bbd58615e5fe5239f1c115b12f94a55db Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 02:02:08 +0900
Subject: [PATCH 13/29] add ref to LocationService project
---
TRViS/TRViS.csproj | 1 +
1 file changed, 1 insertion(+)
diff --git a/TRViS/TRViS.csproj b/TRViS/TRViS.csproj
index ce007f04..5782321f 100644
--- a/TRViS/TRViS.csproj
+++ b/TRViS/TRViS.csproj
@@ -79,6 +79,7 @@
+
From bdff465b7867f3de18aff1427f48b714f7e2a425 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 02:03:04 +0900
Subject: [PATCH 14/29] =?UTF-8?q?LocationService=E3=81=AE=E5=88=A4?=
=?UTF-8?q?=E5=AE=9A=E3=83=AD=E3=82=B8=E3=83=83=E3=82=AF=E3=82=92=E3=83=96?=
=?UTF-8?q?=E3=83=AD=E3=82=B8=E3=82=A7=E3=82=AF=E3=83=88=E5=88=86=E9=9B=A2?=
=?UTF-8?q?=E3=81=97=E3=81=9F=E3=81=9F=E3=82=81=E3=80=81=E6=9C=AC=E4=BD=93?=
=?UTF-8?q?=E5=81=B4=E3=81=AB=E3=81=9D=E3=82=8C=E3=82=92=E5=8F=8D=E6=98=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/PageHeader.cs | 6 +
TRViS/DTAC/VerticalStylePage.xaml.cs | 9 +-
TRViS/DTAC/VerticalTimetableView.Init.cs | 3 +-
.../VerticalTimetableView.LocationService.cs | 87 +++----
TRViS/DTAC/VerticalTimetableView.cs | 4 +-
TRViS/Services/LocationService.cs | 219 +++++++-----------
6 files changed, 128 insertions(+), 200 deletions(-)
diff --git a/TRViS/DTAC/PageHeader.cs b/TRViS/DTAC/PageHeader.cs
index 42339c0b..be1278cd 100644
--- a/TRViS/DTAC/PageHeader.cs
+++ b/TRViS/DTAC/PageHeader.cs
@@ -45,6 +45,12 @@ public string AffectDateLabelText
#region Start / End Run Button
readonly StartEndRunButton StartEndRunButton = new();
+ public event EventHandler>? IsRunningChanged
+ {
+ add => StartEndRunButton.IsCheckedChanged += value;
+ remove => StartEndRunButton.IsCheckedChanged -= value;
+ }
+
partial void OnIsRunningChanged(bool newValue)
{
logger.Info("IsRunning: {0}", newValue);
diff --git a/TRViS/DTAC/VerticalStylePage.xaml.cs b/TRViS/DTAC/VerticalStylePage.xaml.cs
index 5b3e0fec..77c4bf8b 100644
--- a/TRViS/DTAC/VerticalStylePage.xaml.cs
+++ b/TRViS/DTAC/VerticalStylePage.xaml.cs
@@ -102,11 +102,10 @@ public VerticalStylePage()
TimetableView.IgnoreSafeArea = false;
TimetableView.VerticalOptions = LayoutOptions.Start;
- TimetableView.SetBinding(VerticalTimetableView.IsRunStartedProperty, new Binding()
- {
- Source = this.PageHeaderArea,
- Path = nameof(PageHeader.IsRunning)
- });
+ PageHeaderArea.IsRunningChanged += (_, e) => {
+ logger.Info("IsRunningChanged: {0}", e.NewValue);
+ TimetableView.IsRunStarted = e.NewValue;
+ };
TimetableView.ScrollRequested += VerticalTimetableView_ScrollRequested;
diff --git a/TRViS/DTAC/VerticalTimetableView.Init.cs b/TRViS/DTAC/VerticalTimetableView.Init.cs
index c28f4fde..504798ac 100644
--- a/TRViS/DTAC/VerticalTimetableView.Init.cs
+++ b/TRViS/DTAC/VerticalTimetableView.Init.cs
@@ -2,6 +2,7 @@
using TRViS.Controls;
using TRViS.IO.Models;
+using TRViS.Services;
namespace TRViS.DTAC;
@@ -44,7 +45,7 @@ public VerticalTimetableView()
ColumnDefinitions = DTACElementStyles.TimetableColumnWidthCollection;
Grid.SetColumnSpan(CurrentLocationLine, 8);
- LocationService.IsNearbyChanged += LocationService_IsNearbyChanged;
+ LocationService.LocationStateChanged += LocationService_LocationStateChanged;
LocationService.ExceptionThrown += (s, e) =>
{
MainThread.BeginInvokeOnMainThread(() => Shell.Current.DisplayAlert("Location Service Error", e.ToString(), "OK"));
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 6cc19388..7f4ed3bc 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -14,81 +14,46 @@ public partial class VerticalTimetableView : Grid
public event EventHandler>? IsLocationServiceEnabledChanged;
partial void OnIsLocationServiceEnabledChanged(bool newValue)
{
- if (newValue)
- {
- logger.Info("IsLocationServiceEnabled is changed to true -> set NearbyCheckInfo");
- SetNearbyCheckInfo(CurrentRunningRow);
- }
- else
- {
- logger.Info("IsLocationServiceEnabled is changed to false");
- }
+ logger.Info("IsLocationServiceEnabled is changed to {0}", newValue);
LocationService.IsEnabled = newValue;
IsLocationServiceEnabledChanged?.Invoke(this, new(!newValue, newValue));
}
- private void LocationService_IsNearbyChanged(object? sender, bool oldValue, bool newValue)
+ private void LocationService_LocationStateChanged(object? sender, LocationStateChangedEventArgs e)
{
- if (!IsRunStarted || !IsEnabled || CurrentRunningRow is null || !LocationService.IsEnabled)
+ if (!IsLocationServiceEnabled)
{
- logger.Info(
- "!IsRunStarted: {0} || "
- + "!IsEnabled: {1} || "
- + "CurrentRunningRow is null: {2} || "
- + "!LocationService.IsEnabled: {3}"
- + "-> do nothing",
- IsRunStarted,
- IsEnabled,
- CurrentRunningRow is null,
- LocationService.IsEnabled
- );
-
+ logger.Debug("IsLocationServiceEnabled is false -> Do nothing");
return;
}
-
- if (newValue)
+ if (e.NewStationIndex < 0)
{
- logger.Info("IsNearby is changed to true (= Around Current Station) -> set CurrentRunningRow to NextRunningRow({0})", NextRunningRow?.RowIndex ?? -1);
- SetCurrentRunningRow(NextRunningRow);
+ logger.Warn("e.NewStationIndex is less than 0 -> Disable LocationService");
+ IsLocationServiceEnabled = false;
+ return;
}
- else if (CurrentRunningRow is not null)
+ if (RowViewList.Count <= e.NewStationIndex)
{
- logger.Info("IsNearby is changed to false (= Running to next station)"
- + " -> set CurrentRunningRow.LocationState to RunningToNextStation and Update NearbyCheckInfo");
- CurrentRunningRow.LocationState = VerticalTimetableRow.LocationStates.RunningToNextStation;
-
- SetNearbyCheckInfo(NextRunningRow);
+ logger.Warn("RowViewList.Count is less than e.NewStationIndex -> Disable LocationService");
+ IsLocationServiceEnabled = false;
+ return;
}
- }
-
- private void SetNearbyCheckInfo(VerticalTimetableRow? nextRunningRow)
- {
- if (nextRunningRow?.RowData is TimetableRow nextRowData)
- {
- LocationService.NearbyCenter
- = nextRowData.Location is LocationInfo
- {
- Latitude_deg: double lat,
- Longitude_deg: double lon
- }
- ? new Location(lat, lon)
- : null;
-
- logger.Info(
- "Set NearbyCenter to {0}, Radius: {1}, (Row[{2}].StationName: {3})",
- LocationService.NearbyCenter,
- nextRowData.Location.OnStationDetectRadius_m,
- nextRunningRow.RowIndex,
- nextRowData.StationName
- );
- LocationService.NearbyRadius_m = nextRowData.Location.OnStationDetectRadius_m ?? LocationService.DefaultNearbyRadius_m;
- }
- else
- {
- logger.Debug("nextRunningRow is null or nextRunningRow.RowData is null -> do nothing");
- }
+ logger.Info("LocationStateChanged: [{0}](State:{1}) Rows[{2}](IsRunningToNextStation: {3})",
+ CurrentRunningRowIndex,
+ CurrentRunningRow?.LocationState,
+ e.NewStationIndex,
+ e.IsRunningToNextStation
+ );
+ if (CurrentRunningRow is not null)
+ CurrentRunningRow.LocationState = VerticalTimetableRow.LocationStates.Undefined;
+ UpdateCurrentRunningLocationVisualizer(RowViewList[e.NewStationIndex], e.IsRunningToNextStation
+ ? VerticalTimetableRow.LocationStates.RunningToNextStation
+ : VerticalTimetableRow.LocationStates.AroundThisStation
+ );
+ CurrentRunningRow = RowViewList[e.NewStationIndex];
+ CurrentRunningRowIndex = e.NewStationIndex;
}
public void SetCurrentRunningRow(int index)
diff --git a/TRViS/DTAC/VerticalTimetableView.cs b/TRViS/DTAC/VerticalTimetableView.cs
index b0260292..a9711ac9 100644
--- a/TRViS/DTAC/VerticalTimetableView.cs
+++ b/TRViS/DTAC/VerticalTimetableView.cs
@@ -27,6 +27,8 @@ partial void OnSelectedTrainDataChanged(TrainData? newValue)
{
logger.Trace("SelectedTrainData is changed to {0}", newValue?.TrainNumber);
SetRowViews(newValue, newValue?.Rows);
+ IsRunStarted = false;
+ LocationService.SetTimetableRows(newValue?.Rows);
}
partial void OnIsBusyChanged()
@@ -81,7 +83,7 @@ private void RowTapped(object? sender, EventArgs e)
if (!IsRunStarted || !IsEnabled)
{
- logger.Debug("IsRunStarted is false or IsEnabled is false -> do nothing");
+ logger.Debug("IsRunStarted({0}) is false or IsEnabled({1}) is false -> do nothing", IsRunStarted, IsEnabled);
return;
}
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index d8f119a2..80dcee64 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -1,6 +1,7 @@
using CommunityToolkit.Mvvm.ComponentModel;
using TRViS.Controls;
+using TRViS.IO.Models;
using TRViS.MyAppCustomizables;
using TRViS.ViewModels;
@@ -23,95 +24,30 @@ public partial class LocationService : ObservableObject, IDisposable
[ObservableProperty]
bool _IsEnabled;
- [ObservableProperty]
- Location? _NearbyCenter;
-
- [ObservableProperty]
- double _NearbyRadius_m = DefaultNearbyRadius_m;
- public const double DefaultNearbyRadius_m = 200;
+ readonly LonLatLocationService LonLatLocationService;
- bool _IsNearby;
- public bool IsNearby
+ public event EventHandler LocationStateChanged
{
- get => _IsNearby;
- private set
- {
- if (_IsNearby == value)
- return;
-
- logger.Debug("IsNearby is changed to {0}", value);
- this.OnPropertyChanging(nameof(IsNearby));
- _IsNearby = value;
- this.OnPropertyChanged(nameof(IsNearby));
- IsNearbyChanged?.Invoke(this, !value, value);
- }
+ add => LonLatLocationService.LocationStateChanged += value;
+ remove => LonLatLocationService.LocationStateChanged -= value;
}
- Location? _LastLocation;
- public Location? LastLocation
- {
- get => _LastLocation;
-
- private set
- {
- if (
- value == _LastLocation
- || (_LastLocation is not null && value?.Equals(_LastLocation) != false)
- )
- {
- logger.Trace("LastLocation is already {0}, so skipping...", value);
- return;
- }
-
- logger.Info("LastLocation is changing to {0}", value);
- this.OnPropertyChanging(nameof(LastLocation));
-
- setIsNearby(value);
+ public const double DefaultNearbyRadius_m = 200;
- Location? lastLocation = _LastLocation;
- _LastLocation = value;
+ public event EventHandler? ExceptionThrown;
- this.OnPropertyChanged(nameof(LastLocation));
- LastLocationChanged?.Invoke(this, lastLocation, value);
- }
- }
+ CancellationTokenSource? gpsCancelation;
- void setIsNearby(in Location? location)
+ public LocationService()
{
- if (NearbyCenter is null || location is null)
- {
- logger.Trace("NearbyCenter is null or location is null -> do nothing");
- return;
- }
-
- double distance = location.CalculateDistance(NearbyCenter, DistanceUnits.Kilometers) * 1000;
+ logger.Trace("Creating...");
- bool isNearby = distance <= NearbyRadius_m;
- logger.Info("IsNearby: {0} (= distance: {1} <= NearbyRadius_m: {2})", isNearby, distance, NearbyRadius_m);
- logger.Debug("Station Lon:{4:F5}, Lat:{5:F5}\tCurrent Lon:{0:F5}, Lat:{1:F5}",
- NearbyCenter.Longitude,
- NearbyCenter.Latitude,
- location.Longitude,
- location.Latitude
- );
+ IsEnabled = false;
+ LonLatLocationService = new();
- LogView.Add(
- LogView.Priority.Info,
-
- $"setIsNearby() Lon:{location.Longitude:F5}, Lat:{location.Latitude:F5}"
- + $" (Distance:{distance:F2}m/{NearbyRadius_m:F2}m from Lon:{NearbyCenter.Longitude:F5}, Lat:{NearbyCenter.Latitude:F5} -> IsNearBy:{isNearby})"
- );
- IsNearby = isNearby;
+ logger.Debug("LocationService is created");
}
- public event EventHandler? ExceptionThrown;
- public event ValueChangedEventHandler? IsNearbyChanged;
- public event ValueChangedEventHandler? LastLocationChanged;
-
- CancellationTokenSource? gpsCancelation;
-
- private bool disposedValue;
-
partial void OnIsEnabledChanged(bool newValue)
{
// GPS停止
@@ -127,17 +63,12 @@ partial void OnIsEnabledChanged(bool newValue)
}
}
- partial void OnNearbyCenterChanged(Location? newValue)
+ public void SetTimetableRows(TimetableRow[]? timetableRows)
{
- if (LastLocation is null || newValue is null)
- {
- logger.Trace("LastLocation is null or newValue is null -> do nothing");
- return;
- }
+ logger.Trace("Setting TimetableRows...");
- logger.Info("NearbyCenter is changed to {0}", newValue);
- IsNearby = false;
- setIsNearby(LastLocation);
+ IsEnabled = false;
+ LonLatLocationService.StaLocationInfo = timetableRows?.Select(v => new StaLocationInfo(v.Location.Location_m, v.Location.Longitude_deg, v.Location.Latitude_deg, v.Location.OnStationDetectRadius_m)).ToArray();
}
static EasterEggPageViewModel EasterEggPageViewModel { get; } = InstanceManager.EasterEggPageViewModel;
@@ -171,69 +102,93 @@ public Task StartGPS()
}
gpsCancelation = new CancellationTokenSource();
- CancellationToken token = gpsCancelation.Token;
- LastLocation = null;
- _IsNearby = true;
- return Task.Run(async () =>
- {
- // ref: https://docs.microsoft.com/en-us/dotnet/maui/platform-integration/device/geolocation
- // accuracy: 30m - 500m
- GeolocationRequest req = new(GeolocationAccuracy.Default, Interval);
- logger.Info("Starting Location Service... (Interval: {0})", Interval);
-
- LogView.Add("Location Service Starting...");
- while (!token.IsCancellationRequested)
- {
- logger.Trace("Location Service Loop");
- TimeSpan timeout = Interval;
- req.Timeout = timeout;
-
- await Task.WhenAll(new Task[]
- {
- CheckAndNotifyCurrentLocation(req, token),
- Task.Delay(timeout, token),
- });
- }
-
- logger.Info("Location Service Ended");
- LogView.Add("Location Service Ended");
- }, token);
+ return Task.Run(PositioningTask, gpsCancelation.Token);
}
- async Task CheckAndNotifyCurrentLocation(GeolocationRequest req, CancellationToken token)
+ async Task PositioningTask()
{
- logger.Trace("Starting...");
+ // ref: https://docs.microsoft.com/en-us/dotnet/maui/platform-integration/device/geolocation
+ // accuracy: 30m - 500m
+ GeolocationRequest req = new(GeolocationAccuracy.Default, Interval);
+ logger.Info("Starting Location Service... (Interval: {0})", Interval);
- try
+ if (gpsCancelation?.Token is not CancellationToken token)
{
- Location? loc = await Geolocation.Default.GetLocationAsync(req, token);
+ logger.Warn("gpsCancelation is null -> do nothing");
+ return;
+ }
+
+ LogView.Add("Location Service Starting...");
+ bool isFirst = true;
+ while (!token.IsCancellationRequested)
+ {
+ logger.Trace("Location Service Loop");
+ DateTime executeStartTime = DateTime.Now;
+ TimeSpan timeout = Interval;
+ req.Timeout = timeout;
+
+ Location? loc = null;
+
+ try
+ {
+ loc = await Geolocation.Default.GetLocationAsync(req, token);
+ }
+ catch (Exception ex)
+ {
+ logger.Error(ex, "GetLocationAsync failed");
+ IsEnabled = false;
+ gpsCancelation?.Cancel();
+ LogView.Add(LogView.Priority.Error, "GetLocationAsync failed:" + ex.ToString());
+
+ if (ExceptionThrown is null)
+ throw;
+ else
+ ExceptionThrown.Invoke(this, ex);
+ }
if (loc is not null)
{
- logger.Debug("CurrentLocation is {0}", loc);
- LastLocation = loc;
+ if (isFirst)
+ {
+ logger.Info("Location Service First Positioning");
+ LogView.Add("Location Service Started");
+ isFirst = false;
+ LonLatLocationService.ForceSetLocationInfo(loc.Longitude, loc.Latitude);
+ }
+ else
+ {
+ LonLatLocationService.SetCurrentLocation(loc.Longitude, loc.Latitude);
+ }
+ logger.Trace("Location Service Positioning Success (lon: {0}, lat: {1})", loc.Longitude, loc.Latitude);
}
else
{
- logger.Warn("CurrentLocation is null");
- LogView.Add("CurrentLocation is UNKNOWN (value was null)");
+ logger.Warn("Location Service Positioning Failed");
+ LogView.Add("Location Service Positioning Failed");
}
- }
- catch (Exception ex)
- {
- logger.Error(ex, "GetLocationAsync failed");
- IsEnabled = false;
- gpsCancelation?.Cancel();
- System.Diagnostics.Debug.WriteLine(ex);
- LogView.Add(LogView.Priority.Error, "GetLocationAsync failed:" + ex.ToString());
- if (ExceptionThrown is null)
- throw;
+ if (token.IsCancellationRequested)
+ {
+ logger.Debug("gpsCancelation is requested -> break");
+ break;
+ }
+ DateTime executeEndTime = DateTime.Now;
+ if (executeEndTime < (executeStartTime + timeout))
+ {
+ logger.Trace("Location Service Positioning Took {0}", executeEndTime - executeStartTime);
+ await Task.Delay(timeout - (executeEndTime - executeStartTime), token);
+ }
else
- ExceptionThrown.Invoke(this, ex);
+ {
+ logger.Warn("Location Service Positioning Took Too Long (time: {0})", executeEndTime - executeStartTime);
+ }
}
+
+ logger.Info("Location Service Ended");
+ LogView.Add("Location Service Ended");
}
+ private bool disposedValue;
protected virtual void Dispose(bool disposing)
{
From 718461be8bce869bb58b7ce5fe80e66cdeb06df1 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 22:34:31 +0900
Subject: [PATCH 15/29] =?UTF-8?q?=E3=83=A1=E3=82=A4=E3=83=B3=E3=82=B9?=
=?UTF-8?q?=E3=83=AC=E3=83=83=E3=83=89=E4=BB=A5=E5=A4=96=E3=81=A7UI?=
=?UTF-8?q?=E3=82=92=E8=A7=A6=E3=81=A3=E3=81=A6=E3=81=84=E3=81=9F=E3=83=9F?=
=?UTF-8?q?=E3=82=B9=E3=82=92=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/LocationServiceButton.cs | 7 +++++++
TRViS/DTAC/VerticalTimetableView.LocationService.cs | 7 +++++++
2 files changed, 14 insertions(+)
diff --git a/TRViS/DTAC/LocationServiceButton.cs b/TRViS/DTAC/LocationServiceButton.cs
index c99e69e7..f502a001 100644
--- a/TRViS/DTAC/LocationServiceButton.cs
+++ b/TRViS/DTAC/LocationServiceButton.cs
@@ -131,6 +131,13 @@ void OnIsCheckedChanged(object? sender, ValueChangedEventArgs e)
void OnIsCheckedChanged(bool isLocationServiceEnabled)
{
+ if (!MainThread.IsMainThread)
+ {
+ logger.Debug("MainThread is not current thread -> invoke OnIsCheckedChanged on MainThread");
+ MainThread.BeginInvokeOnMainThread(() => OnIsCheckedChanged(isLocationServiceEnabled));
+ return;
+ }
+
if (isLocationServiceEnabled)
{
logger.Info("Location Service is enabled");
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 7f4ed3bc..a8cb3f60 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -124,6 +124,13 @@ void SetCurrentRunningRow(int index, VerticalTimetableRow? value)
void UpdateCurrentRunningLocationVisualizer(VerticalTimetableRow row, VerticalTimetableRow.LocationStates states)
{
+ if (!MainThread.IsMainThread)
+ {
+ logger.Debug("MainThread is not current thread -> invoke UpdateCurrentRunningLocationVisualizer on MainThread");
+ MainThread.BeginInvokeOnMainThread(() => UpdateCurrentRunningLocationVisualizer(row, states));
+ return;
+ }
+
logger.Info("UpdateCurrentRunningLocationVisualizer: {0} ... {1}", row.RowIndex, states);
row.LocationState = states;
From 4eeba60dc5878d1c647181556013bb8b1308ef5e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 22:34:49 +0900
Subject: [PATCH 16/29] =?UTF-8?q?=E4=BD=8D=E7=BD=AE=E6=83=85=E5=A0=B1?=
=?UTF-8?q?=E3=81=AE=E3=83=91=E3=83=BC=E3=83=9F=E3=83=83=E3=82=B7=E3=83=A7?=
=?UTF-8?q?=E3=83=B3=E3=82=92=E6=AF=8E=E5=BA=A6=E7=A2=BA=E8=AA=8D=E3=81=99?=
=?UTF-8?q?=E3=82=8B=E3=82=88=E3=81=86=E3=81=AB=E3=81=97=E3=81=9F?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/Services/LocationService.cs | 38 +++++++++++++++++++++++++++++++
1 file changed, 38 insertions(+)
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index 80dcee64..cae45c3d 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -106,6 +106,7 @@ public Task StartGPS()
return Task.Run(PositioningTask, gpsCancelation.Token);
}
+ static Permissions.LocationWhenInUse LocationWhenInUsePermission { get; } = new();
async Task PositioningTask()
{
// ref: https://docs.microsoft.com/en-us/dotnet/maui/platform-integration/device/geolocation
@@ -128,6 +129,42 @@ async Task PositioningTask()
TimeSpan timeout = Interval;
req.Timeout = timeout;
+ PermissionStatus permissionStatus = await LocationWhenInUsePermission.CheckStatusAsync();
+ logger.Trace("Location Service Current Permission Status: {0}", permissionStatus);
+ if (permissionStatus != PermissionStatus.Granted)
+ {
+ try
+ {
+
+ permissionStatus = await MainThread.InvokeOnMainThreadAsync(LocationWhenInUsePermission.RequestAsync);
+ logger.Trace("Location Service Requested Permission Status: {0}", permissionStatus);
+ }
+ catch (Exception ex)
+ {
+ logger.Error(ex, "Location Service Request Permission Failed");
+ IsEnabled = false;
+ gpsCancelation?.Cancel();
+ LogView.Add(LogView.Priority.Error, "Location Service Request Permission Failed:" + ex.ToString());
+
+ if (ExceptionThrown is null)
+ throw;
+ else
+ ExceptionThrown.Invoke(this, ex);
+ return;
+ }
+ }
+ switch (permissionStatus)
+ {
+ case PermissionStatus.Disabled:
+ case PermissionStatus.Denied:
+ case PermissionStatus.Unknown:
+ logger.Error("Location Service Permission Disabled, Denied or Unknown state");
+ IsEnabled = false;
+ gpsCancelation?.Cancel();
+ ExceptionThrown?.Invoke(this, new Exception("Location Service Permission Disabled, Denied or Unknown state"));
+ return;
+ }
+ logger.Trace("Location Service Permission Granted");
Location? loc = null;
try
@@ -145,6 +182,7 @@ async Task PositioningTask()
throw;
else
ExceptionThrown.Invoke(this, ex);
+ return;
}
if (loc is not null)
From 6971347e61cd6aca8722d0d9d36b168e818b37ae Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Thu, 16 Nov 2023 22:35:29 +0900
Subject: [PATCH 17/29] =?UTF-8?q?=E5=88=97=E8=BB=8A=E3=83=87=E3=83=BC?=
=?UTF-8?q?=E3=82=BF=E5=A4=89=E6=9B=B4=E5=BE=8C=E3=81=AB=E3=83=9C=E3=82=BF?=
=?UTF-8?q?=E3=83=B3=E3=81=AE=E3=80=8C=E9=81=8B=E8=BB=A2=E9=96=8B=E5=A7=8B?=
=?UTF-8?q?=E3=80=8D=E3=83=9C=E3=82=BF=E3=83=B3=E3=82=92=E3=81=8D=E3=81=A1?=
=?UTF-8?q?=E3=82=93=E3=81=A8=E6=88=BB=E3=81=99=E3=82=88=E3=81=86=E3=81=AB?=
=?UTF-8?q?=E3=81=97=E3=81=9F?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/VerticalStylePage.xaml.cs | 1 +
TRViS/DTAC/VerticalTimetableView.cs | 1 +
2 files changed, 2 insertions(+)
diff --git a/TRViS/DTAC/VerticalStylePage.xaml.cs b/TRViS/DTAC/VerticalStylePage.xaml.cs
index 77c4bf8b..a8f9c950 100644
--- a/TRViS/DTAC/VerticalStylePage.xaml.cs
+++ b/TRViS/DTAC/VerticalStylePage.xaml.cs
@@ -154,6 +154,7 @@ partial void OnSelectedTrainDataChanged(TrainData? newValue)
logger.Info("SelectedTrainDataChanged: {0}", newValue);
BindingContext = newValue;
TimetableView.SelectedTrainData = newValue;
+ PageHeaderArea.IsRunning = false;
TrainInfo_BeforeDepartureArea.TrainInfoText = newValue?.TrainInfo ?? "";
TrainInfo_BeforeDepartureArea.BeforeDepartureText = newValue?.BeforeDeparture ?? "";
diff --git a/TRViS/DTAC/VerticalTimetableView.cs b/TRViS/DTAC/VerticalTimetableView.cs
index a9711ac9..f1e8464a 100644
--- a/TRViS/DTAC/VerticalTimetableView.cs
+++ b/TRViS/DTAC/VerticalTimetableView.cs
@@ -29,6 +29,7 @@ partial void OnSelectedTrainDataChanged(TrainData? newValue)
SetRowViews(newValue, newValue?.Rows);
IsRunStarted = false;
LocationService.SetTimetableRows(newValue?.Rows);
+ ScrollRequested?.Invoke(this, new(0));
}
partial void OnIsBusyChanged()
From 85988c268bdbfe9c0e004e990d17e81d475c567c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 11:01:00 +0900
Subject: [PATCH 18/29] =?UTF-8?q?ForceSetLocationInfo=E3=81=AE=E3=83=86?=
=?UTF-8?q?=E3=82=B9=E3=83=88=E3=82=92=E8=BF=BD=E5=8A=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.../LonLatLocationService.Tests.cs | 96 +++++++++++++++++++
1 file changed, 96 insertions(+)
diff --git a/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
index 5f973d3f..6bcef3d3 100644
--- a/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
+++ b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
@@ -99,4 +99,100 @@ public void MoveTest()
Assert.That(service.IsRunningToNextStation, Is.False);
});
}
+
+ [Test]
+ public void ForceSetPositionTest_NearStation()
+ {
+ StaLocationInfo sta1 = new(0, 0, 0, 200);
+ StaLocationInfo sta2 = new(1, 1, 1, 200);
+ StaLocationInfo sta3 = new(2, 2, 2, 200);
+ LonLatLocationService service = new()
+ {
+ StaLocationInfo =
+ [
+ sta1,
+ sta2,
+ sta3,
+ ]
+ };
+
+ // 初期状態は、駅0にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.ForceSetLocationInfo(1, 1);
+
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+ }
+
+ [Test]
+ public void ForceSetPositionTest_RunningToNextStation1()
+ {
+ StaLocationInfo sta1 = new(0, 0, 0, 200);
+ StaLocationInfo sta2 = new(1, 1, 1, 200);
+ StaLocationInfo sta3 = new(2, 2, 2, 200);
+ LonLatLocationService service = new()
+ {
+ StaLocationInfo =
+ [
+ sta1,
+ sta2,
+ sta3,
+ ]
+ };
+
+ // 初期状態は、駅0にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.ForceSetLocationInfo(0.5, 0.5);
+
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+ }
+
+ [Test]
+ public void ForceSetPositionTest_RunningToNextStation2()
+ {
+ StaLocationInfo sta1 = new(0, 0, 0, 200);
+ StaLocationInfo sta2 = new(1, 1, 1, 200);
+ StaLocationInfo sta3 = new(2, 2, 2, 200);
+ LonLatLocationService service = new()
+ {
+ StaLocationInfo =
+ [
+ sta1,
+ sta2,
+ sta3,
+ ]
+ };
+
+ // 初期状態は、駅0にいる
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
+
+ service.ForceSetLocationInfo(1.5, 1.5);
+
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+ }
}
From b238ff27158728cb2067977a745b43655a46bd5b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 11:09:01 +0900
Subject: [PATCH 19/29] =?UTF-8?q?=E3=83=AD=E3=82=B0=E5=87=BA=E5=8A=9B?=
=?UTF-8?q?=E3=82=92=E8=BF=BD=E5=8A=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/Services/LocationService.cs | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index cae45c3d..7663b1ad 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -45,6 +45,11 @@ public LocationService()
IsEnabled = false;
LonLatLocationService = new();
+ LocationStateChanged += (sender, e) =>
+ {
+ LogView.Add($"LocationStateChanged: Station[{e.NewStationIndex}]@({LonLatLocationService.StaLocationInfo?[e.NewStationIndex].Location_lon_deg}, {LonLatLocationService.StaLocationInfo?[e.NewStationIndex].Location_lat_deg} & Radius:{LonLatLocationService.StaLocationInfo?[e.NewStationIndex].NearbyRadius_m}) IsRunningToNextStation:{e.IsRunningToNextStation}");
+ };
+
logger.Debug("LocationService is created");
}
@@ -190,13 +195,14 @@ async Task PositioningTask()
if (isFirst)
{
logger.Info("Location Service First Positioning");
- LogView.Add("Location Service Started");
+ LogView.Add($"Location Service Started with lonlat: ({loc.Longitude}, {loc.Latitude})");
isFirst = false;
LonLatLocationService.ForceSetLocationInfo(loc.Longitude, loc.Latitude);
}
else
{
LonLatLocationService.SetCurrentLocation(loc.Longitude, loc.Latitude);
+ LogView.Add($"lonlat: ({loc.Longitude}, {loc.Latitude})");
}
logger.Trace("Location Service Positioning Success (lon: {0}, lat: {1})", loc.Longitude, loc.Latitude);
}
From ede799685b7120e9777e312748eeb4924a626c4d Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 12:56:10 +0900
Subject: [PATCH 20/29] =?UTF-8?q?=E3=83=AD=E3=82=B0=E5=87=BA=E5=8A=9B?=
=?UTF-8?q?=E3=81=A7NullRef=E3=81=8C=E8=B5=B7=E3=81=8D=E3=82=8B=E3=83=90?=
=?UTF-8?q?=E3=82=B0=E3=82=92=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
存在しない駅は-1を指定するという仕様を忘れてた
---
TRViS/Services/LocationService.cs | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index 6fe07b52..32b53979 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -47,7 +47,8 @@ public LocationService()
LocationStateChanged += (sender, e) =>
{
- LogView.Add($"LocationStateChanged: Station[{e.NewStationIndex}]@({LonLatLocationService.StaLocationInfo?[e.NewStationIndex].Location_lon_deg}, {LonLatLocationService.StaLocationInfo?[e.NewStationIndex].Location_lat_deg} & Radius:{LonLatLocationService.StaLocationInfo?[e.NewStationIndex].NearbyRadius_m}) IsRunningToNextStation:{e.IsRunningToNextStation}");
+ StaLocationInfo? newStaLocationInfo = LonLatLocationService.StaLocationInfo?.ElementAtOrDefault(e.NewStationIndex);
+ LogView.Add($"LocationStateChanged: Station[{e.NewStationIndex}]@({newStaLocationInfo?.Location_lon_deg}, {newStaLocationInfo?.Location_lat_deg} & Radius:{newStaLocationInfo?.NearbyRadius_m}) IsRunningToNextStation:{e.IsRunningToNextStation}");
};
logger.Debug("LocationService is created");
From 06d98ee67a14adf5a28964e17f476f71620dee3c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 12:56:27 +0900
Subject: [PATCH 21/29] =?UTF-8?q?=E9=A7=85=E3=81=8C=E9=80=B2=E3=82=80?=
=?UTF-8?q?=E3=81=A8=E3=81=8D=E3=81=ABHaptic=20Feedback=E3=82=92=E5=87=BA?=
=?UTF-8?q?=E3=81=99=E3=82=88=E3=81=86=E3=81=AB=E3=81=97=E3=81=9F?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.../VerticalTimetableView.LocationService.cs | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index a8cb3f60..87c7100c 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -122,6 +122,7 @@ void SetCurrentRunningRow(int index, VerticalTimetableRow? value)
});
}
+ static bool IsHapticEnabled { get; set; } = true;
void UpdateCurrentRunningLocationVisualizer(VerticalTimetableRow row, VerticalTimetableRow.LocationStates states)
{
if (!MainThread.IsMainThread)
@@ -147,5 +148,21 @@ is VerticalTimetableRow.LocationStates.AroundThisStation
CurrentLocationBoxView.Margin = row.LocationState
is VerticalTimetableRow.LocationStates.RunningToNextStation
? new(0, -(RowHeight.Value / 2)) : new(0);
+
+ try
+ {
+ if (IsHapticEnabled)
+ HapticFeedback.Default.Perform(HapticFeedbackType.Click);
+ }
+ catch (FeatureNotSupportedException)
+ {
+ logger.Warn("HapticFeedback is not supported");
+ IsHapticEnabled = false;
+ }
+ catch (Exception ex)
+ {
+ logger.Error(ex, "Failed to perform HapticFeedback");
+ IsHapticEnabled = false;
+ }
}
}
From 7b471a8016bf7e3eb9c6b2a8795301cd5cbb80d5 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 15:13:48 +0900
Subject: [PATCH 22/29] =?UTF-8?q?Row=E3=81=AE=E3=83=80=E3=83=96=E3=83=AB?=
=?UTF-8?q?=E3=82=BF=E3=83=83=E3=83=97=E3=81=A7=E5=BC=B7=E5=88=B6=E7=9A=84?=
=?UTF-8?q?=E3=81=AB=E7=8F=BE=E5=9C=A8=E9=A7=85=E3=82=92=E3=82=BB=E3=83=83?=
=?UTF-8?q?=E3=83=88=E3=81=A7=E3=81=8D=E3=82=8B=E3=82=88=E3=81=86=E3=81=AB?=
=?UTF-8?q?=E3=81=97=E3=81=9F?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS.LocationService/ILocationService.cs | 2 ++
.../LonLatLocationService.cs | 28 +++++++++++++++++++
TRViS/DTAC/VerticalTimetableView.cs | 9 ++++--
TRViS/Services/LocationService.cs | 13 +++++++++
4 files changed, 49 insertions(+), 3 deletions(-)
diff --git a/TRViS.LocationService/ILocationService.cs b/TRViS.LocationService/ILocationService.cs
index 921bfb5f..491e41bc 100644
--- a/TRViS.LocationService/ILocationService.cs
+++ b/TRViS.LocationService/ILocationService.cs
@@ -49,4 +49,6 @@ public interface ILocationService
bool IsRunningToNextStation { get; }
void ResetLocationInfo();
+
+ void ForceSetLocationInfo(int stationIndex, bool isRunningToNextStation);
}
diff --git a/TRViS.LocationService/LonLatLocationService.cs b/TRViS.LocationService/LonLatLocationService.cs
index 899d72de..d17a588f 100644
--- a/TRViS.LocationService/LonLatLocationService.cs
+++ b/TRViS.LocationService/LonLatLocationService.cs
@@ -173,6 +173,34 @@ public void ForceSetLocationInfo(double lon_deg, double lat_deg)
LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
}
+ public void ForceSetLocationInfo(int stationIndex, bool isRunningToNextStation)
+ {
+ ResetLocationInfo(false);
+ if (StaLocationInfo is null)
+ {
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ return;
+ }
+
+ if (stationIndex < 0 || StaLocationInfo.Length <= stationIndex)
+ {
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ return;
+ }
+
+ bool isNextStationAvailable = 0 <= GetNextStationIndex(StaLocationInfo, stationIndex);
+ // 現在駅に位置情報がセットされていない場合、「IsNearby」判定ができないため、次の駅に走行中であると仮定する
+ // 但し、次の駅が存在しない場合は、次の駅のIsNearby判定ができないため、指定の駅に停車中であると仮定する
+ IsRunningToNextStation = isNextStationAvailable && isRunningToNextStation;
+ if (!StaLocationInfo[stationIndex].HasLonLatLocation)
+ {
+ IsRunningToNextStation = isNextStationAvailable;
+ }
+
+ CurrentStationIndex = stationIndex;
+ LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
+ }
+
double GetDistanceToStationAverage(in StaLocationInfo staLocationInfo, double lon_deg, double lat_deg)
{
double distanceToStation = Utils.CalculateDistance_m(lon_deg, lat_deg, staLocationInfo.Location_lon_deg, staLocationInfo.Location_lat_deg);
diff --git a/TRViS/DTAC/VerticalTimetableView.cs b/TRViS/DTAC/VerticalTimetableView.cs
index 7a893c86..b2a66de7 100644
--- a/TRViS/DTAC/VerticalTimetableView.cs
+++ b/TRViS/DTAC/VerticalTimetableView.cs
@@ -107,10 +107,13 @@ private void RowTapped(object? sender, EventArgs e)
logger.Trace("LocationService is not enabled");
}
- if (IsLocationServiceEnabled)
- logger.Info("Location Service disabled because of double tapping");
_lastTappInfo = null;
- IsLocationServiceEnabled = false;
+ if (IsLocationServiceEnabled)
+ {
+ logger.Info("New LocationInfo is set because of double tapping (row:{0})", row.RowIndex);
+ LocationService.ForceSetLocationInfo(row.RowIndex, false);
+ return;
+ }
logger.Info("Tapped {0} -> set CurrentRunningRow to {0}", row.RowIndex);
switch (row.LocationState)
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index 32b53979..803f5b14 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -112,6 +112,19 @@ public Task StartGPS()
return Task.Run(PositioningTask, gpsCancelation.Token);
}
+ public void ForceSetLocationInfo(int row, bool isRunningToNextStation)
+ {
+ if (!IsEnabled)
+ {
+ logger.Debug("IsEnabled is false -> do nothing");
+ return;
+ }
+
+ logger.Debug("ForceSetLocationInfo({0}, {1})", row, isRunningToNextStation);
+ LonLatLocationService.ForceSetLocationInfo(row, isRunningToNextStation);
+ logger.Debug("Done");
+ }
+
static Permissions.LocationWhenInUse LocationWhenInUsePermission { get; } = new();
async Task PositioningTask()
{
From 4c9f153600e60674309c61de38e5ef0b0f6c7bf0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 15:30:07 +0900
Subject: [PATCH 23/29] =?UTF-8?q?LogView=E3=81=AB=E8=B7=9D=E9=9B=A2?=
=?UTF-8?q?=E6=83=85=E5=A0=B1=E3=82=82=E5=87=BA=E5=8A=9B=E3=81=99=E3=82=8B?=
=?UTF-8?q?=E3=82=88=E3=81=86=E3=81=AB=E3=81=97=E3=81=9F?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.../LonLatLocationService.cs | 16 ++++-
TRViS.LocationService/StaLocationInfo.cs | 68 ++++++++++++++++++-
TRViS/Services/LocationService.cs | 4 +-
3 files changed, 82 insertions(+), 6 deletions(-)
diff --git a/TRViS.LocationService/LonLatLocationService.cs b/TRViS.LocationService/LonLatLocationService.cs
index d17a588f..48ecd100 100644
--- a/TRViS.LocationService/LonLatLocationService.cs
+++ b/TRViS.LocationService/LonLatLocationService.cs
@@ -215,17 +215,26 @@ double GetDistanceToStationAverage(in StaLocationInfo staLocationInfo, double lo
return DistanceHistoryQueue.Average();
}
- public void SetCurrentLocation(double lon_deg, double lat_deg)
+ ///
+ /// 現在の位置情報を設定し、駅到着・駅出発の判定を行う。
+ /// なお、指定回数分の平均距離にて判定を行うため、即時の判定ではない。
+ ///
+ /// 現在の経度 [deg]
+ /// 現在の経度 [deg]
+ /// 判定対象の駅までの距離
+ public double SetCurrentLocation(double lon_deg, double lat_deg)
{
if (StaLocationInfo is null || CurrentStationIndex < 0 || StaLocationInfo.Length <= CurrentStationIndex)
- return;
+ return double.NaN;
+ double distance = double.NaN;
if (IsRunningToNextStation)
{
// LastStationであれば、RunningToNextStationはfalseであるはずである。
// -> 次の駅は必ず存在する
int nextStationIndex = GetNextStationIndex(StaLocationInfo, CurrentStationIndex);
StaLocationInfo nextStation = StaLocationInfo[nextStationIndex];
+ distance = Utils.CalculateDistance_m(nextStation, new LocationLonLat_deg(lon_deg, lat_deg));
double distanceToNextStationAverage = GetDistanceToStationAverage(nextStation, lon_deg, lat_deg);
if (!double.IsNaN(distanceToNextStationAverage)
@@ -241,6 +250,7 @@ public void SetCurrentLocation(double lon_deg, double lat_deg)
{
StaLocationInfo currentStation = StaLocationInfo[CurrentStationIndex];
+ distance = Utils.CalculateDistance_m(currentStation, new LocationLonLat_deg(lon_deg, lat_deg));
double distanceFromCurrentStationAverage = GetDistanceToStationAverage(currentStation, lon_deg, lat_deg);
if (!double.IsNaN(distanceFromCurrentStationAverage)
&& Utils.IsLeaved(currentStation, distanceFromCurrentStationAverage))
@@ -250,5 +260,7 @@ public void SetCurrentLocation(double lon_deg, double lat_deg)
LocationStateChanged?.Invoke(this, new(CurrentStationIndex, IsRunningToNextStation));
}
}
+
+ return distance;
}
}
diff --git a/TRViS.LocationService/StaLocationInfo.cs b/TRViS.LocationService/StaLocationInfo.cs
index 4ffe2305..7d3cab83 100644
--- a/TRViS.LocationService/StaLocationInfo.cs
+++ b/TRViS.LocationService/StaLocationInfo.cs
@@ -1,13 +1,75 @@
namespace TRViS.Services;
-public interface ILocationLonLat_deg
+public interface ILocationLonLat_deg : IEquatable
{
bool HasLonLatLocation { get; }
double Location_lon_deg { get; }
double Location_lat_deg { get; }
+
+ bool IEquatable.Equals(ILocationLonLat_deg? other)
+ {
+ if (other is null)
+ return false;
+
+ if (ReferenceEquals(this, other))
+ return true;
+
+ return
+ HasLonLatLocation == other.HasLonLatLocation
+ &&
+ Location_lon_deg == other.Location_lon_deg
+ &&
+ Location_lat_deg == other.Location_lat_deg
+ ;
+ }
}
-public class StaLocationInfo : ILocationLonLat_deg
+public class LocationLonLat_deg : ILocationLonLat_deg, IEquatable
+{
+ public bool HasLonLatLocation { get; }
+ public double Location_lon_deg { get; }
+ public double Location_lat_deg { get; }
+
+ public LocationLonLat_deg(
+ double location_lon_deg,
+ double location_lat_deg
+ )
+ {
+ Location_lon_deg = location_lon_deg;
+ Location_lat_deg = location_lat_deg;
+ HasLonLatLocation = true;
+ }
+
+ public bool Equals(LocationLonLat_deg? other)
+ {
+ if (other is null)
+ return false;
+
+ if (ReferenceEquals(this, other))
+ return true;
+
+ return
+ ((IEquatable)this).Equals(other)
+ &&
+ Location_lon_deg == other.Location_lon_deg
+ &&
+ Location_lat_deg == other.Location_lat_deg
+ ;
+ }
+
+ public override bool Equals(object obj)
+ => Equals(obj as LocationLonLat_deg);
+
+ public override int GetHashCode()
+ => HashCode.Combine(Location_lon_deg, Location_lat_deg);
+
+ public override string ToString()
+ {
+ return $"{nameof(LocationLonLat_deg)} {{ lon:{Location_lon_deg}, lat:{Location_lat_deg} }}";
+ }
+}
+
+public class StaLocationInfo : ILocationLonLat_deg, IEquatable
{
public const double DefaultNearbyRadius_m = 200;
@@ -61,6 +123,8 @@ public bool Equals(StaLocationInfo? other)
return true;
return
+ ((IEquatable)this).Equals(other)
+ &&
Location_m == other.Location_m
&&
Location_lon_deg == other.Location_lon_deg
diff --git a/TRViS/Services/LocationService.cs b/TRViS/Services/LocationService.cs
index 803f5b14..875cac61 100644
--- a/TRViS/Services/LocationService.cs
+++ b/TRViS/Services/LocationService.cs
@@ -215,8 +215,8 @@ async Task PositioningTask()
}
else
{
- LonLatLocationService.SetCurrentLocation(loc.Longitude, loc.Latitude);
- LogView.Add($"lonlat: ({loc.Longitude}, {loc.Latitude})");
+ double distance = LonLatLocationService.SetCurrentLocation(loc.Longitude, loc.Latitude);
+ LogView.Add($"lonlat: ({loc.Longitude}, {loc.Latitude}), distance: {distance}m");
}
logger.Trace("Location Service Positioning Success (lon: {0}, lat: {1})", loc.Longitude, loc.Latitude);
}
From 7e7dba601dc9befa0f435f2ffc210a4898ef7b10 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:21:50 +0900
Subject: [PATCH 24/29] =?UTF-8?q?ForceLonLat=E3=81=BE=E3=82=8F=E3=82=8A?=
=?UTF-8?q?=E3=81=AE=E3=83=86=E3=82=B9=E3=83=88=E3=82=92=E8=BF=BD=E5=8A=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
駅をセットしたあと、正常に移動できるか
---
.../LonLatLocationService.Tests.cs | 29 +++++++++++++++++++
1 file changed, 29 insertions(+)
diff --git a/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
index 6bcef3d3..63ace70e 100644
--- a/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
+++ b/TRViS.LocationService.Tests/LonLatLocationService.Tests.cs
@@ -162,6 +162,20 @@ public void ForceSetPositionTest_RunningToNextStation1()
Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
Assert.That(service.IsRunningToNextStation, Is.True);
});
+
+ service.SetCurrentLocation(1, 1);
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(0));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+ service.SetCurrentLocation(1, 1);
+ service.SetCurrentLocation(1, 1);
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
}
[Test]
@@ -194,5 +208,20 @@ public void ForceSetPositionTest_RunningToNextStation2()
Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
Assert.That(service.IsRunningToNextStation, Is.True);
});
+
+ service.SetCurrentLocation(2, 2);
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(1));
+ Assert.That(service.IsRunningToNextStation, Is.True);
+ });
+ service.SetCurrentLocation(2, 2);
+ service.SetCurrentLocation(2, 2);
+
+ Assert.Multiple(() =>
+ {
+ Assert.That(service.CurrentStationIndex, Is.EqualTo(2));
+ Assert.That(service.IsRunningToNextStation, Is.False);
+ });
}
}
From 849cb2c431998837620a0e9afb75494e2911e137 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:22:09 +0900
Subject: [PATCH 25/29] =?UTF-8?q?=E3=83=AD=E3=82=B0=E5=87=BA=E5=8A=9B?=
=?UTF-8?q?=E3=82=92=E8=BF=BD=E5=8A=A0?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/VerticalTimetableView.LocationService.cs | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 87c7100c..5ec04936 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -132,8 +132,8 @@ void UpdateCurrentRunningLocationVisualizer(VerticalTimetableRow row, VerticalTi
return;
}
- logger.Info("UpdateCurrentRunningLocationVisualizer: {0} ... {1}", row.RowIndex, states);
row.LocationState = states;
+ logger.Info("UpdateCurrentRunningLocationVisualizer: Row[{0}] ... Requested:{1}, Actual:{2}", row.RowIndex, states, row.LocationState);
int rowCount = row.RowIndex;
@@ -149,6 +149,8 @@ is VerticalTimetableRow.LocationStates.AroundThisStation
is VerticalTimetableRow.LocationStates.RunningToNextStation
? new(0, -(RowHeight.Value / 2)) : new(0);
+ logger.Debug("CurrentLocationBoxView.IsVisible: {0}, CurrentLocationLine.IsVisible: {1}", CurrentLocationBoxView.IsVisible, CurrentLocationLine.IsVisible);
+
try
{
if (IsHapticEnabled)
From 8af752f83d7cf6ba060dc9b054b4f160fa6a1475 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:22:45 +0900
Subject: [PATCH 26/29] =?UTF-8?q?ForceLonLat=E3=81=A7RunningToNextStation?=
=?UTF-8?q?=E3=81=AB=E3=81=AA=E3=82=89=E3=81=AA=E3=81=84=E4=B8=8D=E5=85=B7?=
=?UTF-8?q?=E5=90=88=E3=82=92=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/VerticalTimetableView.LocationService.cs | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 5ec04936..7ac7a0d8 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -48,11 +48,12 @@ private void LocationService_LocationStateChanged(object? sender, LocationStateC
);
if (CurrentRunningRow is not null)
CurrentRunningRow.LocationState = VerticalTimetableRow.LocationStates.Undefined;
- UpdateCurrentRunningLocationVisualizer(RowViewList[e.NewStationIndex], e.IsRunningToNextStation
+ VerticalTimetableRow rowView = RowViewList[e.NewStationIndex];
+ UpdateCurrentRunningLocationVisualizer(rowView, e.IsRunningToNextStation
? VerticalTimetableRow.LocationStates.RunningToNextStation
: VerticalTimetableRow.LocationStates.AroundThisStation
);
- CurrentRunningRow = RowViewList[e.NewStationIndex];
+ _CurrentRunningRow = rowView;
CurrentRunningRowIndex = e.NewStationIndex;
}
From d4f70a2a2d3c28526c362ea0df117ed2d403d0eb Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:29:19 +0900
Subject: [PATCH 27/29] =?UTF-8?q?=E7=8F=BE=E5=9C=A8=E4=BD=8D=E7=BD=AE?=
=?UTF-8?q?=E6=9B=B4=E6=96=B0=E6=99=82=E3=81=AB=E3=82=B9=E3=82=AF=E3=83=AD?=
=?UTF-8?q?=E3=83=BC=E3=83=AB=E3=81=97=E3=81=AA=E3=81=84=E5=95=8F=E9=A1=8C?=
=?UTF-8?q?=E3=82=92=E4=BF=AE=E6=AD=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/VerticalTimetableView.LocationService.cs | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 7ac7a0d8..6ff7ff1a 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -55,6 +55,11 @@ private void LocationService_LocationStateChanged(object? sender, LocationStateC
);
_CurrentRunningRow = rowView;
CurrentRunningRowIndex = e.NewStationIndex;
+
+ if (rowView.LocationState != VerticalTimetableRow.LocationStates.Undefined)
+ {
+ ScrollRequested?.Invoke(this, new(Math.Max(rowView.RowIndex - 1, 0) * RowHeight.Value));
+ }
}
public void SetCurrentRunningRow(int index)
From 9908288c7fcbd1f4e0b69add82ef004390ccf82b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:29:28 +0900
Subject: [PATCH 28/29] =?UTF-8?q?=E4=B8=8D=E8=A6=81=E3=81=AA=E3=83=97?=
=?UTF-8?q?=E3=83=AD=E3=83=91=E3=83=86=E3=82=A3=E3=82=92=E5=89=8A=E9=99=A4?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
TRViS/DTAC/VerticalTimetableView.LocationService.cs | 6 ------
TRViS/DTAC/VerticalTimetableView.cs | 2 --
2 files changed, 8 deletions(-)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 6ff7ff1a..0289eafc 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -119,12 +119,6 @@ void SetCurrentRunningRow(int index, VerticalTimetableRow? value)
logger.Debug("value is null -> set CurrentRunningRowIndex to -1");
CurrentRunningRowIndex = -1;
}
-
- NextRunningRow = RowViewList.ElementAtOrDefault(index + 1);
- logger.Debug("NextRunningRow is set to {0}: `{1}`",
- NextRunningRow?.RowIndex,
- NextRunningRow?.RowData.StationName
- );
});
}
diff --git a/TRViS/DTAC/VerticalTimetableView.cs b/TRViS/DTAC/VerticalTimetableView.cs
index b2a66de7..14139ec3 100644
--- a/TRViS/DTAC/VerticalTimetableView.cs
+++ b/TRViS/DTAC/VerticalTimetableView.cs
@@ -41,8 +41,6 @@ partial void OnIsBusyChanged()
int CurrentRunningRowIndex = -1;
- VerticalTimetableRow? NextRunningRow = null;
-
VerticalTimetableRow? _CurrentRunningRow = null;
VerticalTimetableRow? CurrentRunningRow
{
From f7962aaf138126b2607abe1dca1aacf8f17d1509 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=EF=BC=B4=EF=BC=B2?=
<31824852+TetsuOtter@users.noreply.github.com>
Date: Fri, 24 Nov 2023 16:43:42 +0900
Subject: [PATCH 29/29] =?UTF-8?q?=E3=82=B9=E3=82=AF=E3=83=AD=E3=83=BC?=
=?UTF-8?q?=E3=83=AB=E5=AE=9F=E8=A1=8C=E3=82=92UpdateCurrentRunningLocatio?=
=?UTF-8?q?nVisualizer=E5=81=B4=E3=81=AB=E7=A7=BB=E5=8B=95?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
わざわざ呼び出し元で実行する意味はないため
---
.../VerticalTimetableView.LocationService.cs | 25 ++++++++-----------
1 file changed, 11 insertions(+), 14 deletions(-)
diff --git a/TRViS/DTAC/VerticalTimetableView.LocationService.cs b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
index 0289eafc..4229e707 100644
--- a/TRViS/DTAC/VerticalTimetableView.LocationService.cs
+++ b/TRViS/DTAC/VerticalTimetableView.LocationService.cs
@@ -56,10 +56,7 @@ private void LocationService_LocationStateChanged(object? sender, LocationStateC
_CurrentRunningRow = rowView;
CurrentRunningRowIndex = e.NewStationIndex;
- if (rowView.LocationState != VerticalTimetableRow.LocationStates.Undefined)
- {
- ScrollRequested?.Invoke(this, new(Math.Max(rowView.RowIndex - 1, 0) * RowHeight.Value));
- }
+ logger.Debug("process finished");
}
public void SetCurrentRunningRow(int index)
@@ -103,16 +100,6 @@ void SetCurrentRunningRow(int index, VerticalTimetableRow? value)
{
CurrentRunningRowIndex = index;
UpdateCurrentRunningLocationVisualizer(value, VerticalTimetableRow.LocationStates.AroundThisStation);
-
- if (value.LocationState != VerticalTimetableRow.LocationStates.Undefined)
- {
- logger.Debug("value.LocationState is not Undefined -> invoke ScrollRequested");
- ScrollRequested?.Invoke(this, new(Math.Max(value.RowIndex - 1, 0) * RowHeight.Value));
- }
- else
- {
- logger.Debug("value.LocationState is Undefined -> do nothing");
- }
}
else
{
@@ -166,5 +153,15 @@ is VerticalTimetableRow.LocationStates.RunningToNextStation
logger.Error(ex, "Failed to perform HapticFeedback");
IsHapticEnabled = false;
}
+
+ if (row.LocationState != VerticalTimetableRow.LocationStates.Undefined)
+ {
+ logger.Debug("value.LocationState is not Undefined -> invoke ScrollRequested");
+ ScrollRequested?.Invoke(this, new(Math.Max(row.RowIndex - 1, 0) * RowHeight.Value));
+ }
+ else
+ {
+ logger.Debug("value.LocationState is Undefined -> do nothing");
+ }
}
}