Is there any way to write EXIF data in PNG using c# - c#

I know that EXIF MetaData is not supported in PNG (as per W3C), but i have a tool which can inject EXIF MetaData in PNG in zTXt block, i have searched everywhere but did'nt find anyway how to write EXIF data in PNG using c# using sqtquery or any other way.

As long as you can write your data as text, this is a straightforward solution:
public void WriteTextInPngFile(string filename, string description, string otherText)
{
Stream pngStream = new System.IO.FileStream(filename, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite);
PngBitmapDecoder pngDecoder = new PngBitmapDecoder(pngStream, BitmapCreateOptions.PreservePixelFormat, BitmapCacheOption.Default);
BitmapFrame pngFrame = pngDecoder.Frames[0];
InPlaceBitmapMetadataWriter pngInplace = pngFrame.CreateInPlaceBitmapMetadataWriter();
if (pngInplace.TrySave() == true)
{
pngInplace.SetQuery("/Text/Description", description);
pngInplace.SetQuery("/Text/YourField", otherText);
}
pngStream.Close();
}
You have to set the following references:
PresentationCore
System.Xaml
WindowsBase
This example is based on the help of BitmapFrame Class

Related

How to convert file .DEX (Dexis image file) to jpg image format using c#

I writing a program that it can read .Dex file (Dexis X-ray image file) and convert it to jpg image. but i can't find out how to decode it.
i use this code to read and convert but the image is corrupt.
Read Image:
public static byte[] ImageToByte(string IMG_PATH)
{
byte[] img = null;
try
{
FileStream IM_STREAM = new FileStream(IMG_PATH, FileMode.Open, FileAccess.Read);
BinaryReader IM_BNR = new BinaryReader(IM_STREAM);
img = IM_BNR.ReadBytes((int)IM_STREAM.Length);
IM_BNR.Close();
IM_STREAM.Close();
}
catch (Exception ex)
{
StreamWriter swr = new StreamWriter("LOG.txt", true, Encoding.UTF8);
swr.WriteLine(ex.Message);
swr.Close();
}
return img;
}
Convert Image:
public static void SaveToFile(string path, byte[] b)
{
MemoryStream ms = new MemoryStream(b);
Image img = Image.FromStream(ms);
img.Save(path + "\\exam.jpg", System.Drawing.Imaging.ImageFormat.Jpeg);
img.Dispose();
}
The image before convert (.Dex, size 800x600px) -> after convert (.jpg, size 80x60). plz help me.
.dex is a semi-proprietary format. Using standard image decoding libraries the result you are seeing is the best you can do. If you are looking for a paid solution I know of a team that is currently working on a web services API for this but it hasn't been released publicly yet. If you'd be interested in being an early tester I can put you in touch.

BitMapEncoder in MonoTouch

I'm currently in the process of converting some standard C# files so they work in a MonoTouch iPhone application, however I have hit a wall with this method:
private void WriteTestFile(CGBitmapContext bitmapImage, string fileName)
{
try
{
using (FileStream stream5 = new FileStream(fileName, FileMode.Create))
{
BitmapEncoder encoder5 = new BmpBitmapEncoder();
encoder5.Frames.Add(BitmapFrame.Create(bitmapImage));
encoder5.Save(stream5);
stream5.Close();
}
}
catch (UnauthorizedAccessException)
{
// Do nothing
}
}
I can't seem to find any equivalent to the BitmapEncoder class and I have no idea how to approach converting this part of the code, can anyone suggest a route to take?
Note: The original code used a WritableBitMap in pace of the CGBitmapContext.
I know nothing about MonoTouch nor iPhone.
However it looks like the function is just trying to save the bitmap image as BMP file. There must be an function in CGBitmapContext to Save to a file or some other class than can save a bitmap.
EDIT
After further search, it looks like you should convert CGBitmapContext to a UIImage and then save it; seet How do I save an UIImage as BMP?

Save WriteableBitmap to file using WPF

I have:
WriteableBitmap bmp;
I basicly want to save it into a file on the disk like the following:
C:\bmp.png
I read some forums which mentions to read:
bmp.Pixels
and save those pixels into a Bitmap then use Bitmap.SaveImage() function. However, I can't access any Pixels. Apperantly my WriteableBitmap does not have any property named Pixels.
I use .NET Framework 4.0.
Use your WriteableBitmap's clone and use this function as below:
CreateThumbnail(filename, _frontBitmap.Clone());
...
void CreateThumbnail(string filename, BitmapSource image5)
{
if (filename != string.Empty)
{
using (FileStream stream5 = new FileStream(filename, FileMode.Create))
{
PngBitmapEncoder encoder5 = new PngBitmapEncoder();
encoder5.Frames.Add(BitmapFrame.Create(image5));
encoder5.Save(stream5);
}
}
}

ArgumentException when loading image from byte array using JpegBitmapDecoder

I'm having some trouble reading JPEG files in my class. I need to load metadata and bitmap from a JPEG file. So far, I have this:
public void Load()
{
using (Stream imageStream = File.Open(this.FilePath, FileMode.Open, FileAccess.Read, FileShare.Read))
{
BitmapDecoder decoder = new JpegBitmapDecoder(imageStream, BitmapCreateOptions.PreservePixelFormat, BitmapCacheOption.OnLoad);
BitmapSource source = decoder.Frames[0];
// load metadata
this.metadata = source.Metadata as BitmapMetadata;
// prepare buffer
int octetsPerPixel = source.Format.BitsPerPixel / 8;
byte[] pixelBuffer = new byte[source.PixelWidth * source.PixelHeight * octetsPerPixel];
source.CopyPixels(pixelBuffer, source.PixelWidth * octetsPerPixel, 0);
Stream pixelStream = new MemoryStream(pixelBuffer);
// load bitmap
this.bitmap = new Bitmap(pixelStream); // throws ArgumentException
}
this.status = PhotoStatus.Loaded;
}
But the Bitmap constructor throws an ArgumentException when trying to create a Bitmap instance from a stream.
The documentation says:
System.ArgumentException
stream does not contain image data or is null.
-or-
stream contains a PNG image file with a single dimension greater than 65,535 pixels.
I'm not sure, what I did wrong. Can you please help me?
You're using the Bitmap constructor which is usually used to load an image file in a known format - JPEG, PNG etc. Instead, you've just got a bunch of bytes, and you're not telling it anything about the format you want to use them in.
It's not clear why you want to use BitmapDecoder and BitmapSource at all - why aren't you just using:
Stream imageStream = File.Open(this.FilePath, FileMode.Open,
FileAccess.Read, FileShare.Read));
this.bitmap = new Bitmap(imageStream);
Note that you mustn't use a using statement here - the Bitmap "owns" the stream after you've called the constructor.
Aside from all of this, you seem to be trying to mix WPF and WinForms ideas of images, which I suspect is a generally bad idea :(

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?

Categories