From d3c7ce29ca32e3274fc94c312567641032070ada Mon Sep 17 00:00:00 2001 From: Juha Heinanen Date: Sun, 3 Jun 2018 18:08:31 +0300 Subject: [PATCH] added account_[set_]sipnat API functions added ua_update_account API function go directly to settings of new account fixed some main activity layout bugs keep main activity interactive when screen is locked removed aor from UserAgent class added register method to UserAgent class added foregrounded and isDeviceLocked util functions updated libbaresip distribution --- app/src/main/cpp/baresip.c | 70 ++++++++++---- .../main/kotlin/com/tutpro/baresip/Account.kt | 4 +- .../com/tutpro/baresip/AccountActivity.kt | 32 ++++--- .../com/tutpro/baresip/AccountListAdapter.kt | 7 +- .../com/tutpro/baresip/AccountsActivity.kt | 29 ++++-- .../main/kotlin/com/tutpro/baresip/Call.kt | 9 +- .../kotlin/com/tutpro/baresip/MainActivity.kt | 94 ++++++++++--------- .../com/tutpro/baresip/UaSpinnerAdapter.kt | 2 +- .../kotlin/com/tutpro/baresip/UserAgent.kt | 29 +++++- .../main/kotlin/com/tutpro/baresip/Utils.kt | 30 ++++++ 10 files changed, 204 insertions(+), 102 deletions(-) diff --git a/app/src/main/cpp/baresip.c b/app/src/main/cpp/baresip.c index 13d75d6b..5a52d79d 100644 --- a/app/src/main/cpp/baresip.c +++ b/app/src/main/cpp/baresip.c @@ -274,8 +274,8 @@ Java_com_tutpro_baresip_MainActivity_baresipStart(JNIEnv *env, jobject instance, ua = le->data; sprintf(ua_buf, "%lu", (unsigned long)ua); jstring javaUA = (*env)->NewStringUTF(env, ua_buf); - LOGD("adding account %s/%s\n", ua_aor(ua), ua_buf); - jmethodID accountId = (*env)->GetMethodID(env, pctx->mainActivityClz, "addAccount", + LOGD("adding UA for AoR %s/%s\n", ua_aor(ua), ua_buf); + jmethodID accountId = (*env)->GetMethodID(env, pctx->mainActivityClz, "addUA", "(Ljava/lang/String;)V"); (*env)->CallVoidMethod(env, pctx->mainActivityObj, accountId, javaUA); (*env)->DeleteLocalRef(env, javaUA); @@ -569,29 +569,49 @@ Java_com_tutpro_baresip_AccountKt_account_1set_1mediaenc(JNIEnv *env, jobject th (*env)->ReleaseStringUTFChars(env, javaMencid, mencid); return res; } +JNIEXPORT jstring JNICALL +Java_com_tutpro_baresip_AccountKt_account_1sipnat(JNIEnv *env, jobject thiz, jstring javaAcc) +{ + const char *native_acc = (*env)->GetStringUTFChars(env, javaAcc, 0); + struct account *acc = (struct account *) strtoul(native_acc, NULL, 10); + (*env)->ReleaseStringUTFChars(env, javaAcc, native_acc); + if (acc) { + const char *sipnat = account_sipnat(acc); + if (sipnat) return (*env)->NewStringUTF(env, sipnat); + } + return (*env)->NewStringUTF(env, ""); +} JNIEXPORT jint JNICALL -Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1alloc(JNIEnv *env, jobject thiz, - jstring javaSipUri) { - const char *sip_uri = (*env)->GetStringUTFChars(env, javaSipUri, 0); - struct ua *ua; - LOGD("allocating UA '%s'\n", sip_uri); - int res = ua_alloc(&ua, sip_uri); - (*env)->ReleaseStringUTFChars(env, javaSipUri, sip_uri); - if (res == 0) { - char ua_buf[64]; - UpdateContext *pctx = (UpdateContext*)(&g_ctx); - sprintf(ua_buf, "%lu", (unsigned long)ua); - jstring javaUA = (*env)->NewStringUTF(env, ua_buf); - LOGD("adding account %s/%s\n", ua_aor(ua), ua_buf); - jmethodID accountId = (*env)->GetMethodID(env, pctx->mainActivityClz, "addAccount", - "(Ljava/lang/String;)V"); - (*env)->CallVoidMethod(env, pctx->mainActivityObj, accountId, javaUA); - (*env)->DeleteLocalRef(env, javaUA); - } +Java_com_tutpro_baresip_AccountKt_account_1set_1sipnat(JNIEnv *env, jobject thiz, + jstring javaAcc, jstring javaSipNat) { + const char *native_acc = (*env)->GetStringUTFChars(env, javaAcc, 0); + struct account *acc = (struct account *)strtoul(native_acc, NULL, 10); + (*env)->ReleaseStringUTFChars(env, javaAcc, native_acc); + const char *sipnat = (*env)->GetStringUTFChars(env, javaSipNat, 0); + int res; + if (strlen(sipnat) > 0) + res = account_set_sipnat(acc, sipnat); + else + res = account_set_sipnat(acc, NULL); + (*env)->ReleaseStringUTFChars(env, javaSipNat, sipnat); return res; } +JNIEXPORT jstring JNICALL +Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1alloc(JNIEnv *env, jobject thiz, + jstring javaUri) { + const char *uri = (*env)->GetStringUTFChars(env, javaUri, 0); + struct ua *ua; + LOGD("allocating UA '%s'\n", uri); + int res = ua_alloc(&ua, uri); + (*env)->ReleaseStringUTFChars(env, javaUri, uri); + char ua_buf[64]; + ua_buf[0] = '\0'; + if (res == 0) sprintf(ua_buf, "%lu", (unsigned long)ua); + return (*env)->NewStringUTF(env, ua_buf); +} + JNIEXPORT jint JNICALL Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1register(JNIEnv *env, jobject thiz, jstring javaUA) @@ -622,6 +642,16 @@ Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1isregistered(JNIEnv *env, j return ua_isregistered(ua); } +JNIEXPORT jint JNICALL +Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1update_1account(JNIEnv *env, jobject thiz, + jstring javaUA) +{ + const char *native_ua = (*env)->GetStringUTFChars(env, javaUA, 0); + struct ua *ua = (struct ua *)strtoul(native_ua, NULL, 10); + (*env)->ReleaseStringUTFChars(env, javaUA, native_ua); + return ua_update_account(ua); +} + JNIEXPORT void JNICALL Java_com_tutpro_baresip_UserAgent_00024Companion_ua_1destroy(JNIEnv *env, jobject thiz, jstring javaUA) diff --git a/app/src/main/kotlin/com/tutpro/baresip/Account.kt b/app/src/main/kotlin/com/tutpro/baresip/Account.kt index 2ff1b6fc..622adbed 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/Account.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/Account.kt @@ -93,7 +93,7 @@ class Account(val accp: String) { fun findUA(aor: String): UserAgent? { for (ua in MainActivity.uas) { - if (ua.aor == aor) return ua + if (ua.account.aor == aor) return ua } return null } @@ -117,6 +117,8 @@ external fun account_auth_pass(acc: String): String external fun account_set_auth_pass(acc: String, pass: String): Int external fun account_outbound(acc: String, ix: Int): String external fun account_set_outbound(acc: String, ob: String, ix: Int): Int +external fun account_sipnat(acc: String): String +external fun account_set_sipnat(acc: String, sipnat: String): Int external fun account_audio_codec(acc: String, ix: Int): String external fun account_regint(acc: String): Int external fun account_set_regint(acc: String, regint: Int): Int diff --git a/app/src/main/kotlin/com/tutpro/baresip/AccountActivity.kt b/app/src/main/kotlin/com/tutpro/baresip/AccountActivity.kt index c2b8578a..2988746c 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/AccountActivity.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/AccountActivity.kt @@ -1,5 +1,6 @@ package com.tutpro.baresip +import android.app.Activity import android.content.Intent import android.os.Bundle import android.support.v7.app.AppCompatActivity @@ -58,7 +59,7 @@ class AccountActivity : AppCompatActivity() { while (newCodecs.size < audioCodecs.size) newCodecs.add("") val layout = findViewById(R.id.CodecSpinners) as LinearLayout - var spinnerList = Array(audioCodecs.size, {i -> ArrayList()}) + val spinnerList = Array(audioCodecs.size, {_ -> ArrayList()}) for (i in audioCodecs.indices) { val spinner = Spinner(applicationContext) spinner.id = i + 100 @@ -121,7 +122,7 @@ class AccountActivity : AppCompatActivity() { override fun onOptionsItemSelected(item: MenuItem): Boolean { - val i = Intent(this, MainActivity::class.java) + val intent = Intent(this, MainActivity::class.java) if (item.itemId == R.id.checkIcon) { @@ -163,7 +164,7 @@ class AccountActivity : AppCompatActivity() { if (Utils.checkPrintASCII(ap)) { if (account_set_auth_pass(acc.accp, ap) == 0) { acc.authPass = account_auth_pass(acc.accp) - Log.d("Baresip", "New auth password is ${acc.authPass}") + // Log.d("Baresip", "New auth password is ${acc.authPass}") save = true } else { Log.e("Baresip", "Setting of auth pass failed") @@ -199,6 +200,10 @@ class AccountActivity : AppCompatActivity() { } Log.d("Baresip", "New outbound proxies are ${outbound}") acc.outbound = outbound + if (outbound.isEmpty()) + account_set_sipnat(acc.accp, "") + else + account_set_sipnat(acc.accp, "outbound") save = true } @@ -253,24 +258,25 @@ class AccountActivity : AppCompatActivity() { if (save) { AccountsActivity.saveAccounts() - if (acc.regint > 0) { - Log.d("Baresip", "Registering ${acc.aor}") - UserAgent.ua_register(Account.findUA(acc.aor)!!.uap) + val uaIndex = UserAgent.findAorIndex(MainActivity.uas, aor) + if (uaIndex != null) { + if (UserAgent.ua_update_account(MainActivity.uas[uaIndex].uap) != 0) + Log.e("Baresip", "Failed to update UA with AoR $aor") + else if (acc.regint > 0) + UserAgent.ua_register(MainActivity.uas[uaIndex].uap) + } else { + Log.e("Baresip", "Did not find UA matching AoR $aor") } } - setResult(RESULT_OK, i) + + setResult(RESULT_OK, intent) finish() return true } else if (item.itemId == android.R.id.home) { Log.d("Baresip", "Back array was pressed at Account") - i.putExtra("action", "cancel") - if (acc.regint > 0) { - Log.d("Baresip", "Registering ${acc.aor}") - UserAgent.ua_register(Account.findUA(acc.aor)!!.uap) - } - setResult(RESULT_OK, i) + setResult(RESULT_CANCELED, intent) finish() return true diff --git a/app/src/main/kotlin/com/tutpro/baresip/AccountListAdapter.kt b/app/src/main/kotlin/com/tutpro/baresip/AccountListAdapter.kt index e8388409..ef73a1ec 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/AccountListAdapter.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/AccountListAdapter.kt @@ -37,12 +37,9 @@ class AccountListAdapter(private val cxt: Context, private val rows: ArrayList Log.d("Baresip", "Delete button clicked") val deleteDialog = AlertDialog.Builder(cxt) - deleteDialog.setMessage("Do you want to delete account ${MainActivity.uas[position].aor}?") + deleteDialog.setMessage("Do you want to delete account ${MainActivity.uas[position].account.aor}?") deleteDialog.setPositiveButton("Delete") { dialog, _ -> - if (UserAgent.ua_isregistered(MainActivity.uas[position].uap)) { - UserAgent.ua_unregister(MainActivity.uas[position].uap) - } - UserAgent.ua_destroy(MainActivity.uas[position].uap) + MainActivity.uas[position].destroy() MainActivity.uas.remove(MainActivity.uas[position]) MainActivity.images.removeAt(position) AccountsActivity.saveAccounts() diff --git a/app/src/main/kotlin/com/tutpro/baresip/AccountsActivity.kt b/app/src/main/kotlin/com/tutpro/baresip/AccountsActivity.kt index 54575ad3..fcd450b4 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/AccountsActivity.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/AccountsActivity.kt @@ -15,6 +15,7 @@ import java.util.ArrayList class AccountsActivity : AppCompatActivity() { internal var aor: String = "" + internal lateinit var alAdapter: AccountListAdapter public override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) @@ -22,7 +23,7 @@ class AccountsActivity : AppCompatActivity() { val listview = findViewById(R.id.accounts) as ListView generateAccounts() - val alAdapter = AccountListAdapter(this, accounts) + alAdapter = AccountListAdapter(this, accounts) listview.adapter = alAdapter val addAccountButton = findViewById(R.id.addAccount) as ImageButton @@ -37,17 +38,26 @@ class AccountsActivity : AppCompatActivity() { } else if (Account.exists(MainActivity.uas, aor)) { Log.e("Baresip", "Account $aor already exists") } else { - if (UserAgent.ua_alloc("<$aor>;regq=0.5;pubint=0;regint=600") != 0) { - Log.e("Baresip", "Failed to allocate UA $aor") + val ua = UserAgent.uaAlloc("<$aor>;regq=0.5;pubint=0;regint=0") + if (ua == null) { + Log.e("Baresip", "Failed to allocate UA for $aor") Utils.alertView(this, "Notice", - "Failed to allocate new account. Check your network connection.") + "Failed to allocate new account.") } else { - SystemClock.sleep(200); newAorView.setText("") - newAorView.setHint("SIP URI user@domain") + newAorView.hint = "SIP URI user@domain" newAorView.clearFocus() + MainActivity.uas.add(ua) + MainActivity.images.add(R.drawable.dot_yellow) + generateAccounts() + alAdapter.notifyDataSetChanged() saveAccounts() - recreate() + val i = Intent(this, AccountActivity::class.java) + val b = Bundle() + b.putString("accp", ua.account.accp) + i.putExtras(b) + startActivity(i) + // recreate() } } } @@ -84,7 +94,8 @@ class AccountsActivity : AppCompatActivity() { posAtAccounts.clear() var i = 0; for (ua in MainActivity.uas) { - accounts.add(AccountRow(ua.aor.replace("sip:", ""), R.drawable.action_remove)) + accounts.add(AccountRow(ua.account.aor.replace("sip:", ""), + R.drawable.action_remove)) posAtAccounts.add(i) i++ } @@ -95,7 +106,7 @@ class AccountsActivity : AppCompatActivity() { for (a in Account.accounts()) accounts = accounts + a.print() + "\n" val path = MainActivity.filesPath + "/accounts" Utils.putFileContents(File(path), accounts) -// Log.d("Baresip", "Saved accounts '${accounts}' to '$path") + // Log.d("Baresip", "Saved accounts '${accounts}' to '$path") } } diff --git a/app/src/main/kotlin/com/tutpro/baresip/Call.kt b/app/src/main/kotlin/com/tutpro/baresip/Call.kt index f89d3863..42ca3b30 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/Call.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/Call.kt @@ -36,13 +36,8 @@ class Call(val callp: String, val ua: UserAgent, val peerURI: String, val dir: S return null } - fun index(calls: ArrayList, call: Call, dir: String): Int { - var res = 0 - for (c in calls) { - if (c == call) return res - if ((dir == "") || (call.dir == dir)) res++ - } - return res + fun uaCallIndex(calls: ArrayList, ua: UserAgent, call: Call, dir: String): Int { + return uaCalls(calls, ua, dir).indexOf(call) } } diff --git a/app/src/main/kotlin/com/tutpro/baresip/MainActivity.kt b/app/src/main/kotlin/com/tutpro/baresip/MainActivity.kt index f1ee454f..a3176a68 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/MainActivity.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/MainActivity.kt @@ -56,6 +56,11 @@ class MainActivity : AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) + + window.addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD or + WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED or + WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON) + setContentView(R.layout.activity_main) appContext = applicationContext @@ -75,22 +80,17 @@ class MainActivity : AppCompatActivity() { wl = pm.newWakeLock(PowerManager.FULL_WAKE_LOCK or PowerManager.ACQUIRE_CAUSES_WAKEUP, "") - window.addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD or - WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED or - WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON) - nb = NotificationCompat.Builder(this) nb.setVisibility(VISIBILITY_PUBLIC).setOngoing(true).setSmallIcon(R.drawable.ic_stat) .setContentIntent( PendingIntent.getActivity(this, NOTIFICATION_ID, Intent(this, MainActivity::class.java) .setAction(Intent.ACTION_MAIN) - .addCategory(Intent.CATEGORY_LAUNCHER) - .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK), + .addCategory(Intent.CATEGORY_LAUNCHER), PendingIntent.FLAG_UPDATE_CURRENT)) .setContent(RemoteViews(getPackageName(), R.layout.notification)) - val intentFilter = IntentFilter("android.net.conn.CONNECTIVITY_CHANGE") + val netFilter = IntentFilter("android.net.conn.CONNECTIVITY_CHANGE") receiver = object : BroadcastReceiver() { override fun onReceive(context: Context, intent: Intent) { val intentExtras = intent.extras @@ -99,7 +99,7 @@ class MainActivity : AppCompatActivity() { if (running) UserAgent.register(uas) } } - registerReceiver(receiver, intentFilter) + registerReceiver(receiver, netFilter) aorSpinner = findViewById(R.id.AoRList) as Spinner uaAdapter = UaSpinnerAdapter(applicationContext, uas, images) @@ -150,15 +150,11 @@ class MainActivity : AppCompatActivity() { val `in` = Call.uaCalls(calls, ua, "in") val view_count = layout.childCount Log.d("Baresip", "View count is $view_count") - if (view_count > 7) { - // remove all incoming call views + if (view_count > 7) layout.removeViews(7, view_count - 7) - } - for (c in `in`) { - for (call_index in Call.calls(calls, "in").indices) { + for (c in `in`) + for (call_index in Call.uaCalls(calls, ua,"in").indices) addCallViews(ua, c, (call_index + 1) * 10) - } - } } override fun onNothingSelected(parent: AdapterView<*>) { @@ -278,7 +274,7 @@ class MainActivity : AppCompatActivity() { callButton.tag = "Call" callButton.setOnClickListener { val ua = uas[aorSpinner.selectedItemPosition] - val aor = ua.aor + val aor = ua.account.aor when (callButton.tag) { "Call" -> { val calleeText = (findViewById(R.id.callee) as EditText).text.toString() @@ -341,7 +337,7 @@ class MainActivity : AppCompatActivity() { historyButton.setOnClickListener { val i = Intent(this@MainActivity, HistoryActivity::class.java) val b = Bundle() - b.putString("aor", uas[aorSpinner.selectedItemPosition].aor) + b.putString("aor", uas[aorSpinner.selectedItemPosition].account.aor) i.putExtras(b) startActivityForResult(i, HISTORY_CODE) } @@ -362,6 +358,17 @@ class MainActivity : AppCompatActivity() { } } + override fun onPause() { + super.onPause() + Log.d("Baresip", "Paused") + } + + override fun onResume() { + super.onResume() + Log.d("Baresip", "Resumed") + nm.cancel(INCOMING_ID) + } + override fun onConfigurationChanged(newConfig: Configuration) { super.onConfigurationChanged(newConfig) if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) { @@ -405,11 +412,10 @@ class MainActivity : AppCompatActivity() { am.isSpeakerphoneOn = !am.isSpeakerphoneOn val speakerIcon = findViewById(R.id.speakerIcon) as ActionMenuItemView if (am.isSpeakerphoneOn) - // speakerIcon.setIcon(ContextCompat.getDrawable(this, R.drawable.speaker_on)) speakerIcon.setBackgroundColor(Color.rgb(0x04, 0xb4, 0x04)) else - // speakerIcon.setBackgroundColor(resources.getColor(R.color.colorPrimary, applicationContext.theme)) - speakerIcon.setBackgroundColor(resources.getColor(R.color.colorPrimary)) + speakerIcon.setBackgroundColor(ContextCompat.getColor(applicationContext, + R.color.colorPrimary)) return true } R.id.accounts -> { @@ -489,7 +495,7 @@ class MainActivity : AppCompatActivity() { } if (resultCode == RESULT_CANCELED) { Log.d("Baresip", "History canceled") - if (History.aorHistory(history, uas[aorSpinner.selectedItemPosition].aor) == 0) { + if (History.aorHistory(history, uas[aorSpinner.selectedItemPosition].account.aor) == 0) { holdButton.visibility = View.INVISIBLE } } @@ -727,16 +733,16 @@ class MainActivity : AppCompatActivity() { } @Keep - fun addAccount(ua: String) { - val userAgent = UserAgent(ua) - uas.add(userAgent) - if (UserAgent.ua_isregistered(ua)) { + fun addUA(uap: String) { + val ua = UserAgent(uap) + uas.add(ua) + if (UserAgent.ua_isregistered(uap)) { Log.d("Baresip", "Ua $ua is registered") images.add(R.drawable.dot_green) } else { Log.d("Baresip", "Ua $ua is NOT registered") images.add(R.drawable.dot_yellow) - UserAgent.ua_register(ua) + ua.register() } this@MainActivity.runOnUiThread { uaAdapter.notifyDataSetChanged() @@ -753,14 +759,14 @@ class MainActivity : AppCompatActivity() { Log.e("Baresip", "Update status did not find ua $uap") return } - val aor = ua.aor + val aor = ua.account.aor val acc = ua.account val ev = event.split(",") Log.d("Baresip", "Handling event ${ev[0]} for $uap/$callp/$aor") for (account_index in uas.indices) { - if (uas[account_index].aor == aor) { + if (uas[account_index].account.aor == aor) { Log.d("Baresip", "Found AoR at index $account_index") when (ev[0]) { "registering", "unregistering" -> { @@ -796,13 +802,16 @@ class MainActivity : AppCompatActivity() { this@MainActivity.runOnUiThread { calls.add(new_call) if (ua != uas[aorSpinner.selectedItemPosition]) - aorSpinner.setSelection(UserAgent.findAorIndex(uas, aor)!!) - addCallViews(ua, new_call, Call.calls(calls, "in").size * 10) + aorSpinner.setSelection(account_index) + else + addCallViews(ua, new_call, Call.uaCalls(calls, ua,"in").size * 10) am.mode = AudioManager.MODE_RINGTONE } - val i = Intent(this, MainActivity::class.java) - i.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT) - startActivity(i) + if (Utils.foregrounded()) { + val i = Intent(this, MainActivity::class.java) + i.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT) + startActivity(i) + } } "call established" -> { val call = Call.find(calls, callp) @@ -845,7 +854,7 @@ class MainActivity : AppCompatActivity() { this@MainActivity.runOnUiThread { if (ua == uas[aorSpinner.selectedItemPosition]) { if (acc.mediaenc != "") { - val inIndex = Call.index(calls, call, "in") + val inIndex = Call.uaCallIndex(calls, ua, call, "in") val view_id = (inIndex + 1) * 10 + 3 val securityButton = findViewById(view_id) as ImageButton securityButton.setImageResource(R.drawable.box_red) @@ -895,7 +904,7 @@ class MainActivity : AppCompatActivity() { securityButton.visibility = View.VISIBLE } else { if (ua == uas[aorSpinner.selectedItemPosition]) { - val view_id = (Call.index(calls, call, "in") + 1) * 10 + 3 + val view_id = (Call.uaCallIndex(calls, ua, call,"in") + 1) * 10 + 3 val securityButton = layout.findViewById(view_id) as ImageButton securityButton.setImageResource(security) setSecurityButtonTag(securityButton, security) @@ -913,7 +922,7 @@ class MainActivity : AppCompatActivity() { securityButton.visibility = View.VISIBLE } else { if (ua == uas[aorSpinner.selectedItemPosition]) { - val view_id = (Call.index(calls, call, "in") + 1) * 10 + 3 + val view_id = (Call.uaCallIndex(calls, ua, call,"in") + 1) * 10 + 3 val securityButton = layout.findViewById(view_id) as ImageButton securityButton.setImageResource(R.drawable.box_yellow) securityButton.tag = "yellow" @@ -944,7 +953,7 @@ class MainActivity : AppCompatActivity() { } else { this@MainActivity.runOnUiThread { if (ua == uas[aorSpinner.selectedItemPosition]) { - val view_id = (Call.index(calls, call, "in") + 1) * 10 + 3 + val view_id = (Call.uaCallIndex(calls, ua, call, "in") + 1) * 10 + 3 val securityButton = layout.findViewById(view_id) as ImageButton securityButton.setImageResource(R.drawable.box_green) securityButton.tag = "green" @@ -962,10 +971,10 @@ class MainActivity : AppCompatActivity() { if (call.dir == "in") { Log.d("Baresip", "Removing inbound call ${uap}/${callp}/" + call.peerURI) - val inIndex = Call.index(calls, call, "in") + val inIndex = Call.uaCallIndex(calls, ua, call, "in") val view_id = (inIndex + 1) * 10 - val remove_count = Call.calls(calls, "in").size - inIndex - calls.removeAt(Call.index(calls, call, "")) + val remove_count = Call.uaCalls(calls, ua,"in").size - inIndex + calls.remove(call) this@MainActivity.runOnUiThread { if (ua == uas[aorSpinner.selectedItemPosition]) { if (callButton.tag == "Call") { @@ -974,7 +983,7 @@ class MainActivity : AppCompatActivity() { val caller_heading = layout.findViewById(view_id) val view_index = layout.indexOfChild(caller_heading) layout.removeViews(view_index, 3 * remove_count) - val callsIn = Call.calls(calls, "in") + val callsIn = Call.uaCalls(calls, ua,"in") for (i in inIndex until callsIn.size) { this@MainActivity.addCallViews(ua, callsIn[i], (i + 1) * 10) } @@ -1005,7 +1014,7 @@ class MainActivity : AppCompatActivity() { dtmf.visibility = View.INVISIBLE historyButton.visibility = View.VISIBLE } - calls.removeAt(Call.index(calls, call, "")) + calls.remove(call) } if (!call.hasHistory) { if (History.aorHistory(history, aor) > HISTORY_SIZE) @@ -1079,6 +1088,7 @@ class MainActivity : AppCompatActivity() { const val RECORD_AUDIO_PERMISSION = 1 const val HISTORY_SIZE = 100 const val NOTIFICATION_ID = 10 + const val INCOMING_ID = 11 external fun contacts_remove() external fun contact_add(contact: String) diff --git a/app/src/main/kotlin/com/tutpro/baresip/UaSpinnerAdapter.kt b/app/src/main/kotlin/com/tutpro/baresip/UaSpinnerAdapter.kt index 018c8fe5..37d94fb1 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/UaSpinnerAdapter.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/UaSpinnerAdapter.kt @@ -27,7 +27,7 @@ class UaSpinnerAdapter(private val cxt: Context, private val uas: ArrayList 0) { + Log.d("Baresip", "Registering ${account.aor} UA ${uap}") + val accp = ua_account(uap) + val reg_int = account_regint(accp) + Log.d("Baresip", "reg_int is $reg_int") + if (ua_register(uap) != 0) + Log.e("Baresip", "Registering failed") + } + } + + fun destroy() { + ua_destroy(uap) + } companion object { - external fun ua_alloc(uri: String): Int + external fun ua_alloc(uri: String): String + external fun ua_update_account(ua: String): Int external fun ua_destroy(ua: String) external fun ua_register(ua: String): Int external fun ua_isregistered(ua: String): Boolean external fun ua_unregister(ua: String) + fun uaAlloc(uri: String): UserAgent? { + val uap = ua_alloc(uri) + if (uap != "") return UserAgent(uap) + return null + } + fun find(uas: ArrayList, uap: String): UserAgent? { for (ua in uas) { if (ua.uap == uap) return ua @@ -24,7 +45,7 @@ class UserAgent (val uap: String) { fun findAorIndex(uas: ArrayList, aor: String): Int? { for (i in uas.indices) { - if (uas[i].aor == aor) return i + if (uas[i].account.aor == aor) return i } return null } @@ -32,7 +53,7 @@ class UserAgent (val uap: String) { fun register(uas: ArrayList) { for (ua in uas) { if (ua_register(ua.uap) != 0) - Log.e("Baresip", "Failed to register ${ua.aor}") + Log.e("Baresip", "Failed to register ${ua.account.aor}") } } } diff --git a/app/src/main/kotlin/com/tutpro/baresip/Utils.kt b/app/src/main/kotlin/com/tutpro/baresip/Utils.kt index 3dc50fc5..b635777c 100644 --- a/app/src/main/kotlin/com/tutpro/baresip/Utils.kt +++ b/app/src/main/kotlin/com/tutpro/baresip/Utils.kt @@ -1,11 +1,17 @@ package com.tutpro.baresip +import android.app.ActivityManager import android.content.Context import android.support.v7.app.AlertDialog import android.util.Log import android.net.ConnectivityManager import java.io.* +import android.os.Build +import android.os.PowerManager +import android.app.KeyguardManager + + object Utils { @@ -127,6 +133,30 @@ object Utils { } } + fun foregrounded(): Boolean { + val appProcessInfo = ActivityManager.RunningAppProcessInfo() + ActivityManager.getMyMemoryState(appProcessInfo); + return ((appProcessInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) or + (appProcessInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE)) + } + + fun isDeviceLocked(context: Context): Boolean { + val isLocked: Boolean + + val keyguardManager = context.getSystemService(Context.KEYGUARD_SERVICE) as KeyguardManager + val inKeyguardRestrictedInputMode = keyguardManager.inKeyguardRestrictedInputMode() + + if (inKeyguardRestrictedInputMode) { + isLocked = true + } else { + val powerManager = context.getSystemService(Context.POWER_SERVICE) as PowerManager + isLocked = !powerManager.isInteractive + } + + Log.d("Baresip", "Now device is ${if (isLocked) "locked" else "unlocked"}") + return isLocked + } + external fun cmd_exec(cmd: String): Int external fun uri_decode(uri: String): Boolean external fun audio_codecs(): String