Google Pay AutoResolveHelper.resolveTask () не вызывает onActivityResult во фрагменте - PullRequest
0 голосов
/ 03 января 2019

Я реализовал Google Pay в приложении и отправляю запрос paymentData. Я использую AutoResolveHelper для отображения нижнего листа, а затем получаю результаты с помощью onActivityResult.Я делаю этот запрос от фрагмента, а не от деятельности.Так что я передаю родительскую активность вот так.

 paymentsClient?.loadPaymentData(gpayViewModel.paymentDataRequest)?.let { task ->
            AutoResolveHelper.resolveTask(task, requireActivity(), LOAD_PAYMENT_DATA_REQUEST_CODE)
        }

проблема в том, что этот AutoResolveHelper не вызывает onActivityResult для Fragment, а только для Activity.

Я прочитал что-то вроде этого:

Если вы вызываете startActivityForResult () из фрагмента, вам следует вызывать startActivityForResult (), а не getActivity (). StartActivityForResult (),так как это приведет к фрагменту onActivityResult ().

Таким образом, предполагается, что когда AutoResolveHelper вызывает startActivityForResult () для переданной активности, тогда onActivityResult фрагмента никогда не будет вызываться.

Так что теперь мой единственный вариант - реализовать onActivityResult в Activity и каким-то образом передать управление из этого Activity моему дочернему фрагменту, но для этого нужен некоторый шаблонный код, и поскольку мой фрагмент можно использовать повторно, это решение не является идеальным.

Тем временем я заметил, что этот код правильно запускает startActivityForResult, а onActivityResult фрагмента вызывается правильно:

 val intent = Intent(activity, CardIOActivity::class.java)
        intent.putExtra(CardIOActivity.EXTRA_REQUIRE_EXPIRY, true)
        intent.putExtra(CardIOActivity.EXTRA_REQUIRE_CVV, true)
        intent.putExtra(CardIOActivity.EXTRA_REQUIRE_CARDHOLDER_NAME, true)

        startActivityForResult(intent, CARD_IO_REQUEST_CODE)

Так что я могу как-то заменить этот AutoResolveHelper.resolveTask (), чтобы выполнить эту задачутаким образом, что onActivityResult не понадобится или я мог бы запустить ActivityForResult сам?

Ответы [ 2 ]

0 голосов
/ 26 мая 2019

Вот ссылка на рабочий код.Это может быть не идеальный подход, но он выполняет свою работу.https://readyandroid.wordpress.com/onactivityresult-is-not-being-called-in-fragment/

0 голосов
/ 12 января 2019

На сегодняшний день получение результата привязано к Activity. Частично это объясняется тем, что библиотека не совсем точно использует startActivityForResult для запуска этого процесса; и Fragment поддержка тех же функций на данный момент ограничена.

В настоящее время существует два основных способа обойти это (они также были опубликованы в других темах). Тем не менее, я лично чувствую, что смешивание обязанностей между фрагментом и действием не обеспечивает большую ясность кода и ясную логику, поэтому на данный момент я бы рассмотрел только тот подход, когда действие отвечает за вызов AutoResolveHelper захватывает результат и делится им с фрагментом. Вместо того, чтобы вызывать действие из фрагмента, я бы подумал сделать это через контракт / интерфейс, чтобы уменьшить уровень связи между ними.

Упрощенным примером может быть что-то вроде:

interface PaymentsContract {
    fun loadPaymentData(request: PaymentDataRequest, requestCode: Int)
}

Наличие действия, реализующего его, и передача его в качестве ссылки на фрагмент во время создания позволяет вашему фрагменту оставаться повторно используемым и независимым от действия.

Как только результат будет готов, вы можете найти нужный фрагмент и распространить на него метод onActivityResult или использовать аналогичный подход, основанный на контракте, и для фрагмента.

Было бы полезно узнать больше о ваших конкретных случаях использования, чтобы лучше понять обоснование для обработки этой логики внутри фрагментов, и в конечном итоге передать эту обратную связь команде, чтобы рассмотреть ее для будущих разработок.

Надеюсь, это полезно.

РЕДАКТИРОВАТЬ: Другая альтернатива интерфейсам - это использовать лямбда-выражения, чтобы ваш фрагмент знал о вызываемом объекте, который был определен где-то еще (например: в вашей деятельности), и который должен вызываться, когда что-то происходит (например, когда ваш пользователь нажимает кнопку "Оплатить с помощью Google Pay").

...