1/*
2 * \copyright Copyright (c) 2015-2021 Governikus GmbH & Co. KG, Germany
3 */
4
5import QtQuick 2.12
6import QtQuick.Controls 2.12
7
8import Governikus.EnterPasswordView 1.0
9import Governikus.Global 1.0
10import Governikus.TitleBar 1.0
11import Governikus.ProgressView 1.0
12import Governikus.ResultView 1.0
13import Governikus.SettingsView 1.0
14import Governikus.View 1.0
15import Governikus.Workflow 1.0
16import Governikus.Type.ChangePinModel 1.0
17import Governikus.Type.NumberModel 1.0
18import Governikus.Type.UiModule 1.0
19
20
21SectionPage {
22	id: baseItem
23
24	enum SubViews {
25		Start,
26		Workflow,
27		Password,
28		NoPassword,
29		PasswordInfo,
30		Progress,
31		ProgressNewPin,
32		CardPosition,
33		InputError,
34		Data,
35		PinUnlocked,
36		Result,
37		ReturnToMain,
38		ReaderSettings
39	}
40
41	// Expose private properties, needed for unit tests
42	property alias _d : d
43
44	function showWithPrecedingView(pNextView) {
45		readerView.precedingView = d.activeView
46		d.view = pNextView
47		ApplicationWindow.menuBar.updateActions()
48	}
49
50	function showPasswordInfo() {
51		showWithPrecedingView(ChangePinView.SubViews.PasswordInfo)
52	}
53
54	function showSettings() {
55		showWithPrecedingView(ChangePinView.SubViews.ReaderSettings)
56	}
57
58	Keys.onEscapePressed: if (d.cancelAllowed) ChangePinModel.cancelWorkflow()
59
60	titleBarAction: TitleBarAction {
61		//: LABEL DESKTOP_QML
62		text: qsTr("Change PIN")
63		rootEnabled: d.activeView === ChangePinView.SubViews.Start
64		helpTopic: "pinManagement"
65		showSettings: (changePinController.workflowState === ChangePinController.WorkflowStates.Reader ||
66						changePinController.workflowState === ChangePinController.WorkflowStates.Card)
67						&& d.activeView !== ChangePinView.SubViews.Progress
68						&& d.activeView !== ChangePinView.SubViews.ProgressNewPin
69						&& d.activeView !== ChangePinView.SubViews.NoPassword
70
71		onClicked: {
72			if (d.activeView === ChangePinView.SubViews.PasswordInfo ||
73				d.activeView === ChangePinView.SubViews.NoPassword ||
74				d.activeView === ChangePinView.SubViews.ReaderSettings) {
75					d.view = readerView.precedingView
76					ApplicationWindow.menuBar.updateActions()
77			}
78		}
79
80		customSubAction: CancelAction {
81			visible: d.cancelAllowed
82
83			onClicked: {
84				if (pinResult.visible) {
85					ChangePinModel.continueWorkflow()
86					baseItem.nextView(UiModule.DEFAULT)
87				} else {
88					ChangePinModel.cancelWorkflow()
89				}
90			}
91		}
92
93		customSettingsHandler: baseItem.showSettings
94	}
95
96	QtObject {
97		id: d
98
99		property var view: ChangePinView.SubViews.Start
100		readonly property int activeView: inputError.visible ? ChangePinView.SubViews.InputError : pinUnlocked.visible ? ChangePinView.SubViews.PinUnlocked : view
101		readonly property bool cancelAllowed: view !== ChangePinView.SubViews.NoPassword && view !== ChangePinView.SubViews.Start && (ChangePinModel.isBasicReader || generalWorkflow.waitingFor != Workflow.WaitingFor.Password)
102	}
103
104	TabbedReaderView {
105		id: readerView
106
107		property int precedingView: ChangePinView.SubViews.Start
108
109		visible: d.activeView === ChangePinView.SubViews.ReaderSettings
110		onCloseView: {
111			d.view = precedingView
112			ApplicationWindow.menuBar.updateActions()
113		}
114	}
115
116	ChangePinController {
117		id: changePinController
118
119		onNextView: {
120			if (pName === ChangePinView.SubViews.ReturnToMain) {
121				baseItem.nextView(UiModule.DEFAULT)
122				return;
123			}
124
125			d.view = pName
126		}
127	}
128
129	DecisionView {
130		visible: d.activeView === ChangePinView.SubViews.Start
131
132		style: DecisionView.ButtonStyle.AllButtons
133		mainIconSource: "qrc:/images/material_lock.svg"
134		//: LABEL DESKTOP_QML Title of PIN change start page. User is asked which type of PIN they have.
135		questionText: qsTr("What kind of PIN do you have?")
136		questionSubText: "%1<br><br><a href=\"#\">%2</a>"
137			//: LABEL DESKTOP_QML Description of PIN change start page. User has a choice of which PIN to set.
138			.arg(qsTr("Here you have the possibility to set or change the PIN of your identity card."))
139			//: LABEL DESKTOP_QML More information link. Leads to information about pin letter.
140			.arg(qsTr("More information"))
141		agreeButton.iconText: "?"
142		//: LABEL DESKTOP_QML
143		agreeText: qsTr("No PIN")
144		neutralButton.iconText: "5"
145		//: LABEL DESKTOP_QML
146		neutralText: qsTr("Five-digit Transport PIN")
147		disagreeButton.iconText: "6"
148		//: LABEL DESKTOP_QML
149		disagreeText: qsTr("Six-digit PIN")
150
151		onSubTextLinkActivated: baseItem.showPasswordInfo()
152
153		onNeutral: ChangePinModel.startWorkflow(true)
154		onDisagree: ChangePinModel.startWorkflow(false)
155		onAgree: d.view = ChangePinView.SubViews.NoPassword
156	}
157
158	ResultView {
159		id: noPasswordView
160
161		visible: d.activeView === ChangePinView.SubViews.NoPassword
162
163		resultType: ResultView.Type.IsInfo
164		buttonType: NavigationButton.Type.Check
165		//: LABEL DESKTOP_QML
166		text: qsTr("You cannot find your PIN letter? You have set a PIN when picking up the ID card or later that you cannot recall now?\n\nIf this is the case please turn to the competent authority and set a new PIN there.")
167
168		onNextView: baseItem.nextView(UiModule.DEFAULT)
169	}
170
171	GeneralWorkflow {
172		id: generalWorkflow
173
174		visible: d.activeView === ChangePinView.SubViews.Workflow
175
176		isPinChange: true
177		waitingFor: switch (changePinController.workflowState) {
178						case ChangePinController.WorkflowStates.Reader:
179							return Workflow.WaitingFor.Reader
180						case ChangePinController.WorkflowStates.Card:
181							return Workflow.WaitingFor.Card
182						case ChangePinController.WorkflowStates.Password:
183							return Workflow.WaitingFor.Password
184						default:
185							return Workflow.WaitingFor.None
186		}
187		onSettingsRequested: baseItem.showSettings()
188	}
189
190	EnterPasswordView {
191		id: enterPasswordView
192
193		visible: d.activeView === ChangePinView.SubViews.Password
194
195		onPasswordEntered: {
196			d.view = pWasNewPin ? ChangePinView.SubViews.ProgressNewPin : ChangePinView.SubViews.Progress
197			ChangePinModel.continueWorkflow()
198		}
199
200		onRequestPasswordInfo: baseItem.showPasswordInfo()
201	}
202
203	PasswordInfoView {
204		id: passwordInfoView
205
206		visible: d.activeView === ChangePinView.SubViews.PasswordInfo
207
208		onClose: {
209			d.view = readerView.precedingView
210			ApplicationWindow.menuBar.updateActions()
211		}
212	}
213
214	ProgressView {
215		id: pinProgressView
216
217		visible: d.activeView === ChangePinView.SubViews.Progress || d.activeView === ChangePinView.SubViews.ProgressNewPin
218
219		text: d.activeView === ChangePinView.SubViews.ProgressNewPin
220			//: LABEL DESKTOP_QML Processing screen label while the card communication is running after the new PIN has been entered during PIN change process.
221			? qsTr("Setting new PIN")
222			//: LABEL DESKTOP_QML Processing screen label while the card communication is running after the old PIN has been entered during PIN change process.
223			: qsTr("Change PIN")
224		//: INFO DESKTOP_QML Processing screen text while the card communication is running after the PIN has been entered during PIN change process.
225		subText: qsTr("Please do not move the ID card.")
226	}
227
228	ResultView {
229		id: inputError
230
231		property bool errorConfirmed: false
232
233		visible: !errorConfirmed && NumberModel.hasPasswordError && d.view != ChangePinView.SubViews.Result
234
235		resultType: ResultView.Type.IsError
236		text: NumberModel.inputError
237		onNextView: errorConfirmed = true
238
239		Connections {
240			target: NumberModel
241			onFireInputErrorChanged: inputError.errorConfirmed = false
242		}
243	}
244
245	ResultView {
246		id: pinUnlocked
247
248		property bool confirmed: true
249
250		visible: !confirmed && (d.view === ChangePinView.SubViews.Password || generalWorkflow.waitingFor === Workflow.WaitingFor.Password)
251
252		resultType: ResultView.Type.IsSuccess
253		//: INFO DESKTOP_QML The ID card has just been unblocked and the user can now continue with their PIN change.
254		text: qsTr("Your PIN is unblocked. You now have three more attempts to change your PIN.")
255		onNextView: confirmed = true
256
257		Connections {
258			target: ChangePinModel
259			onFireOnPinUnlocked: pinUnlocked.confirmed = false
260		}
261	}
262
263	ResultView {
264		id: cardPositionView
265
266		visible: d.activeView === ChangePinView.SubViews.CardPosition
267
268		resultType: ResultView.Type.IsInfo
269		//: INFO DESKTOP_QML The NFC signal is weak or unstable, the user is asked to change the card's position to (hopefully) reduce the distance to the NFC chip.
270		text: qsTr("Weak NFC signal. Please\n- change the card position\n- remove the mobile phone case (if present)\n- connect the smartphone with a charging cable")
271		onNextView: ChangePinModel.continueWorkflow()
272	}
273
274	ResultView {
275		id: pinResult
276
277		visible: d.activeView === ChangePinView.SubViews.Result
278
279		resultType: ChangePinModel.error ? ResultView.Type.IsError : ResultView.Type.IsSuccess
280		text: ChangePinModel.resultString
281		onNextView: {
282			ChangePinModel.continueWorkflow()
283			baseItem.nextView(pName)
284		}
285		supportButtonsVisible: ChangePinModel.error && !ChangePinModel.isCancellationByUser()
286		onEmailButtonPressed: ChangePinModel.sendResultMail()
287	}
288}
289