/**************************************************************************** * Copyright (C) 2014 ecsec GmbH. * All rights reserved. * Contact: ecsec GmbH (info@ecsec.de) * * This file is part of the Open eCard App. * * GNU General Public License Usage * This file may be used under the terms of the GNU General Public * License version 3.0 as published by the Free Software Foundation * and appearing in the file LICENSE.GPL included in the packaging of * this file. Please review the following information to ensure the * GNU General Public License version 3.0 requirements will be met: * http://www.gnu.org/copyleft/gpl.html. * * Other Usage * Alternatively, this file may be used in accordance with the terms * and conditions contained in a signed written agreement between * you and ecsec GmbH. * ***************************************************************************/ package org.openecard.plugins.pinplugin.gui; import org.openecard.common.I18n; import org.openecard.gui.definition.PasswordField; import org.openecard.gui.definition.Step; import org.openecard.gui.definition.Text; import org.openecard.plugins.pinplugin.RecognizedState; /** * * @author Hans-Martin Haase */ public class GenericPINStep extends Step { private final boolean capturePin; private final I18n lang = I18n.getTranslation("pinplugin"); // translation constants PIN Change private static final String CHANGE_PIN_TITLE = "action.changepin.userconsent.pinstep.title"; private static final String PINSTEP_NEWPINREPEAT = "action.changepin.userconsent.pinstep.newpinrepeat"; private static final String PINSTEP_NEWPIN = "action.changepin.userconsent.pinstep.newpin"; private static final String PINSTEP_OLDPIN = "action.changepin.userconsent.pinstep.oldpin"; private static final String PINSTEP_DESCRIPTION = "action.changepin.userconsent.pinstep.description"; private static final String PINSTEP_DESCRIPTION_AFTER_CAN = "action.changepin.userconsent.pinstep.description_after_can"; private static final String REMAINING_ATTEMPTS = "action.changepin.userconsent.pinstep.remaining_attempts"; private static final String WRONG_ENTRY = "action.changepin.userconsent.pinstep.wrong_entry"; private static final String INCORRECT_INPUT = "action.changepin.userconsent.pinstep.incorrect_input"; private static final String PINSTEP_NATIV_CHANGE_DESCRIPTION = "action.changepin.userconsent.pinstep.native_start_description"; private static final String PINSTEP_NATIV_CHANGE_DESCRIPTION_AFTER_CAN = "action.changepin.userconsent.pinstep.native_start_description_after_can"; // translation constants PUK entring private static final String PUKSTEP_DESCRIPTION = "action.unblockpin.userconsent.pukstep.description"; private static final String PUKSTEP_TITLE = "action.unblockpin.userconsent.pukstep.title"; private static final String PUKSTEP_PUK = "action.unblockpin.userconsent.pukstep.puk"; private static final String PUKSTEP_START_NATIV_DESCRIPTION = "action.unblockpin.userconsent.pukstep.nativ_start_description"; // translation constants CAN entering private static final String CANSTEP_TITLE = "action.changepin.userconsent.canstep.title"; private static final String CANSTEP_NOTICE = "action.changepin.userconsent.canstep.notice"; private static final String CANSTEP_CAN = "action.changepin.userconsent.canstep.can"; private static final String CANSTEP_DESCRIPTION = "action.changepin.userconsent.canstep.description"; private static final String WRONG_CAN = "action.changepin.userconsent.canstepaction.wrong_can"; private static final String CANSTEP_START_NATIV_DESCRIPTION = "action.changepin.userconsent.canstepaction.nativ_start_description"; private static final String ERROR_TITLE = "action.changepin.userconsent.errorstep.title"; private static final String ERRORSTEP_DEACTIVATED = "action.changepin.userconsent.errorstep.deactivated"; private static final String ERRORSTEP_PUK_BLOCKED = "action.changepin.userconsent.errorstep.puk_blocked"; private static final String ERRORSTEP_UNKNOWN = "action.changepin.userconsent.errorstep.unknown"; // protected GUI element IDs protected static final String OLD_PIN_FIELD = "OLD_PIN_FIELD"; protected static final String NEW_PIN_FIELD = "NEW_PIN_FIELD"; protected static final String NEW_PIN_REPEAT_FIELD = "NEW_PIN_REPEAT_FIELD"; protected static final String PUK_FIELD = "PUK_FIELD"; protected static final String CAN_FIELD = "CAN_FIELD"; // indicators set by the action private boolean wrongPINFormat; private boolean failedPINVerify; private boolean wrongCANFormat; private boolean failedCANVerify; private boolean wrongPUKFormat; private boolean failedPUKVerify; private boolean canSuccess; private int retryCounterPIN; private int retryCounterPUK = 10; private RecognizedState pinState; public GenericPINStep(String id, String title, boolean capturePin, RecognizedState state) { super(id, title); this.capturePin = capturePin; pinState = state; generateGenericGui(); } private void generateGenericGui() { switch(pinState) { case PIN_activated_RC3: setTitle(lang.translationForKey(CHANGE_PIN_TITLE)); retryCounterPIN = 3; if (capturePin) { createPINChangeGui(); } else { createPINChangeGuiNativ(); } break; case PIN_activated_RC2: setTitle(lang.translationForKey(CHANGE_PIN_TITLE)); retryCounterPIN = 2; if (capturePin) { createPINChangeGui(); } else { createPINChangeGuiNativ(); } break; case PIN_blocked: setTitle(lang.translationForKey(PUKSTEP_TITLE)); retryCounterPIN = 0; if (capturePin) { createPUKGui(); } else { createPUKGuiNativ(); } break; case PIN_suspended: setTitle(lang.translationForKey(CANSTEP_TITLE)); retryCounterPIN = 1; if (capturePin) { createCANGui(); } else { createCANGuiNativ(); } break; case PIN_resumed: setTitle(lang.translationForKey(CHANGE_PIN_TITLE)); retryCounterPIN = 1; canSuccess = true; if (capturePin) { createPINChangeGui(); } else { createPINChangeGuiNativ(); } break; case PIN_deactivated: setTitle(lang.translationForKey(ERROR_TITLE)); retryCounterPIN = -1; createErrorGui(); break; case UNKNOWN: setTitle(lang.translationForKey(ERROR_TITLE)); retryCounterPIN = -2; createErrorGui(); break; case PUK_blocked: setTitle(lang.translationForKey(ERROR_TITLE)); createErrorGui(); retryCounterPUK = 0; } } protected void updateState(RecognizedState newState) { pinState = newState; getInputInfoUnits().clear(); generateGenericGui(); } private void createPINChangeGuiNativ() { String nativPinChangeDescriptionText; if (canSuccess) { nativPinChangeDescriptionText = lang.translationForKey(PINSTEP_NATIV_CHANGE_DESCRIPTION_AFTER_CAN); } else { nativPinChangeDescriptionText = lang.translationForKey(PINSTEP_NATIV_CHANGE_DESCRIPTION); } Text nativPinChangeDescription = new Text(nativPinChangeDescriptionText); getInputInfoUnits().add(nativPinChangeDescription); if (failedPINVerify || canSuccess) { addVerifyFailed("PIN"); } addRemainingAttempts(); } private void createPINChangeGui() { String pinChangeDescriptionText; if (canSuccess) { pinChangeDescriptionText = lang.translationForKey(PINSTEP_DESCRIPTION_AFTER_CAN, "PIN"); } else { pinChangeDescriptionText = lang.translationForKey(PINSTEP_DESCRIPTION, "PIN"); } Text pinChangeDescription = new Text(pinChangeDescriptionText); getInputInfoUnits().add(pinChangeDescription); Text dummy = new Text(" "); getInputInfoUnits().add(dummy); Text pinText = new Text(lang.translationForKey(PINSTEP_OLDPIN)); getInputInfoUnits().add(pinText); PasswordField oldPIN = new PasswordField(OLD_PIN_FIELD); oldPIN.setMinLength(5); // in case of transport pin oldPIN.setMaxLength(6); getInputInfoUnits().add(oldPIN); Text newPinText = new Text(lang.translationForKey(PINSTEP_NEWPIN)); getInputInfoUnits().add(newPinText); PasswordField newPIN = new PasswordField(NEW_PIN_FIELD); newPIN.setMaxLength(6); newPIN.setMinLength(6); getInputInfoUnits().add(newPIN); Text newPinAgainText = new Text(lang.translationForKey(PINSTEP_NEWPINREPEAT)); getInputInfoUnits().add(newPinAgainText); PasswordField newPINRepeat = new PasswordField(NEW_PIN_REPEAT_FIELD); newPINRepeat.setMaxLength(6); newPINRepeat.setMinLength(6); getInputInfoUnits().add(newPINRepeat); if (wrongPINFormat) { // add note for mistyped PIN Text noteWrongEntry = new Text(); noteWrongEntry.setText(lang.translationForKey(WRONG_ENTRY, "PIN")); getInputInfoUnits().add(noteWrongEntry); } if (failedPINVerify) { // add note for incorrect input addVerifyFailed("PIN"); } addRemainingAttempts(); } private void createPUKGuiNativ() { Text nativPUKText = new Text(lang.translationForKey(PUKSTEP_START_NATIV_DESCRIPTION)); getInputInfoUnits().add(nativPUKText); // show the puk try counter // Text pukTryCounter = new Text(); // pukTryCounter.setText(lang.translationForKey(REMAINING_ATTEMPTS, retryCounterPUK)); // getInputInfoUnits().add(pukTryCounter); if (failedPUKVerify) { addVerifyFailed("PUK"); } } private void createPUKGui() { Text i1 = new Text(); getInputInfoUnits().add(i1); i1.setText(lang.translationForKey(PUKSTEP_DESCRIPTION)); PasswordField pukField = new PasswordField(PUK_FIELD); pukField.setMaxLength(10); pukField.setMinLength(10); pukField.setDescription(lang.translationForKey(PUKSTEP_PUK)); getInputInfoUnits().add(pukField); // show the puk try counter // Text pukTryCounter = new Text(); // pukTryCounter.setText(lang.translationForKey(REMAINING_ATTEMPTS, retryCounterPUK)); // getInputInfoUnits().add(pukTryCounter); if (wrongPUKFormat) { // add note for mistyped PUK Text noteWrongEntry = new Text(); noteWrongEntry.setText(lang.translationForKey(WRONG_ENTRY, "PUK")); getInputInfoUnits().add(noteWrongEntry); } if (failedPUKVerify) { // add note for incorrect input addVerifyFailed("PUK"); } } private void createCANGuiNativ() { Text nativCANText = new Text(lang.translationForKey(CANSTEP_START_NATIV_DESCRIPTION)); getInputInfoUnits().add(nativCANText); if (failedCANVerify) { addVerifyFailed("CAN"); } } private void createCANGui() { Text i1 = new Text(); i1.setText(lang.translationForKey(CANSTEP_NOTICE)); getInputInfoUnits().add(i1); Text i2 = new Text(); getInputInfoUnits().add(i2); // add description and input fields depending on terminal type i2.setText(lang.translationForKey(CANSTEP_DESCRIPTION)); PasswordField canField = new PasswordField(CAN_FIELD); canField.setMinLength(6); canField.setMaxLength(6); canField.setDescription(lang.translationForKey(CANSTEP_CAN)); getInputInfoUnits().add(canField); if (wrongCANFormat) { // add note for mistyped CAN Text retryText = new Text(); retryText.setText(lang.translationForKey(WRONG_CAN)); getInputInfoUnits().add(retryText); } if (failedCANVerify) { // add note for incorrect input addVerifyFailed("CAN"); } } private void createErrorGui() { setReversible(false); Text errorText = new Text(); switch(pinState) { case PIN_deactivated: errorText.setText(lang.translationForKey(ERRORSTEP_DEACTIVATED)); break; case PUK_blocked: errorText.setText(lang.translationForKey(ERRORSTEP_PUK_BLOCKED)); break; case UNKNOWN: errorText.setText(lang.translationForKey(ERRORSTEP_UNKNOWN)); break; } getInputInfoUnits().add(errorText); } protected void setWrongPINFormat(boolean wrongFormat) { wrongPINFormat = wrongFormat; } protected void setFailedPINVerify(boolean failedVerify) { failedPINVerify = failedVerify; } protected void setWrongCANFormat(boolean wrongFormat) { wrongCANFormat = wrongFormat; } protected void setFailedCANVerify(boolean failedVerify) { failedCANVerify = failedVerify; } protected void setWrongPUKFormat(boolean wrongFormat) { wrongPUKFormat = wrongFormat; } protected void setFailedPUKVerify(boolean failedVerify) { failedPUKVerify = failedVerify; } protected void decreasePUKCounter() { retryCounterPUK--; getInputInfoUnits().clear(); generateGenericGui(); } private void addRemainingAttempts() { Text txtRemainingAttempts = new Text(); txtRemainingAttempts.setText(lang.translationForKey(REMAINING_ATTEMPTS, retryCounterPIN)); getInputInfoUnits().add(txtRemainingAttempts); } private void addVerifyFailed(String did) { Text incorrectInput = new Text(); incorrectInput.setText(lang.translationForKey(INCORRECT_INPUT, did)); getInputInfoUnits().add(incorrectInput); } }