Can't get anything from New-PasswordBox

May 16, 2013 at 6:14 PM
I have a very simple password entry window where users enter a password and have to confirm it as well but I get no output from it
$Pswd = Uniformgrid -Controlname Get-Passwords -Columns 2 {

"Enter Password"
New-PasswordBox -Name EnterPassword
"Confirm Password"
New-PasswordBox" -Name ConfirmPassword
" "
New-Button "OK" -On_click { get-ParentControl | Set-UIValue -passthru | Close-Cotrol}

} -show
Also, how will the password be saved, is it a secure string?

Thank you,

Mike
Coordinator
May 17, 2013 at 9:46 PM
Hopefully someone can post a reply to this before I can, but if not, I'll get you an answer tomorrow night (I only have internet for a minute at a time right now, so I'm just queueing this, and I'll come back Friday).
Coordinator
May 19, 2013 at 4:46 AM
Ok, so. This one's an interesting question, there are a few problems with your code:

First of all, the PasswordBox doesn't have a "Text" property, and so our built-in Get-UIValue isn't going to find the value. (You're calling Set-UIValue without a value, which will recurse the children and try to Get-UIValue from each of them -- if they were TextBoxes, that code would work). I will fix that, but there's a plain text password, and a secure string password... I'll go with the SecureString, but you probably still won't want to use the code above, because you'll just get two secure strings.

You need to implement some sort of logic that would actually ensure your user enters the same thing in both password boxes, and then handle returning a SINGLE secure string. My suggestion is that what you really want to do is write what we call a "Custom Control" which is a panel that wraps the labels and PasswordBoxes that you've got there, and does the validation etc. I've been wanting to write an article about our custom control system, and this is a great example because it's so simple (just two controls in it, and they're the same type), but so necessary because of the logic needed. Anyway, I'll write that up and blog it ... but in the meantime, here's an example that works:
Grid -Controlname Get-Passwords -Rows "Auto","Auto",5,"Auto" -Columns "Auto",100 -Margin 3 {

    New-Label "Enter Password"
    New-PasswordBox -Name EnterPassword -Column 1

    New-Label "Confirm Password" -Row 1
    New-PasswordBox -Name ConfirmPassword -Column 1 -Row 1

    New-Button "OK" -Column 1 -Row 3 -On_Click { 
        if( $EnterPassword.Password -eq $ConfirmPassword.Password) {
            Get-ParentControl | Set-UIValue -Value $EnterPassword.SecurePassword -passthru | Close-Control 
        } else {
            $ConfirmPassword.Clear()
        }
    }
} -show
I used a Grid instead of a UniformGrid just because I hate the look of UniformGrid ... other than that, the change is just the click handler for the button. Note that the case where they're not the same is being handled really crudely here, I just clear the box -- I'll think of something nicer when I blog about it ;-)
May 22, 2013 at 1:33 PM
Thank you for the response, it is very clear. I was going to put the above script in a function and return the secure password, I assume all I have to do is the following:
Function ValidatePswd
{
$ValidPswd = Grid -Controlname Get-Passwords -Rows "Auto","Auto",5,"Auto" -Columns "Auto",100 -Margin 3 {

    New-Label "Enter Password"
    New-PasswordBox -Name EnterPassword -Column 1

    New-Label "Confirm Password" -Row 1
    New-PasswordBox -Name ConfirmPassword -Column 1 -Row 1

    New-Button "OK" -Column 1 -Row 3 -On_Click { 
        if( $EnterPassword.Password -eq $ConfirmPassword.Password) {
            Get-ParentControl | Set-UIValue -Value $EnterPassword.SecurePassword -passthru | Close-Control 
        } else {
            $ConfirmPassword.Clear()
        }
    }
} -show

Return $ValidPswd
}
Great product and Thanks for everything.

Mmike
Coordinator
May 22, 2013 at 5:30 PM
That should work ... you don't need to assign it to a variable, actually -- you can just do `function NewPassword { Grid ... -show }`