<div id="midcolumn">
	<h3>FAQ</h3>
	
	<div id="doccontent">
		<div class="chapter">
			<h5>General Questions</h5>
			
			<h6>Why is it called NatTable?</h6>
			<p>NatTable was originally written by Andy Tsoi and dedicated to his girlfriend, Natalie.</p>
			<p>We also sometimes think of 'Nat' as an acronym for 'Not A Table' given that it's really
				more of a data grid, or a tool for building tables/grids.</p>
			
			<h6>How much data can you put behind it?</h6>
			<p>As much as you want, pretty much. The only practical limit right now is that the number 
			of columns, rows, width and height of your table must be able to be represented as 32-bit 
			integers. We test against virtual data sets of 1 million columns by 1 million rows.</p>
		</div>
		
		<div class="chapter">
			<h5>How To...</h5>
			
			<h6>How to create ComboBoxCellEditors with dynamic content?</h6>
			<p>
				You can either create an instance of <span class="code">ComboBoxCellEditor</span> with a given list of values 
				(which results in a static combobox) or with an instance of a custom <span class="code">IComboBoxDataProvider</span>. 
				By creating and using a custom <span class="code">IComboBoxDataProvider</span> you are able to load the content 
				of the combobox at runtime. As <span class="code">IComboBoxDataProvider.getValues(int, int)</span> gets
				the column and row index of the cell for which the combobox should be rendered, it is possible to get
				information out of other cells to determine which content the combobox should contain.
				<div class="codeBlock">public class MyComboBoxDataProvider implements IComboBoxDataProvider {
				
	private IDataProvider bodyDataProvider;
	
	public MyComboBoxDataProvider(IDataProvider bodyDataProvider) {
		this.bodyDataProvider = bodyDataProvider;
	}
	
	@Override
	public List&lt;?&gt; getValues(int columnIndex, int rowIndex) {
		//guess in column with index == 1 a checkbox editor with a boolean value 
		//is configured, we get the current boolean value out of the body data 
		//provider and decide which values to show
		Boolean checked = (Boolean) bodyDataProvider.getDataValue(1, rowIndex);
		if (checked) {
			return Arrays.asList(new String[] {"Homer", "Bart"});
		} else {
			return Arrays.asList(new String[] {"Marge", "Lisa", "Maggie"});
		}
	}
}</div>
				<p class="subline">Create custom IComboBoxDataProvider to return different lists regarding other cell values</p>

				<div class="codeBlock">//the body data provider needs to be known by this configuration
configRegistry.registerConfigAttribute(
	EditConfigAttributes.CELL_EDITOR, 
	new ComboBoxCellEditor(new MyComboBoxDataProvider(bodyDataProvider))), 
	DisplayMode.EDIT, 
	"myComboBoxLabel");</div>
				<p class="subline">Register a ComboBoxCellEditor with the custom IComboBoxDataProvider</p>

			</p>
			
			<h6>How to autoresize columns programmatically?</h6>
			<p>
				NatTable supports the autoresize feature on double clicking cell edges. Unfortunately the
				existing commands related to that feature doesn't work if they are fired programmatically
				on building the NatTable. This is because when firing the command, the NatTable isn't rendered 
				yet, so the calculation of the width is returning the wrong values.<br/><br/>
				But there is another possibility how to achieve autoresizing columns. The <span class="code">TextPainter</span>
				which is used for rendering cell content as text, can be configured to calculate the column width/row height.
				Modifying the default configuration the following way will resize the columns on rendering the content, so the 
				content can be shown completely. Also note that if the content contains line breaks, the row height will be 
				calculated also.
				<div class="codeBlock">NatTable natTable = new NatTable(tableComposite, grid, false);
//as the autoconfiguration of the NatTable is turned off, we have to add the 
//DefaultNatTableStyleConfiguration and the ConfigRegistry manually	
natTable.setConfigRegistry(configRegistry);
natTable.addConfiguration(new DefaultNatTableStyleConfiguration() {
	{
		cellPainter = new LineBorderDecorator(
						new TextPainter(false, true, 5, true));
	}
});
natTable.configure();</div>
				<p class="subline">Modifying the DefaultNatTableStyleConfiguration to use a TextPainter that calculates cell width/height as cell painter</p>
			</p>
			<p>
				The <span class="code">TextPainter</span> solution has one downsite. If the cell content is not a 
				long text but a long word that can't be wrapped, it is not possible to manually resize the cell 
				anymore to show the content cutted.<br/>
				There is another downsite if the table is editable. The cells will automatically resize if the cell
				content which defines the cell width is modified to be longer/shorter. In fact this can also be a
				requirement, but compared to other well known grids, this behaviour is rather unexpected.<br/><br/>
				In the SourceForge forum <b>josecho2005</b> found a solution that only does the autoresize after rendering
				is finished. With some slight modifications it looks like this. You can find the original post 
				<a href="http://sourceforge.net/projects/nattable/forums/forum/744994/topic/5245501" title="SourceForge forum topic on autoresize">here</a>. 
				<div class="codeBlock">NatTable natTable = new NatTable(tableComposite, grid);
natTable.addListener(SWT.Paint, new Listener(){ 
			
	@Override public void handleEvent(Event arg0) { 
		for (int i=0; i < natTable.getColumnCount(); i++) { 
			InitializeAutoResizeColumnsCommand columnCommand = 
					new InitializeAutoResizeColumnsCommand(
						natTable, i, natTable.getConfigRegistry(), 
						new GCFactory(natTable)); 
			natTable.doCommand(columnCommand); 
		} 
				
		for (int i=0; i < natTable.getRowCount(); i++) { 
			InitializeAutoResizeRowsCommand rowCommand = 
					new InitializeAutoResizeRowsCommand(natTable, i, 
					natTable.getConfigRegistry(), 
					new GCFactory(natTable)); 
			natTable.doCommand(rowCommand); 
		} 
				
		natTable.removeListener(SWT.Paint, this);
	} 
});</div>
				<p class="subline">Adding a listener that autoresizes the NatTable after rendering is finished and removes itself after that</p>
			</p>
			
			<h6>How to add NatTable commands to eclipse menus?</h6>
			TODO
			
			<h6>How to access NatTable icons?</h6>
			TODO
		</div>
	</div>

</div>
