I would like to change all the normals of selected vertices in my scene to be (0,0,1). I am attempting to do this on a single mesh as a test scenario using the following code:
import bpy
mesh = bpy.context.object.data
selected_verts = [v for v in mesh.vertices if v.select]
for v in selected_verts:
print(f"Before Vertex Normal: {v.normal}")
v.normal = [0,0,1]
print(f"After Vertex Normal: {v.normal}")
When doing this, the value appears to change but the normal in the scene remains unchanged. Using Blender 2.83LTS
EDIT - subbed out the averaging routine for a Vector(0,0,1) - this works for my needs since all my Vectors are either UP or DOWN -
#Evaluate face Normals - if negative - flip
for obj in selected:
bpy.ops.object.select_all(action='DESELECT')
obj.select_set(True)
bpy.context.view_layer.objects.active = obj
bpy.ops.object.editmode_toggle()
bm = bmesh.from_edit_mesh( bpy.context.object.data )
# Reference selected face indices
bm.faces.ensure_lookup_table()
selFaces = [ f.index for f in bm.faces if f.select ]
# Positive vector
up = Vector([0,0,1])
# Calculate the dot products between the Up vector and each face normal
dots = [ up.dot( bm.faces[i].normal ) for i in selFaces ]
# Reversed faces have a negative dot product value
reversedFaces = [ i for i, dot in zip( selFaces, dots ) if dot < 0 ]
# Deselect all faces and (later) only select flipped faces as indication of change
for f in bm.faces: f.select = False
bm.select_flush( False )
for i in reversedFaces:
bm.faces[i].select = True
bm.faces[i].normal_flip() # Flip normal
bm.select_flush( True )
bpy.ops.object.editmode_toggle()
bpy.ops.object.select_all(action='DESELECT')
object.data
variable are only refreshed after the object mode is changed. I would suggest as a 1st check verifying that toggling out of edit mode does not update your scene. $\endgroup$