3. The View and Controller Layers

The user interface (UI) is the same as in the plain JavaScript validation app project discussed in Part 2 of the tutorial (or in Chapter 3 of the book). There is only one difference. For responsive constraint validation, where input event handlers are used to check constraints on user input, the generic check functon Book.check is used:

pl.view.createBook = {
  setupUserInterface: function () {
    var formEl = document.forms['Book'],
        submitButton = formEl.commit;
    submitButton.addEventListener("click", 
        this.handleSubmitButtonClickEvent);
    formEl.isbn.addEventListener("input", function () { 
        formEl.isbn.setCustomValidity( 
            Book.check("isbn", formEl.isbn.value).message);
    });
    formEl.title.addEventListener("input", function () { 
        formEl.title.setCustomValidity( 
            Book.check("title", formEl.title.value).message);
    });
   ...
  },
};

While the validation on user input enhances the usability of the UI by providing immediate feedback to the user, validation on form submission is even more important for catching invalid data. Therefore, the event handler handleSubmitButtonClickEvent() performs the property checks again, as shown in the following program listing:

handleSubmitButtonClickEvent: function () {
  var formEl = document.forms['Book'];
  var slots = { isbn: formEl.isbn.value, 
        title: formEl.title.value,
        year: formEl.year.value,
        edition: formEl.edition.value
  };
  // set error messages in case of constraint violations
  formEl.isbn.setCustomValidity( Book.check( "isbn", slots.isbn).message);
  formEl.title.setCustomValidity( Book.check( "title", slots.title).message);
  formEl.year.setCustomValidity( Book.check( "year", slots.year).message);
  formEl.edition.setCustomValidity( Book.check( "edition", slots.edition).message);
  // save the input data only if all of the form fields are valid
  if (formEl.checkValidity()) {
    Book.add( slots);
  }
}