angle between 2 faces

can you help to write a script measuring angle between 2 selected faces? like this:


actually by math it’s just an angle beetwen 2 planes.

You are correct. You just need to get the face normals and use this:

If you are on 2.63+ then this is accessed though the Mesh object, which has a list called ‘polygons’, and each polygon has a ‘normal’ member which is the normal for the plane.

The main trick would be knowing which faces you wanted to compare. For your scene you could just select the 2 faces and then search for the selected faces to do the computation.

Warning, this code has not been tested and might contain logic or syntax errors:


# Get the active object
obj = bpy.context.active_object

# Access the mesh
mesh = obj.data
if type(mesh) != bpy.types.Mesh:
  # They had an Armature, Light, Camera, Empty selected, should do some error handeling.
  pass

# Get just the selected polygons
selectedPolys = [poly for poly in mesh.polygons if poly.select]

# Compute the angle between the first 2
computeAngle(selectedPolys[0], selectedPolys[1])

import bpy
import bmesh
from math import degrees


def main(self, context):
    me = context.edit_object.data
    bm = bmesh.from_edit_mesh(me)
    
    faces = [f for f in bm.faces if f.select]
    
    if len(faces) != 2:
        self.report({'ERROR'}, "Require two selected faces")
        return
    
    angle = faces[0].normal.angle(faces[1].normal)
    self.report({'INFO'}, "Angle: %s°" % round(degrees(angle), 2))


class SimpleOperator(bpy.types.Operator):
    """Tooltip"""
    bl_idname = "object.simple_operator"
    bl_label = "Simple Object Operator"


    @classmethod
    def poll(cls, context):
        return context.edit_object is not None


    def execute(self, context):
        main(self, context)
        return {'FINISHED'}




def register():
    bpy.utils.register_class(SimpleOperator)




def unregister():
    bpy.utils.unregister_class(SimpleOperator)




if __name__ == "__main__":
    register()

Run, select two faces, hit spacebar and search for Simple Object operator

thansk for great help, CoDEmanX you are a rock!

at first, i wrote

import bpy, bmesh, math

# Get the active object data
bm = bmesh.from_edit_mesh(bpy.context.active_object.data)

# get selected faces
sf = [face for face in bm.faces if face.select]

# compute
print(180 - math.degrees( sf[0].normal.angle( sf[1].normal) ))

but your code with operator is much better to use. thanks

You’re welcome :slight_smile:

I wonder if the new Ruler/Protractor tool supports something similar in a visual way…