2 * Copyright (C) 2021 Capsia
3 * Copyright (C) 2016 Canonical, Ltd.
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; version 3.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
19import Lomiri.Components 1.3
24 objectName: "promptPassword"
27 property bool isSecret
28 property bool interactive: true
29 property bool loginError: false
30 property bool hasKeyboard: false
31 property alias enteredText: passwordInput.text
35 signal accepted(string response)
40 readonly property color textColor: passwordInput.enabled ? theme.palette.normal.raisedText
41 : theme.palette.disabled.raisedText
42 readonly property color selectedColor: passwordInput.enabled ? theme.palette.normal.raised
43 : theme.palette.disabled.raised
44 readonly property color drawColor: passwordInput.enabled ? theme.palette.normal.raisedSecondaryText
45 : theme.palette.disabled.raisedSecondaryText
46 readonly property color errorColor: passwordInput.enabled ? theme.palette.normal.negative
47 : theme.palette.disabled.negative
54 Behavior on border.color {
58 color: root.loginError ? d.errorColor : d.drawColor
59 width: root.loginError ? units.dp(2): units.dp(1)
65 objectName: "promptField"
69 opacity: fakeLabel.visible ? 0 : 1
70 activeFocusOnTab: true
71 onActiveFocusChanged: if (activeFocus) Qt.inputMethod.show()
73 onSelectedTextChanged: passwordInput.deselect()
75 validator: RegExpValidator {
79 inputMethodHints: Qt.ImhSensitiveData | Qt.ImhNoPredictiveText |
80 Qt.ImhMultiLine // so OSK doesn't close on Enter
81 echoMode: root.isSecret ? TextInput.Password : TextInput.Normal
84 passwordCharacter: "●"
87 readonly property real frameSpacing: units.gu(1)
91 styleName: "FocusShape"
93 // Properties needed by TextField
94 readonly property color color: d.textColor
95 readonly property color selectedTextColor: d.selectedColor
96 readonly property color selectionColor: d.textColor
97 readonly property color borderColor: "transparent"
98 readonly property color backgroundColor: "transparent"
99 readonly property color errorColor: d.errorColor
100 readonly property real frameSpacing: styledItem.frameSpacing
102 // Properties needed by FocusShape
103 readonly property bool enabled: styledItem.enabled
104 readonly property bool keyNavigationFocus: styledItem.keyNavigationFocus
105 property bool activeFocusOnTab
111 spacing: passwordInput.frameSpacing
112 anchors.verticalCenter: parent.verticalCenter
114 name: "keyboard-caps-enabled"
118 visible: root.isSecret && false // TODO: detect when caps lock is on
119 anchors.verticalCenter: parent.verticalCenter
122 objectName: "greeterPromptKeyboardButton"
123 name: "input-keyboard-symbolic"
127 visible: !lomiriSettings.alwaysShowOsk && root.hasKeyboard
128 anchors.verticalCenter: parent.verticalCenter
131 onClicked: lomiriSettings.alwaysShowOsk = true
135 name: "dialog-warning-symbolic"
139 visible: root.loginError
140 anchors.verticalCenter: parent.verticalCenter
143 name: "toolkit_chevron-ltr_2gu"
144 height: units.gu(2.5)
147 visible: !root.loginError
148 anchors.verticalCenter: parent.verticalCenter
151 onClicked: root.accepted(passwordInput.text)
157 onDisplayTextChanged: {
158 // We use onDisplayTextChanged instead of onTextChanged because
159 // displayText changes after text and if we did this before it
160 // updated, we would use the wrong displayText for fakeLabel.
161 root.loginError = false;
164 onAccepted: respond()
167 if (root.interactive) {
168 root.accepted(passwordInput.text);
172 Keys.onEscapePressed: {
173 lomiriSettings.alwaysShowOsk = false
175 event.accepted = true;
179 // We use our own custom placeholder label instead of the standard
180 // TextField one because the standard one hardcodes baseText as the
181 // palette color, whereas we want raisedSecondaryText.
184 objectName: "promptHint"
186 left: passwordInput ? passwordInput.left : undefined
187 right: passwordInput ? passwordInput.right : undefined
188 verticalCenter: passwordInput ? passwordInput.verticalCenter : undefined
189 leftMargin: units.gu(2)
190 rightMargin: anchors.leftMargin + extraIcons.width
193 visible: passwordInput.text == "" && !passwordInput.inputMethodComposing
196 elide: Text.ElideRight
199 // Have a fake label that covers the text field after the user presses
200 // enter. What we *really* want is a disabled mode that doesn't lose OSK
201 // focus. Because our goal here is simply to keep the OSK up while
202 // we wait for PAM to get back to us, and while waiting, we don't want
203 // the user to be able to edit the field (simply because it would look
204 // weird if we allowed that). But until we have such a disabled mode,
205 // we'll fake it by covering the real text field with a label.
208 anchors.verticalCenter: parent ? parent.verticalCenter : undefined
209 anchors.left: parent ? parent.left : undefined
210 anchors.right: parent ? parent.right : undefined
211 anchors.leftMargin: passwordInput.frameSpacing * 2
212 anchors.rightMargin: passwordInput.frameSpacing * 2 + extraIcons.width
214 text: passwordInput.displayText
215 visible: !root.interactive