ABMediaView 可以显示图片、视频以及现在也可以显示 GIF 和音频!它继承自 UIImageView,并具有从网络懒加载数据图片的功能。此外,它还可以显示通过 URL 从磁盘或网络下载的视频。视频包含一个带有时间线和快进功能的播放器。GIF 也可以通过从网络惰性加载或通过 NSData 设置在 ABMediaView 中显示。下载的 GIF 会保存为 UIImage 对象以便于存储。音频也可以通过仅提供一个来自网络或磁盘的 URL 来在播放器中显示。一个重要的新增功能是,该媒体视图有一个队列并且可以全屏显示媒体视图。有功能允许通过滑动使视图最小化,视图处于右下角作为缩略图。视频可以从此位置继续播放和听。用户可以选择滑动视图以关闭。有许多不同的功能可以开启或关闭以适应个人选择。
要运行示例项目,请先克隆仓库,然后从 Example 目录中运行 pod install
如有进一步功能建议,请在 @TrepIsLife 上发推文!
ABMediaView 可通过 CocoaPods 获取。要安装,只需将以下行添加到您的 Podfile 中
pod "ABMediaView"
您可以使用以下行将 import ABMediaView 添加到您的类中
#import <ABMediaView/ABMediaView.h>
作为一个单例类,您可以通过 + sharedManager 方法在任何地方访问管理器
[ABMediaView sharedManager];
有几个函数可以用于排队、显示和关闭 ABMediaView。这些函数由共享管理器处理,首先是 'queueMediaView' 函数。此函数用于将新的 ABMediaView 添加到队列中。如果队列中没有 ABMediaView,则添加的新队列将显示。
[[ABMediaView sharedManager] queueMediaView:mediaView];
其次,如果您想要显示 ABMediaView 并跳过队列,则可以利用 'presentMediaView' 函数完成此操作。调用此函数将关闭当前正在显示的 ABMediaView,并将提供的 ABMediaView 移至队列的前端。
// Presented with animation
[[ABMediaView sharedManager] presentMediaView:mediaView];
// Presented with the option to animate
[[ABMediaView sharedManager] presentMediaView:mediaView animated:NO];
另一方面,如果您想要关闭当前显示的 ABMediaView,则可以调用 'dismissMediaViewAnimated:withCompletion:' 函数。如果视图已最小化,则使其移动并消失在屏幕上。如果没有,视图将直接消失。它附带一个完成块,以便在消失后执行操作。
[mediaView dismissMediaViewAnimated:YES withCompletion:^(BOOL completed) {
// Executes after mediaView finishes dismissing itself
}];
以下功能结合了前两个功能的功能。如果队列中有多个 ABMediaView,则可以通过在共享管理器上调用 'presentNextMediaView' 函数来显示下一个视图。此函数将关闭当前 ABMediaView,并显示队列中的下一个视图。当前 ABMediaView 关闭后,如果没有其他视图要显示,则不执行任何进一步操作。
[[ABMediaView sharedManager] presentNextMediaView];
如果您想删除队列中的 ABMediaView,可以通过在共享管理器上调用 'removeFromQueue' 函数来实现。这将从队列中删除 ABMediaView。
[[ABMediaView sharedManager] removeFromQueue:mediaView];
ABMediaView 可以通过程序化初始化,或者通过界面构建器中在 ImageView 子类中初始化。
ABMediaView *mediaView = [[ABMediaView alloc] initWithFrame:self.view.frame];
ABMediaView 提供了懒加载功能,只需要提供图像或视频源 URL。还有一个完成块,在其中返回下载的图像以进行缓存。
// Set the image to be displayed in the mediaView, which will be downloaded and available for caching
[mediaView setImageURL:@"http://yoursite.com/yourimage.jpg"];
// Similar to the preview method, with a completion handler for when the image has completed downloading
[mediaView setImageURL:@"http://yoursite.com/yourimage.jpg" withCompletion:^(UIImage *image, NSError *error) {
// Execute code upon completion
}];
// Set the video to be displayed in the mediaView, which will be downloaded and available for caching
[mediaView setVideoURL:@"http://yoursite/yourvideo.mp4"];
// Set both the video url, and the thumbnail image for the mediaView, downloading both and making both available for caching
[mediaView setVideoURL:@"http://yoursite/yourvideo.mp4" withThumbnailURL:@"http://yoursite.com/yourimage.jpg"];
// Set the video url for the mediaView , downloading it and making it available for caching, as well as the thumbnail image
[mediaView setVideoURL:@"http://yoursite/yourvideo.mp4" withThumbnailImage:[UIImage imageNamed: @"thumbnail.png"]];
如果从文档目录加载文件(例如,您从网络上下载了视频现在想要显示它),则可以通过设置 ABMediaView 上的 'fileFromDirectory' 变量来指定目录中的内容 BaselURL。
// Designates that the file is sourced from the Documents Directory of the user's device
[mediaView setFileFromDirectory:YES];
ABMediaView 也支持 GIF。要将 GIF 设置到 ABMediaView 中,只需通过 URL 或 NSData 设置即可,它将被下载并设置到视图中。GIF 作为 UIImages 提供,以便于存储。
// GIFs can be displayed in ABMediaView, where the GIF can be downloaded from the internet
[mediaView setGifURL:@"http://yoursite/yourgif.gif"];
// GIFs can also be displayed via NSData
NSData *gifData = ...;
[mediaView setGifData:gifData];
此外,ABMediaView 也提供了音频支持。要设置音频到 ABMediaView,只需通过 URL 设置即可,它将被下载并设置到视图中。
// Set the audio to be displayed in the mediaView
[mediaView setAudioURL:@"http://yoursite/youraudio.mp4"];
// Set both the audio and thumbnail url for the mediaView
[mediaView setAudioURL:@"http://yoursite/youraudio.mp4" withThumbnailURL:@"http://yoursite.com/yourimage.jpg"];
// Set the audio url for the mediaViee, as well as the thumbnail image
[mediaView setAudioURL:@"http://yoursite/youraudio.mp4" withThumbnailImage:[UIImage imageNamed:@"thumbnail.png"]];
关于应用程序中的播放,已添加功能确保音频在用户设备静音时也能播放。这些变量设置使音频在 ABMediaView 中媒体开始和结束时播放,并且可以使用 ABMediaView 类方法进行设置。
// Toggle this functionality to enable/disable sound to play when an ABMediaView begins playing, and the user's app is on silent
[ABMediaView setPlaysAudioWhenPlayingMediaOnSilent:YES];
// In addition, toggle this functionality to enable/disable sound to play when an ABMediaView ends playing, and the user's app is on silent
[ABMediaView setPlaysAudioWhenStoppingMediaOnSilent:NO];
额外功能: GIF 也可以用作视频和音频的缩略图。
// Set video for mediaView by URL, and set GIF as thumbnail by URL
[mediaView setVideoURL:@"www.video.com/urlHere" withThumbnailGifURL:@"http://yoursite/yourgif.gif"];
// Set video for mediaView by URL, and set GIF as thumbnail using NSData
[mediaView setVideoURL:@"www.video.com/urlHere" withThumbnailGifData:gifData];
// Set audio for mediaView by URL, and set GIF as thumbnail by URL
[mediaView setAudioURL:@"www.audio.com/urlHere" withThumbnailGifURL:@"http://yoursite/yourgif.gif"];
// Set audio for mediaView by URL, and set GIF as thumbnail using NSData
[mediaView setAudioURL:@"www.audio.com/urlHere" withThumbnailGifData:gifData];
另一个额外功能是,当用户按住 ABMediaView 时,会显示 GIF 预览。此功能目前适用于视频,可以使用以下方法实现
/// Set the url where the video can be downloaded from, as well as the image for the thumbnail, and added functionality where when the user presses and holds on the thumbnail, it turns into a GIF. GIF is added via URL
- (void) setVideoURL:(NSString *)videoURL withThumbnailImage:(UIImage *) thumbnail andPreviewGifURL:(NSString *) thumbnailGifURL;
/// Set the url where the video can be downloaded from, as well as the image for the thumbnail, and added functionality where when the user presses and holds on the thumbnail, it turns into a GIF. GIF is added via NSData
- (void) setVideoURL:(NSString *)videoURL withThumbnailImage:(UIImage *) thumbnail andPreviewGifData:(NSData *) thumbnailGifData;
/// Set the url where the video can be downloaded from, as well as the url where the thumbnail image can be found, and added functionality where when the user presses and holds on the thumbnail, it turns into a GIF. GIF is added via URL
- (void) setVideoURL:(NSString *)videoURL withThumbnailURL:(NSString *) thumbnailURL andPreviewGifURL:(NSString *) thumbnailGifURL;
/// Set the url where the video can be downloaded from, as well as the url where the thumbnail image can be found, and added functionality where when the user presses and holds on the thumbnail, it turns into a GIF. GIF is added via NSData
- (void) setVideoURL:(NSString *)videoURL withThumbnailURL:(NSString *) thumbnailURL andPreviewGifData:(NSData *) thumbnailGifData;
极其重要 如果您的应用程序支持设备旋转,请将以下代码块放置在您的应用程序的根视图控制器中,或在初始化 ABMediaView 的视图控制器中。这将允许 ABMediaView 了解用户的设备何时正在旋转,并使其能够相应旋转。
// If 'viewWillTransitionToSize' is already implemented in your code, add the two ABMediaViewNotifications to your 'animateAlongsideTransition' block
- (void)viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id)coordinator {
[super viewWillTransitionToSize:size withTransitionCoordinator:coordinator];
// Executes before and after rotation, that way any ABMediaViews can adjust their frames for the new size. Is especially helpful when users are watching landscape videos and rotate their devices between portrait and landscape.
[coordinator animateAlongsideTransition:^(id _Nonnull context) {
// Notifies the ABMediaView that the device is about to rotate
[[NSNotificationCenter defaultCenter] postNotificationName:ABMediaViewWillRotateNotification object:nil];
} completion:^(id _Nonnull context) {
// Notifies the ABMediaView that the device just finished rotating
[[NSNotificationCenter defaultCenter] postNotificationName:ABMediaViewDidRotateNotification object:nil];
}];
}
关于屏幕旋转,如果您的应用程序的 UI 需要肖像模式,但您希望 ABMediaView 在横屏模式下可见,那么在示例项目中已经包括了处理这种情况的方法。这是一个常用的功能,因此将其包含其中可简化此类功能开发。此方法利用 ABMediaView 的代理方法来决定何时应限制旋转。
最后,当您完成一个 ABMediaView 并希望将其清除以便显示新内容时,有一些方法可以轻松处理此任务。
/// Removes image, video, audio and GIF data from the mediaView
- (void) resetMediaInView;
/// Resets all variables from mediaView, removing image, video, audio and GIF data
- (void) resetVariables;
ABMediaView 还提供了切换功能,允许将媒体视图滑动到右下角,并允许用户在媒体视图最小化时与底层界面交互。如果媒体视图已播放,则视频和音频将继续播放,用户可以向右滑动来关闭最小视图。
[mediaView setIsMinimizable: YES];
对于图像和 GIF 等内容,可以设置 'isDismissable' 变量,允许用户向下滑动来关闭视图而不是最小化它。当设置时,此变量将取代 'isMinimizable',这对于不需要持续播放的内容非常有用。
[mediaView setIsDismissable: YES];
ABMediaView 还提供了一些视频和音频的回放选项。一个选项 'allowLooping' 控制媒体在达到末尾后是否应该重新播放。另一个选项 'autoPlayAfterPresentation' 控制媒体在显示后是否应该自动播放。默认情况下,ABMediaView 设置为在显示后自动播放媒体。
// Toggle looping functionality
[mediaView setAllowLooping:YES];
// Toggle functionality to automatically play videos after presenting
[mediaView setAutoPlayAfterPresentation:YES];
如果您在查找在视频播放完成后全屏媒体视图自动关闭的功能,可以在媒体视图上将 'shouldDismissAfterFinish' 的值设置为 true。对于全屏媒体视图,此功能将优先于 'allowLooping'。
[mediaView setShouldDismissAfterFinish: YES];
ABMediaView 有几个选项,用于启用和编辑显示视频和音频时显示的进度条。
// Enable progress track to show at the bottom of the view
[mediaView setShowTrack:YES];
// Toggles the funtionality which would show remaining time instead of total time on the right label on the track
[mediaView setShowRemainingTime:YES];
/// Change the font for the labels on the track
[mediaView setTrackFont:[UIFont fontWithName:@"STHeitiTC-Medium" size:12.0f]];
ABMediaView 拥有主题颜色,可以更改进度条以及播放按钮的颜色。
// Changing the theme color changes the color of the play indicator as well as the progress track
[mediaView setThemeColor:[UIColor redColor]];
ABMediaView 将根据在视图中设置的 contentMode 显示图像、视频和 GIF。然而,还可以设置 contentMode 为 aspectFill,同时将视频 Gravity 设置为 aspectFit。
// Setting the contentMode to aspectFit will set the videoGravity to aspectFit as well
mediaView.contentMode = UIViewContentModeScaleAspectFit;
// If you desire to have the image to fill the view, however you would like the videoGravity to be aspectFit, then you can implement this functionality
mediaView.contentMode = UIViewContentModeScaleAspectFill;
[mediaView changeVideoToAspectFit: YES];
如果 ABMediaView 不是一个从队列中展示的全屏视图,则可以启用功能,使 ABMediaView 在选择时全屏打开。
[mediaView setShouldDisplayFullscreen:YES];
如果您希望为 ABMediaView 使用自定义播放按钮或失败指示器,请在媒体视图中设置 'customPlayButton' 和 'customFailedButton' 变量。(适用于视频和音频)
// Set a custom image for the play button visible on ABMediaView's with video or audio
mediaView.customPlayButton = [UIImage imageNamed:@"CustomPlayButtonImage"];
// Set a custom image for when the mediaView fails to play media
mediaView.custonFailedButton = [UIImage imageNamed:@"CustomFailedButtonImage"];
有一种功能可以切换隐藏关闭按钮,这样它就不会在全屏弹出媒体视图中显示。如果没有启用 isMinimizable,则不允许此功能,否则将无法关闭弹出窗口。此外,当视图在横屏方向持有时,关闭按钮仍然可见,因为在这种模式下,最小化是禁用的。
[mediaView setCloseButtonHidden:YES];
类似地,对于可播放(视频/音频)的内容,还有隐藏播放按钮的功能。此功能适用于将 ABMediaView 用作背景视频播放器。
[mediaView setPlayButtonHidden:YES];
如果您的屏幕上有一个您不想隐藏的UIStatusBar,或者需要为其他视图保留屏幕顶部的空间时,ABMediaView具有偏移屏幕顶部子视图的能力,以避免隐藏这些视图。通过设置ABMediaView的'topOffset'属性,可以向下移动'关闭按钮'和其他顶部锚定视图。同样,设置此属性的主要用途可能是将'topOffset'设置为20px,以避免覆盖UIStatusBar。
[mediaView setTopBuffer:20.0f];
默认情况下,最小化的ABMediaView与屏幕底部之间有12px的缓冲区。可以通过调整ABMediaView的'bottomBuffer'值来增加更多空间。这对于使媒体视图显示在UITabBars和UIToolbars等视图上方非常有用,以避免覆盖这些需要在屏幕底部预留空间的视图。
[mediaView setBottomBuffer:0.0f];
为了使这些缓冲区更容易使用,我已提供iOS标准预设,以便轻松访问某些缓冲值。
// ABBufferStatusBar = 20px
// ABBufferNavigationBar = 44px
// ABBufferStatusAndNavigationBar = 64px
// ABBufferTabBar = 49px
[mediaView setTopBuffer:ABBufferStatusBar];
[mediaView setBottomBuffer:ABBufferTabBar];
ABMediaView具有设置全屏弹出起始框架的功能。此功能与'shouldDisplayFullscreen'相结合非常有用,因为它将允许弹出从启用'shouldDisplayFullscreen'的媒体视图的框架中发起。
/// Rect that specifies where the mediaView's frame will originate from when presenting, and needs to be converted into its position in the mainWindow
mediaView.originRect = self.mediaView.frame;
/// Rect that specifies where the mediaView's frame will originate from when presenting, and is already converted into its position in the mainWindow
mediaView.originRectConverted = self.mediaView.frame;
然而,如果正在使用动态UI,并不能确定ABMediaView的originRect,可以将属性'presentFromOriginRect'设置为true。使用此功能激活后,全屏ABMediaView将弹出于显示它的ABMediaView的框架。如果启用'presentFromOriginRect',则无需设置'originRect'或'originRectConverted',因为这个属性优先于两者。
self.mediaView.presentFromOriginRect = YES;
可以指定ABMediaView是否将在可重用视图中显示,这将允许对不打算重用的ABMediaView实现更好的UI转换性能。
mediaView.imageViewNotReused = YES;
当ABMediaView的'isMinimizable'值被启用时,可以自定义最小化视图的大小比例。此比例的默认值是预设ABMediaViewRatioPresetLandscape,它是一片16:9的宽屏比例。还有预设选项用于正方形(ABMediaViewRatioPresetSquare)和9:16的竖屏(ABMediaViewRatioPresetPortrait)。
// Aspect ratio of the minimized view
mediaView.minimizedAspectRatio = ABMediaViewRatioPresetLandscape;
mediaView.minimizedAspectRatio = ABMediaViewRatioPresetSquare;
mediaView.minimizedAspectRatio = ABMediaViewRatioPresetPortrait;
mediaView.minimizedAspectRatio = (6.0f/5.0f); // Height/Width
与上述选项相伴随,还可以指定最小化视图将在屏幕宽度占据的比率。默认情况下,最小化视图占据屏幕宽度的一半(0.5比例)。此功能在调整最小化视图大小以适应ABMediaView的'minimizedAspectRatio'大于宽屏的情况时非常有用。
// Ratio of the screen's width that the minimized view will stretch across
mediaView.minimizedWidthRatio = 0.5f;
如果您的项目没有缓存系统,并且您正在寻找自动化的缓存系统,ABMediaView现在提供了这个功能!在ABMediaView中,图像和GIF使用NSCache保存在内存中,而视频和音频文件则保存在磁盘上。有几种选项可以用来管理缓存,但让我们从如何启用自动缓存开始。它可以通过在ABMediaView共享管理器上设置'shouldCacheMedia'变量来实现。
[[ABMediaView sharedManager] setShouldCacheMedia:YES];
如果您希望预载视频和音频,可以在媒体视图上设置videoURL或audioURL时,将ABMediaView设置为始终下载视频和音频,通过在ABMediaView共享管理器中指定'shouldPreloadVideoAndAudio'。但是,如果您希望针对单个实例预载视频或音频,可以使用'preloadVideo'和'preloadAudio'来实现。如果您不打算预载视频或音频,并且只将'shouldCacheMedia'设置为true,那么视频和音频将通过流来传输。目前,视频在从流中加载到缓冲区完全时进行缓存。音频目前是一个正在进行中的工作。
// Ensure that all video and audio is preloaded before playing, instead of just streaming (works best if your app plays videos/audio that is short in length)
[[ABMediaView sharedManager] setShouldPreloadVideoAndAudio:YES];
// Preload the video for this specific mediaView
[mediaView preloadVideo];
// Preload the audio for this specific mediaView
[mediaView preloadAudio];
如果您想清理图片和GIF的内存缓存,只需在ABMediaView的sharedManager上设置'shouldCacheMedia'为false。然而,要清理Documents目录和tmp目录上的缓存,ABMediaView提供了一个易于使用的方法来清除这些缓存。
// Clear all of the documents directory of cached items in the ABMedia folder
[ABMediaView clearABMediaDirectory:AllDirectoryItems];
// Clear the video directory of cached items in the ABMedia folder
[ABMediaView clearABMediaDirectory:VideoDirectoryItems];
// Clear the audio directory of cached items in the ABMedia folder
[ABMediaView clearABMediaDirectory:AudioDirectoryItems];
// Clear all of the temp directory of cached items
[ABMediaView clearABMediaDirectory:TempDirectoryItems];
有一个委托,其中包含可选的方法,用于确定ABMediaView何时在AVPlayer中播放或暂停视频,以及视图最小化的程度。
/// A listener to know what percentage that the view has minimized, at a value from 0 to 1
- (void) mediaView: (ABMediaView *) mediaView didChangeOffset: (float) offsetPercentage;
/// When the mediaView begins playing a video
- (void) mediaViewDidPlayVideo: (ABMediaView *) mediaView;
/// When the mediaView pauses a video
- (void) mediaViewDidPauseVideo: (ABMediaView *) mediaView;
此外,还有委托方法,可以帮助确定ABMediaView即将显示、已经显示、即将消失以及已经消失。
/// Called when the mediaView has begun the presentation process
- (void) mediaViewWillPresent: (ABMediaView *) mediaView;
/// Called when the mediaView has been presented
- (void) mediaViewDidPresent: (ABMediaView *) mediaView;
/// Called when the mediaView has begun the dismissal process
- (void) mediaViewWillDismiss: (ABMediaView *) mediaView;
/// Called when the mediaView has completed the dismissal process. Useful if not looking to utilize the dismissal completion block
- (void) mediaViewDidDismiss: (ABMediaView *) mediaView;
如果您想确定媒体视图是否已经播放完毕其视频,可以使用'mediaViewDidFinishVideo:withLoop:'方法。这还指定了媒体视图是否在播放完毕后设置为循环。
/// When the mediaView finishes playing a video, and whether it will loop
- (void)mediaViewDidFinishVideo:(ABMediaView *)mediaView withLoop:(BOOL)willLoop;
以下委托方法在确定ABMediaView是否开始、进行中或已完成最小化时非常有用。一个常用的用例是根据ABMediaView是否在其后面可见来调整UIStatusBarStyle。
/// Called when the mediaView is in the process of minimizing, and is about to make a change in frame
- (void) mediaViewWillChangeMinimization:(ABMediaView *)mediaView;
/// Called when the mediaView is in the process of minimizing, and has made a change in frame
- (void) mediaViewDidChangeMinimization:(ABMediaView *)mediaView;
/// Called before the mediaView ends minimizing, and informs whether the minimized view will snap to minimized or fullscreen mode
- (void) mediaViewWillEndMinimizing:(ABMediaView *)mediaView atMinimizedState:(BOOL)isMinimized;
/// Called when the mediaView ends minimizing, and informs whether the minimized view has snapped to minimized or fullscreen mode
- (void) mediaViewDidEndMinimizing:(ABMediaView *)mediaView atMinimizedState:(BOOL)isMinimized;
另一方面,如果一个人在他们的ABMediaView上设置了'isDismissable'值,将提供委托方法以监听媒体视图何时将开始和结束消失过程。
/// Called when the mediaView is in the process of minimizing, and is about to make a change in frame
- (void) mediaViewWillChangeDismissing:(ABMediaView *)mediaView;
/// Called when the mediaView is in the process of minimizing, and has made a change in frame
- (void) mediaViewDidChangeDismissing:(ABMediaView *)mediaView;
/// Called before the mediaView ends minimizing, and informs whether the minimized view will snap to minimized or fullscreen mode
- (void) mediaViewWillEndDismissing:(ABMediaView *)mediaView withDismissal:(BOOL)didDismiss;
/// Called when the mediaView ends minimizing, and informs whether the minimized view has snapped to minimized or fullscreen mode
- (void) mediaViewDidEndDismissing:(ABMediaView *)mediaView withDismissal:(BOOL)didDismiss;
如果您想检测ABMediaView中的图片是否已设置或更改,可以监听以下委托方法。
/// Called when the mediaView 'image' property has been set or changed
- (void) mediaView:(ABMediaView *)mediaView didSetImage:(UIImage *) image;
如果您想缓存通过ABMediaView下载的图片、视频或GIF,已经制作了委托来处理获取这些对象。
/// Called when the mediaView has completed downloading the image from the web
- (void) mediaView:(ABMediaView *)mediaView didDownloadImage:(UIImage *) image;
/// Called when the mediaView has completed downloading the video from the web
- (void) mediaView:(ABMediaView *)mediaView didDownloadVideo: (NSString *)video;
/// Called when the mediaView has completed downloading the GIF from the web
- (void) mediaView:(ABMediaView *)mediaView didDownloadGif:(UIImage *)gif;
Andrew Boryk,[email protected]
在Twitter上联系我: @TrepIsLife
ABMediaView可在MIT许可下使用。有关更多信息,请参阅LICENSE文件。