最近项目开发微信公众平台,从微信的平台生成一二维码,会返回得到一个图片地址,这个地址是有timeout,根据图片地址来展示给用户扫码。我们的需求就是,通过(<img scr="请求微信返回的二维码地址" />)img.src请求的图片地址下载到本地展现给用户会慢,还会根据不同的用户设备变的更慢,所以我们这里修改实现方式,给二维码下载并压缩,然后展示给用户。

    

  前台页面调用:

  

  项目采用MVC框架,图片红框为controll调用url,qrCodeContainer为二维码展示区。

  前台JS调用:

  

  动态拼接请求地址,此处的img.src请求地址为后台处理压缩图片地址(Controller中的一个action),下面就是我们整个文章重点代码片段,直接贴代码,前面图片只是给大家展示怎么调用~

  

 

  

  1  #region 压缩图片
  2         /// <summary>
  3         /// 压缩图片处理
  4         /// </summary>
  5         /// <param name="w"></param>
  6         /// <param name="h"></param>
  7         /// <param name="q">图片质量</param>
  8         /// <param name="picUrl">图片地址</param>
  9         /// <returns>图片二进制</returns>
 10         public ActionResult GetImg(string w, string h, string q, string picUrl)
 11         {
 12             //测试用这里picUrl为一个图片地址,这里是就直接网上扒了一个地址。
 13             if (picUrl == null) picUrl = @"http://pica.nipic.com/2007-12-18/200712189215503_2.jpg";
 14 
 15             //282*282 根据测试微信公众平台二维码大小
 16             int dHeight = int.Parse(h);
 17             int dWidth = int.Parse(w);
 18             //压缩质量
 19             var quality = int.Parse(q);
 20             byte[] image;
 21             try
 22             {
 23                 using (System.Net.WebClient wb = new System.Net.WebClient())
 24                     image = wb.DownloadData(picUrl);
 25             }
 26             catch (Exception)
 27             {
 28                 Image img = Image.FromFile(Server.MapPath("/Images/Comm/qc.png"));
 29                 ImageFormat format = img.RawFormat;
 30                 using (MemoryStream ms = new MemoryStream())
 31                 {
 32                     if (format.Equals(ImageFormat.Png))
 33                     {
 34                         img.Save(ms, ImageFormat.Png);
 35                     }
 36 
 37                     byte[] buffer = new byte[ms.Length];
 38                     ms.Seek(0, SeekOrigin.Begin);
 39                     ms.Read(buffer, 0, buffer.Length);
 40                     image = buffer;
 41                 }
 42             }
 43             using (MemoryStream ms = new MemoryStream(image))
 44             {
 45                 try
 46                 {
 47                     return File(CompressionImage(ms, quality, dWidth, dHeight), "image/jpeg");
 48                 }
 49                 catch (Exception e)
 50                 {
 51                     //TestHelper.OutputMsg("【" + this.Session.SessionID + "】请求【图片压缩失败】结果:" + e.Message);
 52                 }
 53                 return null;
 54             }
 55         }
 56 
 57         #endregion
 58 
 59         #region 私有方法
 60         private byte[] CompressionImage(MemoryStream ms, int quality, int weight, int height)
 61         {
 62             using (System.Drawing.Image img = System.Drawing.Image.FromStream(ms))
 63             {
 64                 var bitmap = ZoomImage(img, weight, height);
 65                 ImageCodecInfo CodecInfo = GetEncoder(img.RawFormat);
 66                 if (CodecInfo == null) return null;
 67                 System.Drawing.Imaging.Encoder myEncoder = System.Drawing.Imaging.Encoder.Quality;
 68                 EncoderParameters myEncoderParameters = new EncoderParameters(1);
 69                 EncoderParameter myEncoderParameter = new EncoderParameter(myEncoder, quality);
 70                 myEncoderParameters.Param[0] = myEncoderParameter;
 71                 using (MemoryStream stream = new MemoryStream())
 72                 {
 73                     bitmap.Save(stream, CodecInfo, myEncoderParameters);
 74                     myEncoderParameters.Dispose();
 75                     myEncoderParameter.Dispose();
 76                     return stream.ToArray();
 77                 }
 78             }
 79         }
 80 
 81         /// <summary>
 82         /// 同比缩放
 83         /// </summary>
 84         /// <param name="img"></param>
 85         /// <param name="weight"></param>
 86         /// <param name="height"></param>
 87         /// <returns></returns>
 88         private Bitmap ZoomImage(Image img, int weight, int height)
 89         {
 90             int sW = 0, sH = 0;
 91             Size tem_size = new Size(img.Width, img.Height);
 92             if (tem_size.Width > height || tem_size.Width > weight)
 93             {
 94                 if ((tem_size.Width * height) > (tem_size.Height * weight))
 95                 {
 96                     sW = weight;
 97                     sH = (weight * tem_size.Height) / tem_size.Width;
 98                 }
 99                 else
100                 {
101                     sH = height;
102                     sW = (tem_size.Width * height) / tem_size.Height;
103                 }
104             }
105             else
106             {
107                 sW = tem_size.Width;
108                 sH = tem_size.Height;
109             }
110             Bitmap ob = new Bitmap(weight, height);
111 
112             Graphics g = Graphics.FromImage(ob);
113 
114             g.Clear(Color.WhiteSmoke);
115 
116             g.CompositingQuality = CompositingQuality.HighQuality;
117 
118             g.SmoothingMode = SmoothingMode.HighQuality;
119 
120             g.InterpolationMode = InterpolationMode.HighQualityBicubic;
121 
122             g.DrawImage(img, new Rectangle((weight - sW) / 2, (height - sH) / 2, sW, sH), 0, 0, img.Width, img.Height, GraphicsUnit.Pixel);
123 
124             g.Dispose();
125             return ob;
126         }
127 
128         /// <summary>
129         /// 图片格式
130         /// </summary>
131         /// <param name="imageFormat"></param>
132         /// <returns></returns>
133         private ImageCodecInfo GetEncoder(ImageFormat imageFormat)
134         {
135             ImageCodecInfo codecInfo = null;
136             ImageCodecInfo[] arrayICI = ImageCodecInfo.GetImageEncoders();
137             for (int x = 0; x < arrayICI.Length; x++)
138             {
139                 if (arrayICI[x].FormatDescription.Equals("JPEG"))//这里只做了jpeg,png验证,如果有其他类型可自己加。方式一样,只管copy,修改类型即可
140                 {
141                     codecInfo = arrayICI[x];
142                     break;
143                 }
144             }
145             return codecInfo;
146         }
147         #endregion
View Code

 

 

 

这是测试地址图片效果,经过压缩后:

 

 

介绍完毕,大家可获取代码测试使用。试过在给质量调整为1的情况下,30k图片同比压缩为3k。欢迎大家吐槽互勉