iPhone – Adding Image to UIBarButtonItem

Update @ 2012-08-02: If you are using XCode 4.3 or above. You could following the instruction provided by S.Littlehales.

I found that if u set an image to the UIBarButtomItem directly, only the shape of the image is shown in the view without any color. If you want to add an button image to UIBarButtonItem, you have to create a UIButton and set it to the view of the UIBarButtonItem.

// Initialize the UIButton
UIImage *buttonImage = [UIImage imageNamed:@"buttonImage.png"];
UIButton *aButton = [UIButton buttonWithType:UIButtonTypeCustom];
[aButton setImage:buttonImage forState:UIControlStateNormal];
aButton.frame = CGRectMake(0.0, 0.0, buttonImage.size.width, buttonImage.size.height);

// Initialize the UIBarButtonItem
UIBarButtonItem aBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:aButton];

// Set the Target and Action for aButton
[aButton addTarget:self action:@selector(aButtonClicked:) forControlEvents:UIControlEventTouchUpInside];

// Then you can add the aBarButtonItem to the UIToolbar
...

// Don't need to release the buttonImage as suggested by Nicky
//[buttonImage release];

 

Don ‘t forget to create the aButtonClicked method

- (IBAction)aButtonClicked:(id)sender {
	// Button clicked logic
}

 

Done =)

Reference: Color image on a UIBarButtonItem on a UIToolBar?

Update @ 2011-09-22: Don’t need to release the buttonImage as suggested by Nicky. Thanks =)

17 thoughts on “iPhone – Adding Image to UIBarButtonItem”

  1. Hi ,

    I have a problem with uibarbutton, I need to add a button in toolbar with image ,
    and in response to the click on it I fire

    
    // at h 
    UIBarButtonItem * WindowWidthZoom;
    @property (nonatomic,retain) UIBarButtonItem * WindowWidthZoom;
    
    // at m 
    @synthesize  WindowWidthZoom;
    
    @try {
    		//create bottom toolbar using new
    		toolbar = [UIToolbar new];
    		 toolbar.barStyle = UIBarStyleBlackOpaque ;
    		[toolbar sizeToFit];
    		
    		//Create an array to hold the list of bar button items
    		NSMutableArray *items = [[NSMutableArray alloc] initWithCapacity:2];
    		
    		
    		//Add buttons
    		
    		//load the image
    		UIImage *buttonImage = [UIImage imageNamed:@"pan.png"];
    		//create the button and assign the image
    		UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
    		[button setImage:buttonImage forState:UIControlStateNormal];
    		//set the frame of the button to the size of the image (see note below)
    		button.frame = CGRectMake(0, 0, buttonImage.size.width, buttonImage.size.height);
    		//create a UIBarButtonItem with the button as a custom view
    		WindowWidthZoom = [[UIBarButtonItem alloc]  initWithCustomView:button  ];
    		WindowWidthZoom.target = self; 
    		WindowWidthZoom.action = @selector(WWL:);
    		
    		//[WindowWidthZoom addTarget:self action:@selector(WWL:)  ];
    		[items addObject:WindowWidthZoom ];
    		
    		
    		UIBarButtonItem *flexItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace
    																				  target:nil
    																				  action:nil];
    		[items addObject:flexItem];
    		
    		toolbar.items = items;
    		
    		
    		
    
    		
    		//add array of buttons to toolbar
    		//[toolbar setItems:items ];
    		
    		// let it be visible 
    		[self setToolbarItems:items];
    		[[self navigationController] setToolbarHidden:NO animated:NO];
    		
    		//release buttons
    		[WindowWidthZoom release];
    		
    		//[SendMail release];
    		
    		[flexItem release];
    		[items release];
    		
    		
    	}
    	@catch (NSException * e) {
    		
    		
    		 
    	}
    	@finally {
    		 
    	}
     
    		
    - (void) WWL:(id)sender{
    	
    	 UIBarButtonItem *barButton = (UIBarButtonItem *)sender;
    	
    	if(zooming)
    	{
    		
    		 barButton.image = [UIImage imageNamed:@"ww.png"];
    		 
    		zooming = NO ;
    	}
    	else {
    		barButton.image = [UIImage imageNamed:@"pan.png"];
    		zooming = YES ;
    	}
    	
    	
    }
    
    

    the uibarbutton not fire the WWL

    Like

    1. I am not sure if i am correct or not. but it seems that you didn’t hook the button click action to the event at all.

      i guess sth like

      [aButton addTarget:self action:@selector(aButtonClicked:) forControlEvents:UIControlEventTouchUpInside];
      

      is missing.

      Like

      1. you’re right

        it worked but I need if I clicked this uibarbuttonitem , its image be changed

        – (void) WWL:(id)sender{

        //WindowWidthZoom is the uibarbuttonitem
        WindowWidthZoom.image = [UIImage imageNamed:@”ww.png”];

        }

        do u have any suggestion how to change the image

        Like

      2. You cannot change the image of the UIBarButtonItem directly.

        Actually just like your code did, the image of the button belongs to the UIButton. I think you have to get the UIButton from the UIBarButtonItem first. Then change the UIButton image.

        Like

  2. hi ,
    I have a problem ,I created a spilt view-base controller project,I cannot use your way to modify the UIbarbuttonItem because I cannot find write aButton’s action.
    can u provide a idea?

    Like

    1. do you mean u cannot link the click action to the UIBarButtonItem?

      You need to wire them in the Interface Builder.

      Like

  3. Read the doc on UIBarButtonItem carefully: the image is not simply an image, only the ALPHA VALUES are used to compose the image.

    Like

  4. Hi, It seems that all the above is no longer necessary in Xcode 4.3.
    You can achieve a bar button item with a custom image simply by:
    1. Drag a UIButton onto the storyboard.
    2. Set the button Type to Custom and set your image for that button.
    3. Drag the button onto your Toolbar.

    The storyboard automatically creates a UIBarButtonItem and adds your UIButton as a subview.
    Job done.
    You should be able to hook up events to the UIButton.
    Note that the button image name supports all the conventions for automatic selection of retina images etc.

    Like

    1. Thanks for your comment. I haven’t done any iOS development in the past 2 years so probably the information provided in this blog may be outdated.

      Thanks again. =)

      Like

    2. This definitely works, but in the case where a developer would like to add a popover to that button, it creates a problem, because the button’s properties with respect to this are still identified by the compiler as that of a UIButton and not as that of a UIBarButton item. So even if you were to hook up the Action for the popover, the program will crash during run time.

      Like

      1. Thanks for your comment Aditya. So do you mean if we use the approach suggested by S.Littlehales. We could not create the popover action?

        Like

      2. Hi Aditya,

        Hook the “Touch Up Inside” event of your UIButton (not the UIBarButtonItem) to call an action method in your controller. Pass the UIButton as the sender, then use [Popover presentPopoverFromRect:[sender frame]] rather than presentPopoverFromBarButtonItem. This works fine.

        If you need to reposition the Popover after a rotation, you can also hook up your UIButton to an outlet variable and simply use presentPopoverFromRect:self.myButton.frame to re-present it.

        It would be better if the parent UIBarButtonItem was triggered when the user presses the embedded UIButton – but this method still seems simpler and more manageable than all the code that was previously needed (to me anyway!).

        Like

Leave a comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.