I have a python module for Defold that I use quite frequently when I do batch changes. Removing all layouts, scaling all particle effects, cleaning up gui scenes, generally finding out information and such. Available here if anyone want to check it out https://deftree.readthedocs.io
It works but consider it a beta, as I will highly likely make breaking change to the API in the future (but will keep it versioned properly of course).
You can find the source on
Examples
Here are some examples, updated for 1.0.2
You have removed a lot of images from disk that you know are obsolete and now you need to clean up all atlases.
Remove unused images in atlases
import os
import deftree
def get_files(project_root, ending):
# Generator to get files
for root, folders, files in os.walk(project_root):
for f in files:
if f.endswith(ending):
yield os.path.join(root, f)
def get_images(df_object):
"""get all images paths in a given DefTree Element instance"""
for x in df_object.elements():
if deftree._is_element(x):
get_images(x)
else:
yield x
def missing_images_in_atlas(project_root, atlas):
"""get images in an atlas that does not exist on disk"""
tree = deftree.DefTree()
root = tree.parse(atlas)
for image in get_images(root):
if not os.path.exists(os.path.join(project_root, image[1:])):
yield image
def clean_up_atlas(project_root, atlas):
"""Remove all missing image in entries in the atlas"""
for missing in missing_images_in_atlas(project_root, atlas):
tree = deftree.parse(atlas)
root = tree.get_root()
for img in get_images(root):
if img == missing:
root.remove(img.get_parent())
tree.write(atlas)
def verify(project_folder):
"""Print images that are missing on disk"""
for atlas in get_files(project_folder, ".atlas"):
for missing in missing_images_in_atlas(project_folder, atlas):
print("{}{}{}".format(atlas.replace(project_folder, ""),
(50 - len(atlas.replace(project_folder, ""))) * " ",
missing))
def clean_up_all_atlases(project_folder):
"""Remove all missing image in entries in the project"""
for atlas in get_files(project_folder, ".atlas"):
clean_up_atlas(project_folder, atlas)
You thought you wanted layouts when you started but now you have changed your mind.
Remove Layouts
import deftree
import os
def get_files(project_root, ending):
# Generator to get files
for root, folders, files in os.walk(project_root):
for f in files:
if f.endswith(ending):
yield os.path.join(root, f)
def main(project):
errors = list()
for gui in get_files(project, ".gui"):
# Create our tree
tree = deftree.parse(gui)
root = tree.get_root()
rem = False
# Find all layouts
for layout in root.iter_elements("layouts"):
# For error reporting
errors.append("{}".format(gui))
rem = True
# Remove the child layout from the root
root.remove(layout)
# If we removed a layout rewrite the file
if rem:
tree.write(gui)
# Report our errors
if errors:
[print(x) for x in errors]
You for some reason want to sort your atlases
Sort Atlases
import os
import deftree
def sort_atlas(atlas):
tree = deftree.parse(atlas)
root = tree.get_root()
org = deftree.to_string(root)
new_tree = deftree.DefTree()
new_root = new_tree.get_root()
_atlas = []
_animations = []
for at in root.iter_elements("images"):
_atlas.append(at.get_attribute("image").value)
for ani in root.iter_elements("animations"):
_animations.append(ani)
# Sort the images
for a in sorted(_atlas, key=lambda x: x.split("/")[-1]):
ele = new_root.add_element("images")
ele.add_attribute("image", a)
# Add the animations
for animation in _animations:
new_root.append(animation)
# Add the atlas attributes. Margin, extrude
for at in root.attributes():
if not at.name == "image":
new_root.append(at)
new_tree.write(atlas)
if not deftree.validate(org, deftree.to_string(new_root)):
print("Sorted: {}".format(atlas))
You noticed that without extrude 2 on your altases you get bleeding
Batch Edit Atlas Property
import os
import deftree
def get_files(project_root, ending):
# Generator to get files
for root, folders, files in os.walk(project_root):
for f in files:
if f.endswith(ending):
yield os.path.join(root, f)
def set_atlas_extrude(project_folder, value):
for atlas in get_files(project_folder, ".atlas"):
tree = deftree.parse(atlas)
root = tree.get_root()
root.set_attribute("extrude_borders", value)
tree.write(atlas)
It is made for python 3.3 or newer and is easiest installed with pip install deftree