I have this problem on a larger project and I made the most simplistic example.
I have a controller that has some data in it. This data is fed into the directive and should be displayed using the native ng-repeat. However, when the directive-controller runs, it has not yet parsed the angular variable, thus not rendering the repeat.
How do I make it work so that the repeat works with that outside variable that needs pre-parsing?
Here is a fiddle. Make sure you have the console open as it shows there that it is undefined when the function runs, but defined 1 second later: http://jsfiddle.net/paulocoelho/xqLAs/2/
Here my JS:
var module = angular.module('testApp', [])
.directive('test', function () {
return {
restrict: 'E',
template: '<p ng-repeat="x in sl">{{x.val}}</p>', // this wont work :(
scope: {
sl: '@sl'
},
link: function ($scope, $element, $attrs) {
console.log($attrs.sl); // this will return undefined
setTimeout(function(){
console.log($attrs.sl); // this will return the correct list
},1000);
}
};
});
function sweetCtrl($scope){
$scope.someList =
[
{"val":"a"},
{"val":"b"},
{"val":"c"},
{"val":"d"},
{"val":"e"},
{"val":"f"}
];
}
Here is my dom
<div ng-app="testApp" ng-controller="sweetCtrl">
<p>raw list: {{someList}}</p>
<p>repeat list:</p>
<test sl="{{someList}}"></test>
</div>
EDIT: There is was an error on my previous code where inputdata should read sl.
The fiddle with the solution is here: http://jsfiddle.net/paulocoelho/xqLAs/3/
When you use '@', the result is always a string. If you change your template to show {{x}} instead of {{x.val}} you'll see what I mean.
To pass an object to your isolate scope, use '=':
<test sl="someList"></test>
template: '<p ng-repeat="x in sl">{{x.val}}</p>', // this will work :)
scope: {
sl: '='
},
Also, as I (just now) explained in your other question, when '@' is used, you need to use $attrs.$observe or $scope.$watch() to asynchronously obtain the value (which will be a string). With '=', you don't have to use $observe or $watch.