diff --git a/matrix-sdk-android/src/main/res/values/strings.xml b/matrix-sdk-android/src/main/res/values/strings.xml
index 3cd7674253..a34c3a1f9f 100644
--- a/matrix-sdk-android/src/main/res/values/strings.xml
+++ b/matrix-sdk-android/src/main/res/values/strings.xml
@@ -362,4 +362,7 @@
%s is requesting to verify your key, but your client does not support in-chat key verification. You will need to use legacy key verification to verify keys.
+ Accept
+ Reject
+
diff --git a/vector/src/main/AndroidManifest.xml b/vector/src/main/AndroidManifest.xml
index 1cd522337e..76281afe0b 100644
--- a/vector/src/main/AndroidManifest.xml
+++ b/vector/src/main/AndroidManifest.xml
@@ -12,11 +12,13 @@
-
-
+
+
+
+
@@ -195,15 +197,24 @@
android:name=".core.services.VectorSyncService"
android:exported="false" />
-
+
+
+
+
= Build.VERSION_CODES.M) {
ContextCompat.getSystemService(context, TelecomManager::class.java)?.let { telecomManager ->
phoneAccountHandle?.let { phoneAccountHandle ->
@@ -372,6 +376,7 @@ class WebRtcPeerConnectionManager @Inject constructor(
}
}
}
+ */
}
override fun onCallAnswerReceived(callAnswerContent: CallAnswerContent) {
diff --git a/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpActionReceiver.kt b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpActionReceiver.kt
new file mode 100644
index 0000000000..99f163d42d
--- /dev/null
+++ b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpActionReceiver.kt
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2020 New Vector Ltd
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package im.vector.riotx.features.call.service
+
+import android.content.BroadcastReceiver
+import android.content.Context
+import android.content.Intent
+import timber.log.Timber
+
+class CallHeadsUpActionReceiver : BroadcastReceiver() {
+
+ override fun onReceive(context: Context, intent: Intent?) {
+ when (intent?.getIntExtra(CallHeadsUpService.EXTRA_CALL_ACTION_KEY, 0)) {
+ CallHeadsUpService.CALL_ACTION_ANSWER -> onCallAnswerClicked()
+ CallHeadsUpService.CALL_ACTION_REJECT -> onCallRejectClicked()
+ }
+
+ context.sendBroadcast(Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS))
+ context.stopService(Intent(context, CallHeadsUpService::class.java))
+ }
+
+ private fun onCallRejectClicked() {
+ Timber.d("onCallRejectClicked")
+ }
+
+ private fun onCallAnswerClicked() {
+ Timber.d("onCallAnswerClicked")
+ }
+}
diff --git a/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpService.kt b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpService.kt
new file mode 100644
index 0000000000..b8fa16d6ad
--- /dev/null
+++ b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpService.kt
@@ -0,0 +1,118 @@
+/*
+ * Copyright (c) 2020 New Vector Ltd
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package im.vector.riotx.features.call.service
+
+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.media.AudioAttributes
+import android.media.AudioManager
+import android.net.Uri
+import android.os.Binder
+import android.os.Build
+import android.os.IBinder
+import androidx.core.app.NotificationCompat
+import im.vector.riotx.R
+
+class CallHeadsUpService : Service() {
+
+ private val CHANNEL_ID = "CallChannel"
+ private val CHANNEL_NAME = "Call Channel"
+ private val CHANNEL_DESCRIPTION = "Call Notifications"
+
+ private val binder: IBinder = CallHeadsUpServiceBinder()
+
+ override fun onBind(intent: Intent): IBinder? {
+ return binder
+ }
+
+ override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
+ //val callHeadsUpServiceArgs: CallHeadsUpServiceArgs? = intent?.extras?.getParcelable(EXTRA_CALL_HEADS_UP_SERVICE_PARAMS)
+
+ val answerCallActionReceiver = Intent(applicationContext, CallHeadsUpActionReceiver::class.java).apply {
+ putExtra(EXTRA_CALL_ACTION_KEY, CALL_ACTION_ANSWER)
+ }
+ val rejectCallActionReceiver = Intent(applicationContext, CallHeadsUpActionReceiver::class.java).apply {
+ putExtra(EXTRA_CALL_ACTION_KEY, CALL_ACTION_REJECT)
+ }
+
+ val answerCallPendingIntent = PendingIntent.getBroadcast(applicationContext, CALL_ACTION_ANSWER, answerCallActionReceiver, PendingIntent.FLAG_UPDATE_CURRENT)
+ val rejectCallPendingIntent = PendingIntent.getBroadcast(applicationContext, CALL_ACTION_REJECT, rejectCallActionReceiver, PendingIntent.FLAG_UPDATE_CURRENT)
+
+ createNotificationChannel()
+
+ val notification = NotificationCompat
+ .Builder(applicationContext, CHANNEL_ID)
+ .setContentTitle("Title")
+ .setContentText("Content")
+ .setSmallIcon(R.drawable.ic_call_incoming)
+ .setPriority(NotificationCompat.PRIORITY_HIGH)
+ .setCategory(NotificationCompat.CATEGORY_CALL)
+ .addAction(R.drawable.ic_call_incoming, getString(R.string.call_notification_answer), answerCallPendingIntent)
+ .addAction(R.drawable.ic_call_incoming, getString(R.string.call_notification_reject), rejectCallPendingIntent)
+ .setAutoCancel(true)
+ .setSound(Uri.parse("android.resource://" + applicationContext.packageName + "/ring.ogg"))
+ .setFullScreenIntent(answerCallPendingIntent, true)
+ .build()
+
+ startForeground(NOTIFICATION_ID, notification)
+
+ return START_STICKY
+ }
+
+ private fun createNotificationChannel() {
+ if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) return
+
+ val channel = NotificationChannel(CHANNEL_ID, CHANNEL_NAME, NotificationManager.IMPORTANCE_HIGH).apply {
+ description = CHANNEL_DESCRIPTION
+ setSound(
+ Uri.parse("android.resource://" + applicationContext.packageName + "/ring.ogg"),
+ AudioAttributes
+ .Builder()
+ .setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION)
+ .setLegacyStreamType(AudioManager.STREAM_RING)
+ .build()
+ )
+ }
+ applicationContext.getSystemService(NotificationManager::class.java)?.createNotificationChannel(channel)
+ }
+
+ inner class CallHeadsUpServiceBinder : Binder() {
+
+ fun getService() = this@CallHeadsUpService
+ }
+
+ companion object {
+ private const val EXTRA_CALL_HEADS_UP_SERVICE_PARAMS = "EXTRA_CALL_PARAMS"
+
+ const val EXTRA_CALL_ACTION_KEY = "EXTRA_CALL_ACTION_KEY"
+ const val CALL_ACTION_ANSWER = 100
+ const val CALL_ACTION_REJECT = 101
+
+ private const val NOTIFICATION_ID = 999
+
+ fun newInstance(context: Context, callerDisplayName: String, isIncomingCall: Boolean, isVideoCall: Boolean): Intent {
+ val args = CallHeadsUpServiceArgs(callerDisplayName, isIncomingCall, isVideoCall)
+ return Intent(context, CallHeadsUpService::class.java).apply {
+ putExtra(EXTRA_CALL_HEADS_UP_SERVICE_PARAMS, args)
+ }
+ }
+ }
+}
diff --git a/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpServiceArgs.kt b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpServiceArgs.kt
new file mode 100644
index 0000000000..9769724944
--- /dev/null
+++ b/vector/src/main/java/im/vector/riotx/features/call/service/CallHeadsUpServiceArgs.kt
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2020 New Vector Ltd
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package im.vector.riotx.features.call.service
+
+import android.os.Parcelable
+import kotlinx.android.parcel.Parcelize
+
+@Parcelize
+data class CallHeadsUpServiceArgs(
+ val callerDisplayName: String,
+ val isIncomingCall: Boolean,
+ val isVideoCall: Boolean
+) : Parcelable
diff --git a/vector/src/main/java/im/vector/riotx/features/call/CallConnection.kt b/vector/src/main/java/im/vector/riotx/features/call/telecom/CallConnection.kt
similarity index 94%
rename from vector/src/main/java/im/vector/riotx/features/call/CallConnection.kt
rename to vector/src/main/java/im/vector/riotx/features/call/telecom/CallConnection.kt
index 9523b4ebdd..27bdf24570 100644
--- a/vector/src/main/java/im/vector/riotx/features/call/CallConnection.kt
+++ b/vector/src/main/java/im/vector/riotx/features/call/telecom/CallConnection.kt
@@ -14,13 +14,16 @@
* limitations under the License.
*/
-package im.vector.riotx.features.call
+package im.vector.riotx.features.call.telecom
import android.content.Context
import android.os.Build
import android.telecom.Connection
import android.telecom.DisconnectCause
import androidx.annotation.RequiresApi
+import im.vector.riotx.features.call.VectorCallViewActions
+import im.vector.riotx.features.call.VectorCallViewModel
+import im.vector.riotx.features.call.WebRtcPeerConnectionManager
import org.webrtc.Camera1Enumerator
import org.webrtc.Camera2Enumerator
import org.webrtc.IceCandidate
diff --git a/vector/src/main/java/im/vector/riotx/features/call/VectorConnectionService.kt b/vector/src/main/java/im/vector/riotx/features/call/telecom/VectorConnectionService.kt
similarity index 99%
rename from vector/src/main/java/im/vector/riotx/features/call/VectorConnectionService.kt
rename to vector/src/main/java/im/vector/riotx/features/call/telecom/VectorConnectionService.kt
index fed93c9faa..8185c9fc49 100644
--- a/vector/src/main/java/im/vector/riotx/features/call/VectorConnectionService.kt
+++ b/vector/src/main/java/im/vector/riotx/features/call/telecom/VectorConnectionService.kt
@@ -14,7 +14,7 @@
* limitations under the License.
*/
-package im.vector.riotx.features.call
+package im.vector.riotx.features.call.telecom
import android.content.ComponentName
import android.content.Intent
diff --git a/vector/src/main/java/im/vector/riotx/features/home/room/detail/RoomDetailFragment.kt b/vector/src/main/java/im/vector/riotx/features/home/room/detail/RoomDetailFragment.kt
index 2b743ed940..efa045ddd2 100644
--- a/vector/src/main/java/im/vector/riotx/features/home/room/detail/RoomDetailFragment.kt
+++ b/vector/src/main/java/im/vector/riotx/features/home/room/detail/RoomDetailFragment.kt
@@ -127,7 +127,7 @@ import im.vector.riotx.features.attachments.ContactAttachment
import im.vector.riotx.features.attachments.preview.AttachmentsPreviewActivity
import im.vector.riotx.features.attachments.preview.AttachmentsPreviewArgs
import im.vector.riotx.features.attachments.toGroupedContentAttachmentData
-import im.vector.riotx.features.call.VectorCallActivity
+import im.vector.riotx.features.call.service.CallHeadsUpService
import im.vector.riotx.features.command.Command
import im.vector.riotx.features.crypto.keysbackup.restore.KeysBackupRestoreActivity
import im.vector.riotx.features.crypto.util.toImageRes
@@ -485,9 +485,13 @@ class RoomDetailFragment @Inject constructor(
return true
}
if (item.itemId == R.id.voip_call) {
+ /*
VectorCallActivity.newIntent(requireContext(), roomDetailArgs.roomId).let {
startActivity(it)
}
+ */
+ val callHeadsUpServiceIntent = Intent(requireContext(), CallHeadsUpService::class.java)
+ ContextCompat.startForegroundService(requireContext(), callHeadsUpServiceIntent)
return true
}
return super.onOptionsItemSelected(item)
diff --git a/vector/src/main/res/drawable/ic_call_incoming.xml b/vector/src/main/res/drawable/ic_call_incoming.xml
new file mode 100644
index 0000000000..0f4e2d1d89
--- /dev/null
+++ b/vector/src/main/res/drawable/ic_call_incoming.xml
@@ -0,0 +1,5 @@
+
+
+