1+ import * as React from "react" ;
2+
3+ export interface ProgressiveImageProps extends React . HTMLProps < HTMLDivElement > {
4+ preview : string ;
5+ src : string ;
6+ }
7+
8+ export interface ProgressiveBackgroundImageProps extends React . HTMLProps < HTMLImageElement > {
9+ preview : string ;
10+ src : string ;
11+ background : boolean ;
12+ }
13+
14+ export interface ProgressiveImageState {
15+ src : string ;
16+ blur : number ;
17+ }
18+
19+ export class ProgressiveImage extends React . Component < ProgressiveImageProps & ProgressiveBackgroundImageProps , ProgressiveImageState > {
20+
21+ private clonedProps : React . HTMLProps < HTMLDivElement | HTMLImageElement > = { } ;
22+
23+ componentWillMount ( ) {
24+ const { src, preview} = this . props ;
25+ this . setState ( { src : preview , blur : 10 } ) ;
26+ this . cloneProps ( ) ;
27+ fetch ( src ) . then ( ( ) => this . setState ( { src, blur : 0 } ) ) ;
28+ }
29+
30+ render ( ) {
31+ const { src, style, background} = this . props ;
32+ return (
33+ < div >
34+ < style > { `
35+ @-webkit-keyframes blur {
36+ 0% { -webkit-filter: blur(10px); }
37+ 100% { -webkit-filter: blur(0); }
38+ }
39+ ` } </ style >
40+ {
41+ background ?
42+ < div style = { Object . assign ( this . getBackgroundStyle ( ) , style ) } { ...this . clonedProps } />
43+ :
44+ < img src = { src } style = { Object . assign ( this . getStyle ( ) , style ) } { ...this . clonedProps } />
45+ }
46+
47+ </ div >
48+ ) ;
49+ }
50+
51+ private cloneProps ( ) {
52+ Object . keys ( this . props )
53+ . filter ( prop => [ "style" , "src" , "preview" , "background" ] . indexOf ( prop ) === - 1 )
54+ . forEach ( prop => this . clonedProps [ prop ] = this . props [ prop ] ) ;
55+ }
56+
57+ private getStyle ( ) {
58+ const { blur} = this . state ;
59+ return {
60+ filter : `blur(${ blur } px)` ,
61+ animation : "blur 400ms" ,
62+ animationTimingFunction : "ease"
63+ } ;
64+ }
65+
66+ private getBackgroundStyle ( ) {
67+ const { src, blur} = this . state ;
68+ return {
69+ backgroundImage : `url(${ src } )` ,
70+ filter : `blur(${ blur } px)` ,
71+ animation : "blur 400ms" ,
72+ animationTimingFunction : "ease"
73+ } ;
74+ }
75+ }
0 commit comments