Invalid Memory
Invalid Memory

Reputation: 737

Making a UIButton change a UIImageView image

I'm very new to programming and objective c so please go easy on me.

I would like a UIButton (which I'm using as an IBAction) to change an the image in a UIImageView when pressed. I put the UIImageView into a UIScrollView in the storyboard but I hope I can still programmatically change the image.

I have searched absolutely everywhere for an answer for hours but nothing has worked for me either because it wasn't the right solution or I didn't do it properly.

I have tried this code and some more but they always return a "Thread 1: signal SIGABRT" when I press the button:

imageView.image = [UIImage imageNamed: @"Ruler pic inch.png"];

Here is my code so far:

ViewController.h

#import <UIKit/UIKit.h>
#import <iAd/iAd.h>

@interface ViewController : UIViewController <ADBannerViewDelegate, UIScrollViewDelegate>      {

ADBannerView *adView;
BOOL bannerIsVisible;
IBOutlet UIScrollView *scrollView;
IBOutlet UIImageView *imageView;
IBOutlet UIButton *proVersion;
IBOutlet UIButton *howToUse;

}

- (IBAction)switchUnit:(id)sender;

@property (nonatomic, assign) BOOL bannerIsVisible;
@property (nonatomic, retain) IBOutlet UIScrollView *scrollView;
@property (nonatomic, retain) IBOutlet UIImageView *imageView;

@end

ViewController.m

#import "ViewController.h"

@interface ViewController ()

@end

@implementation ViewController

@synthesize bannerIsVisible;
@synthesize scrollView;
@synthesize imageView;


- (void)viewDidLoad
{
[super viewDidLoad];

// Hide status bar:
[[UIApplication sharedApplication] setStatusBarHidden:YES];

// iAd:
adView = [[ADBannerView alloc] initWithFrame:CGRectZero];
adView.frame = CGRectOffset(adView.frame, 0, -50.0f);
[self.view addSubview:adView];
adView.delegate=self;
self.bannerIsVisible=NO;

// Setting scrollview content size to size of image
scrollView.contentSize = CGSizeMake(320,2246);

}

-(void)bannerViewDidLoadAd:(ADBannerView *)banner
{
if (!self.bannerIsVisible) {

    [UIView beginAnimations:@"animateAdBannerOn" context:NULL];
    banner.frame = CGRectOffset(banner.frame, 0, 50.0f);
    [UIView commitAnimations];
    self.bannerIsVisible = YES;

    }
}

-(void)bannerView:(ADBannerView *)banner didFailToReceiveAdWithError:(NSError *)error
{
if (self.bannerIsVisible) {

    [UIView beginAnimations:@"animateAdBannerOff" context:NULL];
    banner.frame = CGRectOffset(banner.frame, 0, -50.0f);
    [UIView commitAnimations];
    self.bannerIsVisible = NO;

    }
}

- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}


- (IBAction)switchUnit:(id)sender {

// CODE THAT MAKES IMAGE CHANGE GOES HERE (I thought...)

}

@end

Help would be greatly appreciated. I'm fed up with it. I've probably done a silly mistake somewhere but I can't work it out. Thanks in advance.

Upvotes: 1

Views: 990

Answers (1)

Wain
Wain

Reputation: 119041

General pointers:

  1. Try to use @property for all your instance variables (it'll server you well in future)
  2. Don't use @synthesize (the compiler does a better job of it for you)
  3. If you have a property bob, access it by using self.bob
  4. Turn on ARC (looks like you don't have it on currently)
  5. Best not to have any spaces in image names

To be clear on properties, when you have a property you don't need to create instance variables in between {} of the @interface. These should be removed in order to prevent multiple definitions. The auto-synthesising done by the compiler will define the instance variables for you but you should always use the property to access the value (as in item 3 above).

That said, your - (IBAction)switchUnit:(id)sender looks fine, if a little empty. The code should be something like:

self.imageView.image = [UIImage imageNamed:@"Ruler_pic_inch.png"];

For it to work, the image Ruler_pic_inch.png would need to be in your bundle (which means it's in Xcode project and set to copy during the build.

Again, that said, your problem would seem to relate to you being confused somewhere. SIGABRT type issues would usually be picked up by the compiler and notified to you as a warning saying something like "some object may not respond to some selector". If you see any of those, look at them and work out why you're trying to ask the object a question it doesn't understand.

If you don't see any compiler warnings, then you've told the compiler that an object is going to be of one type and then actually set it to something else. In this case I'd look at your IBOutlets in Storyboard and check that they are actually set to the correct destination view (disconnect and reconnect them all to be sure).

Upvotes: 2

Related Questions