Command line argument parsing added, general logging cleanup. Buildchain improvements
10
.idea/.idea.SDFMapCreator/.idea/riderPublish.xml
generated
Normal file
@@ -0,0 +1,10 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="LocationsWithSilentDeleteHolder">
|
||||
<option name="locations">
|
||||
<list>
|
||||
<option value="$PROJECT_DIR$/SDFMapCreator/publish/win-x64" />
|
||||
</list>
|
||||
</option>
|
||||
</component>
|
||||
</project>
|
||||
@@ -1,7 +1,7 @@
|
||||
<component name="ProjectRunConfigurationManager">
|
||||
<configuration default="false" name="SDFMapCreator" type="DotNetProject" factoryName=".NET Project">
|
||||
<option name="EXE_PATH" value="$PROJECT_DIR$/SDFMapCreator/bin/Release/net8.0/SDFMapCreator" />
|
||||
<option name="PROGRAM_PARAMETERS" value="" />
|
||||
<configuration default="false" name="Run SDF Tool" type="DotNetProject" factoryName=".NET Project" focusToolWindowBeforeRun="true">
|
||||
<option name="EXE_PATH" value="$PROJECT_DIR$/SDFMapCreator/bin/Release/net8.0/SDFMapTool" />
|
||||
<option name="PROGRAM_PARAMETERS" value="-d -D "./images" -o "./sdf.png" -i "01.png;02.png;03.png;04.png;05.png;06.png;07.png;08.png"" />
|
||||
<option name="WORKING_DIRECTORY" value="$PROJECT_DIR$/SDFMapCreator/bin/Release/net8.0" />
|
||||
<option name="PASS_PARENT_ENVS" value="1" />
|
||||
<option name="USE_EXTERNAL_CONSOLE" value="0" />
|
||||
@@ -14,7 +14,8 @@
|
||||
<option name="PROJECT_KIND" value="DotNetCore" />
|
||||
<option name="PROJECT_TFM" value="net8.0" />
|
||||
<method v="2">
|
||||
<option name="Build" />
|
||||
<option name="Build" default="false" projectName="SDFMapCreator" projectPath="$PROJECT_DIR$/SDFMapCreator/SDFMapCreator.csproj" />
|
||||
<option name="RunConfigurationTask" enabled="true" run_configuration_name="Copy Images To TestDirs" run_configuration_type="ShConfigurationType" />
|
||||
</method>
|
||||
</configuration>
|
||||
</component>
|
||||
@@ -12,5 +12,6 @@ Global
|
||||
{915A479D-55CC-4B48-B7C0-75E0B8978698}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{915A479D-55CC-4B48-B7C0-75E0B8978698}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{915A479D-55CC-4B48-B7C0-75E0B8978698}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{915A479D-55CC-4B48-B7C0-75E0B8978698}.Debug|Any CPU.Deploy.0 = Debug|Any CPU
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
|
||||
@@ -1,15 +1,40 @@
|
||||
using System.Diagnostics;
|
||||
using System.Numerics;
|
||||
using System.Runtime.CompilerServices;
|
||||
using CommandLine;
|
||||
|
||||
namespace SDFMapCreator;
|
||||
|
||||
public class Options {
|
||||
[Option('d', "debug", Required = false, HelpText = "Enable debug mode.")]
|
||||
public bool Debug { get; set; } = false;
|
||||
[Option('D', "imgDirectory", Required = true, HelpText = "Input Images directory.")]
|
||||
public string ImgDirectory { get; set; } = "images";
|
||||
[Option('i', "images", Required = true, HelpText = "Images file names separated by ';' and in the correct order.")]
|
||||
public string Images { get; set; } = "";
|
||||
[Option('o', "output", Required = true, HelpText = "Output file path.")]
|
||||
public string OutputFile { get; set; } = "output.png";
|
||||
[Option('b', "blur", Required = false, HelpText = "How many blur iterations to run.")]
|
||||
public int BlurIterations { get; set; } = 10;
|
||||
[Option('r', "radius", Required = false, HelpText = "Blur radius.")]
|
||||
public float BlurRadius { get; set; } = 100f;
|
||||
[Option('s', "step", Required = false, HelpText = "Blur step size.")]
|
||||
public float BlurStep { get; set; } = 0.5f;
|
||||
[Option("sigma", Required = false, HelpText = "Blur sigma value (weighting).")]
|
||||
public float BlurSigma { get; set; } = 1f;
|
||||
}
|
||||
|
||||
public static class Program {
|
||||
#region Magic Values
|
||||
const float MAX = 1f;
|
||||
const float MIN = 0f;
|
||||
static readonly int MAX_THREADS = Environment.ProcessorCount - 2;
|
||||
static bool debug = true;
|
||||
static readonly ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = MAX_THREADS };
|
||||
static char PSep => Path.DirectorySeparatorChar;
|
||||
#endregion
|
||||
|
||||
static Options options = null!;
|
||||
|
||||
static List<Image> Images = new();
|
||||
static List<MaskData> ImageMasks = new();
|
||||
static List<TransitionMaskData> TransitionMasks = new();
|
||||
@@ -22,23 +47,32 @@ public static class Program {
|
||||
static void ConsoleUpdateLine(string s) => Console.Write("\r" + s);
|
||||
|
||||
public static void Main(string[] args) {
|
||||
Console.WriteLine("Reading images...");
|
||||
var parser = Parser.Default;
|
||||
|
||||
if (debug) {
|
||||
if (!Directory.Exists("Debug")) Directory.CreateDirectory("Debug");
|
||||
parser.ParseArguments<Options>(args)
|
||||
.WithParsed(o => options = o)
|
||||
.WithNotParsed(o => {
|
||||
Environment.Exit(1);
|
||||
});
|
||||
|
||||
string debugPath = $"{Environment.CurrentDirectory}{PSep}Debug";
|
||||
if (options.Debug) {
|
||||
if (!Directory.Exists(debugPath)) Directory.CreateDirectory(debugPath);
|
||||
Console.WriteLine("Debug mode enabled.");
|
||||
}
|
||||
|
||||
|
||||
var imagesPath = "images";
|
||||
for (var i = 0; i < 8; i++) {
|
||||
var pixels = ImageUtil.LoadImage<Vector3>($"./{imagesPath}{Path.DirectorySeparatorChar}{i + 1:00}.png");
|
||||
Console.WriteLine("Reading images...");
|
||||
var imageNames = options.Images.Split(';');
|
||||
for (var i = 0; i < imageNames.GetLength(0); i++) {
|
||||
string imgPath = $"{options.ImgDirectory}{PSep}{imageNames[i]}";
|
||||
ConsoleUpdateLine($"Reading image {imgPath}");
|
||||
var pixels = ImageUtil.LoadImage<Vector3>(imgPath);
|
||||
Images.Add(new(pixels, pixels.GetLength(0), pixels.GetLength(1)));
|
||||
}
|
||||
|
||||
Console.WriteLine("\n");
|
||||
//check if all the images in Images are the same resolution
|
||||
if (Images.Select(img => (img.Width, img.Height)).Distinct().Count() > 1) {
|
||||
Console.WriteLine("Error: Not all images have the same resolution.");
|
||||
Console.WriteLine("\nError: Not all images have the same resolution.");
|
||||
Environment.Exit(1);
|
||||
}
|
||||
|
||||
@@ -46,7 +80,8 @@ public static class Program {
|
||||
height = (uint)Images[0].Height;
|
||||
|
||||
// sum all images together
|
||||
if(debug) Images[0].Pixels.SaveImage("Debug/Sum0.png");
|
||||
var sumPath = $"{debugPath}{PSep}Sum";
|
||||
if(options.Debug) Images[0].Pixels.SaveImage($"{sumPath}0.png");
|
||||
|
||||
for (int i = 1; i < Images.Count; i++) {
|
||||
for (int x = 0; x < Images[i].Width; x++) {
|
||||
@@ -56,18 +91,19 @@ public static class Program {
|
||||
Images[i].Pixels[x, y].Z = MathF.Min(Images[i - 1].Pixels[x, y].Z + Images[i].Pixels[x, y].X, MAX);
|
||||
}
|
||||
}
|
||||
|
||||
if(debug)Images[i].Pixels.SaveImage($"Debug/Sum{i}.png");
|
||||
if(options.Debug)Images[i].Pixels.SaveImage($"{sumPath}{i}.png");
|
||||
}
|
||||
|
||||
|
||||
Console.WriteLine("Creating masks...");
|
||||
Console.WriteLine("\nCreating masks...");
|
||||
for (var i = 0; i < Images.Count; i++) { //for each image pair, create a mask
|
||||
ConsoleUpdateLine($"Creating mask {i}...");
|
||||
|
||||
var selfMask = SelfMask(Images[i].Pixels);
|
||||
ImageMasks.Add(new(selfMask, Images[i], new()));
|
||||
if (debug) selfMask.SaveImage($"Debug/selfMask{i}.png");
|
||||
if (options.Debug) selfMask.SaveImage($"{debugPath}{PSep}selfMask{i}.png");
|
||||
|
||||
if (i >= Images.Count - 1) continue;
|
||||
ConsoleUpdateLine($"Creating mask {i}...");
|
||||
|
||||
var mask = GetABMask(Images[i].Pixels, Images[i + 1].Pixels);
|
||||
TransitionMasks.Add(new(mask, Images[i], Images[i + 1]));
|
||||
}
|
||||
@@ -78,15 +114,16 @@ public static class Program {
|
||||
ConsoleUpdateLine($"Edge detecting mask {ImageMasks.IndexOf(mask)}...");
|
||||
EdgeDetect(mask);
|
||||
}
|
||||
if (debug)
|
||||
|
||||
if (options.Debug)
|
||||
for (var i = 0; i < TransitionMasks.Count; i++)
|
||||
ImageMasks[i].Mask.SaveImage($"Debug/mask{i}.png");
|
||||
ImageMasks[i].Mask.SaveImage($"{debugPath}{PSep}mask{i}.png");
|
||||
|
||||
Console.WriteLine("Creating SDFs...");
|
||||
for (var i = 0; i < ImageMasks.Count; i++) {
|
||||
var mask = ImageMasks[i];
|
||||
SDFs.Add(SDF(mask));
|
||||
if (debug) SDFs[i].SDF.SaveImage($"Debug/sdf{i}.png");
|
||||
if (options.Debug) SDFs[i].SDF.SaveImage($"{debugPath}{PSep}sdf{i}.png");
|
||||
}
|
||||
|
||||
Console.WriteLine("Creating gradients...");
|
||||
@@ -94,7 +131,7 @@ public static class Program {
|
||||
ConsoleUpdateLine($"Generating gradient {i}...");
|
||||
var gradientData = Gradient(TransitionMasks[i], SDFs[i], SDFs[i + 1]);
|
||||
Gradients.Add(gradientData);
|
||||
if (debug) gradientData.SaveImage($"Debug/gradient{i}.png");
|
||||
if (options.Debug) gradientData.SaveImage($"{debugPath}{PSep}gradient{i}.png");
|
||||
}
|
||||
|
||||
// generate final image
|
||||
@@ -110,7 +147,7 @@ public static class Program {
|
||||
for (var i = 0; i < Gradients.Count; i++) {
|
||||
var mask = ImageMasks[i + 1];
|
||||
var gradient = Gradients[i];
|
||||
Console.WriteLine($"Applying gradient {i}..., {currStep} -> {currStep + stepIncrement}");
|
||||
Console.WriteLine($"Applying gradient {i}..., Step: {currStep:F2} -> Next: {(currStep + stepIncrement):F2}");
|
||||
for (var x = 0; x < mask.Mask.GetLength(0); x++) {
|
||||
for (var y = 0; y < mask.Mask.GetLength(1); y++) {
|
||||
if (mask.Mask[x,y].X == 0) continue;
|
||||
@@ -122,21 +159,21 @@ public static class Program {
|
||||
currStep += stepIncrement;
|
||||
}
|
||||
|
||||
finalImage.SaveImage("Debug/Final.png");
|
||||
finalImage.SaveImage($"{options.OutputFile}.png");
|
||||
|
||||
// apply directional blur
|
||||
var iterations = 1;
|
||||
var radius = 100f;
|
||||
var step = .5f;
|
||||
var sigma = 1f;
|
||||
var iterations = options.BlurIterations;
|
||||
var radius = options.BlurRadius;
|
||||
var step = options.BlurStep;
|
||||
var sigma = options.BlurSigma;
|
||||
var totalMask = SelfMask(Images[^1].Pixels);
|
||||
totalMask.SaveImage("Debug/TotalMask.png");
|
||||
totalMask.SaveImage($"{debugPath}{PSep}TotalMask.png");
|
||||
for (var i = 0; i < iterations; i++) {
|
||||
Console.WriteLine($"Applying directional blur {i + 1}/{iterations}...");
|
||||
finalImage = DirectionalBlur(finalImage, totalMask, radius, step, sigma);
|
||||
}
|
||||
|
||||
finalImage.SaveImage("finalBlur.png");
|
||||
finalImage.SaveImage(options.OutputFile);
|
||||
Console.WriteLine("Done!");
|
||||
}
|
||||
|
||||
|
||||
@@ -21,59 +21,59 @@
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Update="1.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="2.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="TestPattern.png">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\01.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\02.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\03.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\04.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\05.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\06.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\07.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\08.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherecut.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherecut.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherefull.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherecut32.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherehalf.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\sphereempty.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherehalf32.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherefull.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherefull32.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherefull32.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="spherecut32.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherehalf.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="sphereempty.png">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<None Update="images\spherehalf32.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\TestPattern.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\1.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="images\2.png">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
@@ -25,19 +25,19 @@ public partial class SdfKernels {
|
||||
Console.WriteLine("Reading available accelerators (CUDA only)...");
|
||||
foreach (var device in gpuContext.GetCudaDevices()) {
|
||||
using var accelerator = device.CreateAccelerator(gpuContext);
|
||||
Console.WriteLine($"{GetInfoString(accelerator)}");
|
||||
Console.WriteLine($"Found accelerator: {accelerator.Name} {accelerator.AcceleratorType}");
|
||||
}
|
||||
|
||||
Console.WriteLine("Reading available accelerators (OpenCL only)...");
|
||||
foreach (var device in gpuContext.GetCLDevices()) {
|
||||
using var accelerator = device.CreateAccelerator(gpuContext);
|
||||
Console.WriteLine($"{GetInfoString(accelerator)}");
|
||||
Console.WriteLine($"Found accelerator: {accelerator.Name} {accelerator.AcceleratorType}");
|
||||
}
|
||||
|
||||
Console.WriteLine("Reading available accelerators (CPU only)...");
|
||||
foreach (var device in gpuContext.GetCPUDevices()) {
|
||||
using var accelerator = device.CreateAccelerator(gpuContext);
|
||||
Console.WriteLine($"{GetInfoString(accelerator)}");
|
||||
Console.WriteLine($"Found accelerator: {accelerator.Name} {accelerator.AcceleratorType}");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
9
SDFMapCreator/copyImages.sh
Normal file
@@ -0,0 +1,9 @@
|
||||
if [ -d ./bin/Debug/net8.0/ ]; then
|
||||
echo "Copying images to bin/Debug"
|
||||
cp -r ./images ./bin/Debug/net8.0/
|
||||
fi
|
||||
|
||||
if [ -d ./bin/Release/net8.0/ ]; then
|
||||
echo "Copying images to bin/Release"
|
||||
cp -r ./images ./bin/Release/net8.0/
|
||||
fi
|
||||
|
Before Width: | Height: | Size: 2.7 KiB After Width: | Height: | Size: 2.7 KiB |
|
Before Width: | Height: | Size: 3.1 KiB After Width: | Height: | Size: 3.1 KiB |
|
Before Width: | Height: | Size: 1.3 KiB After Width: | Height: | Size: 1.3 KiB |
|
Before Width: | Height: | Size: 8.4 KiB After Width: | Height: | Size: 8.4 KiB |
|
Before Width: | Height: | Size: 680 B After Width: | Height: | Size: 680 B |
|
Before Width: | Height: | Size: 11 KiB After Width: | Height: | Size: 11 KiB |
|
Before Width: | Height: | Size: 11 KiB After Width: | Height: | Size: 11 KiB |
|
Before Width: | Height: | Size: 693 B After Width: | Height: | Size: 693 B |
|
Before Width: | Height: | Size: 6.7 KiB After Width: | Height: | Size: 6.7 KiB |
|
Before Width: | Height: | Size: 540 B After Width: | Height: | Size: 540 B |