added snackbar to indicate smp. more error handling in verify activity

iNPUTmice created

Change summary

src/main/java/eu/siacs/conversations/entities/Conversation.java   |   4 
src/main/java/eu/siacs/conversations/ui/ConversationFragment.java | 125 
src/main/java/eu/siacs/conversations/ui/VerifyOTRActivity.java    | 128 
src/main/res/layout/activity_verify_otr.xml                       |  12 
src/main/res/values/strings.xml                                   |   2 
5 files changed, 158 insertions(+), 113 deletions(-)

Detailed changes

src/main/java/eu/siacs/conversations/ui/ConversationFragment.java 🔗

@@ -35,7 +35,6 @@ import net.java.otr4j.session.SessionStatus;
 
 import java.util.ArrayList;
 import java.util.List;
-import java.util.Set;
 import java.util.concurrent.ConcurrentLinkedQueue;
 
 import eu.siacs.conversations.R;
@@ -53,7 +52,6 @@ import eu.siacs.conversations.ui.XmppActivity.OnValueEdited;
 import eu.siacs.conversations.ui.adapter.MessageAdapter;
 import eu.siacs.conversations.ui.adapter.MessageAdapter.OnContactPictureClicked;
 import eu.siacs.conversations.ui.adapter.MessageAdapter.OnContactPictureLongClicked;
-import eu.siacs.conversations.utils.UIHelper;
 import eu.siacs.conversations.xmpp.jid.Jid;
 
 public class ConversationFragment extends Fragment {
@@ -146,6 +144,19 @@ public class ConversationFragment extends Fragment {
 			}
 		}
 	};
+	protected OnClickListener clickToVerify = new OnClickListener() {
+
+		@Override
+		public void onClick(View v) {
+			if (conversation.getOtrFingerprint() != null) {
+				Intent intent = new Intent(getActivity(), VerifyOTRActivity.class);
+				intent.setAction(VerifyOTRActivity.ACTION_VERIFY_CONTACT);
+				intent.putExtra("contact", conversation.getContact().getJid().toBareJid().toString());
+				intent.putExtra("account", conversation.getAccount().getJid().toBareJid().toString());
+				startActivity(intent);
+			}
+		}
+	};
 	private ConcurrentLinkedQueue<Message> mEncryptedMessages = new ConcurrentLinkedQueue<>();
 	private boolean mDecryptJobRunning = false;
 	private OnEditorActionListener mEditorActionListener = new OnEditorActionListener() {
@@ -296,7 +307,7 @@ public class ConversationFragment extends Fragment {
 											.getConversation());
 								}
 							}
-						}  else {
+						} else {
 							Account account = message.getConversation().getAccount();
 							Intent intent = new Intent(activity, EditAccountActivity.class);
 							intent.putExtra("jid", account.getJid().toBareJid().toString());
@@ -505,6 +516,39 @@ public class ConversationFragment extends Fragment {
 								activity.switchToContactDetails(contact);
 							}
 						});
+			} else if (conversation.getMode() == Conversation.MODE_SINGLE) {
+				makeFingerprintWarning();
+			} else if (!conversation.getMucOptions().online()
+					&& conversation.getAccount().getStatus() == Account.STATUS_ONLINE) {
+				int error = conversation.getMucOptions().getError();
+				switch (error) {
+					case MucOptions.ERROR_NICK_IN_USE:
+						showSnackbar(R.string.nick_in_use, R.string.edit,
+								clickToMuc);
+						break;
+					case MucOptions.ERROR_ROOM_NOT_FOUND:
+						showSnackbar(R.string.conference_not_found,
+								R.string.leave, leaveMuc);
+						break;
+					case MucOptions.ERROR_PASSWORD_REQUIRED:
+						showSnackbar(R.string.conference_requires_password,
+								R.string.enter_password, enterPassword);
+						break;
+					case MucOptions.ERROR_BANNED:
+						showSnackbar(R.string.conference_banned,
+								R.string.leave, leaveMuc);
+						break;
+					case MucOptions.ERROR_MEMBERS_ONLY:
+						showSnackbar(R.string.conference_members_only,
+								R.string.leave, leaveMuc);
+						break;
+					case MucOptions.KICKED_FROM_ROOM:
+						showSnackbar(R.string.conference_kicked, R.string.join,
+								joinMuc);
+						break;
+					default:
+						break;
+				}
 			}
 			for (Message message : this.conversation.getMessages()) {
 				if (message.getEncryption() == Message.ENCRYPTION_PGP
@@ -526,44 +570,6 @@ public class ConversationFragment extends Fragment {
 				updateStatusMessages();
 			}
 			this.messageListAdapter.notifyDataSetChanged();
-			if (conversation.getMode() == Conversation.MODE_SINGLE) {
-				if (messageList.size() >= 1) {
-					makeFingerprintWarning();
-				}
-			} else {
-				if (!conversation.getMucOptions().online()
-						&& conversation.getAccount().getStatus() == Account.STATUS_ONLINE) {
-					int error = conversation.getMucOptions().getError();
-					switch (error) {
-						case MucOptions.ERROR_NICK_IN_USE:
-							showSnackbar(R.string.nick_in_use, R.string.edit,
-									clickToMuc);
-							break;
-						case MucOptions.ERROR_ROOM_NOT_FOUND:
-							showSnackbar(R.string.conference_not_found,
-									R.string.leave, leaveMuc);
-							break;
-						case MucOptions.ERROR_PASSWORD_REQUIRED:
-							showSnackbar(R.string.conference_requires_password,
-									R.string.enter_password, enterPassword);
-							break;
-						case MucOptions.ERROR_BANNED:
-							showSnackbar(R.string.conference_banned,
-									R.string.leave, leaveMuc);
-							break;
-						case MucOptions.ERROR_MEMBERS_ONLY:
-							showSnackbar(R.string.conference_members_only,
-									R.string.leave, leaveMuc);
-							break;
-						case MucOptions.KICKED_FROM_ROOM:
-							showSnackbar(R.string.conference_kicked, R.string.join,
-									joinMuc);
-							break;
-						default:
-							break;
-					}
-				}
-			}
 			updateChatMsgHint();
 			if (!activity.isConversationsOverviewVisable() || !activity.isConversationsOverviewHideable()) {
 				activity.xmppConnectionService.markRead(conversation, true);
@@ -680,24 +686,11 @@ public class ConversationFragment extends Fragment {
 	}
 
 	protected void makeFingerprintWarning() {
-		if (conversation.hasValidOtrSession()
-				&& (!conversation.isMuted())
-				&& (conversation.getOtrSession().getSessionStatus() == SessionStatus.ENCRYPTED)
+		if (conversation.smpRequested()) {
+			showSnackbar(R.string.smp_requested, R.string.verify, clickToVerify);
+		} else if (conversation.hasValidOtrSession() && (conversation.getOtrSession().getSessionStatus() == SessionStatus.ENCRYPTED)
 				&& (!conversation.isOtrFingerprintVerified())) {
-			showSnackbar(R.string.unknown_otr_fingerprint, R.string.verify,
-					new OnClickListener() {
-
-						@Override
-						public void onClick(View v) {
-							if (conversation.getOtrFingerprint() != null) {
-								Intent intent = new Intent(getActivity(),VerifyOTRActivity.class);
-								intent.setAction(VerifyOTRActivity.ACTION_VERIFY_CONTACT);
-								intent.putExtra("contact",conversation.getContact().getJid().toBareJid().toString());
-								intent.putExtra("account",conversation.getAccount().getJid().toBareJid().toString());
-								startActivity(intent);
-							}
-						}
-					});
+			showSnackbar(R.string.unknown_otr_fingerprint, R.string.verify, clickToVerify);
 		}
 	}
 
@@ -824,15 +817,15 @@ public class ConversationFragment extends Fragment {
 		final ConversationActivity activity = (ConversationActivity) getActivity();
 		final XmppConnectionService xmppService = activity.xmppConnectionService;
 		activity.selectPresence(message.getConversation(),
-			new OnPresenceSelected() {
+				new OnPresenceSelected() {
 
-				@Override
-				public void onPresenceSelected() {
-					message.setCounterpart(conversation.getNextCounterpart());
-					xmppService.sendMessage(message);
-					messageSent();
-				}
-			});
+					@Override
+					public void onPresenceSelected() {
+						message.setCounterpart(conversation.getNextCounterpart());
+						xmppService.sendMessage(message);
+						messageSent();
+					}
+				});
 	}
 
 	public void appendText(String text) {

src/main/java/eu/siacs/conversations/ui/VerifyOTRActivity.java 🔗

@@ -7,6 +7,7 @@ import android.view.View;
 import android.widget.Button;
 import android.widget.EditText;
 import android.widget.ImageView;
+import android.widget.RelativeLayout;
 import android.widget.TextView;
 import android.widget.Toast;
 
@@ -27,6 +28,9 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 
 	public static final String ACTION_VERIFY_CONTACT = "verify_contact";
 
+	private RelativeLayout mVerificationAreaOne;
+	private RelativeLayout mVerificationAreaTwo;
+	private TextView mErrorNoSession;
 	private TextView mRemoteJid;
 	private TextView mRemoteFingerprint;
 	private TextView mYourFingerprint;
@@ -38,6 +42,16 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 	private TextView mStatusMessage;
 	private Account mAccount;
 	private Conversation mConversation;
+
+	private View.OnClickListener mVerifyFingerprintListener = new View.OnClickListener() {
+
+		@Override
+		public void onClick(View view) {
+			mConversation.verifyOtrFingerprint();
+			finish();
+		}
+	};
+
 	private View.OnClickListener mCreateSharedSecretListener = new View.OnClickListener() {
 		@Override
 		public void onClick(final View view) {
@@ -53,6 +67,7 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 		@Override
 		public void onClick(View view) {
 			abortSmp();
+			updateView();
 		}
 	};
 	private View.OnClickListener mRespondSharedSecretListener = new View.OnClickListener() {
@@ -103,6 +118,8 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 			try {
 				session.abortSmp();
 				mConversation.smp().status = Conversation.Smp.STATUS_NONE;
+				mConversation.smp().hint = null;
+				mConversation.smp().secret = null;
 				return true;
 			} catch (OtrException e) {
 				return false;
@@ -156,53 +173,67 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 	}
 
 	protected void updateView() {
-		this.mYourFingerprint.setText(this.mAccount.getOtrFingerprint(xmppConnectionService));
-		this.mRemoteFingerprint.setText(this.mConversation.getOtrFingerprint());
-		this.mRemoteJid.setText(this.mConversation.getContact().getJid().toBareJid().toString());
-		Conversation.Smp smp = mConversation.smp();
-		Session session = mConversation.getOtrSession();
-		if (smp.status == Conversation.Smp.STATUS_NONE) {
-			activateButton(mButtonSharedSecretPositive, R.string.create, mCreateSharedSecretListener);
-			deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
-			this.mSharedSecretHint.setFocusableInTouchMode(true);
-			this.mSharedSecretSecret.setFocusableInTouchMode(true);
-			this.mSharedSecretSecret.setText("");
-			this.mSharedSecretHint.setText("");
-			this.mSharedSecretHint.setVisibility(View.VISIBLE);
-			this.mSharedSecretSecret.setVisibility(View.VISIBLE);
-			this.mStatusMessage.setVisibility(View.GONE);
-		} else if (smp.status == Conversation.Smp.STATUS_CONTACT_REQUESTED) {
-			this.mSharedSecretHint.setFocusable(false);
-			this.mSharedSecretHint.setText(smp.hint);
-			this.mSharedSecretSecret.setFocusableInTouchMode(true);
-			this.mSharedSecretHint.setVisibility(View.VISIBLE);
-			this.mSharedSecretSecret.setVisibility(View.VISIBLE);
-			this.mStatusMessage.setVisibility(View.GONE);
-			deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
-			activateButton(mButtonSharedSecretPositive, R.string.respond, mRespondSharedSecretListener);
-		} else if (smp.status == Conversation.Smp.STATUS_FAILED) {
-			activateButton(mButtonSharedSecretNegative, R.string.cancel, mFinishListener);
-			activateButton(mButtonSharedSecretPositive, R.string.try_again, mRetrySharedSecretListener);
-			this.mSharedSecretHint.setVisibility(View.GONE);
-			this.mSharedSecretSecret.setVisibility(View.GONE);
-			this.mStatusMessage.setVisibility(View.VISIBLE);
-			this.mStatusMessage.setText(R.string.secrets_do_not_match);
-			this.mStatusMessage.setTextColor(getWarningTextColor());
-		} else if (smp.status == Conversation.Smp.STATUS_VERIFIED) {
-			this.mSharedSecretHint.setVisibility(View.GONE);
-			this.mSharedSecretSecret.setVisibility(View.GONE);
-			this.mStatusMessage.setVisibility(View.VISIBLE);
-			this.mStatusMessage.setText(R.string.verified);
-			this.mStatusMessage.setTextColor(getPrimaryColor());
-			deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
-			activateButton(mButtonSharedSecretPositive, R.string.finish, mFinishListener);
-		} else if (session != null && session.isSmpInProgress()) {
-			deactivateButton(mButtonSharedSecretPositive,R.string.in_progress);
-			activateButton(mButtonSharedSecretNegative,R.string.cancel,mCancelSharedSecretListener);
-			this.mSharedSecretHint.setVisibility(View.VISIBLE);
-			this.mSharedSecretSecret.setVisibility(View.VISIBLE);
-			this.mSharedSecretHint.setFocusable(false);
-			this.mSharedSecretSecret.setFocusable(false);
+		if (this.mConversation.hasValidOtrSession()) {
+			this.mVerificationAreaOne.setVisibility(View.VISIBLE);
+			this.mVerificationAreaTwo.setVisibility(View.VISIBLE);
+			this.mErrorNoSession.setVisibility(View.GONE);
+			this.mYourFingerprint.setText(this.mAccount.getOtrFingerprint(xmppConnectionService));
+			this.mRemoteFingerprint.setText(this.mConversation.getOtrFingerprint());
+			this.mRemoteJid.setText(this.mConversation.getContact().getJid().toBareJid().toString());
+			Conversation.Smp smp = mConversation.smp();
+			Session session = mConversation.getOtrSession();
+			if (mConversation.isOtrFingerprintVerified()) {
+				deactivateButton(mButtonVerifyFingerprint, R.string.verified);
+			} else {
+				activateButton(mButtonVerifyFingerprint, R.string.verify, mVerifyFingerprintListener);
+			}
+			if (smp.status == Conversation.Smp.STATUS_NONE) {
+				activateButton(mButtonSharedSecretPositive, R.string.create, mCreateSharedSecretListener);
+				deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
+				this.mSharedSecretHint.setFocusableInTouchMode(true);
+				this.mSharedSecretSecret.setFocusableInTouchMode(true);
+				this.mSharedSecretSecret.setText("");
+				this.mSharedSecretHint.setText("");
+				this.mSharedSecretHint.setVisibility(View.VISIBLE);
+				this.mSharedSecretSecret.setVisibility(View.VISIBLE);
+				this.mStatusMessage.setVisibility(View.GONE);
+			} else if (smp.status == Conversation.Smp.STATUS_CONTACT_REQUESTED) {
+				this.mSharedSecretHint.setFocusable(false);
+				this.mSharedSecretHint.setText(smp.hint);
+				this.mSharedSecretSecret.setFocusableInTouchMode(true);
+				this.mSharedSecretHint.setVisibility(View.VISIBLE);
+				this.mSharedSecretSecret.setVisibility(View.VISIBLE);
+				this.mStatusMessage.setVisibility(View.GONE);
+				deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
+				activateButton(mButtonSharedSecretPositive, R.string.respond, mRespondSharedSecretListener);
+			} else if (smp.status == Conversation.Smp.STATUS_FAILED) {
+				activateButton(mButtonSharedSecretNegative, R.string.cancel, mFinishListener);
+				activateButton(mButtonSharedSecretPositive, R.string.try_again, mRetrySharedSecretListener);
+				this.mSharedSecretHint.setVisibility(View.GONE);
+				this.mSharedSecretSecret.setVisibility(View.GONE);
+				this.mStatusMessage.setVisibility(View.VISIBLE);
+				this.mStatusMessage.setText(R.string.secrets_do_not_match);
+				this.mStatusMessage.setTextColor(getWarningTextColor());
+			} else if (smp.status == Conversation.Smp.STATUS_VERIFIED) {
+				this.mSharedSecretHint.setVisibility(View.GONE);
+				this.mSharedSecretSecret.setVisibility(View.GONE);
+				this.mStatusMessage.setVisibility(View.VISIBLE);
+				this.mStatusMessage.setText(R.string.verified);
+				this.mStatusMessage.setTextColor(getPrimaryColor());
+				deactivateButton(mButtonSharedSecretNegative, R.string.cancel);
+				activateButton(mButtonSharedSecretPositive, R.string.finish, mFinishListener);
+			} else if (session != null && session.isSmpInProgress()) {
+				deactivateButton(mButtonSharedSecretPositive, R.string.in_progress);
+				activateButton(mButtonSharedSecretNegative, R.string.cancel, mCancelSharedSecretListener);
+				this.mSharedSecretHint.setVisibility(View.VISIBLE);
+				this.mSharedSecretSecret.setVisibility(View.VISIBLE);
+				this.mSharedSecretHint.setFocusable(false);
+				this.mSharedSecretSecret.setFocusable(false);
+			}
+		} else {
+			this.mVerificationAreaOne.setVisibility(View.GONE);
+			this.mVerificationAreaTwo.setVisibility(View.GONE);
+			this.mErrorNoSession.setVisibility(View.VISIBLE);
 		}
 	}
 
@@ -233,6 +264,9 @@ public class VerifyOTRActivity extends XmppActivity implements XmppConnectionSer
 		this.mSharedSecretSecret = (EditText) findViewById(R.id.shared_secret_secret);
 		this.mSharedSecretHint = (EditText) findViewById(R.id.shared_secret_hint);
 		this.mStatusMessage= (TextView) findViewById(R.id.status_message);
+		this.mVerificationAreaOne = (RelativeLayout) findViewById(R.id.verification_area_one);
+		this.mVerificationAreaTwo = (RelativeLayout) findViewById(R.id.verification_area_two);
+		this.mErrorNoSession = (TextView) findViewById(R.id.error_no_session);
 	}
 
 	@Override

src/main/res/layout/activity_verify_otr.xml 🔗

@@ -8,7 +8,18 @@
         android:layout_width="fill_parent"
         android:layout_height="wrap_content"
         android:orientation="vertical">
+        <TextView
+            android:id="@+id/error_no_session"
+            android:layout_margin="16dp"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="@string/no_otr_session_found"
+            android:layout_gravity="center_horizontal"
+            android:textColor="@color/primarytext"
+            android:textSize="?attr/TextSizeBody"
+            />
         <RelativeLayout
+            android:id="@+id/verification_area_one"
             android:layout_width="fill_parent"
             android:layout_height="fill_parent"
             android:background="@drawable/infocard_border"
@@ -90,6 +101,7 @@
             </LinearLayout>
         </RelativeLayout>
         <RelativeLayout
+            android:id="@+id/verification_area_two"
             android:layout_width="fill_parent"
             android:layout_height="wrap_content"
             android:layout_margin="8dp"

src/main/res/values/strings.xml 🔗

@@ -326,4 +326,6 @@
     <string name="try_again">Try again</string>;
     <string name="finish">Finish</string>
     <string name="verified">Verified!</string>
+    <string name="smp_requested">Contact requested SMP verification</string>
+    <string name="no_otr_session_found">No valid OTR session has been found!</string>
 </resources>