ng-repeat filtering data by date range
Asked Answered
C

3

20

I'm trying to filter a list that contains a timestamp by typing a range of dates

for example:

JSFIDDLE

html

<div ng-app="tst">
    <div ng-controller="MyController">
        <table>
            <tr>
                <td>From:
                    <input ng-model="query.date1" type="text" placeholder="" />
                </td>
                <td>To:
                    <input ng-model="query.date2" type="text" placeholder="" />
                </td>
            </tr>

            <tr ng-repeat="order in orders |filter:query">
                <td>{{order.date1 * 1000 | date:'dd-MM-yyyy'}}</td>
                <td>{{order.date2 * 1000 | date:'dd-MM-yyyy'}}</td>
            </tr>
        </table>
    </div>
</div>

javascript

var nameSpace = angular.module('tst',[]);

nameSpace.controller('MyController', function MyController($scope) {
  $scope.orders = [
  {
    "date1":"1306487800",
    "date2":"1406587800"
  },
  {
    "date1":"1196487800",
    "date2":"1406597800"
  }]
});

i want to be able to fill the "From" field with the value : 27-05-2010

and the "To" field the value of : 29-07-2015

and get only the records that are in this range.

(the first record in the example).

Thanks allot Avi

Clos answered 26/8, 2014 at 21:28 Comment(0)
E
36

You can create a custom filter to achieve this aim.

JSFIDDLE

html

<input ng-model="dateFrom" type="text"/>
<input ng-model="dateTo" type="text"/>
<tr ng-repeat="order in orders | myfilter:dateFrom:dateTo">
  <td>{{order.date1 * 1000 | date:'dd-MM-yyyy'}}</td>
  <td>{{order.date2 * 1000 | date:'dd-MM-yyyy'}}</td>
</tr>

javascript

function parseDate(input) {
  var parts = input.split('-');
  return new Date(parts[2], parts[1]-1, parts[0]); 
}

nameSpace.filter("myfilter", function() {
  return function(items, from, to) {
        var df = parseDate(from);
        var dt = parseDate(to);
        var result = [];        
        for (var i=0; i<items.length; i++){
            var tf = new Date(items[i].date1 * 1000),
                tt = new Date(items[i].date2 * 1000);
            if (tf > df && tt < dt)  {
                result.push(items[i]);
            }
        }            
        return result;
  };
});

also, i changed the timestamp data type from string to numbres.

  $scope.orders = [
  {
    "date1": 1306487800,
    "date2": 1406587800
  },
  {
    "date1": 1196487800,
    "date2": 1406597800
  }]
Elastin answered 27/8, 2014 at 7:56 Comment(6)
Use ISO 8601 date format for cross-browser solution en.wikipedia.org/wiki/ISO_8601Chesna
@Emanuel Ve, I have followed similar way of implementation.Its even iterating for num of arrayList.But while displaying am getting empty data finally.Can u please help me with this.https://mcmap.net/q/662748/-trouble-in-filter-table-data-between-two-selected-dates-using-angularjs/6756805Firebug
@Emanuel Ve : in your case you provide date like '1306487800' ,but in my case date in json .so how i can achived this solution ?plz help me.Weld
@GhanshyamLakhani what date format r'u using in your json?Elastin
@EmanuelVe : my date format like /Date(1224043200000)/ this format im retrive when bind my grid using angular..then how im filter using fromdate and todate ..is any idea.Weld
@GhanshyamLakhani I think you should add a new question referencing this one and explaining this particular scenario.Elastin
H
2

I have created a filter with momentJS to make things easier:

.filter('dateRange', function() {
    return function(items, startDate, endDate) {
        var retArray = [];

        if (!startDate && !endDate) {
            return items;
        }
        angular.forEach(items, function(obj) {
            var receivedDate = obj.date;
            if (moment(receivedDate).isAfter(startDate) && moment(receivedDate).isBefore(endDate)) {
                retArray.push(obj);
            }
        });

        return retArray;

    }
})
Hist answered 26/8, 2016 at 7:43 Comment(1)
If you got momentJS at your disposal, you can use momentjs.com/docs/#/query/is-betweenFootplate
F
1

For time manipulation I strongly recommend libraries such as momentJS; with momentJS and modern browsers this can be achieved in a very declarative way:

.filter('dateRange', function() {
  return function(items, startDate, endDate) {
    //an undefined startDate is converted to the beginning of time
    startDate = startDate || 0;

    const granularity = null // can be 'days', ... see momentJS doc

    //you need support for array.prototype.filter and arrow functions; i.e. IE sucks/needs a polyfill   
    return items.filter(item => moment(item).isBetween(startDate, endDate, granularity, '[]'));
  }
}
Footplate answered 20/1, 2017 at 14:23 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.