Cell types
Registering a cell-type
When you create a custom cell type, a good idea is to assign it as an alias that will refer to this particular type definition. Handsontable defines 9 aliases by default:
autocomplete
forHandsontable.cellTypes.autocomplete
checkbox
forHandsontable.cellTypes.checkbox
date
forHandsontable.cellTypes.date
dropdown
forHandsontable.cellTypes.dropdown
handsontable
forHandsontable.cellTypes.handsontable
numeric
forHandsontable.cellTypes.numeric
password
forHandsontable.cellTypes.password
text
forHandsontable.cellTypes.text
time
forHandsontable.cellTypes.time
It gives users a convenient way for defining which cell type should be used for describing cell properties. User doesn't need to know which part of code is responsible for rendering, validating or editing the cell value, he does not even need to know that there is any functions at all. What is more, you can change the cell behaviour associated with an alias without a need to change the code that defines a cell properties.
To register your own alias use Handsontable.cellTypes.registerCellType()
function. It takes two arguments:
cellTypeName
- a string representing of the cell type objecttype
- an object with keyseditor
,renderer
andvalidator
that will be represented bycellTypeName
If you'd like to register copyablePasswordType
under alias copyable-password
you have to call:
Handsontable.cellTypes.registerCellType('copyable-password', {
editor: copyablePasswordEditor,
renderer: copyablePasswordRenderer,
});
Choose aliases wisely. If you register your cell type under name that is already registered, the target function will be overwritten:
Handsontable.cellTypes.registerCellType('password', {
editor: copyablePasswordEditor,
renderer: copyablePasswordRenderer,
});
// Now 'password' alias points to the newly created object, not Handsontable.cellTypes.password
So, unless you intentionally want to overwrite an existing alias, try to choose a unique name. A good practice is prefixing your aliases with some custom name (for example your GitHub username) to minimize the possibility of name collisions. This is especially important if you want to publish your cell type, because you never know aliases has been registered by the user who uses your cell type.
Handsontable.cellTypes.registerCellType('copyable-password', {
editor: copyablePasswordEditor,
renderer: copyablePasswordRenderer,
});
// Someone might already registered such alias
Handsontable.cellTypes.registerCellType('my.copyable-password', { editor: copyablePasswordEditor, renderer: copyablePasswordRenderer, }); // That's better.
Using an alias
The final touch is to using the registered aliases, so that users can easily refer to it without the need to now the actual cell type object is.
To sum up, a well prepared cell type object should look like this:
(function(Handsontable){
var MyEditor = Handsontable.editors.TextEditor.prototype.extend();
function customRenderer(hotInstance, td, row, column, prop, value, cellProperties) {
// ...renderer logic
}
function customValidator(query, callback) {
// ...validator logic
callback(/* Pass `true` or `false` */);
}
// Register an alias
Handsontable.cellTypes.registerCellType('my.custom', {
editor: MyEditor,
renderer: customRenderer,
validator: customValidator,
// You can add additional options to the cell type based on Handsontable settings
className: 'my-cell',
allowInvalid: true,
// Or you can add custom properties which will be accessible in `cellProperties`
myCustomCellState: 'complete',
});
})(Handsontable);
From now on, you can use your cell definition like so:
var hot = new Handsontable(document.getElementById('container'), {
data: someData,
columns: [
{
type: 'my.custom'
}
]
});
Preview of built-in and custom cell types
The below example shows some of the built-in cell types (in other words, combinations of cell renderers and editors) available in Handsontable:
The same example also shows the declaration of custom cell renderers, namely yellowRenderer
and greenRenderer
.
var data = [ {id: 1, name: 'Ted', isActive: true, color: 'orange', date: '2015-01-01'}, {id: 2, name: 'John', isActive: false, color: 'black', date: null}, {id: 3, name: 'Al', isActive: true, color: 'red', date: null}, {id: 4, name: 'Ben', isActive: false, color: 'blue', date: null} ], container = document.getElementById('example1'), hot1, yellowRenderer, greenRenderer; yellowRenderer = function(instance, td, row, col, prop, value, cellProperties) { Handsontable.renderers.TextRenderer.apply(this, arguments); td.style.backgroundColor = 'yellow'; }; greenRenderer = function(instance, td, row, col, prop, value, cellProperties) { Handsontable.renderers.TextRenderer.apply(this, arguments); td.style.backgroundColor = 'green'; }; hot1 = new Handsontable(container, { data: data, startRows: 5, colHeaders: true, minSpareRows: 1, columns: [ {data: "id", type: 'text'}, // 'text' is default, you don't actually need to declare it {data: "name", renderer: yellowRenderer}, // use default 'text' cell type but overwrite its renderer with yellowRenderer {data: "isActive", type: 'checkbox'}, {data: "date", type: 'date', dateFormat: 'YYYY-MM-DD'}, {data: "color", type: 'autocomplete', source: ["yellow", "red", "orange", "green", "blue", "gray", "black", "white"] } ], cell: [ {row: 1, col: 0, renderer: greenRenderer} ], cells: function (row, col, prop) { if (row === 0 && col === 0) { this.renderer = greenRenderer; } } });
Anatomy of a cell type
A cell type is a predefined set of cell properties. Cell type defines what renderer, editor or validator should be used for a cell. They can also define any different cell property that will be assumed for each matching cell.
For example, writing:
columns: [{
type: 'password'
}]
Equals:
columns: [{
editor: Handsontable.editors.PasswordEditor
renderer: Handsontable.renderers.PasswordRenderer,
copyable: false,
}]
Or using custom cell type definition:
Handsontable.cellTypes.registerCellType('custom', {
renderer: Handsontable.renderers.TextRenderer,
className: 'my-cell',
readOnly: true,
myCustomProperty: 'foo'
})
In Handsontable settings:
columns: [{
type: 'custom'
}]
Equals:
columns: [{
editor: false,
renderer: Handsontable.renderers.TextRenderer,
className: 'my-cell',
readOnly: true,
myCustomProperty: 'foo'
}]
This mapping is defined by files src/cellTypes/