import { Component , Element , Event , EventEmitter , Prop , State } from '@stencil/core' ; @ Component ( { tag : 'lazy-img' , styleUrl : 'lazy-img.css' } ) export class LazyImg { @ Element ( ) el : HTMLElement ; @ Prop ( ) src : string ; @ Prop ( ) alt : string ; @ State ( ) oldSrc : string ; @ Event ( ) lazyImgloaded : EventEmitter < HTMLImageElement > ; io : IntersectionObserver ; componentDidLoad ( ) { this . addIntersectionObserver ( ) ; } componentWillUpdate ( ) { console . log ( 'componentWillUpdate called' , this . src , this . oldSrc ) ; if ( this . src !== this . el . querySelector ( 'img' ) . getAttribute ( 'data-src' ) ) { this . addIntersectionObserver ( ) ; } } handleImage ( ) { const image = this . el . querySelector ( 'img' ) ; console . log ( image . getAttribute ( 'data-src' ) ) ; if ( image . getAttribute ( 'data-src' ) ) { image . setAttribute ( 'src' , image . getAttribute ( 'data-src' ) ) ; image . onload = ( ) => { image . removeAttribute ( 'data-src' ) ; this . lazyImgloaded . emit ( image ) ; } ; } } addIntersectionObserver ( ) { if ( ! this . src ) { return ; } if ( 'IntersectionObserver' in window ) { this . io = new IntersectionObserver ( ( data ) => { if ( data [ 0 ] . isIntersecting ) { this . handleImage ( ) ; this . removeIntersectionObserver ( ) ; } } ) ; this . io . observe ( this . el . querySelector ( 'img' ) ) ; } else { this . handleImage ( ) ; } } removeIntersectionObserver ( ) { if ( this . io ) { this . io . disconnect ( ) ; this . io = null ; } } render ( ) { return ( < img data - src = { this . src } alt = { this . alt } > < /img>); } }