Apex Controller:
public class SampleAuraController {
//Get Contact List
@AuraEnabled
public static List<Contact> getContactList(Integer recordLimit, Integer recordOffset){
Integer intLimit = Integer.valueof(recordLimit);
Integer intOffset = Integer.valueof(recordOffset);
List<Contact> conList = new List<Contact>();
conList = [SELECT Id, Name, Email, Phone FROM Contact LIMIT :intLimit Offset :intOffset];
return conList;
}
//Get Total Number of Contacts
@AuraEnabled
public static Integer getTotalContacts(){
AggregateResult results = [SELECT Count(Id) TotalContacts From Contact];
Integer totalContacts = (Integer)results.get('TotalContacts') ;
return totalContacts;
}
//Delete Contact
@AuraEnabled
public static void deleteContact(Contact con){
Delete con;
}
}
Lightning Component:
<!--Sample.cmp-->
<aura:component controller="SampleAuraController" implements="flexipage:availableForAllPageTypes,force:appHostable">
<!--Declare Attributes-->
<aura:attribute name="data" type="Object"/>
<aura:attribute name="columns" type="List"/>
<aura:attribute name="selectedRowsCount" type="Integer" default="0"/>
<aura:attribute name="selectedRowsDetails" type="Object" />
<aura:attribute name="selectedRowsList" type="List" />
<aura:attribute name="maxRowSelection" type="Integer" default="10"/>
<aura:attribute name="selectedRows" type="List" />
<aura:attribute name="enableInfiniteLoading" type="Boolean" default="true"/>
<aura:attribute name="initialRows" type="Integer" default="10"/>
<aura:attribute name="rowsToLoad" type="Integer" default="10"/>
<aura:attribute name="totalNumberOfRows" type="Integer" default="10"/>
<aura:attribute name="loadMoreStatus" type="String" default="Please scroll down to load more data"/>
<aura:attribute name="showRowNumberColumn" type="Boolean" default="false"/>
<aura:attribute name="rowNumberOffset" type="Integer" default="0"/>
<aura:attribute name="rowsToAdd" type="Integer" default="10"/>
<aura:attribute name="currentCount" type="Integer" default="10"/>
<aura:attribute name="sortedBy" type="String"/>
<aura:attribute name="sortedDirection" type="String"/>
<aura:attribute name="defaultSortDirection" type="String"/>
<!--Declare Handlers-->
<aura:handler name="init" value="{!this}" action="{!c.doInit}"/>
<!--Component Start-->
<div class="slds-m-around_xx-large" style="height: 300px">
<lightning:datatable columns="{!v.columns}"
data="{!v.data}"
keyField="Id"
showRowNumberColumn="true"
rowNumberOffset="0"
onrowaction="{!c.handleRowAction}"
selectedRows="{!v.selectedRows}"
maxRowSelection="{!v.maxRowSelection}"
onrowselection="{!c.handleSelectedRow}"
enableInfiniteLoading="true"
loadMoreOffset="{!v.loadMoreOffset}"
sortedBy="{!v.sortedBy}"
sortedDirection="{!v.sortedDirection}"
defaultSortDirection="{!v.defaultSortDirection }"
onsort="{!c.handleColumnSorting}"
onloadmore="{!c.handleLoadMoreContacts}"/>
<br/>
<div class="slds-float_left">
<strong>Total Rows : {!v.totalNumberOfRows}</strong>
<strong>Selected Rows: {!v.selectedRowsCount }</strong>
</div>
<div class="slds-float_right">
<strong>{!v.loadMoreStatus}</strong>
</div>
<br/>
<br/>
<div class="slds-float_left">
<lightning:button label="Get Selected Contacts" variant="brand" onclick="{!c.handleSelectedRows}"/>
</div>
</div>
<!--Component End-->
</aura:component>
Lightning Component JS Controller:
({
doInit : function(component, event, helper) {
helper.getTotalNumberOfContacts(component);
helper.getColumnAndAction(component);
helper.getContacts(component);
},
handleLoadMoreContacts: function (component, event, helper) {
event.getSource().set("v.isLoading", true);
component.set('v.loadMoreStatus', 'Loading....');
helper.getMoreContacts(component, component.get('v.rowsToLoad')).then($A.getCallback(function (data) {
if (component.get('v.data').length == component.get('v.totalNumberOfRows')) {
component.set('v.enableInfiniteLoading', false);
component.set('v.loadMoreStatus', 'No more data to load');
} else {
var currentData = component.get('v.data');
var newData = currentData.concat(data);
component.set('v.data', newData);
component.set('v.loadMoreStatus', 'Please scroll down to load more data');
}
event.getSource().set("v.isLoading", false);
}));
},
handleSelectedRows: function (component, event, helper) {
var data = component.get('v.data');
var selectedRowList = component.get("v.selectedRowsList");
console.log('selectedRowList-' + selectedRowList);
},
handleSelectedRow: function(component, event, helper){
var selectedRows = event.getParam('selectedRows');
component.set("v.selectedRowsCount", selectedRows.length);
let obj =[] ;
for (var i = 0; i < selectedRows.length; i++){
obj.push({Name:selectedRows[i].Name});
}
component.set("v.selectedRowsDetails", JSON.stringify(obj) );
component.set("v.selectedRowsList", event.getParam('selectedRows'));
},
handleRowAction: function (component, event, helper) {
var action = event.getParam('action');
switch (action.name) {
case 'new':
helper.createContactRecord(component, event);
break;
case 'edit':
helper.editContactRecord(component, event);
break;
case 'delete':
helper.deleteContactRecord(component, event);
break;
case 'view':
helper.viewContactRecord(component, event);
break;
}
},
handleColumnSorting: function (component, event, helper) {
var fieldName = event.getParam('fieldName');
var sortDirection = event.getParam('sortDirection');
component.set("v.sortedBy", fieldName);
component.set("v.sortedDirection", sortDirection);
helper.sortData(component, fieldName, sortDirection);
},
})
Lightning Component JS Helper:
({
getContacts : function(component) {
var action = component.get("c.getContactList");
action.setParams({
"recordLimit": component.get("v.initialRows"),
"recordOffset": component.get("v.rowNumberOffset")
});
action.setCallback(this, function(response) {
var state = response.getState();
if (state === "SUCCESS" ) {
var resultData = response.getReturnValue();
component.set("v.data", resultData);
component.set("v.currentCount", component.get("v.initialRows"));
}
});
$A.enqueueAction(action);
},
getTotalNumberOfContacts : function(component) {
var action = component.get("c.getTotalContacts");
action.setCallback(this, function(response) {
var state = response.getState();
if (state === "SUCCESS" ) {
var resultData = response.getReturnValue();
component.set("v.totalNumberOfRows", resultData);
}
});
$A.enqueueAction(action);
},
getColumnAndAction : function(component) {
var actions = [
{label: 'New', name: 'new'},
{label: 'Edit', name: 'edit'},
{label: 'Delete', name: 'delete'},
{label: 'View', name: 'view'}
];
component.set('v.columns', [
{label: 'Name', fieldName: 'Name', type: 'text', sortable:true},
{label: 'Email', fieldName: 'Email', type: 'email', sortable:true},
{label: 'Phone', fieldName: 'Phone', type: 'phone', sortable:true},
{type: 'action', typeAttributes: { rowActions: actions } }
]);
},
getMoreContacts: function(component , rows){
return new Promise($A.getCallback(function(resolve, reject) {
var action = component.get('c.getContactList');
var recordOffset = component.get("v.currentCount");
var recordLimit = component.get("v.initialRows");
action.setParams({
"recordLimit": recordLimit,
"recordOffset": recordOffset
});
action.setCallback(this, function(response) {
var state = response.getState();
if(state === "SUCCESS"){
var resultData = response.getReturnValue();
resolve(resultData);
recordOffset = recordOffset+recordLimit;
component.set("v.currentCount", recordOffset);
}
});
$A.enqueueAction(action);
}));
},
sortData: function (component, fieldName, sortDirection) {
var data = component.get("v.data");
var reverse = sortDirection !== 'asc';
data.sort(this.sortBy(fieldName, reverse))
component.set("v.data", data);
},
sortBy: function (field, reverse, primer) {
var key = primer ?
function(x) {return primer(x[field])} :
function(x) {return x[field]};
reverse = !reverse ? 1 : -1;
return function (a, b) {
return a = key(a), b = key(b), reverse * ((a > b) - (b > a));
}
},
viewContactRecord : function(component, event) {
var row = event.getParam('row');
var recordId = row.Id;
var navEvt = $A.get("event.force:navigateToSObject");
navEvt.setParams({
"recordId": recordId,
"slideDevName": "detail"
});
navEvt.fire();
},
deleteContactRecord : function(component, event) {
var action = event.getParam('action');
var row = event.getParam('row');
var action = component.get("c.deleteContact");
action.setParams({
"con": row
});
action.setCallback(this, function(response) {
var state = response.getState();
if (state === "SUCCESS" ) {
var rows = component.get('v.data');
var rowIndex = rows.indexOf(row);
rows.splice(rowIndex, 1);
component.set('v.data', rows);
var toastEvent = $A.get("e.force:showToast");
toastEvent.setParams({
"title": "Success!",
"message": "The record has been delete successfully."
});
toastEvent.fire();
}
});
$A.enqueueAction(action);
},
editContactRecord : function(component, event) {
var row = event.getParam('row');
var recordId = row.Id;
var editRecordEvent = $A.get("e.force:editRecord");
editRecordEvent.setParams({
"recordId": recordId
});
editRecordEvent.fire();
},
createContactRecord : function (component, event) {
var createRecordEvent = $A.get("e.force:createRecord");
createRecordEvent.setParams({
"entityApiName": "Contact"
});
createRecordEvent.fire();
}
})
Output: