Skip to content

Instantly share code, notes, and snippets.

@zeffii
Created June 5, 2012 08:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save zeffii/2873680 to your computer and use it in GitHub Desktop.
Save zeffii/2873680 to your computer and use it in GitHub Desktop.
dynamic_menu_not_ideal_but_works
import os
import bpy
from bpy.props import StringProperty
from os.path import join
from collections import OrderedDict
# helper constant strings
split_token = "<--->"
material_locator = "\\Material\\"
locator_prefix = "//"
path_to_scripts = bpy.utils.script_paths()[0]
path_to_script = join(path_to_scripts, 'addons_contrib', 'io_material_loader')
# helper functions
def import_material(file_name, matname):
file_name += '.blend'
opath = locator_prefix + file_name + material_locator + matname
dpath = join(path_to_script, file_name) + material_locator
bpy.ops.wm.link_append(
filepath=opath, # "//filename.blend\\Folder\\"
filename=matname, # "material_name
directory=dpath, # "fullpath + \\Folder\\
filemode=1,
link=False,
autoselect=False,
active_layer=True,
instance_groups=False,
relative_path=True)
def get_source_files():
source_files = []
source_files.extend(source_list(path_to_script,
filename_check=lambda f:f.endswith(".blend")))
return source_files
def source_list(path, filename_check=None):
for dirpath, dirnames, filenames in os.walk(path):
# skip hidden dirs
if dirpath.startswith("."):
continue
for filename in filenames:
# skip non .blend
if not filename.endswith('.blend'):
continue
# we want these
filepath = join(dirpath, filename)
if filename_check is None or filename_check(filepath):
yield filepath
def get_materials_dict():
source_files = get_source_files()
mlist = OrderedDict()
for i, filepath in enumerate(source_files):
file_name = filepath.split(os.sep)[-1].replace('.blend', '')
# print list of materials with users, if present.
with bpy.data.libraries.load(filepath) as (data_from, data_to):
if data_from.materials:
materials_in_file = [mat for mat in data_from.materials]
mlist[file_name] = materials_in_file
return mlist
class AddMaterial(bpy.types.Operator):
bl_idname = "scene.add_material_operator"
bl_label = "Add Material Operator"
selection = StringProperty()
def execute(self, context):
file_name, file_material = self.selection.split(split_token)
import_material(file_name, file_material)
return {'FINISHED'}
class CustomMenu(bpy.types.Menu):
bl_label = "Materials"
bl_idname = "OBJECT_MT_custom_menu"
my_mat_dict = get_materials_dict()
def draw(self, context):
layout = self.layout
for key in self.my_mat_dict:
for material_choice in self.my_mat_dict[key]:
info = key + split_token + material_choice
layout.operator( 'scene.add_material_operator',
text=material_choice).selection = info
layout.label(text=key, icon='MATERIAL')
def draw_item(self, context):
layout = self.layout
layout.menu(CustomMenu.bl_idname)
def register():
bpy.utils.register_class(AddMaterial)
bpy.utils.register_class(CustomMenu)
bpy.types.NODE_HT_header.append(draw_item)
def unregister():
bpy.utils.unregister_class(AddMaterial)
bpy.utils.unregister_class(CustomMenu)
bpy.types.NODE_HT_header.remove(draw_item)
if __name__ == "__main__":
register()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment