Scrolling to the errors – Making XPages Error Handling more user friendly

In this article I will demonstrate how to easily improve the server side form validation process from a user’s perspective.

Introduction

I have to admit that I am not a fan of server side validation. While it suits the developer, it is often not a good user experience. If you complete a large form, hit submit and you have errors returned, it is had to ascertain where the error has occurred. This causes the user to have to scroll up and down the page looking for the error. In an ideal world the form needs to be validated fornt end and back end to provide the optimal experience, while ensure data integrity within the application.

When building the PSC Contest site http://contest.psclistens.com I wanted to make the server side validation as painless as possible for users.

Basic Server side XPages validation

To validate a field on an XPage we use validators and a custom message. In the following example, when the user submits a blank field, an error message will be returned and the JSF validation will prevent the form from saving.

<xp:inputText styleClass="form-control"  disableTheme="true"  value="#{competition.First}"
	id="first1">
	<xp:this.attrs>
		<xp:attr name="placeholder"
			value="Contact First Name">
		</xp:attr>
	</xp:this.attrs>
	<xp:this.validators>
		<xp:validateRequired loaded="true" message="This value is required">
		</xp:validateRequired>
	</xp:this.validators>
</xp:inputText>
<xp:message id="message6" for="first1"
	styleClass="error">
</xp:message>

Here is an example of the failing field. I have assigned a class = “error” to the message and that styles it red and bold.
c1

Scrolling to the error message

Within the onComplete event of the form’s submit button we can add some code to determine if there are any errors. If there are errors we can use some jQuery to “scrollTo()” the message on the screen and it is revealed to the user.

  • The code var temp = $(‘.error:visible’) selects all the error message which are visible to the user.
  • If the length of the selector is greater than 0 there must be an error on the page
  • So determine where it is on the page temp.eq(0).offset().top-250 and then
  • Animate a scroll to the element.
  • http://api.jquery.com/scrolltop/ tells us that we are able to ascertain the scroll bar height of the element and  “Setting the scrollTop positions the vertical scroll of each matched element.”
<xp:button value="Submit" styleClass="btn btn-primary theSubmit" id="button1">
	<xp:eventHandler event="onclick"
		submit="true" refreshMode="partial" immediate="false"
		save="true" refreshId="container">
		<xp:this.onComplete>
			<![CDATA[
				//Check to see if there are any errors
				var temp = $('.error:visible')
				if (temp.length >0){
					$('html, body').animate({scrollTop: temp.eq(0).offset().top-250}, 1000, function(){
					});
				} else {
					alert('Thank you for your submission. PSC will be in touch.')
					location.href="http://www.psclistens.com"
				}
			]]>
		</xp:this.onComplete>
		<xp:this.script><![CDATA[
			//check to see if project sponsor is checked
			if ($('.projectSponsor').is(':checked')){
				console.log('sponsor check')
				app.checkSponsor()
			}
		]]></xp:this.script>
	</xp:eventHandler>
</xp:button>

If there are no errors the user is thanked and redirected to the PSC homepage.

Don’t do a complete submit….

The only way we are able to run an “onComplete” on the button event handler is if we do not submit the entire form. If we do this then all the code will be lost and the page will revert to the top of the page.

Wrap the body of the form in a panel or div which can be refreshed.  Set the button click to partial refresh that section. This way the scroll position on the page will not be lost when the button is clicked.

 

c2

The contest site

Check out the contest site http://contest.psclistens.com before 13 Feb 2015 when PSC will announce the winner

 

5 thoughts on “Scrolling to the errors – Making XPages Error Handling more user friendly

    • Which btw was one line of code – due to the consistent way the form is structured it is easy to find the field related to the error.

      From the error message – go up to the container DIV and then find the for form-control within.

      Love me some jQuery🙂

      temp.eq(0).closest(‘div’).find(‘.form-control’).focus()

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s