Dynamic views
Plone 2.1 adds the display menu, which can be used to set a display of an object on a per-instance basis. RichDocument uses this functionality in two ways:
- It tells Plone that a RichDocument can be used as a default-page for a folder. That is, the user can go to a folder, select "Choose content item as default view" and select a RichDocument to represent that folder.
- It lets users select different layouts for how their RichDocuments will be displayed - as a plain document, with a floating first image, or with a box of image thumbnails - and more views can be added by third party products or an administrator.
Telling Plone that a RichDocument is an acceptable default-page type is easy. In Extensions/Install.py, we simply have to add RichDocument to the list of default_page_types in 'portal_properties/site_properties':
# Add to default_page_types
defaultPageTypes = list(siteProperties.getProperty('default_page_types'))
if 'RichDocument' not in defaultPageTypes:
defaultPageTypes.append('RichDocument')
siteProperties.manage_changeProperties(default_page_types = defaultPageTypes)
Letting RichDocument make use of the display menu itself is more interesting. The magic happens in CMFDynamicViewFTI, which is an extension of the standard CMF Factory Type Information class to allow different view methods to be defined.
If you look in portal_types, you will probably see some blue and some yellow icons. The yellow ones use CMFDynamicViewFTI. Take for example the standard Plone Folder type. If you view this FTI, you will see two fields at the bottom of the Properties tab:
- Default view method
- The id of a page template that will be used as the view for new objects by default. This is probably
folder_listing. - Available view methods
- This is a list of templates that will be selectable from the
displaymenu. In a standard installation, you will sefolder_listing,folder_tile_view,folder_tabular_viewandatct_album_view. Note that the names you see in thedisplaymenu are taken from the (possibly translated) titles of these page templates, which is defined e.g. infolder_listing.pt.metadata.
To use CMFDynamicViewFTI in RichDocument, we have to do a few things:
- Declare support for the
ISelectableBrowserDefaultinterface found in CMFDynamicViewFTI. We get this interface and the standard implementation fromBrowserDefaultMixin, defined inCMFDynamicViewFTI/browserdefault.py, by way ofATDocument, which already mixes in this class and declares support for the interface. - Set
default_viewandsuppl_viewson our class to define the default view and any additional views to be available. Note that this can be changed later throughportal_types. We do this in 'content/richdocument.py':default_view = 'richdocument_view' suppl_views = ('richdocument_view_preview', 'richdocument_view_float') - Write these page templates! In RichDocument, we have
skins/RichDocument/richdocument_view.pt, the default, as well asrichdocument_view_preview.ptandrichdocument_view_float.pt. - Migrate to CMFDynamicViewFTI by calling
migrateFTIs()inInstall.py. Note that calling this method will migrate the FTIs for all the types defined in the product. This is not normally a problem, so long as all types mix inBrowserDefaultMixin(all the ATContentTypes classes do, obviously), because CMFDynamicViewFTI is a direct extension of the standard CMF FTI class.:migrateFTIs(self, product=PROJECTNAME)
Manipulating view methods of existing content types:
If you want to register a custom view at an existent content type (e.g. Folder) you can do this by editing default_views of it's FTI:
folderFTI = portal.portal_types.Folder folderFTI.view_methods = folderFTI.view_methods + ('custom_view',)