################################################################################# # Example of using patterns to change the appearance of a webform. #from twisted.application import internet, service #from twisted.web import static from zope.interface import implements from nevow import rend from nevow import url from nevow import loaders from nevow import tags as T from formless import annotate from formless import webform ################################################################################# # This beasty defines how I want the form to look. It's a table (eek!). # webform looks for patterns to use when rendering parts of the form and fills # slots with key information. # # Key patterns are: # freeform-form -- the form itself, mostly just the structure # argument -- the pattern to use for arguments when nothing better # is found # argument!!fo -- the pattern to use for the 'fo' argument # # Inside the patterns the following slots are filled: # freeform-form: # form-action -- action attribute, where the form will be posted # form-id -- id of the form # form-name -- name of the form # form-label -- form label, extracted from the docstring # form-description -- description, also extracted from the docstring # form-error -- "global" error # form-arguments -- insertion point for the arguments' HTML # argument: # label -- label # input -- the form element (input, textarea, etc) # error -- error message (if any) # description -- description of argument # # Note that you do not have to provide slots for all of the above. For # instance, you may not want to display the descriptions. # # Chances are that this block of text would be in a disk template or # perhaps defined using stan in a taglib module. FORM_LAYOUT = loaders.xmlstr( """
""").load() ################################################################################# # ISomething and Page are just something to test the form rendering on. class ISomething(annotate.TypedInterface): def doSomething( ctx = annotate.Context(), fee = annotate.String(required=True, description="Wee!"), fi = annotate.Integer(description="Tra-la-la"), fo = annotate.Text(), fum = annotate.String(), ): """Do Something Really Exciting Normally you would put a useful description of the interface here but, since the inteface is useless anyway, I cannot think of anything useful to say about it. Although ... did I mention it is useless?""" doSomething = annotate.autocallable(doSomething) class Root(rend.Page): """Render a custom and normal form for an ISomething. """ implements(ISomething) addSlash = True child_webform_css = webform.defaultCSS def render_normalForm(self, ctx, data): return webform.renderForms() def render_customForm(self, ctx, data): return webform.renderForms()[FORM_LAYOUT] def doSomething(self, ctx, **kwargs): print '***** doSomething called with:', kwargs docFactory = loaders.stan( T.html[ T.head[ T.title['Example :: Custom Form Layout'], T.link(rel='stylesheet', type='text/css', href=url.here.child("webform_css")), ], T.body[ T.h1['Custom'], render_customForm, T.h1['Default'], render_normalForm, ] ] ) #application = service.Application('hellostan') #webServer = internet.TCPServer(8080, appserver.NevowSite(Root())) #webServer.setServiceParent(application)