Skip to content

Instantly share code, notes, and snippets.

@ikskuh
Created January 28, 2020 22:25
Show Gist options
  • Save ikskuh/a4fba18f346e5a6806921b07d9c15564 to your computer and use it in GitHub Desktop.
Save ikskuh/a4fba18f346e5a6806921b07d9c15564 to your computer and use it in GitHub Desktop.
HDRP Mask Map Generator
/**
* Licence: MIT
* Author: Felix Queißner, 2020
*
* Compile with:
* csc /out:Generator.cs /r:System.Drawing.dll Generator.cs
*
* Usage:
* Execute with a single file argument, this tool will generate a mask map for
* the Unity HDRP shader set. It assumes that the required files exist with
* the corresponding file postfixes (_metallic, _ao, _detail, _roughness).
*
* The file that is used as an argument is read in, and all channels are replaced
* by either the default (255) or the corresponding pixel from the map file (if any).
*
* The pixel mapping done is the following:
* | Parameter | Channel | Postfixes |
* | Metallic | R | _metallic |
* | AO | G | _ao |
* | Detail mask | B | _detail |
* | Smoothness | A | _roughness, _smoothness |
*
* This tool will then create a new file "filename_mask.ext" that will replace the original
* postfix with `_mask` and keep all other settings.
*
* Pro Tip for Windows: Put a link to the file into the `shell:sendto`-Folder to allow simpe generation
* by using `Right Click → Send To → HDRP MaskMap Generator`.
*/
using System;
using System.Drawing;
using System.IO;
class Program
{
static string[] postfixes = new[]{
"_metallic",
"_normal",
"_albedo",
"_ao",
"_detail",
"_roughness",
"_height",
};
static void PixelMap(Bitmap _out, string fileIn, Func<Color, int, Color> mapper)
{
using (var src = new Bitmap(fileIn))
{
for (int y = 0; y < src.Height; y++)
{
for (int x = 0; x < src.Width; x++)
{
var s = src.GetPixel(x, y);
var d = _out.GetPixel(x, y);
var c = mapper(d, s.R);
_out.SetPixel(x, y, c);
}
}
}
}
[STAThread]
static int Main(string[] args)
{
if (args.Length != 1)
return 1;
var path = Path.GetDirectoryName(args[0]);
var ext = Path.GetExtension(args[0]);
var name = Path.GetFileNameWithoutExtension(args[0]);
int i;
for (i = 0; i < postfixes.Length; i++)
{
if (name.EndsWith(postfixes[i]))
{
name = name.Substring(0, name.Length - postfixes[i].Length);
break;
}
}
if (i == postfixes.Length)
return 1;
using (var any = new Bitmap(args[0]))
{
using (var g = Graphics.FromImage(any))
g.Clear(Color.White);
if (File.Exists(path + "/" + name + "_metallic" + ext))
PixelMap(any, path + "/" + name + "_metallic" + ext, (rgb, v) => Color.FromArgb(rgb.A, v, rgb.G, rgb.B));
if (File.Exists(path + "/" + name + "_ao" + ext))
PixelMap(any, path + "/" + name + "_ao" + ext, (rgb, v) => Color.FromArgb(rgb.A, rgb.R, v, rgb.B));
if (File.Exists(path + "/" + name + "_detail" + ext))
PixelMap(any, path + "/" + name + "_detail" + ext, (rgb, v) => Color.FromArgb(rgb.A, rgb.R, rgb.G, v));
if (File.Exists(path + "/" + name + "_roughness" + ext))
PixelMap(any, path + "/" + name + "_roughness" + ext, (rgb, v) => Color.FromArgb(255 - v, rgb.R, rgb.G, rgb.B));
if (File.Exists(path + "/" + name + "_smoothness" + ext))
PixelMap(any, path + "/" + name + "_smoothness" + ext, (rgb, v) => Color.FromArgb(v, rgb.R, rgb.G, rgb.B));
any.Save(path + "/" + name + "_mask" + ext);
}
return 0;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment