private void LogDumpResults(string prefix, string output, TranslationCount before, TranslationCount after)
        {
            var delta = after - before;

            Logger.LogDebug(
                $"[TextDump] {DumpLevelCompleted + 1}/{DumpLevelMax} lines:{after.Lines,4:D} (new:{delta.Lines,4:D}) translations:{after.TranslatedLines,4:D} (new:{delta.TranslatedLines,4:D}) {prefix} {output}");
        }
Example #2
0
        private void KKS_TextDumpComplete(BaseTextDumpPlugin sender, EventArgs eventArgs)
        {
            var delta = _total - _lastTotal;

            if (DumpLevelCompleted >= DumpLevelMax)
            {
                NotificationMessage = string.Empty;


                if (_total == _lastTotal)
                {
                    _stableCount++;
                }
                else
                {
                    _lastTotal = _total;
                    if (_stableCount != 0)
                    {
                        _lastDelta = delta;
                    }
                    _stableCount = 0;
                }

                if (_stableCount < 3)
                {
                    StartCoroutine(RetryDelay(10));
                    if (_stableCount == 0)
                    {
                        NotificationMessage = $"Number of translations found is continuing to change ({delta})";
                    }
                    else
                    {
                        NotificationMessage = "Number of translations unchanged";
                    }


                    NotificationMessage +=
                        $", will keep re-dumping until it's stable for {3 - _stableCount} more cycle(s)";
                    DumpLevelCompleted--;
                    DumpLevelReady = DumpLevelCompleted;
                }
            }
            else if (DumpLevelCompleted > 0)
            {
                NotificationMessage =
                    "Multiple brute-force dump attempts are required, please wait until you see a message saying files are available";
            }
        }
        private TranslationCount DumpLocalizations()
        {
            var origCount = new TranslationCount(_localizationTotal);

            InitHelpers();
            var folderPath = LocalizationRoot;

            if (!Directory.Exists(folderPath))
            {
                Directory.CreateDirectory(folderPath);
            }

            foreach (var entry in LocalizationDumpHelper.GetLocalizations())
            {
                var output = entry.Path;

                switch (entry)
                {
                case StringTranslationDumper stringDumper:
                {
                    IDictionary <string, string> results;
                    try
                    {
                        results = stringDumper.Collector();
                    }
                    catch (Exception e)
                    {
                        results = new Dictionary <string, string>();
                        Logger.LogError(
                            $"[TextDump] Localization {output}: Error executing {entry.Collector.Method.Name}(): {e.Message}");
                    }

                    var filePath = Path.Combine(folderPath, $"{output}.txt");

                    var translations = GetTranslationsForPath(filePath);

                    var beforeCount = new TranslationCount(translations);
                    translations.Merge(results, TextResourceHelper);
                    var afterCount = new TranslationCount(translations);
                    LogDumpResults("Localization", output, beforeCount, afterCount);
                    var delta = afterCount - beforeCount;
                    _localizationTotal += delta;
                    break;
                }

                case ResizerDumper resizeDumper:
                {
                    IDictionary <string, List <string> > results;
                    try
                    {
                        results = resizeDumper.Collector();
                    }
                    catch (Exception e)
                    {
                        results = new Dictionary <string, List <string> >();
                        Logger.LogError(
                            $"[TextDump] Localization {output}: Error executing {entry.Collector.Method.Name}(): {e.Message}");
                    }

                    try
                    {
                        AssetLoader.UnloadBundles();
                    }
                    catch { }

                    var filePath = Path.Combine(folderPath, $"{output}_resizer.txt");

                    var resizers = GetResizersForPath(filePath);

                    resizers.Merge(results);

                    //var afterCount = new TranslationCount(translations);
                    //LogDumpResults("Localization", output, beforeCount, afterCount);
                    //_localizationTotal += afterCount - beforeCount;

                    break;
                }

                default:
                    Logger.LogError($"[TextDump] Localization {output}: {entry} is unsupported dumper type");
                    break;
                }
            }

            var totalDelta = _localizationTotal - origCount;

            Logger.LogInfo(
                $"[TextDump] Total Localization lines (translated): {_localizationTotal} (change {totalDelta})");
            return(totalDelta);
        }
        private TranslationCount DumpAssets()
        {
            var origCount = new TranslationCount(_assetTotal);

            InitHelpers();
            var folderPath = AssetsRoot;

            if (!Directory.Exists(folderPath))
            {
                Directory.CreateDirectory(folderPath);
            }

            foreach (var assetDumper in AssetDumpHelper.GetAssetDumpers())
            {
                var output = assetDumper.Path;

                switch (assetDumper)
                {
                case StringTranslationDumper stringDumper:
                {
                    IDictionary <string, string> results;
#pragma warning disable CA1031 // Do not catch general exception types
                    try
                    {
                        results = stringDumper.Collector();
                    }

                    catch (Exception e)
                    {
                        results = new Dictionary <string, string>();
                        Logger.LogError(
                            $"[TextDump] Asset {output}: Error executing {assetDumper.Collector.Method.Name}(): {e.Message}");
                        Logger.LogDebug($"[TextDump] Asset {output}:\n{e.StackTrace}");
                    }


                    try
                    {
                        AssetLoader.UnloadBundles();
                    }
                    catch { }
#pragma warning restore CA1031 // Do not catch general exception types

                    var filePath = Path.Combine(folderPath, $"{output}.txt");

                    var translations = GetTranslationsForPath(filePath);

                    var beforeCount = new TranslationCount(translations);
                    translations.Merge(results, TextResourceHelper);
                    var afterCount = new TranslationCount(translations);

                    LogDumpResults("Asset", output, beforeCount, afterCount);

                    var delta = afterCount - beforeCount;
                    _assetTotal += delta;
                    break;
                }

#if RAW_DUMP_SUPPORT
                case RawTranslationDumper rawDumper:
                {
                    var filePath = Path.Combine(folderPath, $"{output}.bytes");
                    Logger.LogFatal($"RawTranslationsDict[{filePath}] = {rawDumper.Collector}");
                    RawTranslationsDict[filePath] = new Func <IEnumerable <byte> >(rawDumper.Collector);
                    break;
                }
#endif
                default:
                    Logger.LogError($"[TextDump] Asset {output}: {assetDumper} is unsupported dumper type");
                    break;
                }
            }

            var totalDelta = _assetTotal - origCount;
            Logger.LogInfo($"[TextDump] Total Asset lines (translated): {_assetTotal} (change {totalDelta})");

            return(totalDelta);
        }
        private void DumpText(string from)
        {
            if (string.IsNullOrEmpty(from))
            {
                throw new ArgumentException("Value cannot be null or empty.", nameof(from));
            }

            InitHelpers();
            DumpStarted = true;
            LogWithMessage(BepInExLogLevel.Warning,
                           $"[TextDump] Starting dump {DumpLevelCompleted + 1}/{DumpLevelMax} from {from}. Application may become unresponsive, please wait.");

            if (Directory.Exists(DumpRoot))
            {
                Directory.Delete(DumpRoot, true);
            }

            // if using BeforeFirstLoad it's best not to try doing localizations (if we're dumping more than once).
            var skipLocalizations = CurrentExecutionMode == ExecutionMode.BeforeFirstLoad && DumpLevelCompleted == 0 &&
                                    DumpLevelMax > 1;

            var dumpAssets = CurrentAssetDumpMode == AssetDumpMode.Always ||
                             DumpLevelCompleted < 1 && CurrentAssetDumpMode.HasFlag(AssetDumpMode.FirstOnly) ||
                             DumpLevelReady == DumpLevelMax && CurrentAssetDumpMode.HasFlag(AssetDumpMode.LastOnly) ||
                             CurrentAssetDumpMode == AssetDumpMode.CustomLevels && AssetDumpLevels != null &&
                             AssetDumpLevels.Contains(DumpLevelCompleted + 1);

            if (dumpAssets)
            {
                _total += DumpAssets();
            }

            if (!skipLocalizations)
            {
                _total += DumpLocalizations();
            }

            Logger.LogInfo($"[TextDump] Total lines (translated):{_assetTotal + _localizationTotal}");
            DumpCompleted = true;
            DumpLevelCompleted++;
            LogWithMessage(BepInExLogLevel.Info, $"[TextDump] Dump {DumpLevelCompleted}/{DumpLevelMax} completed.");

            OnTextDumpLevelComplete(EventArgs.Empty);

            if (AreAllDumpsComplete())
            {
                if (dumpAssets)
                {
                    AssetDumpHelper.LogUnmatchedDumpers();
                }

                try
                {
                    AssetLoader.UnloadBundles();
                }
                catch { }
            }

            if (!WriteAfterEachDump && (!WriteAfterFinalDump || !AreAllDumpsComplete()))
            {
                return;
            }
            if (WriteInProgress)
            {
                return;
            }
            StartCoroutine(WriteTranslations());
        }