✨ Search with tag & category
This commit is contained in:
parent
f7cc4420b3
commit
60d7df4496
@ -109,8 +109,6 @@ PODS:
|
|||||||
- GoogleUtilities/Privacy
|
- GoogleUtilities/Privacy
|
||||||
- image_picker_ios (0.0.1):
|
- image_picker_ios (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
- irondash_engine_context (0.0.1):
|
|
||||||
- Flutter
|
|
||||||
- livekit_client (2.2.0):
|
- livekit_client (2.2.0):
|
||||||
- Flutter
|
- Flutter
|
||||||
- WebRTC-SDK (= 114.5735.10)
|
- WebRTC-SDK (= 114.5735.10)
|
||||||
@ -127,6 +125,8 @@ PODS:
|
|||||||
- nanopb/encode (2.30910.0)
|
- nanopb/encode (2.30910.0)
|
||||||
- package_info_plus (0.4.5):
|
- package_info_plus (0.4.5):
|
||||||
- Flutter
|
- Flutter
|
||||||
|
- pasteboard (0.0.1):
|
||||||
|
- Flutter
|
||||||
- path_provider_foundation (0.0.1):
|
- path_provider_foundation (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
- FlutterMacOS
|
- FlutterMacOS
|
||||||
@ -148,8 +148,6 @@ PODS:
|
|||||||
- sqflite (0.0.3):
|
- sqflite (0.0.3):
|
||||||
- Flutter
|
- Flutter
|
||||||
- FlutterMacOS
|
- FlutterMacOS
|
||||||
- super_native_extensions (0.0.1):
|
|
||||||
- Flutter
|
|
||||||
- SwiftyGif (5.4.5)
|
- SwiftyGif (5.4.5)
|
||||||
- url_launcher_ios (0.0.1):
|
- url_launcher_ios (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
@ -170,19 +168,18 @@ DEPENDENCIES:
|
|||||||
- flutter_secure_storage (from `.symlinks/plugins/flutter_secure_storage/ios`)
|
- flutter_secure_storage (from `.symlinks/plugins/flutter_secure_storage/ios`)
|
||||||
- flutter_webrtc (from `.symlinks/plugins/flutter_webrtc/ios`)
|
- flutter_webrtc (from `.symlinks/plugins/flutter_webrtc/ios`)
|
||||||
- image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`)
|
- image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`)
|
||||||
- irondash_engine_context (from `.symlinks/plugins/irondash_engine_context/ios`)
|
|
||||||
- livekit_client (from `.symlinks/plugins/livekit_client/ios`)
|
- livekit_client (from `.symlinks/plugins/livekit_client/ios`)
|
||||||
- media_kit_libs_ios_video (from `.symlinks/plugins/media_kit_libs_ios_video/ios`)
|
- media_kit_libs_ios_video (from `.symlinks/plugins/media_kit_libs_ios_video/ios`)
|
||||||
- media_kit_native_event_loop (from `.symlinks/plugins/media_kit_native_event_loop/ios`)
|
- media_kit_native_event_loop (from `.symlinks/plugins/media_kit_native_event_loop/ios`)
|
||||||
- media_kit_video (from `.symlinks/plugins/media_kit_video/ios`)
|
- media_kit_video (from `.symlinks/plugins/media_kit_video/ios`)
|
||||||
- package_info_plus (from `.symlinks/plugins/package_info_plus/ios`)
|
- package_info_plus (from `.symlinks/plugins/package_info_plus/ios`)
|
||||||
|
- pasteboard (from `.symlinks/plugins/pasteboard/ios`)
|
||||||
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
|
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
|
||||||
- permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`)
|
- permission_handler_apple (from `.symlinks/plugins/permission_handler_apple/ios`)
|
||||||
- protocol_handler_ios (from `.symlinks/plugins/protocol_handler_ios/ios`)
|
- protocol_handler_ios (from `.symlinks/plugins/protocol_handler_ios/ios`)
|
||||||
- screen_brightness_ios (from `.symlinks/plugins/screen_brightness_ios/ios`)
|
- screen_brightness_ios (from `.symlinks/plugins/screen_brightness_ios/ios`)
|
||||||
- sentry_flutter (from `.symlinks/plugins/sentry_flutter/ios`)
|
- sentry_flutter (from `.symlinks/plugins/sentry_flutter/ios`)
|
||||||
- sqflite (from `.symlinks/plugins/sqflite/darwin`)
|
- sqflite (from `.symlinks/plugins/sqflite/darwin`)
|
||||||
- super_native_extensions (from `.symlinks/plugins/super_native_extensions/ios`)
|
|
||||||
- url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`)
|
- url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`)
|
||||||
- volume_controller (from `.symlinks/plugins/volume_controller/ios`)
|
- volume_controller (from `.symlinks/plugins/volume_controller/ios`)
|
||||||
- wakelock_plus (from `.symlinks/plugins/wakelock_plus/ios`)
|
- wakelock_plus (from `.symlinks/plugins/wakelock_plus/ios`)
|
||||||
@ -226,8 +223,6 @@ EXTERNAL SOURCES:
|
|||||||
:path: ".symlinks/plugins/flutter_webrtc/ios"
|
:path: ".symlinks/plugins/flutter_webrtc/ios"
|
||||||
image_picker_ios:
|
image_picker_ios:
|
||||||
:path: ".symlinks/plugins/image_picker_ios/ios"
|
:path: ".symlinks/plugins/image_picker_ios/ios"
|
||||||
irondash_engine_context:
|
|
||||||
:path: ".symlinks/plugins/irondash_engine_context/ios"
|
|
||||||
livekit_client:
|
livekit_client:
|
||||||
:path: ".symlinks/plugins/livekit_client/ios"
|
:path: ".symlinks/plugins/livekit_client/ios"
|
||||||
media_kit_libs_ios_video:
|
media_kit_libs_ios_video:
|
||||||
@ -238,6 +233,8 @@ EXTERNAL SOURCES:
|
|||||||
:path: ".symlinks/plugins/media_kit_video/ios"
|
:path: ".symlinks/plugins/media_kit_video/ios"
|
||||||
package_info_plus:
|
package_info_plus:
|
||||||
:path: ".symlinks/plugins/package_info_plus/ios"
|
:path: ".symlinks/plugins/package_info_plus/ios"
|
||||||
|
pasteboard:
|
||||||
|
:path: ".symlinks/plugins/pasteboard/ios"
|
||||||
path_provider_foundation:
|
path_provider_foundation:
|
||||||
:path: ".symlinks/plugins/path_provider_foundation/darwin"
|
:path: ".symlinks/plugins/path_provider_foundation/darwin"
|
||||||
permission_handler_apple:
|
permission_handler_apple:
|
||||||
@ -250,8 +247,6 @@ EXTERNAL SOURCES:
|
|||||||
:path: ".symlinks/plugins/sentry_flutter/ios"
|
:path: ".symlinks/plugins/sentry_flutter/ios"
|
||||||
sqflite:
|
sqflite:
|
||||||
:path: ".symlinks/plugins/sqflite/darwin"
|
:path: ".symlinks/plugins/sqflite/darwin"
|
||||||
super_native_extensions:
|
|
||||||
:path: ".symlinks/plugins/super_native_extensions/ios"
|
|
||||||
url_launcher_ios:
|
url_launcher_ios:
|
||||||
:path: ".symlinks/plugins/url_launcher_ios/ios"
|
:path: ".symlinks/plugins/url_launcher_ios/ios"
|
||||||
volume_controller:
|
volume_controller:
|
||||||
@ -279,13 +274,13 @@ SPEC CHECKSUMS:
|
|||||||
GoogleDataTransport: 6c09b596d841063d76d4288cc2d2f42cc36e1e2a
|
GoogleDataTransport: 6c09b596d841063d76d4288cc2d2f42cc36e1e2a
|
||||||
GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15
|
GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15
|
||||||
image_picker_ios: c560581cceedb403a6ff17f2f816d7fea1421fc1
|
image_picker_ios: c560581cceedb403a6ff17f2f816d7fea1421fc1
|
||||||
irondash_engine_context: 3458bf979b90d616ffb8ae03a150bafe2e860cc9
|
|
||||||
livekit_client: 2b3f5185f95d46d62d3570bf981f3d98ad3051e2
|
livekit_client: 2b3f5185f95d46d62d3570bf981f3d98ad3051e2
|
||||||
media_kit_libs_ios_video: a5fe24bc7875ccd6378a0978c13185e1344651c1
|
media_kit_libs_ios_video: a5fe24bc7875ccd6378a0978c13185e1344651c1
|
||||||
media_kit_native_event_loop: e6b2ab20cf0746eb1c33be961fcf79667304fa2a
|
media_kit_native_event_loop: e6b2ab20cf0746eb1c33be961fcf79667304fa2a
|
||||||
media_kit_video: 5da63f157170e5bf303bf85453b7ef6971218a2e
|
media_kit_video: 5da63f157170e5bf303bf85453b7ef6971218a2e
|
||||||
nanopb: 438bc412db1928dac798aa6fd75726007be04262
|
nanopb: 438bc412db1928dac798aa6fd75726007be04262
|
||||||
package_info_plus: 58f0028419748fad15bf008b270aaa8e54380b1c
|
package_info_plus: 58f0028419748fad15bf008b270aaa8e54380b1c
|
||||||
|
pasteboard: 982969ebaa7c78af3e6cc7761e8f5e77565d9ce0
|
||||||
path_provider_foundation: 2b6b4c569c0fb62ec74538f866245ac84301af46
|
path_provider_foundation: 2b6b4c569c0fb62ec74538f866245ac84301af46
|
||||||
permission_handler_apple: 9878588469a2b0d0fc1e048d9f43605f92e6cec2
|
permission_handler_apple: 9878588469a2b0d0fc1e048d9f43605f92e6cec2
|
||||||
PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47
|
PromisesObjC: f5707f49cb48b9636751c5b2e7d227e43fba9f47
|
||||||
@ -295,7 +290,6 @@ SPEC CHECKSUMS:
|
|||||||
Sentry: 016de45ee5ce5fca2a829996f1bfafeb5e62e8b4
|
Sentry: 016de45ee5ce5fca2a829996f1bfafeb5e62e8b4
|
||||||
sentry_flutter: 5fb57c5b7e6427a9dc1fedde4269eb65823982d4
|
sentry_flutter: 5fb57c5b7e6427a9dc1fedde4269eb65823982d4
|
||||||
sqflite: 673a0e54cc04b7d6dba8d24fb8095b31c3a99eec
|
sqflite: 673a0e54cc04b7d6dba8d24fb8095b31c3a99eec
|
||||||
super_native_extensions: 4916b3c627a9c7fffdc48a23a9eca0b1ac228fa7
|
|
||||||
SwiftyGif: 706c60cf65fa2bc5ee0313beece843c8eb8194d4
|
SwiftyGif: 706c60cf65fa2bc5ee0313beece843c8eb8194d4
|
||||||
url_launcher_ios: 5334b05cef931de560670eeae103fd3e431ac3fe
|
url_launcher_ios: 5334b05cef931de560670eeae103fd3e431ac3fe
|
||||||
volume_controller: 531ddf792994285c9b17f9d8a7e4dcdd29b3eae9
|
volume_controller: 531ddf792994285c9b17f9d8a7e4dcdd29b3eae9
|
||||||
|
@ -7,10 +7,13 @@ class PostProvider extends GetConnect {
|
|||||||
httpClient.baseUrl = ServiceFinder.services['interactive'];
|
httpClient.baseUrl = ServiceFinder.services['interactive'];
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<Response> listFeed(int page, {int? realm}) async {
|
Future<Response> listFeed(int page,
|
||||||
|
{int? realm, String? tag, category}) async {
|
||||||
final queries = [
|
final queries = [
|
||||||
'take=${10}',
|
'take=${10}',
|
||||||
'offset=$page',
|
'offset=$page',
|
||||||
|
if (tag != null) 'tag=$tag',
|
||||||
|
if (category != null) 'category=$category',
|
||||||
if (realm != null) 'realmId=$realm',
|
if (realm != null) 'realmId=$realm',
|
||||||
];
|
];
|
||||||
final resp = await get('/api/feed?${queries.join('&')}');
|
final resp = await get('/api/feed?${queries.join('&')}');
|
||||||
|
@ -8,6 +8,7 @@ import 'package:solian/screens/channel/channel_chat.dart';
|
|||||||
import 'package:solian/screens/channel/channel_detail.dart';
|
import 'package:solian/screens/channel/channel_detail.dart';
|
||||||
import 'package:solian/screens/channel/channel_organize.dart';
|
import 'package:solian/screens/channel/channel_organize.dart';
|
||||||
import 'package:solian/screens/chat.dart';
|
import 'package:solian/screens/chat.dart';
|
||||||
|
import 'package:solian/screens/feed_search.dart';
|
||||||
import 'package:solian/screens/posts/post_detail.dart';
|
import 'package:solian/screens/posts/post_detail.dart';
|
||||||
import 'package:solian/screens/realms.dart';
|
import 'package:solian/screens/realms.dart';
|
||||||
import 'package:solian/screens/realms/realm_detail.dart';
|
import 'package:solian/screens/realms/realm_detail.dart';
|
||||||
@ -47,6 +48,17 @@ abstract class AppRouter {
|
|||||||
name: 'feed',
|
name: 'feed',
|
||||||
builder: (context, state) => const FeedScreen(),
|
builder: (context, state) => const FeedScreen(),
|
||||||
),
|
),
|
||||||
|
GoRoute(
|
||||||
|
path: '/feed/search',
|
||||||
|
name: 'feedSearch',
|
||||||
|
builder: (context, state) => TitleShell(
|
||||||
|
state: state,
|
||||||
|
child: FeedSearchScreen(
|
||||||
|
tag: state.uri.queryParameters['tag'],
|
||||||
|
category: state.uri.queryParameters['category'],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
GoRoute(
|
GoRoute(
|
||||||
path: '/posts/view/:alias',
|
path: '/posts/view/:alias',
|
||||||
name: 'postDetail',
|
name: 'postDetail',
|
||||||
|
88
lib/screens/feed_search.dart
Normal file
88
lib/screens/feed_search.dart
Normal file
@ -0,0 +1,88 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:get/get.dart';
|
||||||
|
import 'package:infinite_scroll_pagination/infinite_scroll_pagination.dart';
|
||||||
|
import 'package:solian/models/feed.dart';
|
||||||
|
import 'package:solian/models/pagination.dart';
|
||||||
|
import 'package:solian/providers/content/post.dart';
|
||||||
|
import 'package:solian/widgets/posts/feed_list.dart';
|
||||||
|
|
||||||
|
class FeedSearchScreen extends StatefulWidget {
|
||||||
|
final String? tag;
|
||||||
|
final String? category;
|
||||||
|
|
||||||
|
const FeedSearchScreen({super.key, this.tag, this.category});
|
||||||
|
|
||||||
|
@override
|
||||||
|
State<FeedSearchScreen> createState() => _FeedSearchScreenState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _FeedSearchScreenState extends State<FeedSearchScreen> {
|
||||||
|
final PagingController<int, FeedRecord> _pagingController =
|
||||||
|
PagingController(firstPageKey: 0);
|
||||||
|
|
||||||
|
getPosts(int pageKey) async {
|
||||||
|
final PostProvider provider = Get.find();
|
||||||
|
|
||||||
|
Response resp;
|
||||||
|
try {
|
||||||
|
resp = await provider.listFeed(
|
||||||
|
pageKey,
|
||||||
|
tag: widget.tag,
|
||||||
|
category: widget.category,
|
||||||
|
);
|
||||||
|
} catch (e) {
|
||||||
|
_pagingController.error = e;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
final PaginationResult result = PaginationResult.fromJson(resp.body);
|
||||||
|
final parsed = result.data?.map((e) => FeedRecord.fromJson(e)).toList();
|
||||||
|
if (parsed != null && parsed.length >= 10) {
|
||||||
|
_pagingController.appendPage(parsed, pageKey + parsed.length);
|
||||||
|
} else if (parsed != null) {
|
||||||
|
_pagingController.appendLastPage(parsed);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
super.initState();
|
||||||
|
|
||||||
|
_pagingController.addPageRequestListener(getPosts);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Scaffold(
|
||||||
|
body: Material(
|
||||||
|
color: Theme.of(context).colorScheme.surface,
|
||||||
|
child: Column(
|
||||||
|
children: [
|
||||||
|
if (widget.tag != null)
|
||||||
|
ListTile(
|
||||||
|
leading: const Icon(Icons.label),
|
||||||
|
tileColor: Theme.of(context).colorScheme.surfaceContainer,
|
||||||
|
title: Text('feedSearchWithTag'.trParams({'key': widget.tag!})),
|
||||||
|
),
|
||||||
|
if (widget.category != null)
|
||||||
|
ListTile(
|
||||||
|
leading: const Icon(Icons.category),
|
||||||
|
tileColor: Theme.of(context).colorScheme.surfaceContainer,
|
||||||
|
title: Text('feedSearchWithCategory'.trParams({'key': widget.category!})),
|
||||||
|
),
|
||||||
|
Expanded(
|
||||||
|
child: RefreshIndicator(
|
||||||
|
onRefresh: () => Future.sync(() => _pagingController.refresh()),
|
||||||
|
child: CustomScrollView(
|
||||||
|
slivers: [
|
||||||
|
FeedListWidget(controller: _pagingController),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -11,6 +11,9 @@ class SolianMessages extends Translations {
|
|||||||
'reset': 'Reset',
|
'reset': 'Reset',
|
||||||
'page': 'Page',
|
'page': 'Page',
|
||||||
'feed': 'Feed',
|
'feed': 'Feed',
|
||||||
|
'feedSearch': 'Search Feed',
|
||||||
|
'feedSearchWithTag': 'Searching with tag #@key',
|
||||||
|
'feedSearchWithCategory': 'Searching in category @category',
|
||||||
'chat': 'Chat',
|
'chat': 'Chat',
|
||||||
'apply': 'Apply',
|
'apply': 'Apply',
|
||||||
'cancel': 'Cancel',
|
'cancel': 'Cancel',
|
||||||
@ -265,6 +268,9 @@ class SolianMessages extends Translations {
|
|||||||
'delete': '删除',
|
'delete': '删除',
|
||||||
'page': '页面',
|
'page': '页面',
|
||||||
'feed': '资讯',
|
'feed': '资讯',
|
||||||
|
'feedSearch': '搜索资讯',
|
||||||
|
'feedSearchWithTag': '检索带有 #@key 标签的资讯',
|
||||||
|
'feedSearchWithCategory': '检索位于分类 @category 的资讯',
|
||||||
'chat': '聊天',
|
'chat': '聊天',
|
||||||
'apply': '应用',
|
'apply': '应用',
|
||||||
'search': '搜索',
|
'search': '搜索',
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:solian/models/feed.dart';
|
import 'package:solian/models/feed.dart';
|
||||||
|
import 'package:solian/router.dart';
|
||||||
|
|
||||||
class FeedTagsList extends StatelessWidget {
|
class FeedTagsList extends StatelessWidget {
|
||||||
final List<Tag> tags;
|
final List<Tag> tags;
|
||||||
@ -36,7 +37,11 @@ class FeedTagsList extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
onTap: () {},
|
onTap: () {
|
||||||
|
AppRouter.instance.pushNamed('feedSearch', queryParameters: {
|
||||||
|
'tag': x.alias,
|
||||||
|
});
|
||||||
|
},
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
.toList(),
|
.toList(),
|
||||||
|
Loading…
Reference in New Issue
Block a user