Here's the current code:To render the image:
<CachedImage source={{ uri: item.image }} style={withStyle.leftChildImage} onDownloaded={(uri: string) => DbHelper.newImage(uri, true)} />
Cached Image component:
import React, { Component } from 'react';import { Image, ImageBackground } from 'react-native';import * as FileSystem from 'expo-file-system';import * as Crypto from 'expo-crypto';// https://www.npmjs.com/package/react-native-expo-cached-imageexport default class CachedImage extends Component {state = {imgURI: '',}async componentDidMount() { const filesystemURI = await this.getImageFilesystemKey(this.props.source.uri); await this.loadImage(filesystemURI, this.props.source.uri);}async componentDidUpdate(prevProps) { if (this.props.source.uri === prevProps.source.uri) { return;} const filesystemURI = await this.getImageFilesystemKey(this.props.source.uri); await this.loadImage(filesystemURI, this.props.source.uri);}async getImageFilesystemKey(remoteURI: string | null) { if (null == remoteURI) { return undefined; } const hashed = await Crypto.digestStringAsync( Crypto.CryptoDigestAlgorithm.SHA256, remoteURI ); return `${FileSystem.cacheDirectory}${hashed}`;}async loadImage(filesystemURI: string | undefined, remoteURI: string) { if (!filesystemURI) { return; } try { const metadata = await FileSystem.getInfoAsync(filesystemURI); if (metadata.exists) { this.setState({ imgURI: filesystemURI }); return; } const imageObject = await FileSystem.downloadAsync( remoteURI, filesystemURI ); this.setState({ imgURI: imageObject.uri }); this.props.onDownloaded(imageObject.uri); } catch (err) { // console.log('Image loading error:', err); this.setState({imgURI: remoteURI}); }}render() { var placeholder = require('../assets/images/icon.png'); if (this.props.isBackground) { return (<ImageBackground {...this.props} source={this.state.imgURI ? {uri: this.state.imgURI} : placeholder}> {this.props.children}</ImageBackground>); } else { return (<Image {...this.props} source={this.state.imgURI ? {uri: this.state.imgURI} : placeholder} /> ); }}
}
Now the cached image component is being rendered, of course on another screen inside a flatlist. What if I want the user to be able to open a zoomable image on the screen on tapping on the image?Note: As the image is part of a card, the max dimensions are already set and just increasing the width and height on press just crops it, does not make it large.