[RESOLVED] Run Validations onChange of another field

Good day!

I have a complex validation issue which I can't fix.

Here is my scenario:

I have a drop-down field called 'Staff group'

IF user select Medical & dental from the 'Staff Group' it shows the two single choice hours selectors (see below):

If user selects 'Hours' it will show two hours fields, I want it to validate fields under that choice.

If users select 'PAs', it will show two PAs fields, I want it to validate the fields under that choice.

I have typed up this code to handle both the Hours and PA's

fd.field('NewPAs').validators.push({
    name:"",
    error:"",
    validate: function(value){
        if (fd.field('Main_Staff_Group').value == "Medical & Denatal"){
            if (fd.field("Choice").value == "PAs"){
                if (fd.field('CurrentPAs').value == fd.field('NewPAs').value){
                return false;
                this.error= "Please note Current PAs and New PAs cannot be the same"
                }
                return true;
            }
            if (fd.field("Choice").value == "Hours"){
                if (fd.field('Current_Hours').value == fd.field('PSNewHours').value){
                return false;
                this.error = "Please note Current Hours and New Hours cannot be the same"
                }
            }
        }
    }
});

Here is a screenshot of the form:

image

UPDATE:

I have also tried this code, but no luck.

function validateHours(){
    if (fd.field("Main_Staff_Group").value == "Medical & Dental"){
        if (fd.field("Choice").value == "Hours"){
            fd.field('Current_Hours').required = true;
            fd.field('PSNewHours').required = true;
        }
         if (fd.field("Choice").value == "PAs"){
            fd.field('CurrentPAs').required = true;
            fd.field('NewPAs').required = true;
        }
    }
}

fd.field('Choice').$on('change',validateHours);

I have also tried this:

//validte Hours
fd.field('PSNewHours').validators.push({
    name: '',
    error: 'Please note Current Hours and New Hours cannot be the same.',
    validate: function(value) {
        
        if (fd.field('Choice').value == "Hours"){
        fd.field('CurrentPAs').clear();
        fd.field('NewPAs').clear();
        console.log(value)
         if(value < 0 || value > 40 ){
            return false;
        }
        return true;
        }
        }
});

//validte Hours
fd.field('NewPAs').validators.push({
    name: '',
    error: 'Please note Current PAs and New PAs cannot be the same.',
    validate: function(value) {
        
        if (fd.field('Choice').value == "PAs"){
        fd.field('Current_Hours').clear();
        fd.field('PSNewHours').clear();
        console.log(value)
         if(value < 0 || value > 10 ){
            return false;
        }
        return true;
        }
        }
});

//This will validate the Hours field
fd.field('PSNewHours').addValidator({
        name: '',
        error: '',
        validate:function(value){
            if(fd.field("Main_Staff_Group").value == "Medical & Dental"){
                if (fd.field("Choice").value == "Hours"){
                    if (fd.field("Current_Hours") < 0 && fd.field("Current_Hours").value > 40
                    || fd.field("PSNewHours") < 0 && fd.field("PSNewHours").value > 40){
                    return false
                    this.error = "Please enter a value between 0 and 40"
                    }
                }
            }
        }
});

Ideally, I want to set-up a threshold for the fields. That would be amazing!

I think what you want to do here is push the validators through the "on change" event for your choice field. If your selection is Hours, push Hours validators and your two other validators should be set to fd.field('CurrentPAs').validators.length = 0; and so on. Make sense?

1 Like

Hi @cwalter2,

hmmm, I think I understand what you mean but I'm not sure how to write the syntax for this scenario. I have gained a little confidence on writing functions but the syntax still throws me overboard, especially when it comes to the more complex scenarios.

Dear @DryChips,
Your original code looks correct to me, although, you should not put anything after return statements - they exit the function. Put this.error = 'something'; before the return.

Are you sure there are no typos? Like in this line:
if (fd.field('Main_Staff_Group').value == "Medical & Denatal"){

Also, what's the field type of Choice and Main_Staff_Group fields? Are they both Choice type fields or Lookup fields?

HI Nikita,

Yep, I spotted the typo.

The main staff group is a drop-down choice field and the choice field is a single choice field.

Dear @DryChips,
So this validation should work, though it will only run on save:

fd.spRendered(function(){
  fd.validators.push({
    name:"MyValidator",
    error:"",
    validate: function(value){
        if (fd.field('Main_Staff_Group').value == "Medical & Dental"){
            if (fd.field("Choice").value == "PAs"){
                if (fd.field('CurrentPAs').value == fd.field('NewPAs').value){
                  this.error = "Please note Current PAs and New PAs cannot be the same"
                  return false;
                }
                return true;
            }
            if (fd.field("Choice").value == "Hours"){
                if (fd.field('Current_Hours').value == fd.field('PSNewHours').value){
                  this.error = "Please note Current Hours and New Hours cannot be the same"
                  return false;
                }
                return true;
            }
        }
    }
  });
});

Leave just this code on the form, and check browser's console for errors if it doesn't work.

Hi Nikita,

So the code works in my sandpit but only when I try to hit "submit" as you have mentioned. Is there no way to validate this before moving to another wizard?

If I select a different staff group, I only want to validate the Current Hours and New hours field and not the Current PAs and New PAs fields. If I select a different staff group, it validates the Current PA's and New PAs as well when those fields are hidden.

I'll try to elaborate a bit more on my scenarios:

If users select Medical & Dental in staff group ==> Single Choice Option will appear with Hours and PA's options.

image

If users select a different staff group ==> Only Current Hours and New Hours is displayed. The Current PAs and New PAs are hidden because they're only applicable to Medical staff.

I want to validate the fields dynamically based on the selection that is made from the Main Staff group.

I hope that's clearer.

Dear @DryChips,
Validation has nothing to do with hiding/showing fields, that should be separate code:

function hideShowHours(){
    //first hide all
    $(fd.field('Current_Hours').$parent.$el).hide();
    $(fd.field('PSNewHours').$parent.$el).hide();
    $(fd.field('CurrentPAs').$parent.$el).hide();
    $(fd.field('NewPAs').$parent.$el).hide();
        
    //make not required
    fd.field('Current_Hours').required = false;
    fd.field('PSNewHours').required = false;
    fd.field('CurrentPAs').required = false;
    fd.field('NewPAs').required = false;

    if (fd.field("Main_Staff_Group").value == "Medical & Dental"){
        if (fd.field("Choice").value == "Hours"){
            $(fd.field('Current_Hours').$parent.$el).show();
            $(fd.field('PSNewHours').$parent.$el).show();
            fd.field('Current_Hours').required = true;
            fd.field('PSNewHours').required = true;
        }
         if (fd.field("Choice").value == "PAs"){
            $(fd.field('CurrentPAs').$parent.$el).show();
            $(fd.field('NewPAs').$parent.$el).show();
            fd.field('CurrentPAs').required = true;
            fd.field('NewPAs').required = true;
        }
    }
}

fd.field('Choice').$on('change',hideShowHours);

If you want validation to run on Wizard step change, you need to write a custom validator for each field, something like this:

fd.spRendered(function(){
  fd.field('CurrentPAs').validators.push({
    name:"CurrentPAsValidator",
    error:"",
    validate: function(value){
        if (fd.field('Main_Staff_Group').value == "Medical & Dental"){
            if (fd.field("Choice").value == "PAs"){
                if (fd.field('CurrentPAs').value == fd.field('NewPAs').value){
                  this.error = "Please note Current PAs and New PAs cannot be the same"
                  return false;
                }
            }
        }
       return true;
    }
  fd.field('Current_Hours').validators.push({
    name:"Current_HoursValidator",
    error:"",
    validate: function(value){
        if (fd.field('Main_Staff_Group').value == "Medical & Dental"){
            if (fd.field("Choice").value == "Hours"){
                if (fd.field('Current_Hours').value == fd.field('PSNewHours').value){
                  this.error = "Please note Current Hours and New Hours cannot be the same"
                  return false;
                }
            }
        }
       return true;
    }
  });
1 Like

Hi Nikita,

Thank you very much.

I have been able to cook up this code and it has resolved my issue.

I'll share this for other users, should they come across the same scenario:

//Custom Error Message ‘Current Hours and New Hours cannot be the same’ 
fd.field('PSNewHours').validators.push({
    name: '',
    error: 'New Hours cannot be the same as Current Hours.',
    validate: function(value) {
        if (fd.field('Current_Hours').value == fd.field('PSNewHours').value 
        && (fd.field("Choice").value == "Hours")){
            return false;
        }
        return true;
        
    }
});

//Sets threshold for Current Hours field 
fd.field('Current_Hours').validators.push({
    name: '',
    error: 'Please enter a value between 0 and 40.',
    validate: function(value) {
        if (fd.field('Current_Hours').value <0 || fd.field('Current_Hours').value >40
        && (fd.field("Choice").value == "Hours")){
            return false;
        }
        return true;
        
    }
});
1 Like