Diferencias

Muestra las diferencias entre dos versiones de la página.

Enlace a la vista de comparación

unidades:04_masdirectivas:06_ngif [2014/07/31 18:52]
admin [Herencia de $scope]
unidades:04_masdirectivas:06_ngif [2014/08/29 22:58] (actual)
admin
Línea 1: Línea 1:
 ====== 4.6 ng-if ====== ====== 4.6 ng-if ======
-La directiva ''​ng-if''​ nos permite que exista o no un tag en la página. Podríamos pensar que es similar a [[unidades:​02_angular:​06_ngshow|ng-show]] o [[unidades:​02_angular:​07_nghide|ng-hide]],​ pero éstas últimas directivas simplemente los ocultan mediante CSS mientras que ''​ng-if'' ​lo elimina del DOM o lo vuelve a añadir.+La directiva ''​ng-if''​ nos permite que exista o no un tag en la página. Podríamos pensar que es similar a [[unidades:​02_angular:​06_ngshow|ng-show]] o [[unidades:​02_angular:​07_nghide|ng-hide]],​ pero éstas últimas directivas simplemente los ocultan mediante CSS mientras que ''​ng-if'' ​los elimina del DOM o los vuelve a añadir.
  
-Esta directiva no debería tener mucho que explicar pero realmente tiene un detalle que la hace muy importante. Crea un nuevo ''​$scope''​ heredando de nuestro ''​$scope''​ del controlador. ​Esto realmente tiene una importancia enorme ya que implica saber como funciona la herencia de ''​$scope''​ en JavaScript y AngularJS.+Esta directiva no debería tener mucho que explicar pero realmente tiene un detalle que la hace muy importante. Crea un nuevo ''​$scope''​ heredando de nuestro ''​$scope''​ del controlador. ​Ésto realmente tiene una importancia enorme ya que implica saber cómo funciona la herencia de ''​$scope''​ en JavaScript y AngularJS.
  
 Vamos a ver primeramente un ejemplo y comprobaremos que hay algo que funciona mal. Vamos a ver primeramente un ejemplo y comprobaremos que hay algo que funciona mal.
  
-En el ejemplo prueba a escribir algo en el nombre y en el apellido. ​Veras como el apellido ​si que se modifica en las 2 líneas ​ pero el nombre **no** se modifica en uno de los casos. ​+En el ejemplo prueba a escribir algo en el nombre y en el apellido. ​Verás cómo el apellido ​sí se modifica en las 2 líneas ​ pero el nombre **no** se modifica en uno de los casos. ​
  
 {{url>​http://​embed.plnkr.co/​H0O8Jn1DnwsbpFnOb8Pk}} {{url>​http://​embed.plnkr.co/​H0O8Jn1DnwsbpFnOb8Pk}}
  
-¿Que hay distinto en los 2 ejemplos? Simplemente que en el modelo del apellido hay un punto y en el del nombre no. ¿Recuerdas la advertencia del tema [[unidades:​02_angular:​04_formulario]]. Decía lo siguiente:+¿Qué ​hay distinto en los 2 ejemplos? Simplemente que en el modelo del apellido hay un punto y en el del nombreno.  
 + 
 +<sxh html;​title:​index.html;​highlight:​ [16,​18,​27,​29]>​ 
 +<​!DOCTYPE html> 
 +<html ng-app="​app">​ 
 +  
 +<​head>​ 
 +  <script src="//​ajax.googleapis.com/​ajax/​libs/​angularjs/​1.2.19/​angular.js"></​script>​ 
 +  <script src="​script.js"></​script>​ 
 +</​head>​ 
 +  
 +<body ng-controller="​PruebaController">​ 
 + 
 +<input type="​checkbox"​ ng-model="​showNombre">​¿Mostrar nombre? 
 +<​br>​ 
 +<div ng-if="​showNombre">​ 
 +  Nombre: <input ng-model="​nombre"​ > 
 +  <​br>​ 
 +  El valor de "​nombre"​ en el $scope del "​ng-if"​ es : {{nombre}} 
 +</​div>​ 
 +El valor de "​nombre"​ en el $scope del "​Controlador"​ es : <​strong>​{{nombre}}</​strong>​ 
 + 
 +<​hr>​ 
 + 
 +<input type="​checkbox"​ ng-model="​modelo.showApellido">​¿Mostrar apellido? 
 +<​br>​ 
 +<div ng-if="​modelo.showApellido">​ 
 +  Apellido: <input ng-model="​modelo.apellido"​ > 
 +  <​br>​ 
 +  El valor de "​apellido"​ en el $scope del "​ng-if"​ es : {{modelo.apellido}} 
 +</​div>​ 
 +El valor de "​apellido"​ en el $scope del "​Controlador"​ es : {{modelo.apellido}} 
 + 
 +</​body>​ 
 +  
 +</​html>​ 
 +</​sxh>​ 
 + 
 +  * Línea 16: La expresión ''​%%{{nombre%%}}''​ hace referencia al nuevo ''​$scope''​ creado dentro de la directiva ''​ng-if''​. 
 +  * Línea 18: La expresión ''​%%{{nombre%%}}''​ hace referencia al ''​$scope''​ del controlador. 
 + 
 +  * Línea 27: La expresión ''​%%{{apellido%%}}''​ hace referencia al nuevo ''​$scope''​ creado dentro de la directiva ''​ng-if''​. 
 +  * Línea 29: La expresión ''​%%{{apellido%%}}''​ hace referencia al ''​$scope''​ del controlador. 
 + 
 +<sxh js;​title:​script.js;​highlight:​ [4,8]> 
 +var app = angular.module("​app",​ []); 
 +   
 +app.controller("​PruebaController",​ function($scope) { 
 +  $scope.nombre="​Carlos";​ 
 +  $scope.showNombre=true;​ 
 +   
 +  $scope.modelo={ 
 +    apellido:"​Perez",​ 
 +    showApellido:​true ​  
 +  } 
 +  
 +}); 
 +</​sxh>​ 
 + 
 +  * Linea 4: La propiedad ''​nombre''​ no está dentro de un objeto. 
 +  * Línea 8: La propiedad ''​apellido''​ está dentro de un objeto. 
 + 
 +¿Recuerdas la advertencia del tema [[unidades:​02_angular:​04_formulario]]. Decía lo siguiente:
  
 **//Si el valor de tu directiva ng-model no incluye un punto es que está mal//** **//Si el valor de tu directiva ng-model no incluye un punto es que está mal//**
Línea 16: Línea 78:
 Ahora vamos a explicar del motivo de esta advertancia. ​ Ahora vamos a explicar del motivo de esta advertancia. ​
  
-Voy a volver a recordar que dentro de una directiva ''​ng-if''​ se crea un nuevo ''​$scope''​ que hereda de nuestro ''​$scope''​ del controlador. ​Esto significa que cuando estamos poniendo los tag ''<​input>''​ con el ''​ng-model''​. El nombre de la propiedad a la que hace referencia no es a nuestro ''​$scope''​ de nuestro controlador sino al nuevo ''​$scope''​ que hay dentro del ''​ng-if''​. Lo bueno de todo ello es que el nuevo ''​$scope''​ que hay dentro del ''​ng-if''​ ha copiado ​todos los valores que había en el ''​$scope''​ del controlador. +Voy a volver a recordar que dentro de una directiva ''​ng-if''​ se crea un nuevo ''​$scope''​ que hereda de nuestro ''​$scope''​ del controlador. ​Ésto significa que cuando estamos poniendo los tag ''<​input>''​ con el ''​ng-model''​, el nombre de la propiedad a la que hace referencia no es a nuestro ''​$scope''​ de nuestro controlador sino al nuevo ''​$scope''​ que hay dentro del ''​ng-if''​. Lo bueno de todo ello es que el nuevo ''​$scope''​ que hay dentro del ''​ng-if''​ ha heredado ​todos los valores que había en el ''​$scope''​ del controlador.
 ===== Herencia de $scope ===== ===== Herencia de $scope =====
-Lo importante ahora es comprender ​como se ha hecho dicha herencia. Es algo tan //chapuza// que lo que hace es copiar simplemente el valor de todas las propiedades. El problema es que si una propiedad **NO** es un puntero a un objeto ​resulta que tenemos ​2 propiedades distintas que tienen ahora 2 valores ​independiente.+Lo importante ahora es comprender ​cómo se ha hecho dicha herencia. Es algo tan //chapuza// que lo que hace es copiar simplemente el valor de todas las propiedades. El problema es que si una propiedad **NO** es un puntero a un objeto resulta que tendremos ​2 propiedades distintas que tienen ahora 2 valores ​independientes.
  
 <uml> <uml>
Línea 40: Línea 101:
 </​uml>​ </​uml>​
  
-Fíjate en el diagrama UML de objetos que se ha creado. Ahora cada ''​$scope''​ tiene las propiedades repetidas pero si esa propiedad apuntaba a un objeto, en ambos casos se apunta al mismo objeto ​pero si la propiedad no era un objeto , en cada ''​$scope''​ cada propiedad es independiente.+Fíjate en el diagrama UML de objetos que se ha creado. Ahora cada ''​$scope''​ tiene las propiedades repetidaspero si esa propiedad apuntaba a un objeto, en ambos casos se apunta al mismo objeto. Ahora bien, si la propiedad no era un objeto , en cada ''​$scope''​ cada propiedad es independiente.
  
 Es decir que la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​ es distinta de la propiedad ''​nombre''​ del ''​$scope''​ del controlador , por lo tanto un cambio en la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​ no modifica el ''​$scope''​ del controlador. Es decir que la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​ es distinta de la propiedad ''​nombre''​ del ''​$scope''​ del controlador , por lo tanto un cambio en la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​ no modifica el ''​$scope''​ del controlador.
  
-Sin embargo la propiedad ''​modelo.apellido''​ del ''​$scope''​ del ''​ng-if''​ es la misma que la propiedad ''​modelo.apellido''​ del ''​$scope''​ del controlador , por lo tanto un cambio en la propiedad ''​modelo.apellido''​ del ''​$scope''​ del ''​ng-if''​ **SI** modifica el ''​$scope''​ del controlador ya que ambos apuntan ​al mismo objeto.+Sin embargo la propiedad ''​modelo.apellido''​ del ''​$scope''​ del ''​ng-if''​ es la misma que la propiedad ''​modelo.apellido''​ del ''​$scope''​ del controlador ​ya que ambas apuntan al mismo objeto, por lo tanto un cambio en la propiedad ''​modelo.apellido''​ del ''​$scope''​ del ''​ng-if''​ **SI** modifica el ''​$scope''​ del controlador
 + 
 +De todo ésto se deduce que siempre deberían estar nuestras propiedades dentro de objetos y por eso la frase: 
 + 
 +**//Si el valor de tu directiva ng-model no incluye un punto es que está mal//** 
 + 
 +Ya que tener un punto significa que los datos están dentro de un objeto. 
 + 
 +<note warning>​ 
 +Espero que todo ésto se haya comprendido porque es uno de los mayores motivos de errores en AngularJS. 
 +</​note>​ 
 + 
 +<note tip> 
 +Realmente el modelo de objetos que hemos presentado en el diagrama UML ahí no se corresponde exactamente con la realidad ​ya que no se hace copia del valor en el ''​$scope''​ del ''​ng-if''​ hasta que no se cambia el valor. Mientras tanto sigue apuntando ​al ''​$scope''​ del controlador mediante la cadena de prototipos de JavaScript. 
 + 
 +Ésto último implica que si primero se hace un cambio en la propiedad ''​nombre''​ del ''​$scope''​ del controlador sí que se vería reflejada en la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​. Pero una vez se modifica la propiedad ''​nombre''​ del ''​$scope''​ del ''​ng-if''​ ya se hacen independientes. 
 + 
 +Cambia el ejemplo de esta forma y mira a ver lo que ocurre cuando primero cambias un input u otro del nombre. 
 + 
 +<sxh html;​highlight:​ [3]> 
 +<input type="​checkbox"​ ng-model="​showNombre">​¿Mostrar nombre? 
 +<​br>​ 
 +Nombre: <input ng-model="​nombre"​ > 
 +<div ng-if="​showNombre">​ 
 +  Nombre: <input ng-model="​nombre"​ > 
 +  <​br>​ 
 +  El valor de "​nombre"​ en el $scope del "​ng-if"​ es : {{nombre}} 
 +</​div>​ 
 +El valor de "​nombre"​ en el $scope del "​Controlador"​ es : <​strong>​{{nombre}}</​strong>​ 
 + 
 +</​sxh>​ 
 +Añade la línea 3 al ejemplo y mira lo que ocurre. 
 +</​note>​
  
-de todo ésto se deduce que siempre deberían estar nuestras propiedades dentro de objetos y por eso la frase:+===== Referencias ===== 
 +  * [[https://​docs.angularjs.org/​api/​ng/​directive/​ngIf|ng-if]] 
 +  * [[https://​docs.angularjs.org/​guide/​scope#​scope-hierarchies|/​ Developer Guide / Scopes / Scope Hierarchies]] 
 +  * [[https://​github.com/​angular/​angular.js/​wiki/​Understanding-Scopes|Understanding Scopes]]
unidades/04_masdirectivas/06_ngif.1406825576.txt.gz · Última modificación: 2014/07/31 18:52 por admin
Ir hasta arriba
CC Attribution-Share Alike 3.0 Unported
chimeric.de = chi`s home Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0