diff --git a/Greenshot/Drawing/Filters/BrightnessFilter.cs b/Greenshot/Drawing/Filters/BrightnessFilter.cs
index 33355453a..6adbb83d6 100644
--- a/Greenshot/Drawing/Filters/BrightnessFilter.cs
+++ b/Greenshot/Drawing/Filters/BrightnessFilter.cs
@@ -23,6 +23,7 @@ using System.Drawing;
using Greenshot.Drawing.Fields;
using Greenshot.Plugin.Drawing;
using GreenshotPlugin.Core;
+using System.Drawing.Imaging;
namespace Greenshot.Drawing.Filters {
[Serializable()]
@@ -47,24 +48,23 @@ namespace Greenshot.Drawing.Filters {
return;
}
- using (BitmapBuffer bbb = new BitmapBuffer(applyBitmap, applyRect)) {
- bbb.Lock();
+ using (IFastBitmap fastBitmap = FastBitmap.CreateCloneOf(applyBitmap, applyRect)) {
double brightness = GetFieldValueAsDouble(FieldType.BRIGHTNESS);
- for (int y = 0; y < bbb.Height; y++) {
- for (int x = 0; x < bbb.Width; x++) {
+ for (int y = 0; y < fastBitmap.Height; y++) {
+ for (int x = 0; x < fastBitmap.Width; x++) {
if (parent.Contains(applyRect.Left + x, applyRect.Top + y) ^ Invert) {
- Color color = bbb.GetColorAt(x, y);
+ Color color = fastBitmap.GetColorAt(x, y);
int r = Convert.ToInt16(color.R * brightness);
int g = Convert.ToInt16(color.G * brightness);
int b = Convert.ToInt16(color.B * brightness);
r = (r > 255) ? 255 : r;
g = (g > 255) ? 255 : g;
b = (b > 255) ? 255 : b;
- bbb.SetColorAt(x, y, Color.FromArgb(color.A, r, g, b));
+ fastBitmap.SetColorAt(x, y, Color.FromArgb(color.A, r, g, b));
}
}
}
- bbb.DrawTo(graphics, applyRect.Location);
+ fastBitmap.DrawTo(graphics, applyRect.Location);
}
}
}
diff --git a/Greenshot/Drawing/Filters/GrayscaleFilter.cs b/Greenshot/Drawing/Filters/GrayscaleFilter.cs
index 33ebd90d4..7a42d35a6 100644
--- a/Greenshot/Drawing/Filters/GrayscaleFilter.cs
+++ b/Greenshot/Drawing/Filters/GrayscaleFilter.cs
@@ -40,19 +40,18 @@ namespace Greenshot.Drawing.Filters {
return;
}
- using (BitmapBuffer bbb = new BitmapBuffer(applyBitmap, applyRect)) {
- bbb.Lock();
- for (int y = 0; y < bbb.Height; y++) {
- for (int x = 0; x < bbb.Width; x++) {
+ using (IFastBitmap fastBitmap = FastBitmap.CreateCloneOf(applyBitmap, applyRect)) {
+ for (int y = 0; y < fastBitmap.Height; y++) {
+ for (int x = 0; x < fastBitmap.Width; x++) {
if (parent.Contains(applyRect.Left + x, applyRect.Top + y) ^ Invert) {
- Color color = bbb.GetColorAt(x, y);
+ Color color = fastBitmap.GetColorAt(x, y);
int luma = (int)((0.3 * color.R) + (0.59 * color.G) + (0.11 * color.B));
color = Color.FromArgb(luma, luma, luma);
- bbb.SetColorAt(x, y, color);
+ fastBitmap.SetColorAt(x, y, color);
}
}
}
- bbb.DrawTo(graphics, applyRect.Location);
+ fastBitmap.DrawTo(graphics, applyRect.Location);
}
}
}
diff --git a/Greenshot/Drawing/Filters/HighlightFilter.cs b/Greenshot/Drawing/Filters/HighlightFilter.cs
index 9ff893dcc..757c32348 100644
--- a/Greenshot/Drawing/Filters/HighlightFilter.cs
+++ b/Greenshot/Drawing/Filters/HighlightFilter.cs
@@ -23,6 +23,7 @@ using System.Drawing;
using Greenshot.Drawing.Fields;
using Greenshot.Plugin.Drawing;
using GreenshotPlugin.Core;
+using System.Drawing.Imaging;
namespace Greenshot.Drawing.Filters {
[Serializable()]
@@ -46,19 +47,18 @@ namespace Greenshot.Drawing.Filters {
return;
}
- using (BitmapBuffer bbb = new BitmapBuffer(applyBitmap, applyRect)) {
- bbb.Lock();
+ using (IFastBitmap fastBitmap = FastBitmap.CreateCloneOf(applyBitmap, applyRect)) {
Color highlightColor = GetFieldValueAsColor(FieldType.FILL_COLOR);
- for (int y = 0; y < bbb.Height; y++) {
- for (int x = 0; x < bbb.Width; x++) {
+ for (int y = 0; y < fastBitmap.Height; y++) {
+ for (int x = 0; x < fastBitmap.Width; x++) {
if (parent.Contains(applyRect.Left + x, applyRect.Top + y) ^ Invert) {
- Color color = bbb.GetColorAt(x, y);
+ Color color = fastBitmap.GetColorAt(x, y);
color = Color.FromArgb(color.A, Math.Min(highlightColor.R, color.R), Math.Min(highlightColor.G, color.G), Math.Min(highlightColor.B, color.B));
- bbb.SetColorAt(x, y, color);
+ fastBitmap.SetColorAt(x, y, color);
}
}
}
- bbb.DrawTo(graphics, applyRect.Location);
+ fastBitmap.DrawTo(graphics, applyRect.Location);
}
}
}
diff --git a/Greenshot/Drawing/Filters/MagnifierFilter.cs b/Greenshot/Drawing/Filters/MagnifierFilter.cs
index 16a09d207..c6993f994 100644
--- a/Greenshot/Drawing/Filters/MagnifierFilter.cs
+++ b/Greenshot/Drawing/Filters/MagnifierFilter.cs
@@ -23,6 +23,7 @@ using System.Drawing;
using Greenshot.Drawing.Fields;
using Greenshot.Plugin.Drawing;
using GreenshotPlugin.Core;
+using System.Drawing.Imaging;
namespace Greenshot.Drawing.Filters {
[Serializable]
@@ -40,23 +41,22 @@ namespace Greenshot.Drawing.Filters {
}
int magnificationFactor = GetFieldValueAsInt(FieldType.MAGNIFICATION_FACTOR);
- using (BitmapBuffer bbb = new BitmapBuffer(applyBitmap, applyRect)) {
- int halfWidth = bbb.Size.Width / 2;
- int halfHeight = bbb.Size.Height / 2;
- bbb.Lock();
- using (BitmapBuffer bbbSrc = new BitmapBuffer(applyBitmap, applyRect)) {
- for (int y = 0; y < bbb.Height; y++) {
+ using (IFastBitmap destFastBitmap = FastBitmap.CreateCloneOf(applyBitmap, applyRect)) {
+ int halfWidth = destFastBitmap.Size.Width / 2;
+ int halfHeight = destFastBitmap.Size.Height / 2;
+ using (IFastBitmap sourceFastBitmap = FastBitmap.Create(applyBitmap, applyRect)) {
+ for (int y = 0; y < destFastBitmap.Height; y++) {
int yDistanceFromCenter = halfHeight - y;
- for (int x = 0; x < bbb.Width; x++) {
+ for (int x = 0; x < destFastBitmap.Width; x++) {
int xDistanceFromCenter = halfWidth - x;
if (parent.Contains(applyRect.Left + x, applyRect.Top + y) ^ Invert) {
- Color color = bbbSrc.GetColorAt(halfWidth - xDistanceFromCenter / magnificationFactor, halfHeight - yDistanceFromCenter / magnificationFactor);
- bbb.SetColorAt(x, y, color);
+ Color color = sourceFastBitmap.GetColorAt(halfWidth - xDistanceFromCenter / magnificationFactor, halfHeight - yDistanceFromCenter / magnificationFactor);
+ destFastBitmap.SetColorAt(x, y, color);
}
}
}
}
- bbb.DrawTo(graphics, applyRect.Location);
+ destFastBitmap.DrawTo(graphics, applyRect.Location);
}
}
}
diff --git a/GreenshotPlugin/Core/FastBitmap.cs b/GreenshotPlugin/Core/FastBitmap.cs
index aa4a66e65..49bbb58b1 100644
--- a/GreenshotPlugin/Core/FastBitmap.cs
+++ b/GreenshotPlugin/Core/FastBitmap.cs
@@ -106,6 +106,21 @@ namespace GreenshotPlugin.Core {
get;
set;
}
+
+ ///
+ /// Draw the stored bitmap to the destionation bitmap at the supplied point
+ ///
+ /// Graphics
+ /// Point with location
+ void DrawTo(Graphics graphics, Point destination);
+
+ ///
+ /// Draw the stored Bitmap on the Destination bitmap with the specified rectangle
+ /// Be aware that the stored bitmap will be resized to the specified rectangle!!
+ ///
+ /// Graphics
+ /// Rectangle with destination
+ void DrawTo(Graphics graphics, Rectangle destinationRect);
}
///
@@ -118,6 +133,7 @@ namespace GreenshotPlugin.Core {
protected const int RINDEX = 2;
protected const int GINDEX = 1;
protected const int BINDEX = 0;
+ protected Rectangle area = Rectangle.Empty;
///
/// If this is set to true, the bitmap will be disposed when disposing the IFastBitmap
///
@@ -130,27 +146,33 @@ namespace GreenshotPlugin.Core {
/// The bitmap for which the FastBitmap is creating access
///
protected Bitmap bitmap;
+
protected BitmapData bmData;
protected int stride; /* bytes per pixel row */
protected bool bitsLocked = false;
protected byte* pointer;
+ public static IFastBitmap Create(Bitmap source) {
+ return Create(source, Rectangle.Empty);
+ }
///
/// Factory for creating a FastBitmap depending on the pixelformat of the source
+ /// The supplied rectangle specifies the area for which the FastBitmap does its thing
///
/// Bitmap to access
+ /// Rectangle which specifies the area to have access to, can be Rectangle.Empty for the whole image
/// IFastBitmap
- public static IFastBitmap Create(Bitmap source) {
+ public static IFastBitmap Create(Bitmap source, Rectangle area) {
switch (source.PixelFormat) {
case PixelFormat.Format8bppIndexed:
- return new FastChunkyBitmap(source);
+ return new FastChunkyBitmap(source, area);
case PixelFormat.Format24bppRgb:
- return new Fast24RGBBitmap(source);
+ return new Fast24RGBBitmap(source, area);
case PixelFormat.Format32bppRgb:
- return new Fast32RGBBitmap(source);
+ return new Fast32RGBBitmap(source, area);
case PixelFormat.Format32bppArgb:
case PixelFormat.Format32bppPArgb:
- return new Fast32ARGBBitmap(source);
+ return new Fast32ARGBBitmap(source, area);
default:
throw new NotSupportedException(string.Format("Not supported Pixelformat {0}", source.PixelFormat));
}
@@ -162,7 +184,27 @@ namespace GreenshotPlugin.Core {
/// Bitmap to access
/// IFastBitmap
public static IFastBitmap CreateCloneOf(Image source, PixelFormat pixelFormat) {
- Bitmap destination = ImageHelper.CloneArea(source, Rectangle.Empty, pixelFormat);
+ return CreateCloneOf(source, pixelFormat, Rectangle.Empty);
+ }
+ ///
+ /// Factory for creating a FastBitmap as a destination for the source
+ ///
+ /// Bitmap to access
+ /// Area of the bitmap to access, can be Rectangle.Empty for the whole
+ /// IFastBitmap
+ public static IFastBitmap CreateCloneOf(Image source, Rectangle area) {
+ return CreateCloneOf(source, PixelFormat.DontCare, area);
+ }
+
+ ///
+ /// Factory for creating a FastBitmap as a destination for the source
+ ///
+ /// Bitmap to access
+ /// Pixelformat of the cloned bitmap
+ /// Area of the bitmap to access, can be Rectangle.Empty for the whole
+ /// IFastBitmap
+ public static IFastBitmap CreateCloneOf(Image source, PixelFormat pixelFormat, Rectangle area) {
+ Bitmap destination = ImageHelper.CloneArea(source, area, pixelFormat);
IFastBitmap fastBitmap = Create(destination);
((FastBitmap)fastBitmap).NeedsDispose = true;
return fastBitmap;
@@ -187,8 +229,15 @@ namespace GreenshotPlugin.Core {
/// Constructor which stores the image and locks it when called
///
///
- protected FastBitmap(Bitmap bitmap) {
+ protected FastBitmap(Bitmap bitmap, Rectangle area) {
this.bitmap = bitmap;
+ Rectangle bitmapArea = new Rectangle(Point.Empty, bitmap.Size);
+ if (area != Rectangle.Empty) {
+ area.Intersect(bitmapArea);
+ this.area = area;
+ } else {
+ this.area = bitmapArea;
+ }
Lock();
}
@@ -197,7 +246,10 @@ namespace GreenshotPlugin.Core {
///
public Size Size {
get {
- return bitmap.Size;
+ if (area == Rectangle.Empty) {
+ return bitmap.Size;
+ }
+ return area.Size;
}
}
@@ -206,7 +258,10 @@ namespace GreenshotPlugin.Core {
///
public int Width {
get {
- return bitmap.Width;
+ if (area == Rectangle.Empty) {
+ return bitmap.Width;
+ }
+ return area.Width;
}
}
@@ -215,7 +270,10 @@ namespace GreenshotPlugin.Core {
///
public int Height {
get {
- return bitmap.Height;
+ if (area == Rectangle.Empty) {
+ return bitmap.Height;
+ }
+ return area.Height;
}
}
@@ -271,7 +329,7 @@ namespace GreenshotPlugin.Core {
///
public void Lock() {
if (Width > 0 && Height > 0 && !bitsLocked) {
- bmData = bitmap.LockBits(new Rectangle(Point.Empty, Size), ImageLockMode.ReadWrite, bitmap.PixelFormat);
+ bmData = bitmap.LockBits(area, ImageLockMode.ReadWrite, bitmap.PixelFormat);
bitsLocked = true;
IntPtr Scan0 = bmData.Scan0;
@@ -353,7 +411,7 @@ namespace GreenshotPlugin.Core {
private Color[] colorEntries;
private Dictionary colorCache = new Dictionary();
- public FastChunkyBitmap(Bitmap source) : base(source) {
+ public FastChunkyBitmap(Bitmap source, Rectangle area) : base(source, area) {
colorEntries = bitmap.Palette.Entries;
}
@@ -443,7 +501,7 @@ namespace GreenshotPlugin.Core {
///
public unsafe class Fast24RGBBitmap : FastBitmap {
- public Fast24RGBBitmap(Bitmap source) : base(source) {
+ public Fast24RGBBitmap(Bitmap source, Rectangle area) : base(source, area) {
}
///
@@ -505,7 +563,7 @@ namespace GreenshotPlugin.Core {
/// This is the implementation of the IFastBitmap for 32 bit images (no Alpha)
///
public unsafe class Fast32RGBBitmap : FastBitmap {
- public Fast32RGBBitmap(Bitmap source) : base(source) {
+ public Fast32RGBBitmap(Bitmap source, Rectangle area) : base(source, area) {
}
@@ -571,7 +629,7 @@ namespace GreenshotPlugin.Core {
get;
set;
}
- public Fast32ARGBBitmap(Bitmap source) : base(source) {
+ public Fast32ARGBBitmap(Bitmap source, Rectangle area) : base(source, area) {
BackgroundBlendColor = Color.White;
}