QRScannerCameraX icon indicating copy to clipboard operation
QRScannerCameraX copied to clipboard

When I start activity it starts many times

Open cafeed28 opened this issue 4 years ago • 2 comments

When I start activity in startCamera it starts many times and to close all QrInfoActivity activities you need to press "back" button many times, you can see it if you add messages to the log. Part a new code of startCamera:

val qrCodeAnalyzer = QrCodeAnalyzer { qrCodes ->
     qrCodes.forEach {
          Log.d("QrTag", "MainActivity: QR Code detected: ${it.rawValue}.")
          val qrinfoIntent = Intent(this, QrInfoActivity::class.java)
          val qrinfoString = it.rawValue.toString()
          qrinfoIntent.putExtra(QrInfoActivity.QR_INFO_STRING, qrinfoString)
          startActivity(qrinfoIntent)
     }
}

Part a code of QrInfoActivity:

companion object{
    const val QR_INFO_STRING = "qr_info_string"
}

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_qr_info)
    Log.d("QrTag", "QrInfoActivity: Started")
    showQrInfo()
}
    
    fun showQrInfo(){
        val qrinfo = intent.getStringExtra(QR_INFO_STRING)
        textView_info.text = qrinfo
        Log.d("QrTag", "QrInfoActivity: showQrInfo called with qrinfo: ${qrinfo}")
    }

Screenshot of logcat: https://prnt.sc/ru918q

How to fix it?

cafeed28 avatar Apr 06 '20 18:04 cafeed28

I think following code might be problem:

val qrCodeAnalyzer = QrCodeAnalyzer { qrCodes ->
     qrCodes.forEach {
          Log.d("QrTag", "MainActivity: QR Code detected: ${it.rawValue}.")
          val qrinfoIntent = Intent(this, QrInfoActivity::class.java)
          val qrinfoString = it.rawValue.toString()
          qrinfoIntent.putExtra(QrInfoActivity.QR_INFO_STRING, qrinfoString)
          startActivity(qrinfoIntent)
     }
}

Simple solution can be that Instead of looping through all qrCodes, you can get first item in list and start activitiy once:

val qrCodeAnalyzer = QrCodeAnalyzer { qrCodes ->
     qrCodes.firstOrNull()?.let {
          Log.d("QrTag", "MainActivity: QR Code detected: ${it.rawValue}.")
          val qrinfoIntent = Intent(this, QrInfoActivity::class.java)
          val qrinfoString = it.rawValue.toString()
          qrinfoIntent.putExtra(QrInfoActivity.QR_INFO_STRING, qrinfoString)
          startActivity(qrinfoIntent)
     }
}

natiginfo avatar Apr 09 '20 06:04 natiginfo

Your solution didn't resolve the issue for me.

Could it possibly be a threading error? It seems like the startCamera() method get called a lot of times, which causes a huge lag on the preview TextureView.

Also, I use my webcam as back camera for the AVD emulator in Android, it has LED indicator when it's in use. This keeps blinking rapidly.

This problem also occurs with your repo when I cloned it.

EDIT (found a solution): It was indeed a threading issue, which can be resolved with an Atomic Boolean like this:

CLASS LEVEL
val atomicBoolean: AtomicBoolean = false

...

val qrCodeAnalyzer = QrCodeAnalyzer { qrCodes ->
     qrCodes.firstOrNull()?.let {
          Log.d("QrTag", "MainActivity: QR Code detected: ${it.rawValue}.")
         
          if (atomicBoolean.compareAndSet(false, true)) {
          val qrinfoIntent = Intent(this, QrInfoActivity::class.java)
          val qrinfoString = it.rawValue.toString()
          qrinfoIntent.putExtra(QrInfoActivity.QR_INFO_STRING, qrinfoString)
          startActivity(qrinfoIntent)
          }
     }
}

This guarantees your activity will only be started once, when launched by a thread.

Tom-DK avatar May 12 '20 18:05 Tom-DK