From 836bbc91c62b0dd3a9e841b26cbf26b3897cfd84 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Mon, 17 Aug 2020 11:06:15 +0300 Subject: [PATCH 01/17] add loadImage feature for iOS --- ios/FastImage/FFFastImageViewManager.m | 54 ++++++++++++++++++++++++++ src/index.tsx | 4 ++ 2 files changed, 58 insertions(+) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 4cb522078..be89d3ba8 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -34,5 +34,59 @@ - (FFFastImageView*)view { [[SDWebImagePrefetcher sharedImagePrefetcher] prefetchURLs:urls]; } +// https://github.com/DylanVann/react-native-fast-image/pull/351/files +RCT_REMAP_METHOD( + loadImage, + loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject +) { + SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; + NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; + NSString *imagePath = [imageManager.imageCache defaultCachePathForKey:cacheKey]; + + // set headers + [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { + [imageManager.imageDownloader setValue:header forHTTPHeaderField:key]; + }]; + + // set options + SDWebImageOptions options = 0; + options |= SDWebImageRetryFailed; + switch (source.priority) { + case FFFPriorityLow: + options |= SDWebImageLowPriority; + break; + case FFFPriorityNormal: + // Priority is normal by default. + break; + case FFFPriorityHigh: + options |= SDWebImageHighPriority; + break; + } + + switch (source.cacheControl) { + case FFFCacheControlWeb: + options |= SDWebImageRefreshCached; + break; + case FFFCacheControlCacheOnly: + options |= SDWebImageCacheMemoryOnly; + break; + case FFFCacheControlImmutable: + break; + } + + // load image + [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { + if (error != nil) { + reject(@"FastImage", @"Failed to load image", error); + return; + } + + // store image manually (since image manager may call the completion block before storing it in the disk cache) + [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ + resolve(imagePath); + }]; + }]; +} + @end diff --git a/src/index.tsx b/src/index.tsx index 4734a784c..8a748b1ad 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -203,6 +203,7 @@ interface FastImageStaticProperties { priority: typeof priority cacheControl: typeof cacheControl preload: (sources: Source[]) => void + loadImage: (source: Source) => Promise } const FastImage: React.ComponentType & @@ -217,6 +218,9 @@ FastImage.priority = priority FastImage.preload = (sources: Source[]) => FastImageViewNativeModule.preload(sources) +FastImage.loadImage = (source: Source) => + FastImageViewNativeModule.loadImage(source) + const styles = StyleSheet.create({ imageContainer: { overflow: 'hidden', From 01864b6a766bfc33255f69122b1886e06e83d3b1 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Mon, 17 Aug 2020 11:30:39 +0300 Subject: [PATCH 02/17] fix build issues (iOS) --- ios/FastImage/FFFastImageViewManager.m | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index be89d3ba8..0f6a1bfce 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -41,11 +41,11 @@ - (FFFastImageView*)view { ) { SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; - NSString *imagePath = [imageManager.imageCache defaultCachePathForKey:cacheKey]; + NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; // set headers [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { - [imageManager.imageDownloader setValue:header forHTTPHeaderField:key]; + [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; }]; // set options @@ -68,7 +68,7 @@ - (FFFastImageView*)view { options |= SDWebImageRefreshCached; break; case FFFCacheControlCacheOnly: - options |= SDWebImageCacheMemoryOnly; + options |= SDWebImageFromCacheOnly; break; case FFFCacheControlImmutable: break; From 5ae841785612ab1ac2122c60200a91775e756f36 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Mon, 17 Aug 2020 11:58:04 +0300 Subject: [PATCH 03/17] fix build issues (iOS) --- ios/FastImage/FFFastImageViewManager.m | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 0f6a1bfce..0761b9af7 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -41,7 +41,7 @@ - (FFFastImageView*)view { ) { SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; - NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; + NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey inPath:imageManager.diskCachePath]; // set headers [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { From d3bfedd29570f81e47e5a3b793d82d92ba144d3d Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Mon, 17 Aug 2020 13:19:07 +0300 Subject: [PATCH 04/17] fix build issues (iOS) --- ios/FastImage/FFFastImageViewManager.m | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 0761b9af7..7ece60386 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -41,7 +41,7 @@ - (FFFastImageView*)view { ) { SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; - NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey inPath:imageManager.diskCachePath]; + NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; // set headers [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { @@ -68,7 +68,7 @@ - (FFFastImageView*)view { options |= SDWebImageRefreshCached; break; case FFFCacheControlCacheOnly: - options |= SDWebImageFromCacheOnly; + options |= SDWebImageCacheMemoryOnly; break; case FFFCacheControlImmutable: break; From e3bafbd2197da1e98a497cc2786238caab6bb8db Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Thu, 20 Aug 2020 14:16:33 +0300 Subject: [PATCH 05/17] fix scripts --- ios/FastImage/FFFastImageViewManager.m | 104 ++++++++++++------------- src/index.tsx | 6 +- 2 files changed, 55 insertions(+), 55 deletions(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 7ece60386..f8195675c 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -35,58 +35,58 @@ - (FFFastImageView*)view { } // https://github.com/DylanVann/react-native-fast-image/pull/351/files -RCT_REMAP_METHOD( - loadImage, - loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject -) { - SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; - NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; - NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; - - // set headers - [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { - [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; - }]; - - // set options - SDWebImageOptions options = 0; - options |= SDWebImageRetryFailed; - switch (source.priority) { - case FFFPriorityLow: - options |= SDWebImageLowPriority; - break; - case FFFPriorityNormal: - // Priority is normal by default. - break; - case FFFPriorityHigh: - options |= SDWebImageHighPriority; - break; - } - - switch (source.cacheControl) { - case FFFCacheControlWeb: - options |= SDWebImageRefreshCached; - break; - case FFFCacheControlCacheOnly: - options |= SDWebImageCacheMemoryOnly; - break; - case FFFCacheControlImmutable: - break; - } - - // load image - [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { - if (error != nil) { - reject(@"FastImage", @"Failed to load image", error); - return; - } - - // store image manually (since image manager may call the completion block before storing it in the disk cache) - [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ - resolve(imagePath); - }]; - }]; -} +// RCT_REMAP_METHOD( +// loadImage, +// loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject +// ) { +// SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; +// NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; +// NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; + +// // set headers +// [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { +// [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; +// }]; + +// // set options +// SDWebImageOptions options = 0; +// options |= SDWebImageRetryFailed; +// switch (source.priority) { +// case FFFPriorityLow: +// options |= SDWebImageLowPriority; +// break; +// case FFFPriorityNormal: +// // Priority is normal by default. +// break; +// case FFFPriorityHigh: +// options |= SDWebImageHighPriority; +// break; +// } + +// switch (source.cacheControl) { +// case FFFCacheControlWeb: +// options |= SDWebImageRefreshCached; +// break; +// case FFFCacheControlCacheOnly: +// options |= SDWebImageCacheMemoryOnly; +// break; +// case FFFCacheControlImmutable: +// break; +// } + +// // load image +// [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { +// if (error != nil) { +// reject(@"FastImage", @"Failed to load image", error); +// return; +// } + +// // store image manually (since image manager may call the completion block before storing it in the disk cache) +// [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ +// resolve(imagePath); +// }]; +// }]; +// } @end diff --git a/src/index.tsx b/src/index.tsx index 8a748b1ad..922ba8562 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -203,7 +203,7 @@ interface FastImageStaticProperties { priority: typeof priority cacheControl: typeof cacheControl preload: (sources: Source[]) => void - loadImage: (source: Source) => Promise + // loadImage: (source: Source) => Promise } const FastImage: React.ComponentType & @@ -218,8 +218,8 @@ FastImage.priority = priority FastImage.preload = (sources: Source[]) => FastImageViewNativeModule.preload(sources) -FastImage.loadImage = (source: Source) => - FastImageViewNativeModule.loadImage(source) +// FastImage.loadImage = (source: Source) => +// FastImageViewNativeModule.loadImage(source) const styles = StyleSheet.create({ imageContainer: { From 28f274be93c2ee52d9712459dee0c25e7aad46ed Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Thu, 20 Aug 2020 14:21:42 +0300 Subject: [PATCH 06/17] add dist folder --- .gitignore | 2 +- dist/index.cjs.js | 114 +++++++++++++++++++++++++++++++++++++++ dist/index.d.ts | 101 ++++++++++++++++++++++++++++++++++ dist/index.d.ts.map | 1 + dist/index.js | 109 +++++++++++++++++++++++++++++++++++++ dist/index.js.flow | 71 ++++++++++++++++++++++++ dist/index.test.d.ts | 2 + dist/index.test.d.ts.map | 1 + 8 files changed, 400 insertions(+), 1 deletion(-) create mode 100644 dist/index.cjs.js create mode 100644 dist/index.d.ts create mode 100644 dist/index.d.ts.map create mode 100644 dist/index.js create mode 100644 dist/index.js.flow create mode 100644 dist/index.test.d.ts create mode 100644 dist/index.test.d.ts.map diff --git a/.gitignore b/.gitignore index 0c43f2cd0..a223cdb95 100644 --- a/.gitignore +++ b/.gitignore @@ -42,7 +42,7 @@ example/android/app/src/main/gen # build react-native-fast-image-*.tgz -dist/ +#dist/ # coverage reports coverage diff --git a/dist/index.cjs.js b/dist/index.cjs.js new file mode 100644 index 000000000..a7b16ad9e --- /dev/null +++ b/dist/index.cjs.js @@ -0,0 +1,114 @@ +'use strict'; + +function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } + +var _extends = _interopDefault(require('@babel/runtime/helpers/extends')); +var React = require('react'); +var React__default = _interopDefault(React); +var reactNative = require('react-native'); + +const FastImageViewNativeModule = reactNative.NativeModules.FastImageView; +const resizeMode = { + contain: 'contain', + cover: 'cover', + stretch: 'stretch', + center: 'center' +}; +const priority = { + low: 'low', + normal: 'normal', + high: 'high' +}; +const cacheControl = { + // Ignore headers, use uri as cache key, fetch only if not in cache. + immutable: 'immutable', + // Respect http headers, no aggressive caching. + web: 'web', + // Only load from cache. + cacheOnly: 'cacheOnly' +}; + +function FastImageBase({ + source, + tintColor, + onLoadStart, + onProgress, + onLoad, + onError, + onLoadEnd, + style, + fallback, + children, + // eslint-disable-next-line no-shadow + resizeMode = 'cover', + forwardedRef, + ...props +}) { + if (fallback) { + const cleanedSource = { ...source + }; + delete cleanedSource.cache; + const resolvedSource = reactNative.Image.resolveAssetSource(cleanedSource); + return /*#__PURE__*/React__default.createElement(reactNative.View, { + style: [styles.imageContainer, style], + ref: forwardedRef + }, /*#__PURE__*/React__default.createElement(reactNative.Image, _extends({}, props, { + style: reactNative.StyleSheet.absoluteFill, + source: resolvedSource, + onLoadStart: onLoadStart, + onProgress: onProgress, + onLoad: onLoad, + onError: onError, + onLoadEnd: onLoadEnd, + resizeMode: resizeMode + })), children); + } + + const resolvedSource = reactNative.Image.resolveAssetSource(source); + return /*#__PURE__*/React__default.createElement(reactNative.View, { + style: [styles.imageContainer, style], + ref: forwardedRef + }, /*#__PURE__*/React__default.createElement(FastImageView, _extends({}, props, { + tintColor: tintColor, + style: reactNative.StyleSheet.absoluteFill, + source: resolvedSource, + onFastImageLoadStart: onLoadStart, + onFastImageProgress: onProgress, + onFastImageLoad: onLoad, + onFastImageError: onError, + onFastImageLoadEnd: onLoadEnd, + resizeMode: resizeMode + })), children); +} + +const FastImageMemo = /*#__PURE__*/React.memo(FastImageBase); +const FastImageComponent = /*#__PURE__*/React.forwardRef((props, ref) => /*#__PURE__*/React__default.createElement(FastImageMemo, _extends({ + forwardedRef: ref +}, props))); +FastImageComponent.displayName = 'FastImage'; +const FastImage = FastImageComponent; +FastImage.resizeMode = resizeMode; +FastImage.cacheControl = cacheControl; +FastImage.priority = priority; + +FastImage.preload = sources => FastImageViewNativeModule.preload(sources); // FastImage.loadImage = (source: Source) => +// FastImageViewNativeModule.loadImage(source) + + +const styles = reactNative.StyleSheet.create({ + imageContainer: { + overflow: 'hidden' + } +}); // Types of requireNativeComponent are not correct. + +const FastImageView = reactNative.requireNativeComponent('FastImageView', FastImage, { + nativeOnly: { + onFastImageLoadStart: true, + onFastImageProgress: true, + onFastImageLoad: true, + onFastImageError: true, + onFastImageLoadEnd: true + } +}); + +module.exports = FastImage; diff --git a/dist/index.d.ts b/dist/index.d.ts new file mode 100644 index 000000000..0b1afd5e1 --- /dev/null +++ b/dist/index.d.ts @@ -0,0 +1,101 @@ +import React from 'react'; +import { FlexStyle, LayoutChangeEvent, ShadowStyleIOS, StyleProp, TransformsStyle, AccessibilityProps } from 'react-native'; +export declare type ResizeMode = 'contain' | 'cover' | 'stretch' | 'center'; +declare const resizeMode: { + readonly contain: "contain"; + readonly cover: "cover"; + readonly stretch: "stretch"; + readonly center: "center"; +}; +export declare type Priority = 'low' | 'normal' | 'high'; +declare const priority: { + readonly low: "low"; + readonly normal: "normal"; + readonly high: "high"; +}; +declare type Cache = 'immutable' | 'web' | 'cacheOnly'; +declare const cacheControl: { + readonly immutable: "immutable"; + readonly web: "web"; + readonly cacheOnly: "cacheOnly"; +}; +export declare type Source = { + uri?: string; + headers?: { + [key: string]: string; + }; + priority?: Priority; + cache?: Cache; +}; +export interface OnLoadEvent { + nativeEvent: { + width: number; + height: number; + }; +} +export interface OnProgressEvent { + nativeEvent: { + loaded: number; + total: number; + }; +} +export interface ImageStyle extends FlexStyle, TransformsStyle, ShadowStyleIOS { + backfaceVisibility?: 'visible' | 'hidden'; + borderBottomLeftRadius?: number; + borderBottomRightRadius?: number; + backgroundColor?: string; + borderColor?: string; + borderWidth?: number; + borderRadius?: number; + borderTopLeftRadius?: number; + borderTopRightRadius?: number; + overlayColor?: string; + tintColor?: string; + opacity?: number; +} +export interface FastImageProps extends AccessibilityProps { + source: Source | number; + resizeMode?: ResizeMode; + fallback?: boolean; + onLoadStart?(): void; + onProgress?(event: OnProgressEvent): void; + onLoad?(event: OnLoadEvent): void; + onError?(): void; + onLoadEnd?(): void; + /** + * onLayout function + * + * Invoked on mount and layout changes with + * + * {nativeEvent: { layout: {x, y, width, height}}}. + */ + onLayout?: (event: LayoutChangeEvent) => void; + /** + * + * Style + */ + style?: StyleProp; + /** + * TintColor + * + * If supplied, changes the color of all the non-transparent pixels to the given color. + */ + tintColor?: number | string; + /** + * A unique identifier for this element to be used in UI Automation testing scripts. + */ + testID?: string; + /** + * Render children within the image. + */ + children?: React.ReactNode; +} +interface FastImageStaticProperties { + resizeMode: typeof resizeMode; + priority: typeof priority; + cacheControl: typeof cacheControl; + preload: (sources: Source[]) => void; +} +declare const FastImage: React.ComponentType & FastImageStaticProperties; +export default FastImage; +//# sourceMappingURL=index.d.ts.map \ No newline at end of file diff --git a/dist/index.d.ts.map b/dist/index.d.ts.map new file mode 100644 index 000000000..f88da67c1 --- /dev/null +++ b/dist/index.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA2B,MAAM,OAAO,CAAA;AAC/C,OAAO,EAMH,SAAS,EACT,iBAAiB,EACjB,cAAc,EACd,SAAS,EACT,eAAe,EACf,kBAAkB,EACrB,MAAM,cAAc,CAAA;AAIrB,oBAAY,UAAU,GAAG,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,QAAQ,CAAA;AAEnE,QAAA,MAAM,UAAU;;;;;CAKN,CAAA;AAEV,oBAAY,QAAQ,GAAG,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAA;AAEhD,QAAA,MAAM,QAAQ;;;;CAIJ,CAAA;AAEV,aAAK,KAAK,GAAG,WAAW,GAAG,KAAK,GAAG,WAAW,CAAA;AAE9C,QAAA,MAAM,YAAY;;;;CAOR,CAAA;AAEV,oBAAY,MAAM,GAAG;IACjB,GAAG,CAAC,EAAE,MAAM,CAAA;IACZ,OAAO,CAAC,EAAE;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAA;KAAE,CAAA;IACnC,QAAQ,CAAC,EAAE,QAAQ,CAAA;IACnB,KAAK,CAAC,EAAE,KAAK,CAAA;CAChB,CAAA;AAED,MAAM,WAAW,WAAW;IACxB,WAAW,EAAE;QACT,KAAK,EAAE,MAAM,CAAA;QACb,MAAM,EAAE,MAAM,CAAA;KACjB,CAAA;CACJ;AAED,MAAM,WAAW,eAAe;IAC5B,WAAW,EAAE;QACT,MAAM,EAAE,MAAM,CAAA;QACd,KAAK,EAAE,MAAM,CAAA;KAChB,CAAA;CACJ;AAED,MAAM,WAAW,UAAW,SAAQ,SAAS,EAAE,eAAe,EAAE,cAAc;IAC1E,kBAAkB,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAA;IACzC,sBAAsB,CAAC,EAAE,MAAM,CAAA;IAC/B,uBAAuB,CAAC,EAAE,MAAM,CAAA;IAChC,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,mBAAmB,CAAC,EAAE,MAAM,CAAA;IAC5B,oBAAoB,CAAC,EAAE,MAAM,CAAA;IAC7B,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,OAAO,CAAC,EAAE,MAAM,CAAA;CACnB;AAED,MAAM,WAAW,cAAe,SAAQ,kBAAkB;IACtD,MAAM,EAAE,MAAM,GAAG,MAAM,CAAA;IACvB,UAAU,CAAC,EAAE,UAAU,CAAA;IACvB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAElB,WAAW,CAAC,IAAI,IAAI,CAAA;IAEpB,UAAU,CAAC,CAAC,KAAK,EAAE,eAAe,GAAG,IAAI,CAAA;IAEzC,MAAM,CAAC,CAAC,KAAK,EAAE,WAAW,GAAG,IAAI,CAAA;IAEjC,OAAO,CAAC,IAAI,IAAI,CAAA;IAEhB,SAAS,CAAC,IAAI,IAAI,CAAA;IAElB;;;;;;OAMG;IACH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,iBAAiB,KAAK,IAAI,CAAA;IAE7C;;;OAGG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC,UAAU,CAAC,CAAA;IAE7B;;;;OAIG;IAEH,SAAS,CAAC,EAAE,MAAM,GAAG,MAAM,CAAA;IAE3B;;OAEG;IACH,MAAM,CAAC,EAAE,MAAM,CAAA;IAEf;;OAEG;IACH,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAC7B;AAwED,UAAU,yBAAyB;IAC/B,UAAU,EAAE,OAAO,UAAU,CAAA;IAC7B,QAAQ,EAAE,OAAO,QAAQ,CAAA;IACzB,YAAY,EAAE,OAAO,YAAY,CAAA;IACjC,OAAO,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,IAAI,CAAA;CAEvC;AAED,QAAA,MAAM,SAAS,EAAE,KAAK,CAAC,aAAa,CAAC,cAAc,CAAC,GAChD,yBAAqD,CAAA;AAmCzD,eAAe,SAAS,CAAA"} \ No newline at end of file diff --git a/dist/index.js b/dist/index.js new file mode 100644 index 000000000..ba8c60301 --- /dev/null +++ b/dist/index.js @@ -0,0 +1,109 @@ +import _extends from '@babel/runtime/helpers/extends'; +import React, { forwardRef, memo } from 'react'; +import { NativeModules, StyleSheet, requireNativeComponent, Image, View } from 'react-native'; + +const FastImageViewNativeModule = NativeModules.FastImageView; +const resizeMode = { + contain: 'contain', + cover: 'cover', + stretch: 'stretch', + center: 'center' +}; +const priority = { + low: 'low', + normal: 'normal', + high: 'high' +}; +const cacheControl = { + // Ignore headers, use uri as cache key, fetch only if not in cache. + immutable: 'immutable', + // Respect http headers, no aggressive caching. + web: 'web', + // Only load from cache. + cacheOnly: 'cacheOnly' +}; + +function FastImageBase({ + source, + tintColor, + onLoadStart, + onProgress, + onLoad, + onError, + onLoadEnd, + style, + fallback, + children, + // eslint-disable-next-line no-shadow + resizeMode = 'cover', + forwardedRef, + ...props +}) { + if (fallback) { + const cleanedSource = { ...source + }; + delete cleanedSource.cache; + const resolvedSource = Image.resolveAssetSource(cleanedSource); + return /*#__PURE__*/React.createElement(View, { + style: [styles.imageContainer, style], + ref: forwardedRef + }, /*#__PURE__*/React.createElement(Image, _extends({}, props, { + style: StyleSheet.absoluteFill, + source: resolvedSource, + onLoadStart: onLoadStart, + onProgress: onProgress, + onLoad: onLoad, + onError: onError, + onLoadEnd: onLoadEnd, + resizeMode: resizeMode + })), children); + } + + const resolvedSource = Image.resolveAssetSource(source); + return /*#__PURE__*/React.createElement(View, { + style: [styles.imageContainer, style], + ref: forwardedRef + }, /*#__PURE__*/React.createElement(FastImageView, _extends({}, props, { + tintColor: tintColor, + style: StyleSheet.absoluteFill, + source: resolvedSource, + onFastImageLoadStart: onLoadStart, + onFastImageProgress: onProgress, + onFastImageLoad: onLoad, + onFastImageError: onError, + onFastImageLoadEnd: onLoadEnd, + resizeMode: resizeMode + })), children); +} + +const FastImageMemo = /*#__PURE__*/memo(FastImageBase); +const FastImageComponent = /*#__PURE__*/forwardRef((props, ref) => /*#__PURE__*/React.createElement(FastImageMemo, _extends({ + forwardedRef: ref +}, props))); +FastImageComponent.displayName = 'FastImage'; +const FastImage = FastImageComponent; +FastImage.resizeMode = resizeMode; +FastImage.cacheControl = cacheControl; +FastImage.priority = priority; + +FastImage.preload = sources => FastImageViewNativeModule.preload(sources); // FastImage.loadImage = (source: Source) => +// FastImageViewNativeModule.loadImage(source) + + +const styles = StyleSheet.create({ + imageContainer: { + overflow: 'hidden' + } +}); // Types of requireNativeComponent are not correct. + +const FastImageView = requireNativeComponent('FastImageView', FastImage, { + nativeOnly: { + onFastImageLoadStart: true, + onFastImageProgress: true, + onFastImageLoad: true, + onFastImageError: true, + onFastImageLoadEnd: true + } +}); + +export default FastImage; diff --git a/dist/index.js.flow b/dist/index.js.flow new file mode 100644 index 000000000..71fac3a92 --- /dev/null +++ b/dist/index.js.flow @@ -0,0 +1,71 @@ +// @flow + +import type { ViewProps } from 'react-native/Libraries/Components/View/ViewPropTypes' +import type { SyntheticEvent } from 'react-native/Libraries/Types/CoreEventTypes' + +export type OnLoadEvent = SyntheticEvent< + $ReadOnly<{ + width: number, + height: number, + }>, +> + +export type OnProgressEvent = SyntheticEvent< + $ReadOnly<{| + loaded: number, + total: number, + |}>, +> + +export type ResizeMode = $ReadOnly<{| + contain: 'contain', + cover: 'cover', + stretch: 'stretch', + center: 'center', +|}> + +export type Priority = $ReadOnly<{| + low: 'low', + normal: 'normal', + high: 'high', +|}> + +export type CacheControl = $ReadOnly<{| + immutable: 'immutable', + web: 'web', + cacheOnly: 'cacheOnly', +|}> + +export type ResizeModes = $Values +export type Priorities = $Values +export type CacheControls = $Values + +export type PreloadFn = (sources: Array) => void +export type FastImageSource = { + uri?: string, + headers?: Object, + priority?: Priorities, + cache?: CacheControls, +} + +export type FastImageProps = $ReadOnly<{| + ...ViewProps, + onError?: ?() => void, + onLoad?: ?(event: OnLoadEvent) => void, + onLoadEnd?: ?() => void, + onLoadStart?: ?() => void, + onProgress?: ?(event: OnProgressEvent) => void, + + source: FastImageSource | number, + + resizeMode?: ?ResizeModes, + fallback?: ?boolean, + testID?: ?string, +|}> + +declare export default class FastImage extends React$Component { + static resizeMode: ResizeMode; + static priority: Priority; + static cacheControl: CacheControl; + static preload: PreloadFn; +} diff --git a/dist/index.test.d.ts b/dist/index.test.d.ts new file mode 100644 index 000000000..121d59b38 --- /dev/null +++ b/dist/index.test.d.ts @@ -0,0 +1,2 @@ +export {}; +//# sourceMappingURL=index.test.d.ts.map \ No newline at end of file diff --git a/dist/index.test.d.ts.map b/dist/index.test.d.ts.map new file mode 100644 index 000000000..e451024d1 --- /dev/null +++ b/dist/index.test.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.test.d.ts","sourceRoot":"","sources":["../src/index.test.tsx"],"names":[],"mappings":""} \ No newline at end of file From cafdfd35ff1d1e77c9e0e2d6e98a5e9eed7a29ec Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Thu, 20 Aug 2020 14:27:07 +0300 Subject: [PATCH 07/17] uncomment code --- dist/index.cjs.js | 4 +- dist/index.d.ts | 1 + dist/index.d.ts.map | 2 +- dist/index.js | 4 +- ios/FastImage/FFFastImageViewManager.m | 104 ++++++++++++------------- src/index.tsx | 6 +- 6 files changed, 61 insertions(+), 60 deletions(-) diff --git a/dist/index.cjs.js b/dist/index.cjs.js index a7b16ad9e..a5bd7bf19 100644 --- a/dist/index.cjs.js +++ b/dist/index.cjs.js @@ -91,9 +91,9 @@ FastImage.resizeMode = resizeMode; FastImage.cacheControl = cacheControl; FastImage.priority = priority; -FastImage.preload = sources => FastImageViewNativeModule.preload(sources); // FastImage.loadImage = (source: Source) => -// FastImageViewNativeModule.loadImage(source) +FastImage.preload = sources => FastImageViewNativeModule.preload(sources); +FastImage.loadImage = source => FastImageViewNativeModule.loadImage(source); const styles = reactNative.StyleSheet.create({ imageContainer: { diff --git a/dist/index.d.ts b/dist/index.d.ts index 0b1afd5e1..50d48b4dc 100644 --- a/dist/index.d.ts +++ b/dist/index.d.ts @@ -95,6 +95,7 @@ interface FastImageStaticProperties { priority: typeof priority; cacheControl: typeof cacheControl; preload: (sources: Source[]) => void; + loadImage: (source: Source) => Promise; } declare const FastImage: React.ComponentType & FastImageStaticProperties; export default FastImage; diff --git a/dist/index.d.ts.map b/dist/index.d.ts.map index f88da67c1..173d18c0b 100644 --- a/dist/index.d.ts.map +++ b/dist/index.d.ts.map @@ -1 +1 @@ -{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"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"} \ No newline at end of file +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/dist/index.js b/dist/index.js index ba8c60301..fec297caf 100644 --- a/dist/index.js +++ b/dist/index.js @@ -86,9 +86,9 @@ FastImage.resizeMode = resizeMode; FastImage.cacheControl = cacheControl; FastImage.priority = priority; -FastImage.preload = sources => FastImageViewNativeModule.preload(sources); // FastImage.loadImage = (source: Source) => -// FastImageViewNativeModule.loadImage(source) +FastImage.preload = sources => FastImageViewNativeModule.preload(sources); +FastImage.loadImage = source => FastImageViewNativeModule.loadImage(source); const styles = StyleSheet.create({ imageContainer: { diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index f8195675c..7ece60386 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -35,58 +35,58 @@ - (FFFastImageView*)view { } // https://github.com/DylanVann/react-native-fast-image/pull/351/files -// RCT_REMAP_METHOD( -// loadImage, -// loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject -// ) { -// SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; -// NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; -// NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; - -// // set headers -// [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { -// [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; -// }]; - -// // set options -// SDWebImageOptions options = 0; -// options |= SDWebImageRetryFailed; -// switch (source.priority) { -// case FFFPriorityLow: -// options |= SDWebImageLowPriority; -// break; -// case FFFPriorityNormal: -// // Priority is normal by default. -// break; -// case FFFPriorityHigh: -// options |= SDWebImageHighPriority; -// break; -// } - -// switch (source.cacheControl) { -// case FFFCacheControlWeb: -// options |= SDWebImageRefreshCached; -// break; -// case FFFCacheControlCacheOnly: -// options |= SDWebImageCacheMemoryOnly; -// break; -// case FFFCacheControlImmutable: -// break; -// } - -// // load image -// [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { -// if (error != nil) { -// reject(@"FastImage", @"Failed to load image", error); -// return; -// } - -// // store image manually (since image manager may call the completion block before storing it in the disk cache) -// [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ -// resolve(imagePath); -// }]; -// }]; -// } +RCT_REMAP_METHOD( + loadImage, + loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject +) { + SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; + NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; + NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; + + // set headers + [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { + [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; + }]; + + // set options + SDWebImageOptions options = 0; + options |= SDWebImageRetryFailed; + switch (source.priority) { + case FFFPriorityLow: + options |= SDWebImageLowPriority; + break; + case FFFPriorityNormal: + // Priority is normal by default. + break; + case FFFPriorityHigh: + options |= SDWebImageHighPriority; + break; + } + + switch (source.cacheControl) { + case FFFCacheControlWeb: + options |= SDWebImageRefreshCached; + break; + case FFFCacheControlCacheOnly: + options |= SDWebImageCacheMemoryOnly; + break; + case FFFCacheControlImmutable: + break; + } + + // load image + [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { + if (error != nil) { + reject(@"FastImage", @"Failed to load image", error); + return; + } + + // store image manually (since image manager may call the completion block before storing it in the disk cache) + [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ + resolve(imagePath); + }]; + }]; +} @end diff --git a/src/index.tsx b/src/index.tsx index 922ba8562..8a748b1ad 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -203,7 +203,7 @@ interface FastImageStaticProperties { priority: typeof priority cacheControl: typeof cacheControl preload: (sources: Source[]) => void - // loadImage: (source: Source) => Promise + loadImage: (source: Source) => Promise } const FastImage: React.ComponentType & @@ -218,8 +218,8 @@ FastImage.priority = priority FastImage.preload = (sources: Source[]) => FastImageViewNativeModule.preload(sources) -// FastImage.loadImage = (source: Source) => -// FastImageViewNativeModule.loadImage(source) +FastImage.loadImage = (source: Source) => + FastImageViewNativeModule.loadImage(source) const styles = StyleSheet.create({ imageContainer: { From 2bf6847512a44badddfd17ccc5fba1f9f63dd969 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Thu, 20 Aug 2020 19:10:38 +0300 Subject: [PATCH 08/17] get cache path (iOS) --- ios/FastImage/FFFastImageViewManager.m | 64 +++++--------------------- src/index.tsx | 6 +-- 2 files changed, 15 insertions(+), 55 deletions(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 7ece60386..1b607f568 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -2,6 +2,7 @@ #import "FFFastImageView.h" #import +#import @implementation FFFastImageViewManager @@ -34,59 +35,18 @@ - (FFFastImageView*)view { [[SDWebImagePrefetcher sharedImagePrefetcher] prefetchURLs:urls]; } -// https://github.com/DylanVann/react-native-fast-image/pull/351/files -RCT_REMAP_METHOD( - loadImage, - loadImageWithSource: (nonnull FFFastImageSource *)source resolver:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject -) { - SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; - NSString *cacheKey = [imageManager cacheKeyForURL:source.url]; - NSString *imagePath = [imageManager.imageCache cachePathForKey:cacheKey]; - - // set headers - [source.headers enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString* header, BOOL *stop) { - [imageManager.imageLoader setValue:header forHTTPHeaderField:key]; - }]; - - // set options - SDWebImageOptions options = 0; - options |= SDWebImageRetryFailed; - switch (source.priority) { - case FFFPriorityLow: - options |= SDWebImageLowPriority; - break; - case FFFPriorityNormal: - // Priority is normal by default. - break; - case FFFPriorityHigh: - options |= SDWebImageHighPriority; - break; - } - - switch (source.cacheControl) { - case FFFCacheControlWeb: - options |= SDWebImageRefreshCached; - break; - case FFFCacheControlCacheOnly: - options |= SDWebImageCacheMemoryOnly; - break; - case FFFCacheControlImmutable: - break; - } - - // load image - [imageManager loadImageWithURL:source.url options:options progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) { - if (error != nil) { - reject(@"FastImage", @"Failed to load image", error); - return; +// https://github.com/DylanVann/react-native-fast-image/pull/557 +RCT_EXPORT_METHOD(getCachePath:(NSString *)key + withResolver:(RCTPromiseResolveBlock)resolve + andRejecter:(RCTPromiseRejectBlock)reject) +{ + BOOL isCached = [[SDImageCache sharedImageCache] diskImageDataExistsWithKey:key]; + if (isCached) { + NSString *cachePath = [[SDImageCache sharedImageCache] cachePathForKey:key]; + resolve(cachePath); + } else { + resolve([NSNull null]); } - - // store image manually (since image manager may call the completion block before storing it in the disk cache) - [imageManager.imageCache storeImage:image forKey:cacheKey completion:^{ - resolve(imagePath); - }]; - }]; } @end - diff --git a/src/index.tsx b/src/index.tsx index 8a748b1ad..634a6f8aa 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -203,7 +203,7 @@ interface FastImageStaticProperties { priority: typeof priority cacheControl: typeof cacheControl preload: (sources: Source[]) => void - loadImage: (source: Source) => Promise + getCachePath: (source: Source) => Promise } const FastImage: React.ComponentType & @@ -218,8 +218,8 @@ FastImage.priority = priority FastImage.preload = (sources: Source[]) => FastImageViewNativeModule.preload(sources) -FastImage.loadImage = (source: Source) => - FastImageViewNativeModule.loadImage(source) +FastImage.getCachePath = (source: Source) => + FastImageViewNativeModule.getCachePath(source) const styles = StyleSheet.create({ imageContainer: { From d765e642a47ecc174f731c2aef330e421c9f2cb6 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Thu, 20 Aug 2020 19:14:45 +0300 Subject: [PATCH 09/17] get cache path (iOS) --- dist/index.cjs.js | 2 +- dist/index.d.ts | 2 +- dist/index.d.ts.map | 2 +- dist/index.js | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/dist/index.cjs.js b/dist/index.cjs.js index a5bd7bf19..ff645c465 100644 --- a/dist/index.cjs.js +++ b/dist/index.cjs.js @@ -93,7 +93,7 @@ FastImage.priority = priority; FastImage.preload = sources => FastImageViewNativeModule.preload(sources); -FastImage.loadImage = source => FastImageViewNativeModule.loadImage(source); +FastImage.getCachePath = source => FastImageViewNativeModule.getCachePath(source); const styles = reactNative.StyleSheet.create({ imageContainer: { diff --git a/dist/index.d.ts b/dist/index.d.ts index 50d48b4dc..dc95c4b2b 100644 --- a/dist/index.d.ts +++ b/dist/index.d.ts @@ -95,7 +95,7 @@ interface FastImageStaticProperties { priority: typeof priority; cacheControl: typeof cacheControl; preload: (sources: Source[]) => void; - loadImage: (source: Source) => Promise; + getCachePath: (source: Source) => Promise; } declare const FastImage: React.ComponentType & FastImageStaticProperties; export default FastImage; diff --git a/dist/index.d.ts.map b/dist/index.d.ts.map index 173d18c0b..9500b141f 100644 --- a/dist/index.d.ts.map +++ b/dist/index.d.ts.map @@ -1 +1 @@ -{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"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"} \ No newline at end of file +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA2B,MAAM,OAAO,CAAA;AAC/C,OAAO,EAMH,SAAS,EACT,iBAAiB,EACjB,cAAc,EACd,SAAS,EACT,eAAe,EACf,kBAAkB,EACrB,MAAM,cAAc,CAAA;AAIrB,oBAAY,UAAU,GAAG,SAAS,GAAG,OAAO,GAAG,SAAS,GAAG,QAAQ,CAAA;AAEnE,QAAA,MAAM,UAAU;;;;;CAKN,CAAA;AAEV,oBAAY,QAAQ,GAAG,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAA;AAEhD,QAAA,MAAM,QAAQ;;;;CAIJ,CAAA;AAEV,aAAK,KAAK,GAAG,WAAW,GAAG,KAAK,GAAG,WAAW,CAAA;AAE9C,QAAA,MAAM,YAAY;;;;CAOR,CAAA;AAEV,oBAAY,MAAM,GAAG;IACjB,GAAG,CAAC,EAAE,MAAM,CAAA;IACZ,OAAO,CAAC,EAAE;QAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAA;KAAE,CAAA;IACnC,QAAQ,CAAC,EAAE,QAAQ,CAAA;IACnB,KAAK,CAAC,EAAE,KAAK,CAAA;CAChB,CAAA;AAED,MAAM,WAAW,WAAW;IACxB,WAAW,EAAE;QACT,KAAK,EAAE,MAAM,CAAA;QACb,MAAM,EAAE,MAAM,CAAA;KACjB,CAAA;CACJ;AAED,MAAM,WAAW,eAAe;IAC5B,WAAW,EAAE;QACT,MAAM,EAAE,MAAM,CAAA;QACd,KAAK,EAAE,MAAM,CAAA;KAChB,CAAA;CACJ;AAED,MAAM,WAAW,UAAW,SAAQ,SAAS,EAAE,eAAe,EAAE,cAAc;IAC1E,kBAAkB,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAA;IACzC,sBAAsB,CAAC,EAAE,MAAM,CAAA;IAC/B,uBAAuB,CAAC,EAAE,MAAM,CAAA;IAChC,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,mBAAmB,CAAC,EAAE,MAAM,CAAA;IAC5B,oBAAoB,CAAC,EAAE,MAAM,CAAA;IAC7B,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,OAAO,CAAC,EAAE,MAAM,CAAA;CACnB;AAED,MAAM,WAAW,cAAe,SAAQ,kBAAkB;IACtD,MAAM,EAAE,MAAM,GAAG,MAAM,CAAA;IACvB,UAAU,CAAC,EAAE,UAAU,CAAA;IACvB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAElB,WAAW,CAAC,IAAI,IAAI,CAAA;IAEpB,UAAU,CAAC,CAAC,KAAK,EAAE,eAAe,GAAG,IAAI,CAAA;IAEzC,MAAM,CAAC,CAAC,KAAK,EAAE,WAAW,GAAG,IAAI,CAAA;IAEjC,OAAO,CAAC,IAAI,IAAI,CAAA;IAEhB,SAAS,CAAC,IAAI,IAAI,CAAA;IAElB;;;;;;OAMG;IACH,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,iBAAiB,KAAK,IAAI,CAAA;IAE7C;;;OAGG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC,UAAU,CAAC,CAAA;IAE7B;;;;OAIG;IAEH,SAAS,CAAC,EAAE,MAAM,GAAG,MAAM,CAAA;IAE3B;;OAEG;IACH,MAAM,CAAC,EAAE,MAAM,CAAA;IAEf;;OAEG;IACH,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAC7B;AAwED,UAAU,yBAAyB;IAC/B,UAAU,EAAE,OAAO,UAAU,CAAA;IAC7B,QAAQ,EAAE,OAAO,QAAQ,CAAA;IACzB,YAAY,EAAE,OAAO,YAAY,CAAA;IACjC,OAAO,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,IAAI,CAAA;IACpC,YAAY,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,OAAO,CAAC,MAAM,CAAC,CAAA;CACpD;AAED,QAAA,MAAM,SAAS,EAAE,KAAK,CAAC,aAAa,CAAC,cAAc,CAAC,GAChD,yBAAqD,CAAA;AAmCzD,eAAe,SAAS,CAAA"} \ No newline at end of file diff --git a/dist/index.js b/dist/index.js index fec297caf..459368efd 100644 --- a/dist/index.js +++ b/dist/index.js @@ -88,7 +88,7 @@ FastImage.priority = priority; FastImage.preload = sources => FastImageViewNativeModule.preload(sources); -FastImage.loadImage = source => FastImageViewNativeModule.loadImage(source); +FastImage.getCachePath = source => FastImageViewNativeModule.getCachePath(source); const styles = StyleSheet.create({ imageContainer: { From 6d8570623ad2219cdd24b5ff16bfefd639fd1a4a Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 10:33:24 +0300 Subject: [PATCH 10/17] add getCachePath for Android --- .../fastimage/FastImageViewModule.java | 43 +++++++++++++++++++ 1 file changed, 43 insertions(+) diff --git a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java index 5452c7922..3db894c52 100644 --- a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java +++ b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java @@ -2,8 +2,14 @@ import android.app.Activity; +import android.support.annotation.Nullable; import com.bumptech.glide.Glide; +import com.bumptech.glide.load.DataSource; +import com.bumptech.glide.load.engine.GlideException; import com.bumptech.glide.load.model.GlideUrl; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; +import com.facebook.react.bridge.Promise; import com.facebook.react.bridge.ReactApplicationContext; import com.facebook.react.bridge.ReactContextBaseJavaModule; import com.facebook.react.bridge.ReactMethod; @@ -11,9 +17,12 @@ import com.facebook.react.bridge.ReadableMap; import com.facebook.react.views.imagehelper.ImageSource; +import java.io.File; + class FastImageViewModule extends ReactContextBaseJavaModule { private static final String REACT_CLASS = "FastImageView"; + private static final String ERROR_LOAD_FAILED = "ERROR_LOAD_FAILED"; FastImageViewModule(ReactApplicationContext reactContext) { super(reactContext); @@ -53,4 +62,38 @@ public void run() { } }); } + + @ReactMethod + public void getCachePath(final ReadableMap source, final Promise promise) { + final Activity activity = getCurrentActivity(); + if (activity == null) return; + + activity.runOnUiThread(new Runnable() { + @Override + public void run() { + final FastImageSource imageSource = FastImageViewConverter.getImageSource(activity, source); + final GlideUrl glideUrl = imageSource.getGlideUrl(); + + Glide + .with(activity.getApplicationContext()) + .asFile() + .load(glideUrl) + .apply(FastImageViewConverter.getOptions(activity.getApplicationContext(), imageSource, source)) + .listener(new RequestListener() { + @Override + public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) { + promise.reject(ERROR_LOAD_FAILED, e); + return false; + } + + @Override + public boolean onResourceReady(File resource, Object model, Target target, DataSource dataSource, boolean isFirstResource) { + promise.resolve(resource.getAbsolutePath()); + return false; + } + }) + .submit(); + } + }); + } } From 5e8746a702e4498ec2ba13aec82f3b60c9cc9d88 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 11:20:57 +0300 Subject: [PATCH 11/17] add getCachePath for Android --- .../main/java/com/dylanvann/fastimage/FastImageViewModule.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java index 3db894c52..69079a39c 100644 --- a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java +++ b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java @@ -78,7 +78,7 @@ public void run() { .with(activity.getApplicationContext()) .asFile() .load(glideUrl) - .apply(FastImageViewConverter.getOptions(activity.getApplicationContext(), imageSource, source)) + .apply(FastImageViewConverter.getOptions(activity, imageSource, source)) .listener(new RequestListener() { @Override public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) { From e57d65e22c92c7594df47c2fcb57a92cd3d2812e Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 11:50:50 +0300 Subject: [PATCH 12/17] add getCachePath as map for iOS too --- ios/FastImage/FFFastImageViewManager.m | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/ios/FastImage/FFFastImageViewManager.m b/ios/FastImage/FFFastImageViewManager.m index 1b607f568..18cf8f1f0 100644 --- a/ios/FastImage/FFFastImageViewManager.m +++ b/ios/FastImage/FFFastImageViewManager.m @@ -35,12 +35,14 @@ - (FFFastImageView*)view { [[SDWebImagePrefetcher sharedImagePrefetcher] prefetchURLs:urls]; } -// https://github.com/DylanVann/react-native-fast-image/pull/557 -RCT_EXPORT_METHOD(getCachePath:(NSString *)key +RCT_EXPORT_METHOD(getCachePath:(nonnull FFFastImageSource *)source withResolver:(RCTPromiseResolveBlock)resolve andRejecter:(RCTPromiseRejectBlock)reject) { + SDWebImageManager *imageManager = [SDWebImageManager sharedManager]; + NSString *key = [imageManager cacheKeyForURL:source.url]; BOOL isCached = [[SDImageCache sharedImageCache] diskImageDataExistsWithKey:key]; + if (isCached) { NSString *cachePath = [[SDImageCache sharedImageCache] cachePathForKey:key]; resolve(cachePath); From 434bd2b4a22d2637e0343223edf507de5e480cc0 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 13:55:01 +0300 Subject: [PATCH 13/17] fix Android crash if invalid/unexistent key is specified --- .../main/java/com/dylanvann/fastimage/FastImageSource.java | 6 ++++++ .../java/com/dylanvann/fastimage/FastImageViewModule.java | 6 ++++++ 2 files changed, 12 insertions(+) diff --git a/android/src/main/java/com/dylanvann/fastimage/FastImageSource.java b/android/src/main/java/com/dylanvann/fastimage/FastImageSource.java index 888b38e09..bb7ffc2f2 100644 --- a/android/src/main/java/com/dylanvann/fastimage/FastImageSource.java +++ b/android/src/main/java/com/dylanvann/fastimage/FastImageSource.java @@ -107,6 +107,12 @@ public Headers getHeaders() { } public GlideUrl getGlideUrl() { + Uri uriVal = getUri(); + + if (Uri.EMPTY.equals(uriVal)) { + return null; + } + return new GlideUrl(getUri().toString(), getHeaders()); } } diff --git a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java index 69079a39c..f85835cdb 100644 --- a/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java +++ b/android/src/main/java/com/dylanvann/fastimage/FastImageViewModule.java @@ -3,6 +3,7 @@ import android.app.Activity; import android.support.annotation.Nullable; + import com.bumptech.glide.Glide; import com.bumptech.glide.load.DataSource; import com.bumptech.glide.load.engine.GlideException; @@ -74,6 +75,11 @@ public void run() { final FastImageSource imageSource = FastImageViewConverter.getImageSource(activity, source); final GlideUrl glideUrl = imageSource.getGlideUrl(); + if (glideUrl == null) { + promise.resolve(null); + return; + } + Glide .with(activity.getApplicationContext()) .asFile() From f4babb7bd04a904cad7ed1d8995b117f874ac1f9 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 16:33:01 +0300 Subject: [PATCH 14/17] update README file --- README.md | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/README.md b/README.md index 4a2be142f..449f0d70a 100644 --- a/README.md +++ b/README.md @@ -54,6 +54,7 @@ and - [x] Preload images. - [x] GIF support. - [x] Border radius. +- [x] Get image path from cache. ## Usage @@ -213,6 +214,14 @@ FastImage.preload([ ]) ``` +### `FastImage.getCachePath: (source) => void` + +Get image path from cache by `source` + +```js +FastImage.preload({ uri: 'https://facebook.github.io/react/img/logo_og.png' }) +``` + ## Troubleshooting If you have any problems using this library try the steps in [troubleshooting](docs/troubleshooting.md) and see if they fix it. From 8895f665b08640167b9bbfd24081bc329f1e34a7 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 16:48:26 +0300 Subject: [PATCH 15/17] remove tracked dist/ folder --- .gitignore | 2 +- dist/index.cjs.js | 114 --------------------------------------- dist/index.d.ts | 102 ----------------------------------- dist/index.d.ts.map | 1 - dist/index.js | 109 ------------------------------------- dist/index.js.flow | 71 ------------------------ dist/index.test.d.ts | 2 - dist/index.test.d.ts.map | 1 - 8 files changed, 1 insertion(+), 401 deletions(-) delete mode 100644 dist/index.cjs.js delete mode 100644 dist/index.d.ts delete mode 100644 dist/index.d.ts.map delete mode 100644 dist/index.js delete mode 100644 dist/index.js.flow delete mode 100644 dist/index.test.d.ts delete mode 100644 dist/index.test.d.ts.map diff --git a/.gitignore b/.gitignore index a223cdb95..0c43f2cd0 100644 --- a/.gitignore +++ b/.gitignore @@ -42,7 +42,7 @@ example/android/app/src/main/gen # build react-native-fast-image-*.tgz -#dist/ +dist/ # coverage reports coverage diff --git a/dist/index.cjs.js b/dist/index.cjs.js deleted file mode 100644 index ff645c465..000000000 --- a/dist/index.cjs.js +++ /dev/null @@ -1,114 +0,0 @@ -'use strict'; - -function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } - -var _extends = _interopDefault(require('@babel/runtime/helpers/extends')); -var React = require('react'); -var React__default = _interopDefault(React); -var reactNative = require('react-native'); - -const FastImageViewNativeModule = reactNative.NativeModules.FastImageView; -const resizeMode = { - contain: 'contain', - cover: 'cover', - stretch: 'stretch', - center: 'center' -}; -const priority = { - low: 'low', - normal: 'normal', - high: 'high' -}; -const cacheControl = { - // Ignore headers, use uri as cache key, fetch only if not in cache. - immutable: 'immutable', - // Respect http headers, no aggressive caching. - web: 'web', - // Only load from cache. - cacheOnly: 'cacheOnly' -}; - -function FastImageBase({ - source, - tintColor, - onLoadStart, - onProgress, - onLoad, - onError, - onLoadEnd, - style, - fallback, - children, - // eslint-disable-next-line no-shadow - resizeMode = 'cover', - forwardedRef, - ...props -}) { - if (fallback) { - const cleanedSource = { ...source - }; - delete cleanedSource.cache; - const resolvedSource = reactNative.Image.resolveAssetSource(cleanedSource); - return /*#__PURE__*/React__default.createElement(reactNative.View, { - style: [styles.imageContainer, style], - ref: forwardedRef - }, /*#__PURE__*/React__default.createElement(reactNative.Image, _extends({}, props, { - style: reactNative.StyleSheet.absoluteFill, - source: resolvedSource, - onLoadStart: onLoadStart, - onProgress: onProgress, - onLoad: onLoad, - onError: onError, - onLoadEnd: onLoadEnd, - resizeMode: resizeMode - })), children); - } - - const resolvedSource = reactNative.Image.resolveAssetSource(source); - return /*#__PURE__*/React__default.createElement(reactNative.View, { - style: [styles.imageContainer, style], - ref: forwardedRef - }, /*#__PURE__*/React__default.createElement(FastImageView, _extends({}, props, { - tintColor: tintColor, - style: reactNative.StyleSheet.absoluteFill, - source: resolvedSource, - onFastImageLoadStart: onLoadStart, - onFastImageProgress: onProgress, - onFastImageLoad: onLoad, - onFastImageError: onError, - onFastImageLoadEnd: onLoadEnd, - resizeMode: resizeMode - })), children); -} - -const FastImageMemo = /*#__PURE__*/React.memo(FastImageBase); -const FastImageComponent = /*#__PURE__*/React.forwardRef((props, ref) => /*#__PURE__*/React__default.createElement(FastImageMemo, _extends({ - forwardedRef: ref -}, props))); -FastImageComponent.displayName = 'FastImage'; -const FastImage = FastImageComponent; -FastImage.resizeMode = resizeMode; -FastImage.cacheControl = cacheControl; -FastImage.priority = priority; - -FastImage.preload = sources => FastImageViewNativeModule.preload(sources); - -FastImage.getCachePath = source => FastImageViewNativeModule.getCachePath(source); - -const styles = reactNative.StyleSheet.create({ - imageContainer: { - overflow: 'hidden' - } -}); // Types of requireNativeComponent are not correct. - -const FastImageView = reactNative.requireNativeComponent('FastImageView', FastImage, { - nativeOnly: { - onFastImageLoadStart: true, - onFastImageProgress: true, - onFastImageLoad: true, - onFastImageError: true, - onFastImageLoadEnd: true - } -}); - -module.exports = FastImage; diff --git a/dist/index.d.ts b/dist/index.d.ts deleted file mode 100644 index dc95c4b2b..000000000 --- a/dist/index.d.ts +++ /dev/null @@ -1,102 +0,0 @@ -import React from 'react'; -import { FlexStyle, LayoutChangeEvent, ShadowStyleIOS, StyleProp, TransformsStyle, AccessibilityProps } from 'react-native'; -export declare type ResizeMode = 'contain' | 'cover' | 'stretch' | 'center'; -declare const resizeMode: { - readonly contain: "contain"; - readonly cover: "cover"; - readonly stretch: "stretch"; - readonly center: "center"; -}; -export declare type Priority = 'low' | 'normal' | 'high'; -declare const priority: { - readonly low: "low"; - readonly normal: "normal"; - readonly high: "high"; -}; -declare type Cache = 'immutable' | 'web' | 'cacheOnly'; -declare const cacheControl: { - readonly immutable: "immutable"; - readonly web: "web"; - readonly cacheOnly: "cacheOnly"; -}; -export declare type Source = { - uri?: string; - headers?: { - [key: string]: string; - }; - priority?: Priority; - cache?: Cache; -}; -export interface OnLoadEvent { - nativeEvent: { - width: number; - height: number; - }; -} -export interface OnProgressEvent { - nativeEvent: { - loaded: number; - total: number; - }; -} -export interface ImageStyle extends FlexStyle, TransformsStyle, ShadowStyleIOS { - backfaceVisibility?: 'visible' | 'hidden'; - borderBottomLeftRadius?: number; - borderBottomRightRadius?: number; - backgroundColor?: string; - borderColor?: string; - borderWidth?: number; - borderRadius?: number; - borderTopLeftRadius?: number; - borderTopRightRadius?: number; - overlayColor?: string; - tintColor?: string; - opacity?: number; -} -export interface FastImageProps extends AccessibilityProps { - source: Source | number; - resizeMode?: ResizeMode; - fallback?: boolean; - onLoadStart?(): void; - onProgress?(event: OnProgressEvent): void; - onLoad?(event: OnLoadEvent): void; - onError?(): void; - onLoadEnd?(): void; - /** - * onLayout function - * - * Invoked on mount and layout changes with - * - * {nativeEvent: { layout: {x, y, width, height}}}. - */ - onLayout?: (event: LayoutChangeEvent) => void; - /** - * - * Style - */ - style?: StyleProp; - /** - * TintColor - * - * If supplied, changes the color of all the non-transparent pixels to the given color. - */ - tintColor?: number | string; - /** - * A unique identifier for this element to be used in UI Automation testing scripts. - */ - testID?: string; - /** - * Render children within the image. - */ - children?: React.ReactNode; -} -interface FastImageStaticProperties { - resizeMode: typeof resizeMode; - priority: typeof priority; - cacheControl: typeof cacheControl; - preload: (sources: Source[]) => void; - getCachePath: (source: Source) => Promise; -} -declare const FastImage: React.ComponentType & FastImageStaticProperties; -export default FastImage; -//# sourceMappingURL=index.d.ts.map \ No newline at end of file diff --git a/dist/index.d.ts.map b/dist/index.d.ts.map deleted file mode 100644 index 9500b141f..000000000 --- a/dist/index.d.ts.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/dist/index.js b/dist/index.js deleted file mode 100644 index 459368efd..000000000 --- a/dist/index.js +++ /dev/null @@ -1,109 +0,0 @@ -import _extends from '@babel/runtime/helpers/extends'; -import React, { forwardRef, memo } from 'react'; -import { NativeModules, StyleSheet, requireNativeComponent, Image, View } from 'react-native'; - -const FastImageViewNativeModule = NativeModules.FastImageView; -const resizeMode = { - contain: 'contain', - cover: 'cover', - stretch: 'stretch', - center: 'center' -}; -const priority = { - low: 'low', - normal: 'normal', - high: 'high' -}; -const cacheControl = { - // Ignore headers, use uri as cache key, fetch only if not in cache. - immutable: 'immutable', - // Respect http headers, no aggressive caching. - web: 'web', - // Only load from cache. - cacheOnly: 'cacheOnly' -}; - -function FastImageBase({ - source, - tintColor, - onLoadStart, - onProgress, - onLoad, - onError, - onLoadEnd, - style, - fallback, - children, - // eslint-disable-next-line no-shadow - resizeMode = 'cover', - forwardedRef, - ...props -}) { - if (fallback) { - const cleanedSource = { ...source - }; - delete cleanedSource.cache; - const resolvedSource = Image.resolveAssetSource(cleanedSource); - return /*#__PURE__*/React.createElement(View, { - style: [styles.imageContainer, style], - ref: forwardedRef - }, /*#__PURE__*/React.createElement(Image, _extends({}, props, { - style: StyleSheet.absoluteFill, - source: resolvedSource, - onLoadStart: onLoadStart, - onProgress: onProgress, - onLoad: onLoad, - onError: onError, - onLoadEnd: onLoadEnd, - resizeMode: resizeMode - })), children); - } - - const resolvedSource = Image.resolveAssetSource(source); - return /*#__PURE__*/React.createElement(View, { - style: [styles.imageContainer, style], - ref: forwardedRef - }, /*#__PURE__*/React.createElement(FastImageView, _extends({}, props, { - tintColor: tintColor, - style: StyleSheet.absoluteFill, - source: resolvedSource, - onFastImageLoadStart: onLoadStart, - onFastImageProgress: onProgress, - onFastImageLoad: onLoad, - onFastImageError: onError, - onFastImageLoadEnd: onLoadEnd, - resizeMode: resizeMode - })), children); -} - -const FastImageMemo = /*#__PURE__*/memo(FastImageBase); -const FastImageComponent = /*#__PURE__*/forwardRef((props, ref) => /*#__PURE__*/React.createElement(FastImageMemo, _extends({ - forwardedRef: ref -}, props))); -FastImageComponent.displayName = 'FastImage'; -const FastImage = FastImageComponent; -FastImage.resizeMode = resizeMode; -FastImage.cacheControl = cacheControl; -FastImage.priority = priority; - -FastImage.preload = sources => FastImageViewNativeModule.preload(sources); - -FastImage.getCachePath = source => FastImageViewNativeModule.getCachePath(source); - -const styles = StyleSheet.create({ - imageContainer: { - overflow: 'hidden' - } -}); // Types of requireNativeComponent are not correct. - -const FastImageView = requireNativeComponent('FastImageView', FastImage, { - nativeOnly: { - onFastImageLoadStart: true, - onFastImageProgress: true, - onFastImageLoad: true, - onFastImageError: true, - onFastImageLoadEnd: true - } -}); - -export default FastImage; diff --git a/dist/index.js.flow b/dist/index.js.flow deleted file mode 100644 index 71fac3a92..000000000 --- a/dist/index.js.flow +++ /dev/null @@ -1,71 +0,0 @@ -// @flow - -import type { ViewProps } from 'react-native/Libraries/Components/View/ViewPropTypes' -import type { SyntheticEvent } from 'react-native/Libraries/Types/CoreEventTypes' - -export type OnLoadEvent = SyntheticEvent< - $ReadOnly<{ - width: number, - height: number, - }>, -> - -export type OnProgressEvent = SyntheticEvent< - $ReadOnly<{| - loaded: number, - total: number, - |}>, -> - -export type ResizeMode = $ReadOnly<{| - contain: 'contain', - cover: 'cover', - stretch: 'stretch', - center: 'center', -|}> - -export type Priority = $ReadOnly<{| - low: 'low', - normal: 'normal', - high: 'high', -|}> - -export type CacheControl = $ReadOnly<{| - immutable: 'immutable', - web: 'web', - cacheOnly: 'cacheOnly', -|}> - -export type ResizeModes = $Values -export type Priorities = $Values -export type CacheControls = $Values - -export type PreloadFn = (sources: Array) => void -export type FastImageSource = { - uri?: string, - headers?: Object, - priority?: Priorities, - cache?: CacheControls, -} - -export type FastImageProps = $ReadOnly<{| - ...ViewProps, - onError?: ?() => void, - onLoad?: ?(event: OnLoadEvent) => void, - onLoadEnd?: ?() => void, - onLoadStart?: ?() => void, - onProgress?: ?(event: OnProgressEvent) => void, - - source: FastImageSource | number, - - resizeMode?: ?ResizeModes, - fallback?: ?boolean, - testID?: ?string, -|}> - -declare export default class FastImage extends React$Component { - static resizeMode: ResizeMode; - static priority: Priority; - static cacheControl: CacheControl; - static preload: PreloadFn; -} diff --git a/dist/index.test.d.ts b/dist/index.test.d.ts deleted file mode 100644 index 121d59b38..000000000 --- a/dist/index.test.d.ts +++ /dev/null @@ -1,2 +0,0 @@ -export {}; -//# sourceMappingURL=index.test.d.ts.map \ No newline at end of file diff --git a/dist/index.test.d.ts.map b/dist/index.test.d.ts.map deleted file mode 100644 index e451024d1..000000000 --- a/dist/index.test.d.ts.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"file":"index.test.d.ts","sourceRoot":"","sources":["../src/index.test.tsx"],"names":[],"mappings":""} \ No newline at end of file From 7dcf34f997ed7a0e89d96628de6b06c6acca0685 Mon Sep 17 00:00:00 2001 From: Alexandru Mic Date: Fri, 21 Aug 2020 16:54:24 +0300 Subject: [PATCH 16/17] fix README typo --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 449f0d70a..24fb212b9 100644 --- a/README.md +++ b/README.md @@ -219,7 +219,7 @@ FastImage.preload([ Get image path from cache by `source` ```js -FastImage.preload({ uri: 'https://facebook.github.io/react/img/logo_og.png' }) +FastImage.getCachePath({ uri: 'https://facebook.github.io/react/img/logo_og.png' }) ``` ## Troubleshooting From 78d132b7edc904e6114c05e24dc6201ce113fe12 Mon Sep 17 00:00:00 2001 From: Samin Shams Date: Thu, 19 Jan 2023 11:32:00 -0300 Subject: [PATCH 17/17] Update index.tsx --- src/index.tsx | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/index.tsx b/src/index.tsx index f88bb016b..c1e1f2576 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -254,8 +254,7 @@ FastImage.clearMemoryCache = () => FastImage.clearDiskCache = () => NativeModules.FastImageView.clearDiskCache() -FastImage.getCachePath = (source: Source) => - FastImageViewNativeModule.getCachePath(source) +FastImage.getCachePath = (source: Source) => NativeModules.FastImageView.getCachePath(source) const styles = StyleSheet.create({ imageContainer: {