I'd avoid using datatable as per your comments, as its quite difficult to do anything other than iterate a common set of data and output a column per property. I think this is simply a matter of iterating the inner list and generating its own HTML table rows. E.g.
<apex:repeat value="{!HDDevicesbyArea}" var="HD" id="theRepeat">
<tr>
<td><apex:outputText value= "{!HD.HD_Area"} /></td>
<td><apex:outputText value= "{!HD.HD_Current"}</td>
<td><apex:outputText value= "{!HD.HD_Allocated"}</td>
</tr>
<apex:repeat value="{!HD.ListHDDevicesbyVendor}" var="dev">
<tr>
<td><apex:outputText value= "{!dev.HD_Vendor}" /></td>
<td><apex:outputText value= "{!dev.HD_Current"}</td>
<td><apex:outputText value= "{!dev.HD_Allocated"}</td>
</tr>
</apex:repeat>
</apex:repeat>
That way the first row in the repeat contains the area and current/allocated, and the following rows contain the vendor and the current/allocated.
You have three basic means by which you could construct the page. The first method is to use Dynamic Apex, meaning that the components are rendered by the controller, and then dumped out to the page.
The second option would be to use a self-enclosed component. That would roughly look like:
<apex:component selfClosing="true" controller="MyWrapper">
<apex:attribute name="data" assignTo="{!listdata}" type="MyWrapper"/>
{!listdata.name}
<apex:repeat value="{!listdata.children}" var="data">
<c:recursiveSelf data="{!data}"/>
</apex:repeat>
</apex:component>
The controller for this thing would look like:
public class MyWrapper {
public MyWrapper[] listdata { get; set; }
public string name { get; set; }
public MyWrapper[] children { get; set; }
}
You could then populate it by creating a MyWrapper
, populating the name
and children
attributes, and then supplying it from another controller. This is fairly messy, and I would imagine hurtful to the viewstate.
The third method would actually probably be relatively simple: render the elements as a single flat list, then write a jQuery piece (or any other libary, really) to expand the elements based on some input, like a wrapper element that identifies the indentation level, for example. Or you could use CSS to indent up to an arbitrary depth. I believe the CSS for this would be relatively short if you kept yourself in CSS3 (i.e. you don't care if it doesn't look right in older Internet Explorer browsers).
Best Answer
This is possible, we can identify every 2nd, every 3rd element from apex:repeat and mark them with the class which we want. Please refer below code.
VFPage:
Controller Code:
As a common practice mark this as a solution if this helps you.