UNPKG

react-native-fast-image

Version:

🚩 FastImage, performant React Native image component.

138 lines (121 loc) • 3.79 kB
import _extends from '@babel/runtime/helpers/extends'; import React, { forwardRef, memo } from 'react'; import { NativeModules, StyleSheet, requireNativeComponent, Image, View, Platform } from 'react-native'; 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' }; const resolveDefaultSource = defaultSource => { if (!defaultSource) { return null; } if (Platform.OS === 'android') { // Android receives a URI string, and resolves into a Drawable using RN's methods. const resolved = Image.resolveAssetSource(defaultSource); if (resolved) { return resolved.uri; } return null; } // iOS or other number mapped assets // In iOS the number is passed, and bridged automatically into a UIImage return defaultSource; }; function FastImageBase({ source, defaultSource, 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, { tintColor }], source: resolvedSource, defaultSource: defaultSource, onLoadStart: onLoadStart, onProgress: onProgress, onLoad: onLoad, onError: onError, onLoadEnd: onLoadEnd, resizeMode: resizeMode })), children); } const resolvedSource = Image.resolveAssetSource(source); const resolvedDefaultSource = resolveDefaultSource(defaultSource); return /*#__PURE__*/React.createElement(View, { style: [styles.imageContainer, style], ref: forwardedRef }, /*#__PURE__*/React.createElement(FastImageView, _extends({}, props, { tintColor: tintColor, style: StyleSheet.absoluteFill, source: resolvedSource, defaultSource: resolvedDefaultSource, 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 => NativeModules.FastImageView.preload(sources); FastImage.clearMemoryCache = () => NativeModules.FastImageView.clearMemoryCache(); FastImage.clearDiskCache = () => NativeModules.FastImageView.clearDiskCache(); 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;