diff --git a/lib/video_thumbnail_web.dart b/lib/video_thumbnail_web.dart index 755d361..9421a52 100644 --- a/lib/video_thumbnail_web.dart +++ b/lib/video_thumbnail_web.dart @@ -1,5 +1,5 @@ import 'dart:async'; -import 'dart:html'; +import 'dart:js_interop'; import 'dart:math' as math; import 'package:cross_file/cross_file.dart'; @@ -7,6 +7,7 @@ import 'package:flutter/services.dart'; import 'package:flutter_web_plugins/flutter_web_plugins.dart'; import 'package:get_thumbnail_video/src/image_format.dart'; import 'package:get_thumbnail_video/src/video_thumbnail_platform.dart'; +import 'package:web/web.dart'; // An error code value to error name Map. // See: https://developer.mozilla.org/en-US/docs/Web/API/MediaError/code @@ -61,7 +62,7 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { quality: quality, ); - return XFile(Url.createObjectUrlFromBlob(blob), mimeType: blob.type); + return XFile(URL.createObjectURL(blob), mimeType: blob.type); } @override @@ -83,10 +84,10 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { timeMs: timeMs, quality: quality, ); - final path = Url.createObjectUrlFromBlob(blob); + final path = URL.createObjectURL(blob); final file = XFile(path, mimeType: blob.type); final bytes = await file.readAsBytes(); - Url.revokeObjectUrl(path); + URL.revokeObjectURL(path); return bytes; } @@ -102,7 +103,7 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { }) async { final completer = Completer(); - final video = document.createElement('video') as VideoElement; + final video = document.createElement('video') as HTMLVideoElement; final timeSec = math.max(timeMs / 1000, 0); final fetchVideo = headers != null && headers.isNotEmpty; @@ -110,13 +111,13 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { video.currentTime = timeSec; if (fetchVideo) { - Url.revokeObjectUrl(video.src); + URL.revokeObjectURL(video.src); } }); video.onSeeked.listen((Event e) async { if (!completer.isCompleted) { - final canvas = document.createElement('canvas') as CanvasElement; + final canvas = document.createElement('canvas') as HTMLCanvasElement; final ctx = canvas.getContext('2d')! as CanvasRenderingContext2D; if (maxWidth == 0 && maxHeight == 0) { @@ -142,16 +143,18 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { canvas ..width = maxWidth ..height = maxHeight; - ctx.drawImageScaled(video, 0, 0, maxWidth, maxHeight); + ctx.drawImage(video, 0, 0, maxWidth.toDouble(), maxHeight.toDouble()); } try { - final blob = canvas.toBlob( + void callback(Blob? blob) { + completer.complete(blob); + } + canvas.toBlob( + callback.toJS, _imageFormatToCanvasFormat(imageFormat), - quality / 100, + (quality / 100).toJS, ); - - completer.complete(blob); } catch (e, s) { completer.completeError( PlatformException( @@ -189,7 +192,7 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { headers: headers, ); - video.src = Url.createObjectUrlFromBlob(blob); + video.src = URL.createObjectURL(blob); } catch (e, s) { completer.completeError(e, s); } @@ -205,7 +208,7 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { /// Fetching video by [headers]. /// /// To avoid reading the video's bytes into memory, set the - /// [HttpRequest.responseType] to 'blob'. This allows the blob to be stored in + /// [XMLHttpRequest.responseType] to 'blob'. This allows the blob to be stored in /// the browser's disk or memory cache. Future _fetchVideoByHeaders({ required String videoSrc, @@ -213,10 +216,10 @@ class VideoThumbnailWeb extends VideoThumbnailPlatform { }) async { final completer = Completer(); - final xhr = HttpRequest() - ..open('GET', videoSrc, async: true) + final xhr = XMLHttpRequest() + ..open('GET', videoSrc, true) ..responseType = 'blob'; - headers.forEach(xhr.setRequestHeader); + headers.forEach((key, value) => xhr.setRequestHeader(key, value)); xhr.onLoad.first.then((ProgressEvent value) { completer.complete(xhr.response as Blob);