Hey I need help adding materials to a UIList, I have used this answer as a guide: https://blender.stackexchange.com/a/30446/51645
Here is the functionality I need, I need to be able to click the add button and create a material, apply it and store it in the UIList. I also need to be able to rename the material in the list and have it rename the actual material name. In the same way I need to access and change the material diffuse_color in the UIList. I have tried with a prop_search, it works but I can't edit the material name.
I have commented the sections I have tried to get working.
import bpy
from bpy.props import IntProperty, CollectionProperty
from bpy.types import Panel, UIList
# create material
def add_material():
material = bpy.data.materials.new("cg_")
material.diffuse_color = (1, 0, 0)
stored_selection = bpy.context.selected_objects
for obj in stored_selection:
obj.data.materials.clear()
obj.data.materials.append(material)
return material.name
class Uilist_actions(bpy.types.Operator):
bl_idname = "custom.list_action"
bl_label = "List Action"
action = bpy.props.EnumProperty(
items=(
('UP', "Up", ""),
('DOWN', "Down", ""),
('REMOVE', "Remove", ""),
('ADD', "Add", ""),
)
)
def invoke(self, context, event):
scn = context.scene
idx = scn.custom_index
try:
item = scn.custom[idx]
except IndexError:
pass
else:
if self.action == 'DOWN' and idx < len(scn.custom) - 1:
item_next = scn.custom[idx+1].name
scn.custom.move(idx, idx + 1)
scn.custom_index += 1
info = 'Item %d selected' % (scn.custom_index + 1)
self.report({'INFO'}, info)
elif self.action == 'UP' and idx >= 1:
item_prev = scn.custom[idx-1].name
scn.custom.move(idx, idx-1)
scn.custom_index -= 1
info = 'Item %d selected' % (scn.custom_index + 1)
self.report({'INFO'}, info)
elif self.action == 'REMOVE':
info = 'Item %s removed from list' % (scn.custom[scn.custom_index].name)
scn.custom_index -= 1
self.report({'INFO'}, info)
scn.custom.remove(idx)
if self.action == 'ADD':
item = scn.custom.add()
item.id = len(scn.custom)
# assign material reference by name
item.material_ref = add_material()
scn.custom_index = (len(scn.custom)-1)
info = '%s added to list' % (item.name)
self.report({'INFO'}, info)
return {"FINISHED"}
class UL_items(UIList):
def draw_item(self, context, layout, data, item, icon, active_data, active_propname, index):
split = layout.split(0.5)
# material name
split.prop(item, "material_ref", text="", emboss=False, translate=False, icon='BORDER_RECT')
# material prop search
split.prop_search(item, "material_ref", bpy.data, "materials", text = "")
def invoke(self, context, event):
pass
class UIListPanelExample(Panel):
"""Creates a Panel in the Object properties window"""
bl_idname = 'OBJECT_PT_my_panel'
bl_space_type = "TEXT_EDITOR"
bl_region_type = "UI"
bl_label = "Custom Object List"
def draw(self, context):
layout = self.layout
scn = bpy.context.scene
rows = 2
row = layout.row()
row.template_list("UL_items", "", scn, "custom", scn, "custom_index", rows=rows)
col = row.column(align=True)
col.operator("custom.list_action", icon='ZOOMIN', text="").action = 'ADD'
col.operator("custom.list_action", icon='ZOOMOUT', text="").action = 'REMOVE'
col.separator()
col.operator("custom.list_action", icon='TRIA_UP', text="").action = 'UP'
col.operator("custom.list_action", icon='TRIA_DOWN', text="").action = 'DOWN'
class CustomProp(bpy.types.PropertyGroup):
'''name = StringProperty() '''
# add material_ref
material_ref = bpy.props.StringProperty()
id = IntProperty()
def register():
bpy.utils.register_module(__name__)
bpy.types.Scene.custom = CollectionProperty(type=CustomProp)
bpy.types.Scene.custom_index = IntProperty()
def unregister():
bpy.utils.unregister_module(__name__)
del bpy.types.Scene.custom
del bpy.types.Scene.custom_index
if __name__ == "__main__":
register()
Thank you so much to anyone who helps.