News : The level of daily SPAM has reached insane proportions, all registrations are now manual. I ask you to send me an e-mail (john (at) murga (dot) org), to confirm that you want me to create an account for you.


Post Reply  Post Thread 
murgaLua to html
Author Message
mikshaw
Senior Member
****


Posts: 522
Group: Registered
Joined: Apr 2007
Status: Offline
Reputation: 5
Post: #1
RE: murgaLua to html

Ok, that was easier than I thought. You can now pass the script a "-n" parameter in order to skip the line numbers, or edit the "uselinenumbers" variable to make it default. There are a couple other variables near the top of the file that can be used to change the CSS filename and the HTML character set.

Code:
#!/home/dsl/bin/murgaLua-0.6.4
------------------------------------------------------------------------------
--  Lua 2 HTML (MODIFIED)
--  Original author Peter Shook <http://lua-users.org/wiki/PeterShook>

-- Modified by mikshaw for use specific to MurgaLua
-- http://www.murga-projects.com/murgaLua/
-- and to generate valid 4.01 strict HTML
-- mik's changes:
--    Removed Lua 4.0 code
--    Added FLTK and modules included with murgaLua
--    Replaced much of the long attr table with loops
--    Added code to generate proper HTML 4
--    Uses external CSS file for highlighting (default is Murga.css)
--    Commandline option to skip line numbers
--
-- usage: murgaLua murga2html.lua [-n] myscript.lua > myscript.html
--        use -n to skip writing line numbers
------------------------------------------------------------------------------

local Pkg = { Name = 'Lua2HTML' }

-- a file path relative to the html file
-- See example css file at the bottom
local cssfile='Murga.css'
-- change this to 0 if you don't want to bother with the -n option
local dolinenumber=1
-- not sure what affect on html validation might come from changing this
local charset='ISO-8859-1'

local inputFile
if arg[1] == "-n" then
  inputFile=arg[2]
  dolinenumber=0
else
  inputFile=arg[1]
end

local special_chars = {
  ['&'] = '&amp;',
  ['"'] = '&quot;',
  ['<'] = '&lt;',
  ['>'] = '&gt;',
}

local special
function special(x) return special_chars[x] end

local quote
function quote(str)
  return(string.gsub(str, '([&"<>])', special))
end

local colour
function colour(class)
  local quote = quote
  local b = '<span class="'.. class ..'">'
  local e = '</span>'
  return function(x) return b .. quote(x) .. e end
end

-- CSS classes: <span class="oper">keyword</span>
local operator = colour'oper'
local note     = colour'note'
local ctrl     = colour'ctrl'
local std      = colour'std'
local literal  = colour'lit'
local acomment = colour'com'
local fl       = colour'fl'
local cnst     = colour'cnst'

local keywords_attr = {
  ['nil']       = literal,
  ['true']      = literal,
  ['false']     = literal,
  ['NULL']     = literal,

  ['local']     = note,
  ['function']  = ctrl,
  ['return']    = note,
  ['break']     = note,

  ['not']       = ctrl,
  ['and']       = ctrl,
  ['or']        = ctrl,

  ['if']        = ctrl,
  ['then']      = ctrl,
  ['else']      = ctrl,
  ['elseif']    = ctrl,

  ['for']       = ctrl,
  ['in']        = ctrl,
  ['while']     = ctrl,
  ['do']        = ctrl,
  ['end']       = ctrl,
  ['repeat']    = ctrl,
  ['until']     = ctrl,
}

local other_attr = {
  ['%']   = note,
  ['=']   = note,
  ['{']   = ctrl,
  ['}']   = ctrl,
  ['+']   = operator,
  ['-']   = operator,
  ['*']   = operator,
  ['/']   = operator,
  ['^']   = operator,
  ['<']   = operator,
  ['<=']  = operator,
  ['>']   = operator,
  ['>=']  = operator,
  ['==']  = operator,
  ['~=']  = operator,
  ['..']  = operator,
}

local stdfunctions_attr = {
  arg = std, self = std,
  _G = std, _LOADED = std, _REQUIREDNAME = std, _TRACEBACK = std, _VERSION = std,
  add = std, assert = std, bind_lua_addtovtable = std, collectgarbage = std,
  dofile = std, error = std, gcinfo = std, getMenu = std, getUserData = std,
  getfenv = std, getmetatable = std, ipairs = std, load = std, loadfile = std,
  loadlib = std, loadstring = std, module = std, newproxy = std, next = std,
  pairs = std, pcall = std, print = std, rawequal = std, rawget = std, rawset = std,
  require = std, select = std, setMenu = std, setfenv = std, setmetatable = std,
  tonumber = std, tostring = std, type = std, unpack = std, xpcall = std,
  __index = std, __newindex = std, __gc = std, __eq = std, __add = std, __sub = std,
  __mul = std, __div = std, __unm = std, __pow = std, __lt = std, __le = std,
  __concat = std, __call = std, __tostring = std, __metatable = std, __fenv = std,
  coroutine=std, debug=std, io=std, math=std, os=std, package=std, string=std, table=std,
  copas=std, gzip=std, lfs=std, lzo=std, md5=std, mime=std, murgaLua=std, random=std, socket=std, sqlite3=std, zlib=std,
}

-- This is a LOT easier than typing out tables, and will be
-- dynamically updated with future changes to these modules
local fltk_attr={ fltk = fl, Fl = fl } -- FLTK functions
local fltkcnst_attr = { }      -- FLTK constants
local fltkmeth_attr = { }      -- FLTK methods
local murga_attr = { ['murgaLua_About'] = cnst, ['murgaLua_ExePath'] = cnst, ['murgaLua_Version'] = cnst }
local ml_mods={ copas, coroutine, debug, gzip, io, lfs, lzo, math, md5,
mime, murgaLua, os, package, random, socket, sqlite3, string, table, zlib }

for i,t in pairs(ml_mods) do
--  stdfunctions_attr[t] = std -- can't figure out how to add this
  for k,v in pairs(t) do
    if type(v)=="function" then stdfunctions_attr[k] = std end
  end
end

for k,v in pairs(fltk) do
if type(v)=="function" then fltk_attr[k] = fl
elseif type(v)=="number" then fltkcnst_attr[k] = cnst end
end

for k,v in pairs(_G) do
  if type(v)=="table" and string.find(k,"^Fl") then
   for a,b in pairs(v) do
     if type(b)=="function" then stdfunctions_attr[a] = std end
    end
  end
end

local sqstring
function sqstring(code, e)
  while 1 do
    e = string.find(code, '[\'\\]', e)
    if not e then error'bad single quoted string' end
    if string.find(code, '^\\.', e) then
      e = e+2
    elseif string.find(code, '^\'', e) then
      return e
    else
      error'impossible?'
    end
  end
end

local dqstring
function dqstring(code, e)
  while 1 do
    e = string.find(code, '[\"\\]', e)
    if not e then error'bad double quoted string' end
    if string.find(code, '^\\.', e) then
      e = e+2
    elseif string.find(code, '^\"', e) then
      return e
    else
      error'impossible?'
    end
  end
end

local longstring
function longstring(code, e)
  local count = 0
  local b
  while 1 do
    b,e = string.find(code, '[%[%]].', e)
    if not b then error'bad long comment or string' end
    if string.find(code, '^%[%[', b) then
      e = e+1
      count = count+1
    elseif string.find(code, '^%]%]', b) then
      if count == 0 then
        return e
      end
      e = e+1
      count = count-1
    else
      -- okay
    end
  end
end

local other
function other(code, i)
  local b,e
  b,e = string.find(code, '^\'.', i)
  if b then return sqstring(code, e), literal end

  b,e = string.find(code, '^\".', i)
  if b then return dqstring(code, e), literal end

  b,e = string.find(code, '^%[%[.', i)
  if b then return longstring(code, e), literal end

  b,e = string.find(code, '^%.%.%.', i) if b then return e end
  b,e = string.find(code, '^%.%.', i)   if b then return e end
  b,e = string.find(code, '^%=%=', i)   if b then return e end
  b,e = string.find(code, '^%~%=', i)   if b then return e end
  b,e = string.find(code, '^%>%=', i)   if b then return e end
  b,e = string.find(code, '^%<%=', i)   if b then return e end

  return i
end

local number
function number(code, i)
  local b,e,e1,e2,e3
  b,e1 = string.find(code, '^%d+%.%d*', i)  -- D+ . D*
  b,e2 = string.find(code, '^%d*%.%d+', i)  -- D* . D+
  b,e3 = string.find(code, '^%d+', i)       -- D+
  i = e1 or e2 or e3
  b,e = string.find(code, '^[Ee][+-]?%d+', i+1)
  return e or i, literal
end

local word
function word(code, i)
  local b,e
  b,e = string.find(code, '^[_%a][_%w]*', i)
  local token = string.sub(code, b, e)
  return e, fltk_attr[token] or fltkcnst_attr[token] or keywords_attr[token] or stdfunctions_attr[token] or murga_attr[token]
end

local comment
function comment(code, i)
  local b,e
  b,e = string.find(code, '^%-%-%[%[.', i)
  if b then return longstring(code, e) end

  b,e = string.find(code, '^%-%-[^\n]*', i)
  if b then return e end

  b,e = string.find(code, '^%#[^\n]*', i)
  if b then return e end
end

local highlight
function highlight(code, outfnc)
  code = string.gsub(code, '\r\n', '\n')  -- DOS is a pain

  local line = { number = 0 }
  local ln
  function ln()
    line.number = line.number+1
    return string.format('\n<span class=\"lnum\">%4d</span>  ', line.number)
    --return string.format('\n%4d  ', line.number)
  end
  local output
  function output(x, fmt)
    fmt = fmt or function(x) return x end
    x = string.gsub(x, '(%S[^\n]*)', fmt)  -- format groups of non-newline characters
    if dolinenumber==1 then x = string.gsub(x, '\n', ln)  end         -- add line number after a newline
    outfnc(x)
  end

  output'\n'  -- line number 1

  local ws = 1
  local tok, e, fmt
  while 1 do
    e = ws
    while 1 do
      tok = string.find(code, '%S', e)
      if not tok then return end
      if not string.find(code, '^[-#]', tok) then break end
      e = comment(code, tok)
      if not e then break end
      e = e+1
    end

    output(string.sub(code, ws, tok-1), acomment) -- white space and comments

    if     string.find(code, '^[_%a]', tok) then e,fmt = word  (code, tok)
    elseif string.find(code, '^%.?%d', tok) then e,fmt = number(code, tok)
    elseif string.find(code, '^%p', tok)    then e,fmt = other (code, tok)
    else
      error'impossible?'
    end

    local token = string.sub(code, tok, e)
    output(token, fmt or other_attr[token])

    ws = e+1
  end
end

function Pkg.lua2html(filename, outfnc)
  local fh = io.open(filename, "r")
  local code =  fh:read('*a')
  io.close(fh)

  outfnc = outfnc or io.write
  outfnc([[<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=]]..charset..[[">
<link href="]]..cssfile..[[" rel="stylesheet" type="text/css" title="default">
<title>]]..filename..[[</title>
</head>
<body>]])
  outfnc("<h3>".. filename .."</h3>\n")
  outfnc'<pre>\n'
  highlight(code, outfnc)
  outfnc'</pre>\n</body></html>'
end

--[[

/* Example CSS file */
/*
There are 16 color names accepted by w3c HTML/CSS validator
  aqua, black, blue, fuchsia, gray, green, lime, maroon,
  navy, olive, purple, red, silver, teal, white, yellow
Otherwise you should use RGB or HEX values
*/

span.oper { color: #FF0000; font-weight: bold } /* mathematical/comparison operators */
span.note { color: #CC0033; font-weight: bold } /* controls */
span.ctrl { color: #993333; font-weight: bold } /* controls */
span.std  { color: #009900 } /* Lua functions */
span.lit  { color: #6666CC } /* strings/numbers */
span.com  { color: #999999 } /* comments */
span.lnum { color: #999999 } /* line numbers */
span.fl   { color: #CC6633 } /* FLTK functions/methods */
span.cnst { color: #990033 } /* FLTK constants */

]]
-- I don't know why the above comment gets dropped if it's at the very end of the script

Pkg.lua2html(inputFile)
return Pkg

03-13-2008 12:01 PM
Find all posts by this user Quote this message in a reply
Post Reply  Post Thread 

Messages In This Thread
murgaLua to html - mikshaw - 03-09-2008, 05:42 AM
RE: murgaLua to html - iGame3D - 03-09-2008, 06:52 AM
RE: murgaLua to html - mikshaw - 03-09-2008, 07:56 AM
RE: murgaLua to html - mikshaw - 03-09-2008, 08:31 AM
RE: murgaLua to html - mikshaw - 03-10-2008, 05:44 AM
RE: murgaLua to html - mikshaw - 03-12-2008, 04:59 AM
RE: murgaLua to html - mikshaw - 03-13-2008, 03:47 AM
RE: murgaLua to html - iGame3D - 03-13-2008, 10:10 AM
RE: murgaLua to html - mikshaw - 03-13-2008, 10:34 AM
RE: murgaLua to html - mikshaw - 03-13-2008 12:01 PM

View a Printable Version
Send this Thread to a Friend
Subscribe to this Thread | Add Thread to Favorites

Forum Jump: