I want to allow my team to display some leads and tasks (and any known object) with custom conditions and display all the data on only one screen. I made some custom objects "blocks" containing SOQL elements :

  • base query ; ex: select * from lead where createdDate = TODAY
  • headers ; ex: Name, CreatedDate, id

I have a controller that get all those blocks then get all the records in wrappers with a list of headers and a list of those sobjects.

Then I have a visualforce page that use repeat vf command :

  • repeat on all wrappers to create tables
  • repeat on all headers to create the table header then fill the rows & 1st column is a link to the record

This way my team can work on only one screen with data we want.

But I would like to be able to format the output value, depending on the type. Obviously for dates and datetimes.

I am just thinking about one thing : I could use a map of headers instead of a list, something like:

key = header, value = type. GetHeaders => return List<String>(headers.keySet())

So in my columns i could check the type to use some formated output values.

Edit with code :

Controller with an inner class containing headers (=fields) and a list of records. Some queries are created from values contained in a custom object TodoBlock__c, then they are used to fill the list "records".

public with sharing class ToDoBlockController{
public TodoBlock todoBlock      {get;set;}

public void initComponent(){
    // init todoblock

public class TodoBlock{
    // input
    public String        name       {get;set;}
    public String        query      {get;set;}
    public List<String>  headers    {get;set;}
    public Integer       queryLimit {get;set;}

    // calculation
    public List<SObject> records {get;set;}
    public Integer       count   {get;set;}
    public String        objType {get;set;}

    // modification
    public String        sortColumn     {get{ return sortColumn==null ? headers[0] : sortColumn; } set;}
    public boolean       isAscSort      {get{ return isAscSort==null ? true : isAscSort; }  set;}

    public TodoBlock(TodoBlock__c record, Integer queryLimit, String sortColumn, String isAscSortStr){ 
        // attributes initialization
    public void runQueries(){
        // queries records


Visualforce component containing the table.
I am having trouble displaying it correctly, anyway important part is under the 2 comments. Here i would like to format the value depending on its type. Value is record[header] result. Type can be anything.
I see 2 option :

  • I can get type from VF side => i create tags with conditions in rerender attribute
  • I need to store it somewhere in the controller => instead of String[] header I shoud use Map{String=>String} where key is header/field name and value is type


    {!$ObjectType[todoBlock.objType].fields[header].label} rendered="{!todoBlock.sortColumn = header}" value="/s.gif"/>

                    <!-- 1st col = link -->
                    <apex:outputLink value="/{!rec.Id}" target="_blank" rendered="{!header == todoBlock.headers[0]}">{!rec[header]}</apex:outputLink>
                    <!-- other cols = normal -->
                    <apex:outputLabel rendered="{!header != todoBlock.headers[0]}">{!rec[header]}</apex:outputLabel>
  • 1
    you can try it out and post you code along with the problem you are facing. May 10, 2017 at 14:53
  • I found no way to do it with apex tags for the moment. I will try to handle this with the map but the project became very low priority.
    – Guillaume
    Aug 2, 2017 at 8:00

1 Answer 1


So I made a Map fieldTypeMap and a component to handle the date/datetime format

Here is what I did, maybe it will be usefull for someone else.


I added the map as an attribute of my inner class into the controller:

// header/type mapping
public Map<String,String> headerTypeMap {get;set;}

I initialize it at the end of the constructor, thanks to this.headers (array of string header/field name), after the queries, like this:

        // calculation :

        // mapping
        this.headerTypeMap = new Map<String,String>();
        for(String field : this.headers){

Visualforce component

Because I often need to format date and datetime I thought it could be a good idea to create a formating component So I made a quick and dirty one:

<apex:component controller="FormatedValueController">
<apex:attribute name="dateValue" 
    description="input value to formatTodoBlock__c record that contains data" 
<apex:attribute name="datetimeValue" 
    description="input value to formatTodoBlock__c record that contains data" 



public class FormatedValueController {
    public Date     inputDateValue {get;set;}
    public Datetime inputDateTimeValue {get;set;}

    public String getFormatedValue(){
        String formatedValue = '';
        formatedValue += inputDateValue == null ? '' : inputDateValue.format();
        formatedValue += inputDateTimeValue == null ? '' : inputDateTimeValue.format();
        return formatedValue;

And a quick&dirty test class too (for code coverage only):

global class FormatedValueController_test{
    static testMethod void FormatedValueController() {
        FormatedValueController c = new FormatedValueController();
        Test.startTest ();

100% you-hou ;)

And finally ...

Main Component

Oddly I need to use "{!todoBlock.headerTypeMap[header]}" everywhere, where todoBlock is the instance of my innerclass and header the var of repeat on headers attribute (table with a dynamic number of columns).

I wanted to use an apex variable for each header, kind of:

<apex:variable var="type" value="{!todoBlock.headerTypeMap[header]}" />

but for an unknown reason it just display the last header value in every loop. For example if I have DATE, DATETIME, STRING, it displays STRING, STRING, STRING. Not a big deal to use the full code, it is just less readable.

So here it is :

<apex:outputLabel rendered="{!todoBlock.headerTypeMap[header]=='DATETIME'}">
    <c:FormatedValue datetimeValue="{!rec[header]}"/>

<apex:outputLabel rendered="{!todoBlock.headerTypeMap[header]=='DATE'}">
    <c:FormatedValue dateValue="{!rec[header]}"/>

<apex:outputLabel rendered="{!NOT(AND(todoBlock.headerTypeMap[header]=='DATETIME',todoBlock.headerTypeMap[header]=='DATE'))}">

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .