remove everything related to the custom Dialer, let the system handle it
This commit is contained in:
parent
1b9028ba6c
commit
420a523062
|
@ -224,9 +224,7 @@
|
||||||
|
|
||||||
<activity
|
<activity
|
||||||
android:name=".activities.DialerActivity"
|
android:name=".activities.DialerActivity"
|
||||||
android:label="@string/dialer"
|
android:label="@string/dialer">
|
||||||
android:launchMode="singleTask"
|
|
||||||
android:showOnLockScreen="true">
|
|
||||||
|
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.intent.action.CALL"/>
|
<action android:name="android.intent.action.CALL"/>
|
||||||
|
@ -246,32 +244,6 @@
|
||||||
android:resource="@xml/provider_paths"/>
|
android:resource="@xml/provider_paths"/>
|
||||||
</provider>
|
</provider>
|
||||||
|
|
||||||
<service
|
|
||||||
android:name=".services.MyIncomingCallService"
|
|
||||||
android:permission="android.permission.BIND_INCALL_SERVICE">
|
|
||||||
|
|
||||||
<meta-data
|
|
||||||
android:name="android.telecom.IN_CALL_SERVICE_UI"
|
|
||||||
android:value="true"/>
|
|
||||||
|
|
||||||
<intent-filter>
|
|
||||||
<action android:name="android.telecom.InCallService"/>
|
|
||||||
</intent-filter>
|
|
||||||
</service>
|
|
||||||
|
|
||||||
<service
|
|
||||||
android:name=".services.MyOutgoingCallService"
|
|
||||||
android:exported="true"
|
|
||||||
android:permission="android.permission.BIND_TELECOM_CONNECTION_SERVICE">
|
|
||||||
<intent-filter>
|
|
||||||
<action android:name="android.telecom.ConnectionService"/>
|
|
||||||
</intent-filter>
|
|
||||||
</service>
|
|
||||||
|
|
||||||
<service
|
|
||||||
android:name=".services.DialerCallService"
|
|
||||||
android:exported="false"/>
|
|
||||||
|
|
||||||
<activity-alias
|
<activity-alias
|
||||||
android:name=".activities.SplashActivity.Red"
|
android:name=".activities.SplashActivity.Red"
|
||||||
android:enabled="false"
|
android:enabled="false"
|
||||||
|
|
|
@ -2,188 +2,56 @@ package com.simplemobiletools.contacts.pro.activities
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.annotation.TargetApi
|
import android.annotation.TargetApi
|
||||||
import android.content.BroadcastReceiver
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.content.IntentFilter
|
|
||||||
import android.hardware.Sensor
|
|
||||||
import android.hardware.SensorEvent
|
|
||||||
import android.hardware.SensorEventListener
|
|
||||||
import android.hardware.SensorManager
|
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import android.os.Build
|
import android.os.Build
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.os.Handler
|
|
||||||
import android.os.PowerManager
|
|
||||||
import android.telecom.Call
|
|
||||||
import android.telecom.PhoneAccount
|
import android.telecom.PhoneAccount
|
||||||
import android.telecom.TelecomManager
|
import android.telecom.TelecomManager
|
||||||
import android.view.WindowManager
|
import com.simplemobiletools.commons.extensions.showErrorToast
|
||||||
import androidx.localbroadcastmanager.content.LocalBroadcastManager
|
import com.simplemobiletools.commons.extensions.toast
|
||||||
import com.simplemobiletools.commons.extensions.*
|
|
||||||
import com.simplemobiletools.contacts.pro.R
|
import com.simplemobiletools.contacts.pro.R
|
||||||
import com.simplemobiletools.contacts.pro.helpers.*
|
|
||||||
import com.simplemobiletools.contacts.pro.models.Contact
|
|
||||||
import com.simplemobiletools.contacts.pro.objects.CallManager
|
|
||||||
import com.simplemobiletools.contacts.pro.overloads.times
|
|
||||||
import com.simplemobiletools.contacts.pro.services.DialerCallService
|
|
||||||
import kotlinx.android.synthetic.main.activity_dialer.*
|
|
||||||
|
|
||||||
// incoming call handling inspired by https://github.com/mbarrben/android_dialer_replacement
|
|
||||||
@TargetApi(Build.VERSION_CODES.M)
|
@TargetApi(Build.VERSION_CODES.M)
|
||||||
class DialerActivity : SimpleActivity(), SensorEventListener {
|
class DialerActivity : SimpleActivity() {
|
||||||
private val REQUEST_CODE_SET_DEFAULT_DIALER = 1
|
private val REQUEST_CODE_SET_DEFAULT_DIALER = 1
|
||||||
private val SENSOR_SENSITIVITY = 4
|
private var callNumber: Uri? = null
|
||||||
private val DISCONNECT_DELAY = 3000L
|
|
||||||
private val CALLING_DOT_ANIMATION_DELAY = 500L
|
|
||||||
|
|
||||||
private var callNumber = ""
|
|
||||||
private var callStatus = Call.STATE_NEW
|
|
||||||
private var isIncomingCall = false
|
|
||||||
private var isCallActive = false
|
|
||||||
private var callDuration = 0
|
|
||||||
private var callingDotsCnt = 0
|
|
||||||
private var sensorManager: SensorManager? = null
|
|
||||||
private var proximity: Sensor? = null
|
|
||||||
private var proximityWakeLock: PowerManager.WakeLock? = null
|
|
||||||
private var timerHandler = Handler()
|
|
||||||
private var callingDotsHandler = Handler()
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
super.onCreate(savedInstanceState)
|
super.onCreate(savedInstanceState)
|
||||||
setContentView(R.layout.activity_dialer)
|
|
||||||
initProximityWakeLock()
|
|
||||||
LocalBroadcastManager.getInstance(applicationContext).registerReceiver(messageReceiver, IntentFilter(DIALER_INTENT_FILTER))
|
|
||||||
window.apply {
|
|
||||||
addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED)
|
|
||||||
addFlags(WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)
|
|
||||||
addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
|
|
||||||
}
|
|
||||||
|
|
||||||
val action = intent.action
|
if (intent.action == Intent.ACTION_CALL && intent.data != null) {
|
||||||
val extras = intent.extras
|
callNumber = intent.data
|
||||||
if (extras?.getBoolean(ANSWER_CALL, false) == true) {
|
|
||||||
callNumber = intent.getStringExtra(CALL_NUMBER)
|
// make sure Simple Contacts is the default Phone app before initiating an outgoing call
|
||||||
CallManager.answerCall()
|
val telecomManager = getSystemService(Context.TELECOM_SERVICE) as TelecomManager
|
||||||
tryFillingOtherParticipantsName()
|
if (telecomManager.defaultDialerPackage != packageName) {
|
||||||
initViews()
|
val intent = Intent(TelecomManager.ACTION_CHANGE_DEFAULT_DIALER).putExtra(TelecomManager.EXTRA_CHANGE_DEFAULT_DIALER_PACKAGE_NAME, packageName)
|
||||||
} else if (action == Intent.ACTION_CALL && intent.data != null && intent.dataString?.contains("tel:") == true) {
|
startActivityForResult(intent, REQUEST_CODE_SET_DEFAULT_DIALER)
|
||||||
callNumber = Uri.decode(intent.dataString).substringAfter("tel:")
|
} else {
|
||||||
tryFillingOtherParticipantsName()
|
|
||||||
initOutgoingCall()
|
initOutgoingCall()
|
||||||
initViews()
|
}
|
||||||
} else if (action == INCOMING_CALL && extras?.containsKey(CALL_NUMBER) == true && extras.containsKey(CALL_STATUS)) {
|
|
||||||
isIncomingCall = true
|
|
||||||
callNumber = intent.getStringExtra(CALL_NUMBER)
|
|
||||||
initViews()
|
|
||||||
updateUI(intent.getIntExtra(CALL_STATUS, Call.STATE_NEW))
|
|
||||||
tryFillingOtherParticipantsName()
|
|
||||||
} else if (action == RESUME_DIALER && extras?.containsKey(CALL_NUMBER) == true && extras.containsKey(CALL_STATUS) && extras.containsKey(IS_INCOMING_CALL)) {
|
|
||||||
callNumber = intent.getStringExtra(CALL_NUMBER)
|
|
||||||
callStatus = intent.getIntExtra(CALL_STATUS, Call.STATE_NEW)
|
|
||||||
isIncomingCall = intent.getBooleanExtra(IS_INCOMING_CALL, false)
|
|
||||||
updateUI(callStatus)
|
|
||||||
tryFillingOtherParticipantsName()
|
|
||||||
initViews()
|
|
||||||
} else {
|
} else {
|
||||||
toast(R.string.unknown_error_occurred)
|
toast(R.string.unknown_error_occurred)
|
||||||
finish()
|
finish()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onResume() {
|
|
||||||
super.onResume()
|
|
||||||
updateTextColors(dialer_holder)
|
|
||||||
sensorManager!!.registerListener(this, proximity!!, SensorManager.SENSOR_DELAY_NORMAL)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onPause() {
|
|
||||||
super.onPause()
|
|
||||||
sensorManager!!.unregisterListener(this)
|
|
||||||
if (!isCallActive && callStatus != Call.STATE_DISCONNECTED) {
|
|
||||||
startNotificationService()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDestroy() {
|
|
||||||
super.onDestroy()
|
|
||||||
timerHandler.removeCallbacksAndMessages(null)
|
|
||||||
callingDotsHandler.removeCallbacksAndMessages(null)
|
|
||||||
}
|
|
||||||
|
|
||||||
private val messageReceiver = object : BroadcastReceiver() {
|
|
||||||
override fun onReceive(context: Context, intent: Intent) {
|
|
||||||
if (intent.extras?.containsKey(CALL_STATUS) == true) {
|
|
||||||
updateUI(intent.getIntExtra(CALL_STATUS, Call.STATE_NEW))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onBackPressed() {
|
|
||||||
super.onBackPressed()
|
|
||||||
if (!isCallActive && !isIncomingCall) {
|
|
||||||
hangUp()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// animate the dots after Calling... from 0 to 3
|
|
||||||
private fun handleDotsAnimation() {
|
|
||||||
callingDotsHandler.postDelayed({
|
|
||||||
if (callStatus == Call.STATE_DIALING) {
|
|
||||||
callingDotsCnt = ++callingDotsCnt % 4
|
|
||||||
dialer_label_dots.text = ".".times(callingDotsCnt)
|
|
||||||
handleDotsAnimation()
|
|
||||||
}
|
|
||||||
}, CALLING_DOT_ANIMATION_DELAY)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun initProximityWakeLock() {
|
|
||||||
sensorManager = getSystemService(Context.SENSOR_SERVICE) as SensorManager
|
|
||||||
proximity = sensorManager!!.getDefaultSensor(Sensor.TYPE_PROXIMITY)
|
|
||||||
val powerManager = getSystemService(Context.POWER_SERVICE) as PowerManager
|
|
||||||
proximityWakeLock = if (powerManager.isWakeLockLevelSupported(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK)) {
|
|
||||||
powerManager.newWakeLock(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK, "SimpleContacts:ProximityWakeLock")
|
|
||||||
} else {
|
|
||||||
null
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun initViews() {
|
|
||||||
dialer_hangup_button.setOnClickListener { hangUp() }
|
|
||||||
dialer_incoming_accept.setOnClickListener { CallManager.answerCall() }
|
|
||||||
dialer_incoming_decline.setOnClickListener { hangUp() }
|
|
||||||
|
|
||||||
dialer_hangup_button.beVisibleIf(!isIncomingCall)
|
|
||||||
dialer_incoming_decline.beVisibleIf(isIncomingCall)
|
|
||||||
dialer_incoming_accept.beVisibleIf(isIncomingCall)
|
|
||||||
|
|
||||||
dialer_label.setText(if (isIncomingCall) R.string.incoming_call_from else R.string.calling)
|
|
||||||
if (!isIncomingCall) {
|
|
||||||
handleDotsAnimation()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("MissingPermission")
|
@SuppressLint("MissingPermission")
|
||||||
private fun initOutgoingCall() {
|
private fun initOutgoingCall() {
|
||||||
try {
|
try {
|
||||||
val telecomManager = getSystemService(Context.TELECOM_SERVICE) as TelecomManager
|
val telecomManager = getSystemService(Context.TELECOM_SERVICE) as TelecomManager
|
||||||
val uri = Uri.fromParts(PhoneAccount.SCHEME_TEL, callNumber, null)
|
|
||||||
Bundle().apply {
|
Bundle().apply {
|
||||||
putParcelable(TelecomManager.EXTRA_PHONE_ACCOUNT_HANDLE, telecomManager.getDefaultOutgoingPhoneAccount(PhoneAccount.SCHEME_TEL))
|
putParcelable(TelecomManager.EXTRA_PHONE_ACCOUNT_HANDLE, telecomManager.getDefaultOutgoingPhoneAccount(PhoneAccount.SCHEME_TEL))
|
||||||
putBoolean(TelecomManager.EXTRA_START_CALL_WITH_VIDEO_STATE, false)
|
putBoolean(TelecomManager.EXTRA_START_CALL_WITH_VIDEO_STATE, false)
|
||||||
putBoolean(TelecomManager.EXTRA_START_CALL_WITH_SPEAKERPHONE, false)
|
putBoolean(TelecomManager.EXTRA_START_CALL_WITH_SPEAKERPHONE, false)
|
||||||
telecomManager.placeCall(uri, this)
|
telecomManager.placeCall(callNumber, this)
|
||||||
}
|
|
||||||
callStatus = Call.STATE_DIALING
|
|
||||||
} catch (e: Exception) {
|
|
||||||
// only default Phone apps can initiate outgoing calls. So if we got here and Simple Contacts isnt the default phone app, ask the user to set so
|
|
||||||
if (e is SecurityException) {
|
|
||||||
val intent = Intent(TelecomManager.ACTION_CHANGE_DEFAULT_DIALER).putExtra(TelecomManager.EXTRA_CHANGE_DEFAULT_DIALER_PACKAGE_NAME, packageName)
|
|
||||||
startActivityForResult(intent, REQUEST_CODE_SET_DEFAULT_DIALER)
|
|
||||||
} else {
|
|
||||||
showErrorToast(e)
|
|
||||||
finish()
|
finish()
|
||||||
}
|
}
|
||||||
|
} catch (e: Exception) {
|
||||||
|
showErrorToast(e)
|
||||||
|
finish()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -198,118 +66,4 @@ class DialerActivity : SimpleActivity(), SensorEventListener {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun startNotificationService() {
|
|
||||||
Intent(this, DialerCallService::class.java).apply {
|
|
||||||
putExtra(CALL_NUMBER, callNumber)
|
|
||||||
putExtra(CALL_STATUS, callStatus)
|
|
||||||
putExtra(IS_INCOMING_CALL, isIncomingCall)
|
|
||||||
startService(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun stopNotificationService() {
|
|
||||||
Intent(this, DialerCallService::class.java).apply {
|
|
||||||
stopService(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun hangUp() {
|
|
||||||
callStatus = Call.STATE_DISCONNECTED
|
|
||||||
stopNotificationService()
|
|
||||||
CallManager.declineCall()
|
|
||||||
finish()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun tryFillingOtherParticipantsName() {
|
|
||||||
ContactsHelper(this).getContactWithNumber(callNumber) {
|
|
||||||
runOnUiThread {
|
|
||||||
updateOtherParticipant(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun updateUI(status: Int) {
|
|
||||||
callStatus = status
|
|
||||||
when (status) {
|
|
||||||
Call.STATE_ACTIVE -> statusActive()
|
|
||||||
Call.STATE_DISCONNECTED -> statusDisconnected()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun statusActive() {
|
|
||||||
callingDotsHandler.removeCallbacksAndMessages(null)
|
|
||||||
dialer_label_dots.beGone()
|
|
||||||
startNotificationService()
|
|
||||||
isCallActive = true
|
|
||||||
dialer_call_duration.beVisible()
|
|
||||||
updateCallDuration()
|
|
||||||
|
|
||||||
dialer_label.setText(R.string.ongoing_call)
|
|
||||||
dialer_hangup_button.beVisible()
|
|
||||||
dialer_incoming_accept.beGone()
|
|
||||||
dialer_incoming_decline.beGone()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun updateCallDuration() {
|
|
||||||
dialer_call_duration.text = callDuration.getFormattedDuration()
|
|
||||||
timerHandler.postDelayed({
|
|
||||||
if (isCallActive) {
|
|
||||||
callDuration++
|
|
||||||
updateCallDuration()
|
|
||||||
}
|
|
||||||
}, 1000)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun statusDisconnected() {
|
|
||||||
callingDotsHandler.removeCallbacksAndMessages(null)
|
|
||||||
timerHandler.removeCallbacksAndMessages(null)
|
|
||||||
dialer_label_dots.beGone()
|
|
||||||
stopNotificationService()
|
|
||||||
dialer_hangup_button.beGone()
|
|
||||||
dialer_label.setText(R.string.disconnected)
|
|
||||||
if (isCallActive) {
|
|
||||||
dialer_hangup_button.postDelayed({
|
|
||||||
finish()
|
|
||||||
}, DISCONNECT_DELAY)
|
|
||||||
} else {
|
|
||||||
finish()
|
|
||||||
}
|
|
||||||
isCallActive = false
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun updateOtherParticipant(contact: Contact?) {
|
|
||||||
if (contact != null) {
|
|
||||||
dialer_big_name_number.text = contact.getNameToDisplay()
|
|
||||||
dialer_number.text = callNumber
|
|
||||||
} else {
|
|
||||||
dialer_big_name_number.text = callNumber
|
|
||||||
dialer_number.beGone()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onAccuracyChanged(sensor: Sensor?, accuracy: Int) {}
|
|
||||||
|
|
||||||
override fun onSensorChanged(event: SensorEvent) {
|
|
||||||
if (event.sensor.type == Sensor.TYPE_PROXIMITY) {
|
|
||||||
if (event.values[0] >= -SENSOR_SENSITIVITY && event.values[0] <= SENSOR_SENSITIVITY) {
|
|
||||||
turnOffScreen()
|
|
||||||
} else {
|
|
||||||
turnOnScreen()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("WakelockTimeout")
|
|
||||||
private fun turnOffScreen() {
|
|
||||||
if (proximityWakeLock?.isHeld == false) {
|
|
||||||
proximityWakeLock!!.acquire()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun turnOnScreen() {
|
|
||||||
if (proximityWakeLock?.isHeld == true) {
|
|
||||||
proximityWakeLock!!.release(PowerManager.RELEASE_FLAG_WAIT_FOR_NO_PROXIMITY)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -32,16 +32,6 @@ const val FIRST_GROUP_ID = 10000L
|
||||||
const val KEY_PHONE = "phone"
|
const val KEY_PHONE = "phone"
|
||||||
const val KEY_NAME = "name"
|
const val KEY_NAME = "name"
|
||||||
|
|
||||||
// Dialer
|
|
||||||
const val INCOMING_CALL = "incoming_call"
|
|
||||||
const val RESUME_DIALER = "resume_dialer"
|
|
||||||
const val CALL_NUMBER = "call_number"
|
|
||||||
const val CALL_STATUS = "call_status"
|
|
||||||
const val IS_INCOMING_CALL = "is_incoming_call"
|
|
||||||
const val DIALER_INTENT_FILTER = "dialer_intent_filter"
|
|
||||||
const val DECLINE_CALL = "decline_call"
|
|
||||||
const val ANSWER_CALL = "answer_call"
|
|
||||||
|
|
||||||
const val LOCATION_CONTACTS_TAB = 0
|
const val LOCATION_CONTACTS_TAB = 0
|
||||||
const val LOCATION_FAVORITES_TAB = 1
|
const val LOCATION_FAVORITES_TAB = 1
|
||||||
const val LOCATION_RECENTS_TAB = 2
|
const val LOCATION_RECENTS_TAB = 2
|
||||||
|
|
|
@ -93,31 +93,6 @@ class ContactsHelper(val context: Context) {
|
||||||
}.start()
|
}.start()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun getContactWithNumber(number: String, callback: (contact: Contact?) -> Unit) {
|
|
||||||
Thread {
|
|
||||||
val uri = CommonDataKinds.Phone.CONTENT_URI
|
|
||||||
val projection = arrayOf(ContactsContract.Data.RAW_CONTACT_ID)
|
|
||||||
val selection = "${CommonDataKinds.Phone.NUMBER} = ? OR ${CommonDataKinds.Phone.NORMALIZED_NUMBER} = ?"
|
|
||||||
val selectionArgs = arrayOf(number, number.normalizeNumber())
|
|
||||||
|
|
||||||
var cursor: Cursor? = null
|
|
||||||
try {
|
|
||||||
cursor = context.contentResolver.query(uri, projection, selection, selectionArgs, null)
|
|
||||||
if (cursor?.moveToFirst() == true) {
|
|
||||||
val id = cursor.getIntValue(ContactsContract.Data.RAW_CONTACT_ID)
|
|
||||||
callback(getContactWithId(id, false))
|
|
||||||
return@Thread
|
|
||||||
}
|
|
||||||
} catch (e: Exception) {
|
|
||||||
context.showErrorToast(e)
|
|
||||||
} finally {
|
|
||||||
cursor?.close()
|
|
||||||
}
|
|
||||||
|
|
||||||
callback(LocalContactsHelper(context).getContactWithNumber(number))
|
|
||||||
}.start()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getContentResolverAccounts(): HashSet<ContactSource> {
|
private fun getContentResolverAccounts(): HashSet<ContactSource> {
|
||||||
val uri = ContactsContract.Data.CONTENT_URI
|
val uri = ContactsContract.Data.CONTENT_URI
|
||||||
val projection = arrayOf(
|
val projection = arrayOf(
|
||||||
|
|
|
@ -19,15 +19,6 @@ class LocalContactsHelper(val context: Context) {
|
||||||
|
|
||||||
fun getContactWithId(id: Int) = convertLocalContactToContact(context.contactsDB.getContactWithId(id))
|
fun getContactWithId(id: Int) = convertLocalContactToContact(context.contactsDB.getContactWithId(id))
|
||||||
|
|
||||||
fun getContactWithNumber(number: String): Contact? {
|
|
||||||
context.contactsDB.getContacts().forEach {
|
|
||||||
if (it.phoneNumbers.map { it.value }.contains(number)) {
|
|
||||||
return convertLocalContactToContact(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
|
|
||||||
fun insertOrUpdateContact(contact: Contact): Boolean {
|
fun insertOrUpdateContact(contact: Contact): Boolean {
|
||||||
val localContact = convertContactToLocalContact(contact)
|
val localContact = convertContactToLocalContact(contact)
|
||||||
return context.contactsDB.insertOrUpdate(localContact) > 0
|
return context.contactsDB.insertOrUpdate(localContact) > 0
|
||||||
|
|
|
@ -1,33 +0,0 @@
|
||||||
package com.simplemobiletools.contacts.pro.helpers
|
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
|
||||||
import android.content.Context
|
|
||||||
import android.os.Build
|
|
||||||
import android.telecom.Connection
|
|
||||||
import android.telecom.DisconnectCause
|
|
||||||
|
|
||||||
@TargetApi(Build.VERSION_CODES.M)
|
|
||||||
class MyConnection(val context: Context) : Connection() {
|
|
||||||
override fun onAnswer() {
|
|
||||||
super.onAnswer()
|
|
||||||
setActive()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onReject() {
|
|
||||||
super.onReject()
|
|
||||||
setDisconnected(DisconnectCause(DisconnectCause.REJECTED))
|
|
||||||
destroy()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onAbort() {
|
|
||||||
super.onAbort()
|
|
||||||
setDisconnected(DisconnectCause(DisconnectCause.REMOTE))
|
|
||||||
destroy()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDisconnect() {
|
|
||||||
super.onDisconnect()
|
|
||||||
setDisconnected(DisconnectCause(DisconnectCause.CANCELED))
|
|
||||||
destroy()
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,29 +0,0 @@
|
||||||
package com.simplemobiletools.contacts.pro.objects
|
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
|
||||||
import android.os.Build
|
|
||||||
import android.telecom.Call
|
|
||||||
|
|
||||||
@TargetApi(Build.VERSION_CODES.M)
|
|
||||||
object CallManager {
|
|
||||||
private var currentCall: Call? = null
|
|
||||||
|
|
||||||
fun updateCall(call: Call?) {
|
|
||||||
currentCall = call
|
|
||||||
}
|
|
||||||
|
|
||||||
fun declineCall() {
|
|
||||||
currentCall?.apply {
|
|
||||||
when (state) {
|
|
||||||
Call.STATE_RINGING -> reject(false, "")
|
|
||||||
else -> disconnect()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun answerCall() {
|
|
||||||
currentCall?.apply {
|
|
||||||
answer(details.videoState)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,161 +0,0 @@
|
||||||
package com.simplemobiletools.contacts.pro.services
|
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
|
||||||
import android.app.NotificationChannel
|
|
||||||
import android.app.NotificationManager
|
|
||||||
import android.app.PendingIntent
|
|
||||||
import android.app.Service
|
|
||||||
import android.content.Context
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Build
|
|
||||||
import android.os.Handler
|
|
||||||
import android.telecom.Call
|
|
||||||
import android.widget.RemoteViews
|
|
||||||
import androidx.core.app.NotificationCompat
|
|
||||||
import com.simplemobiletools.commons.extensions.getColoredBitmap
|
|
||||||
import com.simplemobiletools.commons.extensions.setText
|
|
||||||
import com.simplemobiletools.commons.extensions.setVisibleIf
|
|
||||||
import com.simplemobiletools.commons.helpers.isOreoPlus
|
|
||||||
import com.simplemobiletools.contacts.pro.R
|
|
||||||
import com.simplemobiletools.contacts.pro.activities.DialerActivity
|
|
||||||
import com.simplemobiletools.contacts.pro.helpers.*
|
|
||||||
import com.simplemobiletools.contacts.pro.objects.CallManager
|
|
||||||
|
|
||||||
class DialerCallService : Service() {
|
|
||||||
private val REFRESH_REMINDER_PERIOD = 3000L
|
|
||||||
private val CALL_NOTIFICATION_ID = 1
|
|
||||||
private val LAUNCH_DIALER_INTENT_ID = 1
|
|
||||||
private val DISMISS_CALL_INTENT_ID = 2
|
|
||||||
private val ANSWER_CALL_INTENT_ID = 3
|
|
||||||
|
|
||||||
private var callNumber = ""
|
|
||||||
private var callStatus = Call.STATE_NEW
|
|
||||||
private var isIncomingCall = false
|
|
||||||
private var otherParticipantName: String? = null
|
|
||||||
private var reminderRefreshHandler = Handler()
|
|
||||||
|
|
||||||
override fun onBind(intent: Intent?) = null
|
|
||||||
|
|
||||||
override fun onStartCommand(intent: Intent, flags: Int, startId: Int): Int {
|
|
||||||
super.onStartCommand(intent, flags, startId)
|
|
||||||
when {
|
|
||||||
intent.getBooleanExtra(DECLINE_CALL, false) -> {
|
|
||||||
CallManager.declineCall()
|
|
||||||
stopForeground(true)
|
|
||||||
stopSelf()
|
|
||||||
}
|
|
||||||
intent.extras?.containsKey(CALL_STATUS) == true -> {
|
|
||||||
callNumber = intent.getStringExtra(CALL_NUMBER)
|
|
||||||
callStatus = intent.getIntExtra(CALL_STATUS, Call.STATE_NEW)
|
|
||||||
isIncomingCall = intent.getBooleanExtra(IS_INCOMING_CALL, false)
|
|
||||||
getOtherParticipantsName()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return START_STICKY
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDestroy() {
|
|
||||||
super.onDestroy()
|
|
||||||
stopForeground(true)
|
|
||||||
reminderRefreshHandler.removeCallbacksAndMessages(null)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getOtherParticipantsName() {
|
|
||||||
ContactsHelper(this).getContactWithNumber(callNumber) {
|
|
||||||
otherParticipantName = it?.getNameToDisplay() ?: callNumber
|
|
||||||
setupNotification()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@TargetApi(Build.VERSION_CODES.O)
|
|
||||||
private fun setupNotification() {
|
|
||||||
val channelId = "call_channel"
|
|
||||||
if (isOreoPlus()) {
|
|
||||||
val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
|
|
||||||
val name = resources.getString(R.string.app_name)
|
|
||||||
val importance = if (callStatus == Call.STATE_RINGING) NotificationManager.IMPORTANCE_HIGH else NotificationManager.IMPORTANCE_DEFAULT
|
|
||||||
NotificationChannel(channelId, name, importance).apply {
|
|
||||||
enableLights(false)
|
|
||||||
enableVibration(false)
|
|
||||||
setSound(null, null)
|
|
||||||
notificationManager.createNotificationChannel(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
val notificationLayout = RemoteViews(packageName, R.layout.incoming_call_notification).apply {
|
|
||||||
setText(R.id.incoming_call_caller, otherParticipantName!!)
|
|
||||||
setText(R.id.incoming_call_status, getCallStatusString())
|
|
||||||
|
|
||||||
val resources = applicationContext.resources
|
|
||||||
setImageViewBitmap(R.id.call_decline, resources.getColoredBitmap(R.drawable.ic_phone_down, resources.getColor(R.color.theme_dark_red_primary_color)))
|
|
||||||
setImageViewBitmap(R.id.call_answer, resources.getColoredBitmap(R.drawable.ic_phone, resources.getColor(R.color.md_green_700)))
|
|
||||||
|
|
||||||
setVisibleIf(R.id.call_answer, callStatus == Call.STATE_RINGING)
|
|
||||||
|
|
||||||
setOnClickPendingIntent(R.id.call_decline, getDeclineCallIntent())
|
|
||||||
setOnClickPendingIntent(R.id.call_answer, getAnswerCallIntent())
|
|
||||||
}
|
|
||||||
|
|
||||||
val notification = NotificationCompat.Builder(applicationContext, channelId)
|
|
||||||
.setSmallIcon(R.drawable.ic_phone)
|
|
||||||
.setContentIntent(getLaunchDialerIntent())
|
|
||||||
.setVisibility(NotificationCompat.VISIBILITY_PUBLIC)
|
|
||||||
.setPriority(NotificationCompat.PRIORITY_MAX)
|
|
||||||
.setCustomContentView(notificationLayout)
|
|
||||||
.setCustomHeadsUpContentView(notificationLayout)
|
|
||||||
.setCustomBigContentView(notificationLayout)
|
|
||||||
.setOngoing(true)
|
|
||||||
.setCategory(NotificationCompat.CATEGORY_CALL)
|
|
||||||
.setChannelId(channelId)
|
|
||||||
.setSound(null)
|
|
||||||
.setOnlyAlertOnce(false)
|
|
||||||
.setUsesChronometer(callStatus == Call.STATE_ACTIVE)
|
|
||||||
|
|
||||||
startForeground(CALL_NOTIFICATION_ID, notification.build())
|
|
||||||
|
|
||||||
reminderRefreshHandler.postDelayed({
|
|
||||||
if (callStatus == Call.STATE_RINGING) {
|
|
||||||
setupNotification()
|
|
||||||
}
|
|
||||||
}, REFRESH_REMINDER_PERIOD)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getLaunchDialerIntent(): PendingIntent {
|
|
||||||
val intent = Intent(this, DialerActivity::class.java).apply {
|
|
||||||
action = RESUME_DIALER
|
|
||||||
putExtra(CALL_NUMBER, callNumber)
|
|
||||||
putExtra(CALL_STATUS, callStatus)
|
|
||||||
putExtra(IS_INCOMING_CALL, isIncomingCall)
|
|
||||||
}
|
|
||||||
return PendingIntent.getActivity(this, LAUNCH_DIALER_INTENT_ID, intent, PendingIntent.FLAG_UPDATE_CURRENT)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getDeclineCallIntent(): PendingIntent {
|
|
||||||
Intent(this, DialerCallService::class.java).apply {
|
|
||||||
putExtra(DECLINE_CALL, true)
|
|
||||||
return PendingIntent.getService(this@DialerCallService, DISMISS_CALL_INTENT_ID, this, PendingIntent.FLAG_UPDATE_CURRENT)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getAnswerCallIntent(): PendingIntent {
|
|
||||||
val intent = Intent(this, DialerActivity::class.java).apply {
|
|
||||||
action = RESUME_DIALER
|
|
||||||
putExtra(CALL_NUMBER, callNumber)
|
|
||||||
putExtra(CALL_STATUS, callStatus)
|
|
||||||
putExtra(IS_INCOMING_CALL, isIncomingCall)
|
|
||||||
putExtra(ANSWER_CALL, true)
|
|
||||||
}
|
|
||||||
return PendingIntent.getActivity(this, ANSWER_CALL_INTENT_ID, intent, PendingIntent.FLAG_UPDATE_CURRENT)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getCallStatusString(): String {
|
|
||||||
val id = when (callStatus) {
|
|
||||||
Call.STATE_DIALING -> R.string.calling
|
|
||||||
Call.STATE_RINGING -> R.string.incoming_call
|
|
||||||
Call.STATE_ACTIVE -> R.string.ongoing_call
|
|
||||||
else -> if (isIncomingCall) R.string.incoming_call else R.string.calling
|
|
||||||
}
|
|
||||||
|
|
||||||
return applicationContext.getString(id)
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,76 +0,0 @@
|
||||||
package com.simplemobiletools.contacts.pro.services
|
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
|
||||||
import android.app.KeyguardManager
|
|
||||||
import android.content.Context
|
|
||||||
import android.content.Intent
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Build
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.telecom.Call
|
|
||||||
import android.telecom.InCallService
|
|
||||||
import androidx.localbroadcastmanager.content.LocalBroadcastManager
|
|
||||||
import com.simplemobiletools.contacts.pro.activities.DialerActivity
|
|
||||||
import com.simplemobiletools.contacts.pro.helpers.*
|
|
||||||
import com.simplemobiletools.contacts.pro.objects.CallManager
|
|
||||||
|
|
||||||
@TargetApi(Build.VERSION_CODES.M)
|
|
||||||
class MyIncomingCallService : InCallService() {
|
|
||||||
override fun onCallAdded(call: Call) {
|
|
||||||
super.onCallAdded(call)
|
|
||||||
call.registerCallback(callCallback)
|
|
||||||
|
|
||||||
val handle = Uri.decode(call.details.handle.toString())
|
|
||||||
val callerNumber = if (handle.contains("tel:")) {
|
|
||||||
handle.substringAfter("tel:")
|
|
||||||
} else {
|
|
||||||
handle
|
|
||||||
}
|
|
||||||
|
|
||||||
val keyguardManager = getSystemService(Context.KEYGUARD_SERVICE) as KeyguardManager
|
|
||||||
if (keyguardManager.isKeyguardLocked) {
|
|
||||||
Intent(this, DialerActivity::class.java).apply {
|
|
||||||
action = RESUME_DIALER
|
|
||||||
flags = flags or Intent.FLAG_ACTIVITY_NEW_TASK
|
|
||||||
putExtra(CALL_NUMBER, callerNumber)
|
|
||||||
putExtra(CALL_STATUS, call.state)
|
|
||||||
putExtra(IS_INCOMING_CALL, true)
|
|
||||||
startActivity(this)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
Intent(this, DialerCallService::class.java).apply {
|
|
||||||
putExtra(CALL_STATUS, call.state)
|
|
||||||
putExtra(CALL_NUMBER, callerNumber)
|
|
||||||
putExtra(IS_INCOMING_CALL, true)
|
|
||||||
startService(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
CallManager.updateCall(call)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCallRemoved(call: Call) {
|
|
||||||
super.onCallRemoved(call)
|
|
||||||
call.unregisterCallback(callCallback)
|
|
||||||
CallManager.updateCall(null)
|
|
||||||
}
|
|
||||||
|
|
||||||
private val callCallback = object : Call.Callback() {
|
|
||||||
override fun onStateChanged(call: Call, state: Int) {
|
|
||||||
CallManager.updateCall(call)
|
|
||||||
sendCallToActivity(call)
|
|
||||||
if (state == Call.STATE_DISCONNECTED) {
|
|
||||||
Intent(applicationContext, DialerCallService::class.java).apply {
|
|
||||||
stopService(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun sendCallToActivity(call: Call) {
|
|
||||||
Intent(DIALER_INTENT_FILTER).apply {
|
|
||||||
putExtra(CALL_STATUS, call.state)
|
|
||||||
LocalBroadcastManager.getInstance(applicationContext).sendBroadcast(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,18 +0,0 @@
|
||||||
package com.simplemobiletools.contacts.pro.services
|
|
||||||
|
|
||||||
import android.annotation.TargetApi
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Build
|
|
||||||
import android.telecom.*
|
|
||||||
import com.simplemobiletools.contacts.pro.helpers.MyConnection
|
|
||||||
|
|
||||||
@TargetApi(Build.VERSION_CODES.M)
|
|
||||||
class MyOutgoingCallService : ConnectionService() {
|
|
||||||
override fun onCreateIncomingConnection(connectionManagerPhoneAccount: PhoneAccountHandle, request: ConnectionRequest): Connection {
|
|
||||||
val connection = MyConnection(applicationContext)
|
|
||||||
val phoneNumber = request.extras.get(TelecomManager.EXTRA_INCOMING_CALL_ADDRESS) as Uri
|
|
||||||
connection.setAddress(phoneNumber, TelecomManager.PRESENTATION_ALLOWED)
|
|
||||||
connection.setRinging()
|
|
||||||
return connection
|
|
||||||
}
|
|
||||||
}
|
|
Binary file not shown.
Before Width: | Height: | Size: 408 B |
Binary file not shown.
Before Width: | Height: | Size: 507 B |
Binary file not shown.
Before Width: | Height: | Size: 722 B |
Binary file not shown.
Before Width: | Height: | Size: 929 B |
|
@ -1,9 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<shape
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
android:shape="oval">
|
|
||||||
|
|
||||||
<solid
|
|
||||||
android:color="@color/md_green_700"/>
|
|
||||||
|
|
||||||
</shape>
|
|
|
@ -1,9 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<shape
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
android:shape="oval">
|
|
||||||
|
|
||||||
<solid
|
|
||||||
android:color="@color/theme_dark_red_primary_color"/>
|
|
||||||
|
|
||||||
</shape>
|
|
|
@ -1,11 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<ripple
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
android:color="@color/ripple_grey">
|
|
||||||
|
|
||||||
<item android:id="@android:id/mask">
|
|
||||||
<shape android:shape="rectangle">
|
|
||||||
<solid android:color="@color/ripple_grey"/>
|
|
||||||
</shape>
|
|
||||||
</item>
|
|
||||||
</ripple>
|
|
|
@ -1,118 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<androidx.constraintlayout.widget.ConstraintLayout
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/dialer_holder"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="match_parent">
|
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
|
||||||
android:id="@+id/dialer_label"
|
|
||||||
android:layout_width="wrap_content"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="@dimen/dialer_top_margin"
|
|
||||||
android:gravity="center_horizontal"
|
|
||||||
android:text="@string/calling"
|
|
||||||
android:textSize="@dimen/big_text_size"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"
|
|
||||||
app:layout_constraintTop_toTopOf="parent"/>
|
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
|
||||||
android:id="@+id/dialer_label_dots"
|
|
||||||
android:layout_width="wrap_content"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:gravity="center_horizontal"
|
|
||||||
android:textSize="@dimen/big_text_size"
|
|
||||||
app:layout_constraintBottom_toBottomOf="@+id/dialer_label"
|
|
||||||
app:layout_constraintStart_toEndOf="@+id/dialer_label"
|
|
||||||
app:layout_constraintTop_toTopOf="@+id/dialer_label"
|
|
||||||
tools:text="..."/>
|
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
|
||||||
android:id="@+id/dialer_big_name_number"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="@dimen/medium_margin"
|
|
||||||
android:gravity="center_horizontal"
|
|
||||||
android:paddingLeft="@dimen/activity_margin"
|
|
||||||
android:paddingRight="@dimen/activity_margin"
|
|
||||||
android:textSize="@dimen/dialpad_text_size"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"
|
|
||||||
app:layout_constraintTop_toBottomOf="@+id/dialer_label"
|
|
||||||
tools:text="John"/>
|
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
|
||||||
android:id="@+id/dialer_number"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="@dimen/medium_margin"
|
|
||||||
android:gravity="center_horizontal"
|
|
||||||
android:paddingLeft="@dimen/activity_margin"
|
|
||||||
android:paddingRight="@dimen/activity_margin"
|
|
||||||
android:textSize="@dimen/big_text_size"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"
|
|
||||||
app:layout_constraintTop_toBottomOf="@+id/dialer_big_name_number"
|
|
||||||
tools:text="123 456 789"/>
|
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
|
||||||
android:id="@+id/dialer_call_duration"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="@dimen/medium_margin"
|
|
||||||
android:gravity="center_horizontal"
|
|
||||||
android:paddingLeft="@dimen/activity_margin"
|
|
||||||
android:paddingRight="@dimen/activity_margin"
|
|
||||||
android:textSize="@dimen/big_text_size"
|
|
||||||
android:visibility="gone"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"
|
|
||||||
app:layout_constraintTop_toBottomOf="@+id/dialer_number"
|
|
||||||
tools:text="00:00"/>
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/dialer_hangup_button"
|
|
||||||
android:layout_width="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_height="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_marginBottom="@dimen/dialer_bottom_margin"
|
|
||||||
android:background="@drawable/circle_red_background"
|
|
||||||
android:elevation="@dimen/medium_margin"
|
|
||||||
android:padding="@dimen/activity_margin"
|
|
||||||
android:src="@drawable/ic_phone_down"
|
|
||||||
android:visibility="gone"
|
|
||||||
app:layout_constraintBottom_toBottomOf="parent"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"/>
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/dialer_incoming_accept"
|
|
||||||
android:layout_width="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_height="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_marginBottom="@dimen/dialer_bottom_margin"
|
|
||||||
android:background="@drawable/circle_green_background"
|
|
||||||
android:elevation="@dimen/medium_margin"
|
|
||||||
android:padding="@dimen/activity_margin"
|
|
||||||
android:src="@drawable/ic_phone"
|
|
||||||
app:layout_constraintBottom_toBottomOf="parent"
|
|
||||||
app:layout_constraintEnd_toEndOf="parent"
|
|
||||||
app:layout_constraintHorizontal_bias="0.5"
|
|
||||||
app:layout_constraintStart_toEndOf="@+id/dialer_incoming_decline"/>
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/dialer_incoming_decline"
|
|
||||||
android:layout_width="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_height="@dimen/dialer_hangup_button_size"
|
|
||||||
android:layout_marginBottom="@dimen/dialer_bottom_margin"
|
|
||||||
android:background="@drawable/circle_red_background"
|
|
||||||
android:elevation="@dimen/medium_margin"
|
|
||||||
android:padding="@dimen/activity_margin"
|
|
||||||
android:src="@drawable/ic_phone_down"
|
|
||||||
app:layout_constraintBottom_toBottomOf="parent"
|
|
||||||
app:layout_constraintEnd_toStartOf="@+id/dialer_incoming_accept"
|
|
||||||
app:layout_constraintHorizontal_bias="0.5"
|
|
||||||
app:layout_constraintStart_toStartOf="parent"/>
|
|
||||||
|
|
||||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
|
|
@ -1,55 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<RelativeLayout
|
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/call_notification_holder"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content">
|
|
||||||
|
|
||||||
<TextView
|
|
||||||
android:id="@+id/incoming_call_caller"
|
|
||||||
android:layout_width="wrap_content"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="@dimen/normal_margin"
|
|
||||||
android:paddingLeft="@dimen/activity_margin"
|
|
||||||
android:textSize="@dimen/bigger_text_size"
|
|
||||||
android:textStyle="bold"
|
|
||||||
tools:text="John"/>
|
|
||||||
|
|
||||||
<TextView
|
|
||||||
android:id="@+id/incoming_call_status"
|
|
||||||
android:layout_width="wrap_content"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_below="@+id/incoming_call_caller"
|
|
||||||
android:layout_marginBottom="@dimen/small_margin"
|
|
||||||
android:paddingLeft="@dimen/activity_margin"
|
|
||||||
android:textSize="@dimen/normal_text_size"
|
|
||||||
tools:text="Incoming call"/>
|
|
||||||
|
|
||||||
<LinearLayout
|
|
||||||
android:id="@+id/call_notification_actions"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_below="@+id/incoming_call_status"
|
|
||||||
android:orientation="horizontal">
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/call_decline"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_weight="1"
|
|
||||||
android:background="@drawable/ripple"
|
|
||||||
android:padding="@dimen/medium_margin"
|
|
||||||
android:src="@drawable/ic_phone_down"/>
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/call_answer"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_weight="1"
|
|
||||||
android:background="@drawable/ripple"
|
|
||||||
android:padding="@dimen/medium_margin"
|
|
||||||
android:src="@drawable/ic_phone"/>
|
|
||||||
|
|
||||||
</LinearLayout>
|
|
||||||
</RelativeLayout>
|
|
|
@ -1,4 +0,0 @@
|
||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<resources>
|
|
||||||
<color name="ripple_grey">#55000000</color>
|
|
||||||
</resources>
|
|
|
@ -7,9 +7,6 @@
|
||||||
<dimen name="contact_item_with_number_height">56dp</dimen>
|
<dimen name="contact_item_with_number_height">56dp</dimen>
|
||||||
<dimen name="create_new_contact_height">68dp</dimen>
|
<dimen name="create_new_contact_height">68dp</dimen>
|
||||||
<dimen name="dialpad_button_size">60dp</dimen>
|
<dimen name="dialpad_button_size">60dp</dimen>
|
||||||
<dimen name="dialer_hangup_button_size">70dp</dimen>
|
|
||||||
<dimen name="dialer_top_margin">140dp</dimen>
|
|
||||||
<dimen name="dialer_bottom_margin">40dp</dimen>
|
|
||||||
|
|
||||||
<dimen name="dialpad_text_size">34sp</dimen>
|
<dimen name="dialpad_text_size">34sp</dimen>
|
||||||
</resources>
|
</resources>
|
||||||
|
|
Loading…
Reference in New Issue