Skip to content

Instantly share code, notes, and snippets.

@woodpav
Last active November 28, 2023 18:42
Show Gist options
  • Save woodpav/1707e59feff35502ab9801bf84447c16 to your computer and use it in GitHub Desktop.
Save woodpav/1707e59feff35502ab9801bf84447c16 to your computer and use it in GitHub Desktop.
import React, { useState, useEffect } from 'react';
import PropTypes from 'prop-types';
import { Image, StyleSheet, Dimensions } from 'react-native';
import FastImage from 'react-native-fast-image';
import ImageZoom from 'react-native-image-pan-zoom';
// ZoomableImage component renders a zoomable FastImage the size of the screen dimensions.
const dims = Dimensions.get('window');
const styles = StyleSheet.create({
container: {
width: dims.width,
height: dims.height,
},
image: {
...StyleSheet.absoluteFillObject,
},
});
function useImageSize(uri) {
const [imageSize, setImageSize] = useState({ width: null, height: null });
useEffect(() => {
Image.getSize(uri, (width, height) => {
// use aspect ratio to set the size of the image relative to react-native pixels.
setImageSize({ width: dims.width, height: height / width * dims.width });
});
}, []);
return imageSize;
}
function ZoomableImage({ style, source: { uri } }) {
const imageSize = useImageSize(uri);
if (imageSize.width != null) {
return (
<ImageZoom
style={[styles.container, style]}
cropWidth={dims.width}
cropHeight={dims.height}
imageWidth={imageSize.width}
imageHeight={imageSize.height}
>
<FastImage
style={styles.image}
source={{ uri }}
resizeMode={FastImage.resizeMode.cover}
/>
</ImageZoom>
);
}
return null;
}
ZoomableImage.propTypes = {
style: PropTypes.oneOfType([PropTypes.number, PropTypes.object]),
source: PropTypes.shape({ uri: PropTypes.string.isRequired }).isRequired,
};
ZoomableImage.defaultProps = {
style: null,
};
export default ZoomableImage;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment