9dfa06ffee
Docker image / Build (linux/amd64) (push) Has been cancelled
Docker image / Build (linux/arm64) (push) Has been cancelled
Docker image / Merge release multi-arch manifest (push) Has been cancelled
Docker image / Merge debug multi-arch manifest (push) Has been cancelled
Docker image / Build public push gateway (linux/amd64) (push) Has been cancelled
Docker image / Build public push gateway (linux/arm64) (push) Has been cancelled
Docker image / Publish public push gateway image (push) Has been cancelled
Sprig image / Build (linux/amd64) (push) Has been cancelled
Sprig image / Build (linux/arm64) (push) Has been cancelled
Sprig image / Merge multi-arch manifest (push) Has been cancelled
Harbor Buzz Orchestra / Python tests and lint (push) Has been cancelled
CI / Detect Changed Paths (push) Has been cancelled
CI / Rust Lint (push) Has been cancelled
CI / Unit Tests (push) Has been cancelled
CI / Desktop Core (push) Has been cancelled
CI / Desktop Smoke E2E (1) (push) Has been cancelled
CI / Desktop Smoke E2E (2) (push) Has been cancelled
CI / Desktop Smoke E2E (3) (push) Has been cancelled
CI / Desktop Smoke E2E (4) (push) Has been cancelled
CI / Desktop (push) Has been cancelled
CI / Desktop E2E Relay (push) Has been cancelled
CI / Desktop E2E Integration (1/2) (push) Has been cancelled
CI / Desktop E2E Integration (2/2) (push) Has been cancelled
CI / Desktop E2E Integration (push) Has been cancelled
CI / Backend Integration (relay e2e) (push) Has been cancelled
CI / Relay E2E (push) Has been cancelled
CI / Web (push) Has been cancelled
CI / Mobile (push) Has been cancelled
CI / Security (push) Has been cancelled
CI / Dead Token Reference Guard (push) Has been cancelled
CI / Server Cross-Compile (aarch64-unknown-linux-musl) (push) Has been cancelled
CI / Server Cross-Compile (x86_64-unknown-linux-musl) (push) Has been cancelled
CI / Windows Rust (x86_64-pc-windows-msvc) (push) Has been cancelled
CI / Desktop Build (macOS) (push) Has been cancelled
helm chart / lint + unittest + render matrix (push) Has been cancelled
helm chart / install on kind (gated) (push) Has been cancelled
helm chart / publish chart to GHCR (push) Has been cancelled
Mesh Lifecycle / Relay-Driven Mesh Lifecycle Smoke (push) Has been cancelled
Sprig / Build (aarch64-unknown-linux-musl) (push) Has been cancelled
Sprig / Build (x86_64-unknown-linux-musl) (push) Has been cancelled
Sprig / Publish rolling release (push) Has been cancelled
Sprig / Publish tagged release (push) Has been cancelled
Signed-off-by: cls_宁波本机 <908705107@qq.com>
90 lines
2.5 KiB
Dart
90 lines
2.5 KiB
Dart
import '../../l10n/app_localizations.dart';
|
|
import '../../shared/utils/string_utils.dart';
|
|
import 'channel.dart';
|
|
|
|
const int _dmParticipantPreviewLimit = 3;
|
|
|
|
bool isGenericDmChannelName(String name) {
|
|
final normalized = name.trim().toLowerCase();
|
|
if (normalized.isEmpty ||
|
|
normalized == 'dm' ||
|
|
normalized == 'direct message' ||
|
|
normalized == 'direct messages') {
|
|
return true;
|
|
}
|
|
return RegExp(r'^group dm\s*(\(\d+\))?$').hasMatch(normalized);
|
|
}
|
|
|
|
String formatDmParticipantDisplayName(
|
|
List<String> displayNames, {
|
|
AppLocalizations? l10n,
|
|
}) {
|
|
final visible = displayNames.take(_dmParticipantPreviewLimit).toList();
|
|
final hiddenCount = displayNames.length - visible.length;
|
|
return hiddenCount > 0
|
|
? [
|
|
...visible,
|
|
l10n?.dmMore(hiddenCount) ?? '+$hiddenCount more',
|
|
].join(', ')
|
|
: visible.join(', ');
|
|
}
|
|
|
|
String resolveDmChannelDisplayLabel(
|
|
Channel channel, {
|
|
String? currentPubkey,
|
|
AppLocalizations? l10n,
|
|
}) {
|
|
if (!channel.isDm || !isGenericDmChannelName(channel.name)) {
|
|
return channel.name;
|
|
}
|
|
|
|
final normalizedCurrent = currentPubkey?.toLowerCase();
|
|
final participants = <({String label, String? pubkey})>[
|
|
for (var index = 0; index < channel.participantPubkeys.length; index++)
|
|
(
|
|
label: index < channel.participants.length
|
|
? channel.participants[index]
|
|
: shortPubkey(channel.participantPubkeys[index]),
|
|
pubkey: channel.participantPubkeys[index].toLowerCase(),
|
|
),
|
|
];
|
|
|
|
final displayParticipants = normalizedCurrent == null
|
|
? participants
|
|
: participants
|
|
.where((participant) => participant.pubkey != normalizedCurrent)
|
|
.toList();
|
|
final labels = <String>{
|
|
for (final participant
|
|
in displayParticipants.isNotEmpty ? displayParticipants : participants)
|
|
participant.label,
|
|
}.toList();
|
|
|
|
return labels.isNotEmpty
|
|
? formatDmParticipantDisplayName(labels, l10n: l10n)
|
|
: channel.name;
|
|
}
|
|
|
|
List<Channel> sortDmChannelsByDisplayLabel(
|
|
Iterable<Channel> channels, {
|
|
String? currentPubkey,
|
|
}) {
|
|
final sorted = channels.toList();
|
|
sorted.sort((left, right) {
|
|
final leftLabel = resolveDmChannelDisplayLabel(
|
|
left,
|
|
currentPubkey: currentPubkey,
|
|
);
|
|
final rightLabel = resolveDmChannelDisplayLabel(
|
|
right,
|
|
currentPubkey: currentPubkey,
|
|
);
|
|
final labelCompare = leftLabel.toLowerCase().compareTo(
|
|
rightLabel.toLowerCase(),
|
|
);
|
|
if (labelCompare != 0) return labelCompare;
|
|
return left.id.compareTo(right.id);
|
|
});
|
|
return sorted;
|
|
}
|