package dyvil.tools.gensrc;

import java.io.File;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class GenSources
{
	public static final String TARGET_PREFIX = "target=";
	public static final String SOURCE_PREFIX = "source=";

	private List<Template>            templates       = new ArrayList<>();
	private Map<File, Specialization> specializations = new HashMap<>();

	private File sourceDir;
	private File targetDir;

	public static void main(String[] args)
	{
		final GenSources instance = new GenSources();
		instance.processArguments(args);
		instance.findFiles();
		instance.processTemplates();
	}

	private void processArguments(String[] args)
	{
		String sourceDir = null;
		String targetDir = null;
		for (String s : args)
		{
			if (s.startsWith(SOURCE_PREFIX))
			{
				sourceDir = s.substring(SOURCE_PREFIX.length());
			}
			else if (s.startsWith(TARGET_PREFIX))
			{
				targetDir = s.substring(TARGET_PREFIX.length());
			}
			else if (sourceDir == null)
			{
				sourceDir = s;
			}
			else if (targetDir == null)
			{
				targetDir = s;
			}
			else
			{
				System.out.println("Invalid Argument: " + s);
			}
		}

		if (sourceDir == null)
		{
			System.out.println("Missing Source Directory");
			return;
		}
		if (targetDir == null)
		{
			System.out.println("Missing Target Directory");
			return;
		}

		this.sourceDir = new File(sourceDir);
		this.targetDir = new File(targetDir);
	}

	private void findFiles()
	{
		this.findFiles(this.sourceDir, this.targetDir);
	}

	private void findFiles(File sourceDir, File targetDir)
	{
		final String[] subFiles = sourceDir.list();
		if (subFiles == null)
		{
			return;
		}

		Map<String, Template> templates = new HashMap<>();
		List<Specialization> specializations = new ArrayList<>();

		for (String subFile : subFiles)
		{
			final File sourceFile = new File(sourceDir, subFile);
			if (sourceFile.isDirectory())
			{
				this.findFiles(sourceFile, new File(targetDir, subFile));
				continue;
			}

			final int endIndex = subFile.length() - 4;
			if (subFile.endsWith(".dgt"))
			{
				final String fileName = subFile.substring(0, endIndex);
				templates.put(fileName, new Template(sourceFile, targetDir, fileName));
			}
			else if (subFile.endsWith(".dgs"))
			{
				final int dashIndex = subFile.lastIndexOf('-', endIndex);
				final String fileName = subFile.substring(0, dashIndex);
				final String specName = subFile.substring(dashIndex + 1, endIndex);

				specializations.add(new Specialization(sourceFile, fileName, specName));
			}
		}

		for (Specialization spec : specializations)
		{
			this.specializations.put(spec.getSourceFile(), spec);

			final Template template = templates.get(spec.getTemplateName());
			if (template == null)
			{
				System.out.println("Unassociated Specialization: " + spec.getSourceFile());
				continue;
			}

			template.addSpecialization(spec);
		}

		this.templates.addAll(templates.values());
	}

	private void processTemplates()
	{
		for (Specialization spec : this.specializations.values())
		{
			spec.read(this.sourceDir, this.specializations);
		}
		for (Template template : this.templates)
		{
			template.specialize();
		}
	}
}

@@ -773,37 +773,485 @@
 or (
-String s : args)%0A%09%09%7B%0A%09%09%09if (s
+int i = 0, size = args.length; i %3C size; i++)%0A%09%09%7B%0A%09%09%09final String arg = args%5Bi%5D;%0A%0A%09%09%09switch (arg)%0A%09%09%09%7B%0A%09%09%09case %22-s%22:%0A%09%09%09case %22--source%22:%0A%09%09%09%09if (++i == size)%0A%09%09%09%09%7B%0A%09%09%09%09%09System.out.println(%22Invalid -s argument: Source Directory expected%22);%0A%09%09%09%09%7D%0A%09%09%09%09else%0A%09%09%09%09%7B%0A%09%09%09%09%09sourceDir = args%5Bi%5D;%0A%09%09%09%09%7D%0A%09%09%09%09continue;%0A%09%09%09case %22-t%22:%0A%09%09%09case %22--target%22:%0A%09%09%09%09if (++i == size)%0A%09%09%09%09%7B%0A%09%09%09%09%09System.out.println(%22Invalid -t argument: Target Directory expected%22);%0A%09%09%09%09%7D%0A%09%09%09%09continue;%0A%09%09%09%7D%0A%09%09%09if (arg
 .sta
@@ -1291,25 +1291,27 @@
 sourceDir = 
-s
+arg
 .substring(S
@@ -1351,17 +1351,19 @@
 lse if (
-s
+arg
 .startsW
@@ -1403,17 +1403,19 @@
 etDir = 
-s
+arg
 .substri
@@ -1495,25 +1495,27 @@
 sourceDir = 
-s
+arg
 ;%0A%09%09%09%7D%0A%09%09%09el
@@ -1561,17 +1561,19 @@
 etDir = 
-s
+arg
 ;%0A%09%09%09%7D%0A%09
@@ -1630,17 +1630,19 @@
 nt: %22 + 
-s
+arg
 );%0A%09%09%09%7D%0A

Improve GenSources arguments