65.9K
CodeProject 正在变化。 阅读更多。
Home

使用 Ring 编程语言为桌面和 Android 构建体重历史应用程序

starIconstarIconstarIconemptyStarIconemptyStarIcon

3.00/5 (6投票s)

2016年10月11日

CPOL

4分钟阅读

viewsIcon

10031

downloadIcon

90

用 Ring 编程语言编写的适用于桌面和 Android 的简单数据库应用程序

引言

Ring 编程语言是一种创新且实用的通用编程语言。使用 Ring,我们可以开发桌面、Web 和移动应用程序。该语言是免费开源的,并且是多范式的(命令式、过程式、面向对象、函数式、声明式和自然式)。

在本文中,我们将使用 Ring 语言开发一个用于存储体重信息(日期、时间和体重)的 Android 应用程序。该应用程序是基于 Qt 框架通过 RingQt 进行 Ring Android 应用开发的一个示例。

注意:我们将编写的相同代码也可以在桌面(Windows、Linux 和 MacOS X)及其他移动平台上运行。

背景

您可以下载 Ring,也可以查看以下关于该语言的文章。

(1) Ring 编程语言

(2) Ring 编程语言的语法灵活性

 

使用代码

首先,我们将为我们的应用程序创建一个新文件。文件名将是 weighthistory.ring。

在我们的应用程序开始时,我们将加载 guilib.ring。

这个库为我们提供了 GUI 类,我们可以使用它们来创建应用程序的用户界面。

'Load' 命令用于加载库。

然后,我们将创建一个 qApp 类的对象,对象名为 MyApp。

每个 GUI 应用程序都必须包含一个应用程序对象。

创建对象后,我们将定义一个全局变量 $ApplicationObject,其中包含我们将用于应用程序的对象名称,当我们在调用事件时使用它。

然后,我们从 App 类创建一个对象。该对象名为 oApp。

之后,我们调用 exec() 方法,将控制权交给 GUI 事件循环。

最后,我们将调用 closedatabase() 方法。

Load "guilib.ring"

MyApp = new qApp
{    
    $ApplicationObject = "oApp"   # To be used when calling events
    oApp = new App         
    exec()
    oApp.CloseDatabase()
}

现在,我们将开始定义我们的类,即 App 类。

在类名之后,在我们定义类属性的类区域,我们将拥有:

cDir:当前目录的属性。

oCon:数据库的连接对象。

aIDs:包含记录 ID 的列表。

win1:来自 qWidget() 类的对象。

我们还拥有其他用于用户界面的属性,如 layoutButtons、label1、text1、btnAdd、btnDelete、LayoutData、Table1、LayoutClose 和 LayoutMain。

然后,我们将调用 OpenDatabase() 方法和 ShowRecords() 方法。

class App

    cDir = currentdir() + "/"
    oCon 
    aIDs = []

    win1 = new qWidget()
    {
        setWindowTitle("Weight History")
        resize(600,600)
        layoutButtons = new qhboxlayout()
        {
            label1 = new qLabel(win1) { setText("Weight") }
            text1 = new qlineedit(win1)
            btnAdd = new qpushbutton(win1) { 
                    setText("Add") 
                    setClickEvent($ApplicationObject+".AddWeight()") 
            }
            btnDelete = new qpushbutton(win1) { 
                    setText("Delete") 
                    setClickEvent($ApplicationObject+".Deleteweight()") 
            }
            addwidget(label1)
            addwidget(text1)
            addwidget(btnAdd)
            addwidget(btnDelete)
        }
        layoutData  = new qhboxlayout()
        {
            Table1 = new qTableWidget(win1) {
                setrowcount(0)
                setcolumncount(3)
                setselectionbehavior(QAbstractItemView_SelectRows)
                setHorizontalHeaderItem(0, new QTableWidgetItem("Date"))
                setHorizontalHeaderItem(1, new QTableWidgetItem("Time"))
                setHorizontalHeaderItem(2, new QTableWidgetItem("Weight"))
                setitemChangedEvent($ApplicationObject+".ItemChanged()")
                         setAlternatingRowColors(true)    
                         horizontalHeader().setStyleSheet("color: blue")
                         verticalHeader().setStyleSheet("color: red") 
                        }
            addWidget(Table1)
        }
        layoutClose = new qhboxlayout()
        {
            btnclose = new qpushbutton(win1) { setText("Close") setClickEvent("MyApp.Quit()") }
            addwidget(btnClose)
        }
        layoutMain = new qvboxlayout()
        {
            addlayout(layoutButtons)
            addLayout(LayoutData)
            addLayout(layoutClose)
        }
        setlayout(layoutMain)
        self.OpenDatabase()
        self.ShowRecords()                
        show()    
    }


然后,我们拥有 openDatabase() 方法,如下面的代码所示。

该方法检查 SQLite 数据库文件 (weighthistory.db) 是否存在,如果存在则打开它。

如果数据库文件不存在,则使用 Create Table 命令创建它。

Func OpenDatabase
        lCreate = False
        if not fexists(cDir + "weighthistory.db")
            lCreate = True
        ok
        new QSqlDatabase() {
            this.oCon = addDatabase("QSQLITE") {
                setDatabaseName("weighthistory.db")
                Open()            
            }
        }    
        if lCreate
            new QSqlQuery( ) {
                exec("create table weighthistory (id integer primary key, f_date varchar(10), f_time varchar(8), f_weight varchar(8) );")
                delete()
            }
        ok

然后,我们拥有 CloseDatabase() 方法。

此方法使用连接对象 (oCon) 并调用 Close() 方法。

    Func CloseDatabase
        oCon.Close()

然后,我们拥有 Addweight() 和 DeleteWeight() 方法。

Addweight() 方法从文本框获取文本,然后将其传递给 AddRecord() 方法。

DeleteWeight() 方法检查 Table 中的当前记录,然后在从 aIDs 列表中获取记录 ID 后执行 SQL 命令 (Delete)。

  Func AddWeight
        cWeight = text1.text()
        AddRecord(cWeight)

    Func DeleteWeight
        Table1 {
             nRow = CurrentRow() 
            if nRow >= 0
                nID = this.aIDs[nROW+1] 
                new QSqlQuery( ) {
                    exec("delete from weighthistory where id = " + nID )
                }
                Del(this.aIDs,nRow+1)
                removerow(nRow)    
                selectrow(nRow)
            ok
        }

以下代码演示了 AddRecord() 和 ShowRecords() 方法。

AddRecord() 方法将体重作为参数,然后执行 SQL 命令 (Insert Into)。

ShowRecords() 方法将执行 SQL 命令 ("select * from weighthistory") 来获取记录数据。

然后显示 Table 中的数据。

    Func AddRecord cWeight
        new QSqlQuery( ) {
            cStr = "insert into weighthistory (f_date,f_time,f_weight) values ('%f1','%f2','%f3')"
            cDate = Date()
            cTime = Time()
            cStr = substr(cStr,"%f1",cDate)
            cStr = substr(cStr,"%f2",cTime)
            cStr = substr(cStr,"%f3",cWeight)
            exec(cStr)
            delete()
        }
        ShowRecords()
        Table1.selectrow(table1.rowcount()-1)


    Func ShowRecords
        table1.setitemChangedEvent("")
        aIDs = []
        query = new QSqlQuery() {
            exec("select * from weighthistory")
            nRows = 0
            this.Table1.setrowcount(0)
            while movenext() 
                this.table1 {
                    insertRow(nRows)
                    this.aIDs + query.value(0).tostring()
                    for x = 1 to 3 
                        cStr = query.value(x).tostring()
                        item = new qTableWidgetItem(cStr)
                        setItem(nRows,x-1,item)
                    next
                }
                nRows++
            end
            delete()
        }
        table1.setitemChangedEvent($ApplicationObject+".ItemChanged()")
     

最后,我们拥有 itemChanged() 方法。

使用以下方法,我们在通过用户界面更新 Table 控件后,更新数据库中的 Table。

该方法执行 SQL 命令 (Update)。

  Func ItemChanged
        nRow =  table1.currentrow()
        if nRow >= 0 
            myitem = Table1.item(table1.currentrow(),0)
            cDate = myitem.text()
            myitem = Table1.item(table1.currentrow(),1)
            cTime = myitem.text()
            myitem = Table1.item(table1.currentrow(),2)
            cWeight = myitem.text()
            new QSqlQuery( ) {
                cStr = "update weighthistory set f_date ='%f1' , f_time = '%f2' , f_weight ='%f3' where id = " +  this.aIDs[nROW+1] 
                cStr = substr(cStr,"%f1",cDate)
                cStr = substr(cStr,"%f2",cTime)
                cStr = substr(cStr,"%f3",cWeight)    
                exec(cStr)
                delete()
            }
        ok

以下屏幕截图展示了 Windows 上的应用程序。

要在 Android 上构建应用程序,请使用 Qt Creator 打开 Qt 项目并单击构建。

有关下载 Qt、Android SDK 和所需工具的信息,请查看此链接

以下屏幕截图显示了 Android 虚拟设备上的应用程序。

 

关注点

开发和测试应用程序作为桌面应用程序然后为 Android 创建包并获得相同结果非常简单。此外,使用 Ring 可以缩短开发时间,这要归功于动态类型、面向对象、通过 RingQt 提供的漂亮的 Qt 界面以及使用大括号 {} 快速访问对象属性和方法。

历史

Ring 编程语言 1.0 版本于 2016.01.25 发布。

Ring 编程语言 1.1 版本于 2016.10.06 发布。

本文中的此应用程序使用了 Ring 1.1 版本和 Qt 5.5。

© . All rights reserved.