mirror of
https://github.com/AppFlowy-IO/AppFlowy.git
synced 2024-08-30 18:12:39 +00:00
fix: add cover image using url issue (#2733)
* fix: add cover image using url issue * chore: update editor
This commit is contained in:
parent
3e3bdb59ae
commit
f86a98cd51
@ -44,7 +44,6 @@ class _AppFlowyEditorPageState extends State<AppFlowyEditorPage> {
|
|||||||
];
|
];
|
||||||
|
|
||||||
late final slashMenuItems = [
|
late final slashMenuItems = [
|
||||||
dividerMenuItem,
|
|
||||||
inlineGridMenuItem(documentBloc),
|
inlineGridMenuItem(documentBloc),
|
||||||
referenceGridMenuItem,
|
referenceGridMenuItem,
|
||||||
inlineBoardMenuItem(documentBloc),
|
inlineBoardMenuItem(documentBloc),
|
||||||
@ -59,9 +58,6 @@ class _AppFlowyEditorPageState extends State<AppFlowyEditorPage> {
|
|||||||
late final Map<String, BlockComponentBuilder> blockComponentBuilders =
|
late final Map<String, BlockComponentBuilder> blockComponentBuilders =
|
||||||
_customAppFlowyBlockComponentBuilders();
|
_customAppFlowyBlockComponentBuilders();
|
||||||
late final List<CharacterShortcutEvent> characterShortcutEvents = [
|
late final List<CharacterShortcutEvent> characterShortcutEvents = [
|
||||||
// divider
|
|
||||||
convertMinusesToDivider,
|
|
||||||
|
|
||||||
// code block
|
// code block
|
||||||
...codeBlockCharacterEvents,
|
...codeBlockCharacterEvents,
|
||||||
|
|
||||||
|
@ -137,13 +137,13 @@ class CoverImagePickerBloc
|
|||||||
}
|
}
|
||||||
|
|
||||||
String _networkImageName(String url) {
|
String _networkImageName(String url) {
|
||||||
return 'IMG_${DateTime.now().millisecondsSinceEpoch.toString()}.${_getExtention(
|
return 'IMG_${DateTime.now().millisecondsSinceEpoch.toString()}.${_getExtension(
|
||||||
url,
|
url,
|
||||||
fromNetwork: true,
|
fromNetwork: true,
|
||||||
)}';
|
)}';
|
||||||
}
|
}
|
||||||
|
|
||||||
String? _getExtention(
|
String? _getExtension(
|
||||||
String path, {
|
String path, {
|
||||||
bool fromNetwork = false,
|
bool fromNetwork = false,
|
||||||
}) {
|
}) {
|
||||||
@ -153,14 +153,21 @@ class CoverImagePickerBloc
|
|||||||
if (extension.isEmpty) {
|
if (extension.isEmpty) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
ext = extension.substring(1);
|
ext = extension;
|
||||||
} else {
|
} else {
|
||||||
final uri = Uri.parse(path);
|
final uri = Uri.parse(path);
|
||||||
final paramters = uri.queryParameters;
|
final parameters = uri.queryParameters;
|
||||||
final dl = paramters['dl'];
|
if (path.contains('unsplash')) {
|
||||||
|
final dl = parameters['dl'];
|
||||||
if (dl != null) {
|
if (dl != null) {
|
||||||
ext = p.extension(dl).substring(1);
|
ext = p.extension(dl);
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
ext = p.extension(path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (ext != null && ext.isNotEmpty) {
|
||||||
|
ext = ext.substring(1);
|
||||||
}
|
}
|
||||||
if (allowedExtensions.contains(ext)) {
|
if (allowedExtensions.contains(ext)) {
|
||||||
return ext;
|
return ext;
|
||||||
@ -169,7 +176,7 @@ class CoverImagePickerBloc
|
|||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> _validateURL(String path) async {
|
Future<bool> _validateURL(String path) async {
|
||||||
final extension = _getExtention(path, fromNetwork: true);
|
final extension = _getExtension(path, fromNetwork: true);
|
||||||
if (extension == null) {
|
if (extension == null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1,69 +0,0 @@
|
|||||||
import 'package:appflowy/plugins/document/presentation/editor_plugins/base/selectable_svg_widget.dart';
|
|
||||||
import 'package:appflowy/plugins/document/presentation/editor_plugins/divider/divider_node_widget.dart';
|
|
||||||
import 'package:appflowy_editor/appflowy_editor.dart';
|
|
||||||
import 'package:flutter/material.dart';
|
|
||||||
|
|
||||||
/// insert divider into a document by typing three minuses(-).
|
|
||||||
///
|
|
||||||
/// - support
|
|
||||||
/// - desktop
|
|
||||||
/// - web
|
|
||||||
/// - mobile
|
|
||||||
///
|
|
||||||
final CharacterShortcutEvent convertMinusesToDivider = CharacterShortcutEvent(
|
|
||||||
key: 'insert a divider',
|
|
||||||
character: '-',
|
|
||||||
handler: _convertMinusesToDividerHandler,
|
|
||||||
);
|
|
||||||
|
|
||||||
CharacterShortcutEventHandler _convertMinusesToDividerHandler =
|
|
||||||
(editorState) async {
|
|
||||||
final selection = editorState.selection;
|
|
||||||
if (selection == null || !selection.isCollapsed) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
final path = selection.end.path;
|
|
||||||
final node = editorState.getNodeAtPath(path);
|
|
||||||
final delta = node?.delta;
|
|
||||||
if (node == null || delta == null) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (delta.toPlainText() != '--') {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
final transaction = editorState.transaction
|
|
||||||
..insertNode(path, dividerNode())
|
|
||||||
..insertNode(path, paragraphNode())
|
|
||||||
..deleteNode(node)
|
|
||||||
..afterSelection = Selection.collapse(path, 0);
|
|
||||||
editorState.apply(transaction);
|
|
||||||
return true;
|
|
||||||
};
|
|
||||||
|
|
||||||
SelectionMenuItem dividerMenuItem = SelectionMenuItem(
|
|
||||||
name: 'Divider',
|
|
||||||
icon: (editorState, onSelected, style) => SelectableIconWidget(
|
|
||||||
icon: Icons.horizontal_rule,
|
|
||||||
isSelected: onSelected,
|
|
||||||
style: style,
|
|
||||||
),
|
|
||||||
keywords: ['horizontal rule', 'divider'],
|
|
||||||
handler: (editorState, _, __) {
|
|
||||||
final selection = editorState.selection;
|
|
||||||
if (selection == null || !selection.isCollapsed) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
final path = selection.end.path;
|
|
||||||
final node = editorState.getNodeAtPath(path);
|
|
||||||
final delta = node?.delta;
|
|
||||||
if (node == null || delta == null) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
final insertedPath = delta.isEmpty ? path : path.next;
|
|
||||||
final transaction = editorState.transaction
|
|
||||||
..insertNode(insertedPath, dividerNode())
|
|
||||||
..insertNode(insertedPath, paragraphNode())
|
|
||||||
..afterSelection = Selection.collapse(insertedPath.next, 0);
|
|
||||||
editorState.apply(transaction);
|
|
||||||
},
|
|
||||||
);
|
|
@ -1,128 +0,0 @@
|
|||||||
import 'package:appflowy_editor/appflowy_editor.dart';
|
|
||||||
import 'package:flutter/material.dart';
|
|
||||||
|
|
||||||
class DividerBlockKeys {
|
|
||||||
const DividerBlockKeys._();
|
|
||||||
|
|
||||||
static const String type = 'divider';
|
|
||||||
}
|
|
||||||
|
|
||||||
// creating a new callout node
|
|
||||||
Node dividerNode() {
|
|
||||||
return Node(
|
|
||||||
type: DividerBlockKeys.type,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
class DividerBlockComponentBuilder extends BlockComponentBuilder {
|
|
||||||
DividerBlockComponentBuilder({
|
|
||||||
this.padding = const EdgeInsets.symmetric(vertical: 8.0),
|
|
||||||
this.lineColor = Colors.grey,
|
|
||||||
});
|
|
||||||
|
|
||||||
final EdgeInsets padding;
|
|
||||||
final Color lineColor;
|
|
||||||
|
|
||||||
@override
|
|
||||||
BlockComponentWidget build(BlockComponentContext blockComponentContext) {
|
|
||||||
final node = blockComponentContext.node;
|
|
||||||
return DividerBlockComponentWidget(
|
|
||||||
key: node.key,
|
|
||||||
node: node,
|
|
||||||
padding: padding,
|
|
||||||
lineColor: lineColor,
|
|
||||||
showActions: showActions(node),
|
|
||||||
actionBuilder: (context, state) => actionBuilder(
|
|
||||||
blockComponentContext,
|
|
||||||
state,
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
@override
|
|
||||||
bool validate(Node node) => node.children.isEmpty;
|
|
||||||
}
|
|
||||||
|
|
||||||
class DividerBlockComponentWidget extends BlockComponentStatefulWidget {
|
|
||||||
const DividerBlockComponentWidget({
|
|
||||||
super.key,
|
|
||||||
required super.node,
|
|
||||||
super.showActions,
|
|
||||||
super.actionBuilder,
|
|
||||||
super.configuration = const BlockComponentConfiguration(),
|
|
||||||
this.padding = const EdgeInsets.symmetric(vertical: 8.0),
|
|
||||||
this.lineColor = Colors.grey,
|
|
||||||
});
|
|
||||||
|
|
||||||
final EdgeInsets padding;
|
|
||||||
final Color lineColor;
|
|
||||||
|
|
||||||
@override
|
|
||||||
State<DividerBlockComponentWidget> createState() =>
|
|
||||||
_DividerBlockComponentWidgetState();
|
|
||||||
}
|
|
||||||
|
|
||||||
class _DividerBlockComponentWidgetState
|
|
||||||
extends State<DividerBlockComponentWidget> with SelectableMixin {
|
|
||||||
RenderBox get _renderBox => context.findRenderObject() as RenderBox;
|
|
||||||
|
|
||||||
@override
|
|
||||||
Widget build(BuildContext context) {
|
|
||||||
Widget child = Padding(
|
|
||||||
padding: widget.padding,
|
|
||||||
child: Container(
|
|
||||||
height: 10,
|
|
||||||
alignment: Alignment.center,
|
|
||||||
child: Divider(
|
|
||||||
color: widget.lineColor,
|
|
||||||
thickness: 1,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
|
|
||||||
if (widget.actionBuilder != null) {
|
|
||||||
child = BlockComponentActionWrapper(
|
|
||||||
node: widget.node,
|
|
||||||
actionBuilder: widget.actionBuilder!,
|
|
||||||
child: child,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return child;
|
|
||||||
}
|
|
||||||
|
|
||||||
@override
|
|
||||||
Position start() => Position(path: widget.node.path, offset: 0);
|
|
||||||
|
|
||||||
@override
|
|
||||||
Position end() => Position(path: widget.node.path, offset: 1);
|
|
||||||
|
|
||||||
@override
|
|
||||||
Position getPositionInOffset(Offset start) => end();
|
|
||||||
|
|
||||||
@override
|
|
||||||
bool get shouldCursorBlink => false;
|
|
||||||
|
|
||||||
@override
|
|
||||||
CursorStyle get cursorStyle => CursorStyle.cover;
|
|
||||||
|
|
||||||
@override
|
|
||||||
Rect? getCursorRectInPosition(Position position) {
|
|
||||||
final size = _renderBox.size;
|
|
||||||
return Rect.fromLTWH(-size.width / 2.0, 0, size.width, size.height);
|
|
||||||
}
|
|
||||||
|
|
||||||
@override
|
|
||||||
List<Rect> getRectsInSelection(Selection selection) =>
|
|
||||||
[Offset.zero & _renderBox.size];
|
|
||||||
|
|
||||||
@override
|
|
||||||
Selection getSelectionInRange(Offset start, Offset end) => Selection.single(
|
|
||||||
path: widget.node.path,
|
|
||||||
startOffset: 0,
|
|
||||||
endOffset: 1,
|
|
||||||
);
|
|
||||||
|
|
||||||
@override
|
|
||||||
Offset localToGlobal(Offset offset) => _renderBox.localToGlobal(offset);
|
|
||||||
}
|
|
@ -7,8 +7,6 @@ export 'code_block/code_block_shortcut_event.dart';
|
|||||||
export 'cover/change_cover_popover_bloc.dart';
|
export 'cover/change_cover_popover_bloc.dart';
|
||||||
export 'cover/cover_node_widget.dart';
|
export 'cover/cover_node_widget.dart';
|
||||||
export 'cover/cover_image_picker.dart';
|
export 'cover/cover_image_picker.dart';
|
||||||
export 'divider/divider_node_widget.dart';
|
|
||||||
export 'divider/divider_character_shortcut_event.dart';
|
|
||||||
export 'emoji_picker/emoji_menu_item.dart';
|
export 'emoji_picker/emoji_menu_item.dart';
|
||||||
export 'extensions/flowy_tint_extension.dart';
|
export 'extensions/flowy_tint_extension.dart';
|
||||||
export 'grid/grid_menu_item.dart';
|
export 'grid/grid_menu_item.dart';
|
||||||
|
@ -52,10 +52,11 @@ packages:
|
|||||||
appflowy_editor:
|
appflowy_editor:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: appflowy_editor
|
path: "."
|
||||||
sha256: "559906bc150994c433ceb312333629d0f9a551ad95b4ce577352d6a007343cdc"
|
ref: "7fe5bb8"
|
||||||
url: "https://pub.dev"
|
resolved-ref: "7fe5bb85d455416ddbce4bbf2afed1c434466eeb"
|
||||||
source: hosted
|
url: "https://github.com/AppFlowy-IO/appflowy-editor.git"
|
||||||
|
source: git
|
||||||
version: "1.0.0"
|
version: "1.0.0"
|
||||||
appflowy_popover:
|
appflowy_popover:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
@ -684,10 +685,10 @@ packages:
|
|||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: intl
|
name: intl
|
||||||
sha256: "3bc132a9dbce73a7e4a21a17d06e1878839ffbf975568bc875c60537824b0c4d"
|
sha256: a3715e3bc90294e971cb7dc063fbf3cd9ee0ebf8604ffeafabd9e6f16abbdbe6
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.18.1"
|
version: "0.18.0"
|
||||||
intl_utils:
|
intl_utils:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -812,10 +813,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: material_color_utilities
|
name: material_color_utilities
|
||||||
sha256: "586678f20e112219ed0f73215f01bcdf1d769824ba2ebae45ad918a9bfde9bdb"
|
sha256: d92141dc6fe1dad30722f9aa826c7fbc896d021d792f80678280601aff8cf724
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.3.0"
|
version: "0.2.0"
|
||||||
meta:
|
meta:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -1329,10 +1330,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: source_span
|
name: source_span
|
||||||
sha256: "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c"
|
sha256: dd904f795d4b4f3b870833847c461801f6750a9fa8e61ea5ac53f9422b31f250
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.10.0"
|
version: "1.9.1"
|
||||||
stack_trace:
|
stack_trace:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -1425,26 +1426,26 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test
|
name: test
|
||||||
sha256: "4f92f103ef63b1bbac6f4bd1930624fca81b2574464482512c4f0896319be575"
|
sha256: "3dac9aecf2c3991d09b9cdde4f98ded7b30804a88a0d7e4e7e1678e78d6b97f4"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.24.2"
|
version: "1.24.1"
|
||||||
test_api:
|
test_api:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test_api
|
name: test_api
|
||||||
sha256: daadc9baabec998b062c9091525aa95786508b1c48e9c30f1f891b8bf6ff2e64
|
sha256: eb6ac1540b26de412b3403a163d919ba86f6a973fe6cc50ae3541b80092fdcfb
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.5.2"
|
version: "0.5.1"
|
||||||
test_core:
|
test_core:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test_core
|
name: test_core
|
||||||
sha256: "3642b184882f79e76ca57a9230fb971e494c3c1fd09c21ae3083ce891bcc0aa1"
|
sha256: "5138dbffb77b2289ecb12b81c11ba46036590b72a64a7a90d6ffb880f1a29e93"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.5.2"
|
version: "0.5.1"
|
||||||
textfield_tags:
|
textfield_tags:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -1617,10 +1618,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: vm_service
|
name: vm_service
|
||||||
sha256: "518254c0d3ee20667a1feef39eefe037df87439851e4b3cb277e5b3f37afa2f0"
|
sha256: f6deed8ed625c52864792459709183da231ebf66ff0cf09e69b573227c377efe
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "11.4.0"
|
version: "11.3.0"
|
||||||
watcher:
|
watcher:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -42,7 +42,11 @@ dependencies:
|
|||||||
git:
|
git:
|
||||||
url: https://github.com/AppFlowy-IO/appflowy-board.git
|
url: https://github.com/AppFlowy-IO/appflowy-board.git
|
||||||
ref: a183c57
|
ref: a183c57
|
||||||
appflowy_editor: ^1.0.0
|
# appflowy_editor: ^1.0.0
|
||||||
|
appflowy_editor:
|
||||||
|
git:
|
||||||
|
url: https://github.com/AppFlowy-IO/appflowy-editor.git
|
||||||
|
ref: 7fe5bb8
|
||||||
appflowy_popover:
|
appflowy_popover:
|
||||||
path: packages/appflowy_popover
|
path: packages/appflowy_popover
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user