Visualforce Stage Indicator Component

Anonymous 

 5

Hello Everyone,

I designed a stage indicator component which will be useful to show stages or status progress on your page. You only need to include this component in your page and pass some parameters according to your requirements.

How to Use:

In visualforce page, include component and pass parameters. There are following parameters:
1) Stage Colors : For example, if you pass 3 colors(First color for previous stages, second for current stage, third for next remaining stages), into ‘colors’ parameter of component then :

<c:StageIndicator stages = "Prospecting, Qualification, Need Analysis, Value Proposition,  Negotiation, Closed Won" currentStage="Value Proposition" colors = "#9999ff, #00e500, silver"/> 

Output :

 
Stage Indicator

2) Stage Values(Comma seperated) : If you pass comma seperated values, then will show as above.
3) Current Stage Name (Required) : Passed current stage will be highlight in given color.
4) Stage Values(Field’s API Name of picklist type) : For example, you can pass field’s API name in ‘stageFieldName’ parameter.

 <c:StageIndicator stageFieldName = "Account.SLA__C" fontsize = "15px" currentStage="Silver"/>

Here, i used account’s SLA__c picklist type field and i didn’t pass ‘colors’ parameter then will use default.
Output :

1

5) Font Size : In above, i passed font size of stage name, if don’t give then will use default.
6) Indicator Height : You  can give height of Stage Indicator.
7) Indicator Width : You  can give width of Stage Indicator.
    For example,

  <c:StageIndicator stages = "Prospecting, Qualification, Need Analysis, Value Proposition,  Negotiation, Closed Won" fontsize = "18px" currentStage="Value Proposition" indicatorHeight = "50px" indicatorWidth = "150px"/>

Output :

1

If you not give values in colors, fontsize, height and width  then will use default values. And, if you give both comma seperated values and field’s api name then will give precedence to comma seperated values.

VisualForce Component :

<apex:component controller="StageIndicatorController" >
    <apex:pageMessages />
    <apex:attribute type="String" name="colors" assignTo="{!stageColors}" description="Current Color passed to controller" default="#4bca81,#0070d2,#eaedf4"/>
    <apex:attribute type="String" name="stages" assignTo="{!individualvalues}" description="Values passed to controller" />
    <apex:attribute type="String" name="currentStage" assignTo="{!currentValue}" description="Current Values passed to controller" required="true" />
    <apex:attribute type="String" name="stageFieldName" assignTo="{!fieldValues}" description="Field Values passed to controller"/>
    <apex:attribute type="String" name="fontSize" default="15px" description="Font Size passed from component"/>
    <apex:attribute type="String" name="indicatorHeight" default="30px" description="Height passed from component"/>
    <apex:attribute type="String" name="indicatorWidth" default="100px" description="Width passed from component"/>
    <style>
        ul li, ol li{
            margin-left: 0;
        }
        .indicator{ 
            list-style: none; 
            overflow: hidden; 
            font: {!fontSize} Helvetica, Arial, Sans-Serif;            
        }
        .indicator li { 
            float: left; 
        }
        
        .indicator li a {
            color: white;
            text-decoration: none; 
            padding: 5px 0 5px 65px;           
            height: {!indicatorHeight};
            line-height: {!indicatorHeight};
            width: {!indicatorWidth};
            position: relative; 
            display: block;
            text-align: center;
            vertical-align: middle;
            float: left;
        }
        
        .indicator li a:after { 
            content: " "; 
            display: block; 
            width: 0; 
            height: 0;
            border-top: 50px solid transparent;      
            border-bottom: 50px solid transparent;
            border-left: 30px solid;
            position: absolute;
            top: 50%;
            margin-top: -50px; 
            left: 100%;
            z-index: 2; 
        }
        .indicator li a:before { 
            content: " "; 
            display: block; 
            width: 0; 
            height: 0;
            border-top: 50px solid transparent;       
            border-bottom: 50px solid transparent;
            border-left: 32px solid white;
            position: absolute;
            top: 50%;
            margin-top: -50px; 
            margin-left: 1px;
            left: 100%;
            z-index: 1; 
        }
        .indicator li:first-child a {
            padding-left: 10px;
            border-radius: 30px 0px 0px 30px !important;
        }
        .fontwhite{
            color: #fff;
        }
        .fontgrey{
            color: #6e7f9e !important;

        } 
        .prevClass{
            background-color: {!prevClass};
            border-top-left-radius: 15px;
            border-bottom-left-radius: 15px;
        } 
        .nextClass{
            background-color: {!nextClass};            
        }
        .currClass{
            background-color: {!currClass};           
        }      
        .indicator li.prevClass a:after { 
            content: " "; 
            display: block; 
            width: 0; 
            height: 0;
            border-top: 50px solid transparent;      
            border-bottom: 50px solid transparent;
            border-left: 30px solid {!prevClass};
            position: absolute;
            top: 50%;
            margin-top: -50px; 
            left: 100%;
            z-index: 2; 
        }
        .indicator li.currClass a:after { 
            content: " "; 
            display: block; 
            width: 0; 
            height: 0;
            border-top: 50px solid transparent;      
            border-bottom: 50px solid transparent;
            border-left: 30px solid {!currClass};
            position: absolute;
            top: 50%;
            margin-top: -50px; 
            left: 100%;
            z-index: 2; 
        }
        .indicator li.nextClass a:after { 
            content: " "; 
            display: block; 
            width: 0; 
            height: 0;
            border-top: 50px solid transparent;      
            border-bottom: 50px solid transparent;
            border-left: 30px solid {!nextClass};
            position: absolute;
            top: 50%;
            margin-top: -50px; 
            left: 100%;
            z-index: 2; 
        }
    </style>    
    <!-- Display Stages of Indicator -->
    <ul class="indicator">     
      <apex:repeat value="{!valuesList}" var="vl">         
          <li class = "{!IF(vl.color == vl.prevColor, 'prevClass',IF(vl.color == vl.currColor, 'currClass','nextClass'))}">
              <a href="#" class = "{!IF(vl.color == vl.nextColor, 'fontgrey', 'fontWhite')}">                  
                  {!vl.valName}
              </a>
          </li>
      </apex:repeat>      
   </ul>
</apex:component>

Visualforce Page :

<apex:page sidebar="false">
    <c:StageIndicator stages = "Prospecting, Qualification, Need Analysis, Value Proposition,  Negotiation, Closed Won" fontsize = "18px" currentStage="Value Proposition" indicatorHeight = "50px" indicatorWidth = "150px"/>         
</apex:page>

Apex Class :

/**
        Name               :        StageIndicatorController
        Date               :        11th Jan, 2016
        Author             :        Ranu Agarwal (iBirds Software Services)
        Description        :        This class is used to show values in stage indicator.
**/
public class StageIndicatorController{
    
    //Color of Stages passed from component
    public String stageColors{
        get{return stageColors;}
        set{stageColors = value;}
    }
    //Comma seperated values from component
    public  string individualvalues{ 
        get{return individualvalues;}
        set{individualvalues = value;}
    }
    //Field API Name passed from component to get picklist values
    public  string fieldValues{ 
        get{return fieldValues;}
        set{fieldValues = value;}
    }
    //Current Value which is shown in different color passed from component
    public String currentValue{get;set;}
    
    public String prevClass{get;set;}
    public String currClass{get;set;}
    public String nextClass{get;set;}
    
    //Constructor
    public StageIndicatorController(){}
    //Getter to get values of stages 
    public List<StagesWrapper> getvaluesList(){
        try{
            if(!string.isBlank(stageColors) && stageColors.split(',').size() ==3){
                prevClass = stageColors.split(',').get(0).trim();
                currClass = stageColors.split(',').get(1).trim();
                nextClass = stageColors.split(',').get(2).trim();
            }
            List<StagesWrapper> stagesWrapperList = new List<StagesWrapper>();
            Boolean currentMatch = false;
            List<String> stagevalues = new List<String>();
            //If both comma seperated and API Name are blank
            if(string.isBlank(individualvalues) && string.isBlank(fieldValues)){
                ApexPages.Message myMsg = new ApexPages.Message(ApexPages.Severity.ERROR,'Please give values either in comma seperated or field API name.');
                ApexPages.addMessage(myMsg);
                return null;
            }
            //If API Name given otherwise default use comma seperated values
            if(string.isBlank(individualvalues) && !string.isBlank(fieldValues)){
                stagevalues = pickListValues();
            }else{
                stagevalues  = individualvalues.split(',');
            }
            //Fill model class with different colors according to stage's level
            for(String nm : stagevalues ){
                
                //For current value and previous values
                String colorCode = currentValue == nm.trim() ? currClass : prevClass;
                //For next remaining
                if(currentMatch) colorCode = nextClass;
                if(currentValue == nm.trim() && !currentMatch) currentMatch =  true;
                stagesWrapperList.add(new StagesWrapper(nm.trim(),colorCode,prevClass,currClass,nextClass));
            }
            return stagesWrapperList;
        }catch(Exception e){
            ApexPages.addMessages(e); 
            return null;
        }
    }
    //Method to get picklist values using object field's API name which is passed from component
    private List<String> pickListValues(){
    
        //for all values in the picklist list  
        List<String> valList = new List<String>();       
        Schema.sObjectType sObjType = Schema.getGlobalDescribe().get(fieldValues.substring(0, fieldValues.indexOf('.', 0)));    
        Map<String, Schema.SObjectField> field_map = sObjType.getDescribe().fields.getMap(); 
        List<Schema.PicklistEntry> pick_list_values = field_map.get(fieldValues.substring(fieldValues.indexOf('.', 0)+1, fieldValues.length())).getDescribe().getPickListValues();
        for (Schema.PicklistEntry a : pick_list_values) {                                        
            valList.add(a.getValue());
        }
        return valList;
    }
    //Wrapper class to show values of stages and color on page
    public class StagesWrapper{
    
        public String valName{get;set;}
        Public String color {get;set;}
        public String prevColor{get;set;}
        public String currColor{get;set;}
        public String nextColor{get;set;}
        public StagesWrapper(String vn,String c, String prevColor, String currColor, String nextColor){
            this.valName = vn;
            this.color = c;
            this.prevColor = prevColor;
            this.currColor = currColor;
            this.nextColor = nextColor;
        }        
    }
}

Try this component in your project. If you face any issue implementing this, email to me, i will help to set this up. Provide your valuable feedback to me.

Thanks

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.