react-native-sortable-listview
react-native-sortable-listview copied to clipboard
onPress vs. on Long Press?
Silly question is it possible to detect press/tap on a row before the long press trigger? To make the row clickable? Maybe Im missing something super simple?
Hey @barrylachapelle, were you able to figure it out? Thanks!
@fnfilho yes I did. If you nest another component inside the row and have a TouchableHighlight in it... the TouchableHighlight can handle onPress inside the Rows long press. Does that make sense?
Example... checkout RowComponent below...
import React from 'react';
import { StyleSheet, View, TouchableHighlight, Image, Dimensions, Text, Button, ActivityIndicator } from 'react-native';
import firebase from 'firebase';
import SortableListView from 'react-native-sortable-listview';
import { Ionicons } from '@expo/vector-icons';
class RowComponent extends React.Component {
render() {
const window = Dimensions.get('window');
return (
<TouchableHighlight
underlayColor={'#eee'}
onPress={() => this.props.gotoEditPhoto({
photoName: this.props.data.photoName,
photoId: this.props.data.photoId,
photoUrl: this.props.data.photoUrl,
})}
style={{
padding: 16,
backgroundColor: 'white',
borderBottomWidth: 1,
borderColor: '#eee',
width: window.width,
}}
{...this.props.sortHandlers}>
<View style={styles.rowData}>
<View style={styles.photoHolder}>
<Image
style={{ borderRadius: 6, width: 64, height: 64 }}
source={{ uri: this.props.data.photoUrl }} />
</View>
<View style={styles.nameHolder}>
<Text>{this.props.data.photoName}</Text>
</View>
<View style={styles.photoRowIcon}>
<Ionicons name="md-arrow-dropright" size={24} color="#CCCCCC" />
</View>
</View>
</TouchableHighlight>
)
}
}
let tmpImages = {};
let order;
export default class OrganizePhotos extends React.Component {
constructor(props) {
super(props);
this.state = {
loading: false,
photoData: {},
};
order = Object.keys(this.state.photoData)
this.getPhotos = this.getPhotos.bind(this);
}
static navigationOptions = ({ navigation }) => {
const params = navigation.state.params || {};
return {
title: 'Drag to Order',
headerStyle: {
backgroundColor: '#26AE60',
},
headerBackTitle: null,
headerTintColor: '#fff',
headerTitleStyle: {
fontWeight: 'bold',
},
headerRight: (
<Button
onPress={() => params.saveOrder()}
title="Save"
color="#fff"
/>
),
}
};
getPhotos = () => {
tmpImages = {};
tmpImages = this.state.photoData;
let bookRef = firebase.database().ref('users/' + this.props.navigation.getParam('uid') + '/books/' + this.props.navigation.getParam('bookId') + '/_photos');
bookRef.orderByChild('order').on('value', (snapshot) => {
let data = snapshot.val();
if (data !== null) {
snapshot.forEach(function (childSnapshot) {
let photoId = childSnapshot.key;
let childdata = childSnapshot.val();
let photoCreated = childdata.created;
//let photoOrder= childdata.order;
let photoName = childdata.name;
let photoUrl = childdata.image_thumb;
tmpImages[photoId] = {
'photoId': photoId,
'photoCreated': photoCreated,
'photoName': photoName,
'photoUrl': photoUrl,
}
});
}
this.setState({
photoData: tmpImages
});
order = Object.keys(this.state.photoData);
})
}
saveOrder = () => {
this.sortPhotos(order);
}
sortPhotos = (order) => {
this.setState({
loading: true,
});
var photosRef = firebase.database().ref('users/' + this.props.navigation.getParam('uid') + '/books/' + this.props.navigation.getParam('bookId') + '/_photos/');
photosRef.once('value', function (snapshot) {
if (this.isUnmounted) {
return;
}
snapshot.forEach(function (childSnapshot) {
let photoKey = childSnapshot.key;
let orderToWrite = order.indexOf(photoKey);
photosRef.child(photoKey).update({
order: orderToWrite,
});
});
})
.then(() => {
this.setState({
loading: false,
});
//update and go to viewbook
this.props.navigation.state.params.refreshPhotos();
this.props.navigation.goBack();
});
}
gotoEditPhoto = (data) => {
this.props.navigation.navigate('EditPhoto',{
photoName: data.photoName,
photoId: data.photoId,
photoUrl: data.photoUrl,
uid: this.props.navigation.getParam('uid'),
bookId: this.props.navigation.getParam('bookId'),
refreshPhotos: this.getPhotos,
});
}
componentDidMount = () => {
this.getPhotos();
this.props.navigation.setParams({ saveOrder: this.saveOrder });
}
componentWillUnmount() {
this.isMounted = true;
}
render() {
return (
<View style={styles.container}>
<SortableListView
style={styles.sortable}
data={this.state.photoData}
activeOpacity={0.8}
sortRowStyle={styles.rowDrag}
onRowMoved={e => {
order.splice(e.to, 0, order.splice(e.from, 1)[0]);
this.forceUpdate()
}}
order={order}
renderRow={row => <RowComponent data={row} gotoEditPhoto={(data) => this.gotoEditPhoto(data)} />}/>
{this.state.loading &&
<View style={styles.loadingAnimation}><ActivityIndicator size="small" /></View>
}
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#F5F5F5',
alignItems: 'center',
justifyContent: 'center',
},
inputStyle: {
fontSize: 16,
backgroundColor: 'white',
width: '80%',
height: 56,
borderRadius: 6,
marginBottom: 16,
paddingLeft: 16,
},
inputMultiLineStyle: {
fontSize: 16,
backgroundColor: 'white',
width: '80%',
height: 166,
borderRadius: 6,
marginBottom: 16,
paddingLeft: 16,
paddingTop: 16,
},
sortable: {
//backgroundColor: 'green',
},
rowDrag: {
transform: [{ rotate: '3deg' }],
shadowColor: '#000000',
shadowOffset: {
width: 2,
height: 2
},
shadowRadius: 4,
shadowOpacity: 0.0,
},
rowData: {
flexDirection: 'row',
},
photoHolder:{
justifyContent: 'flex-start',
width: 64,
height: 64,
},
nameHolder: {
justifyContent: 'center',
alignItems: 'flex-start',
flex: 1,
height: 64,
paddingLeft: 24,
},
photoRowIcon: {
justifyContent: 'center',
alignItems: 'flex-end',
height: 64,
}
});