StocQt demo improvement

Along with general demo improvements, this task implements the new layout
to the StocQt demo. Also few bugs on the functionality are corrected, like
drawing the stock graph on right way and initial values reset on stock
model when changing active stock.

Task-number: QTBUG-38254
Change-Id: I9d3387ed0e3f23512b8e60c70246589c10237818
Reviewed-by: Topi Reiniö <topi.reinio@digia.com>
This commit is contained in:
Mika Salmela 2014-05-02 14:14:55 +03:00 committed by The Qt Project
parent 7996ac4c0a
commit d98362f5e9
21 changed files with 853 additions and 722 deletions

View File

@ -47,17 +47,17 @@ Rectangle {
property bool buttonEnabled: false
width: Math.max(64, txt.width + 16)
height: 32
color: buttonEnabled ? "#76644A" : "transparent"
border.color: "#76644A"
border.width: 1
color: "transparent"
MouseArea {
anchors.fill: parent
onClicked: button.clicked()
}
Text {
anchors.centerIn: parent
font.pixelSize: 18
color: "#ecc089"
font.family: "Open Sans"
font.pointSize: 19
font.weight: Font.DemiBold
color: button.buttonEnabled ? "#000000" : "#14aaff"
id: txt
}
}

View File

@ -42,10 +42,9 @@ import QtQuick 2.0
Item {
id: button
property alias text: txt.text
property bool buttonEnabled: true
width: 140
height: 25
width: 30
height: 30
x: 5
MouseArea {
id: mouse
@ -59,29 +58,20 @@ Item {
}
Rectangle {
id: checkbox
width: 23
height: 23
width: 30
height: 30
anchors.left: parent.left
border.color: "#76644A"
border.color: "#999999"
border.width: 1
antialiasing: true
radius: 2
color: "transparent"
Rectangle {
anchors.fill: parent
anchors.margins: 4
anchors.margins: 5
antialiasing: true
radius: 1
color: mouse.pressed || buttonEnabled ? "#76644A" : "transparent"
color: mouse.pressed || buttonEnabled ? "#999999" : "transparent"
}
}
Text {
id: txt
anchors.left: checkbox.right
anchors.leftMargin: 4
anchors.verticalCenter: parent.verticalCenter
text: "Close "
color: "#ecc089"
font.pixelSize: 18
}
}

View File

@ -1,131 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of Digia Plc and its Subsidiary(-ies) nor the names
** of its contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
import QtQuick 2.0
Rectangle {
id: root
color: "transparent"
width: 300
height: 40
property var _monthNames: [ "JAN", "FEB", "MAR", "APR", "MAY", "JUN","JUL", "AUG", "SEP", "OCT", "NOV", "DEC" ];
property var date: new Date()
onDateChanged: {
month.text = root._monthNames[root.date.getMonth()];
day.text = date.getDate();
year.text = date.getFullYear();
}
Row {
spacing: 4
anchors.fill: parent
Rectangle {
height: root.height
width: root.width/3 - 20
color: "#272822"
border.color: "#76644A"
border.width: 1
radius: 2
antialiasing: true
TextInput {
id: month
anchors.centerIn: parent
color: "#ecc089"
font.pointSize: 25
font.bold: true
text: root._monthNames[root.date.getMonth()]
onAccepted: {
for (var i = 0; i < 12; i++) {
if (text === root._monthNames[i]) {
root.date.setMonth(i);
root.date = root.date;
return;
}
}
root.date = root.date;
}
}
}
Rectangle {
height: root.height
width: root.width/3 - 20
color: "#272822"
border.color: "#76644A"
border.width: 1
radius: 2
antialiasing: true
TextInput {
id: day
anchors.centerIn: parent
color: "#ecc089"
font.pointSize: 25
font.bold: true
text: root.date.getDate()
validator:IntValidator {bottom: 1; top: 31}
onAccepted: { root.date.setDate(text); root.date = root.date;}
}
}
Rectangle {
height: root.height
width: root.width/3 - 20
color: "#272822"
border.color: "#76644A"
border.width: 1
radius: 2
antialiasing: true
TextInput {
id: year
anchors.centerIn: parent
color: "#ecc089"
font.pointSize: 25
font.bold: true
text: root.date.getFullYear()
validator: IntValidator {bottom: 1995; top: (new Date()).getFullYear()}
onAccepted:{ root.date.setFullYear(text); root.date = root.date;}
}
}
}
}

View File

@ -43,93 +43,155 @@ import QtQuick 2.0
Rectangle {
id: chart
width: 320
height: 320
height: 200
color: "transparent"
property var _months: [ "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" ]
property var stockModel: null
property var startDate: new Date()
property var endDate: new Date()
property string activeChart: "year"
property var settings
function update() {
if (settings.chartType === "year")
endDate = new Date();
if (chart.activeChart === "year")
chart.startDate = new Date(chart.endDate.getFullYear() - 1, chart.endDate.getMonth(), chart.endDate.getDate());
else if (settings.chartType === "month")
else if (chart.activeChart === "month")
chart.startDate = new Date(chart.endDate.getFullYear() , chart.endDate.getMonth() -1, chart.endDate.getDate());
else if (settings.chartType === "week")
else if (chart.activeChart === "week")
chart.startDate = new Date(chart.endDate.getFullYear() , chart.endDate.getMonth(), chart.endDate.getDate() - 7);
else
chart.startDate = new Date(1995, 3, 25);
chart.startDate = new Date(2005, 3, 25);
canvas.requestPaint();
}
Row {
id: activeChartRow
anchors.left: chart.left
anchors.right: chart.right
anchors.top: chart.top
anchors.topMargin: 4
spacing: 52
onWidthChanged: {
var buttonsLen = maxButton.width + yearButton.width + monthButton.width + weekButton.width;
var space = (width - buttonsLen) / 3;
spacing = Math.max(space, 10);
}
Button {
id: maxButton
text: "Max"
buttonEnabled: chart.activeChart === "max"
onClicked: {
chart.activeChart = "max";
chart.update();
}
}
Button {
id: yearButton
text: "Year"
buttonEnabled: chart.activeChart === "year"
onClicked: {
chart.activeChart = "year";
chart.update();
}
}
Button {
id: monthButton
text: "Month"
buttonEnabled: chart.activeChart === "month"
onClicked: {
chart.activeChart = "month";
chart.update();
}
}
Button {
id: weekButton
text: "Week"
buttonEnabled: chart.activeChart === "week"
onClicked: {
chart.activeChart = "week";
chart.update();
}
}
}
Text {
id: fromDate
color: "#6a5b44"
color: "#000000"
width: 50
font.family: "Open Sans"
font.pointSize: 10
wrapMode: Text.WordWrap
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: parent.top
anchors.bottom: parent.bottom
text: _months[startDate.getMonth()] + "\n" + startDate.getFullYear()
}
Text {
id: toDate
color: "#6a5b44"
color: "#000000"
font.pointSize: 10
width: 50
wrapMode: Text.WordWrap
anchors.right: parent.right
anchors.leftMargin: 20
anchors.top: parent.top
anchors.bottom: parent.bottom
text: _months[endDate.getMonth()] + "\n" + endDate.getFullYear()
}
Canvas {
id: canvas
width: parent.width
anchors.top: toDate.bottom
anchors.bottom: parent.bottom
renderTarget: Canvas.FramebufferObject
anchors.top: activeChartRow.bottom
anchors.left: chart.left
anchors.right: chart.right
anchors.bottom: fromDate.top
antialiasing: true
property int frames: first
property int mouseX: 0
property int mouseY: 0
property int mousePressedX: 0
property int mousePressedY: 0
property int movedY: 0
property real scaleX: 1.0
property real scaleY: 1.0
property int first: 0
property int last: 0
property int pixelSkip: 1
property real xGridOffset: width / 13
property real xGridStep: width / 4
property real yGridOffset: height / 26
property real yGridStep: height / 12
function drawBackground(ctx) {
ctx.save();
ctx.fillStyle = "#272822";
ctx.fillStyle = "#ffffff";
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.strokeStyle = "#423a2f";
ctx.strokeStyle = "#d7d7d7";
ctx.beginPath();
for (var i = 0; i < 10; i++) {
ctx.moveTo(0, i * (canvas.height/10.0));
ctx.lineTo(canvas.width, i * (canvas.height/10.0));
// Horizontal grid lines
for (var i = 0; i < 12; i++) {
ctx.moveTo(0, canvas.yGridOffset + i * canvas.yGridStep);
ctx.lineTo(canvas.width, canvas.yGridOffset + i * canvas.yGridStep);
}
for (i = 0; i < 12; i++) {
ctx.moveTo(i * (canvas.width/12.0), 0);
ctx.lineTo(i * (canvas.width/12.0), canvas.height);
// Vertical grid lines
var height = 35 * canvas.height / 36;
var yOffset = canvas.height - height;
for (i = 0; i < 4; i++) {
ctx.moveTo(canvas.xGridOffset + i * canvas.xGridStep, yOffset);
ctx.lineTo(canvas.xGridOffset + i * canvas.xGridStep, height);
}
ctx.stroke();
ctx.strokeStyle = "#5c7a37";
// Right ticks
ctx.strokeStyle = "#666666";
ctx.beginPath();
ctx.moveTo(8 * (canvas.width/12.0), 0);
ctx.lineTo(8 * (canvas.width/12.0), canvas.height);
var xStart = 35 * canvas.width / 36;
ctx.moveTo(xStart, 0);
ctx.lineTo(xStart, canvas.height);
for (i = 0; i < 12; i++) {
ctx.moveTo(xStart, canvas.yGridOffset + i * canvas.yGridStep);
ctx.lineTo(canvas.width, canvas.yGridOffset + i * canvas.yGridStep);
}
ctx.moveTo(0, canvas.yGridOffset + 9 * canvas.yGridStep);
ctx.lineTo(canvas.width, canvas.yGridOffset + 9 * canvas.yGridStep);
ctx.closePath();
ctx.stroke();
ctx.restore();
@ -140,64 +202,29 @@ Rectangle {
ctx.save();
ctx.globalAlpha = 0.7;
ctx.strokeStyle = color;
ctx.lineWidth = 1;
ctx.lineWidth = 3;
ctx.beginPath();
var w = canvas.width/points.length;
var end = points.length;
for (var i = 0; i < end; i+=pixelSkip) {
var x = points[i].x;
var xOffset = canvas.width / 36
for (var i = 0; i < end; i += pixelSkip) {
var x = 34 * points[i].x / 36 + xOffset;
var y = points[i][price];
y = canvas.height * y/highest;
y = canvas.height - y;
y = 9 * y / 12 + yGridOffset; // Scaling to graph area
if (i == 0) {
ctx.moveTo(x+w/2, y);
ctx.moveTo(x, y);
} else {
ctx.lineTo(x+w/2, y);
ctx.lineTo(x, y);
}
}
ctx.stroke();
ctx.restore();
}
function drawKLine(ctx, from, to, points, highest)
{
ctx.save();
ctx.globalAlpha = 0.4;
ctx.lineWidth = 2;
var end = points.length;
for (var i = 0; i < end; i+=pixelSkip) {
var x = points[i].x;
var open = canvas.height * points[i].open/highest - canvas.movedY;
var close = canvas.height * points[i].close/highest - canvas.movedY;
var high = canvas.height * points[i].high/highest - canvas.movedY;
var low = canvas.height * points[i].low/highest - canvas.movedY;
var top, bottom;
if (close <= open) {
ctx.fillStyle = Qt.rgba(1, 0, 0, 1);
ctx.strokeStyle = Qt.rgba(1, 0, 0, 1);
top = close;
bottom = open;
} else {
ctx.fillStyle = Qt.rgba(0, 1, 0, 1);
ctx.strokeStyle = Qt.rgba(0, 1, 0, 1);
top = open;
bottom = close;
}
var w1, w2;
w1 = canvas.width/points.length;
w2 = w1 > 10 ? w1/2 : w1;
ctx.fillRect(x + (w1 - w2)/2, top, w2, bottom - top);
ctx.beginPath();
ctx.moveTo(x+w1/2, high);
ctx.lineTo(x+w1/2, low);
ctx.stroke();
}
ctx.restore();
}
function drawVolume(ctx, from, to, color, price, points, highest)
{
ctx.save();
@ -211,7 +238,8 @@ Rectangle {
var x = points[i].x;
var y = points[i][price];
y = canvas.height * (1 - y/highest);
ctx.fillRect(x, y, canvas.width/points.length, canvas.height - y);
y = 3 * y / 13;
ctx.fillRect(x, canvas.height - y, canvas.width/points.length, y);
}
ctx.restore();
}
@ -223,41 +251,39 @@ Rectangle {
ctx.lineWidth = 1;
drawBackground(ctx);
if (!stockModel.ready)
return;
last = stockModel.indexOf(chart.endDate)
first = last - (chart.endDate.getTime() - chart.startDate.getTime())/86400000;
first = Math.max(first, 0);
console.log("painting... first:" + first + ", last:" + last);
if (!stockModel.ready) {
return;
}
var last = stockModel.indexOf(chart.startDate);
var first = 0;
var highestPrice = stockModel.highestPrice;
var highestVolume = stockModel.highestVolume;
console.log("highest price:" + highestPrice + ", highest volume:" + highestVolume)
var points = [];
for (var i = 0; i <= last - first; i+=pixelSkip) {
var price = stockModel.get(i + first);
var step = canvas.width / (last + 0);
for (var i = last, j = 0; i >= 0 ; i -= pixelSkip, j += pixelSkip) {
var price = stockModel.get(i);
points.push({
x: i*canvas.width/(last-first+1),
x: j * step,
open: price.open,
close: price.close,
high:price.high,
low:price.low,
volume:price.volume
high: price.high,
low: price.low,
volume: price.volume
});
}
if (settings.drawHighPrice)
drawPrice(ctx, first, last, settings.highColor,"high", points, highestPrice);
drawPrice(ctx, first, last, settings.highColor, "high", points, highestPrice);
if (settings.drawLowPrice)
drawPrice(ctx, first, last, settings.lowColor,"low", points, highestPrice);
drawPrice(ctx, first, last, settings.lowColor, "low", points, highestPrice);
if (settings.drawOpenPrice)
drawPrice(ctx, first, last,settings.openColor,"open", points, highestPrice);
drawPrice(ctx, first, last,settings.openColor, "open", points, highestPrice);
if (settings.drawClosePrice)
drawPrice(ctx, first, last, settings.closeColor,"close", points, highestPrice);
if (settings.drawVolume)
drawVolume(ctx, first, last, settings.volumeColor,"volume", points, highestVolume);
if (settings.drawKLine)
drawKLine(ctx, first, last, points, highestPrice);
drawPrice(ctx, first, last, settings.closeColor, "close", points, highestPrice);
drawVolume(ctx, first, last, settings.volumeColor, "volume", points, highestVolume);
}
}
}

View File

@ -0,0 +1,119 @@
/****************************************************************************
**
** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of Digia Plc and its Subsidiary(-ies) nor the names
** of its contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
import QtQuick 2.0
Rectangle {
id: root
width: 440
height: 160
color: "transparent"
property var stock: null
Text {
id: stockIdText
anchors.left: parent.left
anchors.leftMargin: 5
anchors.top: parent.top
anchors.topMargin: 15
color: "#000000"
font.family: "Open Sans"
font.pointSize: 38
font.weight: Font.DemiBold
text: root.stock.stockId
}
Text {
id: stockNameText
anchors.left: parent.left
anchors.leftMargin: 5
anchors.bottom: priceChangePercentage.bottom
anchors.right: priceChangePercentage.left
anchors.rightMargin: 15
color: "#000000"
font.family: "Open Sans"
font.pointSize: 16
elide: Text.ElideRight
text: root.stock.stockName
}
Text {
id: price
anchors.right: parent.right
anchors.rightMargin: 5
anchors.top: parent.top
anchors.topMargin: 15
horizontalAlignment: Text.AlignRight
color: "#000000"
font.family: "Open Sans"
font.pointSize: 30
font.weight: Font.DemiBold
text: root.stock.stockPrice
}
Text {
id: priceChange
anchors.right: parent.right
anchors.rightMargin: 20
anchors.top: price.bottom
anchors.topMargin: 5
horizontalAlignment: Text.AlignRight
color: root.stock.stockPriceChanged < 0 ? "#d40000" : "#328930"
font.family: "Open Sans"
font.pointSize: 20
font.weight: Font.Bold
text: root.stock.stockPriceChanged
}
Text {
id: priceChangePercentage
anchors.right: parent.right
anchors.rightMargin: 20
anchors.top: priceChange.bottom
anchors.topMargin: 5
horizontalAlignment: Text.AlignRight
color: root.stock.stockPriceChanged < 0 ? "#d40000" : "#328930"
font.family: "Open Sans"
font.pointSize: 18
font.weight: Font.Bold
text: Math.abs(Math.round(root.stock.stockPriceChanged/(root.stock.stockPrice - root.stock.stockPriceChanged) * 100))/100 +"%"
}
}

View File

@ -43,104 +43,104 @@ import QtQuick 2.0
ListModel {
id: stocks
// Data from : http://en.wikipedia.org/wiki/NASDAQ-100
ListElement {name: "Activision Blizzard"; stockId: "ATVI"}
ListElement {name: "Adobe Systems Incorporated"; stockId: "ADBE"}
ListElement {name: "Akamai Technologies, Inc"; stockId: "AKAM"}
ListElement {name: "Alexion Pharmaceuticals"; stockId: "ALXN"}
ListElement {name: "Altera Corporation"; stockId: "ALTR"}
ListElement {name: "Amazon.com, Inc."; stockId: "AMZN"}
ListElement {name: "Amgen Inc."; stockId: "AMGN"}
ListElement {name: "Apollo Group, Inc."; stockId: "APOL"}
ListElement {name: "Apple Inc."; stockId: "AAPL"}
ListElement {name: "Applied Materials, Inc."; stockId: "AMAT"}
ListElement {name: "Autodesk, Inc."; stockId: "ADSK"}
ListElement {name: "Automatic Data Processing, Inc."; stockId: "ADP"}
ListElement {name: "Baidu.com, Inc."; stockId: "BIDU"}
ListElement {name: "Bed Bath & Beyond Inc."; stockId: "BBBY"}
ListElement {name: "Biogen Idec, Inc"; stockId: "BIIB"}
ListElement {name: "BMC Software, Inc."; stockId: "BMC"}
ListElement {name: "Broadcom Corporation"; stockId: "BRCM"}
ListElement {name: "C. H. Robinson Worldwide, Inc."; stockId: "CHRW"}
ListElement {name: "CA, Inc."; stockId: "CA"}
ListElement {name: "Celgene Corporation"; stockId: "CELG"}
ListElement {name: "Cephalon, Inc."; stockId: "CEPH"}
ListElement {name: "Cerner Corporation"; stockId: "CERN"}
ListElement {name: "Check Point Software Technologies Ltd."; stockId: "CHKP"}
ListElement {name: "Cisco Systems, Inc."; stockId: "CSCO"}
ListElement {name: "Citrix Systems, Inc."; stockId: "CTXS"}
ListElement {name: "Cognizant Technology Solutions Corporation"; stockId: "CTSH"}
ListElement {name: "Comcast Corporation"; stockId: "CMCSA"}
ListElement {name: "Costco Wholesale Corporation"; stockId: "COST"}
ListElement {name: "Ctrip.com International, Ltd."; stockId: "CTRP"}
ListElement {name: "Dell Inc."; stockId: "DELL"}
ListElement {name: "DENTSPLY International Inc."; stockId: "XRAY"}
ListElement {name: "DirecTV"; stockId: "DTV"}
ListElement {name: "Dollar Tree, Inc."; stockId: "DLTR"}
ListElement {name: "eBay Inc."; stockId: "EBAY"}
ListElement {name: "Electronic Arts Inc."; stockId: "ERTS"}
ListElement {name: "Expedia, Inc."; stockId: "EXPE"}
ListElement {name: "Expeditors International of Washington, Inc."; stockId: "EXPD"}
ListElement {name: "Express Scripts, Inc."; stockId: "ESRX"}
ListElement {name: "F5 Networks, Inc."; stockId: "FFIV"}
ListElement {name: "Fastenal Company"; stockId: "FAST"}
ListElement {name: "First Solar, Inc."; stockId: "FSLR"}
ListElement {name: "Fiserv, Inc."; stockId: "FISV"}
ListElement {name: "Flextronics International Ltd."; stockId: "FLEX"}
ListElement {name: "FLIR Systems, Inc."; stockId: "FLIR"}
ListElement {name: "Garmin Ltd."; stockId: "GRMN"}
ListElement {name: "Gilead Sciences, Inc."; stockId: "GILD"}
ListElement {name: "Google Inc."; stockId: "GOOG"}
ListElement {name: "Green Mountain Coffee Roasters, Inc."; stockId: "GMCR"}
ListElement {name: "Henry Schein, Inc."; stockId: "HSIC"}
ListElement {name: "Illumina, Inc."; stockId: "ILMN"}
ListElement {name: "Infosys Technologies"; stockId: "INFY"}
ListElement {name: "Intel Corporation"; stockId: "INTC"}
ListElement {name: "Intuit, Inc."; stockId: "INTU"}
ListElement {name: "Intuitive Surgical Inc."; stockId: "ISRG"}
ListElement {name: "Joy Global Inc."; stockId: "JOYG"}
ListElement {name: "KLA Tencor Corporation"; stockId: "KLAC"}
ListElement {name: "Lam Research Corporation"; stockId: "LRCX"}
ListElement {name: "Liberty Media Corporation, Interactive Series A"; stockId: "LINTA"}
ListElement {name: "Life Technologies Corporation"; stockId: "LIFE"}
ListElement {name: "Linear Technology Corporation"; stockId: "LLTC"}
ListElement {name: "Marvell Technology Group, Ltd."; stockId: "MRVL"}
ListElement {name: "Mattel, Inc."; stockId: "MAT"}
ListElement {name: "Maxim Integrated Products"; stockId: "MXIM"}
ListElement {name: "Microchip Technology Incorporated"; stockId: "MCHP"}
ListElement {name: "Micron Technology, Inc."; stockId: "MU"}
ListElement {name: "Microsoft Corporation"; stockId: "MSFT"}
ListElement {name: "Mylan, Inc."; stockId: "MYL"}
ListElement {name: "NetApp, Inc."; stockId: "NTAP"}
ListElement {name: "Netflix, Inc."; stockId: "NFLX"}
ListElement {name: "News Corporation, Ltd."; stockId: "NWSA"}
ListElement {name: "NII Holdings, Inc."; stockId: "NIHD"}
ListElement {name: "NVIDIA Corporation"; stockId: "NVDA"}
ListElement {name: "O'Reilly Automotive, Inc."; stockId: "ORLY"}
ListElement {name: "Oracle Corporation"; stockId: "ORCL"}
ListElement {name: "PACCAR Inc."; stockId: "PCAR"}
ListElement {name: "Paychex, Inc."; stockId: "PAYX"}
ListElement {name: "Priceline.com, Incorporated"; stockId: "PCLN"}
ListElement {name: "Qiagen N.V."; stockId: "QGEN"}
ListElement {name: "QUALCOMM Incorporated"; stockId: "QCOM"}
ListElement {name: "Research in Motion Limited"; stockId: "RIMM"}
ListElement {name: "Ross Stores Inc."; stockId: "ROST"}
ListElement {name: "SanDisk Corporation"; stockId: "SNDK"}
ListElement {name: "Seagate Technology Holdings"; stockId: "STX"}
ListElement {name: "Sears Holdings Corporation"; stockId: "SHLD"}
ListElement {name: "Sigma-Aldrich Corporation"; stockId: "SIAL"}
ListElement {name: "Staples Inc."; stockId: "SPLS"}
ListElement {name: "Starbucks Corporation"; stockId: "SBUX"}
ListElement {name: "Stericycle, Inc"; stockId: "SRCL"}
ListElement {name: "Symantec Corporation"; stockId: "SYMC"}
ListElement {name: "Teva Pharmaceutical Industries Ltd."; stockId: "TEVA"}
ListElement {name: "Urban Outfitters, Inc."; stockId: "URBN"}
ListElement {name: "VeriSign, Inc."; stockId: "VRSN"}
ListElement {name: "Vertex Pharmaceuticals"; stockId: "VRTX"}
ListElement {name: "Virgin Media, Inc."; stockId: "VMED"}
ListElement {name: "Vodafone Group, plc."; stockId: "VOD"}
ListElement {name: "Warner Chilcott, Ltd."; stockId: "WCRX"}
ListElement {name: "Whole Foods Market, Inc."; stockId: "WFM"}
ListElement {name: "Wynn Resorts Ltd."; stockId: "WYNN"}
ListElement {name: "Xilinx, Inc."; stockId: "XLNX"}
ListElement {name: "Yahoo! Inc."; stockId: "YHOO"}
ListElement {name: "Apple Inc."; stockId: "AAPL"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Adobe Systems Inc."; stockId: "ADBE"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Analog Devices, Inc."; stockId: "ADI"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Automatic Data Processing, Inc."; stockId: "ADP"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Autodesk, Inc."; stockId: "ADSK"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Akamai Technologies, Inc."; stockId: "AKAM"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Altera Corp."; stockId: "ALTR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Alexion Pharmaceuticals, Inc."; stockId: "ALXN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Applied Materials, Inc."; stockId: "AMAT"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Amgen Inc."; stockId: "AMGN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Amazon.com Inc."; stockId: "AMZN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Activision Blizzard, Inc."; stockId: "ATVI"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Avago Technologies Limited"; stockId: "AVGO"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Bed Bath & Beyond Inc."; stockId: "BBBY"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Baidu, Inc."; stockId: "BIDU"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Biogen Idec Inc."; stockId: "BIIB"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Broadcom Corp."; stockId: "BRCM"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "CA Technologies"; stockId: "CA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Celgene Corporation"; stockId: "CELG"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Cerner Corporation"; stockId: "CERN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Check Point Software Technologies Ltd."; stockId: "CHKP"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "CH Robinson Worldwide Inc."; stockId: "CHRW"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Charter Communications, Inc."; stockId: "CHTR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Comcast Corporation"; stockId: "CMCSA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Costco Wholesale Corporation"; stockId: "COST"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Cisco Systems, Inc."; stockId: "CSCO"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Catamaran Corporation"; stockId: "CTRX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Cognizant Technology Solutions Corporation"; stockId: "CTSH"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Citrix Systems, Inc."; stockId: "CTXS"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Discovery Communications, Inc."; stockId: "DISCA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Dish Network Corp."; stockId: "DISH"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Dollar Tree, Inc."; stockId: "DLTR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "DIRECTV"; stockId: "DTV"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "eBay Inc."; stockId: "EBAY"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Equinix, Inc."; stockId: "EQIX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Express Scripts Holding Company"; stockId: "ESRX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Expeditors International of Washington Inc."; stockId: "EXPD"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Expedia Inc."; stockId: "EXPE"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Fastenal Company"; stockId: "FAST"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Facebook, Inc."; stockId: "FB"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "F5 Networks, Inc."; stockId: "FFIV"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Fiserv, Inc."; stockId: "FISV"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Twenty-First Century Fox, Inc."; stockId: "FOXA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Gilead Sciences Inc."; stockId: "GILD"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Keurig Green Mountain, Inc."; stockId: "GMCR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Google Inc."; stockId: "GOOG"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Google Inc."; stockId: "GOOGL"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Garmin Ltd."; stockId: "GRMN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Henry Schein, Inc."; stockId: "HSIC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Illumina Inc."; stockId: "ILMN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Intel Corporation"; stockId: "INTC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Intuit Inc."; stockId: "INTU"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Intuitive Surgical, Inc."; stockId: "ISRG"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "KLA-Tencor Corporation"; stockId: "KLAC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Kraft Foods Group, Inc."; stockId: "KRFT"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Liberty Global plc"; stockId: "LBTYA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Liberty Interactive Corporation"; stockId: "LINTA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Linear Technology Corporation"; stockId: "LLTC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Liberty Media Corporation"; stockId: "LMCA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Marriott International, Inc."; stockId: "MAR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Mattel, Inc"; stockId: "MAT"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Mondelez International, Inc."; stockId: "MDLZ"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Monster Beverage Corporation"; stockId: "MNST"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Microsoft Corporation"; stockId: "MSFT"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Micron Technology Inc."; stockId: "MU"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Maxim Integrated Products, Inc."; stockId: "MXIM"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Mylan, Inc."; stockId: "MYL"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Netflix, Inc."; stockId: "NFLX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "NetApp, Inc."; stockId: "NTAP"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "NVIDIA Corporation"; stockId: "NVDA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "NXP Semiconductors NV"; stockId: "NXPI"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "O'Reilly Automotive Inc."; stockId: "ORLY"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Paychex, Inc."; stockId: "PAYX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "PACCAR Inc."; stockId: "PCAR"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "The Priceline Group Inc."; stockId: "PCLN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "QUALCOMM Incorporated"; stockId: "QCOM"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Regeneron Pharmaceuticals, Inc."; stockId: "REGN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Ross Stores Inc."; stockId: "ROST"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "SBA Communications Corp."; stockId: "SBAC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Starbucks Corporation"; stockId: "SBUX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Sigma-Aldrich Corporation"; stockId: "SIAL"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Sirius XM Holdings Inc."; stockId: "SIRI"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "SanDisk Corp."; stockId: "SNDK"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Staples, Inc."; stockId: "SPLS"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Stericycle, Inc."; stockId: "SRCL"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Seagate Technology Public Limited Company"; stockId: "STX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Symantec Corporation"; stockId: "SYMC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "TripAdvisor Inc."; stockId: "TRIP"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Tractor Supply Company"; stockId: "TSCO"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Tesla Motors, Inc."; stockId: "TSLA"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Texas Instruments Inc."; stockId: "TXN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Viacom, Inc."; stockId: "VIAB"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "VimpelCom Ltd."; stockId: "VIP"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Vodafone Group Public Limited Company"; stockId: "VOD"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Verisk Analytics, Inc."; stockId: "VRSK"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Vertex Pharmaceuticals Incorporated"; stockId: "VRTX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Western Digital Corporation"; stockId: "WDC"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Whole Foods Market, Inc."; stockId: "WFM"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Wynn Resorts Ltd."; stockId: "WYNN"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
ListElement {name: "Xilinx Inc."; stockId: "XLNX"; value: "0.0"; change: "0.0"; changePercentage: "0.0"}
}

View File

@ -43,8 +43,10 @@ import QtQuick 2.0
Rectangle {
id: root
width: 320
height: 480
color: "#423A2F"
height: 410
anchors.top: parent.top
anchors.bottom: parent.bottom
color: "white"
property string currentStockId: ""
property string currentStockName: ""
@ -52,39 +54,196 @@ Rectangle {
ListView {
id: view
anchors.fill: parent
width: parent.width
clip: true
keyNavigationWraps: true
highlightMoveDuration: 0
focus: true
snapMode: ListView.SnapToItem
model: StockListModel{}
function requestUrl(stockId) {
var endDate = new Date(""); //today
var startDate = new Date()
startDate.setDate(startDate.getDate() - 5);
var request = "http://ichart.finance.yahoo.com/table.csv?";
request += "s=" + stockId;
request += "&g=d";
request += "&a=" + startDate.getMonth();
request += "&b=" + startDate.getDate();
request += "&c=" + startDate.getFullYear();
request += "&d=" + endDate.getMonth();
request += "&e=" + endDate.getDate();
request += "&f=" + endDate.getFullYear();
request += "&g=d";
request += "&ignore=.csv";
return request;
}
function getCloseValue(index) {
var req = requestUrl(model.get(index).stockId);
if (!req)
return;
var xhr = new XMLHttpRequest;
xhr.open("GET", req, true);
xhr.onreadystatechange = function() {
if (xhr.readyState === XMLHttpRequest.LOADING || xhr.readyState === XMLHttpRequest.DONE) {
var records = xhr.responseText.split('\n');
if (records.length > 0) {
var r = records[1].split(',');
model.setProperty(index, "value", r[4]);
var today = parseFloat(r[4]);
r = records[2].split(',');
var yesterday = parseFloat(r[4]);
var change = today - yesterday;
if (change >= 0.0)
model.setProperty(index, "change", "+" + change.toFixed(2));
else
model.setProperty(index, "change", change.toFixed(2));
var changePercentage = (change / yesterday) * 100.0;
if (changePercentage >= 0.0)
model.setProperty(index, "changePercentage", "+" + changePercentage.toFixed(2) + "%");
else
model.setProperty(index, "changePercentage", changePercentage.toFixed(2) + "%");
}
}
}
xhr.send()
}
onCurrentIndexChanged: {
mainRect.listViewActive = 0;
root.currentStockId = model.get(currentIndex).stockId;
root.currentStockName = model.get(currentIndex).name;
console.log("current stock:" + root.currentStockId + " - " + root.currentStockName);
}
delegate: Rectangle {
height: 30
height: 102
width: parent.width
color: "transparent"
MouseArea {
anchors.fill: parent;
onClicked:view.currentIndex = index;
onClicked: {
view.currentIndex = index;
}
}
Text {
anchors.verticalCenter: parent.top
anchors.verticalCenterOffset : 15
color: index == view.currentIndex ? "#ECC089" : "#A58963"
font.pointSize: 12
id: stockIdText
anchors.top: parent.top
anchors.topMargin: 15
anchors.left: parent.left
anchors.leftMargin: 15
width: 125
height: 40
color: "#000000"
font.family: "Open Sans"
font.pointSize: 20
font.weight: Font.Bold
verticalAlignment: Text.AlignVCenter
text: stockId
}
Text {
id: stockValueText
anchors.top: parent.top
anchors.topMargin: 15
anchors.right: parent.right
anchors.rightMargin: 0.31 * parent.width
width: 190
height: 40
color: "#000000"
font.family: "Open Sans"
font.pointSize: 20
font.bold: true
text:" " + stockId + " - " + name
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: value
Component.onCompleted: view.getCloseValue(index);
}
Text {
id: stockValueChangeText
anchors.top: parent.top
anchors.topMargin: 15
anchors.right: parent.right
anchors.rightMargin: 20
width: 135
height: 40
color: "#328930"
font.family: "Open Sans"
font.pointSize: 20
font.bold: true
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: change
onTextChanged: {
if (parseFloat(text) >= 0.0)
color = "#328930";
else
color = "#d40000";
}
}
Text {
id: stockNameText
anchors.top: stockIdText.bottom
anchors.left: parent.left
anchors.leftMargin: 15
width: 330
height: 30
color: "#000000"
font.family: "Open Sans"
font.pointSize: 16
font.bold: false
elide: Text.ElideRight
maximumLineCount: 1
verticalAlignment: Text.AlignVCenter
text: name
}
Text {
id: stockValueChangePercentageText
anchors.top: stockIdText.bottom
anchors.right: parent.right
anchors.rightMargin: 20
width: 120
height: 30
color: "#328930"
font.family: "Open Sans"
font.pointSize: 18
font.bold: false
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: changePercentage
onTextChanged: {
if (parseFloat(text) >= 0.0)
color = "#328930";
else
color = "#d40000";
}
}
Rectangle {
id: endingLine
anchors.bottom: parent.bottom
anchors.left: parent.left
height: 1
width: parent.width
color: "#d7d7d7"
}
}
highlight: Rectangle {
width: parent.width
color: "#662"
color: "#eeeeee"
}
}
}

View File

@ -44,8 +44,6 @@ ListModel {
id: model
property string stockId: ""
property string stockName: ""
property var startDate
property var endDate
property string stockDataCycle: "d"
property bool ready: false
property real stockPrice: 0.0
@ -56,19 +54,28 @@ ListModel {
signal dataReady
function indexOf(date) {
var end = new Date(model.get(0).date);
var start = new Date(model.get(model.count - 1).date);
if (end <= date)
return model.count -1;
var newest = new Date(model.get(0).date);
var oldest = new Date(model.get(model.count - 1).date);
if (newest <= date)
return -1;
if (start >= date)
return 0;
if (oldest >= date)
return model.count - 1;
var currDiff = 0;
var bestDiff = Math.abs(date.getTime() - newest.getTime());
var retval = 0;
for (var i = 0; i < model.count; i++) {
var d = new Date(model.get(i).date);
if ( d === date)
return i;
currDiff = Math.abs(d.getTime() - date.getTime());
if (currDiff < bestDiff) {
bestDiff = currDiff;
retval = i;
}
if (currDiff > bestDiff)
return retval;
}
return -1;
}
@ -76,11 +83,9 @@ ListModel {
if (stockId === "")
return;
if (startDate === undefined)
startDate = new Date(1995, 3, 25); //default: 25 April 1995
var startDate = new Date(2011, 4, 25);
if (endDate === undefined)
endDate = new Date(); //today
var endDate = new Date(); //today
if (stockDataCycle !== "d" && stockDataCycle !== "w" && stockDataCycle !== "m")
stockDataCycle = "d";
@ -94,11 +99,11 @@ ListModel {
*/
var request = "http://ichart.finance.yahoo.com/table.csv?";
request += "s=" + stockId;
request += "&a=" + startDate.getDate();
request += "&b=" + startDate.getMonth();
request += "&a=" + startDate.getMonth();
request += "&b=" + startDate.getDate();
request += "&c=" + startDate.getFullYear();
request += "&d=" + endDate.getDate();
request += "&e=" + endDate.getMonth();
request += "&d=" + endDate.getMonth();
request += "&e=" + endDate.getDate();
request += "&f=" + endDate.getFullYear();
request += "&g=" + stockDataCycle;
request += "&ignore=.csv";
@ -133,6 +138,10 @@ ListModel {
model.ready = false;
model.clear();
highestPrice = 0;
highestVolume = 0;
var i = 1; //skip the first line
xhr.onreadystatechange = function() {
if (xhr.readyState === XMLHttpRequest.LOADING || xhr.readyState === XMLHttpRequest.DONE) {

View File

@ -1,216 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of Digia Plc and its Subsidiary(-ies) nor the names
** of its contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
import QtQuick 2.0
Rectangle {
id: root
width: 320
height: 480
color: "#423A2F"
property var startDate : startDatePicker.date
property var endDate : endDatePicker.date
property bool drawHighPrice: highButton.buttonEnabled
property bool drawLowPrice: lowButton.buttonEnabled
property bool drawOpenPrice: openButton.buttonEnabled
property bool drawClosePrice: closeButton.buttonEnabled
property bool drawVolume: volumeButton.buttonEnabled
property bool drawKLine: klineButton.buttonEnabled
property color highColor: Qt.rgba(1, 0, 0, 1)
property color lowColor: Qt.rgba(0, 1, 0, 1)
property color openColor: Qt.rgba(0, 0, 1, 1)
property color volumeColor: Qt.rgba(0.3, 0.5, 0.7, 1)
property color closeColor: "#ecc088"
property string chartType: "year"
Image {
id: logo
source: "images/logo.png"
anchors.horizontalCenter : parent.horizontalCenter
anchors.top: parent.top
anchors.topMargin: 15
}
Text {
id: startDateText
text: "START DATE:"
color: "#76644A"
font.pointSize: 15
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: logo.bottom
anchors.topMargin: 20
}
DatePicker {
id: startDatePicker
anchors.left: parent.left
anchors.leftMargin: 30
anchors.top: startDateText.bottom
anchors.topMargin: 8
}
Text {
id: endDateText
text: "END DATE:"
color: "#76644A"
font.pointSize: 15
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: startDatePicker.bottom
anchors.topMargin: 20
}
DatePicker {
id: endDatePicker
anchors.left: parent.left
anchors.leftMargin: 30
anchors.top: endDateText.bottom
anchors.topMargin: 8
}
Text {
id: drawOptionsText
text: "DRAW OPTIONS:"
color: "#76644A"
font.pointSize: 15
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: endDatePicker.bottom
anchors.topMargin: 20
}
Column {
id: drawOptions
anchors.top: drawOptionsText.bottom
anchors.topMargin: 8
anchors.left: parent.left
anchors.leftMargin: 30
spacing: 2
Row {
spacing: 10
CheckBox {
id: highButton
text: "High"
buttonEnabled: false
}
CheckBox {
id: lowButton
text: "Low"
buttonEnabled: false
}
}
Row {
spacing: 10
CheckBox {
id: openButton
text: "Open"
buttonEnabled: false
}
CheckBox {
text: "Close"
id: closeButton
buttonEnabled: true
}
}
Row {
spacing: 10
CheckBox {
id: volumeButton
text: "Volume"
buttonEnabled: true
}
CheckBox {
id: klineButton
text: "K Line"
buttonEnabled: false
}
}
}
Text {
id: chartTypeText
text: "SHOW PREVIOUS:"
color: "#76644A"
font.pointSize: 15
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: drawOptions.bottom
anchors.topMargin: 20
}
Row {
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: chartTypeText.bottom
anchors.topMargin: 8
spacing: -1
Button {
id: yearView
text: "YEAR"
buttonEnabled: root.chartType == "year"
onClicked: root.chartType = "year"
}
Button {
id: monthView
text: "MONTH"
buttonEnabled: root.chartType == "month"
onClicked: root.chartType = "month"
}
Button {
id: weekView
text: "WEEK"
buttonEnabled: root.chartType == "week"
onClicked: root.chartType = "week"
}
Button {
id: allView
text: "ALL"
buttonEnabled: root.chartType == "all"
onClicked: root.chartType = "all"
}
}
Component.onCompleted: startDatePicker.date = new Date(1995, 3, 25)
}

View File

@ -0,0 +1,174 @@
/****************************************************************************
**
** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of Digia Plc and its Subsidiary(-ies) nor the names
** of its contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
import QtQuick 2.0
Rectangle {
id: root
width: 440
height: 160
color: "transparent"
property bool drawOpenPrice: openButton.buttonEnabled
property bool drawClosePrice: closeButton.buttonEnabled
property bool drawHighPrice: highButton.buttonEnabled
property bool drawLowPrice: lowButton.buttonEnabled
property string openColor: "#face20"
property string closeColor: "#14aaff"
property string highColor: "#80c342"
property string lowColor: "#f30000"
property string volumeColor: "#14aaff"
Text {
id: openText
anchors.left: root.left
anchors.top: root.top
color: "#000000"
font.family: "Open Sans"
font.pointSize: 19
text: "Open"
}
Text {
id: closeText
anchors.left: root.left
anchors.top: openText.bottom
anchors.topMargin: 10
color: "#000000"
font.family: "Open Sans"
font.pointSize: 19
text: "Close"
}
Text {
id: highText
anchors.left: root.left
anchors.top: closeText.bottom
anchors.topMargin: 10
color: "#000000"
font.family: "Open Sans"
font.pointSize: 19
text: "High"
}
Text {
id: lowText
anchors.left: root.left
anchors.top: highText.bottom
anchors.topMargin: 10
color: "#000000"
font.family: "Open Sans"
font.pointSize: 19
text: "Low"
}
Rectangle {
height: 4
anchors.left: root.left
anchors.leftMargin: 114
anchors.right: openButton.left
anchors.rightMargin: 65
anchors.verticalCenter: openText.verticalCenter
color: openColor
}
Rectangle {
height: 4
anchors.left: root.left
anchors.leftMargin: 114
anchors.right: closeButton.left
anchors.rightMargin: 65
anchors.verticalCenter: closeText.verticalCenter
color: closeColor
}
Rectangle {
height: 4
anchors.left: root.left
anchors.leftMargin: 114
anchors.right: highButton.left
anchors.rightMargin: 65
anchors.verticalCenter: highText.verticalCenter
color: highColor
}
Rectangle {
height: 4
anchors.left: root.left
anchors.leftMargin: 114
anchors.right: lowButton.left
anchors.rightMargin: 65
anchors.verticalCenter: lowText.verticalCenter
color: lowColor
}
CheckBox {
id: openButton
buttonEnabled: false
anchors.verticalCenter: openText.verticalCenter
anchors.right: root.right
anchors.rightMargin: 40
}
CheckBox {
id: closeButton
buttonEnabled: false
anchors.verticalCenter: closeText.verticalCenter
anchors.right: root.right
anchors.rightMargin: 40
}
CheckBox {
id: highButton
buttonEnabled: true
anchors.verticalCenter: highText.verticalCenter
anchors.right: root.right
anchors.rightMargin: 40
}
CheckBox {
id: lowButton
buttonEnabled: true
anchors.verticalCenter: lowText.verticalCenter
anchors.right: root.right
anchors.rightMargin: 40
}
}

View File

@ -39,95 +39,63 @@
****************************************************************************/
import QtQuick 2.0
import QtQuick.Window 2.1
Rectangle {
id: root
width: 320
height: 480
color: "#423A2F"
color: "transparent"
property var stock: null
property var stocklist: null
property var settings: null
signal listViewClicked
signal settingsClicked
function update() {
if (!settings)
return;
chart.endDate = settings.endDate
chart.update()
}
Rectangle {
color: "#272822"
id: mainRect
color: "transparent"
anchors.fill: parent
radius: 20
Image {
source: "images/icon-items.png"
StockInfo {
id: stockInfo
anchors.left: parent.left
anchors.leftMargin: 10
anchors.top: parent.top
anchors.topMargin: 10
MouseArea {
anchors.fill: parent
onClicked: listViewClicked()
}
}
Image {
source: "images/icon-settings.png"
anchors.right: parent.right
anchors.rightMargin: 10
anchors.top: parent.top
anchors.topMargin: 10
MouseArea {
anchors.fill: parent
onClicked: settingsClicked()
}
}
Text {
id: desc
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: parent.top
anchors.topMargin: 40
color: "#564c3A"
font.pointSize: 15
text: root.stock.stockId + " - " + root.stock.stockName
}
Text {
id: price
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: desc.bottom
anchors.topMargin: 5
color: "#ECC089"
font.pointSize: 30
text: root.stock.stockPrice
}
Text {
id: priceChange
anchors.left: parent.left
anchors.leftMargin: 20
anchors.top: price.bottom
anchors.topMargin: 5
color: root.stock.stockPriceChanged < 0 ? "#A43D3D" : "#679B3A"
font.pointSize: 25
text: root.stock.stockPriceChanged + " (" + Math.abs(Math.round(root.stock.stockPriceChanged/(root.stock.stockPrice - root.stock.stockPriceChanged) * 100))/100 +"%)"
anchors.topMargin: 15
height: 160
anchors.right: Screen.primaryOrientation === Qt.PortraitOrientation ? parent.right : chart.left
anchors.rightMargin: 20
stock: root.stock
}
StockChart {
id: chart
anchors.bottom: parent.bottom
anchors.top : priceChange.bottom
anchors.topMargin: 30
width: parent.width
anchors.bottom: Screen.primaryOrientation === Qt.PortraitOrientation ? settingsPanel.top : parent.bottom
anchors.bottomMargin: 20
anchors.top : Screen.primaryOrientation === Qt.PortraitOrientation ? stockInfo.bottom : parent.top
anchors.topMargin: 20
anchors.right: parent.right
anchors.rightMargin: 20
width: Screen.primaryOrientation === Qt.PortraitOrientation ? parent.width - 40 : 0.6 * parent.width
stockModel: root.stock
settings: root.settings
settings: settingsPanel
}
StockSettingsPanel {
id: settingsPanel
anchors.left: parent.left
anchors.leftMargin: 20
anchors.right: Screen.primaryOrientation === Qt.PortraitOrientation ? parent.right : chart.left
anchors.rightMargin: 20
anchors.bottom: parent.bottom
onDrawOpenPriceChanged: root.update()
onDrawClosePriceChanged: root.update();
onDrawHighPriceChanged: root.update();
onDrawLowPriceChanged: root.update();
}
}
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 884 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 887 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 24 KiB

After

Width:  |  Height:  |  Size: 48 KiB

View File

@ -3,6 +3,7 @@ TEMPLATE = app
QT += qml quick
SOURCES += main.cpp
RESOURCES += stocqt.qrc
OTHER_FILES += *.qml content/*.qml content/images/*.png
target.path = $$[QT_INSTALL_EXAMPLES]/quick/demos/stocqt
INSTALLS += target

View File

@ -42,67 +42,103 @@ import QtQuick 2.0
import QtQml.Models 2.1
import "./content"
ListView {
id: root
width: 320
height: 480
snapMode: ListView.SnapOneItem
focus: false
orientation: ListView.Horizontal
boundsBehavior: Flickable.StopAtBounds
currentIndex: 1
Rectangle {
id: mainRect
width: 1000
height: 700
Timer {
id: updateTimer
interval: 500
onTriggered: stock.updateStock()
}
property int listViewActive: 0
StockModel {
id: stock
stockId: listView.currentStockId
stockName: listView.currentStockName
startDate: settings.startDate
endDate: settings.endDate
onStockIdChanged: updateTimer.restart()
onStartDateChanged: updateTimer.restart()
onEndDateChanged: updateTimer.restart()
onDataReady: {
root.positionViewAtIndex(1, ListView.SnapPosition)
stockView.update()
Rectangle {
id: banner
height: 80
anchors.top: parent.top
width: parent.width
color: "#000000"
Image {
id: arrow
source: "./content/images/icon-left-arrow.png"
anchors.left: banner.left
anchors.leftMargin: 20
anchors.verticalCenter: banner.verticalCenter
visible: root.currentIndex == 1 ? true : false
MouseArea {
anchors.fill: parent
onClicked: listViewActive = 1;
}
}
Item {
id: textItem
width: stocText.width + qtText.width
height: stocText.height + qtText.height
anchors.horizontalCenter: banner.horizontalCenter
anchors.verticalCenter: banner.verticalCenter
Text {
id: stocText
anchors.verticalCenter: textItem.verticalCenter
color: "#ffffff"
font.family: "Abel"
font.pointSize: 40
text: "Stoc"
}
Text {
id: qtText
anchors.verticalCenter: textItem.verticalCenter
anchors.left: stocText.right
color: "#5caa15"
font.family: "Abel"
font.pointSize: 40
text: "Qt"
}
}
}
model: ObjectModel {
StockListView {
id: listView
width: root.width
height: root.height
ListView {
id: root
width: parent.width
anchors.top: banner.bottom
anchors.bottom: parent.bottom
snapMode: ListView.SnapOneItem
highlightRangeMode: ListView.StrictlyEnforceRange
highlightMoveDuration: 250
focus: false
orientation: ListView.Horizontal
boundsBehavior: Flickable.StopAtBounds
currentIndex: listViewActive == 0 ? 1 : 0
onCurrentIndexChanged: {
if (currentIndex == 1)
listViewActive = 0;
}
StockView {
id: stockView
width: root.width
height: root.height
stocklist: listView
settings: settings
stock: stock
onListViewClicked: root.currentIndex = 0
onSettingsClicked: root.currentIndex = 2
StockModel {
id: stock
stockId: listView.currentStockId
stockName: listView.currentStockName
onStockIdChanged: stock.updateStock();
onDataReady: {
root.positionViewAtIndex(1, ListView.SnapPosition)
stockView.update()
}
}
StockSettings {
id: settings
width: root.width
height: root.height
onDrawHighPriceChanged: stockView.update()
onDrawLowPriceChanged: stockView.update()
onDrawOpenPriceChanged: stockView.update()
onDrawClosePriceChanged: stockView.update()
onDrawVolumeChanged: stockView.update()
onDrawKLineChanged: stockView.update()
onChartTypeChanged: stockView.update()
model: ObjectModel {
StockListView {
id: listView
width: root.width
height: root.height
}
StockView {
id: stockView
width: root.width
height: root.height
stocklist: listView
stock: stock
}
}
}
}

View File

@ -3,19 +3,15 @@
<file>stocqt.qml</file>
<file>content/Button.qml</file>
<file>content/CheckBox.qml</file>
<file>content/DatePicker.qml</file>
<file>content/StockChart.qml</file>
<file>content/StockListModel.qml</file>
<file>content/StockListView.qml</file>
<file>content/StockModel.qml</file>
<file>content/StockSettings.qml</file>
<file>content/StockView.qml</file>
<file>content/images/icon-calendar-anim.png</file>
<file>content/images/icon-calendar.png</file>
<file>content/images/icon-items.png</file>
<file>content/images/icon-settings.png</file>
<file>content/images/logo.png</file>
<file>content/images/wheel-touch.png</file>
<file>content/images/wheel.png</file>
<file>content/images/icon-left-arrow.png</file>
<file>content/StockSettingsPanel.qml</file>
<file>content/StockInfo.qml</file>
</qresource>
</RCC>