dofile("struct.lua")
dofile("table.lua")
function table.ftable(t, o)
for _, v in pairs(t) do
if (v[1] == o[1]) and (v[2] == o[2]) then
return _
end
end
end
function table.trans(t)
local _ret = {}
for x,v in pairs(t) do
for y,v in pairs(t) do
table.insert(_ret, {x,y})
end
end
return _ret
end
function Class(members)
members = members or {}
local mt = {
__metatable = members;
__index = members;
}
local function new(_, init)
return setmetatable(init or {}, mt)
end
local function copy(obj, ...)
local newobj = obj:new(unpack(arg))
for n,v in pairs(obj) do newobj[n] = v end
return newobj
end
members.new = members.new or new
members.copy = members.copy or copy
return mt
end
--[[Class]] Reader = { --
new = function(self, stream)
local __members__ = {
stream = stream
}
local __meta__ = {__metatable = self, __index = self}
local _return_ = setmetatable(__members__, __meta__)
return _return_
end
,
line = function(self)
return ReadLine(self.stream):trim()
end
,
int = function(self)
return ReadInt(self.stream)
end
,
short = function(self)
return ReadShort(self.stream)
end
,
str = function(self, ln)
return ReadString(self.stream, ln)
end
,
byte = function(self)
return ReadByte(self.stream)
end
}
Class(Reader) --[[Class]]--
--[[Class]] Map = { --
header = "Unreal Software's Counter-Strike 2D Map File",
maxheader = "Unreal Software's Counter-Strike 2D Map File (max)",
mapcheck = "ed.erawtfoslaernu",
new = function(self, file)
local timeit = os.clock()
local __members__ = {
file = file,
data = "",
reader = nil,
metadata = {},
tiles = {},
modes = {},
entities = {},
collisions = {},
gradient = {},
antigradient = {},
}
local __meta__ = {__metatable = self, __index = self}
local _return_ = setmetatable(__members__, __meta__)
_return_:get_meta()
_return_:get_tiles()
_return_:get_entities()
_return_.metadata.loadtime = (os.clock() - timeit)
return _return_
end
,
get_meta = function(self)
local _handle_ = io.open(self.file, "rb")
self.data = _handle_:read(100)
while true do
local block = _handle_:read(100)
if not block then break end
self.data = self.data..block
end
_handle_:close()
self.reader = Reader:new(self.data)
local m = self.metadata
local r = self.reader
--Header Check
m.header = r:line():trim()
if m.header == Map.header then
for i = 1, 9 do r:byte() end
for i = 1, 10 do r:int() end
for i = 1, 10 do r:line() end
m.version = "legacy"
elseif m.header == Map.maxheader then
for i = 1, 10 do r:line() end
m.version = "max"
else
return "MapHeader is incorrect"
end
--Coded Information
m.code = r:line()
m.tileset = r:line()
m.loaded = r:byte()
m.mx = r:int()
m.my = r:int()
m.background = r:line()
m.backgroundx = r:int()
m.backgroundy = r:int()
m.red = r:byte()
m.green = r:byte()
m.blue = r:byte()
--Map Check
m.check = r:line():trim()
if m.check ~= Map.mapcheck then return "MapCheck is incorrect" end
m.tilemode = {}
for i=1, m.loaded + 1 do
table.insert(m.tilemode, r:byte())
end
end
,
get_tiles = function(self)
local t_ = self.tiles
local m_ = self.modes
local m = self.metadata
local r = self.reader
local c_ = self.collisions
local stream = s_get(r.stream):sub(1,(m.mx+1)*(m.my+1))
s_update(r.stream, (m.mx+1)*(m.my+1))
for x=1, m.mx+1 do
for y=1, m.my+1 do
local _b_ = stream:byte((x-1)*(m.my+1)+y)
if _b_ > m.loaded then _b_ = 0 end
local _m_ = m.tilemode[_b_+1]
if not t_[x] then t_[x] = {} end
if not m_[x] then m_[x] = {} end
if not c_[x] then c_[x] = {} end
t_[x][y] = _b_
m_[x][y] = _m_
if isIn(_m_, {1,2,3,4}) then
c_[x][y] = _m_
table.insert(self.gradient, {x,y,_m_})
else
c_[x][y] = 0
table.insert(self.antigradient, {x,y,_m_})
end
end
end
end
,
get_entities = function(self)
local m = self.metadata
local e = self.entities
local r = self.reader
m.entities = r:int()
for i = 1, m.entities do
local name = r:line()
local type = r:byte()
local x = r:int()
local y = r:int()
local trig = r:line()
local _args_ = {}
for _n_ = 1, 10 do
table.insert(_args_, {r:int(), r:line()})
end
table.insert(e, {name = name, type = type, x = x, y = y, trigger = trig, args = _args_})
end
end
,
mapogram = function (self)
local l = self:invert(self.modes)
for _i_, x in ipairs(l) do
local str = ""
for _i__,y in ipairs(x) do
if isIn(y, {1,2,3,4}) then
str = str.."#"
else
str = str .. " "
end
end
print(str)
end
end
,
mark = function (self, vector, marker)
if not marker then marker = "X" end
local l = self:invert(self.modes)
for _i_, x in ipairs(l) do
local str = ""
for _i__,y in ipairs(x) do
if _i_ == vector[2] and _i__ == vector[1] then
str = str..marker
elseif isIn(y, {1,2,3,4}) then
str = str.."#"
else
str = str .. " "
end
end
print(str)
end
end
,
marks = function (self, vectors, marker)
if not marker then marker = "X" end
local l = self:invert(self.modes)
for _i_, x in ipairs(l) do
local str = ""
for _i__,y in ipairs(x) do
if table.ftable(vectors, {_i__,_i_}) then
str = str..marker
elseif isIn(y, {1,2,3,4}) then
str = str.."#"
else
str = str .. " "
end
end
print(str)
end
end
,
obstacles = function(self, _invert)
local l = {}
if _invert then
l = self:invert(self.modes)
else
l = self.modes
end
local _ret_ = {}
for _i_, x in ipairs(l) do
_ret_[_i_] = {}
for _i__,y in ipairs(x) do
if isIn(y, {1,2,3,4}) then
_ret_[_i_][_i__] = 1
else
_ret_[_i_][_i__] = 0
end
end
end
return _ret_
end
,
invert = function (self, list)
local _tab_ = {}
for x, _t_ in ipairs(list) do
for y, v in ipairs(_t_) do
if not _tab_[y] then _tab_[y] = {} end
_tab_[y][x] = v
end
end
return _tab_
end
,
dumpMeta = function(self)
table.dump(self.metadata)
end
}
Class(Map) --[[Class]]--