Skip to content

Instantly share code, notes, and snippets.

@versluis
Created August 15, 2017 18:26
Show Gist options
  • Select an option

  • Save versluis/2e092b466b989b1e91f316599bcce016 to your computer and use it in GitHub Desktop.

Select an option

Save versluis/2e092b466b989b1e91f316599bcce016 to your computer and use it in GitHub Desktop.
Export all Shape Keys from Blender to OBJ files
# Export all Shape Keys as OBJs in Blender
# Version 1.0 - August 2017
# =========================================
# Original Script by Tlousky
# https://blender.stackexchange.com/questions/86674/how-to-batch-export-shapekeys-as-obj-from-the-active-object/86678#86678
# with small tweaks by Jay Versluis
# https://www.versluis.com
import bpy
from os.path import join
# Reference the active object
o = bpy.context.active_object
# CHANGE THIS to the folder you want to save your OBJ files in
# NOTE: no spaces, no trailing slash
exportPath = "/Users/you/somewhere"
# Reset all shape keys to 0 (skipping the Basis shape on index 0
for skblock in o.data.shape_keys.key_blocks[1:]:
skblock.value = 0
# Iterate over shape key blocks and save each as an OBJ file
for skblock in o.data.shape_keys.key_blocks[1:]:
skblock.value = 1.0 # Set shape key value to max
# Set OBJ file path and Export OBJ
objFileName = skblock.name + ".obj" # File name = shapekey name
objPath = join( exportPath, objFileName )
bpy.ops.export_scene.obj( filepath = objPath, use_selection = True, global_scale = 1 )
skblock.value = 0 # Reset shape key value to 0
# THE END
@ecktoreckzahn
Copy link

In 4.2.2 I had to change the expression for scaling back to global_scale:
bpy.ops.wm.obj_export(filepath = objPath,export_selected_objects=True,export_uv=True,global_scale=1.0,apply_modifiers=True,export_materials=False)

@NikkosAM
Copy link

NikkosAM commented Aug 4, 2025

In case anyone was looking for a fix for 4.5:

import bpy
import os

# ——— CONFIGURE THIS ———
export_dir = r""
# ——————————————————————

# 1) Validate export directory
if not os.path.isdir(export_dir):
    raise RuntimeError(f"Export directory not found: {export_dir}")

# 2) Get and validate the active mesh object
obj = bpy.context.active_object
if not obj or obj.type != 'MESH':
    raise RuntimeError("Please select an active mesh object with Shape Keys.")

keys = obj.data.shape_keys
if not keys or len(keys.key_blocks) < 2:
    raise RuntimeError("Mesh has no Shape Keys to export.")

# 3) Ensure we're in Object Mode and the mesh is selected
if bpy.ops.object.mode_set.poll():
    bpy.ops.object.mode_set(mode='OBJECT')
bpy.ops.object.select_all(action='DESELECT')
obj.select_set(True)
bpy.context.view_layer.objects.active = obj

# 4) Reset all Shape Keys (skip the Basis at index 0)
for sk in keys.key_blocks[1:]:
    sk.value = 0.0

# 5) Export each Shape Key as its own OBJ
for sk in keys.key_blocks[1:]:
    sk.value = 1.0
    # Force the dependency graph to update mesh data
    bpy.context.view_layer.update()
    
    # Build the export path
    filename = f"{sk.name}.obj"
    filepath = os.path.join(export_dir, filename)
    
    # Export using the new OBJ operator in Blender 4.x
    bpy.ops.wm.obj_export(
        filepath=filepath,
        export_selected_objects=True,
        export_uv=True,
        apply_modifiers=True,
        export_materials=False
    )
    print(f"✅ Exported Shape Key '{sk.name}' → {filepath}")
    
    # Reset this Shape Key
    sk.value = 0.0

print("All Shape Keys have been exported.")

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment