Package: plone.theme
OverviewTools for managing themes in CMF and Plone sites.plone.themeThis package lets you mark the request with a “layer” interface conditional
on the currently selected skin (theme) in the portal_skins tool.Most Zope 3 “visual” directives, like <browser:page /> or <browser:viewlet />
accept a ‘layer’ attribute, which should point to an interface. Recall that a
view is a multi-adapter on (context, request). Most views are registered
so that the ‘request’ being adapted only needs to provide Interface. This
is equivalent to saying layer=”*”.By applying a marker interface to the request, and registering a view or
viewlet with this interface as the adapted ‘layer’, we can override a more
general view, or make a viewlet that is only shown for a particular layer.In the context of CMF and Plone, we’d like to tie the layer to the current
skin selection. We do that by name.What you have to doFirst, you should create a marker interface:>>> from zope.interface import Interface
>>> class IMyTheme(Interface):
...     """Marker interface for skins part of 'My Theme'
...     """Then, register this as a theme layer in ZCML:<interfaceinterface=”.interfaces.IMyTheme”
type=”zope.publisher.interfaces.browser.IBrowserSkinType”
name=”My Theme”
/>The title here must match the name of the theme/skin selection in
portal_skins.How it worksBehind the scenes, the <interface /> registration marks IMyTheme with the
“IInterface” IThemelayer, and registers IMyTheme as a utility named “My Theme”
and providing IBrowserSkinType.We do something to this effect in tests/tests.zcml.Let us define the “My Theme” skin selection:>>> from Products.CMFCore.utils import getToolByName
>>> portal_skins = getToolByName(layer['portal'], 'portal_skins')
>>> default_skin = portal_skins.getDefaultSkin()
>>> skin_path = portal_skins._getSelections()[default_skin]
>>> portal_skins.addSkinSelection('My Theme', skin_path)In tests/tests.zcml we have registered two version of a view called
@@layer-test-view. One, for the default skin layer, simply outputs “Default”.
The other outputs “My Theme”.Before we turn on the skin, we will get the default view.>>> from plone.testing.z2 import Browser
>>> browser = Browser(layer['app'])>>> browser.open(layer['portal'].absolute_url() + '/@@layer-test-view')
>>> from __future__ import print_function
>>> print(browser.contents)
Default
...However, if we turn the skin on, we should see the effects of the marker
interface being applied.>>> portal_skins.default_skin = 'My Theme'
>>> import transaction
>>> transaction.commit()>>> browser.open(layer['portal'].absolute_url() + '/@@layer-test-view')
>>> print(browser.contents)
My Theme
...And if we switch back:>>> portal_skins.default_skin = 'Plone Default'
>>> transaction.commit()>>> browser.open(layer['portal'].absolute_url() + '/@@layer-test-view')
>>> print(browser.contents)
Default
...Changelog4.0.1 (2023-10-07)Internal:Update configuration files.
[plone devs] (cfffba8c)4.0.0 (2023-04-27)Breaking changes:Drop Python 2 and Plone 5.2 support.
[gforcada] (#6)Internal:Update configuration files.
[plone devs] (2a4ba395)3.0.7 (2020-04-22)Bug fixes:Minor packaging updates. (#1)3.0.6 (2018-06-20)Bug fixes:Tests run on Python 3 [ale-rt]3.0.5 (2018-04-04)Bug fixes:Handle case where we get no skinname in Zope4.
[pbauer]3.0.4 (2018-03-10)Bug fixes:Minor administrativa fixes.
[gforcada]3.0.3 (2017-07-03)Bug fixes:removed unittest2 dependency
[kakshay21]3.0.2 (2017-02-05)Bug fixes:Fixed test when using Zope 4.  [maurits]3.0.1 (2016-11-17)Fixes:Remove ZopeTestCase traces.
[gforcada]3.0.0 (2015-06-10)3.x is plone 5 only
[vangheem]2.1.4 (2015-04-28)Remove dependency on CMFDefault
[tomgross]2.1.3 (2015-03-27)Test layer is testing layer.
[bloodbare]2.1.2 (2015-03-21)Move tests from PloneTestCase to plone.app.testing.
[sdelcourt,timo]2.1.1 (2014-03-02)Remove hard dependency on CMFDefault.
[davisagli]2.1 - 2011-05-12Update to import BeforeTraverseEvent from zope.traversing instead of
zope.app.publication.
[davisagli]Add MANIFEST.in.
[WouterVH]2.0 - 2010-07-18Update license to GPL version 2 only.
[hannosch]2.0b2 - 2010-03-05Protect against running multiple times. This can happen when using ++skin++
traversers or VirtualHostMonster.
[wichert]2.0b1 - 2010-01-02Fix an error introduced by my previous adjustment. If a skin layer
extending the default layer was used (which is typical), then the
default layer would end up with higher precedence than browser
layers not extending the default layer.
[davisagli]2.0a2 - 2009-11-13Inherit from the CMFDefault layer again, for compatibility with products
that depend only on CMF but are also usable within Plone, and register
views to the CMFDefault layer.
[davisagli]2.0a1 - 2009-04-05Avoid inheriting from the CMFDefault browser layer and rather define our
own. We don’t have anything in common with the CMFDefault layer.
[hannosch]Declare test dependencies in an extra.
[hannosch]Specify package dependencies.
[hannosch]1.1 - 2009-04-04Make sure the theme layer takes precedence over other browser layers.
[davisagli]1.0 - 2007-08-15First stable release
[wichert]