feat(communityChart): Add messages over time chart - mocked data
Implementing community messages over time chart Adding `OverviewSettingsChart.qml` to storybook
This commit is contained in:
parent
1a5907e22c
commit
bed7db5528
|
@ -201,6 +201,10 @@ ListModel {
|
||||||
title: "StatusInfoBoxPanel"
|
title: "StatusInfoBoxPanel"
|
||||||
section: "Panels"
|
section: "Panels"
|
||||||
}
|
}
|
||||||
|
ListElement {
|
||||||
|
title: "OverviewSettingsChart"
|
||||||
|
section: "Panels"
|
||||||
|
}
|
||||||
ListElement {
|
ListElement {
|
||||||
title: "BurnTokensPopup"
|
title: "BurnTokensPopup"
|
||||||
section: "Popups"
|
section: "Popups"
|
||||||
|
|
|
@ -236,5 +236,8 @@
|
||||||
],
|
],
|
||||||
"OwnerTokenWelcomeView": [
|
"OwnerTokenWelcomeView": [
|
||||||
"https://www.figma.com/file/17fc13UBFvInrLgNUKJJg5/Kuba%E2%8E%9CDesktop?type=design&node-id=34794%3A590064&mode=design&t=eabTmd6JZbuycoy8-1"
|
"https://www.figma.com/file/17fc13UBFvInrLgNUKJJg5/Kuba%E2%8E%9CDesktop?type=design&node-id=34794%3A590064&mode=design&t=eabTmd6JZbuycoy8-1"
|
||||||
|
],
|
||||||
|
"OverviewSettingsChart": [
|
||||||
|
"https://www.figma.com/file/17fc13UBFvInrLgNUKJJg5/Kuba⎜Desktop?type=design&node-id=31281-635619&mode=design&t=RYpVRgwqCjp8fUEX-0"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,30 @@
|
||||||
|
import QtQuick 2.15
|
||||||
|
import QtQuick.Controls 2.15
|
||||||
|
|
||||||
|
import AppLayouts.Communities.panels 1.0
|
||||||
|
import Models 1.0
|
||||||
|
|
||||||
|
SplitView {
|
||||||
|
|
||||||
|
OverviewSettingsChart {
|
||||||
|
id: chart
|
||||||
|
SplitView.fillWidth: true
|
||||||
|
SplitView.fillHeight: true
|
||||||
|
|
||||||
|
model: generateRandomModel()
|
||||||
|
}
|
||||||
|
|
||||||
|
function generateRandomModel() {
|
||||||
|
var newModel = []
|
||||||
|
const now = Date.now()
|
||||||
|
for(var i = 0; i < 500000; i++) {
|
||||||
|
var date = generateRandomDate(1463154962000, now)
|
||||||
|
newModel.push(date)
|
||||||
|
}
|
||||||
|
return newModel
|
||||||
|
}
|
||||||
|
|
||||||
|
function generateRandomDate(from, to) {
|
||||||
|
return from + Math.random() * (to - from)
|
||||||
|
}
|
||||||
|
}
|
|
@ -97,6 +97,18 @@ Page {
|
||||||
*/
|
*/
|
||||||
property int defaultTimeRangeIndexShown: 0
|
property int defaultTimeRangeIndexShown: 0
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\qmlproperty int StatusChartPanel::headerLeftPadding
|
||||||
|
This property holds the left padding of the header.
|
||||||
|
*/
|
||||||
|
property int headerLeftPadding: 46
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\qmlproperty int StatusChartPanel::headerBottomPadding
|
||||||
|
This property holds the bottom padding of the header.
|
||||||
|
*/
|
||||||
|
property int headerBottomPadding: 0
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\qmlsignal
|
\qmlsignal
|
||||||
This signal is emitted when a header tab bar is clicked.
|
This signal is emitted when a header tab bar is clicked.
|
||||||
|
@ -141,10 +153,10 @@ Page {
|
||||||
|
|
||||||
background: null
|
background: null
|
||||||
header: Item {
|
header: Item {
|
||||||
height: childrenRect.height
|
height: childrenRect.height + root.headerBottomPadding
|
||||||
RowLayout {
|
RowLayout {
|
||||||
anchors.left: parent.left
|
anchors.left: parent.left
|
||||||
anchors.leftMargin: 46
|
anchors.leftMargin: root.headerLeftPadding
|
||||||
anchors.right: parent.right
|
anchors.right: parent.right
|
||||||
StatusTabBar {
|
StatusTabBar {
|
||||||
id: graphsTabBar
|
id: graphsTabBar
|
||||||
|
|
|
@ -10239,7 +10239,7 @@ helpers$1.extend(Chart.prototype, /** @lends Chart */ {
|
||||||
|
|
||||||
// Invoke onHover hook
|
// Invoke onHover hook
|
||||||
// Need to call with native event here to not break backwards compatibility
|
// Need to call with native event here to not break backwards compatibility
|
||||||
helpers$1.callback(options.onHover || options.hover.onHover, [e.native, me.active], me);
|
helpers$1.callback(options.onHover || options.hover.onHover, [e.native, me.active, e], me);
|
||||||
|
|
||||||
if (e.type === 'mouseup' || e.type === 'click') {
|
if (e.type === 'mouseup' || e.type === 'click') {
|
||||||
if (options.onClick) {
|
if (options.onClick) {
|
||||||
|
|
|
@ -248,6 +248,101 @@ QtObject {
|
||||||
return Math.round((d1 - d2) / d.msInADay) // Math.round: not all days are 24 hours long!
|
return Math.round((d1 - d2) / d.msInADay) // Math.round: not all days are 24 hours long!
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the timestamp of the last minute
|
||||||
|
* - `before``: number of minutes before the reference minute
|
||||||
|
* - `time``: timestamp to use as reference
|
||||||
|
* - `rounding``: if true, rounds to the last minute
|
||||||
|
**/
|
||||||
|
function minutes(before = 0, time = Date.now(), rounding = true) {
|
||||||
|
let timestamp = rounding ? Math.floor(time / minutesToMs(5)) * minutesToMs(5)
|
||||||
|
: time
|
||||||
|
return timestamp - minutesToMs(before)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the timestamp of the last hour
|
||||||
|
* - `before``: number of hours before the reference hour
|
||||||
|
* - `time``: timestamp to use as reference
|
||||||
|
* - `rounding``: if true, rounds to the last hour
|
||||||
|
**/
|
||||||
|
function hours(before = 0, time = Date.now(), rounding = true) {
|
||||||
|
let timestamp = rounding ? Math.floor(time / minutesToMs(30)) * minutesToMs(30)
|
||||||
|
: time
|
||||||
|
return timestamp - hoursToMs(before)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the timestamp of the last day
|
||||||
|
* - `before``: number of days before the reference day
|
||||||
|
* - `time``: timestamp to use as reference
|
||||||
|
* - `rounding``: if true, rounds to the last day
|
||||||
|
**/
|
||||||
|
function days(before = 0, time = Date.now(), rounding = true) {
|
||||||
|
let date = new Date(time)
|
||||||
|
if(rounding) {
|
||||||
|
date = new Date(date.getFullYear(), date.getMonth(), date.getDate())
|
||||||
|
}
|
||||||
|
|
||||||
|
date.setDate(date.getDate() - before)
|
||||||
|
return date.getTime()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the timestamp of the last week
|
||||||
|
* - `before``: number of weeks before the reference week
|
||||||
|
* - `time``: timestamp to use as reference
|
||||||
|
* - `rounding``: if true, rounds to the last week
|
||||||
|
**/
|
||||||
|
function months(before = 0, time = Date.now(), rounding = true) {
|
||||||
|
let date = new Date(time)
|
||||||
|
if(rounding) {
|
||||||
|
date = new Date(date.getFullYear(), date.getMonth(), 1)
|
||||||
|
}
|
||||||
|
date.setMonth(date.getMonth() - before)
|
||||||
|
|
||||||
|
return date.getTime()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the timestamp of the last year
|
||||||
|
* - `before``: number of years before the reference year
|
||||||
|
* - `time``: timestamp to use as reference
|
||||||
|
* - `rounding``: if true, rounds to the last year
|
||||||
|
**/
|
||||||
|
function years(before = 0, time = Date.now(), rounding = true) {
|
||||||
|
let date = new Date(time)
|
||||||
|
if(rounding) {
|
||||||
|
date = new Date(date.getFullYear(), 0, 1)
|
||||||
|
}
|
||||||
|
date.setFullYear(date.getFullYear() - before)
|
||||||
|
return date.getTime()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retuns the number of milliseconds in the given amount of minutes
|
||||||
|
* - `count``: number of minutes
|
||||||
|
**/
|
||||||
|
function minutesToMs(count = 1) {
|
||||||
|
return count * 60 * 1000
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retuns the number of milliseconds in the given amount of hours
|
||||||
|
* - `count``: number of hours
|
||||||
|
**/
|
||||||
|
function hoursToMs(count = 1) {
|
||||||
|
return count * minutesToMs(60)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retuns the number of milliseconds in the given amount of days
|
||||||
|
* - `count``: number of days
|
||||||
|
**/
|
||||||
|
function daysToMs(count = 1) {
|
||||||
|
return count * hoursToMs(24)
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Converts the Date to a string containing the date suitable for the specified locale in the specified format.
|
Converts the Date to a string containing the date suitable for the specified locale in the specified format.
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,371 @@
|
||||||
|
import QtQuick 2.15
|
||||||
|
import QtQuick.Controls 2.15
|
||||||
|
import QtQuick.Layouts 1.15
|
||||||
|
import QtQml 2.15
|
||||||
|
|
||||||
|
import StatusQ.Popups 0.1
|
||||||
|
import StatusQ.Components 0.1
|
||||||
|
import StatusQ.Core 0.1
|
||||||
|
import StatusQ.Core.Theme 0.1
|
||||||
|
import StatusQ.Controls 0.1
|
||||||
|
import StatusQ.Components 0.1
|
||||||
|
|
||||||
|
import utils 1.0
|
||||||
|
|
||||||
|
StatusChartPanel {
|
||||||
|
id: root
|
||||||
|
/**
|
||||||
|
* Flat model to use for the chart containing timestamps
|
||||||
|
* type: {Array}
|
||||||
|
*/
|
||||||
|
property var model: []
|
||||||
|
|
||||||
|
QtObject {
|
||||||
|
id: d
|
||||||
|
|
||||||
|
//visual properties
|
||||||
|
readonly property string baseColor1: Theme.palette.baseColor1
|
||||||
|
readonly property string twentyPercentBaseColor1: Theme.palette.alphaColor(baseColor1, 0.2)
|
||||||
|
readonly property string barColor: Theme.palette.primaryColor2
|
||||||
|
readonly property string barBorderColor: Theme.palette.primaryColor1
|
||||||
|
readonly property string messagesLabel: qsTr("Messages")
|
||||||
|
|
||||||
|
property int hoveredBarIndex: 0
|
||||||
|
property int hoveredBarValue: 0
|
||||||
|
readonly property var hoveredModelMetadata: modelMetadata[root.timeRangeTabBarIndex].modelItems[hoveredBarIndex]
|
||||||
|
readonly property var tooltipConfig: modelMetadata[root.timeRangeTabBarIndex].tooltipConfig
|
||||||
|
readonly property var graphTabsModel: [{text: messagesLabel, enabled: true}]
|
||||||
|
readonly property var now: Date.now()
|
||||||
|
|
||||||
|
readonly property var chartData: selectedTabInfo.modelItems.map(x => d.itemsCountInRange(root.model, x.start, x.end))
|
||||||
|
readonly property var labels: selectedTabInfo.modelItems.map(x => x.label)
|
||||||
|
readonly property var selectedTabInfo: modelMetadata[root.timeRangeTabBarIndex]
|
||||||
|
readonly property var modelMetadata: [
|
||||||
|
{
|
||||||
|
text: qsTr("1H"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.minutes(60, now), end: LocaleUtils.minutes(50, now), label: minutesStr(55)},
|
||||||
|
{ start: LocaleUtils.minutes(50, now), end: LocaleUtils.minutes(40, now), label: minutesStr(45)},
|
||||||
|
{ start: LocaleUtils.minutes(40, now), end: LocaleUtils.minutes(30, now), label: minutesStr(35)},
|
||||||
|
{ start: LocaleUtils.minutes(30, now), end: LocaleUtils.minutes(20, now), label: minutesStr(25)},
|
||||||
|
{ start: LocaleUtils.minutes(20, now), end: LocaleUtils.minutes(10, now), label: minutesStr(15)},
|
||||||
|
{ start: LocaleUtils.minutes(10, now), end: LocaleUtils.minutes(0, now, false), label: minutesStr(5)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Time period"),
|
||||||
|
timeRangeFormatter: d.hoursRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("1D"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.hours(24, now), end: LocaleUtils.hours(20, now), label: hourStr(22)},
|
||||||
|
{ start: LocaleUtils.hours(20, now), end: LocaleUtils.hours(16, now), label: hourStr(18)},
|
||||||
|
{ start: LocaleUtils.hours(16, now), end: LocaleUtils.hours(12, now), label: hourStr(14)},
|
||||||
|
{ start: LocaleUtils.hours(12, now), end: LocaleUtils.hours(8, now), label: hourStr(10)},
|
||||||
|
{ start: LocaleUtils.hours(8, now), end: LocaleUtils.hours(4, now), label: hourStr(6)},
|
||||||
|
{ start: LocaleUtils.hours(4, now), end: LocaleUtils.hours(0, now, false), label: hourStr(2)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Time period"),
|
||||||
|
timeRangeFormatter: d.hoursRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("7D"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.days(6, now), end: LocaleUtils.days(5, now), label: dayStr(6)},
|
||||||
|
{ start: LocaleUtils.days(5, now), end: LocaleUtils.days(4, now), label: dayStr(5)},
|
||||||
|
{ start: LocaleUtils.days(4, now), end: LocaleUtils.days(3, now), label: dayStr(4)},
|
||||||
|
{ start: LocaleUtils.days(3, now), end: LocaleUtils.days(2, now), label: dayStr(3)},
|
||||||
|
{ start: LocaleUtils.days(2, now), end: LocaleUtils.days(1, now), label: dayStr(2)},
|
||||||
|
{ start: LocaleUtils.days(1, now), end: LocaleUtils.days(0, now), label: dayStr(1)},
|
||||||
|
{ start: LocaleUtils.days(0, now), end: LocaleUtils.days(0, now, false), label: dayStr(0)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Date"),
|
||||||
|
timeRangeFormatter: d.daysRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("1M"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.days(30, now), end: LocaleUtils.days(25, now), label: dayStr(30)},
|
||||||
|
{ start: LocaleUtils.days(25, now), end: LocaleUtils.days(20, now), label: dayStr(25)},
|
||||||
|
{ start: LocaleUtils.days(20, now), end: LocaleUtils.days(15, now), label: dayStr(20)},
|
||||||
|
{ start: LocaleUtils.days(15, now), end: LocaleUtils.days(10, now), label: dayStr(15)},
|
||||||
|
{ start: LocaleUtils.days(10, now), end: LocaleUtils.days(5, now), label: dayStr(10)},
|
||||||
|
{ start: LocaleUtils.days(5, now), end: LocaleUtils.days(0, now, false), label: dayStr(5)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Time period"),
|
||||||
|
timeRangeFormatter: d.daysRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("6M"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.months(5, now), end: LocaleUtils.months(4, now), label: monthStr(5)},
|
||||||
|
{ start: LocaleUtils.months(4, now), end: LocaleUtils.months(3, now), label: monthStr(4)},
|
||||||
|
{ start: LocaleUtils.months(3, now), end: LocaleUtils.months(2, now), label: monthStr(3)},
|
||||||
|
{ start: LocaleUtils.months(2, now), end: LocaleUtils.months(1, now), label: monthStr(2)},
|
||||||
|
{ start: LocaleUtils.months(1, now), end: LocaleUtils.months(0, now), label: monthStr(1)},
|
||||||
|
{ start: LocaleUtils.months(0, now), end: LocaleUtils.months(0, now, false), label: monthStr(0)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Month"),
|
||||||
|
timeRangeFormatter: d.monthsRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("1Y"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.months(12, now), end: LocaleUtils.months(10, now), label: monthStr(11)},
|
||||||
|
{ start: LocaleUtils.months(10, now), end: LocaleUtils.months(8, now), label: monthStr(9)},
|
||||||
|
{ start: LocaleUtils.months(8, now), end: LocaleUtils.months(6, now), label: monthStr(7)},
|
||||||
|
{ start: LocaleUtils.months(6, now), end: LocaleUtils.months(4, now), label: monthStr(5)},
|
||||||
|
{ start: LocaleUtils.months(4, now), end: LocaleUtils.months(2, now), label: monthStr(3)},
|
||||||
|
{ start: LocaleUtils.months(2, now), end: LocaleUtils.months(0, now, false), label: monthStr(1)}
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Time period"),
|
||||||
|
timeRangeFormatter: d.monthsRangeStr
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
text: qsTr("ALL"),
|
||||||
|
modelItems: [
|
||||||
|
{ start: LocaleUtils.years(7, now), end: LocaleUtils.years(6, now), label: yearsStr(7) },
|
||||||
|
{ start: LocaleUtils.years(6, now), end: LocaleUtils.years(5, now), label: yearsStr(6) },
|
||||||
|
{ start: LocaleUtils.years(5, now), end: LocaleUtils.years(4, now), label: yearsStr(5) },
|
||||||
|
{ start: LocaleUtils.years(4, now), end: LocaleUtils.years(3, now), label: yearsStr(4) },
|
||||||
|
{ start: LocaleUtils.years(3, now), end: LocaleUtils.years(2, now), label: yearsStr(3) },
|
||||||
|
{ start: LocaleUtils.years(2, now), end: LocaleUtils.years(1, now), label: yearsStr(2) },
|
||||||
|
{ start: LocaleUtils.years(1, now), end: LocaleUtils.years(0, now), label: yearsStr(1) },
|
||||||
|
{ start: LocaleUtils.years(0, now), end: LocaleUtils.years(0, now, false), label: yearsStr(0) }
|
||||||
|
],
|
||||||
|
tooltipConfig: {
|
||||||
|
timeRangeString: qsTr("Year"),
|
||||||
|
timeRangeFormatter: d.yearsRangeStr
|
||||||
|
},
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
function itemsCountInRange(array, start, end) {
|
||||||
|
return array ? array.filter(x => x <= end && x > start).length : 0
|
||||||
|
}
|
||||||
|
|
||||||
|
function minutesStr(before = 0, timeReference = now, roundCurrentTime = true) {
|
||||||
|
return LocaleUtils.formatTime(LocaleUtils.minutes(before, timeReference, roundCurrentTime), Locale.ShortFormat)
|
||||||
|
}
|
||||||
|
|
||||||
|
function hourStr(before = 0, timeReference = now, roundCurrentTime = true) {
|
||||||
|
return LocaleUtils.formatTime(LocaleUtils.hours(before, timeReference, roundCurrentTime), Locale.ShortFormat)
|
||||||
|
}
|
||||||
|
|
||||||
|
function dayStr(before = 0, timeReference = now, roundCurrentTime = true) {
|
||||||
|
return LocaleUtils.getDayMonth(LocaleUtils.days(before, timeReference, roundCurrentTime), Locale.ShortFormat)
|
||||||
|
}
|
||||||
|
|
||||||
|
function monthStr(before = 0, timeReference = now, roundCurrentTime = true, shortFormat = true) {
|
||||||
|
const format = shortFormat ? "MMM" : "MMMM"
|
||||||
|
const timeStamp = LocaleUtils.months(before, timeReference, roundCurrentTime)
|
||||||
|
return LocaleUtils.formatDate(timeStamp, format)
|
||||||
|
}
|
||||||
|
|
||||||
|
function yearsStr(before = 0, timeReference = now, roundCurrentTime = true) {
|
||||||
|
return LocaleUtils.formatDate(LocaleUtils.years(before, timeReference, roundCurrentTime), "yyyy");
|
||||||
|
}
|
||||||
|
|
||||||
|
function hoursRangeStr(start, end) {
|
||||||
|
return "%1 - %2".arg(hourStr(0, start, false)).arg(hourStr(0, end, false))
|
||||||
|
}
|
||||||
|
|
||||||
|
function daysRangeStr(start, end) {
|
||||||
|
return (end - start > LocaleUtils.daysToMs(1)) ?
|
||||||
|
"%1 - %2".arg(dayStr(0, start, false)).arg(dayStr(0, end, false)) :
|
||||||
|
dayStr(0, start, false)
|
||||||
|
}
|
||||||
|
|
||||||
|
function monthsRangeStr(start, end) {
|
||||||
|
//End date excluded
|
||||||
|
//Adjust by one ms to exclude the end date
|
||||||
|
//To avoid considering the end date as a new month
|
||||||
|
end = end - 1
|
||||||
|
const startDate = monthStr(0, start, false)
|
||||||
|
const endDate = monthStr(0, end, false)
|
||||||
|
return (startDate !== endDate) ?
|
||||||
|
"%1 - %2".arg(startDate).arg(endDate) :
|
||||||
|
monthStr(0, start, false, false)
|
||||||
|
}
|
||||||
|
|
||||||
|
function yearsRangeStr(start, end) {
|
||||||
|
//End date excluded
|
||||||
|
//Adjust by one ms to exclude the end date
|
||||||
|
//To avoid considering the end date as a new year
|
||||||
|
end = end - 1
|
||||||
|
const startYear = yearsStr(0, start, false)
|
||||||
|
const endYear = yearsStr(0, end, false)
|
||||||
|
return (startYear !== endYear) ?
|
||||||
|
"%1 - %2".arg(startYear).arg(endYear) :
|
||||||
|
startYear
|
||||||
|
}
|
||||||
|
|
||||||
|
function getAdjustedTooltipPosition(event) {
|
||||||
|
// By defaullt the popup is displayed on the right of the cursor
|
||||||
|
// If there is not enough space on the right, display it on the left
|
||||||
|
const relativeMousePoint = event.target.mapToItem(toolTip.parent, event.x, event.y) // relative to tooltip parent
|
||||||
|
const leftPositon = (toolTip.parent.width - (toolTip.width + toolTip.rightPadding + relativeMousePoint.x + 15)) < 0
|
||||||
|
return leftPositon ? Qt.point(relativeMousePoint.x - toolTip.width - 15, relativeMousePoint.y - 5)
|
||||||
|
: Qt.point(relativeMousePoint.x + 15, relativeMousePoint.y - 5)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
headerLeftPadding: 0
|
||||||
|
headerBottomPadding: Style.current.bigPadding
|
||||||
|
graphsModel: d.graphTabsModel
|
||||||
|
timeRangeModel: d.modelMetadata
|
||||||
|
onHeaderTabClicked: {
|
||||||
|
root.chart.animateToNewData();
|
||||||
|
}
|
||||||
|
|
||||||
|
/////////////////////////////
|
||||||
|
// Chartjs configuration //
|
||||||
|
/////////////////////////////
|
||||||
|
chart.chartType: 'bar'
|
||||||
|
chart.chartData: {
|
||||||
|
return {
|
||||||
|
labels: d.labels,
|
||||||
|
datasets: [{
|
||||||
|
xAxisId: 'x-axis-1',
|
||||||
|
yAxisId: 'y-axis-1',
|
||||||
|
backgroundColor: d.barColor,
|
||||||
|
pointRadius: 0,
|
||||||
|
hoverBackgroundColor: d.barColor,
|
||||||
|
hoverBorderColor: d.barBorderColor,
|
||||||
|
hoverBorderWidth: 2,
|
||||||
|
data: d.chartData
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
chart.chartOptions: {
|
||||||
|
return {
|
||||||
|
maintainAspectRatio: false,
|
||||||
|
responsive: true,
|
||||||
|
legend: {
|
||||||
|
display: false
|
||||||
|
},
|
||||||
|
// Popup follows the cursor
|
||||||
|
onHover: function(arg1, hoveredItems, event) {
|
||||||
|
if(!event || hoveredItems.length == 0) {
|
||||||
|
toolTip.close()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
d.hoveredBarIndex = hoveredItems[0]._index
|
||||||
|
d.hoveredBarValue = hoveredItems[0]._chart.config.data.datasets[0].data[hoveredItems[0]._index]
|
||||||
|
const position = d.getAdjustedTooltipPosition(event)
|
||||||
|
toolTip.popup(position.x, position.y)
|
||||||
|
},
|
||||||
|
tooltips: {
|
||||||
|
enabled: false,
|
||||||
|
},
|
||||||
|
scales: {
|
||||||
|
xAxes: [{
|
||||||
|
id: 'x-axis-1',
|
||||||
|
position: 'bottom',
|
||||||
|
stacked: false,
|
||||||
|
gridLines: {
|
||||||
|
drawOnChartArea: false,
|
||||||
|
drawBorder: false,
|
||||||
|
drawTicks: false,
|
||||||
|
},
|
||||||
|
ticks: {
|
||||||
|
fontSize: Style.current.asideTextFontSize,
|
||||||
|
fontColor: d.baseColor1,
|
||||||
|
padding: Style.current.padding,
|
||||||
|
}
|
||||||
|
}],
|
||||||
|
yAxes: [{
|
||||||
|
position: 'left',
|
||||||
|
id: 'y-axis-1',
|
||||||
|
stacked: false,
|
||||||
|
gridLines: {
|
||||||
|
borderDash: [5, 3],
|
||||||
|
lineWidth: 1,
|
||||||
|
drawBorder: false,
|
||||||
|
drawTicks: false,
|
||||||
|
color: d.twentyPercentBaseColor1,
|
||||||
|
},
|
||||||
|
beforeDataLimits: (axis) => {
|
||||||
|
axis.paddingTop = 25;
|
||||||
|
axis.paddingBottom = 0;
|
||||||
|
},
|
||||||
|
ticks: {
|
||||||
|
fontSize: 10,
|
||||||
|
fontColor: d.baseColor1,
|
||||||
|
padding: Style.current.halfPadding,
|
||||||
|
maxTicksLimit: Style.current.asideTextFontSize,
|
||||||
|
beginAtZero: true,
|
||||||
|
stepSize: 1,
|
||||||
|
callback: function(value, index, values) {
|
||||||
|
return LocaleUtils.numberToLocaleString(value)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
StatusMenu {
|
||||||
|
id: toolTip
|
||||||
|
width: 243 //By design
|
||||||
|
topPadding: Style.current.padding
|
||||||
|
bottomPadding: topPadding
|
||||||
|
leftPadding: topPadding
|
||||||
|
rightPadding: topPadding
|
||||||
|
parent: Overlay.overlay
|
||||||
|
|
||||||
|
ColumnLayout {
|
||||||
|
spacing: Style.current.padding
|
||||||
|
RowLayout {
|
||||||
|
Layout.fillWidth: true
|
||||||
|
StatusBaseText {
|
||||||
|
elide: Qt.ElideRight
|
||||||
|
font.pixelSize: Style.current.primaryTextFontSize
|
||||||
|
color: Theme.palette.baseColor1
|
||||||
|
text: d.tooltipConfig.timeRangeString
|
||||||
|
}
|
||||||
|
Item {
|
||||||
|
Layout.fillWidth: true
|
||||||
|
}
|
||||||
|
StatusBaseText {
|
||||||
|
Layout.alignment: Qt.AlignRight
|
||||||
|
elide: Qt.ElideRight
|
||||||
|
font.pixelSize: Style.current.primaryTextFontSize
|
||||||
|
color: Theme.palette.directColor1
|
||||||
|
text: d.hoveredModelMetadata ? d.tooltipConfig.timeRangeFormatter(d.hoveredModelMetadata.start, d.hoveredModelMetadata.end)
|
||||||
|
: ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
RowLayout {
|
||||||
|
Layout.fillWidth: true
|
||||||
|
StatusBaseText {
|
||||||
|
elide: Qt.ElideRight
|
||||||
|
font.pixelSize: Style.current.primaryTextFontSize
|
||||||
|
color: Theme.palette.baseColor1
|
||||||
|
text: qsTr("No. of Messages")
|
||||||
|
}
|
||||||
|
Item { Layout.fillWidth: true }
|
||||||
|
StatusBaseText {
|
||||||
|
Layout.alignment: Qt.AlignRight
|
||||||
|
elide: Qt.ElideRight
|
||||||
|
font.pixelSize: Style.current.primaryTextFontSize
|
||||||
|
color: Theme.palette.directColor1
|
||||||
|
text: LocaleUtils.numberToLocaleString(d.hoveredBarValue)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -55,7 +55,7 @@ StackLayout {
|
||||||
SettingsPage {
|
SettingsPage {
|
||||||
|
|
||||||
rightPadding: 64
|
rightPadding: 64
|
||||||
bottomPadding: 64
|
bottomPadding: 50
|
||||||
topPadding: 0
|
topPadding: 0
|
||||||
header: null
|
header: null
|
||||||
contentItem: ColumnLayout {
|
contentItem: ColumnLayout {
|
||||||
|
@ -109,38 +109,28 @@ StackLayout {
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
|
|
||||||
implicitHeight: 1
|
implicitHeight: 1
|
||||||
visible: root.editable
|
|
||||||
color: Theme.palette.statusMenu.separatorColor
|
color: Theme.palette.statusMenu.separatorColor
|
||||||
}
|
}
|
||||||
|
|
||||||
RowLayout {
|
OverviewSettingsChart {
|
||||||
|
Layout.topMargin: 16
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
|
|
||||||
visible: root.owned
|
|
||||||
|
|
||||||
StatusIcon {
|
|
||||||
icon: "info"
|
|
||||||
color: Theme.palette.directColor1
|
|
||||||
}
|
|
||||||
|
|
||||||
StatusBaseText {
|
|
||||||
Layout.fillWidth: true
|
|
||||||
text: qsTr("This node is the Community Owner Node. For your Community to function correctly try to keep this computer with Status running and online as much as possible.")
|
|
||||||
font.pixelSize: 15
|
|
||||||
color: Theme.palette.directColor1
|
|
||||||
wrapMode: Text.WordWrap
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Item {
|
|
||||||
Layout.fillHeight: true
|
Layout.fillHeight: true
|
||||||
|
Layout.bottomMargin: 16
|
||||||
|
}
|
||||||
|
Rectangle {
|
||||||
|
Layout.fillWidth: true
|
||||||
|
|
||||||
|
implicitHeight: 1
|
||||||
|
color: Theme.palette.statusMenu.separatorColor
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
footer: OverviewSettingsFooter {
|
footer: OverviewSettingsFooter {
|
||||||
rightPadding: 64
|
rightPadding: 64
|
||||||
leftPadding: 64
|
leftPadding: 64
|
||||||
bottomPadding: 50
|
bottomPadding: 64
|
||||||
|
topPadding: 0
|
||||||
loginType: root.loginType
|
loginType: root.loginType
|
||||||
communityName: root.name
|
communityName: root.name
|
||||||
//TODO connect to backend
|
//TODO connect to backend
|
||||||
|
|
|
@ -31,3 +31,4 @@ TokenHoldersProxyModel 1.0 TokenHoldersProxyModel.qml
|
||||||
WarningPanel 1.0 WarningPanel.qml
|
WarningPanel 1.0 WarningPanel.qml
|
||||||
WelcomeBannerPanel 1.0 WelcomeBannerPanel.qml
|
WelcomeBannerPanel 1.0 WelcomeBannerPanel.qml
|
||||||
EditSettingsPanel 1.0 EditSettingsPanel.qml
|
EditSettingsPanel 1.0 EditSettingsPanel.qml
|
||||||
|
OverviewSettingsChart 1.0 OverviewSettingsChart.qml
|
Loading…
Reference in New Issue