I am using Chart Control of .NET 4.0 framework in Windows Forms Application i have been saving Pie Chart image on location through PieChart.SaveImage(Path,ChartImageFormat.Png), when i create doc file with Microsoft.Office.Interop.Word i paste that image in that document. it proceed first time very well and .doc created successfully, but i try to save pie chart 2nd time during win forms Running it give an System.IO.Exception
"The process cannot access the file 'path' because it is being used by
another process."
When i terminate program and run it again it over wright previous image but when i want to save image 2nd time during program running it gives same Exception
This is how i am saving image
private Void SavePieChart()
{
string PieChartPath= Application.StartupPath + #"\Chart.png";
PieChart.SaveImage(PieChartPath, ChartImageFormat.Png);
}
I searched, but did not find any efficient solution which solve my problem,
If anything doing wrong Kindly Point out my mistake, or any helping link to solve this. .
EDIT 1
This is where I am pasting that image in Doc file
System.Drawing.Image PieChart =System.Drawing.Image.FromFile(PieChartPath);
oHeader1 = oDoc.Content.Paragraphs.Add(ref oMissing);
Logothread = new Thread(() => Clipboard.SetImage(PieChart));
Logothread.SetApartmentState(ApartmentState.STA); //Set the thread to STA
Logothread.Start();
Logothread.Join();
oHeader1.Range.Paste();
oHeader1.Range.ParagraphFormat.Alignment = WdParagraphAlignment.wdAlignParagraphCenter;
oHeader1.Range.InsertParagraphAfter();
Thanks in advance
Problem is when i wast pasting image in doc file i was take image like
System.Drawing.Image PieChart =System.Drawing.Image.FromFile(PieChartPath);
as Reza and Taw described FromFile() keeps the file in use so that's why when i try to save image 2nd time it shows exception the file is already in process,
The i use FromStram() add this into my code
byte[] DataBytes= System.IO.File.ReadAllBytes(PieChartPath);
System.IO.MemoryStream ms = new System.IO.MemoryStream(DataBytes);
System.Drawing.Image PieChart = System.Drawing.Image.FromStream(ms);
Related
Having a code that works for ages when loading and storing images, I discovered that I have one single image that breaks this code:
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
i.Save(i2Path, ImageFormat.Jpeg);
The exception is:
System.Runtime.InteropServices.ExternalException occurred
A generic error occurred in GDI+.
at System.Drawing.Image.Save(String filename, ImageCodecInfo encoder, EncoderParameters encoderParams)
at System.Drawing.Image.Save(String filename, ImageFormat format)
at ...
As far as I can see, there is nothing special about the image. It is approx 250 pixels in size and can be opened in e.g. Windows Image Viewer or Paint.NET:
(Since the image above, after being uploaded to Stack Overflow does not produce the error anymore, I've put the original image here)
What I discovered is that upon calling the Save method, the destination image file is being created with zero bytes.
I am really clueless on what causes the error.
My questions:
Can you think of any special thing that would hinder .NET from saving the image?
Is there any way (beside panicing) to narrow down these kind of errors?
While I still did not find out the reason what exactly caused the error when saving the image, I found a workaround to apply:
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
var i2 = new Bitmap(i);
i2.Save(i2Path, ImageFormat.Jpeg);
I.e. by copying the image internally into a Bitmap instance and saving this image instead of the original image, the error disappeared.
I'm assuming that by copying it, the erroneous parts the caused the original Save call to fail are being removed an/or normalized, thus enabling the save operation to succeed.
Interestingly, the so stored image has a smaller file on disk (16 kB) than its original source (26 kB).
First of all make sure, that the desired folder has Read/Write permissions. Changing the permissions solved this problem for me.
Solution is here, you must dispose image object to release the memory on the server.
Try use using statement. Make sure destination directory on server exists too.
The reason may be that the image is loaded lazily and the loading process is not yet finished when you try to save it.
Following what's said in this blog post (assuming you're German by the picture you linked in your question) provides a possible solution. Also this SO question's accepted answer indicates this is due to the fact the image file you're trying to save to is locked.
EDIT
For Ulysses Alves, from the linked blog entry: If you load an image using Image.FromFile() it remains locked until it is disposed of. This prevents calls to Save().
pictureBox1.Image = Image.FromFile("C:\\test\\test1.jpg");
pictureBox1.Image.Save("C:\\test\\test2.jpg");
The above code throws an error.
To make it work, you need to copy the image. The following code works:
pictureBox1.Image = Image.FromFile("C:\\test\\test1.jpg");
Image copy = pictureBox1.Image;
copy.Save("C:\\test\\test2.jpg")
I found this question because I also faced the similar error and the file was actually created with zero length (if you don't see any file, first check the permissions to write into folder as other answers suggest). Although my code was slightly different (I use stream to read the image from memory, not from file), I think my answer may be helpful to anyone facing similar problem.
It may looks counter-intuitive, but you can't really dispose memory stream until you finish with image.
NOT WORKING:
Image patternImage;
using (var ms = new MemoryStream(patternBytes)) {
patternImage = new Bitmap(ms);
}
patternImage.Save(patternFile, ImageFormat.Jpeg);
Just don't dispose the stream until you done with image.
WORKS:
using (var ms = new MemoryStream(patternBytes)) {
patternImage = new Bitmap(ms);
patternImage.Save(patternFile, ImageFormat.Jpeg);
}
What is misleading:
Error message doesn't really tell you anything
You can see the image properties, like width and height, but can't
save it
my solution was to make, write temp content (File.WriteAllText) just before saving the file
Here is the code:
var i = Image.FromFile(i1Path);
File.WriteAllText(i2Path, "empty"); // <---- magic goes here
i.Save(i2Path, ImageFormat.Jpeg);
Please try and let me know
In my case I have accidentally deleted the directory where image was getting stored.
Key Information:
// Using System.Drawing.Imaging:
new Bitmap(image).Save(memoryStream, ImageFormat.Jpeg);
You MUST Cast the Image to a Bitmap to Save it.
Using:
// Using System.Drawing.Imaging:
image.Save(memoryStream, ImageFormat.Jpeg);
WILL throw the Error:
Generic GDI+ error when saving an image
Just use the visual studio as administrator or run the application created by the code as administrator it should work smoothly.
It is user access rights issue.
I faced the same and resolved it by running visual studio as administrator.
In my case, I set validateImageData to false:
Image.FromStream(stream, validateImageData: false);
solution:
Image.FromStream(stream, validateImageData: true);
Open in the program
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
i.Save(i2Path, ImageFormat.Jpeg);
i.Dispose();
I tried this:
string[] files = System.IO.Directory.GetFiles(combinedsatelliteimagesdir);
NumericComparer ns = new NumericComparer();
Array.Sort(files, ns);
pictureBox1.Image = Image.FromFile(files[files.Length -1]);
But i'm getting out of memory exception on the line:
pictureBox1.Image = Image.FromFile(files[files.Length -1]);
the variable files contain 847 indexs for example the first index look like:
C:\Users\user\AppData\Local\mws\My Weather Station\satelliteImages\SatImage0.GIF
From msdn, you get OutOfMemoryException if
The file does not have a valid image format.
-or-
GDI+ does not support the pixel format of the file.
You probably reading some non-image file.
Regarding thumbs.db:
Thumbs.db is an image cache which makes thumbnail viewing faster. The file is automatically created in Windows Vista, 7 and 8 whenever images are encountered in a folder. It's usually hidden but can appear, disappear and is often impossible to delete
try this one
pictureBox1.Image = Image.FromFile(#files[files.Length - 1]);
By the way, are you sure that last file is every time a picture? No hidden "desktop.ini" or something else?
I have created a button where it can upload all the pic files as well as the doc files and the PDF files in the system.
Here is the code for the following:
if (dlg.ShowDialog() == DialogResult.OK)
{
pictureBox2.Image = Image.FromFile(dlg.FileName);
pictureBox2.SizeMode = PictureBoxSizeMode.Zoom;
currentFileName = dlg.FileName;
button2.Enabled = true;
}
}
But i have a error poping out when i want upload a doc files. First of all is it possible to upload a doc file? if yes, then i have a issues showing out of memory in the following line of code
pictureBox2.Image = Image.FromFile(dlg.FileName);
PictureBox control is used only for showing images in a WinForm application (take a look at MSDN). To show .doc file contents in your application you have to use word or some workaround (like posted here)
The reason why you get that error is because a doc file is not a valid image format.
This is outlined in the documentation: http://msdn.microsoft.com/en-us/library/stf701f5.aspx
it is possible to upload a doc file but not in the context you want, i.e. using Image.FromFile and assign it to a picture box object.
http://msdn.microsoft.com/en-us/library/stf701f5.aspx
Out of Memory exception covered in that topic.
The FromFile method will throw an exception if the file type is invalid.
You should do necessary checks on the file type's compatibility first, not to mention wrap a try catch around this method to ensure you're coding as defensively as possible.
Please take reference at the link from MSDN. It will throw OutOfmemoryException when you loading a picture have not appropriate format.
To resolve your problem you should check format of the picture file more than loading directly as above.
Please reference at here to know how can you detect format of an image file.
To loading PDF or Word document you should take reference here.
I was investigating an interesting thing. I want to get Image from Clipboard in my C# program.
Code sample:
[STAThread]
public Image GetClipboardImage()
{
MessageBox.Show("try to get image");
Image returnImage = null;
if (Clipboard.ContainsImage())
{
MessageBox.Show("getting image");
returnImage = Clipboard.GetImage();
}
return returnImage;
}
When I try to get an image that was copied to clipboard from any website the code above works quite good. But it doesn't work when I am copying an image from my computer (I mean desktop for example). Clipboard.ContainsImage() returns false in the second case.
One more difference between copying from web and from desktop:
In the first case I cannot paste the image from Clipboard to folder on my computer.
Of course in the second case it can be done.
It seems that in the second case there is one real image and one file which contains this image. But I am not sure whether it can be.
So, what's the issue in my situation and how I can resolve it?
The next code demonstrate an appropriate solution
IDataObject myDataObject = Clipboard.GetDataObject();
string[] files = (string[])myDataObject.GetData(DataFormats.FileDrop);
MessageBox.Show(files[0]);
You will show massagebox with the full path to the file you have copied to clipboard before.
Having a code that works for ages when loading and storing images, I discovered that I have one single image that breaks this code:
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
i.Save(i2Path, ImageFormat.Jpeg);
The exception is:
System.Runtime.InteropServices.ExternalException occurred
A generic error occurred in GDI+.
at System.Drawing.Image.Save(String filename, ImageCodecInfo encoder, EncoderParameters encoderParams)
at System.Drawing.Image.Save(String filename, ImageFormat format)
at ...
As far as I can see, there is nothing special about the image. It is approx 250 pixels in size and can be opened in e.g. Windows Image Viewer or Paint.NET:
(Since the image above, after being uploaded to Stack Overflow does not produce the error anymore, I've put the original image here)
What I discovered is that upon calling the Save method, the destination image file is being created with zero bytes.
I am really clueless on what causes the error.
My questions:
Can you think of any special thing that would hinder .NET from saving the image?
Is there any way (beside panicing) to narrow down these kind of errors?
While I still did not find out the reason what exactly caused the error when saving the image, I found a workaround to apply:
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
var i2 = new Bitmap(i);
i2.Save(i2Path, ImageFormat.Jpeg);
I.e. by copying the image internally into a Bitmap instance and saving this image instead of the original image, the error disappeared.
I'm assuming that by copying it, the erroneous parts the caused the original Save call to fail are being removed an/or normalized, thus enabling the save operation to succeed.
Interestingly, the so stored image has a smaller file on disk (16 kB) than its original source (26 kB).
First of all make sure, that the desired folder has Read/Write permissions. Changing the permissions solved this problem for me.
Solution is here, you must dispose image object to release the memory on the server.
Try use using statement. Make sure destination directory on server exists too.
The reason may be that the image is loaded lazily and the loading process is not yet finished when you try to save it.
Following what's said in this blog post (assuming you're German by the picture you linked in your question) provides a possible solution. Also this SO question's accepted answer indicates this is due to the fact the image file you're trying to save to is locked.
EDIT
For Ulysses Alves, from the linked blog entry: If you load an image using Image.FromFile() it remains locked until it is disposed of. This prevents calls to Save().
pictureBox1.Image = Image.FromFile("C:\\test\\test1.jpg");
pictureBox1.Image.Save("C:\\test\\test2.jpg");
The above code throws an error.
To make it work, you need to copy the image. The following code works:
pictureBox1.Image = Image.FromFile("C:\\test\\test1.jpg");
Image copy = pictureBox1.Image;
copy.Save("C:\\test\\test2.jpg")
I found this question because I also faced the similar error and the file was actually created with zero length (if you don't see any file, first check the permissions to write into folder as other answers suggest). Although my code was slightly different (I use stream to read the image from memory, not from file), I think my answer may be helpful to anyone facing similar problem.
It may looks counter-intuitive, but you can't really dispose memory stream until you finish with image.
NOT WORKING:
Image patternImage;
using (var ms = new MemoryStream(patternBytes)) {
patternImage = new Bitmap(ms);
}
patternImage.Save(patternFile, ImageFormat.Jpeg);
Just don't dispose the stream until you done with image.
WORKS:
using (var ms = new MemoryStream(patternBytes)) {
patternImage = new Bitmap(ms);
patternImage.Save(patternFile, ImageFormat.Jpeg);
}
What is misleading:
Error message doesn't really tell you anything
You can see the image properties, like width and height, but can't
save it
my solution was to make, write temp content (File.WriteAllText) just before saving the file
Here is the code:
var i = Image.FromFile(i1Path);
File.WriteAllText(i2Path, "empty"); // <---- magic goes here
i.Save(i2Path, ImageFormat.Jpeg);
Please try and let me know
In my case I have accidentally deleted the directory where image was getting stored.
Key Information:
// Using System.Drawing.Imaging:
new Bitmap(image).Save(memoryStream, ImageFormat.Jpeg);
You MUST Cast the Image to a Bitmap to Save it.
Using:
// Using System.Drawing.Imaging:
image.Save(memoryStream, ImageFormat.Jpeg);
WILL throw the Error:
Generic GDI+ error when saving an image
Just use the visual studio as administrator or run the application created by the code as administrator it should work smoothly.
It is user access rights issue.
I faced the same and resolved it by running visual studio as administrator.
In my case, I set validateImageData to false:
Image.FromStream(stream, validateImageData: false);
solution:
Image.FromStream(stream, validateImageData: true);
Open in the program
const string i1Path = #"c:\my\i1.jpg";
const string i2Path = #"c:\my\i2.jpg";
var i = Image.FromFile(i1Path);
i.Save(i2Path, ImageFormat.Jpeg);
i.Dispose();