Simple BBM Integration in Cascades

Did I say simple? I meant very simple. In the following sample app I started with the standard empty cascades project and added a total of ~55 lines of code to the applicationui.cpp and applicationui.app files. In addition the UI is very plain as to not take away from the core purpose of a sample application which is to demonstrate how to do something, right?

Read more...

Easing into Cascades Animations

OverView

One of the many elements that makes the Cascades UI so beautiful is the widespread use of animations. Even without programming it yourself, animations are an integral part of your Cascades application. For example, when you pull in a sheet it slides in, or when you push a new pane within a NavigationPane, you see the built in animations in action.

There are many more subtle animations in Cascades that happen automatically, and I am not going to attempt to name them all because I would be here all day. We will just agree that animations are everywhere in Cascades. With that in mind, using any extra animation can easily become overwhelming to the end-user.  However, adding subtle animations in appropriate places in your app can really improve the overall UX and really give your app a premium feel.

Let's Get Started

So, with all this built in animation why would you want more? While it is true that you could easily overdo it with animation upon animation, adding subtle animations in appropriate places can really give your app a premium feel. Let's look at an example from the BlackBerry Cascades documentation.

freeform titlebar

Free-form title bar containing expandable content

The above example is shown in the official docs (http://developer.blackberry.com/cascades/reference/bb__cascades__titlebar.html) and demonstrates how to have an expanable area that drops down from the TitleBar. An example of this in action can be seen in the native BlackBerry World app when viewing any top list.  

IMG 00000147

There are some key differences between the example above and the implementation in the BlackBerry World app, and it's those differences that give the BBW implementation a more premium feel. The list is styled a bit more and uses check marks instead of radio toggle, and there is an arrow in the top right that flips based on whether the exanable area is expanded or collapsed (similiar to in a dropdown).

Let's take the code from the top example from the the official docs...

Page {
    titleBar: TitleBar {
        kind: TitleBarKind.FreeForm
        kindProperties: FreeFormTitleBarKindProperties {
            Container {
                layout: StackLayout { orientation: LayoutOrientation.LeftToRight }
                leftPadding: 10
                rightPadding: 10
                Label {
                    text: "Show expandable content"
                    textStyle {
                        color: Color.White
                    }
                    verticalAlignment: VerticalAlignment.Center
                    layoutProperties: StackLayoutProperties { spaceQuota: 1 }
                }
                CheckBox {
                    id: toggleExpanded
                    verticalAlignment: VerticalAlignment.Center
                }
            }
            expandableArea {
                content: RadioGroup {
                    Option { id: option1; text: "option 1"; selected: true }
                    Option { id: option2; text: "option 2" }
                    Option { id: option3; text: "option 3" }
                }
                indicatorVisibility: TitleBarExpandableAreaIndicatorVisibility.Hidden
                expanded: toggleExpanded.checked
                onExpandedChanged: {
                    toggleExpanded.checked = expanded
                }
            }
        }
    }
}

So in the above example a CheckBox is used to toggle the expansion and collapse of the expandableArea, and radio toggles are used to on the list items within the expandableArea. While this is fine, and gets the job done, why not style it a bit to make it a bit fancier? In the code below we take the example from the docs and do the following:

  • Replace the checkbox with an ImageView
  • Add RotateTransition animation to ImageView
  • Create and use a custom bool property
  • Dynamically change label to reflect the selected option

 

Page {
    titleBar: TitleBar {
        kind: TitleBarKind.FreeForm
        kindProperties: FreeFormTitleBarKindProperties {
            Container {
                layout: StackLayout {
                    orientation: LayoutOrientation.LeftToRight
                }
                leftPadding: 10.0
                rightPadding: 10.0
                Label {
                    text: radioGroup.selectedOption.text
                    textStyle {
                        color: Color.White
                    }
                    verticalAlignment: VerticalAlignment.Center
                    layoutProperties: StackLayoutProperties {
                        spaceQuota: 1
                    }
                }
                ImageView {
                    id: toggleExpanded
                    property bool checked: false
                  
                    onTouch: {
                        if (checked == false) {
                            if (event.touchType == TouchType.Down) {
                            } else if (event.touchType == TouchType.Move) {
                            } else if (event.touchType == TouchType.Up) {
                                rt1.play()
                                checked = true
                            }
                        } else {
                            if (event.touchType == TouchType.Down) {
                            } else if (event.touchType == TouchType.Move) {
                            } else if (event.touchType == TouchType.Up) {
                                rt2.play()
                                checked = false
                            }
                        }
                    }
                    animations: [
                        RotateTransition {
                            id: rt1
                            duration: 150
                            toAngleZ: -180.0
                            fromAngleZ: 0.0
                            easingCurve: StockCurve.CubicIn
                        },
                        RotateTransition {
                            id: rt2
                            duration: 150
                            toAngleZ: 0
                            fromAngleZ: -180.0
                            easingCurve: StockCurve.CubicIn
                        }
                    ]
                    imageSource: "asset:///ic_to_bottom.png"
                    verticalAlignment: VerticalAlignment.Center
                    horizontalAlignment: HorizontalAlignment.Center
                }
            }
            expandableArea {
                content: RadioGroup {
                    id: radioGroup
                    Option {
                        id: option1
                        text: "Option 1"
                        selected: true
                    }
                    Option {
                        id: option2
                        text: "Option 2"
                    }
                    Option {
                        id: option3
                        text: "Option 3"
                    }
                    onSelectedOptionChanged: {
                        rt2.play()
                        toggleExpanded.checked = false
                    }
                }
                indicatorVisibility: TitleBarExpandableAreaIndicatorVisibility.Hidden
                expanded: toggleExpanded.checked
                onExpandedChanged: {
                    toggleExpanded.checked = expanded
                }
            }
        }
    }
}

 

So there you have it. Import the zip attached to this post into the Momentics IDE and run it on your device to see it in action.  Tinker with the code and see what you can improve and/or create.

Relevant Links:

Read more...

Introducing the Official OSBB App for BlackBerry 10

Earlier today, the official OSBB App for BlackBerry was approved and appeared in the BlackBerry World storefront. We are excited to have an app available that is native, beautiful, and developed soley by us here at OSBB. Version 1.0 of the app is available for both the full touch and QWERTY BlackBerry 10 devices running BlackBerry 10.1 or higher and is, of course, free.  

osbbapp1

Feeds

When designing the OSBB app, we wanted to show our respect to the BlackBerry UI guidelines, but we also wanted to be a little different, so in the news feeds we added a brief description of each article that can be show or hidden with a single tap of the button located just to the right of the title. If the brief description grabs your interest, the full article can be viewed by tapping the list item.

 


 

osbbapp2

Search Feature

When building the search feature into the app, we wanted to mimic the native search present in native BB10 apps such as the File Manager, and we believe we nailed it.  The search feature will allow you to quickly locate whatever it is that you are looking for.

 


 

osbbapp3

Category Filtering

Hiding just above each topic specfic list, is a dropdown menu that will allow you to get more specific results, and allow you to dive a bit deeper. The dropdown is available in the Reviews section, Resources section, and The Rest section.

While we are definitely excited to have the official OSBB app available, we are even more excited to improve it and further develop it, so let us know what features you would like to see in the app, and as always, happy coding!

Download the Official OSBB App today!

getitatbbw

Read more...

Example of a First Run Tutorial in Cascades

I'm sure many of you have installed an app onto your device that displayed a brief tutorial the first time you launched it, right?  If you have ever wondered how you could do that in your own app, this sample application will show you one simple way to accomplish this in a Cascades app. 

Info

This sample app utilizes QSettings, so see my previous tutorial about QSettings if you need some help there.

This post will not be a full-fledged tutorial, but I do want to explain some of the aspects of the sample application. First, here are some of the "stuffs" used in the sample application...

QML elements/components used:

  • Sheet {}
  • Page {}
  • Container {}
  • Label {}
  • ListView {}

QML Signals used:

  • onCreationCompleted:
  • onClicked:
  • onTriggered:

Other used:

  • DockLayout
  • StackLayout
  • XmlDataModel 

 How does the application work?

The application is pretty simple, and it uses QSettings to store a bool (true/false) property that is used to determine if the tutorial should open or not when the app is launched.  By default the bool property is set to true and therefore the tutorial fires up when the app is launched. If the user taps the close button to close the tutorial, the tutorial closes, but it will open up again when the user launches the app the next time.  However, if the user taps the Dismiss button to close the tutorial, the tutorial is closed forever or until the app is uninstalled, reinstallled, and relaunched.  

FirstRunImage 1

For the purposes of this sample app I placed a button on the main.qml file that is visible when the tutorial is closed. This button allows you to restore the tutorial popup functionailty without having to uninstall the app. There is also a Label above to button that displays whether the tutorial pop up is disabled or enabled.  

  FirstRunImage 2 

So, head over to the OSBB GitHub and check it out and I have attached a prebuilt and presigned bar file to this post that can be side loaded onto your device (Q10/Q5/Z10/Dev Alpha).  

If you have issues or REALLY want a tutorial, sound off in the comments, and I will whip one up. Also, if you have specific questions, hit me up on twitter @BerryInformed or via the comment section below.

Thanks guys and happy coding!

Read more...

Simple Example of QSettings in Cascades

There comes a time when building apps, when it is necessary to store a setting, a value, or a string of text in a persistant manner--meaning it remains stored even after the app is closed and reopened. In Cascades, QSettings is one of the options available to developers to accomplish just that.

In this short tutorial, you will learn how to store a string of text via QSettings.  

Starting in the application.cpp (for full source see Github) file we need to add a few things to be able to use QSettings.

...
//!!!ADD!!!
#include <QSettings> ... ApplicationUI::ApplicationUI(bb::cascades::Application *app) : QObject(app) { ... //!!!ADD!!!
qml->setContextProperty("_app", this); ... } ... //!!!ADD!!!
QString ApplicationUI::getValueFor(const QString &objectName, const QString &defaultValue) { QSettings settings; if (settings.value(objectName).isNull()) { return defaultValue; } return settings.value(objectName).toString(); } //!!!ADD!!!
void ApplicationUI::saveValueFor(const QString &objectName, const QString &inputValue) { QSettings settings; settings.setValue(objectName, QVariant(inputValue)); }

The code in bold is what we add to the standard Cascades project source files.

Now to the applicationui.hpp (for full source see GitHub) file

 

 
public:
	...
//!!!ADD!!!
Q_INVOKABLE QString getValueFor(const QString &objectName, const QString &defaultValue); //!!!ADD!!!
Q_INVOKABLE void saveValueFor(const QString &objectName, const QString &inputValue); ...

Now the main.qml file, let's use a TextField to enter a string of text to be stored. When we submit (onSubmitted), we utilize the context property we set in the applicationui.cpp file to call the C++ function from QML. This is what stores the string.

import bb.cascades 1.0
Page {
    Container {
        TextField {
            id: inputField
objectName: "inputField" input { onSubmitted: { //Here is where we save the value or string
_app.saveValueFor(inputField.objectName, inputField.text) outputText.text = inputField.text instructionsLabel.visible = false testLabel.visible = true } } } }

 Now, for the rest of the main.qml the code in this sample is as follows:

import bb.cascades 1.0
Page {
    Container {
        TextField {
            id: inputField
            objectName: "inputField"
            
            input {
                onSubmitted: {
                    //Here is where we save the value or string
                    _app.saveValueFor(inputField.objectName, inputField.text)
                    outputText.text = inputField.text
                    instructionsLabel.visible = false
                    testLabel.visible = true
                }
            }
        
        }
        Label {
            id: outputText
            //Here is where we call or get that value and display it
            text: _app.getValueFor(inputField.objectName, "No Text Set")
            textStyle.base: SystemDefaults.TextStyles.BigText
        }
        Container {
            id: instructionsLabel
            topPadding: 100.0
            visible: true
            Label {
                text: "Type a string of text into the field above and press enter."
                multiline: true
                textStyle.fontSize: FontSize.Large
                textStyle.fontWeight: FontWeight.W100
            }
        }
        Container {
            id: testLabel
            topPadding: 100.0
            visible: false
            Label {
                text: "Now close the app, and the Label above should still have the text you set it to when you open the app back up!"
                multiline: true
                textStyle.fontSize: FontSize.Large
                textStyle.fontWeight: FontWeight.W100
                textStyle.color: Color.Red
            }
        }
    }
}

That's it! Remember to check out the full source on the OSBB GitHub at https://github.com/OpenSourceBB/Cascades-Samples/tree/master/QSettingsExample and you can download the prebuilt and signed bar file attached to this post (Will work for Q10 or Z10 or Dev Alpha).

If you compile and run this sample, it should look similar to the images below.

 

Read more...

BlackBerry Native IDE 10.2: setting up your environment

One aspect about coding natively for Blackberry that intimidates some developers coming from WebWorks or other environments is the use of an IDE -- Momentics in this case.  BlackBerry has done a good job with the latest beta version of Momentics in making things much simpler than they were even a year ago.  The interface is simple and presented in a much less intimating way with the new beta.  So for this tutorial, we will be using the new native IDE version 10.2 Beta 1, which is available here.

Setting up your environment 

When you launch Momentics for the first time you will see the following screen.

First thing you want to do is configure your BlackBerry targets (test device or simulator). You can connect to a test device (Dev Alpha, Q10, or Z10) via wifi or USB, and if you are using a simulator Momentics can automatically discover a simulator that is currently running on your PC. The target device is simply the device on which you want to deploy and test whatever application on which you will be working.

Configuring your target(s) is remarkably simple. First, enable development mode on your device settings (under security and privacy settings). Then, create a password on your device when prompted. Now, connect your device via USB (you can also use the device's wifi IP).  So when the device is connected via USB, the IDE will detect and display confirmation that the device has been detected.  

Click "Next" and you will be prompted for your device password.

Now that you have entered your password, click "Next" again and the IDE will confirm that all went well, and it will detect the OS version of the device. Now, the IDE prompts you for your to choose hte API level in which you want to work. 

In this instance we will choose the Gold 10.1 SDK.  Once you select the API level from the dropdown and click install, the IDE will download and install the selected SDK. Once installed, you are basically off to the races.

Registering Keys with the Signing Authority

Now that you have the SDK installed and everything basically all set up, this is a good time to go ahead and register your signing keys (a one time event).  To do so, click the 'Window' menu, select preferences, click 'Blackberry' on the left vertical menu, then run the 'BlackBerry Deployment Setup Wizard'. 

7

This step may have already been completed earlier in set up. If it looks familiar and you are sure you have done this already you can skip this section.

Once here, click next, then it will find and connect to any devices (which you already did) so move to the next screen.  Hopefully you have requested keys via BlackBerry's website, but if you have not you can register for them at https://www.blackberry.com/SignedKeys/codesigning.html.  One you request keys, you will receive two emails from BlackBerry within about 30 minutes (can take up to 2 hours) and these emails contain two certificates that you will use during this process.

8

IMPORTANT: Please do not forget the PIN you created when registering for your new keys on the Blackberry website!

So select the first option and click next.

9

Save the files attached to each email from BlackBerry somewhere on your hard drive, and from this screen locate and select the requested certificates by browsing for them on your hard drive.  Now enter the PIN you created when you registered for the keys and then create a CSK Password and then confirm the password in the final field, and click next.

On the next screen you will be asked whther or not you want to backup your signing keys.  Please do this, it may save your a lot of headache down the road.  So simply choose a location and a file name, and the IDE will zip up the keys and save them wherever you wish. 

Creating and uploading a Debug Token

Continuing form above, the next screen will prompt you to create a debug token.  A debug token is a .bar file that is installed on your test device that allows you to deploy unsigned applications. This is a crucial part of testing bc you do not want to have to sign builds over and over simply to test your application.  

It is important to point out that the current version or build number of an app can only be signed once, so when you update and build a new version, you have to change the version/build number in order to be able to sign the new version.  Makes sense right?

10

So, to create a debug token simply choose the option to create a debug token and click next.  Once you do so the IDE will create and upload the debug token to your device.

10

Finally, you will receive a confirmation screen to let you know all went well, and I am happy to report that you won't have to do that again unless you request new keys (and its a really simple process anyway). You are now ready to create, test, and sign BlackBerry 10 applications in Momentics.

Creating a Project

To start a new Cascades project choose "New" from the File menu and select "BlackBerry Project" from the pop-out menu.  Then choose Cascades and press next. 

10

On the next screen you can choose from one of the pre-designed templates, or you can start a blank empty project. Choose one and press next, name your project whatever you'd like, and you are now ready to begin coding a new app in the newest BlackBerry Native IDE.

Happy Coding!

Happy Coding!

Read more...

Rock, Paper, Scissors - Full Tutorial

Who doesn't like a good old fashion game of Rock, Paper, Scissors? So here's an example app of it...  This tutorial is broken up into 3 parts:
Part 1 will focus on how to create the logic aspects (QML/JavaScript and C++).
Part 2 will create a user friendly user interface (UI) to liven up the app with graphics (QML).
Part 3 will combine the logic and UI, as well as add some additional features such animations and a help page.

Before getting into the explanations the full source code this app has been posted to github: https://github.com/bcs925/BrianScheirerOpenSource/tree/master/RockPaperScissors

And the app can be downloaded from App World (only available on BB10, Dev Alpha):  http://appworld.blackberry.com/webstore/content/135020/?model=Dev%20Alpha&lang=en

I like to do the logic first because I figure if you can't get the functionality working why bother making a pretty UI?  So without further ado... Let's get started!

Part 1: The Logic

Since this example uses both QML/JavaScript and C++ for the logic it is necessary to have some amount of UI.  As well as creating a barebones UI allows you to test that everything is working as it should. One thing to especially notice is that I chose identifiers for the id of each item to be representative of what the item is or does.  This will be especially true once the final UI is made in Part 2 and things won't be this close together in the code.

First part of the test UI will be 3 buttons: Rock, Paper, and Scissors.  These will act as the 3 signals that control the game.

        Container {
            Button {
                id: rockbutton
                objectName: "rockbutton"
                text: "ROCK!"
                onClicked: {
                }
            }
            Button {
                id: paperbutton
                objectName: "paperbutton"
                text: "PAPER!"
                onClicked: {
                }
            }
            Button {
                id: scissorsbutton
                objectName: "scissorsbutton"
                text: "SCISSORS!"
                onClicked: {
                }
            }
        }

Next is a Label that states what option the computer decided to pick:

            Label {
                id: computerpick
                text: "BlackBerry picks: ..."
            }

After that is the winner:

            Label {
                id: winnerlabel
                text: "Winner"
            }

Finally, there is a container that holds labels for your win/loss/tie record:

        Container {
            layout: StackLayout {
                layoutDirection: LayoutDirection.LeftToRight
            }
            Label {
                text: "Record: "
            }
            Label {
                id: win
                text: "0"
            }
            Label {
                text: "-"
            }
            Label {
                id: lose
                text: "0"
            }
            Label {
                text: "-"
            }
            Label {
                id: tie
                text: "0"
            }
        }

Now it is time to create the logic within the buttons and C++ functions.  The way it made sense for me to do it was to let QML/JavaScript handle the setup for each choice then pass those choices to C++ for it to return the winner.  So for instance for the "rockbutton" onClicked signal it generates a "var = number" of 1-3 for the computer's choice and takes "1" as the user's choice for Rock. (For Scissors it is "2" and for Paper it is "3" for the user's choice.)  Then passes those two numbers into clickedRock() C++ function to find out the winner.  I am not going to go through each line individually but as you see below in the full code it is just a bunch of if/else statements for deciding who wins/loses/ties based off the rules of Rock, Paper, Scissors. 

Lastly, for the win/loss/tie record keeping, this is accomplished by looking at the outcome of the game and the previous total for either win/loss/tie. Based on the outcome the codeWinning() C++ function adds 1 to the appropriate value.

And that's it for logic.  See below for full code of main.qml, app.cpp, and app.hpp.  Since I didn't go too in depth, feel free to ask questions in the comments field about any aspect of the logic.

main.qml

import bb.cascades 1.0

Page {
    content: Container {
        Container {
            Button {
                id: rockbutton
                objectName: "rockbutton"
                text: "ROCK!"
                onClicked: {
                    var winning = win.text;
                    var losing = lose.text;
                    var ties = tie.text;
                    var number = Math.floor((Math.random() * 3) + 1);
                    var gameoutcome = app.clickedRock(1, number);
                    if (number == 1) {
                        computerpick.text = "BlackBerry picks: Rock";
                    } else if (number == 2) {
                        computerpick.text = "BlackBerry picks: Paper";
                    } else {
                        computerpick.text = "BlackBerry picks: Scissors";
                    }
                    if (gameoutcome == 1) {
                        winnerlabel.text = "You WIN!";
                    } else if (gameoutcome == 2) {
                        winnerlabel.text = "BlackBerry WINS!";
                    } else {
                        winnerlabel.text = "Draw";
                    }
                    if (gameoutcome == 1) {
                        win.text = app.codeWinning(winning);
                    } else if (gameoutcome == 2) {
                        lose.text = app.codeWinning(losing);
                    } else {
                        tie.text = app.codeWinning(ties);
                    }
                }
            }
            Button {
                id: paperbutton
                objectName: "paperbutton"
                text: "PAPER!"
                onClicked: {
                    var winning = win.text;
                    var losing = lose.text;
                    var ties = tie.text;
                    var number = Math.floor((Math.random() * 3) + 1);
                    var gameoutcome = app.clickedPaper(2, number);
                    if (number == 1) {
                        computerpick.text = "BlackBerry picks: Rock";
                    } else if (number == 2) {
                        computerpick.text = "BlackBerry picks: Paper";
                    } else {
                        computerpick.text = "BlackBerry picks: Scissors";
                    }
                    if (gameoutcome == 1) {
                        winnerlabel.text = "You WIN!";
                    } else if (gameoutcome == 2) {
                        winnerlabel.text = "BlackBerry WINS!";
                    } else {
                        winnerlabel.text = "Draw";
                    }
                    if (gameoutcome == 1) {
                        win.text = app.codeWinning(winning);
                    } else if (gameoutcome == 2) {
                        lose.text = app.codeWinning(losing);
                    } else {
                        tie.text = app.codeWinning(ties);
                    }
                }
            }
            Button {
                id: scissorsbutton
                objectName: "scissorsbutton"
                text: "SCISSORS!"
                onClicked: {
                    var winning = win.text;
                    var losing = lose.text;
                    var ties = tie.text;
                    var number = Math.floor((Math.random() * 3) + 1);
                    var gameoutcome = app.clickedScissors(3, number);
                    if (number == 1) {
                        computerpick.text = "BlackBerry picks: Rock";
                    } else if (number == 2) {
                        computerpick.text = "BlackBerry picks: Paper";
                    } else {
                        computerpick.text = "BlackBerry picks: Scissors";
                    }
                    if (gameoutcome == 1) {
                        winnerlabel.text = "You WIN!";
                    } else if (gameoutcome == 2) {
                        winnerlabel.text = "BlackBerry WINS!";
                    } else {
                        winnerlabel.text = "Draw";
                    }
                    if (gameoutcome == 1) {
                        win.text = app.codeWinning(winning);
                    } else if (gameoutcome == 2) {
                        lose.text = app.codeWinning(losing);
                    } else {
                        tie.text = app.codeWinning(ties);
                    }
                }
            }
        }
        Container {
            topMargin: 50.0
            Label {
                id: computerpick
                text: "BlackBerry picks: ..."
            }
            Label {
                id: winnerlabel
                text: "Winner"
            }
        }
        Container {
            layout: StackLayout {
                layoutDirection: LayoutDirection.LeftToRight
            }
            Label {
                text: "Record: "
            }
            Label {
                id: win
                text: "0"
            }
            Label {
                text: "-"
            }
            Label {
                id: lose
                text: "0"
            }
            Label {
                text: "-"
            }
            Label {
                id: tie
                text: "0"
            }
        }
    }
}

app.cpp

#include "app.hpp"

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

using namespace bb::cascades;

App::App()
{
    QmlDocument *qml = QmlDocument::create("main.qml");
    qml->setContextProperty("app", this);
    
    AbstractPane *root = qml->createRootNode<AbstractPane>();
    Application::setScene(root);
}

int App::clickedRock(int user1, int user2)
{
    int winner;

    if((user1 == 1) && (user2 == 2))
    winner=2;
    else if ((user1 == 1) && (user2 == 3))
    winner=1;
    else if ((user1 == 1) && (user2 == 1))
    winner=0;

    return (winner);

}

int App::clickedPaper(int user1, int user2)
{
    int winner;

    if((user1 == 2) && (user2 == 2))
    winner=0;
    else if ((user1 == 2) && (user2 == 3))
    winner=2;
    else if ((user1 == 2) && (user2 == 1))
    winner=1;

    return (winner);

}

int App::clickedScissors(int user1, int user2)
{
    int winner;

    if((user1 == 3) && (user2 == 2))
    winner=1;
    else if ((user1 == 3) && (user2 == 3))
    winner=0;
    else if ((user1 == 3) && (user2 == 1))
    winner=2;

    return (winner);

}

int App::codeWinning(int record)
{
    int add1;
    add1 = record+1;
    return add1;
}

app.hpp

#ifndef APP_H
#define APP_H

#include <QObject>


class App : public QObject
{
    Q_OBJECT

public:
    App();

Q_INVOKABLE int clickedRock(int user1, int user2);
Q_INVOKABLE int clickedPaper(int user1, int user2);
Q_INVOKABLE int clickedScissors(int user1, int user2);
Q_INVOKABLE int codeWinning(int record);


};

#endif // ifndef APP_H

Read more...

Running a C++ Functions from QML

When I first read about Cascades "they" said use QML for the UI and C++ for the logic.  Okay, great so I wrote a function in C++ and made a pretty UI in QML... Now what?  In this example I'll go through the steps it takes to call a C++ function from the QML.  However this example won't have a pretty UI.

Read more...
Subscribe to this RSS feed
Subscribe to the official OSBB BBM Channel!

osbbchannelQR

C00013E89

Back to top