A superset of View
component that supports iOS, Android, and Web Native drag and drop feature.
iOS | iPadOS | Android |
---|---|---|
Web |
---|
- Ability to drag and drop images from other apps
- Support multi-selection
β For Bare RN projects, you need to have Expo Module installed.
You can install the package using the following command:
npx expo install expo-drag-drop-content-view
- Requires SDK >= 24 for Compatibility. It acts as a normal view on SDK < 24
- Android applies a highlight over the view when an image is being dragged, You can customize it using
highlightColor
andhighlightBorderRadius
- Remember to add
android.permission.READ_MEDIA_IMAGES
permission since you are accessing an image from disk - It only works in multi-window Reference
onDropStartEvent
andonDropEndEvent
events are yet to implement
import {
DragDropContentView,
DragDropContentViewProps,
OnDropEvent,
} from "expo-drag-drop-content-view";
import React, { useState, useEffect } from "react";
import {
Image,
StyleSheet,
View,
TouchableOpacity,
Text,
PermissionsAndroid,
Platform,
} from "react-native";
export const IDragDropContentView: React.FC<DragDropContentViewProps> = (
props
) => {
usePermission();
const [imageData, setImageData] = useState<OnDropEvent[] | null>(null);
const handleClear = () => setImageData(null);
return (
<DragDropContentView
{...props}
onDropEvent={(event) => {
setImageData(event.assets);
}}
highlightColor="#2f95dc"
highlightBorderRadius={20}
style={[styles.container, props.style]}
>
{imageData ? (
imageData.map(({ uri }, index) => {
const rotation = Math.ceil(index / 2) * 5;
const direction = index % 2 === 0 ? 1 : -1;
const rotate = `${rotation * direction}deg`;
return (
<TouchableOpacity
key={uri}
onPress={handleClear}
style={[styles.imageContainer, { transform: [{ rotate }] }]}
>
<Image source={{ uri }} style={styles.image} v />
</TouchableOpacity>
);
})
) : (
<View style={styles.placeholderContainer}>
<Text style={styles.placeholderText}>Drop any image here!</Text>
</View>
)}
</DragDropContentView>
);
};
const usePermission = () => {
useEffect(() => {
const fn = async () => {
try {
await PermissionsAndroid.request(
"android.permission.READ_MEDIA_IMAGES"
);
} catch (_) {}
};
if (Platform.OS === "android") fn();
}, []);
};
const styles = StyleSheet.create({
container: {
width: "100%",
height: "100%",
backgroundColor: "#fefefe",
borderRadius: 20,
overflow: "visible",
justifyContent: "center",
alignItems: "center",
borderWidth: 3,
borderStyle: "dashed",
borderColor: "#2f95dc",
},
imageContainer: {
position: "absolute",
width: "100%",
height: "100%",
borderRadius: 20,
overflow: "hidden",
},
image: {
width: "100%",
height: "100%",
},
placeholderContainer: {
paddingHorizontal: 30,
backgroundColor: "#2f95dc",
opacity: 0.5,
height: "100%",
width: "100%",
justifyContent: "center",
alignItems: "center",
borderRadius: 20,
},
placeholderText: {
color: "white",
textAlign: "center",
},
});
DragDropContentView
supports all View
Props. Other Props:
Option | iOS | Android | Web | Description |
---|---|---|---|---|
onDropEvent | βοΈ | βοΈ | βοΈ | A callback that returns an array of assets. Refer to Asset Object |
onDropStartEvent | βοΈ | β | βοΈ | A callback that is called when any image is being dragged over |
onDropEndEvent | βοΈ | β | βοΈ | A callback that is called when any image is dragged out of the view's boundary or released |
includeBase64 | βοΈ | βοΈ | β | If true , creates a base64 string of the image (Avoid using on large image files due to performance). It is always true on Web since it is the only available source |
highlightColor | β | βοΈ | β | The background color of overlay that covers the view while content is being dragged Android Doc |
highlightBorderRadius | β | βοΈ | β | The border-radius of overlay that covers the view while content is being dragged Android Doc |
key | iOS | Android | Web | Description |
---|---|---|---|---|
base64 | βοΈ | βοΈ | βοΈ | The base64 string of the image (Optional on Android and iOS, but Required on Web) |
uri | βοΈ | βοΈ | β | The file uri in app-specific cache storage. |
path | βοΈ | βοΈ | β | The original file path. |
width | βοΈ | βοΈ | βοΈ | Asset dimensions |
height | βοΈ | βοΈ | βοΈ | Asset dimensions |
type | βοΈ | βοΈ | βοΈ | The file mime type |
fileName | βοΈ | βοΈ | βοΈ | The file name |
- iOS support
- Android support
- Allowing
children
to be touchable - Web support
- MacOS support
- Adding Drag support
- Dragging texts and videos support
β€οΈ Special thanks to Ali Nabavi for helping to add Android support.
MIT