Angularjs ui-modal 不能正常处理 $http 请求

Angularjs ui-modal is not working properly with $http request

我正在使用 Angularjs 1.5.x 和 AngularUI Bootstrap

我正在尝试打开一个 bootstrap 模式并使用 $http 请求用远程数据填充它。

我正在使用 modal 的打开实例的 resolve 方法来触发 $http 请求并获取数据。之后我更新了一个局部变量并 return 它。但是,$http 正在正确获取数据,但本地范围变量未正确更新,并且它在模板中一直显示为空数组。

代码:

app.controller('ModalCtrl', function ($uibModal, $log, $document, $rootScope, $http) {
      var $cctrl = this;

      $cctrl.modalData = [];

      $cctrl.animationsEnabled = true;

      $cctrl.open = function (size, templateUrl, parentSelector) {
         var parentElem = parentSelector ?
            angular.element($document[0].querySelector('.modal-demo ' + parentSelector)) : undefined;
         var modalInstance = $uibModal.open({
            animation: $cctrl.animationsEnabled,
            ariaLabelledBy: 'modal-title',
            ariaDescribedBy: 'modal-body',
            templateUrl: templateUrl,
            controller: 'ModalInstanceCtrl',
            controllerAs: '$cctrl',
            size: size,
            appendTo: parentElem,
            resolve: {
               modalData: function () {
                  var url;
                  var reqData;
                  var config = {
                     headers: {
                        'Content-Type': 'application/x-www-form-urlencoded',
                        'responseType': 'json',
                        'cache': false
                     }
                  };

                  if (templateUrl == 'test.html') {
                     reqData = $.param({
                        lclasses: ($rootScope.activeTruck.truck.LicenceClassesRequired || ''),
                        subbie: ($rootScope.activeTruck.truck.subbie || '0')
                     });

                     url = 'index.php?module=test&task=fetchJSON';
                  }

                  $http.post(url, reqData, config).then(function (response) {
                     console.log("Success");
                     console.log(response); //here, response fetched data success
                     $cctrl.modalData = response.data;
                     console.log($cctrl.modalData); //here, its [] data 
                     return $cctrl.modalData;
                  }, function (response) {
                     console.log("Failed");
                     console.log(response);
                  });
               }
            }
         });

         modalInstance.result.then(function (selectedItem) {
            console.log("opened");
         }, function () {
            $log.info('Modal dismissed at: ' + new Date());
         });
      };
   });

// Please note that $uibModalInstance represents a modal window (instance) dependency.
// It is not the same as the $uibModal service used above.

   app.controller('ModalInstanceCtrl', function ($uibModalInstance, modalData) {
      var $cctrl = this;
      console.log(modalData);
      $cctrl.modalData = modalData;

      $cctrl.ok = function () {
         //$uibModalInstance.close($cctrl.selected.item);
         $uibModalInstance.close();
      };

      $cctrl.cancel = function () {
         $uibModalInstance.dismiss('cancel');
      };
   });

这里工作正常...

angular.module('ui.bootstrap.demo', ['ui.bootstrap']);
angular.module('ui.bootstrap.demo').controller('ModalDemoCtrl', function ($scope, $uibModal, $log) {
var $cctrl = this;

  $cctrl.items = [
    {
        "id": 0,
        "picture": "https://ultimatemotorcycling.com/wp-content/uploads/2011/11/2012-ducati-panigale-1199-preview-5.jpg",
        "age": 31,
        "name": "Mathews Goff",
        "company": "FXA"
    },
    {
        "id": 1,
        "picture": "http://placehold.it/32x32",
        "age": 36,
        "name": "Collins Alston"
    },
    {
        "id": 2,
        "picture": "http://placehold.it/32x32",
        "age": 27,
        "name": "Jasmine Rollins"
    },
    {
        "id": 3,
        "picture": "http://placehold.it/32x32",
        "age": 32,
        "name": "Julie Jefferson"
    },
    {
        "id": 4,
        "picture": "http://placehold.it/32x32",
        "age": 23,
        "name": "Wilder King"
    },
    {
        "id": 5,
        "picture": "http://placehold.it/32x32",
        "age": 23,
        "name": "Stanley Moore"
    },
    {
        "id": 6,
        "picture": "http://placehold.it/32x32",
        "age": 36,
        "name": "Reynolds Bishop"
    },
    {
        "id": 7,
        "picture": "http://placehold.it/32x32",
        "age": 26,
        "name": "Bryant Flowers"
    },
    {
        "id": 8,
        "picture": "http://placehold.it/32x32",
        "age": 38,
        "name": "Jenifer Martinez"
    },
    {
        "id": 9,
        "picture": "http://placehold.it/32x32",
        "age": 40,
        "name": "Mcguire Pittman"
    },
    {
        "id": 10,
        "picture": "http://placehold.it/32x32",
        "age": 34,
        "name": "Valdez Hyde"
    },
    {
        "id": 11,
        "picture": "http://placehold.it/32x32",
        "age": 34,
        "name": "Marla Mayo"
    },
    {
        "id": 12,
        "picture": "http://placehold.it/32x32",
        "age": 30,
        "name": "Brown Ortega"
    },
    {
        "id": 13,
        "picture": "http://placehold.it/32x32",
        "age": 32,
        "name": "Jeannette William"
    },
    {
        "id": 14,
        "picture": "http://placehold.it/32x32",
        "age": 30,
        "name": "Bridges Ashley"
    },
    {
        "id": 15,
        "picture": "http://placehold.it/32x32",
        "age": 33,
        "name": "Latasha Hewitt"
    },
    {
        "id": 16,
        "picture": "http://placehold.it/32x32",
        "age": 35,
        "name": "Alma Sawyer"
    },
    {
        "id": 17,
        "picture": "http://placehold.it/32x32",
        "age": 21,
        "name": "Liz Mcbride"
    },
    {
        "id": 18,
        "picture": "http://placehold.it/32x32",
        "age": 26,
        "name": "Mcintosh Chandler"
    },
    {
        "id": 19,
        "picture": "http://placehold.it/32x32",
        "age": 20,
        "name": "Alford Hartman"
    },
    {
        "id": 20,
        "picture": "http://placehold.it/32x32",
        "age": 29,
        "name": "Tiffany Green"
    },
    {
        "id": 21,
        "picture": "http://placehold.it/32x32",
        "age": 38,
        "name": "Stafford Riggs"
    },
    {
        "id": 22,
        "picture": "http://placehold.it/32x32",
        "age": 40,
        "name": "Elinor Chambers"
    },
    {
        "id": 23,
        "picture": "http://placehold.it/32x32",
        "age": 27,
        "name": "Carly Howard"
    },
    {
        "id": 24,
        "picture": "http://placehold.it/32x32",
        "age": 27,
        "name": "Rosalind Sanchez"
    },
    {
        "id": 25,
        "picture": "http://placehold.it/32x32",
        "age": 28,
        "name": "Jaclyn Shelton"
    },
    {
        "id": 26,
        "picture": "http://placehold.it/32x32",
        "age": 25,
        "name": "Hughes Phelps"
    },
    {
        "id": 27,
        "picture": "http://placehold.it/32x32",
        "age": 36,
        "name": "Rosetta Barrett"
    },
    {
        "id": 28,
        "picture": "http://placehold.it/32x32",
        "age": 29,
        "name": "Jarvis Wong"
    },
    {
        "id": 29,
        "picture": "http://placehold.it/32x32",
        "age": 23,
        "name": "Kerri Pennington"
    }
];

  $cctrl.open = function (size) {

    var modalInstance = $uibModal.open({
      templateUrl: 'myModalContent.html',
      controller: 'ModalInstanceCtrl',
      controllerAs:'$cctrl',
      resolve: {
        items: function () {
          return $cctrl.items;
        },
        size: function() {
         // console.log('size: ', size);
          return size;
        }
      }
    });

  };
});

// Please note that $modalInstance represents a modal window (instance) dependency.
// It is not the same as the $modal service used above.

angular.module('ui.bootstrap.demo').controller('ModalInstanceCtrl', function ($scope, $uibModalInstance, items, size) {
var $cctrl = this;
  $cctrl.items = items;
  $cctrl.selected = {
    item: $cctrl.items[0]
  };
  $cctrl.size = size;
 // console.log('size in ctrl: ', size);

  $cctrl.ok = function () {
    $uibModalInstance.close($cctrl.selected.item);
  };

  $cctrl.cancel = function () {
    $uibModalInstance.dismiss('cancel');
  };
});
<!doctype html>
<html ng-app="ui.bootstrap.demo">
  <head>
  <style>
  .grid {
    border: solid 1px #ccc padding: 10px 10px 0 0;
}
.grid li {
    display: inline-block;
    width: 100px;
    height: 200px;
    border: solid 1px #ccc;
    margin: 0 0 10px 10px;
    background: #eee;
}

/**** Transitions ****/

.masonry,
.masonry li { /* apply before masonry add class */
    position: absolute; /* important to add it before enter animation start */
    
    -webkit-transition-duration: .7s;
    transition-duration: .7s;
    
    -webkit-transition-property: all;
    transition-property: all;
}

.masonry .masonry-enter { /* limit animated properties for entering elements */
    -webkit-transition-property: -webkit-transform, opacity;
    transition-property: transform, opacity;
}

.masonry-enter,
.masonry-leave.masonry-leave-active {
    opacity: 0;
    -webkit-transform: scale(0.1);
    transform: scale(0.1);
}

.masonry-leave,
.masonry-enter.masonry-enter-active {
    opacity: 1;
    -webkit-transform: scale(1);
    transform: scale(1);
}</style>
  <script src="//cdnjs.cloudflare.com/ajax/libs/jquery/1.10.1/jquery.min.js"></script>
  <script src="//cdnjs.cloudflare.com/ajax/libs/masonry/2.1.08/jquery.masonry.min.js"></script>
    <script src="//ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.js"></script>
    <!--<script src="//angular-ui.github.io/bootstrap/ui-bootstrap-tpls-0.11.2.js"></script>-->
    <script src="https://cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/2.5.0/ui-bootstrap-tpls.js"></script>
    <script src="example.js"></script>
    <link href="//netdna.bootstrapcdn.com/bootstrap/3.1.1/css/bootstrap.min.css" rel="stylesheet">
    <link href="style.css" rel="stylesheet">
  </head>
  <body>
  
  <div ng-controller="ModalDemoCtrl as ctrl">
      <input type="text" ng-model="nameFilter" />
      <a href="#" ng-click="order = 'id'">Order by id</a>
      <a href="#" ng-click="order = 'name'">Order by name</a>
      <a href="#" ng-click="order = 'age'">Order by age</a>
  
      <ul class="grid" masonry="true">
          <li ng-repeat="item in ctrl.items | filter: { name: nameFilter } | orderBy: order">
              <span>{{item.name}}</span>
              <br /> <span>Age: {{item.age}}</span>
              <br /> <span>Company: {{item.company}}</span>
              <img ng-src="{{item.picture}}" width="100" ng-click="ctrl.open(item)"/>
          </li>
      </ul>
  </div>


    <script type="text/ng-template" id="myModalContent.html">
        <div class="modal-header">
            <h3 class="modal-title">I'm a modal!</h3>
        </div>
        <div class="modal-body">
            {{$cctrl.size.name}} {{$cctrl.selected}}
        </div>
        <div class="modal-footer">
            <button class="btn btn-primary" ng-click="$cctrl.ok()">OK</button>
            <button class="btn btn-warning" ng-click="$cctrl.cancel()">Cancel</button>
        </div>
    </script>

    
  </body>
</html>

像下面这样尝试..

$http.post(url, reqData, config).then(function (response) {
 return response.data; //return your response data directly
}

ModalInstanceCtrl 控制器中,您可以得到如下所示。

  $cctrl.modalData = modalData;