角材料加载angularjs 1.5组件到$ mdDialog

时间:2016-07-11 13:48:59

标签: angularjs angularjs-material mddialog

目标:使用组件而不是使用$ scope来设置数据。没有要共享的错误,问题是对话框加载组件时未设置数据元素。屏幕截图显示了对话框的当前状态,应该在选项卡#2(信息)中绑定一个对象。在使用onComplete事件加载对话框后,我可以验证对象(文档)是否可用。我试图通过以下方式将对话框调用可用的数据绑定到组件:

enter image description here

1使用当地人:

  locals: {
         document: document     
  },
  bindToController: true,
  onComplete: function(){
                    console.log('document: %O', document);
  }

2使用绑定:

   bindings: {
         document: '='
    }

3使用resolve:

  resolve: {
              document: function() {
                          return document;
                        }
            }

组件:

我相信错误在这里,绑定,“旧方法”使用$ scope vars,因此绑定毫不费力地连接。

(function(){
'use strict';
angular.module('adminClientApp')
.component('documentEdit', {
    templateUrl: 'js/app/components/document/documentEdit/document-edit.html',
    controller: function DocumentEditController($mdToast, $mdMedia) {
       var var documentEdit = this;
        documentEdit.document;

       },
       bindings: {
         document: '<'
       }
    });
  })();

对话框调用

DialogController中只有$ mdDialog事件。我意识到locals和bindToController都是针对对话框中指定的控制器(DialogController)。我在这里难倒 - 如何设置/传递/连接文档到组件控制器?

   this.showEdit = function ($event, document) {
                var parentEl = angular.element(document.body);

                $mdDialog.show({
                            parent: parentEl,
                            targetEvent: $event,
                            template: '<div><document-edit document="documentEdit.document"></document-edit></div>',
                            resolve: {
                                       document: function(){ return document;}
                            },
                            controller: DialogController,
                            onComplete: function(){
                                console.log('document: %O', document);
                            }
                        });

        }

2 个答案:

答案 0 :(得分:4)

您没有显示您的DialogController,但可能存在问题。我相信当你给它一个控制器参考时你也需要给它一个字符串,例如

controller: 'DialogController',

请参阅下面的示例,其中显示了如何使用$ mdDialog正确传入值。

(function() {
  angular
    .module('exampleApp', ['ngAnimate', 'ngAria', 'ngMaterial'])
    .controller('ExampleController', ExampleController);

  function ExampleController($mdDialog) {
    var vm = this;
    vm.dialogTemplate = '<md-dialog><md-dialog-content><document-edit document="vm.document"></document-edit></md-dialog-content></md-dialog>';
    vm.document = {
      id: '11',
      name: 'test',
    };
    vm.showLocalsBindedDialog = function(event) {
      $mdDialog.show({
        template: vm.dialogTemplate,
        targetEvent: event,
        clickOutsideToClose: true,
        escapeToClose: true,
        controller: 'DocumentDialogCtrl',
        controllerAs: 'vm',
        bindToController: true,
        locals: {
          'document': vm.document
        }
      });
    }

    vm.showResolveBindedDialog = function(event) {
      $mdDialog.show({
        template: vm.dialogTemplate,
        targetEvent: event,
        clickOutsideToClose: true,
        escapeToClose: true,
        controller: 'DocumentDialogCtrl',
        controllerAs: 'vm',
        bindToController: true,
        resolve: {
          document: function() {
            return vm.document;
          }
        }
      });
    }
  }
  ExampleController.$inject = ['$mdDialog'];
})();

(function() {
  angular
    .module('exampleApp')
    .controller('DocumentDialogCtrl', DocumentDialogCtrl);

  function DocumentDialogCtrl(document) {
    var vm = this;
    vm.document = document;
  }
  DocumentDialogCtrl.$inject = ['document'];
})();

(function() {
  'use strict';
  angular.module('exampleApp')
    .component('documentEdit', {
      bindings: {
        document: '<'
      },
      template: '<p>ID:{{vm.document.id}}</p><p>NAME:{{vm.document.name}}</p>',
      controller: DocumentEditController,
      controllerAs: 'vm'
    });

  function DocumentEditController() {
    var vm = this;
  }
})();
<!DOCTYPE html>
<html ng-app='exampleApp'>

<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular.min.js"></script>
  <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular-animate.min.js"></script>
  <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular-aria.min.js"></script>
  <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/angular-material/1.0.9/angular-material.min.css">
  <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/angular-material/1.0.9/angular-material.min.js"></script>
</head>

<body ng-controller="ExampleController as vm">
  <button ng-click="vm.showLocalsBindedDialog($event)">Show dialog with local passed in values</button>
  <button ng-click="vm.showResolveBindedDialog($event)">Show dialog with resolve passed in values</button>
</body>

</html>

答案 1 :(得分:3)

另一种可能性是使用范围选项。

const tempScope = $rootScope.$new(true);
tempScope.document = document; // This is the local variable

$mdDialog.show({
    scope: tempScope // Give the scope to the dialog
    parent: parentEl,
    targetEvent: $event,
    template: '<document-edit document="document"></document-edit>', // Use scope
    onComplete: function() {
        console.log('document: %O', document);
    }
});

这将创建用于编译模板的临时范围。您仍然需要绑定模板中的数据(document="document"),但您可以省略中间控制器。

注意如果您想使用resolve来解决承诺,则需要在显示对话框之前手动执行此操作。