13

Take a look at my code here...

Controller ("tasks" is an array of JSON objects resolved in my Routes.js):

app.controller('testCtrl', function(tasks){
    $scope.tasks = tasks.data;
};

HTML:

 <div class="client-wrapper">
   <div class="task-wrapper" ng-repeat="taskData in tasks">
     <div task="taskData">
     </div>
   </div>
 </div>

Directive:

app.directive('task', function(){
  return {
    restrict: 'A',
    scope: {taskData: '=taskData'},
    templateUrl: "/templates/directives/task.html",
    link: function(scope, element, attribute) {
      console.log(scope.taskData);
    }
  };
});

For some reason, I seem incapable of figuring out how to pass the current object being looped through in the tasks array to this directive so that I can manipulate it therein.

I've tried numerous solutions, as seen below:

how to pass a json as a string param to a directive <--- which tells me to output {{ object }} inside if an HTML attribute, and then $eval that back to JSON in the directive...

That's a very gross way of doing it, and I definitely don't want to do it that way (nor do I think this will allow it to two-way-bind back to the actual object in the tasks array in the controllers scope. This method just converts the JSON to string --> evals back to JSON + makes a copy of that string inside the directives scope).

https://groups.google.com/forum/#!msg/angular/RyywTP64sNs/Y_KQLbbwzzIJ <-- Same as above, they're saying to output the JSON as a string in an attribute, and then $eval it back to JSON... won't work for me for the same reasons as the first link.

http://jsfiddle.net/joshdmiller/FHVD9/ <-- Copying his exact syntax isn't possible because the data I want to pass to my directive is the current index of the tasks array while being ng-repeated... This is close, but doesn't work within the constraints of ng-repeat apparently?

Angularjs pass multiple arguments to directive ng-repeat <-- This syntax isn't working for me -- if I attempt to pass the taskData object (the current representation object in the array being looped through) in a parameter, it passes the literal string "taskData" and not the object itself? At this point I'm really scratching my head.


What I'm trying to accomplish (since I might be going about this in the wrong way entirely and feel I should explain the problem as a whole):

I have a bunch of data called tasks. They have a few properties, such as:

completed: true || false

description: a string

tags: an array of strings

Etc, etc.

I am outputting a big table of rows for all of these tasks. Each row will be a directive, with some buttons you can press on that row in order to change the data pertaining to the task on this row.

I want to have the functions to manipulate the data of each individual task inside the link function of the directive. So like markAsCompleted() would be a function within the directive, that would update the completed boolean of whichever task was being clicked on.

I am doing it this way, because as I see it I have two options:

  1. A function in the controller where I pass in the task to modify as a parameter, and then perform the data manipulation
  2. Or a function in the angular directive that just manipulates the data of the object attached to this particular directive (and my current issue is my apparent inability to two-way bind an object to this particular directive)

I want to be able to accomplish the second option in order to make my directive modular and stand-alone.


So yeah. I'm confused as to how to go about doing this and would greatly appreciate some insight as to where I'm going wrong :)

Community
  • 1
  • 1

2 Answers2

16

scope: {taskData: '=taskData'} means Angular expects an attribute called task-data with the value to be passed in. So give this a try...

<div class="client-wrapper">
   <div class="task-wrapper" ng-repeat="taskData in tasks">
     <div task task-data="taskData">
     </div>
   </div>
</div>
Anthony Chu
  • 37,170
  • 10
  • 81
  • 71
1

In your current attempt your directive is expecting an attribute called task-data.

This should fix your problem:

app.directive('task', function(){
  return {
    restrict: 'A',
    scope: {task: '='},
    templateUrl: "/templates/directives/task.html",
    link: function(scope, element, attribute) {
      console.log(scope.taskData);
    }
  };
});

Notice i changed the name of your property in the directive's scope from task-data to task

CodePrimate
  • 6,646
  • 13
  • 48
  • 86