iads help

Hi,
I have been working on an app with codea and now, thanks to all the tutorials and examples of the people on this forum, it is nearly complete! :slight_smile:
However, I am stuck with implementing the iAds for my app. I used the tutorial from @reefwing from http://codeatuts.blogspot.com.au/2013/04/tutorial-29-codea-v152-objective-c-add.html but when researching how to make it compatible with landscape and iphones I came across the canDisplayBannerAds=YES; function and managed to get the iads working by adding

self.currentController.canDisplayBannerAds=YES;

in the

- (void) codea:(CodeaViewController*)controller didCreateLuaState:(struct lua_State*)L

method. But now I am trying to add the option to remove ads through an in-app purchase but cannot wrap my head around how to remove it using the showAdFromBottom() (or top, it does not matter for my app) and hideAd() functions. I tried to get it working earlier today (as well as remove the duplicate code from the tutorial since I replaced it with canDisplayBannerAds=YES) but ended up making it so the ads don’t work at all :frowning: . here is the source code for iAdsAddon.m:

//
//  IAdsAddon.m
//  AcornMayhem
//
//  
//  Copyright (c) 2014 MyCompany. All rights reserved.
//
//

#import "lua.h"
#import "IAdsAddOn.h"

@implementation IAdsAddOn

#pragma mark - Initialisation

- (id)init
{
    self = [super init];
    if (self)
    {
        //  audioAddOnInstance allows us to access self from within the c functions.
        
        iAdsAddOnInstance = self;
        
        // Initialise our Instance Variables
        
        _isBannerVisible = NO;
        _showBannerFromTop = YES;//YES;
        //  Initialise our iAd Banner View
        
        
        CGRect frame = CGRectZero;
        //frame.size = [ADBannerView sizeFromBannerContentSizeIdentifier: ADBannerContentSizeIdentifierPortrait];
        [_bannerView setAutoresizingMask:UIViewAutoresizingFlexibleWidth];   //replacement for above depricated
        
        
        //[_bannerView setAutoresizesSubviews:YES];//  remove if not working //does not work
        //[_bannerView setAutoresizingMask:     //    does not work
        // UIViewAutoresizingFlexibleWidth |    // does not work
        // UIViewAutoresizingFlexibleTopMargin];    //alternate for next line
        //UIViewAutoresizingFlexibleHeight];   //  does not work
        
        
        _bannerView = [[ADBannerView alloc] initWithFrame: frame];
        //_bannerView.requiredContentSizeIdentifiers = [NSSet setWithObject: ADBannerContentSizeIdentifierPortrait];
        
        _bannerView.delegate = self;
    }
    return self;
}

#pragma mark - CodeaAddon Delegate

//  Classes which comply with the <CodeaAddon> Protocol must implement this method

- (void) codea:(CodeaViewController*)controller didCreateLuaState:(struct lua_State*)L
{
    NSLog(@"iAdAddOn Registering Functions");
    
    //  Register the iAd functions, defined below
    
    lua_register(L, "showAdFromTop", showAdFromTop);
    lua_register(L, "showAdFromBottom", showAdFromBottom);
    lua_register(L, "hideAd", hideAd);
    
    //  Hook up with the CodeaViewController - don't try to add subviews in this method.
    self.currentController = controller;
    if(_showBannerFromTop==YES){
        self.currentController.canDisplayBannerAds=YES;//this one line replaces the rest of the file ///////////////////
    }else{
        self.currentController.canDisplayBannerAds=NO;
    }
}

#pragma mark - iAds Add On Functions and associated Methods

//  Objective C Methods

/*- (void)showBannerViewAnimated:(BOOL)animated
{
    if ([self.bannerView isBannerLoaded])
    {
        //  We only display the banner View if it has ads loaded and isn't already visible.
        //  Set the banner view starting position as off screen.
        
        CGRect frame = _bannerView.frame;
        
        if (_showBannerFromTop)
            frame.origin.y = 0.0f - _bannerView.frame.size.height;
        else
            frame.origin.y = CGRectGetMaxY(self.currentController.view.bounds);
        
        _bannerView.frame = frame;
        
        // Set banner View final position to animate to.
        
        if (_showBannerFromTop)
            frame.origin.y = 0;
        else
            frame.origin.y -= frame.size.height;
        
        if (animated)
            [UIView animateWithDuration: 0.5 animations: ^{self.bannerView.frame = frame;}];
        else
            self.bannerView.frame = frame;
        
        _isBannerVisible = YES;
    }
    else
        NSLog(@"showBannerViewAnimated: Unable to display banner, no Ads loaded.");
}*/

/*- (void)hideBannerViewAnimated:(BOOL)animated
{
    if (_isBannerVisible)
    {
        CGRect frame = self.bannerView.frame;
        
        if (_showBannerFromTop)
            frame.origin.y -= frame.size.height;
        else
            frame.origin.y = CGRectGetMaxY(self.currentController.view.bounds);
        
        if (animated)
            [UIView animateWithDuration: 0.5 animations: ^{self.bannerView.frame = frame;}];
        else
            self.bannerView.frame = frame;
        
        _isBannerVisible = NO;
    }
}*/

//  C Functions
//
//  Note that the returned value from all exported Lua functions is how many values that function should return in Lua.
//  For example, if you return 0 from that function, you are telling Lua that function returns 0 values.
//  If you return 2, you are telling Lua to expect 2 values on the stack when the function returns.
//
//  To actually return values, you need to push them onto the Lua stack and then return the number of values you pushed on.

static int showAdFromTop(struct lua_State *state)
{
    [iAdsAddOnInstance setShowBannerFromTop: YES];
    //[iAdsAddOnInstance showBannerViewAnimated: YES];
    
    return 0;
}

static int showAdFromBottom(struct lua_State *state)
{
    [iAdsAddOnInstance setShowBannerFromTop: YES];
    //[iAdsAddOnInstance showBannerViewAnimated: YES];
    
    return 0;
}

static int hideAd(struct lua_State *state)
{
    //[iAdsAddOnInstance hideBannerViewAnimated: YES];
    //self.currentController.canDisplayBannerAds=NO;
    [iAdsAddOnInstance setShowBannerFromTop: NO];
    return 0;
}

#pragma mark - iAd Banner View Delegate

//  Your application implements this method to be notified when a new advertisement is ready for display.

- (void)bannerViewDidLoadAd:(ADBannerView *)banner
{
    NSLog(@"Banner View loaded Ads for display.");
    NSLog(@"Active View Controller: %@", self.currentController.class);
    
    //  Add our banner view to the CodeaViewController view, if we haven't already.
    
    if(_showBannerFromTop==YES){
   // if (![self.currentController.view.subviews containsObject: _bannerView])
    //    [self.currentController.view addSubview: _bannerView];
        self.currentController.canDisplayBannerAds=YES;
        //[self showBannerViewAnimated: YES];
    }else{
        self.currentController.canDisplayBannerAds=NO;
    }
}

//  This method is triggered when an advertisement could not be loaded from the iAds system
//  (perhaps due to a network connectivity issue).

/*- (void)bannerView:(ADBannerView *)banner didFailToReceiveAdWithError:(NSError *)error
{
    NSLog(@"bannerview failed to receive iAd error: %@", [error localizedDescription]);
    self.currentController.canDisplayBannerAds=NO;
    //[self hideBannerViewAnimated: YES];
}
*/
//  This method is triggered when the banner confirms that an advertisement is available but before the ad is
//  downloaded to the device and is ready for presentation to the user.

- (void)bannerViewWillLoadAd:(ADBannerView *)banner
{
    
}

//candisplaybannerads clicked



//  This method is triggered when the user touches the iAds banner in your application. If the willLeave argument
//  passed through to the method is YES then your application will be placed into the background while the user is
//  taken elsewhere to interact with or view the ad. If the argument is NO then the ad will be superimposed over your
//  running application.

- (BOOL)bannerViewActionShouldBegin:(ADBannerView *)banner willLeaveApplication:(BOOL)willLeave
{
    self.currentController.paused = YES;
    NSLog(@"Ad being displayed - Codea paused.");
    
    return YES;
}

//  This method is called when the ad view removes the ad content currently obscuring the application interface.
//  If the application was paused during the ad view session this method can be used to resume activity.

- (void)bannerViewActionDidFinish:(ADBannerView *)banner
{
    self.currentController.paused = NO;
    NSLog(@"Ad dismissed - Codea running.");
}

@end

how can I fix this?
thanks,
~patrick

I think that @Reefwing’s tutorials were made a while ago and since then some things have been deprecated. I would recommend @Zoyt’s Obj-C add-ons, as they are a bit more recent.

I have used @zoyt 's add on for in app purchases, but I can’t find one for iAds. I am basically replacing the iAds code with the new version

MyViewController *myViewController = ...
myViewController.canDisplayBannerAds = YES;

(above from apple pdf about iads (pg 61) here: https://developer.apple.com/videos/wwdc/2014/#222 )
the main problem is I don’t know what to do for the “myViewController” part of it :frowning: .

@pleiser - sorry yes Apple keep updating their code!

This issue has come up before - have a look at:

http://codea.io/talk/discussion/comment/44640#Comment_44640

Let me know if you are still stuck after that.

There’ a lot of request for and iAd add on, so I might right one and implem it in StackIt.

@pleiser, I believe that library does not work for hiding ads because as soon as a new ad is loaded, it gets shown whether you called hideAd or not. (@Reefwing correct me if I am wrong)

I had the same problem and I fixed it. Here is my version: https://www.dropbox.com/sh/ct6clt8mwm8gt06/AAAdFS12AquUZOz8fJ2ULTbra

All the commands are the same, however when you call hideAd (or you just never call showAd) no more ads will be shown. So, if someone has bought (or buys) your iAP simply call hideAd and they won’t show.

@Zoyt, this does everything I can see you needing for iAds, so you shouldn’t have to make a new one.

@JakAttak. I was having that same problem where the iAd wouldn’t go away after being displayed on my main menu. Do you mind if I use your code to implement the iAds in my app? Also, say I just wanted to hide the iAd temporarily, want would be the correct function to call? Thanks!

@YoloSwag, sure feel free to use it. If you just want the iAds gone temporarily, call hideAd and when you want them back call one of the showAd functions.

@JakAttak. Where would I call such a function? Because, I can’t call it in the draw() function.

Generally in a callback or in setup, I can’t think of any other cases you would need one.

@JakAttak. I’m having a problem where i can’t put the showAdFromBottom() or showAdFromTop() inside the touch function. Is there a function that could only be called once a variable changes, so when I transition from an about screen to a menu, the ad would show?

@YoloSwag, it should work from within touched as long as you only call it once. Mind posting your touched function?

@JakAttak.
Sorry, i didn’t see your post until now. I’ve actually gotten everything to work for my app, except when I start my device in landscape mode, the iAd banner doesn’t fill up all the way, and seems to be taking up the portrait’s width instead. Do you know how to fix this?

I have managed to refresh the ad and then it takes up the correct width, but i am using the orientation changed function, so now the only instance where it doesn’t take up the correct width is right after startup. Thanks so much!

I have also found this on Apples website and added the y variable, but its not getting called inside IAdAddon.m

int y = 0;
- (void) adjustViewsForOrientation:(UIInterfaceOrientation) orientation {
    
    if (orientation == UIInterfaceOrientationPortrait || orientation == UIInterfaceOrientationPortraitUpsideDown)
    {
        //load the portrait view
         y = 1;

    }
    else if (orientation == UIInterfaceOrientationLandscapeLeft || orientation == UIInterfaceOrientationLandscapeRight)
    {
        //load the landscape view
        y=2;

        
    }
}

@YoloSwag, im not sure about the resizing. which iAd add on are you using? I believe some of them (mine included) have the line for auto resizing banners. But I could be wrong as I lock my apps in one orientation

@JakAttak, I’m using both the portrait and landscape. I see the code for the auto-resizing, but it only takes effect after an orientation change. Otherwise, starting out the iPad in landscape mode will cause ads to remain the same size as in portrait mode.

Btw, during an orientation change I always refresh the ad by calling the showAd function because otherwise it doesn’t go to the correct position (either going too high or too low and out of view).

@JakAttak. I have fixed the issue.

If you want the iAds to automatically adjust to landscape view you need some code in the iAdsAddOn.m class. I have posted the modified code below, and this allows iAds in landscape orientation to properly show the correct width size because before the banner would show the portrait width when starting your device out in landscape mode.

Hope this helps anyone trying to add iAd support!

- (id)init
{
    self = [super init];
    if (self)
    {
        
        iAdsAddOnInstance = self;

        
        _isBannerVisible = NO;
        _showBannerFromTop = YES;
        _adsAllowed = NO;
        
        
        CGRect frame = CGRectZero;

        
        _bannerView = [[ADBannerView alloc] initWithFrame: frame];

        [_bannerView setAutoresizingMask: UIViewAutoresizingFlexibleWidth];
        _bannerView.delegate = self;

//Added Code
/////////////
          if (UIDeviceOrientationIsLandscape([UIDevice currentDevice].orientation))
    {
       _bannerView.currentContentSizeIdentifier = ADBannerContentSizeIdentifierLandscape;
    }
        
    
    else {
        _bannerView.currentContentSizeIdentifier = ADBannerContentSizeIdentifierPortrait;
    }
//End of Added Code
/////////////


    }
    return self;
}

@YoloSwag, nice! I never noticed because my app starts in portrait.

if (UIInterfaceOrientationIsLandscape([[UIApplication sharedApplication] statusBarOrientation]))

This is actually a better way to write that if statement. Both should work, but in case that one above doesn’t, this one will fix any errors.

i succeeded to get iads working in landscape correctly in the simulator using the @yoloSwag and @JakAttak code- thanks a lot guys!

i notice that xcode generates warning messages on your modification-“first depreciated in io6”