javascript - change - mouseover angular 6
Ejecuta una funciĆ³n cuando*ngPara terminar en angular 2 (7)
Intento crear una aplicación con angular 2, quiero cuando el último elemento se represente en * ngFor, ejecute una función, algo como esto:
<ul>
<li *ngFor="#i of items">{{i.text}}</li> <==== i want when this completed, execute a functuon in my class
</ul>
Gracias.
Actualizar
Puedes usar @ViewChildren
para ese propósito
Hay tres casos
1. en la inicialización, el elemento ngFor
no se representa debido a ngIf
en él o en su padre
- en cuyo caso, siempre que
ngIf
vuelva sincero, se le notificará mediante la suscripción aViewChildren
2. en la inicialización, el elemento ngFor
se representa independientemente de ngIf
en él o en su padre
- en cuyo caso, la suscripción a
ViewChildren
no le notificará por primera vez, pero puede estar seguro de que se procesa en el ganchongAfterViewInit
3. los elementos se agregan / eliminan a / desde la matriz ngFor
- En cuyo caso también la suscripción a
ViewChildren
te lo notificará.
[Demostración de Plunker] (ver el registro de la consola allí)
@Component({
selector: ''my-app'',
template: `
<ul *ngIf="!isHidden">
<li #allTheseThings *ngFor="let i of items; let last = last">{{i}}</li>
</ul>
<br>
<button (click)="items.push(''another'')">Add Another</button>
<button (click)="isHidden = !isHidden">{{isHidden ? ''Show'' : ''Hide''}}</button>
`,
})
export class App {
items = [1, 2, 3, 4, 5, 6, 7, 8, 9, 0];
@ViewChildren(''allTheseThings'') things: QueryList<any>;
ngAfterViewInit() {
this.things.changes.subscribe(t => {
this.ngForRendred();
})
}
ngForRendred() {
console.log(''NgFor is Rendered'');
}
}
.
Original
Puedes hacerlo de esta manera (pero mira los efectos secundarios por ti mismo )
<ul>
<li *ngFor="let i of items; let last = last">{{i}} {{last ? callFunction(i) : ''''}}</li>
</ul>
Lo cual es inútil, a menos que se use con changeDetectionStrategy.OnPush
Entonces puede tener control sobre la cantidad de veces que se produce la detección de cambios, por lo tanto, cuántas veces se llama su función.
es decir: puede desencadenar el siguiente changeDetection
cuando changeDetection
los datos de los items
, y su función dará una indicación adecuada de que ngFor
se procesa para un cambio real .
Me encontré con este problema también. En mi caso, estaba llamando a un servicio web para recuperar datos y necesitaba ejecutar javascript para inicializar cada plantilla producida por *ngFor
. Esto es lo que se me ocurrió:
updateData() {
this.dataService.getData().subscribe(
function(data) {
this.data = data;
setTimeout(javascriptInitializationFunction, 0);
},
function(err) { /* handle it */ }
);
}
setTimout
esperará a que el DOM se actualice antes de ejecutarse. Esto no es exactamente lo que pediste, pero espero que ayude.
Me enfrento a la misma pregunta y encuentro una manera de evitar esto. No estoy seguro de si es adecuado para usted o no.
Las condiciones previas son que está utilizando ngFor para representar las propiedades de entrada.
contexto: necesito llamar a MDL''s upgradeAllRegistered para hacer la casilla de verificación bastante después de obtener los datos de la red desde el back-end.
Añado un setTimeout dentro de ''ngOnChanges'';
grid.componet.ts:
export class GridComponent {
@Input() public rows: Array<any>;
ngOnChanges(changes: {[propertyName: string]: SimpleChange}) {
for (let propName in changes) {
if (propName == ''rows'') {
setTimeout(() => componentHandler.upgradeAllRegistered());
}
}
}
}
grid.component.html:
<tr #rowDOM *ngFor="let row of rows;"></tr>
Me las arreglé para realizar algunos trucos para evitar que los eventos se activaran (descubrí que el desplazamiento siempre desencadena esos eventos)
Añadiendo: [Añade en tu componente]
private globalFlag = -1;
y este es mi evento que se activará cuando finalice el bucle
ev(flag){
if(flag != this.globalFlag){
console.log("TRIGGER!")
this.globalFlag = flag;
}
}
y este el código de bucle
<div *ngFor="let var of list;let i=index;let last=last">
{{last ? ev(i) : ''''}}
</div>
La idea principal es evitar que el evento se active si la bandera era la misma. Por lo tanto, solo se activará cuando el valor globalFlag difiera con el indicador actual que pasó de ngFor. Lo siento por mi mal inglés, espero que puedas entender mi idea.
Posible solución: la respuesta se muestra en https://stackblitz.com/edit/angular-phpauq?file=src%2Fapp%2Fapp.component.ts
app.component.html
<div [innerHTML]="html"></div>
app.component.ts
html = '''';
ngAfterViewInit(){
let i;
this.html += ''<ul>'';
for(i = 0 ; i < this.abc.length ; i++){
this.html += ''<li>'';
this.html += this.abc[i];
if(parseInt(i) === this.abc.length - 1){
this.callMethod(i);
}
this.html += ''</li>'';
}
this.html += ''</ul>'';
}
callMethod(text){
alert(text);
}
Usé un pequeño truco del enfoque del que otros se han quejado y funcionó a la perfección:
<ul>
<li *ngFor="let i of items; let last = last">{{i}} {{last ? callFunction(i) : ''''}}</li>
</ul>
Luego en tu componente:
shouldDoIt = true; // initialize it to true for the first run
callFunction(stuff) {
if (this.shouldDoIt) {
// Do all the things with the stuff
this.shouldDoIt = false; // set it to false until you need to trigger again
}
}
Esto no aborda la raíz del problema con este enfoque, pero es un truco de muy bajo costo que hizo que mi aplicación funcionara sin problemas. Espero que el equipo de Angular implemente una forma más amigable para activar algún código después de que * ngFor cargue su contenido.
puede hacer lo mismo obteniendo el último índice usando #last
de *ngFor
y llamar a la función obteniendo el último valor de índice y haciendo lo que quiera. Aquí está el código para el mismo
<ul>
<li *ngFor="#item of items; #last = last">
<span *ngIf=''last''>{{hello(last)}}</span>
{{item}}
</li>
</ul>
items: Array<number> = [1,2,3,4,5]
constructor() { console.clear();}
hello(a){
if(a==true)
this.callbackFunction();
}
callbackFunction(){
console.log("last element");
}
Ejemplo de trabajo para el mismo Plunker de trabajo.