web-dev-qa-db-fra.com

Comment regarder le changement de liaison de composant en utilisant Angular composant

Comment puis-je écouter angular composant liaison changer et effectuer des actions?

angular.module('myapp')
    .component('myComponent', {
        templateUrl: 'some.html',
        controller: MyController,
        controllerAs: 'myCtrl',
        bindings: {
            items: '<'
        }
    });

maintenant, quand items change je veux effectuer une autre action en utilisant cette valeur,
Comment puis-je le faire?

34
Dor Cohen

maintenant, quand les éléments changent, je veux effectuer une autre action en utilisant cette valeur, comment puis-je le faire?

Mais je veux éviter d'utiliser la portée $ mourante

Si vous ne pas voulez utiliser $scope vous pouvez utiliser une propriété setter pour détecter tout changement, par exemple. :

class MyController {
    private _items: string[] = []
    set items(value:string[]){
        this._items = value;
        console.log('Items changed:',value);
    }
    get items():string[]{
        return this._items;
    }
}

const ctrl = new MyController();
ctrl.items = ['hello','world']; // will also log to the console

Veuillez noter que vous ne devriez pas l'utiliser pour une logique complexe (raisons: https://basarat.gitbooks.io/TypeScript/content/docs/tips/propertySetters.html ) ????

27
basarat

Vous pouvez ajouter la méthode $onChanges Au contrôleur

$onChanges(changesObj) est appelée chaque fois que les liaisons unidirectionnelles sont mises à jour. ChangesObj est un hachage dont les clés sont les noms des propriétés liées qui ont changé et les valeurs sont un objet du formulaire.

L’exemple suivant gère l’événement canChange change.

angular.module('app.components', [])
.component('changeHandler', {
  controller: function ChangeHandlerController() {
    this.$onChanges = function (changes) {
      if (changes.canChange) 
       this.performActionWithValueOf(changes.canChange);
    };
  },
  bindings: {
    canChange: '<'
  },
  templateUrl: 'change-handler.html'
});

Nécessite AngularJS> = 1.5.3 et fonctionne uniquement avec une liaison de données unidirectionnelle (comme dans l'exemple ci-dessus).

Docs: https://docs.angularjs.org/guide/component

Référence: http://blog.edlytram.io/angularjs/2016/03/29/exploring-angular-1.5-lifecycle-hooks.html

57
David Remie

Voici une version ES5.1 de réponse de basarat :

function MyController() {
  var items = [];

  Object.defineProperty(this, 'items', {
    get: function() {
      return items;
    },

    set: function(newVal) {
      items = newVal;
      console.log('Items changed:', newVal);
    }
  });
}

Utiliser Object.defineProperty () . Pris en charge par tous les principaux navigateurs et IE9 +.

7
jfrej

J'ai découvert un moyen mais pas sûr que ce soit le plus efficace. Commencez par importer $ scope en tant que dépendance et réglez-le sur this._scope ou similaire dans votre constructeur. J'ai alors ce qui suit dans mon $onInit une fonction:

this._scope.$watch(() => {
    return this.items;
  },
  (newVal, oldVal) => {
    // Do what you have to here
  });

La réponse est très inspirante: Angularjs: 'controller as syntax' et $ watch

J'espère que ça va aider, c'est ce que je vais utiliser jusqu'à ce qu'on me dise le contraire.

3
Chris

Actuellement, vous ne pouvez pas utiliser angular sans $ scope car la détection des modifications est basée sur $ scope. Même si vous utilisez des expressions en HTML, ce serait la fonctionnalité de surveillance du délégué vers $ scope =.

Même si vous créez un autre mécanisme de surveillance, vous devez vous rappeler de décompresser manuellement - et avec $ scope cela se fait automatiquement.

0
m1gu3l