Enhancing JPEG, PNG, Text Using C# .NET Part 2 - Gaussian Blur Effect
The Gaussian blur effect is widely used in graphics software to reduce image noise and detail. The visual effect of this blurring technique is a smooth blur resembling that of viewing the image through a translucent screen.
GcBitmap is a class in GrapeCity.Documents.Imaging namespace that represents an image as a modifiable array of pixels. Among other operations, users can apply various effects (grayscale effect, opacity effect, and others) to an image. The Gaussian blur effect works similarly to other effects. You can apply it to the entire image or a part of the image using the ApplyEffect method of GcBitmap.
Ready to Get Started? Download Document Solutions for Imaging Today!
To obtain an instance of the GaussianBlurEffect class, use the static Get method of that class:
/// <summary>
/// Returns an instance of the <see cref="GaussianBlurEffect"/> class.
/// </summary>
/// <param name="radius">The radius of the blur, in pixels.</param>
/// <param name="borderMode">The mapping mode for the pixels outside of the border.</param>
public static GaussianBlurEffect Get(int radius = 9,
GaussianBlurBorderMode borderMode = GaussianBlurBorderMode.Default)
/// <summary>
/// Returns an instance of the <see cref="GaussianBlurEffect"/> class.
/// </summary>
/// <param name="borderColor">The color used to blend with the edge pixels of the image.</param>
/// <param name="radius">The radius of the blur, in pixels.</param>
/// <param name="borderMode">The mapping mode for the pixels outside of the border.</param>
public static GaussianBlurEffect Get(Color borderColor, int radius = 9,
GaussianBlurBorderMode borderMode = GaussianBlurBorderMode.Default)
There are a few parameters in the GaussianBlurEffect.Get method. The main one is the radius of the blur, which specifies the standard deviation of the Gaussian distribution as follows: sigma = radius / 3.
When a blur effect is applied, the color of each pixel blends with all surrounding pixels at the distance of “radius” (pixels) in X and Y directions. For pixels at the edge of the image, some of the surrounding pixels do not exist. We must somehow extrapolate pixel colors beyond the image edge to apply the algorithm to the pixels at the edge. The outer border color can be passed as the first (optional) parameter to the static Get method. If the parameter is not specified, the transparent black color is used.
For example, let's say we want to apply blur to the following image:
It's easy to do in a C# console project for .NET 7:
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap("door.jpg");
bmp.ApplyEffect(GaussianBlurEffect.Get(30));
bmp.SaveAsJpeg("door1.jpg");
The resulting image in door1.jpg:
As you can see, there is a dark frame around the image because the border pixels were mixed with the black outer color. We can make the outer color white:
using System.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap("door.jpg");
bmp.ApplyEffect(GaussianBlurEffect.Get(Color.White, 30));
bmp.SaveAsJpeg("door2.jpg");
The resulting image:
Also, we can blur just a part of the image:
using System.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap("door.jpg");
var rect = new Rectangle(0, 0, bmp.PixelWidth, bmp.PixelHeight);
rect.Inflate(-60, -60);
bmp.ApplyEffect(GaussianBlurEffect.Get(30), rect);
bmp.SaveAsJpeg("door3.jpg");
There is no frame around the blurred part of the image because the algorithm can use the actual pixel colors around the blurred area for the edge pixels. If desired, we can specify a color for the outer border:
using System.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap("door.jpg");
var rect = new Rectangle(0, 0, bmp.PixelWidth, bmp.PixelHeight);
rect.Inflate(-60, -60);
bmp.ApplyEffect(GaussianBlurEffect.Get(Color.ForestGreen,
30, GaussianBlurBorderMode.BorderColor), rect);
bmp.SaveAsJpeg("door4.jpg");
The third parameter of the GaussianBlurEffect.Get method makes it possible to enforce using the specified border color in the above case. Let’s investigate other values to be passed in the borderMode parameter.
For example, if we apply a blur with the Default border mode to a high-contrast image:
using System.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap(600, 400, false);
bmp.Clear(Color.Black);
bmp.Clear(Color.White, new Rectangle(0, 0, 300, 200));
bmp.Clear(Color.White, new Rectangle(300, 200, 300, 200));
var rect = new Rectangle(50, 50, 500, 300);
bmp.ApplyEffect(GaussianBlurEffect.Get(30), rect);
bmp.SaveAsPng("blur1.png");
The result might be poor:
Passing a GaussianBlurBorderMode.Wrap to GaussianBlurEffect.Get changes the output image:
bmp.ApplyEffect(GaussianBlurEffect.Get(30, GaussianBlurBorderMode.Wrap), rect);
Sometimes, it isn't easy to match the proper border color for the image background. Instead, we can imagine that the outer border (beyond the image edge) mirrors the inner pixels near the border.
For example, if we apply a Gaussian blur to the following image:
With this code:
using System.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = new GcBitmap("fiord.jpg");
bmp.ApplyEffect(GaussianBlurEffect.Get(Color.White, 30));
bmp.SaveAsJpeg("fiord1.jpg");
There are white stripes at all edges of the image:
To avoid such stripes, use one of the following border modes- RepeatEdge, Mirror, Bounce, such as:
bmp.ApplyEffect(GaussianBlurEffect.Get(30, GaussianBlurBorderMode.RepeatEdge));
The resulting image:
The Gaussian blur effect might work slowly for big blur radii and large images. To improve performance, set the Multithreaded property of the GaussianBlurEffect instance to true. However, when this option is enabled, it takes 3-4 times more memory and CPU cores. For example:
using System.Drawing;
using System.Numerics;
using GrapeCity.Documents.Drawing;
using GrapeCity.Documents.Imaging;
using var bmp = CreateBitmap();
using (var bmp2 = bmp.Clone())
{
var effect = GaussianBlurEffect.Get(45);
effect.Multithreaded = true;
effect.BorderColor = Color.White;
bmp2.ApplyEffect(effect);
using var g = bmp.CreateGraphics();
g.Renderer.BackgroundBitmap = bmp2;
g.Renderer.Aliased = true;
FillRect(Color.White, 30, 30, 350, 230);
FillRect(Color.DimGray, 425, 30, 350, 230);
FillRect(Color.CornflowerBlue, 820, 30, 350, 230);
FillRect(Color.Red, 30, 290, 350, 230);
FillRect(Color.LimeGreen, 425, 290, 350, 230);
FillRect(Color.Fuchsia, 820, 290, 350, 230);
FillRect(Color.Cyan, 30, 550, 350, 230);
FillRect(Color.Yellow, 425, 550, 350, 230);
FillRect(Color.Blue, 820, 550, 350, 230);
void FillRect(Color c, float x, float y, float w, float h)
{
g.FillRoundRect(new RectangleF(x, y, w, h), 50,
Color.FromArgb(120, c));
}
}
bmp.SaveAsPng("image1.png");
static GcBitmap CreateBitmap()
{
var bmp = new GcBitmap(1200, 810, false);
using var spectrum = new GcBitmap("spectrum.png");
using var g = bmp.CreateGraphics(Color.White);
var rect = new RectangleF(0, 0, spectrum.Width, spectrum.Height);
var mr = Matrix3x2.CreateRotation((float)Math.PI / 4);
for (int i = -254; i < 1203; i += 52)
{
g.Transform = mr * Matrix3x2.CreateTranslation(i, -50);
g.DrawImage(spectrum, rect, null, ImageAlign.StretchImage);
}
mr = Matrix3x2.CreateRotation((float)-Math.PI / 4);
for (int i = -301; i < 1208; i += 52)
{
g.Transform = mr * Matrix3x2.CreateTranslation(i, 520);
g.DrawImage(spectrum, rect, null, ImageAlign.StretchImage);
}
mr = Matrix3x2.CreateRotation((float)Math.PI / 4);
for (int i = -254; i < 1203; i += 52)
{
g.Transform = mr * Matrix3x2.CreateTranslation(i, 525);
g.DrawImage(spectrum, rect, null, ImageAlign.StretchImage);
}
return bmp;
}
The above code uses a spectrum.png that follows:
The resulting image simulates the effect of colored translucent glasses:
MESCIUS' .NET Imaging API Library
This article only scratches the surface of the full capabilities of Document Solutions for Imaging (DsImaging, previously GcImaging). Review our documentation to see the many available features and our demos to see the features in action with downloadable sample projects.
Integrating this .NET imaging server-side API into a desktop or web-based application allows developers to programmatically create and manipulate images at scale and load, process, and save images across many different formats.
Ready to Get Started? Download Document Solutions for Imaging Today!