From f230fb823b6ef0e71659c2c7d747bbcb60ecdfbc Mon Sep 17 00:00:00 2001 From: Pilzinsel64 Date: Fri, 30 Aug 2024 11:43:32 +0200 Subject: [PATCH] convert Pilz to c# & add AppVersion to there --- Pilz.Configuration/Pilz.Configuration.csproj | 2 +- Pilz.IO/Pilz.IO.csproj | 2 +- Pilz.sln | 18 +-- Pilz/AppChannel.cs | 9 ++ Pilz/AppVersion.cs | 152 +++++++++++++++++++ Pilz/GeneralEventArgs/GetValueEventArgs.cs | 18 +++ Pilz/GeneralEventArgs/GetValueEventArgs.vb | 18 --- Pilz/Json/AppVersionStringJsonConverter.cs | 80 ++++++++++ Pilz/Pilz.csproj | 14 ++ Pilz/Pilz.vbproj | 50 ------ Pilz/Runtime/OSType.cs | 9 ++ Pilz/Runtime/OSType.vb | 10 -- Pilz/Runtime/RuntimeInformationsEx.cs | 79 ++++++++++ Pilz/Runtime/RuntimeInformationsEx.vb | 81 ---------- 14 files changed, 372 insertions(+), 170 deletions(-) create mode 100644 Pilz/AppChannel.cs create mode 100644 Pilz/AppVersion.cs create mode 100644 Pilz/GeneralEventArgs/GetValueEventArgs.cs delete mode 100644 Pilz/GeneralEventArgs/GetValueEventArgs.vb create mode 100644 Pilz/Json/AppVersionStringJsonConverter.cs create mode 100644 Pilz/Pilz.csproj delete mode 100644 Pilz/Pilz.vbproj create mode 100644 Pilz/Runtime/OSType.cs delete mode 100644 Pilz/Runtime/OSType.vb create mode 100644 Pilz/Runtime/RuntimeInformationsEx.cs delete mode 100644 Pilz/Runtime/RuntimeInformationsEx.vb diff --git a/Pilz.Configuration/Pilz.Configuration.csproj b/Pilz.Configuration/Pilz.Configuration.csproj index 60441c6..0432be3 100644 --- a/Pilz.Configuration/Pilz.Configuration.csproj +++ b/Pilz.Configuration/Pilz.Configuration.csproj @@ -29,6 +29,6 @@ - + \ No newline at end of file diff --git a/Pilz.IO/Pilz.IO.csproj b/Pilz.IO/Pilz.IO.csproj index 0fbf985..ea2e440 100644 --- a/Pilz.IO/Pilz.IO.csproj +++ b/Pilz.IO/Pilz.IO.csproj @@ -91,6 +91,6 @@ - + \ No newline at end of file diff --git a/Pilz.sln b/Pilz.sln index e3784c6..37cd836 100644 --- a/Pilz.sln +++ b/Pilz.sln @@ -3,7 +3,7 @@ Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio Version 17 VisualStudioVersion = 17.7.34018.315 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{778DAE3C-4631-46EA-AA77-85C1314464D9}") = "Pilz", "Pilz\Pilz.vbproj", "{277D2B83-7613-4C49-9CAB-E080195A6E0C}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Pilz", "Pilz\Pilz.csproj", "{9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}" EndProject Project("{778DAE3C-4631-46EA-AA77-85C1314464D9}") = "Pilz.Drawing", "Pilz.Drawing\Pilz.Drawing.vbproj", "{1A0B8106-2449-4908-B5E1-A00D8E9CF8F6}" EndProject @@ -53,14 +53,14 @@ Global Release|x86 = Release|x86 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Debug|Any CPU.Build.0 = Debug|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Debug|x86.ActiveCfg = Debug|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Debug|x86.Build.0 = Debug|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Release|Any CPU.ActiveCfg = Release|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Release|Any CPU.Build.0 = Release|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Release|x86.ActiveCfg = Release|Any CPU - {277D2B83-7613-4C49-9CAB-E080195A6E0C}.Release|x86.Build.0 = Release|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Debug|Any CPU.Build.0 = Debug|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Debug|x86.ActiveCfg = Debug|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Debug|x86.Build.0 = Debug|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Release|Any CPU.ActiveCfg = Release|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Release|Any CPU.Build.0 = Release|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Release|x86.ActiveCfg = Release|Any CPU + {9559AAE8-BA4B-03B8-1EF3-2AFE7BCD5AAC}.Release|x86.Build.0 = Release|Any CPU {1A0B8106-2449-4908-B5E1-A00D8E9CF8F6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {1A0B8106-2449-4908-B5E1-A00D8E9CF8F6}.Debug|Any CPU.Build.0 = Debug|Any CPU {1A0B8106-2449-4908-B5E1-A00D8E9CF8F6}.Debug|x86.ActiveCfg = Debug|Any CPU diff --git a/Pilz/AppChannel.cs b/Pilz/AppChannel.cs new file mode 100644 index 0000000..fbb1e5e --- /dev/null +++ b/Pilz/AppChannel.cs @@ -0,0 +1,9 @@ +namespace Pilz; + +public enum AppChannel +{ + Stable, + PreRelease, + Beta, + Alpha +} \ No newline at end of file diff --git a/Pilz/AppVersion.cs b/Pilz/AppVersion.cs new file mode 100644 index 0000000..420f7e2 --- /dev/null +++ b/Pilz/AppVersion.cs @@ -0,0 +1,152 @@ +using Newtonsoft.Json; + +namespace Pilz; + +[method: JsonConstructor] +public class AppVersion(Version version, int build, AppChannel channel) : IComparable, IComparable +{ + // P r o p e r t i e s + + [JsonConverter(typeof(Newtonsoft.Json.Converters.VersionConverter))] + public Version Version { get; set; } = version; + [JsonConverter(typeof(Newtonsoft.Json.Converters.StringEnumConverter))] + public AppChannel Channel { get; set; } = channel; + public int Build { get; set; } = build; + + // C o n s t r u c t o r s + + public AppVersion() : this(new Version("1.0.0.0")) + { + } + + public AppVersion(Version version) : this(version, 1, AppChannel.Stable) + { + } + + // F e a t u r e s + + public override string ToString() + { + if (Channel == AppChannel.Stable && Build == 1) + return Version.ToString(); + + return $"{Version} {Channel} {Build}"; + } + + public override bool Equals(object obj) + { + if (ReferenceEquals(this, obj)) + return true; + if (obj is not AppVersion applicationVersion) + return false; + return applicationVersion == this; + } + + public override int GetHashCode() + { + return ToString().GetHashCode(); + } + + public static bool TryParse(string input, out AppVersion version) + { + try + { + version = Parse(input); + } + catch (Exception) + { + version = null; + } + return version != null; + } + + public static AppVersion Parse(string input) + { + if (string.IsNullOrWhiteSpace(input)) + throw new FormatException(); + + if (input.StartsWith("version", StringComparison.InvariantCultureIgnoreCase)) + input = input[7..]; + + var splitted = input.Trim().Split(' '); + + if (splitted.Length < 1 || !Version.TryParse(splitted[0], out Version? version) || version == null) + throw new FormatException(); + + if (splitted.Length < 2 || !Enum.TryParse(splitted[1], out AppChannel channel)) + channel = AppChannel.Stable; + + if (splitted.Length < 3 || !int.TryParse(splitted[2], out int build)) + build = 1; + + return new AppVersion(version, build, channel); + } + + // C o m p a r e + + public int CompareTo(object appVersion) + { + return CompareTo(appVersion as AppVersion); + } + + public int CompareTo(AppVersion appVersion) + { + if (appVersion is null) + return 1; + + if (Version != appVersion.Version) + { + if (Version > appVersion.Version) + return 1; + return -1; + } + + if (Channel != appVersion.Channel) + { + if (Channel < appVersion.Channel) + return 1; + return -1; + } + + if (Build != appVersion.Build) + { + if (Build > appVersion.Build) + return 1; + return -1; + } + + return 0; + } + + // O p e r a t o r s + + public static bool operator >(AppVersion a, AppVersion b) + { + return a.Version > b.Version || a.Version == b.Version && (a.Channel < b.Channel || (a.Channel == b.Channel && a.Build > b.Build)); + } + + public static bool operator <(AppVersion a, AppVersion b) + { + return a.Version < b.Version || a.Version == b.Version && (a.Channel > b.Channel || (a.Channel == b.Channel && a.Build < b.Build)); + } + + public static bool operator ==(AppVersion a, AppVersion b) + { + return a.Version == b.Version && a.Channel == b.Channel && a.Build == b.Build; + } + + public static bool operator !=(AppVersion a, AppVersion b) + { + return a.Version != b.Version || a.Channel != b.Channel || a.Build != b.Build; + } + + public static bool operator >=(AppVersion a, AppVersion b) + { + return a == b || a > b; + } + + public static bool operator <=(AppVersion a, AppVersion b) + { + return a == b || a < b; + } +} \ No newline at end of file diff --git a/Pilz/GeneralEventArgs/GetValueEventArgs.cs b/Pilz/GeneralEventArgs/GetValueEventArgs.cs new file mode 100644 index 0000000..c947acd --- /dev/null +++ b/Pilz/GeneralEventArgs/GetValueEventArgs.cs @@ -0,0 +1,18 @@ +namespace Pilz.GeneralEventArgs; + + +public class GetValueEventArgs : EventArgs +{ + + public T? Value { get; set; } + + public GetValueEventArgs() : base() + { + } + + public GetValueEventArgs(T? value) : base() + { + Value = value; + } + +} \ No newline at end of file diff --git a/Pilz/GeneralEventArgs/GetValueEventArgs.vb b/Pilz/GeneralEventArgs/GetValueEventArgs.vb deleted file mode 100644 index 397e2ed..0000000 --- a/Pilz/GeneralEventArgs/GetValueEventArgs.vb +++ /dev/null @@ -1,18 +0,0 @@ -Namespace GeneralEventArgs - - Public Class GetValueEventArgs(Of T) - Inherits EventArgs - - Public Property Value As T - - Public Sub New() - MyBase.New - End Sub - - Public Sub New(value As T) - MyBase.New - End Sub - - End Class - -End Namespace diff --git a/Pilz/Json/AppVersionStringJsonConverter.cs b/Pilz/Json/AppVersionStringJsonConverter.cs new file mode 100644 index 0000000..1b34551 --- /dev/null +++ b/Pilz/Json/AppVersionStringJsonConverter.cs @@ -0,0 +1,80 @@ +using Newtonsoft.Json; + +namespace Pilz.Json; + +public class AppVersionStringJsonConverter(bool serializeAsObject) : JsonConverter +{ + public AppVersionStringJsonConverter() : this(false) + { + } + + /// + /// Writes the JSON representation of the object. + /// + /// The to write to. + /// The value. + /// The calling serializer. + public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer) + { + if (value == null) + { + writer.WriteNull(); + return; + } + + if (serializeAsObject || value is not AppVersion appVersion) + writer.WriteValue(value); + else + writer.WriteValue(appVersion.ToString()); + } + + /// + /// Reads the JSON representation of the object. + /// + /// The to read from. + /// Type of the object. + /// The existing value of object being read. + /// The calling serializer. + /// The object value. + public override object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer) + { + if (reader.TokenType == JsonToken.Null) + return null; + + try + { + if (reader.TokenType == JsonToken.String) + { + var strValue = reader.Value?.ToString(); + + if (string.IsNullOrWhiteSpace(strValue)) + return null; + + return AppVersion.Parse(strValue); + + } + + if (reader.TokenType == JsonToken.StartObject) + return serializer.Deserialize(reader); + } + catch (Exception ex) + { + throw new JsonSerializationException("Error converting value {0} to type '{1}'.", ex); + } + + // we don't actually expect to get here. + throw new JsonSerializationException("Unexpected token {0} when parsing app version."); + } + + /// + /// Determines whether this instance can convert the specified object type. + /// + /// Type of the object. + /// + /// true if this instance can convert the specified object type; otherwise, false. + /// + public override bool CanConvert(Type objectType) + { + return objectType == typeof(AppVersion); + } +} diff --git a/Pilz/Pilz.csproj b/Pilz/Pilz.csproj new file mode 100644 index 0000000..35d11f3 --- /dev/null +++ b/Pilz/Pilz.csproj @@ -0,0 +1,14 @@ + + + + net8.0 + latest + enable + enable + + + + + + + \ No newline at end of file diff --git a/Pilz/Pilz.vbproj b/Pilz/Pilz.vbproj deleted file mode 100644 index e5cd91f..0000000 --- a/Pilz/Pilz.vbproj +++ /dev/null @@ -1,50 +0,0 @@ - - - netstandard2.0;net8.0 - Pilz.xml - true - latest - Pilz - Pilzinsel64 - Pilz - Copyright © Pilzinsel64 2019 - 2020 - Pilz.xml - true - 42016,41999,42017,42018,42019,42032,42036,42020,42021,42022 - - - true - - - false - - - On - - - Binary - - - Off - On - - - 2.0.0 - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/Pilz/Runtime/OSType.cs b/Pilz/Runtime/OSType.cs new file mode 100644 index 0000000..06dc7cd --- /dev/null +++ b/Pilz/Runtime/OSType.cs @@ -0,0 +1,9 @@ +namespace Pilz.Runtime; + +public enum OSType +{ + Unknown, + Windows, + Linux, + OSX +} \ No newline at end of file diff --git a/Pilz/Runtime/OSType.vb b/Pilz/Runtime/OSType.vb deleted file mode 100644 index 477cc87..0000000 --- a/Pilz/Runtime/OSType.vb +++ /dev/null @@ -1,10 +0,0 @@ -Namespace Runtime - - Public Enum OSType - Unknown - Windows - Linux - OSX - End Enum - -End Namespace diff --git a/Pilz/Runtime/RuntimeInformationsEx.cs b/Pilz/Runtime/RuntimeInformationsEx.cs new file mode 100644 index 0000000..29d91ea --- /dev/null +++ b/Pilz/Runtime/RuntimeInformationsEx.cs @@ -0,0 +1,79 @@ +using System.Runtime.InteropServices; + +namespace Pilz.Runtime; + +public static class RuntimeInformationsEx +{ + private static OSType? osType; + private static OSType? osTypeReal; + + public static OSType OSType => osType ??= GetOSType(); + + public static OSType RealOSType => osTypeReal ??= GetRealOSType(); + + public static OSType GetOSType() + { + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + return OSType.Windows; + + if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + return OSType.Linux; + + if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) + return OSType.OSX; + + return OSType.Unknown; + } + + public static OSType GetRealOSType() + { + var windir = Environment.GetEnvironmentVariable("windir"); + const string ostypeDirWine = @"Z:\proc\sys\kernel\ostype"; + const string ostypeDirNative = "/proc/sys/kernel/ostype"; + const string systemVersionWine = @"Z:\System\Library\CoreServices\SystemVersion.plist"; + const string systemVersionNative = "/System/Library/CoreServices/SystemVersion.plist"; + + // Linux using wine + if (File.Exists(ostypeDirWine)) + { + var osTypeString = File.ReadAllText(ostypeDirWine); + if (osTypeString.StartsWith("Linux", StringComparison.OrdinalIgnoreCase)) + // Note: Android gets here too + return OSType.Linux; + else + return OSType.Unknown; + } + + // Linux native + else if (File.Exists(ostypeDirNative)) + { + var osTypeString = File.ReadAllText(ostypeDirNative); + if (osTypeString.StartsWith("Linux", StringComparison.OrdinalIgnoreCase)) + // Note: Android gets here too + return OSType.Linux; + else + return OSType.Unknown; + } + + // OSX using wine + else if (File.Exists(systemVersionWine)) + // Note: iOS gets here too + return OSType.OSX; + + // OSX native + else if (File.Exists(systemVersionNative)) + // Note: iOS gets here too + return OSType.OSX; + + // Windows + else if (!string.IsNullOrEmpty(windir) && Directory.Exists(windir) && Path.DirectorySeparatorChar == '\\') + return OSType.Windows; + + return OSType.Unknown; + } + + public static bool IsOSPlatform(OSType os, bool checkRealOS) + { + return (checkRealOS ? RealOSType : OSType) == os; + } +} \ No newline at end of file diff --git a/Pilz/Runtime/RuntimeInformationsEx.vb b/Pilz/Runtime/RuntimeInformationsEx.vb deleted file mode 100644 index 6ad5541..0000000 --- a/Pilz/Runtime/RuntimeInformationsEx.vb +++ /dev/null @@ -1,81 +0,0 @@ -Imports System.IO -Imports System.Runtime.InteropServices - -Namespace Runtime - - Public Module RuntimeInformationsEx - - Public ReadOnly Property OSType As OSType - Get - Static t As OSType? = Nothing - - If t Is Nothing Then - Select Case True - Case RuntimeInformation.IsOSPlatform(OSPlatform.Windows) - t = OSType.Windows - Case RuntimeInformation.IsOSPlatform(OSPlatform.Linux) - t = OSType.Linux - Case RuntimeInformation.IsOSPlatform(OSPlatform.OSX) - t = OSType.OSX - Case Else - t = OSType.Unknown - End Select - End If - - Return t - End Get - End Property - - Public ReadOnly Property RealOSType As OSType - Get - Static t As OSType? = Nothing - - If t Is Nothing Then - - Dim windir = Environment.GetEnvironmentVariable("windir") - Const ostypeDirWine = "Z:\proc\sys\kernel\ostype" - Const ostypeDirNative = "/proc/sys/kernel/ostype" - Const systemVersionWine = "Z:\System\Library\CoreServices\SystemVersion.plist" - Const systemVersionNative = "/System/Library/CoreServices/SystemVersion.plist" - - If File.Exists(ostypeDirWine) Then ' Linux using wine - Dim osTypeString As String = File.ReadAllText(ostypeDirWine) - If osTypeString.StartsWith("Linux", StringComparison.OrdinalIgnoreCase) Then - ' Note: Android gets here too - t = OSType.Linux - Else - t = OSType.Unknown - End If - ElseIf File.Exists(ostypeDirNative) Then ' Linux native - Dim osTypeString As String = File.ReadAllText(ostypeDirNative) - If osTypeString.StartsWith("Linux", StringComparison.OrdinalIgnoreCase) Then - ' Note: Android gets here too - t = OSType.Linux - Else - t = OSType.Unknown - End If - ElseIf File.Exists(systemVersionWine) Then ' OSX using wine - ' Note: iOS gets here too - t = OSType.OSX - ElseIf File.Exists(systemVersionNative) Then ' OSX native - ' Note: iOS gets here too - t = OSType.OSX - ElseIf Not String.IsNullOrEmpty(windir) AndAlso Directory.Exists(windir) AndAlso Path.DirectorySeparatorChar = "\"c Then ' Windows - t = OSType.Windows - Else - t = OSType.Unknown - End If - - End If - - Return t - End Get - End Property - - Public Function IsOSPlatform(os As OSType, checkRealOS As Boolean) As Boolean - Return If(checkRealOS, RealOSType, OSType) = os - End Function - - End Module - -End Namespace