Merge pull request #187 from slimbuck/rgba-swizzle

General RGBA swizzle param
diff --git a/basisu_comp.cpp b/basisu_comp.cpp
index 7b5bbe9..7f39a66 100644
--- a/basisu_comp.cpp
+++ b/basisu_comp.cpp
@@ -70,9 +70,13 @@
 			PRINT_BOOL_VALUE(m_read_source_images);
 			PRINT_BOOL_VALUE(m_write_output_basis_files);
 			PRINT_BOOL_VALUE(m_compute_stats);
-			PRINT_BOOL_VALUE(m_check_for_alpha)
-			PRINT_BOOL_VALUE(m_force_alpha)
-			PRINT_BOOL_VALUE(m_seperate_rg_to_color_alpha);
+			PRINT_BOOL_VALUE(m_check_for_alpha);
+			PRINT_BOOL_VALUE(m_force_alpha);
+			debug_printf("swizzle: %d,%d,%d,%d\n",
+				m_params.m_swizzle[0],
+				m_params.m_swizzle[1],
+				m_params.m_swizzle[2],
+				m_params.m_swizzle[3]);
 			PRINT_BOOL_VALUE(m_renormalize);
 			PRINT_BOOL_VALUE(m_multithreading);
 			PRINT_BOOL_VALUE(m_disable_hierarchical_endpoint_codebooks);
@@ -402,19 +406,25 @@
 			if (m_params.m_renormalize)
 				file_image.renormalize_normal_map();
 
-			if (m_params.m_seperate_rg_to_color_alpha)
+			bool alpha_swizzled = false;
+			if (m_params.m_swizzle[0] != 0 ||
+				m_params.m_swizzle[1] != 1 ||
+				m_params.m_swizzle[2] != 2 ||
+				m_params.m_swizzle[3] != 3)
 			{
-				// Used for XY normal maps in RG - puts X in color, Y in alpha
+				// Apply swizzle to incoming data
 				for (uint32_t y = 0; y < file_image.get_height(); y++)
 					for (uint32_t x = 0; x < file_image.get_width(); x++)
 					{
 						const color_rgba &c = file_image(x, y);
-						file_image(x, y).set_noclamp_rgba(c.r, c.r, c.r, c.g);
+						file_image(x, y).set_noclamp_rgba(c[m_params.m_swizzle[0]], c[m_params.m_swizzle[1]], c[m_params.m_swizzle[2]], c[m_params.m_swizzle[3]]);
 					}
+
+				alpha_swizzled = m_params.m_swizzle[3] != 3;
 			}
-						
+
 			bool has_alpha = false;
-			if ((m_params.m_force_alpha) || (m_params.m_seperate_rg_to_color_alpha))
+			if (m_params.m_force_alpha || alpha_swizzled)
 				has_alpha = true;
 			else if (!m_params.m_check_for_alpha)
 				file_image.set_alpha(255);
diff --git a/basisu_comp.h b/basisu_comp.h
index 5672039..aa77bef 100644
--- a/basisu_comp.h
+++ b/basisu_comp.h
@@ -236,7 +236,10 @@
 			m_check_for_alpha.clear();
 			m_force_alpha.clear();
 			m_multithreading.clear();
-			m_seperate_rg_to_color_alpha.clear();
+			m_swizzle[0] = 0;
+			m_swizzle[1] = 1;
+			m_swizzle[2] = 2;
+			m_swizzle[3] = 3;
 			m_renormalize.clear();
 			m_hybrid_sel_cb_quality_thresh.clear();
 			m_global_pal_bits.clear();
@@ -336,9 +339,9 @@
 		// Always put alpha slices in the output basis file, even when the input doesn't have alpha
 		bool_param<false> m_force_alpha; 
 		bool_param<true> m_multithreading;
-		
-		// Split the R channel to RGB and the G channel to alpha, then write a basis file with alpha channels
-		bool_param<false> m_seperate_rg_to_color_alpha;
+
+		// Swizzle incoming channels
+		char m_swizzle[4];
 
 		bool_param<false> m_renormalize;
 
diff --git a/basisu_tool.cpp b/basisu_tool.cpp
index fdca902..3591ed2 100644
--- a/basisu_tool.cpp
+++ b/basisu_tool.cpp
@@ -99,6 +99,7 @@
 		" -no_alpha: Always output non-alpha basis files, even if one or more inputs has alpha\n"
 		" -force_alpha: Always output alpha basis files, even if no inputs has alpha\n"
 		" -separate_rg_to_color_alpha: Separate input R and G channels to RGB and A (for tangent space XY normal maps)\n"
+		" -swizzle rgba: Specify swizzle for the 4 input color channels using r, g, b and a (the -separate_rg_to_color_alpha flag is equivalent to rrrg)\n"
 		" -renorm: Renormalize each input image before any further processing/compression\n"
 		" -no_multithreading: Disable multithreading\n"
 		" -no_ktx: Disable KTX writing when unpacking (faster)\n"
@@ -407,8 +408,40 @@
 			else if (strcasecmp(pArg, "-force_alpha") == 0)
 				m_comp_params.m_force_alpha = true;
 			else if ((strcasecmp(pArg, "-separate_rg_to_color_alpha") == 0) ||
-			        (strcasecmp(pArg, "-seperate_rg_to_color_alpha") == 0)) // was mispelled for a while - whoops!
-				m_comp_params.m_seperate_rg_to_color_alpha = true;
+					(strcasecmp(pArg, "-seperate_rg_to_color_alpha") == 0)) // was mispelled for a while - whoops!
+			{
+				m_comp_params.m_swizzle[0] = 0;
+				m_comp_params.m_swizzle[1] = 0;
+				m_comp_params.m_swizzle[2] = 0;
+				m_comp_params.m_swizzle[3] = 1;
+			}
+			else if (strcasecmp(pArg, "-swizzle") == 0)
+			{
+				REMAINING_ARGS_CHECK(1);
+				const char *swizzle = arg_v[arg_index + 1];
+				if (strlen(swizzle) != 4)
+				{
+					error_printf("Swizzle requires exactly 4 characters\n");
+					return false;
+				}
+				for (int i=0; i<4; ++i)
+				{
+					if (swizzle[i] == 'r')
+						m_comp_params.m_swizzle[i] = 0;
+					else if (swizzle[i] == 'g')
+						m_comp_params.m_swizzle[i] = 1;
+					else if (swizzle[i] == 'b')
+						m_comp_params.m_swizzle[i] = 2;
+					else if (swizzle[i] == 'a')
+						m_comp_params.m_swizzle[i] = 3;
+					else
+					{
+						error_printf("Swizzle must be one of [rgba]");
+						return false;
+					}
+				}
+				arg_count++;
+			}
 			else if (strcasecmp(pArg, "-renorm") == 0)
 				m_comp_params.m_renormalize = true;
 			else if (strcasecmp(pArg, "-no_multithreading") == 0)