refactor url previews

This commit is contained in:
Henry Hiles 2026-04-05 11:26:03 -04:00
commit 639d27a5fc
Signed by: Henry-Hiles
SSH key fingerprint: SHA256:VKQUdS31Q90KvX7EkKMHMBpUspcmItAh86a+v7PGiIs
2 changed files with 13 additions and 10 deletions

View file

@ -7,17 +7,14 @@ import "package:nexus/controllers/header_controller.dart";
import "package:nexus/helpers/extensions/mxc_to_https.dart"; import "package:nexus/helpers/extensions/mxc_to_https.dart";
class UrlPreviewController extends AsyncNotifier<LinkPreviewData?> { class UrlPreviewController extends AsyncNotifier<LinkPreviewData?> {
final TextMessage message; final String link;
UrlPreviewController(this.message); UrlPreviewController(this.link);
@override @override
Future<LinkPreviewData?> build() async { Future<LinkPreviewData?> build() async {
final homeserver = ref.watch(ClientStateController.provider)?.homeserverUrl; final homeserver = ref.watch(ClientStateController.provider)?.homeserverUrl;
final link = RegExp(
r'''https?://[^\s"'<>]+''',
).allMatches(message.text).firstOrNull?.group(0);
if (homeserver != null && link != null && !link.contains("matrix.to")) { if (homeserver != null && !link.contains("matrix.to")) {
{ {
final response = await get( final response = await get(
Uri.parse(homeserver) Uri.parse(homeserver)
@ -57,7 +54,7 @@ class UrlPreviewController extends AsyncNotifier<LinkPreviewData?> {
} }
static final provider = AsyncNotifierProvider.autoDispose static final provider = AsyncNotifierProvider.autoDispose
.family<UrlPreviewController, LinkPreviewData?, TextMessage>( .family<UrlPreviewController, LinkPreviewData?, String>(
UrlPreviewController.new, UrlPreviewController.new,
); );
} }

View file

@ -40,6 +40,12 @@ class TextMessageWrapper extends ConsumerWidget {
final colorScheme = theme.colorScheme; final colorScheme = theme.colorScheme;
final textMessage = message is TextMessage ? message as TextMessage : null; final textMessage = message is TextMessage ? message as TextMessage : null;
final link = textMessage == null
? null
: RegExp(
r'''https?://[^\s"'<>]+''',
).allMatches(textMessage.text).firstOrNull?.group(0);
return MessageWrapper( return MessageWrapper(
message, message,
ClipRRect( ClipRRect(
@ -97,9 +103,9 @@ class TextMessageWrapper extends ConsumerWidget {
), ),
if (textMessage?.editedAt != null) if (textMessage?.editedAt != null)
Text("(edited)", style: theme.textTheme.labelSmall), Text("(edited)", style: theme.textTheme.labelSmall),
if (textMessage != null) if (link != null)
ref ref
.watch(UrlPreviewController.provider(textMessage)) .watch(UrlPreviewController.provider(link))
.betterWhen( .betterWhen(
loading: SizedBox.shrink, loading: SizedBox.shrink,
data: (preview) => preview == null data: (preview) => preview == null
@ -117,7 +123,7 @@ class TextMessageWrapper extends ConsumerWidget {
fit: BoxFit.cover, fit: BoxFit.cover,
errorBuilder: (_, _, _) => SizedBox.shrink(), errorBuilder: (_, _, _) => SizedBox.shrink(),
), ),
text: textMessage.text, text: link,
backgroundColor: isSentByMe backgroundColor: isSentByMe
? colorScheme.inversePrimary ? colorScheme.inversePrimary
: colorScheme.surfaceContainerLow, : colorScheme.surfaceContainerLow,