parent
5ee3449f02
commit
c8e1aef74b
5 changed files with 115 additions and 4 deletions
|
|
@ -371,6 +371,12 @@ class ClientController extends AsyncNotifier<int> {
|
||||||
Future<void> exchangeToken(OAuthExchangeTokenRequest request) async =>
|
Future<void> exchangeToken(OAuthExchangeTokenRequest request) async =>
|
||||||
await _sendCommand("oauth_exchange_token", request.toJson());
|
await _sendCommand("oauth_exchange_token", request.toJson());
|
||||||
|
|
||||||
|
Future<IList<String>> getMutualRooms(String userId) async => IList(
|
||||||
|
((await _sendCommand("get_mutual_rooms", {"user_id": userId}))["joined"]
|
||||||
|
as List?)
|
||||||
|
?.cast<String>(),
|
||||||
|
);
|
||||||
|
|
||||||
Future<SpecVersionsResponse> getSpecVersions() async =>
|
Future<SpecVersionsResponse> getSpecVersions() async =>
|
||||||
.fromJson(await _sendCommand("get_versions"));
|
.fromJson(await _sendCommand("get_versions"));
|
||||||
|
|
||||||
|
|
|
||||||
15
lib/controllers/mutual_rooms.dart
Normal file
15
lib/controllers/mutual_rooms.dart
Normal file
|
|
@ -0,0 +1,15 @@
|
||||||
|
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||||
|
import "package:hooks_riverpod/hooks_riverpod.dart";
|
||||||
|
import "package:nexus/controllers/client.dart";
|
||||||
|
|
||||||
|
class MutualRoomsController(final String userId)
|
||||||
|
extends AsyncNotifier<IList<String>> {
|
||||||
|
@override
|
||||||
|
Future<IList<String>> build() =>
|
||||||
|
ref.read(ClientController.provider.notifier).getMutualRooms(userId);
|
||||||
|
|
||||||
|
static final provider = AsyncNotifierProvider.family
|
||||||
|
.autoDispose<MutualRoomsController, IList<String>, String>(
|
||||||
|
MutualRoomsController.new,
|
||||||
|
);
|
||||||
|
}
|
||||||
72
lib/widgets/mutual_rooms_sheet.dart
Normal file
72
lib/widgets/mutual_rooms_sheet.dart
Normal file
|
|
@ -0,0 +1,72 @@
|
||||||
|
import "package:fast_immutable_collections/fast_immutable_collections.dart";
|
||||||
|
import "package:hooks_riverpod/hooks_riverpod.dart";
|
||||||
|
import "package:material_ui/material_ui.dart";
|
||||||
|
import "package:nexus/controllers/mutual_rooms.dart";
|
||||||
|
import "package:nexus/controllers/rooms.dart";
|
||||||
|
import "package:nexus/controllers/sidebar_page.dart";
|
||||||
|
import "package:nexus/helpers/extensions/better_when.dart";
|
||||||
|
import "package:nexus/helpers/extensions/focus_room.dart";
|
||||||
|
import "package:nexus/widgets/avatar_or_hash.dart";
|
||||||
|
import "package:nexus/widgets/sheet_layout.dart";
|
||||||
|
|
||||||
|
/// The rooms the user shares with [userId].
|
||||||
|
class const MutualRoomsSheet(final String userId, {super.key})
|
||||||
|
extends ConsumerWidget {
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context, WidgetRef ref) => SheetLayout(
|
||||||
|
title: Text("Mutual Rooms"),
|
||||||
|
actions: [
|
||||||
|
TextButton(onPressed: Navigator.of(context).pop, child: Text("Close")),
|
||||||
|
],
|
||||||
|
children: [
|
||||||
|
ref
|
||||||
|
.watch(MutualRoomsController.provider(userId))
|
||||||
|
.betterWhen(
|
||||||
|
data: (roomIds) {
|
||||||
|
final rooms = ref.watch(
|
||||||
|
RoomsController.provider.select(
|
||||||
|
(allRooms) => roomIds
|
||||||
|
.map((roomId) => allRooms[roomId]?.metadata)
|
||||||
|
.nonNulls
|
||||||
|
.toIList(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
return rooms.isEmpty
|
||||||
|
? Text("No mutual rooms")
|
||||||
|
: Column(
|
||||||
|
children: rooms
|
||||||
|
.map(
|
||||||
|
(room) => ListTile(
|
||||||
|
leading: AvatarOrHash(
|
||||||
|
room.avatar,
|
||||||
|
room.name ?? "Unnamed Room",
|
||||||
|
fallback: Icon(Icons.numbers),
|
||||||
|
),
|
||||||
|
title: Text(
|
||||||
|
room.name ?? "Unnamed Room",
|
||||||
|
overflow: .ellipsis,
|
||||||
|
),
|
||||||
|
onTap: () async {
|
||||||
|
final container = ProviderScope.containerOf(
|
||||||
|
context,
|
||||||
|
);
|
||||||
|
// Closes the user popover under this too
|
||||||
|
Navigator.of(context)
|
||||||
|
.popUntil((route) => route.isFirst);
|
||||||
|
await container.focusRoom(room.id);
|
||||||
|
container
|
||||||
|
.read(
|
||||||
|
SidebarPageController.provider.notifier,
|
||||||
|
)
|
||||||
|
.set(.rooms);
|
||||||
|
},
|
||||||
|
),
|
||||||
|
)
|
||||||
|
.toList(),
|
||||||
|
);
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -38,7 +38,6 @@ class const ReadReceiptsSheet(
|
||||||
final name = member?.displayName ?? receipt.userId.localpart;
|
final name = member?.displayName ?? receipt.userId.localpart;
|
||||||
|
|
||||||
return ListTile(
|
return ListTile(
|
||||||
contentPadding: .zero,
|
|
||||||
leading: AvatarOrHash(member?.avatarUrl, name, dimension: 40),
|
leading: AvatarOrHash(member?.avatarUrl, name, dimension: 40),
|
||||||
title: Text(name, overflow: .ellipsis),
|
title: Text(name, overflow: .ellipsis),
|
||||||
subtitle: Text(receipt.userId, overflow: .ellipsis),
|
subtitle: Text(receipt.userId, overflow: .ellipsis),
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@ import "package:intl/intl.dart";
|
||||||
import "package:m3e_buttons/m3e_buttons.dart";
|
import "package:m3e_buttons/m3e_buttons.dart";
|
||||||
import "package:nexus/controllers/client.dart";
|
import "package:nexus/controllers/client.dart";
|
||||||
import "package:nexus/controllers/client_state.dart";
|
import "package:nexus/controllers/client_state.dart";
|
||||||
|
import "package:nexus/controllers/mutual_rooms.dart";
|
||||||
import "package:nexus/controllers/power_level.dart";
|
import "package:nexus/controllers/power_level.dart";
|
||||||
import "package:nexus/controllers/profile.dart";
|
import "package:nexus/controllers/profile.dart";
|
||||||
import "package:nexus/controllers/rooms.dart";
|
import "package:nexus/controllers/rooms.dart";
|
||||||
|
|
@ -18,6 +19,7 @@ import "package:nexus/helpers/extensions/show_adaptive_sheet.dart";
|
||||||
import "package:nexus/helpers/extensions/get_localpart.dart";
|
import "package:nexus/helpers/extensions/get_localpart.dart";
|
||||||
import "package:nexus/widgets/error_dialog.dart";
|
import "package:nexus/widgets/error_dialog.dart";
|
||||||
import "package:nexus/widgets/loading.dart";
|
import "package:nexus/widgets/loading.dart";
|
||||||
|
import "package:nexus/widgets/mutual_rooms_sheet.dart";
|
||||||
import "package:nexus/models/membership_action.dart";
|
import "package:nexus/models/membership_action.dart";
|
||||||
import "package:nexus/widgets/avatar_or_hash.dart";
|
import "package:nexus/widgets/avatar_or_hash.dart";
|
||||||
import "package:nexus/main.dart";
|
import "package:nexus/main.dart";
|
||||||
|
|
@ -141,9 +143,6 @@ final class const UserBottomSheet(
|
||||||
loading: () => Text(""),
|
loading: () => Text(""),
|
||||||
data: (profileResponse) => Column(
|
data: (profileResponse) => Column(
|
||||||
children: [
|
children: [
|
||||||
if (profileResponse.profile.timezone == null &&
|
|
||||||
profileResponse.profile.pronouns.isEmpty)
|
|
||||||
Text(""),
|
|
||||||
Wrap(
|
Wrap(
|
||||||
crossAxisAlignment: .center,
|
crossAxisAlignment: .center,
|
||||||
alignment: .center,
|
alignment: .center,
|
||||||
|
|
@ -195,6 +194,26 @@ final class const UserBottomSheet(
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
||||||
|
if (userId != ref.watch(ClientStateController.provider)?.userId)
|
||||||
|
switch (ref.watch(MutualRoomsController.provider(userId))) {
|
||||||
|
AsyncData(value: final roomIds) => switch (ref.watch(
|
||||||
|
RoomsController.provider.select(
|
||||||
|
(rooms) => roomIds.where(rooms.containsKey).length,
|
||||||
|
),
|
||||||
|
)) {
|
||||||
|
0 => SizedBox.shrink(),
|
||||||
|
final count => TextButton(
|
||||||
|
onPressed: () => context.showAdaptiveSheet(
|
||||||
|
(_) => MutualRoomsSheet(userId),
|
||||||
|
),
|
||||||
|
child: Text(
|
||||||
|
"$count mutual ${Intl.plural(count, one: "room", other: "rooms")}",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
},
|
||||||
|
_ => SizedBox.shrink(),
|
||||||
|
},
|
||||||
|
|
||||||
SizedBox(height: 8),
|
SizedBox(height: 8),
|
||||||
if (userId !=
|
if (userId !=
|
||||||
ref.watch(ClientStateController.provider)?.userId) ...[
|
ref.watch(ClientStateController.provider)?.userId) ...[
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue