I want to make something like below image with custom Keyboard extension,
Create a subclass of your TextField
class CustomTexrtField: UITextField {
//will see implementation later
}
Now simply override paste function inside it :)
override func paste(_ sender: Any?) {
super.paste(sender)
//do whatever you want to do here after paste
print("me here")
}
Hope it helps
Related
I read a lot about the delegates but in practice I cannot use it properly.
Description: I have A: UIViewController, B: UIView, C: UIViewController. I want to run segue from A: UIViewController to the C: UIViewController from the inside of B: UIView.
I've tried:
protocol SegueDelegate {
func runSegue(identifier: String)
}
class B: UIView { ... }
where in my A: UIViewController:
override func viewDidLoad() {
B().delegate = self
}
func runSegue(identifier: String) {
self.performSegueWithIdentifier(identifier, sender: self)
}
and trying to call it via:
#IBAction func send(sender: AnyObject) {
let a: SegueDelegate? = nil
a!.runSegue("goToMainPage")
}
but I'm sure that I do not use it properly. Can anyone help me with it? I do not want just an answer. Please describe me it concept shortly
Delegates are just a Design Pattern that you can use in a number of ways. You can look at the Apple Frameworks to see how and where to use delegates as examples. A table view delegate is probably the best known delegate in UIKit.
Delegates serve as a callback mechanism for code to communicate with an instance of an unknown class without knowing more than that that instance will respond to the methods of the delegate protocol.
An alternative to a delegate is to use a closure (what we used to call a block in Objective-C). When to use one vs. the other is a matter of taste. There are a couple of rules of thumb, like for instance outlined here.
What you are doing is, IMO, the proper way to use delegates. You separate the view functionality from the View Controller's functionalities via a delegate, and so the contract for your view is clear: the user needs to respond to the delegate method.
Your code works and is correct. I made a quick implementation here: https://github.com/kristofvanlandschoot/DelegateUsage/tree/master
The main difference from your example, and maybe that's the place where you made a mistake is the third part of your code where you should write something like:
#IBAction func send(sender: AnyObject) {
delegate?.runSegue("segueAB")
}
There are multiple errors in your code, for example:
Here you are creating a new B, and setting A as a delegate of that new instance, no the one you actually want
override func viewDidLoad() {
«B()».delegate = self
}
And here you are creating force unwrapping a nil value
#IBAction func send(sender: AnyObject) {
let a: SegueDelegate? = «nil»
«a!».runSegue("goToMainPage")
}
If what you want to do is tell A to perform a segue to C, from inside B, all you need to do is to call performSegueWithIdentifier on A
For example:
class B: UIView {
weak var referenceToA: UIViewController? = nil // set this somewhere
#IBAction func send(sender: AnyObject) {
guard let a = referenceToA else {
fatalError("you didn't set the reference to a view controller of class A")
}
a.performSegueWithIdentifier("goToMainPage", sender: self)
}
}
I'm not going to ask how to hide the keyboard after you are done with editing a textField. My question is : Is there a way to do this on each view ? (like a setting) or do I need to write the two following functions and set the delegate properly every time ?
func textFieldShouldReturn(textField: UITextField) -> Bool // called when 'return' key pressed. return NO to ignore.
{
textField.resignFirstResponder()
return true;
}
override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) {
self.view.endEditing(true)
}
I'm developing an app with a lot of textfields (and also views) so I try to avoid redundance code. What is the best solution to avoid this repetition?
Thank you!
You can create your own text field, which is subclass of UITextField. See the simple custom UITextField below:
import UIKit
class CustomTextField: UITextField, UITextFieldDelegate {
override func awakeFromNib() {
super.awakeFromNib()
self.delegate = self
}
func textFieldShouldReturn(textField: UITextField) -> Bool {
self.resignFirstResponder()
return true
}
}
Use your custom text field name to Custom Class in your Storyboard.
See my example at Github
The easiest thing to do, is put one giant invisible button the size of the screen underneath your text fields, then when a non text field is tapped, you call the invisible button action to close it. If this does not apply in your scenario please let me know.
Create an IBAction method to dismiss keyboard
#IBAction func backgroundTapped (sender: UIView)
{
sender.endEditing(true)
}
Change the class of your UIView to UIControl which contains the textfields in storyboard (You can even do that to your view of the viewcontroller as shown)
It looks like this:
Now you can connect the IBAction to the Touch Up Inside event of this view, in the storyboard, as shown.
I have a problem in which when I select a UITextField, out pops up a view controller where the user can type into a search bar and search for particular items via the Google Places API. It looks something like this:
//When clicking on the UITextField, this function is called
#IBAction func selectLocation(){
gpaViewController.placeDelegate = self
presentViewController(gpaViewController, animated: true, completion: nil)
}
Through a the GooglePlacesAutocomplete github I found online: https://github.com/watsonbox/ios_google_places_autocomplete the below Extension was written for me so that everytime you select an entry from the UITableView from the presented gpaViewController, the place.description is printed along with its details as shown below:
extension EventFormController: GooglePlacesAutocompleteDelegate {
func placeSelected(place: Place){
var test: Place?
println(place.description)
place.getDetails { details in
println(details)
}
}
func placeViewClosed() {
dismissViewControllerAnimated(true, completion: nil)
}
}
However, upon doing so, I want it so that I can return the place.description from the placeSelected function as shown above but I am not too sure on how to do so. I tried to edit the placeSelected function inside the library but I don't think you can return anything from the didSelectRowAtIndexPath UITableView function.
public func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
delegate?.placeSelected?(self.places[indexPath.row])
}
Any ideas on how to return the place.description and set that place.description as the text inside the UITextField after selecting an option? Any help would be appreciated!
func placeSelected(place: Place) is an protocol method, you can't change the signature by adding a return value without breaking the callback chain, i.e, if you change the signature of the protocol method, it won't be called. Instead of returing place.description from the function, you're supposed to use it for updating your UI, for example:
func placeSelected(place: Place){
var test: Place?
println(place.description)
// update UI
textField.text = place.description // assuming that your EventFormController has reference to the textField you're trying to access
place.getDetails { details in
println(details)
}
}
It would be better though if you can explain more concretely what you're trying to achieve. I still don't understand the connection between your placeSelected and the didSelectRowAtIndexPath implementations.
How about something like:
place.getDetails { details in
self.textField.text = details.name
}
I didn't read through the documentation but I believe getDetails is a function something like getDetail(completionHandler: (Details) -> Void), which completionHandler is a closure executed after details are fetched.
So I guess what you want to do after fetching the data is to let your textField in your view controller to display the information fetched.
This question already has answers here:
How to disable copy paste option from UITextField programmatically
(17 answers)
Closed 7 years ago.
I want to remove the option "Paste" from the selector
I've tried the code below but it adds other selections to the selector and the paste option is still there, it just disables the functionality
override func canPerformAction(action: Selector, withSender sender: AnyObject?) -> Bool {
if action == "paste:" {
return false
}
return true
}
I want to remove Paste all together so the user doesn't even have the option to see it or click it
Have a look at UIMenuController
You should be able to use
var menuItems: [AnyObject]?
to set up your own object.
It is not a simple switch on or off the existing buttons, looks like you have to provide your own.
try this :
Step 1: You need to create another class which extends the UITextField. In this example, I made my CustomizedUITextField.
import UIKit
class CustomTextField: UITextField {
override func canPerformAction(action: Selector, withSender sender: AnyObject?) -> Bool {
if action == "paste:" {
return false
}
return super.canPerformAction(action, withSender: sender)
}
}
I just want an idea to make something like this.Suppose there is an UILabel string #"don't late." but when it will display it will show like this #"don' tlate.", Now user will rearrange those characters by dragging and dropping and make it correct word.
Now anyone can give me any idea or sample of example that how can i do that in iPhone application development?.
Thanks in Advance
I've created a sample project on my github account.
I think raywenderlich's gesture tutorial may help you.
Below is the most relevant code
// MARK: Actions
extension ViewController {
#IBAction func moveLabel(gesture:UIPanGestureRecognizer) {
if let labelBeingMoved = labelBeingMoved {
labelBeingMoved.center = gesture.locationInView(labelContainer)
}
}
}
// MARK: UIGestureRecognizerDelegate
extension ViewController : UIGestureRecognizerDelegate {
func gestureRecognizerShouldBegin(gesture: UIGestureRecognizer) -> Bool {
let location = gesture.locationInView(labelContainer)
//You'll have to change this to account for labels on top of one another
for label in labels {
if label.frame.contains(location) {
labelBeingMoved = label
labelContainer.bringSubviewToFront(labelBeingMoved!)
return true
}
}
return false
}
}