Getting bigger size image while scaling C# - c#

I am trying to scale the original image to 50% and 25% and try to download the scaled image in MVC. I am using the below code which was taken from Google search.
public byte[] ScaleImageByPercent(byte[] imageBuffer, int Percent)
{
using (Stream imageStream = new MemoryStream(imageBuffer))
{
using (Image scaleImage = Image.FromStream(imageStream))
{
float scalePercent = ((float)Percent / 100);
int originalWidth = scaleImage.Width;
int originalHeight = scaleImage.Height;
int originalXPoint = 0;
int originalYPoint = 0;
int scaleXPoint = 0;
int scaleYPoint = 0;
int scaleWidth = (int)(originalWidth * scalePercent);
int scaleHeight = (int)(originalHeight * scalePercent);
using (Bitmap scaleBitmapImage = new Bitmap(scaleWidth, scaleHeight, PixelFormat.Format24bppRgb))
{
scaleBitmapImage.SetResolution(scaleImage.HorizontalResolution, scaleImage.VerticalResolution);
Graphics graphicImage = Graphics.FromImage(scaleBitmapImage);
graphicImage.CompositingMode = CompositingMode.SourceCopy;
graphicImage.InterpolationMode = InterpolationMode.NearestNeighbor;
graphicImage.DrawImage(scaleImage,
new Rectangle(scaleXPoint, scaleYPoint, scaleWidth, scaleHeight),
new Rectangle(originalXPoint, originalYPoint, originalWidth, originalHeight),
GraphicsUnit.Pixel);
graphicImage.Dispose();
ImageConverter converter = new ImageConverter();
return (byte[])converter.ConvertTo(scaleBitmapImage, typeof(byte[]));
}
}
}
}
When i use 3.4MB image its returning 4.7MB in 50% and even worst in 100% its returning 18 MB.
EDIT:
After getting the byte array i am downloading the image using below code. After downloading while i check the file size in disk its showing bigger size.
HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
result.Content = new StreamContent(new MemoryStream(scaledBytes));
result.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
result.Content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream");
return result;
Am i doing the scaling correctly?. Which one i need to change get the lower size image while scaling using above functionality.

Your code works, I believe it's just a matter of image compression, basically you are pushing your byte array to your output stream as is, while you should save it as a jpeg. In my example I use a FileStream for simplicity, in your case you should use your output stream.
Give this a try (just drop any Jpg file on the compiled executable):
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication3
{
class Program
{
static void Main(string[] args)
{
string filePath = System.IO.Path.GetFullPath(args[0]);
byte[] originalImage = System.IO.File.ReadAllBytes(filePath);
byte[] resizedImage = ScaleImageByPercent(originalImage, 50);
using (Stream imageStream = new MemoryStream(resizedImage))
{
using (Image scaleImage = Image.FromStream(imageStream))
{
string outputPath = System.IO.Path.GetDirectoryName(filePath);
outputPath = System.IO.Path.Combine(outputPath, $"{System.IO.Path.GetFileNameWithoutExtension(filePath)}_resized.jpg");
using (FileStream outputFile = System.IO.File.Open(outputPath, FileMode.Create, FileAccess.Write))
{
scaleImage.Save(outputFile, ImageFormat.Jpeg);
}
}
}
}
public static byte[] ScaleImageByPercent(byte[] imageBuffer, int Percent)
{
using (Stream imageStream = new MemoryStream(imageBuffer))
{
using (Image scaleImage = Image.FromStream(imageStream))
{
float scalePercent = ((float)Percent / 100);
int originalWidth = scaleImage.Width;
int originalHeight = scaleImage.Height;
int originalXPoint = 0;
int originalYPoint = 0;
int scaleXPoint = 0;
int scaleYPoint = 0;
int scaleWidth = (int)(originalWidth * scalePercent);
int scaleHeight = (int)(originalHeight * scalePercent);
using (Bitmap scaleBitmapImage = new Bitmap(scaleWidth, scaleHeight, PixelFormat.Format24bppRgb))
{
scaleBitmapImage.SetResolution(scaleImage.HorizontalResolution, scaleImage.VerticalResolution);
Graphics graphicImage = Graphics.FromImage(scaleBitmapImage);
graphicImage.CompositingMode = CompositingMode.SourceCopy;
graphicImage.InterpolationMode = InterpolationMode.NearestNeighbor;
graphicImage.DrawImage(scaleImage,
new Rectangle(scaleXPoint, scaleYPoint, scaleWidth, scaleHeight),
new Rectangle(originalXPoint, originalYPoint, originalWidth, originalHeight),
GraphicsUnit.Pixel);
graphicImage.Dispose();
ImageConverter converter = new ImageConverter();
return (byte[])converter.ConvertTo(scaleBitmapImage, typeof(byte[]));
}
}
}
}
}
}
Here it is the result:
EDIT:
Ok for the webapi interface try doing like this:
HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
using (Stream imageStream = new MemoryStream(resizedImage))
{
using (Image scaleImage = Image.FromStream(imageStream))
{
using (MemoryStream ms = new MemoryStream())
{
scaleImage.Save(ms, ImageFormat.Jpeg);
result.Content = new StreamContent(ms);
result.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
result.Content.Headers.ContentType = new MediaTypeHeaderValue("image/jpeg");
}
}
}
return result;

I think that we can reduce size of image by change PixelFormat type.
You can refer to this Reducing Bitmap bit-size in C#

Related

Image.Save to MemoryStream fails due to size?

I'm using PDFiumSharp to convert a PDF file to a single image, using the following code:
using System;
using System.IO;
using System.Linq;
using PDFiumSharp;
using System.Drawing.Imaging;
using System.Drawing;
using PDFiumSharp.Types;
public class ImageFromPDF
{
private readonly int DPI = 200;
private readonly int PPI = 72;
private int PointsToPixels(double points)
{
return (int)Math.Ceiling(points / PPI * DPI);
}
public MemoryStream Convert(MemoryStream stream)
{
var outputStream = new MemoryStream();
using (var doc = new PdfDocument(stream.ToArray()))
{
var totalHeight = PointsToPixels(doc.Pages.Sum(bm => bm.Height));
var maxWidth = PointsToPixels(doc.Pages.Max(bm => bm.Width));
using (var img = new Bitmap(maxWidth, totalHeight, PixelFormat.Format32bppArgb))
{
img.SetResolution(DPI, DPI);
using (var g = Graphics.FromImage(img))
{
var heightOffset = 0;
foreach (var page in doc.Pages)
{
using (var bitmap = new PDFiumBitmap(PointsToPixels(page.Width), PointsToPixels(page.Height), false))
{
bitmap.Fill(new FPDF_COLOR(255, 255, 255, 255));
page.Render(bitmap);
using (var bmStream = bitmap.AsBmpStream(DPI, DPI))
{
var widthOffset = (maxWidth - bitmap.Width) / 2;
using (var fromStream = Image.FromStream(bmStream, true))
{
g.DrawImage(fromStream, new Point(widthOffset, heightOffset));
heightOffset += bitmap.Height;
}
}
}
}
}
img.Save(outputStream, ImageFormat.Jpeg);
}
}
return outputStream;
}
}
This works fine most of the times, however occasionally I come across a particularly large PDF file (40+ A4 pages) and then the time comes to img.Save(outputStream, ImageFormat.Jpeg) I get A generic error occurred in GDI+.
Is there a limitation either on the Image class or the memory stream that is causing this behaviour, or is there another problem going on here?
And is there a way to solve this without separating the pages (as that is a constraint I'm working under at the moment)?

Decoding Z64 (ZB64) string

I'm working on breaking down ZPL label definitions generated by NiceLabel label making software. For the most part I don't have to worry about decoding the Z64 because it is just encoded graphics and I don't need to change the underlying data.
However I have a line of text that is used as a graphic by the label for some reason probably due to Font's or something.
Anyways, the Z64 or ZB64 string is created by compressing the original data using LZ77 and encoding that as Base64 and then appending a CRC at the end.
TEST STRING FULL EXAMPLE:
:Z64:eJztkDFOxDAQRb81hRsULmBtruECyRwpZYpFGLmg5AhwFKMUuYal9CtL26QwHsbe3RMguv3lz9P85wD3/CWaiZ+56OjqWA44cwKIAyfeXXL1sQ7YWqd54czltTge+VOdOQsXFp8TrLUw9KEW3+6pLU4Zk3mC0ataonSEzU8JMywGCiFcue+c8YLGvYcLF5a+68WFhbvtRs5jdmVkWolj96vgXe/it7eucT+0+gxV5N5RrdTveQpevhnxO+BEfRe0xIzc/EbUzkn3lhLSIH6DdFeu+c39Hb7c7vksfrJryB8vu6A4cxE/NjpK1/6LkJZ3+nL1gaLt3D33/Ed+AehfkrY=:6C38
TEST STRING TARGET EXAMPLE:
eJztkDFOxDAQRb81hRsULmBtruECyRwpZYpFGLmg5AhwFKMUuYal9CtL26QwHsbe3RMguv3lz9P85wD3/CWaiZ+56OjqWA44cwKIAyfeXXL1sQ7YWqd54czltTge+VOdOQsXFp8TrLUw9KEW3+6pLU4Zk3mC0ataonSEzU8JMywGCiFcue+c8YLGvYcLF5a+68WFhbvtRs5jdmVkWolj96vgXe/it7eucT+0+gxV5N5RrdTveQpevhnxO+BEfRe0xIzc/EbUzkn3lhLSIH6DdFeu+c39Hb7c7vksfrJryB8vu6A4cxE/NjpK1/6LkJZ3+nL1gaLt3D33/Ed+AehfkrY=
My Code to Decode / Decompress:
static string DecompressZb64(string compressedString)
{
var b64 = SmartWarehouse.Shared.Utils.Parser.ConvertFromBase64(compressedString);
var encoding = new ASCIIEncoding();
var inBytes = Encoding.ASCII.GetBytes(b64);
var outBytes = new byte[inBytes.Length];
try
{
using (var memoryStream = new MemoryStream())
using (var decompressionStream = new DeflateStream(memoryStream, CompressionMode.Decompress))
{
decompressionStream.Read(outBytes, 0, inBytes.Length);
}
return encoding.GetString(outBytes);
}
catch (Exception e)
{
// TODO: DOcument exception
Console.WriteLine(e.Message);
}
return string.Empty;
}
Current Exception:
Block length does not match with its complement.
Stacktrace:
at System.IO.Compression.Inflater.DecodeUncompressedBlock(Boolean& end_of_block)
at System.IO.Compression.Inflater.Decode()
at System.IO.Compression.Inflater.Inflate(Byte[] bytes, Int32 offset, Int32 length)
at System.IO.Compression.DeflateStream.Read(Byte[] array, Int32 offset, Int32 count)
at SmartWarehouse.Tools.Program.DecompressZb64(String compressedString) in C:\Users\[user_dir]\Source\Repos\Handheld.[user].[fork]\SmartWarehouse.Tools\Program.cs:line 511
UPDATE:
I was looking into this and I found this SO post it is essentially the same issue. So i did some more research and i found this article on a blog from 2007. Which discusses a workaround by skipping the first 2 bytes in the input array due to those bytes not actually being included in the RFC specification.
CODE CHANGE:
static string DecompressZb64(string compressedString)
{
var b64 = Convert.FromBase64String(compressedString);
var encoding = new ASCIIEncoding();
var outBytes = new byte[b64.Length - 2];
try
{
using (var memoryStream = new MemoryStream(b64))
{
memoryStream.ReadByte();
memoryStream.ReadByte();
using (var decompressionStream = new DeflateStream(memoryStream, CompressionMode.Decompress))
{
decompressionStream.Read(outBytes, 0, b64.Length - 2);
}
}
return encoding.GetString(outBytes);
}
catch (Exception e)
{
// TODO: DOcument exception
Console.WriteLine(e.Message);
}
return string.Empty;
}
This code change doesn't actually produce an exception anymore however it doesn't decompress properly and returns this result:
"\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"
That data looks fine to me, I got this image out of it:
It's a monochrome bitmap, one bit per pixel.
Your code didn't read until the end of the stream, there are actually 1280 bytes of image data, which can then be decoded to the image above.
using System;
using System.Diagnostics;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.IO.Compression;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
namespace ZB64Decode
{
public class Program
{
static void Main(string[] args)
{
//this is C#
var sb = new StringBuilder();
sb.AppendLine("^XA");
sb.AppendLine("^UT1,1");
sb.AppendLine("^Uh0,300,64,4000,2,0,F");
sb.AppendLine("^Uh1,300,64,4000,2,0,F");
sb.AppendLine("^UC1,0,1,0,0");
sb.AppendLine("^LH0,0");
sb.AppendLine("^LT0");
sb.AppendLine("^XZ");
sb.AppendLine("^XA");
sb.AppendLine("^PW3543");
sb.AppendLine("^LL512");
sb.AppendLine("^FO532,66^GFA,885,9272,76,:Z64:eJztWkFywyAMDMOBI0/gKTyNPC1P6RN6zKFTNxiCY0AgJE0nh+zJTc0GrdYES1wu/wWzHfiVIuLR2YZpB4FJpZH38UcouP6oRHddogqPEd/9f0WyLzyTGqpsVuLUj5tvoxv8tv3gqSa3WCSZxrjIoMgUzpAGoxnW2wZMdIFHG9tOEhQtekVyze7VSzYMQ/3DVIMTRt/sFtcUA0epZ2o28GCUfi3CCOjbDWHVhMaElRyOB1nss3+C7no7rAqf4DsTM+vr+A7VUYw4rTixeqAmqdUf2bKjESrz96LGwlQWNxRvPVHNw1N+2p9wJ30UWfkIfbKT5YQY1X/5gxVinMqtXCui53vjWVmMCEcmHS/EGOT1ecnKYoQudlXra3ONIphZ3Oh14H7rCzrKdDxXrijYLV3w5Socmr50HcixCUhfNBeQvkxIQPoiVOA92AkqPdISacwsImnMSklyiVgiu8FyF6+EnUbEXjk8SS4Rq+YUviuXyCOUH6IP14er5npX37/rmiO5rkqu90K/Q5Jcux0Ud0OekCwvuZ+Q3OdI7r9EDJZJJPerkvtoiUQWY0m+d0i+Dwk4/5BJ8P2R++p+enk3XIf5I3uSdYDX93gKTnUEywvypLdmBVlVgwInk1U1iFUcqibCKVo1AjHqhc1Qanm1W2qsq5FouFZqS677diyw2r7LcL0Vnjax7rTgHsEQQC+CUsDvl+8vpMYCOGTQogEwaALBLZo+hk2gpRbYpM1llnLpx4V6fMsQ0TQM6KaAmQqisC1ijWiyahwZ7jZUVxfZIcb0m1F96x12dnzALRx9GHf8x6cFWmzwkQAPH2EA4AE26PMh0lmTagLkMye+HDG5P4+HUCbVsHGZIqqzMLPb/wCr2VTW:718B");
sb.AppendLine("^PQ1,0,1,Y^XZ");
var zpl = sb.ToString();
//extract the Z64-String
var z64Data = "";
var bytesPerRow = 0;
foreach (var item in zpl.Split('^'))
{
if (item.StartsWith("GFA"))
{
var sp= item.Split(':');
z64Data = item.Substring(sp[0].Length);
bytesPerRow = Convert.ToInt32(sp[0].Split(',')[3]);
break;
}
}
//convert String to Bitmap
Bitmap decodedBitmap = null;
if (z64Data.StartsWith(":Z64"))
{
var imageData = DecompressZb64(z64Data.Substring(5));
int width = bytesPerRow * 8;
int height = imageData.Length / bytesPerRow;
decodedBitmap = ArrayToBitmap(imageData, width, height, PixelFormat.Format1bppIndexed);
}
Debug.WriteLine(decodedBitmap.Width + ":" + decodedBitmap.Height);
}
public static Bitmap ArrayToBitmap(byte[] bytes, int width, int height, PixelFormat pixelFormat)
{
var image = new Bitmap(width, height, pixelFormat);
var imageData = image.LockBits(new Rectangle(0, 0, image.Width, image.Height),
ImageLockMode.ReadWrite, pixelFormat);
try
{
Marshal.Copy(bytes, 0, imageData.Scan0, bytes.Length);
}
finally
{
image.UnlockBits(imageData);
}
return image;
}
public static byte[] DecompressZb64(string compressedString)
{
var b64 = Convert.FromBase64String(compressedString.Split(':')[0]).Skip(2).ToArray();
return Decompress(b64);
}
public static byte[] Decompress(byte[] data)
{
byte[] decompressedArray = null;
try
{
using (MemoryStream decompressedStream = new MemoryStream())
{
using (MemoryStream compressStream = new MemoryStream(data))
{
using (DeflateStream deflateStream = new DeflateStream(compressStream, CompressionMode.Decompress))
{
deflateStream.CopyTo(decompressedStream);
}
}
decompressedArray = decompressedStream.ToArray();
}
}
catch (Exception ex)
{
// do something !
}
return decompressedArray;
}
}
}

Resize Webp images

I had Converted Jpg to Webp But I want to resize the image.
using (Bitmap bitmap = new Bitmap(UploadName +jpgFileName))
{
using (var saveImageStream = System.IO.File.Open(webpFileName, FileMode.Create))
{
var encoder = new SimpleEncoder();
encoder.Encode(bitmap, saveImageStream, 90);
}
}
I think you can first resize in jpg then you convert from jpg to webp.
those methods i use to resize image:
You can recive a IFormFile jpgImage and convert to byte[] using method below:
public byte[] GetBytes(IFormFile formFile)
{
using var fileStream = formFile.OpenReadStream();
var bytes = new byte[formFile.Length];
fileStream.Read(bytes, 0, (int)formFile.Length);
return bytes;
}
// Methods to resize the jpg image in byte[]
using SixLabors.ImageSharp;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Processing;
...
public byte[] ResizeImage(byte[] img, int width, int height)
{
using var image = SixLabors.ImageSharp.Image.Load(img);
var options = new ResizeOptions
{
Size = new Size(width, height),
Mode = ResizeMode.Max
};
return Resize(image, options);
}
private byte[] Resize(Image<Rgba32> image, ResizeOptions resizeOptions)
{
byte[] ret;
image.Mutate(i => i.Resize(resizeOptions));
using MemoryStream ms = new MemoryStream();
image.SaveAsJpeg(ms);
ret = ms.ToArray();
ms.Close();
return ret;
}
After resize the jpg image in byte[] you convert to webp

ZXing QrCode renderer exception with .Net Core 2.1

I would like to create a QR code with using ZXing(0.16.4) But I meet following exception,
System.InvalidOperationException: 'You have to set a renderer
instance.'
Almost the same code works well with .Net Framework 4.6.1
here is my code
static void Main(string[] args)
{
var qrCode = CreateQrCode("test");
Console.ReadKey();
}
public static byte[] CreateQrCode(string content)
{
BarcodeWriter<Bitmap> writer = new BarcodeWriter<Bitmap>
{
Format = BarcodeFormat.QR_CODE,
Options = new QrCodeEncodingOptions
{
Width = 100,
Height = 100,
}
};
var qrCodeImage = writer.Write(content); // BOOM!!
using (var stream = new MemoryStream())
{
qrCodeImage.Save(stream, ImageFormat.Png);
return stream.ToArray();
}
}
I solved the issue, Basically I used https://www.nuget.org/packages/ZXing.Net.Bindings.CoreCompat.System.Drawing
I create BarcodeWriter generated from following namespace
ZXing.CoreCompat.System.Drawing
here is my CreateQrCode method
public static byte[] CreateQrCode(string content)
{
BarcodeWriter writer = new BarcodeWriter
{
Format = BarcodeFormat.QR_CODE,
Options = new QrCodeEncodingOptions
{
Width = 100,
Height = 100,
}
};
var qrCodeImage = writer.Write(content); // BOOM!!
using (var stream = new MemoryStream())
{
qrCodeImage.Save(stream, ImageFormat.Png);
return stream.ToArray();
}
}
Here is the read QR code method, maybe someone will need as well.
BarcodeReader also generated from the same namespace like create.
Here is the method
public static string ReadQrCode(byte[] qrCode)
{
BarcodeReader coreCompatReader = new BarcodeReader();
using (Stream stream = new MemoryStream(qrCode))
{
using (var coreCompatImage = (Bitmap)Image.FromStream(stream))
{
return coreCompatReader.Decode(coreCompatImage).Text;
}
}
}
Hope this answer will protect someone's hair against pulling.
There is a newer version of the package available and it works with .NET Core 3.1.
https://www.nuget.org/packages/ZXing.Net.Bindings.Windows.Compatibility/
I needed to add "Renderer = new ZXing.Rendering.BitmapRenderer()" when using ZXing.Net v0.16.6
public static byte[] CreateQrCode(string content)
{
byte[] imageData;
var qrWriter = new ZXing.BarcodeWriter<System.Drawing.Bitmap>
{
Format = BarcodeFormat.QR_CODE,
Options = new ZXing.Common.EncodingOptions { Height = 100, Width = 100, Margin = 0 },
Renderer = new ZXing.Rendering.BitmapRenderer()
};
using (var ms = new System.IO.MemoryStream())
using (System.Drawing.Bitmap pixelData = qrWriter.Write(content))
{
pixelData.Save(ms, System.Drawing.Imaging.ImageFormat.Png);
imageData = ms.ToArray();
}
return imageData;
}
I'm currently moving to .net 6 and I used BarcodeWriter from ZXing.Net.Bindings.SkiaSharp NuGet package.
using ZXing.SkiaSharp;
var barcodeWriter = new BarcodeWriter
{
Format = BarcodeFormat.QR_CODE,
Options = new EncodingOptions
{
Height = _height,
Width = _width,
Margin = _margin
}
};
using var bitmap = barcodeWriter.Write(qrValue);
using var stream = new MemoryStream();
bitmap.Encode(stream, SKEncodedImageFormat.Png, 100);
Your stream is filled now :)

How do you retrieve a snapshot of a website in ASP.NET?

Could anyone tell me how I could retrieve an image or a thumbnail of a website through my ASP.NET application? I have seen this functionality in a few sites such as Alexa etc.
Try SnapCasa's free and easy to use service. Just form your image tag like this:
<img src="http://SnapCasa.com/Get.aspx?code=[code]&size=[size]&url=[url]" />
Requires sign-up, but it's free for 500,000 requests a month. [code] is an api key that they provide after sign-up. [size] is one of three sizes available. [url] is the website address to the site for which you want to display a thumbnail.
If you want to work with the image from your code, here are a couple of helper methods:
static public byte[] GetBytesFromUrl(string url)
{
byte[] b;
HttpWebRequest myReq = (HttpWebRequest)WebRequest.Create(url);
WebResponse myResp = myReq.GetResponse();
Stream stream = myResp.GetResponseStream();
//int i;
using (BinaryReader br = new BinaryReader(stream))
{
//i = (int)(stream.Length);
b = br.ReadBytes(500000);
br.Close();
}
myResp.Close();
return b;
}
static public void WriteBytesToFile(string fileName, byte[] content)
{
FileStream fs = new FileStream(fileName, FileMode.Create);
BinaryWriter w = new BinaryWriter(fs);
try
{
w.Write(content);
}
finally
{
fs.Close();
w.Close();
}
}
Then, in your code, just use:
//get byte array for image
var imageBytes = GetBytesFromUrl("http://SnapCasa.com/Get.aspx?code=[code]&size=[size]&url=[url]");
//save file to disk
WriteBytesToFile("c:\someImageFile.jpg", imageBytes);
Should be doable using a web-browser object and saving the view port to a bitmap resized to thumbnail.
I have not tested this code but try tweaking it after substituting for the thumbnail params.
using (WebBrowser wb = new WebBrowser()) {
wb.ScrollBarsEnabled = false;
wb.AllowNavigation = true;
wb.ScriptErrorsSuppressed = true;
wb.ClientSize = new Size(thumbInfo_viewportWidth, thumbInfo_viewportHeight);
if ((thumbInfo_Uri != null)) {
wb.Navigate(thumbInfo_Uri.AbsoluteUri);
} else {
wb.Navigate("about:blank");
HtmlDocument doc = wb.Document.OpenNew(true);
doc.Write(thumbInfo_HTML);
wb.Refresh(WebBrowserRefreshOption.Completely);
}
// create an image of the client area of the webbrowser control, than
// scale it down to the dimensions specified.
if ((wb.Document != null && wb.Document.Body != null)) {
Rectangle rec = default(Rectangle);
rec.Size = wb.ClientSize;
using (Bitmap fullSizeBitmap = new Bitmap(thumbInfo_viewportWidth, thumbInfo_viewportHeight)) {
wb.DrawToBitmap(fullSizeBitmap, wb.Bounds);
using (Bitmap scaledBitmap = new Bitmap(thumbInfo_width, thumbInfo_height)) {
using (Graphics gr = Graphics.FromImage(scaledBitmap)) {
gr.SmoothingMode = Drawing2D.SmoothingMode.HighQuality;
gr.CompositingQuality = Drawing2D.CompositingQuality.HighQuality;
gr.InterpolationMode = Drawing2D.InterpolationMode.High;
Rectangle rect = new Rectangle(0, 0, thumbInfo_width, thumbInfo_height);
gr.DrawImage(fullSizeBitmap, rect, 0, 0, rec.Size.Width, rec.Size.Height, GraphicsUnit.Pixel);
scaledBitmap.Save(thumbInfo_physicalPath);
}
}
}
}
}
One thing to note that it is an expensive process.

Categories