从$http.get调用更新Angular作用域变量

Updating Angular scope variables from $http.get call

本文关键字:Angular 作用域 变量 更新 调用 http get      更新时间:2024-03-31

我对Angular还很陌生,我正试图弄清楚为什么范围变量在设置后没有更新。

我调用一个Nodeneneneba API,返回包含我的数据的json对象。除了将$scope.profile设置为从API返回的数据之外,一切似乎都很好。

设置:

app.js

(function() {
  var app = angular.module("gamedin", []);

  app.controller('profileController', function($scope, $http, $timeout) {
    $scope.profile = {};
    $scope.getProfile = function() {
      var vanityUrl = $scope.text.substr($scope.text.lastIndexOf('/') + 1);
      $http.get('/steamid/' + vanityUrl)
      .then(function(data) {
        $http.get('/profile/' + data.data.response.steamid)
        .then(function(data) {
          console.log(data.data.response.players[0]); // Correct data
          $scope.profile = data.data.response.players[0]; // View isn't updated
        })
      })
      // Reset the input text
      $scope.text = "";
    }
  });
  ...
  app.directive('giHeader', function() {
    return {
      restrict: 'E',
      templateUrl: 'components/header/template.html'
    };
  })
  app.directive('giProfile', function() {
    return {
      restrict: 'E',
      templateUrl: 'components/profile/template.html'
    }
  })
})();

components/header/template.html

<header>
  <div class="header-content" ng-controller="profileController">
    <div class="col-md-3"></div>
    <div class="col-md-6">
      <div class="header-content-inner">
        <input ng-model="text" ng-keyup="$event.keyCode == 13 && getProfile()" class="form-control" type="text" placeholder="Enter Steam URL">
      </div>
      <p>e.g., http://steamcommunity.com/id/verydankprofilelink</p>
    </div>
    <div class="col-md-3"></div>
  </div>
</header>

components/profile/template.html

<div class="container">
  <div ng-controller="profileController">
    <h3> 
      <strong>Username: {{ profile.personaname }}</strong>
    </h3>
    <p> SteamID: {{ profile.steamid }}</p>
  </div>
</div>

index.html

<!doctype html>
<html ng-app="gamedin">
<head>
  ...
</head>
<body>
  ...
  <gi-header></gi-header>
  <gi-profile></gi-profile>
  ...
</body>
</html>

我试着把它包装在$scope中$应用,就像这个

$scope.$apply(function () {
  $scope.profile = data.data.response.players[0];
});

导致CCD_ 1

然后我尝试了

$timeout(function () {
  $scope.profile = data.data.response.players[0];
}, 0);

$scope.$evalAsync(function() { 
  $scope.profile = data.data.response.players[0]; 
});

尽管没有抛出任何错误,但视图仍然没有更新。

我意识到我可能没有正确理解angular的某些方面,所以请启发我!

问题是您有两个profileController实例,每个指令模板中有一个。它们应该共享同一个实例,因为现在发生的情况是,一个实例在其作用域上更新profile变量,而另一个不知道。也就是说,头模板的profileController实例正在执行调用,您希望看到配置文件模板上的更改。

你需要重组。我建议在使用指令的页面中使用控制器,并在两个指令中共享配置文件对象:

  <gi-header profile="profile"></gi-header>
  <gi-profile profile="profile"></gi-profile>

在每个指令中:

return {
  restrict: 'E',
  scope: {
     profile: '='
  },
  templateUrl: 'components/header/template.html'
};

更一般的一点是,如果你想在指令中使用控制器,你可能应该使用指令的"controller"属性。

尝试使用此方法:

$http.get('/steamid/' + vanityUrl)
  .then(function(data) {
    return $http.get('/profile/' + data.data.response.steamid).then(function(data) { 
      return data;
    });
  })
  .then(function(data) {
     $scope.profile = data.data.response.players[0]; // View isn't updated
  })

使用两个解析而不是一个,然后从第二个解析更新作用域。