0

I've been working on it for a long time, and tried following two methods.However, neither succeeds.

  1. subclassing NSSecureTextField and overriding -(BOOL)becomeFirstResponder and -(void)textDidEndEditing:.

    -(BOOL) becomeFirstResponder
    {
        NSMenu *mainMenu = [[NSApplication sharedApplication]mainMenu];
        NSMenu *appMenu = [[mainMenu itemAtIndex:2]submenu];
        NSLog(@"%@", [appMenu title]);
        for (NSMenuItem *item in [appMenu itemArray]) {
            if ([[item title] isEqual: @"Paste"])
            {
                NSLog(@"%@", [item title]);
                [item setEnabled:NO];             
            }
        }
        return [super becomeFirstResponder];
    }
    
    - (void)textDidEndEditing:(NSNotification *)notification
    {
        NSMenu *mainMenu = [[NSApplication sharedApplication]mainMenu];
        NSMenu *appMenu = [[mainMenu itemAtIndex:2]submenu];
        NSLog(@"%@", [appMenu title]);
        for (NSMenuItem *item in [appMenu itemArray]) {
            if ([[item title] isEqual: @"Paste"])
            {
                NSLog(@"%@", [item title]);
                [item setEnabled:YES];             
            }
        }
    }
    
  2. adding protocol NSUserInterfaceValidation to a subclass of NSSecureTextField(Maybe it's not the correct target to implement this protocol,because breakpoints in this function would never be triggered).

    - (BOOL)validateUserInterfaceItem:(id<NSValidatedUserInterfaceItem>)anItem
    {
      SEL theAction = [anItem action];
      if (theAction == @selector(paste:)) {
      return NO;
      }
      return [super validateUserInterfaceItem:anItem];
    }
    
Gaojin
  • 1
  • 2
  • 5
    Why do you want to disable pasting of passwords? I would say having to type a password is a major usability fail. This is mainly because some people use the password generator in Keychain to generate strong passwords consisting of random characters. Having to type such a password in is a serious pain. – JeremyP Sep 23 '13 at 12:20
  • Because some illegal characters could be pasted in as a password, and I give My superior a choice, disabling the pasting function or checking password after users clicking "sign up" button. He chose the former. – Gaojin Sep 23 '13 at 13:07
  • 1
    And what if they type the illegal characters into the textfield? You still need to filter them or notify the user. – David Snabel-Caunt Sep 23 '13 at 16:23
  • @DavidCaunt NSSecureTextField only accepts TYPING into Roman Characters,but users still could PASTE other illegal characters into it, such as Chinese.All the printable ASCII characters should be acceptable, so once disabling the pasting function, we can ensure the characters typed into the NSSecureTextField are all legal. – Gaojin Sep 24 '13 at 02:36
  • 1
    Instead disabling the paste feature better add good validation. Accept the password only if it complies to rules you set up. You have to do this anyway to ensure a minimum password length, minimum complexity etc. Don't disable the paste feature. It's a major pain if you can't use your password safe to copy over a specific password. – Mike Lischke Sep 24 '13 at 07:42
  • @MikeLischke thanks for your advice,and I can't agree more, but please forget user-expierence, because I couldn't persuade my boss to give it up, so any advice on how to make it? – Gaojin Sep 24 '13 at 10:49
  • Actually, won't NSSecureTextField accept any characters that NSTextField accepts, including non ASCII? – JeremyP Sep 25 '13 at 10:50
  • @JeremyP you can set it only allows Roman characters in Attributes inspector, after that, you will be not allowed to change your input method to type in non ASCII. that's why I think disabling paste attributes is enough. – Gaojin Sep 26 '13 at 02:26
  • 1
    If the user can't paste in a password from the Keychain or 1Password, they are going to choose a less secure password so that they can remember and easily type it. This will make your application less secure—it will be easier to brute-force guess a user's password. – Peter Hosey Sep 30 '13 at 02:35
  • 1
    You say that neither of these solutions worked. What happened instead? – Peter Hosey Sep 30 '13 at 02:35

1 Answers1

0

In your textfield delegate method check the menu item paste tag value if it should be match then don't allow to paste character into your specific NSSecureTextField below:-

1) Set the tag value of menuitem paste in mainmenu.xib as attached in the screenshot and then impelement the below method:-

enter image description here

-(void)controlTextDidChange:(NSNotification *)obj
{
    NSMenu *mainMenu = [[NSApplication sharedApplication]mainMenu];
    NSMenu *appMenu = [[mainMenu itemAtIndex:2]submenu];
    BOOL isAllowPaste=YES;
    NSLog(@"%@", [appMenu title]);
    for (NSMenuItem *item in [appMenu itemArray]) {
        if ([item tag] ==1)
        {
            NSLog(@"%@", [item title]);
            isAllowPaste=NO;
        }

    }
    if (isAllowPaste==NO && [obj object]==secureTextField)
    {
            NSLog(@"Cannot paste");
           isAllowPaste=YES;
    }
    }
Hussain Shabbir
  • 14,801
  • 5
  • 40
  • 56
  • where should I implement it, I get confused while scaning the document. and no matter in the subclass of `NSSecureTextField` or in the'NSWindowController',it couldn't be triggered. – Gaojin Sep 25 '13 at 08:19
  • You can write in your securetextfield subclass as well – Hussain Shabbir Sep 25 '13 at 08:42
  • 1
    You should not go around disabling other menu items when asked to validate a specific one. – Peter Hosey Sep 30 '13 at 02:34
  • @peter Hosey,ok then according to you what will be the best answer for this. Please paste the code. – Hussain Shabbir Sep 30 '13 at 04:30
  • You would check if the `title` of the parameter is `@"Paste"` and return `NO` if it is. This would use less code and would use the API as it was intended. – BergQuester Oct 18 '13 at 01:19
  • @peter Hosey have updated the code . Please have a look once and let me know if still i am going on wrong track:) – Hussain Shabbir Oct 23 '13 at 10:25
  • @BergQuester, Please have a look once and let me know if still i am going on wrong track:) – Hussain Shabbir Oct 23 '13 at 10:26
  • @BergQuester: Comparing the title is wrong; the title of the menu item for pasting may not be “Paste” depending on what localizations the app has and on the user's language settings. – Peter Hosey Oct 23 '13 at 19:15
  • Aside from the problem of comparing a menu item title to a constant string (see above), you're also storing your validation result in a local variable and never using it. An empty method would be equivalent. Also, where you wrote `isAllowPaste`, you meant `disallowPaste`. – Peter Hosey Oct 23 '13 at 19:17
  • Gah, should have said `tag` then. ;-) – BergQuester Oct 23 '13 at 19:41
  • @BergQuester, Now i have modified the code checking tag value. Please follow and let me know, if still i am going on wrong track – Hussain Shabbir Oct 24 '13 at 13:05
  • Tag is better than title, enough that I've taken off my downvote, but the best way is to compare the menu item's action using `sel_isEqual`. The menu item whose action is `paste:` is the Paste menu item, regardless of its title and without having to set a tag (and make sure you don't use it anywhere else). (I also wouldn't hard-code the third menu as the one to search for it. I'd search all of the menus, so as not to assume that there will never be another menu inserted before File or Edit.) – Peter Hosey Oct 24 '13 at 18:36