Esempio n. 1
0
    public void OnSetPath()
    {
        bool validVSROM = (LBA.checkVSROM(pathInput.text) != null);

        if (pathInput && validVSROM)
        {
            conf.VSPath = pathInput.text;
            Memory.SaveConfig(conf);
            Hide(pathCG);
            Show(menuCG);
        }
    }
Esempio n. 2
0
 // Start is called before the first frame update
 void Start()
 {
     if (conf == null)
     {
         conf = Memory.LoadConfig();
         if (conf == null)
         {
             Memory.SaveConfig(new VSPConfig());
             conf = Memory.LoadConfig();
         }
         if (conf.VSPath != null && LBA.checkVSROM(conf.VSPath) != null)
         {
             Hide(pathCG);
             Show(menuCG);
         }
     }
 }
Esempio n. 3
0
    void OnGUI()
    {
        if (conf == null)
        {
            conf = Memory.LoadConfig();
            if (conf == null)
            {
                Memory.SaveConfig(new VSPConfig());
                conf = Memory.LoadConfig();
            }
            if (conf.VSPath != null)
            {
                VSPath = conf.VSPath;
                if (conf.VS_Version == "")
                {
                    conf.VS_Version = LBA.checkVSROM(VSPath);
                    Memory.SaveConfig(conf);
                }
            }
        }

        GUILayout.Label("Vagrant Story Path", EditorStyles.boldLabel);
        GUILayoutOption[] options = { GUILayout.Width(300), GUILayout.MaxWidth(400) };
        VSPath = EditorGUILayout.TextField("Vagrant Story CD path :", VSPath, options);

        GUILayoutOption[] options2 = { GUILayout.MaxWidth(30) };
        bool VSPathTrigger         = GUILayout.Button(new GUIContent("..."), options2);

        if (VSPathTrigger)
        {
            string path = EditorUtility.OpenFolderPanel("Path to Vagrant Story CD", "", "");
            VSPath = path + "/";
        }

        GUILayoutOption[] options3 = { GUILayout.Width(200), GUILayout.MaxWidth(400) };
        bool VSSaveTrigger         = GUILayout.Button(new GUIContent("Save Path"), options3);

        if (VSSaveTrigger)
        {
            conf.VSPath     = VSPath;
            conf.VS_Version = LBA.checkVSROM(VSPath);
            Memory.SaveConfig(conf);
        }

        GUILayout.Label("Vagrant Story Version : " + conf.VS_Version);
        GUILayout.Space(10f);

        GUILayout.Label("| One File import", EditorStyles.boldLabel);
        FilePath = EditorGUILayout.TextField("File path (VS Path relativ) :", FilePath, options);
        bool filePathTrigger = GUILayout.Button(new GUIContent("..."), options2);

        if (filePathTrigger)
        {
            string path = EditorUtility.OpenFilePanel("Path to File", VSPath, "");
            FilePath = path.Replace(VSPath, "");
        }
        bool fileLoadTrigger = GUILayout.Button(new GUIContent("Load"), options3);

        if (fileLoadTrigger && VSPath != "" && FilePath != "")
        {
            string[] hash     = FilePath.Split("/"[0]);
            string[] h2       = hash[hash.Length - 1].Split("."[0]);
            string   folder   = hash[0];
            string   fileName = h2[0];
            string   ext      = h2[1];


            switch (folder)
            {
            case "BATTLE":
                // BATTLE.PRG
                // BOG.DAT
                // INITBTL.PRG
                // SYSTEM.DAT
                switch (ext)
                {
                case "PRG":
                    PRG parser = new PRG();
                    parser.Parse(VSPath + FilePath);
                    break;
                }
                break;

            case "BG":
                // 001OP01A.FAR & TIM
                // 002OP01A.FAR & TIM
                // 007OP01A.FAR & TIM
                // 008OP01A.FAR & TIM
                break;

            case "EFFECT":
                // EFFPURGE.BIN maybe the PLG for E000.P
                // E*.P
                // E*.FBC
                // E*.FBT
                // PLG*.BIN lot of empty
                switch (ext)
                {
                case "P":
                    EFFECT effect = new EFFECT(VSPath + FilePath);
                    break;
                }
                break;

            case "ENDING":
                // ENDING.PRG
                // ENDING.XA
                // ILLUST06.BIN -> ILLUST16.BIN
                // NULL.DAT
                switch (ext)
                {
                case "BIN":
                    TIM parser = new TIM();
                    parser.ParseIllust(VSPath + FilePath);
                    break;
                }
                break;

            case "EVENT":
                // ****.EVT
                ParseEVT(VSPath + FilePath, true);
                break;

            case "MAP":
                // MAP***.MPD
                // Z***U**.ZUD
                // ZONE***.ZND
                switch (ext)
                {
                case "MPD":
                    ParseMPD(VSPath + FilePath, true);
                    break;

                case "ZUD":
                    ParseZUD(VSPath + FilePath, fileName, true);
                    break;

                case "ZND":
                    ParseZND(VSPath + FilePath, true);
                    break;
                }
                break;

            case "MENU":
                break;

            case "MOV":
                break;

            case "MUSIC":
                ParseAKAO(VSPath + FilePath, AKAO.MUSIC, true);
                break;

            case "OBJ":
                // **.SHP
                // **.SEQ
                // **.WEP
                switch (ext)
                {
                case "SHP":
                    ParseSHP(VSPath + FilePath, fileName, true, true);
                    break;

                case "WEP":
                    ParseWEP(VSPath + FilePath, true);
                    break;
                }
                break;

            case "SOUND":
                ParseAKAO(VSPath + FilePath, AKAO.SOUND, true);
                break;
            }
        }



        GUILayout.Label("| Batch imports", EditorStyles.boldLabel);
        GUILayout.BeginVertical();
        GUILayout.Label("3D Model Formats : ");
        bool LoadARMTrigger = GUILayout.Button(new GUIContent("Load MiniMaps.ARM"));

        if (LoadARMTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "SMALL/", "*.ARM");
            float    fileToParse = files.Length;
            float    fileParsed  = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ARM parser = new ARM();
                //parser.UseDebug = true;
                parser.Parse(file);
                parser.BuildPrefab(true);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }

        bool LoadWEPTrigger = GUILayout.Button(new GUIContent("Load Weapons.WEP"));

        if (LoadWEPTrigger && VSPath != "")
        {
            BuildDatabase();
            string[] files       = Directory.GetFiles(VSPath + "OBJ/", "*.WEP");
            float    fileToParse = files.Length;
            float    fileParsed  = 0f;

            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ParseWEP(file, true);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }

        bool LoadSHPTrigger = GUILayout.Button(new GUIContent("Load 3D Models.SHP"));

        if (LoadSHPTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "OBJ/", "*.SHP");
            float    fileToParse = files.Length;
            float    fileParsed  = 0f;

            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ParseSHP(file, filename, false);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }

        bool LoadZUDTrigger = GUILayout.Button(new GUIContent("Load Zones Units Datas.ZUD"));

        if (LoadZUDTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "MAP/", "*.ZUD");
            float    fileToParse = files.Length;
            float    fileParsed  = 0f;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ParseZUD(file, filename, false);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }

        bool LoadMPDTrigger = GUILayout.Button(new GUIContent("Load Map Datas.MPD"));

        if (LoadMPDTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "MAP/", "*.MPD");
            float    fileToParse = files.Length;
            float    fileParsed  = 0f;

            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ParseMPD(file, false);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }

        bool LoadEFFECTTrigger = GUILayout.Button(new GUIContent("Load EFFECT/E0*.P, E0*.FBC, E0*.FBT (Only Texture right now)"));

        if (LoadEFFECTTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "EFFECT/", "*.P");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                EFFECT effect = new EFFECT(file);
                fileParsed++;
            }


            //EFFECT effect = new EFFECT(VSPath + "EFFECT/E008.P");

            EditorUtility.ClearProgressBar();
        }
        GUILayout.EndVertical();

        GUILayout.BeginVertical();
        GUILayout.Label("Texture Formats : ");

        bool LoadGIMTrigger = GUILayout.Button(new GUIContent("Load GIM/*.GIM"));

        if (LoadGIMTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "GIM/", "*.GIM");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                GIM gim = new GIM(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }

        bool LoadMENUBGTrigger = GUILayout.Button(new GUIContent("Load MENU/*BG.BIN"));

        if (LoadMENUBGTrigger && VSPath != "")
        {
            string[] files       = new string[] { VSPath + "MENU/MAPBG.BIN", VSPath + "MENU/MENUBG.BIN" };
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                TIM bg = new TIM();
                bg.ParseBG(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }

        bool LoadDISTrigger = GUILayout.Button(new GUIContent("Load SMALL/*.DIS"));

        if (LoadDISTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "SMALL/", "*.DIS");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                DIS dis = new DIS();
                dis.Parse(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }

        bool LoadTIMTrigger = GUILayout.Button(new GUIContent("BG/*.TIM"));

        if (LoadTIMTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "BG/", "*.TIM");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                TIM parser = new TIM();
                parser.Parse(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }

        bool LoadILLUSTTrigger = GUILayout.Button(new GUIContent("ENDING/ILLUST*.BIN (Not Working Yet)"));

        if (LoadILLUSTTrigger && VSPath != "")
        {
            // not working yet
            string[] files       = Directory.GetFiles(VSPath + "ENDING/", "*.BIN");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                TIM parser = new TIM();
                parser.ParseIllust(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }
        GUILayout.EndVertical();


        GUILayout.BeginVertical();
        GUILayout.Label("Audio Formats : ");

        /*
         * bool LoadAKAOTrigger = GUILayout.Button(new GUIContent("Load Akao SOUND/WAVE*.DAT"));
         * if (LoadAKAOTrigger && VSPath != "")
         * {
         *  string[] files = Directory.GetFiles(VSPath + "SOUND/", "*.DAT");
         *  float fileToParse = files.Length;
         *  float fileParsed = 0;
         *  foreach (string file in files)
         *  {
         *      string[] h = file.Split("/"[0]);
         *      string filename = h[h.Length - 1];
         *      EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
         *      AKAO parser = new AKAO();
         *      parser.UseDebug = true;
         *      parser.Parse(file, AKAO.SOUND);
         *      fileParsed++;
         *  }
         *
         *  EditorUtility.ClearProgressBar();
         * }
         */

        midTrigger = GUILayout.Toggle(midTrigger, new GUIContent("output a MIDI file ?"));
        sf2Trigger = GUILayout.Toggle(sf2Trigger, new GUIContent("output a SF2 (soundfont) file ?"));
        dlsTrigger = GUILayout.Toggle(dlsTrigger, new GUIContent("output a DLS (soundfont) file ? (Not working well yet)"));
        wavTrigger = GUILayout.Toggle(wavTrigger, new GUIContent("output a WAV file ? ( /_!_\\ heavy files)"));
        bool LoadAKAO2Trigger = GUILayout.Button(new GUIContent("Load Akao MUSIC/MUSIC*.DAT"));

        if (LoadAKAO2Trigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "MUSIC/", "*.DAT");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                ParseAKAO(file, AKAO.MUSIC, false);
                fileParsed++;
            }
            EditorUtility.ClearProgressBar();
        }
        GUILayout.EndVertical();

        GUILayout.BeginVertical();
        GUILayout.Label("Data Formats : ");
        bool LoadSYDTrigger = GUILayout.Button(new GUIContent("Load MENU DataBase.SYD"));

        if (LoadSYDTrigger && VSPath != "")
        {
            BuildDatabase();
        }

        bool LoadITEMTrigger = GUILayout.Button(new GUIContent("Load MENU ITEM*.BIN"));

        if (LoadITEMTrigger && VSPath != "")
        {
            BIN itemDB = new BIN();
            itemDB.BuildItems(VSPath + "MENU/ITEMNAME.BIN", VSPath + "MENU/ITEMHELP.BIN");
        }

        bool LoadEVENTTrigger = GUILayout.Button(new GUIContent("Load EVENT/*.EVT"));

        if (LoadEVENTTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "EVENT/", "*.EVT");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));

                ParseEVT(file, false);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }

        bool LoadHFTrigger = GUILayout.Button(new GUIContent("Load InGame Help SMALL/*.HF"));

        if (LoadHFTrigger && VSPath != "")
        {
            string[] files       = Directory.GetFiles(VSPath + "SMALL/", "*.HF0");
            float    fileToParse = files.Length;

            float fileParsed = 0;
            foreach (string file in files)
            {
                string[] h        = file.Split("/"[0]);
                string   filename = h[h.Length - 1];
                EditorUtility.DisplayProgressBar("VS Parsing", "Parsing : " + filename + ", " + fileParsed + " files parsed.", (fileParsed / fileToParse));
                HF0 parser = new HF0();
                parser.Parse(file);
                fileParsed++;
            }


            EditorUtility.ClearProgressBar();
        }
        GUILayout.EndVertical();


        bool LoadEXPLOTrigger = GUILayout.Button(new GUIContent("Explore..."));

        if (LoadEXPLOTrigger && VSPath != "")
        {
            //BIN parser = new BIN();
            //parser.Explore(VSPath + "SLES_027.55"); // spell and skills
            // "BATTLE/INITBTL.PRG" // Fandango
            //parser.Explore(VSPath + "BATTLE/BOG.DAT");

            /*
             * string[] files = Directory.GetFiles(VSPath + "MENU/", "*.PRG");
             * ToolBox.FeedDatabases(files);
             */
            BIN parser = new BIN();
            parser.Explore(VSPath + "SLES_027.55"); // spell and skills
            //PRG parser = new PRG();
            //parser.Parse(VSPath + "TITLE/TITLE.PRG"); // spell and skills
            //parser.Parse(VSPath + "ENDING/ENDING.PRG");
            //parser.Parse(VSPath + "BATTLE/BATTLE.PRG");
            //parser.Parse(VSPath + "BATTLE/INITBTL.PRG");
        }
    }
Esempio n. 4
0
        private int CheckISO(string fileName)
        {
            if (fileName.Substring(fileName.LastIndexOf('.') + 1).ToLower() != "iso")
            {
                return(0);
            }

            if (!File.Exists(fileName))
            {
                return(0);
            }

            try
            {
                LBA lba_t = new LBA(fileName);
                LBA umd   = lba_t[UMD_DATA];
                if (umd == null)
                {
                    return(0);
                }

                System.IO.FileStream fs = System.IO.File.OpenRead(fileName);
                fs.Seek(umd.Off * LBA.ISOBlockSize, 0);
                byte[] t = new byte[id_A.Length];
                fs.Read(t, 0, t.Length);
                fs.Close();

                string s = "";
                for (int i = 0; i < t.Length; i++)
                {
                    s += (char)t[i];
                }

                if (s.ToUpper() == id_A)
                {
                    foreach (string cf in CheckFiles_A)
                    {
                        if (lba_t[cf.Replace(pa, pb)] == null)
                        {
                            return(0);
                        }
                    }
                    return(1);
                }
                else if (s.ToUpper() == id_B)
                {
                    foreach (string cf in CheckFiles_B)
                    {
                        if (lba_t[cf] == null)
                        {
                            return(0);
                        }
                    }

                    foreach (string cf in CheckFiles_A)
                    {
                        if (lba_t[cf] == null)
                        {
                            return(2);
                        }
                    }
                    return(3);
                }
                else
                {
                    return(0);
                }
            }
            catch (Exception)
            {
                return(0);
            }
        }
Esempio n. 5
0
        private void GetCheckFile()
        {
            try
            {
                lba = new LBA(Resources.HEAD);
            }
            catch (Exception)
            {
                MessageBox.Show("读取数据出错!补丁已损坏!退出!", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
                this.Close();
            }

            MemoryStream ms       = new MemoryStream(Resources.data1);
            BinaryReader br       = new BinaryReader(ms);
            int          num      = br.ReadInt32();
            int          off_base = br.ReadInt32();

            pak_subs = new PAK_subs[num];
            for (int i = 0; i < num; i++)
            {
                pak_subs[i] = new PAK_subs();

                pak_subs[i].PAKname = br.ReadString();
                pak_subs[i].num     = br.ReadInt32();

                int pak_subs_num = br.ReadInt32();
                pak_subs[i].subs = new PAK_subs.Sub[pak_subs_num];

                for (int j = 0; j < pak_subs_num; j++)
                {
                    pak_subs[i].subs[j].id   = br.ReadInt32();
                    pak_subs[i].subs[j].off  = br.ReadInt32() + off_base;
                    pak_subs[i].subs[j].size = br.ReadInt32();
                }
            }

            br.Close();
            ms.Close();


            CheckFiles_A = new List <string>();
            CheckFiles_B = new List <string>();

            ms = new MemoryStream(Resources.data0);
            br = new BinaryReader(ms);

            num      = br.ReadInt32();
            off_base = br.ReadInt32();

            sfis = new SubFileInfo[num];

            for (int i = 0; i < num; i++)
            {
                sfis[i] = new SubFileInfo();

                sfis[i].name = br.ReadString();
                sfis[i].type = br.ReadByte();

                if (sfis[i].type == 1)//完全来自补丁
                {
                    sfis[i].off_source = br.ReadInt32() + off_base;
                    sfis[i].size       = br.ReadInt32();
                    sfis[i].pak_subs   = null;
                }
                else if (sfis[i].type == 2)//来自双方
                {
                    int j;
                    for (j = 0; j < pak_subs.Length; j++)
                    {
                        if (pak_subs[j].PAKname.ToLower() == sfis[i].name.ToLower())
                        {
                            sfis[i].pak_subs = pak_subs[j];
                            break;
                        }
                    }

                    if (j == pak_subs.Length)
                    {
                        ms.Close();
                        MessageBox.Show("读取数据出错!补丁已损坏!退出!", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        this.Close();
                    }
                }
                else//完全来自文件
                {
                    sfis[i].pak_subs = null;
                }

                sfis[i].crc32 = br.ReadUInt32();

                if (sfis[i].name == Name_BOOT)
                {
                    i_boot = i;
                }

                if (sfis[i].name == Name_OLDBOOT)
                {
                    i_oldboot = i;
                }

                sfis[i].lba = lba[sfis[i].name];
                if (sfis[i].lba == null)
                {
                    MessageBox.Show("读取数据出错!补丁已损坏!退出!", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    this.Close();
                }

                if (sfis[i].type != 1)
                {
                    if (sfis[i].name.IndexOf(pa) == 0)
                    {
                        CheckFiles_A.Add(sfis[i].name);
                    }
                    else
                    {
                        CheckFiles_B.Add(sfis[i].name);
                    }
                }
            }

            ms.Close();
        }
Esempio n. 6
0
        private object WriteNewISO(string p, BackgroundWorker work, DoWorkEventArgs e)
        {
            LBA  lba_a, lba_b;
            long size_a, size_b;

            FileInfo info_b = new FileInfo(path_iso_b);

            size_b = info_b.Length;

            if (path_iso_a == null)
            {
                size_a = size_b;
            }
            else
            {
                FileInfo info_a = new FileInfo(path_iso_a);
                size_a = info_a.Length;
            }

            int pro;

            crc32_failed_b.Clear();

            if (work.CancellationPending)
            {
                e.Cancel = true;
                return(false);
            }
            pro = 0;
            work.ReportProgress(pro);

            #region 打开
            try
            {
                if (path_iso_a != null)
                {
                    lba_a = new LBA(path_iso_a);
                    fs_a  = File.OpenRead(path_iso_a);
                }
                else
                {
                    lba_a = null;
                    fs_a  = null;
                }
            }
            catch (Exception)
            {
                throw new Exception("无法正确作为ISO镜像打开:\n  " + path_iso_a);
            }

            try
            {
                lba_b = new LBA(path_iso_b);
                fs_b  = File.OpenRead(path_iso_b);
            }
            catch (Exception)
            {
                throw new Exception("无法正确作为ISO镜像打开:\n  " + path_iso_b);
            }

            ms0 = new MemoryStream(Resources.data0);
            ms1 = new MemoryStream(Resources.data1);

            #endregion

            if (work.CancellationPending)
            {
                e.Cancel = true;
                return(false);
            }
            pro = 1;
            work.ReportProgress(pro);

            #region 设置新LBA信息

            int off_new = FirstLBA;

            for (int i = 0; i < sfis.Length; i++)
            {
                sfis[i].off = off_new;

                if (sfis[i].type == 0)//文件完全来自镜像
                {
                    sfis[i].Source_Stream = fs_b;

                    LBA  lbat       = lba_b[sfis[i].name];
                    long size_check = size_b;
                    if (lbat == null)
                    {
                        size_check            = size_a;
                        sfis[i].Source_Stream = fs_a;

                        if (lba_a == null || (lbat = lba_a[sfis[i].name.Replace(pa, pb)]) == null)
                        {
                            throw new Exception("未能在日版镜像中找到相应文件!");
                        }
                    }

                    sfis[i].off_source = lbat.Off * LBA.ISOBlockSize;
                    sfis[i].size       = lbat.Size;

                    if (size_check < sfis[i].off_source + sfis[i].size)
                    {
                        throw new Exception("读取日版镜像中文件时出错!可能是该镜像文件无法被支持!");
                    }
                }
                else if (sfis[i].type == 1)//文件来自补丁
                {
                    sfis[i].Source_Stream = ms0;
                }
                else//文件来自双方
                {
                    sfis[i].Source_Stream = fs_b;

                    LBA  lbat       = lba_b[sfis[i].name];
                    long size_check = size_b;
                    if (lbat == null)
                    {
                        size_check            = size_a;
                        sfis[i].Source_Stream = fs_a;

                        if (lba_a == null || (lbat = lba_a[sfis[i].name.Replace(pa, pb)]) == null)
                        {
                            throw new Exception("未能在日版镜像中找到相应文件!");
                        }
                    }

                    try
                    {
                        sfis[i].Source_Stream.Seek(lbat.Off * LBA.ISOBlockSize, 0);
                        sfis[i].pak_subs.pak = new Pak(sfis[i].Source_Stream);
                    }
                    catch (Exception)
                    {
                        throw new Exception("读取日版镜像中文件时出错!可能是该镜像文件无法被支持!");
                    }

                    if (size_check < lbat.Off * LBA.ISOBlockSize + sfis[i].pak_subs.pak.Size)
                    {
                        throw new Exception("读取日版镜像中文件时出错!可能是该镜像文件无法被支持!");
                    }

                    if (sfis[i].pak_subs.pak.Num != sfis[i].pak_subs.num)
                    {
                        throw new Exception("读取日版镜像中文件时出错!可能是该镜像文件无法被支持!");
                    }

                    for (int j = 0; j < sfis[i].pak_subs.subs.Length; j++)
                    {
                        ms1.Seek(sfis[i].pak_subs.subs[j].off, 0);
                        sfis[i].pak_subs.pak.Replace(sfis[i].pak_subs.subs[j].id, ms1, sfis[i].pak_subs.subs[j].size);
                    }

                    sfis[i].pak_subs.pak.Rebuild();

                    sfis[i].size = sfis[i].pak_subs.pak.Size;
                }

                if (sfis[i].name != pgfFont)
                {
                    off_new = sfis[i].off + sfis[i].size / LBA.ISOBlockSize;

                    if (sfis[i].size % LBA.ISOBlockSize != 0)
                    {
                        off_new++;
                    }
                }
                else
                {
                    off_new = sfis[i].off + SizeFont / LBA.ISOBlockSize;
                }
            }
            int  SizeISO = off_new;
            long Size    = (long)off_new * LBA.ISOBlockSize;

            if (Size > int.MaxValue)
            {
                throw new Exception("生成的镜像将大于2G,不支持!");
            }

            #endregion

            if (work.CancellationPending)
            {
                e.Cancel = true;
                return(false);
            }
            pro = 4;
            work.ReportProgress(pro);

            #region 创建新镜像,写入头

            fs_out = new FileStream(path_iso_new, FileMode.Create, FileAccess.ReadWrite);
            fs_out.SetLength(Size);

            fs_out.Write(Resources.HEAD, 0, Resources.HEAD.Length);

            fs_out.Seek(off_sizeinfo, 0);
            WriteLB(fs_out, SizeISO);

            for (int i = 0; i < sfis.Length; i++)
            {
                fs_out.Seek(sfis[i].lba.Off_Info + 2, 0);
                WriteLB(fs_out, sfis[i].off);
                WriteLB(fs_out, sfis[i].size);
            }

            #endregion

            if (work.CancellationPending)
            {
                e.Cancel = true;
                return(false);
            }
            pro = 5;
            work.ReportProgress(pro);

            #region 写入文件

            Stream stream;

            for (int i = 0; i < sfis.Length; i++)
            {
                if (work.CancellationPending)
                {
                    e.Cancel = true;
                    return(false);
                }

                fs_out.Seek(sfis[i].off * LBA.ISOBlockSize, 0);


                if (sfis[i].type != 2)
                {
                    stream = sfis[i].Source_Stream;

                    stream.Seek(sfis[i].off_source, 0);
                    int count = sfis[i].size;

                    uint value = 0xFFFFFFFF;
                    while (count > 0)
                    {
                        int    size = count > buffsize ? buffsize : count;
                        byte[] buff = new byte[size];
                        stream.Read(buff, 0, size);
                        for (int j = 0; j < size; j++)
                        {
                            value = (value >> 8) ^ crc32table[(value ^ buff[j]) & 0xFF];
                        }
                        count -= buffsize;

                        fs_out.Write(buff, 0, buff.Length);

                        pro = (int)(5 + 994 * fs_out.Position / fs_out.Length);
                        if (pro > 999)
                        {
                            pro = 999;
                        }

                        if (work.CancellationPending)
                        {
                            e.Cancel = true;
                            return(false);
                        }
                        work.ReportProgress(pro);
                    }
                    value ^= 0xFFFFFFFF;

                    if (value != sfis[i].crc32)
                    {
                        if (sfis[i].type != 0)
                        {
                            crc32_failed_b.Add(sfis[i].name);
                        }
                        else
                        {
                            throw new Exception("读取资源文件出错!可能是补丁程序已损坏!");
                        }
                    }
                }
                else
                {
                    sfis[i].pak_subs.pak.WriteTo(fs_out);
                    fs_out.Flush();
                    fs_out.Seek(sfis[i].off * LBA.ISOBlockSize, 0);

                    int count = sfis[i].size;

                    uint value = 0xFFFFFFFF;
                    while (count > 0)
                    {
                        int    size = count > buffsize ? buffsize : count;
                        byte[] buff = new byte[size];
                        fs_out.Read(buff, 0, size);
                        for (int j = 0; j < size; j++)
                        {
                            value = (value >> 8) ^ crc32table[(value ^ buff[j]) & 0xFF];
                        }
                        count -= size;

                        pro = (int)(5 + 994 *
                                    ((long)sfis[i].off * LBA.ISOBlockSize + ((long)(sfis[i].size - count) * 3 + (long)sfis[i].size * 7) / 10)
                                    / fs_out.Length);

                        if (pro < 100)
                        {
                            throw new Exception();
                        }

                        if (pro > 999)
                        {
                            pro = 999;
                        }

                        if (work.CancellationPending)
                        {
                            e.Cancel = true;
                            return(false);
                        }
                        work.ReportProgress(pro);
                    }
                    value ^= 0xFFFFFFFF;

                    if (value != sfis[i].crc32)
                    {
                        crc32_failed_b.Add(sfis[i].name);
                    }
                }
            }

            #endregion

            #region BOOT.BIN 和 EBOOT.OLD的版本补丁

            fs_out.Seek(sfis[i_boot].off * LBA.ISOBlockSize + off_version_path, 0);
            fs_out.WriteByte(0x02);
            fs_out.WriteByte(0x06);

            fs_out.Seek(sfis[i_oldboot].off * LBA.ISOBlockSize + off_version_path, 0);
            //fs_out.WriteByte(0x00);
            //fs_out.WriteByte(0x05);
            fs_out.WriteByte(0x02);
            fs_out.WriteByte(0x06);

            #endregion

            if (work.CancellationPending)
            {
                e.Cancel = true;
                return(false);
            }
            pro = 999;
            work.ReportProgress(pro);

            fs_out.Close(); fs_out = null;

            ms0.Close(); ms0 = null;
            ms1.Close(); ms1 = null;

            if (fs_a != null)
            {
                fs_a.Close(); fs_a = null;
            }
            fs_b.Close(); fs_b = null;

            work.ReportProgress(1000);

            return(true);
        }