"""
A simple object-model for generating HTML; see example at bottom.
Copyright (C) 2004 Joshua M. Sled
Released under a Creative Commons Attribution - NonCommercial - ShareAlike license.
-- http://asynchronous.org/jsled
"""
class Container:
def __init__(self, tagName = None, attribs = None, children = None ):
self.tagName = tagName
if attribs is None: attribs = {}
if children is None: children = []
self.attribs = attribs
self.children = children
def __str__(self):
try:
tag = self.tagName
attribs = self.attrib_str()
content = ""
if self.children == None or len(self.children) == 0:
return ( "<%(tag)s%(attrib)s />" % { 'tag': tag, 'attrib': attribs } )
content = "".join( ["\n" + str(x) for x in self.children] )
return ( "<%(tag)s%(attrib)s>%(ct)s%(tag)s>"
% { 'tag': tag,
'attrib': attribs,
'ct': content } )
except Exception,e:
raise Exception( "[%s] in tag [%s]" % ( str(e), self.tagName ) )
def attrib_str(self):
str = " ".join( ["%s=\"%s\"" % ( key, value ) for key,value in self.attribs.iteritems() ] )
if len(str) > 0:
str = " " + str
return str
def __getitem__(self,key):
return self.attribs[key]
def __setitem__(self,key,val):
self.attribs[key] = val
def append( self, elt ):
self.children.append( elt );
return self
class Text:
def __init__(self, txt = "" ):
self.txt = txt
def __str__(self):
return self.txt
def __len__(self):
return len(self.txt)
class HTML (Container):
css = None
def __init__(self, h, b):
parts = []
if not h == None:
if not HTML.css is None:
h.append( STYLE(HTML.css) )
parts.append( h )
else:
if not HTML.css is None:
h = HEAD( [ STYLE(HTML.css) ] )
parts.append(h)
if not b == None:
parts.append( b )
Container.__init__(self, "html", {}, parts )
class JS (Container):
def __init__(self,jscript):
Container.__init__(self, "script", { 'language': "javascript",
'type': "text/javascript" },
[ Text(jscript) ] )
class STYLE (Container):
def __init__(self, cssStr):
Container.__init__(self, "style", { 'type': "text/css" }, [Text(cssStr)] )
class TITLE (Container):
def __init__(self, title):
Container.__init__(self, "title", {}, [ Text(title) ])
class BODY (Container):
def __init__(self, childs):
Container.__init__(self, "body", {}, childs )
class HEAD (Container):
def __init__(self, parts):
Container.__init__(self, "head", {}, parts )
class A (Container):
def __init__(self, href, children):
Container.__init__(self, "a", { 'href': href }, children )
class DIV (Container):
def __init__(self, parts, id = None, cssClass = None, cssStyle = None ):
attrs = {}
if id != None:
attrs['id'] = id
if cssClass != None:
attrs['class'] = cssClass
if cssStyle != None:
attrs['style'] = cssStyle
Container.__init__( self, "div", attrs, parts )
class P (Container):
def __init__(self, childs):
Container.__init__(self, "p", {}, childs )
class UL (Container):
def __init__(self, childs = None):
if childs == None:
childs = []
Container.__init__(self, "ul", {}, childs )
class LI (Container):
def __init__(self, childs):
Container.__init__(self, "li", {}, childs )
class HR (Container):
def __init__(self):
Container.__init__(self,"hr")
class FORM (Container):
def __init__(self, method = "get", children = None ):
if children == None: children = []
Container.__init__(self, "form", { 'method': method }, children )
class INPUT (Container):
def __init__(self, type, name, value = None, len = None):
attribs = { 'type': type,
'name': name }
if not value == None:
attribs['value'] = value
if not len == None:
attribs['size'] = len
Container.__init__(self, "input", attribs, [] )
class HIDDEN (Container):
def __init__(self, name, value):
attribs = { 'type': 'hidden',
'name': name,
'value': value }
Container.__init__(self, "input", attribs, [] )
class SELECT (Container):
def __init__(self,name,opts = None):
if opts is None: opts = []
attribs = { 'name': name }
Container.__init__( self, "select", attribs, opts)
class OPTION (Container):
def __init__(self, value, child = None):
if child is None: child = [ Text( str(value) ) ]
attribs = { 'value': value }
Container.__init__(self, "option", attribs, child )
class SUBMIT (Container):
def __init__(self, name, value):
Container.__init__(self, "input", { 'type': 'submit',
'name': name,
'value': value }, [] )
class CHECK (Container):
def __init__(self, name, value):
Container.__init__(self,"input", { 'type': 'checkbox',
'name': name,
'value': value } )
class H1 (Container):
def __init__(self, text):
Container.__init__(self, "h1", {}, [Text(text)])
class H2 (Container):
def __init__(self, text):
Container.__init__(self, "h2", {}, [Text(text)])
class BR (Container):
def __init__(self):
Container.__init__(self, "br")
class Null (Container):
def __init__(self, childs):
self.children = childs
def __str__( self ):
return [str(x) for x in self.childs]
class THEAD (Container):
def __init__(self, children):
Container.__init__(self, "thead", {}, children)
class TBODY (Container):
def __init__(self, children):
Container.__init__(self, "tbody", {}, children)
class TR (Container):
def __init__(self, children):
Container.__init__(self, "tr", {}, children)
class TH (Container):
def __init__(self, children):
Container.__init__(self, "th", {}, children)
class TD (Container):
def __init__(self, children):
Container.__init__(self, "td", {}, children)
class TABLE (Container):
def __init__(self, head, body, width = None, border = None ):
"""
@param head A list of header TRs
@param body A list of body TRs
"""
attribs = { 'cellspacing': 0,
'cellpadding': 2 }
if width is not None:
attribs['width'] = width
if border is not None:
border = '1'
attribs['border'] = border
Container.__init__( self, "table", attribs, [ THEAD(head), TBODY(body) ] )
class NID:
nidCounter = 0
def __init__(self):
self.val = NID.nidCounter
NID.nidCounter += 1
if __name__ == "__main__":
css = """
BODY
{
background-color: white;
color: black;
}
"""
doc = HTML( HEAD( [ TITLE( "Test Page" ), STYLE( css ) ] ),
BODY( [ DIV( [ P( [ Text("Foo-"), A( "http://asynchronous.org/", [Text("Bar")] ), Text("-Baz") ] ) ],
id="mainContent" ) ] ) )
print doc