• I have assigned a script-expression driver to a field in a modifier.
  • The expression is a function of properties of the object to which the modifier is assigned, extracted as Single Property variables.

I can CtrlL link the modifier to a new object. I can copy the driver from the old object's modifier, and paste it into the new object's modifier.

But, of course, the driving properties still refer to the old object, and so I have to go in and manually point the variables in the driver to the new object.

How should I use 'self', or suchlike, either in an expression, or in a driver-namespace function, so I can copy the driver between modifiers on separate objects, always referring to the object the modifier is assigned to?


I've just worked out that self in an expression driving a modifier field, refers to the modifier, not the object the modifier is assigned to.

AND YET, if I create single-property variables to be used in the expression in the UI, the root is the object. For example, to reach the value of a field in the driven modifier that way, I use modifiers["name"].modifier_property.

This makes no sense to me at all...


The id_data property of any object returns an ID object

Simple example adding a driver to the count of an array modifier The modifier is on the default cube.

enter image description here

The driver script, prints out self, self.id_data the path from self.id_data to self and returns 2.

import bpy

def test(self):
    return 2

bpy.app.driver_namespace["test"] = test

Here is the output to console

<bpy_struct, ArrayModifier("Array")>
<bpy_struct, Object("Cube")>

Hence other properties of the modifier can be accessed using self.other_modifier_property and properties of the object it is on via self.id_data.some_object_property

The driver UI deals in ID objects, as does the datapath used by fcurves etc. You select the (ID) bpy.types.Object instance the modifier is on, and add the datapath from ID object to modifier. In this case self = self.id_data.modifiers["Array"]

  • $\begingroup$ Phew! Thank you. This begins to crack open a lot more than this particular problem, for me. I've been able to go back and read the API introduction and bpy_struct with a bit more understanding. I often wish the documentation for this and other APIs would kick off with more of a view from 30 000 ft - How to look at the data structures / database, in plain language, before considering how to use them. $\endgroup$ – Robin Betts Jan 9 '19 at 8:28
  • 1
    $\begingroup$ It's the string representation of most blender objects str(obj) Consider <bpy_struct, Object("Cube")> an instance of bpy.types.Object named "Cube". Printing repr(self.id_data) would return bpy.data.objects["Cube"] $\endgroup$ – batFINGER Jan 9 '19 at 9:07

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.