How to show my top posts first in my Infinite Scroll, in descending order with firebase?

WHAT I TROILED (DOES NOT WORK CORRECTLY):

CODE:

<script> var app = angular.module('app', ['firebase']); app.controller('ctrl', function ($scope, $firebaseArray, $timeout) { $scope.data = []; var _n = Math.ceil(($(window).height() - 50) / (350)) + 1; var start = 0; var end = _n - 1; var lastScore = <%=lastScore%>; console.log("FIRST FIRST FIRST LAST SCORE:" + lastScore); var firstElementsLoaded = false; $scope.getDataset = function() { fb.orderByChild('score').endAt(lastScore).limitToLast(_n).on("child_added", function(dataSnapshot) { lastScore = dataSnapshot.child("score").val() - 1; console.log("LAST TOP LIKED:"+ lastScore); $scope.data.push(dataSnapshot.val()); $scope.$apply(); console.log("THE VALUE:"+$scope.data); $scope.data.splice(start, end).concat($scope.data.reverse()); $scope.$apply(); start = start + _n; end = end + _n firstElementsLoaded = true; }); }; $scope.getDataset(); window.addEventListener('scroll', function() { if (firstElementsLoaded == true) { if (window.scrollY === document.body.scrollHeight - window.innerHeight) { $scope.$apply($scope.getDataset()); } } }); }); // Compile the whole <body> with the angular module named "app" angular.bootstrap(document.body, ['app']); 


Question:

How can I return the client part of the data so that my messages from top to bottom correspond to their assessment (from highest to lowest)?


WHAT I WANT TO ACCESS:

Receive my messages in descending order according to an estimate that is a bit more complicated with infinite scrolling.

+5
source share
2 answers

As a result, I used the inversedScore property:

 <script> var app = angular.module('app', ['firebase']); app.controller('ctrl', function ($scope, $firebaseArray, $timeout) { $scope.data = []; var _n = Math.ceil(($(window).height() - 50) / (350)) + 1; var firstElementsLoaded = false; var lastScore = -100000; $scope.getDataset = function() { fb.orderByChild('inversedScore').startAt(lastScore).limitToFirst(_n).on("child_added", function(dataSnapshot) { lastScore = dataSnapshot.child("inversedScore").val() + 1; console.log("LAST LIKE SCORE:"+ lastScore); $scope.data.push(dataSnapshot.val()); $scope.$apply(); console.log("THE VALUE:"+$scope.data); firstElementsLoaded = true; }); }; $scope.getDataset(); window.addEventListener('scroll', function() { if (firstElementsLoaded == true) { if (window.scrollY === document.body.scrollHeight - window.innerHeight) { $scope.$apply($scope.getDataset()); } } }); }); // Compile the whole <body> with the angular module named "app" angular.bootstrap(document.body, ['app']); </script> 
0
source

Since the messages are displayed in reverse order, you must reverse the order of the "pages" (use endAt instead of startAt ) and sort the messages back on each page.

See also this answer.

Example

Setup:

 $scope.data = []; var n = Math.ceil(($(window).height() - 50) / (350)) + 1; var firstElementsLoaded = false; var lastScore = MAX_SCORE, lastKey 

Function for scroll event listener:

 $scope.getDataset = function() { fb.orderByChild('score') .endAt(lastScore, lastKey) //endAt is inclusive, take one more for the n-th .limitToLast(n + firstElementsLoaded) .once('value', loadPosts) function loadPosts(snapshot) { var posts = snapshot.val() function compare(a, b) { if (posts[a].score != posts[b].score) { return b.score - a.score } if (a < b) return 1 if (a > b) return -1 return 0 } //skip the post included by endAt var ordered = Object.keys(posts).sort(compare).slice(firstElementsLoaded) lastKey = ordered[ordered.length-1] lastScore = posts[lastKey].score ordered.forEach(function(key) { $scope.data.push(posts[key]) }) $scope.$apply(); firstElementsLoaded = true; } } 

For a more elegant way, you can try to keep the ratings back or use an extra value.

fb.orderByChild('reversedScore')

0
source

Source: https://habr.com/ru/post/1262189/


All Articles