[drupal-devel] Rewriting use of forms in Drupal
scott at 4th.com
Fri Jun 3 12:33:51 UTC 2005
On Friday 03 June 2005 07:09, Gerhard Killesreiter wrote:
> > For example, my recipe module has a table in it. Each row of that
> > table has 3 input fields in it. I dread to think what the code looks
> > like to generate that with an array of controls.
> I currently have no solution for this. As my proposal is now, you'd need
> to tell your theme what to do with the individual fields. An idea is to
> have form() (which would become theme_form()) call a "form layout"
> hook. Hmmmm.
Take a page from the proverbial "Book of Java" -- delegate form layout into a
layout management object.
In Java, you pick a layout manager class for your form. That class defines the
overall algorithm of how fields will be laid out, e.g., linear vertical, linear
horizontal, grid of MxN cells, etc. (there are more complex layouts avaiable).
Within each of these layout managers, one can assign a "weight" and an ordering
number to each cell. In Java, the "weight" defines the proportion of space that
is allocated to the cell, not its position relative to the others -- the order
of cells is set by their index order.
The *real* versatility of this comes from the fact that the layout managers
can be nested. In other words, I can do a linear vertical array where the top
cell is a single field, the second cell down is a horizontal array of three
fields in a sub-layout, the third cell down is a 2x2 grid with 65%/35%
left/right proportion and 50%/50% top/bottom proportion, and so on. The size
(again, "weight" in Java parlance) and ordering factors are applied at each
nested level of layout manager, and they can be nested to arbitrary depth.
At each level of nesting, the layout manager in charge simply believes it is
layout out one or more fields. Some fields, however, may actually be layout
managers. This is, if you will, simply a hyper-extension of Drupal's existing
The size ("weight") and ordering parameters given to the layout managers with
each contained field are advisory rather than mandatory. The layout manager
makes a "best effort" to deliver what the programmer wants, based on
constraints of the environment such as screen size.
To bring this model into Drupal terms, what you would have is this:
* Drupal core defines layout.module which establishes the API calls for how
layout managers relate to one another, to the application, and to themes.
* layout.module "knows" how to load one or more *.layout (for example) PHP
files that each define a single layout manager type ("grid", "linear",
etc.). This is akin to the architecture of flexinode.module or our theme
* Several basic core layouts are provided as part of Drupal itself, to
provide for all the layout cases we have today in mainstream modules.
Contributors can put additional .layout files in with their module
directories, if they need something heavily customized. Or someone can
create a really slick layout manager and contribute it standalone.
* At runtime, the application programmer builds the lowest level layout objects
and then nests them into higher level layouts, until the full form is defined
(note: for most simple cases, there would be no nesting, just a single layout
with all the fields inserted linearly). Each layout cell is filled with
themeable HTML generated by today's existing form_*() functions or custom
code, or themeable HTML generated by a sub-layout.
* The layout modules take each of their cells' HTML contents and "wrap" them in
the surrounding container tags, with appropriate CSS class and/or ID
attributes, and generate the final HTML for the form. The class and ID
names are standardized as part of the published API spec for layout modules.
Layouts also get one uniquely-named class that they wrap (using "<div>",
probably) around their entire output, and another class that they wrap
around each of their cells' contents. This allows minimal CSS files for the
use of layout modules themselves.
* The full form HTML is passed to the theme engine as it is today. The theme
defines how that form fits into the page and also the CSS for all the class
and ID attributes.
* Since the CSS (if any) from the layout is outside the CSS from the theme,
the theme has the "final say" in how things are laid out, but if it is silent
on a particular feature, the CSS from the layout manager comes through.
This is admittedly a rough proposal, but the general philosophy has been tried-
and-true in the Java world for close to a decade. I've done quite a bit of
coding in Java and have found the system to be great for giving me control of
how fields are placed relative to one another, without getting bogged down in
the details of pixel counts and screen size.
Scott Courtney Drupal user name: "syscrusher" http://drupal.org/user/9184
scott at 4th dot com Drupal projects: http://drupal.org/project/user/9184
More information about the drupal-devel