微信小程序开发之多图片上传+.NET WebAPI后端服务保存图片资源

devtools/2025/1/16 5:56:23/

前言:

  最近开发的一个小程序>微信小程序项目需要做一个同时选中三张(或者是多张)图片一起上传到服务端,服务端保存图片资源并保存的功能。发现在小程序>微信小程序开发中会有很多场景会使用到多图片上传并保存到的功能,所以我把自己总结的一些方法和完整示例写了下来希望能够帮到有需要的同学。

使用技术:

  在这章中将会使用到小程序>微信小程序wx.uploadFile(Object object) 和wx.chooseImage(Object object)接口,对图片大小和来源进行上传,后端则使用的.NET WebAPI来接收图片资源文件并保存。

wx.chooseImage() 概述:

  从本地相册选择图片或使用相机拍照,详细了解请阅读小程序>微信小程序开发文档(wx.chooseImage(Object object) | 微信开放文档)

参数:

属性类型默认值必填说明
countnumber9最多可以选择的图片张数
sizeTypeArray.<string>['original', 'compressed']所选的图片的尺寸
sourceTypeArray.<string>['album', 'camera']选择图片的来源
successfunction接口调用成功的回调函数
failfunction接口调用失败的回调函数
completefunction接口调用结束的回调函数(调用成功、失败都会执行)

wx.uploadFile()概述:

  将本地资源上传到服务器。客户端发起一个 HTTPS POST 请求,其中 content-type 为 multipart/form-data,详细了解请阅读小程序>微信小程序开发文档(UploadTask | 微信开放文档)。

参数:

属性类型默认值必填说明
urlstring开发者服务器地址
filePathstring要上传文件资源的路径
namestring文件对应的 key,开发者在服务端可以通过这个 key 获取文件的二进制内容
headerObjectHTTP 请求 Header,Header 中不能设置 Referer
formDataObjectHTTP 请求中其他额外的 form data
successfunction接口调用成功的回调函数
failfunction接口调用失败的回调函数
completefunction接口调用结束的回调函数(调用成功、失败都会执行)

废话不多说,上代码:

小程序页面代码:

<view class='form-s2'>
<view>门店照片(请选择三张)</view>
<view>
<view class="weui-uploader__files" id="uploaderFiles">
<block wx:for="{{files}}" wx:key="*this">
<view class="weui-uploader__file" bindtap="previewImage" id="{{item}}" style='margin-top:11px;'>
<image class="weui-uploader__img" src="{{item}}" mode="aspectFill" />
</view>
</block>
</view>
<view class="weui-uploader__input-box" style='top:11px;'>
<view class="weui-uploader__input" bindtap="chooseImage"></view>
</view>
</view>
</view>

小程序Js代码:

Page({/*** 页面的初始数据*/
data:
{files: [], //门店图片信息,数组图片保存作为数据源
},
,/*** 多图片上传*/
chooseImage: function(e) {
var that = this;
if (that.data.files.length > 2) {resource.notishi("抱歉最多只允许上传三张图片哟~");return false;
}wx.chooseImage({
count: 3, //默认9张,这里设置三张
sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图,默认二者都有
sourceType: ['album', 'camera'], // 可以指定来源是相册还是相机,默认二者都有
success: function(res) {
wx.showLoading({
title: '上传中,请稍等...',
})
// 返回选定照片的本地文件路径列表,tempFilePath可以作为img标签的src属性显示图片
var tempFilePaths = res.tempFilePaths;//多图片上传,tempFilePaths本地图片地址为一个数组,遍历调用服务器图片上传接口即可实现多图保存
for (var i = 0; i < tempFilePaths.length; i++) {
console.log('图片地址名称' + tempFilePaths[i]);
wx.uploadFile({url: app.globalData.hostUrl + "/api/PictureUpload/Upload", //此处为实际接口地址
filePath: tempFilePaths[i], //获取图片路径
header: {
'content-type': 'multipart/form-data'
},name: 'upload',
success: function(res) {
wx.hideLoading();
let Result = JSON.parse(res.data);
console.log(Result);//接收返回来的服务器图片地址
if (Result.code == 1) {
let picurl = app.globalData.hostUrl + Result.picturePath;
console.log(picurl);that.setData({
files: that.data.files.concat(picurl)
});
} else {resource.notishi("网络异常,请稍后再试");
}
},
fail: function(res) {
wx.hideLoading()
wx.showToast({
title: '上传失败,请重新上传',
icon: 'none',
duration: 2000
})
},
})
}
}
})
},//图片预览
previewImage: function(e) {
wx.previewImage({
current: e.currentTarget.id, // 当前显示图片的http链接
urls: this.data.files // 需要预览的图片http链接列表
})},
})

.NET WebAPI接口服务接收图片资源并保存: 

后端使用MultipartMemoryStreamProvider来上传文件,详情如下所示:

using System;
using System.IO;
using System.Net.Http;
using System.Threading.Tasks;
using System.Web.Hosting;
using System.Web.Http;namespace ShopSite.Controllers
{public class FileUploadController : ApiController{/// <summary>/// 图片上传保存/// </summary>/// <returns></returns>[HttpPost]public IHttpActionResult PictureUpload(){try{var picturePath = "";const string fileTypes = "gif,jpg,jpeg,png,bmp";//运行上传的图片文件格式var content = Request.Content;//获取或设置 HTTP 消息的内容(当需要获取HTTP信息是会使用到)const string tempUploadFiles = "/UploadFile/"; //保存路径var newFilePath = DateTime.Now.ToString("yyyy-MM-dd") + "/";var memoryStreamProvider = new MultipartMemoryStreamProvider();//获取图片文件流信息Task.Run(async () => await Request.Content.ReadAsMultipartAsync(memoryStreamProvider)).Wait();foreach (var item in memoryStreamProvider.Contents){if (item.Headers.ContentDisposition.FileName == null) continue;var filename = item.Headers.ContentDisposition.FileName.Replace("\"", "");var file = new FileInfo(filename);//upload fail(判断是否是运行上传的图片格式)if (Array.IndexOf(fileTypes.Split(','), file.Extension.Substring(1).ToLower()) == -1){return Json(new { code =0,picturePath ="", msg = "不支持上传文件类型" });}//获取后缀var extension = Path.GetExtension(filename);var newFileName = Guid.NewGuid().ToString()+extension;//重命名if (!Directory.Exists(HostingEnvironment.MapPath("/") + tempUploadFiles + newFilePath)){Directory.CreateDirectory(HostingEnvironment.MapPath("/") + tempUploadFiles + newFilePath);}var filePath = Path.Combine(HostingEnvironment.MapPath("/") + tempUploadFiles + newFilePath, newFileName);picturePath=Path.Combine(tempUploadFiles + newFilePath, newFileName);//图片相对路径var result = item.ReadAsStreamAsync().Result;using (var br = new BinaryReader(result)){var data = br.ReadBytes((int)result.Length);File.WriteAllBytes(filePath, data);//保存图片}}//save successfullyreturn Json(new { code = 1, picturePath = picturePath,msg = "图片上传成功~" });}catch (Exception ex){return Json(new { code =0, msg = ex.Message });}}}
}

效果图展示(美女哟,嘻嘻):


http://www.ppmy.cn/devtools/10845.html

相关文章

【面试八股总结】排序算法(二)

参考资料 &#xff1a;阿秀 一、堆排序 堆排序基本思想是先把数组构造成一个大顶堆(父亲节点大于其子节点)&#xff0c;然后把堆顶(数组最大值&#xff0c;数组第一个元素)和数组最后一个元素交换&#xff0c;这样就把最大值放到了数组最后边。把数组长度n-1,再进行构造堆把剩…

揭秘Spring Boot中@Transactional注解失效的七大坑点与修复之道

今天咱们来聊聊SpringBoot中的一个超级重要的新人容易踩的坑&#xff1a; SpringBoot中事务失效的那些坑&#xff01; 在Java开发的世界里&#xff0c;SpringBoot因为它的便捷和强大已经成为了众多开发者的首选。 但是&#xff0c;即使在这么棒的框架下&#xff0c;事务处理也…

Midjourney 中文文档

快速使用 学习如何在Discord上使用Midjourney Bot从简单的文本提示中创建自定义图像。 行为准则 不要表现出不良行为。不要使用我们的工具制作可能引起煽动&#xff0c;不安或引起争议的图像。这包括血腥和成人内容。尊重其他人和团队。 1&#xff1a;加入Discord 访问Midj…

【行为型模式】备忘录模式

一、备忘录模式概述 备忘录模式定义&#xff1a;又称之为快照模式(Snapshop Pattern)或者令牌模式(Token Pattern)&#xff0c;是指在不破坏封装的前提下&#xff0c;捕获一个对象的内部状态&#xff0c;并在对象之外保存这个状态&#xff0c;这样我们就可以在需要的时候将该对…

什么是 XSS 攻击?

概念: XSS 攻击指的是跨站脚本攻击,是一种代码注入攻击。攻击者通过在网站注入恶意脚本,使之在用户的浏览器上运行,从而盗取用户的信息如 cookie 等。 XSS 的本质是因为网站没有对恶意代码进行过滤,与正常的代码混合在一起了,浏览器没有办法分辨哪些脚本是可信的,从而…

密码学 | Schnorr 协议:零知识身份证明和数字签名

&#x1f955;原文&#xff1a; Schnorr 协议&#xff1a;零知识身份证明和数字签名 &#x1f955;写在前面&#xff1a; 本文属搬运博客&#xff0c;自己留存学习。文中的小写字母表示标量&#xff0c;大写字母表示椭圆曲线中的点。 1 Schnorr 简介 Schnorr 由德国数学家和密…

【热门话题】常用经典目标检测算法概述

&#x1f308;个人主页: 鑫宝Code &#x1f525;热门专栏: 闲话杂谈&#xff5c; 炫酷HTML | JavaScript基础 ​&#x1f4ab;个人格言: "如无必要&#xff0c;勿增实体" 文章目录 常用经典目标检测算法概述1. 滑动窗口与特征提取2. Region-based方法R-CNN系列M…

C++ vector容器的swap方法(容器互换)

swap方法可以交换两容器的内容。 int main() {vector<int> v1;v1.push_back(10);v1.push_back(20);vector<int> v2;v2.push_back(30);//printVector是自己编写用于遍历输出vector容器的函数printVector(v1);printVector(v2);v1.swap(v2);printVector(v1);printVec…