summaryrefslogtreecommitdiff
path: root/parsers
diff options
context:
space:
mode:
authorPhilipp Gesang <pgesang@ix.urz.uni-heidelberg.de>2010-08-14 18:53:51 +0200
committerPhilipp Gesang <pgesang@ix.urz.uni-heidelberg.de>2010-08-14 18:53:51 +0200
commitfb7ec40915d2180561189e4ccb10e145d20f1328 (patch)
tree8e0271eaa21ecd3a2483c54303044a86f94960f1 /parsers
parent731fea55e3c23336abc487907df1d0a9c1ed79d2 (diff)
downloadautomata-backgrounds-fb7ec40915d2180561189e4ccb10e145d20f1328.tar.gz
added simple parser for .rle format
Diffstat (limited to 'parsers')
-rw-r--r--parsers/rle.lua95
1 files changed, 95 insertions, 0 deletions
diff --git a/parsers/rle.lua b/parsers/rle.lua
new file mode 100644
index 0000000..cd10493
--- /dev/null
+++ b/parsers/rle.lua
@@ -0,0 +1,95 @@
+-- http://psoup.math.wisc.edu/mcell/ca_files_formats.html#RLE
+local C, Cs, Ct, P, R, S, match = lpeg.C, lpeg.Cs, lpeg.Ct, lpeg.P, lpeg.R, lpeg.S, lpeg.match
+
+local rows = {}
+local coords = {}
+
+local n_row = 1
+rows[n_row] = ""
+
+local eol = P"\n"
+local hashmark = P"#"
+local space = S" \t"
+local whitespace = S(" \n\t")^0
+local num = R"09"
+local comma = P","
+local exclam = P"!"
+local equals = P"="
+local dollar = P"$"
+local state = S"bo"
+--local sign = S("+-")^0 -- support negative grid values? not yet
+
+local comment = hashmark * (1-eol)^0 * eol
+
+local getx = space^0 * P"x" * space^0 * equals * space^0 * C(num^1) / function (x)
+ coords.x = tonumber(x)
+end
+local gety = space^0 * P"y" * space^0 * equals * space^0 * C(num^1) / function (y)
+ coords.y = tonumber(y)
+end
+geometry = getx * comma * gety * (1-eol)^0 * eol
+
+local function n_of_t (n, c)
+ local tmp = ""
+ if c == "o" then -- live
+ c = "1"
+ else -- dead
+ c = "0"
+ end
+
+ for i=1, n, 1 do
+ tmp = tmp .. c
+ end
+ return tmp
+end
+
+local cell = C(num^0) * C(state) / function (n, c)
+ if n == "" then
+ n = 1
+ end
+
+ if n_of_t (tonumber(n), c) == nil then
+ print("OVER HERE", n_row,n, c)
+ end
+ rows[n_row] = rows[n_row] .. n_of_t (tonumber(n), c)
+end
+
+local line = whitespace * (cell * whitespace)^0 * C(num^0) / function (empty)
+
+ if rows[n_row]:len() < coords.x then -- fill grid with dead cells
+ rows[n_row] = rows[n_row] .. n_of_t( coords.x - rows[n_row]:len(), "0" )
+ end
+
+ if empty ~= "" then
+ for n=1, tonumber(empty)-1, 1 do
+ n_row = n_row + 1
+ rows[n_row] = n_of_t( coords.x, "0" )
+ end
+ end
+
+ n_row = n_row + 1
+
+ if n_row <= coords.y then
+ rows[n_row] = ""
+ end
+end
+
+local p_rle = comment^0 * geometry * line * (dollar * line)^0 * whitespace * exclam
+
+local function parser(fname)
+ local file = assert(io.open(fname, "r"), "Not a file: " .. fname)
+ local data = file:read("*all")
+ file:close()
+
+ if p_rle:match(data) then
+ if context then
+ context.writestatus("simpleslides", "Sucessfully loaded frame from "..fname..".")
+ end
+ return rows
+ else
+ return false
+ end
+end
+
+return parser
+