Placement of navigation bar buttons - ios

I am making an iPhone app and I have a UINavigationController as my root view and then UIVIewControllers from this. My Register button segues to the registration screen which automatically creates a Navigation Bar for me with the back button on the top left.
I have replaced the standard back button with my own image with the code below:
UIImage *backImage = [UIImage imageNamed:#"customBackButton.png"];
UIButton *backButton = [UIButton buttonWithType:UIButtonTypeCustom];
backButton.frame = CGRectMake(0, 0, 100, 70);
[backButton setImage:backImage forState:UIControlStateNormal];
[backButton addTarget:self action:#selector(popNavigationController:) forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *backBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:backButton] ;
self.navigationItem.leftBarButtonItem = backBarButtonItem;
I have also added a rightBarButtonItem to test but my issue is however that both these buttons arent in the corners of the screen as can be seen here.
Most other apps have the navigation bar buttons right in the corners as can be seen here from another app I found online as reference
I have tried to change the values here but that does nothing - the buttons stay where they are.
// Changing frames x-coordinate
backButton.frame = CGRectMake(-220, 0, 100, 70);
What do I need to do to set the buttons right in the corners of the navigation bar?
EDIT: If I use [backButton sizeToFit]; my image is displayed as below (the top grey bar is the navigation bar). Do I need to make the image the correct size?

If you want to change position of UIBarButtonItem you should use fake bar items as spacers
UIBarButtonItem *negativeSpacer = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace target:nil action:nil];
negativeSpacer.width = -10;
Now you can set the array of bar items to achieve result needed
self.navigationItem.leftBarButtonItems = #[negativeSpacer, backBarButtonItem];

The width of the buttons is too large. Remove this line:
backButton.frame = CGRectMake(0, 0, 100, 70);
and then call
[backButton sizeToFit];
after
[backButton setImage:backImage forState:UIControlStateNormal];
If this doesn't work, it's possible that there is white space baked into the PNG images themselves.

Have you tried cropping the image you're using (customBackButton.png) to get rid of any transparent margins? It looks like the image might be a little wide. Then you could decrease the width from 100px to something smaller and things should fit better.

Related

iOS: Weird overlay on LeftBarButtonItem on Transition

I have a little problem using the navigation bar in an iOS project using objective-c.
I have some view controllers which are managed by a navigationviewcontroller, in a hierarchy like 1-2-3.
For the Viewcontrollers 2 and 3, I define custom back buttons in the viewWillAppear function, as I need to assign them a more complex logic when touching them. This is the reason why I do not set the back buttons in the previous view controller.
Everything works fine like this, my single problem is that, on transition from one view to another, the arrow of the back button is overlayed by a little view in the color of the navigation bar's background color until up to 50%, and then disappears when the transition has finished.
I create my back buttons in the navigationbar with this function, which is called in viewWillAppear:
- (void)setupCustomBackButton:(NSString *)title
action:(SEL)action
buttonFrame:(CGRect)buttonFrame {
UIButton *backButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
backButton.frame = buttonFrame;
[backButton setImage:[UIImage imageNamed:#"backArrowOwn"] forState:UIControlStateNormal];
backButton.imageEdgeInsets = UIEdgeInsetsMake(0.0f, -8.0f, 0.0f, 0.0f);
[backButton setTitle:title forState:UIControlStateNormal];
[backButton.titleLabel setFont:[UIFont systemFontOfSize:17.0]];
backButton.titleEdgeInsets = UIEdgeInsetsMake(0.0f, -3.0f, 0.0f, 0.0f);
[backButton setContentHorizontalAlignment:UIControlContentHorizontalAlignmentLeft];
[backButton addTarget:self action:action forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *barButton = [[UIBarButtonItem alloc] initWithCustomView:backButton];
self.navigationItem.leftBarButtonItem = barButton;
}
I hope that maybe someone has a good hint for me! Thanks!
After some long trying, I finally managed to save the problem on my own.
So basically, when I create a leftBarButton, the button does not begin at the left margin, but has some space to the left margin. When I now inset my button image with a negative inset, the image will be basically outside my button frame. This portion is then weirdly overlayed on transition.
To fix this, I just add another UIBarButtonItem additionally to my leftBarButtonItems. This seems to fix the issue for me, although I do not really know why exactly.
Also, I think that it is weird that the leftBarButton in the navigationBar does not begin exactly at the margin, but has a space to the margin and I have to inset my image in order to get the exact same position for the image, as the default back button has.
My new code for creating a custom back button now looks like this:
- (void)setupCustomBackButton:(NSString *)title
action:(SEL)action
buttonFrame:(CGRect)buttonFrame {
UIButton *backButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
backButton.frame = buttonFrame;
[backButton setImage:[UIImage imageNamed:#"customBackArrow"] forState:UIControlStateNormal];
backButton.imageEdgeInsets = UIEdgeInsetsMake(0.0f, -8.0f, 0.0f, 0.0f);
[backButton setTitle:title forState:UIControlStateNormal];
[backButton.titleLabel setFont:[UIFont systemFontOfSize:17.0]];
backButton.titleEdgeInsets = UIEdgeInsetsMake(0.0f, -3.0f, 0.0f, 0.0f);
[backButton setContentHorizontalAlignment:UIControlContentHorizontalAlignmentLeft];
[backButton addTarget:self action:action forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *barButton = [[UIBarButtonItem alloc] initWithCustomView:backButton];
UIBarButtonItem *negativeSpacer = [[UIBarButtonItem alloc]
initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace
target:nil action:nil];
self.navigationItem.leftBarButtonItem = nil;
[self.navigationItem setLeftBarButtonItems:[NSArray arrayWithObjects:negativeSpacer,barButton, nil] animated:NO];
}
Thanks everyone and I hope that my answer helps anyone else too!
Try to move the custom button initialization to the viewDidLoad method.

navigating bar item icon not showing correctly

navigation bar item icon colour blue or single colour. Not able to render the original image in the navigation bar. already tried the option render as original from the Assets.xcassets attributes inspector
want to use thisimage
but sadly when tried selecting through storyboard it shows it in only one single colour square i.e only blue , white or any other colour. how can i use the original image for bar button item.
As per my understanding, you want to set image on navigation bar right ?
Hope below code will wok for you,
UIImage *myImage = [UIImage imageNamed:#"myImageName.png"];
myImage = [myImage imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
UIBarButtonItem *searchButton = [[UIBarButtonItem alloc] initWithImage:myImage style:UIBarButtonItemStylePlain target:self action:#selector(menuObject:)];
self.navigationItem.leftBarButtonItem = searchButton;
Try this ...
This one works for me...
UIButton *btnChat = [[UIButton alloc]initWithFrame:CGRectMake(0, 0, 30, 30)];
[btnChat setBackgroundImage:[UIImage imageNamed:#"chat_icon.png"] forState:UIControlStateNormal];
[btnChat addTarget:self action:#selector(chatButtonClicked) forControlEvents:UIControlEventTouchUpInside];
self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc]initWithCustomView:btnChat];

UINavigationBar barButtonItem change back button image and title

Is it possible to change the back button on a UINavigationBar and change the title?
When I try to set the customView property, I get an image right next to the default button.
I use this code
self.navigationItem.backBarButtonItem = [[UIBarButtonItem alloc] initWithImage:backButtonImage landscapeImagePhone:nil style:UIBarButtonItemStylePlain target:nil action:nil];
I want the title to be "Back" which is easy enough to do in Storyboard. But the problem is that no matter if I use code above or use customView property, the default back button remains.
You can add a UIImage to the UIButton. And, then use it as a custom back button. Here's a quick example:
// Custom image
UIImage *backButtonImage = [UIImage imageNamed:#"button-background-image.png"];
UIButton *backButton = [UIButton buttonWithType:UIButtonTypeCustom];
[backButton setFrame:CGRectMake(0, 0, 100, 30)];
[backButton setBackgroundImage:backButtonImage forState:UIControlStateNormal];
// Custom title
[backButton setTitle:#"Back" forState:UIControlStateNormal];
[backButton setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
[backButton addTarget:self action:#selector(barPayButtonPressed:) forControlEvents:UIControlEventTouchUpInside];
[backButton setShowsTouchWhenHighlighted:NO];
UIBarButtonItem *buttonOnBar =[[UIBarButtonItem alloc] initWithCustomView:backButton];
self.navigationItem.leftBarButtonItem = buttonOnBar;
Note: You will loose the chevron (system-provided back arrow) which was introduced in iOS7. It goes as a title and chevron together presenting your previous view controller.
Update:
You can also use UIEdgeInsets to resize your image intelligently.
UIEdgeInsets edgeInsets = UIEdgeInsetsMake(0, 0, 15, 10);
UIImage *backButtonImage = [[UIImage imageNamed:#"button-background-image.png"] resizableImageWithCapInsets:edgeInsets];
You can achieve what you want by setting the navigationItem.leftBarButtonItem of the view controller that's being pushed to the custom bar button item with the look you want. Good Luck!

Navigation bar button item image color is different when design through xib of xcode5

I am creating navigation bar button using xib but when i going to set image to bar button then image colour is different as original image.
Here is my orignal image.
And after adding that image on navigation bar button item than it look like this
First, I agree with #Desdenova's comment.
The two images do not look the same, one has hard right angle edges for each line, and the other rounded.
Make sure you are using the correct image file.
If this is the case, awesome, problem solved without deviating from your xib implementation. If not, just do it programmatically (as per #shankars code).
But another thing to note, I've run into problems setting custom image files to buttons, where the image gets tweaked... make sure to use UIImageRenderingModeAlwaysOriginal when setting the image to the button:
Objective-C:
[button setImage:[[UIImage imageNamed:#"imageName.png"] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal] forState:UIControlStateNormal];
Swift:
someBarButtonItem.image = UIImage(named: "yourPictureName")?.imageWithRenderingMode(UIImageRenderingMode.AlwaysOriginal)
Swift 3:
someBarButtonItem.image = UIImage(named:"myImage")?.withRenderingMode(.alwaysOriginal)
This is sample working code
UIImage *myImage = [UIImage imageNamed:#"myImageFile.png"];
myImage = [myImage imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
UIBarButtonItem *menuButton = [[UIBarButtonItem alloc] initWithImage:myImage style:UIBarButtonItemStylePlain target:self action:#selector(menuObject:)];
self.navigationItem.leftBarButtonItem = menuButton;
Hopefully I am not too late to add an answer of my own, but within Assets.xcassets, you can click on your image and in the attributes inspector, under Rendar As set it to Original Image
Because ios7 storyboard have issue i faced to fix like below.
set your tint color as image color it works
You can create navigation bar button programmatically instead of direct storyboard, this will not affect original image color
self.navigationItem.leftBarButtonItem=[self backButton];
- (UIBarButtonItem *)backButton
{
UIImage *image = [UIImage imageNamed:#"image.png"];
CGRect buttonFrame = CGRectMake(0, 0, image.size.width, image.size.height);
UIButton *button = [[UIButton alloc] initWithFrame:buttonFrame];
//[button addTarget:self action:#selector(backButtonPressed) forControlEvents:UIControlEventTouchUpInside];
[button setImage:image forState:UIControlStateNormal];
UIBarButtonItem *item= [[UIBarButtonItem alloc] initWithCustomView:button];
return item;
}
You need to set tint color as well - which worked for me -
You can generate UIBarButtonItem via code as follows:
#define setTurqoiseColor [UIColor colorWithRed:68.0f/255.0f green:181.0f/255.0f blue:223.0f/255.0f alpha:1.0]
UIBarButtonItem *menuButton = [[UIBarButtonItem alloc] initWithImage:buttonImage style:UIBarButtonItemStyleBordered target:self action:#selector(toggleMenu)];
menuButton.tintColor = setTurqoiseColor;

limit the touchable area of UIbutton

This is how I set button navigation bar
UIButton *addEditButton = [UIButton buttonWithType:UIButtonTypeCustom];
[addEditButton setImage:[UIImage imageNamed:#"edit.png"] forState:UIControlStateNormal];
[addEditButton setFrame:CGRectMake(0, 0, 62, 31)]; used frame same as image
[addEditButton addTarget:self action:#selector(EditTable) forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *addEdit = [[UIBarButtonItem alloc] initWithCustomView:addEditButton];
self.navigationItem.leftBarButtonItem =addEdit;
Everything works perfectly but button get pressed when I touch out side of it. How to solve this is there any way so it get pressed only if I touch on it
This is that image
apple has set this thing in way so user can navigate smoothly. it is advisable not to make such design in which you are putting buttons near navigationBarButton. there are some way to do it but its not good to change this kind of things. its just like reply to message and delete message both button are near beside to each other
I believe that you got this issue because the image you are setting is smaller thant the actual size of the button. please either make the button size smaller or provide a bigger image.
I hope this helps you.
It seems it works like that only, still I came up with a solution.
One is you can hide your navigation bar and use a toolbar indeed.
Other is you can add another button after that and set it's enabled property to FALSE.
I don't know whether this is proper or not, but seems to fulfill your requirement at least.
Here is the code:
UIButton *addEditButton = [UIButton buttonWithType:UIButtonTypeCustom];
[addEditButton setFrame:CGRectMake(0, 0, 62, 31)];
[addEditButton setImage:[UIImage imageNamed:#"edit.png"] forState:UIControlStateNormal];
[addEditButton addTarget:self action:#selector(EditTable) forControlEvents:UIControlEventTouchUpInside];
UIButton *addEditButton1 = [UIButton buttonWithType:UIButtonTypeCustom];
[addEditButton1 setFrame:CGRectMake(63, 0, 30, 31)];
UIBarButtonItem *addEdit = [[UIBarButtonItem alloc] initWithCustomView:addEditButton];
UIBarButtonItem *addEdit1 = [[UIBarButtonItem alloc] initWithCustomView:addEditButton1];
addEdit1.enabled = FALSE;
NSMutableArray *buttonArray=[[NSMutableArray alloc]initWithCapacity:2];
[buttonArray addObject:addEdit];
[buttonArray addObject:addEdit1];
self.navigationItem.leftBarButtonItems =buttonArray;

Resources