Browse Source

feat: 补充主要组成

LanzaSchneider 2 years ago
parent
commit
b36754c42a
4 changed files with 204 additions and 0 deletions
  1. 81 0
      Content.cs
  2. 89 0
      Package.DependencyInfo.cs
  3. 13 0
      Package.FileSystem.cs
  4. 21 0
      Package.cs

+ 81 - 0
Content.cs

@@ -0,0 +1,81 @@
+using System;
+using System.IO;
+using Godot;
+
+namespace TBL.GodotSharp.Content;
+
+/// <summary>
+/// 内容模块扩展功能类
+/// </summary>
+public static class Content
+{
+    /// <summary>
+    /// 考虑依赖项打开文件流
+    /// </summary>
+    /// <param name="package">要打开的内容包</param>
+    /// <param name="path">要打开的路径</param>
+    /// <returns>打开的文件流</returns>
+    public static Stream OpenFileStreamWithDependency(
+        this Package package, string path)
+    {
+        var stream = package.OpenFileStream(path);
+
+        // 直接打开成功的场合
+        if (stream != null)
+            return stream;
+
+        // 在同级节点中寻找依赖项
+        Node container;
+        if (null != (container = package.GetParent()))
+        {
+            for (int i = 0, count = container.GetChildCount();
+                 i < count; 
+                 i++)
+            {
+                if (container.GetChild(i) is not Package dependency)
+                    continue;
+                // 遍历依赖项信息
+                foreach (var info in package.Dependencies)
+                {
+                    // 符合依赖项的包将会被试图追溯
+                    if (dependency.SelfInfo.IsCompatibleWith(info))
+                    {
+                        stream = dependency.OpenFileStreamWithDependency(path);
+                        
+                        // 直接打开成功的场合
+                        if (stream != null)
+                            return stream;
+                    }
+                }
+            }
+        }
+
+        // 打开失败的场合
+        return null;
+    }
+    
+    /// <summary>
+    /// 判断 <paramref name="actualVersion"/> 能否满足 <paramref name="targetVersion"/> 的版本要求
+    /// <para>用于内容包之间的依赖可用性检测</para>
+    /// </summary>
+    /// <param name="actualVersion">当前版本</param>
+    /// <param name="targetVersion">要求的版本</param>
+    /// <param name="level">兼容级别</param>
+    public static bool IsCompatibleWith(Version actualVersion, Version targetVersion, int level)
+    {
+        // 主版本号
+        if (actualVersion.Major != targetVersion.Major)
+            return false;
+        if (level < 1)
+            return true;
+        // 次版本号
+        if (actualVersion.Minor != targetVersion.Minor)
+            return false;
+        if (level < 2)
+            return true;
+        // 构建版本号
+        if (actualVersion.Build != targetVersion.Build)
+            return false;
+        return true;
+    }
+}

+ 89 - 0
Package.DependencyInfo.cs

@@ -0,0 +1,89 @@
+using System;
+
+namespace TBL.GodotSharp.Content;
+
+public partial class Package
+{
+    /// <summary>
+    /// 包信息
+    /// </summary>
+    public struct Info
+    {
+        /// <summary>
+        /// 包名称
+        /// </summary>
+        public readonly string Name;
+
+        /// <summary>
+        /// 作者信息
+        /// </summary>
+        public readonly string AuthorInfo;
+        
+        /// <summary>
+        /// 版本信息
+        /// </summary>
+        public readonly Version VersionInfo;
+
+        public Info(string name, string author, string version)
+        {
+            Name = name;
+            AuthorInfo = author;
+            if (!Version.TryParse(version, out VersionInfo))
+                VersionInfo = new Version();
+        }
+        
+        /// <summary>
+        /// 判断本信息能否满足 <paramref name="target"/> 的版本要求
+        /// </summary>
+        /// <param name="target">依赖项信息</param>
+        public readonly bool IsCompatibleWith(DependencyInfo target)
+        {
+            return Content.IsCompatibleWith(VersionInfo, target.Target.VersionInfo,
+                (target.Flags & DependencyInfo.FlagsEnum.Strict) != 0 ? 1 : 0);
+        }
+    }
+
+    /// <summary>
+    /// 包依赖信息
+    /// </summary>
+    public struct DependencyInfo
+    {
+        /// <summary>
+        /// 依赖目标
+        /// </summary>
+        public readonly Info Target;
+
+        /// <summary>
+        /// 依赖属性
+        /// </summary>
+        public readonly FlagsEnum Flags;
+        
+        /// <summary>
+        /// 依赖项属性
+        /// </summary>
+        [Flags]
+        public enum FlagsEnum
+        {
+            /// <summary>
+            /// 无属性
+            /// </summary>
+            None,
+                
+            /// <summary>
+            /// 非必须依赖项
+            /// </summary>
+            Unnecessary,
+
+            /// <summary>
+            /// 严格(次版本号)兼容依赖项
+            /// </summary>
+            Strict
+        }
+
+        public DependencyInfo(Info target, FlagsEnum flags = FlagsEnum.None)
+        {
+            Target = target;
+            Flags = flags;
+        }
+    }
+}

+ 13 - 0
Package.FileSystem.cs

@@ -0,0 +1,13 @@
+using System.IO;
+
+namespace TBL.GodotSharp.Content;
+
+public partial class Package
+{
+    /// <summary>
+    /// 打开文件流
+    /// </summary>
+    /// <param name="path"></param>
+    /// <returns></returns>
+    public abstract Stream OpenFileStream(string path);
+}

+ 21 - 0
Package.cs

@@ -0,0 +1,21 @@
+using System;
+using System.Collections.Generic;
+using Godot;
+
+namespace TBL.GodotSharp.Content;
+
+/// <summary>
+/// 资源包节点
+/// </summary>
+public abstract partial class Package : Node
+{
+    /// <summary>
+    /// 自身信息
+    /// </summary>
+    public readonly Info SelfInfo;
+
+    /// <summary>
+    /// 依赖项信息集
+    /// </summary>
+    public readonly ICollection<DependencyInfo> Dependencies;
+}