Hello guys.
As I’m not much of a mathematician, I have a few questions about the following lines of code from YouTube for which I’d be very grateful if someone could help me.
I know what normalized means (values from -1 to 1 if I’m not mistaken) but how the cube face “knows” that only egdes must be bent (and not e.g. upper center on the line)?
At a glance, it looks like their “axisA” and “axisB” variables are being used in a less-than-foolproof attempt to produce a non-parallel vector pair to act as a Tangent and Bitangent, versus the Normal of the given “terrain face” (“localUp”, in this case). If all three axes were the same for any reason, the vector would be parallel and a viable cross product wouldn’t be possible, resulting in a zero-vector.
For reference, a normalized vector has a length of 1, regardless of the direction that vector faces. The basic formula, in terms of spatial coordinates, would look something like:
x2 + y2 + z2 = 1
The simplest example(s) of this would be a vector facing straight along any axis, such as (1, 0, 0) or (0, -1, 0). A 45° angle along a pair of axes might be roughly (0.707, 0, -0.707)(sqrt(2) = ~1.414, then divide that by 2)
As a point of reference, many shapes can be "spherized" by normalizing the positions of their vertices. A tessellated cube is a common example of this, since the resulting distribution of vertices will generally be consistent and symmetrical along all three (local) axes.
I know what normalized means (values from -1 to 1 if I’m not mistaken) but how the cube face “knows” that only egdes must be bent (and not e.g. upper center on the line)?
I think your main problem is here. Normalized does not mean values from -1 to 1. A normalized vector has a fix length of 1. It’s true that the individual components are in the range -1 to 1 after normalization, but the important part is the total length of 1. What actually happens is that the initial cube already covers the whole surface area. All you do is take each vertex of the cube relative to the center point and normalize this vector. So the point on the cube gets projected onto the unit sphere. After that you can multiply by your desired radius.
In addition you could apply a hight map displacement which you simply add to the radius when you multiply the unit vector. I’ve made an example long time ago (around 2012) where I even created a Unity WebPlayer build that demonstrated this. However the WebPlayer plugin is no longer supported. I just searched through my local files and found my ancient project. The migration didn’t went that well since it was a really old project. Though I fixed all issues and created a WebGL build of my old example. You can find it here.
Note that there are 3 sliders. The first one is actually a lerp between the initial cube and “spherified” cube. So you can gradually see the change as you move the slider from left(cube) to right(sphere)
The second slider is the target sphere radius. So changing this slider changes the size of the resulting sphere.
The third slider is a multiplication factor for the height map. So if you drag it all the way to the left, no heightmap would be added and you get a perfect sphere.
At the bottom right there’s a “Tex” button that lets you cycle through 4 materials. The first one is just plain white, the second one is the heightmap texture applied as albedo, so it would match the hills and valleys of the heightmap. The other 2 are just debug textures.
You can use the right mouse button to orbit the camera and use the mouse wheel to move the camera closer / further away… The JoinEdges button / toggle lets you disable the simple edge joining code. Because I apply the exact same heightmap to all 6 sides, we get the same displacement on each face. However the edges of two adjacent sides usually do not match, so as a result you would get gaps between the two sides. JoinEdges just makes sure the corresponding vertices along the edge of two faces have the same height. It simply calculates the average of the two. This is by no means a great solution. You usually need to apply a better gradient to slowly merge the two edges. Of course corners get even more trickier since you have 3 edges meeting. JoinEdges at least makes sure the mesh is closed.
The 6 sides are actually seperate meshes and seperate mesh renderers. All 6 gameobjects are located at the center of the sphere / cube and the vertices of each plane are simply offset. The plane mesh is generated procedurally.