I am generating a mesh from a collection of points read from a json file. That collection of points will define the vertices, and from them I will derive the faces of the final mesh
Code is working fine until I try to scale down just one of the faces. I have used the accepted answer of this question as a reference: Using python and bmesh to scale/resize a face in place
The problem is I don't know what is the criteria used in that answer to select the face to be scaled down, since the line face = bm.select_history.active looks very generic. Instead what I tried is to access the first face in the sequence of faces in the mesh with face = bm.faces[0], but then I get the following error:
Traceback (most recent call last):
File "\Text", line 88, in <module>
IndexError: BMElemSeq[index]: outdated internal index table, run ensure_lookup_table() first
Error: Python script failed, check the message in the system console
This is the script I wrote:
import bpy
import json
import bmesh
import os
make collection
new_collection = bpy.data.collections.new('new_collection')
Link object with collection
bpy.context.scene.collection.children.link(new_collection)
Reading from a file a collection of points
with open(r'path\vertices.json','r') as f:
j=json.load(f)
vertices = j["vertices"]
faces = ... # here generating the faces from the vertices
edges = []
Creating Mesh
new_mesh = bpy.data.meshes.new(str(country_name)+'_mesh')
new_mesh.from_pydata(vertices, edges, faces)
Recalculating Normals for each face
bm = bmesh.new()
bm.from_mesh(new_mesh)
bmesh.ops.recalc_face_normals(bm, faces=bm.faces)
bm.to_mesh(new_mesh)
bm.free()
Applying changes to the Mesh
new_mesh.update()
Making object from mesh
new_object = bpy.data.objects.new(str(country_name)+'_object', new_mesh)
add object to scene collection
new_collection.objects.link(new_object)
Scaling one face
bm = bmesh.new()
bm.from_mesh(new_mesh)
scale_factor = 0.5
face = bm.faces[0]
if isinstance(face, bmesh.types.BMFace):
c = face.calc_center_median()
for v in face.verts:
v.co = c + scale_factor * (v.co - c)
bm.to_mesh(new_mesh)
bm.free()
Applying changes to the Mesh
new_mesh.update()
I also tried to select and resize the first face in the mesh like this:
bpy.ops.mesh.select_nth(nth=0)
bpy.ops.transform.resize(value=(0.5, 0.5, 1))
But this approach triggers:
Traceback (most recent call last):
File "\Text", line 91, in <module>
File "C:\Program Files\Blender Foundation\Blender 2.93\2.93\scripts\modules\bpy\ops.py", line 132, in __call__
ret = _op_call(self.idname_py(), None, kw)
RuntimeError: Operator bpy.ops.mesh.select_nth.poll() failed, context is incorrect
How can I select a single face as active to then scale it down?