Reading gif file from base64 into picturebox any other way? C# - c#

I Have gif image in base64.
Currently I am approaching this way. reading base64 gif file and writing it to byte array and writing it back to image file to disk and reading from the file to picturebox.image.
byte[] imageBytes = Convert.FromBase64String(body);
//* this is write file to disk and read
string filename = Username;
File.WriteAllBytes(filename, imageBytes);
fs = new FileStream(filename, FileMode.Open, FileAccess.Read);
pictureBox1.Image = Image.FromStream(fs);
Now, I want to write it to memory without writing it to disk file. like in a form of variable image. that can be assigned to picturebox. Is there any possible of this. because I have to do repeatedly many times for many images.
So I would like find a different approach without writing saving file to disk and reading it again.
Any help appreciated.

byte[] imageBytes = Convert.FromBase64String(body);
MemoryStream stream = new MemoryStream(imageBytes);
pictureBox1.Image = Image.FromStream(stream);

byte[] imageBytes = Convert.FromBase64String(body);
using (var ms = new MemoryStream(imageBytes))
{
pictureBox1.Image = Image.FromStream(ms);
}
Be aware the MemoryStream class is IDisposable so you should Dispose() it. This can happen with using or with try/catch/finally block.

Related

System.Drawing.Image data is different between saving to a file and a stream

I have an image in the png format which I would like to load and convert to a bmp stream. The code I'm using to achieve this is the following:
// Image.FromFile yields the same result.
FileStream originalFile = File.Open("image.png", FileMode.Open);
System.Drawing.Image fileImage = System.Drawing.Image.FromStream(originalFile);
MemoryStream bmpStream = new MemoryStream();
fileImage.Save(bmpStream, System.Drawing.Imaging.ImageFormat.Bmp);
Result: https://pastebin.com/raw/p1TBjnD1
However the stream this produces is different from when saving to a file and opening it like this:
FileStream originalFile = File.Open("image.png", FileMode.Open);
System.Drawing.Image fileImage = System.Drawing.Image.FromStream(originalFile);
FileStream bmpStream;
fileImage.Save("image.bmp", System.Drawing.Imaging.ImageFormat.Bmp);
bmpStream = File.Open("image.bmp", FileMode.Open);
Result: https://pastebin.com/raw/vSdRwZpL
There appears to be some kind of header missing when saving to a stream. Why is this, and how can I easily add it to my streams without having to save to files?
My question is not how to do this, but why the stream doesn't include this header while the file does.
They are not different but when you dump or copy or do something else with memory stream you always have to reset it to its initial position.
fileImage.Save(bmpStream, System.Drawing.Imaging.ImageFormat.Bmp);
bmpStream.Position = 0
... now you can dump or save to file from bmpStream
If you do not reset the position, you might read nothing back from the MemoryStream. In the case of Image.Save(), it is even more tricky because the Save method puts the MemoryStream position at the beginning of the image data (after the header) assuming this is what you want.

FileStream to Bitmap - Parameter is not valid

I have read the posts on this subject but none of them explains it to me clearly enough to be able to fix the problem.
I am trying to upload a file from a local directory to the server.
Here is my code:
string fullPath = Path.Combine(
AppDomain.CurrentDomain.BaseDirectory + #"Images\Readings", PhotoFileName);
Stream s = System.IO.File.OpenRead(fileUpload);
byte[] buffer = new byte[s.Length];
s.Read(buffer, 0, Convert.ToInt32(s.Length));
using (FileStream fs = new FileStream(fullPath, FileMode.Create))
{
fs.Write(buffer, 0, Convert.ToInt32(fs.Length));
Bitmap bmp = new Bitmap((Stream)fs);
bmp.Save(fs, ImageFormat.Jpeg);
}
I keep on getting an Argument Exception: "Parameter is not valid" on line:
Bitmap bmp = new Bitmap((Stream)fs);
Can anyone explain this to me please
There are at least two problems, probably three. First, your copying code is broken:
byte[] buffer = new byte[s.Length];
s.Read(buffer, 0, Convert.ToInt32(s.Length));
You've assumed that this will read all of the data in a single Read call, and ignored the return value for Read. Generally, you'd need to loop round, reading data and writing it (the amount you've just read) to the output stream, until you read the end. However, as of .NET 4, Stream.CopyTo makes this much simpler.
Next is how you're creating the bitmap:
using (FileStream fs = new FileStream(fullPath, FileMode.Create))
{
fs.Write(buffer, 0, Convert.ToInt32(fs.Length));
Bitmap bmp = new Bitmap((Stream)fs);
bmp.Save(fs, ImageFormat.Jpeg);
}
You're trying to read from the stream when you've just written to it - but without "rewinding"... so there's no more data left to read.
Finally, I would strongly advise against using Bitmap.Save to write to the same stream that you're loading the bitmap from. Bitmap will keep a stream open, and read from it when it needs to - if you're trying to write to it at the same time, that could be very confusing.
It's not clear why you're using Bitmap at all, to be honest - if you're just trying to save the file that was uploaded, without any changes, just use:
using (Stream input = File.OpenRead(fileUpload),
output = File.Create(fullPath))
{
input.CopyTo(output);
}
This is assuming that fileUpload really is an appropriate filename - it's not clear why you haven't just written the file to the place you want to write it to straight away, to be honest. Or use File.Copy to copy the file. The above code should work with any stream, so you can change it to save the stream straight from the request...

Generic GDI+ error (error number -2147467259)

My friends,
I am trying convert a image to a Base64 String in a c# console app (.net 4.0).
The method:
public static String ConvertBitmapToBase64String(Bitmap bitmap,
ImageFormat imageFormat)
{
String generatedString = string.Empty;
MemoryStream memoryStream = new MemoryStream();
bitmap.Save(memoryStream, imageFormat);
memoryStream.Position = 0;
byte[] byteBuffer = memoryStream.ToArray();
memoryStream.Close();
generatedString = Convert.ToBase64String(byteBuffer);
byteBuffer = null;
return generatedString;
}
But when I invoke this method it is throwing an exception saying: "generic gdi+ error" and the error number is -2147467259.
Invoker code:
StreamReader streamReader = new StreamReader(#"C:\Anita.jpg");
Bitmap bitmap = new Bitmap(streamReader.BaseStream);
streamReader.Close();
String base64String = ImageUtil.ConvertBitmapToBase64String(bitmap, ImageFormat.Jpeg);
Anybody can give me a help?
Thanks.
The only likely problem I see is that the image is too large or big. Perhaps, instead of using a MemoryStream, you can use File.ReadAllBytes directly instead of passing around the Bitmap object, saving directly to a MemoryStream, and saving.
Also, you're reading the data in with a StreamReader, which is meant for text! Moving to just reading the bytes into an array and calling Convert.ToBase64String() should handle what you want to do.

OutOfMemory exception when loading an image in .Net

Im loading an image from a SQL CE db and then trying to load that into a PictureBox.
I am saving the image like this:
if (ofd.ShowDialog() == DialogResult.OK)
{
picArtwork.ImageLocation = ofd.FileName;
using (System.IO.FileStream fs = new System.IO.FileStream(ofd.FileName, System.IO.FileMode.Open))
{
byte[] imageAsBytes = new byte[fs.Length];
fs.Read(imageAsBytes, 0, imageAsBytes.Length);
thisItem.Artwork = imageAsBytes;
fs.Close();
}
}
and then saving to the Db using LINQ To SQL.
I load the image back like so:
using (FileStream fs = new FileStream(#"C:\Temp\img.jpg", FileMode.CreateNew ,FileAccess.Write ))
{
byte[] img = (byte[])encoding.GetBytes(ThisFilm.Artwork.ToString());
fs.Write(img, 0, img.Length);
}
but am getting an OutOfMemoryException. I have read that this is a slight red herring and that there is probably something wrong with the filetype, but i cant figure what.
Any ideas?
Thanks
picArtwork.Image = System.Drawing.Bitmap.FromFile(#"C:\Temp\img.jpg");
Based on the code you provided it seems like you are treating the image as a string, it might be that data is being lost with the conversion from byte[] to string and string to byte[].
I am not familiar with SQL CE, but if you can you should consider treating the data as a byte[] and not encoding to and from string.
I base my assumption in this line of code
byte[] img = (byte[])encoding.GetBytes(ThisFilm.Artwork.ToString());
The GDI has the bad behavior of throwing an OOM exception whenever it is not capable of understanding a certain image format. Use Irfanview to see what kind of image that really is, it is likely GDI can't handle it.
My advice would be to not use a FileStream to load images unless you need access to the raw bytes. Instead, use the static methods provided in Bitmap or Image objects:
Image img = Image.FromFile(#"c:\temp\img.jpg")
Bitmap bmp = Bitmap.FromFile(#"c:\temp\img.jpg")
To save the file use .Save method of the Image or Bitmap object:
img.Save(#"c:\temp\img.jpg")
bmp.Save(#"c:\temp\img.jpg")
Of course we don't know what type ArtWork is. Would you care to share that information with us?

Convert GD-Sharp stream to Bitmap

im currently trying out GD-Sharp and wanted to convert the graphic into bitmap without saving it to image file.
GD-Sharp method to save to stream is
bool GB.Save(Stream outStream);
for saving using stream is
using(FileStream fs = File.OpenWrite(#"stream1.jpg"))
{
image.Save((System.IO.Stream)fs);
fs.Close();
}
since bitmap supports stream, how do it convert GD-Sharp to Bitmap ? thanks.
You can use a MemoryStream, something like
gdsBitmap.Save(memStream);
memStream.Seek(0);
gdiBitmap = Bitmap.FromStream(memStream);
i did something like this.
MemoryStream memStream = new MemoryStream();
gdimg.Save(memStream);
Bitmap bmp2 = new Bitmap(memStream);

Categories