diff --git a/polymer/eduke32/source/lunatic/con_lang.lua b/polymer/eduke32/source/lunatic/con_lang.lua index 7bea48acd..c81b74c42 100644 --- a/polymer/eduke32/source/lunatic/con_lang.lua +++ b/polymer/eduke32/source/lunatic/con_lang.lua @@ -1,12 +1,10 @@ --- Use this file like --- require("lpeg") --- con = require("con_lang") --- --- Contains: --- * con.labels --- * con.keyword +-- CON language definitions -local lpeg = lpeg +local lpeg = require("lpeg") + +local pairs = pairs +local print = print +local type = type module(...) @@ -304,6 +302,7 @@ wdata_members = local SP = function(memb) return "sprite[%s]"..memb end +local ATSP = function(memb) return "atsprite[%s]"..memb end local AC = function(memb) return "actor[%s]"..memb end local SX = function(memb) return "spriteext[%s]"..memb end @@ -321,7 +320,7 @@ local ActorLabels = { y = SP".y", z = SP".z", cstat = SP".cstat", - picnum = SP".picnum", + picnum = { SP".picnum", SP":set_picnum(%%s)" }, shade = SP".shade", pal = SP".pal", clipdist = SP".clipdist", @@ -331,12 +330,12 @@ local ActorLabels = { yrepeat = SP".yrepeat", xoffset = SP".xoffset", yoffset = SP".yoffset", - sectnum = SP".sectnum", - statnum = SP".statnum", + sectnum = { SP".sectnum" }, + statnum = { SP".statnum" }, ang = SP".ang", - owner = SP".owner", + owner = { SP".owner" }, xvel = SP".xvel", - yvel = SP".yvel", + yvel = { SP".yvel" }, zvel = SP".zvel", lotag = SP".lotag", hitag = SP".hitag", @@ -347,14 +346,14 @@ local ActorLabels = { -- ActorExtra labels... htcgg = AC".cgg", - htpicnum = AC".picnum", + htpicnum = { AC".picnum", AC":set_picnum(%%s)" }, htang = AC".ang", htextra = AC".extra", - htowner = AC".owner", + htowner = { AC".owner", AC":set_owner(%%s)" }, htmovflag = AC".movflag", httempang = AC".tempang", htactorstayput = AC".actorstayput", - htdispicnum = AC".dispicnum", + htdispicnum = { AC".dispicnum" }, httimetosleep = AC".timetosleep", htfloorz = AC".floorz", htceilingz = AC".ceilingz", @@ -374,7 +373,7 @@ local ActorLabels = { mdxoff = SX".xoff", mdyoff = SX".yoff", mdzoff = SX".zoff", - mdflags = SX".mdflags", + mdflags = SX".flags", xpanning = SX".xpanning", ypanning = SX".ypanning", @@ -382,6 +381,26 @@ local ActorLabels = { alpha = { "_math.floor(spriteext[%s].alpha*255)" }, } +local function spr2tspr(code) + if (code and code:find(SP"", 1, true)==1) then + return ATSP(code:sub(#SP"" + 1)) + end + -- else return nothing +end + +local TspriteLabels = {} + +for member, code in pairs(ActorLabels) do + if (type(code)=="string") then + TspriteLabels["tspr"..member] = spr2tspr(code) + else + local rwcodetab = { spr2tspr(code[1]), spr2tspr(code[2]) } + if (#rwcodetab > 0) then + TspriteLabels["tspr"..member] = rwcodetab + end + end +end + local PL = function(memb) return "player[%s]"..memb end local PlayerLabels = { @@ -679,6 +698,12 @@ StructAccessCode = player = PlayerLabels, } +-- These structs cannot be accessed by inline array exprs in CON: +StructAccessCode2 = +{ + tspr = TspriteLabels, +} + -- NOTE: These MUST be in reverse lexicographical order! -- Per CON syntax, valid identifiers names are disjunct from keywords, -- so that a rule like diff --git a/polymer/eduke32/source/lunatic/defs.ilua b/polymer/eduke32/source/lunatic/defs.ilua index 5c027185f..06ffebf96 100644 --- a/polymer/eduke32/source/lunatic/defs.ilua +++ b/polymer/eduke32/source/lunatic/defs.ilua @@ -767,6 +767,17 @@ local actor_mt = { end ffi.cast(actor_ptr_ct, a).t_data[idx] = val end, + + set_picnum = function(a, picnum) + check_tile_idx(picnum) + ffi.cast(actor_ptr_ct, a).picnum = picnum + end, + + set_owner = function(a, owner) + -- XXX: is it permissible to set to -1? + check_sprite_idx(owner) + ffi.cast(actor_ptr_ct, a).owner = owner + end, }, } ffi.metatype("actor_t", actor_mt) diff --git a/polymer/eduke32/source/lunatic/defs_common.lua b/polymer/eduke32/source/lunatic/defs_common.lua index 917da4cdd..afdea070b 100644 --- a/polymer/eduke32/source/lunatic/defs_common.lua +++ b/polymer/eduke32/source/lunatic/defs_common.lua @@ -68,9 +68,13 @@ struct { int8_t xoffset, yoffset; const int16_t sectnum, statnum; int16_t ang; - // NOTE: yvel is often used as player index in game code. Make xvel/zvel - // "const" for consistency, too. - const int16_t owner, xvel, yvel, zvel; + + const int16_t owner; + int16_t xvel; + // NOTE: yvel is often used as player index in game code. + const int16_t yvel; + int16_t zvel; + int16_t lotag, hitag, extra; }]] @@ -107,6 +111,7 @@ typedef struct { const uint32_t mdanimtims; const int16_t mdanimcur; int16_t angoff, pitch, roll; + // TODO: make into an ivec3_t int32_t xoff, yoff, zoff; uint8_t flags; uint8_t xpanning, ypanning; @@ -399,6 +404,7 @@ local spritetype_mt = { end, __index = { + --- Setters set_picnum = function(s, tilenum) check_tile_idx(tilenum) ffi.cast(spritetype_ptr_ct, s).picnum = tilenum diff --git a/polymer/eduke32/source/lunatic/lunacon.lua b/polymer/eduke32/source/lunatic/lunacon.lua index 248b01f45..fb1dd23e1 100644 --- a/polymer/eduke32/source/lunatic/lunacon.lua +++ b/polymer/eduke32/source/lunatic/lunacon.lua @@ -1124,8 +1124,9 @@ local function StructAccess(Structname, writep, index, membertab) local member, parm2 = membertab[1], membertab[2] assert(member ~= nil) + local MemberCode = conl.StructAccessCode[Structname] or conl.StructAccessCode2[Structname] -- Look up array+member name first, e.g. "spriteext[%s].angoff". - local armembcode = conl.StructAccessCode[Structname][member] + local armembcode = MemberCode[member] if (armembcode == nil) then errprintf("invalid %s member `.%s'", Structname, member) return "_MEMBINVALID" @@ -1177,6 +1178,8 @@ local Access = wall = function(...) return StructAccess("wall", ...) end, xsprite = function(...) return StructAccess("sprite", ...) end, player = function(...) return StructAccess("player", ...) end, + + tspr = function(...) return StructAccess("tspr", ...) end, } local function GetStructCmd(accessfunc) @@ -1277,7 +1280,7 @@ local Cinner = { getinput = getstructcmd / handle.NYI, getprojectile = getstructcmd / handle.NYI, getthisprojectile = getstructcmd / handle.NYI, - gettspr = getstructcmd / handle.NYI, + gettspr = GetStructCmd(Access.tspr), -- NOTE: {get,set}userdef is the only struct that can be accessed without -- an "array part", e.g. H266MOD has "setuserdef .weaponswitch 0" (space -- between keyword and "." is mandatory). @@ -1299,7 +1302,7 @@ local Cinner = { setinput = setstructcmd / handle.NYI, setprojectile = setstructcmd / handle.NYI, setthisprojectile = setstructcmd / handle.NYI, - settspr = setstructcmd / handle.NYI, + settspr = SetStructCmd(Access.tspr), setuserdef = (arraypat + sp1)/{} * singlememberpat * sp1 * tok.rvar / handle.NYI, setactorvar = setperxvarcmd, diff --git a/polymer/eduke32/source/lunatic/test.elua b/polymer/eduke32/source/lunatic/test.elua index 82be81334..b22c5e748 100644 --- a/polymer/eduke32/source/lunatic/test.elua +++ b/polymer/eduke32/source/lunatic/test.elua @@ -174,7 +174,7 @@ checkfail('gv.luaJIT_BC_con_lang', "attempt to call a nil value") checkfail('gv.yax_getbunch(0,0)', "access forbidden") checkfail('gv.gethitickms = nil', "write access forbidden") --- we don't have arrays in Lua-accessible structs now +-- actor[].t_data[] is not accessible for now checkfail('local i = actor[0].t_data[15]', "has no member named 't_data'") -- no pointer arithmetic! @@ -348,8 +348,8 @@ print('---=== END TEST SCRIPT ===---') function check_sector_idx() error("bla") end ---]] spritesofsect(0) +--]] --DBG_.oom()