简体   繁体   中英

How to use ng-click in ng-repeat?

I am new to Angular JS and I am trying to use ng-repeat to generate multiple row in my table, and in each row there should be a button to trigger a function with different parameter

<div ng-controller="testing">
    <table>
        <thead>
             <tr>
                  <th>col 1</th>
                  <th>col 2</th>
                  <th>button</th>        
             </tr>
        </thead>
        <tbody>
             <tr ng-repeat="item in items">
                 <td>{{ item.prop1 }}</td>
                 <td>{{ item.prop2 }}</td>
                 <td><button ng-click="myFunction(item.id)">Trigger Function</button></td>
             </tr>
        </tody>
    </table>
</div>

This of course doesn't work, as the ng-repeat creates its own scope, while myFunction is defined in the parent scope (ie the testing controller).

However, all I can find in Google result is the reason of not working, but lacks a way to fix the problem. How should I correct my code so that the ng-click works? Is there a way to define myFunction inside ng-repeat scope or is there a way to tell I want the function in the parent scope?

Please read the comment under the question. The comments are actually doing better by testing my code and found the code works. This helps me to realize the problem is elsewhere, which turns out that the function I am calling is mistakenly put under a child controller in the actual code.

The answers is good but does not solve the problem. It worth some reading, but I would prefer not to mark them as correct answer so as not to mislead people.

ng-click更改为以下

<button ng-click="testing.myFunction(item.id)">

Improve ng-repeat performance – using track by with ng-repeat

Pass $index to track your ng-repeat and which ng-click is being cliked

<tr ng-repeat="item in items track by $index"> <td>{{ item.prop1 }}</td> <td>{{ item.prop2 }}</td> <td><button ng-click="myFunction($index,item.id)">Trigger Function</button></td> </tr>

For Reference

Probably one of the very first things you learned doing with Angular was how to use ngRepeat. It's so easy and simple, you gotta love it. Here's an example:

<ul class="tasks"> <li ng-repeat="task in tasks" ng-class="{done: task.done}"> {{task.id}}: {{task.title}} </li> </ul>

The problem

Now say you have a button above that list to refresh it.

The obvious implementation for this refresh would be something along these lines in your controller:

$scope.tasks = newTasksFromTheServer;

This is a trivial piece of code, but it would cause ngRepeat to remove all li elements of existing tasks and create them again, which might be expensive (eg we have a lot of them or each li's template is complex). That means a lot of DOM operations.

Why would Angular do this? Behind the scenes ngRepeat adds a $$hashKey property to each task to keep track of it. If you replace the original tasks with new tasks objects from the server, even if those are in fact totally identical to your original tasks, they won't have the $$hashKey property and so ngRepeat won't know they represent the same elements.

track by to the rescue

In Angular 1.2 a new addition was made to the syntax of ngRepeat: the amazingly awesome track by clause. It allows you to specify your own key for ngRepeat to identify objects by, instead of just generating unique IDs.

This means that you can change the above to be ng-repeat="task in tasks track by task.id" and since the ID would be the same in both your original tasks and the updated ones from the server – ngRepeat will know not to recreate the DOM elements and reuse them. Boom.

you can also use 'track by $index' if your data source has duplicate data

//Below code will throw Error: dupes Duplicate Key in Repeater

<div ng-repeat="value in [4, 4]"></div>

//Below code will work perfectly fine

<div ng-repeat="value in [4, 4] track by $index"></div>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM