Try โ€‚โ€‰HackMD

Batch Export from Character Studio

10-16-23

Generated all the manifest.json and named them $id_manifest.json in this zip: https://cdn.discordapp.com/attachments/1041270464271622234/1163308582591275079/female_manifest_json.zip?ex=653f1a8b&is=652ca58b&hm=6284e176678f846b1649b5a73d4267c842e975bba669491c9145c354d222c2a1&

I also generated 800x1356 thumbnails for each, and put into folders in this zip: https://cdn.discordapp.com/attachments/1041270464271622234/1163309952610357338/thumbnails_female.zip?ex=653f1bd1&is=652ca6d1&hm=a8af77c485562349baa00e99bf31ceac30dbb84ad269bd12753b69cf28e148fa&

the scripts I used are being uploaded here: https://github.com/M3-org/anata/tree/main/vrm/scripts


10-24-23

Need to debug some vertices being glued together in female clothing blend files

Image Not Showing Possible Reasons
  • The image file may be corrupted
  • The server hosting the image is unavailable
  • The image path is incorrect
  • The image format is not supported
Learn More โ†’

New export script

I modified the code a bit so it export each glass model with the same armature for each, maybe this scripts is also helpful in your side ๐Ÿ™‚ - memelotsqui

import bpy
import os
import sys

# REMEMBER TO SET THE EXPORT PATH
export_path = "/home/$USER/Desktop/Exports"
view_layer_name = 'ViewLayer'
view_layer = bpy.context.scene.view_layers.get(view_layer_name)

if view_layer is None:
    print(f"View Layer '{view_layer_name}' not found.")
    sys.exit(1)

bpy.context.window.view_layer = view_layer

# Get a list of all visible objects in the scene
visible_objects = [obj for obj in bpy.context.scene.objects if obj.parent is None]

# Iterate over each visible object and export it as a separate VRM file
for obj in visible_objects:
    # Skip objects not in the specified view layer
    if obj.name not in view_layer.objects:
        print(f"Object '{obj.name}' is not in view layer '{view_layer_name}'. Skipping.")
        continue
    
    # Search for a mesh in the hierarchy of children
    mesh = None
    for child in obj.children_recursive:
        if child.type == 'MESH':
            mesh = child
            # If a mesh is found and it's in the view layer, select it for export
            if mesh and mesh.name in view_layer.objects:
                # Set the filename for the exported VRM file
                armature = mesh.parent
                armature.data.vrm_addon_extension.spec_version = "0.0"
                filename = mesh.name + ".vrm"
                filepath = os.path.join(export_path, filename)

                # Select the mesh for export
                bpy.context.view_layer.objects.active = mesh
                mesh.select_set(True)
                
                # Export the mesh (VRM)
                bpy.ops.export_scene.vrm(
                    filepath=filepath,
                    export_invisibles=False,
                    enable_advanced_preferences=True,
                    export_fb_ngon_encoding=False,
                    export_only_selections=True,
                    armature_object_name=obj.name
                )
    
    

Prepping VRM Folder

First go into vrm/male or vrm/female and get all the JSON metadata from NFTs into current dir

find ./ -iname "*.json" -exec cp '{}' . \;

Now we need to convert the NFT metadata to a more simpler form. Copy convert_json.py from vrm/scripts and either the male or female renamed_traits.csv from metadata/csv in the Anata repo to current dir. It is a CSV that contains two columns, "Original","Rename".

Running convert_json.py will then copy new files to converted_json folder with the metadata matching the project directory / filename structure. I go into this folder then select / rename everything to be *_renamed.json for organization.

Then bring attributes2.sh from vrm/scripts and run in current directory to get simplified JSON per Anata, like below:

{ "name": "1", "attributes": [ { "trait_type": "BODY", "value": "Masculine" }, { "trait_type": "CLOTHING", "value": "Ragnarok_777_T_Shirt" }, { "trait_type": "HAIR", "value": "Mid_Red-Black" }, { "trait_type": "TYPE", "value": "Ragnarok" }, { "trait_type": "GLASSES", "value": "Modern_Shades" }, { "trait_type": "NECK", "value": "Silver_Links_Chain" }, { "trait_type": "BRACE", "value": "Strobe_Light_Brace" }, { "trait_type": "SET", "value": "Ragnarok" } ] }

I want to get all the preview images into the VRM folders now for male, I'll fetch them from another place in Anata project repo this way (saved as vrm/scripts/copy_previews.sh):

source_directory1="../../img/0-999"
source_directory2="../../img/1000-2000"

# Loop through the JSON files in the current directory
for json_file in *.json; do
    # Extract the filename without the .json extension
    filename=$(basename "$json_file" .json)

    # Debug: Show the filenames being checked
    echo "Checking for $filename.jpg in $source_directory1"

    # Check if a corresponding JPEG file exists in the source directory
    if [ -e "$source_directory1/$filename.jpg" ]; then
        echo "Copying $filename.jpg"
        cp "$source_directory1/$filename.jpg" "$filename.jpg"
    else
        echo "No matching JPEG file found for $filename.json"
    fi
    echo "Checking for $filename.jpg in $source_directory2"
    if [ -e "$source_directory2/$filename.jpg" ]; then
        echo "Copying $filename.jpg"
        cp "$source_directory2/$filename.jpg" "$filename.jpg"
    else
        echo "No matching JPEG file found for $filename.json"
    fi
done

I need to crop them a bit for the UI, using this command to make them the same portrait resolution across the app:

mkdir -p output  # Create an "output" directory if it doesn't exist
for file in *.jpg; do
    output_file="output/t_$file"
    convert "$file" -resize 800x1356^ -gravity center -extent 800x1356 "$output_file"
done

I want to move all the *_attribute.json files to each folder in vrm/male, I mv them from converted_json over to current dir and run this:

for file in *_attributes.json; do
    folder_name="${file%%_*}"  # Extract the numerical value
    mv "$file" "$folder_name/"
done

Combine Skin + Eyes

I'm starting with priority Anata first, and all these share the same skin texture so I want to copy the skintone texture to each folder.

source_file="/path/to/repo/anata/files/BODY/male_skintone/male_body_6.png"

# Define an array of destination folders
destination_folders=(1161 1183 1192 1297 1505 1524 1558 1562 1645 1736 195 32 338 412 718 867)

# Loop through the destination folders and copy the source file to each one
for folder in "${destination_folders[@]}"; do
  cp "$source_file" "$folder"                             
done

Now to combine with eyes, this will 2x eyes resolution to match skin then composite. Just have to run against the folder, it will output skin-eyes_$dirname.png in that folder. Just need tattoos next and it's ready to be used.

#!/bin/bash

# Check if an input directory argument is provided
if [ "$#" -ne 1 ]; then
  echo "Usage: $0 <input_directory>"
  exit 1
fi

input_directory="$1"

# Check if the directory exists
if [ ! -d "$input_directory" ]; then
  echo "Error: Directory $input_directory does not exist."
  exit 1
fi

# Define the desired resolution
resolution="4096x4096"

# Loop through all images starting with "eyes_" in the input directory
for eyes_image in "$input_directory"/eyes_*.png; do
  # Get the basename of the "eyes_" image (e.g., eyes_image.png)
  base_eyes_image=$(basename "$eyes_image")

  # Extract the filename without the extension (e.g., eyes_image)
  eyes_filename="${base_eyes_image%.png}"

  # Compose the output filename
  output_filename="$input_directory/skin-$eyes_filename.png"

  # Use a wildcard to find the male body image (e.g., male_body_*.png)
  male_body_image=$(find "$input_directory" -name "male_body_*.png" -print -quit)

  # Check if a male body image was found
  if [ -n "$male_body_image" ]; then
    # Upscale the "eyes_" image to 4096x4096
    convert "$eyes_image" -resize "$resolution" temp_eyes.png

    # Perform the image operations using the 'composite' command
    composite -gravity center temp_eyes.png "$male_body_image" "$output_filename"

    # Remove the temporary upscaled "eyes_" image
    rm temp_eyes.png

    echo "Processed $base_eyes_image"
  else
    echo "Error: Male body image not found for '$base_eyes_image'. Skipping."
  fi
done

Can batch convert with this snippet:

destination_folders=(1161 1183 1192 1297 1505 1524 1558 1562 1645 1736 195 32 338 412 718 867)

# Loop through the destination folders and copy the source file to each one
for folder in "${destination_folders[@]}"; do
  bash combine_skin-eyes.sh "$folder"                              
done

Score