use of android.telephony.ims.ImsCallProfile in project android_frameworks_opt_telephony by LineageOS.
the class ImsPhoneConnection method updateMediaCapabilities.
/**
* Check for a change in the video capabilities and audio quality for the {@link ImsCall}, and
* update the {@link ImsPhoneConnection} with this information.
*
* @param imsCall The call to check for changes in media capabilities.
* @return Whether the media capabilities have been changed.
*/
public boolean updateMediaCapabilities(ImsCall imsCall) {
if (imsCall == null) {
return false;
}
boolean changed = false;
try {
// The actual call profile (negotiated between local and peer).
ImsCallProfile negotiatedCallProfile = imsCall.getCallProfile();
if (negotiatedCallProfile != null) {
int oldVideoState = getVideoState();
int newVideoState = ImsCallProfile.getVideoStateFromImsCallProfile(negotiatedCallProfile);
if (oldVideoState != newVideoState) {
// unpaused state, we will resume passing the video states from the modem as is.
if (VideoProfile.isPaused(oldVideoState) && !VideoProfile.isPaused(newVideoState)) {
// Video entered un-paused state; recognize updates from now on; we want to
// ensure that the new un-paused state is propagated to Telecom, so change
// this now.
mShouldIgnoreVideoStateChanges = false;
}
if (!mShouldIgnoreVideoStateChanges) {
updateVideoState(newVideoState);
changed = true;
} else {
Rlog.d(LOG_TAG, "updateMediaCapabilities - ignoring video state change " + "due to paused state.");
}
if (!VideoProfile.isPaused(oldVideoState) && VideoProfile.isPaused(newVideoState)) {
// Video entered pause state; ignore updates until un-paused. We do this
// after setVideoState is called above to ensure Telecom is notified that
// the device has entered paused state.
mShouldIgnoreVideoStateChanges = true;
}
}
if (negotiatedCallProfile.mMediaProfile != null) {
mIsRttEnabledForCall = negotiatedCallProfile.mMediaProfile.isRttCall();
if (mIsRttEnabledForCall && mRttTextHandler == null) {
Rlog.d(LOG_TAG, "updateMediaCapabilities -- turning RTT on, profile=" + negotiatedCallProfile);
startRttTextProcessing();
onRttInitiated();
changed = true;
mOwner.getPhone().getVoiceCallSessionStats().onRttStarted(this);
} else if (!mIsRttEnabledForCall && mRttTextHandler != null) {
Rlog.d(LOG_TAG, "updateMediaCapabilities -- turning RTT off, profile=" + negotiatedCallProfile);
mRttTextHandler.tearDown();
mRttTextHandler = null;
mRttTextStream = null;
onRttTerminated();
changed = true;
}
}
}
// Check for a change in the capabilities for the call and update
// {@link ImsPhoneConnection} with this information.
int capabilities = getConnectionCapabilities();
// Use carrier config to determine if downgrading directly to audio-only is supported.
if (mOwner.isCarrierDowngradeOfVtCallSupported()) {
capabilities = addCapability(capabilities, Connection.Capability.SUPPORTS_DOWNGRADE_TO_VOICE_REMOTE | Capability.SUPPORTS_DOWNGRADE_TO_VOICE_LOCAL);
} else {
capabilities = removeCapability(capabilities, Connection.Capability.SUPPORTS_DOWNGRADE_TO_VOICE_REMOTE | Capability.SUPPORTS_DOWNGRADE_TO_VOICE_LOCAL);
}
// Get the current local call capabilities which might be voice or video or both.
ImsCallProfile localCallProfile = imsCall.getLocalCallProfile();
Rlog.v(LOG_TAG, "update localCallProfile=" + localCallProfile);
if (localCallProfile != null) {
capabilities = applyLocalCallCapabilities(localCallProfile, capabilities);
}
// Get the current remote call capabilities which might be voice or video or both.
ImsCallProfile remoteCallProfile = imsCall.getRemoteCallProfile();
Rlog.v(LOG_TAG, "update remoteCallProfile=" + remoteCallProfile);
if (remoteCallProfile != null) {
capabilities = applyRemoteCallCapabilities(remoteCallProfile, capabilities);
}
if (getConnectionCapabilities() != capabilities) {
setConnectionCapabilities(capabilities);
changed = true;
}
if (!mOwner.isViLteDataMetered()) {
Rlog.v(LOG_TAG, "data is not metered");
} else {
if (mImsVideoCallProviderWrapper != null) {
mImsVideoCallProviderWrapper.setIsVideoEnabled(hasCapabilities(Connection.Capability.SUPPORTS_VT_LOCAL_BIDIRECTIONAL));
}
}
// Metrics for audio codec
if (localCallProfile != null && localCallProfile.mMediaProfile.mAudioQuality != mAudioCodec) {
mAudioCodec = localCallProfile.mMediaProfile.mAudioQuality;
mMetrics.writeAudioCodecIms(mOwner.mPhone.getPhoneId(), imsCall.getCallSession());
mOwner.getPhone().getVoiceCallSessionStats().onAudioCodecChanged(this, mAudioCodec);
}
int newAudioQuality = getAudioQualityFromCallProfile(localCallProfile, remoteCallProfile);
if (getAudioQuality() != newAudioQuality) {
setAudioQuality(newAudioQuality);
changed = true;
}
} catch (ImsException e) {
// No session in place -- no change
}
return changed;
}
use of android.telephony.ims.ImsCallProfile in project android_frameworks_opt_telephony by LineageOS.
the class ImsPhoneConnection method updateAddressDisplay.
/**
* Check for a change in the address display related fields for the {@link ImsCall}, and
* update the {@link ImsPhoneConnection} with this information.
*
* @param imsCall The call to check for changes in address display fields.
* @return Whether the address display fields have been changed.
*/
public boolean updateAddressDisplay(ImsCall imsCall) {
if (imsCall == null) {
return false;
}
boolean changed = false;
ImsCallProfile callProfile = imsCall.getCallProfile();
if (callProfile != null && isIncoming()) {
// Only look for changes to the address for incoming calls. The originating identity
// can change for outgoing calls due to, for example, a call being forwarded to
// voicemail. This address change does not need to be presented to the user.
String address = callProfile.getCallExtra(ImsCallProfile.EXTRA_OI);
String name = callProfile.getCallExtra(ImsCallProfile.EXTRA_CNA);
int nump = ImsCallProfile.OIRToPresentation(callProfile.getCallExtraInt(ImsCallProfile.EXTRA_OIR));
int namep = ImsCallProfile.OIRToPresentation(callProfile.getCallExtraInt(ImsCallProfile.EXTRA_CNAP));
if (Phone.DEBUG_PHONE) {
Rlog.d(LOG_TAG, "updateAddressDisplay: callId = " + getTelecomCallId() + " address = " + Rlog.pii(LOG_TAG, address) + " name = " + Rlog.pii(LOG_TAG, name) + " nump = " + nump + " namep = " + namep);
}
if (!mIsMergeInProcess) {
// to the call address while a merge is in process.
if (!equalsBaseDialString(mAddress, address)) {
mAddress = address;
changed = true;
}
if (TextUtils.isEmpty(name)) {
if (!TextUtils.isEmpty(mCnapName)) {
mCnapName = "";
changed = true;
}
} else if (!name.equals(mCnapName)) {
mCnapName = name;
changed = true;
}
if (mNumberPresentation != nump) {
mNumberPresentation = nump;
changed = true;
}
if (mCnapNamePresentation != namep) {
mCnapNamePresentation = namep;
changed = true;
}
}
}
return changed;
}
use of android.telephony.ims.ImsCallProfile in project android_frameworks_opt_telephony by LineageOS.
the class ImsPhoneConnection method updateExtras.
/**
* Check for a change in call extras of {@link ImsCall}, and
* update the {@link ImsPhoneConnection} accordingly.
*
* @param imsCall The call to check for changes in extras.
* @return Whether the extras fields have been changed.
*/
boolean updateExtras(ImsCall imsCall) {
if (imsCall == null) {
return false;
}
final ImsCallProfile callProfile = imsCall.getCallProfile();
final Bundle extras = callProfile != null ? callProfile.mCallExtras : null;
if (extras == null && DBG) {
Rlog.d(LOG_TAG, "Call profile extras are null.");
}
final boolean changed = !areBundlesEqual(extras, mExtras);
if (changed) {
updateImsCallRatFromExtras(extras);
updateEmergencyCallFromExtras(extras);
mExtras.clear();
mExtras.putAll(extras);
setConnectionExtras(mExtras);
}
return changed;
}
use of android.telephony.ims.ImsCallProfile in project android_frameworks_opt_telephony by LineageOS.
the class ImsPhoneCallTracker method handleMessage.
// ****** Overridden from Handler
@Override
public void handleMessage(Message msg) {
AsyncResult ar;
if (DBG)
log("handleMessage what=" + msg.what);
switch(msg.what) {
case EVENT_HANGUP_PENDINGMO:
if (mPendingMO != null) {
mPendingMO.onDisconnect();
removeConnection(mPendingMO);
mPendingMO = null;
}
mPendingIntentExtras = null;
updatePhoneState();
mPhone.notifyPreciseCallStateChanged();
break;
case EVENT_RESUME_NOW_FOREGROUND_CALL:
try {
resumeForegroundCall();
} catch (ImsException e) {
if (Phone.DEBUG_PHONE) {
loge("handleMessage EVENT_RESUME_NOW_FOREGROUND_CALL exception=" + e);
}
}
break;
case EVENT_ANSWER_WAITING_CALL:
try {
answerWaitingCall();
} catch (ImsException e) {
if (Phone.DEBUG_PHONE) {
loge("handleMessage EVENT_ANSWER_WAITING_CALL exception=" + e);
}
}
break;
case EVENT_DIAL_PENDINGMO:
dialInternal(mPendingMO, mClirMode, mPendingCallVideoState, mPendingIntentExtras);
mPendingIntentExtras = null;
break;
case EVENT_EXIT_ECBM_BEFORE_PENDINGMO:
if (mPendingMO != null) {
// Send ECBM exit request
try {
getEcbmInterface().exitEmergencyCallbackMode();
mPhone.setOnEcbModeExitResponse(this, EVENT_EXIT_ECM_RESPONSE_CDMA, null);
pendingCallClirMode = mClirMode;
pendingCallInEcm = true;
} catch (ImsException e) {
e.printStackTrace();
mPendingMO.setDisconnectCause(DisconnectCause.ERROR_UNSPECIFIED);
sendEmptyMessageDelayed(EVENT_HANGUP_PENDINGMO, TIMEOUT_HANGUP_PENDINGMO);
}
}
break;
case EVENT_EXIT_ECM_RESPONSE_CDMA:
// no matter the result, we still do the same here
if (pendingCallInEcm) {
dialInternal(mPendingMO, pendingCallClirMode, mPendingCallVideoState, mPendingIntentExtras);
mPendingIntentExtras = null;
pendingCallInEcm = false;
}
mPhone.unsetOnEcbModeExitResponse(this);
break;
case EVENT_VT_DATA_USAGE_UPDATE:
ar = (AsyncResult) msg.obj;
ImsCall call = (ImsCall) ar.userObj;
Long usage = (long) ar.result;
log("VT data usage update. usage = " + usage + ", imsCall = " + call);
if (usage > 0) {
updateVtDataUsage(call, usage);
}
break;
case EVENT_DATA_ENABLED_CHANGED:
ar = (AsyncResult) msg.obj;
if (ar.result instanceof Pair) {
Pair<Boolean, Integer> p = (Pair<Boolean, Integer>) ar.result;
onDataEnabledChanged(p.first, p.second);
}
break;
case EVENT_CHECK_FOR_WIFI_HANDOVER:
if (msg.obj instanceof ImsCall) {
ImsCall imsCall = (ImsCall) msg.obj;
if (imsCall != mForegroundCall.getImsCall()) {
Rlog.i(LOG_TAG, "handoverCheck: no longer FG; check skipped.");
unregisterForConnectivityChanges();
// Handover check and its not the foreground call any more.
return;
}
if (!mHasAttemptedStartOfCallHandover) {
mHasAttemptedStartOfCallHandover = true;
}
if (!imsCall.isWifiCall()) {
// Call did not handover to wifi, notify of handover failure.
ImsPhoneConnection conn = findConnection(imsCall);
if (conn != null) {
Rlog.i(LOG_TAG, "handoverCheck: handover failed.");
conn.onHandoverToWifiFailed();
}
if (imsCall.isVideoCall() && conn.getDisconnectCause() == DisconnectCause.NOT_DISCONNECTED) {
registerForConnectivityChanges();
}
}
}
break;
case EVENT_ON_FEATURE_CAPABILITY_CHANGED:
{
SomeArgs args = (SomeArgs) msg.obj;
try {
ImsFeature.Capabilities capabilities = (ImsFeature.Capabilities) args.arg1;
handleFeatureCapabilityChanged(capabilities);
} finally {
args.recycle();
}
break;
}
case EVENT_SUPP_SERVICE_INDICATION:
{
ar = (AsyncResult) msg.obj;
ImsPhoneMmiCode mmiCode = new ImsPhoneMmiCode(mPhone);
try {
mmiCode.setIsSsInfo(true);
mmiCode.processImsSsData(ar);
} catch (ImsException e) {
Rlog.e(LOG_TAG, "Exception in parsing SS Data: " + e);
}
break;
}
case EVENT_REDIAL_WIFI_E911_CALL:
{
Pair<ImsCall, ImsReasonInfo> callInfo = (Pair<ImsCall, ImsReasonInfo>) ((AsyncResult) msg.obj).userObj;
removeMessages(EVENT_REDIAL_WIFI_E911_TIMEOUT);
mPhone.getDefaultPhone().mCi.unregisterForOn(this);
ImsPhoneConnection oldConnection = findConnection(callInfo.first);
if (oldConnection == null) {
sendCallStartFailedDisconnect(callInfo.first, callInfo.second);
break;
}
mForegroundCall.detach(oldConnection);
removeConnection(oldConnection);
try {
Connection newConnection = mPhone.getDefaultPhone().dial(mLastDialString, mLastDialArgs);
oldConnection.onOriginalConnectionReplaced(newConnection);
final ImsCall imsCall = mForegroundCall.getImsCall();
final ImsCallProfile callProfile = imsCall.getCallProfile();
/* update EXTRA_EMERGENCY_CALL for clients to infer
from this extra that the call is emergency call */
callProfile.setCallExtraBoolean(ImsCallProfile.EXTRA_EMERGENCY_CALL, true);
ImsPhoneConnection conn = findConnection(imsCall);
conn.updateExtras(imsCall);
} catch (CallStateException e) {
sendCallStartFailedDisconnect(callInfo.first, callInfo.second);
}
break;
}
case EVENT_REDIAL_WIFI_E911_TIMEOUT:
{
Pair<ImsCall, ImsReasonInfo> callInfo = (Pair<ImsCall, ImsReasonInfo>) msg.obj;
mPhone.getDefaultPhone().mCi.unregisterForOn(this);
removeMessages(EVENT_REDIAL_WIFI_E911_CALL);
sendCallStartFailedDisconnect(callInfo.first, callInfo.second);
break;
}
case EVENT_REDIAL_WITHOUT_RTT:
{
Pair<ImsCall, ImsReasonInfo> callInfo = (Pair<ImsCall, ImsReasonInfo>) msg.obj;
removeMessages(EVENT_REDIAL_WITHOUT_RTT);
ImsPhoneConnection oldConnection = findConnection(callInfo.first);
if (oldConnection == null) {
sendCallStartFailedDisconnect(callInfo.first, callInfo.second);
break;
}
mForegroundCall.detach(oldConnection);
removeConnection(oldConnection);
try {
mPendingMO = null;
ImsDialArgs newDialArgs = ImsDialArgs.Builder.from(mLastDialArgs).setRttTextStream(null).setRetryCallFailCause(ImsReasonInfo.CODE_RETRY_ON_IMS_WITHOUT_RTT).setRetryCallFailNetworkType(ServiceState.rilRadioTechnologyToNetworkType(oldConnection.getCallRadioTech())).build();
Connection newConnection = mPhone.getDefaultPhone().dial(mLastDialString, newDialArgs);
oldConnection.onOriginalConnectionReplaced(newConnection);
} catch (CallStateException e) {
sendCallStartFailedDisconnect(callInfo.first, callInfo.second);
}
break;
}
}
}
use of android.telephony.ims.ImsCallProfile in project android_frameworks_opt_telephony by LineageOS.
the class TelephonyTester method testImsECall.
void testImsECall() {
// Attempt to get the active IMS call before parsing the test XML file.
ImsPhone imsPhone = (ImsPhone) mPhone;
if (imsPhone == null) {
return;
}
ImsPhoneCall imsPhoneCall = imsPhone.getForegroundCall();
if (imsPhoneCall == null) {
return;
}
ImsCall imsCall = imsPhoneCall.getImsCall();
if (imsCall == null) {
return;
}
ImsCallProfile callProfile = imsCall.getCallProfile();
Bundle extras = callProfile.getCallExtras();
if (extras == null) {
extras = new Bundle();
}
extras.putBoolean(ImsCallProfile.EXTRA_EMERGENCY_CALL, true);
callProfile.mCallExtras = extras;
imsCall.getImsCallSessionListenerProxy().callSessionUpdated(imsCall.getSession(), callProfile);
}
Aggregations