Welcome to the official BlackBerry Support Community Forums.

This is your resource to discuss support topics with your peers, and learn from each other.

inside custom component

Native Development

Posts: 33
Registered: ‎01-02-2012
My Device: 9900
My Carrier: bell

Circular Slider Tutorial Help

I am currently working on my app kind of like a custom time watch that keeps time, so I though the circular slider example would do, and so I got o everything right. The only thing where the tutorial is incomplete is at the Touch Interaction with the handle.


So they just give us, incomplete code, I tired so much to complete it it just doesn't work any help is appreciated.



PROBLEM: The mRootContainer is to be linked to the touch() event, when the event happens the slider to move.

Which they give us in the Touch Handling Section


connect(mRootContainer, SIGNAL(touch(bb::cascades::TouchEvent *)),
    this, SLOT(onSliderHandleTouched(bb::cascades::TouchEvent *)));
when i put this in the constructor it dosent work. I know this code is incomplete please make it work


Posts: 33
Registered: ‎01-02-2012
My Device: 9900
My Carrier: bell

Re: Circular Slider Tutorial Help

Any one have a working code for this it will be of a great help,


Posts: 610
Registered: ‎10-17-2010
My Device: (BlackBerry Z10)-> Q10/Passport Dual Use

Re: Circular Slider Tutorial Help

I was also unable to get the code to work. BUMP.


Can RIM dev consultant or Open-Source dude post a complete source of this on GitHub or make a zip of the Circular Slider?



Thank you!

Posts: 33
Registered: ‎01-02-2012
My Device: 9900
My Carrier: bell

Re: Circular Slider Tutorial Help

I really dont want to halt my devlopment process, anyone knows how to get in touch with the cascades devlopment team,


Posts: 40
Registered: ‎07-06-2012
My Device: DevAlpha, PlayBook
My Carrier: BaseDE, BouyguesFR

Re: Circular Slider Tutorial Help

for me the example works just fine. I did not do any modification. Just copy-paste of all the code. Compiled and launched it. I agree that it would be great to have it on GitHub .. it is a great example!

Here the code:


#include "CircularSlider.h"
#include <bb/cascades/AbsoluteLayout>
#include <bb/cascades/AbsoluteLayoutProperties>
#include <bb/cascades/DockLayout>
#include <iostream>
#include <math.h>

#define PI 3.141592653589793

	// Create a root container with an AbsoluteLayout.
	mRootContainer = new Container();
	mRootContainer->setLayout(new AbsoluteLayout());

	connect(mRootContainer, SIGNAL(touch(bb::cascades::TouchEvent *)),
			this, SLOT(onSliderHandleTouched(bb::cascades::TouchEvent *)));

	// Create the slider track image.
	mTrackImage = ImageView::create().image(

	// Create the handle container and two images, one for
	// active state and one for inactive.
	mHandleContainer = Container::create()
	.layout(new DockLayout());

	// Disable implicit animations for the handle container so that
	// the handle doesn't jump when it's being dragged.
	mHandleImplicitAnimationController =

	// Load the handle images
	mHandleOn = Image(QUrl("asset:///images/handle_pressed.png"));
	mHandleOff = Image(QUrl("asset:///images/handle_inactive.png"));

	// Create the image view for the handle using the image for
	// the inactive handle
	mHandle = ImageView::create().image(mHandleOff)

	// Add the handle image to the to handle container
	// and add everything to the root container

	// Set the root of the custom control.

	// Connect the signals to your custom slots and check the return value
	// for errors.
	bool res = connect(this, SIGNAL(preferredHeightChanged(float)), this,

	bool res2 = connect(this, SIGNAL(preferredWidthChanged(float)), this,

	// Set the initial size.
	mWidth = 600;
	mHeight = 600;
	setPreferredSize(mWidth, mHeight);

// Set the new width of the custom control and
// initiate the resizing
void CircularSlider::onWidthChanged(float width)
	mWidth = width;
// Set the new height of the custom control and
// initiate the resizing
void CircularSlider::onHeightChanged(float height)
	mHeight = height;

void CircularSlider::onSizeChanged()
	// Define the center of the circle.
	mCenterX = mWidth / 2;
	mCenterY = mHeight / 2;
	mRadiusCircle = mWidth - mCenterX;

	// Set the root container to the new size.
	mRootContainer->setPreferredSize(mWidth, mHeight);

	// Set the track image to be slightly smaller than the root.
	mTrackImage->setPreferredSize(mWidth * 0.85, mHeight * 0.85);

	// Set the handle image and container to be much smaller.
	mHandle->setPreferredSize(0.2 * mWidth, 0.2 * mHeight);
	mHandleContainer->setPreferredSize(mWidth, 0.2 * mHeight);

	// Transform the handle container along its y axis to move it
	// into the correct position.
	mHandleContainer->setTranslationY((mHeight - 0.2 * mHeight) / 2);

	// Transform the position of the track image to the correct
	// position.
	mTrackImage->setTranslation((mWidth - 0.85 * mWidth) / 2,
			(mHeight - 0.85 * mHeight) / 2);

	// Clear the circumference points for the circle
	// and reinitialize them to reflect the new size.

	for (int angle = 0; angle < 360; angle++) {
		float x = mCenterX + (mRadiusCircle) * cos(angle * PI / 180);
		float y = mCenterY + (mRadiusCircle) * sin(angle * PI / 180);
		pointsOnCircumference.push_back(make_pair(x, y));

void CircularSlider::onSliderHandleTouched(TouchEvent* pTouchEvent)
	// Change to the active handle image if isDown()
	if (pTouchEvent->isDown()) {
		// Change to the inactive handle image if isUp()
	} else if (pTouchEvent->isUp()) {
		// Change the position of the slider handle if isMove()
	} else if (pTouchEvent->isMove()) {

void CircularSlider::processRawCoordinates(float touchX, float touchY) {

	// Determine the distance from the center to the touch point.
	float distanceFromCenterToTouchPoint = sqrt(
			(touchX - mCenterX) * (touchX - mCenterX)
			+ (touchY - mCenterY) * (touchY - mCenterY));

	// Determine whether the touch point is outside the center of
	// the circle and in the valid touch area.
	if (distanceFromCenterToTouchPoint >= 0.3 * mRadiusCircle
			&& distanceFromCenterToTouchPoint <= mRadiusCircle) {

		// The minimum distance from the touch.
		float minDistanceFromTouch = INT_MAX;

		// Measure the distance from the touch to the circumference
		// for each point on the circle and store the X and Y
		// coordinates for the shortest distance.
		for (float i = 0; i < pointsOnCircumference.size(); i++) {
			float x = pointsOnCircumference[i].first;
			float y = pointsOnCircumference[i].second;
			float distanceFromTouch = sqrt(
					(x - touchX) * (x - touchX)
					+ (y - touchY) * (y - touchY));
			if (distanceFromTouch < minDistanceFromTouch) {
				minDistanceFromTouch = distanceFromTouch;
				// The angle to rotate the handle container once moved
				mAngle = i;

		// Rotate the handle container along its Z-axis.
		if (mAngle != mrevAngle) {
			// Our slider has a new value, and we want our QML to know
			emit valueChanged(mAngle);
			mrevAngle = mAngle;
// Get the value of the slider.
float CircularSlider::value() const
	return mValue;

// Set the value of the slider.
void CircularSlider::setValue(float value)
	if (mValue != value)
		mValue = value;
		emit valueChanged(mValue);

CircularSlider::~CircularSlider() {
	// TODO Auto-generated destructor stub



#include <bb/cascades/CustomControl>
#include <bb/cascades/Container>
#include <bb/cascades/TouchEvent>
#include <bb/cascades/ImageView>
#include <bb/cascades/Image>
#include <bb/cascades/ImplicitAnimationController>
#include <bb/cascades/Label>

#include <QObject>
#include <vector>

using namespace std;
using namespace bb::cascades;

class CircularSlider: public CustomControl {

    Q_PROPERTY(float value READ value WRITE setValue
            NOTIFY valueChanged FINAL)

    virtual ~CircularSlider();
    float value() const;
    void setValue(float value);
    void innerCircle(QVariant innerCircle);

    void valueChanged(float value);

private slots:
    void onSliderHandleTouched(bb::cascades::TouchEvent *pTouchEvent);

private slots:
    void onWidthChanged(float width);
    void onHeightChanged(float height);

    float convertAngleToValue(float angle);
    void onSizeChanged();
    void processRawCoordinates(float inX, float inY);

    Container *mRootContainer;
    ImageView *mTrackImage;

    float mWidth;
    float mHeight;
    float mrevAngle;

    float mCenterX;
    float mCenterY;
    float mRadiusCircle;

    Image mHandleOn;
    Image mHandleOff;
    ImageView *mHandle;
    Container *mHandleContainer;

    vector<pair<int, int> > pointsOnCircumference;
    float mAngle;
    float mValue;
    ImplicitAnimationController mHandleImplicitAnimationController;

#endif /* CIRCULARSLIDER_H_ */

CircularSliderDemo.cpp (the application file that was generated automatically):

// Default empty project template
#include "CircularSliderDemo.hpp"
#include "CircularSlider.h"

#include <bb/cascades/Application>
#include <bb/cascades/QmlDocument>
#include <bb/cascades/AbstractPane>

using namespace bb::cascades;

CircularSliderDemo::CircularSliderDemo(bb::cascades::Application *app)
: QObject(app)
	// Register our custom control
	qmlRegisterType<CircularSlider>("custom.lib", 1,
			0, "CircularSlider");

	QmlDocument *qml = QmlDocument::create("asset:///main.qml").parent(this);

	AbstractPane *root = qml->createRootObject<AbstractPane>();




import bb.cascades 1.0
import custom.lib 1.0
Page {
    // The root container
    content: Container {
        topMargin: 130
        layout: DockLayout {}
        background: Color.create ("#404040")
        // Display the current rotation of the slider handle.
        Label {
            id: myLabel
            text: "0"
            horizontalAlignment: HorizontalAlignment.Center
            textStyle {
                base: SystemDefaults.TextStyles.BigText
                fontWeight: FontWeight.Bold
        // Create the CircularSlider and lay it out
        // just like any other control.
        CircularSlider {
            horizontalAlignment: HorizontalAlignment.Center
            verticalAlignment: VerticalAlignment.Center
            // Capture the valueChanged signal and update
            // the label.
            onValueChanged: {
                console.debug (value);
                myLabel.text = value;
        } // Ends the circular slider
    } // Ends the root container
} // Ends the page


Posts: 24
Registered: ‎05-16-2013
My Device: Developer
My Carrier: Developer

Re: Circular Slider Tutorial Help