Created
October 8, 2015 07:55
-
-
Save davidpurkiss/12a40e8f60094e4de574 to your computer and use it in GitHub Desktop.
Custom Element - Aurelia Kendo Grid
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<template> | |
<require from='kendo-ui/styles/kendo.common-bootstrap.min.css'></require> | |
<require from='kendo-ui/styles/kendo.bootstrap.min.css'></require> | |
<div> | |
<content></content> | |
</div> | |
</template> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import {inject, processContent, customAttribute, bindable, sync, ViewCompiler, ViewSlot, Container, ViewResources, TargetInstruction} from 'aurelia-framework'; | |
import { EventAggregator } from 'aurelia-event-aggregator'; | |
import {Compiler} from '../kendo/compiler'; | |
import * as kendoUi from 'kendo-ui'; | |
@processContent((compiler, resources, element, instruction) => { | |
parseUserTemplate(element, resources, instruction); | |
return true; | |
}) | |
@inject(Element, Compiler, EventAggregator, TargetInstruction) | |
export class KendoGrid { | |
element: HTMLElement; | |
widget: any; | |
columns: any[] = null; | |
model: any = null; | |
@bindable selectable: boolean; | |
@bindable filterable: boolean; | |
@bindable pageable: boolean; | |
@bindable sortable: boolean; | |
@bindable pageSize: number = 10; | |
@bindable page: number = 1; | |
@bindable selectedItem: any; | |
@bindable selectedItems: any[]; | |
@bindable autoBind: boolean; | |
@bindable editable: boolean; | |
@bindable toolbar: any[]; | |
@bindable refreshFlag: any; | |
@bindable read: any; | |
aggregator: EventAggregator; | |
compiler: Compiler; | |
dataSource: kendo.data.DataSource; | |
constructor(element, compiler, aggregator, targetInstruction) { | |
this.element = element; | |
this.compiler = compiler; | |
this.aggregator = aggregator; | |
kendo.culture("en-GB"); | |
this.columns = targetInstruction.behaviorInstructions[0].kendoGridColumns; | |
this.model = targetInstruction.behaviorInstructions[0].kendoDataSourceModel; | |
} | |
bind(ctx) { | |
this["$parent"] = ctx; | |
// Post parse the templates in "columns" | |
this.columns.forEach(c => { | |
if (c.hasOwnProperty("template")) { | |
// If there's no template string it must be the first time we are visiting the columns | |
// Push the template string into a new property and wrap the string with a func to compile the template | |
if (!c.hasOwnProperty("templateString")) | |
c["templateString"] = c["template"]; | |
c["template"] = (dataItem) => { | |
try { | |
var cellctx = { "$item": dataItem, "$parent": ctx }; | |
return this.compiler.compile(c["templateString"], cellctx).fragment.innerHTML; | |
} | |
catch (ex) { | |
console.error(ex); | |
} | |
} | |
} | |
}); | |
} | |
refreshFlagChanged() { | |
this.refresh(); | |
} | |
selectedItemChanged() { | |
} | |
attached() { | |
// Create the datasource | |
this.dataSource = new kendoUi.data.DataSource({ | |
serverFiltering: true, | |
serverSorting: true, | |
serverPaging: true, | |
page: this.page, | |
pageSize: this.pageSize, | |
schema: { | |
data: "data", | |
total: "total", | |
model: this.model | |
}, | |
transport: { | |
read: (options) => { | |
// Check if we have a grid read setup | |
if (!this.read) { | |
console.warn("No read method provided to Kendo Grid"); | |
options.error([]); | |
return; | |
} | |
// User can transform the kendo options | |
return Promise.resolve(this.read(options.data)) | |
.then(e => { | |
return options.success(e); | |
}) | |
.catch(e => { | |
return options.error([]); | |
}); | |
} | |
} | |
}); | |
// Create the widget | |
$(this.element).kendoGrid({ | |
dataSource: this.dataSource, | |
columns: this.columns, | |
filterable: this.filterable, | |
pageable: this.pageable, | |
selectable: this.selectable, | |
sortable: this.sortable, | |
autoBind: this.autoBind, | |
editable: this.editable, | |
toolbar: this.toolbar, | |
// Row selection | |
change: (e) => { | |
var selectedRows = this.widget.select(); | |
var selectedItems = Array.prototype.slice.call(selectedRows).map(row => { | |
return this.widget.dataItem(row); | |
}); | |
this.selectedItem = selectedItems[0]; | |
this.selectedItems = selectedItems; | |
} | |
}); | |
this.widget = $(this.element).data("kendoGrid"); | |
} | |
refresh() { | |
if (this.widget) | |
this.widget.dataSource.read(); | |
} | |
detached() { | |
$(this.element).data("kendoGrid").destroy(); | |
} | |
} | |
function parseUserTemplate(element, resources, instruction) { | |
// Pull all of the attributes off the kendo-grid-col element | |
var columns = Array.prototype.slice.call(element.querySelectorAll("kendo-grid-col")); | |
var colSpecs = columns.map(col => { | |
var obj = {}; | |
for (var i = col.attributes.length - 1; i >= 0; i--) { | |
var attr = col.attributes.item(i); | |
obj[attr.name] = attr.value; | |
} | |
parseCellTemplate(col, obj); | |
return obj; | |
}); | |
var modelSpecs = {}; | |
modelSpecs["fields"] = {}; | |
columns.forEach(col => { | |
var colField = col.getAttribute("field"); | |
if (colField != null) { | |
var model = col.querySelector("kendo-model"); | |
if (model != null) { | |
var modelValidation = model.querySelector("kendo-model-validation"); | |
var modelObj = {} | |
for (var i = model.attributes.length - 1; i >= 0; i--) { | |
var attr = model.attributes.item(i); | |
if (attr.name == "identifier") { | |
if (attr.value == "true") | |
modelSpecs["id"] = colField; | |
} | |
else { | |
modelObj[attr.name] = attr.value; | |
} | |
} | |
modelSpecs["fields"][colField] = modelObj; | |
if (modelValidation != null) { | |
var modelValidationObj = {}; | |
for (var i = modelValidation.attributes.length - 1; i >= 0; i--) { | |
var attr = modelValidation.attributes.item(i); | |
modelValidationObj[attr.name] = attr.value; | |
} | |
modelSpecs["fields"][colField]["validation"] = modelValidationObj; | |
} | |
} | |
} | |
}); | |
// Remove any inner HTML from the element - we don't want it in the DOM | |
element.innerHTML = ""; | |
instruction.kendoGridColumns = colSpecs; | |
instruction.kendoDataSourceModel = modelSpecs; | |
} | |
function parseCellTemplate(element, spec) { | |
var template = element.querySelector("kendo-template"); | |
if (template) | |
spec.template = template.innerHTML; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment