Yes, you can change a mesh at runtime.
- get the current mesh from your object using
Mesh mesh = GetComponent<MeshFilter>().mesh
. Alternatively, if you want to replace the mesh with a completely new one, create one withMesh mesh = new Mesh();
and assign it to your object withGetComponent<MeshFilter>().mesh = mesh;
- When you intend to modify the same mesh every frame, you should call the
MarkDynamic()
method on it. This might improve performance in that situation (thanks, Kroltan). - Modify the
Mesh
object. It is a reference-type, so any changes you make will be reflected by the object which owns the mesh. For a minimum functional mesh you need to set at least its.vertices
and.triangles
component, if you want it to be textured also theuv
component. If you are really just going to change the positions of vertices of an existing mesh, then the.vertices
property is likely the only one you need. But keep in mind that you have little control over the order in which your 3d modeling program saves the vertices of a 3d model, so a slight change to the model can mean that the indexes of all vertices change in a completely unpredictable way. - When you are finished, call
mesh.RecalculateNormals()
which is required by almost every shader to calculate brightness levels correctly. - Calling
mesh.RecalculateTangents()
is also required for some shaders, especially those which use bump mapping. This step depends on the normals, so it needs to be executed after you recalculated the normals. - You should also call
mesh.RecalculateBounds()
. This is required for reliably detecting if the mesh is off-screen (so it can be culled) and for collision detection if you are using it as a MeshCollider. This method actually gets called automatically when you set the .triangles, but not when you set the .vertices.
Will it be fast enough for mobile phones? That depends on countless factors, like what kind of mobile phone you are talking about, how often you are going to change the mesh, how effective your mesh changing algorithm is, what shaders you are using and much more. You need to test it for yourself. By the way, if your changes will usually be localized, it might help to break down your terrain into multiple sub-objects and only update the meshes of those which were affected.