11import { Injectable } from '@angular/core' ;
2- import { File , FileEntry , FileReader } from '@ionic-native/file' ;
2+ import { File , FileEntry , FileReader , FileError } from '@ionic-native/file' ;
33import { Transfer } from '@ionic-native/transfer' ;
44import { ImageLoaderConfig } from "./image-loader-config" ;
55import { Platform } from 'ionic-angular' ;
66import * as _ from 'lodash' ;
77
8+ interface IndexItem {
9+ name : string ;
10+ modificationTime : Date ;
11+ size : number ;
12+ }
13+
14+ interface QueueItem {
15+ imageUrl : string ;
16+ resolve : Function ;
17+ reject : Function ;
18+ }
19+
820@Injectable ( )
921export class ImageLoader {
1022
@@ -32,19 +44,11 @@ export class ImageLoader {
3244 * Queue items
3345 * @type {Array }
3446 */
35- private queue : Array < {
36- imageUrl : string ;
37- resolve : Function ;
38- reject : Function ;
39- } > = [ ] ;
47+ private queue : QueueItem [ ] = [ ] ;
4048
4149 private processing : number = 0 ;
4250
43- private cacheIndex : Array < {
44- name : string ;
45- modificationTime : Date ;
46- size : number ;
47- } > = [ ] ;
51+ private cacheIndex : IndexItem [ ] = [ ] ;
4852
4953 private currentCacheSize : number = 0 ;
5054
@@ -134,7 +138,7 @@ export class ImageLoader {
134138 getImagePath ( imageUrl : string ) : Promise < string > {
135139 return new Promise < string > ( ( resolve , reject ) => {
136140
137- let getImage = ( ) => {
141+ const getImage = ( ) => {
138142 this . getCachedImagePath ( imageUrl )
139143 . then ( resolve )
140144 . catch ( ( ) => {
@@ -144,7 +148,7 @@ export class ImageLoader {
144148
145149 } ;
146150
147- let check = ( ) => {
151+ const check = ( ) => {
148152 if ( this . isInit ) {
149153 if ( this . isCacheReady ) {
150154 getImage ( ) ;
@@ -204,7 +208,7 @@ export class ImageLoader {
204208 this . processing ++ ;
205209
206210 // take the first item from queue
207- const currentItem = this . queue . splice ( 0 , 1 ) [ 0 ] ;
211+ const currentItem : QueueItem = this . queue . splice ( 0 , 1 ) [ 0 ] ;
208212
209213 // process more items concurrently if we can
210214 if ( this . canProcess ) this . processQueue ( ) ;
@@ -217,7 +221,7 @@ export class ImageLoader {
217221 this . processQueue ( ) ;
218222 } ;
219223
220- let localPath = this . file . cacheDirectory + this . config . cacheDirectoryName + '/' + this . createFileName ( currentItem . imageUrl ) ;
224+ const localPath = this . file . cacheDirectory + this . config . cacheDirectoryName + '/' + this . createFileName ( currentItem . imageUrl ) ;
221225 this . downloadImage ( currentItem . imageUrl , localPath )
222226 . then ( ( file : FileEntry ) => {
223227
@@ -333,12 +337,31 @@ export class ImageLoader {
333337
334338 if ( this . config . maxCacheSize > - 1 && this . indexed ) {
335339
336- // we exceeded max cache size
337- while ( this . currentCacheSize > this . config . maxCacheSize ) {
338- let file = this . cacheIndex . splice ( 0 , 1 ) [ 0 ] ;
339- this . file . removeFile ( this . file . cacheDirectory + this . config . cacheDirectoryName , file . name ) ;
340- this . currentCacheSize -= file . size ;
341- }
340+ const maintain = ( ) => {
341+ if ( this . currentCacheSize > this . config . maxCacheSize ) {
342+
343+ // called when item is done processing
344+ const next : Function = ( ) => {
345+ this . currentCacheSize -= file . size ;
346+ maintain ( ) ;
347+ } ;
348+
349+ // grab the first item in index since it's the oldest one
350+ const file : IndexItem = this . cacheIndex . splice ( 0 , 1 ) [ 0 ] ;
351+
352+ // delete the file then process next file if necessary
353+ this . file . removeFile ( this . file . cacheDirectory + this . config . cacheDirectoryName , file . name )
354+ . then ( ( ) => next ( ) )
355+ . catch ( ( e : FileError ) => {
356+ next ( ) ;
357+ if ( e . code != 1 ) { // ignore File not found error
358+ this . throwError ( 'Error deleting file from cache to maintain size. ' , e )
359+ }
360+ } ) ;
361+ }
362+ } ;
363+
364+ maintain ( ) ;
342365
343366 }
344367
@@ -358,10 +381,10 @@ export class ImageLoader {
358381 }
359382
360383 // get file name
361- let fileName = this . createFileName ( url ) ;
384+ const fileName = this . createFileName ( url ) ;
362385
363386 // get full path
364- let dirPath = this . file . cacheDirectory + this . config . cacheDirectoryName ;
387+ const dirPath = this . file . cacheDirectory + this . config . cacheDirectoryName ;
365388
366389 // check if exists
367390 this . file . resolveLocalFilesystemUrl ( dirPath + '/' + fileName )
@@ -396,21 +419,23 @@ export class ImageLoader {
396419
397420 /**
398421 * Throws a console error if debug mode is enabled
399- * @param error {string } Error message
422+ * @param args {any[] } Error message
400423 */
401- private throwError ( error : any ) : void {
424+ private throwError ( ... args : any [ ] ) : void {
402425 if ( this . config . debugMode ) {
403- console . error ( 'ImageLoader Error' , error ) ;
426+ args . unshift ( 'ImageLoader Error: ' ) ;
427+ console . error . apply ( console , args ) ;
404428 }
405429 }
406430
407431 /**
408432 * Throws a console warning if debug mode is enabled
409- * @param error {string } Error message
433+ * @param args {any[] } Error message
410434 */
411- private throwWarning ( error : any ) : void {
435+ private throwWarning ( ... args : any [ ] ) : void {
412436 if ( this . config . debugMode ) {
413- console . warn ( 'ImageLoader Warning' , error ) ;
437+ args . unshift ( 'ImageLoader Warning: ' ) ;
438+ console . warn . apply ( console , args ) ;
414439 }
415440 }
416441
0 commit comments