This is the first post in a short series about the ideas, trials and tribulations of my first theme product. I’ll be posting the whole story in one place when the series is complete.
I’m working on a large-scale inventory management system built as a series of Plone content types. It’s primary focus is on scientific research labs in a university setting. This means we’ll have a lot of individual labs with specific needs using the system in different ways. I took on the task of building a generic, centralized theme that each lab theme can extend. I wanted to define a specific look for the system, but also allow instances to be tailored for end users.
The first step was to build a mockup in a graphics program, and show it around to my colleagues for review.
I produced this in Inkscape. It’s heavily based on the stock Plone theme, but things are re-arranged a bit. I could have gone to more extremes in moving things around, but at this point what I could do with the viewlets and portlets is pretty much unknonwn. No sense in pushing the envelope when you haven’t written the letter yet :)
I want the theme to be customizable in simple ways, and easily extended, so I want to place strong emphasis on CSS for the look and feel, and utilize Plone conventions to control the regions that are being styled.
By studying the default Plone theme and comparing it to my design, I was able to break down what the differences into a replacement header, with existing components rearranged within it. I’d then hide the existing header elements.
This accomplishes a couple of things:
- The theme stays flexible. Theoretically, the viewlets in my new header can be controlled by the @@manage-viewlets view, so they can be changed as needed after the theme is installed (although I’ll probably want to keep the changes in the theme product)
- Maximizes code re-use. By re-styling and re-organizing the stock viewlets, I can avoid re-implementing the stock viewlet code. This should help keep the theme future-proof.
I’m (still) not sure if this is the best possible approach, but I think it’s flexible enough to allow a site to fall back to plone defaults in a worst-case scenario.
Now that I’ve got my layout and an idea of how this will happen, I needed to build the theme product.
The Plan: The Lone Viewlet
After reading the reference materials I had available (primarily Professional Plone Development and Web Component Development with Zope 3) on viewlets and the
provider prefix, I came up with a theory. There weren’t many examples of viewlet manager creation; most of the information I had was focused on overriding existing viewlets. I didn’t want to stick my neck out too far, so a lone viewlet, possibly overriding and existing viewlet, would be the way to go.
I thought that because viewlets were registered providers, I could easily get the stock plone viewlets I wanted to re-organize to show up in my new viewlet by simply using the
provider prefix in TALES expressions in my page template.
This was a bad plan. When I started testing my theory, it became apparent that viewlets are only accessible from within their viewlet managers. Worse, it seemed that only viewlet managers are presentable using the
During the process of putting this series together, I’ve come to the realization that this is due to a silly bug in Plone’s viewlet base. More on this later.
The Other Plan: DIY Viewlet Manager
If a hack won’t work, you just have to do things “right”. :P Apparently, the correct way to reuse existing viewlets is to create your own viewlet manager and assign those viewlets to it using ZCML. You can rename the viewlets if you’d like, or extend the viewlets if you need to, but it all revolves around creating your own viewlet manager.
I went down this path twice. The first time I hadn’t seen this: http://plone.org/documentation/manual/theme-reference/elements/viewletmanager. Or if I had, I didn’t look at it critically enough.
I built a viewlet manager using Web Component Development with Zope 3, and it just wouldn’t show up in Plone’s viewlet manager.
What I didn’t know until I was turned on to the tutorial, was that Plone has to specifically render each viewlet manager it wants in
main_template (which is the core template that Plone uses to display everything). There’s a slight reference on the page about moving viewlet managers about how to move a manager in your own product. This was the break I needed. All I had to do was edit
main_template to get my viewlet manager to stick.
I’m not happy with this, though. I shouldn’t have to duplicate a core piece of Plone functionality just to add one little additional piece of functionality. Still a small price to pay for total control :).