Smooth Shade is a simple command one can call via:

row.operator("object.shade_smooth", text="Smooth", icon="SMOOTHCURVE")

But how to you set a auto smooth to False or True?

bpy.context.object.data.use_auto_smooth = False

Can this be used like an operator as well?

row.operator("object.data.use_auto_smooth = False", text="AutoSmooth", icon="SMOOTHCURVE")

I highly assume this is wrong and that this must be maybe a flag to turn on or off.

  • $\begingroup$ Did a search on Blender API documentation . Can't find the line in question, bpy.context.object.data.use_auto_smooth if it's not found then most probably it's not exposed and you can't do anything with that. Can you post an image ... regarding which check box are you trying to turn on or off on the blender interface? $\endgroup$ – hawkenfox Jan 2 '16 at 2:20
  • $\begingroup$ According to the documentation, UILayout.operator needs an identifier as first argument. That excludes arbitrary Python statements. $\endgroup$ – HalfKiloByte Jan 2 '16 at 8:25

Specifically this line makes no sense to bpy:

row.operator("object.data.use_auto_smooth = False", text="AutoSmooth", icon="SMOOTHCURVE")

The first parameter in row.operator() needs to be a known operator path. That parameter isn't used for setting anything, but merely to identify which operator you want to call.

If you rightlick the AutoSmooth button in Normals panel, and select Edit Source and open the TextEditor's textblock properties_data_mesh.py, it opens directly at the line used by Blender's UI system to show you how it does the layout.

it shows:

mesh = context.mesh
col.prop(mesh, "use_auto_smooth")

mesh is available in this context because it's the Mesh Properties panel. If you have a menu elsewhere you'll have to get at it using obj.data.

This assumes there's an (active) object, use a poll in your menu to ensure this.

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

    obj = context.object
    mesh = obj.data

    split = layout.split()

    col = split.column()
    col.prop(mesh, "use_auto_smooth")
    sub = col.column()
    sub.active = mesh.use_auto_smooth and not mesh.has_custom_normals
    sub.prop(mesh, "auto_smooth_angle", text="Angle")
| improve this answer | |

Doing a search on the Blender API page this is what it says:

use_auto_smooth Auto smooth (based on smooth/sharp faces/edges and angle between faces), or use custom split normals data if available

Type: boolean, default False

Click Here to link to reference

enter image description here

| improve this answer | |
  • $\begingroup$ row.operator("Mesh.use_auto_smooth", text="AutoSmooth") --- seems not wot work either $\endgroup$ – Claas Kuhnen Jan 2 '16 at 4:47
  • $\begingroup$ Mesh is a class, you need an instance of that class. object.data would be an example for getting a Mesh instance from an object you have. The last line of that tooltip shows the incantation to get to that checkbox from Python scripts. That line can be tried in the Python console. You can set that to True or False, and that will set or clear the checkbox (maybe you will need to force a redraw of that area to see the effect). $\endgroup$ – HalfKiloByte Jan 2 '16 at 8:11

I'm assuming this is a line from a draw() function.

row.operator("object.shade_smooth", text="Smooth", icon="SMOOTHCURVE")

The first argument is an identifier for an operator. It is not a Python statement, it won't get executed. The whole string is used to select an operator from Blender's internal list.

bpy.context.object.data.use_auto_smooth = False

This will clear the Auto Smooth checkbox on the active object's mesh. But you can't use this in a draw() function. Redrawing must not modify any data structures.

row.operator("object.data.use_auto_smooth = False", text="AutoSmooth", icon="SMOOTHCURVE")

This won't work, as there is no operator with that identifier. If you have the main Blender console enabled (not the internal Python console), you can see a "search for unknown operator" error shown in there.

If there is no operator for setting Auto Smooth, row.operator() definitely won't do it.

So how about making an operator for it?

# based on operator_simple.py template
import bpy

class SetAutoSmoothOperator(bpy.types.Operator):
    bl_idname = "object.set_auto_smooth"
    bl_label = "Set Auto Smooth"

    def poll(cls, context):
        object = context.active_object
        return object is not None and hasattr(object.data, "use_auto_smooth")

    def execute(self, context):
        context.active_object.data.use_auto_smooth = True
        return {'FINISHED'}

def register():

def unregister():

if __name__ == "__main__":

This can be used with row.operator("object.set_auto_smooth"), or some other name specified by bl_idname on the class.

| improve this answer | |

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.