このトピックでは、ApsaraVideo Player SDK for iOS の高度な機能の使用方法について説明します。すべての機能の詳細については、「API リファレンス」をご参照ください。
専門能力の確認
アプリケーションの起動時、またはプレーヤーの API 操作を呼び出す前にリスナーを設定します。
void premiumVeryfyCallback(AVPPremiumBizType biztype, bool isValid, NSString* errorMsg) {
NSLog(@"onPremiumLicenseVerifyCallback: %d, isValid: %d, errorMsg: %@", biztype, isValid, errorMsg);
}
[AliPrivateService setOnPremiumLicenseVerifyCallback:premiumVeryfyCallback];ここで、AVPPremiumBizType は高度な機能の列挙です。関連機能を使用すると、プレーヤーはライセンスを検証し、このコールバックを通じて結果を返します。isValid が false の場合、errorMsg には失敗の理由が含まれます。
再生
リスト再生
ApsaraVideo Player SDK for iOS は、フル機能のリスト再生機能を提供します。SDK はプリロードなどのメカニズムを使用して、ショートビデオの初回フレーム表示時間 (TTTF) を最小限に抑えます。
リスト再生の体験を向上させるには、当社の短編ドラマソリューションをご利用ください。詳細については、「短編ドラマのクライアントサイド開発」をご参照ください。
アルファチャンネル付きビデオの再生
概要
ApsaraVideo Player SDK は、アルファチャンネルのレンダリングをサポートしており、アニメーションギフトなどの動的な効果を作成できます。ライブストリーミング中に、メインコンテンツを隠すことなくアニメーションギフトを再生でき、ユーザーエクスペリエンスを向上させます。
制限事項
アルファチャンネルレンダリングは、オールインワン SDK V6.8.0 以降、または ApsaraVideo Player SDK V6.9.0 以降でサポートされています。
メリット
アニメーション効果に透明度のある MP4 ビデオを使用すると、APNG や IXD などのフォーマットと比較して、品質が向上し、ファイルサイズが小さくなり、互換性が高まります。
より良いアニメーション品質:MP4 ビデオは、他のフォーマットよりも元のアニメーションの詳細と色をより正確に保持します。
より小さいファイルサイズ:MP4 ビデオファイルは、APNG や IXD などの他のフォーマットのファイルよりも小さいため、読み込みが速くなり、ネットワーク帯域幅の消費が削減されます。
より高い互換性:MP4 フォーマットは、デバイスやブラウザで広くサポートされています。
より高い開発効率:ギフト効果に MP4 ビデオを使用することは簡単なアプローチであり、開発者は複雑な解析やレンダリングロジックを調査・実装する必要がなく、他の機能に集中できます。
Metal レンダリング
ApsaraVideo Player SDK for iOS は、Metal フレームワークを使用したビデオレンダリングをサポートしています。
現在、背景色、スケーリングモード、ピクチャーインピクチャー (PiP) のみがサポートされています。
構成項目
/**
@brief ビデオレンダリングタイプ。0 はデフォルトレンダリング、1 は混合レンダリングを意味します。デフォルトは 0 です。
*/
/****
@brief ビデオレンダリングタイプ。0 はデフォルトレンダリング、1 は混合レンダリングを意味します。
*/
@property(nonatomic, assign) int videoRenderType;例
AVPConfig *config = [self.player getConfig];
// Metal レンダリングを有効にします。
config.videoRenderType = 1;
[self.player setConfig:config];
[self.player prepare];外部字幕
詳細なコード例については、API-Example プロジェクトの ExternalSubtitle モジュールをご参照ください。
ApsaraVideo Player SDK for iOS は、SRT、SSA、ASS、VTT 形式の外部字幕の追加と切り替えをサポートしています。
例:
字幕を表示するためのビューの作成
異なるフォーマットに対して異なるビューを作成します。
// カスタム subTitleLabel を初期化します。 UILabel *subTitleLabel = [[UILabel alloc] initWithFrame:frame]; // 字幕ラベルをカスタム superView に追加します。superView はカスタムインターフェイスに存在する親ビューです。 [superView addSubview:subTitleLabel];字幕関連リスナーの設定
// 外部字幕が追加されました。 - (void)onSubtitleExtAdded:(AliPlayer*)player trackIndex:(int)trackIndex URL:(NSString *)URL {} // 字幕ヘッダー情報コールバック。 - (void)onSubtitleHeader:(AliPlayer *)player trackIndex:(int)trackIndex Header:(NSString *)header{} // 字幕表示コールバック。 - (void)onSubtitleShow:(AliPlayer*)player trackIndex:(int)trackIndex subtitleID:(long)subtitleID subtitle:(NSString *)subtitle { subTitleLabel.text =subtitle; subTitleLabel.tag =subtitleID; } // 字幕非表示コールバック。 - (void)onSubtitleHide:(AliPlayer*)player trackIndex:(int)trackIndex subtitleID:(long)subtitleID{ [subTitleLabel removeFromSuperview]; }字幕トラックの追加
[self.player addExtSubtitle:URL];字幕トラックの切り替え
[self.player selectExtSubtitle:trackIndexenable:YES];
カスタムレンダリングされた外部字幕
AliVttSubtitleView と AliVttRenderImpl を使用して、WebVTT 外部字幕を完全にサポートし、フォントサイズ、色、特定のフォントを柔軟にカスタマイズできます。
ユースケース:
フォント、色、サイズなどの WebVTT 字幕スタイルをカスタマイズします。
ApsaraVideo Player SDK V7.11.0 を統合し、AliVttSubtitleView を使用します。
多言語字幕 (アラビア語、中国語、日本語、韓国語など) をサポートし、適切なフォントを自動的に一致させます。
前提条件:
フォントファイル (.ttf) が Xcode プロジェクトに追加されていること。
字幕リスナーが追加され、WebVTT コンテンツを取得できること。
loadFontFromBundle メソッドがフォントの読み込みに成功していること。
字幕スタイリングをカスタマイズする手順
カスタムレンダリング実装クラス (AliVttRenderImpl) の作成
// CustomFontVttRenderImpl.h @interface CustomFontVttRenderImpl : AliVttRenderImpl @end // CustomFontVttRenderImpl.m @implementation CustomFontVttRenderImpl // 任意:フォント生成ロジックをオーバーライド - (UIFont *)customizeFont:(UIFont *)originalFont contentAttribute:(VttContentAttribute *)contentAttribute contentText:(NSString *)text { // 例:コンテンツに基づいてフォントを自動選択 if ([self containsArabicCharacters:text]) { return [UIFont fontWithName:@"NotoSansArabic-Regular" size:originalFont.pointSize]; } if ([self containsCJKCharacters:text]) { return [UIFont fontWithName:@"NotoSansCJKsc-Regular" size:originalFont.pointSize]; } return originalFont; } // 任意:色を強制的に変更 - (void)applyColorStyle:(NSMutableDictionary *)attrs contentAttribute:(VttContentAttribute *)contentAttribute { // 赤色を強制 attrs[NSForegroundColorAttributeName] = [UIColor redColor]; } // 任意:フォントサイズをスケーリング - (void)applyFontStyle:(NSMutableDictionary *)attrs contentAttribute:(VttContentAttribute *)contentAttribute context:(RenderContext *)context { CGFloat originalSize = contentAttribute.fontSizePx / context.contentsScale; CGFloat newSize = originalSize * 2.0; // サイズを2倍にする UIFont *font = [self generateFontWithName:contentAttribute.fontName fontSize:newSize isBold:contentAttribute.mBold isItalic:contentAttribute.mItalic]; attrs[NSFontAttributeName] = font; } // ヘルパーメソッド:アラビア文字を検出 - (BOOL)containsArabicCharacters:(NSString *)text { for (NSUInteger i = 0; i < text.length; i++) { unichar c = [text characterAtIndex:i]; if ((c >= 0x0600 && c <= 0x06FF) || (c >= 0x0750 && c <= 0x077F)) { return YES; } } return NO; } // ヘルパーメソッド:CJK 文字を検出 - (BOOL)containsCJKCharacters:(NSString *)text { for (NSUInteger i = 0; i < text.length; i++) { unichar c = [text characterAtIndex:i]; if ((c >= 0x4E00 && c <= 0x9FFF) || // 中国語 (c >= 0x3040 && c <= 0x309F) || // 日本語ひらがな (c >= 0xAC00 && c <= 0xD7AF)) { // 韓国語 return YES; } } return NO; } @end(任意) カスタムフォントの動的読み込み
- (void)loadCustomFontFromBundle:(NSString *)fontName { NSString *path = [[NSBundle mainBundle] pathForResource:fontName ofType:@"ttf"]; if (path) { NSData *fontData = [NSData dataWithContentsOfFile:path]; CGDataProviderRef provider = CGDataProviderCreateWithCFData((__bridge CFDataRef)fontData); CGFontRef fontRef = CGFontCreateWithDataProvider(provider); if (CTFontManagerRegisterGraphicsFont(fontRef, NULL)) { NSLog(@"フォントの登録に成功しました: %@", fontName); } else { NSLog(@"フォントの登録に失敗しました: %@", fontName); } CGFontRelease(fontRef); CGDataProviderRelease(provider); } }字幕ビューの初期化とカスタムレンダラーのバインド
// 字幕ビューの作成 AliVttSubtitleView *subtitleView = [[AliVttSubtitleView alloc] init]; // カスタムレンダーファクトリの設定 [subtitleView setRenderImplFactory:^AliVttRenderImpl*() { CustomFontVttRenderImpl *impl = [[CustomFontVttRenderImpl alloc] init]; // 任意:フォントのプリロード [impl loadCustomFontFromBundle:@"LongCang-Regular"]; return impl; }]; // プレーヤーとの関連付け [player setExternalSubtitleView:subtitleView];プレーヤー字幕コールバックの処理
AVPDelegate に以下のメソッドを実装します。
// 字幕ヘッダー (スタイルとリージョン定義を含む) - (void)onSubtitleHeader:(AliPlayer *)player trackIndex:(int)trackIndex Header:(NSString *)header { [self.subtitleView setVttHeader:player trackIndex:trackIndex Header:header]; } // 字幕の表示 - (void)onSubtitleShow:(AliPlayer *)player trackIndex:(int)trackIndex subtitleID:(long)subtitleID subtitle:(NSString *)subtitle { [self.subtitleView show:player trackIndex:trackIndex subtitleID:subtitleID subtitle:subtitle]; } // 字幕の非表示 - (void)onSubtitleHide:(AliPlayer *)player trackIndex:(int)trackIndex subtitleID:(long)subtitleID { [self.subtitleView hide:player trackIndex:trackIndex subtitleID:subtitleID]; } // 字幕が正常に追加された (トラックを有効にするために使用) - (void)onSubtitleExtAdded:(AliPlayer *)player trackIndex:(int)trackIndex URL:(NSString *)URL { [player selectExtSubtitle:trackIndex enable:YES]; }
音声のみの再生
動画の再生を無効化し、音声トラックのみを再生する。この設定は、prepare を呼び出す前に構成してください。
AVPConfig *config = [self.player getConfig];
config.disableVideo = YES;
[self.player setConfig:config];ソフトウェアデコードとハードウェアデコードの切り替え
iOS Player SDK は、H.264 および H.265 のハードウェアデコード機能を提供し、enableHardwareDecoder トグルを含みます。デフォルトでは、ハードウェアデコードが有効になっています。ハードウェアデコードの初期化に失敗した場合、ビデオ再生を確実にするためにソフトウェアデコードが自動的に使用されます。以下の例を示します。
// ハードウェアデコードを有効にします。デフォルトで有効です。
self.player.enableHardwareDecoder = YES;ハードウェアデコードからソフトウェアデコードへの自動切り替えが発生した場合、onPlayerEvent コールバックがトリガーされます。以下の例を示します。
-(void)onPlayerEvent:(AliPlayer*)player eventWithString:(AVPEventWithString)eventWithString description:(NSString *)description {
if (eventWithString == EVENT_SWITCH_TO_SOFTWARE_DECODER) {
// ソフトウェアデコードに切り替わりました。
}
}H.265 アダプティブ再生
現在お使いのデバイスモデルがクラウドベースの H.265 ブラックリストに含まれている場合、または H.265 ハードウェアデコードに失敗した場合に、アダプティブフォールバックがトリガーされます。H.264 バックアップストリームが設定されている場合は、それが再生されます。それ以外の場合、プレーヤーは H.265 ソフトウェアデコードにフォールバックします。
この機能は、アダプティブ再生を有効にした後にのみ利用可能です。アダプティブ再生は付加価値サービスです。ライセンスを申請するには、Yida フォームを送信する必要があります。
クラウドネイティブのアダプティブデコードサービスには、ハードウェアデコード互換性データの動的配信と、H.265 から H.264 ストリームへのアダプティブフォールバックが含まれます。
この付加価値サービスが有効になっていなくても、ハードウェアデコードの失敗時に SDK は自動的にソフトウェアデコードに切り替わります。
バックアップストリームの設定例:
// アプリケーション層は、元の URL からバックアップ URL へのマップを維持します。
NSString* getBackupUrlCallback(AVPBizScene scene, AVPCodecType codecType, NSString* oriurl){
NSMutableDictionary *globalMap = [AliPlayerViewController getGlobalBackupUrlMap];
NSString *backupUrl = globalMap[oriurl];
return backupUrl;
}
[AliPlayerGlobalSettings setAdaptiveDecoderGetBackupURLCallback:getBackupUrlCallback];ネットワーク状況に応じた画質切り替え
ApsaraVideo VOD のビデオパッケージングテンプレートを使用して、マルチビットレート HLS ストリームを生成します。手順については、「ビデオ・オン・デマンドのアダプティブビットレートストリーミング設定」をご参照ください。
ApsaraVideo VOD トランスコーディングによって生成されたアダプティブストリームでは、Vid ベースの再生を使用してアダプティブビデオストリームを再生する場合、デフォルトの再生画質リストを
AUTOとして指定する必要があります。そうしないと、システムはデフォルトのロジックに従って低画質のビデオストリームを選択します。デフォルトの再生画質順序については、「ビデオトランスコーディングによって複数の画質が生成された場合、プレーヤー SDK はデフォルトでどの画質を再生しますか?」をご参照ください。以下のサンプルコードは、VidAuth ベースの再生でデフォルトの再生画質を指定する方法の例です。AVPVidAuthSource *authSource = [[AVPVidAuthSource alloc] init]; authSource.definitions = @"AUTO";
ApsaraVideo Player SDK for iOS は、HTTP Live Streaming (HLS) ビデオストリームと Dynamic Adaptive Streaming over HTTP (DASH) ビデオストリームのアダプティブビットレートストリーミングをサポートしています。prepare が成功した後、getMediaInfo を通じて各ビットレートストリームの情報、すなわち TrackInfo を取得できます。以下の例は、その方法を示しています。
AVPMediaInfo *info = [self.player getMediaInfo];
NSArray<AVPTrackInfo*>* tracks = info.tracks;再生中に、プレーヤーの selectTrack メソッドを呼び出してビットレートストリームを切り替えることができます。値を SELECT_AVPTRACK_TYPE_VIDEO_AUTO に設定すると、アダプティブビットレートストリーミングが有効になります。以下のコードは例です。
// 特定のビットレートに切り替えます。
[self.player selectTrack:track.trackIndex];
// アダプティブビットレート切り替えを有効にします。
[self.player selectTrack:SELECT_AVPTRACK_TYPE_VIDEO_AUTO];切り替えは、onTrackChanged リスナーが呼び出された後にコールバックをトリガーします。以下のサンプルコードは、これを実装する方法を示しています。
- (void)onTrackChanged:(AliPlayer*)player info:(AVPTrackInfo*)info {
if (info.trackType == AVPTRACK_TYPE_VIDEO) {
// 画質が変更されました。
}
// など
}任意:selectTrack メソッドを呼び出してアダプティブビットレートストリーミングに切り替える前に、アダプティブビットレート (ABR) 切り替えの上限画質を設定して、プレーヤーが予期しないビットレートに自動的に切り替わるのを防ぐことができます。例:(設定を有効にするには、プレーヤーが prepare メソッドを呼び出す前、またはリストプレーヤーが moveTo メソッドを呼び出す前にコードを呼び出すことを推奨します。)
AVPConfig *config = [self.player getConfig];
config.maxAllowedAbrVideoPixelNumber = 921600;// ABR の最大許容ピクセル数を 1280x720 に設定します。プレーヤーはこの値以下のピクセル数の画質にのみ切り替えます。
[self.player setConfig:config];スナップショットの撮影
iOS Player SDK は、snapShot インターフェイスを通じて現在のビデオのスクリーンショットを撮る方法を提供します。スクリーンショットは生データをキャプチャし、bitmap として返します。コールバックインターフェイスは onCaptureScreen です。以下の例は、その方法を示しています。
// スナップショットコールバック。
- (void)onCaptureScreen:(AliPlayer *)player image:(UIImage *)image {
// スナップショットを処理します。
}
// 現在のフレームのスナップショットを撮ります。
[self.player snapShot];スナップショットには UI は含まれません。
プレビュー
ApsaraVideo VOD の設定と組み合わせることで、プレビュー機能を実装できます。これは VidSts と VidAuth (推奨) の両方の再生でサポートされています。設定手順については、「ビデオのプレビュー」をご参照ください。
ビデオプレビュー機能を設定した後、VidPlayerConfigGen インターフェイスを使用して setPreviewTime メソッドを呼び出し、プレーヤーのプレビュー時間を設定します。以下のサンプルコードは、VidSts ベースの例を示しています。
AVPVidStsSource *source = [[AVPVidStsSource alloc] init];
....
VidPlayerConfigGenerator* vp = [[VidPlayerConfigGenerator alloc] init];
[vp setPreviewTime:20];// 20 秒のプレビュー
source.playConfig = [vp generatePlayerConfig];// 再生ソースに設定します
...プレビュー時間が設定されると、サーバーはその期間のコンテンツのみを返します。
VidPlayerConfigGen は、さまざまなサーバーサイドリクエストパラメーターの設定をサポートしています。「リクエストパラメーターの説明」をご参照ください。
Referer の設定
iOS Player SDK は Referer の設定をサポートしており、コンソールの Referer ブラックリストおよびホワイトリストと組み合わせて使用することで、アクセス権限を制御できます。リクエストの Referer は AVPConfig メソッドを使用して設定します。以下のサンプルコードは例です。
// まず構成を取得します。
AVPConfig *config = [self.player getConfig];
// Referer を設定します。
config.referer = referer;
....// その他の設定
// プレーヤーの構成を設定します。
[self.player setConfig:config];User-Agent の設定
iOS Player SDK は AVPConfig を提供して User Agent を設定します。User Agent を設定すると、プレーヤーはリクエストに User Agent 情報を含めます。例:
// まず構成を取得します。
AVPConfig *config = [self.player getConfig];
// User-Agent を設定します。
config.userAgent = userAgent;
....// その他の設定
// プレーヤーの構成を設定します。
[self.player setConfig:config];ネットワークのリトライ回数とタイムアウトの設定
iOS Player SDK のネットワークタイムアウトとリトライ回数は、AVPConfig メソッドを使用して設定できます。以下のコードは例です。
// 現在の構成を取得します。
AVPConfig *config = [self.player getConfig];
// ネットワークタイムアウト期間を指定します。単位:ミリ秒。
config.networkTimeout = 5000;
// ネットワークタイムアウト時の最大リトライ回数を指定します。リトライ間隔は networkTimeout パラメーターの値です。値 0 はリトライを行わないことを示します。アプリケーションがリトライポリシーを決定します。デフォルト値は 2 です。
config.networkRetryCount = 2;
....// 他の構成を設定します。
// プレーヤーの構成を設定します。
[self.player setConfig:config];networkRetryCount が 0 より大きい場合、ネットワークの問題が発生すると、プレーヤーは networkRetryCount 回リトライし、リトライ間の間隔は networkTimeout です。
すべてのリトライ後も読み込み状態が続く場合、
onErrorイベントがトリガーされ、AVPErrorModel.code が ERROR_LOADING_TIMEOUT に設定されます。networkRetryCountを 0 に設定すると、ネットワークタイムアウトが発生したときに、プレーヤーはeventWithStringがEVENT_PLAYER_NETWORK_RETRYと等しいonPlayerEventコールバックをトリガーします。その後、プレーヤーのreloadメソッドを呼び出してストリームを再読み込みするか、他の操作を実行できます。
キャッシュと遅延の制御
キャッシュ制御はプレーヤーにとって重要です。適切な構成を使用することで、起動時の読み込み時間を短縮し、再生の滑らかさを向上させることができます。iOS Player SDK は、キャッシュと遅延を構成するための AVPConfig インターフェイスを提供します。以下に例を示します。
// 構成を取得します。
AVPConfig *config = [self.player getConfig];
// 最大遅延を指定します。注意:このパラメーターはライブストリーミングでのみ有効です。遅延が大きい場合、Player SDK はフレームを同期して、遅延が指定された制限内にあることを保証します。
config.maxDelayTime = 5000;
// 最大バッファ期間を指定します。単位:ミリ秒。このパラメーターは、プレーヤーが一度にバッファリングできるデータの最大期間を指定します。
config.maxBufferDuration = 50000;
// ピークバッファ期間を指定します。単位:ミリ秒。ネットワーク状況が悪いためにプレーヤーがデータを読み込む場合、バッファリングされたデータの期間がこの値に達すると、プレーヤーは読み込みを停止します。
config.highBufferDuration = 3000;
// 起動バッファ期間を指定します。単位:ミリ秒。値が小さいほど、起動時の読み込み時間は短くなります。ただし、再生開始後すぐにプレーヤーが読み込み状態になる可能性があります。
config.startBufferDuration = 500;
// 他の構成を設定します。
// 構成をプレーヤーに適用します。
[self.player setConfig:config];バッファ期間は、startBufferDuration ≤ highBufferDuration ≤ maxBufferDuration を満たす必要があります。
最大バッファ期間 (mMaxBufferDuration) が 5 分を超える場合、過剰なメモリ使用を防ぐために、システムはデフォルトで 5 分の期間を使用します。
HTTP ヘッダーの設定
AVPConfig メソッドを使用して、プレーヤーのリクエストに HTTP ヘッダーパラメーターを追加できます。以下に例を示します。
// 構成を取得します。
AVPConfig *config = [self.player getConfig];
// ヘッダーを定義します。
NSMutableArray *httpHeaders = [[NSMutableArray alloc] init];
// たとえば、HTTPDNS を使用するときにホストを構成します。
[httpHeaders addObject:@"Host:example.com"];
// ヘッダーを構成します。
config.httpHeaders = httpHeaders;
....// 他の構成を設定します。
// プレーヤーの構成を設定します。
[self.player setConfig:config];ピクチャーインピクチャー
詳細なコード例については、API-Example プロジェクトの PictureInPicture モジュールをご参照ください。
PiP には iOS 15 以降と ApsaraVideo Player SDK for iOS 5.4.9.0 以降が必要です。
ApsaraVideo Player SDK for iOS 5.5.2.0 より前のバージョンでは、PiP 機能は PiP の有効化と無効化、およびアプリがバックグラウンドにあるときに PiP ウィンドウを表示するメソッドのみを提供します。バージョン 5.5.2.0 以降、SDK は外部からの PiP デリゲートの設定をサポートし、よりパーソナライズされた PiP 機能の開発を可能にします。
PiP を使用するには、デバイスの設定 (設定 > 一般 > ピクチャーインピクチャー) で有効になっていることを確認してください。
PiP の有効化
ピクチャーインピクチャー (PiP) 機能が有効になると、アプリケーションがバックグラウンドに切り替わったときに、ビデオはフローティングウィンドウで再生を続けます。アプリケーションがフォアグラウンドに切り替わると、ビデオは元の再生モードで再開します。PiP は setPictureInPictureEnable メソッドによって制御されます。PiP を有効にするには、AVPEventPrepareDone イベントが発生したときにこのメソッドを呼び出す必要があります。以下の例は、PiP 機能を有効にする方法を示しています。
- (void)onPlayerEvent:(AliPlayer *)player eventType:(AVPEventType)eventType {
switch (eventType) {
case AVPEventPrepareDone:
{
[self.player setPictureInPictureEnable:YES];
}
break;
default:
break;
}
}再生を停止するには、まず setPictureInPictureEnable を呼び出してピクチャーインピクチャー (PiP) を無効にし、次に stop を呼び出します。
PiP デリゲートの設定
以下のコード例は、ピクチャーインピクチャー (PiP) ウィンドウとプレーヤーウィンドウ間の一般的なインタラクションを示しており、PiP の一時停止、再生、早送り、早戻し、リプレイボタンを表示するロジックを含みます。デリゲートメソッドの詳細については、Player SDK デモ、特に AliyunPlayer.framework フォルダ内の AliPlayerPictureInPictureDelegate.h ヘッダーファイルをご参照ください。
PiP デリゲートの設定
/** * @brief PiP デリゲートを設定します。 */ -(void) setPictureinPictureDelegate:(id<AliPlayerPictureInPictureDelegate>)delegate; // PiP デリゲートを設定します。 [self.player setPictureinPictureDelegate:self];変数の追加とデリゲートインターフェイスの実装
(グローバル変数) を追加して、プレーヤーの状態変化を制御できます。
#import "YourUIViewController.h" #import <AliyunPlayer/AliyunPlayer.h> @interface YourUIViewController () <AVPDelegate, AliPlayerPictureInPictureDelegate> // プレーヤーインスタンス。 @property (nonatomic, strong) AliPlayer *player; // プレーヤービューコンテナー。 @property (nonatomic, strong) UIView *playerView; // PiP が現在一時停止しているかどうかをリッスンします。 @property (nonatomic, assign) BOOL isPipPaused; // プレーヤーの現在の再生ステータスをリッスンします。再生イベントステータス変更リスナーの newStatus コールバックを通じて設定します。 @property (nonatomic, assign) AVPStatus currentPlayerStatus; // PiP コントローラーを設定します。PiP が開始されようとしているときのコールバックメソッドで設定します。ページが破棄されようとしているときにアクティブに nil に設定する必要があります。設定することを推奨します。 @property (nonatomic, weak) AVPictureInPictureController *pipController; // プレーヤーの現在の再生進捗をリッスンします。currentPosition を現在のビデオ再生位置のコールバックの position パラメーターの値に設定します。 @property (nonatomic, assign) int64_t currentPosition; @end説明pipController には weak または assign 修飾子を使用する必要があります。assign 修飾子を使用する場合は、正しい変数を null に設定していることを確認してください。
onPlayerStatusChanged イベントをリッスンするときに PiP コントローラーのステータスを更新します。
- (void)onPlayerStatusChanged:(AliPlayer*)player oldStatus:(AVPStatus)oldStatus newStatus:(AVPStatus)newStatus { self.currentPlayerStatus = newStatus; if (_pipController) { [self.pipController invalidatePlaybackState]; } }onPlayerEvent イベントをリッスンするときに PiP コントローラーのステータスを更新します。
- (void)onPlayerEvent:(AliPlayer*)player eventType:(AVPEventType)eventType { if (eventType == AVPEventCompletion) { if (_pipController) { self.isPipPaused = YES; // 再生終了後、PiP ステータスを一時停止に変更します。 [self.pipController invalidatePlaybackState]; } } else if (eventType == AVPEventSeekEnd) { // シークが完了しました。 if (_pipController) { [self.pipController invalidatePlaybackState]; } } }リスナーの設定
PiP が開始されようとしているときのコールバックをリッスンします。
/** @brief ピクチャーインピクチャーが開始されようとしています。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 */ - (void)pictureInPictureControllerWillStartPictureInPicture:(AVPictureInPictureController *)pictureInPictureController { if (!_pipController) { self.pipController = pictureInPictureController; } self.isPipPaused = !(self.currentPlayerStatus == AVPStatusStarted); [pictureInPictureController invalidatePlaybackState]; }PiP が停止しようとしているときのコールバックをリッスンします。
/** @brief ピクチャーインピクチャーが停止しようとしています。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 */ - (void)pictureInPictureControllerWillStopPictureInPicture:(AVPictureInPictureController *)pictureInPictureController { self.isPipPaused = NO; [pictureInPictureController invalidatePlaybackState]; }PiP が停止する前にユーザーインターフェイスを復元するようにデリゲートに指示するコールバックをリッスンします。
/** @brief PiP が停止する前にユーザーインターフェイスを復元するようにデリゲートに指示します。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 @param completionHandler 呼び出して YES を渡すと、システムがプレーヤーのユーザーインターフェイスの復元を完了できます。 */ - (void)pictureInPictureController:(AVPictureInPictureController *)pictureInPictureController restoreUserInterfaceForPictureInPictureStopWithCompletionHandler:(void (^)(BOOL restored))completionHandler { if (_pipController) { _pipController = nil; } completionHandler(YES); }PiP の現在の再生可能時間範囲を設定するコールバックをリッスンします。
/** @brief 現在の再生可能時間範囲をピクチャーインピクチャーコントローラーに通知します。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 @return 現在の再生可能時間範囲。 */ - (CMTimeRange)pictureInPictureControllerTimeRangeForPlayback:(nonnull AVPictureInPictureController *)pictureInPictureController layerTime:(CMTime)layerTime{ Float64 current64 = CMTimeGetSeconds(layerTime); Float64 start; Float64 end; if (currentPosition <= self.player.duration) { double curPostion = self.currentPosition / 1000.0; double duration = self.player.duration / 1000.0; double interval = duration - curPostion; start = current64 - curPostion; end = current64 + interval; CMTime t1 = CMTimeMakeWithSeconds(start, layerTime.timescale); CMTime t2 = CMTimeMakeWithSeconds(end, layerTime.timescale); return CMTimeRangeFromTimeToTime(t1, t2); } else { return CMTimeRangeMake(kCMTimeNegativeInfinity, kCMTimePositiveInfinity); } }PiP が一時停止しているか再生中かを設定するコールバックをリッスンします。
/** @brief UI に一時停止または再生状態を反映します。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 @return 一時停止または再生中。 */ - (BOOL)pictureInPictureControllerIsPlaybackPaused:(nonnull AVPictureInPictureController *)pictureInPictureController{ return self.isPipPaused; }説明このコールバックは PiP が開始される前にトリガーされます。この時点でこのコールバックの戻り値が false であることを確認してください。そうしないと、PiP をアクティブ化できません。
ユーザーが早送りまたは早戻ししたときに、再生進捗をプレーヤーに同期するためのコールバックをリッスンします。
/** @brief 早送りまたは早戻しボタンがクリックされました。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 @param skipInterval 早送りまたは早戻しの時間間隔。 @param completionHandler シーク操作が完了したことを示すために呼び出す必要があるクロージャ。 */ - (void)pictureInPictureController:(nonnull AVPictureInPictureController *)pictureInPictureController skipByInterval:(CMTime)skipInterval completionHandler:(nonnull void (^)(void))completionHandler { int64_t skipTime = skipInterval.value / skipInterval.timescale; int64_t skipPosition = self.currentPosition + skipTime * 1000; if (skipPosition < 0) { skipPosition = 0; } else if (skipPosition > self.player.duration) { skipPosition = self.player.duration; } [self.player seekToTime:skipPosition seekMode:AVP_SEEKMODE_INACCURATE]; [pictureInPictureController invalidatePlaybackState]; }PiP で一時停止または再生ボタンがクリックされたときのコールバックをリッスンし、必要な操作を実行します。
/** @brief ピクチャーインピクチャーの一時停止ボタンがクリックされました。 @param pictureInPictureController ピクチャーインピクチャーコントローラー。 @param playing 再生中かどうか。 */ - (void)pictureInPictureController:(nonnull AVPictureInPictureController *)pictureInPictureController setPlaying:(BOOL)playing { if (!playing){ [self.player pause]; self.isPipPaused = YES; } else { // 推奨:PiP 再生が完了し、リプレイが必要な場合は、以下の if 文のコードをさらに実行できます。 if (self.currentPlayerStatus == AVPStatusCompletion) { [self.player seekToTime:0 seekMode:AVP_SEEKMODE_ACCURATE]; } [self.player start]; self.isPipPaused = NO; } [pictureInPictureController invalidatePlaybackState]; }
アプリ内ピクチャーインピクチャー
デフォルトでは、ピクチャーインピクチャー (PiP) 機能はアプリ外で動作します。アプリ内 PiP を実装するには、まず以下のインターフェイスを使用して PiP が有効になっているかどうかを判断できます。
/**
@brief PiP が開始されているかどうか。
@param pictureInPictureController PiP コントローラー。
@param isEnable PiP が開始されているかどうか。
*/
/****
@brief ピクチャーインピクチャーが有効かどうか
@param pictureInPictureController ピクチャーインピクチャーコントローラー
@param isEnable 有効かどうか
*/
- (void)pictureInPictureControllerIsPictureInPictureEnable:(nullable AVPictureInPictureController *)pictureInPictureController isEnable:(BOOL)isEnable;PiP が有効な場合、自動アクティベーションを無効にし、手動で制御します。
- (void) pictureInPictureControllerIsPictureInPictureEnable:(nullable AVPictureInPictureController *) pictureInPictureController isEnable:(BOOL) isEnable
{
if (isEnable && pictureInPictureController) {
_pipController = pictureInPictureController;
// pip 自動開始を閉じる
if (@available(iOS 15.0, *)) {
_pipController.canStartPictureInPictureAutomaticallyFromInline = false;
}
} else {
_pipController = NULL;
}
}
- (void) switchPip:(bool) enable {
if (_pipController == nil) {
return;
}
if (enable) {
// pip を開始
[_pipController startPictureInPicture];
} else {
// pip を閉じる
[_pipController stopPictureInPicture];
}
}ライブ RTS フォールバック
詳細なコード例については、API-Example プロジェクトの RtsLiveStream モジュールをご参照ください。
詳細については、「RTS ライブ再生」をご参照ください。
左右の音声チャンネルの切り替え
iOS Player SDK は、outputAudioChannel プロパティを使用して出力音声チャンネルを設定します。入力ソースがステレオの場合、以下のメソッドを使用して左または右の音声チャンネルに切り替えることができます。入力ソースがモノラルの場合、この設定は効果がありません。
出力音声チャンネルの設定は、音声レンダリングと PCM データコールバックの両方に影響します。
// AVPOutputAudioChannel 列挙値を設定してチャンネルを切り替えます。
// AVP_AUDIO_CHANNEL_NONE:チャンネルを指定しません。入力ソースの音声チャンネルで再生します。これがデフォルト値です。
// AVP_AUDIO_CHANNEL_LEFT:左音声チャンネルに切り替えて再生します。
// AVP_AUDIO_CHANNEL_RIGHT:右音声チャンネルに切り替えて再生します。
self.player.outputAudioChannel = AVP_AUDIO_CHANNEL_NONE;ビデオ背景色の設定
iOS Player SDK では、プレーヤーレンダリングの背景色を設定できます。インターフェイスと使用方法は以下の通りです。
API の例
/**
@brief ビデオの背景色を設定します。
@param color 色
*/
/****
@brief ビデオの背景色を設定します
@param color 色
*/
-(void) setVideoBackgroundColor:(UIColor *)color;使用方法
// パラメーターは 8 桁の 16 進数値です。8 桁はペアにグループ化され、A (アルファ/透明度)、R (赤)、G (緑)、B (青) を順番に表します。
// たとえば、0x0000ff00 は緑を表します。
[self.player setVideoBackgroundColor:0x0000ff00]VidAuth の再生ドメインの指定
VidAuth メソッドを使用すると、vid の再生ドメインなどのパラメーターを指定できます。サポートされているフィールドのリストについては、「GetPlayInfo」をご参照ください。以下では、vidAuth ベースの再生でドメイン名を指定する方法とサンプルコードについて説明します。
API の例
/**
@brief vid+playauth メソッドを使用して再生します。https://www.alibabacloud.com/help/zh/vod/user-guide/use-playback-credentials-to-play-videos をご参照ください
@param source AVPVidAuthSource の入力タイプ。
@see AVPVidAuthSource
*/
- (void)setAuthSource:(AVPVidAuthSource*)source;使用方法
VidPlayerConfigGenerator インターフェイスを介して playDomain フィールドを追加します。
VidPlayerConfigGenerator* gen = [[VidPlayerConfigGenerator alloc]init];
// playDomain フィールドを追加します。追加できるフィールドについては、
// https://www.alibabacloud.com/help/zh/vod/developer-reference/api-vod-2017-03-21-getplayinfo をご参照ください
[gen addVidPlayerConfigByStringValue:@"playDomain" value: @"com.xxx.xxx"];
[source setPlayConfig:[gen generatePlayerConfig]];
[self.player setAuthSource:source]:バックグラウンドデコード
バージョン 6.12.0 以降、SDK はバックグラウンドデコードをサポートしています。有効にすると、アプリがバックグラウンドにあるときにプレーヤーはビデオストリームのデコードと再生を続行できます。
// 値 1 はバックグラウンドデコードを有効にします。値 0 はバックグラウンドデコードを無効にします。デフォルト値は 0 です。
[self.player setOption:ALLOW_DECODE_BACKGROUND valueInt:1];H.266 デコードプラグイン
H.266 は、Versatile Video Coding (VVC) とも呼ばれ、同じ品質で大幅に低いビットレートを提供する次世代のビデオコーディング標準です。H.266 デコード機能は、オンデマンド統合用の個別のプラグインとして提供されます。
前提条件
Player またはオールインワン SDK V7.6.0 以降を使用します。
Professional Edition ライセンスの権限付与が完了していること。詳細については、「Player SDK ライセンスの取得」をご参照ください。
H.266 デコードプラグインを備えた ApsaraVideo Player は、ApsaraVideo Transcoding によってエンコードされた H.266 ビデオのみをサポートします。
プラグインの統合
プラグインのアクティベート
v7.7.0 以降、プラグインはデフォルトで有効になっており、手動でアクティベートする必要はありません。
[AliPlayerGlobalSettings enableCodecPlugin:@"vvc" valid:true];関連エラーコード
H.266 プラグインに関連するエラーコードについては、「異なるプラットフォームのプレーヤーに関する一般的な FAQ」をご参照ください。
再生ソースの自動更新
再生ソースの自動更新を有効にすると、認証の有効期限切れによる再生の中断を防ぐことができます。この機能は、ソースの有効期限が切れるとリスナーをトリガーし、新しい URL を取得してスムーズで中断のない再生を保証します。
前提条件
Player またはオールインワン SDK V7.9.0 以降を使用します。
VidAuth ソースを使用するか、URL 署名を設定します。
VidAuth ソース
API の例
/**
@brief VidAuth ソースの有効期限通知のコールバックを設定します。
プレーヤーが現在の VidAuth ソースの有効期限が切れたことを検出すると、このメソッドはコールバックをトリガーします。
VidAuth ソースの有効期限には、PlayAuth の有効期限と再生 URL の有効期限が含まれます。
コールバックで VidAuth ソースを更新し、新しい VidAuth ソースオブジェクトを `callback` 経由で送信して、安定したスムーズな再生を保証できます。
@param callback VidAuth ソースの有効期限が切れたときにトリガーされるコールバックブロック。
このコールバックを使用して、有効な `VidAuth` オブジェクトを返してプレーヤーを更新できます。
*/
/****
@brief VidAuth ソースの有効期限通知のコールバックを設定します。
このメソッドは、プレーヤーが現在の VidAuth ソースの有効期限が切れたことを検出したときにトリガーされます。
コールバック内で VidAuth ソースを更新し、`callback` を使用して更新された VidAuth ソースを返すことで、
中断のないスムーズなビデオ再生を保証できます。
@param callback VidAuth ソースの有効期限が切れたときにトリガーされるコールバックブロック。
このコールバックを使用して、有効な `VidAuth` オブジェクトを提供してプレーヤーを更新します。
*/
-(void)setOnVidAuthExpiredCallback:(void (^)(id expiredSource, id<AVPSourceRefreshCallback> callback))callback;機能構成
使用方法
GetVideoPlayAuth 操作を使用してビデオ再生認証情報を取得できます。手動での署名を避けるために、ApsaraVideo VOD サーバーサイド SDK を統合して認証情報を取得することを推奨します。詳細については、「OpenAPI Explorer」をご参照ください。
[self.player setOnVidAuthExpiredCallback:^(id expiredSource, id<AVPSourceRefreshCallback> callback) {
// AVPVidAuthSource を取得
if ([expiredSource isKindOfClass:[AVPVidAuthSource class]]) {
// ------------------- ユーザー実装開始 -------------------
// 独自の関数を呼び出して、アプリサーバーから新しい PlayAuth を取得します。
// clinetGetPlayAuthFunction はサンプル関数名です。独自の実装に置き換えてください。
[self clinetGetPlayAuthFunction:vid success:^(NSString* newPlayAuth){
// 1. 新しい認証情報の取得成功のコールバック
[vidAuth setPlayAuth:newPlayAuth];
// 2. SDK コールバックを介して更新されたオブジェクトをプレーヤーに返す
[callback onSuccess:vidAuth];
} failure:^(NSString* errorMsg) {
// 認証情報取得失敗のコールバック。
// errorMsg には詳細なエラー情報が含まれます。
[callback onError:errorMsg];
}];
// ------------------- ユーザー実装終了 -------------------
}
}];URL ソース
API の例
/**
@brief URL ソースの有効期限通知のコールバックを設定します。
プレーヤーが現在の URL ソースの有効期限が切れたことを検出すると、このメソッドはコールバックをトリガーします。
コールバックで URL ソースを更新し、`callback` を使用して新しい URL ソースを返して、中断のない再生を保証できます。
@note URL 署名の構成については、Alibaba Cloud ドキュメントをご参照ください:
https://www.alibabacloud.com/help/zh/vod/user-guide/configure-url-signing?spm=a2c4g.11186623.0.0.560c4140fGh8MW
@param callback URL ソースの有効期限が切れたときにトリガーされるコールバックブロック。
このコールバックを使用して、有効な `URLSource` オブジェクトを提供してプレーヤーを更新できます。
*/
/****
@brief URL ソースの有効期限通知のコールバックを設定します。
このメソッドは、プレーヤーが現在の URL ソースの有効期限が切れたことを検出したときにトリガーされます。
コールバック内で URL ソースを更新し、`callback` を使用して更新された URL ソースを返すことで、
中断のないビデオ再生を保証できます。
@param callback URL ソースの有効期限が切れたときにトリガーされるコールバックブロック。
このコールバックを使用して、有効な `URLSource` オブジェクトを提供してプレーヤーを更新します。
*/
-(void)setOnURLSourceExpiredCallback:(void (^)(id expiredSource, id<AVPSourceRefreshCallback> callback))callback;機能構成
使用方法
[self.player setOnURLSourceExpiredCallback:^(id expiredSource, id<AVPSourceRefreshCallback> callback) {
// AVPUrlSource を取得
if ([expiredSource isKindOfClass:[AVPUrlSource class]]) {
AVPUrlSource *expiredUrlSource = (AVPUrlSource *)expiredSource;
NSString *expiredUrl = [expiredUrlSource.playerUrl absoluteString];
// auth_key が含まれているか確認
if (![expiredUrl containsString:@"auth_key="]) {
return;
}
// 1. 期限切れの URL から元の URL を抽出
NSRange authKeyQuestionRange = [expiredUrl rangeOfString:@"?auth_key="];
NSRange authKeyAmpersandRange = [expiredUrl rangeOfString:@"&auth_key="];
NSInteger authKeyIndex = NSNotFound;
if (authKeyQuestionRange.location != NSNotFound) {
authKeyIndex = authKeyQuestionRange.location;
} else if (authKeyAmpersandRange.location != NSNotFound) {
authKeyIndex = authKeyAmpersandRange.location;
}
NSString *originalUrl = nil;
if (authKeyIndex != NSNotFound) {
originalUrl = [expiredUrl substringToIndex:authKeyIndex];
} else {
// auth_key が見つからない場合、URL 全体を元の URL として扱う
originalUrl = expiredUrl;
}
// 2. 新しい認証パラメーターを準備:authKey と有効期限
// クラスメンバーの authKey が有効な場合はそれを使用
NSString *key = (self.authKey.length > 0) ? self.authKey : @"";
if (!NOT_EMPTY(key)) {
[callback onError:@"REFRESH_ERROR:key fail"];
return;
}
// クラスメンバーの validTime が有効な場合はそれを使用、そうでなければデフォルト値を使用
NSTimeInterval validTime = (self.validTime > 0) ? self.validTime : 3600; // デフォルト 3600 秒
NSTimeInterval newExpireTime = [[NSDate date] timeIntervalSince1970] + validTime;
// 3. CdnAuthUtil を使用して新しい認証済み URL を生成 (メソッド A)
NSString *newAuthUrl = [CdnAuthUtil aAuthWithUri:originalUrl key:key exp:newExpireTime];
AVPUrlSource *resultSource = [[AVPUrlSource alloc] urlWithString:newAuthUrl];
// 4. コールバック処理
if (newAuthUrl) {
[callback onSuccess:resultSource];
} else {
[callback onError:@"REFRESH_ERROR:refresh fail"];
}
}
}];ユーティリティ関数
署名メソッド A を使用した例。
パフォーマンス
再生シナリオの設定
再生シナリオを設定すると、setConfig インターフェイスを介して設定されたカスタムパラメーターを保持しながら、最適なパラメーター (バッファ設定や機能の切り替えを含む) が自動的に構成されます (カスタム設定が優先されます)。
再生シナリオを設定した後、
getConfigインターフェイスを使用してパラメーター構成を表示できます。
API の例
/**
@brief プレーヤーシナリオを設定します。
@param scene プレーヤーシナリオ。
@see AVPScenario
*/
/****
@brief プレーヤーシーンを設定します。
@param scene プレーヤーシーン。
@see AVPScene
*/
-(void) setPlayerScene:(AVPScene)scene;再生シナリオ
typedef enum _AVPScene {
/**
* シナリオ:なし
*/
/****
* シーンなし
*/
SceneNone,
/**
* 長編ビデオシナリオ:30 分以上のビデオに適用
*/
/****
* 長編シーン:30 分以上に適用
*/
SceneLong,
/**
* 中編ビデオシナリオ:5~30 分のビデオに適用
*/
/****
* 中編シーン:5 分~30 分に適用
*/
SceneMedium,
/**
* 短編ビデオシナリオ:5 分以下のビデオに適用
*/
/****
* 短編シーン:0 秒~5 分に適用
*/
SceneShort,
/**
* ライブストリーミングシナリオ
*/
/****
* ライブシーン
*/
SceneLive,
/**
* 超低遅延ライブストリーミングシナリオ
*/
/****
* RTS ライブシーン
*/
SceneRTSLive
} AVPScene;使用方法
// 短編ビデオシナリオを設定
[self.player setPlayerScene:SceneShort];
// 中編ビデオシナリオを設定
[self.player setPlayerScene:SceneMedium];
// 長編ビデオシナリオを設定
[self.player setPlayerScene:SceneLong];
// ライブストリーミングシナリオを設定
[self.player setPlayerScene:SceneLive]; プリレンダリング
iOS Player SDK は、再生開始前に最初のフレームを高速にレンダリングし、起動速度を向上させることをサポートしています。
この機能はデフォルトで無効になっています。
有効にすると、準備完了イベントと初回フレームレンダリングイベントの順序に影響します。デフォルトでは、準備完了イベントが最初に発生し、次に初回フレームレンダリングイベントが発生します。プリレンダリングを有効にすると、デコードとレンダリングの速度によっては、初回フレームレンダリングイベントが準備完了イベントの前に発生する可能性がありますが、再生には影響しません。
例:
[self.player setOption:ALLOW_PRE_RENDER valueInt:1];ローカルキャッシュ
詳細なコード例については、API-Example プロジェクトの PreloadUrl モジュールをご参照ください。
iOS Player SDK は、ローカルキャッシュを提供して、起動速度、シーク速度を向上させ、繰り返しビデオ再生の途切れを減らし、帯域幅を節約します。
ローカルキャッシュの有効化
デフォルトでは、ローカルキャッシュ機能は無効になっています。この機能を使用するには、手動で有効にする必要があります。この機能は、AliPlayerGlobalSettings クラスの enableLocalCache プロパティを使用して構成されます。以下の例は、この設定を構成する方法を示しています。
/**
* ローカルキャッシュを有効にします。有効にすると、ローカルファイルにキャッシュされます。
* @param enable: ローカルキャッシュの切り替え。true: 有効、false: 無効。デフォルトは無効です。
* @param maxBufferMemoryKB: V5.4.7.1 以降非推奨。効果なし。
* @param localCacheDir: 必須。ローカルキャッシュディレクトリの絶対パス。
*/
[AliPlayerGlobalSettings enableLocalCache:true maxBufferMemoryKB:1024 localCacheDir:@""];
/**
@brief ローカルキャッシュファイルの自動クリア設定。
@param expireMin: V5.4.7.1 以降非推奨。効果なし。
@param maxCapacityMB: メガバイト単位の最大キャッシュ容量。デフォルトは 20 GB です。クリーンアップ中に、合計キャッシュ容量がこのサイズを超えた場合、cacheItem の最終キャッシュ時間でソートされた最も古いキャッシュファイルが、容量が最大キャッシュ容量以下になるまで 1 つずつ削除されます。
@param freeStorageMB: メガバイト単位の最小空きディスク領域。デフォルトは 0 です。クリーンアップ中に、最大キャッシュ容量と同様に、現在のディスク領域がこの値より小さい場合、freeStorage がこの値以上になるか、すべてのキャッシュがクリアされるまで、ルールに従ってキャッシュファイルも 1 つずつ削除されます。
*/
[AliPlayerGlobalSettings setCacheFileClearConfig:0 maxCapacityMB:0 freeStorageMB:0];
/**
* 読み込まれた URL のハッシュ値を取得するためのコールバック。URL の一意の ID として使用されます。各 URL が異なることを確認する必要があります。
*/
// この関数を自分で実装し、関数ポインターを setCacheUrlHashCallback に渡す必要があります。
static NSString *CaheUrlHashHandle(NSString *url) {
return @"xxx";
}
[AliPlayerGlobalSettings setCacheUrlHashCallback:&CaheUrlHashHandle];ビデオ再生 URL に認証パラメーターがある場合、これらのパラメーターはローカルキャッシュと再生中に変更されます。異なる認証を持つ同じ URL のキャッシュヒット率を向上させるには、
setCacheUrlHashCallbackインターフェイスでハッシュ値 (たとえば MD5) を計算する前に、URL から認証パラメーターを削除できます。たとえば、認証付きの再生 URL がhttp://****.mp4?aaaの場合、読み込み時にハッシュ値を計算するためにhttp://****.mp4を使用します。ただし、ビデオが暗号化された M3U8 ビデオの場合、ハッシュ値を計算する前に認証パラメーターを削除してキー URL を処理すると、異なるビデオがキャッシュ内の同じキーにヒットし、再生に失敗します。解決策:setCacheUrlHashCallbackコールバックで、ドメインチェックを実行し、再生ドメイン (http(s)://xxxxx.m3u8?aaaa) の認証パラメーターのみを削除し、キー URL のドメイン (http(s)://yyyyy?bbbb) の認証パラメーターは削除しません。
サーバーが HTTP と HTTPS の両方のプロトコルをサポートしているが、異なるプロトコルが指すメディアファイルが同一である場合、MD5 値を計算する前にリクエストヘッダーを削除または統一できます。例:
ビデオ再生 URL が
https://****.mp4とhttp://****.mp4の場合、MD5 値を計算するために****.mp4を使用します。ビデオ再生 URL が
https://****.mp4の場合、MD5 値を計算する前にhttp://****.mp4に統一します。
ApsaraVideo Player SDK V5.5.4.0 以降で、ビデオ再生 URL に認証パラメーターが含まれ、再生プロトコルが HLS の場合、
AVPConfig.enableStrictAuthModeフィールドを設定して異なる認証モードを選択できます。以前のバージョンのデフォルト値は false です。V7.13.0 以降のデフォルト値は true です。:非厳密認証 (false):認証はキャッシュされます。以前にメディアの一部のみがキャッシュされていた場合、プレーヤーはキャッシュされた認証を使用してキャッシュされていない部分をリクエストします。URL 認証の有効期間が短い場合、または一時停止後長時間経ってから再生を再開する場合、認証が期限切れになる可能性があります。再生ソースの自動更新と組み合わせて、再開時の認証期限切れを処理します。
厳密認証 (true):認証はキャッシュされません。再生が開始されるたびに認証が実行されます。ネットワーク接続がないと再生は失敗します。
単一 URL のローカルキャッシュの有効化または無効化
特定の URL のローカルキャッシュ機能を無効にしたい場合は、player config で設定できます。以下の例は、その方法を示しています。
// まず構成を取得します。
AVPConfig *config = [self.player getConfig];
// 再生 URL のローカルキャッシュを有効にするかどうか。デフォルトは true です。AliPlayerGlobalSettings を介してローカルキャッシュがグローバルに有効になっており、ここでも有効 (true に設定) になっている場合、この URL のローカルキャッシュが有効になります。ここで false に設定すると、この URL のローカルキャッシュは無効になります。
config.enableLocalCache = false;
....// その他の設定
// プレーヤーの構成を設定します。
[self.player setConfig:config];デフォルトのキャッシュパスの使用
キャッシュにデフォルトのパスを使用したい場合は、AliPlayerGlobalSettings を通じて次のように構成できます。
[AliPlayerGlobalSettings enableLocalCache:true];プリロード
iOS Player SDK は、ローカルキャッシュのアップグレードであるプリロードを提供し、再生開始前にビデオの一部をキャッシュにダウンロードすることで、起動速度をさらに向上させます。
プリロードの制限:
プリロードは、MP4、MP3、FLV、HLS などの単一メディアファイルをサポートします。
iOS Player SDK は、現在再生中のビデオに干渉しないように、デフォルトでプリロードネットワークリクエストをスケジュールします。プリロードリクエストは、バッファリングされたコンテンツが特定のしきい値に達した後にのみ送信されます。これを無効にしてリクエストをリアルタイムで管理するには、以下を使用します。
[AliPlayerGlobalSettings enableNetworkBalance:false];「ローカルキャッシュ」で説明されているように、ローカルキャッシュ機能を有効にします。
ソースの設定
VidAuth (推奨)
AVPVidAuthSource* vidAuthSource = [[AVPVidAuthSource alloc] init]; [vidAuthSource setVid:@"Vid 情報"]; // 必須。ビデオ ID (VideoId)。 [vidAuthSource setPlayAuth:@"<yourPlayAuth>"]; // 必須。再生認証情報。ApsaraVideo VOD の GetVideoPlayAuth 操作を呼び出して生成する必要があります。 [vidAuthSource setRegion:@"アクセスリージョン"]; // Player SDK V5.5.5.0 以降、このパラメーターは非推奨です。リージョンを設定する必要はありません。プレーヤーが自動的にリージョンを解析します。Player SDK V5.5.5.0 より前のバージョンでは、このパラメーターは必須です。ApsaraVideo VOD のアクセスリージョン。デフォルトは cn-shanghai です。 [vidAuthSource setQuality:@"選択された画質"]; // "AUTO" はアダプティブビットレートを表します。VidSts
AVPVidStsSource* vidStsSource = [[AVPVidStsSource alloc] init]; [vidStsSource setVid: @"Vid 情報"]; // 必須。ビデオ ID (VideoId)。 [vidStsSource setRegion:@"アクセスリージョン"]; // 必須。ApsaraVideo VOD のアクセスリージョン。デフォルトは cn-shanghai です。 [vidStsSource setSecurityToken: @"<yourSecurityToken>"]; // 必須。STS セキュリティトークン。STS の AssumeRole 操作を呼び出して生成する必要があります。 [vidStsSource setAccessKeySecret: @"<yourAccessKeySecret>"]; // 必須。一時的な STS AccessKey ペアの AccessKey Secret。STS の AssumeRole 操作を呼び出して生成する必要があります。 [vidStsSource setAccessKeyId: @"<yourAccessKeyId>"]; // 必須。一時的な STS AccessKey ペアの AccessKey ID。STS の AssumeRole 操作を呼び出して生成する必要があります。 [vidStsSource setQuality:@"選択された画質"]; // "AUTO" はアダプティブビットレートを表します。UrlSource
NSString* url = @"再生 URL"; // 必須。再生 URL。サードパーティの VOD URL または ApsaraVideo VOD からの再生 URL にすることができます。 AVPUrlSource* urlSource = [[AVPUrlSource alloc]urlWithString:url];タスクパラメーターの設定
説明これはマルチビットレートビデオにのみ適用されます。
setDefaultBandWidth、setDefaultResolution、またはsetDefaultQualityのいずれかを選択できます。AVPPreloadConfig *config = [[AVPPreloadConfig alloc]init]; // マルチビットレートストリームのプリロードビットレートを設定します。 [config setDefaultBandWidth:400000]; // マルチビットレートストリームのプリロード解像度を設定します。 [config setDefaultResolution:640 * 480]; // マルチビットレートストリームのプリロード品質を設定します。 [config setDefaultQuality:@"FD"]; // プリロード時間を設定します。 [config setDuration:1000];タスクリスナーの追加
タスクをビルドし、
MediaLoaderV2インスタンスに追加して、プリロードを開始します。VidAuth (推奨)
// プリロードタスクをビルドします。 AVPPreloadTask* mPreloadTask = [[AVPPreloadTask alloc]initWithVidAuthSource:vidAuthSource preloadConfig:config]; // MediaLoaderV2 インスタンスを取得します。 AliMediaLoaderV2* vodMedialoader = [AliMediaLoaderV2 shareInstance]; // タスクを追加してプリロードを開始します。 NSString* taskId = [vodMedialoader addTask:mPreloadTask listener:self];VidSts
// プリロードタスクをビルドします。 AVPPreloadTask* mPreloadTask = [[AVPPreloadTask alloc]initWithVidStsSource:vidStsSource preloadConfig:config]; // MediaLoaderV2 インスタンスを取得します。 AliMediaLoaderV2* vodMedialoader = [[AliMediaLoaderV2 alloc]init]; // タスクを追加してプリロードを開始します。 NSString* taskId = [vodMedialoader addTask:mPreloadTask listener:self];UrlSource
// プリロードタスクをビルドします。 AVPPreloadTask* mPreloadTask = [[AVPPreloadTask alloc]initWithUrlSource:urlSource preloadConfig:config]; // MediaLoaderV2 インスタンスを取得します。 AliMediaLoaderV2* vodMedialoader = [[AliMediaLoaderV2 alloc]init]; // タスクを追加してプリロードを開始します。 NSString* taskId = [vodMedialoader addTask:mPreloadTask listener:self];任意:タスクの管理
[vodMedialoader cancelTask:taskId];// 指定されたタスク ID のプリロードタスクをキャンセルします。 [vodMedialoader pauseTask:taskId];// 指定されたタスク ID のプリロードタスクを一時停止します。 [vodMedialoader resumeTask:taskId];// 指定されたタスク ID のプリロードタスクを再開します。任意:読み込まれたファイルの削除
必要に応じて読み込まれたファイルを削除して、スペースを節約できます。SDK は削除インターフェイスを提供していません。アプリの読み込みディレクトリ内のファイルを削除する必要があります。
動的プリロード
動的プリロード戦略では、現在のビデオのキャッシュとプリロードされるアイテムの数を制御することで、再生体験とコストのバランスを取ることができます。
マルチビットレート HLS ビデオのプリロード
マルチビットレート HLS ビデオを使用する listPlayer シナリオでは、現在の再生画質に一致するストリームをプリロードし、ビジネスニーズに基づいてプリロードモードを選択できます。
ダウンロード速度の取得
onCurrentDownloadSpeed コールバックで、現在再生中のビデオのダウンロード速度を取得します。
- (void)onCurrentDownloadSpeed:(AliPlayer *)player speed:(int64_t)speed{
intspeed_=speed;
}ネットワーク機能
HTTPDNS
HTTPDNS は、DNS 名前解決技術を使用して、特定の HTTPDNS サーバーにドメイン名の名前解決リクエストを送信し、より高速で安定したドメイン名の名前解決結果を取得し、DNS ハイジャックのリスクを低減します。
ApsaraVideo Player SDK は、特に Alibaba Cloud CDN ドメイン名向けに強化された HTTPDNS 機能を提供し、Alibaba Cloud CDN ネットワークの正確なスケジューリングとリアルタイムの名前解決をサポートし、ネットワークパフォーマンスを効果的に向上させます。
強化された HTTPDNS の使用例
強化された HTTPDNS は、Alibaba Cloud CDN ドメイン名に対してのみ HTTPDNS サービスを提供します。構成するドメイン名が Alibaba Cloud CDN ドメイン名であり、ドメイン名構成が完全で正常に使用できることを確認してください。ApsaraVideo VOD で CDN ドメイン名を追加および構成するには、「高速化ドメイン名の追加」をご参照ください。CDN ドメイン名の詳細については、「Alibaba Cloud CDN」をご参照ください。
// 強化された HTTPDNS を有効にします。
[AliPlayerGlobalSettings enableEnhancedHttpDns:YES];
// 任意。HTTPDNS 事前解決用のドメイン名を追加します。
[[AliDomainProcessor shareInstance] addPreResolveDomain:@"player.***alicdn.com"];HTTP/2
iOS Player SDK は、バージョン 5.5.0.0 以降、デフォルトで HTTP/2 を有効にします。
iOS Player SDK は HTTP/2 をサポートしており、多重化を使用して head-of-line ブロッキングを回避し、再生パフォーマンスを向上させます。
[AliPlayerGlobalSettings setUseHttp2:true];HTTP の TCP 接続の事前確立
HTTP (HTTPS ではない) ビデオ再生リクエストの場合、TCP 接続を事前に確立することで、ユーザーエクスペリエンスが大幅に向上し、接続時間が短縮され、再生の即時性と継続性が確保され、ネットワークとシステムのリソース使用量が最適化されます。
// ドメイン形式は host[:port] です。ポートは任意です。複数のドメインはセミコロン (;) で区切ります。
// グローバル設定。
// 完全なインターフェイスが設定されるたびに、現在の文字列が使用されます (追加する場合は追加、削除する場合は削除)。空の文字列は事前接続を停止します。
[AliPlayerGlobalSettings setOption:SET_PRE_CONNECT_DOMAIN value: @"domain1;domain2"];ビデオダウンロード
詳細なコード例については、API-Example プロジェクトの Download モジュールをご参照ください。
iOS Player SDK は、ApsaraVideo VOD コンテンツのビデオダウンロード機能を提供し、標準モードとセキュアモードがあります。
標準ダウンロード:ダウンロードされたビデオは暗号化されておらず、サードパーティのプレーヤーで再生できます。
セキュアダウンロード:ダウンロードされたビデオは暗号化されており、ApsaraVideo Player でのみ再生できます。
使用上の注意
ビデオダウンロード機能は、VidSts および VidAuth メソッドでのみサポートされています。
ApsaraVideo VOD コンソールでダウンロードモードを有効にして構成します。詳細については、「オフラインダウンロード」をご参照ください。
ビデオダウンロードは、レジューム転送をサポートしています。
操作手順
任意: セキュアダウンロード用の暗号化検証ファイルを構成します。セキュアダウンロードの場合のみ構成します。標準ダウンロードでは構成は不要です。
説明暗号化検証ファイルがアプリ情報と一致していることを確認してください。そうしないと、ビデオのダウンロードに失敗します。
セキュアダウンロードを使用する場合は、ApsaraVideo VOD コンソールで生成されたキーファイルを Player SDK に構成します。キーファイルは、ダウンロードと再生のためにビデオを復号化および検証するために使用されます。キーファイルの生成方法の詳細については、「セキュアダウンロードの有効化」をご参照ください。
キーファイルは Application で一度構成することを推奨します。
NSString *encrptyFilePath = [[NSBundle mainBundle] pathForResource:@"encryptedApp" ofType:@"dat"]; [AliPrivateService initKey:encrptyFilePath];ダウンローダーの作成と設定
例:
AliMediaDownloader *downloader = [[AliMediaDownloader alloc] init]; [downloader setSaveDirectory:self.downLoadPath]; [downloader setDelegate:self];イベントリスナーの設定
ダウンローダーは複数のリスナーを提供します。
-(void)onPrepared:(AliMediaDownloader *)downloader mediaInfo:(AVPMediaInfo *)info { // ダウンロード項目が正常に準備されました。 } -(void)onError:(AliMediaDownloader *)downloader errorModel:(AVPErrorModel *)errorModel { // ダウンロードエラーが発生しました。 } -(void)onDownloadingProgress:(AliMediaDownloader *)downloader percentage:(int)percent { // ダウンロード進捗率。 } -(void)onProcessingProgress:(AliMediaDownloader *)downloader percentage:(int)percent { // 処理進捗率。 } -(void)onCompletion:(AliMediaDownloader *)downloader { // ダウンロードが成功しました。 }ダウンロードソースの準備
prepareメソッドを呼び出してダウンロードソースを準備できます。サポートされているソースタイプには、VidStsSource と VidAuthSource があります。VidSts
// VidSts を作成します。 AVPVidStsSource* stsSource = [[AVPVidStsSource alloc] init]; stsSource.region = @"アクセスリージョン"; // ApsaraVideo VOD のアクセスリージョン。デフォルトは cn-shanghai です。 stsSource.vid = @"Vid 情報"; // ビデオ ID (VideoId)。 stsSource.securityToken = @"<yourSecurityToken>"; // STS セキュリティトークン。STS の AssumeRole 操作を呼び出して生成する必要があります。 stsSource.accessKeySecret = @"<yourAccessKeySecret>"; // 一時的な STS AccessKey ペアの AccessKey Secret。STS の AssumeRole 操作を呼び出して生成する必要があります。 stsSource.accessKeyId = @"<yourAccessKeyId>"; // 一時的な STS AccessKey ペアの AccessKey ID。STS の AssumeRole 操作を呼び出して生成する必要があります。 // VOD コンソールで HLS 標準暗号化パラメーターのパススルーを有効にしており、デフォルトのパラメーター名が MtsHlsUriToken の場合は、config を設定して vid に渡す必要があります。以下をご参照ください。 // VOD コンソールで HLS 標準暗号化パラメーターのパススルーを有効にしていない場合は、以下のコードを統合する必要はありません。 VidPlayerConfigGenerator* vp = [[VidPlayerConfigGenerator alloc] init]; [vp setHlsUriToken:yourMtsHlsUriToken]; stsSource.playConfig = [vp generatePlayerConfig]; // ダウンロードソースを準備します。 [downloader prepareWithVid:stsSource];VidAuth
// VidAuth を作成します。 AVPVidAuthSource *authSource = [[AVPVidAuthSource alloc] init]; authSource.vid = @"Vid 情報"; // ビデオ ID (VideoId)。 authSource.playAuth = @"<yourPlayAuth>"; // 再生認証情報。ApsaraVideo VOD の GetVideoPlayAuth 操作を呼び出して生成する必要があります。 authSource.region = @"アクセスリージョン"; // Player SDK V5.5.5.0 以降、このパラメーターは非推奨です。リージョンを設定する必要はありません。プレーヤーが自動的にリージョンを解析します。Player SDK V5.5.5.0 より前のバージョンでは、このパラメーターは必須です。ApsaraVideo VOD のアクセスリージョン。デフォルトは cn-shanghai です。 // VOD コンソールで HLS 標準暗号化パラメーターのパススルーを有効にしており、デフォルトのパラメーター名が MtsHlsUriToken の場合は、config を設定して vid に渡す必要があります。以下をご参照ください。 // VOD コンソールで HLS 標準暗号化パラメーターのパススルーを有効にしていない場合は、以下のコードを統合する必要はありません。 VidPlayerConfigGenerator* vp = [[VidPlayerConfigGenerator alloc] init]; [vp setHlsUriToken:yourMtsHlsUriToken]; authSource.playConfig = [vp generatePlayerConfig]; // ダウンロードソースを準備します。 [downloader prepareWithVid:authSource];
説明ApsaraVideo VOD コンソールで HLS 暗号化のパラメーターパススルーを有効にする場合、デフォルトのパラメーターは MtsHIsUriToken です。詳細については、「HLS 暗号化のパラメーターパススルー」をご参照ください。次に、前のコードに従って MtsHIsUriToken の値を ApsaraVideo VOD ソースに設定します。
準備が成功した後にダウンロード項目を選択
ダウンロードソースの準備が完了すると、
onPreparedメソッドが呼び出されます。返される TrackInfo には、画質などの各ビデオトラックの情報が含まれています。その後、ダウンロードするトラックを選択できます。以下のサンプルコードは例です。-(void)onPrepared:(AliMediaDownloader *)downloader mediaInfo:(AVPMediaInfo *)info { NSArray<AVPTrackInfo*>* tracks = info.tracks; // たとえば、最初の TrackInfo をダウンロードします。 [downloader selectTrack:[tracks objectAtIndex:0].trackIndex]; }ダウンロードソースを更新してダウンロードを開始
VidSts または VidAuth は、ダウンロード前に有効期限が切れる可能性があります。そのため、ダウンロードを開始する前にダウンロードソースを更新することを推奨します。
// ダウンロードソースを更新します。 [downloader updateWithVid:vidSource] // ダウンロードを開始します。 [downloader start];ダウンロードが成功または失敗した後にダウンローダーを解放
ダウンロードが成功した後、
destroyを呼び出してダウンローダーを解放します。[self.downloader destroy]; self.downloader = nil;
暗号化再生
ApsaraVideo VOD は、HLS 標準暗号化、Alibaba Cloud 独自暗号化、および DRM 暗号化をサポートしています。手順については、「暗号化されたビデオの再生」をご参照ください。
ネイティブ RTS 再生
SDK は、低遅延ライブストリーミングを実装するためにネイティブ RTS SDK を統合しています。詳細については、「iOS での RTS ベースのストリームフェッチングの実装」をご参照ください。