Based on below Part of code, May i know how to passing the picturebox image in image cell iTextSharp in C# ? kindly advise. thank you
Image<Bgr, Byte> img1 = new Image<Bgr, Byte>(Application.StartupPath + "/TrainedFaces/" + reader.GetString(11) + ".bmp");
Application.Idle -= new EventHandler(ProcessFrame);
pictureBox1.Image = img1;
Shall I use string format ?
cell = ImageCell(string.Format("+ img1 +"), 25f, PdfPCell.ALIGN_CENTER);
ImageCell takes byte[] data, it won't take string.
Here is the entire implementation,
// Code resides in your page codebehind, do not confuse with AppLevel, it's just my static class
System.Drawing.Image imgResized = AppLevel.Resize(AppLevel.byteArrayToImage(File.ReadAllBytes(Server.MapPath("~/images/companylogo.jpg"))), 194, 138, RotateFlipType.RotateNoneFlipNone);
cell = AppLevel.ImageCell(AppLevel.imageToByteArray(imgResized), 30f, PdfPCell.ALIGN_RIGHT);
table.AddCell(cell);
///Helper methods///
/// <summary>
/// Resizes and rotates an image, keeping the original aspect ratio. Does not dispose the original
/// Image instance.
/// </summary>
/// <param name="image">Image instance</param>
/// <param name="width">desired width</param>
/// <param name="height">desired height</param>
/// <param name="rotateFlipType">desired RotateFlipType</param>
/// <returns>new resized/rotated Image instance</returns>
public static System.Drawing.Image Resize(System.Drawing.Image image, int width, int height, RotateFlipType rotateFlipType)
{
// clone the Image instance, since we don't want to resize the original Image instance
var rotatedImage = image.Clone() as System.Drawing.Image;
rotatedImage.RotateFlip(rotateFlipType);
var newSize = CalculateResizedDimensions(rotatedImage, width, height);
var resizedImage = new Bitmap(newSize.Width, newSize.Height, PixelFormat.Format32bppArgb);
resizedImage.SetResolution(72, 72);
using (var graphics = Graphics.FromImage(resizedImage))
{
// set parameters to create a high-quality thumbnail
graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
graphics.SmoothingMode = SmoothingMode.AntiAlias;
graphics.CompositingQuality = CompositingQuality.HighQuality;
graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;
// use an image attribute in order to remove the black/gray border around image after resize
// (most obvious on white images), see this post for more information:
// http://www.codeproject.com/KB/GDI-plus/imgresizoutperfgdiplus.aspx
using (var attribute = new ImageAttributes())
{
attribute.SetWrapMode(WrapMode.TileFlipXY);
// draws the resized image to the bitmap
graphics.DrawImage(rotatedImage, new System.Drawing.Rectangle(new Point(0, 0), newSize), 0, 0, rotatedImage.Width, rotatedImage.Height, GraphicsUnit.Pixel, attribute);
}
}
return resizedImage;
}
public static System.Drawing.Image byteArrayToImage(byte[] byteArrayIn)
{
MemoryStream ms = new MemoryStream(byteArrayIn);
System.Drawing.Image returnImage = System.Drawing.Image.FromStream(ms);
eturnImage;
}
Related
I tried to capture my screen in C# (.NET 4.6.2 in console mode) to get a base64 string of the bitmap.
My issue is that the base64 is too big in my case so I want to decrease the resolution of the Bitmap, I tried this code:
public static string TakeScreenshotToBase64()
{
Bitmap memoryImage = new Bitmap(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height);
Size size = new Size(memoryImage.Width, memoryImage.Height);
Graphics memoryGraphics = Graphics.FromImage(memoryImage);
memoryGraphics.CopyFromScreen(0, 0, 0, 0, size);
MemoryStream ms = new MemoryStream();
memoryImage.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg);
return Convert.ToBase64String(ms.ToArray());
}
If I try to edit the width and the height values, I got a smaller picture but I don't have the full picture sadly.
So I tried to create a new Bitmap from my existing Bitmap with another resolution, but it doesn't work, any suggestions? thank you for your help.
As requested, i hope this helps. I can explain better if the comments are not enough.
using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.IO;
using System.Windows.Forms;
namespace BitMapResize
{
public partial class Form1 : Form
{
/// <summary>
/// Function to Create the images.
/// </summary>
/// <param name="resizeWidth">If it is null, the application will create an image with the original size.</param>
/// <param name="resizeHeight">If it is null, the application will create an image with the original size.</param>
public static void TakeScreenshotToBase64(float? resizeWidth, float? resizeHeight)
{
using (MemoryStream ms = new MemoryStream())
{
/* First things first, creating a bitmap of the original data to the memorystream, so we can use later.*/
Bitmap memoryImage = new Bitmap(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height);
Size size = new Size(memoryImage.Width, memoryImage.Height);
using (Graphics memoryGraphics = Graphics.FromImage(memoryImage))
{
memoryGraphics.CopyFromScreen(0, 0, 0, 0, size); // Persisting the full screen resolution.
memoryImage.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg); // Saving in the memory stream...
}
string imageName = "Print"; // This won't change if the size is the original.
// This conditions checks if the resize parameters are not null. If they are not null, a resizing process begins.
if (!(resizeWidth is null) || !(resizeHeight is null))
{
var bmp = new Bitmap((int)resizeWidth.Value, (int)resizeHeight.Value); // Create a new bitmap with the new dimensions.
using (Graphics memoryGraphics = Graphics.FromImage(bmp)) // Using a Graphics that operates on the new bitmap.
{
// Defining scale factor. This way we maintain aspect ratio.
float scale = Math.Min(resizeWidth.Value / memoryImage.Width, resizeHeight.Value / memoryImage.Height);
int scaleWidth = (int)(memoryImage.Width * scale);
int scaleHeight = (int)(memoryImage.Height * scale);
// Optional: Set this for better output quality.
memoryGraphics.InterpolationMode = InterpolationMode.High;
memoryGraphics.CompositingQuality = CompositingQuality.HighQuality;
memoryGraphics.SmoothingMode = SmoothingMode.AntiAlias;
// Here, choose the background color for the image.
/* Why the background?
* As long as we keep the aspect ratio, if the given dimension does not respect the scale of the original dimension,
* an area of the new image will not be filled. So we can set a background color for these empty areas.
*/
Brush baseColor = new SolidBrush(Color.White);
memoryGraphics.FillRectangle(baseColor, new RectangleF(0, 0, resizeWidth.Value, resizeHeight.Value));
// Process the resize, based on the in-memory buffer that we wrote earlier.
memoryGraphics.DrawImage(Image.FromStream(ms), ((int)resizeWidth.Value - scaleWidth) / 2, ((int)resizeHeight.Value - scaleHeight) / 2, scaleWidth, scaleHeight);
}
imageName = "ResizedPrint";
// Not requested, but now can save this in a file.
using (FileStream fs = new FileStream(Application.StartupPath + "/" + imageName + ".jpg", FileMode.Create))
{
bmp.Save(fs, System.Drawing.Imaging.ImageFormat.Jpeg);
}
}
else
{
using (FileStream fs = new FileStream(Application.StartupPath + "/" + imageName + ".jpg", FileMode.Create))
{
// If no resize was done, save the original data.
memoryImage.Save(fs, System.Drawing.Imaging.ImageFormat.Jpeg);
}
}
}
}
// Print event start.
private void button1_Click(object sender, EventArgs e)
{
TakeScreenshotToBase64(1024, 768);
//TakeScreenshotToBase64(null, null);
}
}
}
How to do this programmatically in C#? I´m using MS Office Professional 2016
.
To insert an image I use this code:
DialogResult result;
OpenFileDialog ofd = new OpenFileDialog();
ofd.Title = "Choose image file";
result = ofd.ShowDialog();
if (result == DialogResult.OK)
{
//GetInstance().ActiveSheet.Shapes.AddPicture(ofd.FileName, MsoTriState.msoFalse, MsoTriState.msoCTrue, 10, 10, -1, -1);
GetInstance().ActiveSheet.Shapes.AddPicture2(ofd.FileName, MsoTriState.msoFalse, MsoTriState.msoCTrue, 10, 10, -1, -1, 1);
Excel.Shape newShape = GetInstance().ActiveSheet.Shapes.Item(GetInstance().ActiveSheet.Shapes.Count);
newShape.ZOrder(MsoZOrderCmd.msoSendToBack);
newShape.Placement = Excel.XlPlacement.xlMoveAndSize;
}
Then I have my images as shapes. Maybe there is a way to do the picture compression on shapes?
There are several ways to get the job done:
The enter link description here provides the last argument compress which allows specifying whether the picture should be compressed when inserted. You can use the following values:
msoPictureCompressDocDefault - The picture is compressed or not depending on the settings for the document.
msoPictureCompressFalse - The picture is not compressed.
msoPictureCompressTrue - The picture will be compressed.
You can use .net BCL classes to reduce the size of image before adding it to Excel documents:
/// <summary>
/// Resize the image to the specified width and height.
/// </summary>
/// <param name="image">The image to resize.</param>
/// <param name="width">The width to resize to.</param>
/// <param name="height">The height to resize to.</param>
/// <returns>The resized image.</returns>
public static Bitmap ResizeImage(Image image, int width, int height)
{
var destRect = new Rectangle(0, 0, width, height);
var destImage = new Bitmap(width, height);
destImage.SetResolution(image.HorizontalResolution, image.VerticalResolution);
using (var graphics = Graphics.FromImage(destImage))
{
graphics.CompositingMode = CompositingMode.SourceCopy;
graphics.CompositingQuality = CompositingQuality.HighQuality;
graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
graphics.SmoothingMode = SmoothingMode.HighQuality;
graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;
using (var wrapMode = new ImageAttributes())
{
wrapMode.SetWrapMode(WrapMode.TileFlipXY);
graphics.DrawImage(image, destRect, 0, 0, image.Width,image.Height, GraphicsUnit.Pixel, wrapMode);
}
}
return destImage;
}
You may find more ways and information:
How to resize an Image C#
Resize Image In C#
I have a form which has a image. I am using a slider to change the opacity of the image. So in the "ValueChanged" event of the slider I am calling the following method to change the opacity.
//Setting the opacity of the image
public static Image SetImgOpacity(Image imgPic, float imgOpac)
{
Bitmap bmpPic = new Bitmap(imgPic.Width, imgPic.Height);
Graphics gfxPic = Graphics.FromImage(bmpPic);
ColorMatrix cmxPic = new ColorMatrix();
cmxPic.Matrix33 = imgOpac;
ImageAttributes iaPic = new ImageAttributes();
iaPic.SetColorMatrix(cmxPic, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
gfxPic.DrawImage(imgPic, new Rectangle(0, 0, bmpPic.Width, bmpPic.Height), 0, 0, imgPic.Width, imgPic.Height, GraphicsUnit.Pixel, iaPic);
gfxPic.Dispose();
return bmpPic;
}
The returned Image is set to the original image.
My problem is that the opacity of the image is not changing... If there is any error please be kind enough to point out.. Thnx...
Try this one from CodeProject - Change Opacity of Image in C#:
/// <summary>
/// method for changing the opacity of an image
/// </summary>
/// <param name="image">image to set opacity on</param>
/// <param name="opacity">percentage of opacity</param>
/// <returns></returns>
public Image SetImageOpacity(Image image, float opacity)
{
try
{
//create a Bitmap the size of the image provided
Bitmap bmp = new Bitmap(image.Width, image.Height);
//create a graphics object from the image
using (Graphics gfx = Graphics.FromImage(bmp)) {
//create a color matrix object
ColorMatrix matrix = new ColorMatrix();
//set the opacity
matrix.Matrix33 = opacity;
//create image attributes
ImageAttributes attributes = new ImageAttributes();
//set the color(opacity) of the image
attributes.SetColorMatrix(matrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
//now draw the image
gfx.DrawImage(image, new Rectangle(0, 0, bmp.Width, bmp.Height), 0, 0, image.Width, image.Height, GraphicsUnit.Pixel, attributes);
}
return bmp;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
return null;
}
}
You loop over the pixels and play only the alpha channel.
If you do this with Bitmap.LockBits it will actually be very fast.
private const int bytesPerPixel = 4;
/// <summary>
/// Change the opacity of an image
/// </summary>
/// <param name="originalImage">The original image</param>
/// <param name="opacity">Opacity, where 1.0 is no opacity, 0.0 is full transparency</param>
/// <returns>The changed image</returns>
public static Image ChangeImageOpacity(Image originalImage, double opacity)
{
if ((originalImage.PixelFormat & PixelFormat.Indexed) == PixelFormat.Indexed)
{
// Cannot modify an image with indexed colors
return originalImage;
}
Bitmap bmp = (Bitmap)originalImage.Clone();
// Specify a pixel format.
PixelFormat pxf = PixelFormat.Format32bppArgb;
// Lock the bitmap's bits.
Rectangle rect = new Rectangle(0, 0, bmp.Width, bmp.Height);
BitmapData bmpData = bmp.LockBits(rect, ImageLockMode.ReadWrite, pxf);
// Get the address of the first line.
IntPtr ptr = bmpData.Scan0;
// Declare an array to hold the bytes of the bitmap.
// This code is specific to a bitmap with 32 bits per pixels
// (32 bits = 4 bytes, 3 for RGB and 1 byte for alpha).
int numBytes = bmp.Width * bmp.Height * bytesPerPixel;
byte[] argbValues = new byte[numBytes];
// Copy the ARGB values into the array.
System.Runtime.InteropServices.Marshal.Copy(ptr, argbValues, 0, numBytes);
// Manipulate the bitmap, such as changing the
// RGB values for all pixels in the the bitmap.
for (int counter = 0; counter < argbValues.Length; counter += bytesPerPixel)
{
// argbValues is in format BGRA (Blue, Green, Red, Alpha)
// If 100% transparent, skip pixel
if (argbValues[counter + bytesPerPixel - 1] == 0)
continue;
int pos = 0;
pos++; // B value
pos++; // G value
pos++; // R value
argbValues[counter + pos] = (byte) (argbValues[counter + pos] * opacity);
}
// Copy the ARGB values back to the bitmap
System.Runtime.InteropServices.Marshal.Copy(argbValues, 0, ptr, numBytes);
// Unlock the bits.
bmp.UnlockBits(bmpData);
return bmp;
}
I am not familiar with the ImageAttributes approach, but you should be able to simply run through all the pixels of the image and modify the alpha component of the color of the pixel.
The ImageAttributes method will work fine with PNG as the original post has it listed, but for JPEG you need to flood fill the graphics canvas with a color first. Since this can leave a tiny undesired border, only do it if the opacity is something less than 1.0:
if(opacity < 1.0)
{
// g is a Graphics object
g.Clear(Color.White);
}
// set color matrix and draw image as shown in other posts
// ...
I would like to create Thumbnail from my wpf window and would like to save it into database and display it later. Is there any good solution?
I have started with RenderTargetBitmap but I can't find any easy way to get it into bytes.
RenderTargetBitmap bmp = new RenderTargetBitmap(180, 180, 96, 96, PixelFormats.Pbgra32);
bmp.Render(myWpfWindow);
Using user32.dll and Graphics.CopyFromScreen() is not good for me and
as it is here because I want to do a screenshot from user controls as well.
Thanks
Steven Robbins has written a great blog post about capturing a screenshot of a control, which contains the following extension method:
public static class Screenshot
{
/// <summary>
/// Gets a JPG "screenshot" of the current UIElement
/// </summary>
/// <param name="source">UIElement to screenshot</param>
/// <param name="scale">Scale to render the screenshot</param>
/// <param name="quality">JPG Quality</param>
/// <returns>Byte array of JPG data</returns>
public static byte[] GetJpgImage(this UIElement source, double scale, int quality)
{
double actualHeight = source.RenderSize.Height;
double actualWidth = source.RenderSize.Width;
double renderHeight = actualHeight * scale;
double renderWidth = actualWidth * scale;
RenderTargetBitmap renderTarget = new RenderTargetBitmap((int) renderWidth, (int) renderHeight, 96, 96, PixelFormats.Pbgra32);
VisualBrush sourceBrush = new VisualBrush(source);
DrawingVisual drawingVisual = new DrawingVisual();
DrawingContext drawingContext = drawingVisual.RenderOpen();
using (drawingContext)
{
drawingContext.PushTransform(new ScaleTransform(scale, scale));
drawingContext.DrawRectangle(sourceBrush, null, new Rect(new Point(0, 0), new Point(actualWidth, actualHeight)));
}
renderTarget.Render(drawingVisual);
JpegBitmapEncoder jpgEncoder = new JpegBitmapEncoder();
jpgEncoder.QualityLevel = quality;
jpgEncoder.Frames.Add(BitmapFrame.Create(renderTarget));
Byte[] _imageArray;
using (MemoryStream outputStream = new MemoryStream())
{
jpgEncoder.Save(outputStream);
_imageArray = outputStream.ToArray();
}
return _imageArray;
}
}
This method takes a control and a scale factor and returns a byte array. So this seems to be a quite good fit with your requirements.
Check out the post for further reading and an example project that is quite neat.
You can use a BitmapEncoder to encode your Bitmap to a PNG, JPG or even BMP file. Check the MSDN documentation on BitmapEncoder.Frames, which has an example that saves to a FileStream. You can save it to any stream.
To get the BitmapFrame from the RenderTargetBitmap, simply create it using the BitmapFrame.Create(BitmapSource) method.
public void CreateThumbnail(Image img1, Photo photo, string targetDirectoryThumbs)
{
int newWidth = 700;
int newHeight = 700;
double ratio = 0;
if (img1.Width > img1.Height)
{
ratio = img1.Width / (double)img1.Height;
newHeight = (int)(newHeight / ratio);
}
else
{
ratio = img1.Height / (double)img1.Width;
newWidth = (int)(newWidth / ratio);
}
Image bmp1 = img1.GetThumbnailImage(newWidth, newHeight, null, IntPtr.Zero);
bmp1.Save(targetDirectoryThumbs + photo.PhotoID + ".jpg");
img1.Dispose();
bmp1.Dispose();
}
I've put 700px so that you can have better insight of the problem.
Here is original image and resized one.
Any good recommendation?
Thanks,
Ile
You should find my answer to this question helpful. It includes a sample for high quality image scaling in C#.
The full sample in my other answer includes how to save the image as a jpeg.
Here's the relevant bit of code...
/// <summary>
/// Resize the image to the specified width and height.
/// </summary>
/// <param name="image">The image to resize.</param>
/// <param name="width">The width to resize to.</param>
/// <param name="height">The height to resize to.</param>
/// <returns>The resized image.</returns>
public static System.Drawing.Bitmap ResizeImage(System.Drawing.Image image, int width, int height)
{
//a holder for the result
Bitmap result = new Bitmap(width, height);
//use a graphics object to draw the resized image into the bitmap
using (Graphics graphics = Graphics.FromImage(result))
{
//set the resize quality modes to high quality
graphics.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
graphics.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
graphics.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
//draw the image into the target bitmap
graphics.DrawImage(image, 0, 0, result.Width, result.Height);
}
//return the resulting bitmap
return result;
}
If the image contains a thumbnail it'll automatically stretch it to the desired size...which will make it look like crap (like your case ;))
Straight outta MSDN...
If the Image contains an embedded
thumbnail image, this method retrieves
the embedded thumbnail and scales it
to the requested size. If the Image
does not contain an embedded thumbnail
image, this method creates a thumbnail
image by scaling the main image.
In your case I just double checked the source image for it's thumbnail and got this...
New Windows Thumbnail : JPEG Format (Offset:830Size:3234)
Thumbnail Type : JPEG
Thumnail Width : 112
Thumbnail Height : 84
Try to draw the original image to another smaller image, and save the result.
Bitmap bmp1 = new Bitmap(newWidth, newHeight);
Graphics g = Graphics.FromImage(bmp);
g.DrawImage(img1, 0, 0, newWidth, newHeight);
bmp1.Save(targetDirectoryThumbs + photo.PhotoID + ".jpg", ImageFormat.Jpeg);
Are you allowed to use third party applications? If so, you may want to check out ImageMagick to manage thumbnail creation. There's a .NET wrapper.
http://imagemagick.codeplex.com/
I wrote a free .dll that does this easily. It's here if you want to see the documentation....
Git Repository & Tutorial