UI Frameworks & Libraries
UI Frameworks & Themes
A UI Framework pulls together one or more UI Libraries and compiles them into the CSS, JavaScript, and component views that style a site. Sites and pages point at a framework through a theme, so changing the look of a site, or standing up a second brand, is a matter of pointing at a different theme rather than rebuilding components.
Framework structure
UI Frameworks live under /etc/ui-frameworks/. A managed framework is a root node whose children are its versions; each version node carries the vendor-library references and one or more themes:
/etc/ui-frameworks/my-ui-framework/ # kes:ManagedUiFramework (root)
versions/
1.0.0/ # kes:UiFramework (a version)
css/ # framework-level styles
js/ # framework-level scripts
themes/
default/ # kes:Theme
Sites and pages bind to a framework by setting kes:theme on their jcr:content node, for example /etc/ui-frameworks/my-ui-framework/versions/1.0.0/themes/default.
kes:ManagedUiFramework root with a versions/ folder, the root itself is a kes:UiFramework that carries kes:vendorLibraries and kes:uiFrameworkCode directly.Creating a UI Framework
Create the framework folder and a .content.xml for the root node. The root is a kes:ManagedUiFramework:
| Property | Type | Req | Description |
|---|---|---|---|
jcr:primaryType | Y | Must be kes:ManagedUiFramework | |
jcr:title | String | Rec | Name shown in the authoring dialog |
kes:uiFrameworkCode | String | System code for the framework. Keep it equal to the folder name, or omit it and let the folder name apply. Set it here on the root, not on version nodes. |
<jcr:root xmlns:jcr="http://www.jcp.org/jcr/1.0"
xmlns:kes="http://kestros.io/kes/1.0"
jcr:primaryType="kes:ManagedUiFramework"
jcr:title="My UI Framework"/>
uiFrameworkCode lives matters. For a managed framework the code is read from the root node; the property on a version node is ignored. If the root code doesn’t match how the framework is referenced, the compiled theme CSS request returns a 400 (Failed to retrieve UiFramework) and pages render unstyled with no page error. Keeping the code equal to the folder name avoids this.Versions and themes
Frameworks are versioned. Under the root, create a version folder and a default theme: versions/1.0.0/themes/default/. The version and theme folders each need a .content.xml; the intermediate themes folder does not.
Version node (kes:UiFramework):
| Property | Type | Req | Description |
|---|---|---|---|
jcr:primaryType | Y | Must be kes:UiFramework | |
jcr:title | String | Rec | Name shown in the authoring dialog |
kes:vendorLibraries | String[] | Rec | The UI Libraries this framework pulls in (see format below) |
jcr:description | String | Optional description of the framework |
kes:vendorLibraries reference format. Reference each library by its JCR node name (not its library code, which can differ). Unversioned: [my-library]. Versioned: [my-versioned-library/0.0.1] (node name, a slash, then the version).Theme node (kes:Theme):
| Property | Type | Req | Description |
|---|---|---|---|
jcr:primaryType | Y | Must be kes:Theme | |
jcr:title | String | Rec | Name shown in the authoring dialog |
Custom CSS and JavaScript
Styling shared across every theme belongs at the framework version level: versions/1.0.0/css and versions/1.0.0/js, siblings of themes. The version node is itself a UI Library, and its compiled output appends the framework’s own CSS/JS after the UI Libraries it references.
A theme can carry its own CSS and JavaScript as well, for styling specific to that theme, layered on top of the shared framework styles.
js folder.Framework-provided component views
A UI Framework can supply its own component views at {component}/{uiFrameworkCode}/{frameworkVersion}/. Use this to keep site- or brand-specific markup with the framework that owns it:
- Generic, reusable views → put them in a UI Library.
- Site- or brand-specific views → put them in that site’s UI Framework (which lives in the site’s
applicationmodule and references the generic libraries viakes:vendorLibraries).
HTL templates
A framework or library can expose reusable HTL templates: add a templates folder and any .html file in it is picked up automatically and made available to component views. See Writing HTL for template syntax.
For example, the Font Awesome vendor library defines a reusable icon template in its templates folder. The data-sly-template statement names the template and declares the parameters it accepts:
<template
data-sly-template.fontAwesomeIcon="${ @ iconClass, additionalClasses}"
data-title="Base Icon">
<i class="${additionalClasses} ${iconClass}"></i>
</template>
A component view loads a template file with data-sly-use and invokes one of its named templates with data-sly-call. This section view loads the shared includes.html and calls its contentArea template (unrelated attributes trimmed). These two snippets are independent real-world examples: the first shows the define half (declaring a template), the second shows the call half (using and invoking a template), so the template named above is not the one invoked here:
<sly data-sly-use.includes="/libs/kestros/commons/components/includes.html"/>
<div class="${section.inlineVariations}" ...>
<sly data-sly-call="${includes.contentArea}"/>
</div>