JQGrid optionally editable columns - asp.net-mvc-3

NOTE: I am using the JQGrid MVC component NOT the jquery plugin.
I have an editable column.
In some cases the user should not be able to edit it. I want to base this decision on another column value, which will be hidden.
I am aware of ClientSideEvents.AfterEditDialogShown but I'd like to do this with inline edit.
Is this possible?

You can use the beforeEditCell event to disable the cell editing conditionall for the column.
The column you want to apply conditional editing
{
cellEdit : true,
beforeEditCell : function(rowid, cellname, value, iRow, iCol) {
...
}
}
To know more check this.

Related

How to disable dropdown after binding dynamically in JqGrid form editing

In my JqGrid I am binding the dropdown dynamically, also I want the dropdown to be disabled after bindind, I written the code for this beforeShowForm event in edit portion but it get fired before buildSelect event in colModel,
as a result attribute is not getting applied, please give me some direction to disable the dropdown in this situation.
Thnaks.
I found the answer to that question,
editOptions{
dataInit: function (elem) {
$(elem).width(150);
$(elem).attr('disabled', 'disabled');
},
}
Use the following code , Its may be heplfyll
$("#dropdown").prop("disabled", true);
$("#dropdown").prop("disabled", false);

How to reset the dropdown value to the old value in jqgrid

I have a simple dropdown with two values.Lets say Staus:active and inactive.
During the onchange event, I want to perfrom some validation and revert back if the validation fails. Thai is if I change from active-inactive and my validation fails, I should change the dropdown back to active.
So far I am able to catch the on change event through the dataevents options of editOptions.
Below is my code, Thanks for the assist.
editoptions:{value:{Y:'Active',N:'Inactive'}, dataEvents:[
{
type: 'change',
fn: function(e) {
alert("inside change trigger");
$grid.setColProp('Status', { editoptions:{value:{Y:'Active',N:'Inactive'}}});
}
}
]}
I also read I have to set recreate form :true. I tried that also.
I would recommend you to consider to make the column non-editable or to readonly/disabled if the validation condition could be checked before editing will be started. It shows the user more clear that the field mayn't be changed.
Alternatively you can get savedRow parameter of jqGrid if you use inline editing mode or cell editing mode (with var savedRows = $(this).jqGrid("getGridParam", "savedRow")). To get the "old" data in case of form editing you can just get the data of selected row by using getGridParam with selrow (or alternatively from the hidden field of the form which have id="id_g". Something like var serRowId = $("#id_g").val();) and by using getRowData/getCell.

JqGrid setCell properties lost when sorting column

Just after editing a row (mode inline) I try to change some css properties of cells according the new value.
Typically : After editing of one row all cell of this row that contains the letter "D" I update the cell with a new css property : background-color: grey (using setCell method)
For that I use inline editing :
grid.jqGrid('navGrid',"#pager",{edit:false, add:false, del:false});
grid.jqGrid('inlineNav',"#pager",{edit:true, add:false, del:false, editParams: myEditParam});
For change the background after editing I use the method aftersavefunc
myEditParam :
...
aftersavefunc: function(rowId, dataFromServer)
{
var rowData = $("#list").jqGrid("getRowData", rowId);
for (var key in rowData)
{
if (rowData[key] == "D")
{
key++;
$("#list").jqGrid("setCell",rowId, key, "", {"background-color": "#ECECEC"} );
}
}
},
...
This code works but unfortunatly, when I sort one column of the grid the setCell method is not perserved ! (the cell lost it's background-color: grey)
Does it exist a better method for change the background after editing in function of the new value ?
Thx for your help ;)
I would suggest removing the Style from that event and rather move it to the more general function below. If the style isn't applied you can always trigger a refresh on the jqGrid as part of your after edit code.
The following function will examine each column cell value and if the TestValue is matching add the class to the row.
rowattr: function (rd) {
if (rd.ColumnName == TestValue) { return {"class": "RowBoldClass"}; }//if
},
and the matching class
RowBoldClass { font-weight:bold; .....
My answer from Making a row bold, changing background color - dwr
If you really need to change the format/color/style of the cell in the column which can the value "D" then you should use cellattr (see the answer or this one).
If you need to change the format/color/style of the row then you should use rowattr (see the answer).
One thing is important to understand: neither cellattr nor rowattr will be called at the end of row editing. So you will still have to use aftersavefunc callback.
The current code of aftersavefunc seems me a little strange. First of all I never had requirements to mark the value in any column of the grid based on the value ("D" in your case). Typically one need to test only specific column or columns for the value and then mark the cell or mark some other cell in the row.
In any way one need typically not just add the class in the value will be "D", but remove the class if the value is not "D".
I modified the demo from the answer to support inline editing (one should use double-click to start editing and press Enter to stop editing). The modified demo uses the following code of aftersavefunc additionally to cellattr used in the old demo:
aftersavefunc: function (rowId) {
var closed = $(this).jqGrid("getCell", rowId, "closed"), indexOfColumn;
if (closed === "Yes") {
// add CSS classes to the cell used to mark
$(this).jqGrid("setCell", rowId, "name", "",
"ui-state-error ui-state-error-text");
} else {
// remove CSS classes from the cell used to mark
indexOfColumn = getColumnIndexByName.call(this, "name");
$(this.rows.namedItem(rowId).cells[indexOfColumn])
.removeClass("ui-state-error ui-state-error-text");
}
}

jqGrid Autocomplete Inline Editing

I have a grid using jqGrid and in this grid I have the rows editable with inline editing. I'm trying to do autocomplete in the rows that is editable. Is this possible to do? And in case of yes, how can I identify these rows?
You could set the classes: autoCompleteFieldClassName in the colModel of the column, and then use that to add in your auto complete fields on edit.
Example:
in the colModel you can assign a class to the column cells via the option
classes: autoCompleteFieldClassName
This class would then allow you to set a jQuery selector on the inline edit event which would allow you to select the input element attached to this cell column. Once you have this element you can attach an jQuery autocomplete
$(inputElement).autocomplete({ source: '/Controller/GetAutocompleteInformation',
minLength: 2, autosearch: true,
select: function (event, ui) {
$(elem).val(ui.item.value);

JQGrid - toggling multiselect

Is there a way to toggle the multiselect option of a grid?
Changing the multiselect parameter of the grid and calling for a reload has the side-effect of leaving the header behind when disabling or not creating the header column if multiselect was not TRUE upon the grid creation.
The closest I have come is setting multiselect to TRUE upon grid creation and using showCol and hideCol to toggle: $('#grid').showCol("cb").trigger('reloadGrid');
This has a side effect of changing the grid width when toggled. It appears the cb column width is reserved when it is not hidden.
Basically I'm attempting to create a grid with an "edit/cancel" button to toggle the multiselect -- very similar to how the iPhone/iPad handles deleting multiple mail or text messages.
Thank you in advance.
I full agree with Justin that jqGrid don't support toggling of multiselect parameter dynamically. So +1 to his answer in any way. I agree, that the simplest and the only supported way to toggle multiselect parameter will be connected with re-initialize (re-creating) the grid.
So if you need to change the value of multiselect parameter of jqGrid you need first change multiselect parameter with respect of respect setGridParam and then re-creating the grid with respect of GridUnload method for example. See the demo from the answer.
Nevertheless I find your question very interesting (+1 for you too). It's a little sport task at least to try to implement the behavior.
Some remarks for the understanding the complexity of the problem. During filling of the body of the grid jqGrid code calculate positions of the cells based on the value of multiselect parameter (see setting of gi value here and usage it later, here for example). So if you will hide the column 'cb', which hold the checkboxes, the cell position will be calculated wrong. The grid will be filled correctly only if either the column 'cb' not exists at all or if you have multiselect: true. So you have to set multiselect: true before paging or sorting of the grid if the column 'cb' exist in the grid. Even for hidden column 'cb' you have to set multiselect to true. On the other side you have to set multiselect to the value which corresponds the real behavior which you need directly after filling of the grid (for example in the loadComplete).
I hope I express me clear inspite of my bad English. To be sure that all understand me correctly I repeat the same one more time. If you want try to toggle multiselect dynamically you have to do the following steps:
create grid in any way with multiselect: true to have 'cb' column
set multiselect: false and hide 'cb' column in the loadComplete if you want to have single select behavior
set multiselect: true always before refreshing the grid: before paging, sorting, filtering, reloading and so on.
I created the demo which seems to work. It has the button which can be used to toggle multiselect parameter:
In the demo I used the trick with subclassing (overwriting of the original event handle) of reloadGrid event which I described the old answer.
The most important parts of the code from the demo you will find below:
var events, originalReloadGrid, $grid = $("#list"), multiselect = false,
enableMultiselect = function (isEnable) {
$(this).jqGrid('setGridParam', {multiselect: (isEnable ? true : false)});
};
$grid.jqGrid({
// ... some parameters
multiselect: true,
onPaging: function () {
enableMultiselect.call(this, true);
},
onSortCol: function () {
enableMultiselect.call(this, true);
},
loadComplete: function () {
if (!multiselect) {
$(this).jqGrid('hideCol', 'cb');
} else {
$(this).jqGrid('showCol', 'cb');
}
enableMultiselect.call(this, multiselect);
}
});
$grid.jqGrid('navGrid', '#pager', {add: false, edit: false, del: false}, {}, {}, {},
{multipleSearch: true, multipleGroup: true, closeOnEscape: true, showQuery: true, closeAfterSearch: true});
events = $grid.data("events"); // read all events bound to
// Verify that one reloadGrid event hanler is set. It should be set
if (events && events.reloadGrid && events.reloadGrid.length === 1) {
originalReloadGrid = events.reloadGrid[0].handler; // save old
$grid.unbind('reloadGrid');
$grid.bind('reloadGrid', function (e, opts) {
enableMultiselect.call(this, true);
originalReloadGrid.call(this, e, opts);
});
}
$("#multi").button().click(function () {
var $this = $(this);
multiselect = $this.is(":checked");
$this.button("option", "label", multiselect ?
"To use single select click here" :
"To use multiselect click here");
enableMultiselect.call($grid[0], true);
$grid.trigger("reloadGrid");
});
UPDATED: In case of usage jQuery in version 1.8 or higher one have to change the line events = $grid.data("events"); to events = $._data($grid[0], "events");. One can find the modified demo here.
I really like what you are trying to do here, and think it would be a great enhancement for jqGrid, but unfortunately this is not officially supported. In the jqGrid documentation under Documentation | Options | multiselect you can see the Can be changed? column for multiselect reads:
No. see HOWTO
It would be nice if there was a link or more information about that HOWTO. Anyway, this is probably why you are running into all of the weird behavior. You may be able to work around it if you try hard enough - if so, please consider posting your solution here.
Alternatively, perhaps you could re-initialize the grid in place and change it from/to a multi-select grid? Not an ideal solution because the user will have to wait longer for the grid to be set up, but this is probably the quickest solution.
A simpler answer:
<input type="button" value="Multiselect" onclick="toggle_multiselect()">
<script>
function toggle_multiselect()
{
if ($('#list1 .cbox:visible').length > 0)
{
$('#list1').jqGrid('hideCol', 'cb');
jQuery('.jqgrow').click(function(){ jQuery('#list1').jqGrid('resetSelection'); this.checked = true; });
}
else
{
$('#list1').jqGrid('showCol', 'cb');
jQuery('.jqgrow').unbind('click');
}
}
</script>
Where list1 is from <table id="list1"></table>.

Resources