#Context:
Generating PNGs from PDF pages and showing them in a ListView through an ImageList
#Desired behaviour:
When the user chooses another file to be displayed in the listview -> clear both the ImageList and ListView items (obvious) and also delete the generated image files.
#Issue:
Exception thrown on delete: "The process cannot access the file 'X.png' because it is being used by another process."
previewImageList.Images.Clear();
previewListView.Items.Clear();
// folder containing the generated PNGs, created at runtime
string folderToDelete = Path.Combine(outputFolder, Path.GetFileNameWithoutExtension(selectedSong));
try
{
Directory.Delete(folderToDelete, true); // Image file "X.png" is used by another process
}
catch (Exception)
{}
Solution found:
calling the Garbage Collector manually before deleting the said PNG files seems to do the trick.
previewImageList.Images.Clear(); previewListView.Items.Clear();
string folderToDelete = Path.Combine(outputFolder, Path.GetFileNameWithoutExtension(selectedSong));
try { GC.Collect(); GC.WaitForPendingFinalizers();
Directory.Delete(folderToDelete, true);
} catch (Exception ex) { MessageBox.Show(ex.Message); }
But as i researched so far it isn't a good thing to do. Do I have an alternative to calling the Garbage collector? The reason I need to delete the PNGs is to be able to reuse respective filename with a PDF from another path...
The closest I got to are here and here but didn't help much.
EDIT additional details Generating the PNGs:
i use ImageMagik like this:
startInfo = new ProcessStartInfo(); startInfo.FileName = """ + UtilitiesFolder + "\convert.exe""; startInfo.Arguments = """ + selectedPDFFile.pdf" + "" " + " -resample 168x140 "" + Path.Combine(outputFolder, selectedPDFFileShortName) + ".png" + """; startInfo.UseShellExecute = false; startInfo.CreateNoWindow = true; startInfo.WindowStyle = ProcessWindowStyle.Hidden; startInfo.RedirectStandardError = true; startInfo.RedirectStandardOutput = true;
process = Process.Start(startInfo); process.WaitForExit(5000); // wait no more than 5 seconds
if (process.HasExited) { //good } else{ //abort everything }
Loading images into ImageList & ListView:
void previewSelectedPresentation(string presentationName)
{
previewImageList.Images.Clear();
previewListView.Items.Clear();
DirectoryInfo dir = new DirectoryInfo(@"E:\\test\\" + presentationName);
foreach (FileInfo file in dir.GetFiles())
{
try
{
this.previewImageList.Images.Add(Image.FromFile(file.FullName));
}
catch
{
Console.WriteLine("This is not an image file");
}
}
for (int j = 0; j < this.previewImageList.Images.Count; j++)
{
ListViewItem item = new ListViewItem();
item.ImageIndex = j;
item.Text = (j + 1).ToString();
this.previewListView.Items.Add(item);
}
}
gc
is bad? – Tudor