文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

react如何实现图片选择

2023-07-05 00:38

关注

这篇文章主要讲解了“react如何实现图片选择”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“react如何实现图片选择”吧!

react实现图片选择的方法:1、使用import引入“react-native-image-picker”插件;2、使用“{this.setState({uploadImgs: urls})}}src={uploadImgs}/>”调用实现图片选择上传即可。

React Native七牛上传+本地图片选择

参考:

react-native-image-crop-picker图片选择并裁减 //这个看需求使用https://github.com/ivpusic/react-native-image-crop-pickerreact-native-image-picker图片选择https://github.com/react-native-image-picker/react-native-image-pickerreact-native-qiniuhttps://github.com/buhe/react-native-qiniu

我只要一个多图片上传功能,所以就写简单一点

效果

react如何实现图片选择

已上传状态

react如何实现图片选择

上传中状态

步骤

手机图片、视频选择功能

用react-native-image-picker插件

yarn add react-native-image-picker;ios需要pod install;

import {launchCamera, launchImageLibrary, ImageLibraryOptions, PhotoQuality} from 'react-native-image-picker';export async function chooseImage(options: {  count?: number,  quality?: PhotoQuality  sourceType?: 'camera',  //默认'album'} = {}) {  return new Promise<any>(async(resolve, reject) => {    const Opts: ImageLibraryOptions = {      mediaType: 'photo',      quality: options.quality || 1,      selectionLimit: options.count || 1    };    const result = options.sourceType == 'camera'?       await launchCamera(Opts) :       await launchImageLibrary(Opts);    resolve(result)  })}export async function chooseVideo(options: {  count?: number,  quality?: 'low' | 'high'  sourceType?: 'camera',  //默认'album'} = {}) {  return new Promise<any>(async(resolve, reject) => {    const Opts: ImageLibraryOptions = {      mediaType: 'video',      videoQuality: options.quality,      selectionLimit: options.count || 1    };    const result = options.sourceType == 'camera'?       await launchCamera(Opts) :       await launchImageLibrary(Opts);    resolve(result)  })}

七牛上传文件功能

class qiniuUpload {  private UP_HOST = 'http://upload.qiniu.com';  // private RS_HOST = 'http://rs.qbox.me';  // private RSF_HOST = 'http://rsf.qbox.me';  // private API_HOST = 'http://api.qiniu.com';  public upload = async(uri:string, key:string, token:string) => {    return new Promise<any>((resolve, reject) => {      let formData = new FormData();      formData.append('file', {uri: uri, type: 'application/octet-stream', name: key});      formData.append('key', key);      formData.append('token', token);          let options:any = {        body: formData,        method: 'post',      };      fetch(this.UP_HOST, options).then((response) => {        resolve(response)      }).catch(error => {        console.error(error)        resolve(null)      });      })  }   //...后面再加别的功能}const qiniu = new qiniuUpload();export default qiniu;import qiniu from '@/modules/qiniu/index'...    uploadFile: async (filePath: string) => {    const res = await createBaseClient('GET', '/v1/file')();  //这是接口请求方法,用来拿后端的七牛token、key        if( !res ) {      return res;    }    const { key, token } = res;    const fileSegments = filePath.split('.');    const fileKey = key + '.' + fileSegments[fileSegments.length - 1];    try {      const result = await qiniu.upload(filePath, fileKey, token)      if(result && result.ok) {        return {          url: ASSET_HOST + '/' + fileKey,  //ASSET_HOST是资源服务器域名前缀        };      }else {        return null      }    } catch (error) {      return null;    }  },...

多图上传组件封装

(这里Base、Image、ActionSheet都是封装过的,需看情况调整)

import React from 'react'import {  ViewStyle,  StyleProp,  ImageURISource,  ActivityIndicator} from 'react-native'import Base from '@/components/Base';import { Image, View, Text } from '@/components';   //Image封装过的,所以有些属性不一样import ActionSheet from "@/components/Feedback/ActionSheet";  //自己封装import styles from './styleCss';  //样式就不放上来了interface Props {  type?: 'video'  src?: string[]  count?: number  btnPath?: ImageURISource  style?: StyleProp<ViewStyle>  itemStyle?: StyleProp<ViewStyle>  itemWidth?: number  itemHeight?: number  //默认正方形  onChange?: (e) => void}interface State {  imageUploading: boolean  images: string[]}export default class Uploader extends Base<Props, State> {  public state: State = {    imageUploading: false,    images: []  };  public didMount() {    this.initSrc(this.props.src)  }  public componentWillReceiveProps(nextProps){    if(nextProps.hasOwnProperty('src') && !!nextProps.src){      this.initSrc(nextProps.src)    }  }    private initSrc = (srcProp:any) => {    if(!this.isEqual(srcProp, this.state.images)) {      this.setState({        images: srcProp      })    }  }    public render() {    const { style, btnPath, count, itemStyle, itemWidth, itemHeight, type } = this.props;    const { imageUploading, images } = this.state;    let countNumber = count? count: 1    return (      <React.Fragment>        <View style={[styles.uploaderBox, style]}>          {images.length > 0 && images.map((res, ind) => (            <View style={[styles.item, itemStyle]} key={res}>              <View style={styles.imgItem}>                <Image                  source={{uri: res}}                  width={this.itemW}                  height={this.itemH}                  onPress={() => {                    this.singleEditInd = ind;                    this.handleShowActionSheet()                  }}                />                <Text style={styles.del} onPress={this.handleDelete.bind(null, ind)}>删除</Text>              </View>            </View>          ))}          {images.length < countNumber  &&            <View style={[styles.item, itemStyle]}>               {imageUploading? (                <View style={[{                  width: this.itemW,                  height: this.itemH,                }, styles.loading]}>                  <ActivityIndicator size={this.itemW*0.4}></Loading>                  <Text style={{                    fontSize: 14,                    color: '#888',                    marginTop: 5                  }}>                    上传中...                  </Text>                </View>              ): (                <View style={styles.btn}>                  <Image                    source={btnPath || this.assets.uploadIcon}                    width={this.itemW}                    height={this.itemH}                    onPress={() => {                      this.singleEditInd = undefined;                      this.handleShowActionSheet()                    }}                  />                </View>              )}                          </View>          }                  </View>        <ActionSheet          name="uploaderActionSheet"          options={[{            name: type == 'video'? '拍摄': '拍照',            onClick: () => {              if(type == 'video') {                this.handleChooseVideo('camera')              }else if(this.singleEditInd !== undefined) {                this.handleChooseSingle('camera')              }else {                this.handleChooseImage('camera')              }            }          }, {            name: '相册',            onClick: () => {              if(type == 'video') {                this.handleChooseVideo()              }else if(this.singleEditInd !== undefined) {                this.handleChooseSingle()              }else {                this.handleChooseImage()              }            }          }]}        ></ActionSheet>      </React.Fragment>    );  }  private get itemW() {    return this.props.itemWidth || 92  }  private get itemH() {    return this.props.itemHeight || this.itemW;  }    private isEqual = (firstValue, secondValue) => {        if (Array.isArray(firstValue)) {      if (!Array.isArray(secondValue)) {        return false;      }      if(firstValue.length != secondValue.length) {        return false;      }      return firstValue.every((item, index) => {        return item === secondValue[index];      });    }    return firstValue === secondValue;  }  private handleShowActionSheet = () => {    this.feedback.showFeedback('uploaderActionSheet');  //这是显示ActionSheet选择弹窗。。。  }  private handleChooseImage = async (sourceType?: 'camera') => {    const { imageUploading, images } = this.state;    const { count } = this.props    if (imageUploading) {      return;    }    let countNumber = count? count: 1    const { assets } = await this.interface.chooseImage({  //上面封装的选择图片方法      count: countNumber,      sourceType: sourceType || undefined,    });        if(!assets) {      return;    }    this.setState({      imageUploading: true,    });        let request:any = []    assets.map(res => {      let req = this.apiClient.uploadFile(res.uri)   //上面封装的七牛上传方法      request.push(req)    })    Promise.all(request).then(res => {      let imgs:any = []      res.map((e:any) => {        if(e && e.url){          imgs.push(e.url)        }      })      imgs = [...images, ...imgs];      this.setState({        images: imgs.splice(0,countNumber),        imageUploading: false,      },        this.handleChange      );    })      }  private singleEditInd?: number;  //修改单个时的索引值  private handleChooseSingle = async(sourceType?: 'camera') => {    let { imageUploading, images } = this.state;    if (imageUploading) {      return;    }        const { assets } = await this.interface.chooseImage({   //上面封装的选择图片方法      count: 1,      sourceType: sourceType || undefined,    });    if(!assets) {      return;    }    this.setState({      imageUploading: true,    });    const res = await this.apiClient.uploadFile(assets[0].uri)   //上面封装的七牛上传方法    if(res && res.url && this.singleEditInd){      images[this.singleEditInd] = res.url    }    this.setState({      images: [...images],      imageUploading: false,    },      this.handleChange    );      }  private handleChooseVideo = async(sourceType?: 'camera') => {    const { onChange } = this.props    let { imageUploading } = this.state;    if (imageUploading) {      return;    }        const { assets } = await this.interface.chooseVideo({      sourceType: sourceType    });    if(!assets) {      return;    }    this.setState({      imageUploading: true,    });    const res = await this.apiClient.uploadFile(assets[0].uri)   //上面封装的七牛上传方法    if(res && res.url){      //视频就不在组件中展示了,父组件处理      if(onChange) {        onChange(res.url)      }    }    this.setState({      imageUploading: false,    });      }  private handleDelete = (ind:number) => {    let { images } = this.state    images.splice(ind,1)    this.setState({      images: [...images]    },      this.handleChange    )  }  private handleChange = () => {    const { onChange } = this.props    const { images } = this.state    if(onChange) {      onChange(images)    }  }}

最后调用

import Uploader from "@/components/Uploader";...          <Uploader            count={6}            onChange={urls => {              this.setState({                uploadImgs: urls              })            }}            src={uploadImgs}          />...

感谢各位的阅读,以上就是“react如何实现图片选择”的内容了,经过本文的学习后,相信大家对react如何实现图片选择这一问题有了更深刻的体会,具体使用情况还需要大家实践验证。这里是编程网,小编将为大家推送更多相关知识点的文章,欢迎关注!

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯