Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit bf48840e authored by Nivedita Sarkar's avatar Nivedita Sarkar Committed by Gerrit - the friendly Code Review server
Browse files

IMS-VT: Notify call substate/session modification per call

- Notify call substate changes and session modification cause
  for each call separately

- Maintain a map of current calls and the respective integer
  value to store call substate/session modifictaion cause to
  keep track on a per call basis and notify
  message controller per call. The toast message will display
  only for primary call

- This fixes issues when we have multiple calls and conference
  calls and we see incorrect toast messages

Change-Id: I2e675d950de349a03ac89be7d114c4dbd675504a
CRs-Fixed: 1044111
parent 017d2e5d
Loading
Loading
Loading
Loading
+62 −18
Original line number Diff line number Diff line
@@ -31,25 +31,25 @@ package com.android.incallui;
import org.codeaurora.ims.QtiCallConstants;
import android.os.Bundle;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.HashMap;
import java.util.List;

import com.google.common.base.Preconditions;
import com.android.incallui.InCallPresenter.InCallDetailsListener;

/**
 * This class listens to incoming events from the {@class InCallDetailsListener}.
 * When call details change, this class is notified and we parse the extras from the details to
 * When call details change, this class is notified and we parse the callExtras from the details to
 * figure out if call substate has changed and notify the {@class InCallMessageController} to
 * display the indication on UI.
 *
 */
public class CallSubstateNotifier implements InCallDetailsListener {
public class CallSubstateNotifier implements InCallDetailsListener, CallList.Listener {

    private final List<InCallSubstateListener> mCallSubstateListeners =
            new CopyOnWriteArrayList<>();

    private static CallSubstateNotifier sCallSubstateNotifier;
    private int mCallSubstate = QtiCallConstants.CALL_SUBSTATE_NONE;
    private final HashMap<String, Integer> mCallSubstateMap = new HashMap<>();

    /**
     * This method returns a singleton instance of {@class CallSubstateNotifier}
@@ -89,26 +89,70 @@ public class CallSubstateNotifier implements InCallDetailsListener {
    private CallSubstateNotifier() {
    }

    private int getCallSubstate(Bundle callExtras) {
        return callExtras.getInt(QtiCallConstants.CALL_SUBSTATE_EXTRA_KEY,
                QtiCallConstants.CALL_SUBSTATE_NONE);
    }

    /**
     * This method overrides onDetailsChanged method of {@class InCallDetailsListener}. We are
     * notified when call details change and extract the call substate from the extras, detect if
     * call substate changed and notify all registered listeners.
     * notified when call details change and extract the call substate from the callExtras, detect
     * if call substate changed and notify all registered listeners.
     */
    @Override
    public void onDetailsChanged(Call call, android.telecom.Call.Details details) {
        Log.d(this, "onDetailsChanged - call: " + call + "details: " + details);
        final Bundle extras =  (call != null && details != null) ? details.getExtras() : null;
        final int callSubstate = (extras != null) ? extras.getInt(
                QtiCallConstants.CALL_SUBSTATE_EXTRA_KEY,
                QtiCallConstants.CALL_SUBSTATE_NONE) :
                QtiCallConstants.CALL_SUBSTATE_NONE;

        if (callSubstate != mCallSubstate) {
            mCallSubstate = callSubstate;

        if (call == null || details == null ||
                !Call.State.isConnectingOrConnected(call.getState())) {
            Log.d(this, "onDetailsChanged - Call/details is null/Call is not connected. Return");
            return;
        }

        final Bundle callExtras = details.getExtras();

        if (callExtras == null) {
            return;
        }

        final String callId = call.getId();

        final int oldCallSubstate = mCallSubstateMap.containsKey(callId) ?
                mCallSubstateMap.get(callId) : QtiCallConstants.CALL_SUBSTATE_NONE;
        final int newCallSubstate = getCallSubstate(callExtras);

        if (oldCallSubstate == newCallSubstate) {
            return;
        }

        mCallSubstateMap.put(callId, newCallSubstate);
        Preconditions.checkNotNull(mCallSubstateListeners);
        for (InCallSubstateListener listener : mCallSubstateListeners) {
                listener.onCallSubstateChanged(call, mCallSubstate);
            listener.onCallSubstateChanged(call, newCallSubstate);
        }
    }

    /**
     * This method overrides onDisconnect method of {@interface CallList.Listener}
     */
    @Override
    public void onDisconnect(final Call call) {
        Log.d(this, "onDisconnect: call: " + call);
        mCallSubstateMap.remove(call.getId());
    }

    @Override
    public void onUpgradeToVideo(Call call) {
        //NO-OP
    }

    @Override
    public void onIncomingCall(Call call) {
        //NO-OP
    }

    @Override
    public void onCallListChange(CallList callList) {
        //NO-OP
    }
}
+4 −0
Original line number Diff line number Diff line
@@ -360,6 +360,8 @@ public class InCallPresenter implements CallList.Listener,
        OrientationModeHandler.getInstance().setUp();
        addDetailsListener(CallSubstateNotifier.getInstance());
        addDetailsListener(SessionModificationCauseNotifier.getInstance());
        CallList.getInstance().addListener(CallSubstateNotifier.getInstance());
        CallList.getInstance().addListener(SessionModificationCauseNotifier.getInstance());

        InCallZoomController.getInstance().setUp(mContext);
        Log.d(this, "Finished InCallPresenter.setUp");
@@ -391,6 +393,8 @@ public class InCallPresenter implements CallList.Listener,

        InCallZoomController.getInstance().tearDown();
        removeDetailsListener(SessionModificationCauseNotifier.getInstance());
        CallList.getInstance().removeListener(CallSubstateNotifier.getInstance());
        CallList.getInstance().removeListener(SessionModificationCauseNotifier.getInstance());
    }

    private void attemptFinishActivity() {
+58 −9
Original line number Diff line number Diff line
@@ -32,6 +32,7 @@ import android.os.Bundle;
import com.android.incallui.InCallPresenter.InCallDetailsListener;
import com.google.common.base.Preconditions;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.HashMap;
import java.util.List;

import org.codeaurora.ims.QtiCallConstants;
@@ -42,12 +43,13 @@ import org.codeaurora.ims.QtiCallConstants;
 * figure out if session modification cause has been sent when a call upgrades/downgrades and
 * notify the {@class InCallMessageController} to display the indication on UI.
 */
public class SessionModificationCauseNotifier implements InCallDetailsListener{
public class SessionModificationCauseNotifier implements InCallDetailsListener, CallList.Listener {

    private final List<InCallSessionModificationCauseListener> mSessionModificationCauseListeners
            = new CopyOnWriteArrayList<>();

    private static SessionModificationCauseNotifier sSessionModificationCauseNotifier;
    private final HashMap<String, Integer> mSessionModificationCauseMap = new HashMap<>();

    /**
     * Returns a singleton instance of {@class SessionModificationCauseNotifier}
@@ -87,6 +89,10 @@ public class SessionModificationCauseNotifier implements InCallDetailsListener{
    private SessionModificationCauseNotifier() {
    }

    private int getSessionModificationCause(Bundle callExtras) {
        return callExtras.getInt(QtiCallConstants.SESSION_MODIFICATION_CAUSE_EXTRA_KEY,
                QtiCallConstants.CAUSE_CODE_UNSPECIFIED);
    }
    /**
     * Overrides onDetailsChanged method of {@class InCallDetailsListener}. We are
     * notified when call details change and extract the session modification cause from the
@@ -95,18 +101,61 @@ public class SessionModificationCauseNotifier implements InCallDetailsListener{
    @Override
    public void onDetailsChanged(Call call, android.telecom.Call.Details details) {
        Log.d(this, "onDetailsChanged: - call: " + call + "details: " + details);
        final Bundle extras =  (call != null && details != null) ? details.getExtras() : null;
        final int sessionModificationCause = (extras != null) ? extras.getInt(
                QtiCallConstants.SESSION_MODIFICATION_CAUSE_EXTRA_KEY,
                QtiCallConstants.CAUSE_CODE_UNSPECIFIED) :
                QtiCallConstants.CAUSE_CODE_UNSPECIFIED;

        if (sessionModificationCause != QtiCallConstants.CAUSE_CODE_UNSPECIFIED) {
        if (call == null || details == null ||
                !Call.State.isConnectingOrConnected(call.getState())) {
            Log.d(this, "onDetailsChanged - Call/details is null/Call is not connected. Return");
            return;
        }

        final Bundle callExtras = details.getExtras();

        if (callExtras == null) {
            return;
        }

        final String callId = call.getId();

        final int oldSessionModificationCause = mSessionModificationCauseMap.containsKey(callId) ?
            mSessionModificationCauseMap.get(callId) : QtiCallConstants.CAUSE_CODE_UNSPECIFIED;
        final int newSessionModificationCause = getSessionModificationCause(callExtras);

        if (oldSessionModificationCause == newSessionModificationCause) {
            return;
        }

        mSessionModificationCauseMap.put(callId, newSessionModificationCause);
        // Notify all listeners only when there is a valid value
        if (newSessionModificationCause != QtiCallConstants.CAUSE_CODE_UNSPECIFIED) {
            Preconditions.checkNotNull(mSessionModificationCauseListeners);
            for (InCallSessionModificationCauseListener listener :
                mSessionModificationCauseListeners) {
                listener.onSessionModificationCauseChanged(call, sessionModificationCause);
                    listener.onSessionModificationCauseChanged(call, newSessionModificationCause);
            }
        }
    }

    /**
     * This method overrides onDisconnect method of {@interface CallList.Listener}
     */
    @Override
    public void onDisconnect(final Call call) {
        Log.d(this, "onDisconnect: call: " + call);
        mSessionModificationCauseMap.remove(call.getId());
    }

    @Override
    public void onUpgradeToVideo(Call call) {
        //NO-OP
    }

    @Override
    public void onIncomingCall(Call call) {
        //NO-OP
    }

    @Override
    public void onCallListChange(CallList callList) {
        //NO-OP
    }
}