Circular Plane
This shader makes a circular plane, from a plane mesh.
Instructions:
1) make a PlaneMesh
2) set the size of the PlaneMesh to 1×1
3) subdivide it
4) the orientation of the mesh must be “Face Y”
5) just add the material shader.
PD: My intention was to create something like a terrain, so the shader have a noise texture and two colors to paint it, and add some Y vertex distortion at the same time.
Shader code
shader_type spatial;
uniform float radius : hint_range(0.1, 15.0); //radio máximo del círculo
uniform float power : hint_range(-1.0, 1.0) = -0.999; //controla el espaciado entre anillos
uniform int num_rings : hint_range(1, 5) = 5; //número de anillos concéntricos (Dejar en 5)
uniform float circularity : hint_range(0.0, 1.0) = 1.0; //controla la transición hacia la circularidad
varying vec2 real_uv; //para texturizar como si fuese un decal
varying vec2 circular_pos;
varying float circularity_factor;
uniform sampler2D random: filter_nearest,repeat_enable;
uniform vec3 colorTop : source_color = vec3(0.0);
uniform vec3 colorBot : source_color = vec3(0.0);
uniform float deep : hint_range(-1.0, 10.0, 0.01) = 0.45; //blend entre los colores
void vertex() {
// Coordenadas UV normalizadas, centradas en (0,0)
vec2 uv = (VERTEX.xz + vec2(0.5)) * 2.0 - vec2(1.0);
//calculamos la distancia cuadrada para hacer un ajuste suave hacia los bordes
float grid_distance = max(abs(uv.x), abs(uv.y));
//enumeramos los anillos en función de la cuadrícula
float ring_index = floor(grid_distance * float(num_rings));
float quantized_distance = ring_index / float(num_rings);
//ajustamos con el parámetro `power` para el espaciado entre anillos
quantized_distance = mix(quantized_distance, pow(quantized_distance, 1.0 + power), 0.5);
float scaled_distance = quantized_distance * radius;
//convertimos a coordenadas polares (?) para la posición circular
float angle = atan(uv.y, uv.x);
circular_pos = vec2(scaled_distance * cos(angle), scaled_distance * sin(angle));
//mezclamos la posición original con la posición circular en función de la distancia al centro
circularity_factor = smoothstep(0.0, 1.0, grid_distance * circularity);
VERTEX.x = mix(VERTEX.x, circular_pos.x, circularity_factor);
VERTEX.z = mix(VERTEX.z, circular_pos.y, circularity_factor);
real_uv = vec2(VERTEX.x, VERTEX.z); //podemos usar esto como UV para la textura.
VERTEX.y += texture(random, UV).y * 0.1; //le ponemos un poquito de altura a la cosa.
}
void fragment() {
float depth = texture(random, real_uv).r * deep;
ALBEDO = mix(colorTop, colorBot, depth);
}