I recently got my simple widget example working (thanks Kevin!).   I'll
share my simple example here and try to explain it.

Start with creating a form. (I did this in a seperate file since I
didn't want to clutter up controllers.py)

myForms.py:
createUserForm = widgets.TableForm(widgets=[
                widgets.TextField("userId",
validator=validators.PlainText()),
#                widgets.TextField("userId",
validator=validators.PlainText(not_empty=True)),
                widgets.TextField("emailAddress",
validator=validators.Email()),
                widgets.TextField("emailAddress"),
                widgets.TextField("age", default=0,
                                validator=validators.Int())])

That is your widget table form which you'll use in controllers.py:

    @turbogears.expose( html="my.templates.createUser")
    def createUser( self):
        return dict(message="", form=myForms.createUserForm)

By passing form=myForms.createUserForm you are making form accessible
to the kid template. Later in the kid timplate you can simply call
form.insert(...)

You'll probably want a way to save that data too. (I've made it a
seperate function for simplicity.

Note that I've set inputform=myForms.createUserForm, this tells TG that
I'm using that form to validate.
    @turbogears.expose( html="my.templates.createUser",
inputform=myForms.createUserForm)
    def createUserSave( self, userId='', emailAddress='', age='',
submit=''):
        # Check for validation errors
        if cherrypy.request.form_errors:
            return dict(message="", form=myForms.createUserForm)

        # The user doesn't exist. Create the user
        hub.begin()
        u=TG_User( userId=userId, emailAddress=emailAddress,
displayName=userId, password="passwd" )
        g=TG_Group.byGroupId("admin")
        u.addTG_Group(g)
        hub.end()
        raise cherrypy.HTTPRedirect(turbogears.url("/login"))


So now we just have to use this form in the kid template

createUser.kid
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
          "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd";>
<html xmlns="http://www.w3.org/1999/xhtml";
      xmlns:py="http://purl.org/kid/ns#";
      py:extends="'master.kid'">

  <head>
    <meta content="text/html; charset=UTF-8"
          http-equiv="content-type" py:replace="''"/>
    <title>Create User</title>
  </head>

  <body>
    <h2>Create Account</h2>
    <p>${message}</p>
    <div py:replace="form.insert(action='createUserSave')"/>
  </body>
</html>

The magic line is  <div
py:replace="form.insert(action='createUserSave')"/>.

This will pretty much work how you'd expect. If the age is not a valid
number, it will return you to the input form with the correct error
message. I hope I got this all correct and explained it in a way that
isn't too twisted.

Caveat Emptor:
I have found a bug
widgets.TextField("userId",
validator=validators.PlainText(not_empty=True))
causes an error. I'm not sure why inserting not_empty=True does this,
but the insert code for the widgets doesn't like it. I've also not been
able to get the validdators.Email() to work as a widget validator
either. :(

Anyway, that should do it.

I was thinking that it might be nice to generate a list of useful
widgets that should be created. I was thinking something like
changePasswordForm - old password, new password field 1, new password
checked against field 1
loginForm - username, password
creditCardForm - card number, expiration

Since these are common to many web applications.

A more advanced widget set my be a shopping cart...

Anyway, just a thought.

Lucas.-

Reply via email to