1

I'm developing an app that will only be used in house for testing purpose. I have searched a lot and tried different suggestions as suggested in different post but none seems to be working for me.

I'm open to any suggestions like Reflections, Accessibility Service, root or any other hack. Please help.

Regards

eC Droid
  • 651
  • 2
  • 9
  • 26

3 Answers3

1

You can use accessibility events to detect the call duration and from that you can detect if the outgoing call is answered or not..

I have answered it in detail in Here` you can check that.

kaustav07
  • 284
  • 3
  • 17
0

TRY THIS

Set all required permission in manifest.xml file.

Call this class in Service

public class PhoneListener extends PhoneStateListener {

private static PhoneListener instance = null;

/**
 * Must be called once on app startup
 *
 * @param context - application context
 * @return
 */
public static PhoneListener getInstance(Context context) {
    if (instance == null) {
        instance = new PhoneListener(context);
    }
    return instance;
}

public static boolean hasInstance() {
    return null != instance;
}

private final Context context;
private CallLog phoneCall;

private PhoneListener(Context context) {
    this.context = context;
}

AtomicBoolean isRecording = new AtomicBoolean();
AtomicBoolean isWhitelisted = new AtomicBoolean();


/**
 * Set the outgoing phone number
 * <p/>
 * Called by {@link MyCallReceiver}  since that is where the phone number is available in a outgoing call
 *
 * @param phoneNumber
 */
public void setOutgoing(String phoneNumber) {
    if (null == phoneCall)
        phoneCall = new CallLog();
    phoneCall.setPhoneNumber(phoneNumber);
    phoneCall.setOutgoing();
    // called here so as not to miss recording part of the conversation in TelephonyManager.CALL_STATE_OFFHOOK
    isWhitelisted.set(Database.isWhitelisted(context, phoneCall.getPhoneNumber()));
}

@Override
public void onCallStateChanged(int state, String incomingNumber) {
    super.onCallStateChanged(state, incomingNumber);

    switch (state) {
        case TelephonyManager.CALL_STATE_IDLE: // Idle... no call
            if (isRecording.get()) {
                RecordCallService.stopRecording(context);
                phoneCall = null;
                isRecording.set(false);
            }
            break;
        case TelephonyManager.CALL_STATE_OFFHOOK: // Call answered
            if (isWhitelisted.get()) {
                isWhitelisted.set(false);
                return;
            }
            if (!isRecording.get()) {
                isRecording.set(true);
                // start: Probably not ever usefull
                if (null == phoneCall)
                    phoneCall = new CallLog();
                if (!incomingNumber.isEmpty()) {
                    phoneCall.setPhoneNumber(incomingNumber);
                }
                // end: Probably not ever usefull
                RecordCallService.sartRecording(context, phoneCall);
            }
            break;
        case TelephonyManager.CALL_STATE_RINGING: // Phone ringing
            // DO NOT try RECORDING here! Leads to VERY poor quality recordings
            // I think something is not fully settled with the Incoming phone call when we get CALL_STATE_RINGING
            // a "SystemClock.sleep(1000);" in the code will allow the incoming call to stabilize and produce a good recording...(as proof of above)
            if (null == phoneCall)
                phoneCall = new CallLog();
            if (!incomingNumber.isEmpty()) {
                phoneCall.setPhoneNumber(incomingNumber);
                // called here so as not to miss recording part of the conversation in TelephonyManager.CALL_STATE_OFFHOOK
                isWhitelisted.set(Database.isWhitelisted(context, phoneCall.getPhoneNumber()));
            }
            break;
    }

}

}

And use Broadcast Receiver

public class MyCallReceiver extends BroadcastReceiver {

public MyCallReceiver() {
}

static TelephonyManager manager;

@Override
public void onReceive(Context context, Intent intent) {
    Log.i("JLCreativeCallRecorder", "MyCallReceiver.onReceive ");

    if (!AppPreferences.getInstance(context).isRecordingEnabled()) {
        removeListener();
        return;
    }

    if (Intent.ACTION_NEW_OUTGOING_CALL.equals(intent.getAction())) {
        if (!AppPreferences.getInstance(context).isRecordingOutgoingEnabled()) {
            removeListener();
            return;
        }
        PhoneListener.getInstance(context).setOutgoing(intent.getStringExtra(Intent.EXTRA_PHONE_NUMBER));
    } else {
        if (!AppPreferences.getInstance(context).isRecordingIncomingEnabled()) {
            removeListener();
            return;
        }
    }

    // Start Listening to the call....
    if (null == manager) {
        manager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
    }
    if (null != manager)
        manager.listen(PhoneListener.getInstance(context), PhoneStateListener.LISTEN_CALL_STATE);
}

private void removeListener() {
    if (null != manager) {
        if (PhoneListener.hasInstance())
            manager.listen(PhoneListener.getInstance(null), PhoneStateListener.LISTEN_NONE);
    }
}

}

I hope you get some help from this code.

Thanks

  • Thanks for trying to help but the above code wouldn't tell when **exactly** the call is answered! – eC Droid Jan 12 '17 at 08:02
  • This issue may be due to dual sim or lack of phoneListener of your device. In Samsung devices its working successfully. – Dheeraj Kumar Jan 12 '17 at 09:02
  • What does this actually does? I'm trying to understand it but it would be cool to have a small explanation of that already on the answer. – Edw590 Dec 23 '20 at 21:06
  • where AppPreferences.getInstance(context) came from ? and these phoneCall.setPhoneNumber(phoneNumber); phoneCall.setOutgoing(); function are not getting from PhoneCall object – Ahsan Syed Oct 19 '21 at 13:26
-1

You need this permission in manifest

<uses-permission android:name="android.permission.READ_PHONE_STATE"/>

TelephonyManager has a listener to get phone state. implement this tho know if the phone is ringing or in a call.

TelephonyManager telephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
        PhoneStateListener callStateListener = new PhoneStateListener() {

            public void onCallStateChanged(int state, String incomingNumber) {
                // TODO React to a incoming call.

                try {
                    if (state == TelephonyManager.CALL_STATE_RINGING) {
                        Toast.makeText(getApplicationContext(), "Phone Is Ringing" + incomingNumber, Toast.LENGTH_LONG).show();
                        number = incomingNumber;
                        //g.setPhoneNo(incomingNumber);
                        AndroidNetCommunicationClientActivity.mMsgSendRequest("CommandMsgCallIncoming" + number);
                    } else if (state == TelephonyManager.CALL_STATE_OFFHOOK) {
                        Toast.makeText(getApplicationContext(), "Phone is Currently in A call" + incomingNumber, Toast.LENGTH_LONG).show();
                        //number = mIntent.getStringExtra(Intent.EXTRA_PHONE_NUMBER);
                        number = incomingNumber;


                    } else if (state == TelephonyManager.DATA_DISCONNECTED) {
                        number = "";
                        CallID = "";
                    }
                } catch (Exception e) {
                    // TODO Auto-generated catch block
                    //conn.MessageBox(MainActivity.this, e.getMessage());
                    e.printStackTrace();
                }
                super.onCallStateChanged(state, incomingNumber);

            }
        };
        telephonyManager.listen(callStateListener, PhoneStateListener.LISTEN_CALL_STATE);
Sadiq Md Asif
  • 882
  • 6
  • 18