Creating custom QML components in BB10 Cascades

December 10, 2012 Ergin Babani

Note: This tutorial was written for BB10 Cascades. You can get the BB10 Cascades NDK and Simulator from the Cascades website.

BB10 Cascades supports the creation of custom qml components. This is a powerful feature allowing creation of components that are reusable in other qml documents. In this blog post I will describe how to create a custom ShadowLabel component.

A ShadowLabel will be a Label whose text has a shadow. We want our ShadowLabel to behave as close to the native Label as possible, with some additional setting the shadow colour and weight. In this example I won’t implement all the Label properties, but just the most commonly used ones.

We will start by creating a ShadowLabel.qml file with an empty container.

import bb.cascades 1.0

Container {
}

To create the shadow effect on the text we will use two Labels superimposed on each other, with the shadow Label being shifted down by some pixels. One way to do this is to place both labels in a Container with a DockLayout. The DockLayout allows elements to overlap each other. We want to shift the shadow text down by some amount, but the Label does not support padding. Instead we will put the shadow Label inside a Container and add top padding to that.

import bb.cascades 1.0

Container {
    id: root

    layout: DockLayout { }

    Container {
        topPadding: 1
        horizontalAlignment: HorizontalAlignment.Center
        verticalAlignment: VerticalAlignment.Center
        Label {
            id: shadow
        }
    }
    Label {
        id: main
        horizontalAlignment: HorizontalAlignment.Center
        verticalAlignment: VerticalAlignment.Center
    }
}

One of the goals of ShadowLabel is to have an interface as similar to Label as possible. To satisfy this requirement, we will need to implement the commonly used Label properties on our root container, and use Property Binding to update our main Label and shadow Label.

import bb.cascades 1.0
Container {
    id: root
    layout: DockLayout { }

    property string text;
    property variant shadowColor
    property int shadowWeight
    property bool multiline
    property TextStyleDefinition textStyle

    Container {
        topPadding: root.shadowWeight
        horizontalAlignment: HorizontalAlignment.Center
        verticalAlignment: VerticalAlignment.Center
        Label {
            id: shadow

            multiline: root.multiline
            enabled: root.enabled
            text: root.text

            textStyle {
                base: root.textStyle.style
                color: root.shadowColor
            }
        }
    }

    Label {
        id: main
        horizontalAlignment: HorizontalAlignment.Center
        verticalAlignment: VerticalAlignment.Center

        multiline: root.multiline
        enabled: root.enabled
        text: root.text

        textStyle {
            base: root.textStyle.style
        }
    }
}

Notice that we use the same property names as in the regular Label. A feature of Property Binding is that whenever a property is updated, the update is propagated to any other properties bound to it. This ensures that whenever someone updates the ShadowLabel property the main Label and shadow Label bound properties will also update.

There are two new property defined for our ShadowLabel component, shadowColor and shadowWeight. shadowColor specifies what color the text shadow should have, and the shadowWeight defines how strong the shadow should be. In our implementation the shadowWeight defines the shadow Label vertical offset.

The main and shadow Label textStyle parameter can’t be bound as easily as other properties. textStyle itself is read only, but we can bind textStyle.base to root.textStyle.style. The textStyle.base parameter defines the default parameters for a textStyle, but still allows us to overwrite them as required. We take advantage of this for setting our shadow Label colour. (See TextStyleDefinition for more details)

This is the basic work needed to use our ShadowLabel component in other qml files. Here’s an example on how to use it:

import bb.cascades 1.0

Container {
    background: Color.Gray
    ShadowLabel {
	    text: "Sample Text nMultiline"
	    shadowColor: Color.White
	    shadowWeight: 2
	    multiline: true
	    background: Color.Black

	    textStyle: TextStyleDefinition {
	        color: Color.Red
	        fontSize: FontSize.PointValue
	        fontSizeValue: 7
        }
    }
}

Result:

Shadow Label Example

About the Author

Biography

Previous
Data Science vs. Data Analytics
Data Science vs. Data Analytics

With Big Data becoming one of the year’s top buzzwords, terms describing the practitioners working with sai...

Next
Study Finds Surprising Links Between Social Media and Music Sales
Study Finds Surprising Links Between Social Media and Music Sales

With the music industry still scrambling to make money in the age of digital distribution, companies and mu...