feat(chat): prevent duplicate paste image context menu options
This commit is contained in:
@@ -319,10 +319,9 @@ class _ModernChatInputState extends ConsumerState<ModernChatInput>
|
|||||||
|
|
||||||
/// Builds a custom context menu with standard options plus "Paste Image".
|
/// Builds a custom context menu with standard options plus "Paste Image".
|
||||||
///
|
///
|
||||||
/// The standard paste only works for text. This adds a "Paste Image"
|
/// Adds a "Paste Image" option when there's an image in the clipboard,
|
||||||
/// option that uses the pasteboard package to read images from clipboard
|
/// but only if the system hasn't already provided one (to avoid duplicates
|
||||||
/// on both iOS and Android. The option only appears when there's actually
|
/// on platforms like iOS that may include their own paste image option).
|
||||||
/// an image in the clipboard.
|
|
||||||
Widget _buildContextMenu(
|
Widget _buildContextMenu(
|
||||||
BuildContext context,
|
BuildContext context,
|
||||||
EditableTextState editableTextState,
|
EditableTextState editableTextState,
|
||||||
@@ -348,27 +347,41 @@ class _ModernChatInputState extends ConsumerState<ModernChatInput>
|
|||||||
final hasImage = imageData != null && imageData.isNotEmpty;
|
final hasImage = imageData != null && imageData.isNotEmpty;
|
||||||
|
|
||||||
if (hasImage) {
|
if (hasImage) {
|
||||||
// Find the index of the standard Paste button to insert after it
|
// Check if the system already provides a paste image option
|
||||||
final pasteIndex = buttonItems.indexWhere(
|
// (e.g., iOS may include one automatically). Look for any button
|
||||||
(item) => item.type == ContextMenuButtonType.paste,
|
// with a label containing "image" (case-insensitive) to avoid
|
||||||
|
// adding a duplicate.
|
||||||
|
final pasteImageLabel =
|
||||||
|
AppLocalizations.of(context)?.pasteImage ?? 'Paste Image';
|
||||||
|
final alreadyHasPasteImage = buttonItems.any(
|
||||||
|
(item) =>
|
||||||
|
item.label != null &&
|
||||||
|
item.label!.toLowerCase().contains('image'),
|
||||||
);
|
);
|
||||||
|
|
||||||
// Capture imageData in closure to avoid re-reading clipboard
|
if (!alreadyHasPasteImage) {
|
||||||
final pasteImageItem = ContextMenuButtonItem(
|
// Find the index of the standard Paste button to insert after it
|
||||||
label: AppLocalizations.of(context)?.pasteImage ?? 'Paste Image',
|
final pasteIndex = buttonItems.indexWhere(
|
||||||
onPressed: () {
|
(item) => item.type == ContextMenuButtonType.paste,
|
||||||
// Close the context menu first
|
);
|
||||||
ContextMenuController.removeAny();
|
|
||||||
// Use the captured imageData directly
|
|
||||||
_handleClipboardPasteWithData(imageData);
|
|
||||||
},
|
|
||||||
);
|
|
||||||
|
|
||||||
// Insert after Paste if found, otherwise add at the end
|
// Capture imageData in closure to avoid re-reading clipboard
|
||||||
if (pasteIndex >= 0) {
|
final pasteImageItem = ContextMenuButtonItem(
|
||||||
buttonItems.insert(pasteIndex + 1, pasteImageItem);
|
label: pasteImageLabel,
|
||||||
} else {
|
onPressed: () {
|
||||||
buttonItems.add(pasteImageItem);
|
// Close the context menu first
|
||||||
|
ContextMenuController.removeAny();
|
||||||
|
// Use the captured imageData directly
|
||||||
|
_handleClipboardPasteWithData(imageData);
|
||||||
|
},
|
||||||
|
);
|
||||||
|
|
||||||
|
// Insert after Paste if found, otherwise add at the end
|
||||||
|
if (pasteIndex >= 0) {
|
||||||
|
buttonItems.insert(pasteIndex + 1, pasteImageItem);
|
||||||
|
} else {
|
||||||
|
buttonItems.add(pasteImageItem);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1621,7 +1634,7 @@ class _ModernChatInputState extends ConsumerState<ModernChatInput>
|
|||||||
.toList(),
|
.toList(),
|
||||||
onContentInserted: _handleContentInserted,
|
onContentInserted: _handleContentInserted,
|
||||||
),
|
),
|
||||||
// Custom context menu with "Paste Image" option for iOS
|
// Custom context menu with "Paste Image" option
|
||||||
contextMenuBuilder: (context, editableTextState) {
|
contextMenuBuilder: (context, editableTextState) {
|
||||||
return _buildContextMenu(context, editableTextState);
|
return _buildContextMenu(context, editableTextState);
|
||||||
},
|
},
|
||||||
|
|||||||
Reference in New Issue
Block a user