I have added custom menu controller when long press on UICollectionViewCell
[self becomeFirstResponder];
UIMenuItem *menuItem = [[UIMenuItem alloc] initWithTitle:@"Custom Action"
action:@selector(customAction:)];
[[UIMenuController sharedMenuController] setMenuItems:[NSArray arrayWithObject:menuItem]];
[[UIMenuController sharedMenuController] setTargetRect: self.frame inView:self.superview];
[[UIMenuController sharedMenuController] setMenuVisible:YES animated: YES];
canBecomeFirstResponder Is also being called
- (BOOL)canBecomeFirstResponder {
// NOTE: This menu item will not show if this is not YES!
return YES;
}
//This method is not being called
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender {
NSLog(@"canPerformAction");
// The selector(s) should match your UIMenuItem selector
if (action == @selector(customAction:)) {
return YES;
}
return NO;
}
I have Also Implemented these methods
- (BOOL)collectionView:(UICollectionView *)collectionView
canPerformAction:(SEL)action
forItemAtIndexPath:(NSIndexPath *)indexPath
withSender:(id)sender {
if([NSStringFromSelector(action) isEqualToString:@"customAction:"]){
NSLog(@"indexpath : %@",indexPath);
UIAlertView *alertview = [[UIAlertView alloc] initWithTitle:@"warning.." message:@"Do you really want to delete this photo?" delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil, nil];
[alertview show];
return YES;
}
return YES;
}
- (BOOL)collectionView:(UICollectionView *)collectionView shouldShowMenuForItemAtIndexPath:(NSIndexPath *)indexPath {
return YES;
}
- (void)collectionView:(UICollectionView *)collectionView
performAction:(SEL)action
forItemAtIndexPath:(NSIndexPath *)indexPath
withSender:(id)sender {
NSLog(@"performAction");
}
Though it is showing only "cut, copy, and paste" menus
On iOS 9 with Swift to SHOW ONLY CUSTOM ITEMS (without the default cut, paste and so on), I only managed to make work with the following code.
On method
viewDidLoad
:Override method
canBecomeFirstResponder
:Override these two collection related methods:
Create the gesture handler method:
And, finally, create the selector's methods:
Hope that helps. :)
Cheers.
Swift 3 Solution:
Simply do all stuff inside UICollectionView class and assign this class to UICollectionView object.
Maybe a bit late but i maybe found a better solution for those who are still search for this:
In viewDidLoad of your UICollectionViewController add your item:
Add the following delegate methods:
Subclass UICollectionViewCell if you didn't already. Add the method you specified for your item:
This way you don't need any becomeFirstResponder or other methods. You have all actions in one place and you can easily handle different cells if you call a general method with the cell itself as a parameter.
Edit: Somehow the uicollectionview needs the existence of this method (this method isn't called for your custom action, i think the uicollectionview just checks for existance)
You need to trigger delegate functions from custom UICollectionViewCell
Here is my working sample code for Swift3
CollectionViewController
Add following functions to your custom UICollectionViewCell
To call delegate function from cell (needs to be in your custom UICollectionViewCell)
I've just spent two days trying to figure out the "correct" way of doing this, and barking up the wrong tree with some of the suggestions that are around.
This article shows the correct way of doing this. I hope that by posting it here someone will be saved a few hours.
http://dev.glide.me/2013/05/custom-item-in-uimenucontroller-of.html
When people have trouble getting menus to work on long press in a collection view (or table view, for that matter), it is always for one of two reasons:
You're using the long press gesture recognizer for something. You cannot, for example, have both dragging and menus in the same collection view.
You've forgotten to implement the selector in the cell.
For example, the OP's code says:
The implication is that
customAction
is a method this class. This is wrong.customAction:
must be a method of the cell class. The reason is that the runtime will look at the cell class and will not show the menu item unless the cell implements the menu item's action method.For a complete minimal working example (in Swift), see my answer here: https://stackoverflow.com/a/51898182/341994