diff --git a/README.md b/README.md index e5515225..6b9f490d 100644 --- a/README.md +++ b/README.md @@ -38,6 +38,7 @@ This plugin built upon flutter's official [`video_player`](https://pub.dartlang. - Custom overlay - Custom progress bar - Custom labels +- Video Watermark (With ability to show/hide the watermark from the controller) - `Change video quality` (for vimeo and youtube) - Enable/disable full-screen player - support for live youtube video @@ -299,6 +300,34 @@ Widget build(BuildContext context) { } ``` +## Add Video Watermark + +```dart +@override +Widget build(BuildContext context) { + return Scaffold( + body: PodVideoPlayer( + controller: controller, + videoWatermark: const Center( + child: FlutterLogo(size: 150), + ), + ), + ); +} +``` + +You can also use the `controller` to show/hide the watermark at any time. + +```dart +// show watermark +controller.showWatermark(); + +// hide watermark +controller.hideWatermark(); +``` + +**Note:** The watermark is **hidden** by default. + ## How to play video from youtube --- diff --git a/example/lib/screens/cutom_video_controllers.dart b/example/lib/screens/cutom_video_controllers.dart index ce511edb..0aa5528a 100644 --- a/example/lib/screens/cutom_video_controllers.dart +++ b/example/lib/screens/cutom_video_controllers.dart @@ -110,6 +110,9 @@ class _CustomVideoControllsState extends State { matchFrameAspectRatioToVideo: true, matchVideoAspectRatioToFrame: true, videoTitle: videoTitle, + videoWatermark: const Center( + child: FlutterLogo(size: 150), + ), ), Padding( padding: const EdgeInsets.all(12.0), @@ -165,6 +168,17 @@ class _CustomVideoControllsState extends State { onPressed: () { controller.hideOverlay(); }), + sizeH20, + _iconButton('Show Watermark', Icons.verified_rounded, + onPressed: () { + controller.showWatermark(); + }), + sizeH20, + _iconButton('Hide Watermark', Icons.verified_outlined, + onPressed: () { + controller.hideWatermark(); + }), + sizeH20, _iconButton('Backward video 5s', Icons.replay_5_rounded, onPressed: () { controller.doubleTapVideoBackward(5); diff --git a/lib/src/controllers/pod_player_controller.dart b/lib/src/controllers/pod_player_controller.dart index 229ce884..dfc03276 100644 --- a/lib/src/controllers/pod_player_controller.dart +++ b/lib/src/controllers/pod_player_controller.dart @@ -268,4 +268,10 @@ class PodPlayerController { /// Show overlay of video void showOverlay() => _ctr.isShowOverlay(true); + + /// Hide watermark of video + void hideWatermark() => _ctr.isShowWatermark(false); + + /// Show watermark of video + void showWatermark() => _ctr.isShowWatermark(true); } diff --git a/lib/src/controllers/pod_ui_controller.dart b/lib/src/controllers/pod_ui_controller.dart index 7b19cf2a..c55287d4 100644 --- a/lib/src/controllers/pod_ui_controller.dart +++ b/lib/src/controllers/pod_ui_controller.dart @@ -6,6 +6,7 @@ class _PodUiController extends _PodBaseController { Widget Function(OverLayOptions options)? overlayBuilder; Widget? videoTitle; DecorationImage? videoThumbnail; + Widget? videoWatermark; /// Callback when fullscreen mode changes Future Function(bool isFullScreen)? onToggleFullScreen; diff --git a/lib/src/controllers/pod_video_controller.dart b/lib/src/controllers/pod_video_controller.dart index 0a0d4ea6..bb4e95f3 100644 --- a/lib/src/controllers/pod_video_controller.dart +++ b/lib/src/controllers/pod_video_controller.dart @@ -5,6 +5,7 @@ class _PodVideoController extends _PodUiController { Timer? showOverlayTimer1; bool isOverlayVisible = true; + bool isWatermarkVisible = false; bool isLooping = false; bool isFullScreen = false; bool isvideoPlaying = false; @@ -111,6 +112,15 @@ class _PodVideoController extends _PodUiController { }); } + /// Toggle watermark visibility. + void isShowWatermark(bool val) { + if (isWatermarkVisible == val) return; + + isWatermarkVisible = val; + update(['watermark']); + update(['update-all']); + } + ///overlay above video contrller void toggleVideoOverlay() { if (!isOverlayVisible) { diff --git a/lib/src/pod_player.dart b/lib/src/pod_player.dart index 82f451f8..201d67f8 100644 --- a/lib/src/pod_player.dart +++ b/lib/src/pod_player.dart @@ -20,6 +20,8 @@ part 'widgets/core/overlays/mobile_overlay.dart'; part 'widgets/core/overlays/overlays.dart'; +part 'widgets/core/video_watermark.dart'; + part 'widgets/core/overlays/web_dropdown_menu.dart'; part 'widgets/core/overlays/web_overlay.dart'; @@ -45,6 +47,9 @@ class PodVideoPlayer extends StatefulWidget { final Color? backgroundColor; final DecorationImage? videoThumbnail; + /// Optional watermark widget that is shown on the top of the video. + final Widget? videoWatermark; + /// Optional callback, fired when full screen mode toggles. /// /// Important: If this method is set, the configuration of [DeviceOrientation] @@ -72,6 +77,7 @@ class PodVideoPlayer extends StatefulWidget { this.videoThumbnail, this.onToggleFullScreen, this.onLoading, + this.videoWatermark, }) { addToUiController(); } @@ -90,7 +96,8 @@ class PodVideoPlayer extends StatefulWidget { ..videoTitle = videoTitle ..onToggleFullScreen = onToggleFullScreen ..onLoading = onLoading - ..videoThumbnail = videoThumbnail; + ..videoThumbnail = videoThumbnail + ..videoWatermark = videoWatermark; } @override diff --git a/lib/src/widgets/core/pod_core_player.dart b/lib/src/widgets/core/pod_core_player.dart index 7a7a3e47..4e14e349 100644 --- a/lib/src/widgets/core/pod_core_player.dart +++ b/lib/src/widgets/core/pod_core_player.dart @@ -68,6 +68,7 @@ class _PodCoreVideoPlayer extends StatelessWidget { }, ), ), + _VideoWatermark(tag: tag), _VideoOverlays(tag: tag), IgnorePointer( child: GetBuilder( diff --git a/lib/src/widgets/core/video_watermark.dart b/lib/src/widgets/core/video_watermark.dart new file mode 100644 index 00000000..dd388f24 --- /dev/null +++ b/lib/src/widgets/core/video_watermark.dart @@ -0,0 +1,26 @@ +part of 'package:pod_player/src/pod_player.dart'; + +class _VideoWatermark extends StatelessWidget { + final String tag; + + const _VideoWatermark({ + required this.tag, + }); + + @override + Widget build(BuildContext context) { + return IgnorePointer( + child: GetBuilder( + tag: tag, + id: 'watermark', + builder: (podCtr) { + if (podCtr.videoWatermark == null || !podCtr.isWatermarkVisible) { + return const SizedBox.shrink(); + } + + return podCtr.videoWatermark!; + }, + ), + ); + } +}