4

In the view I have this:

     <table class="table table-bordered" id="resultsTable">
        <thead>
          <th>Classification</th>
          <th>Date</th>
        </thead>
        <tr ng-repeat="result in results">
          <td>{{result.result}}</td>
          <td>{{result.date}}</td>
        </tr>
      </table>

I want to use floating header, but as the table is empty when page is first loaded, it gives me weird results (http://www.fixedheadertable.com/)

If table content was static, this would work fine:

$(document).ready(function() {
  $('#resultsTable').fixedHeaderTable({ footer: true, cloneHeadToFoot: false, fixedColumn: false   });
});

In controller I have this function which loads data after pressing a button:

 $scope.loadResults = function() {
    var url = "URL WITH QUERY";
    $http.get(url).success(
      function(data, status, headers, config) {
        for (var i = 0; i < data.length; i++) {
            $scope.results.push({date: data[i].date, p: data[i].p, result: data[i].result});
        }

//**IDEALLY I WOULD WANT TO RUN THE JQUERY LINE HERE**

      }
    );
  };

So what I want to do is to run this line that I would normally run on document ready, after loading all data into the results array.

How would you do it?

Please, please, supply an example as I keep reading about "directives" but nobody says how exactly it allows calling jquery, where wanted line of jquery should be put or how it can be called from my controller.

4
  • your comment for the jquery location is incorrect. needs to be inside the function Commented Jun 1, 2013 at 21:51
  • @galchen Does AngularJS guarantee DOM manipulation from model changes synchronously? Commented Jun 1, 2013 at 21:51
  • @galchen fixed. @ user it's incorrect but I want to show what I want to achieve Commented Jun 1, 2013 at 21:53
  • I think you can use events to solve this. I'm not sure if DOM manipulation is synchronous, but i'd assume that using $emit after updating the $scope.results array would do the trick Commented Jun 1, 2013 at 22:05

2 Answers 2

2

You can simply achieve this using scope events $emit or $broadcast and $on in your scope to call jQuery functions at appropriate time.

Difference between $emit and $broadcast :

  • $broadcast -- dispatches the event downwards to all child scopes,
  • $emit -- dispatches the event upwards through the scope hierarchy.

This example will help to understand it : http://jsfiddle.net/sebmade/GkarV/

Sign up to request clarification or add additional context in comments.

3 Comments

This example is other way round. I see an event being emitted and picked up by controller. I want an event emitted from controller and picked up by something else that will run jquery
If you want to pick-up that event out of the $scope, then you can use $rootScope.
Also, I see one more option in this case. You can use $q.when(value) to hold the function call until the value is not resolved. -- $q.when
1

There is nothing stopping you from doing this:

$scope.loadResults = function() {
    var url = "URL WITH QUERY";
    $http.get(url).success(
      function(data, status, headers, config) {
        for (var i = 0; i < data.length; i++) {
            $scope.results.push({date: data[i].date, p: data[i].p, result: data[i].result});
        }
        $('#resultsTable').fixedHeaderTable({ footer: true, cloneHeadToFoot: false, fixedColumn: false   });
      }
    );
  };

but it is not considered best practice.

Additionally, you may need to wait for the Angular digest cycle to complete so that the ng-repeat has been processed. You can do that using either $timeout() or possibly a $scope.$evalAsync() (I am not 100% sure on the later working in this case, it may still fire too early so you would need to test it).

A cleaner solution would be to create a directive for that plugin. I don't see anything in the docs for the Fixed Header Table plugin to allow for dynamic data, so you would need to resolve that issue with either promises to ensure initialization happens after the data is ready and rendered, or a watch on the results array in order to call destroy on the plugin and re-initialize it.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.