Custom dynamic properties

Purpose

Page authors can use custom dynamic properties to style components or elements based on the state of the application without relying on low level functionality that cannot be guaranteed to work across devices. Custom dynamic properties are defined using the @ui|dynamic-property CSS rule.

The following restrictions apply:

Exported Features

cf2:ui.DynamicProperties#Custom

Imported Features

cf2:Property

Defining dynamic properties

The @ui:dynamic-property rule defines a custom dynamic property. The syntax of the property is as follows:

@ui|dynamic-property {
  name: <property-name>;
  type: <property-type>;
  [<qualified-pseudo-class>: <property-value>;]{2,}
}

Where:

property-name

Specifies the name of the client-side observable property that contains the state of the dynamic property. It must start with cx and must match the general pattern for observable property names.

property-type

Specifies the type of the client-side observable property and must be one of:

  • boolean - the client-side property is of type boolean. The dynamic property must have two states, and the values for the states are specified as either of the following CSS identifiers: 'true'; 'false'. On the client they are represented as values of the client-side equivalent of a boolean type, e.g. in JavaScript they are of type boolean and correspond to the JavaScript values 'true' and 'false', respectively. The following shows an example of defining a boolean property that indicates whether the device is in portrait mode or not.

    @namespace my "http://my.com/";
    
    @ui|dynamic-property {
      name: cx-portrait;
      type: boolean;
      my|portrait: true;
      my|landscape: false;
    }
  • string - the client-side property is of type string. The dynamic property can have two or more states, and the values for the states are represented as a CSS string. On the client they are represented as values of the client-side equivalent of a string type, e.g. in JavaScript they are of type String. The following shows an example of defining a string property that indicates whether the device is in portrait mode or not.

    @namespace my "http://my.com/";
    
    @ui|dynamic-property {
      name: cx-orientation;
      type: string;
      my|portrait: "portrait";
      my|landscape: "landscape";
    }
  • integer - the client-side property is of type integer. The dynamic property can have two or more states, and the values for the states are represented as a CSS integer. On the client they are represented as values of the client-side equivalent of an integer type, e.g. in JavaScript they are of type Numeric, with the restriction that they must be integer values, i.e. have no decimal point, or fractional part. The following shows an example of defining an integer property that indicates whether the device is in portrait mode or not.

    @namespace my "http://my.com/";
    
    @ui|dynamic-property {
      name: cx-portrait;
      type: integer;
      my|portrait: 1;
      my|landscape: 2;
    }
qualified-pseudo-class

The name of the pseudo-class. It must be qualified by a prefix associated with a custom namespace.

property-value

The value that is stored in the client-side observable property to represent the pseudo-class. The values must be of the type specified in the property-type and must be unique within the dynamic property definition.

Note:

In order to access a custom pseudo-class of an element, the pseudo-class must be set for that element on the initial XDIME page. Otherwise MCS will not create the pseudo-class for the selected element and as a consequence a custom JavaScript code or a cf2:on element may try to use the non-existent pseudo-class.

Default state

The default state is the first pseudo-class in the dynamic property definition.

Pseudo-classes

The pseudo-classes are specified in the dynamic property definition along with the corresponding value of the client-side property that represents the state. They must be qualified by a prefix that has been bound to a custom namespace.

Observable property

The name of the observable property is specified in the dynamic property definition. It must follow the JavaScript naming conventions and be prefixed with cx; it is an error if it is not.

A custom dynamic property is used on a presentation element, i.e. one whose appearance is affected by styles, if either of the following are true:

The observable property is set to the client-side value that corresponds to the initial state. If no such state is specified, then it is set to the value associated with the default state, which is the first pseudo-class specified in the dynamic property definition.

Initial state attribute

The initial state of a property is set on an element using the ui:initial-state or initial-state attributes. The former must be used on XHTML 2 and XForms elements, the latter must be used on CF2 and other MCS extension elements.

Example

<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/2002/06/xhtml2"
  xmlns:mcs="http://www.volantis.com/xmlns/2006/01/xdime/mcs"
  xmlns:cf2="http://www.volantis.com/xmlns/2009/07/cf2"
  xmlns:ui="http://www.volantis.com/xmlns/2009/07/cf2/ui"
  xmlns:my="http://my.com/">
  <head>
    <title>Custom dynamic properties</title>
    <style type="text/css">
      @namespace my "http://my.com/";
      
      @ui|dynamic-property {
        name: cx-select;
        type: string;
        my|default: "default";
        my|front: "front";
      }
     
      .box {
        width: 190px;
        border: 1px solid #BFBFBF;
        background-color: white;
      }
      
      .box:my|front, .box:my|front {
        background: yellow;
      }
    </style>
  </head>
  <body>
    <div>
      <ui:button>
        <span>| Select Box 1 |</span>
        <cf2:on event="cf2:activate" set="box1#cx-select" string="front"/>
        <cf2:on event="cf2:activate" set="box2#cx-select" string="default"/>
      </ui:button>
       
      <ui:button>
        <span>| Select Box 2 |</span>
        <cf2:on event="cf2:activate" set="box1#cx-select" string="default"/>
        <cf2:on event="cf2:activate" set="box2#cx-select" string="front"/>
      </ui:button>
    </div>
    <div>
      <div id="box1" class="box" ui:initial-state="my:front">
        <p>Box 1</p>
      </div>
      <div id="box2" class="box">
        <p>Box 2</p>
      </div>
    </div>
  </body>
</html>

Related topics