KSP-Conformal-Decals/Source/ConformalDecals/MaterialModifiers/MaterialPropertyCollection.cs

114 lines
4.7 KiB
C#
Raw Normal View History

2020-05-27 22:19:46 +00:00
using System;
using System.Collections.Generic;
using UnityEngine;
namespace ConformalDecals.MaterialModifiers {
public class MaterialPropertyCollection : ScriptableObject {
public TextureMaterialProperty MainTextureProperty { get; set; }
2020-05-30 04:02:58 +00:00
public Material parsedMaterial;
2020-05-27 22:19:46 +00:00
public bool UseBaseNormal { get; private set; }
private List<MaterialProperty> _materialProperties;
private List<TextureMaterialProperty> _textureMaterialProperties;
2020-05-27 22:19:46 +00:00
public String BaseNormalSrc { get; private set; }
public String BaseNormalDest { get; private set; }
2020-05-30 04:02:58 +00:00
private const string _normalTextureName = "_BumpMap";
2020-05-27 22:19:46 +00:00
public void Initialize(ConfigNode node, PartModule module) {
2020-05-27 22:19:46 +00:00
2020-05-30 04:02:58 +00:00
// Initialize fields
_materialProperties = new List<MaterialProperty>();
_textureMaterialProperties = new List<TextureMaterialProperty>();
2020-05-27 22:19:46 +00:00
2020-05-30 04:02:58 +00:00
// Get shader
var shaderString = node.GetValue("shader") ?? throw new FormatException("Missing shader name in material");
2020-05-27 22:19:46 +00:00
2020-05-30 04:02:58 +00:00
var shaderRef = Shabby.Shabby.FindShader(shaderString);
// note to self: null coalescing does not work on UnityEngine classes
if (shaderRef == null) {
throw new FormatException($"Shader not found: '{shaderString}'");
}
2020-05-27 22:19:46 +00:00
parsedMaterial = new Material(shaderRef);
2020-05-27 22:19:46 +00:00
2020-05-30 04:02:58 +00:00
// Get useBaseNormal value
var useBaseNormalString = node.GetValue("useBaseNormal");
if (useBaseNormalString != null) {
if (bool.TryParse(useBaseNormalString, out var useBaseNormalRef)) {
UseBaseNormal = useBaseNormalRef;
}
else {
throw new FormatException($"Improperly formatted bool value for 'useBaseNormal' : {useBaseNormalString}");
}
}
else {
UseBaseNormal = false;
}
2020-05-30 04:02:58 +00:00
// Get basenormal source and destination property names
BaseNormalSrc = node.GetValue("baseNormalSource") ?? _normalTextureName;
BaseNormalDest = node.GetValue("baseNormalDestination") ?? _normalTextureName;
// Parse all materialProperties
2020-05-27 22:19:46 +00:00
foreach (ConfigNode propertyNode in node.nodes) {
try {
MaterialProperty property;
2020-05-27 22:19:46 +00:00
switch (propertyNode.name) {
case "FLOAT":
property = new FloatMaterialProperty(propertyNode);
2020-05-27 22:19:46 +00:00
break;
case "COLOR":
property = new ColorMaterialProperty(propertyNode);
2020-05-27 22:19:46 +00:00
break;
case "TEXTURE":
property = new TextureMaterialProperty(propertyNode);
var textureModifier = (TextureMaterialProperty) property;
2020-05-27 22:19:46 +00:00
if (textureModifier.IsMain) {
2020-05-30 04:02:58 +00:00
if (MainTextureProperty == null) {
MainTextureProperty = textureModifier;
2020-05-27 22:19:46 +00:00
}
else {
2020-05-27 22:49:17 +00:00
// multiple textures have been marked as main!
// non-fatal issue, ignore this one and keep using current main texture
module.LogWarning(
2020-05-27 22:19:46 +00:00
$"Material texture property {textureModifier.TextureUrl} is marked as main, but material already has a main texture! \n" +
2020-05-30 04:02:58 +00:00
$"Defaulting to {MainTextureProperty.TextureUrl}");
2020-05-27 22:19:46 +00:00
}
}
2020-05-30 04:02:58 +00:00
_textureMaterialProperties.Add(textureModifier);
2020-05-27 22:19:46 +00:00
break;
default:
throw new FormatException($"Invalid property type '{propertyNode.name}' in material");
}
2020-05-30 04:02:58 +00:00
_materialProperties.Add(property);
property.Modify(parsedMaterial);
2020-05-27 22:19:46 +00:00
}
catch (Exception e) {
2020-05-27 22:49:17 +00:00
// Catch exception from parsing current material property
// And print it to the log as an Error
2020-05-30 07:16:40 +00:00
module.LogException("Exception while parsing material node", e);
2020-05-27 22:19:46 +00:00
}
}
module.Log($"Parsed {_materialProperties.Count} properties");
2020-05-27 22:19:46 +00:00
}
2020-05-30 04:02:58 +00:00
public void UpdateMaterial(Vector2 scale) {
foreach (var textureProperty in _textureMaterialProperties) {
textureProperty.UpdateScale(parsedMaterial, scale);
2020-05-30 04:02:58 +00:00
}
}
2020-05-27 22:19:46 +00:00
}
}