0
$\begingroup$

I'm dynamically registering a variable number of panel classes, all sub-classed from a custom panel class that includes an operator. Thus all the new panel sub-classes contain a button that executes this common, ancestral operator code. When the button on one of these new sub-class panels is clicked I would like the operator code to be able to determine which of the panel/button instances invoked it. Is such a thing possible? My apologies if I've not described this very clearly. Basically I'm trying to recreate the same functionality as the 'X' button that sits in the header of modifiers sub-panels. In my example, the code behind the X button needs to know which panel class the clicked button belongs to in order to unregister the correct panel. Any advice is greatly welcomed and appreciated. Thank you!

$\endgroup$
2
  • 1
    $\begingroup$ Suggest you could do this by setting a context pointer in layout to the class to unregister. eg blender.stackexchange.com/a/203443/15543 row.context_pointer_set(name="foo", data=self.__class__) $\endgroup$ – batFINGER Dec 7 '20 at 16:05
  • $\begingroup$ @batFINGER Thanks! Per the idea from lemon, I just got this working by storing the panel class bl_idname in an operator variable when the panel is registered, then later using that to unregister the panel. That works but it still feels a little imperfect, a pointer would be much cleaner. I'll try your suggestion later, thank you again for taking the time to answer. $\endgroup$ – Quentin Walker Dec 7 '20 at 16:51
1
$\begingroup$

You can define a property for the operator in order to identify something.

For instance:

class SimpleOperator(bpy.types.Operator):
    """Tooltip"""
    bl_idname = "object.simple_operator"
    bl_label = "Simple Object Operator"

    # >>>> Declare a property
    some_value = IntProperty(default=0)

    @classmethod
    def poll(cls, context):
        return context.active_object is not None

    def execute(self, context):
        print(self.some_value)
        return {'FINISHED'}

Then, in the panel you can assign the property value as you want:

class HelloWorldPanel(bpy.types.Panel):
    """Creates a Panel in the Object properties window"""
    bl_label = "Hello World Panel"
    bl_idname = "OBJECT_PT_hello"
    bl_space_type = 'PROPERTIES'
    bl_region_type = 'WINDOW'
    bl_context = "object"

    def draw(self, context):
        layout = self.layout

        row = layout.row()
        op = row.operator("object.simple_operator")
        # >>>> Assign its value
        op.some_value = 1
        op = row.operator("object.simple_operator")
        # >>>> Assign its value
        op.some_value = 2

Alternatively, you can assign the value in a subclass if your want to work with subclasses.

$\endgroup$
1
  • 1
    $\begingroup$ That's perfect, thank you! And what a resounding forehead slap! I knew I was making it more complicated than it needed to be. Much appreciated! $\endgroup$ – Quentin Walker Dec 7 '20 at 15:42

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.