I created a side menu using a container view. It slides in the main view each time i press a menu.
You can find my project here:
https://github.com/marybnq/side-menu
I need to dismiss it by tapping anywhere in the mainVC.
How do I do it?
Try this:
class FirstViewController: UIViewController {
#IBOutlet weak var menuConstraint: NSLayoutConstraint!
var sideMenuOpen = false
var gesture : UITapGestureRecognizer?
override func viewDidLoad() {
super.viewDidLoad()
NotificationCenter.default.addObserver(self,
selector: #selector(toggleSideMenu), name: NSNotification.Name("ToggleSideMenu"), object: nil)
gesture = UITapGestureRecognizer(target: self, action: #selector(FirstViewController.toggleSideMenu))
}
#objc func toggleSideMenu() {
if sideMenuOpen {
sideMenuOpen = false
menuConstraint.constant = -240
self.view.removeGestureRecognizer(gesture!)
} else {
sideMenuOpen = true
menuConstraint.constant = 0
self.view.addGestureRecognizer(gesture!)
}
}
}
Simple:
1. Add tap gesture to view of mainVC and disable it by default
2. Enable tap gesture on showing side menu, to handle taps
3. Disable tap gesture on hiding side menu
Related
I have view controller like screenshot below.
When I touch textfield, the keyboard shows up.
I want to dismiss keyboard when I tap,drag on any screen.
I tried to put this code in viewcontroller, but doesn't work.
func dismissKey() {
let tap: UITapGestureRecognizer = UITapGestureRecognizer( target: self, action: #selector(dismissKeyboard))
tap.cancelsTouchesInView = false
addGestureRecognizer(tap)
}
#objc func dismissKeyboard() {
endEditing(true)
resignFirstResponder()
}
but if I put this code in custom cell class type 1 ,it dismisses keyboard only when I tap on this cell.
how can I dismiss keyboard when I touch on any screen?
If you're trying to dismiss keyboard in UIViewController try:
#objc func dismissKeyboard() {
view.endEditing(true)
resignFirstResponder()
}
I have a custom UIView that is a subview on a UIViewController.
I have it added in my storyboard and set it to Hidden.
My subview is also within another UIView that I'm using as a 'blur view' which is also initially Hidden.
I have functions that will unhide & hide the subviews.
My custom subview has a UITextField. I can show the keyboard and move the subview up with no problems. When I type in the keyboard or dismiss it my subview moves up and to the left. When I try to show my subview again it shows incorrectly (up and to the left).
The custom subview starts at the center of my screen.
The goal is move it up when the keyboard shows so it will not cover the subview or the UITextField, allow the user to type in the UITextField, and then dismiss the keyboard and move the custom subview back to the center.
In my UIViewController:
// Showing the custom sub view
func displayCustomSubView() {
if let window = UIApplication.shared.keyWindow {
self.blurView.isHidden = false
self.customSubView.isHidden = false
self.blurView.frame = window.frame
self.customSubView.center = window.center
window.addSubview(self.blurView)
UIApplication.shared.keyWindow?.bringSubviewToFront(self.blurView)
}
}
// Hiding the custom sub view
// the custom sub view has a button I tap to hide
#objc func dismissCustomSubView() {
self.blurView.isHidden = true
self.customSubView.isHidden = true
}
// Show Keyboard
// Since I am using the window to make sure my blur view expands to the full frame, I have tried just moving the window up
#objc func keyboardWillShow(sender: NSNotification) {
if let window = UIApplication.shared.keyWindow {
window.frame.origin.y = -75
}
}
// Hide Keyboard
#objc func keyboardWillHide(sender: NSNotification) {
if let window = UIApplication.shared.keyWindow {
window.frame.origin.y = 0
}
}
// Custom Subview Extension
extension CustomSubView: UITextFieldDelegate {
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
textField.resignFirstResponder()
return true
}
}
Added the Custom Subview Extension above.
First add this notification within your viewDidLoad(). And make a global variable called var keyboardH: CGFloat = 0:
NotificationCenter.default.addObserver(
self,
selector: #selector(keyboardWillShow),
name: UIResponder.keyboardWillShowNotification,
object: nil
)
And this function below:
#objc func keyboardWillShow(_ notification: Notification) {
if let keyboardFrame: NSValue = notification.userInfo?[UIResponder.keyboardFrameEndUserInfoKey] as? NSValue {
let keyboardRectangle = keyboardFrame.cgRectValue
let keyboardHeight = keyboardRectangle.height
self.keyboardH = keyboardHeight
}
This function is called every time the keyboard is present and will reveal the keyboard height and later we can use this variable.
So in your code:
#objc func keyboardWillShow(sender: NSNotification) {
if let window = UIApplication.shared.keyWindow {
let position = window.frame.origin.y - keyboardH
window.frame.origin.y = position
}
}
I have a Swift project that has a Table View Controller with multiple Static Cell Sections. Some cells have UITextFields and others have Accessory: Disclosure Indicators. I’ve implemented the following Swift code to dismiss the keyboard when the background is tapped:
override func viewDidLoad() {
super.viewDidLoad()
let tapGesture = UITapGestureRecognizer(target: self, action: Selector("hideKeyboard"))
tapGesture.cancelsTouchesInView = true
tableView.addGestureRecognizer(tapGesture)
}
func hideKeyboard() {
tableView.endEditing(true)
}
This works great for releasing the keyboard on tapping the background, but it also removed the tap gesture for the Disclosure Indicators (swipe still works). Does anyone know how to re-activate the tap gesture for the Disclosure Indicators cells after implementing this hideKeyboard() function?
Keep a reference to the gesture recognizer and remove it from the view when you hide the keyboard.
class YourController: UITableViewController {
let tapGesture: UITapGestureRecognizer = {
let tg = UITapGestureRecognizer(target: self, action: "hideKeyboard")
tg.cancelsTouchesInView = true
return tg
}()
override func viewDidLoad() {
super.viewDidLoad()
tableView.addGestureRecognizer(tapGesture)
}
func hideKeyboard() {
tableView.endEditing(true)
tableView.removeGestureRecognizer(tapGesture)
}
}
I would like to go back to the previous view by using Pangesture (drag view) but I can’t. I can do function “pan” only on the left edge of the screen, let’s say 5%. The other area of current view the Pangesture function is not working. Is there any way that I can go back to the root view with Pangesture? Please advise. Thank you.
var pan = UIPanGestureRecognizer(target: self, action: "handlePanGesture:")
self.mainView.addGestureRecognizer(pan)
func handlePanGesture(recognizer: UIPanGestureRecognizer) {
var touchLocation = recognizer.translationInView(self.view)
????
}
Here's an example of a view controller that uses a UIPanGestureRecognizer setup on the storyboard:
(Just one inspector shown for example purposes)
ViewController:
class PhotoDetaislViewController: UIViewController {
// the connection
#IBOutlet var swipeRight: UISwipeGestureRecognizer!
override func viewDidLoad() {
super.viewDidLoad()
//Swipe navigation
swipeRight.addTarget(self, action: "swipeRight:") // sets up the swipeRight var
}
func swipeRight(sender: UISwipeGestureRecognizer) {
// do your navigation here
}
}
I'm trying to figure out if theres a way to tie the location a programatically created UIAlertView is displayed on screen to the location of the button pressed to activate it.
I would like to have my alert view display directly below my button.
Thanks to gutenmorgenuhu for setting me on the right direction I was able to create a UIPopover that locates its self to the button pressed.
I first created a new UIViewController with the content of my popover (a UIPickerView in this case), that view is given the storyboard name Popover.
Then in my original view I created 2 buttons, topButton and bottomButton and linked them to their respective actions and outlets.
My code follows:
import UIKit
class ViewController: UIViewController, UIPopoverControllerDelegate, UIPopoverPresentationControllerDelegate {
//declare variables
var popOverLocation: CGRect!
// Set outlets for all buttons
#IBOutlet weak var topButton: UIButton!
#IBOutlet weak var bottomButton: UIButton!
//Add actions to buttons, first trigger popOverLocation to take the frame properties of the active button, then call the popover function.
#IBAction func topButton(sender: AnyObject) {
popOverLocation = topButton.frame
popOver()
}
#IBAction func bottomButton(sender: AnyObject) {
popOverLocation = bottomButton.frame
popOver()
}
//function for creating the popover
func popOver() {
//Read the height, and XY coordinates of the active button
var h = popOverLocation.height
var x = popOverLocation.origin.x
var y = popOverLocation.origin.y + h
//create the popover
var popoverContent = self.storyboard!.instantiateViewControllerWithIdentifier("Popover") as UIViewController
var nav = UINavigationController(rootViewController: popoverContent)
nav.modalPresentationStyle = UIModalPresentationStyle.Popover
var popover = nav.popoverPresentationController! as UIPopoverPresentationController
popover.sourceView = self.view
popover.delegate = self
//set the size of the popover
popoverContent.preferredContentSize = CGSizeMake(200,300);
//set the direction the popover arrow is allowed to point
popover.permittedArrowDirections = UIPopoverArrowDirection.Up
//using the buttons coordinates set the location of the popover
popover.sourceRect = CGRectMake(x,y,0,0)
self.presentViewController(nav, animated: true, completion: nil)
}
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}