Javascript 使用AngularJS在ngclick上触发功能

Javascript 使用AngularJS在ngclick上触发功能,javascript,angularjs,angularjs-ng-click,Javascript,Angularjs,Angularjs Ng Click,我有一个函数,它对外部API进行$http调用,然后在ng repeat数组中填充一些结果 现在,在ng repeat上的每个元素上都会触发该函数,这会创建大量的服务器调用。我希望函数只在单击ng repeat中的元素后进行调用 我试过使用ng click,但我想说我遗漏了一些东西 我试图在单击时调用的$http查询是第二个: function ImageCtrl($scope, $http) { $scope.image = 'img/record-default.png';

我有一个函数,它对外部API进行$http调用,然后在ng repeat数组中填充一些结果

现在,在ng repeat上的每个元素上都会触发该函数,这会创建大量的服务器调用。我希望函数只在单击ng repeat中的元素后进行调用

我试过使用ng click,但我想说我遗漏了一些东西

我试图在单击时调用的$http查询是第二个:

function ImageCtrl($scope, $http) {
      $scope.image = 'img/record-default.png'; 
      $http.get('http://ws.audioscrobbler.com/2.0/?method=album.getinfo&api_key=e8aefa857fc74255570c1ee62b01cdba&artist=' + $scope.artist.name + '&album=' + $scope.release.title + '&format=json').
        success(function (data4) {
          $scope.image = data4.album.image[2]['#text'];
        }
      )

    function getVersions ($scope, $http){    
      $http.get('http://api.discogs.com/masters/' + $scope.release.id + '/versions').
        success(function (data5) {
          $scope.versions = data5.versions;
      });
  }   

}
以及相关的html:

<div class="col-md-3" ng-controller="ImageCtrl" ng-repeat="release in releases | filter:album | filter:year | filter:{ role: \'main\' }" > 
  <div class="release" ng-click="getVersions()"> \
     <img class="img-responsive" ng-src="{{image}}" /> {{release.title}} 
        <ul ng-controller="ImageCtrl">
           <li ng-repeat="version in versions">{{version.format}}</li>
        </ul>            
  </div> 
</div>

\
{{release.title}
  • {{version.format}

还有一个。所讨论的函数是script.js上的第60行,所以我最终接受了您所展示的内容并进行了一些重构

我将
getVersions
移动到原型中,并使用它将版本附加到发布对象,而不是
$scope

function ImageCtrl($scope, fakeService) {
  var _this = this;
  this.fakeService = fakeService;
  this.$scope = $scope;

  fakeService.getReleases()
      .then(function (releases) {
      $scope.releases = releases;
  });

  this.$scope.getVersions = function(release){
      _this.getVersions(release);
  };
}

ImageCtrl.$inject = ['$scope', 'fakeService'];

ImageCtrl.prototype.getVersions = function (release) {
  this.fakeService.getVersions(release.id)
      .then(function (versions) {
      release.versions = versions;
  });
};
标记没有太大的不同,但是您可以看到我在单击事件中将实际的
release
对象传递到
getVersions
函数的位置。这样,它总是直接作用于绑定到该特定行的对象

<div class="row" ng-controller="ImageCtrl">
    <div class="col-md-3" ng-repeat="release in releases">
        <div class="release" ng-click="getVersions(release)">
            <h1>{{release.title}}</h1>
            <img class="img-responsive" height="100" width="100" ng-src="{{release.image}}" />
            <ul>
                <li ng-repeat="version in release.versions">{{version.format}}</li>
            </ul>
        </div>
    </div>
</div>

{{release.title}
  • {{version.format}
下面是一个工作演示,展示了整个过程:


我在这里使用一个假服务来模拟调用web服务以获取数据。我强烈建议您结束对
$http
的呼叫,以便在控制器中封装数据访问。

可能是我理解错误的问题。为什么不将ng click='getVersions()'移动到li?这是否已完成?看起来你甚至没有注册你的控制器。@EricMitjans-好的。所以不是为了让你失望,但是你的实现有很多问题。给我一点时间,我会重构你的Plunkr。将超过5分钟;)@EricMitjans-我现在正在努力。应该可以帮助我找出代码中的问题。@EricMitjans-这是完全重构的Plunkr,很好地解释了Josh。我同意应该封装数据访问层,并且喜欢伪服务的想法。然而,在我看来,这里的代表团有点紧张,代码可能会变得复杂。最好是一路进行重构,并简单地使用一个专门用于此目的的角度服务。@EliranMalka-实际上我在这里进行了重构:说起来很奇怪。