過程分析
圖片上傳主要分成三部分:
一、本地表單處理
- 1、表單美化
- 2、獲取上傳文件信息(選擇、拖拽、一張、多張)
- 3、圖片信息校驗(格式、大小)
- 4、本地展示
二、調用接口獲取上傳需要的參數
- 1、引入cos-js-sdk-v5(jquery、axios如果必要)
- 2、ajax\jsonp,獲取bucket\region\appid參數
三、上傳圖片
- 1、創建cos實例
- 2、上傳,上傳成功后清空表單,進度監控(如果必要)
- 3、將獲取的圖片url上傳到數據庫,其他處理,放大效果等
本地上傳控件處理
表單美化
上傳控件一般需要美化,比如可以用label標簽,顯示樣式,把input標簽做透明處理,寬高設置為0,outline:none,接着就可以隨心所欲的美化了。
<div>
<label for="file" class="demo">上傳</label><input class="selImg" type="file" id="file" onchange="handleFiles(this.files)" multiple="multiple" >
<!--如果需要顯示本地圖片-->
<!-- <img id="showImg" src="" alt=""> -->
</div>
<style>
input{outline:none;background:transparent;width:0;height:0;}
.demo{border:1px solid #999;background:#999;color:#fff;border-radius:5px;display:block;width:100px;height:30px;text-align: center;line-height: 30px;}
</style>
獲取上傳文件信息
這里我們處理選擇圖片,兼容一張和多張
// 選擇圖片
function handleFiles (files) {
console.info(files)//打印出來信息見圖1
checkPic(files);
}
// 拖拽圖片
function handleFiles1 (files) {
console.info(files)
checkPic(files);
}
// 獲取到圖片的名稱、大小、圖片格式等
圖一:
圖片信息校驗
function checkPic (files) {
var fileList = [];
// 如果只需要單張上傳,去掉multiple="multiple",直接獲取數組第1個元素即可file = files[0];
// 如果是允許多張上傳,將上傳的圖片放入數組中,循環數組
if (files.length === 0) {
return
} else {
for(var i=0; i<files.length; i++){
fileList.push(files[i]);
}
}
//循環待上傳的圖片
fileList.forEach((item) => {
// 1 校驗上傳圖片格式
if(!/\.(jpg|jpeg|png|JPG|PNG)$/.test(item.name)){
alert('僅支持png,jpeg,jpg格式圖片');
return
}
//校驗上傳圖片大小
var size = item.size/1024;
if(size>5000){
alert('圖片最大不能超過5M');
return
}
// 上傳
// upload(obj,item)
})
}
本地展示
function showImg (file) {
var imgURL = '';
try{
imgURL = file.getAsDataURL();
}catch(e){
imgRUL = window.URL.createObjectURL(file);
}
return imgRUL;
}
調用接口獲取上傳需要的參數
引入cos-js-sdk-v5
npm i cos-js-sdk-v5 或
<script src="cos-js-sdk-v5.js"></script>
獲取bucket\region\appid參數
這些參數是從騰訊雲配置存儲桶時,帶有的。調試的時可放在前端,部署時需要放在后端。
一般騰訊雲存儲都需要用到跨域,這里可以在騰訊雲配置允許訪問的域名。
后台現在使用的時jsonp請求接口。
// 封裝原生的ajax
function ajax(opt) {
opt = opt || {};
opt.method = opt.method.toUpperCase() || 'POST';
opt.url = opt.url || '';
opt.async = opt.async || true;
opt.data = opt.data || null;
opt.success = opt.success || function () {};
var xmlHttp = null;
if (XMLHttpRequest) {
xmlHttp = new XMLHttpRequest();
}
else {
xmlHttp = new ActiveXObject('Microsoft.XMLHTTP');
}var params = [];
for (var key in opt.data){
params.push(key + '=' + opt.data[key]);
}
var postData = params.join('&');
if (opt.method.toUpperCase() === 'POST') {
xmlHttp.open(opt.method, opt.url, opt.async);
xmlHttp.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded;charset=utf-8');
xmlHttp.send(postData);
}
else if (opt.method.toUpperCase() === 'GET') {
xmlHttp.open(opt.method, opt.url + '?' + postData, opt.async);
xmlHttp.send(null);
}
xmlHttp.onreadystatechange = function () {
if (xmlHttp.readyState == 4 && xmlHttp.status == 200) {
opt.success(xmlHttp.responseText);
}
};
}
// 調用ajax
function http () {
ajax({
method: 'GET',
url: 'http://localhost/users/cosV5',
success: function(res) {
obj = JSON.parse(res);
console.info('res', obj)
}
})
}
// 這里返回的參數見下圖,后面new COS 時需要用到。
上傳圖片
創建cos實例
由於圖片過多,如果不去重命名圖片,會導致圖片太亂,可以定義函數,重置圖片名稱。
Key 的值如果加上 /pic, 系統會默認放在pic文件夾下面。
// obj為上一步請求的配置參數
function upload (obj,file) {
var cos = new COS({
AppId: obj.appId,
SecretId: obj.secretId,
SecretKey: obj.secretKey,
});
cos.sliceUploadFile({
Bucket: obj.bucket,
Region: obj.region,
Key:'/pic/'+file.name, //上傳的文件夾和圖片名稱
Body: file, //要上傳的文件
onProgress: function (progressData) {
/* 上傳進度 */
}
}, function (err, data) {
console.log(err, data);
// 上傳成功返回url
// 需要清空上傳控件,方法見下一步
});
}
返回參數說明
上傳成功后處理
這里如果沒有清理控件,會出現當第二次選擇同一張圖片時,由於圖片相同,無法觸發onchange事件,導致無法上傳,這里的解決辦法是將file的value值設置為空或重新初始化
如果不能訪問可能是權限的問題,可以在騰訊雲存儲桶配置權限,解決方法見圖三
//清空上傳控件的值id
function clearInput (ele) {
var demo = document.getElementById(ele);
if (demo.outerHTML) {
demo.outerHTML = demo.outerHTML;
} else { // FF(包括3.5)
demo.value = "";
}
}
圖三:
注意點:
- 1、上傳成功后一定要清空表單,防止上傳同一張圖片失敗;
- 2、cos-js-sdk-v5版本和cos-js-sdk-v4調用方法不同
- 3、使用a標簽注意阻止默認事件
- 4、input是h5兼容性的標簽,所以對不支持h5的標簽不支持
- 5、騰訊雲參考文檔https://cloud.tencent.com/document/product/436/11459