Hi Paul,

Thanks a lot for this!

You can override the updateActions method and modify the css after the
buttons are created.  As you may have read, buttons are like schema
fields, and actions are like the widgets for a schema field.  So to
modify the appearance of a button, you have to actually modify the
action:

@button.buttonAndHander("My Button", name="myButton")
def handleMyButton(self, action):
    print "handling my button"

def updateActions(self):
    super(MyForm, self).updateActions()
    self.actions["myButton"].addClass("my-custom-css-class")

Nice one! That works.

 - Some fields on the form are provided by the content item. Others can come
from other schemata. There will be adapters from the context to these
interfaces. How do it up so that z3c.form uses the appropriate adapter to
read and write values, including in the add form?

In the add form, it is up to you to handle the data input, by
implementing the create and add methods.

Ah right. I guess I should be able to do that. I had guessed that form.applyChanges() could do something implicit, but I guess that's a bit too much to ask.

As for the edit forms, I'm
not entirely sure about this but I believe the form framework will
just do the right thing.  i.e. you might say:

fields = field.Fields(IMyInterface)
fields += field.Fields(IMyOtherInterface)

Okay, I'll try that. I actually don't know which interfaces will be used until runtime (i.e. the form looks those up dynamically), but I'm guessing I can build that dynamically anyway.

And it will automatically try to adapt the context to the interface
from which the field was defined.  An alternative way which will
definitely work (even if you don't have adapters) is to use groups:

class MyOtherInterfaceGroup(group.Group):
    fields = field.Fields(IMyOtherInterface)
    def getContent(self):
        # do whatever you have to do to get something implementing
IMyOtherInterface, adaptation or otherwise
        return myInterfaceToOtherInterfaceAdapter(self.context) #even
a direct call to a specific adapter

class MyForm(group.GroupForm):
    fields = field.Fields(IMyOtherInterface)
    groups = (MyOtherInterfaceGroup,)

This is essentially the poor man's version of having a subform.  It's
also a great way to fake "object widgets" when one of the fields of
IMyInterface is of type zope.schema.Object.

Interesting... can you elaborate on that (I may need it for something else)?

 - I'd like to group widgets together into fieldsets. A fieldset may contain
widgets from multiple interfaces. All fieldsets will be on the same form, in
different <fieldset /> tags. Should I look to use groups for this? Subforms?
Or something else?

I'd recommend just writing your own template.  I've found that the
templates in z3c.formui can only take you so far, and are best used as
prototyping tools and reference documents.  Of course, you can always
reuse many of the macros, especially when it comes to displaying
widget error messages.

Yeah, I'm happy enough to do that. Right now, I'm using a Ploneish template from plone.z3cform, and I may yet try to generalise this and extend that instead of my own code, but I'd expected to hack some TAL.

However, I'd like to know if z3c.form has some support for grouping fields from across multiple adapters/schemata interfaces and marking them up so that I could render the fields in the right order, in the right logical groupings.

I'm guessing z3c.form groups do that, of course, but it's not clear to me whether it's appropriate to use them for this kind of thing, especially since the logical groupings and field ordering will only be calculable at runtime.

Cheers,
Martin

--
Author of `Professional Plone Development`, a book for developers who
want to work with Plone. See http://martinaspeli.net/plone-book

_______________________________________________
Zope3-users mailing list
Zope3-users@zope.org
http://mail.zope.org/mailman/listinfo/zope3-users

Reply via email to