From 050eb0af9df02902250a705deb41cf4ca2b62aeb Mon Sep 17 00:00:00 2001 From: Benoit Marty Date: Fri, 24 Jan 2020 14:29:03 +0100 Subject: [PATCH] Create dedicated View and Epoxy item for QrCode --- .../riotx/features/debug/DebugMenuActivity.kt | 4 +- .../debug/res/layout/activity_debug_menu.xml | 2 +- .../im/vector/riotx/core/qrcode/QrCode.kt | 11 +-- .../riotx/core/ui/views/QrCodeImageView.kt | 94 +++++++++++++++++++ .../VerificationChooseMethodController.kt | 16 +--- .../BottomSheetVerificationBigImageItem.kt | 10 +- .../BottomSheetVerificationQrCodeItem.kt | 56 +++++++++++ .../res/layout/item_verification_qr_code.xml | 8 ++ 8 files changed, 170 insertions(+), 31 deletions(-) create mode 100644 vector/src/main/java/im/vector/riotx/core/ui/views/QrCodeImageView.kt create mode 100644 vector/src/main/java/im/vector/riotx/features/crypto/verification/epoxy/BottomSheetVerificationQrCodeItem.kt create mode 100644 vector/src/main/res/layout/item_verification_qr_code.xml diff --git a/vector/src/debug/java/im/vector/riotx/features/debug/DebugMenuActivity.kt b/vector/src/debug/java/im/vector/riotx/features/debug/DebugMenuActivity.kt index 31998e9b99..81708182b7 100644 --- a/vector/src/debug/java/im/vector/riotx/features/debug/DebugMenuActivity.kt +++ b/vector/src/debug/java/im/vector/riotx/features/debug/DebugMenuActivity.kt @@ -29,7 +29,6 @@ import im.vector.riotx.R import im.vector.riotx.core.di.ActiveSessionHolder import im.vector.riotx.core.di.ScreenComponent import im.vector.riotx.core.platform.VectorBaseActivity -import im.vector.riotx.core.qrcode.toQrCode import im.vector.riotx.core.utils.PERMISSIONS_FOR_TAKING_PHOTO import im.vector.riotx.core.utils.PERMISSION_REQUEST_CODE_LAUNCH_CAMERA import im.vector.riotx.core.utils.allGranted @@ -56,8 +55,7 @@ class DebugMenuActivity : VectorBaseActivity() { } private fun renderQrCode(text: String) { - val qrBitmap = text.toQrCode(200, 200) - debug_qr_code.setImageBitmap(qrBitmap) + debug_qr_code.setData(text, true) } @OnClick(R.id.debug_test_text_view_link) diff --git a/vector/src/debug/res/layout/activity_debug_menu.xml b/vector/src/debug/res/layout/activity_debug_menu.xml index 272432526a..6578258e70 100644 --- a/vector/src/debug/res/layout/activity_debug_menu.xml +++ b/vector/src/debug/res/layout/activity_debug_menu.xml @@ -68,7 +68,7 @@ android:layout_height="wrap_content" android:text="Scan QR-code" /> - 0 } + ?.let { + if (animate) { + // NOT SUPPORTED YET val anim = createAnimation(it) + // NOT SUPPORTED YET setImageDrawable(anim) + // NOT SUPPORTED YET anim.start() + // NOT SUPPORTED YET setImageDrawable(BitmapDrawable(resources, it.toBitMatrix(width).toBitmap())) + val bitmap = it.toBitMatrix(width).toBitmap() + post { setImageBitmap(bitmap) } + } else { + val bitmap = it.toBitMatrix(width).toBitmap() + post { setImageBitmap(bitmap) } + } + } + } + + private fun createAnimation(data: String): AnimationDrawable { + val finalQr = data.toBitMatrix(width) + + val list = mutableListOf(finalQr) + + val random = Random(System.currentTimeMillis()) + val repeatTime = 8 + repeat(repeatTime) { index -> + val alteredQr = finalQr.clone() + for (x in 0 until alteredQr.width) { + for (y in 0 until alteredQr.height) { + if (random.nextInt(repeatTime - index) == 0) { + // Pb is that it does not toggle a whole black square, but only a pixel + alteredQr.unset(x, y) + } + } + } + list.add(alteredQr) + } + + val animDrawable = AnimationDrawable() + + list.asReversed() + .forEach { + animDrawable.addFrame(BitmapDrawable(resources, it.toBitmap()), 150) + } + + return animDrawable + } +} diff --git a/vector/src/main/java/im/vector/riotx/features/crypto/verification/choose/VerificationChooseMethodController.kt b/vector/src/main/java/im/vector/riotx/features/crypto/verification/choose/VerificationChooseMethodController.kt index 0bf38979da..f5568331a9 100644 --- a/vector/src/main/java/im/vector/riotx/features/crypto/verification/choose/VerificationChooseMethodController.kt +++ b/vector/src/main/java/im/vector/riotx/features/crypto/verification/choose/VerificationChooseMethodController.kt @@ -19,19 +19,16 @@ package im.vector.riotx.features.crypto.verification.choose import com.airbnb.epoxy.EpoxyController import im.vector.riotx.R import im.vector.riotx.core.epoxy.dividerItem -import im.vector.riotx.core.qrcode.toQrCode import im.vector.riotx.core.resources.ColorProvider import im.vector.riotx.core.resources.StringProvider -import im.vector.riotx.core.utils.DimensionConverter import im.vector.riotx.features.crypto.verification.epoxy.bottomSheetVerificationActionItem -import im.vector.riotx.features.crypto.verification.epoxy.bottomSheetVerificationBigImageItem import im.vector.riotx.features.crypto.verification.epoxy.bottomSheetVerificationNoticeItem +import im.vector.riotx.features.crypto.verification.epoxy.bottomSheetVerificationQrCodeItem import javax.inject.Inject class VerificationChooseMethodController @Inject constructor( private val stringProvider: StringProvider, - private val colorProvider: ColorProvider, - private val dimensionConverter: DimensionConverter + private val colorProvider: ColorProvider ) : EpoxyController() { var listener: Listener? = null @@ -53,13 +50,10 @@ class VerificationChooseMethodController @Inject constructor( } if (state.otherCanScanQrCode && !state.QRtext.isNullOrBlank()) { - // Generate the QR code - val size = dimensionConverter.dpToPx(180) - val qrCodeBitmap = state.QRtext.toQrCode(size, size) - - bottomSheetVerificationBigImageItem { + bottomSheetVerificationQrCodeItem { id("qr") - imageBitmap(qrCodeBitmap) + data(state.QRtext) + animate(false) } dividerItem { diff --git a/vector/src/main/java/im/vector/riotx/features/crypto/verification/epoxy/BottomSheetVerificationBigImageItem.kt b/vector/src/main/java/im/vector/riotx/features/crypto/verification/epoxy/BottomSheetVerificationBigImageItem.kt index 4973f425cd..5163f5e8a8 100644 --- a/vector/src/main/java/im/vector/riotx/features/crypto/verification/epoxy/BottomSheetVerificationBigImageItem.kt +++ b/vector/src/main/java/im/vector/riotx/features/crypto/verification/epoxy/BottomSheetVerificationBigImageItem.kt @@ -16,7 +16,6 @@ */ package im.vector.riotx.features.crypto.verification.epoxy -import android.graphics.Bitmap import android.widget.ImageView import androidx.core.view.ViewCompat import com.airbnb.epoxy.EpoxyAttribute @@ -34,18 +33,11 @@ abstract class BottomSheetVerificationBigImageItem : VectorEpoxyModel() { + + @EpoxyAttribute + lateinit var data: String + + @EpoxyAttribute + var animate = false + + @EpoxyAttribute + var contentDescription: String? = null + + override fun bind(holder: Holder) { + holder.qsrCodeImage.setData(data, animate) + + if (contentDescription == null) { + ViewCompat.setImportantForAccessibility(holder.qsrCodeImage, ViewCompat.IMPORTANT_FOR_ACCESSIBILITY_NO) + } else { + ViewCompat.setImportantForAccessibility(holder.qsrCodeImage, ViewCompat.IMPORTANT_FOR_ACCESSIBILITY_YES) + holder.qsrCodeImage.contentDescription = contentDescription + } + } + + class Holder : VectorEpoxyHolder() { + val qsrCodeImage by bind(R.id.itemVerificationBigImage) + } +} diff --git a/vector/src/main/res/layout/item_verification_qr_code.xml b/vector/src/main/res/layout/item_verification_qr_code.xml new file mode 100644 index 0000000000..2407d2754d --- /dev/null +++ b/vector/src/main/res/layout/item_verification_qr_code.xml @@ -0,0 +1,8 @@ + +