Merge pull request #2139 from Naxela/master
Add map range node, vector rotate node, missing math operations and blackbody node
This commit is contained in:
commit
8118733474
|
@ -331,6 +331,7 @@ def parse_vector(node: bpy.types.Node, socket: bpy.types.NodeSocket) -> str:
|
|||
'COMBXYZ': nodes_converter.parse_combxyz,
|
||||
'VECT_MATH': nodes_converter.parse_vectormath,
|
||||
'DISPLACEMENT': nodes_vector.parse_displacement,
|
||||
'VECTOR_ROTATE': nodes_vector.parse_vectorrotate,
|
||||
}
|
||||
|
||||
if node.type in node_parser_funcs:
|
||||
|
@ -433,6 +434,7 @@ def parse_value(node, socket):
|
|||
'SEPRGB': nodes_converter.parse_seprgb,
|
||||
'SEPXYZ': nodes_converter.parse_sepxyz,
|
||||
'VECT_MATH': nodes_converter.parse_vectormath,
|
||||
'MAP_RANGE': nodes_converter.parse_maprange,
|
||||
}
|
||||
|
||||
if node.type in node_parser_funcs:
|
||||
|
|
|
@ -332,3 +332,186 @@ vec3 wrap(const vec3 value, const vec3 max, const vec3 min) {
|
|||
\t wrap(value.z, max.z, min.z));
|
||||
}
|
||||
"""
|
||||
|
||||
str_blackbody = """
|
||||
vec3 blackbody(const float temperature){
|
||||
|
||||
vec3 rgb = vec3(0.0, 0.0, 0.0);
|
||||
|
||||
vec3 r = vec3(0.0, 0.0, 0.0);
|
||||
vec3 g = vec3(0.0, 0.0, 0.0);
|
||||
vec3 b = vec3(0.0, 0.0, 0.0);
|
||||
|
||||
float t_inv = float(1.0 / temperature);
|
||||
|
||||
if (temperature >= 12000.0) {
|
||||
|
||||
rgb = vec3(0.826270103, 0.994478524, 1.56626022);
|
||||
|
||||
} else if(temperature < 965.0) {
|
||||
|
||||
rgb = vec3(4.70366907, 0.0, 0.0);
|
||||
|
||||
} else {
|
||||
|
||||
if (temperature >= 6365.0) {
|
||||
vec3 r = vec3(3.78765709e+03, 9.36026367e-06, 3.98995841e-01);
|
||||
vec3 g = vec3(-5.00279505e+02, -4.59745390e-06, 1.09090465e+00);
|
||||
vec4 b = vec4(6.72595954e-13, -2.73059993e-08, 4.24068546e-04, -7.52204323e-01);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
} else if (temperature >= 3315.0) {
|
||||
vec3 r = vec3(4.60124770e+03, 2.89727618e-05, 1.48001316e-01);
|
||||
vec3 g = vec3(-1.18134453e+03, -2.18913373e-05, 1.30656109e+00);
|
||||
vec4 b = vec4(-2.22463426e-13, -1.55078698e-08, 3.81675160e-04, -7.30646033e-01);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
} else if (temperature >= 1902.0) {
|
||||
vec3 r = vec3(4.66849800e+03, 2.85655028e-05, 1.29075375e-01);
|
||||
vec3 g = vec3(-1.42546105e+03, -4.01730887e-05, 1.44002695e+00);
|
||||
vec4 b = vec4(-2.02524603e-11, 1.79435860e-07, -2.60561875e-04, -1.41761141e-02);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
} else if (temperature >= 1449.0) {
|
||||
vec3 r = vec3(4.10671449e+03, -8.61949938e-05, 6.41423749e-01);
|
||||
vec3 g = vec3(-1.22075471e+03, 2.56245413e-05, 1.20753416e+00);
|
||||
vec4 b = vec4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
} else if (temperature >= 1167.0) {
|
||||
vec3 r = vec3(3.37763626e+03, -4.34581697e-04, 1.64843306e+00);
|
||||
vec3 g = vec3(-1.00402363e+03, 1.29189794e-04, 9.08181524e-01);
|
||||
vec4 b = vec4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
} else {
|
||||
vec3 r = vec3(2.52432244e+03, -1.06185848e-03, 3.11067539e+00);
|
||||
vec3 g = vec3(-7.50343014e+02, 3.15679613e-04, 4.73464526e-01);
|
||||
vec4 b = vec4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
rgb = vec3(r.r * t_inv + r.g * temperature + r.b, g.r * t_inv + g.g * temperature + g.b, ((b.r * temperature + b.g) * temperature + b.b) * temperature + b.a );
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
return rgb;
|
||||
|
||||
}
|
||||
"""
|
||||
|
||||
# Adapted from https://github.com/blender/blender/blob/594f47ecd2d5367ca936cf6fc6ec8168c2b360d0/source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl
|
||||
str_map_range_linear = """
|
||||
float map_range_linear(const float value, const float fromMin, const float fromMax, const float toMin, const float toMax) {
|
||||
if (fromMax != fromMin) {
|
||||
return float(toMin + ((value - fromMin) / (fromMax - fromMin)) * (toMax - toMin));
|
||||
}
|
||||
else {
|
||||
return float(0.0);
|
||||
}
|
||||
}
|
||||
"""
|
||||
|
||||
str_map_range_stepped = """
|
||||
float map_range_stepped(const float value, const float fromMin, const float fromMax, const float toMin, const float toMax, const float steps) {
|
||||
if (fromMax != fromMin) {
|
||||
float factor = (value - fromMin) / (fromMax - fromMin);
|
||||
factor = (steps > 0.0) ? floor(factor * (steps + 1.0)) / steps : 0.0;
|
||||
return float(toMin + factor * (toMax - toMin));
|
||||
}
|
||||
else {
|
||||
return float(0.0);
|
||||
}
|
||||
}
|
||||
"""
|
||||
|
||||
str_map_range_smoothstep = """
|
||||
float map_range_smoothstep(const float value, const float fromMin, const float fromMax, const float toMin, const float toMax)
|
||||
{
|
||||
if (fromMax != fromMin) {
|
||||
float factor = (fromMin > fromMax) ? 1.0 - smoothstep(fromMax, fromMin, value) :
|
||||
smoothstep(fromMin, fromMax, value);
|
||||
return float(toMin + factor * (toMax - toMin));
|
||||
}
|
||||
else {
|
||||
return float(0.0);
|
||||
}
|
||||
}
|
||||
"""
|
||||
|
||||
str_map_range_smootherstep = """
|
||||
float safe_divide(float a, float b)
|
||||
{
|
||||
return (b != 0.0) ? a / b : 0.0;
|
||||
}
|
||||
|
||||
float smootherstep(float edge0, float edge1, float x)
|
||||
{
|
||||
x = clamp(safe_divide((x - edge0), (edge1 - edge0)), 0.0, 1.0);
|
||||
return x * x * x * (x * (x * 6.0 - 15.0) + 10.0);
|
||||
}
|
||||
|
||||
float map_range_smootherstep(const float value, const float fromMin, const float fromMax, const float toMin, const float toMax) {
|
||||
if (fromMax != fromMin) {
|
||||
float factor = (fromMin > fromMax) ? 1.0 - smootherstep(fromMax, fromMin, value) :
|
||||
smootherstep(fromMin, fromMax, value);
|
||||
return float(toMin + factor * (toMax - toMin));
|
||||
}
|
||||
else {
|
||||
return float(0.0);
|
||||
}
|
||||
}
|
||||
"""
|
||||
|
||||
str_rotate_around_axis = """
|
||||
vec3 rotate_around_axis(const vec3 p, const vec3 axis, const float angle)
|
||||
{
|
||||
float costheta = cos(angle);
|
||||
float sintheta = sin(angle);
|
||||
vec3 r;
|
||||
|
||||
r.x = ((costheta + (1.0 - costheta) * axis.x * axis.x) * p.x) +
|
||||
(((1.0 - costheta) * axis.x * axis.y - axis.z * sintheta) * p.y) +
|
||||
(((1.0 - costheta) * axis.x * axis.z + axis.y * sintheta) * p.z);
|
||||
|
||||
r.y = (((1.0 - costheta) * axis.x * axis.y + axis.z * sintheta) * p.x) +
|
||||
((costheta + (1.0 - costheta) * axis.y * axis.y) * p.y) +
|
||||
(((1.0 - costheta) * axis.y * axis.z - axis.x * sintheta) * p.z);
|
||||
|
||||
r.z = (((1.0 - costheta) * axis.x * axis.z - axis.y * sintheta) * p.x) +
|
||||
(((1.0 - costheta) * axis.y * axis.z + axis.x * sintheta) * p.y) +
|
||||
((costheta + (1.0 - costheta) * axis.z * axis.z) * p.z);
|
||||
|
||||
return r;
|
||||
}
|
||||
"""
|
||||
|
||||
str_euler_to_mat3 = """
|
||||
mat3 euler_to_mat3(vec3 euler)
|
||||
{
|
||||
float cx = cos(euler.x);
|
||||
float cy = cos(euler.y);
|
||||
float cz = cos(euler.z);
|
||||
float sx = sin(euler.x);
|
||||
float sy = sin(euler.y);
|
||||
float sz = sin(euler.z);
|
||||
|
||||
mat3 mat;
|
||||
mat[0][0] = cy * cz;
|
||||
mat[0][1] = cy * sz;
|
||||
mat[0][2] = -sy;
|
||||
|
||||
mat[1][0] = sy * sx * cz - cx * sz;
|
||||
mat[1][1] = sy * sx * sz + cx * cz;
|
||||
mat[1][2] = cy * sx;
|
||||
|
||||
mat[2][0] = sy * cx * cz + sx * sz;
|
||||
mat[2][1] = sy * cx * sz - sx * cz;
|
||||
mat[2][2] = cy * cx;
|
||||
return mat;
|
||||
}
|
||||
"""
|
|
@ -8,73 +8,43 @@ import arm.material.cycles_functions as c_functions
|
|||
from arm.material.parser_state import ParserState
|
||||
from arm.material.shader import floatstr, vec3str
|
||||
|
||||
def parse_maprange(node: bpy.types.ShaderNodeMapRange, out_socket: bpy.types.NodeSocket, state: ParserState) -> floatstr:
|
||||
|
||||
interp = node.interpolation_type
|
||||
|
||||
value: str = c.parse_value_input(node.inputs[0]) if node.inputs[0].is_linked else c.to_vec1(node.inputs[0].default_value)
|
||||
fromMin = c.parse_value_input(node.inputs[1])
|
||||
fromMax = c.parse_value_input(node.inputs[2])
|
||||
toMin = c.parse_value_input(node.inputs[3])
|
||||
toMax = c.parse_value_input(node.inputs[4])
|
||||
|
||||
if interp == "LINEAR":
|
||||
|
||||
state.curshader.add_function(c_functions.str_map_range_linear)
|
||||
return f'map_range_linear({value}, {fromMin}, {fromMax}, {toMin}, {toMax})'
|
||||
|
||||
elif interp == "STEPPED":
|
||||
|
||||
steps = float(c.parse_value_input(node.inputs[5]))
|
||||
state.curshader.add_function(c_functions.str_map_range_stepped)
|
||||
return f'map_range_stepped({value}, {fromMin}, {fromMax}, {toMin}, {toMax}, {steps})'
|
||||
|
||||
elif interp == "SMOOTHSTEP":
|
||||
|
||||
state.curshader.add_function(c_functions.str_map_range_smoothstep)
|
||||
return f'map_range_smoothstep({value}, {fromMin}, {fromMax}, {toMin}, {toMax})'
|
||||
|
||||
elif interp == "SMOOTHERSTEP":
|
||||
|
||||
state.curshader.add_function(c_functions.str_map_range_smootherstep)
|
||||
return f'map_range_smootherstep({value}, {fromMin}, {fromMax}, {toMin}, {toMax})'
|
||||
|
||||
def parse_blackbody(node: bpy.types.ShaderNodeBlackbody, out_socket: bpy.types.NodeSocket, state: ParserState) -> vec3str:
|
||||
t = float(c.parse_value_input(node.inputs[0]))
|
||||
|
||||
rgb = [0, 0, 0]
|
||||
blackbody_table_r = [
|
||||
[2.52432244e+03, -1.06185848e-03, 3.11067539e+00],
|
||||
[3.37763626e+03, -4.34581697e-04, 1.64843306e+00],
|
||||
[4.10671449e+03, -8.61949938e-05, 6.41423749e-01],
|
||||
[4.66849800e+03, 2.85655028e-05, 1.29075375e-01],
|
||||
[4.60124770e+03, 2.89727618e-05, 1.48001316e-01],
|
||||
[3.78765709e+03, 9.36026367e-06, 3.98995841e-01]
|
||||
]
|
||||
blackbody_table_g = [
|
||||
[-7.50343014e+02, 3.15679613e-04, 4.73464526e-01],
|
||||
[-1.00402363e+03, 1.29189794e-04, 9.08181524e-01],
|
||||
[-1.22075471e+03, 2.56245413e-05, 1.20753416e+00],
|
||||
[-1.42546105e+03, -4.01730887e-05, 1.44002695e+00],
|
||||
[-1.18134453e+03, -2.18913373e-05, 1.30656109e+00],
|
||||
[-5.00279505e+02, -4.59745390e-06, 1.09090465e+00]
|
||||
]
|
||||
blackbody_table_b = [
|
||||
[0.0, 0.0, 0.0, 0.0],
|
||||
[0.0, 0.0, 0.0, 0.0],
|
||||
[0.0, 0.0, 0.0, 0.0],
|
||||
[-2.02524603e-11, 1.79435860e-07, -2.60561875e-04, -1.41761141e-02],
|
||||
[-2.22463426e-13, -1.55078698e-08, 3.81675160e-04, -7.30646033e-01],
|
||||
[6.72595954e-13, -2.73059993e-08, 4.24068546e-04, -7.52204323e-01]
|
||||
]
|
||||
|
||||
if t >= 12000:
|
||||
rgb[0] = 0.826270103
|
||||
rgb[1] = 0.994478524
|
||||
rgb[2] = 1.56626022
|
||||
|
||||
elif t < 965.0:
|
||||
rgb[0] = 4.70366907
|
||||
rgb[1] = 0.0
|
||||
rgb[2] = 0.0
|
||||
|
||||
else:
|
||||
if t >= 6365.0:
|
||||
i = 5
|
||||
elif t >= 3315.0:
|
||||
i = 4
|
||||
elif t >= 1902.0:
|
||||
i = 3
|
||||
elif t >= 1449.0:
|
||||
i = 2
|
||||
elif t >= 1167.0:
|
||||
i = 1
|
||||
else:
|
||||
i = 0
|
||||
|
||||
r = blackbody_table_r[i]
|
||||
g = blackbody_table_g[i]
|
||||
b = blackbody_table_b[i]
|
||||
|
||||
t_inv = 1.0 / t
|
||||
|
||||
rgb[0] = r[0] * t_inv + r[1] * t + r[2]
|
||||
rgb[1] = g[0] * t_inv + g[1] * t + g[2]
|
||||
rgb[2] = ((b[0] * t + b[1]) * t + b[2]) * t + b[3]
|
||||
|
||||
# Pass constant
|
||||
return c.to_vec3([rgb[0], rgb[1], rgb[2]])
|
||||
|
||||
t = c.parse_value_input(node.inputs[0])
|
||||
|
||||
state.curshader.add_function(c_functions.str_blackbody)
|
||||
return f'blackbody({t})'
|
||||
|
||||
def parse_clamp(node: bpy.types.ShaderNodeClamp, out_socket: bpy.types.NodeSocket, state: ParserState) -> floatstr:
|
||||
value = c.parse_value_input(node.inputs['Value'])
|
||||
|
@ -262,14 +232,21 @@ def parse_math(node: bpy.types.ShaderNodeMath, out_socket: bpy.types.NodeSocket,
|
|||
out_val = '({0} * {1})'.format(val1, val2)
|
||||
elif op == 'DIVIDE':
|
||||
out_val = '({0} / {1})'.format(val1, val2)
|
||||
elif op == 'MULTIPLY_ADD':
|
||||
val3 = c.parse_value_input(node.inputs[2])
|
||||
out_val = '({0} * {1} + {2})'.format(val1, val2, val3)
|
||||
elif op == 'POWER':
|
||||
out_val = 'pow({0}, {1})'.format(val1, val2)
|
||||
elif op == 'LOGARITHM':
|
||||
out_val = 'log({0})'.format(val1)
|
||||
elif op == 'SQRT':
|
||||
out_val = 'sqrt({0})'.format(val1)
|
||||
elif op == 'INVERSE_SQRT':
|
||||
out_val = 'inversesqrt({0})'.format(val1)
|
||||
elif op == 'ABSOLUTE':
|
||||
out_val = 'abs({0})'.format(val1)
|
||||
elif op == 'EXPONENT':
|
||||
out_val = 'exp({0})'.format(val1)
|
||||
elif op == 'MINIMUM':
|
||||
out_val = 'min({0}, {1})'.format(val1, val2)
|
||||
elif op == 'MAXIMUM':
|
||||
|
@ -278,6 +255,17 @@ def parse_math(node: bpy.types.ShaderNodeMath, out_socket: bpy.types.NodeSocket,
|
|||
out_val = 'float({0} < {1})'.format(val1, val2)
|
||||
elif op == 'GREATER_THAN':
|
||||
out_val = 'float({0} > {1})'.format(val1, val2)
|
||||
elif op == 'SIGN':
|
||||
out_val = 'sign({0})'.format(val1)
|
||||
elif op == 'COMPARE':
|
||||
val3 = c.parse_value_input(node.inputs[2])
|
||||
out_val = 'float((abs({0} - {1}) <= max({2}, 1e-5)) ? 1.0 : 0.0)'.format(val1, val2, val3)
|
||||
elif op == 'SMOOTH_MIN':
|
||||
val3 = c.parse_value_input(node.inputs[2])
|
||||
out_val = 'float(float({2} != 0.0 ? min({0},{1}) - (max({2} - abs({0} - {1}), 0.0) / {2}) * (max({2} - abs({0} - {1}), 0.0) / {2}) * (max({2} - abs({0} - {1}), 0.0) / {2}) * {2} * (1.0 / 6.0) : min({0}, {1})))'.format(val1, val2, val3)
|
||||
elif op == 'SMOOTH_MAX':
|
||||
val3 = c.parse_value_input(node.inputs[2])
|
||||
out_val = 'float(0-(float({2} != 0.0 ? min(-{0},-{1}) - (max({2} - abs(-{0} - (-{1})), 0.0) / {2}) * (max({2} - abs(-{0} - (-{1})), 0.0) / {2}) * (max({2} - abs(-{0} - (-{1})), 0.0) / {2}) * {2} * (1.0 / 6.0) : min(-{0}, (-{1})))))'.format(val1, val2, val3)
|
||||
elif op == 'ROUND':
|
||||
# out_val = 'round({0})'.format(val1)
|
||||
out_val = 'floor({0} + 0.5)'.format(val1)
|
||||
|
@ -285,11 +273,20 @@ def parse_math(node: bpy.types.ShaderNodeMath, out_socket: bpy.types.NodeSocket,
|
|||
out_val = 'floor({0})'.format(val1)
|
||||
elif op == 'CEIL':
|
||||
out_val = 'ceil({0})'.format(val1)
|
||||
elif op == 'TRUNC':
|
||||
out_val = 'trunc({0})'.format(val1)
|
||||
elif op == 'FRACT':
|
||||
out_val = 'fract({0})'.format(val1)
|
||||
elif op == 'MODULO':
|
||||
# out_val = 'float({0} % {1})'.format(val1, val2)
|
||||
out_val = 'mod({0}, {1})'.format(val1, val2)
|
||||
elif op == 'WRAP':
|
||||
val3 = c.parse_value_input(node.inputs[2])
|
||||
out_val = 'float((({1}-{2}) != 0.0) ? {0} - (({1}-{2}) * floor(({0} - {2}) / ({1}-{2}))) : {2})'.format(val1, val2, val3)
|
||||
elif op == 'SNAP':
|
||||
out_val = 'floor(({1} != 0.0) ? {0} / {1} : 0.0) * {1}'.format(val1, val2)
|
||||
elif op == 'PINGPONG':
|
||||
out_val = 'float(({1} != 0.0) ? abs(fract(({0} - {1}) / ({1} * 2.0)) * {1} * 2.0 - {1}) : 0.0)'.format(val1, val2)
|
||||
elif op == 'SINE':
|
||||
out_val = 'sin({0})'.format(val1)
|
||||
elif op == 'COSINE':
|
||||
|
@ -304,6 +301,16 @@ def parse_math(node: bpy.types.ShaderNodeMath, out_socket: bpy.types.NodeSocket,
|
|||
out_val = 'atan({0})'.format(val1)
|
||||
elif op == 'ARCTAN2':
|
||||
out_val = 'atan({0}, {1})'.format(val1, val2)
|
||||
elif op == 'SINH':
|
||||
out_val = 'sinh({0})'.format(val1)
|
||||
elif op == 'COSH':
|
||||
out_val = 'cosh({0})'.format(val1)
|
||||
elif op == 'TANH':
|
||||
out_val = 'tanh({0})'.format(val1)
|
||||
elif op == 'RADIANS':
|
||||
out_val = 'radians({0})'.format(val1)
|
||||
elif op == 'DEGREES':
|
||||
out_val = 'degrees({0})'.format(val1)
|
||||
|
||||
if node.use_clamp:
|
||||
return 'clamp({0}, 0.0, 1.0)'.format(out_val)
|
||||
|
|
|
@ -4,6 +4,7 @@ import bpy
|
|||
from mathutils import Euler, Vector
|
||||
|
||||
import arm.material.cycles as c
|
||||
import arm.material.cycles_functions as c_functions
|
||||
from arm.material.parser_state import ParserState
|
||||
from arm.material.shader import floatstr, vec3str
|
||||
|
||||
|
@ -141,3 +142,33 @@ def parse_displacement(node: bpy.types.ShaderNodeDisplacement, out_socket: bpy.t
|
|||
scale = c.parse_value_input(node.inputs[2])
|
||||
nor = c.parse_vector_input(node.inputs[3])
|
||||
return f'(vec3({height}) * {scale})'
|
||||
|
||||
def parse_vectorrotate(node: bpy.types.ShaderNodeVectorRotate, out_socket: bpy.types.NodeSocket, state: ParserState) -> vec3str:
|
||||
|
||||
type = node.rotation_type
|
||||
input_vector: bpy.types.NodeSocket = c.parse_vector_input(node.inputs[0])
|
||||
input_center: bpy.types.NodeSocket = c.parse_vector_input(node.inputs[1])
|
||||
input_axis: bpy.types.NodeSocket = c.parse_vector_input(node.inputs[2])
|
||||
input_angle: bpy.types.NodeSocket = c.parse_value_input(node.inputs[3])
|
||||
input_rotation: bpy.types.NodeSocket = c.parse_vector_input(node.inputs[4])
|
||||
|
||||
if node.invert:
|
||||
input_invert = "0"
|
||||
else:
|
||||
input_invert = "1"
|
||||
|
||||
state.curshader.add_function(c_functions.str_rotate_around_axis)
|
||||
|
||||
if type == 'AXIS_ANGLE':
|
||||
return f'vec3( (length({input_axis}) != 0.0) ? rotate_around_axis({input_vector} - {input_center}, normalize({input_axis}), {input_angle} * {input_invert}) + {input_center} : {input_vector} )'
|
||||
elif type == 'X_AXIS':
|
||||
return f'vec3( rotate_around_axis({input_vector} - {input_center}, vec3(1.0, 0.0, 0.0), {input_angle} * {input_invert}) + {input_center} )'
|
||||
elif type == 'Y_AXIS':
|
||||
return f'vec3( rotate_around_axis({input_vector} - {input_center}, vec3(0.0, 1.0, 0.0), {input_angle} * {input_invert}) + {input_center} )'
|
||||
elif type == 'Z_AXIS':
|
||||
return f'vec3( rotate_around_axis({input_vector} - {input_center}, vec3(0.0, 0.0, 1.0), {input_angle} * {input_invert}) + {input_center} )'
|
||||
elif type == 'EULER_XYZ':
|
||||
state.curshader.add_function(c_functions.str_euler_to_mat3)
|
||||
return f'vec3( mat3(({input_invert} < 0.0) ? transpose(euler_to_mat3({input_rotation})) : euler_to_mat3({input_rotation})) * ({input_vector} - {input_center}) + {input_center})'
|
||||
|
||||
return f'(vec3(1.0, 0.0, 0.0))'
|
||||
|
|
Loading…
Reference in a new issue