The question is answered, right answer was accepted
infinite vector 3 generate method for Sierpinski Tetrahedron C#,infinite vector 3 generate method for a Sierpinski tetrahedron?
sierpinski tetrahedron in unity
Level of coding will only help with implementation. You might want to get the problem worked out on paper first, then start worrying about how to type it.
Answer by Bunny83 · Mar 07, 2018 at 01:43 PM
It's a recursive algorithm which of course can be carried out linearly as well. The only thing you have to create is creating 4 tetrahedron out of the bigger one. That's all you need. So you start with a single tetrahedron and apply your "conversion" to every tetrahedron (at the first step there's only 1).
To do this it's actually easier to represent your tetrahedron "logically". For example using the center point and a "size" variable. You would calculate 4 new center positions based on the given center and the size. Just cut the size in half. If you do the same for the new 4 center positions you get again 4 new ones for each old one. So you end up with 16 center points.
You should seperate the "meshing" from the actual subdivision. Just run the algorithm as often as you want and when you reached your desired level run the mesher on the tetrahedron centers + size.
I quickly created a class that can build such a construct:
public class STetrahedron
{
static float s8_9 = Mathf.Sqrt(8f/9f);
static float s2_9 = Mathf.Sqrt(2f / 9f);
static float s2_3 = Mathf.Sqrt(2f / 3f);
static float f1_3 = 1f / 3f;
public float Size = 1;
public List<Vector3> centers = new List<Vector3>();
public STetrahedron Subdivide()
{
var result = new STetrahedron();
float s = result.Size = Size*0.5f;
if (centers.Count == 0)
centers.Add(Vector3.zero);
foreach(var c in centers)
{
result.centers.Add(c + new Vector3(0, s, 0));
result.centers.Add(c + new Vector3(-s2_3*s, -f1_3 * s, -s2_9*s));
result.centers.Add(c + new Vector3( s2_3*s, -f1_3 * s, -s2_9*s));
result.centers.Add(c + new Vector3(0, -f1_3 * s, s8_9*s));
}
return result;
}
public STetrahedron Subdivide(int aCount)
{
var res = this;
for (int i = 0; i < aCount; i++)
res = res.Subdivide();
return res;
}
public Mesh CreateMesh()
{
Vector3[] vertices = new Vector3[centers.Count*12];
Vector3[] normals = new Vector3[vertices.Length];
float s = Size;
int i = 0;
foreach (var c in centers)
{
var v0 = c + new Vector3(0, s, 0);
var v1 = c + new Vector3(-s2_3 * s, -f1_3 * s, -s2_9 * s);
var v2 = c + new Vector3(s2_3 * s, -f1_3 * s, -s2_9 * s);
var v3 = c + new Vector3(0, -f1_3 * s, s8_9 * s);
normals[i] = normals[i + 1] = normals[i + 2] = Vector3.Cross(v2 - v0, v1 - v0).normalized;
vertices[i++] = v0; vertices[i++] = v2; vertices[i++] = v1;
normals[i] = normals[i + 1] = normals[i + 2] = Vector3.Cross(v1 - v0, v3 - v0).normalized;
vertices[i++] = v0; vertices[i++] = v1; vertices[i++] = v3;
normals[i] = normals[i + 1] = normals[i + 2] = Vector3.Cross(v3 - v0, v2 - v0).normalized;
vertices[i++] = v0; vertices[i++] = v3; vertices[i++] = v2;
normals[i] = normals[i + 1] = normals[i + 2] = Vector3.down;
vertices[i++] = v1; vertices[i++] = v2; vertices[i++] = v3;
}
int[] triangles = new int[vertices.Length];
for (int n = 0; n < triangles.Length; n++)
triangles[n] = n;
var m = new Mesh();
m.vertices = vertices;
m.normals = normals;
m.triangles = triangles;
m.RecalculateBounds();
return m;
}
}
You just create an instance of that class and call subdivide which will return a subdivided version of the given structure. When done call CreateMesh to get a mesh from it. Note that at subdivision level 6 the resulting mesh would already have nearly 50k vertices. The result going from 0 to lvl 6 looks like this:
Follow this Question
Related Questions
Moving GameObject a specific distance in the Z direction and back again - regardless of rotation 1 Answer
Need help getting randomly moving particles to head to the nearest of 4 coordinates. 1 Answer
InverseTransformPoint() help 0 Answers
Set variable to position of collided object. 0 Answers
Vector 3 moving to certain place? 2 Answers