- use countdown timer to force stop app after 5 seconds and kill after

10 seconds from quit
- removed not needed param from findAorIndex function
This commit is contained in:
Juha Heinanen
2018-11-25 05:45:46 +02:00
parent 5be7265dac
commit 6f652f3872
5 changed files with 60 additions and 41 deletions
@@ -9,6 +9,7 @@ import android.view.MenuItem
import android.view.View import android.view.View
import android.widget.LinearLayout.LayoutParams import android.widget.LinearLayout.LayoutParams
import android.widget.* import android.widget.*
import kotlinx.android.synthetic.main.activity_account.* import kotlinx.android.synthetic.main.activity_account.*
class AccountActivity : AppCompatActivity() { class AccountActivity : AppCompatActivity() {
@@ -34,7 +35,7 @@ class AccountActivity : AppCompatActivity() {
acc = Account.find(intent.extras.getString("accp"))!! acc = Account.find(intent.extras.getString("accp"))!!
aor = acc.aor aor = acc.aor
uaIndex = UserAgent.findAorIndex(UserAgent.uas(), aor)!! uaIndex = UserAgent.findAorIndex(aor)!!
setTitle(aor.replace("sip:", "")) setTitle(aor.replace("sip:", ""))
@@ -15,10 +15,11 @@ import android.support.v4.app.NotificationCompat
import android.util.Log import android.util.Log
import android.view.View import android.view.View
import android.widget.RemoteViews import android.widget.RemoteViews
import java.io.File
import android.support.v4.content.LocalBroadcastManager import android.support.v4.content.LocalBroadcastManager
import android.os.Build import android.os.Build
import android.support.v4.app.NotificationCompat.VISIBILITY_PRIVATE import android.support.v4.app.NotificationCompat.VISIBILITY_PRIVATE
import java.io.File
import java.nio.charset.StandardCharsets import java.nio.charset.StandardCharsets
import java.io.InputStream import java.io.InputStream
import java.util.* import java.util.*
@@ -38,7 +39,6 @@ class BaresipService: Service() {
internal var rtTimer: Timer? = null internal var rtTimer: Timer? = null
internal var filesPath = "" internal var filesPath = ""
internal var restarting = false
override fun onCreate() { override fun onCreate() {
@@ -72,7 +72,7 @@ class BaresipService: Service() {
if (isConnected) { if (isConnected) {
Log.d(LOG_TAG, "Network is connected/connecting") Log.d(LOG_TAG, "Network is connected/connecting")
if (disconnected) { if (disconnected) {
UserAgent.register(uas) UserAgent.register()
disconnected = false disconnected = false
} }
} else { } else {
@@ -166,13 +166,13 @@ class BaresipService: Service() {
updateStatusNotification() updateStatusNotification()
} }
"Stop" -> { "Stop", "Stop Force" -> {
stop() if (action == "Stop") cleanService()
if (isServiceRunning) baresipStop(action == "Stop Force")
} }
"Kill" -> { "Kill" -> {
restarting = true stopped()
stop()
} }
} }
@@ -184,11 +184,11 @@ class BaresipService: Service() {
} }
override fun onDestroy() { override fun onDestroy() {
Log.d(LOG_TAG, "In onDestroy") Log.d(LOG_TAG, "In onDestroy restart baresip killed by Android")
super.onDestroy() super.onDestroy()
Log.i(LOG_TAG, "Restart baresip killed by Android") cleanService()
restarting = true val broadcastIntent = Intent("com.tutpro.baresip.Restart")
stop() sendBroadcast(broadcastIntent)
} }
private fun createNotificationChannels() { private fun createNotificationChannels() {
@@ -337,13 +337,13 @@ class BaresipService: Service() {
if (rt.isPlaying) rt.stop() if (rt.isPlaying) rt.stop()
} }
am.mode = AudioManager.MODE_IN_COMMUNICATION am.mode = AudioManager.MODE_IN_COMMUNICATION
requestAudioFocus( AudioManager.STREAM_VOICE_CALL) requestAudioFocus(AudioManager.STREAM_VOICE_CALL)
am.isSpeakerphoneOn = false am.isSpeakerphoneOn = false
} }
"call transfer" -> { "call transfer" -> {
val call = Call.find(callp) val call = Call.find(callp)
if (call == null) { if (call == null) {
Log.d("Baresip","AoR $aor call $callp to be transferred is not found") Log.d("Baresip", "AoR $aor call $callp to be transferred is not found")
return return
} }
if (!Utils.isVisible()) { if (!Utils.isVisible()) {
@@ -388,7 +388,7 @@ class BaresipService: Service() {
nm.cancel(CALL_NOTIFICATION_ID) nm.cancel(CALL_NOTIFICATION_ID)
val call = Call.find(callp) val call = Call.find(callp)
if (call == null) { if (call == null) {
Log.d("Baresip","AoR $aor call $callp that is closed is not found") Log.d("Baresip", "AoR $aor call $callp that is closed is not found")
return return
} }
Log.d("Baresip", "AoR $aor call $callp is closed") Log.d("Baresip", "AoR $aor call $callp is closed")
@@ -501,7 +501,7 @@ class BaresipService: Service() {
@Keep @Keep
fun stopped() { fun stopped() {
Log.d(LOG_TAG, "got event 'stopped'") Log.d(LOG_TAG, "'stopped' from baresip or 'Kill' from MainActivity")
isServiceRunning = false isServiceRunning = false
val intent = Intent("service event") val intent = Intent("service event")
intent.putExtra("event", "stopped") intent.putExtra("event", "stopped")
@@ -509,12 +509,11 @@ class BaresipService: Service() {
LocalBroadcastManager.getInstance(this).sendBroadcast(intent) LocalBroadcastManager.getInstance(this).sendBroadcast(intent)
stopForeground(true) stopForeground(true)
stopSelf() stopSelf()
if (restarting) restart()
} }
private fun updateStatusNotification() { private fun updateStatusNotification() {
val contentView = RemoteViews(getPackageName(), R.layout.status_notification) val contentView = RemoteViews(getPackageName(), R.layout.status_notification)
for (i: Int in 0 .. 5) { for (i: Int in 0..5) {
val resID = resources.getIdentifier("status$i", "id", packageName) val resID = resources.getIdentifier("status$i", "id", packageName)
if (i < status.size) { if (i < status.size) {
contentView.setImageViewResource(resID, status[i]) contentView.setImageViewResource(resID, status[i])
@@ -598,7 +597,7 @@ class BaresipService: Service() {
} }
} }
private fun stop() { private fun cleanService() {
uas.clear() uas.clear()
status.clear() status.clear()
history.clear() history.clear()
@@ -611,17 +610,6 @@ class BaresipService: Service() {
if (this::nm.isInitialized) nm.cancelAll() if (this::nm.isInitialized) nm.cancelAll()
if (this::wl.isInitialized && wl.isHeld) wl.release() if (this::wl.isInitialized && wl.isHeld) wl.release()
if (this::fl.isInitialized && fl.isHeld) fl.release() if (this::fl.isInitialized && fl.isHeld) fl.release()
if (isServiceRunning) {
baresipStop(forceStop)
if (!forceStop) forceStop = true
} else if (restarting)
restart()
}
private fun restart() {
restarting = false
val broadcastIntent = Intent("com.tutpro.baresip.Restart")
sendBroadcast(broadcastIntent)
} }
external fun baresipStart(path: String) external fun baresipStart(path: String)
@@ -638,7 +626,6 @@ class BaresipService: Service() {
var isServiceRunning = false var isServiceRunning = false
var disconnected = false var disconnected = false
var forceStop = false
var libraryLoaded = false var libraryLoaded = false
var uas = ArrayList<UserAgent>() var uas = ArrayList<UserAgent>()
@@ -14,6 +14,7 @@ import android.view.MenuItem
import android.content.pm.PackageManager import android.content.pm.PackageManager
import android.graphics.Color import android.graphics.Color
import android.media.* import android.media.*
import android.os.CountDownTimer
import android.support.v4.content.LocalBroadcastManager import android.support.v4.content.LocalBroadcastManager
import android.support.v7.view.menu.ActionMenuItemView import android.support.v7.view.menu.ActionMenuItemView
import android.view.inputmethod.InputMethodManager import android.view.inputmethod.InputMethodManager
@@ -50,6 +51,8 @@ class MainActivity : AppCompatActivity() {
internal lateinit var imm: InputMethodManager internal lateinit var imm: InputMethodManager
internal lateinit var nm: NotificationManager internal lateinit var nm: NotificationManager
internal lateinit var serviceEventReceiver: BroadcastReceiver internal lateinit var serviceEventReceiver: BroadcastReceiver
internal lateinit var quitTimer: CountDownTimer
internal lateinit var stopState: String
override fun onCreate(savedInstanceState: Bundle?) { override fun onCreate(savedInstanceState: Bundle?) {
@@ -96,6 +99,27 @@ class MainActivity : AppCompatActivity() {
LocalBroadcastManager.getInstance(this).registerReceiver(serviceEventReceiver, LocalBroadcastManager.getInstance(this).registerReceiver(serviceEventReceiver,
IntentFilter("service event")) IntentFilter("service event"))
stopState = "initial"
quitTimer = object: CountDownTimer(5000, 1000) {
override fun onTick(millisUntilFinished: Long) {
Log.d("Baresip", "seconds remaining: ${millisUntilFinished/1000}")
}
override fun onFinish() {
when (stopState) {
"initial" -> {
baresipService.setAction("Stop Force");
startService(baresipService)
stopState = "force"
quitTimer.start()
}
"force" -> {
baresipService.setAction("Kill");
startService(baresipService)
}
}
}
}
if (ContextCompat.checkSelfPermission(this, if (ContextCompat.checkSelfPermission(this,
Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) { Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) {
Log.w("Baresip", "Baresip does not have RECORD_AUDIO permission") Log.w("Baresip", "Baresip does not have RECORD_AUDIO permission")
@@ -378,6 +402,7 @@ class MainActivity : AppCompatActivity() {
private fun handleServiceEvent(event: String, params: ArrayList<String>) { private fun handleServiceEvent(event: String, params: ArrayList<String>) {
if (event == "stopped") { if (event == "stopped") {
Log.d("Baresip", "Handling service event 'stopped'") Log.d("Baresip", "Handling service event 'stopped'")
quitTimer.cancel()
finishAndRemoveTask() finishAndRemoveTask()
System.exit(0) System.exit(0)
return return
@@ -814,10 +839,16 @@ class MainActivity : AppCompatActivity() {
return true return true
} }
R.id.quit -> { R.id.quit -> {
if (stopState == "initial") {
Log.d("Baresip", "Quiting") Log.d("Baresip", "Quiting")
if (BaresipService.isServiceRunning) { if (BaresipService.isServiceRunning) {
baresipService.setAction("Stop"); baresipService.setAction("Stop");
startService(baresipService) startService(baresipService)
quitTimer.start()
} else {
finishAndRemoveTask()
System.exit(0)
}
} }
return true return true
} }
@@ -54,15 +54,15 @@ class UserAgent (val uap: String) {
return null return null
} }
fun findAorIndex(uas: ArrayList<UserAgent>, aor: String): Int? { fun findAorIndex(aor: String): Int? {
for (i in uas.indices) { for (i in BaresipService.uas.indices) {
if (uas[i].account.aor == aor) return i if (BaresipService.uas[i].account.aor == aor) return i
} }
return null return null
} }
fun register(uas: ArrayList<UserAgent>) { fun register() {
for (ua in uas) { for (ua in BaresipService.uas) {
if (ua.account.regint > 0) if (ua.account.regint > 0)
if (Api.ua_register(ua.uap) != 0) if (Api.ua_register(ua.uap) != 0)
Log.e("Baresip", "Failed to register ${ua.account.aor}") Log.e("Baresip", "Failed to register ${ua.account.aor}")
+1 -1
View File
@@ -11,7 +11,7 @@
- peers of calls and messages can be added to contacts by long clicks\n - peers of calls and messages can be added to contacts by long clicks\n
- long clicks can also be used to remove calls, chats, messages, and contacts\n - long clicks can also be used to remove calls, chats, messages, and contacts\n
- call click when callee has not been given can be used for re-dial\n - call click when callee has not been given can be used for re-dial\n
- quit without network connectivity needs to be forced by selecting it twice\n - quit without network connectivity may take up to 10 seconds\n
</string> </string>
<string name="noAccounts">No accounts</string> <string name="noAccounts">No accounts</string>
<string name="dispName">Name (if any) used in From URI of outbound requests.</string> <string name="dispName">Name (if any) used in From URI of outbound requests.</string>