Ios 可以使用NSURLProtocol的子类,使用MPMovieController或AVFoundation播放视频吗?

Ios 可以使用NSURLProtocol的子类,使用MPMovieController或AVFoundation播放视频吗?,ios,mpmovieplayercontroller,avfoundation,avplayer,nsurlprotocol,Ios,Mpmovieplayercontroller,Avfoundation,Avplayer,Nsurlprotocol,我目前正在尝试播放一个URL的视频,该URL在自定义NSURLProtocol子类中定义了自定义方案。最初,我使用MPMoviePlayerController试图实现这一点,但在遇到问题并检查堆栈溢出后,我发现MPMoviePlayerController没有像预期的那样处理NSURLProtocol子类 因此,我决定研究一下AVFoundation框架,然而,这似乎也不起作用。我只是想知道这是可能的,还是我想穿过墙壁 使用AVFoundation,我使用的方法如下所示。可能值得一提的是,当

我目前正在尝试播放一个URL的视频,该URL在自定义NSURLProtocol子类中定义了自定义方案。最初,我使用MPMoviePlayerController试图实现这一点,但在遇到问题并检查堆栈溢出后,我发现MPMoviePlayerController没有像预期的那样处理NSURLProtocol子类

因此,我决定研究一下AVFoundation框架,然而,这似乎也不起作用。我只是想知道这是可能的,还是我想穿过墙壁

使用AVFoundation,我使用的方法如下所示。可能值得一提的是,当使用internet上托管的视频的标准URL时,这种方法是有效的,但不适用于自定义NSURL协议

// this doesn't work
//AVPlayer *player = [[AVPlayer alloc] initWithURL:[NSURL urlWithString:@"custom URL scheme"]];
// this works
AVPlayer *player = [[AVPlayer alloc] initWithURL:[NSURL urlWithString:@"some url to video on remote server"]];

AVPlayerLayer *layer = [AVAVPlayerLayer playerLayerWithPlayer:player];
// configure the layer
[self.view.layer addSublayer:layer];

[player play];

为了从定义的NSURLProtocol子类播放,是否需要执行一些不同的操作?

最近,我设法让NSURLProtocol与MPMoviePlayerController一起工作。这主要是有用的,因为MPMoviePlayerController只接受NSURL,所以它不允许我们传递cookie或标头(用于身份验证)。NSURL协议的使用允许这样做。我想我应该在这里为社区分享一些代码

基本上,通过使用NSURL协议,我们可以拦截MPMoviePlayerController和流式请求之间的通信,在传输过程中注入cookie,或者可能脱机保存流,或者用cat视频等替换流式请求。。。为此,您需要创建一个新类My extending NSURLProtocol:

MyURLProtocol.h:

#import <Foundation/Foundation.h>

@interface MyURLProtocol : NSURLProtocol
+ (void) register;
+ (void) injectURL:(NSString*) urlString cookie:(NSString*)cookie;
@end
#import "MyURLProtocol.h"

@interface MyURLProtocol() <NSURLConnectionDelegate> {
    NSMutableURLRequest* myRequest;
    NSURLConnection * connection;
}
@end

static NSString* injectedURL = nil;
static NSString* myCookie = nil;

@implementation MyURLProtocol
// register the class to intercept all HTTP calls
+ (void) register
{
    [NSURLProtocol registerClass:[self class]];
}

// public static function to call when injecting a cookie
+ (void) injectURL:(NSString*) urlString cookie:(NSString*)cookie
{
    injectedURL = urlString;
    myCookie = cookie;
}

// decide whether or not the call should be intercepted
+ (BOOL)canInitWithRequest:(NSURLRequest *)request {
    if([[[request allHTTPHeaderFields] objectForKey:@"BANANA"] isEqualToString:@"DELICIOUS"])
    {
        return NO;
    }
    return [[[request URL] absoluteString] isEqualToString:injectedURL];
}

// required (don't know what this means)
+ (NSURLRequest *)canonicalRequestForRequest:(NSURLRequest *)request {
    return request;
}

// intercept the request and handle it yourself
- (id)initWithRequest:(NSURLRequest *)request cachedResponse:(NSCachedURLResponse *)cachedResponse client:(id<NSURLProtocolClient>)client {

    if (self = [super initWithRequest:request cachedResponse:cachedResponse client:client]) {
        myRequest = request.mutableCopy;
        [myRequest setValue:@"DELICIOUS" forHTTPHeaderField:@"BANANA"]; // add your own signature to the request
    }
    return self;
}

// load the request
- (void)startLoading {
    //  inject your cookie
    [myRequest setValue:myCookie forHTTPHeaderField:@"Cookie"];
    connection = [[NSURLConnection alloc] initWithRequest:myRequest delegate:self];
}

// overload didReceive data
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
    [[self client] URLProtocol:self didLoadData:data];
}

// overload didReceiveResponse
- (void)connection:(NSURLConnection*)connection didReceiveResponse:(NSURLResponse *)response {
    [[self client] URLProtocol:self didReceiveResponse:response cacheStoragePolicy:[myRequest cachePolicy]];
}

// overload didFinishLoading
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
    [[self client] URLProtocolDidFinishLoading:self];
}

// overload didFail
- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error
{
    [[self client] URLProtocol:self didFailWithError:error];
}

// handle load cancelation
- (void)stopLoading {
    [connection cancel];
}

@end
[MyURLProtocol register];
[MyURLProtocol injectURL:@"http://server/your-video-url.mp4" cookie:@"mycookie=123"];
MPMoviePlayerController* moviePlayer = [[MPMoviePlayerController alloc]initWithContentURL:@"http://server/your-video-url.mp4"];
[moviePlayer play];

嗨,塔兹,你成功了吗?嘿,杰拉德,没有,我从来没成功过。AVFoundation似乎也不支持NSURLProtocol子类。你能播放视频吗?有演示吗?我也有。它可以在模拟器上工作,但不能在设备上工作。我用iOS 8.1和xcode 6.1进行了测试。你能在设备上使用它吗?我能在mp3/m4a流媒体上使用它,但使用iOS的mp4视频捕获无法加载。我不久前做过这件事,是的,它能在设备上正常工作。虽然我没有它的演示,但我已经有一段时间没有接触过这个项目了。@jacklehamster它有可能在iOS 7上工作(不久前),但现在不再工作了吗?从一个开放的雷达上我看到它看起来可能是这样的。。。