View controllers in iOS such as UITabBarController and UINavigationController allow users to navigate between screens quickly. Developers using these controllers often hesitate to create new GADBannerViews for each screen because the user may not spend enough time on each screen to see the ad, thus diluting their click-through rate (CTR). A nice alternative here is to use a singleton GADBannerView across the entire application. This blog post will outline the steps to get this up and running.
Initialization
Create a class that wraps around GADBannerView to add some minimal functionality. We’ll call this class GADMasterViewController in our example. Define your header file to have properties similar to what’s below:
@interface GADMasterViewController : UIViewController {
GADBannerView *adBanner_;
BOOL didCloseWebsiteView_;
BOOL isLoaded_;
id currentDelegate_;
}
You need to provide a static accessor method in your GADMasterViewController class:
+(GADMasterViewController *)singleton {
static dispatch_once_t pred;
static GADMasterViewController *shared;
// Will only be run once, the first time this is called
dispatch_once(&pred, ^{
shared = [[GADMasterViewController alloc] init];
});
return shared;
}
You also need an init: method in GADMasterViewController. You can now initialize the GADBannerView normally. Presume the initialization gets called only once:
-(id)init {
if (self = [super init]) {
adBanner_ = [[GADBannerView alloc]
initWithFrame:CGRectMake(0.0,
0.0,
GAD_SIZE_320x50.width,
GAD_SIZE_320x50.height)];
// Has an ad request already been made
isLoaded_ = NO;
}
return self;
}
Placing the Ad
Write a method which takes a new view controller and places the GADBannerView into that view controller’s view hierarchy. Again, this code will go into GADMasterViewController. This will be called every time you want to display an ad inside a different view controller:
-(void)resetAdView:(UIViewController *)rootViewController {
// Always keep track of currentDelegate for notification forwarding
currentDelegate_ = rootViewController;
// Ad already requested, simply add it into the view
if (isLoaded_) {
[rootViewController.view addSubview:adBanner_];
} else {
adBanner_.delegate = self;
adBanner_.rootViewController = rootViewController;
adBanner_.adUnitID = kSampleAdUnitID;
GADRequest *request = [GADRequest request];
[adBanner_ loadRequest:request];
[rootViewController.view addSubview:adBanner_];
isLoaded_ = YES;
}
}
At this point, putting an ad into a view that’s not the GADMasterViewController becomes extremely easy. The code can go into any view controller’s viewWillAppear: method (assuming the view conforms to the GADBannerViewDelegate protocol):
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
shared = [GADMasterViewController singleton];
[shared resetAdView:self];
}
Forwarding Delegate Notifications
An important note is that the AdMob SDK doesn’t let you change delegates after a request has been made. This means that if you switch view controllers after making an ad request, all GADBannerViewDelegate notifications will continue to be sent to the initial delegate (first view controller). A workaround for this is to make GADMasterViewController conform to the GADBannerViewDelegate protocol, then forward any notifications it receives to the correct view controller. This is the reasoning behind always setting currentDelegate_ in resetAdView: . Forwarding the notification takes minimal code. Here is an example of forwarding the adViewDidReceiveAd: notification:
- (void)adViewDidReceiveAd:(GADBannerView *)view {
// Make sure that the delegate actually responds to this notification
if ) {
[currentDelegate_ adViewDidReceiveAd:view];
}
}
With these easy steps, your application is set up to use a singleton GADBannerView. If you have any questions about this topic or the SDK in general, feel free to post them in our forum or come join us in our upcoming office hours .
- Raj Parameswaran , AdMob Team