I converted a simple barrel distortion shader from Shadertoy for use in Codea. Barrel distortion is commonly used to produce the curved look of a CRT monitor (see the attached image).
EDITED 09-20-17: The shader is now updated and embedded in code which allows you to adjust the distortion amount to produce a barrel or pincushion effect.
-- Barrel Distortion Shader
function setup()
print("Set positive distortion for barrel effect, negative distortion for pincushion effect.")
print("Adapted from https://www.shadertoy.com/view/lddGDN")
parameter.number("Distortion", -0.1, 0.5, 0.25)
parameter.boolean("Original", false)
myMesh = mesh()
local rIdx = myMesh:addRect(0, 0, 0, 0)
myMesh.texture = "Cargo Bot:Codea Icon"
meshWidth, meshHeight = spriteSize(myMesh.texture)
myMesh:setRect(rIdx, 0, 0, meshWidth, meshHeight)
myMesh.shader = shader(barrelShader.vert, barrelShader.frag)
myMesh.shader.resolution = 32.0
myMesh.shader.size = 1.0
end
function draw()
background(0)
if Original then
pushMatrix()
translate(WIDTH/2, HEIGHT/2)
sprite(myMesh.texture)
popMatrix()
else
myMesh.shader.distortion = Distortion
pushMatrix()
translate(WIDTH/2, HEIGHT/2)
myMesh:draw()
popMatrix()
end
end
barrelShader = {
vert = [[
uniform mat4 modelViewProjection;
attribute vec4 position;
attribute vec4 color;
attribute vec2 texCoord;
varying lowp vec4 vColor;
varying highp vec2 vTexCoord;
void main()
{
vColor = color;
vTexCoord = texCoord;
gl_Position = modelViewProjection * position;
}
]],
frag = [[
// Adapted from https://www.shadertoy.com/view/lddGDN
precision highp float;
uniform lowp sampler2D texture;
varying lowp vec4 vColor;
varying highp vec2 vTexCoord;
uniform highp float distortion;
void main()
{
//Sample the texture at the interpolated coordinate
lowp vec4 col = texture2D( texture, vTexCoord ) * vColor;
//Set the output color to the texture color
gl_FragColor = col;
vec2 uv = vTexCoord;
uv = uv * 2.0 - 1.0;
float r = uv.x*uv.x + uv.y*uv.y;
uv *= 1.6 + distortion * r + distortion * r * r;
uv = 0.5 * (uv * 0.5 + 1.0);
gl_FragColor = texture2D(texture, uv);
}
]]
}