Common Design base theme implementation notes
OCHAcommon_design is a Drupal 8 base theme, with a component library.
A sub theme is available for implementations.
Prod Demo site: https://web.brand.unocha.org
Dev Demo site: https://demo.commondesign-unocha-org.ahconu.org/
Table of Contents
Implementation
Base theme
Using composer, a tagged release of the base theme can be added to /themes/contrib. The version can be updated as needed to avail of improvements to the base theme. See its README for details.
Sub theme
There is a sub theme repo as a starting point for implementations. See its README for more info. All customisations should happen there. Overriding templates and using twig `extend` and `include` should provide a basic consistency for the Common header and footer. This is Drupal-specific and remains similar to D7 ocha_basic in site building approach (using Drupal regions and system menu blocks)
No dependency on jQuery
We have dropped the dependency on jQuery and thus dropped the Bootstrap dropdown plugin. We have replaced the Bootstrap dropdown plugin with a custom JS solution.
Javascript cd-dropdown component
cd-dropdown component is the vanilla JS replacement for Bootstrap’s dropdown plugin (used in ocha_basic Drupal 7 and jquery-dependent). It serves the same purpose and the behaviour from the end-user perspective is the same, but there are some notable differences in implementation.
The bootstrap plugin used classes on the parent element, and accompanying CSS rules to hide and show both the toggle button and the dropdown element as needed, which meant both elements were present in the markup at all times. Now, we use javascript to create and remove the toggle button as needed and no classes are added to the parent element. We use the attribute data-cd-hidden to apply the display rules.
Behaviour
All elements with the data-cd-toggable will be turned into a dropdown element and have a toggler button created, as a sibling element. The toggable element needs to be encapsulated as we rely on the previous sibling being the toggler button.
There is a script attached to the head to detect if javascript is enabled. This is to compensate for a similar detection from Drupal.js (adds .js class to the html element) which happens too late to prevent the flash of content as the dropdowns display on load and then are hidden.
There are two elements: the button (referred to in code as “toggler”) and the dropdown (referred to as “element”). The dropdown element needs to be included in the markup and requires the attribute of `data-cd-toggable`.
When one dropdown element is expanded while another is open and/or when the area outside the dropdown is clicked, all other dropdowns will collapse, unless a specific element is an exception or has `data-cd-toggable-keep` attribute. When the ESC key is pressed, the dropdown element is collapsed and focus is returned to its toggler button.
OCHA Services and the main menu template override provide good examples. All elements with `data-cd-toggable` attribute will be processed as dropdown elements, and toggler buttons will be created via setToggable, unsetToggable and updateToggable functions.
Additional attributes should be added to the dropdown element markup for the button icons and to create BEM classes for styling purposes. This is self-explanatory in the createButton function. Note also the data-cd-toggable-keep and data-cd-label-switch attributes to extend the default dropdown behaviour.
Minimum requirements
The following attributes should be added to the dropdown element’s markup:
- `data-cd-toggable` - the value is used for the Button label
- `id` - this is also used to set the aria-controls attribute on the toggler
- `aria-labelledby` - The value should correspond to the ID of a heading attribute eg. OCHA Services `<h2 id="cd-ocha-services-title">` and `<div aria-labelledby="cd-ocha-services-title"...>`
- `data-cd-component` - the component name, for namespaced BEM selectors (eg. cd-filters)
Optional
- `data-cd-logo` and/or `data-cd-icon` if either are required for the button
- `data-cd-logo-only` adds a class visually-hidden to the button label
- `data-cd-label-switch` for different labels depending on open/closed state
- `data-cd-focus-target` for adding focus to a specific element when dropdown is toggled (this works well with the Search component. Add the ID of the search input field and it will have focus when the dropdown is expanded)
- `data-cd-replace=”ID”` will replace the element with the given ID with a toggler. The element (eg: a link) serves as a fallback element for progressive enhancement when the cd-dropdown script cannot run.
Dropdowns on based on viewport dimensions
We listen to the resize event to register changes on the window object, and this enables us to create the toggler based on viewport dimensions. We use a CSS custom property --dropdown and set its value to true as default. For scenarios where the toggler should only be created on mobile (eg. Main menu) we set the --dropdown value to false at the desired breakpoint. A condition in updateToggable verifies the value of the CSS custom property and runs either setToggable or unsetToggable as appropriate.
For background on this technique, refer to https://justmarkup.com/articles/2017-01-24-handling-states-on-resize-using-css-custom-properties
Since CSS custom properties are not supported in IE11, we’ve needed to compensate with some additional display rules. These are wrapped in a media query that only IE11 will pick up and in time can be removed completely.
Drupal Menus and dropdown
We have added a separate function to deal with Drupal nested menus (Main menu is a good example). The function provides a default selector which we can change in an override javascript file if needed. This prevents the need to change the Drupal menu markup to suit the javascript code.
Component library
A variety of components in the Component library can cater for some generic or widely used content elements. The implementation of these will depend on context.
The Component library consists of individual components, made up of markup (.html), CSS, JS (sometimes) and a Drupal implementation (.html.twig) to display the component on the demo site. This requires Drupal Components module.
The component library can inform design and development decisions, and can demonstrate how elements work in specific contexts and in relation to each other, as well as their individual behaviour.
We encourage simple, performant, accessible and shareable design patterns.
Namespacing
- Twig namespacing is provided by Drupal and extended using the Components module
- Data attribute prefixes. The custom javascript for dropdown behaviour uses `data-cd-[attribute]` to prevent conflicts with 3rd party libraries.
- BEM with the cd-[component-name] convention for selectors.
- SVG icons with cd- prefix
Performance and Support
Drupal libraries can attach to templates so only loaded when the template is *Note the caching issue here
See Browsers to test and Supporting a global audience doc for our current commitments
Use `@supports` Feature queries with basic one column layout as default. Attention to displaying readable content as a priority as noted in the docs above.
Variables
For the Common Design Header and Footer styles, we use SASS and dart-sass to compile to CSS.
Custom components can be CSS or SASS. We currently use CSS custom properties to define colours in CSS components (IE11 does not support so attention to fallback colours is important)
BEM
See Drupal Best practices for background
Task management
NPM scripts are described in common_design README
Variants and Drupal-specific components
- Language switcher
Authenticated user UX
Most implementations will use the Social Auth Humanitarian ID module. This module has an option to redirect the HID login, and disable Drupal default log in forms.
When there are additional menu items, or menus, or widgets in the global header area, see CD user login and user actions doc for configuration (Drupal-specific) and design criteria (generic)
Packagist
We can include common_design base theme in sites that use composer using `composer require unocha/common_design` and optionally set release versions
https://packagist.org/packages/unocha/common_design
Local set up
Basic docksal config is included in the repo for local set up or docker stack set up with a local reverse proxy.
Snapshots: https://snapshots.aws.ahconu.org/commondesign/demo
Deployment
We can bump the version on the common-design-site composer.json `composer update unocha/common_design` and regenerate the composer.lock in a new PR that we merge to common-design-site develop branch.
To deploy a new version of the common_design base theme to either CD Prod, Feature or Demo sites, a release of the base theme or a feature branch can be created.
Deployments to the demo site are automatically triggered when the develop branch of common-design-site is updated.
Testing
See README for e2e tests.
There is a Jenkins job using ocha_vrt for VRTs
Versioning
Refer to Releases in common_design README
Print Styles
Using `@media print` should be sufficient in most cases, unless there is a specific reason to have a specific print.css stylesheet (eg. used by a PDF generation tool). Refer to _print.scss for basic rules
Drupal theme implementation and site build
Refer to Common Design checklist for guidance.
- Template overrides are preferred over preprocess functions to manipulate markup. However, for complicated markup like the search form it’s hard to avoid preprocess functions.
- Main menu should be placed in `header navigation` region
- Maximum 2 levels only, if dropdown menus are needed.
- Main menu parent items should be set to ‘Show as expanded’
There is a max number of top-level items before layout breaks (search and menu gets pushed below logo, although still usable)
- Search block needs to be placed in `header search` region
- Site branding block needs to be placed in `header logo` region
- User menu block needs to be placed `header top` region. Additional blocks can also be placed here, like the language switcher or another menu
- Footer menu block needs to be placed in `Footer navigation` region
- Social media links can be overridden in the sub theme template
- Copyright/disclaimer and CC logo is hardcoded
- Ocha Services is hardcoded and the first column can be overridden in the sub theme template.
See Inclusion and order of items arrived at by analytics and alphabetical for history.