feat: added 'Add Video' feature

This commit is contained in:
jideguru 2021-06-06 21:09:09 +01:00
parent 066b2019f2
commit 7b809401ec
6 changed files with 100 additions and 25 deletions

View File

@ -474,6 +474,25 @@ var editor = {
} }
}, },
insertVideo: function(url, width, height, fromDevice) {
console.log(url);
if (fromDevice) {
this._insertVideo(url, width, height);
} else {
this._insertYoutubeVideo(url, width, height);
}
},
_insertYoutubeVideo: function(url, width, height) {
var html = '<iframe width="'+ width +'" height="'+ height +'" src="' + url + '" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture"></iframe>';
this._insertHtml(html);
},
_insertVideo: function(url, width, height) {
var html = '<video width="'+ width +'" height="'+ height +'" controls><source type="video/mp4" src="'+ url +'"></video>'
this._insertHtml(html);
},
insertCheckbox: function(text) { insertCheckbox: function(text) {
var editor = this; var editor = this;

View File

@ -88,6 +88,11 @@ class BasicDemo extends StatelessWidget {
String base64String = 'data:image/png;base64, $base64'; String base64String = 'data:image/png;base64, $base64';
return base64String; return base64String;
}, },
getVideoUrl: (video) {
String link = 'https://file-examples-com.github.io/uploads/2017/'
'04/file_example_MP4_480_1_5MG.mp4';
return link;
},
), ),
); );
} }

View File

@ -88,11 +88,7 @@ class RichEditorState extends State<RichEditor> {
children: [ children: [
Visibility( Visibility(
visible: widget.editorOptions!.barPosition == BarPosition.TOP, visible: widget.editorOptions!.barPosition == BarPosition.TOP,
child: EditorToolBar( child: _buildToolBar(),
getImageUrl: widget.getImageUrl,
javascriptExecutor: javascriptExecutor,
enableVideo: widget.editorOptions!.enableVideo,
),
), ),
Expanded( Expanded(
child: InAppWebView( child: InAppWebView(
@ -135,16 +131,21 @@ class RichEditorState extends State<RichEditor> {
), ),
Visibility( Visibility(
visible: widget.editorOptions!.barPosition == BarPosition.BOTTOM, visible: widget.editorOptions!.barPosition == BarPosition.BOTTOM,
child: EditorToolBar( child: _buildToolBar(),
getImageUrl: widget.getImageUrl,
javascriptExecutor: javascriptExecutor,
enableVideo: widget.editorOptions!.enableVideo,
),
), ),
], ],
); );
} }
_buildToolBar() {
return EditorToolBar(
getImageUrl: widget.getImageUrl,
getVideoUrl: widget.getVideoUrl,
javascriptExecutor: javascriptExecutor,
enableVideo: widget.editorOptions!.enableVideo,
);
}
_setInitialValues() async { _setInitialValues() async {
if (widget.value != null) await javascriptExecutor.setHtml(widget.value!); if (widget.value != null) await javascriptExecutor.setHtml(widget.value!);
if (widget.editorOptions!.padding != null) if (widget.editorOptions!.padding != null)

View File

@ -198,6 +198,23 @@ class JavascriptExecutorBase {
); );
} }
insertVideo(String url,
{int? width, int? height, bool fromDevice = true}) async {
bool? local;
local = fromDevice ? true : null;
if (width == null) width = 300;
if (height == null) height = 220;
// check if link is yt link
if (url.contains('youtu')) {
// Get Video id from link.
String youtubeId = url.split(r'?v=')[1];
url = 'https://www.youtube.com/embed/$youtubeId';
}
await executeJavascript(
"insertVideo('$url', '$width', '$height', $local);",
);
}
insertCheckbox(String text) async { insertCheckbox(String text) async {
await executeJavascript("insertCheckbox('$text');"); await executeJavascript("insertCheckbox('$text');");
} }

View File

@ -71,7 +71,6 @@ class EditorToolBar extends StatelessWidget {
onTap: () async { onTap: () async {
var link = await showDialog( var link = await showDialog(
context: context, context: context,
barrierDismissible: false,
builder: (_) { builder: (_) {
return InsertImageDialog(); return InsertImageDialog();
}, },
@ -88,11 +87,27 @@ class EditorToolBar extends StatelessWidget {
}, },
), ),
Visibility( Visibility(
visible: false, visible: enableVideo!,
child: TabButton( child: TabButton(
tooltip: 'Insert video', tooltip: 'Insert video',
icon: Icons.video_call_sharp, icon: Icons.video_call_sharp,
onTap: () async {}, onTap: () async {
var link = await showDialog(
context: context,
builder: (_) {
return InsertImageDialog(isVideo: true);
},
);
if(link != null) {
if (getVideoUrl != null && link[2]) {
link[0] = await getVideoUrl!(File(link[0]));
}
await javascriptExecutor.insertVideo(
link[0],
fromDevice: link[2],
);
}
},
), ),
), ),
TabButton( TabButton(

View File

@ -4,6 +4,10 @@ import 'package:image_picker/image_picker.dart';
import 'custom_dialog_template.dart'; import 'custom_dialog_template.dart';
class InsertImageDialog extends StatefulWidget { class InsertImageDialog extends StatefulWidget {
final bool isVideo;
InsertImageDialog({this.isVideo = false});
@override @override
_InsertImageDialogState createState() => _InsertImageDialogState(); _InsertImageDialogState createState() => _InsertImageDialogState();
} }
@ -21,7 +25,7 @@ class _InsertImageDialogState extends State<InsertImageDialog> {
Row( Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween, mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [ children: [
Text('Image link'), Text(widget.isVideo ? 'Video link' : 'Image link'),
ElevatedButton( ElevatedButton(
onPressed: () => getImage(), onPressed: () => getImage(),
child: Text('...'), child: Text('...'),
@ -34,12 +38,21 @@ class _InsertImageDialogState extends State<InsertImageDialog> {
hintText: '', hintText: '',
), ),
), ),
SizedBox(height: 20.0), Visibility(
Text('Alt text (optional)'), visible: !widget.isVideo,
TextField( child: Column(
controller: alt, mainAxisSize: MainAxisSize.min,
decoration: InputDecoration( crossAxisAlignment: CrossAxisAlignment.start,
hintText: '', children: [
SizedBox(height: 20.0),
Text('Alt text (optional)'),
TextField(
controller: alt,
decoration: InputDecoration(
hintText: '',
),
),
],
), ),
), ),
], ],
@ -50,11 +63,16 @@ class _InsertImageDialogState extends State<InsertImageDialog> {
Future getImage() async { Future getImage() async {
final picker = ImagePicker(); final picker = ImagePicker();
var image = await picker.getImage( var image;
source: ImageSource.gallery, if (widget.isVideo) {
maxWidth: 800.0, image = await picker.getVideo(source: ImageSource.gallery);
maxHeight: 600.0, } else {
); image = await picker.getImage(
source: ImageSource.gallery,
maxWidth: 800.0,
maxHeight: 600.0,
);
}
if (image != null) { if (image != null) {
link.text = image.path; link.text = image.path;