• 首页 首页 icon
  • 工具库 工具库 icon
    • IP查询 IP查询 icon
  • 内容库 内容库 icon
    • 快讯库 快讯库 icon
    • 精品库 精品库 icon
    • 问答库 问答库 icon
  • 更多 更多 icon
    • 服务条款 服务条款 icon

删除另进程正在使用的图像

用户头像
it1352
帮助1

问题说明

我正在用 C# 编写一个 winform 应用程序来打开一个图像并在它上面覆盖另一个图像.

I am writing a winform application in C# to open an image and overlay another image on top of it.

底部图像是 .jpg,顶部图像是从 .svg 转换而来的 .bmp..jpg 和 .svg 是我想要保留在文件夹中的唯一文件..bmp 用作临时文件.

The bottom image is a .jpg and the top one is a .bmp converted from .svg. The .jpg and the .svg are the only ones I want to keep in the folder. The .bmp works as a temp.

我使用以下代码来覆盖图像.但是我无法删除 temp .bmp,因为它被另一个进程使用.我认为正是这个组合代码仍然可以访问最后一个 .bmp 文件.

I was using the following code to overlay the images. But I am having trouble to delete the temp .bmp as it is used by another process. I think it is this combine code still have access to the last .bmp file.

有人能帮我解决这个问题吗?谢谢.

Could anyone help me on this? Thanks.

    private void buttonSearch_Click(object sender, EventArgs e)
    {
        FailInfo.Text = "";

        deletebmp(strFolderPath); 

        ...

        // Check if the specified front image exists. Yes, show the file name and convert SVG to BMP. No, show the error msg.
        if (File.Exists(strFilePathF))
        {
            labelFront.Text = strFileNameF;
            var svgConvert = SvgDocument.Open(svgFilePathF);
            svgConvert.Draw().Save(bmpFilePathF);
            pictureBoxFront.Image = Image.FromFile(strFilePathF);
        }
        else
        {
            labelFront.Text = "Couldn't find the file!";
            pictureBoxFront.Image = null;
        }

        // Check if the specified back image exists. Yes, show the file name and convert SVG to BMP. No, show the error msg.   
        if (File.Exists(strFilePathBF))
        {
            labelBack.Text = strFileNameBF;
            strFilePathB = strFilePathBF;
            pictureBoxBack.Image = Image.FromFile(strFilePathB);
            labelResult.Text = "FAIL";
            labelResult.BackColor = Color.FromArgb(255, 0, 0);
            var svgConvert = SvgDocument.Open(svgFilePathBF);
            bmpFilePathB = strFolderPath   strFileNameBF   ".bmp";
            svgConvert.Draw().Save(bmpFilePathB);
            svgFilePathB = svgFilePathBF;
            inspectionres(svgFilePathB);
            labelreason.Visible = true;
        }
        else if (File.Exists(strFilePathBP))
        {
            labelBack.Text = strFileNameBP;
            strFilePathB = strFilePathBP;
            pictureBoxBack.Image = Image.FromFile(strFilePathB);
            labelResult.Text = "PASS";
            labelResult.BackColor = Color.FromArgb(0, 255, 0);
            var svgConvert = SvgDocument.Open(svgFilePathBP);
            bmpFilePathB = strFolderPath   strFileNameBP   ".bmp";
            svgConvert.Draw().Save(bmpFilePathB);
            svgFilePathB = svgFilePathBP;
            inspectionres(svgFilePathB);
            labelreason.Visible = false;
        }
        else
        {
            labelBack.Text = "Couldn't find the file!";
            pictureBoxBack.Image = null;
            labelResult.Text = "ERROR";
            labelResult.BackColor = Color.FromArgb(0, 255, 255);
            labelreason.Visible = false;
        }
    }

    //
    // Overlay the SVG file on top of the JPEG file
    //
    private Bitmap Combine(string jpegFile, string bmpFile)
    {        
        Image image1 = Image.FromFile(jpegFile);
        Image image2 = Image.FromFile(bmpFile);
        Bitmap temp = new Bitmap(image1.Width, image1.Height);

        using (Graphics g = Graphics.FromImage(temp))
        {
            g.DrawImageUnscaled(image1, 0, 0);
            g.DrawImageUnscaled(image2, 0, 0);
        }

        return temp;
    }

    //
    // Show the overlaid graphic in the picturebox
    //
    private void checkBoxOverlay_CheckedChanged(object sender, EventArgs e)
    {
        try
        {
            if (FindFront)
                if (checkBoxOverlay.Checked)
                    pictureBoxFront.Image = Combine(strFilePathF, bmpFilePathF);
                else
                    pictureBoxFront.Image = Image.FromFile(strFilePathF);
            else
                pictureBoxFront.Image = null;

            if (FindBack)
                if (checkBoxOverlay.Checked)
                    pictureBoxBack.Image = Combine(strFilePathB, bmpFilePathB);
                else
                    pictureBoxBack.Image = Image.FromFile(strFilePathB);
            else
                pictureBoxBack.Image = null;
        }
        catch (Exception ex)
        {
            MessageBox.Show("Error loading image"   ex.Message);
        }
    }

    //
    // Option of changing the image folder
    //
    private void buttonPath_Click(object sender, EventArgs e)
    {
        FolderBrowserDialog FolderBrowserDialog1 = new FolderBrowserDialog();
        if (FolderBrowserDialog1.ShowDialog() == DialogResult.OK)
        {
            strFolderPath = FolderBrowserDialog1.SelectedPath   "\\";
        }
    }

    //
    // Pull the inspection result info from the SVG file
    //
    private void inspectionres(string filename)
    {
        XDocument document = XDocument.Load(filename);
        XElement svg_Element = document.Root;
        string sb = null;

        var faillist = (from svg_path in svg_Element.Descendants("{http://www.w3.org/2000/svg}text") select svg_path).ToList();

        foreach (var item in faillist)
        {
            sb  = item.ToString();
        }
    }

    //
    // Delete all the .bmp files generated from .svg files
    //
    private void deletebmp(string path)
    {
        // Unload the images from the picturebox if applicable
        pictureBoxFront.Image = null;
        pictureBoxBack.Image = null;

        string[] files = Directory.GetFiles(path, "*.bmp");
        for (int i = 0; i < files.Length; i    )
            File.Delete(files[i]);
    }
}

正确答案

#1

Image 实现了 IDisposable,所以只需设置 pictureBox.Image 属性为 null 不会释放资源(在您的情况下,是文件).您的 Combine 方法也会使图像保持打开状态.您必须在尝试删除文件之前调用 Dispose:

Image implements IDisposable, so simply setting the pictureBox.Image property to null will not release resources (in your case, the file). Your Combine method also leaves the images open. You have to call Dispose before attempting to delete the file:

Image image1 = Image.FromFile(path1);
File.Delete(path1);  // error - file is locked 

Image image2 = Image.FromFile(path2);
image2.Dispose();
File.Delete(path2);  // works

另一种方法(我假设您在这里使用的是 WinForms,在 WPF 中它有点不同)是手动从文件加载位图(使用 FromStream).然后,您可以立即关闭流并删除文件:

An alternative approach (and I assume you're using WinForms here, in WPF it's a little different) would be to load the bitmap from the file manually (using FromStream). Then, you can close the stream immediately and delete the file:

Image image;
using (Stream stream = File.OpenRead(path))
{
    image = System.Drawing.Image.FromStream(stream);
}
pictureBox.Image = image;
File.Delete("e:\\temp\\copy1.png");  //works

这篇好文章是转载于:学新通技术网

  • 版权申明: 本站部分内容来自互联网,仅供学习及演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,请提供相关证据及您的身份证明,我们将在收到邮件后48小时内删除。
  • 本站站名: 学新通技术网
  • 本文地址: /reply/detail/tanhcfijea
系列文章
更多 icon
同类精品
更多 icon
继续加载