diff --git a/src/js/_enqueues/admin/user-profile.js b/src/js/_enqueues/admin/user-profile.js
index b73f2ab5c4..3e9797b1a0 100644
a
|
b
|
|
14 | 14 | $toggleButton, |
15 | 15 | $submitButtons, |
16 | 16 | $submitButton, |
17 | | currentPass; |
| 17 | currentPass, |
| 18 | $passwordWrapper; |
18 | 19 | |
19 | 20 | function generatePassword() { |
20 | 21 | if ( typeof zxcvbn !== 'function' ) { |
21 | 22 | setTimeout( generatePassword, 50 ); |
22 | 23 | return; |
23 | | } else if ( ! $pass1.val() ) { |
24 | | // zxcvbn loaded before user entered password. |
| 24 | } else if ( ! $pass1.val() || $passwordWrapper.hasClass( 'is-open' ) ) { |
| 25 | // zxcvbn loaded before user entered password, or generating new password. |
25 | 26 | $pass1.val( $pass1.data( 'pw' ) ); |
26 | 27 | $pass1.trigger( 'pwupdate' ); |
27 | 28 | showOrHideWeakPasswordCheckbox(); |
28 | | } |
29 | | else { |
| 29 | } else { |
30 | 30 | // zxcvbn loaded after the user entered password, check strength. |
31 | 31 | check_pass_strength(); |
32 | 32 | showOrHideWeakPasswordCheckbox(); |
33 | 33 | } |
34 | 34 | |
| 35 | // Install screen. |
35 | 36 | if ( 1 !== parseInt( $toggleButton.data( 'start-masked' ), 10 ) ) { |
| 37 | // Show the password not masked if admin_password hasn't been posted yet. |
36 | 38 | $pass1.attr( 'type', 'text' ); |
37 | 39 | } else { |
| 40 | // Otherwise, mask the password. |
38 | 41 | $toggleButton.trigger( 'click' ); |
39 | 42 | } |
40 | 43 | |
… |
… |
|
56 | 59 | |
57 | 60 | currentPass = $pass1.val(); |
58 | 61 | |
| 62 | // Refresh password strength area |
59 | 63 | $pass1.removeClass( 'short bad good strong' ); |
60 | 64 | showOrHideWeakPasswordCheckbox(); |
61 | 65 | } ); |
… |
… |
|
84 | 88 | $pass1.attr( 'type', 'password' ); |
85 | 89 | resetToggle( true ); |
86 | 90 | } |
87 | | |
88 | | $pass1.focus(); |
89 | | |
90 | | if ( ! _.isUndefined( $pass1[0].setSelectionRange ) ) { |
91 | | $pass1[0].setSelectionRange( 0, 100 ); |
92 | | } |
93 | 91 | }); |
94 | 92 | } |
95 | 93 | |
96 | 94 | function bindPasswordForm() { |
97 | | var $passwordWrapper, |
98 | | $generateButton, |
| 95 | var $generateButton, |
99 | 96 | $cancelButton; |
100 | 97 | |
101 | 98 | $pass1Row = $( '.user-pass1-wrap, .user-pass-wrap' ); |
… |
… |
|
123 | 120 | $pass1 = $( '#user_pass' ); |
124 | 121 | } |
125 | 122 | |
126 | | /** |
| 123 | /* |
127 | 124 | * Fix a LastPass mismatch issue, LastPass only changes pass2. |
128 | 125 | * |
129 | 126 | * This fixes the issue by copying any changes from the hidden |
… |
… |
|
149 | 146 | |
150 | 147 | bindToggleButton(); |
151 | 148 | |
152 | | if ( $generateButton.length ) { |
153 | | $passwordWrapper.hide(); |
154 | | } |
| 149 | // Generate the first password and cache it, but don't set it yet. |
| 150 | wp.ajax.post( 'generate-password' ) |
| 151 | .done( function( data ) { |
| 152 | // Cache password |
| 153 | $pass1.data( 'pw', data ); |
| 154 | } ); |
155 | 155 | |
156 | 156 | $generateButton.show(); |
157 | 157 | $generateButton.on( 'click', function () { |
158 | 158 | updateLock = true; |
159 | 159 | |
160 | | $generateButton.hide(); |
161 | | $passwordWrapper.show(); |
| 160 | // Make sure the password fields are shown. |
| 161 | $generateButton.attr( 'aria-expanded', 'true' ); |
| 162 | $passwordWrapper |
| 163 | .show() |
| 164 | .addClass( 'is-open' ); |
162 | 165 | |
163 | 166 | // Enable the inputs when showing. |
164 | 167 | $pass1.attr( 'disabled', false ); |
165 | 168 | $pass2.attr( 'disabled', false ); |
166 | 169 | |
167 | | if ( $pass1.val().length === 0 ) { |
168 | | generatePassword(); |
169 | | } |
170 | | } ); |
171 | | |
172 | | $cancelButton = $pass1Row.find( 'button.wp-cancel-pw' ); |
173 | | $cancelButton.on( 'click', function () { |
174 | | updateLock = false; |
| 170 | // Set the password to the generated value |
| 171 | generatePassword(); |
175 | 172 | |
176 | | // Clear any entered password. |
177 | | $pass1.val( '' ); |
| 173 | // Show generated password in plaintext by default |
| 174 | resetToggle ( false ); |
178 | 175 | |
179 | | // Generate a new password. |
| 176 | // Generate the next password and cache |
180 | 177 | wp.ajax.post( 'generate-password' ) |
181 | 178 | .done( function( data ) { |
| 179 | // Cache password in data attribute |
182 | 180 | $pass1.data( 'pw', data ); |
183 | 181 | } ); |
| 182 | } ); |
184 | 183 | |
185 | | $generateButton.show().focus(); |
186 | | $passwordWrapper.hide(); |
187 | | |
188 | | $weakRow.hide( 0, function () { |
189 | | $weakCheckbox.removeProp( 'checked' ); |
190 | | } ); |
| 184 | $cancelButton = $pass1Row.find( 'button.wp-cancel-pw' ); |
| 185 | $cancelButton.on( 'click', function () { |
| 186 | updateLock = false; |
191 | 187 | |
192 | 188 | // Disable the inputs when hiding to prevent autofill and submission. |
193 | 189 | $pass1.prop( 'disabled', true ); |
194 | 190 | $pass2.prop( 'disabled', true ); |
195 | 191 | |
| 192 | // Clear password field and update the ui |
| 193 | $pass1.val( '' ).trigger( 'pwupdate' ); |
196 | 194 | resetToggle( false ); |
197 | 195 | |
| 196 | // Hide |
| 197 | $passwordWrapper |
| 198 | .hide() |
| 199 | .removeClass( 'is-open' ); |
| 200 | |
198 | 201 | if ( $pass1Row.closest( 'form' ).is( '#your-profile' ) ) { |
199 | | // Clear password field to prevent update. |
| 202 | // Clear password field to prevent update when form is submitted. |
200 | 203 | $pass1.val( '' ).trigger( 'pwupdate' ); |
| 204 | |
| 205 | // Stop an empty password from being submitted as a change |
201 | 206 | $submitButtons.prop( 'disabled', false ); |
202 | 207 | } |
203 | 208 | } ); |
… |
… |
|
399 | 404 | |
400 | 405 | window.generatePassword = generatePassword; |
401 | 406 | |
402 | | /* Warn the user if password was generated but not saved */ |
| 407 | // Warn the user if password was generated but not saved. |
403 | 408 | $( window ).on( 'beforeunload', function () { |
404 | 409 | if ( true === updateLock ) { |
405 | 410 | return __( 'Your new password has not been saved.' ); |
diff --git a/src/wp-admin/css/forms.css b/src/wp-admin/css/forms.css
index 2f03173491..5e18f508c1 100644
a
|
b
|
fieldset label, |
533 | 533 | margin: 0 0 1em; |
534 | 534 | } |
535 | 535 | |
| 536 | .wp-generate-pw { |
| 537 | margin-top: 1em; |
| 538 | } |
| 539 | |
| 540 | .wp-pwd { |
| 541 | margin-top: 1em; |
| 542 | } |
| 543 | |
536 | 544 | #misc-publishing-actions label { |
537 | 545 | vertical-align: baseline; |
538 | 546 | } |
diff --git a/src/wp-admin/user-edit.php b/src/wp-admin/user-edit.php
index 29e8f1a994..37869521a5 100644
a
|
b
|
endif; |
632 | 632 | <th><label for="pass1"><?php _e( 'New Password' ); ?></label></th> |
633 | 633 | <td> |
634 | 634 | <input class="hidden" value=" " /><!-- #24364 workaround --> |
635 | | <button type="button" class="button wp-generate-pw hide-if-no-js"><?php _e( 'Generate Password' ); ?></button> |
| 635 | <button type="button" class="button wp-generate-pw hide-if-no-js" aria-expanded="false"><?php _e( 'Set New Password' ); ?></button> |
636 | 636 | <div class="wp-pwd hide-if-js"> |
637 | 637 | <span class="password-input-wrapper"> |
638 | 638 | <input type="password" name="pass1" id="pass1" class="regular-text" value="" autocomplete="off" data-pw="<?php echo esc_attr( wp_generate_password( 24 ) ); ?>" aria-describedby="pass-strength-result" /> |
… |
… |
endif; |
641 | 641 | <span class="dashicons dashicons-hidden" aria-hidden="true"></span> |
642 | 642 | <span class="text"><?php _e( 'Hide' ); ?></span> |
643 | 643 | </button> |
644 | | <button type="button" class="button wp-cancel-pw hide-if-no-js" data-toggle="0" aria-label="<?php esc_attr_e( 'Cancel password change' ); ?>"> |
| 644 | <button type="button" class="button wp-cancel-pw hide-if-no-js" data-toggle="0" aria-label="<?php esc_attr_e( 'Cancel' ); ?>"> |
645 | 645 | <span class="dashicons dashicons-no" aria-hidden="true"></span> |
646 | 646 | <span class="text"><?php _e( 'Cancel' ); ?></span> |
647 | 647 | </button> |
… |
… |
endif; |
652 | 652 | <tr class="user-pass2-wrap hide-if-js"> |
653 | 653 | <th scope="row"><label for="pass2"><?php _e( 'Repeat New Password' ); ?></label></th> |
654 | 654 | <td> |
655 | | <input name="pass2" type="password" id="pass2" class="regular-text" value="" autocomplete="off" /> |
656 | | <p class="description"><?php _e( 'Type your new password again.' ); ?></p> |
| 655 | <input name="pass2" type="password" id="pass2" class="regular-text" value="" autocomplete="off" aria-describedby="pass2-desc" /> |
| 656 | <?php if ( IS_PROFILE_PAGE ) : ?> |
| 657 | <p class="description" id="pass2-desc"><?php _e( 'Type your new password again.' ); ?></p> |
| 658 | <?php else : ?> |
| 659 | <p class="description" id="pass2-desc"><?php _e( 'Type the new password again.' ); ?></p> |
| 660 | <?php endif; ?> |
657 | 661 | </td> |
658 | 662 | </tr> |
659 | 663 | <tr class="pw-weak"> |
… |
… |
endif; |
661 | 665 | <td> |
662 | 666 | <label> |
663 | 667 | <input type="checkbox" name="pw_weak" class="pw-checkbox" /> |
664 | | <span id="pw-weak-text-label"><?php _e( 'Confirm use of potentially weak password' ); ?></span> |
| 668 | <span id="pw-weak-text-label"><?php _e( 'Confirm use of weak password' ); ?></span> |
665 | 669 | </label> |
666 | 670 | </td> |
667 | 671 | </tr> |
diff --git a/src/wp-admin/user-new.php b/src/wp-admin/user-new.php
index 09ffdfeace..11fb9c3c61 100644
a
|
b
|
if ( current_user_can( 'create_users' ) ) { |
560 | 560 | </th> |
561 | 561 | <td> |
562 | 562 | <input class="hidden" value=" " /><!-- #24364 workaround --> |
563 | | <button type="button" class="button wp-generate-pw hide-if-no-js"><?php _e( 'Show password' ); ?></button> |
564 | | <div class="wp-pwd hide-if-js"> |
| 563 | <div class="wp-pwd"> |
565 | 564 | <?php $initial_password = wp_generate_password( 24 ); ?> |
566 | 565 | <span class="password-input-wrapper"> |
567 | | <input type="password" name="pass1" id="pass1" class="regular-text" autocomplete="off" data-reveal="1" data-pw="<?php echo esc_attr( $initial_password ); ?>" aria-describedby="pass-strength-result" /> |
| 566 | <input type="password" name="pass1" id="pass1" class="regular-text" autocomplete="off" data-reveal="1" data-pw="<?php echo esc_attr( $initial_password ); ?>" value="<?php echo esc_attr( $initial_password ); ?>" aria-describedby="pass-strength-result" /> |
568 | 567 | </span> |
569 | 568 | <button type="button" class="button wp-hide-pw hide-if-no-js" data-toggle="0" aria-label="<?php esc_attr_e( 'Hide password' ); ?>"> |
570 | 569 | <span class="dashicons dashicons-hidden" aria-hidden="true"></span> |
571 | 570 | <span class="text"><?php _e( 'Hide' ); ?></span> |
572 | 571 | </button> |
573 | | <button type="button" class="button wp-cancel-pw hide-if-no-js" data-toggle="0" aria-label="<?php esc_attr_e( 'Cancel password change' ); ?>"> |
574 | | <span class="dashicons dashicons-no" aria-hidden="true"></span> |
575 | | <span class="text"><?php _e( 'Cancel' ); ?></span> |
576 | | </button> |
| 572 | |
577 | 573 | <div style="display:none" id="pass-strength-result" aria-live="polite"></div> |
578 | 574 | </div> |
579 | 575 | </td> |
… |
… |
if ( current_user_can( 'create_users' ) ) { |
581 | 577 | <tr class="form-field form-required user-pass2-wrap hide-if-js"> |
582 | 578 | <th scope="row"><label for="pass2"><?php _e( 'Repeat Password' ); ?> <span class="description"><?php _e( '(required)' ); ?></span></label></th> |
583 | 579 | <td> |
584 | | <input name="pass2" type="password" id="pass2" autocomplete="off" /> |
| 580 | <input name="pass2" type="password" id="pass2" autocomplete="off" aria-describedby="pass2-desc" /> |
| 581 | <p class="description" id="pass2-desc"><?php _e( 'Type the password again.' ); ?></p> |
585 | 582 | </td> |
586 | 583 | </tr> |
587 | 584 | <tr class="pw-weak"> |