Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ def unpack_all_assets(source_folder : str, destination_folder : str):
img.save(dest)

# alternative way which keeps the original path
for path,obj in env.container.items():
for path,obj in env.container:
if obj.type.name in ["Texture2D", "Sprite"]:
data = obj.read()
# create dest based on original path
Expand Down Expand Up @@ -181,7 +181,7 @@ One of these objects can be an AssetBundle, which contains a file path for some

All objects can be found in the `.objects` dict - `{ID : object}`.

The objects with a file path can be found in the `.container` dict - `{path : object}`.
The objects with a file path can be found in the `.container` list - `[(path, object)]`.

### [Object](UnityPy/files/ObjectReader.py)

Expand Down
8 changes: 3 additions & 5 deletions UnityPy/classes/AssetBundle.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,6 @@ def __init__(self, reader):
preload_table_size = reader.read_int()
self.m_PreloadTable = [PPtr(reader) for _ in range(preload_table_size)]
container_size = reader.read_int()
self.m_Container = {}
# TODO - m_Container is a multi-dict, multiple values can have the same key
for i in range(container_size):
key = reader.read_aligned_string()
self.m_Container[key] = AssetInfo(reader)
self.m_Container = []
for _ in range(container_size):
self.m_Container.append((reader.read_aligned_string(), AssetInfo(reader)))
8 changes: 4 additions & 4 deletions UnityPy/classes/ResourceManager.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,17 +7,17 @@ class ResourceManager(Object):
def __init__(self, reader):
super().__init__(reader)
m_ContainerSize = reader.read_int()
self.m_Container = {
reader.read_aligned_string(): PPtr(reader)
self.m_Container = [
(reader.read_aligned_string(), PPtr(reader))
for _ in range(m_ContainerSize)
}
]

def save(self, writer: EndianBinaryWriter = None):
if not writer:
writer = EndianBinaryWriter(endian=self.reader.endian)
super().save(writer, intern_call=True)
writer.write_int(len(self.m_Container))
for key, val in self.m_Container.items():
for key, val in self.m_Container:
writer.write_aligned_string(key)
save_ptr(val, writer)
return writer
14 changes: 7 additions & 7 deletions UnityPy/environment.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import List, Callable, Dict, Union
from typing import List, Tuple, Callable, Dict, Union
import io
import os
from zipfile import ZipFile
Expand Down Expand Up @@ -179,14 +179,14 @@ def search(item):
return search(self)

@property
def container(self) -> Dict[str, ObjectReader]:
"""Returns a dictionary of all objects in the Environment."""
return {
path: obj
def container(self) -> List[Tuple[str, ObjectReader]]:
"""Returns a list of all objects in the Environment."""
return [
(path, obj)
for f in self.files.values()
if isinstance(f, File)
for path, obj in f.container.items()
}
for path, obj in f.container
]

@property
def assets(self) -> list:
Expand Down
8 changes: 4 additions & 4 deletions UnityPy/files/File.py
Original file line number Diff line number Diff line change
Expand Up @@ -128,12 +128,12 @@ def get_writeable_cab(self, name: str = None):

@property
def container(self):
return {
path: obj
return [
(path, obj)
for f in self.files.values()
if isinstance(f, File)
for path, obj in f.container.items()
}
for path, obj in f.container
]

def get(self, key, default=None):
return getattr(self, key, default)
Expand Down
10 changes: 5 additions & 5 deletions UnityPy/files/SerializedFile.py
Original file line number Diff line number Diff line change
Expand Up @@ -181,7 +181,7 @@ class SerializedFile(File.File):
externals: list
_container: dict
objects: dict
container_: dict
container_: list
_cache: dict
header: SerializedFileHeader

Expand Down Expand Up @@ -210,7 +210,7 @@ def __init__(self, reader: EndianBinaryReader, parent=None, name=None):
self._container = {}

self.objects = {}
self.container_ = {}
self.container_ = []
# used to speed up mass asset extraction
# some assets refer to each other, so by keeping the result
# of specific assets cached the extraction can be speed up by a lot.
Expand Down Expand Up @@ -292,13 +292,13 @@ def __init__(self, reader: EndianBinaryReader, parent=None, name=None):
for obj in self.objects.values():
if obj.type == ClassIDType.AssetBundle:
data = obj.read()
for container, asset_info in data.m_Container.items():
for container, asset_info in data.m_Container:
asset = asset_info.asset
self.container_[container] = asset
self.container_.append((container, asset))
if hasattr(asset, "path_id"):
self._container[asset.path_id] = container
# if environment is not None:
# environment.container = {**environment.container, **self.container}
# environment.container = [*environment.container, *self.container]

@property
def container(self):
Expand Down
2 changes: 1 addition & 1 deletion UnityPy/tools/extractor.py
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ def defaulted_export_index(type: ClassIDType):

if use_container:
container = sorted(
env.container.items(), key=lambda x: defaulted_export_index(x[1].type)
env.container, key=lambda x: defaulted_export_index(x[1].type)
)
for obj_path, obj in container:
# The filter here can only access metadata. The same filter may produce a different result later in extract_obj after obj.read()
Expand Down
2 changes: 1 addition & 1 deletion examples/AssetPatch/patch.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ def main():
src = os.path.join(root, "522608825")
e = UnityPy.load(src)
# iterate over all localisation assets
for cont, obj in e.container.items():
for cont, obj in e.container:
# read the asset data
data = obj.read()
# get the localisation data
Expand Down