1
votes

Filtering a column by date range works nice with solution that i've found in SO
How to define a Kendo grid Column filter between two dates? - proposed by MWinstead

But
"The only problem with this solution is that if you only select the End Date and apply the filter, the next time you open the filter menu, the Begin Date will get populated with the End Date you entered and the LTE operator will be selected, which will be changed by the jQuery code, resulting in a wrong filter"

Question asked by ataravati in the same thread

How we can resolve this issue ?

1

1 Answers

0
votes

The soltion is to provide the Begin Date with null value, even if the user hasn't selected it.
But, we must take control of submit button...

function grid_filterMenuInit(e) {
    var currentFieldName = e.field;
    if(currentFieldName === "yourFieldDate") {
        console.info("ignoring this field: <"   + currentFieldName + ">");
        return;
    }
    console.info("performing this field: <"     + currentFieldName + ">");

    var filterSubmit = e.container.find("[type=submit]:eq(0)");
    $(filterSubmit).click(function() {
        var searchDateAfter     = e.container.find("input:eq(0)");
        var searchDateAfter1    = $(searchDateAfter).val();
        var searchDateBefore    = e.container.find("input:eq(1)");
        var searchDateBefore1   = $(searchDateBefore).val();
        var gridDatasource      = $("#yourGridId").data("kendoGrid").dataSource;

        var jsDateBefore   = null;
        var jsDateAfter    = null;

        // we must convert kendoDateTime to JavaScript DateTime object
        // in my case the date time format is : yyyy/MM/dd HH:mm:ss
        if (typeof searchDateBefore1 !== 'undefined') {
            jsDateBefore  = newJsDate(searchDateBefore1);
        }
        if (typeof searchDateAfter1  !== 'undefined') {
            jsDateAfter = newJsDate(searchDateAfter1);
        }

        var previousFilter      = gridDatasource.filter();
        var previousFilters     = new Array();
        var newFilters          = new Array();

        // storing the previous filters ...
        if (typeof previousFilter === 'object' && previousFilter.hasOwnProperty("filters")) {
            previousFilters = previousFilter.filters;
            for (var i=0 ; i<previousFilters.length ; i++) {
                if (previousFilters[i].field !== currentFieldName) {
                    if (newFilters.length == 0) {
                        newFilters = [previousFilters[i]];
                    }
                    else {
                        newFilters.push(previousFilters[i]);
                    }
                }
            }
        }

        // this is the soltion : we must provide the first filter, even if the user has not provide the begin date
        // and the value will be : null
        if (newFilters.length == 0) {
            newFilters =    [{field: currentFieldName, operator: "gte", value: jsDateAfter   }];
        }
        else {
            newFilters.push ({field: currentFieldName, operator: "gte", value: jsDateAfter   });
        }

        if (jsDateBefore !== null) {
            newFilters.push ({field: currentFieldName, operator: "lte", value: jsDateBefore  });  
        }
        gridDatasource.filter (newFilters);
        $(".k-animation-container").hide();
        // to stop the propagation of filter submit button 
        return false;
    });
}


function newJsDate(dateTime) {
    if (dateTime        === null        || 
        typeof dateTime === 'undefined' ||
        dateTime        === "") {
        return null;
    }
    var dateTime1        = dateTime.split(" ");
    var date             = dateTime1[0];
    var time             = dateTime1[1];

    var date1     = date.split("/");
    var time1     = time.split(":");

    var year      = parseInt(date1[0], 10);
    var month     = parseInt(date1[1], 10);
        month     = month - 1;
    var day       = parseInt(date1[2], 10);

    var hour      = parseInt(time1[0], 10);
    var minute    = parseInt(time1[1], 10);
    var second    = parseInt(time1[2], 10);

    var jsDate    = new Date(year, month,  day,
                    hour, minute, second);

    return jsDate;
}