diff --git a/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationActivity.java index 9b89740e3..852f82bff 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationActivity.java @@ -46,9 +46,11 @@ import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault; import org.briarproject.bramble.api.plugin.ConnectionRegistry; import org.briarproject.bramble.api.plugin.event.ContactConnectedEvent; import org.briarproject.bramble.api.plugin.event.ContactDisconnectedEvent; +import org.briarproject.bramble.api.sync.ClientId; import org.briarproject.bramble.api.sync.MessageId; import org.briarproject.bramble.api.sync.event.MessagesAckedEvent; import org.briarproject.bramble.api.sync.event.MessagesSentEvent; +import org.briarproject.bramble.api.versioning.event.ClientVersionUpdatedEvent; import org.briarproject.briar.R; import org.briarproject.briar.android.activity.ActivityComponent; import org.briarproject.briar.android.activity.BriarActivity; @@ -99,7 +101,6 @@ import javax.inject.Inject; import de.hdodenhof.circleimageview.CircleImageView; import im.delight.android.identicons.IdenticonDrawable; import uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt; -import uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.PromptStateChangeListener; import static android.arch.lifecycle.Lifecycle.State.STARTED; import static android.os.Build.VERSION.SDK_INT; @@ -130,8 +131,6 @@ import static org.briarproject.briar.android.util.UiUtils.getBulbTransitionName; import static org.briarproject.briar.android.util.UiUtils.observeOnce; import static org.briarproject.briar.api.messaging.MessagingConstants.MAX_ATTACHMENTS_PER_MESSAGE; import static org.briarproject.briar.api.messaging.MessagingConstants.MAX_PRIVATE_MESSAGE_TEXT_LENGTH; -import static uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.STATE_DISMISSED; -import static uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.STATE_FINISHED; @MethodsNotNullByDefault @ParametersNotNullByDefault @@ -263,11 +262,15 @@ public class ConversationActivity extends BriarActivity ImagePreview imagePreview = findViewById(R.id.imagePreview); sendController = new TextAttachmentController(textInputView, imagePreview, this, viewModel); - observeOnce(viewModel.hasImageSupport(), this, hasSupport -> { - if (hasSupport != null && hasSupport) { - // TODO: remove cast when removing feature flag - ((TextAttachmentController) sendController) - .setImagesSupported(); + viewModel.hasImageSupport().observe(this, new Observer() { + @Override + public void onChanged(@Nullable Boolean hasSupport) { + if (hasSupport != null && hasSupport) { + // TODO: remove cast when removing feature flag + ((TextAttachmentController) sendController) + .setImagesSupported(); + viewModel.hasImageSupport().removeObserver(this); + } } }); } else { @@ -649,6 +652,15 @@ public class ConversationActivity extends BriarActivity LOG.info("Contact disconnected"); displayContactOnlineStatus(); } + } else if (e instanceof ClientVersionUpdatedEvent) { + ClientVersionUpdatedEvent c = (ClientVersionUpdatedEvent) e; + if (c.getContactId().equals(contactId)) { + ClientId clientId = c.getClientVersion().getClientId(); + if (clientId.equals(MessagingManager.CLIENT_ID)) { + LOG.info("Contact's messaging client was updated"); + viewModel.recheckFeaturesAndOnboarding(contactId); + } + } } } @@ -829,9 +841,7 @@ public class ConversationActivity extends BriarActivity private void showImageOnboarding() { // TODO: remove cast when removing feature flag - ((TextAttachmentController) sendController) - .showImageOnboarding(this, () -> - viewModel.onImageOnboardingSeen()); + ((TextAttachmentController) sendController).showImageOnboarding(this); } private void showIntroductionOnboarding(@Nullable Boolean show) { @@ -865,11 +875,6 @@ public class ConversationActivity extends BriarActivity return; } - PromptStateChangeListener listener = (prompt, state) -> { - if (state == STATE_DISMISSED || state == STATE_FINISHED) { - viewModel.onIntroductionOnboardingSeen(); - } - }; new MaterialTapTargetPrompt.Builder(ConversationActivity.this, R.style.OnboardingDialogTheme).setTarget(target) .setPrimaryText(R.string.introduction_onboarding_title) @@ -877,7 +882,6 @@ public class ConversationActivity extends BriarActivity .setIcon(R.drawable.ic_more_vert_accent) .setBackgroundColour( ContextCompat.getColor(this, R.color.briar_primary)) - .setPromptStateChangeListener(listener) .show(); } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationViewModel.java b/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationViewModel.java index cb1c4128a..9886c9895 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationViewModel.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/conversation/ConversationViewModel.java @@ -231,47 +231,24 @@ public class ConversationViewModel extends AndroidViewModel boolean introductionSupported = contacts.size() > 1; showIntroductionAction.postValue(introductionSupported); + // we only show one onboarding dialog at a time Settings settings = settingsManager.getSettings(SETTINGS_NAMESPACE); if (imagesSupported && settings.getBoolean(SHOW_ONBOARDING_IMAGE, true)) { - // check if we should show onboarding, only if images are supported + onOnboardingShown(SHOW_ONBOARDING_IMAGE); showImageOnboarding.postEvent(true); - // allow observer to stop listening for changes - showIntroductionOnboarding.postEvent(false); - } else { - // allow observer to stop listening for changes - showImageOnboarding.postEvent(false); - // we only show one onboarding dialog at a time - if (introductionSupported && - settings.getBoolean(SHOW_ONBOARDING_INTRODUCTION, true)) { - showIntroductionOnboarding.postEvent(true); - } else { - // allow observer to stop listening for changes - showIntroductionOnboarding.postEvent(false); - } + } else if (introductionSupported && + settings.getBoolean(SHOW_ONBOARDING_INTRODUCTION, true)) { + onOnboardingShown(SHOW_ONBOARDING_INTRODUCTION); + showIntroductionOnboarding.postEvent(true); } } - @UiThread - void onImageOnboardingSeen() { - onOnboardingSeen(SHOW_ONBOARDING_IMAGE); - } - - @UiThread - void onIntroductionOnboardingSeen() { - onOnboardingSeen(SHOW_ONBOARDING_INTRODUCTION); - } - - private void onOnboardingSeen(String key) { - dbExecutor.execute(() -> { - try { - Settings settings = new Settings(); - settings.putBoolean(key, false); - settingsManager.mergeSettings(settings, SETTINGS_NAMESPACE); - } catch (DbException e) { - logException(LOG, WARNING, e); - } - }); + @DatabaseExecutor + private void onOnboardingShown(String key) throws DbException { + Settings settings = new Settings(); + settings.putBoolean(key, false); + settingsManager.mergeSettings(settings, SETTINGS_NAMESPACE); } private void createMessage(GroupId groupId, @Nullable String text, @@ -352,4 +329,14 @@ public class ConversationViewModel extends AndroidViewModel return addedHeader; } + @UiThread + void recheckFeaturesAndOnboarding(ContactId contactId) { + dbExecutor.execute(() -> { + try { + checkFeaturesAndOnboarding(contactId); + } catch (DbException e) { + logException(LOG, WARNING, e); + } + }); + } } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/view/TextAttachmentController.java b/briar-android/src/main/java/org/briarproject/briar/android/view/TextAttachmentController.java index 87cb9fb24..e2b89bdc1 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/view/TextAttachmentController.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/view/TextAttachmentController.java @@ -28,7 +28,6 @@ import java.util.Collection; import java.util.List; import uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt; -import uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.PromptStateChangeListener; import static android.arch.lifecycle.Lifecycle.State.DESTROYED; import static android.content.Intent.ACTION_GET_CONTENT; @@ -44,8 +43,6 @@ import static android.widget.Toast.LENGTH_LONG; import static org.briarproject.briar.android.util.UiUtils.resolveColorAttribute; import static org.briarproject.briar.api.messaging.MessagingConstants.IMAGE_MIME_TYPES; import static org.briarproject.briar.api.messaging.MessagingConstants.MAX_ATTACHMENTS_PER_MESSAGE; -import static uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.STATE_DISMISSED; -import static uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt.STATE_FINISHED; @UiThread @NotNullByDefault @@ -269,13 +266,7 @@ public class TextAttachmentController extends TextSendController reset(); } - public void showImageOnboarding(Activity activity, - Runnable onOnboardingSeen) { - PromptStateChangeListener listener = (prompt, state) -> { - if (state == STATE_DISMISSED || state == STATE_FINISHED) { - onOnboardingSeen.run(); - } - }; + public void showImageOnboarding(Activity activity) { int color = resolveColorAttribute(activity, R.attr.colorControlNormal); new MaterialTapTargetPrompt.Builder(activity, R.style.OnboardingDialogTheme).setTarget(sendButton) @@ -284,7 +275,6 @@ public class TextAttachmentController extends TextSendController .setBackgroundColour(getColor(activity, R.color.briar_primary)) .setIcon(R.drawable.ic_image) .setIconDrawableColourFilter(color) - .setPromptStateChangeListener(listener) .show(); }