[Bf-committers] Getting the associated Blender object name from a uiBut object

Matthew Keller matthew.ed.keller at gmail.com
Sun Aug 6 23:15:20 CEST 2017


Hi Jeff,

Not sure if you've seen this, but there is a way to perform the 'Restrict
View' action in the ui recursively by pressing Ctrl while clicking. This is
the function that enables that behavior as far as I can tell:
https://developer.blender.org/diffusion/B/browse/master/source/blender/editors/space_outliner/outliner_draw.c;f5f6f9c9ac3ec37ef98eae54464a801c2b7ddcc9$175

They seem to be using the currently selected object and then iterating
through all the objects and checking every time if the object is a child of
the currently selected object.

Could you follow that approach by setting the keyframe on the underlying
object as opposed to setting the keyframe on the button? (there's even
logic in there to actually set the keyframe, although I'm not quite sure
under what circumstances that functionality is triggered)

HTH,

Matt

On Sun, Aug 6, 2017 at 4:04 PM The Simple Carnival <jeff at simplecarnival.com>
wrote:

> Hello --
>
> I recently discovered that it's possible to automate the render or view
> capability of an object via the Outliner:
>
> https://blenderartists.org/forum/showthread.php?237747-How-can-i-hide-object-during-animation
>
>
> This is a fantastic feature, but I need a way to select multiple objects
> and automate their render or view capability simultaneously,
> particularly in a parent/child scenario. For example, let's say I have a
> parent object with 100 child objects. If I want all of those objects to
> not be rendered, it's very tedious to right click on the render icon of
> each of those objects in the Outliner and and choose "Insert Keyframe"
> from the popup menu.
>
> In my custom Blender fork, I've added a right-click menu option for the
> Outliner called "Insert Recursive Keyframes" and have implemented the
> following code. Right now, I'm able to set the keyframe for the initial
> object that I right-clicked on. I can also iterate through all of the
> other buttons in the outliner and set a keyframe for the same type (i.e.
> if you right-click on a render icon to set a keyframe, this code will
> set render icon keyframes for *all* of the objects in the scene).
>
> Now for my question. I cannot figure out how to determine what a uiBut
> object *is* in relation to the actual Blender object in the scene. In
> other words, I can see all of the properties of the uiBut objects that
> I'm iterating through...except for the actual Blender object name that
> is somehow tied to it. Since I can't figure out the Blender object name,
> I can't determine if the uiBut object that I'm looking at is a child of
> the uiBut object where I just inserted a keyframe.Or maybe I'm going
> about this all wrong and there's some other way to determine if one
> uiBut object is the child of another uiBut object. I've been looking at
> this for hours and I haven't been able to figure out how to do it.
>
> Any help would be greatly appreciated!
>
> Jeff Boller
> http://www.sundriftproductions.com
>
>
> static int insert_recursive_key_button_exec(bContext *C, wmOperator *op)
> {
>      Scene *scene = CTX_data_scene(C);
>      PointerRNA ptr = { { NULL } };
>      PropertyRNA *prop = NULL;
>      uiBut *but;
>      short success = 0;
>      int index;
>      const bool all = RNA_boolean_get(op->ptr, "all");
>      short flag = 0;
>
>      flag = ANIM_get_keyframing_flags(scene, 1);
>      but = UI_context_active_but_get(C);
>      UI_context_active_but_prop_get(C, &ptr, &prop, &index);
>
>      // Set the keyframe that we actually clicked on.
>      success = set_custom_keyframe(C, op, ptr, prop, but, all, index,
> flag);
>      if (!success) return OPERATOR_CANCELLED;
>
>      // Now look around for child objects where we need to set
> additional keyframes.
>      uiBut *but_found = NULL;
>      ARegion *ar = CTX_wm_region(C);
>      if (ar) {
>          uiBlock *block;
>          uiBut *but2, *otherbut = NULL;
>          for (block = ar->uiblocks.first; block; block = block->next) {
>              for (but2 = block->buttons.first; but2; but2 = but2->next) {
>                  if (!but2->active) {
>                      // OK, so we know this isn't the main button we
> just picked.
>                      // Can we pull some properties out of this and
> determine exactly what it is?
>                      otherbut = but2;
>                      if (otherbut && otherbut->rnapoin.data) {
>                          PointerRNA otherptr = otherbut->rnapoin;
>                          PropertyRNA *otherprop = otherbut->rnaprop;
>                          int otherindex = otherbut->rnaindex;
>
>                          // Make sure we're dealing with the same sort
> of keyframe (hide, hide_select, hide_render)
>                          if (!memcmp(otherprop->identifier,
> prop->identifier, 11)) {
>
>                              // HOW CAN WE CHECK THAT THIS IS A CHILD OF
> THE ORIGINAL THING WE CLICKED ON???????????????
>
>                              // Assuming that this is a child of the
> original thing we clicked on, set this keyframe too.
>                              success = set_custom_keyframe(C, op,
> otherptr, otherprop, otherbut, all, otherindex, flag);
>                              if (!success) return OPERATOR_CANCELLED;
>                          }
>                      }
>                  }
>              }
>          }
>      }
>
>      if (success) {
>          /* send updates */
>          UI_context_update_anim_flag(C);
>
>          /* send notifiers that keyframes have been changed */
>          WM_event_add_notifier(C, NC_ANIMATION | ND_KEYFRAME | NA_ADDED,
> NULL);
>      }
>
>      return (success) ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
> }
>
>
>
> _______________________________________________
> Bf-committers mailing list
> Bf-committers at blender.org
> https://lists.blender.org/mailman/listinfo/bf-committers
>


More information about the Bf-committers mailing list