✨ Publisher list on account
This commit is contained in:
		| @@ -9,6 +9,7 @@ import 'package:gap/gap.dart'; | |||||||
| import 'package:hooks_riverpod/hooks_riverpod.dart'; | import 'package:hooks_riverpod/hooks_riverpod.dart'; | ||||||
| import 'package:island/models/chat.dart'; | import 'package:island/models/chat.dart'; | ||||||
| import 'package:island/models/developer.dart'; | import 'package:island/models/developer.dart'; | ||||||
|  | import 'package:island/models/publisher.dart'; | ||||||
| import 'package:island/models/relationship.dart'; | import 'package:island/models/relationship.dart'; | ||||||
| import 'package:island/models/account.dart'; | import 'package:island/models/account.dart'; | ||||||
| import 'package:island/pods/config.dart'; | import 'package:island/pods/config.dart'; | ||||||
| @@ -224,7 +225,13 @@ class _AccountProfileDetail extends StatelessWidget { | |||||||
|           spacing: 6, |           spacing: 6, | ||||||
|           children: [ |           children: [ | ||||||
|             Icon(Symbols.fingerprint, size: 17, fill: 1).padding(right: 2), |             Icon(Symbols.fingerprint, size: 17, fill: 1).padding(right: 2), | ||||||
|             Text(data.id), |             Flexible( | ||||||
|  |               child: Text( | ||||||
|  |                 data.id, | ||||||
|  |                 maxLines: 1, | ||||||
|  |                 overflow: TextOverflow.ellipsis, | ||||||
|  |               ), | ||||||
|  |             ), | ||||||
|           ], |           ], | ||||||
|         ), |         ), | ||||||
|         onTap: () { |         onTap: () { | ||||||
| @@ -314,6 +321,56 @@ class _AccountProfileLinks extends StatelessWidget { | |||||||
|   } |   } | ||||||
| } | } | ||||||
|  |  | ||||||
|  | class _AccountPublisherList extends StatelessWidget { | ||||||
|  |   final List<SnPublisher> publishers; | ||||||
|  |  | ||||||
|  |   const _AccountPublisherList({required this.publishers}); | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   Widget build(BuildContext context) { | ||||||
|  |     if (publishers.isEmpty) return const SizedBox.shrink(); | ||||||
|  |     return Card( | ||||||
|  |       child: Column( | ||||||
|  |         crossAxisAlignment: CrossAxisAlignment.start, | ||||||
|  |         children: [ | ||||||
|  |           Text( | ||||||
|  |             'publishers', | ||||||
|  |           ).tr().bold().padding(horizontal: 24, top: 12, bottom: 4), | ||||||
|  |           for (final publisher in publishers) | ||||||
|  |             ListTile( | ||||||
|  |               title: Text(publisher.nick), | ||||||
|  |               subtitle: | ||||||
|  |                   publisher.bio.isNotEmpty | ||||||
|  |                       ? Text( | ||||||
|  |                         publisher.bio, | ||||||
|  |                         maxLines: 3, | ||||||
|  |                         overflow: TextOverflow.ellipsis, | ||||||
|  |                       ) | ||||||
|  |                       : null, | ||||||
|  |               leading: ProfilePictureWidget( | ||||||
|  |                 file: publisher.picture, | ||||||
|  |                 borderRadius: publisher.type == 1 ? 8 : null, | ||||||
|  |               ), | ||||||
|  |               isThreeLine: true, | ||||||
|  |               contentPadding: EdgeInsets.symmetric(horizontal: 24), | ||||||
|  |               trailing: const Icon(Symbols.chevron_right), | ||||||
|  |               shape: RoundedRectangleBorder( | ||||||
|  |                 borderRadius: const BorderRadius.all(Radius.circular(8)), | ||||||
|  |               ), | ||||||
|  |               onTap: () { | ||||||
|  |                 Navigator.pop(context, true); | ||||||
|  |                 context.pushNamed( | ||||||
|  |                   'publisherProfile', | ||||||
|  |                   pathParameters: {'name': publisher.name}, | ||||||
|  |                 ); | ||||||
|  |               }, | ||||||
|  |             ), | ||||||
|  |         ], | ||||||
|  |       ), | ||||||
|  |     ); | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
| class _AccountAction extends StatelessWidget { | class _AccountAction extends StatelessWidget { | ||||||
|   final SnAccount data; |   final SnAccount data; | ||||||
|   final AsyncValue<SnRelationship?> accountRelationship; |   final AsyncValue<SnRelationship?> accountRelationship; | ||||||
| @@ -335,6 +392,7 @@ class _AccountAction extends StatelessWidget { | |||||||
|   Widget build(BuildContext context) { |   Widget build(BuildContext context) { | ||||||
|     return Card( |     return Card( | ||||||
|       child: Column( |       child: Column( | ||||||
|  |         spacing: 8, | ||||||
|         children: [ |         children: [ | ||||||
|           Row( |           Row( | ||||||
|             spacing: 8, |             spacing: 8, | ||||||
| @@ -427,6 +485,7 @@ class _AccountAction extends StatelessWidget { | |||||||
|                   color: Theme.of(context).colorScheme.onError, |                   color: Theme.of(context).colorScheme.onError, | ||||||
|                 ), |                 ), | ||||||
|                 style: ButtonStyle( |                 style: ButtonStyle( | ||||||
|  |                   visualDensity: VisualDensity.compact, | ||||||
|                   backgroundColor: WidgetStatePropertyAll( |                   backgroundColor: WidgetStatePropertyAll( | ||||||
|                     Theme.of(context).colorScheme.error, |                     Theme.of(context).colorScheme.error, | ||||||
|                   ), |                   ), | ||||||
| @@ -533,6 +592,20 @@ Future<SnDeveloper?> accountBotDeveloper(Ref ref, String uname) async { | |||||||
|   } |   } | ||||||
| } | } | ||||||
|  |  | ||||||
|  | @riverpod | ||||||
|  | Future<List<SnPublisher>> accountPublishers(Ref ref, String id) async { | ||||||
|  |   final apiClient = ref.watch(apiClientProvider); | ||||||
|  |   try { | ||||||
|  |     final resp = await apiClient.get('/sphere/publishers/of/$id'); | ||||||
|  |     return resp.data | ||||||
|  |         .map((e) => SnPublisher.fromJson(e)) | ||||||
|  |         .cast<SnPublisher>() | ||||||
|  |         .toList(); | ||||||
|  |   } catch (err) { | ||||||
|  |     return []; | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
| class AccountProfileScreen extends HookConsumerWidget { | class AccountProfileScreen extends HookConsumerWidget { | ||||||
|   final String name; |   final String name; | ||||||
|   const AccountProfileScreen({super.key, required this.name}); |   const AccountProfileScreen({super.key, required this.name}); | ||||||
| @@ -625,8 +698,9 @@ class AccountProfileScreen extends HookConsumerWidget { | |||||||
|     ); |     ); | ||||||
|  |  | ||||||
|     return account.when( |     return account.when( | ||||||
|       data: |       data: (data) { | ||||||
|           (data) => AppScaffold( |         final accountPublishers = ref.watch(accountPublishersProvider(data.id)); | ||||||
|  |         return AppScaffold( | ||||||
|           isNoBackground: false, |           isNoBackground: false, | ||||||
|           appBar: |           appBar: | ||||||
|               isWideScreen(context) |               isWideScreen(context) | ||||||
| @@ -657,9 +731,7 @@ class AccountProfileScreen extends HookConsumerWidget { | |||||||
|                             style: TextStyle( |                             style: TextStyle( | ||||||
|                               color: |                               color: | ||||||
|                                   appbarColor.value ?? |                                   appbarColor.value ?? | ||||||
|                                     Theme.of( |                                   Theme.of(context).appBarTheme.foregroundColor, | ||||||
|                                       context, |  | ||||||
|                                     ).appBarTheme.foregroundColor, |  | ||||||
|                               shadows: [appbarShadow], |                               shadows: [appbarShadow], | ||||||
|                             ), |                             ), | ||||||
|                           ), |                           ), | ||||||
| @@ -728,6 +800,11 @@ class AccountProfileScreen extends HookConsumerWidget { | |||||||
|                         child: CustomScrollView( |                         child: CustomScrollView( | ||||||
|                           slivers: [ |                           slivers: [ | ||||||
|                             SliverGap(24), |                             SliverGap(24), | ||||||
|  |                             SliverToBoxAdapter( | ||||||
|  |                               child: _AccountPublisherList( | ||||||
|  |                                 publishers: accountPublishers.value ?? [], | ||||||
|  |                               ), | ||||||
|  |                             ), | ||||||
|                             if (user.value != null && !isCurrentUser) |                             if (user.value != null && !isCurrentUser) | ||||||
|                               SliverToBoxAdapter( |                               SliverToBoxAdapter( | ||||||
|                                 child: _AccountAction( |                                 child: _AccountAction( | ||||||
| @@ -837,6 +914,11 @@ class AccountProfileScreen extends HookConsumerWidget { | |||||||
|                             data: data, |                             data: data, | ||||||
|                           ).padding(horizontal: 4), |                           ).padding(horizontal: 4), | ||||||
|                         ), |                         ), | ||||||
|  |                       SliverToBoxAdapter( | ||||||
|  |                         child: _AccountPublisherList( | ||||||
|  |                           publishers: accountPublishers.value ?? [], | ||||||
|  |                         ).padding(horizontal: 4), | ||||||
|  |                       ), | ||||||
|                       SliverToBoxAdapter( |                       SliverToBoxAdapter( | ||||||
|                         child: _AccountProfileDetail( |                         child: _AccountProfileDetail( | ||||||
|                           data: data, |                           data: data, | ||||||
| @@ -863,7 +945,8 @@ class AccountProfileScreen extends HookConsumerWidget { | |||||||
|                       ), |                       ), | ||||||
|                     ], |                     ], | ||||||
|                   ), |                   ), | ||||||
|           ), |         ); | ||||||
|  |       }, | ||||||
|       error: |       error: | ||||||
|           (error, stackTrace) => AppScaffold( |           (error, stackTrace) => AppScaffold( | ||||||
|             appBar: AppBar(leading: const PageBackButton()), |             appBar: AppBar(leading: const PageBackButton()), | ||||||
|   | |||||||
| @@ -762,5 +762,127 @@ class _AccountBotDeveloperProviderElement | |||||||
|   String get uname => (origin as AccountBotDeveloperProvider).uname; |   String get uname => (origin as AccountBotDeveloperProvider).uname; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | String _$accountPublishersHash() => r'25f5695b4a5154163d77f1769876d826bf736609'; | ||||||
|  |  | ||||||
|  | /// See also [accountPublishers]. | ||||||
|  | @ProviderFor(accountPublishers) | ||||||
|  | const accountPublishersProvider = AccountPublishersFamily(); | ||||||
|  |  | ||||||
|  | /// See also [accountPublishers]. | ||||||
|  | class AccountPublishersFamily extends Family<AsyncValue<List<SnPublisher>>> { | ||||||
|  |   /// See also [accountPublishers]. | ||||||
|  |   const AccountPublishersFamily(); | ||||||
|  |  | ||||||
|  |   /// See also [accountPublishers]. | ||||||
|  |   AccountPublishersProvider call(String id) { | ||||||
|  |     return AccountPublishersProvider(id); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   AccountPublishersProvider getProviderOverride( | ||||||
|  |     covariant AccountPublishersProvider provider, | ||||||
|  |   ) { | ||||||
|  |     return call(provider.id); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   static const Iterable<ProviderOrFamily>? _dependencies = null; | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   Iterable<ProviderOrFamily>? get dependencies => _dependencies; | ||||||
|  |  | ||||||
|  |   static const Iterable<ProviderOrFamily>? _allTransitiveDependencies = null; | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   Iterable<ProviderOrFamily>? get allTransitiveDependencies => | ||||||
|  |       _allTransitiveDependencies; | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   String? get name => r'accountPublishersProvider'; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /// See also [accountPublishers]. | ||||||
|  | class AccountPublishersProvider | ||||||
|  |     extends AutoDisposeFutureProvider<List<SnPublisher>> { | ||||||
|  |   /// See also [accountPublishers]. | ||||||
|  |   AccountPublishersProvider(String id) | ||||||
|  |     : this._internal( | ||||||
|  |         (ref) => accountPublishers(ref as AccountPublishersRef, id), | ||||||
|  |         from: accountPublishersProvider, | ||||||
|  |         name: r'accountPublishersProvider', | ||||||
|  |         debugGetCreateSourceHash: | ||||||
|  |             const bool.fromEnvironment('dart.vm.product') | ||||||
|  |                 ? null | ||||||
|  |                 : _$accountPublishersHash, | ||||||
|  |         dependencies: AccountPublishersFamily._dependencies, | ||||||
|  |         allTransitiveDependencies: | ||||||
|  |             AccountPublishersFamily._allTransitiveDependencies, | ||||||
|  |         id: id, | ||||||
|  |       ); | ||||||
|  |  | ||||||
|  |   AccountPublishersProvider._internal( | ||||||
|  |     super._createNotifier, { | ||||||
|  |     required super.name, | ||||||
|  |     required super.dependencies, | ||||||
|  |     required super.allTransitiveDependencies, | ||||||
|  |     required super.debugGetCreateSourceHash, | ||||||
|  |     required super.from, | ||||||
|  |     required this.id, | ||||||
|  |   }) : super.internal(); | ||||||
|  |  | ||||||
|  |   final String id; | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   Override overrideWith( | ||||||
|  |     FutureOr<List<SnPublisher>> Function(AccountPublishersRef provider) create, | ||||||
|  |   ) { | ||||||
|  |     return ProviderOverride( | ||||||
|  |       origin: this, | ||||||
|  |       override: AccountPublishersProvider._internal( | ||||||
|  |         (ref) => create(ref as AccountPublishersRef), | ||||||
|  |         from: from, | ||||||
|  |         name: null, | ||||||
|  |         dependencies: null, | ||||||
|  |         allTransitiveDependencies: null, | ||||||
|  |         debugGetCreateSourceHash: null, | ||||||
|  |         id: id, | ||||||
|  |       ), | ||||||
|  |     ); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   AutoDisposeFutureProviderElement<List<SnPublisher>> createElement() { | ||||||
|  |     return _AccountPublishersProviderElement(this); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   bool operator ==(Object other) { | ||||||
|  |     return other is AccountPublishersProvider && other.id == id; | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   int get hashCode { | ||||||
|  |     var hash = _SystemHash.combine(0, runtimeType.hashCode); | ||||||
|  |     hash = _SystemHash.combine(hash, id.hashCode); | ||||||
|  |  | ||||||
|  |     return _SystemHash.finish(hash); | ||||||
|  |   } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | @Deprecated('Will be removed in 3.0. Use Ref instead') | ||||||
|  | // ignore: unused_element | ||||||
|  | mixin AccountPublishersRef on AutoDisposeFutureProviderRef<List<SnPublisher>> { | ||||||
|  |   /// The parameter `id` of this provider. | ||||||
|  |   String get id; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | class _AccountPublishersProviderElement | ||||||
|  |     extends AutoDisposeFutureProviderElement<List<SnPublisher>> | ||||||
|  |     with AccountPublishersRef { | ||||||
|  |   _AccountPublishersProviderElement(super.provider); | ||||||
|  |  | ||||||
|  |   @override | ||||||
|  |   String get id => (origin as AccountPublishersProvider).id; | ||||||
|  | } | ||||||
|  |  | ||||||
| // ignore_for_file: type=lint | // ignore_for_file: type=lint | ||||||
| // ignore_for_file: subtype_of_sealed_class, invalid_use_of_internal_member, invalid_use_of_visible_for_testing_member, deprecated_member_use_from_same_package | // ignore_for_file: subtype_of_sealed_class, invalid_use_of_internal_member, invalid_use_of_visible_for_testing_member, deprecated_member_use_from_same_package | ||||||
|   | |||||||
| @@ -66,8 +66,8 @@ class _PublisherBasisWidget extends StatelessWidget { | |||||||
|             ), |             ), | ||||||
|           ), |           ), | ||||||
|           onTap: () { |           onTap: () { | ||||||
|             Navigator.pop(context, true); |  | ||||||
|             if (data.account?.name != null) { |             if (data.account?.name != null) { | ||||||
|  |               Navigator.pop(context, true); | ||||||
|               context.pushNamed( |               context.pushNamed( | ||||||
|                 'accountProfile', |                 'accountProfile', | ||||||
|                 pathParameters: {'name': data.account!.name}, |                 pathParameters: {'name': data.account!.name}, | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user