using System;
using System.Drawing;
using System.Collections;
using System.ComponentModel;
using System.Windows.Forms;

namespace DM2AE
{
	/// <summary>
	/// Summary description for Form1.
	/// </summary>
	public class Form1 : System.Windows.Forms.Form
	{
		private System.Windows.Forms.Label label1;
		private System.Windows.Forms.ComboBox comboBoxCfg;
		private System.Windows.Forms.GroupBox groupBox1;
		private System.Windows.Forms.Label label2;
		private System.Windows.Forms.TextBox textBoxFile2Open;
		private System.Windows.Forms.Label label3;
		private System.Windows.Forms.TextBox textBoxDir2Save;
		private System.Windows.Forms.GroupBox groupBox2;
		private System.Windows.Forms.Label label4;
		private System.Windows.Forms.ComboBox comboBoxEndian;
		private System.Windows.Forms.Label label5;
		private System.Windows.Forms.ComboBox comboBoxLang;
		private System.Windows.Forms.Button buttonStart;
		private System.Windows.Forms.Button buttonBrowse4Dat;
		private System.Windows.Forms.Button buttonBrowse4SaveDir;
		private System.Windows.Forms.OpenFileDialog openFileDialog1;
		private System.Windows.Forms.SaveFileDialog saveFileDialog1;
		private System.Windows.Forms.StatusBar statusBar1;
		private System.Windows.Forms.CheckBox checkBoxReadIOI;
		private System.Windows.Forms.Button buttonTest;
		private System.Windows.Forms.ComboBox comboBoxImgType;
		private System.Windows.Forms.Label label6;
		private System.Windows.Forms.CheckBox checkBoxTransparentSup;
		private System.Windows.Forms.CheckBox checkBoxDevExp;
		/// <summary>
		/// Required designer variable.
		/// </summary>
		private System.ComponentModel.Container components = null;

		public Form1()
		{
			//
			// Required for Windows Form Designer support
			//
			InitializeComponent();
		}

		/// <summary>
		/// Clean up any resources being used.
		/// </summary>
		protected override void Dispose( bool disposing )
		{
			if( disposing )
			{
				if (components != null) 
				{
					components.Dispose();
				}
			}
			base.Dispose( disposing );
		}

		#region Windows Form Designer generated code
		/// <summary>
		/// Required method for Designer support - do not modify
		/// the contents of this method with the code editor.
		/// </summary>
		private void InitializeComponent()
		{
			this.label1 = new System.Windows.Forms.Label();
			this.comboBoxCfg = new System.Windows.Forms.ComboBox();
			this.groupBox1 = new System.Windows.Forms.GroupBox();
			this.checkBoxDevExp = new System.Windows.Forms.CheckBox();
			this.checkBoxTransparentSup = new System.Windows.Forms.CheckBox();
			this.comboBoxImgType = new System.Windows.Forms.ComboBox();
			this.label6 = new System.Windows.Forms.Label();
			this.buttonBrowse4SaveDir = new System.Windows.Forms.Button();
			this.textBoxDir2Save = new System.Windows.Forms.TextBox();
			this.label3 = new System.Windows.Forms.Label();
			this.buttonBrowse4Dat = new System.Windows.Forms.Button();
			this.textBoxFile2Open = new System.Windows.Forms.TextBox();
			this.label2 = new System.Windows.Forms.Label();
			this.groupBox2 = new System.Windows.Forms.GroupBox();
			this.checkBoxReadIOI = new System.Windows.Forms.CheckBox();
			this.comboBoxLang = new System.Windows.Forms.ComboBox();
			this.label5 = new System.Windows.Forms.Label();
			this.comboBoxEndian = new System.Windows.Forms.ComboBox();
			this.label4 = new System.Windows.Forms.Label();
			this.buttonStart = new System.Windows.Forms.Button();
			this.openFileDialog1 = new System.Windows.Forms.OpenFileDialog();
			this.saveFileDialog1 = new System.Windows.Forms.SaveFileDialog();
			this.statusBar1 = new System.Windows.Forms.StatusBar();
			this.buttonTest = new System.Windows.Forms.Button();
			this.groupBox1.SuspendLayout();
			this.groupBox2.SuspendLayout();
			this.SuspendLayout();
			// 
			// label1
			// 
			this.label1.AutoSize = true;
			this.label1.Location = new System.Drawing.Point(8, 8);
			this.label1.Name = "label1";
			this.label1.Size = new System.Drawing.Size(99, 12);
			this.label1.TabIndex = 0;
			this.label1.Text = "Platform selection";
			// 
			// comboBoxCfg
			// 
			this.comboBoxCfg.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.comboBoxCfg.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
			this.comboBoxCfg.Items.AddRange(new object[] {
															 "DM2 Amiga",
															 "DM2 PC",
															 "DM2 PC9801"});
			this.comboBoxCfg.Location = new System.Drawing.Point(8, 24);
			this.comboBoxCfg.Name = "comboBoxCfg";
			this.comboBoxCfg.Size = new System.Drawing.Size(264, 20);
			this.comboBoxCfg.TabIndex = 1;
			this.comboBoxCfg.SelectedIndexChanged += new System.EventHandler(this.comboBoxCfg_SelectedIndexChanged);
			// 
			// groupBox1
			// 
			this.groupBox1.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.groupBox1.Controls.AddRange(new System.Windows.Forms.Control[] {
																					this.checkBoxDevExp,
																					this.checkBoxTransparentSup,
																					this.comboBoxImgType,
																					this.label6,
																					this.buttonBrowse4SaveDir,
																					this.textBoxDir2Save,
																					this.label3,
																					this.buttonBrowse4Dat,
																					this.textBoxFile2Open,
																					this.label2});
			this.groupBox1.Location = new System.Drawing.Point(8, 48);
			this.groupBox1.Name = "groupBox1";
			this.groupBox1.Size = new System.Drawing.Size(264, 184);
			this.groupBox1.TabIndex = 2;
			this.groupBox1.TabStop = false;
			this.groupBox1.Text = "Basic settings";
			// 
			// checkBoxDevExp
			// 
			this.checkBoxDevExp.Location = new System.Drawing.Point(8, 160);
			this.checkBoxDevExp.Name = "checkBoxDevExp";
			this.checkBoxDevExp.Size = new System.Drawing.Size(240, 16);
			this.checkBoxDevExp.TabIndex = 17;
			this.checkBoxDevExp.Text = "Expose unknown binary entries";
			// 
			// checkBoxTransparentSup
			// 
			this.checkBoxTransparentSup.Location = new System.Drawing.Point(8, 144);
			this.checkBoxTransparentSup.Name = "checkBoxTransparentSup";
			this.checkBoxTransparentSup.Size = new System.Drawing.Size(240, 16);
			this.checkBoxTransparentSup.TabIndex = 16;
			this.checkBoxTransparentSup.Text = "Transparent support (experimental)";
			// 
			// comboBoxImgType
			// 
			this.comboBoxImgType.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.comboBoxImgType.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
			this.comboBoxImgType.Items.AddRange(new object[] {
																 ".PNG files",
																 ".GIF files"});
			this.comboBoxImgType.Location = new System.Drawing.Point(8, 112);
			this.comboBoxImgType.Name = "comboBoxImgType";
			this.comboBoxImgType.Size = new System.Drawing.Size(240, 20);
			this.comboBoxImgType.TabIndex = 15;
			// 
			// label6
			// 
			this.label6.AutoSize = true;
			this.label6.Location = new System.Drawing.Point(10, 96);
			this.label6.Name = "label6";
			this.label6.Size = new System.Drawing.Size(105, 12);
			this.label6.TabIndex = 14;
			this.label6.Text = "&Image type for html";
			// 
			// buttonBrowse4SaveDir
			// 
			this.buttonBrowse4SaveDir.Anchor = (System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right);
			this.buttonBrowse4SaveDir.Location = new System.Drawing.Point(188, 72);
			this.buttonBrowse4SaveDir.Name = "buttonBrowse4SaveDir";
			this.buttonBrowse4SaveDir.Size = new System.Drawing.Size(64, 19);
			this.buttonBrowse4SaveDir.TabIndex = 5;
			this.buttonBrowse4SaveDir.Text = "B&rowse";
			this.buttonBrowse4SaveDir.Click += new System.EventHandler(this.buttonBrowse4SaveDir_Click);
			// 
			// textBoxDir2Save
			// 
			this.textBoxDir2Save.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.textBoxDir2Save.Location = new System.Drawing.Point(8, 72);
			this.textBoxDir2Save.Name = "textBoxDir2Save";
			this.textBoxDir2Save.Size = new System.Drawing.Size(168, 19);
			this.textBoxDir2Save.TabIndex = 4;
			this.textBoxDir2Save.Text = "";
			// 
			// label3
			// 
			this.label3.AutoSize = true;
			this.label3.Location = new System.Drawing.Point(8, 56);
			this.label3.Name = "label3";
			this.label3.Size = new System.Drawing.Size(147, 12);
			this.label3.TabIndex = 3;
			this.label3.Text = "&Output folder for extraction";
			// 
			// buttonBrowse4Dat
			// 
			this.buttonBrowse4Dat.Anchor = (System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right);
			this.buttonBrowse4Dat.Location = new System.Drawing.Point(188, 32);
			this.buttonBrowse4Dat.Name = "buttonBrowse4Dat";
			this.buttonBrowse4Dat.Size = new System.Drawing.Size(64, 19);
			this.buttonBrowse4Dat.TabIndex = 2;
			this.buttonBrowse4Dat.Text = "&Browse";
			this.buttonBrowse4Dat.Click += new System.EventHandler(this.buttonBrowse4Dat_Click);
			// 
			// textBoxFile2Open
			// 
			this.textBoxFile2Open.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.textBoxFile2Open.Location = new System.Drawing.Point(8, 32);
			this.textBoxFile2Open.Name = "textBoxFile2Open";
			this.textBoxFile2Open.Size = new System.Drawing.Size(168, 19);
			this.textBoxFile2Open.TabIndex = 1;
			this.textBoxFile2Open.Text = "";
			// 
			// label2
			// 
			this.label2.AutoSize = true;
			this.label2.Location = new System.Drawing.Point(8, 16);
			this.label2.Name = "label2";
			this.label2.Size = new System.Drawing.Size(88, 12);
			this.label2.TabIndex = 0;
			this.label2.Text = "GRAPHICS.&DAT";
			// 
			// groupBox2
			// 
			this.groupBox2.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.groupBox2.Controls.AddRange(new System.Windows.Forms.Control[] {
																					this.checkBoxReadIOI,
																					this.comboBoxLang,
																					this.label5,
																					this.comboBoxEndian,
																					this.label4});
			this.groupBox2.Location = new System.Drawing.Point(8, 240);
			this.groupBox2.Name = "groupBox2";
			this.groupBox2.Size = new System.Drawing.Size(264, 128);
			this.groupBox2.TabIndex = 8;
			this.groupBox2.TabStop = false;
			this.groupBox2.Text = "Advanced settings";
			this.groupBox2.Enter += new System.EventHandler(this.groupBox2_Enter);
			// 
			// checkBoxReadIOI
			// 
			this.checkBoxReadIOI.Location = new System.Drawing.Point(8, 104);
			this.checkBoxReadIOI.Name = "checkBoxReadIOI";
			this.checkBoxReadIOI.Size = new System.Drawing.Size(240, 16);
			this.checkBoxReadIOI.TabIndex = 14;
			this.checkBoxReadIOI.Text = "It has Delta-info";
			// 
			// comboBoxLang
			// 
			this.comboBoxLang.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.comboBoxLang.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
			this.comboBoxLang.Items.AddRange(new object[] {
															  "English",
															  "Japanese"});
			this.comboBoxLang.Location = new System.Drawing.Point(8, 72);
			this.comboBoxLang.Name = "comboBoxLang";
			this.comboBoxLang.Size = new System.Drawing.Size(244, 20);
			this.comboBoxLang.TabIndex = 11;
			// 
			// label5
			// 
			this.label5.AutoSize = true;
			this.label5.Location = new System.Drawing.Point(8, 56);
			this.label5.Name = "label5";
			this.label5.Size = new System.Drawing.Size(117, 12);
			this.label5.TabIndex = 10;
			this.label5.Text = "&Language of text data";
			// 
			// comboBoxEndian
			// 
			this.comboBoxEndian.Anchor = ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) 
				| System.Windows.Forms.AnchorStyles.Right);
			this.comboBoxEndian.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
			this.comboBoxEndian.Items.AddRange(new object[] {
																"LITTLE ENDIAN",
																"BIG ENDIAN"});
			this.comboBoxEndian.Location = new System.Drawing.Point(8, 32);
			this.comboBoxEndian.Name = "comboBoxEndian";
			this.comboBoxEndian.Size = new System.Drawing.Size(244, 20);
			this.comboBoxEndian.TabIndex = 9;
			// 
			// label4
			// 
			this.label4.AutoSize = true;
			this.label4.Location = new System.Drawing.Point(8, 16);
			this.label4.Name = "label4";
			this.label4.Size = new System.Drawing.Size(39, 12);
			this.label4.TabIndex = 8;
			this.label4.Text = "&Endian";
			// 
			// buttonStart
			// 
			this.buttonStart.Location = new System.Drawing.Point(8, 376);
			this.buttonStart.Name = "buttonStart";
			this.buttonStart.Size = new System.Drawing.Size(104, 40);
			this.buttonStart.TabIndex = 9;
			this.buttonStart.Text = "&Start Extraction";
			this.buttonStart.Click += new System.EventHandler(this.buttonStart_Click);
			this.buttonStart.KeyDown += new System.Windows.Forms.KeyEventHandler(this.buttonStart_KeyDown);
			// 
			// openFileDialog1
			// 
			this.openFileDialog1.DefaultExt = "dat";
			this.openFileDialog1.Filter = "DM2 GRAPHICS.DAT (*.dat)|*.dat|All (*.*)|*.*";
			// 
			// saveFileDialog1
			// 
			this.saveFileDialog1.AddExtension = false;
			this.saveFileDialog1.Filter = "Output folder for extraction (*.*)|*.*";
			this.saveFileDialog1.OverwritePrompt = false;
			// 
			// statusBar1
			// 
			this.statusBar1.Location = new System.Drawing.Point(0, 423);
			this.statusBar1.Name = "statusBar1";
			this.statusBar1.Size = new System.Drawing.Size(288, 22);
			this.statusBar1.TabIndex = 10;
			// 
			// buttonTest
			// 
			this.buttonTest.Enabled = false;
			this.buttonTest.Location = new System.Drawing.Point(120, 376);
			this.buttonTest.Name = "buttonTest";
			this.buttonTest.Size = new System.Drawing.Size(40, 40);
			this.buttonTest.TabIndex = 11;
			this.buttonTest.Text = ":P";
			this.buttonTest.Visible = false;
			this.buttonTest.Click += new System.EventHandler(this.buttonTest_Click);
			// 
			// Form1
			// 
			this.AutoScaleBaseSize = new System.Drawing.Size(5, 12);
			this.ClientSize = new System.Drawing.Size(288, 445);
			this.Controls.AddRange(new System.Windows.Forms.Control[] {
																		  this.buttonTest,
																		  this.statusBar1,
																		  this.buttonStart,
																		  this.groupBox1,
																		  this.comboBoxCfg,
																		  this.label1,
																		  this.groupBox2});
			this.Name = "Form1";
			this.Text = "Initialize - DM2AE";
			this.Closing += new System.ComponentModel.CancelEventHandler(this.Form1_Closing);
			this.Load += new System.EventHandler(this.Form1_Load);
			this.groupBox1.ResumeLayout(false);
			this.groupBox2.ResumeLayout(false);
			this.ResumeLayout(false);

		}
		#endregion

		/// <summary>
		/// The main entry point for the application.
		/// </summary>
		[STAThread]
		static void Main() 
		{
			Application.Run(new Form1());
		}

		///////////////////////////////////////////////////////////////

		protected class ExportStatistics
		{
			// 
			private System.DateTime m_pTimeBegin;
			// 
			private System.DateTime m_pTimeEnd;
			// 
			private int m_nExportImages;
			// 
			private int m_nExportHtmls;
			// 
			private int m_nExportWavs;
			// 
			private int m_nExportBins;
			// 
			private string m_sIndexHtml;

			// 
			public ExportStatistics()
			{
				m_nExportImages = m_nExportHtmls = m_nExportWavs = m_nExportBins = 0;
			}
			// 
			public void MarkBegin()
			{
				m_pTimeBegin = System.DateTime.Now;
			}
			// 
			public void MarkEnd()
			{
				m_pTimeEnd = System.DateTime.Now;
			}
			// 
			public void MarkExportedImage()
			{
				m_nExportImages++;
			}
			// 
			public void MarkExportedHtml()
			{
				m_nExportHtmls++;
			}
			// 
			public void MarkExportedWav()
			{
				m_nExportWavs++;
			}
			// 
			public void MarkExportedBin()
			{
				m_nExportBins++;
			}
			// 
			public void MarkIndexHtml(System.String sIndexHtml)
			{
				m_sIndexHtml = sIndexHtml;
			}
			// 
			public System.String Report()
			{
				System.Text.StringBuilder s = new System.Text.StringBuilder(1024);

				s.AppendFormat(""
					+ "Export work results:\r\n"
					+ "\r\n"
					+ "Work began at {0}\r\n"
					+ "Work ended at {1}\r\n"
					+ "\r\n"
					+ "It exported {3} htmls & {4} images & {5} wav files & {6} bin files.\r\n"
					+ "\r\n"
					+ "Here is location for main result page:\r\n"
					+ "{2}\r\n"
					, m_pTimeBegin
					, m_pTimeEnd
					, m_sIndexHtml
					, m_nExportHtmls
					, m_nExportImages
					, m_nExportWavs
					, m_nExportBins
					);
				s.Replace("\r\n", "\r\r\n");

				return s.ToString();
			}
		};

		protected class ExportBinMng
		{
			// 
			System.Collections.SortedList m_pMap;

			// 
			public class Basis : IComparable
			{
				// 
				public int m_iIdx;
				// 
				public Basis(int iIdx)
				{
					m_iIdx = iIdx;
				}
				// 
				public int CompareTo(object obj)
				{
					Basis p = obj as Basis;
					return m_iIdx.CompareTo(p.m_iIdx);
				}
			}

			// 
			public ExportBinMng(int nItemsMax)
			{
				m_pMap = new System.Collections.SortedList(nItemsMax);
			}
			// 
			public void Add(int iIdx)
			{
				m_pMap[new Basis(iIdx)] = null;
			}
			// 
			public Basis[] Export()
			{
				Basis[] pEntries = new Basis[m_pMap.Count];
				int i = 0;
				foreach (Basis p in m_pMap.Keys)
				{
					pEntries[i] = p;
					i++;
				}
				return pEntries;
			}
		};

		protected class ExportWavMng
		{
			// 
			System.Collections.SortedList m_pMap;

			// 
			public class Basis : IComparable
			{
				// 
				public int m_iIdx;
				// 
				public int m_iSPR;
				// 
				public Basis(int iIdx, int iSPR)
				{
					m_iIdx = iIdx; m_iSPR = iSPR;
				}
				// 
				public int CompareTo(object obj)
				{
					Basis p = obj as Basis;
					return m_iIdx.CompareTo(p.m_iIdx);
				}
			}

			// 
			public ExportWavMng(int nItemsMax)
			{
				m_pMap = new System.Collections.SortedList(nItemsMax);
			}
			// 
			public void Add(int iIdx, int iSPR)
			{
				m_pMap[new Basis(iIdx, iSPR)] = null;
			}
			// 
			public Basis[] Export()
			{
				Basis[] pEntries = new Basis[m_pMap.Count];
				int i = 0;
				foreach (Basis p in m_pMap.Keys)
				{
					pEntries[i] = p;
					i++;
				}
				return pEntries;
			}
		};

		protected class ExportImgMng
		{
			// 
			public class Key : IComparable
			{
				// 
				public int m_iIdx;
				// 
				public Key(int iIdx)
				{
					m_iIdx = iIdx;
				}
				// 
				public int CompareTo(
					object obj
					)
				{
					Key p = (Key)obj;
					if (m_iIdx < p.m_iIdx)
						return -1;
					else if (m_iIdx > p.m_iIdx)
						return +1;
					return 0;
				}
			};
			// 
			public class Val
			{
				// 
				public GDR.ChromakeySpecifier m_pMH;
				// 
				public Val(GDR.ChromakeySpecifier pMH)
				{
					m_pMH = pMH;
				}
			};
			// 
			public class Basis
			{
				// 
				public int m_iIdx;
				// 
				public GDR.ChromakeySpecifier m_pMH;
				// 
				public Basis(Key pKey, Val pVal)
				{
					m_iIdx = pKey.m_iIdx;
					m_pMH = pVal.m_pMH;
				}
			};

			// 
			private System.Collections.SortedList m_pMap;

			// 
			public ExportImgMng(int nItemsMax)
			{
				m_pMap = new System.Collections.SortedList(nItemsMax);
			}
			// 
			public void Add(Key pKey, Val pVal)
			{
				m_pMap[pKey] = pVal;
			}
			// 
			public Basis[] Export()
			{
				Basis[] pEntries = new Basis[m_pMap.Count];
				int i = 0;
				foreach (DictionaryEntry p in m_pMap)
				{
					pEntries[i] = new Basis((Key)p.Key, (Val)p.Value);
					i++;
				}
				return pEntries;
			}
		};

		///////////////////////////////////////////////////////////////

		protected void RegSerialize(
			WinIni pReg,
			string sApp,
			string sKey,
			System.Windows.Forms.Control pWnd,
			bool fSave
			)
		{
			string sWndType = pWnd.GetType().Name;
			string sVal;

			if (fSave)
			{
				switch (sWndType)
				{
					case "TextBox":
						pReg.WriteProfileString(
							sApp, 
							sKey, 
							((System.Windows.Forms.TextBox)pWnd).Text
							);
						break;
					case "ComboBox":
						System.Diagnostics.Debug.Assert(
							((System.Windows.Forms.ComboBox)pWnd).DropDownStyle == System.Windows.Forms.ComboBoxStyle.DropDownList,
							"Unexpected DropDownStyle"
							);
						pReg.WriteProfileString(
							sApp, 
							sKey, 
							((System.Windows.Forms.ComboBox)pWnd).SelectedIndex.ToString()
							);
						break;
					case "CheckBox":
						pReg.WriteProfileString(
							sApp, 
							sKey, 
							((System.Windows.Forms.CheckBox)pWnd).Checked ? "1" : "0"
							);
						break;
				}
			}
			else
			{
				switch (sWndType)
				{
					case "TextBox":
						((System.Windows.Forms.TextBox)pWnd).Text = pReg.GetProfileString(
							sApp, 
							sKey, 
							""
							);
						break;
					case "ComboBox":
						System.Diagnostics.Debug.Assert(
							((System.Windows.Forms.ComboBox)pWnd).DropDownStyle == System.Windows.Forms.ComboBoxStyle.DropDownList,
							"Unexpected DropDownStyle"
							);
						sVal = pReg.GetProfileString(
							sApp, 
							sKey, 
							""
							);
						if (sVal.Length > 0)
							((System.Windows.Forms.ComboBox)pWnd).SelectedIndex = int.Parse(sVal);
						break;
					case "CheckBox":
						sVal = pReg.GetProfileString(
							sApp, 
							sKey, 
							""
							);
						if (sVal.Length > 0)
							((System.Windows.Forms.CheckBox)pWnd).Checked = (sVal == "1") ? true : false;
						break;
				}
			}
		}

		protected static string g_sApp = "DM2AE.Initialize";

		protected void RegExchanger(bool fSave)
		{
			try
			{
				WinIni pReg = new WinIni();
				string sReg = Util.IniPath;
				pReg.LoadFrom(sReg);

				RegSerialize(pReg, g_sApp, "predefined_game_configuration", comboBoxCfg, fSave);
				RegSerialize(pReg, g_sApp, "graphics_dat", textBoxFile2Open, fSave);
				RegSerialize(pReg, g_sApp, "output_folder_for_extraction", textBoxDir2Save, fSave);
				RegSerialize(pReg, g_sApp, "endian", comboBoxEndian, fSave);
				RegSerialize(pReg, g_sApp, "language_of_text_data", comboBoxLang, fSave);
				RegSerialize(pReg, g_sApp, "image_type_for_html", comboBoxImgType, fSave);
				RegSerialize(pReg, g_sApp, "it_has_image_override_information", checkBoxReadIOI, fSave);
				RegSerialize(pReg, g_sApp, "transparent_support", checkBoxTransparentSup, fSave);
				RegSerialize(pReg, g_sApp, "expose_unknown_entries", checkBoxDevExp, fSave);

				if (fSave)
				{
					pReg.SaveTo(sReg);
				}
			}
			catch (System.ApplicationException)
			{

			}
		}

		protected bool MakeHtmlz(
			System.String sDir,
			GDR pGDR,
			GDRE0 pGDRE0,
			bool fUsePng,
			ExportImgMng pImgMng,
			ExportWavMng pWavMng,
			ExportBinMng pBinMng,
			bool fTextEN,
			bool fDiscoveryMode,
			bool fTransparentSup,
			ExportStatistics pES
			)
		{
			System.Text.StringBuilder sMux = new System.Text.StringBuilder(600000);

			string sImgExt = fUsePng ? ".png" : ".gif";
			string sWavExt = ".wav";

			for (int iCat1=0x01; iCat1<=0x1A; iCat1++)
			{
				string sParam = string.Empty;
				switch (iCat1)
				{
					case 0x01: sParam = "Interface - Main Screen"; break;
					case 0x03: sParam = "Messages"; break;
					case 0x04: sParam = "Raw Music Data"; break;
					case 0x05: sParam = "Main Menu and Credits"; break;
					case 0x06: sParam = "Credits"; break;
					case 0x07: sParam = "Interface - Character Sheet"; break;
					case 0x08: sParam = "Dungeon Graphics"; break;
					case 0x09: sParam = "Wall Ornates"; break;
					case 0x0A: sParam = "Floor Ornates"; break;
					case 0x0B: sParam = "Door Ornates"; break;
					case 0x0D: sParam = "Missiles"; break;
					case 0x0E: sParam = "Doors"; break;
					case 0x0F: sParam = "Creatures"; break;
					case 0x10: sParam = "Weapons"; break;
					case 0x11: sParam = "Clothes"; break;
					case 0x12: sParam = "Scrolls"; break;
					case 0x13: sParam = "Potions"; break;
					case 0x14: sParam = "Chests"; break;
					case 0x15: sParam = "Miscellaneous"; break;
					case 0x16: sParam = "Heroes"; break;
					case 0x17: sParam = "Skullkeep and Weather"; break;
					case 0x18: sParam = "Teleporter"; break;
					case 0x1A: sParam = "Dialog boxes"; break;
				}
				if (sParam == string.Empty)
					continue;
				sMux.Length = 0;
				//
				string[] sParamz = sParam.Split('/');
				sMux.AppendFormat(""
					+ "<html>\r\n"
					+ "<head>\r\n"
					+ "<link rel=\"stylesheet\" type=\"text/css\" href=\"DM2AE.css\">\r\n"
					+ "<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\">\r\n"
					+ "<meta name=\"GENERATOR\" content=\"DM2AE\">\r\n"
					+ "<title>{0}</title>\r\n"
					+ "</head>\r\n"
					+ "<body>\r\n"
					+ "<p><strong>{0}</strong></p>\r\n"
					, sParamz[0]
					);
				// Index
				sMux.Append("<p><strong>Index</strong></p>\r\n");
				sMux.Append("<p>\r\n");
				for (int iCat2=0; iCat2<256; iCat2++)
				{
					GDRE0.Entry[] pEntries = pGDRE0.QueryEntries(
						new GDRE0.ETP_EQ((byte)iCat1),
						new GDRE0.ETP_EQ((byte)iCat2),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS()
						);
					if (pEntries == null)
						continue;
					System.String sText = "";
					switch (iCat1)
					{
						case 0x0F:
						case 0x10:
						case 0x11:
						case 0x12:
						case 0x13:
						case 0x14:
						case 0x15:
						case 0x16:
							int[] pTextIdx3 = null;
							switch (iCat1)
							{
								case 0x0F:
									if (fTextEN)
										pTextIdx3 = new int[] {0x00, 0xF0, 0x00};
									break;
								case 0x10:
								case 0x11:
								case 0x12:
								case 0x13:
								case 0x14:
								case 0x15:
									pTextIdx3 = fTextEN
										? new int[] {0x18, 0x10, 0x00}
										: new int[] {0x18, 0x20, 0x00}
										;
									break;
								case 0x16:
									pTextIdx3 = new int[] {0x18, 0x00, 0x00};
									break;
							}
							if (pTextIdx3 != null)
							{
								GDRE0.Entry pTextEntity = pGDRE0.QueryEntry(iCat1, iCat2, 5, pTextIdx3[0], pTextIdx3[1], pTextIdx3[2]);
								if (pTextEntity != null)
								{
									GDR.Entry pEntry = pGDR.ReadEntryAt(pTextEntity.BinIdx);
									sText = Util.EncodeToHtmlText(pGDRE0.DecodeText(pEntry.Binary)).Replace("\r\n", "<br>");
								}
							}
							break;
					}
					if (sText != "")
					{
						sMux.AppendFormat(
							"<a href=\"#I{0}\">{0}:{1}</a><br>"
							, iCat2
							, sText
							);
					}
					else
					{
						sMux.AppendFormat(
							"<a href=\"#I{0}\">{0}</a><br>"
							, iCat2
							);
					}
				}
				sMux.Append("</p>\r\n");
				// Contents
				sMux.Append("<p><strong>Contents</strong></p>\r\n");
				for (int iCat2=0; iCat2<256; iCat2++)
				{
					GDRE0.Entry[] pEntries = pGDRE0.QueryEntries(
						new GDRE0.ETP_EQ((byte)iCat1),
						new GDRE0.ETP_EQ((byte)iCat2),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS(),
						new GDRE0.ETP_PASS()
						);
					if (pEntries == null)
						continue;
					sMux.AppendFormat(""
						+ "<p><a name=\"I{0}\"><strong>{0} (0x{0:X2})</strong></a></p>\r\n"
						+ "<table>\r\n"
						, iCat2
						);
					// Contents Serving
					foreach (GDRE0.Entry A in pEntries)
					{
						switch (A.Cat3)
						{
							case 0x01: // Html for Images
								sMux.AppendFormat(""
									+ "<tr><td class=\"imglc1\"><nobr>Image</nobr></td>"
									+ "<td class=\"imglc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
									, A.Binary[3]
									, A.Binary[4]
									, A.Binary[5]
									);
								sMux.AppendFormat(""
									+ "<td class=\"imglc3\"><img src=\"Img/{0:0000}{1}\"></td></tr>\r\n"
									, A.BinIdx
									, sImgExt
									);
								GDR.ChromakeySpecifier pMH = null;
								if (fTransparentSup)
								{
									switch (A.Cat1)
									{
										case 0x08: // Transparent support for Dungeon Graphics images (experimental)
											if (A.Cat4 == 0xF9)
												pMH = new GDR.ChromakeySpecifier(10);
											else if (A.Cat4 < 0x03)
												pMH = null;
											else if (A.Cat4 <= 0xFF)
											{
												GDRE0.Entry pE0 = pGDRE0.QueryEntry(A.Cat1, A.Cat2, 0x0B, 0x64, 0x00, 0x00);
												if (pE0 != null)
												{
													pMH = new GDR.ChromakeySpecifier(pE0.BinIdx);
												}
											}
											break;
										case 0x09: // Transparent support for Wall Ornate images (experimental)
										case 0x0A: // Transparent support for Floor Ornate images (experimental)
											if (A.Cat4 == 0xF9)
												pMH = new GDR.ChromakeySpecifier(10);
											else if (A.Cat4 < 0xF9)
											{
												GDRE0.Entry pE0 = pGDRE0.QueryEntry(A.Cat1, A.Cat2, 0x0B, 0x04, 0x00, 0x00);
												if (pE0 != null)
												{
													pMH = new GDR.ChromakeySpecifier(pE0.BinIdx);
												}
											}
											break;
										case 0x0D: // Transparent support for Magical effect thing images (experimental)
											//if (A.Cat4 < 0x42)
											//	pMH = new GDR.ChromakeySpecifier(10);
											//else if (A.Cat4 < 0xF9)
											//	pMH = new GDR.ChromakeySpecifier(12);
											//else if (A.Cat4 == 0xF9)
											//	pMH = new GDR.ChromakeySpecifier(10);
											break;
										case 0x0E: // Transparent support for Door images (experimental)
											if (A.Cat4 < 0x42)
											{
												GDRE0.Entry pE0 = pGDRE0.QueryEntry(A.Cat1, A.Cat2, 0x0B, 0x04, 0x00, 0x00);
												if (pE0 != null)
												{
													pMH = new GDR.ChromakeySpecifier(pE0.BinIdx);
												}
											}
											else if (A.Cat4 < 0xF9)
												pMH = new GDR.ChromakeySpecifier(12);
											break;
										case 0x0F: // Transparent support for Creature images (experimental)
											if (A.Cat4 == 0xF9)
											{
												pMH = new GDR.ChromakeySpecifier(10);
											}
											else
											{
												GDRE0.Entry pE0 = pGDRE0.QueryEntry(A.Cat1, A.Cat2, 0x0B, 0x04, 0x00, 0x00);
												if (pE0 != null)
												{
													pMH = new GDR.ChromakeySpecifier(pE0.BinIdx);
												}
											}
											break;
										case 0x10: // Transparent support for Weapon images (experimental)
										case 0x11: // Transparent support for Clothe images (experimental)
										case 0x12: // Transparent support for Scroll item images (experimental)
										case 0x13: // Transparent support for Potion images (experimental)
										case 0x15: // Transparent support for Miscellaneous item images (experimental)
											if (A.Cat4 == 0x10)
												pMH = null;
											else if (A.Cat4 < 0x10)
												pMH = new GDR.ChromakeySpecifier(10);
											else if (A.Cat4 < 0x18)
												pMH = new GDR.ChromakeySpecifier(12);
											else if (A.Cat4 < 0x40)
												pMH = new GDR.ChromakeySpecifier(12);
											else if (A.Cat4 == 0xF9)
												pMH = new GDR.ChromakeySpecifier(10);
											break;
									}
								}
								pImgMng.Add(
									new ExportImgMng.Key(A.BinIdx),
									new ExportImgMng.Val(pMH)
									);
								break;
							case 0x02: // Html for Sounds
								sMux.AppendFormat(""
									+ "<tr><td class=\"wavlc1\"><nobr>Sound</nobr></td>"
									+ "<td class=\"wavlc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
									, A.Binary[3]
									, A.Binary[4]
									, A.Binary[5]
									);
								sMux.AppendFormat(""
									+ "<td class=\"wavlc3\"><a href=\"Wav/{0:0000}{1}\">{0:0000}{1}</a></td></tr>\r\n"
									, A.BinIdx
									, sWavExt
									);
								pWavMng.Add(A.BinIdx, 11025);
								break;
							case 0x05: // Html for Text messages
								GDR.Entry pEntry = pGDR.ReadEntryAt(A.BinIdx);
								string sItemText = Util.EncodeToHtmlText(pGDRE0.DecodeText(pEntry.Binary)).Replace("\r\n", "<br>");
								sMux.Append("<tr><td class=\"txtlc1\"><nobr>Text</nobr></td>");
								sMux.AppendFormat(
									"<td class=\"txtlc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
									, A.Binary[3]
									, A.Binary[4]
									, A.Binary[5]
									);
								sMux.AppendFormat(
									"<td class=\"txtlc3\"><nobr>{0}</nobr></td></tr>\r\n"
									, sItemText
									);
								break;
							case 0x0B: // Html for variant raw value data
							case 0x0C: // Html for variant raw value data
								sMux.AppendFormat(
									"<tr><td class=\"lc1\"><nobr>{0:X2}</nobr></td>"
									, A.Cat3
									);
								sMux.AppendFormat(
									"<td class=\"lc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
									, A.Binary[3]
									, A.Binary[4]
									, A.Binary[5]
									);
								sMux.AppendFormat(
									"<td class=\"lc3\"><nobr>{0}</nobr></td></tr>\r\n"
									, (A.Cat3 == 0x0B) ? Format0BEntryText(A) : Format0CEntryText(A)
									);
								break;
							case 0x03: // Html for variant raw binary data
								if (fDiscoveryMode)
								{
									sMux.AppendFormat(
										"<tr><td class=\"lc1\"><nobr>Raw Music</nobr></td>"
										);
									sMux.AppendFormat(
										"<td class=\"lc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
										, A.Binary[3]
										, A.Binary[4]
										, A.Binary[5]
										);
									sMux.AppendFormat(
										"<td class=\"lc3\"><nobr><a class=\"txt\" href=\"bin/{0}\" target=\"_blank\">{0}</a>&nbsp;<a class=\"bin\" href=\"bin/{1}\">{1}</a></nobr></td></tr>\r\n"
										, string.Format("{0:0000}.dump.txt", A.BinIdx)
										, string.Format("{0:0000}.bin", A.BinIdx)
										, A.BinIdx
										);

									pBinMng.Add(A.BinIdx);
								}
								break;
							case 0x04: // Html for variant raw binary data
							case 0x06: // Html for variant raw binary data
							case 0x07: // Html for variant raw binary data
							case 0x08: // Html for variant raw binary data
							case 0x09: // Html for variant raw binary data
							case 0x0E: // Html for variant raw binary data
								if (fDiscoveryMode)
								{
									sMux.AppendFormat(
										"<tr><td class=\"lc1\"><nobr>{0:X2}</nobr></td>"
										, A.Cat3
										);
									sMux.AppendFormat(
										"<td class=\"lc2\"><nobr>{0:X2} {1:X2} {2:X2}</nobr></td>"
										, A.Binary[3]
										, A.Binary[4]
										, A.Binary[5]
										);
									sMux.AppendFormat(
										"<td class=\"lc3\"><nobr><a class=\"txt\" href=\"bin/{0}\" target=\"_blank\">{0}</a>&nbsp;<a class=\"bin\" href=\"bin/{1}\">{1}</a></nobr></td></tr>\r\n"
										, string.Format("{0:0000}.dump.txt", A.BinIdx)
										, string.Format("{0:0000}.bin", A.BinIdx)
										, A.BinIdx
										);

									pBinMng.Add(A.BinIdx);
								}
								break;
						}
					}
					//
					sMux.Append(""
						+ "</table>\r\n"
						);
				}
				sMux.Append(""
					+ "</body>\r\n"
					+ "</html>\r\n"
					);
				//
				string sHtmlPathName = Util.JoinPath(sDir, sParamz[0]+".html");
				if (!WriteHtmlTo(sHtmlPathName, sMux.ToString()))
				{
					return false;
				}
				pES.MarkExportedHtml();
			}

			if (true) // index.html
			{
				sMux.Length = 0;
				sMux.Append(""
					+ "<html>\r\n"
					+ "<head><title>DM2</title></head>\r\n"
					+ "<body>\r\n"
					+ "<p><strong>DM2</strong></p>\r\n"
					);
				string[] sTables = "Interface - Main Screen/Messages/Raw Music Data/Main Menu and Credits/Credits/Interface - Character Sheet/Dungeon Graphics/Wall Ornates/Floor Ornates/Door Ornates/Missiles/Doors/Creatures/Weapons/Clothes/Scrolls/Potions/Chests/Miscellaneous/Heroes/Skullkeep and Weather/Teleporter/Dialog boxes".Split('/');
				foreach (string sTable in sTables)
				{
					sMux.AppendFormat(""
						+ "<p><a href=\"{0}.html\" target=\"_blank\">{0}</a></p>\r\n"
						, sTable
						);
				}
				sMux.Append(""
					+ "</body>\r\n"
					+ "</html>\r\n"
					);
				string sHtmlPathName = Util.JoinPath(sDir, "index.html");
				if (!WriteHtmlTo(sHtmlPathName, sMux.ToString()))
				{
					return false;
				}
				pES.MarkIndexHtml(sHtmlPathName);
				pES.MarkExportedHtml();
			}
			if (true) // DM2AE.css
			{
				sMux.Length = 0;
				sMux.Append("td.lc1\r\n{\r\n\tbackground-color: #e4e2e1;\r\n}\r\ntd.lc2\r\n{\r\n\tfont-family: Courier New;\r\n\tbackground-color: #dcdcdc;\r\n}\r\ntd.lc3\r\n{\r\n\t\r\n}\r\ntd.imglc1\r\n{\r\n\tbackground-color: #e4e2e1;\r\n}\r\ntd.imglc2\r\n{\r\n\tfont-family: Courier New;\r\n\tbackground-color: #dcdcdc;\r\n}\r\ntd.imglc3\r\n{\r\n\t\r\n}\r\ntd.wavlc1\r\n{\r\n\tbackground-color: #e4e2e1;\r\n}\r\ntd.wavlc2\r\n{\r\n\tfont-family: Courier New;\r\n\tbackground-color: #dcdcdc;\r\n}\r\ntd.wavlc3\r\n{\r\n\t\r\n}\r\ntd.txtlc1\r\n{\r\n\tbackground-color: #e4e2e1;\r\n}\r\ntd.txtlc2\r\n{\r\n\tfont-family: Courier New;\r\n\tbackground-color: #dcdcdc;\r\n}\r\ntd.txtlc3\r\n{\r\n\t\r\n}\r\na.bin\r\n{\r\n\tfont-size: 75%\r\n}\r\na.txt\r\n{\r\n\tfont-size: 75%\r\n}\r\n");
				string sHtmlPathName = Util.JoinPath(sDir, "DM2AE.css");
				if (!WriteHtmlTo(sHtmlPathName, sMux.ToString()))
				{
					return false;
				}
			}

			return true;
		}

		protected void ReportExportStatistics(
			ExportStatistics pES
			)
		{
			Form2 form2 = new Form2();
			form2.Init(pES.Report());
			form2.ShowDialog();
		}

		protected bool ExportImagez(
			string sDir,
			GDR pGDR,
			bool fUsePng,
			ExportImgMng pImgMng,
			ExportStatistics pES
			)
		{
			try
			{
				sDir = Util.JoinPath(sDir, "Img");
				System.IO.Directory.CreateDirectory(sDir);
				string sExt = fUsePng ? ".png" : ".gif";

				ExportImgMng.Basis[] pImgbs = pImgMng.Export();
				foreach (ExportImgMng.Basis pImgb in pImgbs)
				{
					int iIdx = pImgb.m_iIdx;

					System.Diagnostics.Debug.WriteLine("----------\nTrying:" + iIdx.ToString());

					System.Drawing.Bitmap pImg;
					GDR.ChromakeySpecifier pMH = pImgb.m_pMH;

					if (pGDR.ReadEntryAsImage(iIdx, pMH, out pImg) && pImg != null)
					{
						//System.Diagnostics.Debug.WriteLine("Done.");

						string sImg = Util.JoinPath(sDir, iIdx.ToString("0000")) + sExt;
						pImg.Save(
							sImg,
							(fUsePng) ? System.Drawing.Imaging.ImageFormat.Png : System.Drawing.Imaging.ImageFormat.Gif
							);
						pImg.Dispose();

						pES.MarkExportedImage();
					}
					else
					{
						//System.Diagnostics.Debug.WriteLine("Failed.");
					}
				}
				return true;
			}
			catch(System.Exception err)
			{
				System.Diagnostics.Debug.WriteLine(err.Message);
			}
			return false;
		}

		protected bool WriteHtmlTo(
			string sPathName,
			string sHtml
			)
		{
			try
			{
				System.Byte[] pBinary = System.Text.Encoding.UTF8.GetBytes(sHtml);
				System.IO.Stream pFileInto = System.IO.File.OpenWrite(sPathName);
				pFileInto.Write(pBinary, 0, pBinary.Length);
				pFileInto.SetLength(pFileInto.Position);
				pFileInto.Close();
				return true;
			}
			catch(System.Exception err)
			{
				System.Diagnostics.Debug.WriteLine(err.Message);
			}
			return false;
		}

		protected bool ExportBinz(
			System.String sDestDir,
			GDR pGDR,
			ExportBinMng pBinMng,
			ExportStatistics pES
			)
		{
			try
			{
				string sDir = Util.JoinPath(sDestDir, "Bin");
				System.IO.Directory.CreateDirectory(sDir);
				string sExtBin = ".bin";
				string sExtTxt = ".dump.txt";

				ExportBinMng.Basis[] pBinbs = pBinMng.Export();
				foreach (ExportBinMng.Basis pBinb in pBinbs)
				{
					int iIdx = pBinb.m_iIdx;

					DM2AE.GDR.Entry pEntry = pGDR.ReadEntryAt(iIdx);
					if (pEntry != null)
					{
						string sFilePathBin = Util.JoinPath(sDir, string.Format("{0:0000}{1}", iIdx, sExtBin));
						string sFilePathTxt = Util.JoinPath(sDir, string.Format("{0:0000}{1}", iIdx, sExtTxt));

						System.IO.Stream pFileInto = System.IO.File.OpenWrite(sFilePathBin);
						pFileInto.Write(pEntry.Binary, 0, pEntry.Binary.Length);
						pFileInto.SetLength(pFileInto.Position);
						pFileInto.Close();

						Util.SaveBDTo(sFilePathTxt, pEntry.Binary);

						pES.MarkExportedBin();
					}
				}
				return true;
			}
			catch (System.Exception err)
			{
				System.Diagnostics.Debug.WriteLine(err.Message);
			}
			return false;
		}

		protected bool ExportWavez(
			System.String sDestDir,
			GDR pGDR,
			ExportWavMng pWavMng,
			bool fLittleEndian,
			ExportStatistics pES
			)
		{
			try
			{
				string sDir = Util.JoinPath(sDestDir, "Wav");
				System.IO.Directory.CreateDirectory(sDir);
				string sExt = ".wav";

				ExportWavMng.Basis[] pWavbs = pWavMng.Export();
				foreach (ExportWavMng.Basis pWavb in pWavbs)
				{
					int iIdx = pWavb.m_iIdx;

					System.Byte[] pWav;
					if (pGDR.ReadEntryAsSound(iIdx, out pWav))
					{
						string sWav = Util.JoinPath(sDir, iIdx.ToString("0000")) + sExt;
						System.IO.Stream pFileInto = System.IO.File.OpenWrite(sWav);
						pFileInto.Write(pWav, 0, pWav.Length);
						pFileInto.SetLength(pFileInto.Position);
						pFileInto.Close();

						pES.MarkExportedWav();
					}
				}
				return true;
			}
			catch(System.Exception err)
			{
				System.Diagnostics.Debug.WriteLine(err.Message);
			}
			return false;
		}

		static protected string Format0CEntryText(
			GDRE0.Entry pEntry
			)
		{
			return string.Format("{0:X2} {1:X2}", pEntry.Binary[6], pEntry.Binary[7]);
		}

		static protected System.String Format0BEntryText(
			GDRE0.Entry pEntry
			)
		{
			System.Text.StringBuilder sText = new System.Text.StringBuilder(64);
			int nValue = pEntry.Binary[6] * 256 + pEntry.Binary[7];
			int nCase = pEntry.Cat4 + pEntry.Cat5 * 256 + pEntry.Cat6 * 65536;
			switch (pEntry.Cat1)
			{
				case 0x08: // Dungeon Graphics
					switch (nCase)
					{
						case 0x000064: // 0B - 00 00 64 : Transparent color index
							sText.AppendFormat(
								"<strong>Index of Transparent color: {0}</strong>"
								, nValue
								);
							return sText.ToString();
					}
					break;
				case 0x09: // Wall Ornates
				case 0x0A: // Floor Ornates
					switch (nCase)
					{
						case 0x000004: // 0B - 00 00 04 : Transparent color index
							sText.AppendFormat(
								"<strong>Index of Transparent color: {0}</strong>"
								, nValue
								);
							return sText.ToString();
					}
					break;
				case 0x0E: // Doors
					switch (nCase)
					{
						case 0x000004: // 0B - 00 00 04 : Transparent color index inner part
							sText.AppendFormat(
								"<strong>Index of Transparent color for inside part: {0}</strong>"
								, nValue
								);
							return sText.ToString();
						case 0x000012: // 0B - 00 00 12 : Transparent color index outer part
							sText.AppendFormat(
								"<strong>Index of Transparent color for outside part: {0}</strong>"
								, nValue
								);
							return sText.ToString();
					}
					break;
				case 0x0F: // Creatures
					switch (nCase)
					{
						case 0x000004: // 0B - 00 00 04 : Transparent color index
							sText.AppendFormat(
								"<strong>Index of Transparent color: {0}</strong>"
								, nValue
								);
							return sText.ToString();
					}
					break;
				case 0x10:
				case 0x11:
				case 0x12:
				case 0x13:
				case 0x14:
				case 0x15:
					switch (nCase)
					{
						case 0x000001: // 0B - 00 00 01 : Weight
							sText.AppendFormat(
								"<strong>Weight: {0}.{1}kg</strong>"
								, nValue / 10
								, nValue % 10
								);
							return sText.ToString();
						case 0x000002: // 0B - 00 00 02 : Money value
							sText.AppendFormat(
								"<strong>Money value: {0}</strong>&nbsp;&nbsp;({1})"
								, nValue
								, FormatMoneyValueText(nValue)
								);
							return sText.ToString();
						case 0x000003: // 0B - 00 00 03 : Food value
							sText.AppendFormat(
								"<strong>Food value: {0}</strong>"
								, nValue
								);
							return sText.ToString();
						case 0x000004: // 0B - 00 00 04 : Equip, Portability
							System.String sType = System.String.Empty;
							System.String sContainer = System.String.Empty;
							if ((nValue & 0x0001) != 0) sType += "Helm|";
							if ((nValue & 0x0002) != 0) sType += "Neckless|";
							if ((nValue & 0x0004) != 0) sType += "Wear or Plate|";
							if ((nValue & 0x0008) != 0) sType += "Pants|";
							if ((nValue & 0x0010) != 0) sType += "Boots|";
							if ((nValue & 0x0020) != 0) sContainer += "Left 2 Pouches|";
							if ((nValue & 0x0040) != 0) sContainer += "Right 4 Pouches|";
							if ((nValue & 0x0080) != 0) sContainer += "Right first Pouch|";
							if ((nValue & 0x8000) == 0) sContainer += "Chest or Bag|";
							//if ((nValue & 0x0100) != 0) sContainer += "0x0100|";
							//if ((nValue & 0x0200) != 0) sContainer += "0x0200|";
							//if ((nValue & 0x0400) != 0) sContainer += "0x0400|";
							//if ((nValue & 0x0800) != 0) sContainer += "0x0800|";
							//if ((nValue & 0x1000) != 0) sContainer += "0x1000|";
							//if ((nValue & 0x2000) != 0) sContainer += "0x2000|";
							//if ((nValue & 0x4000) != 0) sContainer += "0x4000|";
							System.String sLine;
							System.String[] sAttrs;

							sAttrs = sType.Split('|'); sLine = System.String.Empty;
							foreach (System.String s in sAttrs)
							{
								if (s.Length < 1) continue;
								if (sLine.Length > 0) sLine = sLine + ", ";
								sLine = sLine + s;
							}
							if (sLine.Length > 0) sText.AppendFormat("<strong>Equip: {0}</strong><br>", sLine);

							sAttrs = sContainer.Split('|'); sLine = System.String.Empty;
							foreach (System.String s in sAttrs)
							{
								if (s.Length < 1) continue;
								if (sLine.Length > 0) sLine = sLine + ", ";
								sLine = sLine + s;
							}
							sText.AppendFormat("<strong>Portability: {0}</strong><br>", sLine);

							return sText.ToString();
						case 0x000008: // 0B - 00 00 08 : Attack strength (for Weapons)
							sText.AppendFormat(
								"<strong>Attack strength: {0}</strong>"
								, nValue
								);
							return sText.ToString();
						case 0x000009: // 0B - 00 00 09 : Throw strength (for Weapons)
							sText.AppendFormat(
								"<strong>Throw strength: {0}</strong>"
								, nValue
								);
							return sText.ToString();
						case 0x00000A: // 0B - 00 00 0A : Accuracy (for Weapons)
							sText.AppendFormat(
								"<strong>Accuracy: {0}</strong>"
								, nValue
								);
							return sText.ToString();
						case 0x00000B: // 0B - 00 00 0B : Sharp resistance, Armor strength (for Clothes)
							sText.AppendFormat(
								"<strong>Sharp resistance: {0}</strong><br><strong>Armor strength: {1}</strong>"
								, nValue / 256
								, nValue % 256
								);
							return sText.ToString();
						case 0x000014: // 0B - 00 00 14 : MANA bonus
						case 0x000016: // 0B - 00 00 16 : Strength bonus
						case 0x000017: // 0B - 00 00 17 : Dexterity bonus
						case 0x000019: // 0B - 00 00 19 : Vitality bonus
						case 0x00001A: // 0B - 00 00 1A : Anti-magic bonus
						case 0x00001B: // 0B - 00 00 1B : Anti-fire bonus
							if (nValue < 0x10)
							{
								System.String sItem = System.String.Empty;
								switch (pEntry.Cat4)
								{
									case 0x14: sItem = "MANA"; break;
									case 0x16: sItem = "Strength"; break;
									case 0x17: sItem = "Dexterity"; break;
									case 0x19: sItem = "Vitality"; break;
									case 0x1A: sItem = "Anti-magic"; break;
									case 0x1B: sItem = "Anti-fire"; break;
								}
								sText.AppendFormat(
									"<strong>Equipment bonus: {0} +{1}</strong>"
									, sItem
									, nValue
									);
								return sText.ToString();
							}
							break;
					}
					break;
			}
			sText.Length = 0;
			sText.AppendFormat(
				"{0:X2} {1:X2}"
				, pEntry.Binary[6]
				, pEntry.Binary[7]
				);
			return sText.ToString();
		}

		static System.String FormatMoneyValueText(
			int nValue
			)
		{
			if (nValue < 1) return "Not for trade?";
			System.Text.StringBuilder sText = new System.Text.StringBuilder(32);
			int[] nChips = new int[] {
										 (nValue / 4 / 4 / 4 / 4 / 4) % 4,
										 (nValue / 4 / 4 / 4 / 4) % 4,
										 (nValue / 4 / 4 / 4) % 4,
										 (nValue / 4 / 4) % 4,
										 (nValue / 4) % 4,
										 (nValue) % 4
									 };
			System.String[] sNames = "Blue gem/Red gem/Green gem/Gold coin/Silver coin/Copper coin".Split('/');
			for (int i = 0; i < 6; i++)
			{
				if (nChips[i] != 0)
				{
					if (sText.Length > 0) sText.Append(", ");
					sText.AppendFormat(
						nChips[i] < 2 ? "{0} {1}" : "{0} {1}s"
						, nChips[i]
						, sNames[i]
						);
				}
			}
			return sText.ToString();
		}

		///////////////////////////////////////////////////////////////

		private void Form1_Load(object sender, System.EventArgs e)
		{
			RegExchanger(false);
		}

		private void groupBox2_Enter(object sender, System.EventArgs e)
		{
		
		}

		private void Form1_Closing(object sender, System.ComponentModel.CancelEventArgs e)
		{
			RegExchanger(true);
		}

		private void comboBoxCfg_SelectedIndexChanged(object sender, System.EventArgs e)
		{
			switch (comboBoxCfg.SelectedIndex)
			{
				case 0:
					comboBoxEndian.SelectedIndex = 1;
					comboBoxLang.SelectedIndex = 0;
					checkBoxReadIOI.Checked = true;
					break;
				case 1:
					comboBoxEndian.SelectedIndex = 0;
					comboBoxLang.SelectedIndex = 0;
					checkBoxReadIOI.Checked = false;
					break;
				case 2:
					comboBoxEndian.SelectedIndex = 0;
					comboBoxLang.SelectedIndex = 1;
					checkBoxReadIOI.Checked = true;
					break;
			}
		}

		private void buttonStart_Click(object sender, System.EventArgs e)
		{
			System.Windows.Forms.DialogResult rb = System.Windows.Forms.MessageBox.Show(""
				+"This will generate some html pages and extract much images for browsing with Web Browser.\r\n"
				+"\r\n"
				+"It takes some minutes or much hours to complete & you cannot stop once extractor begins to work.\r\n"
				+"If extraction work finishes successfully, a report window appears.\r\n"
				+"\r\n"
				+"Would you retry?"
				,
				this.Text,
				System.Windows.Forms.MessageBoxButtons.RetryCancel,
				System.Windows.Forms.MessageBoxIcon.Exclamation
				);
			if (rb != System.Windows.Forms.DialogResult.Retry)
				return;

			Update();

			bool fLittleEndian = comboBoxEndian.SelectedIndex == 0;
			bool fTextEN = comboBoxLang.SelectedIndex == 0;
			bool fUsePng = comboBoxImgType.SelectedIndex == 0;
			bool fReadImageOverri = checkBoxReadIOI.Checked;
			bool fDiscoveryMode = checkBoxDevExp.Checked;
			bool fTransparentSup = checkBoxTransparentSup.Checked;

			statusBar1.Text = string.Empty;

			Cursor = System.Windows.Forms.Cursors.WaitCursor;

			GDR pGDR = new GDR();
			try
			{
				ExportStatistics pES = new ExportStatistics();
				pES.MarkBegin();
				if (!pGDR.OpenRead(textBoxFile2Open.Text, fLittleEndian))
					throw(new System.ApplicationException("ERR while opening file."));
				if (fReadImageOverri && !pGDR.ReadImageOverriderEntryAt(1))
					throw(new System.ApplicationException("ERR while dealing with Image-overrider information."));
				GDR.Entry pE0 = pGDR.ReadEntryAt(0);
				GDRE0 pGDRE0 = new GDRE0();
				if (!pGDRE0.Init(pE0.Binary, fLittleEndian, fTextEN))
					throw(new System.ApplicationException("ERR while initializing Category Database"));
				if (!pGDRE0.ReadAltTextFrom(Util.GetNeighborFile("DM2AE.text.ini")))
					throw(new System.ApplicationException("ERR while dealing with DM2AE.text.ini"));
				ExportImgMng pImgMng = new ExportImgMng(pGDR.PlaceHolders.Length);
				ExportWavMng pWavMng = new ExportWavMng(pGDR.PlaceHolders.Length);
				ExportBinMng pBinMng = new ExportBinMng(pGDR.PlaceHolders.Length);
				if (!MakeHtmlz(textBoxDir2Save.Text, pGDR, pGDRE0, fUsePng, pImgMng, pWavMng, pBinMng, fTextEN, fDiscoveryMode, fTransparentSup, pES))
					throw(new System.ApplicationException("ERR while generating htmls"));
				if (!ExportBinz(textBoxDir2Save.Text, pGDR, pBinMng, pES))
					throw(new System.ApplicationException("ERR while exporting raw binaries"));
				if (!ExportWavez(textBoxDir2Save.Text, pGDR, pWavMng, fLittleEndian, pES))
					throw(new System.ApplicationException("ERR while exporting images"));
				if (!ExportImagez(textBoxDir2Save.Text, pGDR, fUsePng, pImgMng, pES))
					throw(new System.ApplicationException("ERR while exporting images"));

				statusBar1.Text = "OK!";

				pES.MarkEnd();
				ReportExportStatistics(pES);
			}
			catch(System.Exception err)
			{
				statusBar1.Text = err.Message;

				System.Diagnostics.Debug.WriteLine(err.Message);
			}
			finally
			{
				pGDR.Close();

				Cursor = System.Windows.Forms.Cursors.Default;
			}
		}

		private void buttonBrowse4Dat_Click(object sender, System.EventArgs e)
		{
			openFileDialog1.FileName = textBoxFile2Open.Text;

			System.Windows.Forms.DialogResult r;
			r = openFileDialog1.ShowDialog();
			if (r == System.Windows.Forms.DialogResult.OK)
			{
				textBoxFile2Open.Text = openFileDialog1.FileName;
			}
		}

		private void buttonBrowse4SaveDir_Click(object sender, System.EventArgs e)
		{
			saveFileDialog1.FileName = Util.JoinPath(Util.GetDir(textBoxDir2Save.Text), "(DIR)");

			System.Windows.Forms.DialogResult r;
			r = saveFileDialog1.ShowDialog();
			if (r == System.Windows.Forms.DialogResult.OK)
			{
				textBoxDir2Save.Text = Util.GetDir(saveFileDialog1.FileName);
			}
		}

		private System.Drawing.Imaging.ImageCodecInfo findMimeTypeEncoder(
			string sMime
			)
		{
			System.Drawing.Imaging.ImageCodecInfo[] ps = System.Drawing.Imaging.ImageCodecInfo.GetImageEncoders();
			foreach (System.Drawing.Imaging.ImageCodecInfo p in ps)
			{
				if (p.MimeType == sMime)
					return p;
			}
			return null;
		}

		private void buttonTest_Click(object sender, System.EventArgs e)
		{
#if DEBUG
			statusBar1.Text = string.Empty;
			try
			{
				GDR pGDR = new GDR();
				if (!pGDR.OpenRead(textBoxFile2Open.Text, comboBoxEndian.SelectedIndex == 0))
					throw (new System.ApplicationException("ERR"));
				if (checkBoxReadIOI.Checked && !pGDR.ReadImageOverriderEntryAt(1))
					throw (new System.ApplicationException("ERR"));
				System.Drawing.Bitmap pImg;
				int[] iImgs = new int[] {2982};
				foreach (int i in iImgs)
				{
					if (!pGDR.ReadEntryAsImage(i, null, out pImg))
						throw (new System.ApplicationException("ERR"));
					System.Drawing.Imaging.EncoderParameters pEPs = new System.Drawing.Imaging.EncoderParameters(1);
					pEPs.Param[0] = new System.Drawing.Imaging.EncoderParameter(System.Drawing.Imaging.Encoder.ColorDepth, 24L);
					pImg.Save("\\"+ i.ToString("0000") +".png", findMimeTypeEncoder("image/png"), pEPs);
				}
			}
			catch (System.Exception err)
			{
				statusBar1.Text = err.Message;
			}
#endif
		}

		private void buttonStart_KeyDown(object sender, System.Windows.Forms.KeyEventArgs e)
		{
			switch (e.KeyCode)
			{
				case System.Windows.Forms.Keys.BrowserFavorites:
					buttonTest.Enabled = true;
					buttonTest.Visible = true;
					break;
			}
		}
	}
}
