formatted everything
This commit is contained in:
2
main.lua
2
main.lua
@@ -21,7 +21,7 @@ function love.update(dt)
|
||||
end
|
||||
|
||||
function love.draw()
|
||||
display:draw(function ()
|
||||
display:draw(function()
|
||||
core:draw()
|
||||
end)
|
||||
end
|
||||
|
||||
@@ -136,7 +136,7 @@ function badr:update()
|
||||
end
|
||||
|
||||
return setmetatable({ new = badr.new }, {
|
||||
__call = function (t, ...)
|
||||
__call = function(t, ...)
|
||||
return badr:new(...)
|
||||
end,
|
||||
})
|
||||
|
||||
@@ -64,7 +64,7 @@ local function assertIsRect(x, y, w, h)
|
||||
assertIsPositiveNumber(h, 'h')
|
||||
end
|
||||
|
||||
local defaultFilter = function ()
|
||||
local defaultFilter = function()
|
||||
return 'slide'
|
||||
end
|
||||
|
||||
@@ -273,16 +273,16 @@ end
|
||||
-- Responses
|
||||
------------------------------------------
|
||||
|
||||
local touch = function (world, col, x, y, w, h, goalX, goalY, filter)
|
||||
local touch = function(world, col, x, y, w, h, goalX, goalY, filter)
|
||||
return col.touch.x, col.touch.y, {}, 0
|
||||
end
|
||||
|
||||
local cross = function (world, col, x, y, w, h, goalX, goalY, filter)
|
||||
local cross = function(world, col, x, y, w, h, goalX, goalY, filter)
|
||||
local cols, len = world:project(col.item, x, y, w, h, goalX, goalY, filter)
|
||||
return goalX, goalY, cols, len
|
||||
end
|
||||
|
||||
local slide = function (world, col, x, y, w, h, goalX, goalY, filter)
|
||||
local slide = function(world, col, x, y, w, h, goalX, goalY, filter)
|
||||
goalX = goalX or x
|
||||
goalY = goalY or y
|
||||
|
||||
@@ -302,7 +302,7 @@ local slide = function (world, col, x, y, w, h, goalX, goalY, filter)
|
||||
return goalX, goalY, cols, len
|
||||
end
|
||||
|
||||
local bounce = function (world, col, x, y, w, h, goalX, goalY, filter)
|
||||
local bounce = function(world, col, x, y, w, h, goalX, goalY, filter)
|
||||
goalX = goalX or x
|
||||
goalY = goalY or y
|
||||
|
||||
@@ -393,7 +393,7 @@ end
|
||||
local function getCellsTouchedBySegment(self, x1, y1, x2, y2)
|
||||
local cells, cellsLen, visited = {}, 0, {}
|
||||
|
||||
grid_traverse(self.cellSize, x1, y1, x2, y2, function (cx, cy)
|
||||
grid_traverse(self.cellSize, x1, y1, x2, y2, function(cx, cy)
|
||||
local row = self.rows[cy]
|
||||
if not row then return end
|
||||
local cell = row[cx]
|
||||
@@ -701,7 +701,7 @@ function World:check(item, goalX, goalY, filter)
|
||||
filter = filter or defaultFilter
|
||||
|
||||
local visited = { [item] = true }
|
||||
local visitedFilter = function (itm, other)
|
||||
local visitedFilter = function(itm, other)
|
||||
if visited[other] then return false end
|
||||
return filter(itm, other)
|
||||
end
|
||||
@@ -735,7 +735,7 @@ end
|
||||
|
||||
-- Public library functions
|
||||
|
||||
bump.newWorld = function (cellSize)
|
||||
bump.newWorld = function(cellSize)
|
||||
cellSize = cellSize or 64
|
||||
assertIsPositiveNumber(cellSize, 'cellSize')
|
||||
local world = setmetatable({
|
||||
|
||||
@@ -13,11 +13,11 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local radius_x, radius_y = 3, 3
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec2 direction;
|
||||
extern number radius;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _) {
|
||||
@@ -32,31 +32,31 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
setters.radius = function(v)
|
||||
if type(v) == "number" then
|
||||
if type(v) == 'number' then
|
||||
radius_x, radius_y = v, v
|
||||
elseif type(v) == "table" and #v >= 2 then
|
||||
elseif type(v) == 'table' and #v >= 2 then
|
||||
radius_x, radius_y = tonumber(v[1] or v.h or v.x), tonumber(v[2] or v.v or v.y)
|
||||
else
|
||||
error("Invalid argument `radius'")
|
||||
error "Invalid argument `radius'"
|
||||
end
|
||||
end
|
||||
setters.radius_x = function(v) radius_x = tonumber(v) end
|
||||
setters.radius_y = function(v) radius_y = tonumber(v) end
|
||||
|
||||
local draw = function(buffer)
|
||||
shader:send('direction', {1 / love.graphics.getWidth(), 0})
|
||||
shader:send('direction', { 1 / love.graphics.getWidth(), 0 })
|
||||
shader:send('radius', math.floor(radius_x + .5))
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
|
||||
shader:send('direction', {0, 1 / love.graphics.getHeight()})
|
||||
shader:send('direction', { 0, 1 / love.graphics.getHeight() })
|
||||
shader:send('radius', math.floor(radius_y + .5))
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "boxblur",
|
||||
return moonshine.Effect {
|
||||
name = 'boxblur',
|
||||
draw = draw,
|
||||
setters = setters,
|
||||
defaults = {radius = 3}
|
||||
defaults = { radius = 3 }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -13,10 +13,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec3 factors;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _) {
|
||||
return vec4(factors, 1.0) * Texel(texture, tc) * color;
|
||||
@@ -24,10 +24,10 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "colorgradesimple",
|
||||
return moonshine.Effect {
|
||||
name = 'colorgradesimple',
|
||||
shader = shader,
|
||||
setters = {factors = function(v) shader:send("factors", v) end},
|
||||
defaults = {factors = {1,1,1}}
|
||||
setters = { factors = function(v) shader:send('factors', v) end },
|
||||
defaults = { factors = { 1, 1, 1 } }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -13,13 +13,13 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
-- Barrel distortion adapted from Daniel Oaks (see commit cef01b67fd)
|
||||
-- Added feather to mask out outside of distorted texture
|
||||
local distortionFactor
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec2 distortionFactor;
|
||||
extern vec2 scaleFactor;
|
||||
extern number feather;
|
||||
@@ -44,34 +44,34 @@ return function(moonshine)
|
||||
local setters = {}
|
||||
|
||||
setters.distortionFactor = function(v)
|
||||
assert(type(v) == "table" and #v == 2, "Invalid value for `distortionFactor'")
|
||||
distortionFactor = {unpack(v)}
|
||||
shader:send("distortionFactor", v)
|
||||
assert(type(v) == 'table' and #v == 2, "Invalid value for `distortionFactor'")
|
||||
distortionFactor = { unpack(v) }
|
||||
shader:send('distortionFactor', v)
|
||||
end
|
||||
|
||||
setters.x = function(v) setters.distortionFactor{v, distortionFactor[2]} end
|
||||
setters.y = function(v) setters.distortionFactor{distortionFactor[1], v} end
|
||||
setters.x = function(v) setters.distortionFactor { v, distortionFactor[2] } end
|
||||
setters.y = function(v) setters.distortionFactor { distortionFactor[1], v } end
|
||||
|
||||
setters.scaleFactor = function(v)
|
||||
if type(v) == "table" and #v == 2 then
|
||||
shader:send("scaleFactor", v)
|
||||
elseif type(v) == "number" then
|
||||
shader:send("scaleFactor", {v,v})
|
||||
if type(v) == 'table' and #v == 2 then
|
||||
shader:send('scaleFactor', v)
|
||||
elseif type(v) == 'number' then
|
||||
shader:send('scaleFactor', { v, v })
|
||||
else
|
||||
error("Invalid value for `scaleFactor'")
|
||||
error "Invalid value for `scaleFactor'"
|
||||
end
|
||||
end
|
||||
|
||||
setters.feather = function(v) shader:send("feather", v) end
|
||||
setters.feather = function(v) shader:send('feather', v) end
|
||||
|
||||
local defaults = {
|
||||
distortionFactor = {1.06, 1.065},
|
||||
distortionFactor = { 1.06, 1.065 },
|
||||
feather = 0.02,
|
||||
scaleFactor = 1,
|
||||
}
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "crt",
|
||||
return moonshine.Effect {
|
||||
name = 'crt',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = defaults
|
||||
|
||||
@@ -13,10 +13,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec4 tint;
|
||||
extern number strength;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _) {
|
||||
@@ -28,8 +28,8 @@ return function(moonshine)
|
||||
local setters = {}
|
||||
|
||||
setters.tint = function(c)
|
||||
assert(type(c) == "table" and #c == 3, "Invalid value for `tint'")
|
||||
shader:send("tint", {
|
||||
assert(type(c) == 'table' and #c == 3, "Invalid value for `tint'")
|
||||
shader:send('tint', {
|
||||
(tonumber(c[1]) or 0) / 255,
|
||||
(tonumber(c[2]) or 0) / 255,
|
||||
(tonumber(c[3]) or 0) / 255,
|
||||
@@ -38,13 +38,13 @@ return function(moonshine)
|
||||
end
|
||||
|
||||
setters.strength = function(v)
|
||||
shader:send("strength", math.max(0, math.min(1, tonumber(v) or 0)))
|
||||
shader:send('strength', math.max(0, math.min(1, tonumber(v) or 0)))
|
||||
end
|
||||
|
||||
local defaults = {tint = {255,255,255}, strength = 0.5}
|
||||
local defaults = { tint = { 255, 255, 255 }, strength = 0.5 }
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "desaturate",
|
||||
return moonshine.Effect {
|
||||
name = 'desaturate',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = defaults
|
||||
|
||||
@@ -21,80 +21,80 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
local palettes = {
|
||||
-- Default color palette. Source:
|
||||
-- http://en.wikipedia.org/wiki/List_of_video_game_console_palettes#Original_Game_Boy
|
||||
{
|
||||
name = "default",
|
||||
name = 'default',
|
||||
colors = {
|
||||
{ 15/255, 56/255, 15/255},
|
||||
{ 48/255, 98/255, 48/255},
|
||||
{139/255,172/255, 15/255},
|
||||
{155/255,188/255, 15/255}
|
||||
{ 15 / 255, 56 / 255, 15 / 255 },
|
||||
{ 48 / 255, 98 / 255, 48 / 255 },
|
||||
{ 139 / 255, 172 / 255, 15 / 255 },
|
||||
{ 155 / 255, 188 / 255, 15 / 255 }
|
||||
}
|
||||
},
|
||||
-- Hardcore color profiles. Source:
|
||||
-- http://www.hardcoregaming101.net/gbdebate/gbcolours.htm
|
||||
{
|
||||
name = "dark_yellow",
|
||||
name = 'dark_yellow',
|
||||
colors = {
|
||||
{33/255,32/255,16/255},
|
||||
{107/255,105/255,49/255},
|
||||
{181/255,174/255,74/255},
|
||||
{255/255,247/255,123/255}
|
||||
{ 33 / 255, 32 / 255, 16 / 255 },
|
||||
{ 107 / 255, 105 / 255, 49 / 255 },
|
||||
{ 181 / 255, 174 / 255, 74 / 255 },
|
||||
{ 255 / 255, 247 / 255, 123 / 255 }
|
||||
}
|
||||
},
|
||||
{
|
||||
name = "light_yellow",
|
||||
name = 'light_yellow',
|
||||
colors = {
|
||||
{102/255,102/255,37/255},
|
||||
{148/255,148/255,64/255},
|
||||
{208/255,208/255,102/255},
|
||||
{255/255,255/255,148/255}
|
||||
{ 102 / 255, 102 / 255, 37 / 255 },
|
||||
{ 148 / 255, 148 / 255, 64 / 255 },
|
||||
{ 208 / 255, 208 / 255, 102 / 255 },
|
||||
{ 255 / 255, 255 / 255, 148 / 255 }
|
||||
}
|
||||
},
|
||||
{
|
||||
name = "green",
|
||||
name = 'green',
|
||||
colors = {
|
||||
{8/255,56/255,8/255},
|
||||
{48/255,96/255,48/255},
|
||||
{136/255,168/255,8/255},
|
||||
{183/255,220/255,17/255}
|
||||
{ 8 / 255, 56 / 255, 8 / 255 },
|
||||
{ 48 / 255, 96 / 255, 48 / 255 },
|
||||
{ 136 / 255, 168 / 255, 8 / 255 },
|
||||
{ 183 / 255, 220 / 255, 17 / 255 }
|
||||
}
|
||||
},
|
||||
{
|
||||
name = "greyscale",
|
||||
name = 'greyscale',
|
||||
colors = {
|
||||
{56/255,56/255,56/255},
|
||||
{117/255,117/255,117/255},
|
||||
{178/255,178/255,178/255},
|
||||
{239/255,239/255,239/255}
|
||||
{ 56 / 255, 56 / 255, 56 / 255 },
|
||||
{ 117 / 255, 117 / 255, 117 / 255 },
|
||||
{ 178 / 255, 178 / 255, 178 / 255 },
|
||||
{ 239 / 255, 239 / 255, 239 / 255 }
|
||||
}
|
||||
},
|
||||
{
|
||||
name = "stark_bw",
|
||||
name = 'stark_bw',
|
||||
colors = {
|
||||
{0/255,0/255,0/255},
|
||||
{117/255,117/255,117/255},
|
||||
{178/255,178/255,178/255},
|
||||
{255/255,255/255,255/255}
|
||||
{ 0 / 255, 0 / 255, 0 / 255 },
|
||||
{ 117 / 255, 117 / 255, 117 / 255 },
|
||||
{ 178 / 255, 178 / 255, 178 / 255 },
|
||||
{ 255 / 255, 255 / 255, 255 / 255 }
|
||||
}
|
||||
},
|
||||
{
|
||||
name = "pocket",
|
||||
name = 'pocket',
|
||||
colors = {
|
||||
{108/255,108/255,78/255},
|
||||
{142/255,139/255,87/255},
|
||||
{195/255,196/255,165/255},
|
||||
{227/255,230/255,201/255}
|
||||
{ 108 / 255, 108 / 255, 78 / 255 },
|
||||
{ 142 / 255, 139 / 255, 87 / 255 },
|
||||
{ 195 / 255, 196 / 255, 165 / 255 },
|
||||
{ 227 / 255, 230 / 255, 201 / 255 }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
local lookup_palette = function(name)
|
||||
for _,palette in pairs(palettes) do
|
||||
for _, palette in pairs(palettes) do
|
||||
if palette.name == name then
|
||||
return palette
|
||||
end
|
||||
@@ -105,10 +105,10 @@ local is_valid_palette = function(v)
|
||||
-- Needs to match: {{R,G,B},{R,G,B},{R,G,B},{R,G,B}}
|
||||
if #v ~= 4 then return false end
|
||||
|
||||
for i = 1,4 do
|
||||
if type(v[i]) ~= "table" or #v[i] ~= 3 then return false end
|
||||
for c = 1,3 do
|
||||
if type(v[i][c]) ~= "number" then return false end
|
||||
for i = 1, 4 do
|
||||
if type(v[i]) ~= 'table' or #v[i] ~= 3 then return false end
|
||||
for c = 1, 3 do
|
||||
if type(v[i][c]) ~= 'number' then return false end
|
||||
local x = v[i][c]
|
||||
if x > 1 then x = x / 255 end
|
||||
if x < 0 or x > 1 then return false end
|
||||
@@ -119,7 +119,7 @@ local is_valid_palette = function(v)
|
||||
end
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec3 palette[ 4 ];
|
||||
|
||||
vec4 effect(vec4 color, Image texture, vec2 texture_coords, vec2 pixel_coords) {
|
||||
@@ -131,23 +131,23 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
setters.palette = function(v)
|
||||
if type(v) == "number" and palettes[math.floor(v)] then -- indexed palette
|
||||
if type(v) == 'number' and palettes[math.floor(v)] then -- indexed palette
|
||||
palette = palettes[math.floor(v)]
|
||||
elseif type(v) == "string" then -- named palette
|
||||
elseif type(v) == 'string' then -- named palette
|
||||
palette = lookup_palette(v)
|
||||
elseif type(v) == "table" and is_valid_palette(v) then -- custom palette
|
||||
palette = {colors=v}
|
||||
else -- Fall back to default
|
||||
elseif type(v) == 'table' and is_valid_palette(v) then -- custom palette
|
||||
palette = { colors = v }
|
||||
else -- Fall back to default
|
||||
palette = palettes[1]
|
||||
end
|
||||
shader:send("palette", palette.colors[1], palette.colors[2],
|
||||
palette.colors[3], palette.colors[4], {})
|
||||
shader:send('palette', palette.colors[1], palette.colors[2],
|
||||
palette.colors[3], palette.colors[4], {})
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "dmg",
|
||||
return moonshine.Effect {
|
||||
name = 'dmg',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = {palette = "default"}
|
||||
defaults = { palette = 'default' }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -21,7 +21,7 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
-- Bilinear Gaussian blur filter as detailed here: http://rastergrid.com/blog/2010/09/efficient-gaussian-blur-with-linear-sampling/
|
||||
-- Produces near identical results to a standard Gaussian blur by using sub-pixel sampling,
|
||||
@@ -39,11 +39,11 @@ local function build_shader(taps, offset, offset_type, sigma)
|
||||
local g_offsets = {}
|
||||
local g_weights = {}
|
||||
for i = 1, steps, 1 do
|
||||
g_offsets[i] = offset * (i - 1)
|
||||
g_offsets[i] = offset * (i - 1)
|
||||
|
||||
-- We don't need to include the constant part of the gaussian function as we normalize later.
|
||||
-- 1 / math.sqrt(2 * sigma ^ math.pi) * math.exp(-0.5 * ((offset - 0) / sigma) ^ 2 )
|
||||
g_weights[i] = math.exp(-0.5 * (g_offsets[i] - 0) ^ 2 * 1 / sigma ^ 2 )
|
||||
g_weights[i] = math.exp(-0.5 * (g_offsets[i] - 0) ^ 2 * 1 / sigma ^ 2)
|
||||
end
|
||||
|
||||
-- Calculate offsets and weights for sub-pixel samples.
|
||||
@@ -58,17 +58,17 @@ local function build_shader(taps, offset, offset_type, sigma)
|
||||
weights[#weights + 1] = weight
|
||||
end
|
||||
|
||||
local code = {[[
|
||||
local code = { [[
|
||||
extern vec2 direction;
|
||||
vec4 effect(vec4 color, Image tex, vec2 tc, vec2 sc) {]]}
|
||||
vec4 effect(vec4 color, Image tex, vec2 tc, vec2 sc) {]] }
|
||||
|
||||
local norm = 0
|
||||
if #g_weights % 2 == 0 then
|
||||
code[#code+1] = 'vec4 c = vec4( 0.0 );'
|
||||
code[#code + 1] = 'vec4 c = vec4( 0.0 );'
|
||||
else
|
||||
local weight = g_weights[1]
|
||||
norm = norm + weight
|
||||
code[#code+1] = ('vec4 c = %f * texture2D(tex, tc);'):format(weight)
|
||||
code[#code + 1] = ('vec4 c = %f * texture2D(tex, tc);'):format(weight)
|
||||
end
|
||||
|
||||
local tmpl = 'c += %f * ( texture2D(tex, tc + %f * direction)+ texture2D(tex, tc - %f * direction));\n'
|
||||
@@ -76,9 +76,9 @@ local function build_shader(taps, offset, offset_type, sigma)
|
||||
local offset = offsets[i]
|
||||
local weight = weights[i]
|
||||
norm = norm + weight * 2
|
||||
code[#code+1] = tmpl:format(weight, offset, offset)
|
||||
code[#code + 1] = tmpl:format(weight, offset, offset)
|
||||
end
|
||||
code[#code+1] = ('return c * vec4(%f) * color; }'):format(1 / norm)
|
||||
code[#code + 1] = ('return c * vec4(%f) * color; }'):format(1 / norm)
|
||||
|
||||
local shader = table.concat(code)
|
||||
return love.graphics.newShader(shader)
|
||||
@@ -89,10 +89,10 @@ return function(moonshine)
|
||||
local shader = build_shader(taps, offset, offset_type, sigma)
|
||||
|
||||
local function draw(buffer)
|
||||
shader:send('direction', {1 / love.graphics.getWidth(), 0})
|
||||
shader:send('direction', { 1 / love.graphics.getWidth(), 0 })
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
|
||||
shader:send('direction', {0, 1 / love.graphics.getHeight()})
|
||||
shader:send('direction', { 0, 1 / love.graphics.getHeight() })
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
end
|
||||
|
||||
@@ -102,7 +102,7 @@ return function(moonshine)
|
||||
-- More taps = larger blur, but slower.
|
||||
setters.taps = function(v)
|
||||
assert(tonumber(v) >= 3, "Invalid value for `taps': Must be >= 3")
|
||||
assert(tonumber(v)%2 == 1, "Invalid value for `taps': Must be odd")
|
||||
assert(tonumber(v) % 2 == 1, "Invalid value for `taps': Must be odd")
|
||||
taps = tonumber(v)
|
||||
shader = build_shader(taps, offset, offset_type, sigma)
|
||||
end
|
||||
@@ -110,7 +110,7 @@ return function(moonshine)
|
||||
-- Offset of each tap.
|
||||
-- For highest quality this should be <=1 but if the image has low entropy we
|
||||
-- can approximate the blur with a number > 1 and less taps, for better performance.
|
||||
setters.offset = function(v)
|
||||
setters.offset = function(v)
|
||||
offset = tonumber(v) or 0
|
||||
shader = build_shader(taps, offset, offset_type, sigma)
|
||||
end
|
||||
@@ -125,13 +125,13 @@ return function(moonshine)
|
||||
end
|
||||
|
||||
-- Sigma value for gaussian distribution. You don't normally need to set this.
|
||||
setters.sigma = function(v)
|
||||
setters.sigma = function(v)
|
||||
sigma = tonumber(v) or -1
|
||||
shader = build_shader(taps, offset, offset_type, sigma)
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "fastgaussianblur",
|
||||
return moonshine.Effect {
|
||||
name = 'fastgaussianblur',
|
||||
draw = draw,
|
||||
setters = setters,
|
||||
-- no defaults here, as we dont want the shader to be built 3 times on startup
|
||||
|
||||
@@ -13,17 +13,17 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local noisetex = love.image.newImageData(256,256)
|
||||
local noisetex = love.image.newImageData(256, 256)
|
||||
noisetex:mapPixel(function()
|
||||
local l = love.math.random() * 255
|
||||
return l,l,l,l
|
||||
return l, l, l, l
|
||||
end)
|
||||
noisetex = love.graphics.newImage(noisetex)
|
||||
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern number opacity;
|
||||
extern number size;
|
||||
extern vec2 noise;
|
||||
@@ -38,24 +38,24 @@ return function(moonshine)
|
||||
return color * Texel(texture, tc) * mix(1.0, rand(tc+vec2(noise)), opacity);
|
||||
}]]
|
||||
|
||||
shader:send("noisetex", noisetex)
|
||||
shader:send("tex_ratio", {love.graphics.getWidth() / noisetex:getWidth(),
|
||||
love.graphics.getHeight() / noisetex:getHeight()})
|
||||
shader:send('noisetex', noisetex)
|
||||
shader:send('tex_ratio', { love.graphics.getWidth() / noisetex:getWidth(),
|
||||
love.graphics.getHeight() / noisetex:getHeight() })
|
||||
|
||||
local setters = {}
|
||||
for _,k in ipairs{"opacity", "size"} do
|
||||
for _, k in ipairs { 'opacity', 'size' } do
|
||||
setters[k] = function(v) shader:send(k, math.max(0, tonumber(v) or 0)) end
|
||||
end
|
||||
|
||||
local defaults = {opacity = .3, size = 1}
|
||||
local defaults = { opacity = .3, size = 1 }
|
||||
|
||||
local draw = function(buffer)
|
||||
shader:send("noise", {love.math.random(), love.math.random()})
|
||||
shader:send('noise', { love.math.random(), love.math.random() })
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "filmgrain",
|
||||
return moonshine.Effect {
|
||||
name = 'filmgrain',
|
||||
draw = draw,
|
||||
setters = setters,
|
||||
defaults = defaults
|
||||
|
||||
@@ -3,7 +3,7 @@ Animated 2D Fog (procedural)
|
||||
Originally for Godot Engine by Gonkee https://www.youtube.com/watch?v=QEaTsz_0o44&t=6s
|
||||
|
||||
Translated for löve by Brandon Blanker Lim-it @flamendless
|
||||
]]--
|
||||
]] --
|
||||
|
||||
--[[
|
||||
SAMPLE USAGE:
|
||||
@@ -43,7 +43,7 @@ return function(moonshine)
|
||||
local speed
|
||||
local time
|
||||
|
||||
local shader = love.graphics.newShader([[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec3 fog_color = vec3(0.35, 0.48, 0.95);
|
||||
extern int octaves = 4;
|
||||
extern vec2 speed = vec2(0.0, 1.0);
|
||||
@@ -86,44 +86,44 @@ return function(moonshine)
|
||||
float final = fbm(coord + motion);
|
||||
return vec4(fog_color, final * 0.5);
|
||||
}
|
||||
]])
|
||||
]]
|
||||
|
||||
local setters = {}
|
||||
|
||||
setters.fog_color = function(t)
|
||||
assert(type(t) == "table", "Passed argument to fog_color must be a table containing 3 color values")
|
||||
assert(type(t) == 'table', 'Passed argument to fog_color must be a table containing 3 color values')
|
||||
fog_color = t
|
||||
shader:send("fog_color", fog_color)
|
||||
shader:send('fog_color', fog_color)
|
||||
end
|
||||
|
||||
setters.octaves = function(i)
|
||||
assert(type(i) == "number", "Passed argument to octaves must be an integer")
|
||||
assert(type(i) == 'number', 'Passed argument to octaves must be an integer')
|
||||
octaves = i
|
||||
shader:send("octaves", octaves)
|
||||
shader:send('octaves', octaves)
|
||||
end
|
||||
|
||||
setters.speed = function(t)
|
||||
assert(type(t) == "table", "Passed argument to speed must be a table containing 2 values")
|
||||
assert(type(t) == 'table', 'Passed argument to speed must be a table containing 2 values')
|
||||
speed = t
|
||||
shader:send("speed", speed)
|
||||
shader:send('speed', speed)
|
||||
end
|
||||
|
||||
setters.time = function(n)
|
||||
assert(type(n) == "number", "Passed argument to time must be a number")
|
||||
assert(type(n) == 'number', 'Passed argument to time must be a number')
|
||||
time = n
|
||||
shader:send("time", time)
|
||||
shader:send('time', time)
|
||||
end
|
||||
|
||||
local defaults = {
|
||||
fog_color = {0.35, 0.48, 0.95},
|
||||
fog_color = { 0.35, 0.48, 0.95 },
|
||||
octaves = 4,
|
||||
speed = {0.5, 0.5},
|
||||
speed = { 0.5, 0.5 },
|
||||
}
|
||||
|
||||
return moonshine.Effect({
|
||||
name = "fog",
|
||||
return moonshine.Effect {
|
||||
name = 'fog',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = defaults,
|
||||
})
|
||||
}
|
||||
end
|
||||
|
||||
@@ -6,26 +6,26 @@ Copyright (C) 2017 by Matthias Richter <vrld@vrld.org>
|
||||
Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
local function resetShader(sigma)
|
||||
local support = math.max(1, math.floor(3*sigma + .5))
|
||||
local support = math.max(1, math.floor(3 * sigma + .5))
|
||||
local one_by_sigma_sq = sigma > 0 and 1 / (sigma * sigma) or 1
|
||||
local norm = 0
|
||||
|
||||
local code = {[[
|
||||
local code = { [[
|
||||
extern vec2 direction;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _)
|
||||
{ vec4 c = vec4(0.0);
|
||||
]]}
|
||||
local blur_line = "c += vec4(%f) * Texel(texture, tc + vec2(%f) * direction);"
|
||||
]] }
|
||||
local blur_line = 'c += vec4(%f) * Texel(texture, tc + vec2(%f) * direction);'
|
||||
|
||||
for i = -support,support do
|
||||
local coeff = math.exp(-.5 * i*i * one_by_sigma_sq)
|
||||
for i = -support, support do
|
||||
local coeff = math.exp(-.5 * i * i * one_by_sigma_sq)
|
||||
norm = norm + coeff
|
||||
code[#code+1] = blur_line:format(coeff, i)
|
||||
code[#code + 1] = blur_line:format(coeff, i)
|
||||
end
|
||||
|
||||
code[#code+1] = ("return c * vec4(%f) * color;}"):format(norm > 0 and 1/norm or 1)
|
||||
code[#code + 1] = ('return c * vec4(%f) * color;}'):format(norm > 0 and 1 / norm or 1)
|
||||
|
||||
return love.graphics.newShader(table.concat(code))
|
||||
end
|
||||
@@ -35,21 +35,21 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
setters.sigma = function(v)
|
||||
shader = resetShader(math.max(0,tonumber(v) or 1))
|
||||
shader = resetShader(math.max(0, tonumber(v) or 1))
|
||||
end
|
||||
|
||||
local draw = function(buffer)
|
||||
shader:send('direction', {1 / love.graphics.getWidth(), 0})
|
||||
shader:send('direction', { 1 / love.graphics.getWidth(), 0 })
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
|
||||
shader:send('direction', {0, 1 / love.graphics.getHeight()})
|
||||
shader:send('direction', { 0, 1 / love.graphics.getHeight() })
|
||||
moonshine.draw_shader(buffer, shader)
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "gaussianblur",
|
||||
return moonshine.Effect {
|
||||
name = 'gaussianblur',
|
||||
draw = draw,
|
||||
setters = setters,
|
||||
defaults = {sigma = 1},
|
||||
defaults = { sigma = 1 },
|
||||
}
|
||||
end
|
||||
|
||||
@@ -13,36 +13,36 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
|
||||
-- unroll convolution loop for gaussian blur shader
|
||||
local function make_blur_shader(sigma)
|
||||
local support = math.max(1, math.floor(3*sigma + .5))
|
||||
local support = math.max(1, math.floor(3 * sigma + .5))
|
||||
local one_by_sigma_sq = sigma > 0 and 1 / (sigma * sigma) or 1
|
||||
local norm = 0
|
||||
|
||||
local code = {[[
|
||||
local code = { [[
|
||||
extern vec2 direction;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _) {
|
||||
vec4 c = vec4(0.0);
|
||||
]]}
|
||||
local blur_line = "c += vec4(%f) * Texel(texture, tc + vec2(%f) * direction);"
|
||||
]] }
|
||||
local blur_line = 'c += vec4(%f) * Texel(texture, tc + vec2(%f) * direction);'
|
||||
|
||||
for i = -support,support do
|
||||
local coeff = math.exp(-.5 * i*i * one_by_sigma_sq)
|
||||
for i = -support, support do
|
||||
local coeff = math.exp(-.5 * i * i * one_by_sigma_sq)
|
||||
norm = norm + coeff
|
||||
code[#code+1] = blur_line:format(coeff, i)
|
||||
code[#code + 1] = blur_line:format(coeff, i)
|
||||
end
|
||||
|
||||
code[#code+1] = ("return c * vec4(%f) * color;}"):format(1 / norm)
|
||||
code[#code + 1] = ('return c * vec4(%f) * color;}'):format(1 / norm)
|
||||
|
||||
return love.graphics.newShader(table.concat(code))
|
||||
end
|
||||
|
||||
return function(moonshine)
|
||||
local blurshader -- set in setters.glow_strength
|
||||
local threshold = love.graphics.newShader[[
|
||||
local threshold = love.graphics.newShader [[
|
||||
extern number min_luma;
|
||||
vec4 effect(vec4 color, Image texture, vec2 tc, vec2 _) {
|
||||
vec4 c = Texel(texture, tc);
|
||||
@@ -52,10 +52,10 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
setters.strength = function(v)
|
||||
blurshader = make_blur_shader(math.max(0,tonumber(v) or 1))
|
||||
blurshader = make_blur_shader(math.max(0, tonumber(v) or 1))
|
||||
end
|
||||
setters.min_luma = function(v)
|
||||
threshold:send("min_luma", math.max(0, math.min(1, tonumber(v) or 0.5)))
|
||||
threshold:send('min_luma', math.max(0, math.min(1, tonumber(v) or 0.5)))
|
||||
end
|
||||
|
||||
local scene = love.graphics.newCanvas()
|
||||
@@ -70,7 +70,7 @@ return function(moonshine)
|
||||
love.graphics.draw(scene)
|
||||
|
||||
-- 2nd pass: apply blur shader in x
|
||||
blurshader:send('direction', {1 / love.graphics.getWidth(), 0})
|
||||
blurshader:send('direction', { 1 / love.graphics.getWidth(), 0 })
|
||||
love.graphics.setCanvas(back)
|
||||
love.graphics.clear()
|
||||
love.graphics.setShader(blurshader)
|
||||
@@ -82,23 +82,23 @@ return function(moonshine)
|
||||
|
||||
-- original scene without blur shader
|
||||
love.graphics.setShader()
|
||||
love.graphics.setBlendMode("add", "premultiplied")
|
||||
love.graphics.setBlendMode('add', 'premultiplied')
|
||||
love.graphics.draw(scene) -- original scene
|
||||
|
||||
-- second pass of light blurring
|
||||
blurshader:send('direction', {0, 1 / love.graphics.getHeight()})
|
||||
blurshader:send('direction', { 0, 1 / love.graphics.getHeight() })
|
||||
love.graphics.setShader(blurshader)
|
||||
love.graphics.draw(back)
|
||||
|
||||
-- restore things as they were before entering draw()
|
||||
love.graphics.setBlendMode("alpha", "premultiplied")
|
||||
love.graphics.setBlendMode('alpha', 'premultiplied')
|
||||
scene = back
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "glow",
|
||||
return moonshine.Effect {
|
||||
name = 'glow',
|
||||
draw = draw,
|
||||
setters = setters,
|
||||
defaults = {min_luma=.7, strength = 5}
|
||||
defaults = { min_luma = .7, strength = 5 }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -34,10 +34,10 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern number exposure;
|
||||
extern number decay;
|
||||
extern number density;
|
||||
@@ -64,29 +64,29 @@ return function(moonshine)
|
||||
|
||||
local setters, light_position = {}
|
||||
|
||||
for _,k in ipairs{"exposure", "decay", "density", "weight"} do
|
||||
for _, k in ipairs { 'exposure', 'decay', 'density', 'weight' } do
|
||||
setters[k] = function(v)
|
||||
shader:send(k, math.min(1, math.max(0, tonumber(v) or 0)))
|
||||
end
|
||||
end
|
||||
|
||||
setters.light_position = function(v)
|
||||
light_position = {unpack(v)}
|
||||
shader:send("light_position", v)
|
||||
light_position = { unpack(v) }
|
||||
shader:send('light_position', v)
|
||||
end
|
||||
|
||||
setters.light_x = function(v)
|
||||
assert(type(v) == "number", "Invalid value for `light_x'")
|
||||
setters.light_position{v, light_position[2]}
|
||||
assert(type(v) == 'number', "Invalid value for `light_x'")
|
||||
setters.light_position { v, light_position[2] }
|
||||
end
|
||||
|
||||
setters.light_y = function(v)
|
||||
assert(type(v) == "number", "Invalid value for `light_y'")
|
||||
setters.light_position{light_position[1], v}
|
||||
assert(type(v) == 'number', "Invalid value for `light_y'")
|
||||
setters.light_position { light_position[1], v }
|
||||
end
|
||||
|
||||
setters.samples = function(v)
|
||||
shader:send("samples", math.max(1,tonumber(v) or 1))
|
||||
shader:send('samples', math.max(1, tonumber(v) or 1))
|
||||
end
|
||||
|
||||
local defaults = {
|
||||
@@ -94,12 +94,12 @@ return function(moonshine)
|
||||
decay = 0.95,
|
||||
density = 0.15,
|
||||
weight = 0.5,
|
||||
light_position = {0.5,0.5},
|
||||
light_position = { 0.5, 0.5 },
|
||||
samples = 70
|
||||
}
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "godsray",
|
||||
return moonshine.Effect {
|
||||
name = 'godsray',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = defaults
|
||||
|
||||
@@ -20,7 +20,7 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
local BASE = ...
|
||||
|
||||
@@ -36,14 +36,14 @@ moonshine.draw_shader = function(buffer, shader)
|
||||
love.graphics.draw(back)
|
||||
end
|
||||
|
||||
moonshine.chain = function(w,h,effect)
|
||||
moonshine.chain = function(w, h, effect)
|
||||
-- called as moonshine.chain(effect)'
|
||||
if h == nil then
|
||||
effect, w,h = w, love.window.getMode()
|
||||
effect, w, h = w, love.window.getMode()
|
||||
end
|
||||
assert(effect ~= nil, "No effect")
|
||||
assert(effect ~= nil, 'No effect')
|
||||
|
||||
local front, back = love.graphics.newCanvas(w,h), love.graphics.newCanvas(w,h)
|
||||
local front, back = love.graphics.newCanvas(w, h), love.graphics.newCanvas(w, h)
|
||||
local buffer = function()
|
||||
back, front = front, back
|
||||
return front, back
|
||||
@@ -52,7 +52,7 @@ moonshine.chain = function(w,h,effect)
|
||||
local disabled = {} -- set of disabled effects
|
||||
local chain = {}
|
||||
chain.resize = function(w, h)
|
||||
front, back = love.graphics.newCanvas(w,h), love.graphics.newCanvas(w,h)
|
||||
front, back = love.graphics.newCanvas(w, h), love.graphics.newCanvas(w, h)
|
||||
return chain
|
||||
end
|
||||
|
||||
@@ -72,8 +72,8 @@ moonshine.chain = function(w,h,effect)
|
||||
|
||||
-- process all shaders
|
||||
love.graphics.setColor(fg_r, fg_g, fg_b, fg_a)
|
||||
love.graphics.setBlendMode("alpha", "premultiplied")
|
||||
for _,e in ipairs(chain) do
|
||||
love.graphics.setBlendMode('alpha', 'premultiplied')
|
||||
for _, e in ipairs(chain) do
|
||||
if not disabled[e.name] then
|
||||
(e.draw or moonshine.draw_shader)(buffer, e.shader)
|
||||
end
|
||||
@@ -82,7 +82,7 @@ moonshine.chain = function(w,h,effect)
|
||||
-- present result
|
||||
love.graphics.setShader()
|
||||
love.graphics.setCanvas(canvas)
|
||||
love.graphics.draw(front,0,0)
|
||||
love.graphics.draw(front, 0, 0)
|
||||
|
||||
-- restore state
|
||||
love.graphics.setBlendMode(blendmode)
|
||||
@@ -90,7 +90,7 @@ moonshine.chain = function(w,h,effect)
|
||||
end
|
||||
|
||||
chain.next = function(e)
|
||||
if type(e) == "function" then
|
||||
if type(e) == 'function' then
|
||||
e = e()
|
||||
end
|
||||
assert(e.name, "Invalid effect: must provide `name'.")
|
||||
@@ -116,16 +116,16 @@ moonshine.chain = function(w,h,effect)
|
||||
|
||||
setmetatable(chain, {
|
||||
__call = function(_, ...) return chain.draw(...) end,
|
||||
__index = function(_,k)
|
||||
__index = function(_, k)
|
||||
for _, e in ipairs(chain) do
|
||||
if e.name == k then return e end
|
||||
end
|
||||
error(("Effect `%s' not in chain"):format(k), 2)
|
||||
end,
|
||||
__newindex = function(_, k, v)
|
||||
if k == "parameters" or k == "params" or k == "settings" then
|
||||
for e,par in pairs(v) do
|
||||
for k,v in pairs(par) do
|
||||
if k == 'parameters' or k == 'params' or k == 'settings' then
|
||||
for e, par in pairs(v) do
|
||||
for k, v in pairs(par) do
|
||||
chain[e][k] = v
|
||||
end
|
||||
end
|
||||
@@ -140,32 +140,35 @@ end
|
||||
|
||||
moonshine.Effect = function(e)
|
||||
-- set defaults
|
||||
for k,v in pairs(e.defaults or {}) do
|
||||
for k, v in pairs(e.defaults or {}) do
|
||||
assert(e.setters[k], ("No setter for parameter `%s'"):format(k))(v, k)
|
||||
e.setters[k](v,k)
|
||||
e.setters[k](v, k)
|
||||
end
|
||||
|
||||
-- expose setters
|
||||
return setmetatable(e, {
|
||||
__newindex = function(self,k,v)
|
||||
__newindex = function(self, k, v)
|
||||
assert(self.setters[k], ("Unknown property: `%s.%s'"):format(e.name, k))
|
||||
self.setters[k](v, k)
|
||||
end})
|
||||
end
|
||||
})
|
||||
end
|
||||
|
||||
-- autoloading effects
|
||||
moonshine.effects = setmetatable({}, {__index = function(self, key)
|
||||
local ok, effect = pcall(require, BASE .. "." .. key)
|
||||
if not ok then
|
||||
error("No such effect: "..key, 2)
|
||||
moonshine.effects = setmetatable({}, {
|
||||
__index = function(self, key)
|
||||
local ok, effect = pcall(require, BASE .. '.' .. key)
|
||||
if not ok then
|
||||
error('No such effect: ' .. key, 2)
|
||||
end
|
||||
|
||||
-- expose moonshine to effect
|
||||
local con = function(...) return effect(moonshine, ...) end
|
||||
|
||||
-- cache effect constructor
|
||||
self[key] = con
|
||||
return con
|
||||
end
|
||||
})
|
||||
|
||||
-- expose moonshine to effect
|
||||
local con = function(...) return effect(moonshine, ...) end
|
||||
|
||||
-- cache effect constructor
|
||||
self[key] = con
|
||||
return con
|
||||
end})
|
||||
|
||||
return setmetatable(moonshine, {__call = function(_, ...) return moonshine.chain(...) end})
|
||||
return setmetatable(moonshine, { __call = function(_, ...) return moonshine.chain(...) end })
|
||||
|
||||
@@ -13,10 +13,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern vec2 size;
|
||||
extern number feedback;
|
||||
vec4 effect(vec4 color, Image tex, vec2 tc, vec2 _)
|
||||
@@ -38,18 +38,18 @@ return function(moonshine)
|
||||
|
||||
local setters = {}
|
||||
setters.size = function(v)
|
||||
if type(v) == "number" then v = {v,v} end
|
||||
assert(type(v) == "table" and #v == 2, "Invalid value for `size'")
|
||||
shader:send("size", v)
|
||||
if type(v) == 'number' then v = { v, v } end
|
||||
assert(type(v) == 'table' and #v == 2, "Invalid value for `size'")
|
||||
shader:send('size', v)
|
||||
end
|
||||
setters.feedback = function(v)
|
||||
shader:send("feedback", math.min(1, math.max(0, tonumber(v) or 0)))
|
||||
shader:send('feedback', math.min(1, math.max(0, tonumber(v) or 0)))
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "pixelate",
|
||||
return moonshine.Effect {
|
||||
name = 'pixelate',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = {size = {5,5}, feedback = 0}
|
||||
defaults = { size = { 5, 5 }, feedback = 0 }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -16,10 +16,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern number num_bands;
|
||||
vec3 rgb2hsv(vec3 c)
|
||||
{
|
||||
@@ -46,14 +46,14 @@ return function(moonshine)
|
||||
return vec4(hsv2rgb(hsv), color.a);
|
||||
}]]
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "posterize",
|
||||
return moonshine.Effect {
|
||||
name = 'posterize',
|
||||
shader = shader,
|
||||
setters = {
|
||||
num_bands = function(v)
|
||||
shader:send("num_bands", math.max(1, tonumber(v) or 1))
|
||||
shader:send('num_bands', math.max(1, tonumber(v) or 1))
|
||||
end
|
||||
},
|
||||
defaults = {num_bands = 3}
|
||||
defaults = { num_bands = 3 }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -13,10 +13,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern number width;
|
||||
extern number phase;
|
||||
extern number thickness;
|
||||
@@ -36,36 +36,36 @@ return function(moonshine)
|
||||
phase = 0,
|
||||
thickness = 1,
|
||||
opacity = 1,
|
||||
color = {0,0,0},
|
||||
color = { 0, 0, 0 },
|
||||
}
|
||||
|
||||
local setters = {}
|
||||
setters.width = function(v)
|
||||
shader:send("width", tonumber(v) or defaults.width)
|
||||
shader:send('width', tonumber(v) or defaults.width)
|
||||
end
|
||||
setters.frequency = function(v)
|
||||
shader:send("width", love.graphics.getHeight()/(tonumber(v) or love.graphics.getHeight()))
|
||||
shader:send('width', love.graphics.getHeight() / (tonumber(v) or love.graphics.getHeight()))
|
||||
end
|
||||
setters.phase = function(v)
|
||||
shader:send("phase", tonumber(v) or defaults.phase)
|
||||
shader:send('phase', tonumber(v) or defaults.phase)
|
||||
end
|
||||
setters.thickness = function(v)
|
||||
shader:send("thickness", math.max(0, tonumber(v) or defaults.thickness))
|
||||
shader:send('thickness', math.max(0, tonumber(v) or defaults.thickness))
|
||||
end
|
||||
setters.opacity = function(v)
|
||||
shader:send("opacity", math.min(1, math.max(0, tonumber(v) or defaults.opacity)))
|
||||
shader:send('opacity', math.min(1, math.max(0, tonumber(v) or defaults.opacity)))
|
||||
end
|
||||
setters.color = function(c)
|
||||
assert(type(c) == "table" and #c == 3, "Invalid value for `color'")
|
||||
shader:send("color", {
|
||||
assert(type(c) == 'table' and #c == 3, "Invalid value for `color'")
|
||||
shader:send('color', {
|
||||
(tonumber(c[1]) or defaults.color[0]) / 255,
|
||||
(tonumber(c[2]) or defaults.color[1]) / 255,
|
||||
(tonumber(c[3]) or defaults.color[2]) / 255
|
||||
})
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "scanlines",
|
||||
return moonshine.Effect {
|
||||
name = 'scanlines',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = defaults,
|
||||
|
||||
@@ -21,18 +21,18 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local noisetex = love.image.newImageData(256,256)
|
||||
local noisetex = love.image.newImageData(256, 256)
|
||||
noisetex:mapPixel(function()
|
||||
return love.math.random() * 255,love.math.random() * 255, 0, 0
|
||||
return love.math.random() * 255, love.math.random() * 255, 0, 0
|
||||
end)
|
||||
noisetex = love.graphics.newImage(noisetex)
|
||||
noisetex:setWrap ("repeat", "repeat")
|
||||
noisetex:setFilter("nearest", "nearest")
|
||||
noisetex:setWrap('repeat', 'repeat')
|
||||
noisetex:setFilter('nearest', 'nearest')
|
||||
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern Image noisetex;
|
||||
extern number amp;
|
||||
extern vec2 center;
|
||||
@@ -44,21 +44,21 @@ return function(moonshine)
|
||||
return Texel(texture, tc);
|
||||
}]]
|
||||
|
||||
shader:send("noisetex", noisetex)
|
||||
shader:send('noisetex', noisetex)
|
||||
|
||||
local setters = {}
|
||||
setters.amp = function(v)
|
||||
shader:send("amp", math.max(0, tonumber(v) or 0))
|
||||
shader:send('amp', math.max(0, tonumber(v) or 0))
|
||||
end
|
||||
setters.center = function(v)
|
||||
assert(type(v) == "table" and #v == 2, "Invalid value for `center'")
|
||||
shader:send("center", v)
|
||||
assert(type(v) == 'table' and #v == 2, "Invalid value for `center'")
|
||||
shader:send('center', v)
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "sketch",
|
||||
return moonshine.Effect {
|
||||
name = 'sketch',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = {amp = .0007, center = {0,0}}
|
||||
defaults = { amp = .0007, center = { 0, 0 } }
|
||||
}
|
||||
end
|
||||
|
||||
@@ -13,10 +13,10 @@ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
PERFORMANCE OF THIS SOFTWARE.
|
||||
]]--
|
||||
]] --
|
||||
|
||||
return function(moonshine)
|
||||
local shader = love.graphics.newShader[[
|
||||
local shader = love.graphics.newShader [[
|
||||
extern number radius;
|
||||
extern number softness;
|
||||
extern number opacity;
|
||||
@@ -32,12 +32,12 @@ return function(moonshine)
|
||||
}]]
|
||||
|
||||
local setters = {}
|
||||
for _,k in ipairs{"radius", "softness", "opacity"} do
|
||||
for _, k in ipairs { 'radius', 'softness', 'opacity' } do
|
||||
setters[k] = function(v) shader:send(k, math.max(0, tonumber(v) or 0)) end
|
||||
end
|
||||
setters.color = function(c)
|
||||
assert(type(c) == "table" and #c == 3, "Invalid value for `color'")
|
||||
shader:send("color", {
|
||||
assert(type(c) == 'table' and #c == 3, "Invalid value for `color'")
|
||||
shader:send('color', {
|
||||
(tonumber(c[1]) or 0) / 255,
|
||||
(tonumber(c[2]) or 0) / 255,
|
||||
(tonumber(c[3]) or 0) / 255,
|
||||
@@ -45,15 +45,15 @@ return function(moonshine)
|
||||
})
|
||||
end
|
||||
|
||||
return moonshine.Effect{
|
||||
name = "vignette",
|
||||
return moonshine.Effect {
|
||||
name = 'vignette',
|
||||
shader = shader,
|
||||
setters = setters,
|
||||
defaults = {
|
||||
radius = .8,
|
||||
softness = .5,
|
||||
opacity = .5,
|
||||
color = {0,0,0}
|
||||
color = { 0, 0, 0 }
|
||||
}
|
||||
}
|
||||
end
|
||||
|
||||
@@ -84,7 +84,7 @@ rs.game_zone = {
|
||||
--- })
|
||||
--- ```
|
||||
--- @param options table?
|
||||
rs.conf = function (options)
|
||||
rs.conf = function(options)
|
||||
-- Sanitize.
|
||||
if type(options) == 'nil' then
|
||||
options = {}
|
||||
@@ -163,7 +163,7 @@ end
|
||||
--- rs.pop()
|
||||
--- end
|
||||
--- ```
|
||||
rs.push = function ()
|
||||
rs.push = function()
|
||||
love.graphics.push()
|
||||
love.graphics.origin()
|
||||
love.graphics.translate(rs.x_offset, rs.y_offset)
|
||||
@@ -198,7 +198,7 @@ end
|
||||
--- rs.pop()
|
||||
--- end
|
||||
--- ```
|
||||
rs.pop = function ()
|
||||
rs.pop = function()
|
||||
love.graphics.pop()
|
||||
end
|
||||
|
||||
@@ -225,7 +225,7 @@ end
|
||||
--- ```
|
||||
--- @param window_width number?
|
||||
--- @param window_height number?
|
||||
rs.resize = function (window_width, window_height)
|
||||
rs.resize = function(window_width, window_height)
|
||||
-- Sanitize.
|
||||
-- Window width.
|
||||
if type(window_width) == 'nil' then
|
||||
@@ -323,7 +323,7 @@ end
|
||||
--- rs.pop()
|
||||
--- end
|
||||
--- ```
|
||||
rs.resize_callback = function () end
|
||||
rs.resize_callback = function() end
|
||||
|
||||
--- This is a function to help you debug. It shows information about the library states. You can
|
||||
--- display these states on the screen to help you troubleshoot. Calling rs.debug_info() without
|
||||
@@ -342,7 +342,7 @@ rs.resize_callback = function () end
|
||||
--- - rs.y_offset
|
||||
--- @param debug_x number? If you pass nothing or nil, then it will same as if you pass 0.
|
||||
--- @param debug_y number? If you pass nothing or nil, then it will same as if you pass 0.
|
||||
rs.debug_info = function (debug_x, debug_y)
|
||||
rs.debug_info = function(debug_x, debug_y)
|
||||
-- Set width and height for debug "window".
|
||||
local debug_width, debug_height = 215, 120
|
||||
|
||||
@@ -408,7 +408,7 @@ end
|
||||
--- @return number game_zone.y
|
||||
--- @return number game_zone.w
|
||||
--- @return number game_zone.h
|
||||
rs.get_game_zone = function ()
|
||||
rs.get_game_zone = function()
|
||||
local game_zone = rs.game_zone
|
||||
return game_zone.x, game_zone.y, game_zone.w, game_zone.h
|
||||
end
|
||||
@@ -423,7 +423,7 @@ end
|
||||
--- ```
|
||||
--- @return number rs.game_width
|
||||
--- @return number rs.game_height
|
||||
rs.get_game_size = function ()
|
||||
rs.get_game_size = function()
|
||||
return rs.game_width, rs.game_height
|
||||
end
|
||||
|
||||
@@ -488,7 +488,7 @@ end
|
||||
--- ```
|
||||
--- @param it_x number
|
||||
--- @param it_y number
|
||||
rs.is_it_inside = function (it_x, it_y)
|
||||
rs.is_it_inside = function(it_x, it_y)
|
||||
-- Input sanitizing.
|
||||
if type(it_x) ~= 'number' then
|
||||
error('.is_it_inside: Argument #1 should be number. You passed: ' .. type(it_x) .. '.', 2)
|
||||
@@ -527,7 +527,7 @@ end
|
||||
--- ```
|
||||
--- @return number rs.scale_width
|
||||
--- @return number rs.scale_height
|
||||
rs.get_both_scales = function ()
|
||||
rs.get_both_scales = function()
|
||||
return rs.scale_width, rs.scale_height
|
||||
end
|
||||
|
||||
@@ -574,7 +574,7 @@ end
|
||||
--- @param y number
|
||||
--- @return number|nil ScaledGameX
|
||||
--- @return number|nil ScaledGameY
|
||||
rs.to_game = function (x, y)
|
||||
rs.to_game = function(x, y)
|
||||
-- User passed only x.
|
||||
if type(x) == 'number' and type(y) == 'nil' then
|
||||
return (x - rs.x_offset) / rs.scale_width
|
||||
@@ -647,7 +647,7 @@ end
|
||||
--- @param y number
|
||||
--- @return number|nil ScaledWindowX
|
||||
--- @return number|nil ScaledWindowY
|
||||
rs.to_window = function (x, y)
|
||||
rs.to_window = function(x, y)
|
||||
-- User passed only X.
|
||||
if type(x) == 'number' and type(y) == 'nil' then
|
||||
return (x * rs.scale_width) + rs.x_offset
|
||||
@@ -693,7 +693,7 @@ end
|
||||
--- @param width number
|
||||
--- @param height number
|
||||
--- @param flags table
|
||||
rs.setMode = function (width, height, flags)
|
||||
rs.setMode = function(width, height, flags)
|
||||
local okay, errorMessage = pcall(love.window.setMode, width, height, flags)
|
||||
if not okay then
|
||||
error('.setMode: Error: ' .. errorMessage, 2)
|
||||
@@ -732,7 +732,7 @@ end
|
||||
--- @param width number
|
||||
--- @param height number
|
||||
--- @param flags table
|
||||
rs.updateMode = function (width, height, flags)
|
||||
rs.updateMode = function(width, height, flags)
|
||||
local okay, errorMessage = pcall(love.window.updateMode, width, height, flags)
|
||||
if not okay then
|
||||
error('.updateMode: Error: ' .. errorMessage, 2)
|
||||
|
||||
@@ -25,8 +25,8 @@ THE SOFTWARE.
|
||||
]] --
|
||||
|
||||
local Registry = {}
|
||||
Registry.__index = function (self, key)
|
||||
return Registry[key] or (function ()
|
||||
Registry.__index = function(self, key)
|
||||
return Registry[key] or (function()
|
||||
local t = {}
|
||||
rawset(self, key, t)
|
||||
return t
|
||||
@@ -95,7 +95,7 @@ local default = Registry.new()
|
||||
local module = {}
|
||||
for k in pairs(Registry) do
|
||||
if k ~= '__index' then
|
||||
module[k] = function (...) return default[k](default, ...) end
|
||||
module[k] = function(...) return default[k](default, ...) end
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
@@ -84,12 +84,9 @@ function Game.new(core)
|
||||
.chain(moonshine.effects.scanlines)
|
||||
.chain(moonshine.effects.glow)
|
||||
.chain(moonshine.effects.vignette)
|
||||
-- .chain(moonshine.effects.crt)
|
||||
self.effect.filmgrain.size = 2
|
||||
self.effect.chromasep.radius = 4
|
||||
self.effect.scanlines.opacity = 0.95
|
||||
-- self.effect.crt.distortionFactor = { 1.3, 1.306 }
|
||||
-- self.effect.crt.feather = 0.5
|
||||
|
||||
return self
|
||||
end
|
||||
|
||||
@@ -57,10 +57,10 @@ end
|
||||
|
||||
function MainMenu:_createMain(settings, credits)
|
||||
local main = component { column = true, gap = 10 }
|
||||
+ button { text = 'New game', width = 200, onClick = function () self.core:switchState(self.core.states.game) end }
|
||||
+ button { text = 'Settings', width = 200, onClick = function () self:_pushScreen(settings) end }
|
||||
+ button { text = 'Credits', width = 200, onClick = function () self:_pushScreen(credits) end }
|
||||
+ button { text = 'Quit', width = 200, onClick = function () love.event.quit() end }
|
||||
+ button { text = 'New game', width = 200, onClick = function() self.core:switchState(self.core.states.game) end }
|
||||
+ button { text = 'Settings', width = 200, onClick = function() self:_pushScreen(settings) end }
|
||||
+ button { text = 'Credits', width = 200, onClick = function() self:_pushScreen(credits) end }
|
||||
+ button { text = 'Quit', width = 200, onClick = function() love.event.quit() end }
|
||||
main:updatePosition(
|
||||
love.graphics.getWidth() * 0.5 - main.width * 0.5,
|
||||
love.graphics.getHeight() * 0.5 - main.height * 0.5
|
||||
@@ -72,7 +72,7 @@ end
|
||||
function MainMenu:_createSettings()
|
||||
local settings = component { column = true, gap = 10 }
|
||||
+ label { text = 'Settings' }
|
||||
+ button { text = 'Back', width = 200, onClick = function () self:_popScreen() end }
|
||||
+ button { text = 'Back', width = 200, onClick = function() self:_popScreen() end }
|
||||
settings:updatePosition(
|
||||
love.graphics.getWidth() * 0.5 - settings.width * 0.5,
|
||||
love.graphics.getHeight() * 0.5 - settings.height * 0.5
|
||||
@@ -84,7 +84,7 @@ end
|
||||
function MainMenu:_createCredits()
|
||||
local credits = component { column = true, gap = 10 }
|
||||
+ label { text = 'Credits' }
|
||||
+ button { text = 'Back', width = 200, onClick = function () self:_popScreen() end }
|
||||
+ button { text = 'Back', width = 200, onClick = function() self:_popScreen() end }
|
||||
credits:updatePosition(
|
||||
love.graphics.getWidth() * 0.5 - credits.width * 0.5,
|
||||
love.graphics.getHeight() * 0.5 - credits.height * 0.5
|
||||
|
||||
@@ -9,7 +9,7 @@ local function Hex(hex, value)
|
||||
value or 1 }
|
||||
end
|
||||
|
||||
return function (props)
|
||||
return function(props)
|
||||
local font = props.font or love.graphics.getFont()
|
||||
local padding = {
|
||||
horizontal = (props.leftPadding or 12) + (props.rightPadding or 12),
|
||||
@@ -47,7 +47,7 @@ return function (props)
|
||||
onHover = props.onHover,
|
||||
disabled = props.disabled or false,
|
||||
hoverCalled = false,
|
||||
onUpdate = function (self)
|
||||
onUpdate = function(self)
|
||||
if love.mouse.isDown(1) then
|
||||
if self.mousePressed == false and self:isMouseInside() and self.parent.visible then
|
||||
self.mousePressed = true
|
||||
@@ -58,7 +58,7 @@ return function (props)
|
||||
end
|
||||
end,
|
||||
--
|
||||
draw = function (self)
|
||||
draw = function(self)
|
||||
if not self.visible then return love.mouse.setCursor() end
|
||||
love.graphics.push()
|
||||
love.graphics.rotate(self.angle)
|
||||
@@ -84,7 +84,7 @@ return function (props)
|
||||
self.onMouseExit = self.onHover(self)
|
||||
self.hoverCalled = true
|
||||
end
|
||||
love.mouse.setCursor(love.mouse.getSystemCursor('hand'))
|
||||
love.mouse.setCursor(love.mouse.getSystemCursor 'hand')
|
||||
love.graphics.setColor(self.hoverColor[1], self.hoverColor[2], self.hoverColor[3], self.opacity)
|
||||
self.hovered = true
|
||||
elseif self.hovered then
|
||||
|
||||
@@ -13,7 +13,7 @@ local function label(options)
|
||||
height = _font:getHeight(),
|
||||
onClick = options.onClick or nil,
|
||||
font = _font,
|
||||
draw = function (self)
|
||||
draw = function(self)
|
||||
if not self.visible then return end
|
||||
love.graphics.setFont(self.font)
|
||||
love.graphics.setColor {
|
||||
|
||||
Reference in New Issue
Block a user