0.背景描述
我遇到的问题并非是如标题所述,而是反过来。
如官方文档所言,在iPhone上UIWebView的allowsInlineMediaPlayback参数默认为false,运行效果是网页视频播放时会显示全屏的播放器。如果不需要全屏播放,那么请将allowsInlineMediaPlayback设为true。
我需要的正是如此,网页视频需要在页面直接播放的,而实际效果正是如此。但是奇怪的是,在看代码时我发现代码并没有将allowsInlineMediaPlayback设为YES!!!
1.问题查找
我首先创建了一个demo工程验证这个问题,主体代码如下:
UIWebView *uiWebView = [[UIWebView alloc] initWithFrame:self.view.bounds];
[self.view addSubview:uiWebView];
NSString *urlString = @"带有视频的网页地址";
[uiWebView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:urlString]]];
实际的运行效果确实如官方文档所言,默认是全屏播放。
而同样的代码,我放到我的项目工程当中,默认却是在网页内播放……
一开始怀疑有其他工程设置对实际效果有影响,比如页面横屏处理,项目设置参数等等。但查到一遍后发现不是这些点的影响。
而且在排查过程中出现好几次运行效果的变化,一会儿是符合官方文档描述的,一会儿又不符合。
后来,我将怀疑点放到了allowsInlineMediaPlayback这个特殊参数上面。
2.问题原因
因为我全局搜索了一下项目工程,所有代码中只有其他页面的代码中将allowsInlineMediaPlayback设置为了YES,我所测试的页面是没有操作这个属性的。所以,我怀疑allowsInlineMediaPlayback这个参数在UIWebView中是全局存在的。
然后进行代码验证:
UIWebView *uiWebView = [[UIWebView alloc] initWithFrame:self.view.bounds];
[self.view addSubview:uiWebView];
NSString *urlString = @"带有视频的网页地址";
UIWebView *tempUIWebView = [UIWebView new];
tempUIWebView.allowsInlineMediaPlayback = YES;
[uiWebView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:urlString]]];
效果确实如此,对其他webView对象的操作,也会影响当前webView的视频播放效果。
反向验证:
UIWebView *uiWebView = [[UIWebView alloc] initWithFrame:self.view.bounds];
[self.view addSubview:uiWebView];
uiWebView.allowsInlineMediaPlayback = YES;
NSString *urlString = @"带有视频的网页地址";
UIWebView *tempUIWebView = [UIWebView new];
tempUIWebView.allowsInlineMediaPlayback = NO;
[uiWebView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:urlString]]];
效果也是一样的。
索引,我遇到的这个问题,以及本文标题中所说的问题,其原因可能都是因为allowsInlineMediaPlayback参数的全局性质导致的,所以实际开发时才会出现代码和运行效果不一致的问题。
而WKWebView中没有allowsInlineMediaPlayback属性,而是放到了初始化方法中需要传入config对象中。或许是因为这个变动,WKWebView的没有上述问题的。
3.解决办法
针对该问题的解决要点,其实就是使用UIWebView的controller,都需要在初始化的时候对allowsInlineMediaPlayback进行显式的初始化,屏蔽其他页面的影响。
具体的解决办法可以参照下面两种:
- 在Controller中创建UIWebView时对allowsInlineMediaPlayback进行显式赋值,或者创建UIWebView的统一子类。
- 使用category替换UIWebView的
initWithFrame:
和initWithCoder:
初始化方法,强制初始化allowsInlineMediaPlayback属性。