Merge branch 'main' into feature-better-tweakables

Probably breaks everything
This commit is contained in:
2022-03-14 21:48:48 -07:00
18 changed files with 574 additions and 222 deletions

View File

@ -1,11 +1,11 @@
<Project Sdk="Microsoft.NET.Sdk">
<?xml version="1.0" ?><Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net48</TargetFramework>
<LangVersion>8</LangVersion>
<IsPackable>false</IsPackable>
<PlatformTarget>x64</PlatformTarget>
<NoWarn>1701;1702;CS0649;CS1591</NoWarn>
<AssemblyVersion>0.2.7</AssemblyVersion>
<AssemblyVersion>9.9.9</AssemblyVersion>
</PropertyGroup>
<ItemGroup>
@ -36,23 +36,23 @@
</ItemGroup>
<ItemGroup>
<Compile Remove="dlls\**" />
<Compile Remove="dlls\**"/>
</ItemGroup>
<ItemGroup>
<EmbeddedResource Remove="dlls\**" />
<EmbeddedResource Remove="dlls\**"/>
</ItemGroup>
<ItemGroup>
<None Remove="dlls\**" />
<None Remove="dlls\**"/>
</ItemGroup>
<ItemGroup>
<None Include="..\.editorconfig" />
</ItemGroup>
<Target Name="PostBuild" AfterTargets="PostBuildEvent">
<Exec Command="/bin/cp -v '$(OutDir)ConformalDecals.dll' '$(SolutionDir)../GameData/ConformalDecals/Plugins'" />
<Exec Command="/bin/cp -v '$(OutDir)ConformalDecals.dll' '$(SolutionDir)../GameData/ConformalDecals/Plugins/ConformalDecals.dll'" IgnoreExitCode="true"/>
<!--Fuck you MSBuild stop trying to run CMD.exe on macOS-->
</Target>
</Project>

View File

@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;
using ConformalDecals.Text;
using ConformalDecals.Util;
using TMPro;
@ -9,6 +10,7 @@ namespace ConformalDecals {
public static class DecalConfig {
private static Texture2D _blankNormal;
private static List<string> _shaderBlacklist;
private static List<Regex> _shaderRegexBlacklist;
private static Dictionary<string, DecalFont> _fontList;
private static int _decalLayer = 31;
private static bool _selectableInFlight;
@ -55,7 +57,17 @@ namespace ConformalDecals {
}
public static bool IsBlacklisted(string shaderName) {
return _shaderBlacklist.Contains(shaderName);
if (_shaderBlacklist.Contains(shaderName)) return true;
foreach (var regex in _shaderRegexBlacklist) {
if (regex.IsMatch(shaderName)) {
_shaderBlacklist.Add(shaderName);
Logging.Log($"Caching blacklisted shader name '{shaderName}' which matches '{regex}'");
return true;
}
}
return false;
}
public static bool IsLegacy(string shaderName, out string newShader, out string[] keywords) {
@ -88,6 +100,10 @@ namespace ConformalDecals {
foreach (var shaderName in blacklist.GetValuesList("shader")) {
_shaderBlacklist.Add(shaderName);
}
foreach (var shaderRegex in blacklist.GetValuesList("shaderRegex")) {
_shaderRegexBlacklist.Add(new Regex(shaderRegex));
}
}
var allFonts = Resources.FindObjectsOfTypeAll<TMP_FontAsset>();
@ -121,13 +137,14 @@ namespace ConformalDecals {
// ReSharper disable once UnusedMember.Global
public static void ModuleManagerPostLoad() {
_shaderBlacklist = new List<string>();
_shaderRegexBlacklist = new List<Regex>();
_fontList = new Dictionary<string, DecalFont>();
var configs = GameDatabase.Instance.GetConfigs("CONFORMALDECALS");
if (configs.Length > 0) {
Logging.Log("Loading config");
foreach (var config in configs) {
Logging.Log($"loading config node '{config.url}'");
ParseConfig(config.config);
}
}
@ -143,4 +160,4 @@ namespace ConformalDecals {
_blankNormal = MakeBlankNormal();
}
}
}
}

View File

@ -441,12 +441,14 @@ namespace ConformalDecals {
}
}
/// Setup decal by calling update functions relevent for the current situation
protected virtual void SetupDecal() {
if (HighLogic.LoadedSceneIsEditor) {
// Update tweakables in editor mode
UpdateTweakables();
}
// find all valid renderers
var renderers = part.parent.FindModelComponents<MeshRenderer>();
foreach (var renderer in renderers) {
// skip disabled renderers
if (renderer.gameObject.activeInHierarchy == false) continue;
// skip blacklisted shaders
if (DecalConfig.IsBlacklisted(renderer.material.shader)) continue;
if (HighLogic.LoadedSceneIsGame) {
UpdateAll();
@ -671,4 +673,4 @@ namespace ConformalDecals {
}
}
}
}
}

View File

@ -22,35 +22,64 @@ namespace ConformalDecals {
return string.IsNullOrEmpty(part.flagURL) ? HighLogic.CurrentGame.flagURL : part.flagURL;
}
// If we are not in game, use the default flag (for icon rendering)
return DefaultFlag;
}
}
public override void OnLoad(ConfigNode node) {
base.OnLoad(node);
// Since OnLoad is called for all modules, we only need to update this module
// Updating symmetry counterparts would be redundent
UpdateFlag();
}
public override void OnStart(StartState state) {
base.OnStart(state);
if (HighLogic.LoadedSceneIsGame) {
GameEvents.onMissionFlagSelect.Add(OnEditorFlagSelected);
}
if (HighLogic.LoadedSceneIsEditor) {
// Register flag change event
GameEvents.onMissionFlagSelect.Add(OnEditorFlagSelected);
// Register reset button event
Events[nameof(ResetFlag)].guiActiveEditor = useCustomFlag;
}
// Since OnStart is called for all modules, we only need to update this module
// Updating symmetry counterparts would be redundent
UpdateFlag();
}
public override void OnDestroy() {
GameEvents.onMissionFlagSelect.Remove(OnEditorFlagSelected);
if (HighLogic.LoadedSceneIsEditor) {
// Unregister flag change event
GameEvents.onMissionFlagSelect.Remove(OnEditorFlagSelected);
}
base.OnDestroy();
}
[KSPEvent(guiActive = false, guiActiveEditor = true, guiName = "#LOC_ConformalDecals_gui-select-flag")]
public void SelectFlag() {
var flagBrowser = (Instantiate((Object) (new FlagBrowserGUIButton(null, null, null, null)).FlagBrowserPrefab) as GameObject)?.GetComponent<FlagBrowser>();
if (flagBrowser is { }) flagBrowser.OnFlagSelected = OnCustomFlagSelected;
// Button for selecting a flag
// This is a bit of a hack to bring up the stock flag selection menu
// When its done, it calls OnCustomFlagSelected()
// ReSharper disable once PossibleNullReferenceException
var flagBrowser = (Instantiate((Object) (new FlagBrowserGUIButton(null, null, null, null)).FlagBrowserPrefab) as GameObject).GetComponent<FlagBrowser>();
flagBrowser.OnFlagSelected = OnCustomFlagSelected;
}
[KSPEvent(guiActive = false, guiActiveEditor = true, guiName = "#LOC_ConformalDecals_gui-reset-flag")]
public void ResetFlag() {
// we are no longer using a custom flag, so instead use the mission or agency flag
useCustomFlag = false;
flagUrl = "Mission";
UpdateFlag(true);
// disable the reset button, since it no longer makes sense
Events[nameof(ResetFlag)].guiActiveEditor = false;
flagUrl = MissionFlagUrl;
useCustomFlag = false;
@ -64,33 +93,55 @@ namespace ConformalDecals {
}
private void OnCustomFlagSelected(FlagBrowser.FlagEntry newFlagEntry) {
// Callback for when a flag is selected in the menu spawned by SelectFlag()
// we are now using a custom flag with the URL of the new flag entry
useCustomFlag = true;
flagUrl = newFlagEntry.textureInfo.name;
UpdateFlag(true);
// make sure the reset button is now available
Events[nameof(ResetFlag)].guiActiveEditor = true;
flagUrl = newFlagEntry.textureInfo.name;
useCustomFlag = true;
UpdateAll();
foreach (var decal in part.symmetryCounterparts.Select(o => o.GetComponent<ModuleConformalFlag>())) {
decal.Events[nameof(ResetFlag)].guiActiveEditor = true;
decal.flagUrl = flagUrl;
decal.useCustomFlag = true;
decal.UpdateAll();
private void OnEditorFlagSelected(string newFlagUrl) {
if (!useCustomFlag) {
flagUrl = newFlagUrl;
// Since this callback is called for all modules, we only need to update this module
// Updating symmetry counterparts would be redundent
UpdateFlag();
}
}
private void OnEditorFlagSelected(string newFlagUrl) {
if (!useCustomFlag) UpdateAll();
}
protected override void UpdateTextures() {
_flagTextureProperty ??= materialProperties.AddOrGetTextureProperty("_Decal", true);
base.UpdateTextures();
if (useCustomFlag) {
_flagTextureProperty.TextureUrl = flagUrl;
// Update the displayed flag texture for this decal or optionally any symmetry counterparts
private void UpdateFlag(bool recursive = false) {
// get the decal material property for the decal texture
var textureProperty = materialProperties.AddOrGetTextureProperty("_Decal", true);
if(useCustomFlag) {
// set the texture to the custom flag
textureProperty.TextureUrl = flagUrl;
}
else {
_flagTextureProperty.TextureUrl = MissionFlagUrl;
// set the texture to the mission flag
textureProperty.TextureUrl = MissionFlagUrl;
}
UpdateMaterials();
UpdateScale();
if (recursive) {
// for each symmetry counterpart, copy this part's properties and update it in turn
foreach (var counterpart in part.symmetryCounterparts) {
var decal = counterpart.GetComponent<ModuleConformalFlag>();
decal.useCustomFlag = useCustomFlag;
decal.flagUrl = flagUrl;
decal.UpdateFlag();
}
}
}
}
}
}

View File

@ -281,6 +281,9 @@ namespace ConformalDecals {
// Render text
var newText = new DecalText(text, font, style, vertical, lineSpacing, charSpacing);
var output = TextRenderer.UpdateText(_currentText, newText);
// update the _currentText state variable
// this is the ONLY place this variable should be set! otherwise the current state is lost
_currentText = newText;
_decalTextureProperty.Texture = output.Texture;
@ -317,4 +320,4 @@ namespace ConformalDecals {
base.UpdateTweakables();
}
}
}
}