I wanted to implement a UITapGestureRecognizer that closes a FanMenu (a circular based menu around a button with other buttons) when the user press outside of the menu.
let tapRecognizer = UITapGestureRecognizer(target: self, action: #selector(handleTap(sender:)))
tapRecognizer.numberOfTapsRequired = 1
tapRecognizer.delegate = self
tapRecognizer.require(toFail: doubleTapRecognizer)
scrollView.addGestureRecognizer(tapRecognizer)
var planScaleDetermination : PlanScaleDetermination?
@objc func handleTap(sender: UITapGestureRecognizer) {
if(sender.state == .ended) {
let point = sender.location(in: viewForTilingView)
if(fanMenu.isOpen && outerFanMenu.isOpen) {
fanMenu.close()
outerFanMenu.close()
outerFanMenu.isHidden = true
fanMenu.isHidden = true
}
if(isPointInPlanDimensions(point: point)) {
if(!planControlHelper!.scaleView.isHidden && planScaleDetermination != nil) {
if let psd = planScaleDetermination {
psd.addPoint(point: MobiPlanPoint(X: point.x, Y: point.y))
}
}
else if(isModeActive && planControlHelper!.documentationMode == .area && !area!.isCorrectionModeActive) {
area!.addPoint(point: MobiPlanPoint(X: point.x, Y: point.y), drawOnly: false)
}
}
}
}
If the menu isOpen it closes it correctly, but it closes it also when I select a button inside the menu. I found the ignore(_:for:) method that tells the gesture recognizer to ignore a specific press of the given event.
How can I implement the method correctly so that my menu will not close when I select a button?
Implementation of the button looks like this:
var outerActionItems : [FanMenuButton] = []
func initOuterFanMenu() {
outerFanMenu.button = FanMenuButton(
id: "main",
image: "baseline_clear_white_18pt_1x",
color: Color(val: 0xFFFFFFFF)
)
outerActionItems = [
FanMenuButton(
id: "cancelButton",
image: "baseline_clear_white_18pt_1x",
color: Color(val: 0xF55B58)
),
FanMenuButton(
id: "confirmButton",
image: "baseline_done_white_18pt_1x",
color: Color(val: 0xF55B58)
)
]
outerFanMenu.items = outerActionItems
outerFanMenu.menuRadius = 110.0
outerFanMenu.radius = 15.0
outerFanMenu.duration = 0.35
outerFanMenu.delay = 0.05
outerFanMenu.interval = (0, 2.0 * .pi)
outerFanMenu.onItemDidClick = { button in
self.contextMenuButtonClicked(buttonId: button.id)
}
outerFanMenu.onItemWillClick = { button in
if(button.id != "rotateMarker") {
self.outerFanMenu.isHidden = !self.outerFanMenu.isHidden
}
}
}
You can check if tapped view is menu button:
@objc func handleTap(sender: UITapGestureRecognizer) {
if sender.view is FanMenuButton { return }
... your code ... }
Just add another view with the name of the background view and add a gesture recognizer on it. Background view should be behind your view. just an example in objective c, you can translate to swift.
_backgroundView.userInteractionEnabled = YES;
UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(backgroundTapAction:)];
[_backgroundView addGestureRecognizer:tapGesture];
- (void)backgroundTapAction:(UITapGestureRecognizer *)sender {
//dismiss your view here.
}
User contributions licensed under CC BY-SA 3.0