一、js文件,这个是封装过的,借用了网络上的代码然后修改的

  1. (function(window,undefined){
  2.  
  3. var upload = function(){
  4. this.init();
  5. };
  6.  
  7. upload.prototype={
  8. init:function(){
  9. var inputDom = document.createElement("input");
  10. inputDom.type = "file";
  11. inputDom.setAttribute("accept","image/*");
  12. inputDom.setAttribute("multiple","multiple");
  13. this.inputDom = inputDom;
  14. this.bindChange();
  15. },
  16. start:function(o){
  17. this.opt = this.setOpt(o);
  18. this.inputDom.value = "";
  19. this.canvasBefore();
  20. this.inputDom.click();
  21. },
  22. bindChange:function(){
  23. var dom = this.inputDom;
  24. var that = this;
  25. dom.onchange = function() {
  26. try{
  27.  
  28. if (!this.files.length) return;
  29. var files = Array.prototype.slice.call(this.files);
  30. if (files.length > 1) {
  31. alert("最多只可上传1张图片");
  32. return;
  33. }
  34.  
  35. _shade_layer.show("上传中,请稍后...");
  36. files.forEach(function(file, i) {
  37. if (!/\/(?:jpeg|png|gif)/i.test(file.type)) return;
  38. var reader = new FileReader();
  39.  
  40. //获取图片大小
  41. var size = file.size / 1024 > 1024 ? (~~ (10 * file.size / 1024 / 1024)) / 10 + "MB": ~~ (file.size / 1024) + "KB";
  42.  
  43. reader.onload = function() {
  44. var result = this.result;
  45. var img = new Image();
  46. img.src = result;
  47.  
  48. //超出大小
  49. if(result.length > that.opt.maxSize){
  50. alert("图片大小不能超过5M");
  51. _shade_layer.hide();
  52. return;
  53. }
  54.  
  55. //如果图片大小小于100kb,则直接上传
  56. if (result.length <= that.opt.minSize) {
  57. img = null;
  58. that.upload(result, file.type);
  59. return;
  60. }
  61. //图片加载完毕之后进行压缩,然后上传
  62. if (img.complete) {
  63. callback();
  64. } else {
  65. img.onload = callback;
  66. }
  67. function callback() {
  68. var data = that.compress(img);
  69. that.upload(data, file.type);
  70. img = null;
  71. }
  72. };
  73. reader.readAsDataURL(file);
  74. })
  75.  
  76. }catch(e){
  77. _shade_layer.hide();
  78. alert("上传出现错误");
  79. return ;
  80. }
  81. };
  82. },
  83. /**
  84. * 绘制压缩图片的canvas
  85. */
  86. canvasBefore:function(){
  87. var canvasDom = document.getElementById("canvas_id");
  88. if(canvasDom){canvasDom.parent().remove();}
  89.  
  90. var tCanvasDom = document.getElementById("tCanvas_id");
  91. if(tCanvasDom){tCanvasDom.parent().remove();}
  92.  
  93. //用于压缩图片的canvas
  94. var canvas = document.createElement("canvas");
  95. canvas.id = "canvas_id";
  96. this.canvas = canvas;
  97. this.ctx = canvas.getContext('2d');
  98.  
  99. //瓦片canvas
  100. var tCanvas = document.createElement("canvas");
  101. tCanvas.id = "tCanvas_id";
  102. this.tCanvas = tCanvas;
  103. this.tctx = tCanvas.getContext("2d");
  104. },
  105. /**
  106. * 使用canvas对大图片进行压缩
  107. * @param {} img 图片对象
  108. * @return {}
  109. */
  110. compress:function(img) {
  111. var canvas = this.canvas;
  112. var tCanvas = this.tCanvas;
  113. var tctx = this.tctx;
  114. var ctx = this.ctx;
  115.  
  116. var initSize = img.src.length;
  117. var width = img.width;
  118. var height = img.height;
  119.  
  120. //如果图片大于四百万像素,计算压缩比并将大小压至400万以下
  121. var ratio;
  122. if ((ratio = width * height / 4000000) > 1) {
  123. ratio = Math.sqrt(ratio);
  124. width /= ratio;
  125. height /= ratio;
  126. } else {
  127. ratio = 1;
  128. }
  129. canvas.width = width;
  130. canvas.height = height;
  131.  
  132. //铺底色
  133. ctx.fillStyle = "#fff";
  134. ctx.fillRect(0, 0, canvas.width, canvas.height);
  135.  
  136. //如果图片像素大于100万则使用瓦片绘制
  137. var count;
  138. if ((count = width * height / 1000000) > 1) {
  139. count = ~~ (Math.sqrt(count) + 1); //计算要分成多少块瓦片
  140. //计算每块瓦片的宽和高
  141. var nw = ~~ (width / count);
  142. var nh = ~~ (height / count);
  143. tCanvas.width = nw;
  144. tCanvas.height = nh;
  145. for (var i = 0; i < count; i++) {
  146. for (var j = 0; j < count; j++) {
  147. tctx.drawImage(img, i * nw * ratio, j * nh * ratio, nw * ratio, nh * ratio, 0, 0, nw, nh);
  148. ctx.drawImage(tCanvas, i * nw, j * nh, nw, nh);
  149. }
  150. }
  151. } else {
  152. ctx.drawImage(img, 0, 0, width, height);
  153. }
  154.  
  155. //进行最小压缩
  156. var ndata = canvas.toDataURL('image/jpeg', this.opt.proportion);
  157. /*
  158. console.log('压缩前:' + initSize);
  159. console.log('压缩后:' + ndata.length);
  160. console.log('压缩率:' + ~~ (100 * (initSize - ndata.length) / initSize) + "%");
  161. */
  162. tCanvas.width = tCanvas.height = canvas.width = canvas.height = 0;
  163.  
  164. this.canvas = canvas;
  165. this.tCanvas = tCanvas;
  166. this.tctx = tctx;
  167. this.ctx = ctx;
  168. return ndata;
  169. },
  170. /**
  171. * 获取blob对象的兼容性写法
  172. * @param buffer
  173. * @param format
  174. * @returns {*}
  175. */
  176. getBlob:function(buffer, format) {
  177. try {
  178. return new Blob(buffer, {
  179. type: format
  180. });
  181. } catch(e) {
  182. var bb = new(window.BlobBuilder || window.WebKitBlobBuilder || window.MSBlobBuilder);
  183. buffer.forEach(function(buf) {
  184. bb.append(buf);
  185. });
  186. return bb.getBlob(format);
  187. }
  188. },
  189. /**
  190. * 获取formdata
  191. * @return {}
  192. */
  193. getFormData:function() {
  194. var isNeedShim = ~navigator.userAgent.indexOf('Android') && ~navigator.vendor.indexOf('Google') && !~navigator.userAgent.indexOf('Chrome') && navigator.userAgent.match(/AppleWebKit\/(\d+)/).pop() <= 534;
  195. return isNeedShim ? new this.FormDataShim() : new FormData();
  196. },
  197. /**
  198. * formdata 补丁, 给不支持formdata上传blob的android机打补丁
  199. */
  200. FormDataShim:function() {
  201. var o = this,
  202. parts = [],
  203. boundary = Array(21).join('-') + ( + new Date() * (1e16 * Math.random())).toString(36),
  204. oldSend = XMLHttpRequest.prototype.send;
  205. this.append = function(name, value, filename) {
  206. parts.push('--' + boundary + '\r\nContent-Disposition: form-data; name="' + name + '"');
  207. if (value instanceof Blob) {
  208. parts.push('; filename="' + (filename || 'blob') + '"\r\nContent-Type: ' + value.type + '\r\n\r\n');
  209. parts.push(value);
  210. } else {
  211. parts.push('\r\n\r\n' + value);
  212. }
  213. parts.push('\r\n');
  214. };
  215.  
  216. // Override XHR send()
  217. XMLHttpRequest.prototype.send = function(val) {
  218. var fr, data, oXHR = this;
  219. if (val === o) {
  220. // Append the final boundary string
  221. parts.push('--' + boundary + '--\r\n');
  222. // Create the blob
  223. data = getBlob(parts);
  224. // Set up and read the blob into an array to be sent
  225. fr = new FileReader();
  226. fr.onload = function() {
  227. oldSend.call(oXHR, fr.result);
  228. };
  229. fr.onerror = function(err) {
  230. throw err;
  231. };
  232. fr.readAsArrayBuffer(data);
  233. // Set the multipart content type and boudary
  234. this.setRequestHeader('Content-Type', 'multipart/form-data; boundary=' + boundary);
  235. XMLHttpRequest.prototype.send = oldSend;
  236. } else {
  237. oldSend.call(this, val);
  238. }
  239. };
  240. },
  241. /**
  242. * 图片上传,将base64的图片转成二进制对象,塞进formdata上传
  243. * @param {} basestr
  244. * @param {} type
  245. * @param {} $li
  246. */
  247. upload:function(basestr, type) {
  248. var that = this;
  249. var text = window.atob(basestr.split(",")[1]);
  250. var buffer = new Uint8Array(text.length);
  251. var pecent = 0,
  252. loop = null;
  253. for (var i = 0; i < text.length; i++) {
  254. buffer[i] = text.charCodeAt(i);
  255. }
  256. var blob = this.getBlob([buffer], type);
  257. var xhr = new XMLHttpRequest();
  258. var formdata = this.getFormData();
  259. formdata.append('imagefile', blob);
  260. xhr.open('post', this.opt.uploadURL);
  261. xhr.onreadystatechange = function() {
  262. this.canvas = null;
  263. this.tCanvas = null;
  264. this.tctx = null;
  265. this.ctx = null;
  266.  
  267. var func = that.opt.callBackFunc;
  268. var id = that.opt.id;
  269.  
  270. var oDataObj = that.opt.oDataObj;
  271. var nType = that.opt.nType;
  272. var frameCallBackFunc = that.opt.frameCallBackFunc;
  273. var strCallbackFunc = that.opt.strCallbackFunc;
  274. oDataObj["strCallbackFunc"] = strCallbackFunc;
  275. oDataObj["nType"] = nType;
  276.  
  277. if (xhr.readyState == 4 && xhr.status == 200) {
  278. var url = xhr.responseText || "";
  279. console.log(url);
  280. var nState = url.length == 0 ? -1 : 0;
  281. var strMsg = url.length == 0 ? "上传失败" : url;
  282. oDataObj["nState"] = nState;
  283. oDataObj["strMsg"] = strMsg;
  284. oDataObj = JSON.stringify(oDataObj);
  285. eval(frameCallBackFunc+"('"+oDataObj+"')");
  286. _shade_layer.hide();
  287. }
  288.  
  289. if(xhr.status != 200){
  290. oDataObj["nState"] = -1;
  291. oDataObj["strMsg"] = "上传失败";
  292. oDataObj = JSON.stringify(oDataObj);
  293. eval(frameCallBackFunc+"('"+oDataObj+"')");
  294. _shade_layer.hide();
  295. }
  296. };
  297. xhr.send(formdata);
  298.  
  299. },setOpt:function(o){
  300. var defaultOptions={
  301. nType:'', //回调的不同类型,通过这个类型来改_plus.callbackuploadPicture里面对于回调的具体方法,其实主要就是控制最终回调函数的参数
  302. minSize:100 * 1024, //最小为100kb,也就是说100kb以下的不压缩直接上传
  303. maxSize:1024 * 1024 * 5, //最大为10M,也就是说100kb以下的不压缩直接上传
  304. proportion:0.3, //压缩比例:从0-1之间
  305. strCallbackFunc:'',
  306. frameCallBackFunc:'',
  307. oDataObj:{},
  308. uploadURL:'http://pocketwap.xxx.com/Servlet/fileUpload.svl'
  309. };
  310. if(o && Object.prototype.toString.call(o)=='[object Object]')
  311. {
  312. for(var k in o)
  313. {
  314. defaultOptions[k]= typeof o[k]==='undefined' ? defaultOptions[k] : o[k];
  315. }
  316. }
  317. return defaultOptions;
  318. }
  319. }
  320.  
  321. window.upload=upload;
  322. })(window,undefined)
  323.  
  324. var _upload = new upload();

二、js页面使用如下:

  1. _upload.start({
  2. id:Id,
  3. callBackFunc:strCallbackFunc //回调地址
  4. });

三、服务端接收,这边因为是要统一上传到文件服务器,所以这里中转了一下,如果不需要中转,直接就可以在这里面处理就行

  1. package com.xxx.businesscenter.web;
  2.  
  3. import java.io.BufferedInputStream;
  4. import java.io.DataOutputStream;
  5. import java.io.IOException;
  6. import java.io.InputStream;
  7. import java.net.HttpURLConnection;
  8. import java.net.URL;
  9. import java.util.List;
  10.  
  11. import javax.servlet.ServletException;
  12. import javax.servlet.http.HttpServlet;
  13. import javax.servlet.http.HttpServletRequest;
  14. import javax.servlet.http.HttpServletResponse;
  15.  
  16. import org.apache.commons.fileupload.FileItem;
  17. import org.apache.commons.fileupload.FileUploadException;
  18. import org.apache.commons.fileupload.disk.DiskFileItemFactory;
  19. import org.apache.commons.fileupload.servlet.ServletFileUpload;
  20. import org.apache.log4j.Logger;
  21.  
  22. import com.alibaba.fastjson.JSON;
  23. import com.alibaba.fastjson.JSONObject;
  24. import com.cdoframework.cdolib.base.UUidGenerator;
  25.  
  26. /**
  27. * Servlet implementation class FileUploadServlet
  28. */
  29. public class FileUploadServlet extends HttpServlet {
  30. private static final long serialVersionUID = 1L;
  31. private Logger log=Logger.getLogger(ApplicationListener.class);
  32. /**
  33. * @see HttpServlet#HttpServlet()
  34. */
  35. public FileUploadServlet() {
  36. super();
  37. // TODO Auto-generated constructor stub
  38. }
  39.  
  40. /**
  41. * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
  42. */
  43. protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
  44. // TODO Auto-generated method stub
  45. this.doPost(request, response);
  46. }
  47.  
  48. /**
  49. * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
  50. */
  51. protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
  52. // TODO Auto-generated method stub
  53.  
  54. String strResult = "";
  55. DiskFileItemFactory factory = new DiskFileItemFactory();
  56. ServletFileUpload upload = new ServletFileUpload(factory);
  57. try {
  58. List<FileItem> items = upload.parseRequest(request);
  59. if(items.size() > 0 ){
  60. FileItem item = items.get(0);
  61. if(!item.isFormField()){
  62. strResult = uploadFile(item);
  63. }
  64. }
  65. } catch (FileUploadException e) {
  66. log.info(e);
  67. }
  68.  
  69. response.getWriter().print(strResult);
  70.  
  71. }
  72.  
  73. private String uploadFile(FileItem item) {
  74. String contentType = item.getContentType();
  75. String postfix = contentType.split("/")[1];
  76. String result = "";
  77. String end = "\r\n";
  78. String twoHyphens = "--";
  79. String boundary = "*****";
  80. String newName = UUidGenerator.genenator() + "."+postfix;
  81. String actionUrl = "http://file.xxx.com.cn/Servlet/fileUpload.svl";
  82. BufferedInputStream bufin = null;
  83. InputStream is = null;
  84. try {
  85. URL url = new URL(actionUrl);
  86. HttpURLConnection conn = (HttpURLConnection) url.openConnection();
  87. conn.setConnectTimeout(10000); //超时时间为10秒
  88. conn.setDoInput(true);
  89. conn.setDoOutput(true);
  90. conn.setUseCaches(false);
  91. conn.setRequestMethod("POST");
  92. conn.setRequestProperty("Connection", "Keep-Alive");
  93. conn.setRequestProperty("Charset", "UTF-8");
  94. conn.setRequestProperty("Content-Type","multipart/form-data;boundary=" + boundary);
  95. DataOutputStream ds = new DataOutputStream(conn.getOutputStream());
  96. ds.writeBytes(twoHyphens + boundary + end);
  97. ds.writeBytes("Content-Disposition: form-data; " + "name=\"file1\";filename=\"" + newName + "\"" + end);
  98. ds.writeBytes("Content-Type:" + contentType + "\r\n\r\n");
  99.  
  100. bufin = new BufferedInputStream(item.getInputStream());
  101. int bufferSize = 2048;
  102. byte[] buffer = new byte[bufferSize];
  103. int length = -1;
  104. while ((length = bufin.read(buffer)) != -1) {
  105. ds.write(buffer, 0, length);
  106. }
  107. ds.writeBytes(end);
  108. ds.writeBytes(twoHyphens + boundary + twoHyphens + end);
  109. bufin.close();
  110. ds.flush();
  111.  
  112. //获取上传返回结果
  113. int code = conn.getResponseCode();
  114. is = conn.getInputStream();
  115. int ch;
  116. StringBuffer b = new StringBuffer();
  117. while ((ch = is.read()) != -1) {
  118. b.append((char) ch);
  119. }
  120.  
  121. String str = b.toString();
  122. log.info("-------------------------"+str);
  123. if (conn.getResponseCode() == 200) {
  124. if(str.length() > 0 ){
  125. JSONObject jObject = JSON.parseObject(str);
  126. String strFilePath = (String) jObject.get("strFilePath");
  127. String strFileName = (String) jObject.get("strFileName");
  128. result = strFilePath+strFileName;
  129. log.info("-------------------------图片上传地址="+result);
  130. }
  131. }else{
  132. log.info("-------------------------上传失败code="+code);
  133. }
  134.  
  135. } catch (Exception e) {
  136. log.info(e);
  137. return result;
  138. }finally{
  139. try {
  140. if(bufin!=null){
  141. bufin.close();
  142. }
  143. if(is!=null){
  144. is.close();
  145. }
  146. } catch (IOException e) {
  147. log.info("-------------------------流关闭失败-------------------------");
  148. e.printStackTrace();
  149. }
  150. }
  151. return result;
  152. }
  153.  
  154. }

js等比压缩上传的更多相关文章

  1. 纯原生js移动端图片压缩上传插件

    前段时间,同事又来咨询一个问题了,说手机端动不动拍照就好几M高清大图,上传服务器太慢,问问我有没有可以压缩图片并上传的js插件,当然手头上没有,别慌,我去网上搜一搜. 结果呢,呵呵...诶~又全是基于 ...

  2. js 图片压缩上传(纯js的质量压缩,非长宽压缩)

    下面是大神整理的demo,很实用,这里存一下备用,感谢大神! 此demo为大于1M对图片进行压缩上传 若小于1M则原图上传,可以根据自己实际需求更改. demo源码如下 <!DOCTYPE ht ...

  3. 前端图片压缩上传(纯js的质量压缩,非长宽压缩)

    此demo为大于1M对图片进行压缩上传 若小于1M则原图上传,可以根据自己实际需求更改. demo源码如下: <!DOCTYPE html> <html> <head&g ...

  4. 基于vue + axios + lrz.js 微信端图片压缩上传

    业务场景 微信端项目是基于Vux + Axios构建的,关于图片上传的业务场景有以下几点需求: 1.单张图片上传(如个人头像,实名认证等业务) 2.多张图片上传(如某类工单记录) 3.上传图片时期望能 ...

  5. js 图片压缩上传(base64位)以及上传类型分类

    一.input file上传类型 1.指明只需要图片 <input type="file" accept='image/*'> 2.指明需要多张图片 <input ...

  6. JS—图片压缩上传(单张)

    *vue+webpack环境,这里的that指到vue实例 <input type="file" name="file" accept="ima ...

  7. 三款不错的图片压缩上传插件(webuploader+localResizeIMG4+LUploader)

    涉及到网页图片的交互,少不了图片的压缩上传,相关的插件有很多,相信大家都有用过,这里我就推荐三款,至于好处就仁者见仁喽: 1.名气最高的WebUploader,由Baidu FEX 团队开发,以H5为 ...

  8. HTML5 图片本地压缩上传插件「localResizeIMG」

    移动应用中用户往往需要上传照片,但是用户上传的照片尺寸通常很大,而手机的流量却很有限,所以在上传前对图像进行压缩是很有必要的. 原生应用可以直接对文件进行处理,网页应用就没有这个优势了.不过 canv ...

  9. Html5+asp.net mvc 图片压缩上传

    在做图片上传时,大图片如果没有压缩直接上传时间会非常长,因为有的图片太大,传到服务器上再压缩太慢了,而且损耗流量. 思路是将图片抽样显示在canvas上,然后用通过canvas.toDataURL方法 ...

随机推荐

  1. 数据库导出Excel(转载)

    来源:https://jingyan.baidu.com/article/3065b3b68f2ab7becef8a449.html SQLServer2005或者SQLServer2008.SQLS ...

  2. C# 的逻辑运算

    &.^.!和|操作符称为逻辑操作符,用逻辑操作符把运算对象连接起来符合C#语法的式子称为逻辑表达式.逻辑 操作符“!”和“^”只作用于其后的操作数,故称为一元操作符.而“&&” ...

  3. PHP 错误解决锦集

    Part1:Maximum execution time of 120 seconds exceeded 120秒运行超时的错误 解决办法: 方法一,修改php.ini文件 max_execution ...

  4. K:图的存储结构

      常用的图的存储结构主要有两种,一种是采用数组链表(邻接表)的方式,一种是采用邻接矩阵的方式.当然,图也可以采用十字链表或者边集数组的方式来进行表示,但由于不常用,为此,本博文不对其进行介绍. 邻接 ...

  5. QT的信号和槽机制简介

    信号与槽作为QT的核心机制在QT编程中有着广泛的应用,本文介绍了信号与槽的一些基本概念.元对象工具以及在实际使用过程中应注意的一些问题. QT是一个跨平台的C++ GUI应用构架,它提供了丰富的窗口部 ...

  6. CentOS 7 yum安装配置mysql

    首先去官网下载要用的yum源 传送门:http://dev.mysql.com/downloads/repo/yum/ yum源文件:/home/mysql57-community-release-e ...

  7. ACK-Ackermann, 阿克曼函数

    以前好几次在学语言的使用都有实现这个ack函数的经历,今天读本算法书,偶尔又提到了这个,查了下wiki来头好大 Values of A(m, n) m\n 0 1 2 3 4 n 0 1 2 3 4 ...

  8. 虚拟主机服务器php fsockopen函数被禁用的解决方法

    为了服务器安全考虑很多主机商禁用了php的fsockopen函数,昨天进博客,使用cos-html-cache生成静态文件,尼玛提示: Warning: fsockopen() has been di ...

  9. Jquery插件网站持续添加。。。

    Look Fro Less,Do More www.jq22.com

  10. Pig安装与应用

    1.  参考说明 参考文档: http://pig.apache.org/docs/r0.17.0/start.html#build 2.  安装环境说明 2.1.  环境说明 CentOS7.4+ ...