/*
This file is part of GNU Taler
(C) 2019 Taler Systems S.A.
GNU Taler is free software; you can redistribute it and/or modify it under the
terms of the GNU General Public License as published by the Free Software
Foundation; either version 3, or (at your option) any later version.
GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License along with
GNU Taler; see the file COPYING. If not, see
*/
package net.taler.wallet
import android.content.BroadcastReceiver
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.os.Bundle
import android.util.Log
import android.view.Menu
import android.view.MenuItem
import android.view.View
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.widget.Toolbar
import androidx.core.view.GravityCompat
import androidx.drawerlayout.widget.DrawerLayout
import androidx.lifecycle.ViewModelProviders
import androidx.navigation.NavController
import androidx.navigation.findNavController
import androidx.navigation.ui.AppBarConfiguration
import androidx.navigation.ui.setupWithNavController
import com.google.android.material.floatingactionbutton.FloatingActionButton
import com.google.android.material.navigation.NavigationView
import com.google.android.material.snackbar.Snackbar
import com.google.zxing.integration.android.IntentIntegrator
import com.google.zxing.integration.android.IntentResult
import me.zhanghai.android.materialprogressbar.MaterialProgressBar
import java.util.*
class MainActivity : AppCompatActivity(), NavigationView.OnNavigationItemSelectedListener, ResetDialogEventListener {
lateinit var model: WalletViewModel
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val toolbar: Toolbar = findViewById(R.id.toolbar)
setSupportActionBar(toolbar)
val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
val navView: NavigationView = findViewById(R.id.nav_view)
navView.menu.getItem(0).isChecked = true
val fab: FloatingActionButton = findViewById(R.id.fab)
fab.setOnClickListener {
val integrator = IntentIntegrator(this)
integrator.setPrompt("Place merchant's QR Code inside the viewfinder rectangle to initiate payment.")
integrator.initiateScan(listOf("QR_CODE"))
}
fab.hide()
navView.setNavigationItemSelectedListener(this)
val navController = findNavController(R.id.nav_host_fragment)
val appBarConfiguration =
AppBarConfiguration(setOf(R.id.showBalance, R.id.settings, R.id.walletHistory), drawerLayout)
findViewById(R.id.toolbar)
.setupWithNavController(navController, appBarConfiguration)
model = ViewModelProviders.of(this)[WalletViewModel::class.java]
val progressBar = findViewById(R.id.progress_bar)
progressBar.visibility = View.INVISIBLE
model.init()
model.getBalances()
val triggerPaymentFilter = IntentFilter(HostCardEmulatorService.TRIGGER_PAYMENT_ACTION)
registerReceiver(object : BroadcastReceiver() {
override fun onReceive(p0: Context?, p1: Intent?) {
if (navController.currentDestination?.id == R.id.promptPayment) {
return
}
val url = p1!!.extras!!.get("contractUrl") as String
findNavController(R.id.nav_host_fragment).navigate(R.id.action_global_promptPayment)
model.preparePay(url)
}
}, triggerPaymentFilter)
val nfcConnectedFilter = IntentFilter(HostCardEmulatorService.MERCHANT_NFC_CONNECTED)
registerReceiver(object : BroadcastReceiver() {
override fun onReceive(p0: Context?, p1: Intent?) {
Log.v(TAG, "got MERCHANT_NFC_CONNECTED")
//model.startTunnel()
}
}, nfcConnectedFilter)
val nfcDisconnectedFilter = IntentFilter(HostCardEmulatorService.MERCHANT_NFC_DISCONNECTED)
registerReceiver(object : BroadcastReceiver() {
override fun onReceive(p0: Context?, p1: Intent?) {
Log.v(TAG, "got MERCHANT_NFC_DISCONNECTED")
//model.stopTunnel()
}
}, nfcDisconnectedFilter)
IntentFilter(HostCardEmulatorService.HTTP_TUNNEL_RESPONSE).also { filter ->
registerReceiver(object : BroadcastReceiver() {
override fun onReceive(p0: Context?, p1: Intent?) {
Log.v("taler-tunnel", "got HTTP_TUNNEL_RESPONSE")
model.tunnelResponse(p1!!.getStringExtra("response"))
}
}, filter)
}
if (intent.action == Intent.ACTION_VIEW) {
val uri = intent.dataString
if (uri != null)
handleTalerUri(uri, "intent")
}
//model.startTunnel()
}
override fun onBackPressed() {
val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
drawerLayout.closeDrawer(GravityCompat.START)
} else {
super.onBackPressed()
}
}
override fun onCreateOptionsMenu(menu: Menu): Boolean {
// Inflate the menu; this adds items to the action bar if it is present.
//menuInflater.inflate(R.menu.main, menu)
return false
}
override fun onOptionsItemSelected(item: MenuItem): Boolean {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
return when (item.itemId) {
R.id.action_settings -> true
else -> super.onOptionsItemSelected(item)
}
}
override fun onNavigationItemSelected(item: MenuItem): Boolean {
// Handle navigation view item clicks here.
when (item.itemId) {
R.id.nav_home -> {
findNavController(R.id.nav_host_fragment).navigate(R.id.showBalance)
}
R.id.nav_settings -> {
findNavController(R.id.nav_host_fragment).navigate(R.id.settings)
}
R.id.nav_history -> {
findNavController(R.id.nav_host_fragment).navigate(R.id.walletHistory)
}
}
val drawerLayout: DrawerLayout = findViewById(R.id.drawer_layout)
drawerLayout.closeDrawer(GravityCompat.START)
return true
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (requestCode != IntentIntegrator.REQUEST_CODE) {
return
}
val scanResult: IntentResult? = IntentIntegrator.parseActivityResult(requestCode, resultCode, data)
if (scanResult == null || scanResult.contents == null) {
val bar: Snackbar = Snackbar.make(
findViewById(R.id.nav_host_fragment),
"QR Code scan canceled.",
Snackbar.LENGTH_SHORT
)
bar.show()
return
}
val url = scanResult.contents!!
handleTalerUri(url, "QR code")
}
private fun handleTalerUri(url: String, from: String) {
when {
url.toLowerCase(Locale.ROOT).startsWith("taler://pay/") -> {
Log.v(TAG, "navigating!")
findNavController(R.id.nav_host_fragment).navigate(R.id.action_showBalance_to_promptPayment)
model.preparePay(url)
}
url.toLowerCase(Locale.ROOT).startsWith("taler://withdraw/") -> {
Log.v(TAG, "navigating!")
findNavController(R.id.nav_host_fragment).navigate(R.id.action_showBalance_to_promptWithdraw)
model.getWithdrawalInfo(url)
}
else -> {
val bar: Snackbar = Snackbar.make(
findViewById(R.id.nav_host_fragment),
"URL from $from doesn't contain Taler payment.",
Snackbar.LENGTH_SHORT
)
bar.show()
}
}
}
override fun onResetConfirmed() {
model.dangerouslyReset()
val snackbar = Snackbar.make(findViewById(R.id.nav_host_fragment), "Wallet has been reset", Snackbar.LENGTH_SHORT)
snackbar.show()
}
override fun onResetCancelled() {
val snackbar = Snackbar.make(findViewById(R.id.nav_host_fragment), "Reset cancelled", Snackbar.LENGTH_SHORT)
snackbar.show()
}
}