180 lines
8.3 KiB
Lua
180 lines
8.3 KiB
Lua
local root = app.params["root"]
|
|
local assetDir = root .. "/public/assets"
|
|
local sourceDir = assetDir .. "/source"
|
|
app.fs.makeDirectory(root .. "/public")
|
|
app.fs.makeDirectory(assetDir)
|
|
app.fs.makeDirectory(sourceDir)
|
|
|
|
local C = {
|
|
transparent = Color{ r=0, g=0, b=0, a=0 },
|
|
grass = Color{ r=104, g=190, b=82, a=255 },
|
|
grass2 = Color{ r=76, g=158, b=70, a=255 },
|
|
cream = Color{ r=255, g=233, b=164, a=255 },
|
|
honey = Color{ r=239, g=151, b=49, a=255 },
|
|
orange = Color{ r=199, g=97, b=43, a=255 },
|
|
sky = Color{ r=93, g=190, b=224, a=255 },
|
|
water = Color{ r=68, g=171, b=216, a=255 },
|
|
water2 = Color{ r=139, g=224, b=231, a=255 },
|
|
stone = Color{ r=206, g=199, b=171, a=255 },
|
|
stone2 = Color{ r=162, g=155, b=133, a=255 },
|
|
brown = Color{ r=91, g=54, b=43, a=255 },
|
|
wood = Color{ r=151, g=91, b=48, a=255 },
|
|
leaf = Color{ r=51, g=130, b=60, a=255 },
|
|
pink = Color{ r=237, g=111, b=150, a=255 },
|
|
red = Color{ r=194, g=66, b=64, a=255 },
|
|
white = Color{ r=247, g=244, b=226, a=255 },
|
|
gray = Color{ r=194, g=199, b=199, a=255 },
|
|
gray2 = Color{ r=132, g=142, b=145, a=255 },
|
|
black = Color{ r=48, g=38, b=37, a=255 },
|
|
yellow = Color{ r=255, g=213, b=62, a=255 },
|
|
purple = Color{ r=133, g=89, b=159, a=255 },
|
|
}
|
|
|
|
local function fill(img, x, y, w, h, color)
|
|
for yy = y, y + h - 1 do
|
|
for xx = x, x + w - 1 do img:drawPixel(xx, yy, color) end
|
|
end
|
|
end
|
|
|
|
local function pixel(img, x, y, color) img:drawPixel(x, y, color) end
|
|
|
|
local function outlineRect(img, x, y, w, h, color)
|
|
fill(img, x, y, w, 1, color); fill(img, x, y+h-1, w, 1, color)
|
|
fill(img, x, y, 1, h, color); fill(img, x+w-1, y, 1, h, color)
|
|
end
|
|
|
|
local function save(sprite, sourceName, pngName)
|
|
sprite:saveAs(sourceDir .. "/" .. sourceName)
|
|
sprite:saveCopyAs(assetDir .. "/" .. pngName)
|
|
sprite:close()
|
|
end
|
|
|
|
local function makeTileset()
|
|
local sprite = Sprite(256, 64, ColorMode.RGB)
|
|
sprite.filename = "tileset"
|
|
sprite.cels[1].image:clear(C.transparent)
|
|
local img = sprite.cels[1].image
|
|
local function tile(index, base)
|
|
local x = (index % 16) * 16; local y = math.floor(index / 16) * 16
|
|
fill(img, x, y, 16, 16, base)
|
|
return x, y
|
|
end
|
|
|
|
for i=0,63 do
|
|
local palette = {C.grass, C.stone, C.water, C.cream, C.wood, C.gray}
|
|
local x,y = tile(i, palette[(i % #palette)+1])
|
|
if i % 6 == 0 then
|
|
pixel(img,x+3,y+5,C.grass2); pixel(img,x+11,y+3,C.cream); pixel(img,x+12,y+3,C.pink)
|
|
elseif i % 6 == 1 then
|
|
outlineRect(img,x+1,y+1,7,6,C.stone2); outlineRect(img,x+8,y+7,7,8,C.stone2)
|
|
elseif i % 6 == 2 then
|
|
fill(img,x,y+3,16,2,C.water2); fill(img,x+5,y+10,9,1,C.water2)
|
|
elseif i % 6 == 3 then
|
|
fill(img,x,y,16,4,C.honey); fill(img,x+2,y+7,4,3,C.orange); fill(img,x+10,y+6,4,4,C.orange)
|
|
elseif i % 6 == 4 then
|
|
fill(img,x,y+4,16,2,C.brown); fill(img,x+4,y,2,16,C.brown); fill(img,x+12,y,1,16,C.brown)
|
|
else
|
|
outlineRect(img,x+1,y+1,14,14,C.gray2); fill(img,x+3,y+3,10,10,C.white)
|
|
end
|
|
end
|
|
|
|
local x,y = tile(0,C.grass); pixel(img,x+3,y+5,C.grass2); pixel(img,x+11,y+9,C.grass2)
|
|
x,y = tile(1,C.stone); outlineRect(img,x,y,8,8,C.stone2); outlineRect(img,x+8,y+8,8,8,C.stone2)
|
|
x,y = tile(2,C.water); fill(img,x,y+4,12,2,C.water2); fill(img,x+5,y+11,11,1,C.water2)
|
|
x,y = tile(3,C.cream); fill(img,x,y,16,3,C.honey); fill(img,x,y+13,16,3,C.honey)
|
|
x,y = tile(4,C.wood); fill(img,x,y+4,16,2,C.brown); fill(img,x,y+11,16,1,C.brown)
|
|
x,y = tile(5,C.white); outlineRect(img,x,y,16,16,C.gray)
|
|
x,y = tile(6,C.grass); fill(img,x+2,y+3,12,10,C.leaf); pixel(img,x+6,y+6,C.red); pixel(img,x+11,y+9,C.red)
|
|
x,y = tile(7,C.grass); fill(img,x+1,y+2,14,12,C.leaf); fill(img,x+4,y+4,3,3,C.pink); fill(img,x+10,y+7,3,3,C.yellow)
|
|
x,y = tile(8,C.honey); fill(img,x,y+6,16,10,C.cream); outlineRect(img,x,y+6,16,10,C.orange)
|
|
x,y = tile(9,C.orange); fill(img,x,y+6,16,10,C.cream); fill(img,x+6,y+9,4,7,C.brown)
|
|
x,y = tile(10,C.cream); fill(img,x+2,y+5,12,8,C.wood); outlineRect(img,x+2,y+5,12,8,C.brown)
|
|
x,y = tile(11,C.grass); fill(img,x+6,y,4,16,C.wood); fill(img,x+1,y,14,8,C.leaf)
|
|
x,y = tile(12,C.grass); fill(img,x+2,y+2,12,12,C.pink); fill(img,x+5,y+5,6,6,C.yellow)
|
|
x,y = tile(13,C.wood); fill(img,x+4,y+2,8,14,C.black); fill(img,x+6,y+3,4,11,C.water)
|
|
x,y = tile(14,C.sky); fill(img,x+4,y,8,16,C.white); fill(img,x+1,y+4,14,8,C.white)
|
|
x,y = tile(15,C.white); fill(img,x,y,16,3,C.gray); fill(img,x,y+13,16,3,C.gray)
|
|
x,y = tile(16,C.grass); fill(img,x+3,y+5,10,7,C.white); outlineRect(img,x+3,y+5,10,7,C.brown); pixel(img,x+8,y+8,C.red)
|
|
save(sprite, "tileset.aseprite", "tileset.png")
|
|
end
|
|
|
|
local speciesColors = {C.cream,C.pink,C.brown,C.orange,C.gray,C.honey,C.grass2,C.purple,C.red,C.sky,C.yellow,C.wood,C.white}
|
|
|
|
local function drawCharacter(img, ox, oy, body, facing, step, expression, species)
|
|
fill(img,ox,oy,16,24,C.transparent)
|
|
local skin = body
|
|
fill(img,ox+4,oy+3,8,8,skin)
|
|
fill(img,ox+3,oy+5,10,5,skin)
|
|
if species == "rabbit" then fill(img,ox+4,oy,2,5,skin); fill(img,ox+10,oy,2,5,skin) end
|
|
if species == "deer" then pixel(img,ox+3,oy+2,C.brown); pixel(img,ox+12,oy+2,C.brown) end
|
|
if species == "bird" then fill(img,ox+3,oy+6,10,8,skin); pixel(img,ox+13,oy+8,C.honey) end
|
|
local eyeY = oy+6
|
|
pixel(img,ox+6,eyeY,C.black); pixel(img,ox+10,eyeY + (expression == "off" and 1 or 0),C.black)
|
|
if expression == "smile" then pixel(img,ox+7,oy+9,C.red); pixel(img,ox+8,oy+10,C.red); pixel(img,ox+9,oy+9,C.red)
|
|
elseif expression == "flat" then fill(img,ox+7,oy+9,3,1,C.black)
|
|
else pixel(img,ox+7,oy+9,C.black); fill(img,ox+8,oy+10,3,1,C.black) end
|
|
fill(img,ox+4,oy+12,8,8,body)
|
|
fill(img,ox+3,oy+13,2,6,C.cream); fill(img,ox+11,oy+13,2,6,C.cream)
|
|
local foot = step % 2
|
|
if facing == "left" or facing == "right" then
|
|
fill(img,ox+4-foot,oy+20,3,3,C.black); fill(img,ox+9+foot,oy+20,3,3,C.black)
|
|
else
|
|
fill(img,ox+4+foot,oy+20,3,3,C.black); fill(img,ox+9-foot,oy+20,3,3,C.black)
|
|
end
|
|
if facing == "up" then fill(img,ox+5,oy+5,6,4,skin); fill(img,ox+5,oy+6,6,2,C.brown) end
|
|
if facing == "left" then pixel(img,ox+5,eyeY,C.black); fill(img,ox+10,eyeY,2,2,skin) end
|
|
if facing == "right" then pixel(img,ox+11,eyeY,C.black); fill(img,ox+4,eyeY,2,2,skin) end
|
|
end
|
|
|
|
local function makeCharacters()
|
|
local cols, rows = 16, 4
|
|
local sprite = Sprite(cols*16, rows*24, ColorMode.RGB)
|
|
sprite.cels[1].image:clear(C.transparent)
|
|
local img = sprite.cels[1].image
|
|
local dirs = {"down","up","left","right"}
|
|
for d=0,3 do for f=0,3 do drawCharacter(img,f*16,d*24,C.sky,dirs[d+1],f,"smile","human") end end
|
|
local npc = {
|
|
{C.honey,"dog"},{C.white,"rabbit"},{C.brown,"bear"},{C.orange,"cat"},
|
|
{C.cream,"deer"},{C.sky,"bird"},{C.grass2,"turtle"}
|
|
}
|
|
for n=0,6 do for e=0,2 do
|
|
local index = 16 + n*3 + e; local ox=(index%cols)*16; local oy=math.floor(index/cols)*24
|
|
local exp=({"smile","flat","off"})[e+1]
|
|
drawCharacter(img,ox,oy,npc[n+1][1],"down",0,exp,npc[n+1][2])
|
|
end end
|
|
for n=0,4 do
|
|
local index=37+n; local ox=(index%cols)*16; local oy=math.floor(index/cols)*24
|
|
drawCharacter(img,ox,oy,speciesColors[n+8],"down",n%2,"smile","human")
|
|
end
|
|
for n=0,3 do
|
|
local index=42+n; local ox=(index%cols)*16; local oy=math.floor(index/cols)*24
|
|
drawCharacter(img,ox,oy,(n%2==0 and C.pink or C.sky),"down",n%2,"smile","bird")
|
|
if n%2==1 then fill(img,ox+7,oy+9,4,2,C.black) end
|
|
end
|
|
save(sprite,"characters.aseprite","characters.png")
|
|
end
|
|
|
|
local function drawPortrait(img, ox, body, expression, real)
|
|
fill(img,ox,0,48,48,C.cream)
|
|
fill(img,ox+7,6,34,34,C.brown)
|
|
fill(img,ox+9,8,30,30,body)
|
|
fill(img,ox+14,17,4,5,C.black); fill(img,ox+30,17 + (expression=="off" and 2 or 0),4,5,C.black)
|
|
if real then
|
|
fill(img,ox+15,31,18,2,C.black); fill(img,ox+13,13,8,2,C.gray2); fill(img,ox+27,13,8,2,C.gray2)
|
|
elseif expression == "smile" then
|
|
fill(img,ox+17,29,4,3,C.red); fill(img,ox+21,32,8,3,C.red); fill(img,ox+29,29,3,3,C.red)
|
|
else fill(img,ox+18,30,14,2,C.black) end
|
|
end
|
|
|
|
local function makePortraits()
|
|
local sprite=Sprite(9*48,48,ColorMode.RGB); sprite.cels[1].image:clear(C.transparent)
|
|
local img=sprite.cels[1].image
|
|
drawPortrait(img,0,C.sky,"smile",false); drawPortrait(img,48,C.gray,"flat",true)
|
|
local colors={C.honey,C.white,C.brown,C.orange,C.cream,C.sky,C.grass2}
|
|
for i=0,6 do drawPortrait(img,(i+2)*48,colors[i+1],"smile",false) end
|
|
save(sprite,"portraits.aseprite","portraits.png")
|
|
end
|
|
|
|
makeTileset(); makeCharacters(); makePortraits()
|
|
print("Generated original Aseprite assets in " .. assetDir)
|