AngularJS $ destroy动态插入的组件

问题描述 投票:2回答:1

我正在建立一个提供服务以启用和禁用它的模式。该模态有一个小的控制器,它控制关闭按钮,以及进入模态内容的模板的$compile

该模板是一个组件,当然,该组件具有一个控制器。

隐藏模态后如何销毁该组件?从技术上讲,当ng-if负责从DOM中删除我的模式时,它仍然会加载该组件。

这里是代码:

modal.controller.js

class ModalController {
  constructor($scope, modalService, $compile, $timeout) {
    this.$scope = $scope;
    this.modalService = modalService;
    this.$compile = $compile;
    this.$timeout = $timeout;
  }

  $onInit() {
    this.$scope.$watch(this.modalService.getConfig(), (newVal) => {
      this.config = newVal.isDisplayed
        ? angular.extend(this.config, newVal)
        : {};

      // I wait for ng-if to put the modal into the DOM then I 
      // compile the component.
      this.$timeout(() => {
        if (this.config.template) {
          const component = this.$compile(this.config.template)(this.$scope);
          angular.element('#modal-content').html(component);
          this.config.isRendered = true;
        }
      }, 0);
    }, true);
  }

  close() {
    this.modalService.close();
  }
}

ModalController.$inject = [
  '$scope',
  'modalService',
  '$compile',
  '$timeout',
];

export default ModalController;

modal.service.js

class ModalService {
  constructor($timeout) {
    this.config = {};
    this.$timeout = $timeout;
  }

  open(newConfig) {
    this.config = newConfig;
    this.config.isDisplayed = true;
  }

  close() {
    this.config.template = null;
    this.config.isRendered = false;

    // the reason there is timeout here is to run my CSS animation
    // before ng-if removes the modal from the DOM.
    this.$timeout(() => {
      this.config.isDisplayed = false;
      this.config = {};
    }, 310);
  }

  getConfig() {
    return () => this.config;
  }
}

ModalService.$inject = [
  '$timeout',
];

export default ModalService;

BarController,我称之为模态:

class BarController {
  constructor(modalService) {
    this.modalService = modalService;
  }

  openModal() {
    this.modalService.open({
      title: 'Add a document',
      template: '<foo-component></foo-component>',
    });
  }
}

BarController.$inject = [
  'modalService',
];

export default BarController;
angularjs angular-components
1个回答
2
投票

啊哈!事实证明,它并不那么复杂。您只需要存储组件的作用域,然后在模式控制器的close函数内调用$ destroy。

class ModalController {
  constructor($scope, modalService, $compile, $timeout) {
    this.$scope = $scope;
    this.modalService = modalService;
    this.$compile = $compile;
    this.$timeout = $timeout;
  }

  $onInit() {
    this.childScope = null;

    this.$scope.$watch(this.modalService.getConfig(), (newVal) => {
      this.config = newVal.isDisplayed
        ? angular.extend(this.config, newVal)
        : {};

      this.$timeout(() => {
        if (this.config.template) {
          this.childScope = this.$scope.$new();

          angular
            .element('#modal-content')
            .html(this.$compile(this.config.template)(this.childScope));

          this.config.isRendered = true;
        }
      }, 0);
    }, true);
  }

  close() {
    this.config.isRendered = false;

    // this timout is used to make sure the CSS transition is executed
    // before the component is removed from the DOM.
    this.$timeout(() => {
      this.childScope.$destroy();
      angular.element('#modal-content').empty();
      this.modalService.close();
    }, 310);
  }
}

ModalController.$inject = [
  '$scope',
  'modalService',
  '$compile',
  '$timeout',
];

export default ModalController;
© www.soinside.com 2019 - 2024. All rights reserved.