Browse Source

Attempting to include light extension

Vicente Penades 6 years ago
parent
commit
a965d090e0

+ 2 - 1
build/SharpGLTF.CodeGen/Constants.cs

@@ -28,7 +28,8 @@ namespace SharpGLTF
         public static string KhronosDracoSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_draco_mesh_compression", "schema");
         public static string KhronosPbrSpecGlossSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_materials_pbrSpecularGlossiness", "schema", "glTF.KHR_materials_pbrSpecularGlossiness.schema.json");
         public static string KhronosUnlitSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_materials_unlit", "schema", "glTF.KHR_materials_unlit.schema.json");
-        public static string KhronosLightsPunctualSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_lights_punctual", "schema", "glTF.KHR_lights_punctual.schema.json");
+        public static string KhronosModelLightsPunctualSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_lights_punctual", "schema", "glTF.KHR_lights_punctual.schema.json");
+        public static string KhronosNodeLightsPunctualSchemaFile => System.IO.Path.Combine(KhronosSchemaDir, "KHR_lights_punctual", "schema", "node.KHR_lights_punctual.schema.json");
 
 
         /// <summary>

+ 17 - 6
build/SharpGLTF.CodeGen/Program.cs

@@ -23,7 +23,8 @@ namespace SharpGLTF
 
             _ProcessKhronosPBRExtension();
             _ProcessKhronosUnlitExtension();
-            _ProcessKhronosLightsPunctualExtension();
+            _ProcessKhronosModelLightsPunctualExtension();
+            _ProcessKhronosNodeLightsPunctualExtension();
 
             // these extansions are not fully supported and temporarily removed:
             // _ProcessDracoExtension();
@@ -129,9 +130,9 @@ namespace SharpGLTF
             ProcessSchema("ext.Unlit.g", ctx);
         }
 
-        private static void _ProcessKhronosLightsPunctualExtension()
+        private static void _ProcessKhronosModelLightsPunctualExtension()
         {
-            var ctx = LoadSchemaContext(Constants.KhronosLightsPunctualSchemaFile);            
+            var ctx = LoadSchemaContext(Constants.KhronosModelLightsPunctualSchemaFile);            
             ctx.Remove("glTF Property");
             ctx.Classes.FirstOrDefault(item => item.PersistentName == "glTF Child of Root Property").IgnoredByEmitter = true;
 
@@ -144,9 +145,19 @@ namespace SharpGLTF
                 .SetDefaultValue("Vector3.One")
                 .SetItemsRange(0);
 
-            ProcessSchema("ext.LightsPunctual.g", ctx);
+            ProcessSchema("ext.ModelLightsPunctual.g", ctx);
         }
 
+        private static void _ProcessKhronosNodeLightsPunctualExtension()
+        {
+            var ctx = LoadSchemaContext(Constants.KhronosNodeLightsPunctualSchemaFile);
+            ctx.Remove("glTF Property");            
+
+            ProcessSchema("ext.NodeLightsPunctual.g", ctx);
+        }
+
+
+
         /*
         private static void _ProcessMicrosoftLODExtension()
         {
@@ -204,8 +215,8 @@ namespace SharpGLTF
             newEmitter.SetRuntimeName("KHR_materials_pbrSpecularGlossiness glTF extension", "MaterialPBRSpecularGlossiness_KHR");
             newEmitter.SetRuntimeName("KHR_materials_unlit glTF extension", "MaterialUnlit_KHR");
 
-            newEmitter.SetRuntimeName("light", "Light_KHR");
-            newEmitter.SetRuntimeName("light/spot", "LightSpot_KHR");
+            newEmitter.SetRuntimeName("light", "PunctualLight");
+            newEmitter.SetRuntimeName("light/spot", "PunctualLightSpot");
 
 
 

+ 137 - 0
src/SharpGLTF/Schema2/Generated/ext.ModelLightsPunctual.g.cs

@@ -0,0 +1,137 @@
+//------------------------------------------------------------------------------------------------
+//      This file has been programatically generated; DON´T EDIT!
+//------------------------------------------------------------------------------------------------
+
+#pragma warning disable SA1001
+#pragma warning disable SA1027
+#pragma warning disable SA1028
+#pragma warning disable SA1121
+#pragma warning disable SA1205
+#pragma warning disable SA1309
+#pragma warning disable SA1402
+#pragma warning disable SA1505
+#pragma warning disable SA1507
+#pragma warning disable SA1508
+#pragma warning disable SA1652
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Numerics;
+using Newtonsoft.Json;
+
+namespace SharpGLTF.Schema2
+{
+	using Collections;
+
+	partial class PunctualLightSpot : glTFProperty
+	{
+	
+		private const Double _innerConeAngleDefault = 0;
+		private const Double _innerConeAngleMinimum = 0;
+		private const Double _innerConeAngleMaximum = 1.5707963267949;
+		private Double? _innerConeAngle = _innerConeAngleDefault;
+		
+		private const Double _outerConeAngleDefault = 0.785398163397448;
+		private const Double _outerConeAngleMinimum = 0;
+		private const Double _outerConeAngleMaximum = 1.5707963267949;
+		private Double? _outerConeAngle = _outerConeAngleDefault;
+		
+	
+		/// <inheritdoc />
+		protected override void SerializeProperties(JsonWriter writer)
+		{
+			base.SerializeProperties(writer);
+			SerializeProperty(writer, "innerConeAngle", _innerConeAngle, _innerConeAngleDefault);
+			SerializeProperty(writer, "outerConeAngle", _outerConeAngle, _outerConeAngleDefault);
+		}
+	
+		/// <inheritdoc />
+		protected override void DeserializeProperty(JsonReader reader, string property)
+		{
+			switch (property)
+			{
+				case "innerConeAngle": _innerConeAngle = DeserializeValue<Double?>(reader); break;
+				case "outerConeAngle": _outerConeAngle = DeserializeValue<Double?>(reader); break;
+				default: base.DeserializeProperty(reader, property); break;
+			}
+		}
+	
+	}
+
+	/// <summary>
+	/// A directional, point, or spot light.
+	/// </summary>
+	partial class PunctualLight : LogicalChildOfRoot
+	{
+	
+		private static readonly Vector3 _colorDefault = Vector3.One;
+		private Vector3? _color = _colorDefault;
+		
+		private const Double _intensityDefault = 1;
+		private const Double _intensityMinimum = 0;
+		private Double? _intensity = _intensityDefault;
+		
+		private const Double _rangeMinimum = 0;
+		private Double? _range;
+		
+		private PunctualLightSpot _spot;
+		
+		private String _type;
+		
+	
+		/// <inheritdoc />
+		protected override void SerializeProperties(JsonWriter writer)
+		{
+			base.SerializeProperties(writer);
+			SerializeProperty(writer, "color", _color, _colorDefault);
+			SerializeProperty(writer, "intensity", _intensity, _intensityDefault);
+			SerializeProperty(writer, "range", _range);
+			SerializePropertyObject(writer, "spot", _spot);
+			SerializeProperty(writer, "type", _type);
+		}
+	
+		/// <inheritdoc />
+		protected override void DeserializeProperty(JsonReader reader, string property)
+		{
+			switch (property)
+			{
+				case "color": _color = DeserializeValue<Vector3?>(reader); break;
+				case "intensity": _intensity = DeserializeValue<Double?>(reader); break;
+				case "range": _range = DeserializeValue<Double?>(reader); break;
+				case "spot": _spot = DeserializeValue<PunctualLightSpot>(reader); break;
+				case "type": _type = DeserializeValue<String>(reader); break;
+				default: base.DeserializeProperty(reader, property); break;
+			}
+		}
+	
+	}
+
+	partial class KHR_lights_punctualglTFextension : glTFProperty
+	{
+	
+		private const int _lightsMinItems = 1;
+		private ChildrenCollection<PunctualLight,ModelRoot> _lights;
+		
+	
+		/// <inheritdoc />
+		protected override void SerializeProperties(JsonWriter writer)
+		{
+			base.SerializeProperties(writer);
+			SerializeProperty(writer, "lights", _lights, _lightsMinItems);
+		}
+	
+		/// <inheritdoc />
+		protected override void DeserializeProperty(JsonReader reader, string property)
+		{
+			switch (property)
+			{
+				case "lights": DeserializeList<PunctualLight>(reader, _lights); break;
+				default: base.DeserializeProperty(reader, property); break;
+			}
+		}
+	
+	}
+
+}

+ 53 - 0
src/SharpGLTF/Schema2/Generated/ext.NodeLightsPunctual.g.cs

@@ -0,0 +1,53 @@
+//------------------------------------------------------------------------------------------------
+//      This file has been programatically generated; DON´T EDIT!
+//------------------------------------------------------------------------------------------------
+
+#pragma warning disable SA1001
+#pragma warning disable SA1027
+#pragma warning disable SA1028
+#pragma warning disable SA1121
+#pragma warning disable SA1205
+#pragma warning disable SA1309
+#pragma warning disable SA1402
+#pragma warning disable SA1505
+#pragma warning disable SA1507
+#pragma warning disable SA1508
+#pragma warning disable SA1652
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Numerics;
+using Newtonsoft.Json;
+
+namespace SharpGLTF.Schema2
+{
+	using Collections;
+
+	partial class KHR_lights_punctualnodeextension : glTFProperty
+	{
+	
+		private Int32 _light;
+		
+	
+		/// <inheritdoc />
+		protected override void SerializeProperties(JsonWriter writer)
+		{
+			base.SerializeProperties(writer);
+			SerializeProperty(writer, "light", _light);
+		}
+	
+		/// <inheritdoc />
+		protected override void DeserializeProperty(JsonReader reader, string property)
+		{
+			switch (property)
+			{
+				case "light": _light = DeserializeValue<Int32>(reader); break;
+				default: base.DeserializeProperty(reader, property); break;
+			}
+		}
+	
+	}
+
+}

+ 9 - 0
src/SharpGLTF/Schema2/gltf.ExtensionsFactory.cs

@@ -8,12 +8,21 @@ namespace SharpGLTF.Schema2
 
     static class ExtensionsFactory
     {
+        // extensions design inconsistencies:
+        // https://github.com/KhronosGroup/glTF/issues/1491
+
         #region supported extensions must be registered here
 
         static ExtensionsFactory()
         {
             RegisterExtension<MaterialPBRSpecularGlossiness_KHR>("KHR_materials_pbrSpecularGlossiness");
             RegisterExtension<MaterialUnlit_KHR>("KHR_materials_unlit");
+
+            // if found in model:
+            // RegisterExtension<KHR_lights_punctualglTFextension>("KHR_lights_punctual");
+
+            // if found in node
+            // RegisterExtension<KHR_lights_punctualnodeextension>("KHR_lights_punctual");
         }
 
         #endregion

+ 133 - 0
src/SharpGLTF/Schema2/khr.lights.cs

@@ -0,0 +1,133 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+using System.Numerics;
+
+namespace SharpGLTF.Schema2
+{
+    using Collections;
+
+    partial class KHR_lights_punctualglTFextension
+    {
+        public ChildrenCollection<PunctualLight, ModelRoot> GetLightsCollection(ModelRoot root)
+        {
+            if (_lights == null) _lights = new ChildrenCollection<PunctualLight, ModelRoot>(root);
+
+            return _lights;
+        }
+    }
+
+    public partial class PunctualLight
+    {
+        /// <summary>
+        /// Gets the zero-based index of this <see cref="PunctualLight"/> at <see cref="ModelRoot.LogicalPunctualLights"/>
+        /// </summary>
+        public int LogicalIndex => this.LogicalParent.LogicalPunctualLights.IndexOfReference(this);
+
+        public Vector3 Color
+        {
+            get => _color.AsValue(_colorDefault);
+            set => _color = value.AsNullable(_colorDefault);
+        }
+
+        public Double Intensity
+        {
+            get => _intensity.AsValue(_intensityDefault);
+            set => _intensity = value.AsNullable(_intensityDefault, _intensityMinimum, double.MaxValue);
+        }
+
+        public Double Range
+        {
+            get => _range.AsValue(0);
+            set => _range = value.AsNullable(0, _rangeMinimum, double.MaxValue);
+        }
+
+        public string LightType => _type;
+    }
+
+    partial class PunctualLightSpot
+    {
+        public Double InnerConeAngle
+        {
+            get => _innerConeAngle.AsValue(_innerConeAngleDefault);
+            set => _innerConeAngle = value.AsNullable(_innerConeAngleDefault, _innerConeAngleMinimum, _innerConeAngleMaximum);
+        }
+
+        public Double OuterConeAngle
+        {
+            get => _outerConeAngle.AsValue(_outerConeAngleDefault);
+            set => _outerConeAngle = value.AsNullable(_outerConeAngleDefault, _outerConeAngleMinimum, _outerConeAngleMaximum);
+        }
+    }
+
+    partial class ModelRoot
+    {
+        public IReadOnlyList<PunctualLight> LogicalPunctualLights
+        {
+            get
+            {
+                var ext = this.GetExtension<KHR_lights_punctualglTFextension>();
+                if (ext == null) return new PunctualLight[0];
+
+                return ext.GetLightsCollection(this);
+            }
+        }
+
+        /// <summary>
+        /// Creates a new <see cref="PunctualLight"/> instance.
+        /// and adds it to <see cref="ModelRoot.LogicalPunctualLights"/>.
+        /// </summary>
+        /// <param name="name">The name of the instance.</param>
+        /// <returns>A <see cref="PunctualLight"/> instance.</returns>
+        public PunctualLight CreatePunctualLight(string name = null)
+        {
+            var ext = this.GetExtension<KHR_lights_punctualglTFextension>();
+            if (ext == null)
+            {
+                ext = new KHR_lights_punctualglTFextension();
+                this.SetExtension(ext);
+            }
+
+            var light = new PunctualLight();
+            light.Name = name;
+
+            ext.GetLightsCollection(this).Add(light);
+
+            return light;
+        }
+    }
+
+    partial class KHR_lights_punctualnodeextension
+    {
+        public int LightIndex
+        {
+            get => _light;
+            set => _light = value;
+        }
+    }
+
+    partial class Node
+    {
+        public PunctualLight PunctualLight
+        {
+            get
+            {
+                var ext = this.GetExtension<KHR_lights_punctualnodeextension>();
+                if (ext == null) return null;
+
+                return this.LogicalParent.LogicalPunctualLights[ext.LightIndex];
+            }
+            set
+            {
+                if (value == null) { this.RemoveExtensions<KHR_lights_punctualnodeextension>(); return; }
+
+                Guard.MustShareLogicalParent(this, value, nameof(value));
+
+                var ext = new KHR_lights_punctualnodeextension();
+                ext.LightIndex = value.LogicalIndex;
+
+                this.SetExtension(ext);
+            }
+        }
+    }
+}

+ 9 - 1
tests/SharpGLTF.Tests/Schema2/LoadAndSave/LoadModelTests.cs

@@ -127,7 +127,7 @@ namespace SharpGLTF.Schema2.LoadAndSave
         }
 
         [Test]
-        public void TestLoadUnlitMode()
+        public void TestLoadUnlitModel()
         {
             var f = TestFiles.GetSampleFilePaths()
                 .FirstOrDefault(item => item.EndsWith(@"UnlitTest\glTF-Binary\UnlitTest.glb"));
@@ -142,8 +142,16 @@ namespace SharpGLTF.Schema2.LoadAndSave
             Assert.NotNull(modelBis);
 
             Assert.IsTrue(modelBis.LogicalMaterials[0].Unlit);
+        }
 
+        [Test]
+        public void TestLoadLightsModel()
+        {
+            var f = TestFiles.GetSchemaFilePaths()
+                .FirstOrDefault(item => item.EndsWith("lights.gltf"));
 
+            var model = GltfUtils.LoadModel(f);
+            Assert.NotNull(model);
         }
 
         #endregion

+ 16 - 1
tests/SharpGLTF.Tests/TestFiles.cs

@@ -16,6 +16,8 @@ namespace SharpGLTF
         {
             var workingDir = System.IO.Path.GetDirectoryName(typeof(TestFiles).Assembly.Location);
 
+            _SchemaDir = System.IO.Path.Combine(workingDir, "glTF-Schema");
+
             _SampleModelsDir = System.IO.Path.Combine(workingDir, "glTF-Sample-Models");
             _PollyModelsDir = System.IO.Path.Combine(workingDir, "glTF-Blender-Exporter");
             _GeneratedAssetsDir = System.IO.Path.Combine(workingDir, "glTF-Asset-Generator");
@@ -34,7 +36,8 @@ namespace SharpGLTF
 
             TestUtils.SyncronizeGitRepository("https://github.com/KhronosGroup/glTF-Sample-Models.git", _SampleModelsDir);
             TestUtils.SyncronizeGitRepository("https://github.com/KhronosGroup/glTF-Blender-Exporter.git", _PollyModelsDir);
-            TestUtils.SyncronizeGitRepository("https://github.com/bghgary/glTF-Asset-Generator.git", _GeneratedAssetsDir);            
+            TestUtils.SyncronizeGitRepository("https://github.com/bghgary/glTF-Asset-Generator.git", _GeneratedAssetsDir);
+            TestUtils.SyncronizeGitRepository("https://github.com/KhronosGroup/glTF.git", _SchemaDir);
         }
 
         #endregion
@@ -42,6 +45,8 @@ namespace SharpGLTF
         #region data
 
         private static Boolean _RemotesChecked = false;
+
+        private static readonly string _SchemaDir;
         private static readonly string _SampleModelsDir;
         private static readonly string _PollyModelsDir;
         private static readonly string _GeneratedAssetsDir;
@@ -52,6 +57,16 @@ namespace SharpGLTF
 
         #region API
 
+        public static string[] GetSchemaFilePaths()
+        {
+            var dir = System.IO.Path.Combine(_SchemaDir, "extensions", "2.0");
+
+            var gltf = System.IO.Directory.GetFiles(dir, "*.gltf", System.IO.SearchOption.AllDirectories);
+            var glbb = System.IO.Directory.GetFiles(dir, "*.glb", System.IO.SearchOption.AllDirectories);
+
+            return gltf.Concat(glbb).ToArray();            
+        }
+
         public static string[] GetSampleFilePaths()
         {
             var dir = System.IO.Path.Combine(_SampleModelsDir, "2.0");