2
\$\begingroup\$

I need to run the following checks in two occasions:

  1. When a certain modal is first shown or clicked,
  2. When one of two inputs is filled.

How can I remove redundancy in the following code?

jQuery(document).ready( function($) {
 $(document.body).on( 'DOMNodeInserted click', '.media-modal', function( event ) {
 var test = $('label.setting[data-setting=alt] input:visible').val();
 var test2 = $('input[data-setting=alt]:visible').val();
 if (!test && !test2) {
 $('.media-modal .media-button-insert').prop("disabled",true);
 $('.media-modal .media-button-select').prop("disabled",true);
 } else {
 $('.media-modal .media-button-insert').prop("disabled",false);
 $('.media-modal .media-button-select').prop("disabled",false);
 }
 $(document.body).on( 'input propertychange paste', 'label.setting[data-setting=alt] input, input[data-setting=alt]', function( event ) {
 var test = $('label.setting[data-setting=alt] input:visible').val();
 var test2 = $('input[data-setting=alt]:visible').val();
 if (!test && !test2) {
 $('.media-modal .media-button-insert').prop("disabled",true);
 $('.media-modal .media-button-select').prop("disabled",true);
 } else {
 $('.media-modal .media-button-insert').prop("disabled",false);
 $('.media-modal .media-button-select').prop("disabled",false);
 }
 });
 });
});
200_success
145k22 gold badges190 silver badges478 bronze badges
asked Jun 19, 2017 at 19:04
\$\endgroup\$

2 Answers 2

2
\$\begingroup\$

I would write it as something like:

jQuery(document).ready( function($) {
 function updateDisabled() {
 var test = $('label.setting[data-setting=alt] input:visible').val();
 var test2 = $('input[data-setting=alt]:visible').val();
 var disabled = !test && !test2;
 $('.media-modal .media-button-insert').prop("disabled", disabled);
 $('.media-modal .media-button-select').prop("disabled", disabled);
 } 
 $(document.body).on( 'DOMNodeInserted click', '.media-modal', updateDisabled);
 $(document.body).on( 'input propertychange paste', 'label.setting[data-setting=alt] input, input[data-setting=alt]', updateDisabled);
}

You could also rewrite:

$('.media-modal .media-button-insert').prop("disabled", disabled);
$('.media-modal .media-button-select').prop("disabled", disabled);

As

$('.media-modal .media-button-insert, .media-modal .media-button-select').prop("disabled", disabled);

(Although I prefer keeping them separate) or maybe better giving your buttons an extra class and writing:

$('.media-modal .media-button').prop("disabled", disabled);
answered Jun 19, 2017 at 22:58
\$\endgroup\$
1
  • \$\begingroup\$ Amazing, exactly what I needed! Thanks! I also rewrote the var lines as a single line. \$\endgroup\$ Commented Jun 21, 2017 at 0:46
2
\$\begingroup\$

Marc's answer is pretty much what I would have posted, except his code differs from yours in that your input/paste/propertychange handler is not registered until after the node/click handler. He did that because yours is going to register that inner event handler over and over exponentially every time there's a click. You can fix that by removing the handler after it's no longer needed.

jQuery(document).ready( function($) {
 function updateDisabled() {
 var test = $('label.setting[data-setting=alt] input:visible').val();
 var test2 = $('input[data-setting=alt]:visible').val();
 var disabled = !test && !test2;
 $('.media-modal .media-button-insert').prop("disabled", disabled);
 $('.media-modal .media-button-select').prop("disabled", disabled);
 } 
 $(document.body).on( 'DOMNodeInserted click', '.media-modal', function(){
 updateDisabled();
 $(document.body).on( 'input propertychange paste', 'label.setting[data-setting=alt] input, input[data-setting=alt]', function(){
 updateDisabled();
 $(document.body).off('input propertychange paste', 'label.setting[data-setting=alt] input, input[data-setting=alt]');
 });
 });
}
answered Jun 20, 2017 at 0:24
\$\endgroup\$
3
  • \$\begingroup\$ Thanks for calling my attention to the unnecessary event nesting! \$\endgroup\$ Commented Jun 20, 2017 at 13:54
  • \$\begingroup\$ Wouldn't this only handle the first change to the input as you disable the event afterwards? \$\endgroup\$ Commented Jun 21, 2017 at 4:36
  • \$\begingroup\$ Yes. But the even is registered again when the element is clicked. It's hard to tell wht the OP wanted. \$\endgroup\$ Commented Jun 21, 2017 at 11:21

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.