mirror of
https://github.com/tanema/light_world.lua.git
synced 2024-12-24 20:24:19 +00:00
Add reflection.
This commit is contained in:
parent
c8c7ec418a
commit
bae4a0db4d
BIN
gfx/water.png
Normal file
BIN
gfx/water.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 11 KiB |
71
light.lua
71
light.lua
@ -7,6 +7,8 @@ LOVE_LIGHT_SHADOW_GEOMETRY = nil
|
|||||||
|
|
||||||
LOVE_LIGHT_BLURV = love.graphics.newShader("shader/blurv.glsl")
|
LOVE_LIGHT_BLURV = love.graphics.newShader("shader/blurv.glsl")
|
||||||
LOVE_LIGHT_BLURH = love.graphics.newShader("shader/blurh.glsl")
|
LOVE_LIGHT_BLURH = love.graphics.newShader("shader/blurh.glsl")
|
||||||
|
LOVE_LIGHT_BLURV:send("screen", {love.window.getWidth(), love.window.getHeight()})
|
||||||
|
LOVE_LIGHT_BLURH:send("screen", {love.window.getWidth(), love.window.getHeight()})
|
||||||
|
|
||||||
LOVE_LIGHT_TRANSLATE_X = 0
|
LOVE_LIGHT_TRANSLATE_X = 0
|
||||||
LOVE_LIGHT_TRANSLATE_Y = 0
|
LOVE_LIGHT_TRANSLATE_Y = 0
|
||||||
@ -33,6 +35,8 @@ function love.light.newWorld()
|
|||||||
o.glowMap2 = love.graphics.newCanvas()
|
o.glowMap2 = love.graphics.newCanvas()
|
||||||
o.refractionMap = love.graphics.newCanvas()
|
o.refractionMap = love.graphics.newCanvas()
|
||||||
o.refractionMap2 = love.graphics.newCanvas()
|
o.refractionMap2 = love.graphics.newCanvas()
|
||||||
|
o.reflectionMap = love.graphics.newCanvas()
|
||||||
|
o.reflectionMap2 = love.graphics.newCanvas()
|
||||||
o.glowBlur = 1.0
|
o.glowBlur = 1.0
|
||||||
o.isGlowBlur = false
|
o.isGlowBlur = false
|
||||||
o.refractionStrength = 8.0
|
o.refractionStrength = 8.0
|
||||||
@ -41,6 +45,11 @@ function love.light.newWorld()
|
|||||||
o.shader = love.graphics.newShader("shader/poly_shadow.glsl")
|
o.shader = love.graphics.newShader("shader/poly_shadow.glsl")
|
||||||
o.normalShader = love.graphics.newShader("shader/normal.glsl")
|
o.normalShader = love.graphics.newShader("shader/normal.glsl")
|
||||||
o.refractionShader = love.graphics.newShader("shader/refraction.glsl")
|
o.refractionShader = love.graphics.newShader("shader/refraction.glsl")
|
||||||
|
o.refractionShader:send("screen", {love.window.getWidth(), love.window.getHeight()})
|
||||||
|
o.reflectionShader = love.graphics.newShader("shader/reflection.glsl")
|
||||||
|
o.reflectionShader:send("screen", {love.window.getWidth(), love.window.getHeight()})
|
||||||
|
o.reflectionStrength = 16.0
|
||||||
|
o.reflectionVisibility = 1.0
|
||||||
o.changed = true
|
o.changed = true
|
||||||
o.blur = 2.0
|
o.blur = 2.0
|
||||||
-- update
|
-- update
|
||||||
@ -178,7 +187,6 @@ function love.light.newWorld()
|
|||||||
end
|
end
|
||||||
|
|
||||||
-- update pixel shadow
|
-- update pixel shadow
|
||||||
love.graphics.setColor(255, 255, 255)
|
|
||||||
love.graphics.setBlendMode("alpha")
|
love.graphics.setBlendMode("alpha")
|
||||||
|
|
||||||
-- create normal map
|
-- create normal map
|
||||||
@ -190,12 +198,10 @@ function love.light.newWorld()
|
|||||||
if o.img[i].normal then
|
if o.img[i].normal then
|
||||||
love.graphics.setColor(255, 255, 255)
|
love.graphics.setColor(255, 255, 255)
|
||||||
love.graphics.draw(o.img[i].normal, o.img[i].x - o.img[i].ox2 + LOVE_LIGHT_TRANSLATE_X, o.img[i].y - o.img[i].oy2 + LOVE_LIGHT_TRANSLATE_Y)
|
love.graphics.draw(o.img[i].normal, o.img[i].x - o.img[i].ox2 + LOVE_LIGHT_TRANSLATE_X, o.img[i].y - o.img[i].oy2 + LOVE_LIGHT_TRANSLATE_Y)
|
||||||
else
|
|
||||||
love.graphics.setColor(0, 0, 0, 0)
|
|
||||||
love.graphics.rectangle("fill", o.img[i].x - o.img[i].ox2 + LOVE_LIGHT_TRANSLATE_X, o.img[i].y - o.img[i].oy2, o.img[i].imgWidth, o.img[i].imgHeight + LOVE_LIGHT_TRANSLATE_Y)
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
love.graphics.setColor(255, 255, 255)
|
love.graphics.setColor(255, 255, 255)
|
||||||
|
love.graphics.setBlendMode("alpha")
|
||||||
end
|
end
|
||||||
|
|
||||||
o.pixelShadow2:clear()
|
o.pixelShadow2:clear()
|
||||||
@ -275,6 +281,35 @@ function love.light.newWorld()
|
|||||||
love.graphics.rectangle("fill", o.refraction[i].x - o.refraction[i].ox + LOVE_LIGHT_TRANSLATE_X, o.refraction[i].y - o.refraction[i].oy, o.refraction[i].normalWidth, o.refraction[i].normalHeight + LOVE_LIGHT_TRANSLATE_Y)
|
love.graphics.rectangle("fill", o.refraction[i].x - o.refraction[i].ox + LOVE_LIGHT_TRANSLATE_X, o.refraction[i].y - o.refraction[i].oy, o.refraction[i].normalWidth, o.refraction[i].normalHeight + LOVE_LIGHT_TRANSLATE_Y)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
for i = 1, #o.img do
|
||||||
|
if o.img[i].img then
|
||||||
|
love.graphics.setColor(0, 0, 0)
|
||||||
|
love.graphics.draw(o.img[i].img, o.img[i].x - o.img[i].ox2 + LOVE_LIGHT_TRANSLATE_X, o.img[i].y - o.img[i].oy2 + LOVE_LIGHT_TRANSLATE_Y)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
-- create reflection map
|
||||||
|
if o.changed then
|
||||||
|
o.reflectionMap:clear(0, 0, 0)
|
||||||
|
love.graphics.setCanvas(o.reflectionMap)
|
||||||
|
for i = 1, #o.refraction do
|
||||||
|
if o.refraction[i].reflective and o.refraction[i].normal then
|
||||||
|
love.graphics.setColor(255, 0, 0)
|
||||||
|
else
|
||||||
|
love.graphics.setColor(0, 0, 0)
|
||||||
|
end
|
||||||
|
o.refraction[i].mesh:setVertices(o.refraction[i].vertices)
|
||||||
|
love.graphics.draw(o.refraction[i].mesh, o.refraction[i].x - o.refraction[i].ox + LOVE_LIGHT_TRANSLATE_X, o.refraction[i].y - o.refraction[i].oy + LOVE_LIGHT_TRANSLATE_Y)
|
||||||
|
end
|
||||||
|
for i = 1, #o.img do
|
||||||
|
if o.img[i].reflective and o.img[i].img then
|
||||||
|
love.graphics.setColor(0, 255, 0)
|
||||||
|
else
|
||||||
|
love.graphics.setColor(0, 0, 0)
|
||||||
|
end
|
||||||
|
love.graphics.draw(o.img[i].img, o.img[i].x - o.img[i].ox2 + LOVE_LIGHT_TRANSLATE_X, o.img[i].y - o.img[i].oy2 + LOVE_LIGHT_TRANSLATE_Y)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
love.graphics.setShader()
|
love.graphics.setShader()
|
||||||
@ -386,7 +421,23 @@ function love.light.newWorld()
|
|||||||
o.refractionShader:send("refractionStrength", o.refractionStrength)
|
o.refractionShader:send("refractionStrength", o.refractionStrength)
|
||||||
love.graphics.setShader(o.refractionShader)
|
love.graphics.setShader(o.refractionShader)
|
||||||
love.graphics.draw(o.refractionMap, LOVE_LIGHT_TRANSLATE_X, LOVE_LIGHT_TRANSLATE_Y)
|
love.graphics.draw(o.refractionMap, LOVE_LIGHT_TRANSLATE_X, LOVE_LIGHT_TRANSLATE_Y)
|
||||||
--love.graphics.rectangle("fill", LOVE_LIGHT_TRANSLATE_X, LOVE_LIGHT_TRANSLATE_Y, love.graphics.getWidth(), love.graphics.getHeight())
|
love.graphics.setShader()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
-- draw reflection
|
||||||
|
o.drawReflection = function()
|
||||||
|
LOVE_LIGHT_LAST_BUFFER = love.graphics.getCanvas()
|
||||||
|
if LOVE_LIGHT_LAST_BUFFER then
|
||||||
|
love.graphics.setColor(255, 255, 255)
|
||||||
|
love.graphics.setBlendMode("alpha")
|
||||||
|
love.graphics.setCanvas(o.reflectionMap2)
|
||||||
|
love.graphics.draw(LOVE_LIGHT_LAST_BUFFER, LOVE_LIGHT_TRANSLATE_X, LOVE_LIGHT_TRANSLATE_Y)
|
||||||
|
love.graphics.setCanvas(LOVE_LIGHT_LAST_BUFFER)
|
||||||
|
o.reflectionShader:send("backBuffer", o.reflectionMap2)
|
||||||
|
o.reflectionShader:send("reflectionStrength", o.reflectionStrength)
|
||||||
|
o.reflectionShader:send("reflectionVisibility", o.reflectionVisibility)
|
||||||
|
love.graphics.setShader(o.reflectionShader)
|
||||||
|
love.graphics.draw(o.reflectionMap, LOVE_LIGHT_TRANSLATE_X, LOVE_LIGHT_TRANSLATE_Y)
|
||||||
love.graphics.setShader()
|
love.graphics.setShader()
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -449,6 +500,14 @@ function love.light.newWorld()
|
|||||||
o.setRefractionStrength = function(strength)
|
o.setRefractionStrength = function(strength)
|
||||||
o.refractionStrength = strength
|
o.refractionStrength = strength
|
||||||
end
|
end
|
||||||
|
-- set reflection strength
|
||||||
|
o.setReflectionStrength = function(strength)
|
||||||
|
o.reflectionStrength = strength
|
||||||
|
end
|
||||||
|
-- set reflection visibility
|
||||||
|
o.setReflectionVisibility = function(visibility)
|
||||||
|
o.reflectionVisibility = visibility
|
||||||
|
end
|
||||||
-- new rectangle
|
-- new rectangle
|
||||||
o.newRectangle = function(x, y, w, h)
|
o.newRectangle = function(x, y, w, h)
|
||||||
return love.light.newRectangle(o, x, y, w, h)
|
return love.light.newRectangle(o, x, y, w, h)
|
||||||
@ -986,6 +1045,7 @@ function love.light.newImage(p, img, x, y, width, height, ox, oy)
|
|||||||
o.glowBlue = 255
|
o.glowBlue = 255
|
||||||
o.glowStrength = 0.0
|
o.glowStrength = 0.0
|
||||||
o.refractionStrength = 1.0
|
o.refractionStrength = 1.0
|
||||||
|
o.reflective = true
|
||||||
o.type = "image"
|
o.type = "image"
|
||||||
p.changed = true
|
p.changed = true
|
||||||
o.data = {
|
o.data = {
|
||||||
@ -1215,6 +1275,7 @@ function love.light.newRefraction(p, normal, x, y)
|
|||||||
o.normalWidth = normal:getWidth()
|
o.normalWidth = normal:getWidth()
|
||||||
o.normalHeight = normal:getHeight()
|
o.normalHeight = normal:getHeight()
|
||||||
o.strength = strength or 1.0
|
o.strength = strength or 1.0
|
||||||
|
o.reflective = true
|
||||||
o.type = "refraction"
|
o.type = "refraction"
|
||||||
p.changed = true
|
p.changed = true
|
||||||
-- set position
|
-- set position
|
||||||
|
19
main.lua
19
main.lua
@ -62,6 +62,7 @@ function love.load()
|
|||||||
tile_normal = love.graphics.newImage("gfx/tile_normal.png")
|
tile_normal = love.graphics.newImage("gfx/tile_normal.png")
|
||||||
tile_glow = love.graphics.newImage("gfx/tile_glow.png")
|
tile_glow = love.graphics.newImage("gfx/tile_glow.png")
|
||||||
refraction_normal = love.graphics.newImage("gfx/refraction_normal.png")
|
refraction_normal = love.graphics.newImage("gfx/refraction_normal.png")
|
||||||
|
water = love.graphics.newImage("gfx/water.png")
|
||||||
|
|
||||||
-- light world
|
-- light world
|
||||||
lightRange = 400
|
lightRange = 400
|
||||||
@ -69,6 +70,7 @@ function love.load()
|
|||||||
lightWorld = love.light.newWorld()
|
lightWorld = love.light.newWorld()
|
||||||
lightWorld.setAmbientColor(15, 15, 31)
|
lightWorld.setAmbientColor(15, 15, 31)
|
||||||
lightWorld.setRefractionStrength(16.0)
|
lightWorld.setRefractionStrength(16.0)
|
||||||
|
lightWorld.setReflectionVisibility(0.75)
|
||||||
mouseLight = lightWorld.newLight(0, 0, 255, 127, 63, lightRange)
|
mouseLight = lightWorld.newLight(0, 0, 255, 127, 63, lightRange)
|
||||||
mouseLight.setGlowStrength(0.3)
|
mouseLight.setGlowStrength(0.3)
|
||||||
mouseLight.setSmooth(lightSmooth)
|
mouseLight.setSmooth(lightSmooth)
|
||||||
@ -216,6 +218,16 @@ function love.draw()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
love.graphics.setBlendMode("multiplicative")
|
||||||
|
for i = 1, phyCnt do
|
||||||
|
if phyLight[i].getType() == "refraction" then
|
||||||
|
if not normalOn then
|
||||||
|
love.graphics.setColor(255, 255, 255, 127)
|
||||||
|
love.graphics.draw(water, phyLight[i].x - phyLight[i].ox, phyLight[i].y - phyLight[i].oy)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
-- draw lightmap shadows
|
-- draw lightmap shadows
|
||||||
if lightOn and not normalOn then
|
if lightOn and not normalOn then
|
||||||
lightWorld.drawShadow()
|
lightWorld.drawShadow()
|
||||||
@ -236,6 +248,7 @@ function love.draw()
|
|||||||
lightWorld.drawShine()
|
lightWorld.drawShine()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
love.graphics.setBlendMode("alpha")
|
||||||
for i = 1, phyCnt do
|
for i = 1, phyCnt do
|
||||||
if phyLight[i].getType() == "image" then
|
if phyLight[i].getType() == "image" then
|
||||||
if not normalOn then
|
if not normalOn then
|
||||||
@ -259,6 +272,9 @@ function love.draw()
|
|||||||
lightWorld.drawGlow()
|
lightWorld.drawGlow()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- draw reflection
|
||||||
|
lightWorld.drawReflection()
|
||||||
|
|
||||||
-- draw refraction
|
-- draw refraction
|
||||||
lightWorld.drawRefraction()
|
lightWorld.drawRefraction()
|
||||||
|
|
||||||
@ -498,6 +514,7 @@ function love.keypressed(k, u)
|
|||||||
phyLight[phyCnt].setHeightMap(tile_normal, 2.0)
|
phyLight[phyCnt].setHeightMap(tile_normal, 2.0)
|
||||||
phyLight[phyCnt].setGlowMap(tile_glow)
|
phyLight[phyCnt].setGlowMap(tile_glow)
|
||||||
phyLight[phyCnt].setShadow(false)
|
phyLight[phyCnt].setShadow(false)
|
||||||
|
phyLight[phyCnt].reflective = false
|
||||||
phyBody[phyCnt] = love.physics.newBody(physicWorld, mx, my, "dynamic")
|
phyBody[phyCnt] = love.physics.newBody(physicWorld, mx, my, "dynamic")
|
||||||
phyShape[phyCnt] = love.physics.newRectangleShape(0, 0, 64, 64)
|
phyShape[phyCnt] = love.physics.newRectangleShape(0, 0, 64, 64)
|
||||||
phyFixture[phyCnt] = love.physics.newFixture(phyBody[phyCnt], phyShape[phyCnt])
|
phyFixture[phyCnt] = love.physics.newFixture(phyBody[phyCnt], phyShape[phyCnt])
|
||||||
@ -535,7 +552,7 @@ function love.keypressed(k, u)
|
|||||||
phyFixture[phyCnt]:setRestitution(0.5)
|
phyFixture[phyCnt]:setRestitution(0.5)
|
||||||
elseif k == "0" then
|
elseif k == "0" then
|
||||||
phyCnt = phyCnt + 1
|
phyCnt = phyCnt + 1
|
||||||
phyLight[phyCnt] = lightWorld.newRefraction(refraction_normal, mx, my, 1.0)
|
phyLight[phyCnt] = lightWorld.newRefraction(refraction_normal, mx, my)
|
||||||
--phyBody[phyCnt] = love.physics.newBody(physicWorld, mx, my, "dynamic")
|
--phyBody[phyCnt] = love.physics.newBody(physicWorld, mx, my, "dynamic")
|
||||||
--phyShape[phyCnt] = love.physics.newRectangleShape(0, 0, phyLight[phyCnt].getWidth(), phyLight[phyCnt].getHeight())
|
--phyShape[phyCnt] = love.physics.newRectangleShape(0, 0, phyLight[phyCnt].getWidth(), phyLight[phyCnt].getHeight())
|
||||||
--phyFixture[phyCnt] = love.physics.newFixture(phyBody[phyCnt], phyShape[phyCnt])
|
--phyFixture[phyCnt] = love.physics.newFixture(phyBody[phyCnt], phyShape[phyCnt])
|
||||||
|
24
shader/reflection.glsl
Normal file
24
shader/reflection.glsl
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
extern Image backBuffer;
|
||||||
|
|
||||||
|
extern vec2 screen = vec2(800.0, 600.0);
|
||||||
|
extern float reflectionStrength;
|
||||||
|
extern float reflectionVisibility;
|
||||||
|
|
||||||
|
vec4 effect(vec4 color, Image texture, vec2 texture_coords, vec2 pixel_coords) {
|
||||||
|
vec2 pSize = vec2(1.0 / screen.x, 1.0 / screen.y);
|
||||||
|
vec4 normal = Texel(texture, texture_coords);
|
||||||
|
if(normal.a > 0.0 && normal.r > 0.0) {
|
||||||
|
vec3 pColor = Texel(backBuffer, texture_coords).rgb;
|
||||||
|
vec4 pColor2;
|
||||||
|
for(int i = 0; i < reflectionStrength; i++) {
|
||||||
|
pColor2 = Texel(texture, vec2(texture_coords.x, texture_coords.y + pSize.y * i));
|
||||||
|
if(pColor2.a > 0.0 && pColor2.g > 0.0) {
|
||||||
|
vec3 rColor = Texel(backBuffer, vec2(texture_coords.x, texture_coords.y + pSize.y * i * 2.0)).rgb;
|
||||||
|
return vec4(rColor, (1.0 - i / reflectionStrength) * reflectionVisibility);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return vec4(0.0);
|
||||||
|
} else {
|
||||||
|
return vec4(0.0);
|
||||||
|
}
|
||||||
|
}
|
@ -7,7 +7,7 @@ extern vec3 refractionColor = vec3(1.0, 1.0, 1.0);
|
|||||||
vec4 effect(vec4 color, Image texture, vec2 texture_coords, vec2 pixel_coords) {
|
vec4 effect(vec4 color, Image texture, vec2 texture_coords, vec2 pixel_coords) {
|
||||||
vec2 pSize = vec2(1.0 / screen.x, 1.0 / screen.y);
|
vec2 pSize = vec2(1.0 / screen.x, 1.0 / screen.y);
|
||||||
vec4 normal = Texel(texture, texture_coords);
|
vec4 normal = Texel(texture, texture_coords);
|
||||||
if(normal.a > 0.0) {
|
if(normal.b > 0.0) {
|
||||||
return vec4(Texel(backBuffer, vec2(texture_coords.x + (normal.x - 0.5) * pSize.x * refractionStrength, texture_coords.y + (normal.y - 0.5) * pSize.y * refractionStrength)).rgb * refractionColor, 1.0);
|
return vec4(Texel(backBuffer, vec2(texture_coords.x + (normal.x - 0.5) * pSize.x * refractionStrength, texture_coords.y + (normal.y - 0.5) * pSize.y * refractionStrength)).rgb * refractionColor, 1.0);
|
||||||
} else {
|
} else {
|
||||||
return vec4(0.0);
|
return vec4(0.0);
|
||||||
|
Loading…
Reference in New Issue
Block a user