A PyQt6-based desktop tool for Unreal Engine projects, providing three core capabilities:
- Folder comparison and patch management
- UE MemReport memory analysis and multi-report comparison
- UAsset / UMap read-only viewer, single-asset structured Compare, and Bundle directory scanning
The UI uses a custom modern desktop style with persistent light/dark themes and Chinese/English switching. The UAsset tool never modifies original asset files.
- Installation & Running
- Feature 1: Folder Compare & Patch
- Feature 2: MemReport Analysis
- Feature 3: UAsset Tools
- Appearance, Language & Updates
- Building an exe
- Project Structure
- Python 3.11+
- Windows 10/11
pip install -r requirements.txtKey dependencies:
PyQt6>=6.6— desktop UImatplotlib>=3.8— MemReport chartsCython>=3.0— optional, for recompiling the accelerated parser (pre-built.pydfiles are included in the repo)
python main.pyOn startup a cache/ directory is automatically created next to the script (or the packed exe), used for settings and runtime cache.
General folder comparison for file diffing and patch workflows, independent from the UAsset Bundle directory scanner.
- Select a source folder and a target folder.
- Click Compare — the tool recursively scans files and uses MD5 to detect changes.
- Use status filters, swap left/right, expand/collapse, and the bottom summary to review results.
Supported statuses: same, modified, added (target only), and deleted (source only). Double-clicking a file opens a text Diff or binary Hex Diff.
Patches are ZIP archives containing a manifest.json change list and the full content of added/modified files. Before applying, a summary of add/modify/delete operations is shown for confirmation.
Parses Unreal Engine memreport -full output files (.memreport, .txt, or .log).
On import, a JSON intermediate cache is automatically created or reused under the cache/ directory. The filename includes the original filename and a path hash — it is never written to the report's own directory. Cache validity is checked against the source file state. Use Export JSON to save data to a user-selected path.
The left-side section tree supports overview, table, key-value, and raw text views. Tables support keyword filtering, numeric alignment, thousands formatting, column resizing, and read-only browsing. After importing multiple files you can switch between reports and use the multi-report comparison view for aggregated metrics, shared key-value / table sections, bar charts, and line charts.
Sections are one of three types:
| type | Description | Fields |
|---|---|---|
table |
Tabular data | headers and rows |
kv |
Key-value pairs | data |
raw |
Raw text | lines |
Supports .uasset and .umap primary assets. The parser automatically locates associated external data; Bundle directory scanning also associates .uexp, .ubulk, and .uptnl sidecars.
The UAsset parser supports two backends, preferring the Cython-compiled version:
| Backend | Files | Notes |
|---|---|---|
| Cython | app/uasset/parser/*.pyd |
Pre-built, better performance, included in repo |
| Pure Python | app/uasset/uasset_parser.py |
Fallback, no compilation needed |
To recompile the pyd files, run build_cython.bat (requires Cython installed).
Assets can be opened via the toolbar, the empty-state button, or drag-and-drop. The left-side content tree is dynamically built from actual asset content:
- General Information, Name Map, Imports, Export Information
- Soft Object Paths, Depends Map, Soft Package References, Data Resources
- Custom Versions, Export Properties, Extra Data
- Raw Binary for individual exports, and Raw Binary (All) for the entire file
Tables are read-only with support for selection, column resizing, copy, and find. Object references can jump between Import/Export nodes; parsed results can be exported as JSON.
Raw Binary uses a virtualized hex table for large files, with Offset, Hex, ASCII, and Region columns. Regions identify Header, Export, properties, and Extra Data areas.
Click Compare Assets to load left and right assets. The Compare page uses background loading and diff computation, supporting:
- General, Name Map, Imports, Export Information, Properties, Extra Data, and Raw Binary
- Structured alignment for Name Map, Imports, Exports, and property rows
- Diff categories: Added, Removed, Changed, Binary, Offset Noise, Heuristic Cascade
- Diff-only view, prev/next/first/last diff navigation, and precise structured positioning
- Synchronized left/right scrolling, Hex/ASCII diff highlighting, and region/byte alignment
Scans directories as Asset Bundles, grouping primary files with their sidecars:
- Primary:
.uasset,.umap - Sidecars:
.uexp,.ubulk,.uptnl - Results show same, diff, left-only, right-only, and error; displays Changed Parts, Bundle size, and scan issues
- Recursive scanning, progress, cancel, path history, status filtering, up to 500 results per page
- Export JSON Schema v3: roots, entries, parts, issues, and orphan sidecars
- Double-click a matched pair to open single-asset Compare; double-click a single-side file to open the viewer
Statistics are split into scan stats (available immediately after scanning) and on-demand structured stats (computed by a background worker). The stats page has five sections:
- Overview: total,
.umap, file count, diff, left-only, right-only, same, error, left/right sizes, Delta - File type distribution: diffs, unique files, sizes, and Delta for primary files vs. sidecars
- Change reason analysis: counts, affected files, and byte impact by
DiffEntry.reason - Section frequency: counts, affected files, and byte impact by
DiffLocation.section - Field frequency: counts, affected files, and byte impact by
DiffLocation.field
- Switch light/dark theme in Settings; the selection is saved to
cache/. - Switch Chinese/English in Settings; main pages, tables, and toolbars update immediately.
- The Help menu provides version info, update check, and release history. New versions are checked silently on startup — the same version is only prompted once.
Double-click build.bat. The script handles everything automatically:
- Installs
requirements.txtdependencies and PyInstaller - Attempts to compile Cython extensions (silently falls back to pure Python on failure)
- Packages
dist/PatchTool.exeusingbuild.spec
To recompile only the pyd files:
build_cython.batPatchTool/
├── main.py
├── requirements.txt
├── build.bat # one-click build
├── build_cython.bat # recompile Cython extensions only
├── build.py / build.spec
├── gui/ # Cython pyd compatibility shim (property_parser_loader)
├── app/
│ ├── main_window.py # main window, menus, workspace, update entry
│ ├── i18n.py # Chinese / English strings
│ ├── theme.py / styles.py # themes, palette, QSS
│ ├── update_checker.py # version check
│ ├── release_dialog.py # release history
│ ├── compare/ # folder compare, Diff, and patch
│ ├── memreport/
│ │ ├── memreport_parser.py # MemReport parser
│ │ ├── memreport_widget.py # MemReport page and JSON import/export
│ │ ├── cache.py # JSON cache
│ │ ├── compare_view.py # multi-report comparison
│ │ └── chart_widgets.py # charts
│ └── uasset/
│ ├── uasset_widget.py # viewer and UAsset workspace
│ ├── uasset_parser.py # UAsset / UMap parser (pure Python)
│ ├── property_parser.py # export property parser (pure Python)
│ ├── table_handler.py # tables and virtual Raw Binary
│ ├── compare_dialog.py # single-asset structured Compare
│ ├── folder_compare_dialog.py# Bundle directory scan, filter, paging, export
│ ├── diff_stats_dialog.py # five-section scan / on-demand structured stats
│ ├── workers.py # load, scan, Compare, stats analysis workers
│ ├── models/ # AssetBundle, DiffReport, etc.
│ ├── services/ # Bundle scan, single-asset diff, stats services
│ └── parser/
│ ├── uasset_parser_cy.pyd # pre-built Cython parser
│ ├── property_parser_cy.pyd # pre-built Cython property parser
│ ├── backend.py # backend selection (Cython / pure Python)
│ └── setup.py # Cython build config
└── tests/
└── uasset/ # UAsset worker, service, and page tests