Skip to content

Commit cd3406e

Browse files
authored
Fix crash due to multiple fragment transactions (#253)
1 parent 29da131 commit cd3406e

File tree

6 files changed

+43
-112
lines changed

6 files changed

+43
-112
lines changed

CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,10 @@ All notable changes to this project will be documented in this file.
77
### Removed
88
### Fixed
99

10+
## [0.80.17]
11+
### Changed
12+
* core / ui: replace headless fragment with different result launcher for google pay
13+
1014
## [0.80.16]
1115
### Added
1216
* core: Add support for different time formats in the receipts API

core/src/main/java/io/snabble/sdk/googlepay/GooglePayHelper.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -183,7 +183,7 @@ class GooglePayHelper(
183183
val priceToPayDecimal = priceToPay.toBigDecimal().divide(100.toBigDecimal())
184184
val task = getLoadPaymentDataTask(priceToPayDecimal.toString())
185185
task.addOnCompleteListener {
186-
paymentDataLauncher!!.launch(it)
186+
paymentDataLauncher?.launch(it)
187187
}
188188

189189
return false

core/src/main/java/io/snabble/sdk/googlepay/HeadlessGooglePlayFragment.kt

Lines changed: 0 additions & 38 deletions
This file was deleted.

ui/src/main/java/io/snabble/sdk/ui/cart/CheckoutBar.kt

Lines changed: 0 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,9 @@
11
package io.snabble.sdk.ui.cart
22

3-
import android.content.ActivityNotFoundException
43
import android.content.Context
54
import android.content.DialogInterface
6-
import android.content.Intent
7-
import android.content.pm.PackageManager
8-
import android.net.Uri
95
import android.os.Bundle
106
import android.util.AttributeSet
11-
import android.util.Log
127
import android.view.KeyEvent
138
import android.view.View
149
import android.widget.ArrayAdapter
@@ -18,7 +13,6 @@ import android.widget.LinearLayout
1813
import android.widget.TextView
1914
import android.widget.Toast
2015
import androidx.appcompat.app.AlertDialog
21-
import androidx.compose.foundation.layout.add
2216
import androidx.core.view.isVisible
2317
import androidx.core.view.marginTop
2418
import androidx.fragment.app.FragmentActivity
@@ -35,8 +29,6 @@ import io.snabble.sdk.checkout.DepositReturnVoucher
3529
import io.snabble.sdk.checkout.DepositReturnVoucherState
3630
import io.snabble.sdk.config.ExternalBillingSubjectLength
3731
import io.snabble.sdk.config.ProjectId
38-
import io.snabble.sdk.extensions.getApplicationInfoCompat
39-
import io.snabble.sdk.googlepay.HeadlessGooglePlayFragment
4032
import io.snabble.sdk.shoppingcart.ShoppingCart
4133
import io.snabble.sdk.shoppingcart.data.Taxation
4234
import io.snabble.sdk.shoppingcart.data.listener.SimpleShoppingCartListener
@@ -81,7 +73,6 @@ open class CheckoutBar @JvmOverloads constructor(
8173
private val articleCount = findViewById<TextView>(R.id.article_count)
8274

8375
private lateinit var progressDialog: DelayedProgressDialog
84-
private var headlessFragment: HeadlessGooglePlayFragment? = null
8576

8677
private val paymentSelectionHelper by lazy { PaymentSelectionHelper.getInstance() }
8778
private lateinit var project: Project
@@ -110,36 +101,6 @@ open class CheckoutBar @JvmOverloads constructor(
110101
}
111102
}
112103

113-
override fun onAttachedToWindow() {
114-
super.onAttachedToWindow()
115-
if (headlessFragment == null) {
116-
val fragmentManager = requireFragmentActivity().supportFragmentManager
117-
var foundFragment =
118-
fragmentManager.findFragmentByTag(HeadlessGooglePlayFragment.TAG) as? HeadlessGooglePlayFragment
119-
120-
if (foundFragment == null) {
121-
foundFragment = HeadlessGooglePlayFragment.newInstance(Snabble.checkedInProject.value?.id)
122-
fragmentManager.beginTransaction()
123-
.add(foundFragment, HeadlessGooglePlayFragment.TAG)
124-
.commitNowAllowingStateLoss()
125-
}
126-
headlessFragment = foundFragment
127-
}
128-
}
129-
130-
override fun onDetachedFromWindow() {
131-
super.onDetachedFromWindow()
132-
val activity = requireFragmentActivity()
133-
headlessFragment?.let { fragment ->
134-
if (!activity.isChangingConfigurations) {
135-
activity.supportFragmentManager.beginTransaction()
136-
.remove(fragment)
137-
.commitAllowingStateLoss()
138-
}
139-
}
140-
headlessFragment = null
141-
}
142-
143104
private fun initBusinessLogic(project: Project) {
144105
if (this::project.isInitialized && this.project == project) {
145106
return

ui/src/main/java/io/snabble/sdk/ui/checkout/CheckoutActivity.kt

Lines changed: 19 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ package io.snabble.sdk.ui.checkout
33
import android.annotation.SuppressLint
44
import android.content.Context
55
import android.content.Intent
6-
import android.graphics.Color
76
import android.os.Bundle
87
import android.view.View
98
import android.view.ViewGroup
@@ -24,17 +23,18 @@ import androidx.navigation.NavController
2423
import androidx.navigation.NavGraph
2524
import androidx.navigation.NavOptions
2625
import androidx.navigation.fragment.NavHostFragment
26+
import com.google.android.gms.wallet.PaymentData
27+
import com.google.android.gms.wallet.contract.ApiTaskResult
28+
import com.google.android.gms.wallet.contract.TaskResultContracts
2729
import com.google.android.material.appbar.MaterialToolbar
2830
import io.snabble.sdk.InitializationState
2931
import io.snabble.sdk.PaymentMethod
3032
import io.snabble.sdk.Snabble
3133
import io.snabble.sdk.checkout.Checkout
3234
import io.snabble.sdk.checkout.CheckoutState
33-
import io.snabble.sdk.googlepay.HeadlessGooglePlayFragment
3435
import io.snabble.sdk.ui.R
3536
import io.snabble.sdk.ui.remotetheme.onToolBarColorForProject
3637
import io.snabble.sdk.ui.remotetheme.toolBarColorForProject
37-
import io.snabble.sdk.ui.utils.requireFragmentActivity
3838
import io.snabble.sdk.utils.Logger
3939

4040
class CheckoutActivity : FragmentActivity() {
@@ -71,7 +71,22 @@ class CheckoutActivity : FragmentActivity() {
7171
private lateinit var navGraph: NavGraph
7272
private lateinit var navController: NavController
7373
private var checkout: Checkout? = null
74-
private var headlessFragment: HeadlessGooglePlayFragment? = null
74+
75+
init {
76+
with(Snabble.checkedInProject.value?.googlePayHelper) {
77+
this?.paymentDataLauncher =
78+
this@CheckoutActivity.registerForActivityResult(
79+
/* contract = */ TaskResultContracts.GetPaymentDataResult()
80+
) { result: ApiTaskResult<PaymentData?>? ->
81+
result?.let {
82+
onResult(
83+
resultCode = it.status,
84+
paymentData = it.result
85+
)
86+
}
87+
}
88+
}
89+
}
7590

7691
override fun onCreate(savedInstanceState: Bundle?) {
7792
super.onCreate(savedInstanceState)
@@ -281,34 +296,4 @@ class CheckoutActivity : FragmentActivity() {
281296
setPopUpTo(currentNavigationId ?: 0, true)
282297
}.build())
283298
}
284-
285-
override fun onAttachedToWindow() {
286-
super.onAttachedToWindow()
287-
if (headlessFragment == null) {
288-
val fragmentManager = requireFragmentActivity().supportFragmentManager
289-
var foundFragment =
290-
fragmentManager.findFragmentByTag(HeadlessGooglePlayFragment.TAG) as? HeadlessGooglePlayFragment
291-
292-
if (foundFragment == null) {
293-
foundFragment = HeadlessGooglePlayFragment.newInstance(Snabble.checkedInProject.value?.id)
294-
fragmentManager.beginTransaction()
295-
.add(foundFragment, HeadlessGooglePlayFragment.TAG)
296-
.commitNowAllowingStateLoss()
297-
}
298-
headlessFragment = foundFragment
299-
}
300-
}
301-
302-
override fun onDetachedFromWindow() {
303-
super.onDetachedFromWindow()
304-
val activity = requireFragmentActivity()
305-
headlessFragment?.let { fragment ->
306-
if (!activity.isChangingConfigurations) {
307-
activity.supportFragmentManager.beginTransaction()
308-
.remove(fragment)
309-
.commitAllowingStateLoss()
310-
}
311-
}
312-
headlessFragment = null
313-
}
314299
}

ui/src/main/java/io/snabble/sdk/ui/scanner/SelfScanningFragment.kt

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@ import androidx.core.view.MenuHost
2424
import androidx.core.view.MenuProvider
2525
import androidx.core.view.ViewCompat
2626
import androidx.lifecycle.Lifecycle
27+
import com.google.android.gms.wallet.PaymentData
28+
import com.google.android.gms.wallet.contract.ApiTaskResult
29+
import com.google.android.gms.wallet.contract.TaskResultContracts
2730
import com.google.android.material.snackbar.Snackbar
2831
import io.snabble.accessibility.focusForAccessibility
2932
import io.snabble.accessibility.isTalkBackActive
@@ -68,6 +71,22 @@ open class SelfScanningFragment : BaseFragment(), MenuProvider {
6871
}
6972
}
7073

74+
init {
75+
with(Snabble.checkedInProject.value?.googlePayHelper) {
76+
this?.paymentDataLauncher =
77+
this@SelfScanningFragment.registerForActivityResult(
78+
/* contract = */ TaskResultContracts.GetPaymentDataResult()
79+
) { result: ApiTaskResult<PaymentData?>? ->
80+
result?.let {
81+
onResult(
82+
resultCode = it.status,
83+
paymentData = it.result
84+
)
85+
}
86+
}
87+
}
88+
}
89+
7190
/**
7291
* Add a listener to get notified if the camera permission has been granted
7392
*/

0 commit comments

Comments
 (0)