本日は Blender の技術調査枠です。
Blender3.0で利用可能なpythonスクリプトを作ります。
poll() failed, context is incorrect エラー
Blender の python スクリプトから特定のオペレータを呼び出そうとしたとき、以下のエラーが発生することがあります。
RuntimeError: Operator bpy.ops.XXX.YYY.poll() failed, context is incorrect
これは指定のオペレータを実行する際、適切なコンテキストの参照が設定されていないことが原因である可能性があります。
指定種別のエリアコンテキストの参照を取得する
Blender のオペレータには特定のウィンドウエリアでのみ利用可能なオペレータが存在します。
例えば、bpy.ops.action.select_all はドープシートのエリアで利用可能です。
通常 GUI 操作の場合はこれらのオペレータは各エリア内のメニューから実行するため意識する必要はありません。
しかし python スクリプトから実行する場合はどのエリアでオペレータ操作を行うかコンテキストを渡して指定する必要があります。
各エリアの参照と種別は bpy.context.screen.areas から取得可能です。
docs.blender.org
以下の例のように各エリアのコンテキストの参照(context)を走査して指定の種別の参照を取得することができます。
# bpy.ops.action のオペレータはドープシートエリアで実行可能 # 全エリアを確認してドープシートの参照を取得する override_context = None for area in bpy.context.screen.areas: # エリアの種別マニュアル # https://docs.blender.org/api/current/bpy.types.Area.html#bpy.types.Area.type if area.type == 'DOPESHEET_EDITOR': # context の参照を作成する override_context = bpy.context.copy() override_context["space_data"] = area.spaces[0] override_context["area"] = area if override_context == None: return False # ドープシートエリア内のアクションのキーフレームをすべて選択する bpy.ops.action.select_all(override_context, action='SELECT')
エリア種別の定義については以下を参照ください。
docs.blender.org
EMPTY | Empty | |
VIEW_3D | 3D Viewport | Manipulate objects in a 3D environment. |
IMAGE_EDITOR | UV/Image Editor | View and edit images and UV Maps. |
NODE_EDITOR | Node Editor | Editor for node-based shading and compositing tools. |
SEQUENCE_EDITOR | Video Sequencer | Video editing tools. |
CLIP_EDITOR | Movie Clip Editor | Motion tracking tools. |
DOPESHEET_EDITOR | Dope Sheet | Adjust timing of keyframes. |
GRAPH_EDITOR | Graph Editor | Edit drivers and keyframe interpolation. |
NLA_EDITOR | Nonlinear Animation | Combine and layer Actions. |
TEXT_EDITOR | Text Editor | Edit scripts and in-file documentation. |
CONSOLE | Python Console | Interactive programmatic console for advanced editing and script development. |
INFO | Info | Log of operations, warnings and error messages. |
TOPBAR | Top Bar | Global bar at the top of the screen for global per-window settings. |
STATUSBAR | Status Bar | Global bar at the bottom of the screen for general status information. |
OUTLINER | Outliner | Overview of scene graph and all available data-blocks. |
PROPERTIES | Properties | Edit properties of active object and related data-blocks. |
FILE_BROWSER | File Browser | Browse for files and assets. |
SPREADSHEET | Spreadsheet | Explore geometry data in a table. |
PREFERENCES | Preferences | Edit persistent configuration settings. |
サンプルスクリプト
スクリプトを実行すると画面内のドープシートのコンテキスト参照を取得してアクションのキーフレームの全選択オペレータを実行します。
・Script_override_context_example.py
# bpyインポート import bpy # ドープシートエリア内のアクションのキーフレームをすべて選択する def select_all_key() -> bool: """ドープシートエリア内のアクションのキーフレームをすべて選択する Keyword Arguments: Returns: bool -- 実行成否 """ # bpy.ops.action のオペレータはドープシートエリアで実行可能 # 全エリアを確認してドープシートの参照を取得する override_context = None for area in bpy.context.screen.areas: # エリアの種別マニュアル # https://docs.blender.org/api/current/bpy.types.Area.html#bpy.types.Area.type if area.type == 'DOPESHEET_EDITOR': # context の参照を作成する override_context = bpy.context.copy() override_context["space_data"] = area.spaces[0] override_context["area"] = area if override_context == None: return False # ドープシートエリア内のアクションのキーフレームをすべて選択する bpy.ops.action.select_all(override_context, action='SELECT') return True # 関数の実行例 select_all_key()