马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有账号?立即注册
×
本帖最后由 被诅咒的章鱼 于 2021-7-23 16:36 编辑
最近在研究shader,此贴为中间副产品。需Ren'Py 7.4.5以上版本。
此贴中使用的shader代码来源为
ShaderToy-StarNest
我只是做了一点修改和移植到Ren'Py上。
首先是主体的shader代码(不要问我是怎么来的,问就是我也不懂):
[RenPy] 纯文本查看 复制代码 init python:
renpy.register_shader("shadertoy.StarNest", variables="""
uniform float u_time;
uniform vec2 u_model_size;
""",fragment_functions="""
vec2 MatMultiplayVec(vec4 m, vec2 v)
{
return vec2(m.x * v.x + m.z * v.y, m.y * v.x + m.w * v.y);
}
float SCurve (float value)
{
if(value < 0.5)
{
return value * value * value * value * value * 16.0;
}
value -= 1.0;
return value * value * value * value * value * 16.0 + 1.0;
}
""",vertex_300="""
v_tex_coord = vec2(a_tex_coord.s, 1.0 - a_tex_coord.t);
""",
fragment_300="""
#define iterations 17
#define formuparam 0.53
#define volsteps 20
#define stepsize 0.1
#define zoom 0.800
#define tile 0.850
#define speed 0.002
#define brightness 0.002
#define darkmatter 0.300
#define distfading 0.750
#define saturation 0.750
vec2 uv=v_tex_coord-.5;
uv.y*=u_model_size.y/u_model_size.x;
vec3 dir=vec3(uv*zoom,1.);
float time=u_time*speed+.25;
vec3 from=vec3(1.,.5,0.5);
from+=vec3(time*2.,time,-2.);
float s=0.1,fade=1.;
vec3 v=vec3(0.);
for (int r=0; r<volsteps; r++)
{
vec3 p=from+s*dir*.5;
p = abs(vec3(tile)-mod(p,vec3(tile*2.)));
float pa,a=pa=0.;
for (int i=0; i<iterations; i++)
{
p=abs(p)/dot(p,p)-formuparam;
a+=abs(length(p)-pa);
pa=length(p);
}
float dm=max(0.,darkmatter-a*a*.001);
a = pow(a, 2.5);
if (r>6) fade*=1.-dm;
v+=fade;
v+=vec3(s,s*s,s*s*s*s)*a*brightness*fade;
fade*=distfading;
s+=stepsize;
}
v=mix(vec3(length(v)),v,saturation);
vec4 C = vec4(v*.01,1.);
C.r = pow(C.r, 0.35);
C.g = pow(C.g, 0.36);
C.b = pow(C.b, 0.4);
vec4 L = C;
C.r = mix(L.r, SCurve(C.r), 1.0);
C.g = mix(L.g, SCurve(C.g), 0.9);
C.b = mix(L.b, SCurve(C.b), 0.6);
gl_FragColor = C;
""")
然后是在自定义可视组件中应用这个shader:
[RenPy] 纯文本查看 复制代码 init python:
class StarNest(renpy.Displayable):
def __init__(self, child, width, height, **kwargs):
super(StarNest, self).__init__(**kwargs)
self.child = renpy.displayable(child)
self.width = width
self.height = height
def render(self, width, height, st, at):
render = renpy.Render(self.width, self.height)
render.place(self.child)
render.add_shader("shadertoy.StarNest")
render.add_uniform("u_time", st)
render.add_uniform("u_model_size", (self.width, self.height))
renpy.redraw(self, 0)
return render
script.rpy中使用图像:
[RenPy] 纯文本查看 复制代码 image starnest = StarNest("texture", width = 1280, height = 720)
label main_menu:
return
label start:
show starnest
pause
注意这里使用一张名为“texture”的图片,图片内容是什么不重要,尺寸需要为1280×720(或者根据需求修改)。
shader中几个预编译的值都可以修改。(我就是不做成从类的构造函数传入参数)
|