如何在 glsl 中编写 cga 着色器?
how to write a cga shader in glsl?
如何编写将调色板限制为 4 种颜色并将原始颜色与这些颜色(青色、品红色、黑色、白色)相匹配的 CGA 着色器??
我正在开发 Game Maker Studio Professional,它实际上允许使用着色器编写顶点和片段代码
我已经在 yoyogames 社区和 openGl 论坛中问过这个问题
有人这样回答我:
varying vec2 v_vTexcoord;
varying vec4 v_vColour;
const mat3 rgb_to_wcm = mat3(1,-1, 0, 1, 0,-1, -1, 1, 1);
void main()
{
vec4 rgba = v_vColour * texture2D(gm_BaseTexture, v_vTexcoord);
vec3 wcm = rgb_to_wcm * rgba.rgb;
vec3 rgb = dot(wcm,vec3(1,1,1)) < 0.5
? vec3(0,0,0)
: wcm.x > wcm.y
? (wcm.x > wcm.z ? vec3(1,1,1) : vec3(1,0,1))
: (wcm.y > wcm.z ? vec3(0,1,1) : vec3(1,0,1));
gl_FragColor = vec4(rgb, rgba.a);
}
它有效,但不是 return cga 调色板,它 return 黑白(非灰度)
我该怎么办?
非常感谢
我用不同的方式做了,也许更简单
https://www.shadertoy.com/view/MdlyDH
// ▄████████ ▄██████▄ ▄████████
// ███ ███ ███ ███ ███ ███
// ███ █▀ ███ █▀ ███ ███
// ███ ▄███ ███ ███
// ███ ▀▀███ ████▄ ▀███████████
// ███ █▄ ███ ███ ███ ███
// ███ ███ ███ ███ ███ ███
// ████████▀ ████████▀ ███ █▀
//
/*
////only for game maker studio////
varying vec2 v_vTexcoord;
varying vec4 v_vColour;
varying vec2 fragCoord;
//you have to put varying vec2 fragCoord also in the vertex shader
//after write in the last row of the local scope of the vertex shader: fragCoord = in_Position.xy
uniform vec2 iResolution;
uniform float iGlobalTime;
//palette 0 is not cga but gameboy, I put it as bonus
uniform int palette;
uniform float gamma;
*/
// rgb to float
// rgb to float = rgb / 255
// 0 = 0.0
// 85 = 0.333
// 170 = 0.666
// 255 = 1.0
void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
vec2 uv = fragCoord.xy / iResolution.xy;
vec3 c = vec3(0.0);
float alpha = 1.0;
//only for shadertoy
int palette = 2; //the number between 0 and 6 change palette
float gamma = 1.5; //the gamma change the threshold of the palette swapper
//c = texture2D(gm_BaseTexture,uv).rgb;
c = texture(iChannel0,uv).rgb;
c.r = pow(abs(c.r),gamma);
c.g = pow(abs(c.g),gamma);
c.b = pow(abs(c.b),gamma);
vec3 col1 = vec3(0.0);
vec3 col2 = vec3(0.0);
vec3 col3 = vec3(0.0);
vec3 col4 = vec3(0.0);
if(palette == 0) {
col1 = vec3(0.612,0.725,0.086);
col2 = vec3(0.549,0.667,0.078);
col3 = vec3(0.188,0.392,0.188);
col4 = vec3(0.063,0.247,0.063);
}
if(palette == 1) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.666);
col3 = vec3(0.666,0.0,0.666);
col4 = vec3(0.666,0.666,0.666);
}
if(palette == 2) {
col1 = vec3(0.0);
col2 = vec3(0.333,1.0,1.0);
col3 = vec3(1.0,0.333,1.0);
col4 = vec3(1.0);
}
if(palette == 3) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.0);
col3 = vec3(0.666,0.0,0.0);
col4 = vec3(0.666,0.333,0.0);
}
if(palette == 4) {
col1 = vec3(0.0);
col2 = vec3(0.333,1.0,0.333);
col3 = vec3(1.0,0.333,0.333);
col4 = vec3(1.0,1.0,0.333);
}
if(palette == 5) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.666);
col3 = vec3(0.666,0.0,0.0);
col4 = vec3(0.666,0.666,0.666);
}
if(palette == 6) {
col1 = vec3(0.0);
col2 = vec3(0.333,0.666,0.666);
col3 = vec3(1.0,0.333,0.333);
col4 = vec3(1.0);
}
float dist1 = length(c - col1);
float dist2 = length(c - col2);
float dist3 = length(c - col3);
float dist4 = length(c - col4);
float d = min(dist1,dist2);
d = min(d,dist3);
d = min(d,dist4);
if(d == dist1) {
c = col1;
}
else if(d == dist2) {
c = col2;
}
else if(d == dist3) {
c = col3;
}
else {
c = col4;
}
//gl_FragColor = vec4(c,alpha).rgba;
fragColor = vec4(c,alpha).rgba;
}
这里我还包括了将这个 shadertoy 着色器转换为 game maker studio 着色器的方法,因为在 game maker studio 中没有统一的时间和分辨率来进行时间编辑和 vec2 uv
我还包括了所有 cga 调色板的评论右调色板和一个 gameboy 调色板的奖励调色板 0
我还包括了从 rgb 255 值到无法转换的浮点数的转换
这里唯一的问题是它不能反转颜色或改变调色板中颜色的位置,它采用原始源并输出 4 种颜色,这是唯一的差距。
如何编写将调色板限制为 4 种颜色并将原始颜色与这些颜色(青色、品红色、黑色、白色)相匹配的 CGA 着色器??
我正在开发 Game Maker Studio Professional,它实际上允许使用着色器编写顶点和片段代码
我已经在 yoyogames 社区和 openGl 论坛中问过这个问题
有人这样回答我:
varying vec2 v_vTexcoord;
varying vec4 v_vColour;
const mat3 rgb_to_wcm = mat3(1,-1, 0, 1, 0,-1, -1, 1, 1);
void main()
{
vec4 rgba = v_vColour * texture2D(gm_BaseTexture, v_vTexcoord);
vec3 wcm = rgb_to_wcm * rgba.rgb;
vec3 rgb = dot(wcm,vec3(1,1,1)) < 0.5
? vec3(0,0,0)
: wcm.x > wcm.y
? (wcm.x > wcm.z ? vec3(1,1,1) : vec3(1,0,1))
: (wcm.y > wcm.z ? vec3(0,1,1) : vec3(1,0,1));
gl_FragColor = vec4(rgb, rgba.a);
}
它有效,但不是 return cga 调色板,它 return 黑白(非灰度)
我该怎么办?
非常感谢 我用不同的方式做了,也许更简单
https://www.shadertoy.com/view/MdlyDH
// ▄████████ ▄██████▄ ▄████████
// ███ ███ ███ ███ ███ ███
// ███ █▀ ███ █▀ ███ ███
// ███ ▄███ ███ ███
// ███ ▀▀███ ████▄ ▀███████████
// ███ █▄ ███ ███ ███ ███
// ███ ███ ███ ███ ███ ███
// ████████▀ ████████▀ ███ █▀
//
/*
////only for game maker studio////
varying vec2 v_vTexcoord;
varying vec4 v_vColour;
varying vec2 fragCoord;
//you have to put varying vec2 fragCoord also in the vertex shader
//after write in the last row of the local scope of the vertex shader: fragCoord = in_Position.xy
uniform vec2 iResolution;
uniform float iGlobalTime;
//palette 0 is not cga but gameboy, I put it as bonus
uniform int palette;
uniform float gamma;
*/
// rgb to float
// rgb to float = rgb / 255
// 0 = 0.0
// 85 = 0.333
// 170 = 0.666
// 255 = 1.0
void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
vec2 uv = fragCoord.xy / iResolution.xy;
vec3 c = vec3(0.0);
float alpha = 1.0;
//only for shadertoy
int palette = 2; //the number between 0 and 6 change palette
float gamma = 1.5; //the gamma change the threshold of the palette swapper
//c = texture2D(gm_BaseTexture,uv).rgb;
c = texture(iChannel0,uv).rgb;
c.r = pow(abs(c.r),gamma);
c.g = pow(abs(c.g),gamma);
c.b = pow(abs(c.b),gamma);
vec3 col1 = vec3(0.0);
vec3 col2 = vec3(0.0);
vec3 col3 = vec3(0.0);
vec3 col4 = vec3(0.0);
if(palette == 0) {
col1 = vec3(0.612,0.725,0.086);
col2 = vec3(0.549,0.667,0.078);
col3 = vec3(0.188,0.392,0.188);
col4 = vec3(0.063,0.247,0.063);
}
if(palette == 1) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.666);
col3 = vec3(0.666,0.0,0.666);
col4 = vec3(0.666,0.666,0.666);
}
if(palette == 2) {
col1 = vec3(0.0);
col2 = vec3(0.333,1.0,1.0);
col3 = vec3(1.0,0.333,1.0);
col4 = vec3(1.0);
}
if(palette == 3) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.0);
col3 = vec3(0.666,0.0,0.0);
col4 = vec3(0.666,0.333,0.0);
}
if(palette == 4) {
col1 = vec3(0.0);
col2 = vec3(0.333,1.0,0.333);
col3 = vec3(1.0,0.333,0.333);
col4 = vec3(1.0,1.0,0.333);
}
if(palette == 5) {
col1 = vec3(0.0);
col2 = vec3(0.0,0.666,0.666);
col3 = vec3(0.666,0.0,0.0);
col4 = vec3(0.666,0.666,0.666);
}
if(palette == 6) {
col1 = vec3(0.0);
col2 = vec3(0.333,0.666,0.666);
col3 = vec3(1.0,0.333,0.333);
col4 = vec3(1.0);
}
float dist1 = length(c - col1);
float dist2 = length(c - col2);
float dist3 = length(c - col3);
float dist4 = length(c - col4);
float d = min(dist1,dist2);
d = min(d,dist3);
d = min(d,dist4);
if(d == dist1) {
c = col1;
}
else if(d == dist2) {
c = col2;
}
else if(d == dist3) {
c = col3;
}
else {
c = col4;
}
//gl_FragColor = vec4(c,alpha).rgba;
fragColor = vec4(c,alpha).rgba;
}
这里我还包括了将这个 shadertoy 着色器转换为 game maker studio 着色器的方法,因为在 game maker studio 中没有统一的时间和分辨率来进行时间编辑和 vec2 uv
我还包括了所有 cga 调色板的评论右调色板和一个 gameboy 调色板的奖励调色板 0
我还包括了从 rgb 255 值到无法转换的浮点数的转换
这里唯一的问题是它不能反转颜色或改变调色板中颜色的位置,它采用原始源并输出 4 种颜色,这是唯一的差距。