1
0
mirror of https://github.com/DigvijaysinhGohil/Godot-Shader-Lib.git synced 2025-01-09 02:43:25 +08:00

Voronoi node revamped

This commit is contained in:
Digvijaysinh Gohil 2024-03-19 13:03:56 +05:30
parent f06a680212
commit 600079e3e5
3 changed files with 122 additions and 38 deletions

View File

@ -17,9 +17,17 @@ func _get_return_icon_type() -> VisualShaderNode.PortType:
return PORT_TYPE_SCALAR return PORT_TYPE_SCALAR
func _get_input_port_count() -> int: func _get_input_port_count() -> int:
var distance_index: int = get_option_index(0)
match distance_index:
2:
return 4
_:
return 3 return 3
func _get_input_port_name(port: int) -> String: func _get_input_port_name(port: int) -> String:
var distance_index: int = get_option_index(0)
match distance_index:
2:
match port: match port:
0: 0:
return "uv" return "uv"
@ -27,17 +35,38 @@ func _get_input_port_name(port: int) -> String:
return "cell density" return "cell density"
2: 2:
return "angle offset" return "angle offset"
return "" _:
return "chebyshev power"
_:
match port:
0:
return "uv"
1:
return "cell density"
_:
return "angle offset"
func _get_input_port_type(port: int) -> VisualShaderNode.PortType: func _get_input_port_type(port: int) -> VisualShaderNode.PortType:
match port: match port:
0: 0:
return PORT_TYPE_VECTOR_2D return PORT_TYPE_VECTOR_2D
1, 2: _:
return PORT_TYPE_SCALAR
return PORT_TYPE_SCALAR return PORT_TYPE_SCALAR
func _get_input_port_default_value(port: int) -> Variant: func _get_input_port_default_value(port: int) -> Variant:
var distance_index: int = get_option_index(0)
match distance_index:
2:
match port:
1:
return 5.0
2:
return 2.0
3:
return 2.0
_:
return null
_:
match port: match port:
1: 1:
return 5.0 return 5.0
@ -53,13 +82,24 @@ func _get_output_port_name(port: int) -> String:
match port: match port:
0: 0:
return "output" return "output"
1: _:
return "cells" return "cells"
return ""
func _get_output_port_type(port: int) -> VisualShaderNode.PortType: func _get_output_port_type(port: int) -> VisualShaderNode.PortType:
return PORT_TYPE_SCALAR return PORT_TYPE_SCALAR
func _get_property_count() -> int:
return 1
func _get_property_name(index: int) -> String:
return "Distance"
func _get_property_default_index(index: int) -> int:
return 0
func _get_property_options(index: int) -> PackedStringArray:
return ["Euclidean", "Manhattan", "Chebyshev"]
func _get_global_code(mode: Shader.Mode) -> String: func _get_global_code(mode: Shader.Mode) -> String:
var code: String = preload("Voronoi.gdshaderinc").code var code: String = preload("Voronoi.gdshaderinc").code
return code return code
@ -70,9 +110,17 @@ func _get_code(input_vars: Array[String], output_vars: Array[String], mode: Shad
if input_vars[0]: if input_vars[0]:
uv = input_vars[0] uv = input_vars[0]
var distance_index: int = get_option_index(0)
var cell_density: String = input_vars[1] var cell_density: String = input_vars[1]
var angle_offset: String = input_vars[2] var angle_offset: String = input_vars[2]
var chebyshev_power: String = "0."
if distance_index == 2:
if input_vars[3]:
chebyshev_power = input_vars[3]
var output: String = output_vars[0] var output: String = output_vars[0]
var cells: String = output_vars[1] var cells: String = output_vars[1]
return "voronoi_noise(%s,%s, %s, %s, %s);" % [uv, cell_density, angle_offset, output, cells] return "voronoi_noise(%s, %s, %s, %s, %s, %s, %s);" % [uv, cell_density, angle_offset, distance_index, chebyshev_power, output, cells]

View File

@ -1,24 +1,54 @@
void voronoi_noise(vec2 uv, float cell_density, float angle_offset, out float output, out float cells){ vec2 voronoi_random_vector(vec2 p) {
vec2 _g = floor(uv * cell_density); mat2 matrix = mat2(vec2(15.27, 47.63), vec2(99.41, 89.98));
vec2 _f = fract(uv * cell_density); return fract(sin(p * matrix) * 46839.32);
vec3 _res = vec3(8.0, 0.0, 0.0); }
mat2 _matrix = mat2(vec2(15.27, 47.63), vec2(99.41, 89.98));
for(int y=-1; y<=1; y++) float voronoi_euclidean_distance(vec2 point1, vec2 point2){
{ return distance(point1, point2);
for(int x=-1; x<=1; x++) }
{
vec2 lattice = vec2(float(x), float(y)); float voronoi_manhattan_distance(vec2 point1, vec2 point2) {
vec2 new_uv = lattice + _g; vec2 d = point1 - point2;
new_uv = fract(sin(new_uv * _matrix) * 46839.32); return abs(d.x) + abs(d.y);
vec2 offset = vec2(sin(new_uv.y * angle_offset) * 0.5 + 0.5, cos(new_uv.x * angle_offset) * 0.5 + 0.5); }
float d = distance(lattice + offset, _f);
if(d < _res.x) float voronoi_chebyshev_distance(vec2 point1, vec2 point2, float power) {
{ vec2 p = point1 - point2;
_res = vec3(d, offset.x, offset.y); return pow(pow(p.x, power) + pow(p.y, power), 1. / power);
output = _res.x; }
cells = _res.y;
void voronoi_noise(vec2 uv, float cell_density, float angle_offset, int distance_index, float chebyshev_power, out float output, out float cells){
vec2 grid_uv = fract(uv * cell_density);
vec2 grid_id = floor(uv * cell_density);
vec2 cell_id = vec2(0);
float min_dist = 100.;
for(float y = -1.; y <= 1.; y++) {
for(float x = -1.; x <= 1.; x++) {
vec2 offset = vec2(x, y);
vec2 n = voronoi_random_vector(grid_id + offset);
vec2 p = offset + sin(n + angle_offset) * .5 + .5;
float d = min_dist;
switch(distance_index){
case 1:
d = voronoi_manhattan_distance(grid_uv, p);
break;
case 2:
d = voronoi_chebyshev_distance(grid_uv, p, chebyshev_power);
break;
default:
d = voronoi_euclidean_distance(grid_uv, p);
break;
}
if(d < min_dist) {
min_dist = d;
cell_id = voronoi_random_vector(grid_id + offset);
} }
} }
} }
output = min_dist;
cells = cell_id.y;
} }

View File

@ -2,12 +2,18 @@
Generates a Voronoi or Worley noise based on input UV. Voronoi noise is generated by calculating distances between a pixel and a lattice of points. By offsetting these points by a pseudo-random number, controlled by <b><i>angle offset</i></b>, a cluster of cells can be generated. Generates a Voronoi or Worley noise based on input UV. Voronoi noise is generated by calculating distances between a pixel and a lattice of points. By offsetting these points by a pseudo-random number, controlled by <b><i>angle offset</i></b>, a cluster of cells can be generated.
<hr> <hr>
**Controls**
|Name|Options|Description|
|---|---|---|
|Distance|Euclidean, Manhattan, Chebyshev|Distance matrix used to calculate the noise|
**Inputs** **Inputs**
|Name|Type|Binding|Description| |Name|Type|Binding|Description|
|---|---|---|---| |---|---|---|---|
|uv|vec2|UV|Input UV value| |uv|vec2|UV|Input UV value|
|cell density|float|none|Density of generated cells| |cell density|float|none|Density of generated cells|
|angle offset|float|none|Offset values for points| |angle offset|float|none|Offset values for points|
|chebyshev power|float|none|Power values for Chebyshev distance matrix|
**Outputs** **Outputs**
|Name|Type|Binding|Description| |Name|Type|Binding|Description|