$ aplicativo () e $ diger () são dois conceitos principais no AngularJs, mas às vezes são confusos. Para entender como o AngularJS funciona, você primeiro precisa entender como $ APLIC () e $ DIGEST () funcionam. Este artigo tem como objetivo explicar o que os $ aplicativos () e $ digery () são e como eles são aplicados na codificação diária.
1. Explore $ Aplicar () e $ Digest ()
1.1. Entender a ligação de dados bidirecional e $ watch ();
O AngularJS fornece um recurso muito legal chamado ligação de dados bidirecional, o que simplifica bastante como escrevemos nosso código. A ligação de dados significa que, quando quaisquer dados na visualização alteram, a alteração será automaticamente alimentada de volta aos dados do escopo, o que significa que o modelo de escopo será atualizado automaticamente. Da mesma forma, quando o modelo de escopo muda, os dados na visualização são atualizados para o valor mais recente. Então, como o AngularJS faz isso? Quando você escreve uma expressão como {{amodel}}, o AngularJS define um observador para você no modelo de escopo, que é usado para atualizar a visualização quando os dados mudarem. O observador aqui é o mesmo que o observador que você definirá no AngularJS:
$ scope. $ watch ('amodel', function (newvalue, OldValue) {// Atualize o DOM com newValue});O segundo parâmetro passado para $ watch () é uma função de retorno de chamada, que será chamada quando o valor da amodel for alterado. Quando a Amodel muda, não é difícil entender que essa função de retorno de chamada será chamada para atualizar a visualização, mas ainda há um problema muito importante! Como o AngularJS sabe quando chamar essa função de retorno de chamada? Em outras palavras, como o AngularJS chamou a função de retorno de chamada correspondente quando sabe que a Amodel mudou? Ele executará uma função periodicamente para verificar se os dados no modelo de escopo foram alterados? Bem, é aí que entra o loop $ Digest.
No loop $ Digest, os observadores serão demitidos. Quando um observador é acionado, o AngularJS detecta o modelo de escopo. Se mudar, a função de retorno de chamada associada ao observador será chamada. Então, a próxima pergunta é quando o $ Digest Loop começa de várias maneiras?
Depois de ligar para $ SCOPE. $ DIGEST (), o loop $ DIGEST começa. Suponha que você altere os dados no escopo da função Handler correspondente a uma diretiva NG-Click, o AngularJs acionará automaticamente um loop $ digery ligando para $ DIGEST (). Quando o loop $ Digest inicia, ele desencadeia cada observador. Esses observadores verificarão se o valor atual do modelo no escopo é diferente do valor do modelo calculado da última vez. Se for diferente, a função de retorno de chamada correspondente será executada. O resultado de chamar essa função é que o conteúdo da expressão na visualização (nota do tradutor: como {{amodel}}) será atualizado. Além da Diretiva NG-Click, existem outras diretivas e serviços internos para permitir que você altere modelos (como NG-Model, $ Timeout, etc.) e aciona automaticamente um loop $ Digest.
Até agora não é ruim! No entanto, há um pequeno problema. No exemplo acima, o AngularJS não chama $ DIGEST () diretamente, mas chama $ SCOPE. $ APLIC (), que chama $ RootScope. $ Digest (). Portanto, um loop $ digery começa em $ Rootscope, que acessará todos os observadores de escopo de crianças.
NOTA: $ SCOPE. $ APPL () LIGUARARÁ automaticamente $ RootsCope. $ DIGEST ().
O método $ apply () possui dois formulários:
O primeiro aceitará uma função como um parâmetro, executará a função e acionará um loop $ Digest.
O segundo tipo não aceitará nenhum parâmetros e apenas acionará um loop $ digery. Veremos imediatamente por que o primeiro formulário é melhor.
1.2. Quando chamar manualmente o método $ apply ()?
Se o AngularJS sempre envolve nosso código em uma função e passa em $ apply () para iniciar um loop $ digery, quando precisamos chamar o método $ apply () manualmente? De fato, o AngularJS tem um requisito muito claro para isso, de que é responsável apenas por responder automaticamente a alterações que ocorrem no contexto AngularJS (isto é, alterações nos modelos que ocorrem no método $ apply ()). É assim que a diretiva interna do AngularJS faz isso, portanto, qualquer alteração do modelo será refletida na visualização. No entanto, se você modificar o modelo em qualquer lugar fora do contexto do AngularJS, precisará notificar o AngularJS chamando $ APLIC () manualmente. É como dizer ao AngularJS que você modificou alguns modelos e espera que o AngularJS possa ajudá -lo a acionar os observadores a responder corretamente.
Por exemplo, se você usar o setTimeout () no JavaScript para atualizar um modelo de escopo, o AngularJS não terá como saber o que você mudou. Nesse caso, é sua responsabilidade chamar $ APLIC () e acionar um loop $ DIGEST chamando -o. Da mesma forma, se você tiver uma diretiva para definir um ouvinte de evento DOM e modificar alguns modelos nesse ouvinte, também precisará ligar para o $ Aplicar () para garantir que as alterações sejam refletidas corretamente na visualização.
Vejamos um exemplo. Participe de uma página que, uma vez carregado, você deseja exibir uma mensagem após dois segundos. Sua implementação pode ser assim:
html:
<corpo ng-app = "myApp"> <div ng-controller = "messageController"> Mensagem atrasada: {{message}} </div> </body>JavaScript:
/ * O que acontece sem um $ aplicativo () */ angular.module ('myApp', []). } $ scope.getMessage ();Ao executar este exemplo, você verá que, após dois segundos, o console mostra o modelo atualizado, no entanto, a visualização não é atualizada. Talvez você já saiba o motivo, ou seja, esquecemos de chamar o método $ apply (). Portanto, precisamos modificar getMessage () da seguinte maneira:
/ * O que acontece com $ Aplicar */angular.module ('MyApp', []). $ scope.Message);Se você executar o exemplo acima, verá que a visualização também será atualizada após dois segundos. A única alteração é que nosso código agora está envolvido em $ SCOPE. $ APPL (), que acionará automaticamente $ RootScope. $ Digest (), para que os observadores sejam acionados para atualizar a visualização.
NOTA: A propósito, você deve usar o Serviço de Timeout $ em vez de Settimeout (), porque o primeiro chamará $ APLIC () para você, para que você não precise chamá -lo manualmente.
Além disso, observe que, no código acima, você também pode chamar manualmente $ Aplicar () sem parâmetros após modificar o modelo, assim como o seguinte:
$ scope.getMessage = function () {setTimeout (function () {$ scope.message = 'buscado após dois segundos'; console.log ('message:' + $ scope.Message); $ scope. $ aplicativo (); // este candidato a $ digest}, 2000); };O código acima usa o segundo formulário de $ aplicativo (), ou seja, o formulário sem parâmetros. É importante lembrar que você sempre deve usar o método $ APLAP () que toma uma função como um parâmetro. Isso ocorre porque, quando você passa uma função em $ apply (), a função será embrulhada em uma tentativa ... Catch Block; assim, uma vez que ocorre uma exceção, a exceção será processada pelo Serviço de $ ExceptionHandler.
A situação do uso de $ apply () é a seguinte:
• Geralmente, você pode ligar para $ APLIC () com base em qualquer diretiva fornecida pelo Angular que possa ser usada na visualização. Todas as diretivas NG- [Evento] (como NG-Click, NG-Keepress) chamarão $ APLIC ().
• Além disso, você também pode confiar em uma série de serviços embutidos angulares para chamar $ digery (). Por exemplo, o serviço $ http ligará para $ Aplicar () após a solicitação XHR ser concluída e o valor de retorno da atualização for acionado.
• Sempre que lidamos manualmente em eventos, use estruturas de terceiros (como jQuery, API do Facebook) ou ligue para o setTimeout (), podemos usar a função $ apply () para tornar o angular retornar um loop $ digery.
Chamada setTimeout ():
<! Doctype html> <html ng-app = "myApp"> <head> <title> $ scope. $ Apply () uso </title> <meta charset = "utf-8"> <script src = "http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"> </sCript> </ad Head> <body> <div id = "div1" ng-controller = "myText> <div> {{text}} </sbotroller =" myText> <div> {{text}} <// value = "jQuery-event"> </input> </div> </body> </html> <script type = "text/javascript"> var myModule = angular.module ('myApp', []); myModule.Controller ("MyText", função ($ scope) {$ scope.text = "Place"; setTimeout (function () {$ scope.text = "valor definido após o tempo"; $ scope. </script>Use estruturas de terceiros (como jQuery, API do Facebook):
<! Doctype html> <html ng-app = "myApp"> <head> <title> $ scope. $ Apply () uso </ititle> <meta charset = "utf-8"> <script src = "https://cdn.jsdelivr.nnet/jquery/.1.0 src = "http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"> </sCript> <body> <div id = "div1" ng-controller = "myText"> <d> {{text}} </div> value = "jQuery-event"> </input> </div> </body> </html> <script type = "text/javascript"> var myModule = angular.module ('myApp', []); myModule.Controller ("MyText", function ($ scope) {$ scope.text = "Place";}); $ (function () {$ ("#btn"). clique (function () {var $ scope = $ ("#btn"). scope (); $ scope.text = "Valor definido em jQuery"; $ scope. $ APPL ();});}) </script>1.3. Quantas vezes o $ Digest Loop vai executar?
Quando um loop $ digery estiver em execução, os observadores serão executados para verificar se os modelos no escopo foram alterados. Se ocorrer uma alteração, a função do ouvinte correspondente será executada. Isso envolve uma questão importante. E se a função do ouvinte modificará um modelo de escopo? Como o AngularJS lidará com essa situação?
A resposta é que o loop $ Digest não será executado apenas uma vez. Após o término do loop atual, ele executará outro loop para verificar se os modelos foram alterados. Esta é uma verificação suja, usada para lidar com alterações de modelo que podem ocorrer quando a função do ouvinte é executada. Portanto, o loop $ Digest continuará sendo executado até que o modelo não mude mais, ou o loop $ Digest atingir 10 vezes. Portanto, tente não modificar o modelo na função do ouvinte o máximo possível.
Nota: O loop $ Digest também será executado pelo menos duas vezes, mesmo que nenhum modelo seja alterado na função do ouvinte. Conforme discutido acima, ele funcionará mais uma vez para garantir que os modelos não estejam mudando.
Conclusão
A coisa mais importante a lembrar é se o AngularJS pode detectar suas modificações no modelo. Se não puder ser detectado, você precisará ligar para $ Aplicar () manualmente.
Se você tiver alguma dúvida, deixe -me uma mensagem e o editor responderá a todos a tempo. Muito obrigado pelo seu apoio ao site wulin.com!