on ffe76cc help sign in
unity8/qml/Components/PinLockscreen.qml
229 lines 7.5 kB history raw
1/*
2 * Copyright (C) 2013 Canonical, Ltd.
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 3.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
17import QtQuick 2.0
18import Ubuntu.Components 0.1
19import Ubuntu.Components.ListItems 0.1
20import "../Components"
22Column {
23 id: root
24 anchors.top: parent.top
25 anchors.topMargin: units.gu(4)
26 anchors.horizontalCenter: parent.horizontalCenter
27 spacing: units.gu(2)
29 property string infoText
30 property string retryText
31 property string errorText
32 property int padWidth: units.gu(34)
33 property int padHeight: units.gu(28)
34 property int minPinLength: -1
35 property int maxPinLength: -1
36 property bool showCancelButton: true
38 readonly property string passphrase: pinentryField.text
40 signal entered(string passphrase)
41 signal cancel()
43 property bool entryEnabled: true
45 function clear(showAnimation) {
46 pinentryField.text = "";
47 if (showAnimation) {
48 pinentryField.incorrectOverride = true;
49 wrongPasswordAnimation.start();
50 }
51 }
53 Column {
54 id: shakeContainer
55 anchors.horizontalCenter: parent.horizontalCenter
56 width: parent.width
57 spacing: units.gu(1)
59 Label {
60 id: infoField
61 objectName: "infoTextLabel"
62 fontSize: "large"
63 color: "#f3f3e7"
64 anchors.horizontalCenter: parent.horizontalCenter
65 text: root.infoText
66 }
68 Item {
69 id: pinContainer
70 anchors { left: parent.left; right: parent.right; margins: units.gu(2) }
71 height: units.gu(4)
73 Row {
74 id: pinentryField
75 objectName: "pinentryField"
76 anchors.horizontalCenter: parent.horizontalCenter
77 anchors.verticalCenter: parent.verticalCenter
78 spacing: Math.max(0, Math.min(units.gu(3), (parent.width / root.maxPinLength) - units.gu(3)))
80 property string text
81 property bool incorrectOverride: false
83 Repeater {
84 model: pinentryField.text.length
85 delegate: Rectangle {
86 color: "#f3f3e7"
87 width: Math.min(units.gu(2), (pinContainer.width - pinContainer.height*2 ) / (root.maxPinLength >= 0 ? root.maxPinLength : 16))
88 height: width
89 radius: width / 2
90 }
91 }
93 function appendNumber(number) {
94 if (incorrectOverride) {
95 incorrectOverride = false;
96 }
98 pinentryField.text = pinentryField.text + number
100 if (root.minPinLength > 0 && root.maxPinLength > 0
101 && root.minPinLength == root.maxPinLength && pinentryField.text.length == root.minPinLength) {
102 root.entered(pinentryField.text)
103 }
104 }
106 function backspace() {
107 pinentryField.text = pinentryField.text.substring(0, pinentryField.text.length-1)
108 }
109 }
110 Label {
111 id: wrongNoticeLabel
112 objectName: "wrongNoticeLabel"
113 fontSize: "x-large"
114 color: "#f3f3e7"
115 anchors.horizontalCenter: parent.horizontalCenter
116 horizontalAlignment: Text.AlignHCenter
117 text: root.errorText
118 visible: pinentryField.incorrectOverride
119 scale: Math.min(1, parent.width / width)
120 }
122 AbstractButton {
123 objectName: "backspaceIcon"
124 anchors { right: parent.right; top: parent.top; bottom: parent.bottom }
125 width: height
127 Icon {
128 anchors.fill: parent
129 name: "erase"
130 color: "#f3f3e7"
131 }
133 opacity: (pinentryField.text.length && !pinentryField.incorrectOverride) > 0 ? 1 : 0
135 Behavior on opacity {
136 UbuntuNumberAnimation {}
137 }
139 onClicked: pinentryField.backspace()
140 }
141 }
143 Label {
144 objectName: "retryLabel"
145 fontSize: "x-small"
146 color: "#f3f3e7"
147 anchors.horizontalCenter: parent.horizontalCenter
148 text: root.retryText || " "
149 }
150 }
152 ThinDivider {
153 anchors { left: parent.left; right: parent.right; margins: units.gu(2) }
154 }
156 Grid {
157 id: numbersGrid
158 anchors { horizontalCenter: parent.horizontalCenter }
159 columns: 3
161 property int buttonHeight: units.gu(8)
162 property int buttonWidth: units.gu(12)
164 Repeater {
165 model: 9
167 PinPadButton {
168 objectName: "pinPadButton" + text
169 text: index + 1
170 height: numbersGrid.buttonHeight
171 width: numbersGrid.buttonWidth
172 enabled: root.entryEnabled && (root.maxPinLength == -1 ||
173 pinentryField.text.length < root.maxPinLength ||
174 pinentryField.incorrectOverride)
176 onClicked: {
177 pinentryField.appendNumber(index + 1)
178 }
179 }
180 }
181 Item {
182 height: numbersGrid.buttonHeight
183 width: numbersGrid.buttonWidth
184 }
185 PinPadButton {
186 text: "0"
187 height: numbersGrid.buttonHeight
188 width: numbersGrid.buttonWidth
189 enabled: root.entryEnabled && (root.maxPinLength == -1 ||
190 pinentryField.text.length < root.maxPinLength ||
191 pinentryField.incorrectOverride)
193 onClicked: {
194 pinentryField.appendNumber(0)
195 }
196 }
197 Item {
198 height: numbersGrid.buttonHeight
199 width: numbersGrid.buttonWidth
200 }
201 PinPadButton {
202 iconName: "close"
203 height: units.gu(5) // visual spec has this row a little closer in
204 width: numbersGrid.buttonWidth
206 onClicked: root.cancel()
207 visible: root.showCancelButton
208 }
209 Item {
210 height: units.gu(5)
211 width: numbersGrid.buttonWidth
212 }
213 PinPadButton {
214 iconName: "tick"
215 objectName: "confirmButton"
216 height: units.gu(5)
217 width: numbersGrid.buttonWidth
218 enabled: root.enabled && pinentryField.text.length >= root.minPinLength
219 visible: root.minPinLength == -1 || root.minPinLength !== root.maxPinLength
221 onClicked: root.entered(pinentryField.text)
222 }
223 }
224 WrongPasswordAnimation {
225 id: wrongPasswordAnimation
226 objectName: "wrongPasswordAnimation"
227 target: shakeContainer
228 }