4

I am working on a news feed page with angular.js and jquery.

I am using a directive to detect the last feed to show. when it return scope.$last ==true, I call a function to do some Jquery animation.

Then, I added a ng-model showYear to filer elements by date, and added ng-if to filter elements.

My problem is, when the last element is filtered by ng-if and not rendered, the directive can not detect scope.$last and run feedPosition().

I've tried to do it like the url below but it face the same problem: here.

Kindly please Help.

here's my code:

HTML:

<div id="feedList">
    <div ng-repeat="feed in feeds | orderBy: '-date'" ng-if="show(feed.date)" feed-list-repeat-directive>
        //some content here
    </div>
</div>

Javascript:

<script>
var feeds = [{
    "type" : "publications",
    "source" :"AAA",
    "date" : new Date(2014, 4, 10),
    "title" : "title 2014",
    "thrumb" : "thrumb1.jpg"
},{
    "type" : "tvc",
    "source" : "BBB",
    "date" : new Date(2015, 4, 10),
    "title" : "title 2015",
    "thrumb" : "thrumb2.jpg"
}];

var app = angular.module('anApp', []);
app.controller('anCtrl', function($scope) {
     $scope.showYear = 2015;
     $scope.feeds = feeds;
    $scope.show = function(yr){
        return Number(yr.getFullYear())==$scope.showYear;
    };
})
.directive('feedListRepeatDirective', function() {
  return function(scope, element, attrs) {
    if (scope.$last){
        feedPosition(true);
    };
  };
});


function feedPosition(){
    for(a=0; a<$('#feedList > div').length; a++){       
        // do something to animate elements position
    };
};
</script>
Community
  • 1
  • 1
Wesleywai
  • 175
  • 10

1 Answers1

3

At the moment, $last applies to the array feeds, ordered by date. The ng-if is controlling whether each item is rendered or not, but it is not actually filtering the list.

In order to filter the list in such a way that $last will behave as required, remove the ng-if and use Angular's filter. filter selects a subset of items from the feeds array, according to the show function, and returns them as a new array. The new array contains only those elements that the show function returns true for.

<div ng-repeat="feed in feeds | filter: show | orderBy: '-date'" feed-list-repeat-directive>
    //some content here
</div>

Note that the show function will have to be modified slightly to take a full feed as input rather than a date:

$scope.show = function(feed){
    return Number(feed.yr.getFullYear())==$scope.showYear;
};
sheilak
  • 5,573
  • 7
  • 31
  • 38
  • Hi, someone suggested me to use ng-show instead of ng-if. I think that looks alike your solution. However, I don't want all feeds of all years rendered in the dom and just hiding unseleted items. btw, I've given up ng-if. Instead, I setup a model for selecting year, each time user change the selected year I made a new $http call. – Wesleywai Sep 14 '15 at 06:05
  • Hi, `ng-show` isn't like my solution. `ng-show` renders the items to the DOM but hides them by applying `.ng-hide` class. The solution in my answer uses `filter` to select a subset of items from the array and return them as a new array. So the excluded items are not rendered. Answer updated to clarify this. However your solution sounds like it will also work, although with the overhead of additional `$http` calls. – sheilak Sep 15 '15 at 08:25
  • 1
    Ic, thanks very much, I found the $http way suits my job more as I don't need the data of all years at the same time. but I think this is still a useful showcase. Will try it when available, thanks very much. :) – Wesleywai Sep 17 '15 at 14:45