在QML中利用Javascript动态生成画面

在这篇文章中介绍如何使用Javascript来动态生产画面。 我们在先前的例子中“如何使用QML动态产生Component来完成我们的气球游戏 (2)”已经对动态生产QML做了一些描述。也许那个项目比较复制,现在我来用一些简单的例子来说明一下,这样更加直观。更多的说明可以参阅文章“Dynamic
QML Object Creation from JavaScript
”。

1)创建我们的动态QML文件

这个文件将被用来被Javascript来动态生产。这是一个模版尽管每次生成的object的属性可能会不一样。

dynamic-image.qml

import QtQuick 2.0

Image {
    width: 400
    height: 225

    source: "images/image1.jpg"

    Image {
        id: overlay

        anchors.fill: parent

        source: "images/image2.jpg"

        opacity: 0;
        Behavior on opacity { NumberAnimation { duration: 300 } }
    }

    MouseArea {
        anchors.fill: parent
        onClicked: {
            if (overlay.opacity === 0)
                overlay.opacity = 1;
            else
                overlay.opacity = 0;
        }
    }
}

这是一个很简单的QML文件。它显示了一个画面,当我们点击画面时,overlay中的画面将会交叉显示或隐藏。

2)创建动态生产QML Object的Javascript

create-component.js

var component;

function createImageObject(x, y) {
    component = Qt.createComponent("dynamic-image.qml");
    if (component.status === Component.Ready || component.status === Component.Error)
        finishCreation(x, y);
    else
        component.statusChanged.connect(finishCreation);
}

function finishCreation(x, y) {
    if (component.status === Component.Ready)
    {
        var image = component.createObject(container, {"x": x, "y": y, width: 300, height:200});
        if (image == null)
            console.log("Error creating image");
    }
    else if (component.status === Component.Error)
        console.log("Error loading component:", component.errorString());
}

这个文件被用来动态生产我们所需要的QML Object。它采用的模版就是我们在上一节中所使用的“dynamic-image.qml”。我们可以设置它的位置参数。当然我们也可以设置它的其它的属性。这里的“container”是我们希望被生产的QML Object所希望放置的位置,也就是它的“父亲”。

3)在QML代码中调用Javascript来生产QML object

import QtQuick 2.0
import Ubuntu.Components 1.1
import "create-component.js" as ImageCreator

/*!
    \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: "dynamicqml.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 {
        id: root
        title: i18n.tr("dynamicqml")
        property int position: 0

        Flickable {
            width: parent.width
            height: parent.height
            clip:true
            contentHeight: container.childrenRect.height

            Column {
                id: container
                anchors.centerIn: parent
            }
        }

        Row {
            anchors.bottom: parent.bottom
            anchors.horizontalCenter: parent.horizontalCenter
            anchors.bottomMargin: units.gu(1)
            spacing: units.gu(1)

            Button {
                text: "Create New"

                onClicked: {
                    ImageCreator.createImageObject(0, root.position);
                    root.position += 200;
                }
            }

            Button {
                text: "Create from string"

                onClicked: {
                   var newObject = Qt.createQmlObject('import QtQuick 2.0;
                        Image {source: "images/image3.jpg"; width: 300; height: 200}',
                        container, "dynamicSnippet1");
                    newObject.x = 0;
                    newObject.y = root.position;
                }

            }

        }

        Component.onCompleted: {
            ImageCreator.createImageObject(0, 0);
            root.position += 200
        }
    }
}

在上面的代码中:

   Button {
                text: "Create New"

                onClicked: {
                    ImageCreator.createImageObject(0, root.position);
                    root.position += 200;
                }
            }

这个代码被用来生产我们所需要的QML Object, 并放置于我们所需要的位置。就像我们上一节中所介绍的那样,我们定义了一个“container”。这里实际上是一个Column的布局管理器。

另外,我们也可以使用代码:

           Button {
                text: "Create from string"

                onClicked: {
                   var newObject = Qt.createQmlObject('import QtQuick 2.0;
                        Image {source: "images/image3.jpg"; width: 300; height: 200}',
                        container, "dynamicSnippet1");
                    newObject.x = 0;
                    newObject.y = root.position;
                }

            }

使用字符串的方式 ,使用Qt.createQmlObject来创建我们的QML object。这也是一种简洁的方式。

运行我们的应用:

我们可以利用屏幕下面的按钮来动态生产我们的QML object。为了能够删除我们生产的QML object。

4)动态生产QML Object的管理

我们可以通过使用destroy来销毁已经生产的QML object。为了管理我们的object,我们来创建一个ListModel:

        ListModel {
            id: objectsModel
        }

我们可以通过如下的方式来添加我们生成的object:

 function itemAdded(obj, source) {
        objectsModel.append({"obj": obj, "source": source})
    }

这样,每当我们创建一个新的object时,我们也把它添加进来:

       Row {
            anchors.bottom: parent.bottom
            anchors.horizontalCenter: parent.horizontalCenter
            anchors.bottomMargin: units.gu(1)
            spacing: units.gu(1)

            Button {
                text: "Create New"

                onClicked: {
                    var image = ImageCreator.createImageObject(0, root.position);
                    itemAdded(image, "dynamic-image.qml");
                    root.position += 200;
                }
            }

最后,我们可以通过如下的方式来销毁我们所创建的所有的dynamic-image.qml的object。

            Button {
                text: "Clear objects"

                onClicked: {
                    while(objectsModel.count > 0) {
                        objectsModel.get(0).obj.destroy();
                        objectsModel.remove(0);
                    }
                }
            }

   

上面右图是按下“Clear objects”后的显示。

整个项目的源码在: git clone https://gitcafe.com/ubuntu/dynamicqml.git

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-07-29 16:53:56

在QML中利用Javascript动态生成画面的相关文章

[搬运自我的CSDN博客] python抓取javascript动态生成HTML内容的实践

<注:CSDN博客在美国访问特别卡,所以转移到cnblogs来发文章> 本实验在Ubuntu14.04上完成.使用的浏览器是火狐(Firefox 33.0),python版本是2.7.6. 大家都知道用urllib配合正则表达式抓取静态HTML的内容很方便,但是如果网页中有javascript动态生成的内容,urllib就无能为力了. 此时我们要借助一个额外的工具:selenium.它的工作原理是操纵(火狐)浏览器浏览目标网页,等待网页中的javascript全部执行完毕后再对HTML源码进行

利用Java动态生成 PDF 文档

利用Java动态生成 PDF 文档,则需要开源的API.首先我们先想象需求,在企业应用中,客户会提出一些复杂的需求,比如会针对具体的业务,构建比较典型的具备文档性质的内容,一般会导出PDF进行存档.那么目前最佳的解决方案,你可能会想到 iText ,对没错... iText+(Velocity / Freemarker)可以实现.不过据我熟悉,iText本身提供的HTML解析器还是不够强大,许多HTML标签和属性无法识别,更悲催的是简单的CSS它不认识,排版调整样式会让你头大的.不要失望,接下来

Javascript动态生成表格的性能调优

    vision 0.8 [耗时672ms]终极优化 将字符串作为数组对象的方式是目前效率最高,性能最优的方式.   <script> var t1 = new Date(); </script> <html> <head> <title></title> <script> function testTime(){ var t2 = new Date(); alert(t2-t1+"ms"); }

Firefox中利用javascript调用本地程序

http://blog.csdn.net/jensonhjt/article/details/1765557 script>function hello () {  netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");  var file = Components.classes["@mozilla.org/file/local;1"].createInstance(

QML中的JavaScript用法详解

熟悉JavaScript的应该都了解Netscape公司,一代骄子虽然倒下了,却给后人留下了最为珍贵的产品和经验,在互联网发展史上享有举足轻重的地位,这里就不讲故事了,虽然很精彩,从未被磨灭.QML是对JavaScript的扩展,提供了JS主机环境,用法相似,但有些地方与浏览器/服务器端提供的JS主机环境(如Node.js)是不同的,用起来又有一些限制,下面列举一些常用的方法. 1.QML文件中的JS表达式 初始化时属性绑定-- // Property.qml import QtQuick 2.

利用runtime动态生成对象?

利用runtime我们能够动态生成对象.属性.方法这特性 假定我们要动态生成DYViewController,并为它创建属性propertyName 1)对象名 NSString *class = @"DYViewController"; const char *className = [class cStringUsingEncoding:NSASCIIStringEncoding]; 2)从一个字符串返回一个Class Class newClass = objc_getClass(

ASP.NET中Literal使用——动态生成页面

在页面中添加内容时,如果是静态内容,无需使用容器,可以直接将标记作为HTML直接添加到页面中:但是,如果是动态内容,则必须借助容器将内容添加到页面中.典型的容器有:Label控件.Literal控件.Panel控件和PlaceHolder控件. 一.控件选择:Literal Literal控件与Lable控件的区别在于,Literal控件不向文本中添加任何HTML元素:而Label控件呈现一个span元素. Panel和PlaceHolder控件呈现为DIV元素,这将在页面上创建离散块,与Lab

nginx利用image_filter动态生成缩略图

原文:http://www.open-open.com/lib/view/open1416193847945.html "我现在是有些图片需要生成缩略图,这个现在加了image_filter这个已经实现了,但我不知道怎么样才能访问我上传的原图" 刚开始觉得也不太好弄,让他用程序区处理,实际上稍微动脑筋分析一下也可以不修改程序实现动态生成缩略图且能够访问原图. 前提是需要定好图片的访问规则. 先来看一下什么是nginx的image filter模块. HttpImageFilterMod

如何在QML中利用Sprite来做我们需要的动画

在游戏中动画的设计非常中要.在QML中,它提供了丰富的animation,但是有时我们需要对图像进行变化,就像放电影一样.在今天的这篇文章中,我们将设计一个可以变化图像的动画.我们可以通过Qt所提供的Sprite功能来实现. 为了设计的方便,我们先设计一个我们自己的bear动画,这个动画的图像大小为: 2048x256.它刚好是8副图256x256 在我们的Sprite设计中,我们想按照上述图像显示的顺序依次显示每个图像,这样就可以形成一个可以连续变化的动画效果. 直接把我们的动画设计文件Bea