Custom NavigationItem's TouchUpInside Event is outside boundaries - iphone

I'm using a custom UIBarButtonItem to replace the leftBarButtonItem, however when I press outside of the button, within around 20 pixels of the button, it detects it as the button being pressed.
Here's my code:
- (void)changeNavbarButtons
{
UIButton *backButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, 44, 44)];
[backButton setBackgroundImage:[UIImage imageNamed:#"navbarBack.png"] forState:UIControlStateNormal];
[backButton addTarget:self action:#selector(popViewController) forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *backItem = [[UIBarButtonItem alloc] initWithCustomView:backButton];
UIBarButtonItem *negativeSpacer = [[UIBarButtonItem alloc]
initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace
target:nil action:nil];
negativeSpacer.width = -5;
self.navigationItem.leftBarButtonItems = [NSArray
arrayWithObjects:negativeSpacer, backItem, nil]; self.navigationItem.hidesBackButton = YES;
}
The negativeSpacer is to move the button 5 pixels to the left.
What would be causing this?

It is the default behaviour of UINavigationBarButton item.
It's about ease of use. The navigation bar at the top tends to mean people tap lower than you may expect. Always leave that gap there, or have a sufficiently large hit area that the user stabbing their finger towards the middle of your "below the nav bar" item will avoid the dead area.

Related

Can't adjust spacing of UIBarButtonItem(s) when assigned to navigationItem.rightBarButtonItems

This is a weird problem.
The situation is that I want to adjust the spacing between my UIBarButtonItem(s) so that they are just 2 pixels apart.
I am able to do this quite easily with UIToolbar:
// Make bottom button bar buttons
NSMutableArray *bottomButtons = [[NSMutableArray alloc] initWithCapacity:3];
// Create spacer between buttons
UIBarButtonItem *spacer = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
[bottomButtons addObject:spacer];
UIBarButtonItem* noSpace = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace target:nil action:nil];
noSpace.width = -10;
// Add button 1
self.addAlbumButton = [UIGlossyButton buttonWithType:UIButtonTypeCustom];
[self.addAlbumButton setTitle:#"Button 1" forState:UIControlStateNormal];
[self.addAlbumButton addTarget:self action:#selector(addAlbum:) forControlEvents:UIControlEventTouchUpInside];
self.addAlbumBarButton = [[UIBarButtonItem alloc] initWithCustomView:self.addAlbumButton];
[bottomButtons addObject:self.addAlbumBarButton];
[bottomButtons addObject:noSpace];
// Add button2
self.downloadAllItemsButton = [UIGlossyButton buttonWithType:UIButtonTypeCustom];
[self.downloadAllItemsButton setTitle:#"Button 2" forState:UIControlStateNormal];
[self.downloadAllItemsButton addTarget:self action:#selector(downloadAllItemsAction:) forControlEvents:UIControlEventTouchUpInside];
self.downloadAllItemsBarButton = [[UIBarButtonItem alloc] initWithCustomView:self.downloadAllItemsButton];
[bottomButtons addObject:self.downloadAllItemsBarButton];
// add all button to bottom toolbar
[self.bottomToolbar setItems:bottomButtons];
The problem is when I try to do this with the navigationbar. For some reason, when I insert a fixed length button (with a negative value), it won't shrink the space between the buttons. I know the fixed length button is there and working because if I change the width to a positive number, the spacing between the buttons increases.
The code is basically the same except that instead of adding the buttons to self.bottomToolbar, I'm calling the following code:
self.navigationItem.rightBarButtonItems = bottomButtons;
I have found the same issue with the MasterViewController. I'm using a splitviewcontroller and the bottom toolbar works fine but the top toolbar has the same spacing problem. That problem, is I can't make the space between buttons less than the default.
It seems like navigationItem.rightBarButtonItems works differently than all other toolbars.
after adding all navigationButtonItem in to an array you can do it like the following way. i guess this will help you also coz this works for me and if you want to change space between button you can change it with help of macro
#define ONE_BUTTON_WIDTH 30.0f
#define SPACE_BETWEEN_BUTTONS 12.0f
#define ONE_BUTTON_TOTAL_WIDTH (ONE_BUTTON_WIDTH + SPACE_BETWEEN_BUTTONS)
#define kBookmarksImage [UIImage imageNamed:#"bookmarks.png"]
/* CREATE BOOKMARKS BUTTON */
UIButton *bookmarksButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, kBookmarksImage.size.width, kBookmarksImage.size.height)];
[bookmarksButton setImage:kBookmarksImage forState:UIControlStateNormal];
[bookmarksButton addTarget:target action:#selector(toolbarButtonTapped:) forControlEvents:UIControlEventTouchDown];
bookmarksButton.tag = kBookmarksButtonTag;
UIBarButtonItem *bookmarksButtonItem = [[UIBarButtonItem alloc] initWithCustomView:bookmarksButton];
UIBarButtonItem *spacer = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
spacer.width = SPACE_BETWEEN_BUTTONS;
[buttons addObjectsFromArray:#[bookmarksButtonItem,spacer]];
/* ADD ALL THESE BUTTONS TO CUSTOM TOOLBAR AND TOOLBAR TO NAVIGATION BAR */
UIToolbar *customToolbar = [[UIToolbar alloc]
initWithFrame:CGRectMake(0.0f, 0.0f, ([bottomButtons count]/2*ONE_BUTTON_TOTAL_WIDTH), 44.01f)]; // 44.01 shifts it up 1px for some reason
customToolbar.clearsContextBeforeDrawing = NO;
customToolbar.clipsToBounds = NO;
customToolbar.tintColor = [UIColor colorWithWhite:0.305f alpha:0.0f]; // closest I could get by eye to black, translucent style.
customToolbar.barStyle = -1; // clear background
[customToolbar setItems: bottomButtons animated:NO];
UIBarButtonItem *customUIBarButtonitem = [[UIBarButtonItem alloc] initWithCustomView:customToolbar];
self.navigationItem.rightBarButtonItem = customUIBarButtonitem;
Easiest way just create a method to set up UIButton for each UIBarButtonItem like so:
- (UIBarButtonItem*)createAddAlbumBarButtonWithImage:(NSString*)imageName
{
UIButton* button = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, 30, 30)];
[button setImage:[UIImage imageNamed:imageName] forState:UIControlStateNormal];
[button addTarget:self action:#selector(addAlbum:) forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem* barButton = [[UIBarButtonItem alloc] initWithCustomView:button];
return barButton;
}

UIBarButtonItem:setBackgroundVerticalPositionAdjustment not working properly with custom button

I have the following code to customize the display of an UIBarButtonItem (locationButton):
UIButton *locationButtonAux = [UIButton buttonWithType:UIButtonTypeCustom];
[locationButtonAux setFrame:CGRectMake(0, 0, LOCATION_BUTTON_WIDTH, LOCATION_BUTTON_HEIGHT)];
[locationButtonAux setBackgroundImage:[UIImage imageNamed:#"location_button.png"] forState:UIControlStateNormal];
[locationButtonAux setBackgroundImage:[UIImage imageNamed:#"location_button.png"] forState:UIControlStateHighlighted];
[locationButtonAux addTarget:self action:#selector(userLocation) forControlEvents:UIControlEventTouchUpInside];
UIBarButtonItem *locationButton = [[UIBarButtonItem alloc] initWithCustomView:locationButtonAux];
UIBarButtonItem * item = [[UIBarButtonItem alloc] initWithTitle:#"title"
style:UIBarButtonItemStyleDone
target:nil action:#selector(someMssage)];
[locationButton setBackgroundVerticalPositionAdjustment:-20.0 forBarMetrics:UIBarMetricsDefault];
self.navigationItem.rightBarButtonItem = locationButton;
And I want to adjust the position of this button into the NavigationBar, because my NavigationBar is taller than normal (is customized using Appeareance).
I'm using the method setBackgroundVerticalPositionAdjustment, as you can see in the code, to do that. But is not working at all with my UIBarButtonItem, no matter what offset I put there, the button always appear close to the bottom of the bar (snapshot).
BUT, if I use a normal UIBarButtonItem with a normal style (the one I called button) I DO can see how the position of the button will be altered the offset of -20. Very strange... Any ideas?
Thank you!
Perhaps something like this would work for you:
UIView *rightView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 150, 30)]; //change this frame to counteract for your taller navbar
[rightView addSubview:locationButtonAux];
UIBarButtonItem *rightBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:rightView];
self.navigationItem.rightBarButtonItem = rightBarButtonItem;
Hope this helps
You need to put the button inside a blank view and position it within that blank view. Now make that view the custom view of the bar button item.
You really don't need a button here, since this is just an image and you are not using any of the button capabilities (you can attach a gesture recognizer to spot the tap). So here's a simple solution using an image view:
UIImageView *locationButtonAux =
[[UIImageView alloc] initWithImage:[UIImage imageNamed:#"location_button.png"]];
UIView* v = [[UIView alloc] initWithFrame:locationButtonAux.frame];
[v addSubview:locationButtonAux];
CGRect f = locationButtonAux.frame;
f.origin.y -= 10;
locationButtonAux.frame = f;
UIBarButtonItem *locationButton = [[UIBarButtonItem alloc] initWithCustomView:v];
self.navigationItem.rightBarButtonItem = locationButton;
I've omitted the gesture recognizer part but you can easily see how to add it.

UIToolBar item coordinates

My problem is following: i want to know the coordinates to an item of a toolbar so that i could pop some data right there. These barbuttonitems never reveal me there frame properties.
Is there a solution?
You can use if you want to give spacing.
UIBarButtonItem *fixedLeftSpace = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace target:self action:nil];
// for adding Custom view
UIButton *webButton = [UIButton buttonWithType:UIButtonTypeCustom];
[webButton setFrame:CGRectMake(0, 0, 50, 40)];
[webButton setImage:[UIImage imageNamed:#\"webIcon.jpg\"] forState:UIControlStateNormal];
[webButton addTarget:self action:#selector(goToWebPage) forControlEvents:UIControlEventTouchDown];
UIBarButtonItem *webpageBtn = [[UIBarButtonItem alloc]initWithCustomView:webButton];
[webpageBtn setTarget:self];
[webpageBtn setAction:#selector(goToWebPage)];
[toolbar setItems:[NSArray arrayWithObjects: webpageBtn,fixedLeftSpace,webpageBtn, nil]];
Also see the link.
UIToolbar* tools = [[UIToolbar alloc] initWithFrame:CGRectMake(0, 0, 210, 44)];
UIBarButtonItem *space = [[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemFixedSpace target:nil action:nil];
NSMutableArray* buttons = [[NSMutableArray alloc] initWithObjects:bt1,space,bt2,space,bt3, nil];
[tools setItems:buttons animated:YES];
UIBarButtonItem *toolsBtn = [[UIBarButtonItem alloc]initWithCustomView:tools];
self.navigationItem.rightBarButtonItem = toolsBtn;
If you are creating a toolbar from xib file then you need to add multiple "flexible space bar button item" before and after the buttons if you multiple bar buttons on toolbar until you get the desired spacing.
If you are creating UIToolbar dynamically then you need to add flexible buttons dynamically.

How to hide default navigation bar button and add custom button in it?

I have one navigation based application in which i want to hide the default navigation
which is display at left side and i want to add my own custom button.I have written following 2 code.
code sample 1:
- (void)viewDidLoad {
appDelegate=[(FoodAppDelegate *)[UIApplication sharedApplication]delegate];
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
[button setImage:[UIImage imageNamed:#"Volunteers_back.png"] forState:UIControlStateNormal];
[button addTarget:self action:#selector(back:) forControlEvents:UIControlEventTouchUpInside];
[button setFrame:CGRectMake(0, 0, 86, 30)];
self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:button];
But this displays default navigation button.
second code sample:
self.navigationItem.hidesBackButton=YES;
UIBarButtonItem *barButton = [[UIBarButtonItem alloc] initWithTitle:#"DontWorryAboutThis" style:UIBarButtonItemStylePlain target:self action:#selector(back:)];
[barButton setImage:[UIImage imageNamed:#"Volunteers_back.png"]];
[self.navigationItem setLeftBarButtonItem:barButton];
This one displays both button default and custom overlapping each other.
Does anyone have any idea what is the problem here?or any sample code to achieve this?
You shouldn't have to hide the back button. If you replace the leftBarButtonItem, it should overwrite whatever button is there. I use this code, and ONLY this code to accomplish this in several of my apps.
UIBarButtonItem *btnCancel =
[[UIBarButtonItem alloc] initWithTitle: #"Cancel"
style: UIBarButtonItemStylePlain
target: self
action: #selector(actionButtonCancel)];
self.navigationItem.leftBarButtonItem = btnCancel;
[btnCancel release];

UIButton animation view

I am new developer in iPhone.
I want to create uibutton.
When I click the button, then the button will be flash like as below.
How to create the flash, when I click my button?
There is a property of UIButton named showsTouchWhenHighlighted. If you set the property to YES, it will show the glow when you touch the button. It's default value is NO.
[yourButton setShowsTouchWhenHighlighted:YES];
What you do is set the highlighted image. For example:
[someButton setImage:[UIImage imageNamed:#"MyHighlight.png"]
forState:UIControlStateHighlighted];
Then when a user taps it, your MyHighlight.png will show.
toolbar = [UIToolbar new];
toolbar.barStyle = UIBarStyleDefault;
[toolbar sizeToFit];
toolbar.frame = CGRectMake(0, 410, 320, 50);
//Add buttons
UIBarButtonItem *systemItem1 = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAdd
target:self
action:#selector(pressButton1:)];
UIBarButtonItem *systemItem2 = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAction
target:self
action:#selector(pressButton2:)];
UIBarButtonItem *systemItem3 = [[UIBarButtonItem alloc]
initWithBarButtonSystemItem:UIBarButtonSystemItemCamera
target:self action:#selector(pressButton3:)];
//Use this to put space in between your toolbox buttons
UIBarButtonItem *flexItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace
target:nil
action:nil];
//Add buttons to the array
NSArray *items = [NSArray arrayWithObjects: systemItem1, flexItem, systemItem2, flexItem, systemItem3, nil];
//release buttons
[systemItem1 release];
[systemItem2 release];
[systemItem3 release];
[flexItem release];
//add array of buttons to toolbar
[toolbar setItems:items animated:NO];
[self.view addSubview:toolbar];
use this to create toolBar.
and use this for search button
UIBarButtonSystemItemSearch
If you want to change the button image when you clicked on button now set different images for both default and highlighted stats. As:
[tempButton setImage:[UIImage imageNamed:#"NormalImage.png"]
forState:UIControlStateNormal];
[tempButton setImage:[UIImage imageNamed:#"HighlightImage.png"]
forState:UIControlStateHighlighted];
If you want the flash effect for the same image, when button is clicked on,
In your XIB, Goto Inspector window > control > check the Highlighted property.
You can try this by code as:
[tempButton setShowsTouchWhenHighlighted:YES];
//or
tempButton.highlighted = YES;