Hi ,
I've tried the following code to insert a png file to a zip file. But I didn't find any compression happened.
Please help.
.Open, iso)
(fs)
"Resources/Images/"
.CreateDirectory(FolderPath) zFile.Entries.Add(newDir)
zFile.Entries.Add(newDir)
"Image_0.png"
.CreateFile(EntryName, FolderPath, EntryContent) zFile.Entries.Add(newFile) zFile.CompressionLevel =
zFile.Entries.Add(newFile)
zFile.CompressionLevel =
.Level9
.Create, iso)
Hello eldhosembabu,
First thing that pops into your mind looking at your code is ZipFile object contents is saved only after call to Save(Steam) method. It is not enough to add the entry into the Entries connection of ZipFile.
Another thing you do not need to add an entry for the directory where you want the image file to be put in. The Compression Library will check out the path for every entry and if a dir is not preasant it will create it for you.
And finally the Compression Library is not able to add an entry to an archive directly(I mean using the approach you used in your code) if some of its input is provided through streams. This basically means that if you have instatiated your ZipFile using the constructor which takes a stream and/or try to add an ZipEntry which is created by a stream Save operation wont be successful.
In your case you have two possible approaches to workaround this limitation:
The first one is to read the stream containing the zip file in a byte Array and providing it to the ZipFile's constructor. You will need to do the same with the stream containing the image when createing the ZipEntry you want to add to the archive. And finally you should call ZipFile.Save() method so the changed ZIpFileObject to be saved:
private void btnLoad_Click(object sender, RoutedEventArgs e) { var openFileDialog = new OpenFileDialog(); openFileDialog.ShowDialog(); using (var fs = new IsolatedStorageFileStream("Template.zip", FileMode.Open, iso)) { byte[] buffer = new byte[fs.Length]; int n, totalBytesRead = 0; do { n = fs.Read(buffer, totalBytesRead, buffer.Length); totalBytesRead += n; } while (n > 0); zFile = new ZipFile(buffer); } var folderPath = "Resources/Images/"; string fileName = "Image_0.png"; var EntryContent = new IsolatedStorageFileStream(fileName, FileMode.Open, iso); ZipEntry newEntry = ZipEntry.CreateFile(fileName, folderPath, ReadStream(EntryContent)); zFile.Entries.Add(newEntry); using (var fs = new IsolatedStorageFileStream("Template.zip", FileMode.CreateNew, iso)) { zFile.Save(fs); } } private byte[] ReadStream(Stream s) { byte[] buffer = new byte[s.Length]; int n, totalBytesRead = 0; do { n = s.Read(buffer, totalBytesRead, buffer.Length); totalBytesRead += n; } while (n > 0); return buffer; }
2. Your second option is to load your zip file and then to copy its entries into new ZIpFile object and then to save the second ZipFile over the original source. Here is a code sample:
public partial class MainPage : UserControl { public ZipFile _zipFile; public ZipFile _zipFile2; public MainPage() { InitializeComponent(); } //Ok private void btnLoad_Click(object sender, RoutedEventArgs e) { var openFileDialog = new OpenFileDialog(); openFileDialog.ShowDialog(); using (var fileStream = openFileDialog.File.OpenRead()) { _zipFile = new ZipFile(fileStream); _zipFile2 = new ZipFile(); //zipFile2.Save(x); ZipEntry zipEntry; foreach (ZipEntry entry in this._zipFile) { if (entry.IsDirectory) { zipEntry = ZipEntry.CreateDirectory(entry.FileName, "/"); } else { //zipEntry = ZipEntry.CreateFile(entry.FileName, "/", entry.) CrcCalculatorStream crcStream = entry.OpenReader(); byte[] buffer = new byte[crcStream.Length]; int n, totalBytesRead = 0; do { n = crcStream.Read(buffer, 0, buffer.Length); totalBytesRead += n; } while (n > 0); zipEntry = ZipEntry.CreateFile(entry.FileName, "/", buffer); } _zipFile2.Entries.Add(zipEntry); } } } private void btnSave_Click(object sender, RoutedEventArgs e) { if (_zipFile2 != null) { var saveFileDialog = new SaveFileDialog(); saveFileDialog.ShowDialog(); using (var fileStream = saveFileDialog.OpenFile()) { _zipFile2.Save(fileStream); } } } }Hope that helps.
Hi,
As You said I've used the following code :
AddImageToZip()
= ReadStream(fs)
(byteArr)
= ReadStream(EntryContent)
.CreateFile(EntryName, FolderPath, contentByteArr) zFile.Entries.Add(newFile) zFile.CompressionLevel =
.BestCompression
.Create, iso) zFile.Save(newFS) newFS.Close() EntryContent.Close() fs.Close()
zFile.Save(newFS)
newFS.Close()
EntryContent.Close()
fs.Close()
Sub
()
MemoryStream
s.CopyTo(ms)
ms.ToArray()
Function
But I didn't find any compression happening.
Please find the attached sample.
Hi eldhosembabu,
Zip Library does not try to apply any compression on files with following extension mp3, png, docx, xlsx, pptx, jpg, zip because it is expected that these files are already compressed and if Zip Library applies compression on them it is highly possible that their size will expand.
You could override this behavior by using WantCompression property of ZipFile object as follows:
_zipFile.WantCompression = new WantCompressionCallback((localFileName,fileNameInArchive) => { //put your logic here which will decide which file will be compressed //it is called for every zip entry return true;});For more information on WantCompression property check out this help page.HTH
But when I use the SharpZip Library which is available free, it is compressing it to around 1/4th of its original size..
Compression Library uses Deflate compression algorithm to compress its entries. When I enabled the compression(as explained in my previous post) I managed to compress "Image_0.png" from the sample you've provided earlier from 1.08 MB to 180KB which is around 6 times decrease of its original size!
Regards
Thanks.....:)