Use QML Localstorage to store our data

Source: Internet
Author: User
Tags json sqlite sqlite database


In the previous example, we could "use the SQLite offline storage API to store the app's settings". We also show how to store the JSON we need in a local file in the example "How to dynamically modify the data in the Listmodel in the QML application and store it in JSON format". In this article, we will use the localstorage provided by Qtquick to store the data we need.






To illustrate the problem, I'll start by creating a template based on the "QtQuick App with QML UI (qmake)". First we revise our main.cpp as follows:




MAIN.QML



#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQuickView>
# Include <QDebug>

int main (int argc, char *argv[])
{
    qguiapplication app (argc, argv);

    Qquickview view;
    Qdebug () << "Local Storage path:" << view.engine ()->offlinestoragepath ();
    Qobject::connect (View.engine (), SIGNAL (Quit ()), Qapp, SLOT (Quit ()));

    View.setsource (Qurl (qstringliteral ("qrc:///main.qml"));
    View.setresizemode (Qquickview::sizerootobjecttoview);
    View.show ();
    return app.exec ();
}

When we run our application, we can see:

Local Storage path:  "/home/phablet/.local/share/localstorage/qml/offlinestorage"

This path is obviously different from the actual path we produce when we actually run it on the phone:



This also shows that the implementation on Ubuntu is different from the standard QT implementation. From the above we can see that the time path of the database is:

phablet@ubuntu-phablet:~/.local/share/localstorage.liu-xiao-guo/databases$ ls
4ff10001f402923590ceb1d12a0cffc6.ini  4ff10001f402923590ceb1d12a0cffc6.sqlite


To enable the application to exit itself, we have added the following statement:

  Qobject::connect (View.engine (), SIGNAL (Quit ()), Qapp, SLOT (Quit ()));

This allows the app to exit when you use Qt.quit () in our QML code. This is different from our general design. We generally do not need to do this. For this application, we would like to get an event at the exit to save our settings, all of which we have such a special treatment.

In order to be able to access the SQLite database, we designed the following Database.js file:
Database.js

.import QtQuick.LocalStorage 2.0 as Sql

var db;

function initDatabase() {
    print('initDatabase()')

    db = Sql.LocalStorage.openDatabaseSync("CrazyBox", "1.0", "A box who remembers its position", 100000);
    db.transaction( function(tx) {
        print('... create table')
        tx.executeSql('CREATE TABLE IF NOT EXISTS data(name TEXT, value TEXT)');
    });
}

function readData() {
    print('readData()')

    if(!db) { return; }
    db.transaction( function(tx) {
        print('... read crazy object')
        var result = tx.executeSql('select * from data where name="crazy"');
        if(result.rows.length === 1) {
            print('... update crazy geometry')
            // get the value column
            var value = result.rows[0].value;
            // convert to JS object
            var obj = JSON.parse(value)
            // apply to object
            crazy.x = obj.x;
            crazy.y = obj.y;
        }
    });
}

function storeData() {
    print('storeData()')

    if(!db) { return; }
    db.transaction( function(tx) {
        print('... check if a crazy object exists')
        var result = tx.executeSql('SELECT * from data where name = "crazy"');
        // prepare object to be stored as JSON
        var obj = { x: crazy.x, y: crazy.y };
        if(result.rows.length === 1) {// use update
            print('... crazy exists, update it')
            result = tx.executeSql('UPDATE data set value=? where name="crazy"', [JSON.stringify(obj)]);
        } else { // use insert
            print('... crazy does not exists, create it')
            result = tx.executeSql('INSERT INTO data VALUES (?,?)', ['crazy', JSON.stringify(obj)]);
        }
    });
}


Here, we can create a database called "Crazybox" and produce a table in it called data. We can update the data to the table. From this example, we can see that this method is used to store our JSON data without using the C + + code (the reference routine "how to dynamically modify the data in the Listmodel in the QML application and store it in JSON format"). This is good news for most developers who are not very familiar with C + + code.

MAIN.QML

import QtQuick 2.0
import Ubuntu.Components 1.1
import "database.js" as DB

/*!
    \brief MainView with a Label and Button elements.
*/

MainView {
    // objectName for functional testing purposes (autopilot-qt5)
    objectName: "mainView"

    // Note! applicationName needs to match the "name" field of the click manifest
    applicationName: "localstorage.liu-xiao-guo"

    /*
     This property enables the application to change orientation
     when the device is rotated. The default is false.
    */
    //automaticOrientation: true

    // Removes the old toolbar and enables new features of the new header.
    useDeprecatedToolbar: false

    width: units.gu(60)
    height: units.gu(85)

    Page {
        title: i18n.tr("Localstorage")

        Rectangle {
            id: crazy
            objectName: 'crazy'
            width: 200
            height: 200
            x: 50
            y: 50
            color: "#53d769"
            border.color: Qt.lighter(color, 1.1)

            Text {
                anchors.centerIn: parent
                text: Math.round(parent.x) + '/' + Math.round(parent.y)
            }

            MouseArea {
                anchors.fill: parent
                drag.target: parent
            }
        }


        Component.onCompleted: {
            DB.initDatabase();

            print("it is going to read data");
            DB.readData();
        }

        Component.onDestruction: {
            print("it is going to save data");
            DB.storeData();
        }

        Button {
            anchors.bottom: parent.bottom
            anchors.bottomMargin: units.gu(1)
            anchors.horizontalCenter: parent.horizontalCenter
            text: "Close"
            onClicked: {
                Qt.quit();
            }
        }
    }
}


Our MAIN.QML design is very simple. After the UI is loaded, we initialize the database and read the data that has been stored. If the data already exists, read it out and initialize our rectangle "crazy". When the app exits, we store our data. It should be noted that when we use our fingers to drag and drop the app, our app does not accept the following events:

        Component.ondestruction: {
            print ("It is going to save data");
            Db.storedata ();
        }

We have to get this event by selecting the "Quit" button.
To run our application:



Whenever we exit the app and restart the app, we can see that our green squares are in the same position as the last time we exited.
The source code of the whole project is: https://github.com/liu-xiao-guo/localstorage

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.