Lunatic: add engine.saveLookupDat() and document, related tweaks.

- Mapster32: before loading LOOKUP.DAT, set palookup[0][239]=239 to
  make an identity map of the base shade table's shade 0
- Rewrite color index remapping case of makepalookup() for clarity

BUILD_LUNATIC.

git-svn-id: https://svn.eduke32.com/eduke32@4336 1a8010ca-5511-0410-912e-c29ae57300e0
This commit is contained in:
helixhorned 2014-02-16 19:16:06 +00:00
parent df25e3cd7c
commit b79fa42903
8 changed files with 109 additions and 22 deletions

View file

@ -14827,9 +14827,7 @@ int32_t setpalookup(int32_t palnum, const uint8_t *shtab)
//
void makepalookup(int32_t palnum, const char *remapbuf, int8_t r, int8_t g, int8_t b, char dastat)
{
int32_t i, j, palscale;
const char *ptr;
char *ptr2;
int32_t i, j;
static char idmap[256] = {1};
@ -14864,27 +14862,26 @@ void makepalookup(int32_t palnum, const char *remapbuf, int8_t r, int8_t g, int8
{
// "black fog"/visibility case -- only remap color indices
for (i=0; i<256; i++)
{
ptr = palookup[0] + remapbuf[i];
ptr2 = palookup[palnum] + i;
for (j=0; j<numshades; j++)
{ *ptr2 = *ptr; ptr += 256; ptr2 += 256; }
}
for (j=0; j<numshades; j++)
for (i=0; i<256; i++)
{
const char *src = palookup[0];
palookup[palnum][256*j + i] = src[256*j + remapbuf[i]];
}
}
else
{
// colored fog case
ptr2 = palookup[palnum];
char *ptr2 = palookup[palnum];
for (i=0; i<numshades; i++)
{
palscale = divscale16(i,numshades);
int32_t palscale = divscale16(i,numshades);
for (j=0; j<256; j++)
{
ptr = (char *)&palette[remapbuf[j]*3];
const char *ptr = (const char *)&palette[remapbuf[j]*3];
*ptr2++ = getclosestcol(ptr[0] + mulscale16(r-ptr[0],palscale),
ptr[1] + mulscale16(g-ptr[1],palscale),
ptr[2] + mulscale16(b-ptr[2],palscale));

View file

@ -2847,6 +2847,11 @@ static int32_t ReadPaletteTable(void)
{
int32_t fp;
// Make base shade table at shade 0 into the identity map.
// (In the shade table of Duke3D's PALETTE.DAT, palookup[0][239]==143.)
// This makes it possible to sensibly use Lunatic's engine.saveLookupDat().
palookup[0][239] = 239;
if ((fp=kopen4load("lookup.dat",0)) == -1)
{
if ((fp=kopen4load("lookup.dat",1)) == -1)

View file

@ -2308,6 +2308,17 @@ There must be no duplicate blending table numbers.
The function returns a status `ok` which is *true* on success and *nil* on
failure. In the latter case, `errmsg` is a diagnostic error message.
===== `engine.saveLookupDat(filename, lookups)` -> `ok, errmsg`
Writes out a LOOKUP.DAT-formatted file named `filename` with the lookup tables
specified by `lookups` at the beginning and the five additional base palettes
at the end.
The `lookups` argument is interpreted analogously to the `moreblends` argument
of `engine.savePaletteDat` (with the numbers being palookup numbers instead of
blending table numbers) and the return values `ok` and `errmsg` have the same
meaning as well.
The `fs` module -- virtual file system facilities
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

View file

@ -108,6 +108,8 @@ g_elCON;
El_SetCON;
El_OnError;
basepaltable;
g_elSavecode;
El_FreeSaveCode;
El_SerializeGamevars;

View file

@ -109,4 +109,6 @@ g_argv;
listsearchpath;
basepaltable;
};

View file

@ -18,6 +18,7 @@ decl[[
int32_t getclosestcol_lim(int32_t r, int32_t g, int32_t b, int32_t lastokcol);
char *palookup[256]; // MAXPALOOKUPS
uint8_t palette[768];
uint8_t *basepaltable[];
const char *getblendtab(int32_t blend);
void setblendtab(int32_t blend, const char *tab);
@ -237,7 +238,7 @@ if (ismapster32) then
ffi.cdef[[size_t fwrite(const void * restrict ptr, size_t size, size_t nmemb, void * restrict stream);]]
local function validate_more_blendtabs(moreblends)
local function validate_more_blendtabs(moreblends, kindname, gettabfunc)
if (moreblends == nil) then
return nil, nil
end
@ -262,18 +263,18 @@ if (ismapster32) then
if (not (type(blend1)=="number" and blend1 >= 1 and blend1 <= 255 and
type(blend2)=="number" and blend2 >= 1 and blend2 <= 255)) then
error("invalid argument #4: blending table numbers must be in [1 .. 255]", 3)
error("invalid argument #4: "..kindname.." table numbers must be in [1 .. 255]", 3)
end
for bi=blend1,blend2 do
if (haveblend[bi]) then
error("invalid argument #4: duplicate blending table number "..bi, 3)
error("invalid argument #4: duplicate "..kindname.." table number "..bi, 3)
end
haveblend[bi] = true
local ptr = C.getblendtab(bi)
local ptr = gettabfunc(bi)
if (ptr == nil) then
error("invalid argument #4: blending table for number "..bi.." is void", 3)
error("invalid argument #4: "..kindname.." table for number "..bi.." is void", 3)
end
blendnumtab[#blendnumtab+1] = bi
@ -285,7 +286,7 @@ if (ismapster32) then
return blendnumtab, blendptrtab
end
-- [ok, errmsg] = engine.savePaletteDat(filename [, palnum [, blendnum [, moreblends]]])
-- ok, errmsg = engine.savePaletteDat(filename [, palnum [, blendnum [, moreblends]]])
function engine.savePaletteDat(filename, palnum, blendnum, moreblends)
local sht = engine.getshadetab(palnum or 0)
local tab = engine.getblendtab(blendnum or 0)
@ -296,7 +297,8 @@ if (ismapster32) then
return nil, "no blending table with number "..blendnum
end
local blendnumtab, blendptrtab = validate_more_blendtabs(moreblends)
local blendnumtab, blendptrtab = validate_more_blendtabs(
moreblends, "blending", C.getblendtab)
local f, errmsg = io.open(filename, "wb+")
if (f == nil) then
@ -328,6 +330,57 @@ if (ismapster32) then
return true
end
-- ok, errmsg = engine.saveLookupDat(filename, lookups)
function engine.saveLookupDat(filename, lookups)
if (lookups == nil) then
-- set to an invalid value, validate_more_blendtabs will error
lookups = 0
end
local lookupnumtab, lookupptrtab = validate_more_blendtabs(
lookups, "lookup", engine.getshadetab)
local f, errmsg = io.open(filename, "wb+")
if (f == nil) then
return nil, errmsg
end
f:write(string.char(#lookupnumtab))
for i=1,#lookupnumtab do
f:write(string.char(lookupnumtab[i]))
if (C.fwrite(lookupptrtab[i], 1, 256, f) ~= 256) then
return nil, "failed writing lookup table"
end
end
-- Write five base palettes
for i=1,5 do
local bpi = (i==3 or i==4) and 4+3-i or i
if (C.fwrite(C.basepaltable[bpi], 1, 768, f) ~= 768) then
return nil, "failed writing base palette"
end
end
f:close()
return true
end
function engine.setupDebugBasePal()
for i=0,14 do
local ptr = C.basepaltable[1] + 3*(16*i)
local src = ptr + 3*i
local r, g, b = src[0], src[1], src[2]
for j=0,15 do
local dst = ptr + 3*j
dst[0], dst[1], dst[2] = r, g, b
end
end
end
end

View file

@ -23,6 +23,10 @@ local gv = gv
local shadexfog = {}
-- Example:
-- lua "shadexfog.createremap(30, {[2]=0, [3]=1, [12]=0, [13]=1})"
-- creates a pal 30 which maps the blue and orange ramps to the gray ones.
-- (Compare with the rows of http://wiki.eduke32.com/wiki/File:Pala.png)
function shadexfog.createremap(palnum, remaptab)
local sht = engine.getshadetab(0)
engine.setshadetab(palnum, sht:remap16(remaptab))
@ -214,6 +218,19 @@ if (gv.LUNATIC_CLIENT == gv.LUNATIC_CLIENT_MAPSTER32) then
printf(" Also wrote additional translucency tables.")
end
end
function shadexfog.saveLookupDat(filename, lookups)
if (lookups == nil) then
lookups = {
-- Duke3D 1.5 LOOKUP.DAT order
1,2,6,7,8, 3,4,5,9,10,
12,13,15,16,18, 19,11,14,17,20,
21,22,23,24,25
}
end
assert(engine.saveLookupDat(filename, lookups))
printf('Wrote lookup tables and 5 base palettes to "%s".', filename)
end
end
-- Create our (failed) version of the base shade table at set it to palookup

View file

@ -78,7 +78,7 @@ static void FuncMenu(void);
static uint8_t WATERpalette[768], SLIMEpalette[768], TITLEpalette[768];
static uint8_t REALMSpalette[768], BOSS1palette[768];
static uint8_t *basepaltable[BASEPALCOUNT] = {
uint8_t *basepaltable[BASEPALCOUNT] = {
palette, WATERpalette, SLIMEpalette,
REALMSpalette, TITLEpalette, BOSS1palette,
};