예제 #1
0
        private async void AskLoadCompressedBundle(BundleFileInstance bundleInst)
        {
            const string fileOption   = "File";
            const string memoryOption = "Memory";
            const string cancelOption = "Cancel";
            string       result       = await MessageBoxUtil.ShowDialogCustom(
                this, "Note", "This bundle is compressed. Decompress to file or memory?",
                fileOption, memoryOption, cancelOption);

            if (result == fileOption)
            {
                SaveFileDialog sfd = new SaveFileDialog();
                sfd.Title   = "Save as...";
                sfd.Filters = new List <FileDialogFilter>()
                {
                    new FileDialogFilter()
                    {
                        Name = "All files", Extensions = new List <string>()
                        {
                            "*"
                        }
                    }
                };

                string savePath;
                while (true)
                {
                    savePath = await sfd.ShowAsync(this);

                    if (savePath == "" || savePath == null)
                    {
                        return;
                    }

                    if (Path.GetFullPath(savePath) == Path.GetFullPath(bundleInst.path))
                    {
                        await MessageBoxUtil.ShowDialog(this,
                                                        "File in use", "Since this file is already open in UABEA, you must pick a new file name (sorry!)");

                        continue;
                    }
                    else
                    {
                        break;
                    }
                }

                DecompressToFile(bundleInst, savePath);
            }
            else if (result == memoryOption)
            {
                DecompressToMemory(bundleInst);
            }
            else //if (result == cancelOption || result == closeOption)
            {
                return;
            }

            LoadBundle(bundleInst);
        }
예제 #2
0
 private async void MenuCreatePackageFile_Click(object?sender, RoutedEventArgs e)
 {
     await MessageBoxUtil.ShowDialog(this, "Not implemented",
                                     "Bundle pkgs are not supported at the moment.\n" +
                                     "Trying to install an emip file? Try running\n" +
                                     "UABEAvalonia applyemip from the command line.");
 }
예제 #3
0
        private async void BtnOk_Click(object?sender, Avalonia.Interactivity.RoutedEventArgs e)
        {
            var fileInsts     = new List <AssetsFileInstance>();
            var replacerLists = new Dictionary <AssetsFileInstance, List <AssetsReplacer> >();

            foreach (LoadModPackageTreeFileInfo fileItem in affectedFiles.Items)
            {
                if (fileItem.selected && File.Exists(fileItem.fullPath))
                {
                    AssetsFileInstance fileInst = am.LoadAssetsFile(fileItem.fullPath, true);
                    fileInsts.Add(fileInst);

                    if (!replacerLists.ContainsKey(fileInst))
                    {
                        replacerLists[fileInst] = new List <AssetsReplacer>();
                    }

                    foreach (AssetsReplacer replacer in fileItem.assetDesc.replacers)
                    {
                        replacerLists[fileInst].Add(replacer);
                    }
                }
            }

            if (fileInsts.Count == 0)
            {
                await MessageBoxUtil.ShowDialog(this,
                                                "Error", "Did not load any files. Did you select any (double click) or set the correct base path?");

                return;
            }

            if (!await LoadOrAskTypeData(fileInsts[0]))
            {
                Close(false);
                return;
            }

            InfoWindow info = new InfoWindow(am, fileInsts, false);

            foreach (KeyValuePair <AssetsFileInstance, List <AssetsReplacer> > kvp in replacerLists)
            {
                AssetsFileInstance    fileInst     = kvp.Key;
                List <AssetsReplacer> replacerList = kvp.Value;
                foreach (AssetsReplacer replacer in replacerList)
                {
                    info.Workspace.AddReplacer(fileInst, replacer);
                }
            }
            info.Show();

            //temporary hack
            Hide();

            info.Closed += (object?sender, EventArgs e) =>
            {
                Close(true);
            };
        }
예제 #4
0
        private async void BtnInfo_Click(object?sender, RoutedEventArgs e)
        {
            if (bundleInst != null && comboBox.SelectedItem != null)
            {
                int index = (int)((ComboBoxItem)comboBox.SelectedItem).Tag;

                string bunAssetName = bundleInst.file.bundleInf6.dirInf[index].name;

                //when we make a modification to an assets file in the bundle,
                //we replace the assets file in the manager. this way, all we
                //have to do is not reload from the bundle if our assets file
                //has been modified
                MemoryStream assetStream;
                if (!newFiles.ContainsKey(bunAssetName))
                {
                    byte[] assetData = BundleHelper.LoadAssetDataFromBundle(bundleInst.file, index);
                    assetStream = new MemoryStream(assetData);
                }
                else
                {
                    //unused if the file already exists
                    assetStream = null;
                }

                //warning: does not update if you import an assets file onto
                //a file that wasn't originally an assets file
                var  fileInf      = BundleHelper.GetDirInfo(bundleInst.file, index);
                bool isAssetsFile = bundleInst.file.IsAssetsFile(bundleInst.file.reader, fileInf);

                if (isAssetsFile)
                {
                    string             assetMemPath = Path.Combine(bundleInst.path, bunAssetName);
                    AssetsFileInstance fileInst     = am.LoadAssetsFile(assetStream, assetMemPath, true);

                    if (!await LoadOrAskTypeData(fileInst))
                    {
                        return;
                    }

                    if (bundleInst != null && fileInst.parentBundle == null)
                    {
                        fileInst.parentBundle = bundleInst;
                    }

                    InfoWindow info = new InfoWindow(am, new List <AssetsFileInstance> {
                        fileInst
                    }, true);
                    info.Closing += InfoWindow_Closing;
                    info.Show();
                }
                else
                {
                    await MessageBoxUtil.ShowDialog(this,
                                                    "Error", "This doesn't seem to be a valid assets file.\n" +
                                                    "If you want to export a non-assets file,\n" +
                                                    "use Export.");
                }
            }
        }
예제 #5
0
        private async Task AskForLocationAndCompress()
        {
            if (bundleInst != null)
            {
                //temporary, maybe I should just write to a memory stream or smth
                //edit: looks like uabe just asks you to open a file instead of
                //using your currently opened one, so that may be the workaround
                if (changesMade)
                {
                    ButtonResult continueWithChanges = await MessageBoxUtil.ShowDialog(
                        this, "Note", "You've modified this file, but only file before changes is loaded. If you want to compress the file with " +
                        "changes, please close this bundle and open the new file. Click Ok to compress the file without changes.",
                        ButtonEnum.OkCancel);

                    if (continueWithChanges == ButtonResult.Cancel)
                    {
                        return;
                    }
                }

                SaveFileDialog sfd = new SaveFileDialog();
                sfd.Title = "Save as...";

                string file = await sfd.ShowAsync(this);

                if (file == null)
                {
                    return;
                }

                const string lz4Option    = "LZ4";
                const string lzmaOption   = "LZMA";
                const string cancelOption = "Cancel";
                string       result       = await MessageBoxUtil.ShowDialogCustom(
                    this, "Note", "What compression method do you want to use?\nLZ4: Faster but larger size\nLZMA: Slower but smaller size",
                    lz4Option, lzmaOption, cancelOption);

                AssetBundleCompressionType compType = result switch
                {
                    lz4Option => AssetBundleCompressionType.LZ4,
                    lzmaOption => AssetBundleCompressionType.LZMA,
                    _ => AssetBundleCompressionType.NONE
                };

                if (compType != AssetBundleCompressionType.NONE)
                {
                    CompressBundle(bundleInst, file, compType);
                }
            }
            else
            {
                await MessageBoxUtil.ShowDialog(this, "Note", "Please open a bundle file before using compress.");
            }
        }
예제 #6
0
        private async Task AskForSave()
        {
            if (modified && bundleInst != null)
            {
                ButtonResult choice = await MessageBoxUtil.ShowDialog(this, "Changes made", "You've modified this file. Would you like to save?",
                                                                      ButtonEnum.YesNo);

                if (choice == ButtonResult.Yes)
                {
                    await AskForSaveLocation();
                }
            }
        }
예제 #7
0
        private async void MenuClose_Click(object?sender, Avalonia.Interactivity.RoutedEventArgs e)
        {
            if (modified)
            {
                ButtonResult choice = await MessageBoxUtil.ShowDialog(this, "Changes made", "You've modified this file. Would you like to save?",
                                                                      ButtonEnum.YesNo);

                if (choice == ButtonResult.Yes)
                {
                    await SaveFile();
                }
            }
            CloseFile();
        }
예제 #8
0
        private async Task <string?> AskLoadSplitFile(string selectedFile)
        {
            ButtonResult splitRes = await MessageBoxUtil.ShowDialog(this,
                                                                    "Split file detected", "This file ends with .split0. Create merged file?\n",
                                                                    ButtonEnum.YesNoCancel);

            if (splitRes == ButtonResult.Yes)
            {
                SaveFileDialog sfd = new SaveFileDialog();
                sfd.Title           = "Select location for merged file";
                sfd.Directory       = Path.GetDirectoryName(selectedFile);
                sfd.InitialFileName = Path.GetFileName(selectedFile.Substring(0, selectedFile.Length - ".split0".Length));
                string splitFilePath = await sfd.ShowAsync(this);

                if (splitFilePath != null && splitFilePath != string.Empty)
                {
                    using (FileStream mergeFile = File.OpenWrite(splitFilePath))
                    {
                        int    idx = 0;
                        string thisSplitFileNoNum = selectedFile.Substring(0, selectedFile.Length - 1);
                        string thisSplitFileNum   = selectedFile;
                        while (File.Exists(thisSplitFileNum))
                        {
                            using (FileStream thisSplitFile = File.OpenRead(thisSplitFileNum))
                            {
                                thisSplitFile.CopyTo(mergeFile);
                            }

                            idx++;
                            thisSplitFileNum = $"{thisSplitFileNoNum}{idx}";
                        }
                        ;
                    }
                    return(splitFilePath);
                }
                else
                {
                    return(null);
                }
            }
            else if (splitRes == ButtonResult.No)
            {
                return(selectedFile);
            }
            else //if (splitRes == ButtonResult.Cancel)
            {
                return(null);
            }
        }
예제 #9
0
        private async void MainWindow_Initialized(object?sender, EventArgs e)
        {
            am = new AssetsManager();
            if (File.Exists("classdata.tpk"))
            {
                am.LoadClassPackage("classdata.tpk");
            }
            else
            {
                await MessageBoxUtil.ShowDialog(this, "Error", "Missing classdata.tpk by exe.\nPlease make sure it exists.");

                Close();
                Environment.Exit(1);
            }
        }
예제 #10
0
        private async void BtnInfo_Click(object?sender, RoutedEventArgs e)
        {
            //when dependency loading is supported:
            //make sure cab:// dependencies in the bundle are loaded as well
            if (bundleInst != null && comboBox.SelectedItem != null)
            {
                int index = (int)((ComboBoxItem)comboBox.SelectedItem).Tag;

                string bunAssetName = bundleInst.file.bundleInf6.dirInf[index].name;

                //when we make a modification to an assets file in the bundle,
                //we replace the assets file in the manager. this way, all we
                //have to do is not reload from the bundle if our assets file
                //has been modified
                MemoryStream assetStream;
                if (!newFiles.ContainsKey(bunAssetName))
                {
                    byte[] assetData = BundleHelper.LoadAssetDataFromBundle(bundleInst.file, index);
                    assetStream = new MemoryStream(assetData);
                }
                else
                {
                    //unused if the file already exists
                    assetStream = null;
                }

                //warning: does not update if you import an assets file onto
                //a file that wasn't originally an assets file
                var  fileInf      = BundleHelper.GetDirInfo(bundleInst.file, index);
                bool isAssetsFile = bundleInst.file.IsAssetsFile(bundleInst.file.reader, fileInf);

                if (isAssetsFile)
                {
                    AssetsFileInstance fileInst = am.LoadAssetsFile(assetStream, bundleInst.path, true);
                    am.LoadClassDatabaseFromPackage(fileInst.file.typeTree.unityVersion);

                    InfoWindow info = new InfoWindow(am, fileInst, bunAssetName, true);
                    info.Closing += InfoWindowClosing;
                    info.Show();
                }
                else
                {
                    await MessageBoxUtil.ShowDialog(this, "Error", "This doesn't seem to be a valid assets file.\n" +
                                                    "If you want to export a non-assets file,\n" +
                                                    "use Export.");
                }
            }
        }
예제 #11
0
        private async void BtnExportDump_Click(object?sender, Avalonia.Interactivity.RoutedEventArgs e)
        {
            if (await FailIfNothingSelected())
            {
                return;
            }

            SaveFileDialog sfd = new SaveFileDialog();

            sfd.Title   = "Save As";
            sfd.Filters = new List <FileDialogFilter>()
            {
                new FileDialogFilter()
                {
                    Name = "UABE text dump", Extensions = new List <string>()
                    {
                        "txt"
                    }
                },
                new FileDialogFilter()
                {
                    Name = "UABE json dump", Extensions = new List <string>()
                    {
                        "json"
                    }
                }
            };

            string file = await sfd.ShowAsync(this);

            if (file != null && file != string.Empty)
            {
                if (file.EndsWith(".json"))
                {
                    await MessageBoxUtil.ShowDialog(this, "Not implemented", "There's no json dump support yet, sorry. Exporting as .txt anyway.");

                    file = file.Substring(0, file.Length - 5) + ".txt";
                }

                using (FileStream fs = File.OpenWrite(file))
                    using (StreamWriter sw = new StreamWriter(fs))
                    {
                        AssetImportExport dumper = new AssetImportExport();
                        dumper.DumpTextAsset(sw, GetSelectedField());
                    }
            }
        }
예제 #12
0
        private async void AskLoadCompressedBundle(BundleFileInstance bundleInst)
        {
            const string fileOption   = "File";
            const string memoryOption = "Memory";
            const string cancelOption = "Cancel";
            string       result       = await MessageBoxUtil.ShowDialogCustom(
                this, "Note", "This bundle is compressed. Decompress to file or memory?",
                fileOption, memoryOption, cancelOption);

            if (result == fileOption)
            {
                SaveFileDialog sfd = new SaveFileDialog();
                sfd.Title   = "Save as...";
                sfd.Filters = new List <FileDialogFilter>()
                {
                    new FileDialogFilter()
                    {
                        Name = "All files", Extensions = new List <string>()
                        {
                            "*"
                        }
                    }
                };
                string savePath = await sfd.ShowAsync(this);

                if (savePath == null)
                {
                    return;
                }

                DecompressToFile(bundleInst, savePath);
            }
            else if (result == memoryOption)
            {
                DecompressToMemory(bundleInst);
            }
            else //if (result == cancelOption || result == closeOption)
            {
                return;
            }

            LoadBundle(bundleInst);
        }
예제 #13
0
        private async void ReturnAssetToGoTo()
        {
            int    fileId     = ddFileId.SelectedIndex; //hopefully in order
            string pathIdText = boxPathId.Text;

            if (fileId < 0)
            {
                await MessageBoxUtil.ShowDialog(this, "Bad input", "File was invalid.");

                return;
            }

            if (!long.TryParse(pathIdText, out long pathId))
            {
                await MessageBoxUtil.ShowDialog(this, "Bad input", "Path ID was invalid.");

                return;
            }

            AssetPPtr pptr = new AssetPPtr(fileId, pathId);

            Close(pptr);
        }
예제 #14
0
        private async void ReturnAssetToAdd()
        {
            int    fileId           = ddFileId.SelectedIndex; //hopefully in order
            string pathIdText       = boxPathId.Text;
            string typeIdText       = boxTypeId.Text;
            string monoIdText       = boxMonoId.Text;
            bool   createBlankAsset = chkCreateZerodAsset.IsChecked ?? false;

            AssetsFileInstance file = workspace.LoadedFiles[fileId];

            AssetTypeTemplateField tempField;

            byte[] assetBytes;
            long   pathId;
            int    typeId;
            ushort monoId;

            if (!long.TryParse(pathIdText, out pathId))
            {
                await MessageBoxUtil.ShowDialog(this, "Bad input", "Path ID was invalid.");

                return;
            }

            if (file.file.typeTree.hasTypeTree)
            {
                if (!TryParseTypeTree(file, typeIdText, createBlankAsset, out tempField, out typeId))
                {
                    if (!TryParseClassDatabase(typeIdText, createBlankAsset, out tempField, out typeId))
                    {
                        await MessageBoxUtil.ShowDialog(this, "Bad input", "Class type was invalid.");

                        return;
                    }
                    else
                    {
                        //has typetree but had to lookup to cldb
                        //we need to add a new typetree entry because this is
                        //probably not a type that existed in this bundle
                        file.file.typeTree.unity5Types.Add(C2T5.Cldb2TypeTree(workspace.am.classFile, typeId));
                    }
                }
            }
            else
            {
                if (!TryParseClassDatabase(typeIdText, createBlankAsset, out tempField, out typeId))
                {
                    await MessageBoxUtil.ShowDialog(this, "Bad input", "Class type was invalid.");

                    return;
                }
            }

            if (monoIdText == "-1")
            {
                monoId = 0xffff;
            }
            else if (!ushort.TryParse(monoIdText, out monoId))
            {
                await MessageBoxUtil.ShowDialog(this, "Bad input", "Mono ID was invalid.");

                return;
            }

            if (createBlankAsset)
            {
                AssetTypeValueField baseField = ValueBuilder.DefaultValueFieldFromTemplate(tempField);
                assetBytes = baseField.WriteToByteArray();
            }
            else
            {
                assetBytes = new byte[0];
            }

            workspace.AddReplacer(file, new AssetsReplacerFromMemory(0, pathId, typeId, monoId, assetBytes), new MemoryStream(assetBytes));

            Close(true);
        }
예제 #15
0
        private async void BtnImportDump_Click(object?sender, Avalonia.Interactivity.RoutedEventArgs e)
        {
            if (await FailIfNothingSelected())
            {
                return;
            }

            OpenFileDialog ofd = new OpenFileDialog();

            ofd.Title   = "Open";
            ofd.Filters = new List <FileDialogFilter>()
            {
                new FileDialogFilter()
                {
                    Name = "UABE text dump", Extensions = new List <string>()
                    {
                        "txt"
                    }
                },
                new FileDialogFilter()
                {
                    Name = "UABE json dump", Extensions = new List <string>()
                    {
                        "json"
                    }
                }
            };

            string[] fileList = await ofd.ShowAsync(this);

            if (fileList.Length == 0)
            {
                return;
            }

            string file = fileList[0];

            if (file != null && file != string.Empty)
            {
                if (file.EndsWith(".json"))
                {
                    await MessageBoxUtil.ShowDialog(this, "Not implemented", "There's no json dump support yet, sorry.");

                    return;
                }

                using (FileStream fs = File.OpenRead(file))
                    using (StreamReader sr = new StreamReader(fs))
                    {
                        AssetFileInfoEx selectedInfo = GetSelectedInfo();
                        long            selectedId   = selectedInfo.index;

                        AssetImportExport importer = new AssetImportExport();
                        byte[]? bytes = importer.ImportTextAsset(sr);

                        if (bytes == null)
                        {
                            await MessageBoxUtil.ShowDialog(this, "Parse error", "Something went wrong when reading the dump file.");

                            return;
                        }

                        AssetsReplacer replacer = AssetImportExport.CreateAssetReplacer(assetsFile.file, selectedInfo, bytes);
                        newAssets[selectedId]     = replacer;
                        newAssetDatas[selectedId] = new MemoryStream(bytes);

                        SetSelectedFieldModified();
                        modified = true;
                    }
            }
        }