Jak używać $ rootScope w Angular do przechowywania zmiennych?


217

Jak używać $rootScopedo przechowywania zmiennych w kontrolerze, do którego chcę później uzyskać dostęp w innym kontrolerze? Na przykład:

angular.module('myApp').controller('myCtrl', function($scope) {
  var a = //something in the scope
  //put it in the root scope
});

angular.module('myApp').controller('myCtrl2', function($scope) {
  var b = //get var a from root scope somehow
  //use var b
});

Jak mam to zrobić?


1
powinieneś wstrzyknąć $ rootScope do kontrolera i używać go jako prostego javascript
Ajay Beniwal 18.09.2013

30
$ rootScope nie jest właściwym sposobem na zrobienie tego. Udostępnianie zmiennych na wielu kontrolerach jest właściwie tym, do czego służą usługi.
Steve

11
@Steve: FAQ Angulara mówi: „nie twórz usługi, której jedynym celem w życiu jest przechowywanie i zwracanie bitów danych”. Spowoduje to zbyt duże obciążenie cyklu $ digest ..
Marwen Trabelsi

Jeśli nie mogę wprowadzić kontrolerów do usług, jak mogę wysłać zmienną z tej usługi do mojego innego kontrolera? Nie widzę sposobu, żeby to zadziałało ... doceniam twój wgląd tutaj ...
wylądował

2
Cóż, ponieważ nie można go wstrzykiwać, do tego będzie potrzebna strzykawka.
Xsmael,

Odpowiedzi:


248

Zmienne ustawione w zakresie głównym są dostępne dla zakresu kontrolera poprzez dziedziczenie prototypowe.

Oto zmodyfikowana wersja dema @ Nitisha, która pokazuje relację nieco jaśniej: http://jsfiddle.net/TmPk5/6/

Zauważ, że zmienna rootScope jest ustawiana podczas inicjalizacji modułu, a następnie każdy z dziedziczonych zakresów otrzymuje swoją własną kopię, którą można ustawić niezależnie ( changefunkcja). Można również zaktualizować wartość rootScope ( changeRsfunkcja w myCtrl2)

angular.module('myApp', [])
.run(function($rootScope) {
    $rootScope.test = new Date();
})
.controller('myCtrl', function($scope, $rootScope) {
  $scope.change = function() {
        $scope.test = new Date();
    };

    $scope.getOrig = function() {
        return $rootScope.test;
    };
})
.controller('myCtrl2', function($scope, $rootScope) {
    $scope.change = function() {
        $scope.test = new Date();
    };

    $scope.changeRs = function() {
        $rootScope.test = new Date();
    };

    $scope.getOrig = function() {
        return $rootScope.test;
    };
});

7
Plus 1 za ... uh ... faktycznie odpowiadającą na pytanie OP. (Chociaż @MBielski i inni mają rację).
Rap

Jeśli to zrobię $scope.test = 'Some value', czy $rootScope.testzmiana również będzie?
Allen Linatoc

@AllenLinatoc nie, nie są to dwa różne obiekty, chociaż zakres $rootScope jest globalny (dla wszystkich kontrolerów), ale $scopepozostaje lokalny dla kontrolera. Jeśli używasz $scope.testdwóch różnych kontrolerów, wiedz, że są to dwie różne zmienne, niezależnie $rootScope.test od tego , czy byłyby takie same we wszystkich kontrolerach
Xsmael

Zakładam, że nie chcesz często używać $ rootScope z tego samego powodu, dla którego nie używałbyś zmiennych globalnych w innych językach?
Zypps987

Ile liczb zmiennych rootscope możemy stworzyć w aplikacji?
Jay

161

Udostępnianie danych między administratorami jest tym, do czego Fabryki / Usługi są bardzo dobre. Krótko mówiąc, działa coś takiego.

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

app.factory('items', function() {
    var items = [];
    var itemsService = {};

    itemsService.add = function(item) {
        items.push(item);
    };
    itemsService.list = function() {
        return items;
    };

    return itemsService;
});

function Ctrl1($scope,items) {
    $scope.list = items.list; 
}

function Ctrl2($scope, items) {
    $scope.add = items.add;
}

Można zobaczyć działający przykład w tym skrzypcach: http://jsfiddle.net/mbielski/m8saa/


49
+1 Nie $rootScopenależy używać do udostępniania zmiennych, gdy mamy takie rzeczy jak usługi i fabryki.
jjperezaguinaga,

74
Cóż, Angular FAQ mówi to na dole strony: „I odwrotnie, nie twórz usługi, której jedynym celem w życiu jest przechowywanie i zwracanie bitów danych”. Patrz: docs.quarejs.org/misc/faq
Oytun

11
To jest prosty przykład. Uważam, że twierdzą, że nie mają usługi, która pojawia się tylko w jednym kontrolerze. Nie mogę zliczyć, ile miejsc pracownicy, którzy opracowali Angular, wyraźnie stwierdzili, że usługi są oficjalnym sposobem przesyłania danych między administratorami. Rozejrzyj się po liście mailingowej, zapytaj różnych opraw Angular i zobacz, co dostajesz. Mogę również zauważyć, że twój cytat znajduje się na dole sekcji zatytułowanej „$ rootScope istnieje, ale można go użyć do zła”. Przekazywanie danych z jednego kontrolera do drugiego jest złe.
MBielski,

1
Ale jeśli chcesz zapętlić swoje elementy w dwóch różnych widokach / kontrolerach, musisz najpierw skopiować dane do kontrolera, aby je wyświetlić? (Wydaje mi się, że rozwiązano $ rootScope)
Thomas Decaux

1
Deweloper decyduje o tym, czy należy skorzystać z usługi, czy też o szybkiej poprawce rootScope, w niektórych przypadkach zakres globalny jest narzędziem i przydatnym - i myślę, że tak właśnie mówią doktorzy Angular. Pozwala zachować sztukę programowania i nie stać się całkowicie robotami MVC bla bla bla. Możesz skorzystać z powyższej usługi i obserwować zmienną, jeśli potrzebujesz jednego kontrolera, aby wiedzieć o zmianie, jednak w tym przypadku tak naprawdę nie jest to komunikacja między kontrolerami.
wylądował

21
angular.module('myApp').controller('myCtrl', function($scope, $rootScope) {
   var a = //something in the scope
   //put it in the root scope
    $rootScope.test = "TEST";
 });

angular.module('myApp').controller('myCtrl2', function($scope, $rootScope) {
   var b = //get var a from root scope somehow
   //use var b

   $scope.value = $rootScope.test;
   alert($scope.value);

 //    var b = $rootScope.test;
 //  alert(b);
 });

PRÓBNY


Więc w Angular zazwyczaj nie używasz var?
trysis

1
to zależy od stanu. jeśli chcesz pokazać w html, musisz użyć inaczej, możesz użyć var
Nitish Kumar 18.09.19

Och, zakres jest dla rzeczy DOM?
trysis

1
Może to być późno, ale w przypadku każdego spóźnionego zakresu zakres jest klejem między widokiem a kontrolerem dla dokumentacji AJS. zakres nie odnosi się bezpośrednio do DOM. co to robi? tutaj jest bardziej dokładna dokumentacja docs.quarejs.org/guide/scope
yantaq

9

nie znajduję żadnego powodu, aby zrobić to $ scope.value = $ rootScope.test;

Zakres $ jest już dziedzictwem prototypowym z $ rootScope.

Zobacz ten przykład

var app = angular.module('app',[]).run(function($rootScope){
$rootScope.userName = "Rezaul Hasan";
});

teraz możesz powiązać tę zmienną zakresu w dowolnym miejscu w tagu aplikacji.


6

najpierw przechowuj wartości w $ rootScope jako

.run(function($rootScope){
$rootScope.myData = {name : "nikhil"}
})

.controller('myCtrl', function($scope) {
var a ="Nikhilesh";
$scope.myData.name = a;
});

.controller('myCtrl2', function($scope) {
var b = $scope.myData.name;
)}

$ rootScope jest rodzicem wszystkich $ scope, każdy $ scope otrzymuje kopię danych $ rootScope, do których można uzyskać dostęp za pomocą samego $ scope.


3

Jeśli jest to po prostu „dostęp do innego kontrolera”, możesz do tego użyć stałych kątowych, korzyścią jest to; możesz dodać niektóre ustawienia globalne lub inne rzeczy, do których chcesz uzyskać dostęp w całej aplikacji

app.constant(‘appGlobals’, {
    defaultTemplatePath: '/assets/html/template/',
    appName: 'My Awesome App'
});

a następnie uzyskaj do niego dostęp w następujący sposób:

app.controller(‘SomeController’, [‘appGlobals’, function SomeController(config) {
    console.log(appGlobals);
    console.log(‘default path’, appGlobals.defaultTemplatePath);
}]);

(nie testowałem)

więcej informacji: http://ilikekillnerds.com/2014/11/constants-values-global-variables-in-angularjs-the-right-way/



1

Istnieje wiele sposobów na osiągnięcie tego:

1. Dodaj $rootScopew .runmetodzie

.run(function ($rootScope) {
    $rootScope.name = "Peter";
});

// Controller
.controller('myController', function ($scope,$rootScope) {
    console.log("Name in rootscope ",$rootScope.name);
    OR
    console.log("Name in scope ",$scope.name);
});

2. Utwórz jedną usługę i uzyskaj do niej dostęp w obu kontrolerach.

.factory('myFactory', function () {
     var object = {};

     object.users = ['John', 'James', 'Jake']; 

     return object;
})
// Controller A

.controller('ControllerA', function (myFactory) {
    console.log("In controller A ", myFactory);
})

// Controller B

.controller('ControllerB', function (myFactory) {
    console.log("In controller B ", myFactory);
})
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.