Les SDK IMA permettent d'intégrer facilement des annonces multimédias à vos sites Web et applications. Les SDK IMA peuvent demander des annonces à partir de n'importe quel ad server compatible avec la norme VAST et gérer la lecture des annonces dans vos applications. Avec les SDK IMA côté client, vous gardez le contrôle de la lecture du contenu vidéo, tandis que le SDK gère la lecture des annonces. Les annonces sont diffusées dans un lecteur vidéo distinct situé au-dessus du lecteur vidéo de contenu de l'application.
Ce guide explique comment intégrer le SDK IMA dans une simple application de lecteur vidéo. Si vous souhaitez consulter ou suivre un exemple d'intégration complet, téléchargez l'exemple BasicExample sur GitHub.
Présentation de l'IMA côté client
L'implémentation d'IMA côté client implique quatre composants principaux du SDK, qui sont décrits dans ce guide:
IMAAdDisplayContainer
: objet conteneur dans lequel les annonces sont affichées.IMAAdsLoader
: objet qui demande des annonces et gère les événements à partir des réponses aux requêtes d'annonces. Vous ne devez instancier qu'un seul chargeur d'annonces, qui peut être réutilisé tout au long de la durée de vie de l'application.IMAAdsRequest
: objet qui définit une requête d'annonces. Les requêtes d'annonces spécifient l'URL du tag d'emplacement publicitaire VAST, ainsi que des paramètres supplémentaires, tels que les dimensions de l'annonce.IMAAdsManager
: objet qui contient la réponse à la demande d'annonce, contrôle la lecture des annonces et écoute les événements d'annonce déclenchés par le SDK.
Prérequis
Avant de commencer, vous avez besoin des éléments suivants :
- Xcode 13 ou version ultérieure
- CocoaPods (recommandé), Swift Package Manager ou une copie téléchargée du SDK IMA pour tvOS
1. Créer un projet Xcode
Dans Xcode, créez un projet tvOS à l'aide d'Objective-C ou de Swift. Utilisez BasicExample comme nom de projet.
2. Ajouter le SDK IMA au projet Xcode
Installer le SDK à l'aide de CocoaPods (recommandé)
CocoaPods est un gestionnaire de dépendances pour les projets Xcode. Il s'agit de la méthode recommandée pour installer le SDK IMA. Pour en savoir plus sur l'installation ou l'utilisation de CocoaPods, consultez la documentation CocoaPods. Une fois CocoaPods installé, suivez les instructions ci-dessous pour installer le SDK IMA:
Dans le même répertoire que votre fichier BasicExample.xcodeproj, créez un fichier texte appelé Podfile et ajoutez la configuration suivante :
source 'https://github.com/CocoaPods/Specs.git' platform :tvos, '14' target "BasicExample" do pod 'GoogleAds-IMA-tvOS-SDK', '~> 4.13.0' end
Dans le répertoire contenant le Podfile, exécutez
pod install --repo-update
.Vérifiez que l'installation a réussi en ouvrant le fichier BasicExample.xcworkspace et en confirmant qu'il contient deux projets : BasicExample et Pods (les dépendances installées par CocoaPods).
Installer le SDK à l'aide de Swift Package Manager
Le SDK Interactive Media Ads est compatible avec le gestionnaire de paquets Swift à partir de la version 4.8.2. Suivez les étapes ci-dessous pour importer le package Swift.
Dans Xcode, installez le package Swift du SDK IMA en accédant à File > Add Packages (Fichier > Ajouter des packages).
Dans l'invite qui s'affiche, recherchez le dépôt GitHub du package Swift du SDK IMA :
https://github.com/googleads/swift-package-manager-google-interactive-media-ads-tvos
Sélectionnez la version du package IMA SDK Swift que vous souhaitez utiliser. Pour les nouveaux projets, nous vous recommandons d'utiliser l'option Jusqu'à la prochaine version majeure.
Une fois que vous avez terminé, Xcode résout vos dépendances de package et les télécharge en arrière-plan. Pour en savoir plus sur l'ajout de dépendances de paquets, consultez cet article d'Apple.
Télécharger et installer manuellement le SDK
Si vous ne souhaitez pas utiliser CocoaPods, vous pouvez télécharger le SDK IMA et l'ajouter manuellement à votre projet.
3. Créer un lecteur vidéo simple
Commencez par implémenter un lecteur vidéo de base. Au départ, ce lecteur n'utilise pas le SDK IMA et ne contient pas encore de méthode permettant de déclencher la lecture.
ViewController.m
Objective-C
#import "ViewController.h" #import <AVKit/AVKit.h> NSString *const kContentURLString = @"https://storage.googleapis.com/interactive-media-ads/media/stock.mp4"; @interface ViewController () @property(nonatomic) AVPlayerViewController *contentPlayerViewController; @end @implementation ViewController - (void)viewDidLoad { [super viewDidLoad]; self.view.backgroundColor = UIColor.blackColor; [self setupContentPlayer]; } - (void)setupContentPlayer { // Create a content video player. NSURL *contentURL = [NSURL URLWithString:kContentURLString]; AVPlayer *player = [AVPlayer playerWithURL:contentURL]; self.contentPlayerViewController = [[AVPlayerViewController alloc] init]; self.contentPlayerViewController.player = player; self.contentPlayerViewController.view.frame = self.view.bounds; // Attach content video player to view hierarchy. [self showContentPlayer]; } // Add the content video player as a child view controller. - (void)showContentPlayer { [self addChildViewController:self.contentPlayerViewController]; self.contentPlayerViewController.view.frame = self.view.bounds; [self.view insertSubview:self.contentPlayerViewController.view atIndex:0]; [self.contentPlayerViewController didMoveToParentViewController:self]; } // Remove and detach the content video player. - (void)hideContentPlayer { // The whole controller needs to be detached so that it doesn't capture events from the remote. [self.contentPlayerViewController willMoveToParentViewController:nil]; [self.contentPlayerViewController.view removeFromSuperview]; [self.contentPlayerViewController removeFromParentViewController]; } @end
Swift
import AVFoundation import UIKit class ViewController: UIViewController { static let ContentURLString = "https://storage.googleapis.com/interactive-media-ads/media/stock.mp4" var playerViewController: AVPlayerViewController! override func viewDidLoad() { super.viewDidLoad() self.view.backgroundColor = UIColor.black; setUpContentPlayer() } func setUpContentPlayer() { // Load AVPlayer with path to your content. let contentURL! = URL(string: ViewController.ContentURLString) let player = AVPlayer(url: contentURL) playerViewController = AVPlayerViewController() playerViewController.player = player showContentPlayer() } func showContentPlayer() { self.addChild(playerViewController) playerViewController.view.frame = self.view.bounds self.view.insertSubview(playerViewController.view, at: 0) playerViewController.didMove(toParent:self) } func hideContentPlayer() { // The whole controller needs to be detached so that it doesn't capture events from the remote. playerViewController.willMove(toParent:nil) playerViewController.view.removeFromSuperview() playerViewController.removeFromParent() } }
4. Importer le SDK IMA
Ajoutez ensuite le framework IMA à l'aide d'une instruction d'importation sous les importations existantes.
ViewController.m
Objective-C
#import "ViewController.h" #import <AVKit/AVKit.h> #import <GoogleInteractiveMediaAds/GoogleInteractiveMediaAds.h> NSString *const kContentURLString = @"https://storage.googleapis.com/interactive-media-ads/media/stock.mp4";
Swift
import AVFoundation import GoogleInteractiveMediaAds import UIKit class ViewController: UIViewController { static let ContentURLString = "https://storage.googleapis.com/interactive-media-ads/media/stock.mp4"
5. Implémenter le suivi de la position de lecture du contenu et l'observateur de fin de flux
Pour diffuser des annonces mid-roll, le SDK IMA doit suivre la position actuelle de votre contenu vidéo. Pour ce faire, créez une classe qui implémente IMAContentPlayhead
. Si vous utilisez un AVPlayer
, comme illustré dans cet exemple, le SDK fournit la classe IMAAVPlayerContentPlayhead
qui effectue cette opération pour vous.
Si vous n'utilisez pas AVPlayer
, vous devez implémenter IMAContentPlayhead
sur une classe de votre choix.
Vous devez également indiquer au SDK quand la lecture de votre contenu est terminée afin qu'il puisse afficher des annonces post-roll. Pour ce faire, appelez contentComplete
sur IMAAdsLoader
à l'aide de AVPlayerItemDidPlayToEndTimeNotification
.
ViewController.m
Objective-C
... @interface ViewController () @property(nonatomic) IMAAVPlayerContentPlayhead *contentPlayhead; @property(nonatomic) AVPlayerViewController *contentPlayerViewController; @end ... - (void)setupContentPlayer { // Create a content video player. NSURL *contentURL = [NSURL URLWithString:kContentURLString]; AVPlayer *player = [AVPlayer playerWithURL:contentURL]; self.contentPlayerViewController = [[AVPlayerViewController alloc] init]; self.contentPlayerViewController.player = player; self.contentPlayerViewController.view.frame = self.view.bounds; self.contentPlayhead = [[IMAAVPlayerContentPlayhead alloc] initWithAVPlayer:self.contentPlayerViewController.player]; // Track end of content. AVPlayerItem *contentPlayerItem = self.contentPlayerViewController.player.currentItem; [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(contentDidFinishPlaying:) name:AVPlayerItemDidPlayToEndTimeNotification object:contentPlayerItem]; // Attach content video player to view hierarchy. [self showContentPlayer]; } ... - (void)contentDidFinishPlaying:(NSNotification *)notification {} - (void)dealloc { [NSNotificationCenter.defaultCenter removeObserver:self]; } @end
Swift
... class ViewController: UIViewController { static let ContentURLString = "https://storage.googleapis.com/interactive-media-ads/media/stock.mp4" var contentPlayhead: IMAAVPlayerContentPlayhead? var playerViewController: AVPlayerViewController! deinit { NotificationCenter.default.removeObserver(self) } ... func setUpContentPlayer() { // Load AVPlayer with path to your content. let contentURL! = URL(string: ViewController.ContentURLString) let player = AVPlayer(url: contentURL) playerViewController = AVPlayerViewController() playerViewController.player = player // Set up your content playhead and contentComplete callback. contentPlayhead = IMAAVPlayerContentPlayhead(avPlayer: player) NotificationCenter.default.addObserver( self, selector: #selector(ViewController.contentDidFinishPlaying(_:)), name: NSNotification.Name.AVPlayerItemDidPlayToEndTime, object: player.currentItem); showContentPlayer() } ... @objc func contentDidFinishPlaying(_ notification: Notification) { adsLoader.contentComplete() } }
6. Initialiser le chargeur d'annonces et envoyer une demande d'annonces
Pour demander un ensemble d'annonces, vous devez créer une instance IMAAdsLoader
.
Ce chargeur peut être utilisé pour traiter les objets IMAAdsRequest
associés à une URL de balise publicitaire spécifiée.
Nous vous recommandons de ne conserver qu'une seule instance de IMAAdsLoader
pour l'ensemble du cycle de vie de votre application. Pour envoyer des demandes d'annonces supplémentaires, créez un objet IMAAdsRequest
, mais réutilisez le même IMAAdsLoader
. Pour en savoir plus, consultez les questions fréquentes sur le SDK IMA.
ViewController.m
Objective-C
... NSString *const kContentURLString = @"https://storage.googleapis.com/interactive-media-ads/media/stock.mp4"; NSString *const kAdTagURLString = @"https://pubads.g.doubleclick.net/gampad/ads?" @"iu=/21775744923/external/vmap_ad_samples&sz=640x480&" @"cust_params=sample_ar%3Dpremidpostlongpod&" @"ciu_szs=300x250&gdfp_req=1&ad_rule=1&output=vmap&unviewed_position_start=1&" @"env=vp&impl=s&cmsid=496&vid=short_onecue&correlator="; @interface ViewController () @property(nonatomic) IMAAdsLoader *adsLoader; @property(nonatomic) IMAAVPlayerContentPlayhead *contentPlayhead; @property(nonatomic) AVPlayerViewController *contentPlayerViewController; @end @implementation ViewController - (void)viewDidLoad { [super viewDidLoad]; self.view.backgroundColor = UIColor.blackColor; [self setupContentPlayer]; [self setupAdsLoader]; } - (void)viewDidAppear:(BOOL)animated { [super viewDidAppear:animated]; [self requestAds]; } - (void)setupAdsLoader { self.adsLoader = [[IMAAdsLoader alloc] init]; } - (void)requestAds { // Pass the main view as the container for ad display. IMAAdDisplayContainer *adDisplayContainer = [[IMAAdDisplayContainer alloc] initWithAdContainer:self.view]; IMAAdsRequest *request = [[IMAAdsRequest alloc] initWithAdTagUrl:kAdTagURLString adDisplayContainer:adDisplayContainer contentPlayhead:self.contentPlayhead userContext:nil]; [self.adsLoader requestAdsWithRequest:request]; } ... - (void)contentDidFinishPlaying:(NSNotification *)notification { // Notify the SDK that the postrolls should be played. [self.adsLoader contentComplete]; } ... @end
Swift
... class ViewController: UIViewController { static let ContentURLString = "https://storage.googleapis.com/interactive-media-ads/media/stock.mp4" static let AdTagURLString = "https://pubads.g.doubleclick.net/gampad/ads?iu=/21775744923/external/single_ad_samples&sz=640x480&cust_params=sample_ct%3Dlinear&ciu_szs=300x250%2C728x90&gdfp_req=1&output=vast&unviewed_position_start=1&env=vp&impl=s&correlator=" var adsLoader: IMAAdsLoader! var contentPlayhead: IMAAVPlayerContentPlayhead? var playerViewController: AVPlayerViewController! ... override func viewDidLoad() { super.viewDidLoad() self.view.backgroundColor = UIColor.black; setUpContentPlayer() setUpAdsLoader() } override func viewDidAppear(_ animated: Bool) { super.viewDidAppear(animated); requestAds() } ... func setUpAdsLoader() { adsLoader = IMAAdsLoader(settings: nil) } func requestAds() { // Create ad display container for ad rendering. let adDisplayContainer = IMAAdDisplayContainer(adContainer: self.view) // Create an ad request with your ad tag, display container, and optional user context. let request = IMAAdsRequest( adTagUrl: ViewController.AdTagURLString, adDisplayContainer: adDisplayContainer, contentPlayhead: contentPlayhead, userContext: nil) adsLoader.requestAds(with: request) } @objc func contentDidFinishPlaying(_ notification: Notification) { adsLoader.contentComplete() } }
7. Configurer un délégué de chargeur d'annonces
En cas de succès d'un événement de chargement, IMAAdsLoader
appelle la méthode adsLoadedWithData
de son délégué attribué, en lui transmettant une instance de IMAAdsManager
. Vous pouvez ensuite initialiser le gestionnaire d'annonces, qui charge les annonces individuelles, comme défini par la réponse à l'URL du tag d'annonce.
En outre, veillez à gérer les erreurs susceptibles de se produire lors du processus de chargement. Si les annonces ne se chargent pas, assurez-vous que la lecture multimédia continue, sans annonces, afin de ne pas perturber l'expérience utilisateur.
ViewController.m
Objective-C
... @interface ViewController () <IMAAdsLoaderDelegate> @property(nonatomic) IMAAdsLoader *adsLoader; @property(nonatomic) IMAAdsManager *adsManager; @property(nonatomic) IMAAVPlayerContentPlayhead *contentPlayhead; @property(nonatomic) AVPlayerViewController *contentPlayerViewController; @end @implementation ViewController ... - (void)setupAdsLoader { self.adsLoader = [[IMAAdsLoader alloc] init]; self.adsLoader.delegate = self; } ... #pragma mark - IMAAdsLoaderDelegate - (void)adsLoader:(IMAAdsLoader *)loader adsLoadedWithData:(IMAAdsLoadedData *)adsLoadedData { // Initialize and listen to the ads manager loaded for this request. self.adsManager = adsLoadedData.adsManager; [self.adsManager initializeWithAdsRenderingSettings:nil]; } - (void)adsLoader:(IMAAdsLoader *)loader failedWithErrorData:(IMAAdLoadingErrorData *)adErrorData { // Fall back to playing content. NSLog(@"Error loading ads: %@", adErrorData.adError.message); [self.contentPlayerViewController.player play]; } @end
Swift
... class ViewController: UIViewController, IMAAdsLoaderDelegate { ... var adsLoader: IMAAdsLoader! var adsManager: IMAAdsManager! var contentPlayhead: IMAAVPlayerContentPlayhead? var playerViewController: AVPlayerViewController! ... func setUpAdsLoader() { adsLoader = IMAAdsLoader(settings: nil) adsLoader.delegate = self } ... // MARK: - IMAAdsLoaderDelegate func adsLoader(_ loader: IMAAdsLoader!, adsLoadedWith adsLoadedData: IMAAdsLoadedData!) { adsManager = adsLoadedData.adsManager adsManager.initialize(with: nil) } func adsLoader(_ loader: IMAAdsLoader!, failedWith adErrorData: IMAAdLoadingErrorData!) { print("Error loading ads: " + adErrorData.adError.message) showContentPlayer() playerViewController.player?.play() } }
8. Configurer un délégué Ad Manager
Enfin, pour gérer les événements et les modifications d'état, le gestionnaire d'annonces a besoin de son propre délégué. IMAAdManagerDelegate
dispose de méthodes pour gérer les événements et les erreurs d'annonces, ainsi que pour déclencher la lecture et la mise en pause de votre contenu vidéo.
Démarrage de la lecture...
La méthode didReceiveAdEvent
peut gérer de nombreux événements, mais pour cet exemple de base, il vous suffit d'écouter l'événement LOADED
pour indiquer au gestionnaire d'annonces de commencer la lecture du contenu et des annonces.
ViewController.m
Objective-C
@interface ViewController () <IMAAdsLoaderDelegate, IMAAdsManagerDelegate> ... - (void)adsLoader:(IMAAdsLoader *)loader adsLoadedWithData:(IMAAdsLoadedData *)adsLoadedData { // Initialize and listen to the ads manager loaded for this request. self.adsManager = adsLoadedData.adsManager; self.adsManager.delegate = self; [self.adsManager initializeWithAdsRenderingSettings:nil]; } ... #pragma mark - IMAAdsManagerDelegate - (void)adsManager:(IMAAdsManager *)adsManager didReceiveAdEvent:(IMAAdEvent *)event { // Play each ad once it has loaded. if (event.type == kIMAAdEvent_LOADED) { [adsManager start]; } } ...
Swift
... class ViewController: UIViewController, IMAAdsLoaderDelegate, IMAAdsManagerDelegate { ... func adsLoader(_ loader: IMAAdsLoader!, adsLoadedWith adsLoadedData: IMAAdsLoadedData!) { // Grab the instance of the IMAAdsManager and set yourself as the delegate. adsManager = adsLoadedData.adsManager adsManager.delegate = self adsManager.initialize(with: nil) } ... // MARK: - IMAAdsManagerDelegate func adsManager(_ adsManager: IMAAdsManager!, didReceive event: IMAAdEvent!) { // Play each ad once it has been loaded if event.type == IMAAdEventType.LOADED { adsManager.start() } } ...
Traiter les erreurs
Ajoutez également un gestionnaire pour les erreurs d'annonces. Si une erreur se produit, comme à l'étape précédente, reprenez la lecture du contenu.
ViewController.m
Objective-C
... - (void)adsManager:(IMAAdsManager *)adsManager didReceiveAdError:(IMAAdError *)error { // Fall back to playing content. NSLog(@"AdsManager error: %@", error.message); [self showContentPlayer]; [self.contentPlayerViewController.player play]; } @end
Swift
... func adsManager(_ adsManager: IMAAdsManager!, didReceive error: IMAAdError!) { // Fall back to playing content print("AdsManager error: " + error.message) showContentPlayer() playerViewController.player?.play() }
Déclencher des événements de lecture et de mise en pause
Les deux dernières méthodes de délégué que vous devez implémenter permettent de déclencher des événements de lecture et de mise en pause sur le contenu vidéo sous-jacent, à la demande du SDK IMA. Le déclenchement de la mise en pause et de la lecture à la demande empêche l'utilisateur de manquer des parties du contenu vidéo lorsque des annonces sont diffusées.
ViewController.m
Objective-C
... - (void)adsManagerDidRequestContentPause:(IMAAdsManager *)adsManager { // Pause the content for the SDK to play ads. [self.contentPlayerViewController.player pause]; [self hideContentPlayer]; } - (void)adsManagerDidRequestContentResume:(IMAAdsManager *)adsManager { // Resume the content since the SDK is done playing ads (at least for now). [self showContentPlayer]; [self.contentPlayerViewController.player play]; } @end
Swift
... func adsManagerDidRequestContentPause(_ adsManager: IMAAdsManager!) { // Pause the content for the SDK to play ads. playerViewController.player?.pause() hideContentPlayer() } func adsManagerDidRequestContentResume(_ adsManager: IMAAdsManager!) { // Resume the content since the SDK is done playing ads (at least for now). showContentPlayer() playerViewController.player?.play() } }
Et voilà ! Vous demandez et affichez désormais des annonces avec le SDK IMA. Pour en savoir plus sur les fonctionnalités supplémentaires du SDK, consultez les autres guides ou les exemples sur GitHub.
Étapes suivantes
Pour maximiser les revenus publicitaires sur la plate-forme tvOS, demandez l'autorisation d'utiliser l'IDFA pour la transparence et le suivi des applications.