Schedule Google IMA ads (iOS v3)

Add advertising breaks to your content when using the Google IMA ad client in an iOS app.


🚧

As per Google, IMA SDK 3.11.3 will be the final version of the IMA SDK that supports iOS 9.x.

After adding the Google IMA SDK to your app and acquiring the required items listed in the Requirements section, you can schedule Google IMA ads in your iOS app.



Requirements



Add a pre-roll ad to a player

🚧

If you use the IAB Open Measurement Interface Definition (OMID) and run Google IMA ads, all custom video controls that overlay the media element must be registered as friendly obstructions.


Use the following steps to add a pre-roll ad to the player you added to your view:

  1. Instantiate a JWAdBreak object called adBreak. At a minimum, you must assign an ad tag URL to the tag property. Be sure that the ad tag URL is an absolute URL.
  2. Instantiate a JWAdConfig object and assign it to config.advertising.
  3. Define config.advertising.client as JWAdClientGoogima (Obj-C) or .googima (Swift). This defines the ad client.
  4. Add adBreak to the schedule array property of the JWAdConfig. This adds the ad schedule to the player's config property.
@property (nonatomic) JWPlayerController *player;
@property (nonatomic, weak) IBOutlet UIView *playerContainerView;
@end

@implementation ObjCViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    // Create the Ad Break
    JWAdBreak *adBreak = [JWAdBreak adBreakWithTag:ADTAG_URL offset:@"pre"];

    // Create the AdConfig
    JWAdConfig *adConfig = [JWAdConfig new];
    adConfig.client = JWAdClientGoogima;
    adConfig.schedule = @[adBreak];

    // Initialize the JWConfig and create the JWPlayerController
    JWConfig *config = [JWConfig configWithContentURL:CONTENT_URL];
    config.advertising = adConfig;

    self.player = [[JWPlayerController alloc] initWithConfig:config];
}

- (void)viewDidAppear {
    [super viewDidAppear];
    [self.view addSubview:self.player.view];
}
class ViewController: UIViewController {
    @IBOutlet weak var playerContainerView: UIView!
    var player: JWPlayerController?

    override func viewDidLoad() {
        super.viewDidLoad()

        // Create the Ad Break
        let adBreak = JWAdBreak(tag: ADTAG_URL, offset: "pre")

        // Create the AdConfig
        let adConfig = JWAdConfig()
        adConfig.client = .googima
        adConfig.schedule = [adBreak]

        // Initialize the JWConfig and create the JWPlayerController
        let config = JWConfig(contentURL: CONTENT_URL)
        config.advertising = adConfig

        player = JWPlayerController(config: config)
    }

    override func viewDidAppear(_ animated: Bool) {
        super.viewDidAppear(animated)
        playerContainerView.addSubview(player!.view)
    }
}

You can build upon this basic implementation by adding more ad breaks.



Add multiple ad breaks to a player

🚧

If you use the IAB Open Measurement Interface Definition (OMID) and run Google IMA ads, all custom video controls that overlay the media element must be registered as friendly obstructions.


Use the following steps to add multiple ad breaks to the previous pre-roll example:

  1. Instantiate an additional JWAdBreak object.
  2. Assign an ad tag to the tag property. Be sure that the ad tag URL is an absolute URL.
  3. When defining the offset property, choose one of the following values to schedule a mid-roll or post-roll ad.

    Mid-roll
    Β Β - {number}: (String) Ad plays after the specified number of seconds.
    Β Β - {timecode}: (String) Ad plays at a specific time, in hh:mm:ss:mmm format.

    Post-roll
    Β Β - post: (String) Ad plays after the content.

  4. Add the additional AdBreak object to the schedule array.
@property (nonatomic) JWPlayerController *player;
@property (nonatomic, weak) IBOutlet UIView *playerContainerView;
@end

@implementation ObjCViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    // Create the Ad Breaks
    JWAdBreak *adBreak = [JWAdBreak adBreakWithTag:ADTAG_URL offset:@"pre"];
    JWAdBreak *adBreak2 = [JWAdBreak adBreakWithTag:ADTAG2_URL offset:@"10"];
    JWAdBreak *adBreak3 = [JWAdBreak adBreakWithTag:ADTAG3_URL offset:@"00:00:15:000"];
    JWAdBreak *adBreak4 = [JWAdBreak adBreakWithTag:ADTAG4_URL offset:@"25%"];
    JWAdBreak *adBreak5 = [JWAdBreak adBreakWithTag:ADTAG5_URL offset:@"post"];

    // Create the AdConfig
    JWAdConfig *adConfig = [JWAdConfig new];
    adConfig.client = JWAdClientGoogima;
    adConfig.schedule = @[adBreak, adBreak2, adBreak3, adBreak4, adBreak5];

    // Initialize the JWConfig and create the JWPlayerController
    JWConfig *config = [JWConfig configWithContentURL:CONTENT_URL];
    config.advertising = adConfig;

    self.player = [[JWPlayerController alloc] initWithConfig:config];
}

- (void)viewDidAppear {
    [super viewDidAppear];
    [self.view addSubview:self.player.view];
}
class ViewController: UIViewController {
    @IBOutlet weak var playerContainerView: UIView!
    var player: JWPlayerController?

    override func viewDidLoad() {
        super.viewDidLoad()

        // Create the Ad Breaks
        let adBreak = JWAdBreak(tag: ADTAG_URL, offset: "pre")
        let adBreak2 = JWAdBreak(tag: ADTAG2_URL, offset: "10")
        let adBreak3 = JWAdBreak(tag: ADTAG3_URL, offset: "00:00:15:000")
        let adBreak4 = JWAdBreak(tag: ADTAG4_URL, offset: "25%")
        let adBreak5 = JWAdBreak(tag: ADTAG5_URL, offset: "post")

        // Create the AdConfig
        let adConfig = JWAdConfig()
        adConfig.client = .googima
        adConfig.schedule = [adBreak, adBreak2, adBreak3, adBreak4, adBreak5]

        // Initialize the JWConfig and create the JWPlayerController
        let config = JWConfig(contentUrl: CONTENT_URL)
        config.advertising = adConfig
        
        player = JWPlayerController(config: config)
    }

    override func viewDidAppear(_ animated: Bool) {
        super.viewDidAppear(animated)
        playerContainerView.addSubview(player!.view)
    }
}


FAQ

Why don't the ad breaks play when I build and run my project?

Check the output panel in XCode for the error displayed. One common error is "The resource could not be loaded because the App Transport Security policy requires the use of a secure connection".

You can resolve this issue by updating the info.plist file.

  1. From your project's target, open info.plist.
  2. Add a key named App Transport Security Settings as a Dictionary.
  3. Add a subkey named Allow Arbitrary Loads as a Boolean with a value set to YES.

You can also update the source code of info.plist:

<key>NSAppTransportSecurity</key>  
	<dict>  
		<key>NSAllowsArbitraryLoads</key>  
		<true/>  
	</dict>