Warning, /libraries/kirigami-addons/src/dateandtime/TimePicker.qml is written in an unsupported language. File is not indexed.
0001 // SPDX-FileCopyrightText: 2021 Han Young <hanyoung@protonmail.com>
0002 // SPDX-FileCopyrightText: 2022 Carl Schwan <carl@carlschwan.eu>
0003 // SPDX-License-Identifier: LGPL-2.1-or-later
0004
0005 import QtQuick 2.15
0006 import QtQuick.Controls 2.15
0007 import org.kde.kirigami 2.20 as Kirigami
0008 import QtQuick.Layouts 1.15
0009 import org.kde.kirigamiaddons.dateandtime 1.0
0010
0011 /**
0012 * A large time picker
0013 * Represented as a clock provides a very visual way for a user
0014 * to set and visulise a time being chosen
0015 */
0016 RowLayout {
0017 id: root
0018
0019 /**
0020 * This property holds the current hours selected. This is a number between 0 and 23.
0021 */
0022 property int hours
0023
0024 /**
0025 * This property holds the current minutes selected. This is a number between 0 and 59.
0026 */
0027 property int minutes
0028
0029 property bool _pm: false
0030
0031 property bool _init: false
0032
0033 readonly property bool _isAmPm: Qt.locale().timeFormat().includes("AP")
0034
0035 implicitHeight: Kirigami.Units.gridUnit * 5
0036 implicitWidth: Kirigami.Units.gridUnit * 10
0037
0038 Component.onCompleted: {
0039 hoursTumbler.currentIndex = (_isAmPm && hours > 12 ? hours - 12 : hours);
0040 minutesTumbler.currentIndex = minutes;
0041 if (_isAmPm) {
0042 amPmTumbler.currentIndex = hours > 12 ? 1 : 0;
0043 }
0044
0045 // Avoid initialisation bug where thumbler are by default initialised
0046 // to currentIndex 0
0047 _init = true;
0048 }
0049
0050 function formatText(count, modelData) {
0051 var data = count === 12 && modelData === 0 ? 12 : modelData;
0052 return data.toString().length < 2 ? "0" + data : data;
0053 }
0054
0055 FontMetrics {
0056 id: fontMetrics
0057 }
0058
0059 Component {
0060 id: delegateComponent
0061 Label {
0062 id: delegate
0063
0064 text: formatText(Tumbler.tumbler.count, modelData)
0065 opacity: 1.0 - Math.abs(Tumbler.displacement) / (Tumbler.tumbler.visibleItemCount / 2)
0066 horizontalAlignment: Text.AlignHCenter
0067 verticalAlignment: Text.AlignVCenter
0068 font.pixelSize: fontMetrics.font.pixelSize * 1.25
0069 Accessible.ignored: true
0070
0071 Rectangle {
0072 anchors.fill: parent
0073 color: 'transparent'
0074 radius: Kirigami.Units.mediumSpacing
0075 border {
0076 width: delegate === Tumbler.tumbler.currentItem ? 1 : 0
0077 color: Kirigami.Theme.highlightColor
0078 }
0079 }
0080 }
0081 }
0082
0083 Item {
0084 Layout.fillWidth: true
0085 }
0086
0087 Tumbler {
0088 id: hoursTumbler
0089 Layout.preferredHeight: Kirigami.Units.gridUnit * 10
0090 model: _isAmPm ? 12 : 24
0091 delegate: delegateComponent
0092 visibleItemCount: 5
0093 onCurrentIndexChanged: if (_init) {
0094 hours = currentIndex + (_isAmPm && _pm ? 12 : 0)
0095 }
0096 Accessible.name: if (!_isAmPm) {
0097 i18ndc("kirigami-addons6", "time in hour in 24h format", "%1 hours", root.hours)
0098 } else if (_isAmPm && _pm) {
0099 i18ndc("kirigami-addons6", "time in hour (PM)", "%1 PM", currentIndex + 12)
0100 } else {
0101 i18ndc("kirigami-addons6", "time in hour (AM)", "%1 AM", currentIndex)
0102 }
0103 Accessible.role: Accessible.Dial
0104 Accessible.onDecreaseAction: hoursTumbler.currentIndex = (hoursTumbler.currentIndex + hoursTumbler.model - 1) % hoursTumbler.model
0105 Accessible.onIncreaseAction: hoursTumbler.currentIndex = (hoursTumbler.currentIndex + 1) % hoursTumbler.model
0106 focus: true
0107 }
0108
0109 Label {
0110 Layout.alignment: Qt.AlignCenter
0111 text: i18ndc("kirigami-addons6", "Time separator", ":")
0112 font.pointSize: Kirigami.Theme.defaultFont.pointSize * 1.3
0113 Accessible.ignored: true
0114 }
0115
0116 Tumbler {
0117 id: minutesTumbler
0118 Layout.preferredHeight: Kirigami.Units.gridUnit * 10
0119 model: 60
0120 delegate: delegateComponent
0121 visibleItemCount: 5
0122 onCurrentIndexChanged: if (_init) {
0123 minutes = currentIndex;
0124 }
0125
0126 Accessible.name: i18ndc("kirigami-addons6", "number of minutes", "%1 minutes", root.minutes)
0127 Accessible.role: Accessible.Dial
0128 Accessible.onDecreaseAction: minutesTumbler.currentIndex = (minutesTumbler.currentIndex + 59) % 60
0129 Accessible.onIncreaseAction: minutesTumbler.currentIndex = (minutesTumbler.currentIndex + 1) % 60
0130 }
0131
0132 Tumbler {
0133 id: amPmTumbler
0134 visible: _isAmPm
0135 Layout.preferredHeight: Kirigami.Units.gridUnit * 10
0136 model: [Qt.locale().amText, Qt.locale().pmText]
0137 Accessible.name: currentItem.text
0138 Accessible.role: Accessible.CheckBox
0139 Accessible.ignored: !_isAmPm
0140 Accessible.onPressAction: amPmTumbler.currentIndex = (amPmTumbler.currentIndex + 1) % 2
0141 Accessible.onToggleAction: amPmTumbler.currentIndex = (amPmTumbler.currentIndex + 1) % 2
0142 delegate: delegateComponent
0143 visibleItemCount: 5
0144 onCurrentIndexChanged: if (_isAmPm && _init) {
0145 _pm = currentIndex;
0146 hours = (hours + 12) % 24;
0147 }
0148 }
0149
0150 Item {
0151 Layout.fillWidth: true
0152 }
0153 }