1.废话少说,先上效果。
2.效果实现思路
横向的listView+viewPager(android很好实现,react-native也差不多)
3.贴源码
扫描二维码关注公众号,回复:
1483645 查看本文章
用法:
大图浏览的控件代码:
import React, {Component} from 'react'; import { BackAndroid, View, Platform, } from 'react-native'; var data =[]; var currentPosition =0; import ImageViewer from 'react-native-image-zoom-viewer'; var images = []; export default class GalleryView extends Component { constructor(props) { super(props); images =[]; data =this.props.data; currentPosition=this.props.p var count = data.length; if(count>9){ count = 9; } for(var i=0 ;i<count;i++){ var imageInfo = data[i]; var urlobject=new Object; urlobject.url = imageInfo['path']; if( imageInfo['width'] !=null && imageInfo['width'] != '' ){ urlobject.width = imageInfo['width']; } if( imageInfo['height'] !=null && imageInfo['height'] != '' ){ urlobject.height = imageInfo['height']; } images.push(urlobject); } this.state={ dataSourse:images } } componentDidMount(){ if (Platform.OS === 'android') { BackAndroid.addEventListener('hardwareBackPress', this.onBackAndroid); } } componentWillUnmount() { if (Platform.OS === 'android') { BackAndroid.removeEventListener('hardwareBackPress', this.onBackAndroid); } } onBackAndroid = () => { this.props.navigator.pop(); return true; } render() { return ( <ImageViewer imageUrls={this.state.dataSourse} index={currentPosition} saveToLocalByLongPress={false} onClick ={()=> { this.props.nav.pop(); }}/> ); } }
横向滑动控件代码:
import React, { Component } from 'react'; import { Text, View, Image, BackAndroid, TouchableHighlight, ScrollView, Platform } from 'react-native'; import ImagePicker from 'react-native-image-crop-picker'; import GalleryView from './GalleryView.js'; //导入json数据 var Dimensions = require('Dimensions'); //定义全局的一些变量 var {width} = Dimensions.get('window'); var cols = 3; var hMargin = 10; //默认水平距离 var vMargin = 10; //默认垂直距离 var marginLeft = 0; var marginTop = 0; var marginRight =0; var marginBottom =0; var itemWidth = (width-(cols+1)*hMargin-marginRight- marginLeft)/cols; var itemHeight = itemWidth var boxW = 100; var boxH =100; var isBack =false; var currentPosition =0; export default class CustomScrollImageView extends Component { static defaultProps = { showAddImageButton:true }; state:{ 'showAddImageButton':boolean, 'dataList':object, 'showBigView':boolean, 'showDefault':boolean } constructor(props) { super(props); //事件绑定 // (this:any).showBigView = this.showBigView.bind(this); if(this.props.hMargin != null){ hMargin = this.props.hMargin; //默认水平距离 } if(this.props.vMargin != null){ vMargin =this.props.vMargin; //默认垂直距离 } if(this.props.marginLeft != null){ marginLeft =this.props.marginLeft; } if(this.props.marginTop != null){ marginTop =this.props.marginTop; } if(this.props.marginRight != null){ marginRight =this.props.marginRight; } if(this.props.marginBottom != null){ marginBottom =this.props.marginBottom; } itemWidth = (width-(cols+1)*hMargin-marginRight- marginLeft)/cols; itemHeight = (itemWidth) this.state={ showAddImageButton:this.props.showAddImageButton, dataList:this.props.dataSourse, showBigView:false, showDefault:true }; } render() { return ( <ScrollView automaticallyAdjustContentInsets={false} bounces ={false} showsHorizontalScrollIndicator ={false} ref={(scrollView) => { this._scrollView = scrollView; }} horizontal={true}> { this.renderAllBadge() } </ScrollView> ); } showBigView(postion) { isBack =true; currentPosition = postion; this.setState({showBigView: true}); } addImageDialog(){ this.props.onAddImage(); } deleteImage(postion){ this.props.deleteImage(postion); } renderAllBadge(){ //定义数组所有的子组件 var allBadge = []; let dataSourse =this.props.dataSourse; let maxLength = this.props.maxLength ? this.props.maxLength : 9; //遍历json数据 //如果没有数据只是显示添加的按钮 if(dataSourse.length == 0){ if(this.state.showAddImageButton){ allBadge.push(this.getImageAddViewItem(0)) } }else if(dataSourse.length >= maxLength){ let count = dataSourse.length ; if(count > maxLength){ count = maxLength; } for(var i=0 ;i<count;i++){ var model = dataSourse[i]; //直接装入数组 allBadge.push( this.getImageViewItem(model,i) ); } }else{ for(var i=0 ;i<dataSourse.length;i++){ var model = dataSourse[i]; //直接装入数组 allBadge.push( this.getImageViewItem(model,i) ); } if(this.state.showAddImageButton){ allBadge.push(this.getImageAddViewItem(dataSourse.length)); } } return allBadge; } getImageAddViewItem(postion){ return( <TouchableHighlight key={postion} onPress={this.addImageDialog.bind(this)} style={{ alignItems:'center',width:itemWidth,height:itemHeight,marginLeft:hMargin,marginBottom:hMargin}}> <View style={{backgroundColor:'#FFFFFF',borderWidth:1,borderColor:'#E8E8E8',width:itemWidth,height:itemHeight,justifyContent: 'center',alignItems:'center'}}> <Image style={{width:35,height:35}} source={require('./../images/add_release_pass.png')}/> <Text >选择图片</Text> </View> </TouchableHighlight> ); } setLoadingImage = (postion) =>{ if(Platform.OS === 'android'){ let dataSourse =this.props.dataSourse; if(postion == (dataSourse.length-1) && this.state.showDefault){ this.setState({ showDefault:false }); } } } getImageViewItem(imageUrl,postion){ var deleteItem = this.props.deleteImage!= null? <TouchableHighlight onPress={() => { this.deleteImage(postion); }} style={{width:itemWidth/5,height:itemWidth/5 ,position:'absolute' ,top:0,right:0}}> <Image source={ require('./../images/image_delete.png')} style={{width:itemWidth/5,height:itemWidth/5 }}/> </TouchableHighlight> :null; var imagePath = require('./../images/default_image.png'); var path = imageUrl['path']; if(Platform.OS === 'android'){ if(!this.state.showDefault){ if(this.isURL(path)){ imagePath ={uri:path}; }else { imagePath =require('./../images/default_image.png'); } } }else{ imagePath ={uri:path}; } return( <View key={postion} style={{width:itemWidth,height:itemHeight,marginLeft:(postion ===0?0:hMargin),marginBottom:hMargin}}> <TouchableHighlight onPress={() => { this.getGalleryView(postion); }} style={{alignItems:'center',width:itemWidth,height:itemHeight}}> <View > <Image defaultSource={require('./../images/default_image.png')} style={{width:itemWidth,height:itemHeight}} source={imagePath} onLoadStart ={this.setLoadingImage.bind(this,postion)}/> </View> </TouchableHighlight> {deleteItem} </View> ); } isURL(str_url) {// 验证url if(str_url != '' && str_url != null){ return true; } return false; } isLocalUrl(filepath){ var extStart=filepath.lastIndexOf('.'); var ext=filepath.substring(extStart,filepath.length).toUpperCase(); if(ext!=".BMP"&&ext!=".PNG"&&ext!=".GIF"&&ext!=".JPG"&&ext!=".JPEG"){ return false; } return true; } getGalleryView(postion){ currentPosition = postion; const { navigator } = this.props; let _this = this; let scenes = { component: GalleryView, passProps: { p:currentPosition, data: _this.props.dataSourse, nav:navigator } }; navigator.push(scenes); } }