11
$\begingroup$

I am trying to use loopcut in a python script in Blender 2.71. I have tried using the following code from "Loop cut and slide using python script in blender":

old_type = bpy.context.area.type
bpy.ops.object.mode_set(mode='EDIT')
bpy.context.area.type = 'VIEW_3D'

bpy.ops.mesh.loopcut_slide(MESH_OT_loopcut={"number_cuts":10,"smoothness":0,"falloff":'ROOT', "edge_index":1})
bpy.ops.mesh.loopcut_slide(MESH_OT_loopcut={"number_cuts":10,"smoothness":0,"falloff":'ROOT', "edge_index":0})
bpy.context.area.type = old_type 

I get the following error when the call to loopcut is made:

RuntimeError: Operator bpy.ops.mesh.loopcut_slide.poll() expected a view3d region & editmesh

I have also tried overriding the context using the following:

import bpy

win      = bpy.context.window
scr      = win.screen
areas3d  = [area for area in scr.areas if area.type == 'VIEW_3D']
region   = [region for region in areas3d[0].regions if region.type == 'WINDOW']

override = {'window':win,
            'screen':scr,
            'area'  :areas3d[0],
            'region':region,
            'scene' :bpy.context.scene,
            }

bpy.ops.object.mode_set(mode='EDIT')
bpy.ops.mesh.loopcut(override=override, number_cuts=1, smoothness=0, falloff='ROOT', edge_index=5)

But I get the same error.

I am able to call other mesh operators such as merge() and primitive_plane_add() successfully...

Any ideas as to what I'm doing wrong or not understanding?

Follow up

I tried tracing this by debugging the Blender source in VS. As far as I can tell, the context I'm passing in as an override gets passed to the C side of things as python specific context contained in a data pointer of some sort (I haven't investigated enough to fully understand what is going on). When the poll function gets called for the operator it gets the context indicating a TEXT space instead of a 3D view space so it fails. It appears that the override isn't happening. I'm not sure at this point if an override is intended to work in this case or if I'm just going about it the wrong way.

If I run my code as a addon instead of trying to run it from the TEXT window it works fine (no override needed). This doesn't address why I can't get overrides to work but at least I can work around it since I'm ultimately writing an addon anyway...

$\endgroup$
2

2 Answers 2

12
$\begingroup$

A custom context needs to be passed as positional argument, not keyword argument.

bpy.ops.mesh.loopcut(override, number_cuts=...,) # not override=override!

Macros follow the same pattern:

bpy.ops.mesh.loopcut_slide(override, MESH_OT_loopcut={"number_cuts": ...,})

What the Macro bpy.ops.mesh.loopcut_slide() specifically needs as context is a 3D View area (Area.type == 'VIEW_3D'), the window region of that 3D View (usually Area.regions[-1]) and the active object to be a mesh and in edit-mode.

$\endgroup$
10
$\begingroup$

The code where you try to override the context has a small bug at the region part as you're trying to pass list of regions instead of region object(the same as you did with the area):

override = {'window':win,
            'screen':scr,
            'area'  :areas3d[0],
            'region':region[0],
            'scene' :bpy.context.scene,
            }

This way it worked for me.

$\endgroup$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .