diff --git a/app/src/main/java/com/vitorpamplona/amethyst/service/lnurl/LnWithdrawalUtil.kt b/app/src/main/java/com/vitorpamplona/amethyst/service/lnurl/LnWithdrawalUtil.kt new file mode 100644 index 000000000..bc5d60083 --- /dev/null +++ b/app/src/main/java/com/vitorpamplona/amethyst/service/lnurl/LnWithdrawalUtil.kt @@ -0,0 +1,29 @@ +package com.vitorpamplona.amethyst.service.lnurl + +import java.util.regex.Pattern + +object LnWithdrawalUtil { + private val withdrawalPattern = Pattern.compile( + "lnurl.*", + Pattern.CASE_INSENSITIVE + ) + + /** + * Finds LN withdrawal in the provided input string and returns it. + * For example for input = "aaa bbb lnbc1xxx ccc" it will return "lnbc1xxx" + * It will only return the first withdrawal found in the input. + * + * @return the invoice if it was found. null for null input or if no invoice is found + */ + fun findWithdrawal(input: String?): String? { + if (input == null) { + return null + } + val matcher = withdrawalPattern.matcher(input) + return if (matcher.find()) { + matcher.group() + } else { + null + } + } +} diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/components/ClickableWithdrawal.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/components/ClickableWithdrawal.kt new file mode 100644 index 000000000..418e25b45 --- /dev/null +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/components/ClickableWithdrawal.kt @@ -0,0 +1,27 @@ +package com.vitorpamplona.amethyst.ui.components + +import android.content.Intent +import android.net.Uri +import androidx.compose.foundation.text.ClickableText +import androidx.compose.material.LocalTextStyle +import androidx.compose.material.MaterialTheme +import androidx.compose.runtime.Composable +import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.text.AnnotatedString +import androidx.core.content.ContextCompat + +@Composable +fun ClickableWithdrawal(withdrawalString: String) { + val context = LocalContext.current + + ClickableText( + text = AnnotatedString("$withdrawalString "), + onClick = { + runCatching { + val intent = Intent(Intent.ACTION_VIEW, Uri.parse("lightning:$withdrawalString")) + ContextCompat.startActivity(context, intent, null) + } + }, + style = LocalTextStyle.current.copy(color = MaterialTheme.colors.primary) + ) +} diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/components/RichTextViewer.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/components/RichTextViewer.kt index a4afa60fb..a184d420c 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/components/RichTextViewer.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/components/RichTextViewer.kt @@ -37,6 +37,7 @@ import com.halilibo.richtext.ui.resolveDefaults import com.vitorpamplona.amethyst.model.LocalCache import com.vitorpamplona.amethyst.model.checkForHashtagWithIcon import com.vitorpamplona.amethyst.service.lnurl.LnInvoiceUtil +import com.vitorpamplona.amethyst.service.lnurl.LnWithdrawalUtil import com.vitorpamplona.amethyst.service.nip19.Nip19 import com.vitorpamplona.amethyst.ui.note.NoteCompose import com.vitorpamplona.amethyst.ui.screen.loggedIn.AccountViewModel @@ -138,6 +139,7 @@ fun RichTextViewer( if (canPreview) { // Explicit URL val lnInvoice = LnInvoiceUtil.findInvoice(word) + val lnWithdrawal = LnWithdrawalUtil.findWithdrawal(word) if (lnInvoice != null) { InvoicePreview(lnInvoice) } else if (isValidURL(word)) { @@ -149,6 +151,8 @@ fun RichTextViewer( } else { UrlPreview(word, "$word ") } + } else if (lnWithdrawal != null) { + ClickableWithdrawal(withdrawalString = lnWithdrawal) } else if (Patterns.EMAIL_ADDRESS.matcher(word).matches()) { ClickableEmail(word) } else if (Patterns.PHONE.matcher(word).matches() && word.length > 6) {