Hide join group call for inactive groups.

This commit is contained in:
Alan Evans 2020-12-08 14:44:21 -04:00 committed by Greyson Parrelli
parent 944a180b68
commit 3949f4fd45
4 changed files with 72 additions and 38 deletions

View file

@ -2134,7 +2134,7 @@ public class ConversationActivity extends PassphraseRequiredActivity
joinGroupCallButton.setVisibility(hasActiveCall ? View.VISIBLE : View.GONE); joinGroupCallButton.setVisibility(hasActiveCall ? View.VISIBLE : View.GONE);
}); });
groupCallViewModel.canJoinGroupCall().observe(this, canJoin -> joinGroupCallButton.setText(canJoin ? R.string.ConversationActivity_join : R.string.ConversationActivity_full)); groupCallViewModel.groupCallHasCapacity().observe(this, hasCapacity -> joinGroupCallButton.setText(hasCapacity ? R.string.ConversationActivity_join : R.string.ConversationActivity_full));
} }
private void showStickerIntroductionTooltip() { private void showStickerIntroductionTooltip() {

View file

@ -50,15 +50,18 @@ public final class ConversationUpdateItem extends LinearLayout
private TextView body; private TextView body;
private TextView actionButton; private TextView actionButton;
private LiveRecipient sender;
private ConversationMessage conversationMessage; private ConversationMessage conversationMessage;
private Recipient conversationRecipient;
private Optional<MessageRecord> nextMessageRecord; private Optional<MessageRecord> nextMessageRecord;
private MessageRecord messageRecord; private MessageRecord messageRecord;
private LiveData<Spannable> displayBody; private LiveData<Spannable> displayBody;
private EventListener eventListener; private EventListener eventListener;
private final UpdateObserver updateObserver = new UpdateObserver(); private final UpdateObserver updateObserver = new UpdateObserver();
private final SenderObserver senderObserver = new SenderObserver();
private final PresentOnChange presentOnChange = new PresentOnChange();
private final RecipientObserverManager senderObserver = new RecipientObserverManager(presentOnChange);
private final RecipientObserverManager groupObserver = new RecipientObserverManager(presentOnChange);
public ConversationUpdateItem(Context context) { public ConversationUpdateItem(Context context) {
super(context); super(context);
@ -91,7 +94,7 @@ public final class ConversationUpdateItem extends LinearLayout
{ {
this.batchSelected = batchSelected; this.batchSelected = batchSelected;
bind(lifecycleOwner, conversationMessage, nextMessageRecord); bind(lifecycleOwner, conversationMessage, nextMessageRecord, conversationRecipient);
} }
@Override @Override
@ -106,20 +109,26 @@ public final class ConversationUpdateItem extends LinearLayout
private void bind(@NonNull LifecycleOwner lifecycleOwner, private void bind(@NonNull LifecycleOwner lifecycleOwner,
@NonNull ConversationMessage conversationMessage, @NonNull ConversationMessage conversationMessage,
@NonNull Optional<MessageRecord> nextMessageRecord) @NonNull Optional<MessageRecord> nextMessageRecord,
@NonNull Recipient conversationRecipient)
{ {
this.conversationMessage = conversationMessage; this.conversationMessage = conversationMessage;
this.messageRecord = conversationMessage.getMessageRecord(); this.messageRecord = conversationMessage.getMessageRecord();
this.nextMessageRecord = nextMessageRecord; this.nextMessageRecord = nextMessageRecord;
this.conversationRecipient = conversationRecipient;
observeSender(lifecycleOwner, messageRecord.getIndividualRecipient()); senderObserver.observe(lifecycleOwner, messageRecord.getIndividualRecipient());
if (conversationRecipient.isActiveGroup() && conversationMessage.getMessageRecord().isGroupCall()) {
groupObserver.observe(lifecycleOwner, conversationRecipient);
} else {
groupObserver.observe(lifecycleOwner, null);
}
UpdateDescription updateDescription = Objects.requireNonNull(messageRecord.getUpdateDisplayBody(getContext())); UpdateDescription updateDescription = Objects.requireNonNull(messageRecord.getUpdateDisplayBody(getContext()));
LiveData<Spannable> liveUpdateMessage = LiveUpdateMessage.fromMessageDescription(getContext(), updateDescription, ContextCompat.getColor(getContext(), R.color.conversation_item_update_text_color)); LiveData<Spannable> liveUpdateMessage = LiveUpdateMessage.fromMessageDescription(getContext(), updateDescription, ContextCompat.getColor(getContext(), R.color.conversation_item_update_text_color));
LiveData<Spannable> spannableMessage = loading(liveUpdateMessage); LiveData<Spannable> spannableMessage = loading(liveUpdateMessage);
present(conversationMessage, nextMessageRecord);
observeDisplayBody(lifecycleOwner, spannableMessage); observeDisplayBody(lifecycleOwner, spannableMessage);
} }
@ -132,16 +141,31 @@ public final class ConversationUpdateItem extends LinearLayout
public void unbind() { public void unbind() {
} }
private void observeSender(@NonNull LifecycleOwner lifecycleOwner, @Nullable Recipient recipient) { static final class RecipientObserverManager {
if (sender != null) {
sender.getLiveData().removeObserver(senderObserver); private final Observer<Recipient> recipientObserver;
private LiveRecipient recipient;
RecipientObserverManager(@NonNull Observer<Recipient> observer){
this.recipientObserver = observer;
}
public void observe(@NonNull LifecycleOwner lifecycleOwner, @Nullable Recipient recipient) {
if (this.recipient != null) {
this.recipient.getLiveData().removeObserver(recipientObserver);
} }
if (recipient != null) { if (recipient != null) {
sender = recipient.live(); this.recipient = recipient.live();
sender.getLiveData().observe(lifecycleOwner, senderObserver); this.recipient.getLiveData().observe(lifecycleOwner, recipientObserver);
} else { } else {
sender = null; this.recipient = null;
}
}
@NonNull Recipient getObservedRecipient() {
return recipient.get();
} }
} }
@ -168,7 +192,7 @@ public final class ConversationUpdateItem extends LinearLayout
} }
} }
private void present(ConversationMessage conversationMessage, @NonNull Optional<MessageRecord> nextMessageRecord) { private void present(ConversationMessage conversationMessage, @NonNull Optional<MessageRecord> nextMessageRecord, @NonNull Recipient conversationRecipient) {
if (batchSelected.contains(conversationMessage)) setSelected(true); if (batchSelected.contains(conversationMessage)) setSelected(true);
else setSelected(false); else setSelected(false);
@ -195,7 +219,7 @@ public final class ConversationUpdateItem extends LinearLayout
} }
} }
if (text != 0) { if (text != 0 && conversationRecipient.isGroup() && conversationRecipient.isActiveGroup()) {
actionButton.setText(text); actionButton.setText(text);
actionButton.setVisibility(VISIBLE); actionButton.setVisibility(VISIBLE);
actionButton.setOnClickListener(v -> { actionButton.setOnClickListener(v -> {
@ -218,11 +242,14 @@ public final class ConversationUpdateItem extends LinearLayout
super.setOnClickListener(new InternalClickListener(l)); super.setOnClickListener(new InternalClickListener(l));
} }
private final class SenderObserver implements Observer<Recipient> { private final class PresentOnChange implements Observer<Recipient> {
@Override @Override
public void onChanged(Recipient recipient) { public void onChanged(Recipient recipient) {
present(conversationMessage, nextMessageRecord); if (recipient.getId() == conversationRecipient.getId()) {
conversationRecipient = recipient;
}
present(conversationMessage, nextMessageRecord, conversationRecipient);
} }
} }
@ -253,7 +280,7 @@ public final class ConversationUpdateItem extends LinearLayout
return; return;
} }
final Recipient sender = ConversationUpdateItem.this.sender.get(); final Recipient sender = ConversationUpdateItem.this.senderObserver.getObservedRecipient();
IdentityUtil.getRemoteIdentityKey(getContext(), sender).addListener(new ListenableFuture.Listener<Optional<IdentityRecord>>() { IdentityUtil.getRemoteIdentityKey(getContext(), sender).addListener(new ListenableFuture.Listener<Optional<IdentityRecord>>() {
@Override @Override

View file

@ -16,6 +16,7 @@ import org.thoughtcrime.securesms.recipients.Recipient;
import org.thoughtcrime.securesms.ringrtc.RemotePeer; import org.thoughtcrime.securesms.ringrtc.RemotePeer;
import org.thoughtcrime.securesms.service.WebRtcCallService; import org.thoughtcrime.securesms.service.WebRtcCallService;
import org.thoughtcrime.securesms.util.FeatureFlags; import org.thoughtcrime.securesms.util.FeatureFlags;
import org.thoughtcrime.securesms.util.livedata.LiveDataUtil;
import java.util.Objects; import java.util.Objects;
@ -23,31 +24,37 @@ public class GroupCallViewModel extends ViewModel {
private static final String TAG = Log.tag(GroupCallViewModel.class); private static final String TAG = Log.tag(GroupCallViewModel.class);
private final MutableLiveData<Boolean> activeGroupCall; private final MutableLiveData<Boolean> activeGroup;
private final MutableLiveData<Boolean> canJoin; private final MutableLiveData<Boolean> ongoingGroupCall;
private final LiveData<Boolean> activeGroupCall;
private final MutableLiveData<Boolean> groupCallHasCapacity;
private @Nullable Recipient currentRecipient; private @Nullable Recipient currentRecipient;
GroupCallViewModel() { GroupCallViewModel() {
this.activeGroupCall = new MutableLiveData<>(false); this.activeGroup = new MutableLiveData<>(false);
this.canJoin = new MutableLiveData<>(false); this.ongoingGroupCall = new MutableLiveData<>(false);
this.groupCallHasCapacity = new MutableLiveData<>(false);
this.activeGroupCall = LiveDataUtil.combineLatest(activeGroup, ongoingGroupCall, (active, ongoing) -> active && ongoing);
} }
public @NonNull LiveData<Boolean> hasActiveGroupCall() { public @NonNull LiveData<Boolean> hasActiveGroupCall() {
return activeGroupCall; return activeGroupCall;
} }
public @NonNull LiveData<Boolean> canJoinGroupCall() { public @NonNull LiveData<Boolean> groupCallHasCapacity() {
return canJoin; return groupCallHasCapacity;
} }
public void onRecipientChange(@NonNull Context context, @Nullable Recipient recipient) { public void onRecipientChange(@NonNull Context context, @Nullable Recipient recipient) {
activeGroup.postValue(recipient != null && recipient.isActiveGroup());
if (Objects.equals(currentRecipient, recipient)) { if (Objects.equals(currentRecipient, recipient)) {
return; return;
} }
activeGroupCall.postValue(false); ongoingGroupCall.postValue(false);
canJoin.postValue(false); groupCallHasCapacity.postValue(false);
currentRecipient = recipient; currentRecipient = recipient;
@ -67,10 +74,10 @@ public class GroupCallViewModel extends ViewModel {
public void onGroupCallPeekEvent(@NonNull GroupCallPeekEvent groupCallPeekEvent) { public void onGroupCallPeekEvent(@NonNull GroupCallPeekEvent groupCallPeekEvent) {
if (isGroupCallCapable(currentRecipient) && groupCallPeekEvent.getGroupRecipientId().equals(currentRecipient.getId())) { if (isGroupCallCapable(currentRecipient) && groupCallPeekEvent.getGroupRecipientId().equals(currentRecipient.getId())) {
Log.i(TAG, "update UI with call event: active call: " + groupCallPeekEvent.hasActiveCall() + " canJoin: " + groupCallPeekEvent.canJoinCall()); Log.i(TAG, "update UI with call event: ongoing call: " + groupCallPeekEvent.isOngoing() + " hasCapacity: " + groupCallPeekEvent.callHasCapacity());
activeGroupCall.postValue(groupCallPeekEvent.hasActiveCall()); ongoingGroupCall.postValue(groupCallPeekEvent.isOngoing());
canJoin.postValue(groupCallPeekEvent.canJoinCall()); groupCallHasCapacity.postValue(groupCallPeekEvent.callHasCapacity());
} else { } else {
Log.i(TAG, "Ignore call event for different recipient."); Log.i(TAG, "Ignore call event for different recipient.");
} }

View file

@ -22,11 +22,11 @@ public final class GroupCallPeekEvent {
return groupRecipientId; return groupRecipientId;
} }
public boolean hasActiveCall() { public boolean isOngoing() {
return eraId != null && deviceCount > 0; return eraId != null && deviceCount > 0;
} }
public boolean canJoinCall() { public boolean callHasCapacity() {
return hasActiveCall() && deviceCount < deviceLimit; return isOngoing() && deviceCount < deviceLimit;
} }
} }