Imposta la variabile di ambito angolare nel markup


94

Domanda semplice: come posso impostare un valore di ambito in html, che deve essere letto dal mio controller?

var app = angular.module('app', []);

app.controller('MyController', function($scope) {
  console.log($scope.myVar);
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app='app'>
  <div ng-controller="MyController" app-myVar="test">
    {{myVar}}
  </div>
</div>

JSFiddle: http://jsfiddle.net/ncapito/YdQcX/


Potrebbe essere meglio creare una direttiva per gestire questo. Una direttiva incapsulerebbe: i parametri, un controller specifico per questa direttiva e un modello per il markup "myMap".
— Ian Mercer

Questo è in realtà quello che ho fatto ... ho solo alcuni problemi con l'accesso a $ scope.myVar nel controller di direttiva. Perché devo utilizzare un orologio nel controller per accedere alle variabili di ambito?
— Nix

1
Forse potresti pubblicare la tua direttiva? Dai un'occhiata a "Capire la transclusione e gli ambiti" qui docs.angularjs.org/guide/directive Probabilmente hai bisogno di scope: {myVar: '='} e diresti my-var="foo"quando lo chiami. Nota l'uso di trattino contro camelCase. Nota: fooqui viene valutato , se non si desidera utilizzare "@" nella definizione dell'ambito per accedere al valore dell'attributo.
— Ian Mercer

1
@Nix Puoi spiegare perché il valore deve essere inizializzato nella vista, piuttosto che nel tuo controller? Presumo che tu sappia già che non è il modo convenzionale di inizializzare i valori (altrimenti non lo chiederesti), e altri saranno in grado di darti risposte migliori se capiscono meglio il tuo caso d'uso.
— Sean the Bean

1
@SeantheBean ero giovane e sciocco ...;) non ho idea del perché avessi bisogno di farlo. Probabilmente stavo cercando di aggirare qualcosa.
— Nix

Risposte:


138

ng-initnon funziona quando si assegnano variabili all'interno di loop. Uso {{myVariable=whatever;""}}

Il trailing ""interrompe la valutazione dell'espressione angolare su qualsiasi testo.

Quindi puoi semplicemente chiamare {{myVariable}}per visualizzare il valore della tua variabile.

L'ho trovato molto utile durante l'iterazione di più array annidati e volevo mantenere le mie attuali informazioni sull'iterazione in una variabile invece di interrogarle più volte.


1
Anche se funziona, sembra hacky. Cioè, è generalmente buona pratica usare {{}}solo per l'output di una singola variabile, non per l'assegnazione di variabili. Direi che stackoverflow.com/a/16799763/814160 è più corretto (meno codice JS nella vista).
— Sean the Bean

1
+1 per @SeantheBean - L'ho provato. Sembra che ci siano problemi con i controller figlio e l'ambito di assegnazione della variabile nel markup. La direttiva funziona per i miei scopi e sembra essere una soluzione solida.
— Paul Carlton

2
Questo non sembra funzionare in angular2 / 4 - I binding non possono contenere incarichi
— Demodave

1
@Demodave dovresti invece impostare tutte le variabili del tuo controller nel codice Typescript e usare il template solo per connettere Typescript a HTML. Il modello non dovrebbe assegnare variabili.
— boxmein

80

ngInit può aiutare a inizializzare le variabili.

<div ng-app='app'>
    <div ng-controller="MyController" ng-init="myVar='test'">
        {{myVar}}
    </div>
</div>

jsfiddle esempio


3
Va notato che non consigliano questa soluzione per app reali (ma non suggeriscono davvero un'alternativa): docs.angularjs.org/guide/dev_guide.mvc.understanding_model
— Mike Robinson

Questo ha funzionato per me, tuttavia, all'inizio la variabile era ancora indefinita nel controller. Ho fatto un piccolo ciclo di intervallo: var interval = setInterval (function () {if ($ scope.wwhat) {// dostuff clearInterval (interval);}}, 10);
— roelleor

19

Crea una direttiva chiamata myVarcon

scope : { myVar: '@' }

e chiamalo così:

<div name="my_map" my-var="Richmond,VA">

Notare in particolare il riferimento del caso del cammello nella direttiva al nome del tag con trattino.

Per ulteriori informazioni, vedere "Capire la transclusione e gli ambiti" qui: - http://docs.angularjs.org/guide/directive

Ecco un violino che mostra come copiare i valori dagli attributi alle variabili di ambito in vari modi diversi all'interno di una direttiva.


Voglio essere in grado di farne più di uno var-nick='my' var-nick2='test'. A meno che tu non riesca a pensare a un modo per implementarlo con le direttive che userò solong-init
— Nix,

Puoi includere più attributi nello scope, tutto ciò di cui hai bisogno è che uno di essi sia il nome della direttiva che vuoi eseguire (o includi anche quel nome di direttiva nell'html). scope: {varNick: '@', varNick2: '@'}
— Ian Mercer

Ma non è scalabile? Dovrei definire una direttiva per variabile?
— Nix

No, non hai bisogno di una direttiva per variabile. Dai un'occhiata al violino che ho aggiunto alla risposta.
— Ian Mercer

Scusa se mi manca la lettura, il tuo esempio è perfetto, la mia unica modifica è stata l'ambito {'@': '@ "}.
— Nix,

10

Puoi impostare valori da html in questo modo. Non credo che ci sia ancora una soluzione diretta da angular.

 <div style="visibility: hidden;">{{activeTitle='home'}}</div>

7
Bel trucco ... lo consiglierei <div style="display: none">comunque.
— Roger

3

È possibile utilizzare ng-initcome mostrato di seguito

<div class="TotalForm">
  <label>B/W Print Total</label>
  <div ng-init="{{BWCount=(oMachineAccounts|sumByKey:'BWCOUNT')}}">{{BWCount}}</div>
</div>
<div class="TotalForm">
  <label>Color Print Total</label>
  <div ng-init="{{ColorCount=(oMachineAccounts|sumByKey:'COLORCOUNT')}}">{{ColorCount}}</div>
</div>

e quindi utilizzare la variabile di ambito locale in altre sezioni:

<div>Total: BW: {{BWCount}}</div>
<div>Total: COLOR: {{ColorCount}}</div>

Mi piace questo approccio; sembra meno hacky. Un chiarimento, però, ng-init non ha bisogno delle parentesi graffe.
— mklbtz

1
$scope.$watch('myVar', function (newValue, oldValue) {
        if (typeof (newValue) !== 'undefined') {
            $scope.someothervar= newValue;
//or get some data
            getData();
        }


    }, true);

La variabile si inizializza dopo il controller quindi è necessario controllarla e quando non è inizializzata la si usa.


0

Mi piace la risposta, ma penso che sarebbe meglio creare una funzione di ambito globale che ti consentirà di impostare la variabile di ambito necessaria.

Quindi nel globalController creare

$scope.setScopeVariable = function(variable, value){
    $scope[variable] = value;
}

e poi nel tuo file html chiamalo

{{setScopeVariable('myVar', 'whatever')}}

Questo ti permetterà quindi di usare $ scope.myVar nel tuo rispettivo controller


0

Se non sei in un ciclo, puoi usare ng-init altrimenti puoi usare

{{var=foo;""}}

il "" consente di non visualizzare la tua variabile

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.