Advanced Progress Bar
A custom progress bar can be added to the form to enhance the user experience and indicate the remaining steps within the form. More features have been added to advance the functionalities of the progress bar.
Features added
ability to perform validity checks on all the components ( e.g. input component) in each tab component
ability to indicate error colour in case the validity checks fail
each progress bar step has a title that corresponds with the title of each tab of the tab component
Type A: Progress Bar with TabComponent
This Progress Bar is designed to work with TabComponent, and with the Next and Previous Button
Type B: Progress Bar with any Layout Component
This Progress Bar is designed to work with any layout component and with the Next and Previous Button
How does it work
Its functionality has been developed almost similarly to Formio Wizard. You switch between each layout using the Previous and Next buttons. It uses the hide attribute of each layout by setting it to true or false and using the triggerRedraw function to redraw the component to the screen.
Demo: https://submit.digital.gov.bc.ca/app/form/submit?f=539e778b-de05-4e49-b3f7-c8da16567dd1
Set Up
Type A
Step 1: Start by dragging an ‘HTML Component’ into the form builder.
Step2: change the ‘HTML tag’ field from p
to div
, and in the ‘Display’ tag enter a unique and custom class name in the ‘CSS Class. In this screenshot, we used “healthStepper”
Step 3: Copy the following code into the ‘Content’ section
<ol class="c-stepper">
<li class="c-stepper__item active">
<h3 class="c-stepper__title">Step 1</h3>
<p class="c-stepper__desc">Facility Information</p>
</li>
<li class="c-stepper__item disabled">
<h3 class="c-stepper__title">Step 2</h3>
<p class="c-stepper__desc">Bed Occupancy</p>
</li>
<li class="c-stepper__item disabled">
<h3 class="c-stepper__title">Step 3</h3>
<p class="c-stepper__desc">Staffing Level</p>
</li>
<li class="c-stepper__item disabled">
<h3 class="c-stepper__title">Step 4</h3>
<p class="c-stepper__desc">Operating Level</p>
</li>
<!-- Other steps -->
</ol>
Step 4: Click on the ‘Logic’ tab and click on the ‘Add Logic’ button
Step 5: Logic Name: enter any name
Step 6: In ‘Trigger' section, click on ‘Type’ dropdown menu, and select 'Javascript’
Step 7: Click “Add Action“ button
Step 8: Enter any name in “Action Name“
Step 9: In ‘Trigger' section, click on ‘Type’ dropdown menu, and select 'Javascript’
Step 10: Copy the following code into the ‘Text Area’ section
let cssId = 'myCss';
const head = document.getElementsByTagName('head')[0];
if (!document.getElementById(cssId))
{
const link = document.createElement('link');
link.id = cssId;
link.rel = 'stylesheet';
link.type = 'text/css';
link.href = 'https://timisenco2015.github.io/formulator.github.com/css/chefsCustom.css';
link.media = 'all';
head.appendChild(link);
const script = document.createElement('script');
script.type = 'text/javascript';
script.src = 'https://cdn.form.io/formiojs/formio.full.min.js';
head.appendChild(script);
}
Step 11: Click on ‘Save Logic’ and then ‘Save’ the component.
Step 12: Next, add a ‘Tabs’ component from the ‘Advanced Fields’ into the builder
Step 13: enter a unique name in the label field.
Step 14: Add as many tabs as you want and details for each tab added
Step 15: Under the ‘Logic’ tab, click on the ‘Add Logic’ button and add any ‘Logic Name’
Step 16:
I) Under 'Logic Name': enter any name
II) Under ‘Trigger', select ‘Type’ dropdown menu, and select 'Event’
Step 17: enter “change“ in the “Event Name“ field and click on “Add Action“ button
Step 18: Click on the “Add Action“ Button
Step 19: enter any name in the “Action Name“ field, select the “Type“ dropdown menu, and select the “Custom Action“
Step 20: paste lines of codes into the “Custom Action(Javascript)“ field
const { root} = instance;
root.setPristine(false);
const comp = root ? root.getComponent('data') : null;
const index = comp.currentTab;
const progressStepper = document.querySelectorAll(".healthStepper ol li");
leftOfIndex(index);
rightOfIndex(index, progressStepper.length)
progressStepper[index].classList.remove('errors');
progressStepper[index].classList.remove('disabled');
progressStepper[index].classList.add('active');
progressStepper[index].classList.remove('completed');
function leftOfIndex(index){
for(let i=0; i<index; i++) {
if(i===0) {
if(!validateFacilityInformationTabComponents()) {
progressStepper[i].classList.remove('completed');
progressStepper[i].classList.remove('disabled');
progressStepper[i].classList.remove('active');
progressStepper[i].classList.add('errors');
} else {
progressStepper[i].classList.remove('errors');
progressStepper[i].classList.remove('disabled');
progressStepper[i].classList.remove('active');
progressStepper[i].classList.add('completed');
}
} else {
progressStepper[i].classList.remove('errors');
progressStepper[i].classList.remove('disabled');
progressStepper[i].classList.remove('active');
progressStepper[i].classList.add('completed');
}
}
}
function rightOfIndex(index, endIndex){
for (let i=(endIndex-1); i>index; i--){
progressStepper[i].classList.remove('completed');
progressStepper[i].classList.remove('errors');
progressStepper[i].classList.remove('active');
progressStepper[i].classList.add('disabled');
}
}
function validateFacilityInformationTabComponents() {
const firstNameComp = root.getComponent('firstName');
const lastNameComp = root.getComponent('lastName');
let isAllFieldValue = true;
isAllFieldValue = firstNameComp.checkValidity();
isAllFieldValue = lastNameComp.checkValidity();
return isAllFieldValue;
}
Note
change the ‘data' in the
root.getComponent('data')
to the name you enter in the “label” field of the TabComponent in Figure A9
2. change the 'healthStepper' in the document.querySelectorAll(".healthStepper ol li")
to the name you enter in the “CSS Class“ field in Figure A1
3. in this demo, we are only validating two input components in the first tab of the TabComponent which is why this line of code if the index is equal to zero
3. the lines of codes below read the two input components in the first tab of the TabComponent and execute a validity check on them. See figure 1 for reference
Step 21: “Next Button“. Drag the button component to the builder, and change the label to “Next“. Under “Action“, click the dropdown and change select “Custom“
Step 22: copy and paste the lines of codes into “Button Custom Logic“ field
Note
change the ‘data' in the
form.getComponent('data')
to the name you enter in the “label” field of the TabComponent in Figure A9
2. change the 'healthStepper' in the document.querySelectorAll(".healthStepper ol li")
to the name you enter in the “CSS Class“ field in Figure A1
const progressStepper = document.querySelectorAll(".healthStepper ol li");
Step 23: “Previous Button“. Drag the button component to the builder, and change the label to “Previous“. Under “Action“, click the dropdown and change select “Custom“
Step 24: copy and paste the lines of codes into “Button Custom Logic“ field
Note
change the ‘data' in the
form.getComponent('data')
to the name you enter in the “label” field of the TabComponent in Figure A9
2. change the 'healthStepper' in the
document.querySelectorAll(".healthStepper ol li")
to the name you enter in the “CSS Class“ field in Figure A1
const progressStepper = document.querySelectorAll(".healthStepper ol li");
Type B: Progress Bar with Any Layout Component.
This Progress Bar is designed to work with TabComponent, and with the Next and Previous Button
Step 1: Start by dragging an ‘HTML Component’ into the form builder.
Step2: change the ‘HTML tag’ field from p
to div
, and in the ‘Display’ tag enter a unique and custom class name in the ‘CSS Class. In this screenshot, we used “healthStepper”
Step 3: Copy the following code into the ‘Content’ section
Step 4: Click on the ‘Logic’ tab and click on the ‘Add Logic’ button
Step 5: Logic Name: enter any name
Step 6: In ‘Trigger' section, click on ‘Type’ dropdown menu, and select 'Javascript’
Step 7: Click “Add Action“ button
Step 8: Enter any name in “Action Name“
Step 9: In ‘Trigger' section, click on ‘Type’ dropdown menu, and select 'Javascript’
Step 10: Copy the following code into the ‘Text Area’ section
Step 11: Click on ‘Save Logic’ and then ‘Save’ the component.
Step 12: Next, add a ‘Tabs’ component from the ‘Advanced Fields’ into the builder
Step 13: “Previous Button“. Drag the button component to the builder, and change the label to “Previous“. Under “Action“, click the dropdown and change select “Custom“
Step 14: copy and paste the lines of codes into “Button Custom Logic“ field
Step 15: “Next Button“. Drag the button component to the builder, and change the label to “Next“. Under “Action“, click the dropdown and change select “Custom“
Step 16: copy and paste the lines of codes into “Button Custom Logic“ field
Note: replace this array with an array of layout components you want to hide and show using the “Previous“ and “Next“ button.