💄 Optimizations
This commit is contained in:
@@ -114,9 +114,9 @@ final apiClientProvider = Provider<Dio>((ref) {
|
||||
dio: dio,
|
||||
retries: 3,
|
||||
retryDelays: const [
|
||||
Duration(seconds: 1),
|
||||
Duration(seconds: 2),
|
||||
Duration(seconds: 3),
|
||||
Duration(milliseconds: 300),
|
||||
Duration(milliseconds: 500),
|
||||
Duration(milliseconds: 1000),
|
||||
],
|
||||
retryEvaluator: (err, _) => err.requestOptions.method == 'GET',
|
||||
),
|
||||
|
@@ -469,24 +469,28 @@ class ChatInput extends HookConsumerWidget {
|
||||
),
|
||||
UploadMenu(
|
||||
items: [
|
||||
MenuItemData(
|
||||
UploadMenuItemData(
|
||||
Symbols.add_a_photo,
|
||||
'addPhoto',
|
||||
() => onPickFile(true),
|
||||
),
|
||||
MenuItemData(
|
||||
UploadMenuItemData(
|
||||
Symbols.videocam,
|
||||
'addVideo',
|
||||
() => onPickFile(false),
|
||||
),
|
||||
MenuItemData(Symbols.mic, 'addAudio', onPickAudio),
|
||||
MenuItemData(
|
||||
UploadMenuItemData(
|
||||
Symbols.mic,
|
||||
'addAudio',
|
||||
onPickAudio,
|
||||
),
|
||||
UploadMenuItemData(
|
||||
Symbols.file_upload,
|
||||
'uploadFile',
|
||||
onPickGeneralFile,
|
||||
),
|
||||
if (onLinkAttachment != null)
|
||||
MenuItemData(
|
||||
UploadMenuItemData(
|
||||
Symbols.attach_file,
|
||||
'linkAttachment',
|
||||
onLinkAttachment!,
|
||||
|
@@ -161,6 +161,7 @@ class MessageItem extends HookConsumerWidget {
|
||||
clipBehavior: Clip.none,
|
||||
children: [
|
||||
SwipeTo(
|
||||
swipeSensitivity: 15,
|
||||
rightSwipeWidget: Transform.flip(
|
||||
flipX: true,
|
||||
child: Icon(Symbols.menu_open),
|
||||
@@ -477,6 +478,8 @@ class _MessageActionSheetState extends State<MessageActionSheet> {
|
||||
Navigator.pop(context);
|
||||
},
|
||||
),
|
||||
|
||||
Gap(MediaQuery.of(context).padding.bottom),
|
||||
],
|
||||
),
|
||||
),
|
||||
|
@@ -16,7 +16,6 @@ import 'package:island/widgets/post/compose_shared.dart';
|
||||
import 'package:material_symbols_icons/symbols.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
import 'package:styled_widget/styled_widget.dart';
|
||||
import 'package:textfield_tags/textfield_tags.dart';
|
||||
|
||||
part 'compose_settings_sheet.g.dart';
|
||||
|
||||
@@ -37,98 +36,6 @@ Future<List<SnPostCategory>> postCategories(Ref ref) async {
|
||||
return uniqueCategories.values.toList();
|
||||
}
|
||||
|
||||
/// A reusable widget for tag input fields with chip display
|
||||
class ChipTagInputField extends StatelessWidget {
|
||||
final InputFieldValues inputFieldValues;
|
||||
final String labelText;
|
||||
final String hintText;
|
||||
|
||||
const ChipTagInputField({
|
||||
super.key,
|
||||
required this.inputFieldValues,
|
||||
required this.labelText,
|
||||
required this.hintText,
|
||||
});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
controller: inputFieldValues.textEditingController,
|
||||
focusNode: inputFieldValues.focusNode,
|
||||
decoration: InputDecoration(
|
||||
label: Text(labelText).tr(),
|
||||
border: OutlineInputBorder(borderRadius: BorderRadius.circular(12)),
|
||||
contentPadding: const EdgeInsets.all(16),
|
||||
hintText: inputFieldValues.tags.isNotEmpty ? '' : hintText.tr(),
|
||||
errorText: inputFieldValues.error,
|
||||
prefixIconConstraints: BoxConstraints(
|
||||
maxWidth: MediaQuery.of(context).size.width * 0.8,
|
||||
),
|
||||
prefixIcon:
|
||||
inputFieldValues.tags.isNotEmpty
|
||||
? SingleChildScrollView(
|
||||
controller: inputFieldValues.tagScrollController,
|
||||
scrollDirection: Axis.vertical,
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(top: 8, bottom: 8, left: 8),
|
||||
child: Wrap(
|
||||
runSpacing: 4.0,
|
||||
spacing: 4.0,
|
||||
children:
|
||||
inputFieldValues.tags.map<Widget>((dynamic tag) {
|
||||
return Container(
|
||||
decoration: BoxDecoration(
|
||||
borderRadius: BorderRadius.all(
|
||||
Radius.circular(20.0),
|
||||
),
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
),
|
||||
margin: const EdgeInsets.only(left: 5),
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 10.0,
|
||||
vertical: 5.0,
|
||||
),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
InkWell(
|
||||
child: Text(
|
||||
'#$tag',
|
||||
style: TextStyle(
|
||||
color:
|
||||
Theme.of(
|
||||
context,
|
||||
).colorScheme.onPrimary,
|
||||
),
|
||||
),
|
||||
),
|
||||
const Gap(4),
|
||||
InkWell(
|
||||
child: const Icon(
|
||||
Icons.cancel,
|
||||
size: 14.0,
|
||||
color: Color.fromARGB(255, 233, 233, 233),
|
||||
),
|
||||
onTap: () {
|
||||
inputFieldValues.onTagRemoved(tag);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}).toList(),
|
||||
),
|
||||
),
|
||||
)
|
||||
: null,
|
||||
),
|
||||
onChanged: inputFieldValues.onTagChanged,
|
||||
onSubmitted: inputFieldValues.onTagSubmitted,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class ComposeSettingsSheet extends HookConsumerWidget {
|
||||
final ComposeState state;
|
||||
|
||||
|
@@ -82,10 +82,10 @@ class ComposeToolbar extends HookConsumerWidget {
|
||||
}
|
||||
|
||||
final uploadMenuItems = [
|
||||
MenuItemData(Symbols.add_a_photo, 'addPhoto', pickPhotoMedia),
|
||||
MenuItemData(Symbols.videocam, 'addVideo', pickVideoMedia),
|
||||
MenuItemData(Symbols.mic, 'addAudio', addAudio),
|
||||
MenuItemData(Symbols.file_upload, 'uploadFile', pickGeneralFile),
|
||||
UploadMenuItemData(Symbols.add_a_photo, 'addPhoto', pickPhotoMedia),
|
||||
UploadMenuItemData(Symbols.videocam, 'addVideo', pickVideoMedia),
|
||||
UploadMenuItemData(Symbols.mic, 'addAudio', addAudio),
|
||||
UploadMenuItemData(Symbols.file_upload, 'uploadFile', pickGeneralFile),
|
||||
];
|
||||
|
||||
final colorScheme = Theme.of(context).colorScheme;
|
||||
|
@@ -2,16 +2,16 @@ import 'package:easy_localization/easy_localization.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:material_symbols_icons/symbols.dart';
|
||||
|
||||
class MenuItemData {
|
||||
class UploadMenuItemData {
|
||||
final IconData icon;
|
||||
final String textKey;
|
||||
final VoidCallback onPressed;
|
||||
|
||||
const MenuItemData(this.icon, this.textKey, this.onPressed);
|
||||
const UploadMenuItemData(this.icon, this.textKey, this.onPressed);
|
||||
}
|
||||
|
||||
class UploadMenu extends StatelessWidget {
|
||||
final List<MenuItemData> items;
|
||||
final List<UploadMenuItemData> items;
|
||||
final bool isCompact;
|
||||
final Color? iconColor;
|
||||
|
||||
@@ -51,6 +51,7 @@ class UploadMenu extends StatelessWidget {
|
||||
onPressed: item.onPressed,
|
||||
leadingIcon: Icon(item.icon),
|
||||
style: ButtonStyle(
|
||||
visualDensity: VisualDensity.compact,
|
||||
padding: WidgetStatePropertyAll(
|
||||
EdgeInsets.only(left: 12, right: 16, top: 20, bottom: 20),
|
||||
),
|
||||
|
Reference in New Issue
Block a user