diff --git a/programs/light_client/Operations.cpp b/programs/light_client/Operations.cpp
index bca91508..f1109ebb 100644
--- a/programs/light_client/Operations.cpp
+++ b/programs/light_client/Operations.cpp
@@ -28,12 +28,25 @@ TransferOperation* OperationBuilder::transfer(ObjectId sender, ObjectId receiver
QString TransferOperation::memo() const {
if (!m_op.memo)
return QString::null;
+ if (memoIsEncrypted())
+ return tr("Encrypted Memo");
QString memo = QString::fromStdString(m_op.memo->get_message({}, {}));
while (memo.endsWith('\0'))
memo.chop(1);
return memo;
}
+bool TransferOperation::memoIsEncrypted() const
+{
+ if (!m_op.memo)
+ return false;
+ if (m_op.memo->message.empty())
+ return false;
+ if (m_op.memo->from == public_key_type() && m_op.memo->to == public_key_type())
+ return false;
+ return true;
+}
+
bool TransferOperation::canEncryptMemo(Wallet* wallet, ChainDataModel* model) const
{
if (!m_op.memo) return false;
diff --git a/programs/light_client/Operations.hpp b/programs/light_client/Operations.hpp
index 2a226ed6..e56d5852 100644
--- a/programs/light_client/Operations.hpp
+++ b/programs/light_client/Operations.hpp
@@ -35,6 +35,7 @@ class TransferOperation : public OperationBase {
Q_PROPERTY(qint64 amount READ amount WRITE setAmount NOTIFY amountChanged)
Q_PROPERTY(ObjectId amountType READ amountType WRITE setAmountType NOTIFY amountTypeChanged)
Q_PROPERTY(QString memo READ memo WRITE setMemo NOTIFY memoChanged)
+ Q_PROPERTY(bool memoIsEncrypted READ memoIsEncrypted NOTIFY memoChanged)
graphene::chain::transfer_operation m_op;
@@ -60,6 +61,7 @@ public:
/// performed by calling encryptMemo()
QString memo() const;
+ bool memoIsEncrypted()const;
Q_INVOKABLE bool canEncryptMemo(Wallet* wallet, ChainDataModel* model) const;
Q_INVOKABLE bool canDecryptMemo(Wallet* wallet, ChainDataModel* model) const;
Q_INVOKABLE QString decryptedMemo(Wallet* wallet, ChainDataModel* model) const;
diff --git a/programs/light_client/qml/TransactionConfirmationForm.qml b/programs/light_client/qml/TransactionConfirmationForm.qml
index 2924665c..ff195962 100644
--- a/programs/light_client/qml/TransactionConfirmationForm.qml
+++ b/programs/light_client/qml/TransactionConfirmationForm.qml
@@ -62,36 +62,19 @@ FormBase {
Loader {
sourceComponent: trx && Array.prototype.slice.call(trx.operations).length > 0? transactionDelegate : undefined
}
- RowLayout {
+ UnlockingFinishButtons {
+ app: base.app
Layout.fillWidth: true
- Item { Layout.fillWidth: true }
- Button {
- text: qsTr("Cancel")
- onClicked: {
- canceled({})
- trx = null
- }
+ onLeftButtonClicked: {
+ canceled({})
+ trx = null
}
- TextField {
- id: passwordField
- Layout.preferredWidth: app.wallet.isLocked? Scaling.cm(4) : 0
- echoMode: TextInput.Password
- placeholderText: qsTr("Wallet password")
- visible: width > 0
- onAccepted: finishButton.clicked()
-
- Behavior on Layout.preferredWidth { NumberAnimation { duration: 200; easing.type: Easing.InOutQuad } }
- }
- Button {
- id: finishButton
- text: app.wallet.isLocked? qsTr("Unlock") : qsTr("Finish")
- onClicked: {
- if (app.wallet.isLocked)
- app.wallet.unlock(passwordField.text)
- else {
- app.wallet.sign(trx)
- completed(trx)
- }
+ onRightButtonClicked: {
+ if (app.wallet.isLocked)
+ app.wallet.unlock(passwordField.text)
+ else {
+ app.wallet.sign(trx)
+ completed(trx)
}
}
}
diff --git a/programs/light_client/qml/TransferForm.qml b/programs/light_client/qml/TransferForm.qml
index 310a2765..f4c99dd9 100644
--- a/programs/light_client/qml/TransferForm.qml
+++ b/programs/light_client/qml/TransferForm.qml
@@ -1,6 +1,5 @@
import QtQuick 2.5
import QtQuick.Controls 1.4
-import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.2
import Graphene.Client 0.1
@@ -19,7 +18,7 @@ FormBase {
property alias receiverAccount: recipientPicker.account
function operation() {
- if (!transferButton.enabled) return app.operationBuilder.transfer(0,0,0,0, memoField.text, 0)
+ if (!finishLine.rightButtonEnabled) return app.operationBuilder.transfer(0,0,0,0, memoField.text, 0)
return app.operationBuilder.transfer(senderPicker.account.id, recipientPicker.account.id,
amountField.value * amountField.precisionAdjustment,
@@ -56,10 +55,18 @@ FormBase {
placeholderText: qsTr("Recipient")
layoutDirection: Qt.RightToLeft
}
- TextField {
- id: memoField
+ RowLayout {
Layout.fillWidth: true
- placeholderText: qsTr("Memo")
+ TextField {
+ id: memoField
+ Layout.fillWidth: true
+ placeholderText: qsTr("Memo")
+ }
+ CheckBox {
+ id: encryptMemoField
+ text: qsTr("Encrypt Memo")
+ checked: true
+ }
}
RowLayout {
Layout.fillWidth: true
@@ -97,18 +104,25 @@ FormBase {
return qsTr("Fee:
") + amountField.maxBalance.type.formatAmount(operation().fee) + " CORE"
}
}
- Item { Layout.fillWidth: true }
- Button {
- text: qsTr("Cancel")
- onClicked: canceled({})
- }
- Button {
- id: transferButton
- text: !senderAccount ||
+ }
+ UnlockingFinishButtons {
+ id: finishLine
+ app: base.app
+ rightButtonText: {
+ return !senderAccount ||
!senderAccount.isLoaded ||
senderPicker.accountControlLevel >= 1? qsTr("Transfer") : qsTr("Propose")
- enabled: senderPicker.account && recipientPicker.account && senderPicker.account !== recipientPicker.account && amountField.value
- onClicked: completed([operation()])
+ }
+ rightButtonEnabled: senderPicker.account && recipientPicker.account && senderPicker.account !== recipientPicker.account && amountField.value
+ requiresUnlocking: encryptMemoField.checked
+ Layout.fillWidth: true
+
+ onLeftButtonClicked: canceled({})
+ onRightButtonClicked: {
+ var op = operation()
+ if (encryptMemoField.checked)
+ op.encryptMemo(app.wallet, app.model)
+ completed([op])
}
}
}
diff --git a/programs/light_client/qml/UnlockingFinishButtons.qml b/programs/light_client/qml/UnlockingFinishButtons.qml
new file mode 100644
index 00000000..b566ac4a
--- /dev/null
+++ b/programs/light_client/qml/UnlockingFinishButtons.qml
@@ -0,0 +1,50 @@
+import QtQuick 2.5
+import QtQuick.Controls 1.4
+import QtQuick.Layouts 1.2
+
+import "."
+
+import Graphene.Client 0.1
+
+RowLayout {
+ property string leftButtonText: qsTr("Cancel")
+ property string unlockButtonText: qsTr("Unlock")
+ property string rightButtonText: qsTr("Finish")
+ property bool leftButtonEnabled: true
+ property bool rightButtonEnabled: true
+ property bool requiresUnlocking: true
+ property GrapheneApplication app
+
+ signal leftButtonClicked
+ signal rightButtonClicked
+
+ Item { Layout.fillWidth: true }
+ Button {
+ text: leftButtonText
+ onClicked: leftButtonClicked()
+ }
+ TextField {
+ id: passwordField
+ property bool shown: requiresUnlocking && app.wallet.isLocked
+ property real desiredWidth: shown? Scaling.cm(4) : 0
+ Layout.preferredWidth: desiredWidth
+ echoMode: TextInput.Password
+ placeholderText: qsTr("Wallet password")
+ visible: desiredWidth > 0
+ onAccepted: rightButton.clicked()
+
+ Behavior on desiredWidth { NumberAnimation { duration: 200; easing.type: Easing.InOutQuad } }
+ }
+ Button {
+ id: rightButton
+ text: passwordField.shown? unlockButtonText : rightButtonText
+ enabled: rightButtonEnabled
+ onClicked: {
+ if (passwordField.visible)
+ return app.wallet.unlock(passwordField.text)
+
+ rightButtonClicked()
+ }
+ Behavior on implicitWidth { NumberAnimation {} }
+ }
+}
diff --git a/programs/light_client/qml/qml.qrc b/programs/light_client/qml/qml.qrc
index ae4c86f6..9d8847b5 100644
--- a/programs/light_client/qml/qml.qrc
+++ b/programs/light_client/qml/qml.qrc
@@ -6,6 +6,7 @@
TransactionConfirmationForm.qml
FormBox.qml
FormFlipper.qml
+ UnlockingFinishButtons.qml
Scaling.qml
Identicon.qml
AccountPicker.qml