1
0
Fork 0
mirror of https://github.com/seiichiro0185/sailotp.git synced 2024-11-22 07:39:42 +00:00

Preparations for version 0.6 release

Added possibility to cycle through the tokens from the cover
This commit is contained in:
seiichiro 2014-02-09 10:50:58 +01:00
parent 82ea4f182c
commit dc02a1aa3f
5 changed files with 97 additions and 53 deletions

View file

@ -38,28 +38,30 @@ CoverBackground {
property double lastUpdated: 0 property double lastUpdated: 0
function updateOTP() {
// get seconds from current Date
var curDate = new Date();
if (lOTP.text == "------" || curDate.getSeconds() == 30 || curDate.getSeconds() == 0 || (curDate.getTime() - lastUpdated > 2000)) {
appWin.coverOTP = OTP.calcOTP(appWin.coverSecret, "TOTP", 0);
}
// Change color of the OTP to red if less than 5 seconds left
if (29 - (curDate.getSeconds() % 30) < 5) {
lOTP.color = "red"
} else {
lOTP.color = Theme.highlightColor
}
lastUpdated = curDate.getTime();
}
Timer { Timer {
interval: 1000 interval: 1000
// Timer runs only when cover is visible and favourite is set // Timer runs only when cover is visible and favourite is set
running: !Qt.application.active && appWin.coverSecret != "" && appWin.coverType == "TOTP" running: !Qt.application.active && appWin.coverSecret != "" && appWin.coverType == "TOTP"
repeat: true repeat: true
onTriggered: { onTriggered: updateOTP();
// get seconds from current Date
var curDate = new Date();
if (lOTP.text == "------" || curDate.getSeconds() == 30 || curDate.getSeconds() == 0 || (curDate.getTime() - lastUpdated > 2000)) {
appWin.coverOTP = OTP.calcOTP(appWin.coverSecret, "TOTP", 0);
}
// Change color of the OTP to red if less than 5 seconds left
if (29 - (curDate.getSeconds() % 30) < 5) {
lOTP.color = "red"
} else {
lOTP.color = Theme.highlightColor
}
lastUpdated = curDate.getTime();
}
} }
// Show the SailOTP Logo // Show the SailOTP Logo
@ -79,7 +81,6 @@ CoverBackground {
Label { Label {
text: appWin.coverTitle text: appWin.coverTitle
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
color: Theme.secondaryColor
} }
Label { Label {
id: lOTP id: lOTP
@ -91,11 +92,28 @@ CoverBackground {
} }
// CoverAction to update a HOTP-Token, only visible for HOTP-Type Tokens // CoverAction to update a HOTP-Token, only visible for HOTP-Type Tokens
CoverActionList { CoverActionList {
enabled: appWin.coverType == "HOTP" ? true : false
CoverAction { CoverAction {
iconSource: "image://theme/icon-m-refresh" iconSource: appWin.coverType == "HOTP" ? "image://theme/icon-cover-refresh" : "image://theme/icon-cover-previous"
onTriggered: { onTriggered: {
appWin.coverOTP = OTP.calcOTP(appWin.coverSecret, "HOTP", DB.getCounter(appWin.coverTitle, appWin.coverSecret, true)); if (appWin.coverType == "HOTP") {
appWin.coverOTP = OTP.calcOTP(appWin.coverSecret, "HOTP", DB.getCounter(appWin.coverTitle, appWin.coverSecret, true));
} else {
var index = appWin.coverIndex - 1
if (index < 0) index = appWin.listModel.count - 1
appWin.setCover(index);
DB.setFav(appWin.coverTitle, appWin.coverSecret)
if (appWin.coverType == "TOTP") updateOTP();
}
}
}
CoverAction {
iconSource: "image://theme/icon-cover-next"
onTriggered: {
var index = appWin.coverIndex + 1
if (index >= appWin.listModel.count) index = 0
appWin.setCover(index);
DB.setFav(appWin.coverTitle, appWin.coverSecret)
if (appWin.coverType == "TOTP") updateOTP();
} }
} }
} }

View file

@ -37,15 +37,50 @@ ApplicationWindow
id: appWin id: appWin
// Properties to pass values between MainPage and Cover // Properties to pass values between MainPage and Cover
property alias listModel: otpListModel
property string coverTitle: "SailOTP" property string coverTitle: "SailOTP"
property string coverSecret: "" property string coverSecret: ""
property string coverType: "" property string coverType: ""
property string coverOTP: "------" property string coverOTP: "------"
property int coverIndex: 0
// Global Listmodel for Tokens
ListModel { id: otpListModel }
// Global Component for showing notification banners
NotifyBanner { id: notify } NotifyBanner { id: notify }
// Add an entry to the list
function appendOTP(title, secret, type, counter, fav) {
listModel.append({"secret": secret, "title": title, "fav": fav, "type": type, "counter": counter, "otp": "------"});
}
// Set the OTP shown on the Cover
function setCover(index) {
if (index >= 0 && index < listModel.count) {
coverTitle = listModel.get(index).title;
coverSecret = listModel.get(index).secret;
coverType = listModel.get(index).type;
coverIndex = index;
if (coverType == "TOTP") { coverOTP = "------"; } else { coverOTP = listModel.get(index).otp; }
for (var i=0; i<listModel.count; i++) {
if (i != index) {
listModel.setProperty(i, "fav", 0);
} else {
listModel.setProperty(i, "fav", 1);
}
}
} else {
coverTitle = "SailOTP";
coverSecret = "";
coverType = "";
coverIndex = -1;
}
}
initialPage: Component { MainView { } } initialPage: Component { MainView { } }
cover: Qt.resolvedUrl("cover/CoverPage.qml") cover: Qt.resolvedUrl("cover/CoverPage.qml")
} }

View file

@ -65,8 +65,8 @@ function getOTP() {
function(tx) { function(tx) {
var res = tx.executeSql("select * from OTPStorage;"); var res = tx.executeSql("select * from OTPStorage;");
for (var i=0; i < res.rows.length; i++) { for (var i=0; i < res.rows.length; i++) {
mainPage.appendOTP(res.rows.item(i).title, res.rows.item(i).secret, res.rows.item(i).type, res.rows.item(i).counter, res.rows.item(i).fav); appWin.appendOTP(res.rows.item(i).title, res.rows.item(i).secret, res.rows.item(i).type, res.rows.item(i).counter, res.rows.item(i).fav);
if (res.rows.item(i).fav) mainPage.setCoverOTP(res.rows.item(i).title, res.rows.item(i).secret, res.rows.item(i).type); if (res.rows.item(i).fav) appWin.setCover(i);
} }
}); });
} }

View file

@ -36,18 +36,9 @@ import "../lib/crypto.js" as OTP
Page { Page {
id: mainPage id: mainPage
ListModel {
id: otpListModel
}
// This holds the time of the last update of the page as Unix Timestamp (in Milliseconds) // This holds the time of the last update of the page as Unix Timestamp (in Milliseconds)
property double lastUpdated: 0 property double lastUpdated: 0
// Add an entry to the list
function appendOTP(title, secret, type, counter, fav) {
otpListModel.append({"secret": secret, "title": title, "fav": fav, "type": type, "counter": counter, "otp": "------"});
}
// Hand favorite over to the cover // Hand favorite over to the cover
function setCoverOTP(title, secret, type) { function setCoverOTP(title, secret, type) {
appWin.coverTitle = title appWin.coverTitle = title
@ -63,7 +54,7 @@ Page {
// Reload the List of OTPs from storage // Reload the List of OTPs from storage
function refreshOTPList() { function refreshOTPList() {
otpList.visible = false; otpList.visible = false;
otpListModel.clear(); appWin.listModel.clear();
DB.getOTP(); DB.getOTP();
refreshOTPValues(); refreshOTPValues();
otpList.visible = true; otpList.visible = true;
@ -76,16 +67,16 @@ Page {
var seconds = curDate.getSeconds(); var seconds = curDate.getSeconds();
// Iterate over all List entries // Iterate over all List entries
for (var i=0; i<otpListModel.count; i++) { for (var i=0; i<appWin.listModel.count; i++) {
if (otpListModel.get(i).type == "TOTP") { if (appWin.listModel.get(i).type == "TOTP") {
// Only update on full 30 / 60 Seconds or if last run of the Functions is more than 2s in the past (e.g. app was in background) // Only update on full 30 / 60 Seconds or if last run of the Functions is more than 2s in the past (e.g. app was in background)
if (otpListModel.get(i).otp == "------" || seconds == 30 || seconds == 0 || (curDate.getTime() - lastUpdated > 2000)) { if (appWin.listModel.get(i).otp == "------" || seconds == 30 || seconds == 0 || (curDate.getTime() - lastUpdated > 2000)) {
var curOTP = OTP.calcOTP(otpListModel.get(i).secret, "TOTP") var curOTP = OTP.calcOTP(appWin.listModel.get(i).secret, "TOTP")
otpListModel.setProperty(i, "otp", curOTP); appWin.listModel.setProperty(i, "otp", curOTP);
} }
} else if (appWin.coverType == "HOTP" && (curDate.getTime() - lastUpdated > 2000) && otpListModel.get(i).fav == 1) { } else if (appWin.coverType == "HOTP" && (curDate.getTime() - lastUpdated > 2000) && appWin.listModel.get(i).fav == 1) {
// If we are coming back from the CoverPage update OTP value if current favourite is HOTP // If we are coming back from the CoverPage update OTP value if current favourite is HOTP
otpListModel.setProperty(i, "otp", appWin.coverOTP); appWin.listModel.setProperty(i, "otp", appWin.coverOTP);
} }
} }
@ -98,7 +89,7 @@ Page {
Timer { Timer {
interval: 500 interval: 500
// Timer only runs when app is acitive and we have entries // Timer only runs when app is acitive and we have entries
running: Qt.application.active && otpListModel.count running: Qt.application.active && appWin.listModel.count
repeat: true repeat: true
onTriggered: refreshOTPValues(); onTriggered: refreshOTPValues();
} }
@ -132,7 +123,7 @@ Page {
anchors.top: parent.top anchors.top: parent.top
anchors.topMargin: 48 anchors.topMargin: 48
// Only show when there are enries // Only show when there are enries
visible: otpListModel.count visible: appWin.listModel.count
} }
SilicaListView { SilicaListView {
@ -141,7 +132,7 @@ Page {
title: "SailOTP" title: "SailOTP"
} }
anchors.fill: parent anchors.fill: parent
model: otpListModel model: appWin.listModel
width: parent.width width: parent.width
ViewPlaceholder { ViewPlaceholder {
@ -158,7 +149,7 @@ Page {
function remove() { function remove() {
// Show 5s countdown, then delete from DB and List // Show 5s countdown, then delete from DB and List
remorseAction(qsTr("Deleting"), function() { DB.removeOTP(title, secret); otpListModel.remove(index) }) remorseAction(qsTr("Deleting"), function() { DB.removeOTP(title, secret); appWin.listModel.remove(index) })
} }
onClicked: { onClicked: {
@ -178,19 +169,19 @@ Page {
onClicked: { onClicked: {
if (fav == 0) { if (fav == 0) {
DB.setFav(title, secret) DB.setFav(title, secret)
setCoverOTP(title, secret, type) appWin.setCover(index)
if (type == "HOTP") appWin.coverOTP = otp if (type == "HOTP") appWin.coverOTP = otp
for (var i=0; i<otpListModel.count; i++) { for (var i=0; i<appWin.listModel.count; i++) {
if (i != index) { if (i != index) {
otpListModel.setProperty(i, "fav", 0); appWin.listModel.setProperty(i, "fav", 0);
} else { } else {
otpListModel.setProperty(i, "fav", 1); appWin.listModel.setProperty(i, "fav", 1);
} }
} }
} else { } else {
DB.resetFav(title, secret) DB.resetFav(title, secret)
setCoverOTP("SailOTP", "", "") appWin.setCover(-1)
otpListModel.setProperty(index, "fav", 0); appWin.listModel.setProperty(index, "fav", 0);
} }
} }
} }
@ -221,8 +212,8 @@ Page {
anchors.right: parent.right anchors.right: parent.right
visible: type == "HOTP" ? true : false visible: type == "HOTP" ? true : false
onClicked: { onClicked: {
otpListModel.setProperty(index, "counter", DB.getCounter(title, secret, true)); appWin.listModel.setProperty(index, "counter", DB.getCounter(title, secret, true));
otpListModel.setProperty(index, "otp", OTP.calcOTP(secret, "HOTP", counter)); appWin.listModel.setProperty(index, "otp", OTP.calcOTP(secret, "HOTP", counter));
if (fav == 1) appWin.coverOTP = otp; if (fav == 1) appWin.coverOTP = otp;
} }
} }

View file

@ -1,6 +1,6 @@
Name: harbour-sailotp Name: harbour-sailotp
Summary: SailOTP Summary: SailOTP
Version: 0.5 Version: 0.6
Release: 1 Release: 1
Group: Security Group: Security
URL: https://github.com/seiichiro0185/sailotp/ URL: https://github.com/seiichiro0185/sailotp/