Accesso agli attributi da una direttiva AngularJS


95

Il mio modello AngularJS contiene una sintassi HTML personalizzata come:

<su-label tooltip="{{field.su_documentation}}">{{field.su_name}}</su-label>

Ho creato una direttiva per elaborarlo:

.directive('suLabel', function() {
  return {
    restrict: 'E',
    replace: true,
    transclude: true,
    scope: {
      title: '@tooltip'
    },
    template: '<label><a href="#" rel="tooltip" title="{{title}}" data-placement="right" ng-transclude></a></label>',
    link: function(scope, element, attrs) {
      if (attrs.tooltip) {
        element.addClass('tooltip-title');
      }
    },
  }
})

Tutto funziona bene, ad eccezione attrs.tooltipdell'espressione, che restituisce sempre undefined, anche se l' tooltipattributo è visibile dalla console JavaScript di Google Chrome quando si esegue un file console.log(attrs).

Qualche suggerimento?

AGGIORNAMENTO: Una soluzione è stata offerta da Artem. Consisteva nel fare questo:

link: function(scope, element, attrs) {
  attrs.$observe('tooltip', function(value) {
    if (value) {
      element.addClass('tooltip-title');
    }
  });
}

AngularJS + stackoverflow = beatitudine


Questa risposta a un'altra domanda spiega come esprimere correttamente un ternario in AngularJS.
Ismael Ghalimi

Quindi molto questo: "AngularJS + stackoverflow = bliss"
twip

Risposte:


83

Vedere la sezione Attributi dalla documentazione sulle direttive.

osservazione degli attributi interpolati : utilizzare $ osservare per osservare i cambiamenti di valore degli attributi che contengono l'interpolazione (es. src = "{{bar}}"). Questo non solo è molto efficiente, ma è anche l'unico modo per ottenere facilmente il valore effettivo perché durante la fase di collegamento l'interpolazione non è stata ancora valutata e quindi il valore è in questo momento impostato su undefined.



25

Sebbene l'utilizzo di "@" sia più appropriato rispetto all'utilizzo di "=" per il tuo particolare scenario, a volte utilizzo "=" in modo da non dovermi ricordare di utilizzare attrs. $ Osservare ():

<su-label tooltip="field.su_documentation">{{field.su_name}}</su-label>

Direttiva:

myApp.directive('suLabel', function() {
    return {
        restrict: 'E',
        replace: true,
        transclude: true,
        scope: {
            title: '=tooltip'
        },
        template: '<label><a href="#" rel="tooltip" title="{{title}}" data-placement="right" ng-transclude></a></label>',
        link: function(scope, element, attrs) {
            if (scope.title) {
                element.addClass('tooltip-title');
            }
        },
    }
});

Fiddle .

Con '=' si ottiene l'associazione dati bidirezionale, quindi è necessario prestare attenzione per garantire che scope.title non venga modificato accidentalmente nella direttiva. Il vantaggio è che durante la fase di collegamento, viene definita la proprietà dell'ambito locale (scope.title).


Ehi Mark, qual è la tua opinione sull'utilizzo di queste soluzioni, esiste una linea guida specifica per utilizzare l'osservazione sul collegamento attrs contro l'utilizzo dell'associazione dati bidirezionale? Penso che sembri più pulito usare l'associazione dati bidirezionale ma mi chiedo se ci sia un motivo per non usarlo?
Jeroen

@ Jeroen, ho postato una discussione più lunga sull'utilizzo di @vs = qui .
Mark Rajcok
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.