Custom Sorting in AngularJS

Today I had to implement custom sorting in AngularJS. As with most things in Angular it’s very simple once you figure out how.

AngularJS has an orderBy function which can be used to sort a list of objects by any property. A common use case is when we want to sort by one of a few pre-determined sort orders.

Sort by a Property

As an example, let’s create a list of contacts.

function ContactListCtrl($scope){
  $scope.contacts = 
  [
    { "name":"Richard", "surname":"Stallman", "telephone":"1234 98765" },
    { "name":"Linus", "surname":"Torvalds", "telephone":"2345 87654" },
    { "name":"Donald", "surname":"Knuth", "telephone":"3456 76543" }
  ];
};

I can now easily display these contacts in a table by using the ng-repeat directive.

<table class="contacts">
  <tr>
    <th>Name</th>
    <th>Telephone</th>
  </tr>

  <tr ng-repeat="contact in contacts">
    <td ng-class-even="'even'">, </td>
    <td ng-class-even="'even'"></td>
  </tr>
</table>

Now let’s add a select with 2 different sort options. As per the documentation, we can specify a property to sort by and optionally a + or – to specify ascending or descending.

<select ng-model="sortorder">
  <option value="+surname">Surname (A-Z)</option>
  <option value="-surname">Surname (Z-A)</option>
</select>

Because we are using ng-model here we also need to specify a default sort order in our controller.

$scope.sortorder = 'surname';

Now we simply need to specify the orderBy clause in the ng-repeat directive.

<tr ng-repeat="contact in contacts | orderBy:sortorder">

You can see the full example in this jsFiddle.

Sort with a Custom Function

The documentation also says that we can sort using a function instead of a simply property. Let’s see how that would work.

I’m going to use the same HTML and contacts as before, but I’m going to change the ng-repeat directive to the following:

<tr ng-repeat="contact in contacts | orderBy:randomSort">

Now I’m going to implement a function called randomSort which will be used to sort the objects.

$scope.randomSort = function(contact) {
  return Math.random();
};

The function takes a single parameter – a contact object. The value you return here will be used to sort on, so you could combine any properties on the contact object to do the sorting.

You can see the full example in this jsFiddle. Every time you run the example you should see a different sort order.

Sort by a List of Properties

The documentation also says that we can sort by a list of properties. I’m going to modify my original example to sort by surname first and name second.

Again, I’m going to change the ng-repeat directive to specify an array of properties.

<tr ng-repeat="contact in contacts | orderBy:['surname','name']">

That’s all we need to do. You can see the full example in this jsFiddle.

As with most things in Angular, sorting is very simple once you figure out how. Happy coding.