Compare commits
No commits in common. "25550ba1975ca458084320e5a3d3ec57af935a7a" and "e16bc80eeaff2a1cbb45606d9f0807c403f67000" have entirely different histories.
25550ba197
...
e16bc80eea
@ -769,7 +769,5 @@
|
||||
"decryptingKeyNotFound": "Key not found or exchange failed, the other party may not be online",
|
||||
"messageUnablePreview": "Unable preview",
|
||||
"messageUnablePreviewEncrypted": "Unable preview encrypted message",
|
||||
"postViewInGlobalDescription": "Do not view the post in the specific realm.",
|
||||
"postDraftSaved": "The draft has been saved.",
|
||||
"postDraftBox": "Draft Box"
|
||||
"postViewInGlobalDescription": "Do not view the post in the specific realm."
|
||||
}
|
||||
|
@ -767,7 +767,5 @@
|
||||
"decryptingKeyNotFound": "未找到密钥对或交换失败,对方可能不在线",
|
||||
"messageUnablePreview": "无法预览消息",
|
||||
"messageUnablePreviewEncrypted": "无法预览加密消息",
|
||||
"postViewInGlobalDescription": "不查看特定领域的帖子。",
|
||||
"postDraftSaved": "已保存为草稿。",
|
||||
"postDraftBox": "草稿箱"
|
||||
"postViewInGlobalDescription": "不查看特定领域的帖子。"
|
||||
}
|
||||
|
@ -767,7 +767,5 @@
|
||||
"decryptingKeyNotFound": "未找到密鑰對或交換失敗,對方可能不在線",
|
||||
"messageUnablePreview": "無法預覽消息",
|
||||
"messageUnablePreviewEncrypted": "無法預覽加密消息",
|
||||
"postViewInGlobalDescription": "不查看特定領域的帖子。",
|
||||
"postDraftSaved": "已保存為草稿。",
|
||||
"postDraftBox": "草稿箱"
|
||||
"postViewInGlobalDescription": "不查看特定領域的帖子。"
|
||||
}
|
||||
|
@ -767,7 +767,5 @@
|
||||
"decryptingKeyNotFound": "未找到密鑰對或交換失敗,對方可能不在線",
|
||||
"messageUnablePreview": "無法預覽消息",
|
||||
"messageUnablePreviewEncrypted": "無法預覽加密消息",
|
||||
"postViewInGlobalDescription": "不查看特定領域的帖子。",
|
||||
"postDraftSaved": "已保存為草稿。",
|
||||
"postDraftBox": "草稿箱"
|
||||
"postViewInGlobalDescription": "不查看特定領域的帖子。"
|
||||
}
|
||||
|
@ -208,7 +208,6 @@ class PostWriteController extends ChangeNotifier {
|
||||
SnRealm? realm;
|
||||
SnPublisher? publisher;
|
||||
SnPost? editingPost, repostingPost, replyingPost;
|
||||
bool editingDraft = false;
|
||||
|
||||
int visibility = 0;
|
||||
List<int> visibleUsers = List.empty();
|
||||
@ -255,8 +254,6 @@ class PostWriteController extends ChangeNotifier {
|
||||
post.preload?.attachments?.map((ele) => PostWriteMedia(ele)) ?? []);
|
||||
poll = post.preload?.poll;
|
||||
|
||||
editingDraft = post.isDraft;
|
||||
|
||||
if (post.preload?.thumbnail != null &&
|
||||
(post.preload?.thumbnail?.rid.isNotEmpty ?? false)) {
|
||||
thumbnail = PostWriteMedia(post.preload!.thumbnail);
|
||||
@ -477,10 +474,7 @@ class PostWriteController extends ChangeNotifier {
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
Future<void> sendPost(
|
||||
BuildContext context, {
|
||||
bool saveAsDraft = false,
|
||||
}) async {
|
||||
Future<void> sendPost(BuildContext context) async {
|
||||
if (isBusy || publisher == null) return;
|
||||
|
||||
final sn = context.read<SnNetworkProvider>();
|
||||
@ -558,7 +552,7 @@ class PostWriteController extends ChangeNotifier {
|
||||
// Posting the content
|
||||
try {
|
||||
final baseProgressVal = progress!;
|
||||
final resp = await sn.client.request(
|
||||
await sn.client.request(
|
||||
[
|
||||
'/cgi/co/$mode',
|
||||
if (editingPost != null) '${editingPost!.id}',
|
||||
@ -591,7 +585,6 @@ class PostWriteController extends ChangeNotifier {
|
||||
if (videoAttachment != null) 'video': videoAttachment!.rid,
|
||||
if (poll != null) 'poll': poll!.id,
|
||||
if (realm != null) 'realm': realm!.id,
|
||||
'is_draft': saveAsDraft,
|
||||
},
|
||||
onSendProgress: (count, total) {
|
||||
progress =
|
||||
@ -608,16 +601,7 @@ class PostWriteController extends ChangeNotifier {
|
||||
method: editingPost != null ? 'PUT' : 'POST',
|
||||
),
|
||||
);
|
||||
if (saveAsDraft) {
|
||||
if (!context.mounted) return;
|
||||
editingDraft = true;
|
||||
final out = SnPost.fromJson(resp.data);
|
||||
final pt = context.read<SnPostContentProvider>();
|
||||
editingPost = await pt.completePostData(out);
|
||||
notifyListeners();
|
||||
} else {
|
||||
reset();
|
||||
}
|
||||
reset();
|
||||
} catch (err) {
|
||||
if (!context.mounted) return;
|
||||
context.showErrorDialog(err);
|
||||
|
@ -60,24 +60,16 @@ class SnPostContentProvider {
|
||||
|
||||
out[i] = out[i].copyWith(
|
||||
preload: SnPostPreload(
|
||||
thumbnail: attachments
|
||||
.where((ele) => ele?.rid == out[i].body['thumbnail'])
|
||||
.firstOrNull,
|
||||
attachments: attachments
|
||||
.where((ele) =>
|
||||
out[i].body['attachments']?.contains(ele?.rid) ?? false)
|
||||
.toList(),
|
||||
video: attachments
|
||||
.where((ele) => ele?.rid == out[i].body['video'])
|
||||
.firstOrNull,
|
||||
thumbnail: attachments.where((ele) => ele?.rid == out[i].body['thumbnail']).firstOrNull,
|
||||
attachments: attachments.where((ele) => out[i].body['attachments']?.contains(ele?.rid) ?? false).toList(),
|
||||
video: attachments.where((ele) => ele?.rid == out[i].body['video']).firstOrNull,
|
||||
poll: poll,
|
||||
realm: realm,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
uids.addAll(
|
||||
attachments.where((ele) => ele != null).map((ele) => ele!.accountId));
|
||||
uids.addAll(attachments.where((ele) => ele != null).map((ele) => ele!.accountId));
|
||||
await _ud.listAccount(uids);
|
||||
|
||||
return out;
|
||||
@ -115,23 +107,15 @@ class SnPostContentProvider {
|
||||
|
||||
out = out.copyWith(
|
||||
preload: SnPostPreload(
|
||||
thumbnail: attachments
|
||||
.where((ele) => ele?.rid == out.body['thumbnail'])
|
||||
.firstOrNull,
|
||||
attachments: attachments
|
||||
.where(
|
||||
(ele) => out.body['attachments']?.contains(ele?.rid) ?? false)
|
||||
.toList(),
|
||||
video: attachments
|
||||
.where((ele) => ele?.rid == out.body['video'])
|
||||
.firstOrNull,
|
||||
thumbnail: attachments.where((ele) => ele?.rid == out.body['thumbnail']).firstOrNull,
|
||||
attachments: attachments.where((ele) => out.body['attachments']?.contains(ele?.rid) ?? false).toList(),
|
||||
video: attachments.where((ele) => ele?.rid == out.body['video']).firstOrNull,
|
||||
poll: poll,
|
||||
realm: realm,
|
||||
),
|
||||
);
|
||||
|
||||
uids.addAll(
|
||||
attachments.where((ele) => ele != null).map((ele) => ele!.accountId));
|
||||
uids.addAll(attachments.where((ele) => ele != null).map((ele) => ele!.accountId));
|
||||
await _ud.listAccount(uids);
|
||||
|
||||
return out;
|
||||
@ -154,22 +138,17 @@ class SnPostContentProvider {
|
||||
Iterable<String>? tags,
|
||||
String? realm,
|
||||
String? channel,
|
||||
bool isDraft = false,
|
||||
}) async {
|
||||
final resp = await _sn.client.get(
|
||||
'/cgi/co/posts${isDraft ? '/drafts' : ''}',
|
||||
queryParameters: {
|
||||
'take': take,
|
||||
'offset': offset,
|
||||
if (type != null) 'type': type,
|
||||
if (author != null) 'author': author,
|
||||
if (tags?.isNotEmpty ?? false) 'tags': tags!.join(','),
|
||||
if (categories?.isNotEmpty ?? false)
|
||||
'categories': categories!.join(','),
|
||||
if (realm != null) 'realm': realm,
|
||||
if (channel != null) 'channel': channel,
|
||||
},
|
||||
);
|
||||
final resp = await _sn.client.get('/cgi/co/posts', queryParameters: {
|
||||
'take': take,
|
||||
'offset': offset,
|
||||
if (type != null) 'type': type,
|
||||
if (author != null) 'author': author,
|
||||
if (tags?.isNotEmpty ?? false) 'tags': tags!.join(','),
|
||||
if (categories?.isNotEmpty ?? false) 'categories': categories!.join(','),
|
||||
if (realm != null) 'realm': realm,
|
||||
if (channel != null) 'channel': channel,
|
||||
});
|
||||
final List<SnPost> out = await _preloadRelatedDataInBatch(
|
||||
List.from(resp.data['data']?.map((e) => SnPost.fromJson(e)) ?? []),
|
||||
);
|
||||
@ -182,8 +161,7 @@ class SnPostContentProvider {
|
||||
int take = 10,
|
||||
int offset = 0,
|
||||
}) async {
|
||||
final resp = await _sn.client
|
||||
.get('/cgi/co/posts/$parentId/replies', queryParameters: {
|
||||
final resp = await _sn.client.get('/cgi/co/posts/$parentId/replies', queryParameters: {
|
||||
'take': take,
|
||||
'offset': offset,
|
||||
});
|
||||
@ -222,9 +200,4 @@ class SnPostContentProvider {
|
||||
);
|
||||
return out;
|
||||
}
|
||||
|
||||
Future<SnPost> completePostData(SnPost post) async {
|
||||
final out = await _preloadRelatedDataSingle(post);
|
||||
return out;
|
||||
}
|
||||
}
|
||||
|
@ -28,7 +28,6 @@ import 'package:surface/screens/news/news_detail.dart';
|
||||
import 'package:surface/screens/news/news_list.dart';
|
||||
import 'package:surface/screens/notification.dart';
|
||||
import 'package:surface/screens/post/post_detail.dart';
|
||||
import 'package:surface/screens/post/post_draft.dart';
|
||||
import 'package:surface/screens/post/post_editor.dart';
|
||||
import 'package:surface/screens/post/publisher_page.dart';
|
||||
import 'package:surface/screens/post/post_search.dart';
|
||||
@ -66,11 +65,6 @@ final _appRoutes = [
|
||||
name: 'explore',
|
||||
builder: (context, state) => const ExploreScreen(),
|
||||
routes: [
|
||||
GoRoute(
|
||||
path: '/draft',
|
||||
name: 'postDraftBox',
|
||||
builder: (context, state) => const PostDraftBox(),
|
||||
),
|
||||
GoRoute(
|
||||
path: '/write',
|
||||
name: 'postEditor',
|
||||
|
@ -91,12 +91,8 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
_showCategories = !_showCategories;
|
||||
if (_showCategories) {
|
||||
_tabController = TabController(length: _categories.length, vsync: this);
|
||||
_listKey.currentState?.setCategory(_categories[_tabController.index]);
|
||||
_listKey.currentState?.refreshPosts();
|
||||
} else {
|
||||
_tabController = TabController(length: kPostChannels.length, vsync: this);
|
||||
_listKey.currentState?.setCategory(null);
|
||||
_listKey.currentState?.refreshPosts();
|
||||
}
|
||||
_tabListen();
|
||||
setState(() {});
|
||||
@ -196,21 +192,6 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
),
|
||||
],
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
Text('postDraftBox').tr(),
|
||||
const Gap(20),
|
||||
FloatingActionButton(
|
||||
heroTag: null,
|
||||
tooltip: 'postDraftBox'.tr(),
|
||||
onPressed: () {
|
||||
GoRouter.of(context).pushNamed('postDraftBox');
|
||||
_fabKey.currentState!.toggle();
|
||||
},
|
||||
child: const Icon(Symbols.box_edit),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
body: NestedScrollView(
|
||||
@ -224,47 +205,37 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
title: Row(
|
||||
children: [
|
||||
IconButton(
|
||||
icon: const Icon(Symbols.shuffle),
|
||||
onPressed: () {},
|
||||
padding: EdgeInsets.zero,
|
||||
constraints: const BoxConstraints(),
|
||||
visualDensity: VisualDensity.compact,
|
||||
icon: _listKey.currentState?.realm != null
|
||||
? AccountImage(
|
||||
content: _listKey.currentState!.realm!.avatar,
|
||||
radius: 14,
|
||||
)
|
||||
: const Icon(Symbols.group),
|
||||
onPressed: () {
|
||||
showModalBottomSheet(
|
||||
context: context,
|
||||
builder: (context) => _PostListRealmPopup(
|
||||
realms: _realms,
|
||||
onUpdate: (realm) {
|
||||
_listKey.currentState?.setRealm(realm);
|
||||
_listKey.currentState?.refreshPosts();
|
||||
Future.delayed(const Duration(milliseconds: 100),
|
||||
() {
|
||||
if (mounted) {
|
||||
setState(() {});
|
||||
}
|
||||
});
|
||||
},
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
Expanded(
|
||||
child: Center(
|
||||
child: IconButton(
|
||||
padding: EdgeInsets.zero,
|
||||
constraints: const BoxConstraints(),
|
||||
visualDensity: VisualDensity.compact,
|
||||
icon: _listKey.currentState?.realm != null
|
||||
? AccountImage(
|
||||
content: _listKey.currentState!.realm!.avatar,
|
||||
radius: 18,
|
||||
)
|
||||
: Image.asset(
|
||||
'assets/icon/icon-dark.png',
|
||||
width: 36,
|
||||
height: 36,
|
||||
color: Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor,
|
||||
),
|
||||
onPressed: () {
|
||||
showModalBottomSheet(
|
||||
context: context,
|
||||
builder: (context) => _PostListRealmPopup(
|
||||
realms: _realms,
|
||||
onUpdate: (realm) {
|
||||
_listKey.currentState?.setRealm(realm);
|
||||
_listKey.currentState?.refreshPosts();
|
||||
Future.delayed(
|
||||
const Duration(milliseconds: 100), () {
|
||||
if (mounted) {
|
||||
setState(() {});
|
||||
}
|
||||
});
|
||||
},
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
child: Text('screenExplore').tr(),
|
||||
),
|
||||
),
|
||||
],
|
||||
@ -308,12 +279,11 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
Icon(
|
||||
kCategoryIcons[category.alias] ??
|
||||
Symbols.question_mark,
|
||||
color: Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor!,
|
||||
),
|
||||
kCategoryIcons[category.alias] ??
|
||||
Symbols.question_mark,
|
||||
color: Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor!),
|
||||
const Gap(8),
|
||||
Flexible(
|
||||
child: Text(
|
||||
@ -323,11 +293,9 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
.tr()
|
||||
: category.name,
|
||||
maxLines: 1,
|
||||
).textColor(
|
||||
Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor!,
|
||||
),
|
||||
).textColor(Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor!),
|
||||
),
|
||||
],
|
||||
),
|
||||
@ -353,11 +321,9 @@ class _ExploreScreenState extends State<ExploreScreen>
|
||||
child: Text(
|
||||
'postChannel$channel',
|
||||
maxLines: 1,
|
||||
).tr().textColor(
|
||||
Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor,
|
||||
),
|
||||
).tr().textColor(Theme.of(context)
|
||||
.appBarTheme
|
||||
.foregroundColor),
|
||||
),
|
||||
],
|
||||
),
|
||||
|
@ -1,88 +0,0 @@
|
||||
import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:gap/gap.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
import 'package:surface/providers/post.dart';
|
||||
import 'package:surface/types/post.dart';
|
||||
import 'package:surface/widgets/dialog.dart';
|
||||
import 'package:surface/widgets/loading_indicator.dart';
|
||||
import 'package:surface/widgets/navigation/app_scaffold.dart';
|
||||
import 'package:surface/widgets/post/post_item.dart';
|
||||
import 'package:very_good_infinite_list/very_good_infinite_list.dart';
|
||||
|
||||
class PostDraftBox extends StatefulWidget {
|
||||
const PostDraftBox({super.key});
|
||||
|
||||
@override
|
||||
State<PostDraftBox> createState() => _PostDraftBoxState();
|
||||
}
|
||||
|
||||
class _PostDraftBoxState extends State<PostDraftBox> {
|
||||
bool _isBusy = false;
|
||||
final List<SnPost> _posts = List.empty(growable: true);
|
||||
int? _totalCount;
|
||||
|
||||
Future<void> _fetchPosts() async {
|
||||
setState(() => _isBusy = true);
|
||||
try {
|
||||
final pt = context.read<SnPostContentProvider>();
|
||||
final resp = await pt.listPosts(
|
||||
take: 10,
|
||||
offset: _posts.length,
|
||||
isDraft: true,
|
||||
);
|
||||
final out = resp.$1;
|
||||
_totalCount = resp.$2;
|
||||
if (!mounted) return;
|
||||
_posts.addAll(out);
|
||||
} catch (err) {
|
||||
if (!mounted) return;
|
||||
context.showErrorDialog(err);
|
||||
} finally {
|
||||
setState(() => _isBusy = false);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return AppScaffold(
|
||||
appBar: AppBar(
|
||||
title: Text('postDraftBox').tr(),
|
||||
),
|
||||
body: Column(
|
||||
children: [
|
||||
LoadingIndicator(isActive: _isBusy),
|
||||
Expanded(
|
||||
child: RefreshIndicator(
|
||||
onRefresh: () {
|
||||
_posts.clear();
|
||||
return _fetchPosts();
|
||||
},
|
||||
child: InfiniteList(
|
||||
padding: EdgeInsets.only(top: 8),
|
||||
hasReachedMax:
|
||||
_totalCount != null && _posts.length >= _totalCount!,
|
||||
itemCount: _posts.length,
|
||||
onFetchData: () => _fetchPosts(),
|
||||
itemBuilder: (context, idx) {
|
||||
final ele = _posts[idx];
|
||||
return OpenablePostItem(
|
||||
data: ele,
|
||||
onChanged: (data) {
|
||||
_posts[idx] = data;
|
||||
},
|
||||
onDeleted: () {
|
||||
_posts.clear();
|
||||
_fetchPosts();
|
||||
},
|
||||
);
|
||||
},
|
||||
separatorBuilder: (_, __) => const Gap(8),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
@ -138,15 +138,6 @@ class _PostEditorScreenState extends State<PostEditorScreen>
|
||||
],
|
||||
scope: HotKeyScope.inapp,
|
||||
);
|
||||
final HotKey _saveDraftHotKey = HotKey(
|
||||
key: PhysicalKeyboardKey.keyS,
|
||||
modifiers: [
|
||||
(!kIsWeb && Platform.isMacOS)
|
||||
? HotKeyModifier.meta
|
||||
: HotKeyModifier.control
|
||||
],
|
||||
scope: HotKeyScope.inapp,
|
||||
);
|
||||
|
||||
void _registerHotKey() {
|
||||
if (kIsWeb || Platform.isAndroid || Platform.isIOS) return;
|
||||
@ -162,11 +153,6 @@ class _PostEditorScreenState extends State<PostEditorScreen>
|
||||
]);
|
||||
setState(() {});
|
||||
});
|
||||
hotKeyManager.register(_saveDraftHotKey, keyDownHandler: (_) async {
|
||||
if (mounted) {
|
||||
_writeController.sendPost(context);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void _showPublisherPopup() {
|
||||
@ -232,7 +218,6 @@ class _PostEditorScreenState extends State<PostEditorScreen>
|
||||
_writeController.dispose();
|
||||
if (!kIsWeb && !(Platform.isAndroid || Platform.isIOS)) {
|
||||
hotKeyManager.unregister(_pasteHotKey);
|
||||
hotKeyManager.unregister(_saveDraftHotKey);
|
||||
}
|
||||
super.dispose();
|
||||
}
|
||||
@ -284,20 +269,6 @@ class _PostEditorScreenState extends State<PostEditorScreen>
|
||||
: 'untitled'.tr(),
|
||||
),
|
||||
actions: [
|
||||
IconButton(
|
||||
icon: _writeController.editingDraft
|
||||
? const Icon(Icons.save)
|
||||
: const Icon(Symbols.save_as),
|
||||
onPressed: () {
|
||||
_writeController.sendPost(context, saveAsDraft: true).then(
|
||||
(_) {
|
||||
if (!context.mounted) return;
|
||||
context.showSnackbar('postDraftSaved'.tr());
|
||||
HapticFeedback.mediumImpact();
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
IconButton(
|
||||
icon: const Icon(Symbols.tune),
|
||||
onPressed: _writeController.isBusy ? null : _updateMeta,
|
||||
@ -325,8 +296,7 @@ class _PostEditorScreenState extends State<PostEditorScreen>
|
||||
),
|
||||
body: Column(
|
||||
children: [
|
||||
if (_writeController.editingPost != null &&
|
||||
!_writeController.editingDraft)
|
||||
if (_writeController.editingPost != null)
|
||||
Container(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 4, bottom: 4, left: 20, right: 20),
|
||||
|
@ -13,7 +13,6 @@ class AccountImage extends StatelessWidget {
|
||||
final double? borderRadius;
|
||||
final Widget? fallbackWidget;
|
||||
final Widget? badge;
|
||||
final Offset? badgeOffset;
|
||||
|
||||
const AccountImage({
|
||||
super.key,
|
||||
@ -24,7 +23,6 @@ class AccountImage extends StatelessWidget {
|
||||
this.borderRadius,
|
||||
this.fallbackWidget,
|
||||
this.badge,
|
||||
this.badgeOffset,
|
||||
});
|
||||
|
||||
@override
|
||||
@ -42,8 +40,7 @@ class AccountImage extends StatelessWidget {
|
||||
borderRadius: BorderRadius.circular(borderRadius ?? radius ?? 20),
|
||||
child: (content?.isEmpty ?? true)
|
||||
? Container(
|
||||
color: backgroundColor ??
|
||||
Theme.of(context).colorScheme.primaryContainer,
|
||||
color: backgroundColor ?? Theme.of(context).colorScheme.primaryContainer,
|
||||
child: (fallbackWidget ??
|
||||
Icon(
|
||||
Symbols.account_circle,
|
||||
@ -61,8 +58,8 @@ class AccountImage extends StatelessWidget {
|
||||
),
|
||||
if (badge != null)
|
||||
Positioned(
|
||||
right: badgeOffset?.dx ?? -4,
|
||||
bottom: badgeOffset?.dy ?? -2,
|
||||
right: -4,
|
||||
bottom: -2,
|
||||
child: badge!,
|
||||
),
|
||||
],
|
||||
|
@ -214,8 +214,7 @@ class ChatMessage extends StatelessWidget {
|
||||
data.type == 'messages.new' &&
|
||||
(data.body['text']?.isNotEmpty ?? false) &&
|
||||
(cfg.prefs.getBool(kAppExpandChatLink) ?? true))
|
||||
LinkPreviewWidget(text: data.body['text']!)
|
||||
.padding(left: isCompact ? 0 : 48),
|
||||
LinkPreviewWidget(text: data.body['text']!).padding(left: 48),
|
||||
if (data.preload?.attachments?.isNotEmpty ?? false)
|
||||
AttachmentList(
|
||||
data: data.preload!.attachments!,
|
||||
|
@ -223,7 +223,7 @@ class PostItem extends StatelessWidget {
|
||||
onShareImage: () => _doShareViaPicture(context),
|
||||
onSelectAnswer: onSelectAnswer,
|
||||
onDeleted: () {
|
||||
onDeleted?.call();
|
||||
if (onDeleted != null) {}
|
||||
},
|
||||
).padding(bottom: 8),
|
||||
if (data.preload?.video != null)
|
||||
@ -272,7 +272,7 @@ class PostItem extends StatelessWidget {
|
||||
onShareImage: () => _doShareViaPicture(context),
|
||||
onSelectAnswer: onSelectAnswer,
|
||||
onDeleted: () {
|
||||
onDeleted?.call();
|
||||
if (onDeleted != null) {}
|
||||
},
|
||||
).padding(horizontal: 12, top: 8, bottom: 8),
|
||||
if (data.preload?.video != null)
|
||||
@ -363,7 +363,7 @@ class PostItem extends StatelessWidget {
|
||||
onShareImage: () => _doShareViaPicture(context),
|
||||
onSelectAnswer: onSelectAnswer,
|
||||
onDeleted: () {
|
||||
onDeleted?.call();
|
||||
if (onDeleted != null) onDeleted!();
|
||||
},
|
||||
).padding(horizontal: 12, vertical: 8),
|
||||
if (data.preload?.video != null)
|
||||
@ -923,48 +923,27 @@ class _PostContentHeader extends StatelessWidget {
|
||||
return Row(
|
||||
children: [
|
||||
GestureDetector(
|
||||
child: data.preload?.realm == null
|
||||
? AccountImage(
|
||||
content: data.publisher.avatar,
|
||||
radius: isCompact ? 12 : 20,
|
||||
borderRadius:
|
||||
data.publisher.type == 1 ? (isCompact ? 4 : 8) : 20,
|
||||
badge: (user?.badges.isNotEmpty ?? false)
|
||||
? Icon(
|
||||
kBadgesMeta[user!.badges.first.type]?.$2 ??
|
||||
Symbols.question_mark,
|
||||
color: kBadgesMeta[user.badges.first.type]?.$3,
|
||||
fill: 1,
|
||||
size: 18,
|
||||
shadows: [
|
||||
Shadow(
|
||||
offset: Offset(1, 1),
|
||||
blurRadius: 5.0,
|
||||
color: Color.fromARGB(200, 0, 0, 0),
|
||||
),
|
||||
],
|
||||
)
|
||||
: null,
|
||||
)
|
||||
: AccountImage(
|
||||
content: data.preload!.realm!.avatar,
|
||||
radius: isCompact ? 12 : 20,
|
||||
borderRadius: isCompact ? 4 : 8,
|
||||
badgeOffset: Offset(-6, -4),
|
||||
badge: Container(
|
||||
decoration: BoxDecoration(
|
||||
border: Border.all(
|
||||
color: Theme.of(context).colorScheme.surface,
|
||||
width: 2,
|
||||
child: AccountImage(
|
||||
content: data.publisher.avatar,
|
||||
radius: isCompact ? 12 : 20,
|
||||
borderRadius: data.publisher.type == 1 ? (isCompact ? 4 : 8) : 20,
|
||||
badge: (user?.badges.isNotEmpty ?? false)
|
||||
? Icon(
|
||||
kBadgesMeta[user!.badges.first.type]?.$2 ??
|
||||
Symbols.question_mark,
|
||||
color: kBadgesMeta[user.badges.first.type]?.$3,
|
||||
fill: 1,
|
||||
size: 18,
|
||||
shadows: [
|
||||
Shadow(
|
||||
offset: Offset(1, 1),
|
||||
blurRadius: 5.0,
|
||||
color: Color.fromARGB(200, 0, 0, 0),
|
||||
),
|
||||
borderRadius: BorderRadius.circular(10),
|
||||
),
|
||||
child: AccountImage(
|
||||
content: data.publisher.avatar,
|
||||
radius: 10,
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
)
|
||||
: null,
|
||||
),
|
||||
onTap: () {
|
||||
showPopover(
|
||||
backgroundColor: Theme.of(context).colorScheme.surface,
|
||||
@ -1009,17 +988,7 @@ class _PostContentHeader extends StatelessWidget {
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
children: [
|
||||
Text(data.publisher.nick).bold(),
|
||||
if (data.preload?.realm != null)
|
||||
const Icon(Symbols.arrow_right, size: 16)
|
||||
.padding(horizontal: 2)
|
||||
.opacity(0.5),
|
||||
if (data.preload?.realm != null)
|
||||
Text(data.preload!.realm!.name),
|
||||
],
|
||||
),
|
||||
Text(data.publisher.nick).bold(),
|
||||
Row(
|
||||
children: [
|
||||
Text('@${data.publisher.name}').fontSize(13),
|
||||
|
56
pubspec.lock
56
pubspec.lock
@ -173,10 +173,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: built_value
|
||||
sha256: ea90e81dc4a25a043d9bee692d20ed6d1c4a1662a28c03a96417446c093ed6b4
|
||||
sha256: "8b158ab94ec6913e480dc3f752418348b5ae099eb75868b5f4775f0572999c61"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "8.9.5"
|
||||
version: "8.9.4"
|
||||
cached_network_image:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -301,10 +301,10 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: croppy
|
||||
sha256: "99f4fbb4a4b44d2712e8dcd61c57c1acac151bd53cab11de3babec80407ed266"
|
||||
sha256: bf99b00023df0d7d047e04d27d496d87cbefd968f578d0bd30f342ff75570a12
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.3.5"
|
||||
version: "1.3.3"
|
||||
cross_file:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -429,18 +429,18 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: drift
|
||||
sha256: "14a61af39d4584faf1d73b5b35e4b758a43008cf4c0fdb0576ec8e7032c0d9a5"
|
||||
sha256: "97d5832657d49f26e7a8e07de397ddc63790b039372878d5117af816d0fdb5cb"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.26.0"
|
||||
version: "2.25.1"
|
||||
drift_dev:
|
||||
dependency: "direct dev"
|
||||
description:
|
||||
name: drift_dev
|
||||
sha256: "0d3f8b33b76cf1c6a82ee34d9511c40957549c4674b8f1688609e6d6c7306588"
|
||||
sha256: f1db88482dbb016b9bbddddf746d5d0a6938b156ff20e07320052981f97388cc
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.26.0"
|
||||
version: "2.25.2"
|
||||
drift_flutter:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -710,14 +710,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.4.1"
|
||||
flutter_card_swiper:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: flutter_card_swiper
|
||||
sha256: "1eacbfab31b572223042e03409726553aec431abe48af48c8d591d376d070d3d"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "7.0.2"
|
||||
flutter_colorpicker:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -839,10 +831,10 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: flutter_map
|
||||
sha256: f7d0379477274f323c3f3bc12d369a2b42eb86d1e7bd2970ae1ea3cff782449a
|
||||
sha256: bbf145e8220531f2f727608c431871c7457f3b134e513543913afd00fdc1cd47
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "8.1.1"
|
||||
version: "8.1.0"
|
||||
flutter_markdown:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -1185,10 +1177,10 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: image_picker_android
|
||||
sha256: "8bd392ba8b0c8957a157ae0dc9fcf48c58e6c20908d5880aea1d79734df090e9"
|
||||
sha256: "82652a75e3dd667a91187769a6a2cc81bd8c111bbead698d8e938d2b63e5e89a"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.8.12+22"
|
||||
version: "0.8.12+21"
|
||||
image_picker_for_web:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1417,10 +1409,10 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: material_symbols_icons
|
||||
sha256: ca30ccbd97763353bde6bb1076aa4f4d17a40db0804384da77df142102aa225d
|
||||
sha256: "1403944c2a68dbdf934fca2b2115a372e70a4a185c136ab71a9d16e2108d0b14"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.2808.0"
|
||||
version: "4.2805.1"
|
||||
media_kit:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@ -1609,10 +1601,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_android
|
||||
sha256: "0ca7359dad67fd7063cb2892ab0c0737b2daafd807cf1acecd62374c8fae6c12"
|
||||
sha256: "4adf4fd5423ec60a29506c76581bc05854c55e3a0b72d35bb28d661c9686edf2"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.2.16"
|
||||
version: "2.2.15"
|
||||
path_provider_foundation:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1793,10 +1785,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: pub_semver
|
||||
sha256: "5bfcf68ca79ef689f8990d1160781b4bad40a3bd5e5218ad4076ddb7f4081585"
|
||||
sha256: "7b3cfbf654f3edd0c6298ecd5be782ce997ddf0e00531b9464b55245185bbbbd"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.2.0"
|
||||
version: "2.1.5"
|
||||
pubspec_parse:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -1961,10 +1953,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: shared_preferences_android
|
||||
sha256: "3ec7210872c4ba945e3244982918e502fa2bfb5230dff6832459ca0e1879b7ad"
|
||||
sha256: a768fc8ede5f0c8e6150476e14f38e2417c0864ca36bb4582be8e21925a03c22
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.8"
|
||||
version: "2.4.6"
|
||||
shared_preferences_foundation:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -2126,10 +2118,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: sqlite3
|
||||
sha256: "310af39c40dd0bb2058538333c9d9840a2725ae0b9f77e4fd09ad6696aa8f66e"
|
||||
sha256: "32b632dda27d664f85520093ed6f735ae5c49b5b75345afb8b19411bc59bb53d"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.7.5"
|
||||
version: "2.7.4"
|
||||
sqlite3_flutter_libs:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -2334,10 +2326,10 @@ packages:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: url_launcher_android
|
||||
sha256: "1d0eae19bd7606ef60fe69ef3b312a437a16549476c42321d5dc1506c9ca3bf4"
|
||||
sha256: "6fc2f56536ee873eeb867ad176ae15f304ccccc357848b351f6f0d8d4a40d193"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.3.15"
|
||||
version: "6.3.14"
|
||||
url_launcher_ios:
|
||||
dependency: transitive
|
||||
description:
|
||||
|
@ -138,7 +138,6 @@ dependencies:
|
||||
flutter_map: ^8.1.0
|
||||
geolocator: ^13.0.2
|
||||
fast_rsa: ^3.8.0
|
||||
flutter_card_swiper: ^7.0.2
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
|
Loading…
x
Reference in New Issue
Block a user