0

Hi guys I would like to scroll to the first erroneous input on the product page. Currently it doesn't and stays at the bottom.

You then have to manually scroll up till you see the swatch option group that is not selected. So, no visual cue to show at bottom.

I tried to run a on DOMNodeInserted function to see if it has class validation-advice. And if so run the scroll to element.

Didn't works as expected.

So would anyone how know to edit the validation script bottom of product view page in rwd theme or validation.js in magento-root/js/varien/prototype to scroll to the first input/ swatch where this is required is shown.

UPDATE:

Using the answer below I attempted to scroll to the first error (First element element without swatch select).

But, it doesn't work, as previous validation is still being used thus add to cart has to be pressed twice, logically working one step back.

console.log(jQuery(".validation-advice:not([style])")); 

Using this line I logged the following:

console log for error

Showing that first submit returns no element, even though on purpose iv'e selected no swatches, so every option has error. Second submit picks up the error elements. Then I have chosen a swatch for the first option and pressed add to cart again, still it hasn't picked up that the first element no longer has error, the second submit picks it up. This trend continues throughout.

Is the else in the wrong place ?

1

Edit product template: /app/design/frontend/YOUR_PACKAGE/YOUR_THEME/template/catalog/product/view.phtml

find:

<script type="text/javascript">
    //<![CDATA[
        var productAddToCartForm = new VarienForm('product_addtocart_form');
        productAddToCartForm.submit = function(button, url) {
            if (this.validator.validate()) {
                var form = this.form;
                var oldUrl = form.action;

                if (url) {
                   form.action = url;
                }
                var e = null;
                try {
                    this.form.submit();
                } catch (e) {
                }
                this.form.action = oldUrl;
                if (e) {
                    throw e;
                }

                if (button && button != 'undefined') {
                    button.disabled = true;
                }
            } 
        }.bind(productAddToCartForm);

add

else {
      // do what you need to do e.g. scrollTop();
      // or scroll to id
      }

before

}.bind(productAddToCartForm);

Complete code

<script type="text/javascript">
    //<![CDATA[
        var productAddToCartForm = new VarienForm('product_addtocart_form');
        productAddToCartForm.submit = function(button, url) {
            if (this.validator.validate()) {
                var form = this.form;
                var oldUrl = form.action;

                if (url) {
                   form.action = url;
                }
                var e = null;
                try {
                    this.form.submit();
                } catch (e) {
                }
                this.form.action = oldUrl;
                if (e) {
                    throw e;
                }

                if (button && button != 'undefined') {
                    button.disabled = true;
                }
            } else {
                // do what you need to do e.g. scrollTop();
            }
        }.bind(productAddToCartForm);

That's all.

[Edit]

To achieve what you need just add before productAddToCartForm.submit

var myFormValidation = new Validation('product_addtocart_form');
//watch for select change
    $j(".super-attribute-select").on("change", function() {
    // check if .validation-failed class exist to prevent form validation before user click add to cart
    if ($j('.validation-failed').length ) {
          if ( !myFormValidation.validate()) {
            //form not validated,do your scroll stuff here.
           } else {
            //form is validated. remove this else if not needed
          }

    }
    });
| improve this answer | |
  • This has put me on the right path: I just need to pick up the first erroneous input. I tried var thefirsterror = $j('.validation-advice:first')[0].id; but magento just hides the first error, when corrected. So won't work correctly. – Vaishal Patel Sep 6 '16 at 9:05
  • I'm not sure if this is what you want to acomplish (sorry my english has seen better days) but if you need to target first erroneous select just find the first one with validation-failed class. However after you choose proper value for one option it doesn't autovalidate, you need to press Add To Cart. If you need to autovalidate selected option you need to write custom js function checking for select change. – Kaziko Sep 6 '16 at 13:24
  • I have this code in the else part: var thefirsterror = $j('.validation-failed:first').attr("id"); var theadvice = $j("#advice-required-entry-"+ thefirsterror); $j('html, body').animate({ scrollTop: $j(theadvice).offset().top }, 2000); That works but only on second click, is there a way to fire it after it has validated, instead of second click ? – Vaishal Patel Sep 6 '16 at 13:41
  • It fires on click because validation is run after submitting the form ( productAddToCartForm.submit ). To achieve what you want you need to write second js function where you need to check if there are .validation-failed (we need to give users a chance to select options and click submit without executing validation.). After that you need to execute validation and if the form doesnt validate do your stuff (scrolling). Something like – Kaziko Sep 7 '16 at 9:18
  • I exceedeed 5 minutes allowed for edit in prevoius comment so here is part two :) So you need to check if 'validation-failed' exists and on select change execute validation (you can target selects with 'super-attribute-select' class) and if the form doesnt validate do your stuff (scrolling). If you need sample code let me know in comment – Kaziko Sep 7 '16 at 9:27

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.