2012-03-01 30 views
0

我有一个图像上传页面,只在上传文件时工作得很好。GDI +上传多个图像时出错,然后创建缩略图

我添加了“创建缩略图”功能。当缩略图进程启动时,它看起来像文件系统对图像有句柄。

只有当图像超过250K时,我才会得到'未指定的GDI +错误'。当文件低于250K时,按预期创建缩略图。

我有什么选择?这里有一个优雅的解决方案吗?我想要的东西不哈克。
此外,我使用HttpFileCollection,所以我们可以一次上传多个图像。我试图使用.Dispose创建缩略图,但在我们到达这一点之前失败。

public void Upload_Click(object Sender, EventArgs e) 
{ 
string directory = Server.MapPath(@"~\images\"); 
    HttpFileCollection hfc = Request.Files; 
    for (int i = 0; i < hfc.Count; i++) 
    { 
    HttpPostedFile hpf = hfc[i]; 

    if (hpf.ContentLength > 0) 
    { 
     string fileName = hpf.FileName; 
     fileName = fileName.Replace(" ", ""); 
     hpf.SaveAs(fileName); 
     createThumbnail(fileName); 
    } 
    } 
} 

private void createThumbnail(string filename) 
{ 
    Image image = Image.FromFile(filename); 
    Image thumb = image.GetThumbnailImage(100,100,() => false, IntPtr.Zero); 
    thumb.Save(filename); 
    image.Dispose(); 
    thumb.Dispose(); 
} 
+0

我们可以看到有问题的代码? – asawyer 2012-03-01 21:43:30

+0

尝试删除image.dispose();和thumb.dispose(); – coder 2012-03-01 22:07:17

+0

没有什么不同。 – JonHiggens 2012-03-01 22:12:11

回答

3

请让我知道,如果这个工程没有更好:

public string ImageDirectory { get { return Server.MapPath(@"~\images\"); } } 

    public void OnUploadClick(object sender, EventArgs e) 
    { 
     var files = HttpContext.Request.Files.AllKeys.AsEnumerable() 
      .Select(k =>HttpContext.Request.Files[k]); 

     foreach(var file in files) 
     { 
      if(file.ContentLength <= 0) 
       continue; 

      string savePath = GetFullSavePath(file); 
      var dimensions = new Size(100, 100); 

      CreateThumbnail(file,savePath,dimensions); 
     } 
    } 

    private void CreateThumbnail(HttpPostedFile file,string savePath, Size dimensions) 
    { 
     using (var image = Image.FromStream(file.InputStream)) 
     { 
      using (var thumb = image.GetThumbnailImage(dimensions.Width, dimensions.Height,() => false, IntPtr.Zero)) 
      { 
       thumb.Save(savePath); 
      } 
     } 
    } 

    private string GetFullSavePath(HttpPostedFile file) 
    { 
     string fileName = System.IO.Path.GetFileName(file.FileName).Replace(" ", ""); 
     string savePath = System.IO.Path.Combine(this.ImageDirectory, fileName); 
     return savePath; 
    } 

编辑 -

在foreach应遵循更多的这种模式:

var files = HttpContext.Request.Files.AllKeys.AsEnumerable() 
       .Select(k =>HttpContext.Request.Files[k]); 

foreach(var file in files) 
{ 

} 
+0

这解决了这个问题。这段代码有几个问题。主要是字符串和Request.Files之间的转换问题(来自'foreach(HttpPostedFile ....)') 我也需要保存上传的文件,但是在破解之后,我保存了原始文件和缩略图,它还不是很漂亮,但最初的问题已经解决了。感谢您提供一个清晰直接的答案。 – JonHiggens 2012-03-03 02:17:23

+0

@JonHiggens对不起,我没有真正尝试编译或运行此,其他 – asawyer 2012-03-03 02:23:07

+0

没问题 - 我认为我们不能这样做: (HttpPostedFileHttpContext.Request.Files中的HttpPostedFile文件) – JonHiggens 2012-03-05 00:40:19

0

你可以试试这个代码来创建你的缩略图。

 MemoryStream ms = new MemoryStream(File.ReadAllBytes(path)); 
     Bitmap originalBMP = new Bitmap(ms); 

     int maxWidth = 200; 
     int maxHeight = 200; 

     // Calculate the new image dimensions 
     int origWidth = originalBMP.Width; 
     int origHeight = originalBMP.Height; 
     double sngRatio = Convert.ToDouble(origWidth)/Convert.ToDouble(origHeight); 

     // New dimensions 
     int newWidth = 0; 
     int newHeight = 0; 
     try 
     { 
      // max 200 by 200 

      if ((origWidth <= maxWidth && origHeight <= maxHeight) || origWidth <= maxWidth) 
      { 
       newWidth = origWidth; 
       newHeight = origHeight; 
      } 
      else 
      { 
       // Width longer (shrink width) 
       newWidth = 200; 
       newHeight = Convert.ToInt32(Convert.ToDouble(newWidth)/sngRatio); 
      } 

      // Create a new bitmap which will hold the previous resized bitmap 
      Bitmap newBMP = new Bitmap(originalBMP, newWidth, newHeight); 
      // Create a graphic based on the new bitmap 
      Graphics oGraphics = Graphics.FromImage(newBMP); 

      // Set the properties for the new graphic file 
      oGraphics.SmoothingMode = SmoothingMode.AntiAlias; 
      oGraphics.InterpolationMode = InterpolationMode.High; 
      // Draw the new graphic based on the resized bitmap 
      oGraphics.CompositingQuality = CompositingQuality.HighSpeed; 

      oGraphics.DrawImage(originalBMP, 0, 0, newWidth, newHeight); 

      // Save the new graphic file to the server 
      EncoderParameters p = new EncoderParameters(1); 
      p.Param[0] = new EncoderParameter(System.Drawing.Imaging.Encoder.Compression, 70);  // Percent Compression 

      MemoryStream savedBmp = new MemoryStream(); 

      newBMP.Save(savedBmp, ImageCodecInfo.GetImageEncoders()[1], p); 

          // Once finished with the bitmap objects, we deallocate them. 
      originalBMP.Dispose(); 
      newBMP.Dispose(); 
      oGraphics.Dispose(); 
      savedBmp.Dispose(); 

当然多一点工作,但它确实给你更大的控制。

+0

随着两位亚当的回答,我相信我们会弄清楚。 – asawyer 2012-03-02 13:39:57

+1

您应该在'使用'从句中包装非管理资源,以确保您在发生异常时不会泄漏它们。 – asawyer 2012-03-02 13:52:29

+0

感谢提示:) – 2012-03-03 13:05:04

相关问题