Is there a way to block copy/paste from textview? - iphone

i need a way to deactivate the auto selection from a UITextView.
I deselected all the attributes from interface builder, but when i touch the text, the selection appear!
Have a solution? A magick tricks?
thanks.

You need to create a subclass of UITextView and override the canPerformAction method.
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender
{
if (action == #selector(copy:)
return NO;
return [super canPerformAction:action withSender:sender];
}
The selector values you can expect from canPerformAction can be found in the UIResponderStandardEditActions Protocol Reference
The UIResponder Class Reference will help as well.
canPerformAction:withSender:
This default implementation of this
method returns YES if the responder
class implements the requested action
and calls the next responder if it
does not. Subclasses may override this
method to enable menu commands based
on the current state; for example, you
would enable the Copy command if there
is a selection or disable the Paste
command if the pasteboard did not
contain data with the correct
pasteboard representation type. If no
responder in the responder chain
returns YES, the menu command is
disabled.

Look at UIResponder Class Reference
So create a subclass of UITextView that overrides the canPerformAction:withSender: method and return 'NO' for every action that you don't want to perform on textview.

Related

NSTextField: exposing its Copy and Paste methods

I am trying to access the copy, cut, and paste methods of a NSTextField instance in its window delegate so I can customize these methods. I find that unlike tableViews and textViews, the textfield's copy, paste and cut actions are not responsive in the delegate. My understanding is that all text controls share the window's field editor yet this does not seem to be the case.
I thought perhaps the TextField's field editor was not being shared with the window delegate, however I did some testing I see that as I am typing in control, those field editors are identical--very strange.
My current work-around is to use a subclass instance of NSTextView where the copy and paste action methods respond as needed. This, however, has its own issues and I was hoping there was some way to get NSTextFields to work as expected.
A nstextfield does not have copy and paste functions. Those are only found in nstextview. the catch is that when a textfield is edited it opens up a textview called a fieldeditor during the editing and sets that as the first responder.
How to solve:
Each text field has a cell as a child connected to it (called cell in the picture but should be named more appropriately, e.g. CustomTextEditor):
The cell has a method for implementing a custom field editor called fieldEditorForView:
class cell: NSTextFieldCell {
var editor: NSTextView
override func fieldEditorForView(aControlView: NSView) -> NSTextView? {
if editor == nil {
editor = ESPasteView()
}
return editor
}
}
This above function allows you to provide your own custom NSTextView subclass:
class ESPasteView: NSTextView, NSTextViewDelegate {
override func paste(sender: AnyObject?) {
Swift.print("user tries to paste")
super.pasteAsPlainText(nil)
}
}
Credit to:
How to disable context menus with right mouse click in an NSTextField (Cocoa)?
and Ken Thomases who pointed out the field editor.
Maybe you could take a look at NSTextField's:
- (BOOL)writeSelectionToPasteboard:(NSPasteboard *)pboard type:(NSString *)type;
- (BOOL)readSelectionFromPasteboard:(NSPasteboard *)pboard type:(NSString *)type;
This would allow you to intercept the call customize the response.

UIViewController Edit button status always same

I added an Edit button to Navigation bar in my app.
I have a UIViewController which implements UITableViewDataSource and UITableViewDelegate.
I added the UITableView using storyboards and made connections to data source and delegate.
I did like this in implementation file of the view controller:
self.navigationItem.rightBarButtonItem = self.editButtonItem;
[self.editButtonItem setAction:#selector(setEditing:animated:)];
and
- (void)setEditing:(BOOL)editing animated:(BOOL)animated
{
DLog(#"Editing = %d", editing)
NSLog(editing ? #"Yes" : #"No");
[self.recentSearchList setEditing:editing animated:YES];
}
The problem is that whenever I tap on Edit button, the BOOL variable "editing" is always "YES". And for the first it sets the UITableView to editing mode but the Edit button still shows "Edit" label instead of "Done". And the since the parameter is always YES, the table view is never set to normal mode.
I read from an Answer in here: UITableView in edit mode - 'Edit' button doesn't change status
I am assuming the Edit button should change its state itself on tapping. And the parameter in the overridden method should also toggle.
I can write code of my own to set flags in the UIViewController to check the mode and toggle the tableView accordingly but I am assuming that there must be some other way.
From the documentation
Also remove the line [self.editButtonItem setAction:#selector(setEditing:animated:)];
The editButtonItem gets implicitly associated with the method - (void)setEditing:(BOOL)editing animated:(BOOL)animated.
So you just gotta override that method and call super's implementation at the top as the documentation says.
I think if you look more closely you will see that editing is actually a reference to the control itself.
When you call setAction on a UIControl ( your right button in this case ) your target can have one of the following signatures.
- (void)action
- (void)action:(id)sender
- (void)action:(id)sender forEvent:(UIEvent *)
You have to handle edit mode within this method separately.

How to identify UITextFields and Keyboard Activity?

I've searched in the web but didn't found anything similar to what I want. So,I am creating an application and I need to recognize when the user leaves a specific UITextField,more clearly.when the user enters a value in the UITextField and after touch outside to dismiss the keyboard, I need to recognize that the UITextField has lost activity for,after I perform an action.
Is this possible?
Look up UITextFieldDelegate in the Apple docs. Specifically the methods textFieldDidEndEditing: and textFieldShouldReturn:. Hook up the specific UITextField to an outlet and assign its delegate to your viewController. Then in the delegate method, if you need to make sure it's a specific text field, compare it to the IBOutlet.
write UITextFieldDelegate in .h file then after include the following method in .m file.
- (BOOL)textFieldShouldReturn:(UITextField *)textField
{
[textField resignFirstResponder];
return NO;
}

why override canBecomeFirstResponder?

I'm looking at TVAnimationGestures from WWDC 2010, and in the TableVieWController.m, they override canBecomeFirstResponder:
- (BOOL)canBecomeFirstResponder {
return YES;
}
Is there a reason they do this? I don't see this method called anywhere. Thanks.
So you can mark your question as answered...
They are using an UIMenuController within the sample, and in order to receive messages from that controller to your controller, you must make your controller the first responder (and accept becoming first responder via canBecomeFirstResponder.
This method is called by the Cocoa framework and not typically application to see if a controller should become the first responder. While I haven't looked at that specific example, it probably allows the table to be editable.
I needed to override canBecomeFirstResponder in a custom UIView so I could use a custom InputView and InputAccessoryView.
Custom Views for Data Input
I had to do it this way because if I used a UITextField or UITextView, a hardware keyboard would subvert the more limited on-screen keyboard.

Disable Magnifying Glass in UITextField

Is there a way to prevent the user from moving the cursor in a UITextField? I'd like it to stay at the end of the string.
This is an old question, but I was looking for an answer to the same question, and found a solution.
It is actually quite simple to prevent the user from moving the cursor. Just subclass UITextField and provide the following implementation of caretRectForPosition:
- (CGRect)caretRectForPosition:(UITextPosition *)position
{
return [super caretRectForPosition:self.endOfDocument];
}
NO SUBCLASS needed.
You Could use UITextFieldDelegate. It will make disable magnifying glass & text selection.
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField {
textField.userInteractionEnabled = NO;
return YES;
}
- (void)textFieldDidEndEditing:(UITextField *)textField {
textField.userInteractionEnabled = YES;
}
NB: This is just a bypass.
There's no way to prevent them from moving the cursor. You can, however, prevent them from editing the text except at the end by implementing the
– textField:shouldChangeCharactersInRange:replacementString:
method in your text field's delegate.
Edit: you can also set userInteractionEnabled to NO so that the user can't tap the field. Call becomeFirstResponder manually so that the field gets focus since the user can't tap to focus.
I'd suggest to check the gestureRecognizers property.
You will find a lot of them in the array and might want to either remove them all or to find the ones that triggers the event you want to intercept and remove/replace it.
I used it to remove copy/paste and magnifying glass functionalities from an UITextField
I haven't check if you can disable the magnifying glass, but the recommended way to selectively disable editing behavior in a UIResponder (and thus a UITextField) is to implement canPerformAction:withSender of UIResponder.
See UIResponder documentation.
Maybe if you return "NO" for the select and selectAll action you can disable it.
Another, more brutal, way is to intercept any touch event and reset the cursor to the end.