Flexigrid: selection of rows to survive refresh - javascript

I am using flexigrid in a project and I would like to be able to keep the selected rows after the grid is refreshing. I asked the same question on the flexigrid discussion board and I got this answer:
Add a click handler, save the id if the row id of the row selected. On refresh completion, select the row again (if still present)
Not sure how to proceed on this, I don't even know how a function will look like, so that's why I don't have any code to start with.
If someone could point me in the right direction will be greatly appreciated.
Thanks,
Cristian.

Flexigrid adds a class called trSelected to selected rows, so whenever a click event happens on the grid you could just look for all the selected rows and save them in some way. Below is just a quick example of what you could do:
var selectedRows = new Array();
$('#myGrid').click(function() {
selectedRows = new Array();
$(this).find('tr.trSelected').each(function(i, selectedRow) {
selectedRows.push($(selectedRow));
});
});

I have done small code to keep multi-selection between pagination and also during refresh.
$("#searchPhonoList").flexigrid($.extend({}, flexigridAttrs, {
url: './rest/phono/search',
preProcess: formatSearchPhonoResults,
onSuccess: successSearchPhono,
onSubmit: submit,
method: 'GET',
dataType: 'json',
colModel : [
{display: 'titre', name: 'titre_brut', width : 240, sortable : true, align: 'left'},
{display: 'version', name: 'version_brut', width : 60, sortable : true, align: 'left'}
],
height: "auto",
sortname: "score",
sortorder: "desc",
showTableToggleBtn: false,
showToggleBtn: false,
singleSelect: false,
onToggleCol: false,
usepager: true,
title: "Liste des candidats",
resizable: true,
rp:20,
useRp: true
}));
var searchPhonoListSelection = new Array();
$('#searchPhonoList').click(function(event){
$(' tbody tr', this).each( function(){
var id = $(this).attr('id').substr(3);
if ( searchPhonoListSelection.indexOf(id) != -1 ) {
searchPhonoListSelection.splice(searchPhonoListSelection.indexOf(id), 1);
}
});
$('.trSelected', this).each( function(){
var id = $(this).attr('id').substr(3);
if ( searchPhonoListSelection.indexOf(id) == -1 ) {
searchPhonoListSelection.push(id);
}
});
});
function successSearchPhono() {
$("#searchPhonoList tbody tr").each( function() {
var id = $(this).attr('id').substr(3);
if ( searchPhonoListSelection.indexOf(id) != -1 ) {
$(this).addClass("trSelected");
}
});
}

Related

Remove row from Kendo UI Grid with jQuery

I am using a Kendo UI grid and for deleting a row I am using a custom button with bootstrap that when I click on it, with ajax I call a web api method to remove that row and if it is successfully deleted that row removes it from the DOM. (I'm not using the command destroy of kendo)
The problem I have is that if I try to filter that row that was removed, it appears again in the grid and it seems that it was not removed at all.
This is my Kendo UI grid:
var table = $("#grid").kendoGrid({
dataSource: {
transport: {
read: {
url: "/api/customers",
dataType: "json"
}
},
pageSize: 10
},
height: 550,
filterable: true,
sortable: true,
pageable: {
refresh: true,
pageSizes: true,
buttonCount: 5
},
columns: [{
template: "<a href='' class='btn-link glyphicon glyphicon-remove js-delete' title='Delete' data-customer-id= #: Id #></a>",
field: "Id",
title: " ",
filterable: false,
sortable: false,
width: 50,
attributes: {
style: "text-align: center"
}
}, {
field: "Name",
title: "Name",
width: 100,
}, {
field: "LastName",
title: "LastName",
width: 100,
}, {
field: "Email",
title: "Email",
width: 150
}]
});
And this is my jQuery code for deleting a row:
$("#grid").on("click", ".js-delete", function () {
var button = $(this);
if (confirm("Are you sure you want to delete this customer?")) {
$.ajax({
url: "/api/customers/" + button.attr("data-customer-id"),
method: "DELETE",
success: function () {
button.parents("tr").remove(); //This part is removing the row but when i filtered it still there.
}
});
}
});
I know that in jQuery DataTables when can do something like this:
table.row(button.parents("tr")).remove().draw();
How can i do something like this with Kendo UI using jQuery?
Don't ever play with a Kendo's widget DOM. Always use it's methods instead.
Using Grid's removeRow():
$("#grid").on("click", "button.remove", function() {
var $tr = $(this).closest("tr"),
grid = $("#grid").data("kendoGrid");
grid.removeRow($tr);
});
Demo
Using DataSource's remove():
$("#grid").on("click", "button.remove", function() {
var $tr = $(this).closest("tr"),
grid = $("#grid").data("kendoGrid"),
dataItem = grid.dataItem($tr);
grid.dataSource.remove(dataItem);
});
Demo
My usage was a little different. I have a custom delete button, so I needed to delete by ID, not UID.
You should be able to match on any field value instead of ID.
var grid = $("#grid").data("kendoGrid");
var dataItem = grid.dataSource.get(ID);
var row = grid.tbody.find("tr[data-uid='" + dataItem.uid + "']");
grid.removeRow(row);
We were trying to prevent messing with the controller, and this calls the existing delete function.
The removed row will be present in the kendo ui till you push changes to server.
To remove the row entirely you need to use
grid.saveChanges()
So the code below will remove row from server as well from ui
const row = $(e.target).closest('tr')[0];
const grid = $(e.target).closest('#grid').data("kendoGrid");
grid.removeRow(row);
grid.saveChanges() //comment out if you need to remove only from ui

Two DataTable in One Page - Second one initialising weird

I have two dataTable in my page and I have a method like below:
function ToDataTable()
{
$(".dataTable").css("width", "100%");
$(".dataTable").each(function ()
{
var $that = $(this);
/* Start of method */
function ToDataTableInternal()
{
var table = $that.DataTable({
responsive: {
details: { type: "column", target: -1 },
},
columnDefs: [{
className: "control", orderable: !1, targets: -1,
},
{ orderable: !1 }],
"paging": false,
"ordering": false,
"info": false,
"searching": false,
retrieve: true
});
}
/* End of method */
if ($that.is(":visible"))
{
ToDataTableInternal()
}
else
{
// Observe all invisible parents or table to trigger
// ToDataTableInternal method if made visible
var $arr = $(this).parentsUntil(":visible").filter(function ()
{
return $(this).css("display") === "none";
}).add($(this));
var observers = [];
$arr.each(function ()
{
var observer = new MutationObserver(function (mutations)
{
mutations.forEach(function (mutation)
{
if ((mutation.attributeName === 'style' ||
mutation.attributeName === 'class') &&
$that.is(":visible"))
{
ToDataTableInternal();
for (var i = 0; i < observers.length; i++)
{
// Disconnect observers
observers[i].disconnect();
}
}
});
});
observers.push(observer);
observer.observe(this, {
attributes: true
});
});
}
});
}
The reason I have this method is that when table's display is none, it really lags browser(especially IE, where I cannot do anything for minimum of 5 seconds) which is the reason of that I'm changing the table to DataTable after it made visible.
But the problem with calling methods individually is the second DataTable doesn't have the same settings which I passed on.(The first one has) Instead, second one has filters, paging, sort elements in it too.
If I call both at the same time, nothing out of ordinary happens. What may be the problem?
EDIT: I can't reproduce the same behaviour in fiddles.
There seems to be no problems in another environments when I'm trying to do the same thing.
An another library we use is causing problems and there is no problem with DataTable library.
you can add following properties of dataTable in your datatable configuration to remove filtering, pageing and sorting:
Datatable 1.9
"bPaginate":false, //Enable or disable pagination.
"bFilter": false, //Enable or disable filtering of data
"bLengthChange": false, //Enable or disable the size dropdown
"bSort": false, //Enable or disable sorting of columns.
"bInfo": false, //Enable or disable the table information display.
Update
Datatable 1.10
Option name update in datatable 1.10
bPaginate -> paging
bFilter -> searching
bLengthChange -> lengthChange
bSort -> ordering
bInfo -> info

ExtJS qtip is not getting displayed

I have a grid panel and im trying to display a hover popup on a particular column. I have tried both tooltip and qtip but they are just not getting displayed. My grid panel looks as:
Ext.create('Ext.grid.Panel', {
id: 'frPanel-'+interfaceId,
store: frStore,
columns : [ {text : 'Source',
dataIndex : 'source',
renderer : function(value) {
return convertObjValue(value);
},
listeners: {
afterrender: function ()
{
Ext.create('Ext.tip.ToolTip',
{
target: this.el,
trackMouse: true,
html: "Hello there"
});
}
}
}, {
text : 'Destination',
dataIndex : 'destination',
menuDisabled : true,
renderer : function(value, metaData) {
var newValue = convertObjValue(value);
metaData.tdAttr = 'data-qtip="' + newValue + '"';
return newValue;
}
}
What am i doing wrong here? Any help how i can achieve this?
EDIT : So i made the second column work by adding Ext.QuickTips.init(); in the onReady() function. But i still wanna know how to make it work using the approach in first column.

reloading dataurl elements in jqGrid

I have a simple grid with the following options:
jQuery("#mygrid").jqGrid({
url: 'dataurl.htm',
datatype: 'json',
ajaxSelectOptions: { cache: false }
...
colModel: [
{ name: 'foo', index: 'foo', width: 25, stype: 'select', searchoptions:{ sopt:
['eq'], dataUrl: 'someurl.htm?columnName=foo'}}
]
});
However, when I call $("#mygrid").trigger("reloadGrid"); it only loads the data for the table from dataurl.htm but it does not load the data for the foo column from the some url.htm link.
I've read couple of questions like these on SO and it was suggested to have ajaxSelectOptions: { cache: false } but this is not working for me.
The someurl.htm returns <select> <option val=''>something</option></select>
It's absolutely correct question! The current implementation of jqGrid has only toggleToolbar method which can hide the toolbar, but the toolbar itself will be created once. So all properties of the toolbar stay unchanged the whole time.
To fix the problem I wrote small additional method destroyFilterToolbar which is pretty simple:
$.jgrid.extend({
destroyFilterToolbar: function () {
"use strict";
return this.each(function () {
if (!this.ftoolbar) {
return;
}
this.triggerToolbar = null;
this.clearToolbar = null;
this.toggleToolbar = null;
this.ftoolbar = false;
$(this.grid.hDiv).find("table thead tr.ui-search-toolbar").remove();
});
}
});
The demo uses the method. One can recreate searching toolbar after changing of properties of some columns. In the code below one can change the language of some texts from the searching toolbar:
The corresponding code is below:
$("#recreateSearchingToolbar").change(function () {
var language = $(this).val();
// destroy searching toolbar
$grid.jqGrid("destroyFilterToolbar");
// set some searching options
$grid.jqGrid("setColProp", "closed",
language === "de" ?
{searchoptions: {value: ":Beliebig;true:Ja;false:Nein"}} :
{searchoptions: {value: ":Any;true:Yes;false:No"}});
$grid.jqGrid("setColProp", "ship_via",
language === "de" ?
{searchoptions: {value: ":Beliebig;FE:FedEx;TN:TNT;IN:Intim"}} :
{searchoptions: {value: ":Any;FE:FedEx;TN:TNT;IN:Intim"}});
// create new searching toolbar with nes options
$grid.jqGrid("filterToolbar", {stringResult: true, defaultSearch: "cn"});
});

Call custom method on keypress SlickGrid

I am using slickgrid to display certain data. How can i add custom method to slickgrid rows ?
For eg: I want to open modal box with current row data whenever enter key is pressed.
You can subscribe to the onKeyDown event in the grid to check this. Something like:
grid.onKeyDown.subscribe(function(e) {
if (e.which == 13) {
// open modal window
}
});
Let me know if this helps!
If i got your requirement well, then try out this code,
createInvoiceDetailsTable : function () {
var gridOptions, gridColumns;
gridColumns = [
{id:'ean_code', name:'EAN', field:'ean_code', width:125, cssClass: 'grid-cell'},
{id:'description', name:'Product Description', field:'description', width:250, formatter:opr.invoice.productGridDescriptionFormatter, cssClass: 'grid-cell'},
{id:'qty', name:'Qty', field:'qty', width:40, , formatter:UpdateQtyBtnFormatter},
];
gridOptions = {
editable: true,
autoEdit: true,
enableAddRow: false,
enableCellNavigation: true,
asyncEditorLoading: false,
enableColumnReorder: false,
rowHeight: 35
};
dataView = new Slick.Data.DataView();
invoiceProductGrid = new Slick.Grid($('#invoice_details_grid_div'), dataView , gridColumns, gridOptions);
function UpdateQtyBtnFormatter (row, cell, value, columnDef, dataContext) {
return '<input type="button" style="width:30px; height:30px;" class="update_invoice_product_qty" id="' + value + '" value="Q"/>';
}
}
Using this update_invoice_product_qty class name you can write event.
If this is not your requirement then please share with some code or procedure which you tried earlier.

Categories