I'd like an example of saving the user settings of the igGrid to the database and restoring these settings when the grid loads. I've found a few examples of this using the igGrid on the client-side, but I'd like to see how to do this using either Chaining or GridModel. I have this working loading the settings to the GridModel, but I need help capturing the entered values from the client and saving to the server.
Thanks in advance for your help.
Any help with this would be greatly appreciated. Thanks
Hello ericl,
Thank you for posting in our forum.
In order to be sure I understand your scenario and your question is addressed correctly, some additional information would be greatly appreciated:
Looking forward to hearing from you.
Thank you for the provided details.
As this is a custom scenario and the igGrid doesn’t support this functionality out-of-the-box, I am in the process of investigating which approach would best allow to fulfill the requirement that you have and I will get back to you tomorrow with more information regarding this matter.
Please feel free to contact me with any updates or additional questions regarding this scenario in the meantime.
Thanks Vasil,
I have a solution for filtering and paging; those are accessible via the controller using the GridDataSourceAction attribute and requesting those parameters from the query string, but I will need to find a solution for setting and saving other features including column moving, hiding, fixing. I can't seem to figure out how to access these events from the server at the time when the grid is changed by the user. Those parameters are not passed in the query string.
There are several events that get raised when the user interacts with the grid and might be useful - columnHidden, columnShown, columnMoved and columnFixed. Handling those event allows for ajax requests to be made to the server so that the necessary data be sent after a user interaction.
The query strings could be manipulated before being sent by setting the “urlParamsEncoded” option of the igDataSource.
Consider having the following sample object that has to be serialized and sent with the request also:
var obj = {"someOption1": 1, "someOption2": 2}
Then it could be done with code that looks like this:
$(document).on("iggridrendered", "#grid", function () { //setting the "urlParamsEncoded" dataSource option $("#grid").data("igGrid").dataSource.settings.urlParamsEncoded = function (item, params) { params.extraParams.obj = JSON.stringify(obj); } })
This would add the serialized object to the query string and it would be sent to the server as well. Please note the method that returns an ActionResult in your Controller has to be changed also in order to receive the extra parameters that get sent from the client.
I am still investigating if there is a better way to achieve your requirement and would contact you soon with more details.
I was able to capture the events. Thanks for pointing me in the right direction there. Below is my code for that.
//Bind after initialization $(document).delegate("#grid", "iggridhidingcolumnhidden", function (evt, ui) { evt;
// the index of the column, which is hidden console.log(ui.columnIndex); // the key of the column, which is hidden console.log(ui.columnKey);
//TODO: ajax call });
//Bind after initialization $(document).delegate("#grid", "iggridhidingcolumnshowing", function (evt, ui) { evt;
// the index of the column, which is shown console.log(ui.columnIndex); // the key of the column, which is shown console.log(ui.columnKey);
However, I was not able to get the query string manipulation to work as you showed. I am not using .DataSource() on my wrapper. Instead I am using .DataSourceUrl(). I'm assuming this is the reason? Also, It doesn't look like the grid gets rendered (iggridrendered event doesnt get fired) on the Hiding or Moving events. Is that what should be expected to happen with your example?
Thanks
Upon further research there is another approach that might be more suitable for your scenario. I have attached an MVC code sample for you, here is a more detailed explanation:
On the client side:
The Column Hiding and Column Fixing features modify the columns collection of the grid. This line of code:
let gridColumn = JSON.stringify($("#grid").data("igGrid").options.columns); allows me to get this array of column definitions and serialize it so I could send it to the server. The features that operate on the dataSource could be serialized this way:
let sortOpts = JSON.stringify($("#grid").data("igGrid").dataSource.settings.sorting.expression); let filterOpts = JSON.stringify($("#grid").data("igGrid").dataSource.settings.filtering.expression); let pagingOpts = JSON.stringify($("#grid").data("igGrid").dataSource.settings.paging);
You said you don’t want to have a “Save” button, which requires me to handle some events so that the new grid state gets saved. In the sample I have handled the columnMoved, columnHidden and columnShown events just for demonstrational purposes – the idea is the same for all the other features and it depends on how often you would need to save the state and how many server requests you want to send.
On the server:
I have replaced the Chaining that you have used in your View with a GridModel instance in the Controller. The reason is that is allows the grid properties to be modified dynamically when the server receives the new state of the grid after a user interaction. There is an internal GridModel instance which holds the current state of the grid and this is the object that has to be stored in the database – I am using an in-memory object just for the sake of simplicity.
The “SaveChanges” request handler method deserializes the columns query string and casts it to a List of GridColumn objects so that I am able to update the columns of the internal GridModel instance – if the user reloads the page this instance would be sent to the View instead of the initial one and the grid would keep its last saved state.
For the dataSource operations – Filtering, Sorting and Paging the approach is a little bit different. For the sake of simplicity I save the Paging only, but the idea is the same for the Filtering and Sorting: I have a class that describes the datasource options (that is because I don’t have a GridModel for the dataSource) and it allows me to deserialize the query strings instead of having to slice them into substrings. Then I update the internal GridModel dynamically at runtime.
remoteSaveState.zip
Feel free to contact me if you need any additional assistance regarding this matter.
Vasil, I got it working. Thank you again for your help!
Vasil,
All is working except for the grouping. How can I get the groupBy settings when changed?
In Controller:
groupBy.AddClientEvent("groupedColumnsChanged", "groupByChangedHandler");
On the client:
let groupByOpts = JSON.stringify($("#grid").data("igGrid").dataSource.settings.groupby);
which returns
{"defaultCollapseState":false,"groupRecordKey":"__gbRecord","groupSummaryRecordKey":"__gbSummaryRecord","summaries":[],"summariesPosition":"bottom","pagingMode":"dataRecordsOnly"}
I'm not sure if this is the data I need or how to use this to set the group by.
Thanks.
The GroupBy feature operates both on dataSource level by using the sorting expressions from the dataSource, and on UI level where the user is able to collapse and expand the groups - hence it is a little bit different than the Filtering/Sorting/Paging features. Please note that the grouped/ungrouped state of the columns may be sent to the server and restored later on the client, but the expand/collapse state gets lost when the page gets reloaded.
I am currently investigating which would be the most suitable way to save the grouping state on the back-end: I will contact you soon with more details as well as a modified MVC code sample.
Feel free to contact me with any updates or additional questions regarding this scenario in the meantime.
I have attached the modified MVC sample, as promised. Here are some details:
The GroupBy feature uses the dataSource sorting expressions, which I serialize on the client side along with the filtering and paging options before the ajax call is being made. The new code I have added finds the GroupBy feature object in the internalGridModel (this is the static object that keeps the current modified grid state instead of the initial one). Then I delete the GroupBy columnSettings because I want to create new ones - for each grouped column.
The sorting expressions provide the necessary information regarding which columns are currently grouped. For the deserialization the Newtonsoft JSON framework provides the JObject class, which has some useful methods – I have used the JObject.Parse() when deserializing the sorting expressions, as well as the GetValue() to get the values of a given key: value pair. First I check if the given columnSetting exists and set its new values, otherwise I create a new one and add it to the columnSettings collection.
remoteSaveStateGroupBy.zip
If you need any additional assistance, feel free to contact me.