I'm looking for a way to be sure a script affect only f-curves that are showing up to the user in the graph editor (post filtering) for WYSIWYG style control.

In details: Currently I'm getting the actions from the objects directly after checking the properties of the graph editor (check if "show_only_selected" is on for exemple) in the graph editor, then try to get related actions from selected objects.

Problem is : With the filter show_only_selected toggled On in graph editor, In the case of armature selected, if some of it's bones are unselected there are hided in editor but still affected by the script (I get all the fcurves of the actions). Other animated properties might be affected while being invisible to the user or on the contrary being not affected while being visible.

A way to directly iterate on filtered f-curves would be really nice (if not necessary) to apply some script on what the user see/isolate.

Even more details in this blender artist thread :

  • 1
    $\begingroup$ Please expand your question here too, rather than having link to BA. Wont take long with cut n paste. $\endgroup$
    – batFINGER
    Oct 10 '17 at 10:06
  • $\begingroup$ Done. Now does the legendary batFINGER has any solution for this ? ;) $\endgroup$
    – Pullup
    Oct 10 '17 at 13:32


New to blender 2.79.1 is context.selected_editable_fcurves Test script. Prepends a toggle button to graph editor header. Runs update code on each toggle that will print the visible fcurves to console.

Edited to include all "visible" fcurves in the graph editor.

import bpy
from bpy.props import BoolProperty

def foo(self, context):
    selected = context.selected_editable_fcurves[:]
    others = context.selected_editable_fcurves[:]
    others = set(others)
    print("-" * 72)
    print("%d selected of %d visible" % (len(selected), len(others)))
    for fc in others:
        fc.select = fc in selected
        print("action:", fc.id_data.name, 
              "data_path:", fc.data_path, 
              "{%d}" % fc.array_index,

    return None

bpy.types.Scene.testfc = BoolProperty(update=foo)

def testfc(self, context):
    scene = context.scene
    self.layout.prop(scene, "testfc", toggle=True)


Even before this context attribute became available, the same thing could be done by deselecting all fcurves (using a.fcurves.foreach_set("select", [False] * len(a.fcurves))) in all actions, then selecting all with bpy.ops.graph.select_all_toggle, those selected will be the visible ones, and reinstating to original selection.

  • $\begingroup$ This is not exactly what I was looking for (since I want to get all the visible Fcurve, not selected only) But it's really interesting and might be super usefull ! When I use your script I get the Error : AttributeError: 'Context' object has no attribute 'selected_editable_fcurves'. in what context you suppose to get this ? I tried to find it manually in interactive console (with lines like bpy.context.window_manager.windows[0].screen.areas[8].spaces ...) but I could not found anything. $\endgroup$
    – Pullup
    Oct 13 '17 at 14:46
  • $\begingroup$ Need to have version 2.79.1, but could use same method in prior versions, see edit on bottom of q. $\endgroup$
    – batFINGER
    Oct 14 '17 at 13:44
  • $\begingroup$ The legendary BATfinger struck again ! I appreciate that you described a way to do this in older Blender version because I'm currently stuck in a 2.77 environment (yeah, I know...). Thank you. $\endgroup$
    – Pullup
    Oct 16 '17 at 9:09
  • $\begingroup$ It looks like bpy.ops.graph.select_all_toggle(invert=True) has been replaced with bpy.ops.graph.select_all(action='INVERT') in 2.80! Also, if using filters in the graph editor results in NO visible fcurves, calling the select_all operator throws an incorrect context error! Any ideas on how to get around that? Thanks :) $\endgroup$
    – andyV
    Dec 15 '18 at 3:56
  • 1
    $\begingroup$ Cool, pays to check. Could be a bug.(shrug) (and if so) may be easier in short term to use try except for that case. $\endgroup$
    – batFINGER
    Dec 15 '18 at 9:38

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.