OCR -Image splitting now a bit faster

git-svn-id: https://subtitleedit.googlecode.com/svn/trunk@2090 99eadd0c-20b8-1223-b5c4-2a2b2df33de2
This commit is contained in:
niksedk 2013-09-15 17:55:35 +00:00
parent f945f00e5a
commit 31cdbbf416
5 changed files with 836 additions and 110 deletions

View File

@ -1351,7 +1351,7 @@ namespace Nikse.SubtitleEdit.Forms
private static NOcrChar NOcrFindExpandedMatch(Bitmap parentBitmap, ImageSplitterItem targetItem, int topMargin, List<NOcrChar> nOcrChars)
{
var nbmp = new NikseBitmap(parentBitmap);
int w = targetItem.Bitmap.Width;
int w = targetItem.NikseBitmap.Width;
int index = 0;
foreach (NOcrChar oc in nOcrChars)
{
@ -1455,7 +1455,7 @@ namespace Nikse.SubtitleEdit.Forms
private static NOcrChar NOcrFindBestMatch(Bitmap parentBitmap, ImageSplitterItem targetItem, int topMargin, out bool italic, List<NOcrChar> nOcrChars, double unItalicFactor, bool tryItalicScaling, bool deepSeek)
{
italic = false;
var nbmp = new NikseBitmap(targetItem.Bitmap);
var nbmp = targetItem.NikseBitmap;
int index = 0;
foreach (NOcrChar oc in nOcrChars)
{
@ -2158,23 +2158,23 @@ namespace Nikse.SubtitleEdit.Forms
// Fix uppercase/lowercase issues (not I/l)
if (result.Text == "e")
_nocrLastLowercaseHeight = targetItem.Bitmap.Height;
_nocrLastLowercaseHeight = targetItem.NikseBitmap.Height;
else if (_nocrLastLowercaseHeight == -1 && result.Text == "a")
_nocrLastLowercaseHeight = targetItem.Bitmap.Height;
_nocrLastLowercaseHeight = targetItem.NikseBitmap.Height;
if (result.Text == "E" || result.Text == "H" || result.Text == "R" || result.Text == "D" || result.Text == "T")
_nocrLastUppercaseHeight = targetItem.Bitmap.Height;
_nocrLastUppercaseHeight = targetItem.NikseBitmap.Height;
else if (_nocrLastUppercaseHeight == -1 && result.Text == "M")
_nocrLastUppercaseHeight = targetItem.Bitmap.Height;
_nocrLastUppercaseHeight = targetItem.NikseBitmap.Height;
if (result.Text == "V" || result.Text == "W" || result.Text == "U" || result.Text == "S" || result.Text == "Z" || result.Text == "O" || result.Text == "X" || result.Text == "Ø" || result.Text == "C")
{
if (_nocrLastLowercaseHeight > 3 && targetItem.Bitmap.Height - _nocrLastLowercaseHeight < 2)
if (_nocrLastLowercaseHeight > 3 && targetItem.NikseBitmap.Height - _nocrLastLowercaseHeight < 2)
result.Text = result.Text.ToLower();
}
else if (result.Text == "v" || result.Text == "w" || result.Text == "u" || result.Text == "s" || result.Text == "z" || result.Text == "o" || result.Text == "x" || result.Text == "ø" || result.Text == "c")
{
if (_nocrLastUppercaseHeight > 3 && _nocrLastUppercaseHeight - targetItem.Bitmap.Height < 2)
if (_nocrLastUppercaseHeight > 3 && _nocrLastUppercaseHeight - targetItem.NikseBitmap.Height < 2)
result.Text = result.Text.ToUpper();
}
@ -2197,23 +2197,23 @@ namespace Nikse.SubtitleEdit.Forms
// Fix uppercase/lowercase issues (not I/l)
if (result.Text == "e")
p.NOcrLastLowercaseHeight = targetItem.Bitmap.Height;
p.NOcrLastLowercaseHeight = targetItem.NikseBitmap.Height;
else if (p.NOcrLastLowercaseHeight == -1 && result.Text == "a")
p.NOcrLastLowercaseHeight = targetItem.Bitmap.Height;
p.NOcrLastLowercaseHeight = targetItem.NikseBitmap.Height;
if (result.Text == "E" || result.Text == "H" || result.Text == "R" || result.Text == "D" || result.Text == "T")
p.NOcrLastUppercaseHeight = targetItem.Bitmap.Height;
p.NOcrLastUppercaseHeight = targetItem.NikseBitmap.Height;
else if (p.NOcrLastUppercaseHeight == -1 && result.Text == "M")
p.NOcrLastUppercaseHeight = targetItem.Bitmap.Height;
p.NOcrLastUppercaseHeight = targetItem.NikseBitmap.Height;
if (result.Text == "V" || result.Text == "W" || result.Text == "U" || result.Text == "S" || result.Text == "Z" || result.Text == "O" || result.Text == "X" || result.Text == "Ø" || result.Text == "C")
{
if (p.NOcrLastLowercaseHeight > 3 && targetItem.Bitmap.Height - p.NOcrLastLowercaseHeight < 2)
if (p.NOcrLastLowercaseHeight > 3 && targetItem.NikseBitmap.Height - p.NOcrLastLowercaseHeight < 2)
result.Text = result.Text.ToLower();
}
else if (result.Text == "v" || result.Text == "w" || result.Text == "u" || result.Text == "s" || result.Text == "z" || result.Text == "o" || result.Text == "x" || result.Text == "ø" || result.Text == "c")
{
if (p.NOcrLastUppercaseHeight > 3 && p.NOcrLastUppercaseHeight - targetItem.Bitmap.Height < 2)
if (p.NOcrLastUppercaseHeight > 3 && p.NOcrLastUppercaseHeight - targetItem.NikseBitmap.Height < 2)
result.Text = result.Text.ToUpper();
}
@ -2223,22 +2223,23 @@ namespace Nikse.SubtitleEdit.Forms
return new CompareMatch(result.Text, result.Italic, 0, null, result);
}
private CompareMatch GetCompareMatch(ImageSplitterItem targetItem, Bitmap parentBitmap, out CompareMatch secondBestGuess)
private CompareMatch GetCompareMatch(ImageSplitterItem targetItem, NikseBitmap parentBitmap, out CompareMatch secondBestGuess)
{
secondBestGuess = null;
int index = 0;
int smallestDifference = 10000;
int smallestIndex = -1;
Bitmap target = targetItem.Bitmap;
NikseBitmap target = targetItem.NikseBitmap;
foreach (CompareItem compareItem in _compareBitmaps)
{
// check for expand match!
if (compareItem.ExpandCount > 0 && compareItem.Bitmap.Width > targetItem.Bitmap.Width)
if (compareItem.ExpandCount > 0 && compareItem.Bitmap.Width > target.Width &&
parentBitmap.Width >= compareItem.Bitmap.Width + targetItem.X &&
parentBitmap.Height >= compareItem.Bitmap.Height + targetItem.Y)
{
Bitmap cutBitmap = ImageSplitter.Copy(parentBitmap, new Rectangle(targetItem.X, targetItem.Y, compareItem.Bitmap.Width, compareItem.Bitmap.Height));
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, cutBitmap);
cutBitmap.Dispose();
var cutBitmap = parentBitmap.CopyRectangle(new Rectangle(targetItem.X, targetItem.Y, compareItem.Bitmap.Width, compareItem.Bitmap.Height));
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, cutBitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2257,58 +2258,48 @@ namespace Nikse.SubtitleEdit.Forms
{
if (smallestDifference > 0.9 && target.Width > 25)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(4, 0, target.Width - 4, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(4, 0, target.Width - 4, target.Height));
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap);
cutBitmap.Dispose();
double differencePercentage = smallestDifference * 100.0 / (target.Width * target.Height);
}
if (smallestDifference > 0 && target.Width > 12)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(1, 0, target.Width - 2, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(1, 0, target.Width - 2, target.Height));
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap);
cutBitmap.Dispose();
}
if (smallestDifference > 0 && target.Width > 12)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(0, 0, target.Width - 2, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(0, 0, target.Width - 2, target.Height));
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap);
cutBitmap.Dispose();
}
if (smallestDifference > 0 && target.Width > 12)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(1, 0, target.Width - 2, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(1, 0, target.Width - 2, target.Height));
int topCrop = 0;
Bitmap cutBitmap2 = ImageSplitter.CropTopAndBottom(cutBitmap, out topCrop, 2);
var cutBitmap2 = NikseBitmapImageSplitter.CropTopAndBottom(cutBitmap, out topCrop, 2);
if (cutBitmap2.Height != target.Height)
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap2);
cutBitmap.Dispose();
cutBitmap2.Dispose();
}
if (smallestDifference > 0 && target.Width > 15)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(1, 0, target.Width - 2, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(1, 0, target.Width - 2, target.Height));
int topCrop = 0;
Bitmap cutBitmap2 = ImageSplitter.CropTopAndBottom(cutBitmap, out topCrop);
var cutBitmap2 = NikseBitmapImageSplitter.CropTopAndBottom(cutBitmap, out topCrop);
if (cutBitmap2.Height != target.Height)
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap2);
cutBitmap.Dispose();
cutBitmap2.Dispose();
}
if (smallestDifference > 0 && target.Width > 15)
{
Bitmap cutBitmap = CopyBitmapSection(target, new Rectangle(1, 0, target.Width - 2, target.Height));
var cutBitmap = target.CopyRectangle(new Rectangle(1, 0, target.Width - 2, target.Height));
int topCrop = 0;
Bitmap cutBitmap2 = ImageSplitter.CropTopAndBottom(cutBitmap, out topCrop);
var cutBitmap2 = NikseBitmapImageSplitter.CropTopAndBottom(cutBitmap, out topCrop);
if (cutBitmap2.Height != target.Height)
FindBestMatch(ref index, ref smallestDifference, ref smallestIndex, cutBitmap2);
cutBitmap.Dispose();
cutBitmap2.Dispose();
}
}
@ -2378,9 +2369,8 @@ namespace Nikse.SubtitleEdit.Forms
return bmp;
}
private void FindBestMatch(ref int index, ref int smallestDifference, ref int smallestIndex, Bitmap target2)
private void FindBestMatch(ref int index, ref int smallestDifference, ref int smallestIndex, NikseBitmap target)
{
NikseBitmap target = new NikseBitmap(target2);
int numberOfForegroundColors = CalculateNumberOfForegroundColors(target);
int minForeColorMatch = 90;
@ -2396,7 +2386,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < 3)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2424,7 +2414,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < 40)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2454,7 +2444,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2480,7 +2470,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2506,7 +2496,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2532,7 +2522,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2558,7 +2548,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2584,7 +2574,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2610,7 +2600,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2636,7 +2626,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2662,7 +2652,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2688,7 +2678,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < minForeColorMatch)
{
int dif = ImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -2716,6 +2706,8 @@ namespace Nikse.SubtitleEdit.Forms
}
}
private unsafe static int CalculateNumberOfForegroundColors(NikseBitmap nikseBitmap)
{
int count = 0;
@ -2810,7 +2802,8 @@ namespace Nikse.SubtitleEdit.Forms
if (threadText == null)
{
var matches = new List<CompareMatch>();
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(bitmap, (int)numericUpDownPixelsIsSpace.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
NikseBitmap parentBitmap = new NikseBitmap(bitmap);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(parentBitmap, (int)numericUpDownPixelsIsSpace.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
int index = 0;
bool expandSelection = false;
bool shrinkSelection = false;
@ -2867,14 +2860,14 @@ namespace Nikse.SubtitleEdit.Forms
_italicCheckedLast = _vobSubOcrCharacter.IsItalic;
}
else if (item.Bitmap == null)
else if (item.NikseBitmap == null)
{
matches.Add(new CompareMatch(item.SpecialCharacter, false, 0, null));
}
else
{
CompareMatch bestGuess;
CompareMatch match = GetCompareMatch(item, bitmap, out bestGuess);
CompareMatch match = GetCompareMatch(item, parentBitmap, out bestGuess);
if (match == null)
{
_vobSubOcrCharacter.Initialize(bitmap, item, _manualOcrDialogPosition, _italicCheckedLast, false, bestGuess, _lastAdditions, this);
@ -3101,20 +3094,20 @@ namespace Nikse.SubtitleEdit.Forms
private void NOCRIntialize(Bitmap bitmap)
{
var matches = new List<CompareMatch>();
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(bitmap, (int)numericUpDownNumberOfPixelsIsSpaceNOCR.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(new NikseBitmap(bitmap), (int)numericUpDownNumberOfPixelsIsSpaceNOCR.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
foreach (ImageSplitterItem item in list)
{
if (item.Bitmap != null)
if (item.NikseBitmap != null)
{
var old = item.Bitmap;
var nbmp = new NikseBitmap(item.Bitmap);
//var old = item.Bitmap;
var nbmp = item.NikseBitmap;
nbmp.ReplaceNonWhiteWithTransparent();
item.Y += nbmp.CropTopTransparent(0);
nbmp.CropTransparentSidesAndBottom(0, true);
nbmp.ReplaceTransparentWith(Color.Black);
item.Bitmap = nbmp.GetBitmap();
old.Dispose();
//item.Bitmap = nbmp.GetBitmap();
//old.Dispose();
GetNOcrCompareMatch(item, bitmap, _nocrChars, _unItalicFactor, false, false);
}
@ -3131,25 +3124,21 @@ namespace Nikse.SubtitleEdit.Forms
line = _nocrThreadResults[listViewIndex];
if (string.IsNullOrEmpty(line))
{
NikseBitmap nbmp = new NikseBitmap(bitmap);
nbmp.ReplaceNonWhiteWithTransparent();
bitmap = nbmp.GetBitmap();
var nbmpInput = new NikseBitmap(bitmap);
nbmpInput.ReplaceNonWhiteWithTransparent();
//bitmap = nbmp.GetBitmap();
var matches = new List<CompareMatch>();
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(bitmap, (int)numericUpDownNumberOfPixelsIsSpaceNOCR.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(nbmpInput, (int)numericUpDownNumberOfPixelsIsSpaceNOCR.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
foreach (ImageSplitterItem item in list)
{
if (item.Bitmap != null)
if (item.NikseBitmap != null)
{
var old = item.Bitmap;
nbmp = new NikseBitmap(item.Bitmap);
nbmp.ReplaceNonWhiteWithTransparent();
item.Y += nbmp.CropTopTransparent(0);
nbmp.CropTransparentSidesAndBottom(0, true);
nbmp.ReplaceTransparentWith(Color.Black);
item.Bitmap = nbmp.GetBitmap();
old.Dispose();
item.NikseBitmap.ReplaceNonWhiteWithTransparent();
item.Y += item.NikseBitmap.CropTopTransparent(0);
item.NikseBitmap.CropTransparentSidesAndBottom(0, true);
item.NikseBitmap.ReplaceTransparentWith(Color.Black);
}
}
int index = 0;
@ -3173,16 +3162,12 @@ namespace Nikse.SubtitleEdit.Forms
expandSelectionList.Add(list[index]);
}
item = GetExpandedSelection(bitmap, expandSelectionList, checkBoxRightToLeft.Checked);
if (item.Bitmap != null)
if (item.NikseBitmap != null)
{
var old = item.Bitmap;
nbmp = new NikseBitmap(item.Bitmap);
nbmp.ReplaceNonWhiteWithTransparent();
item.Y += nbmp.CropTopTransparent(0);
nbmp.CropTransparentSidesAndBottom(0, true);
nbmp.ReplaceTransparentWith(Color.Black);
item.Bitmap = nbmp.GetBitmap();
old.Dispose();
item.NikseBitmap.ReplaceNonWhiteWithTransparent();
item.Y += item.NikseBitmap.CropTopTransparent(0);
item.NikseBitmap.CropTransparentSidesAndBottom(0, true);
item.NikseBitmap.ReplaceTransparentWith(Color.Black);
}
_vobSubOcrNOcrCharacter.Initialize(bitmap, item, _manualOcrDialogPosition, _italicCheckedLast, expandSelectionList.Count > 1, null, _lastAdditions, this);
@ -3224,7 +3209,7 @@ namespace Nikse.SubtitleEdit.Forms
_italicCheckedLast = _vobSubOcrNOcrCharacter.IsItalic;
}
else if (item.Bitmap == null)
else if (item.NikseBitmap == null)
{
matches.Add(new CompareMatch(item.SpecialCharacter, false, 0, null));
}
@ -3796,21 +3781,21 @@ namespace Nikse.SubtitleEdit.Forms
e.Result = p;
Bitmap bitmap = p.Picture;
var matches = new List<CompareMatch>();
List<ImageSplitterItem> lines = ImageSplitter.SplitVertical(bitmap);
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(lines, p.NumberOfPixelsIsSpace, p.RightToLeft, Configuration.Settings.VobSubOcr.TopToBottom);
List<ImageSplitterItem> lines = NikseBitmapImageSplitter.SplitVertical(bitmap);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(lines, p.NumberOfPixelsIsSpace, p.RightToLeft, Configuration.Settings.VobSubOcr.TopToBottom);
int index = 0;
int outerIndex = 0;
while (outerIndex < list.Count)
{
ImageSplitterItem item = list[outerIndex];
if (item.Bitmap == null)
if (item.NikseBitmap == null)
{
matches.Add(new CompareMatch(item.SpecialCharacter, false, 0, null));
}
else
{
var target = new NikseBitmap(item.Bitmap);
var target = item.NikseBitmap;
int numberOfForegroundColors = CalculateNumberOfForegroundColors(target);
int smallestDifference = 10000;
@ -3828,7 +3813,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < 30)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -3854,7 +3839,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < 50)
{
int dif = ImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(target, compareItem.Bitmap);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -3882,7 +3867,7 @@ namespace Nikse.SubtitleEdit.Forms
if (Math.Abs(compareItem.NumberOfForegroundColors - numberOfForegroundColors) < 55)
{
int dif = ImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
int dif = NikseBitmapImageSplitter.IsBitmapsAlike(compareItem.Bitmap, target);
if (dif < smallestDifference)
{
smallestDifference = dif;
@ -3897,7 +3882,7 @@ namespace Nikse.SubtitleEdit.Forms
}
CompareMatch match = null;
double differencePercentage = smallestDifference * 100.0 / (item.Bitmap.Width * item.Bitmap.Height);
double differencePercentage = smallestDifference * 100.0 / (item.NikseBitmap.Width * item.NikseBitmap.Height);
double maxDiff = (double)p.MaxErrorPercent;
if (differencePercentage <= maxDiff)
{
@ -4027,10 +4012,10 @@ namespace Nikse.SubtitleEdit.Forms
var p = (NOcrThreadParameter)e.Argument;
e.Result = p;
Bitmap bitmap = p.Picture;
var nbmp = new NikseBitmap(bitmap);
nbmp.ReplaceNonWhiteWithTransparent();
bitmap = nbmp.GetBitmap();
//Bitmap bitmap = p.Picture;
var nbmpInput = new NikseBitmap(p.Picture);
nbmpInput.ReplaceNonWhiteWithTransparent();
// bitmap = nbmp.GetBitmap();
var matches = new List<CompareMatch>();
int minLineHeight = p.NOcrLastLowercaseHeight;
@ -4040,34 +4025,32 @@ namespace Nikse.SubtitleEdit.Forms
if (maxLineHeight < 10)
minLineHeight = 80;
List<ImageSplitterItem> lines = ImageSplitter.SplitVertical(bitmap, minLineHeight);
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(lines, p.NumberOfPixelsIsSpace, p.RightToLeft, Configuration.Settings.VobSubOcr.TopToBottom);
List<ImageSplitterItem> lines = NikseBitmapImageSplitter.SplitVertical(nbmpInput, minLineHeight);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(lines, p.NumberOfPixelsIsSpace, p.RightToLeft, Configuration.Settings.VobSubOcr.TopToBottom);
foreach (ImageSplitterItem item in list)
{
if (item.Bitmap != null)
if (item.NikseBitmap != null)
{
var old = item.Bitmap;
nbmp = new NikseBitmap(item.Bitmap);
var nbmp = item.NikseBitmap;
nbmp.ReplaceNonWhiteWithTransparent();
item.Y += nbmp.CropTopTransparent(0);
nbmp.CropTransparentSidesAndBottom(0, true);
nbmp.ReplaceTransparentWith(Color.Black);
item.Bitmap = nbmp.GetBitmap();
old.Dispose();
// item.Bitmap = nbmp.GetBitmap();
}
}
int index = 0;
while (index < list.Count)
{
ImageSplitterItem item = list[index];
if (item.Bitmap == null)
if (item.NikseBitmap == null)
{
matches.Add(new CompareMatch(item.SpecialCharacter, false, 0, null));
}
else
{
CompareMatch match = GetNOcrCompareMatch(item, bitmap, p);
CompareMatch match = GetNOcrCompareMatch(item, nbmpInput.GetBitmap(), p);
if (match == null)
{
//if (p.AdvancedItalicDetection)
@ -6028,8 +6011,9 @@ namespace Nikse.SubtitleEdit.Forms
Cursor = Cursors.WaitCursor;
Bitmap bitmap = GetSubtitleBitmap(subtitleListView1.SelectedItems[0].Index);
NikseBitmap parentBitmap = new NikseBitmap(bitmap);
var matches = new List<CompareMatch>();
List<ImageSplitterItem> list = ImageSplitter.SplitBitmapToLetters(bitmap, (int)numericUpDownPixelsIsSpace.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
List<ImageSplitterItem> list = NikseBitmapImageSplitter.SplitBitmapToLetters(parentBitmap, (int)numericUpDownPixelsIsSpace.Value, checkBoxRightToLeft.Checked, Configuration.Settings.VobSubOcr.TopToBottom);
int index = 0;
var imageSources = new List<Bitmap>();
while (index < list.Count)
@ -6043,7 +6027,7 @@ namespace Nikse.SubtitleEdit.Forms
else
{
CompareMatch bestGuess;
CompareMatch match = GetCompareMatch(item, bitmap, out bestGuess);
CompareMatch match = GetCompareMatch(item, parentBitmap, out bestGuess);
if (match == null)
{
matches.Add(new CompareMatch(Configuration.Settings.Language.VobSubOcr.NoMatch, false, 0, null));

View File

@ -7,7 +7,23 @@ namespace Nikse.SubtitleEdit.Logic
public int X { get; set; }
public int Y { get; set; }
public int ParentY { get; set; }
public Bitmap Bitmap { get; set; }
public Bitmap Bitmap
{
get
{
if (NikseBitmap == null)
return null;
return NikseBitmap.GetBitmap();
}
set
{
if (value == null)
NikseBitmap = null;
else
NikseBitmap = new NikseBitmap(value);
}
}
public NikseBitmap NikseBitmap { get; set; }
public string SpecialCharacter { get; set; }
public ImageSplitterItem(int x, int y, Bitmap bitmap)
@ -18,12 +34,20 @@ namespace Nikse.SubtitleEdit.Logic
SpecialCharacter = null;
}
public ImageSplitterItem(int x, int y, NikseBitmap bitmap)
{
X = x;
Y = y;
NikseBitmap = bitmap;
SpecialCharacter = null;
}
public ImageSplitterItem(string specialCharacter)
{
X = 0;
Y = 0;
SpecialCharacter = specialCharacter;
Bitmap = null;
NikseBitmap = null;
}
}
}

View File

@ -29,6 +29,13 @@ namespace Nikse.SubtitleEdit.Logic
_bitmapData = new byte[Width * Height * 4];
}
public NikseBitmap(int width, int height, byte[] bitmapData)
{
Width = width;
Height = height;
_bitmapData = bitmapData;
}
public NikseBitmap(Bitmap inputBitmap)
{
if (inputBitmap == null)
@ -892,5 +899,25 @@ namespace Nikse.SubtitleEdit.Logic
return newBitmap;
}
public NikseBitmap CopyRectangle(Rectangle section)
{
if (section.Bottom > Height)
section = new Rectangle(section.Left, section.Top, section.Width, Height - section.Top);
if (section.Width + section.Left > Width)
section = new Rectangle(section.Left, section.Top, Width - section.Left, section.Height);
var newBitmapData = new byte[section.Width * section.Height * 4];
int index = 0;
for (int y = section.Top; y < section.Bottom; y++)
{
int pixelAddress = (section.Left * 4) + (y * 4 * Width);
Buffer.BlockCopy(_bitmapData, pixelAddress, newBitmapData, index, 4 * section.Width);
index += 4 * section.Width;
}
return new NikseBitmap(section.Width, section.Height, newBitmapData);
}
}
}

View File

@ -0,0 +1,690 @@
using System;
using System.Collections.Generic;
using System.Drawing;
namespace Nikse.SubtitleEdit.Logic
{
public class NikseBitmapImageSplitter
{
public static bool IsColorClose(Color a, Color b, int tolerance)
{
if (a.A < 120 && b.A < 120)
return true; // transparent
if (a.A > 250 && a.R > 90 && a.G > 90 && a.B > 90 &&
b.A > 250 && b.R > 90 && b.G > 90 && b.B > 90)
return true; // dark, non transparent
int diff = (a.R + a.G + a.B) - (b.R + b.G + b.B);
return diff < tolerance && diff > -tolerance;
}
public static NikseBitmap Copy(NikseBitmap sourceBitmap, Rectangle section)
{
return sourceBitmap.CopyRectangle(section);
}
public static NikseBitmap CropTopAndBottom(NikseBitmap bmp, out int topCropping)
{
int startTop = 0;
int maxTop = bmp.Height-2;
if (maxTop > bmp.Height)
maxTop = bmp.Height;
for (int y = 0; y < maxTop; y++)
{
bool allTransparent = true;
for (int x = 1; x < bmp.Width - 1; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
allTransparent = false;
break;
}
}
if (!allTransparent)
break;
startTop++;
}
if (startTop > 9)
startTop -= 5; // if top space > 9, then allways leave blank 5 pixels on top (so . is not confused with ').
topCropping = startTop;
for (int y = bmp.Height-1; y > 3; y--)
{
bool allTransparent = true;
for (int x = 1; x < bmp.Width-1; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
allTransparent = false;
break;
}
}
if (allTransparent == false)
return Copy(bmp, new Rectangle(0, startTop, bmp.Width - 1, y-startTop+1));
}
return bmp;
}
public static NikseBitmap CropTopAndBottom(NikseBitmap bmp, out int topCropping, int maxDifferentPixelsOnLine)
{
int startTop = 0;
int maxTop = bmp.Height - 2;
if (maxTop > bmp.Height)
maxTop = bmp.Height;
for (int y = 0; y < maxTop; y++)
{
int difference = 0;
bool allTransparent = true;
for (int x = 1; x < bmp.Width - 1; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
difference++;
if (difference >= maxDifferentPixelsOnLine)
{
allTransparent = false;
break;
}
}
}
if (!allTransparent)
break;
startTop++;
}
if (startTop > 9)
startTop -= 5; // if top space > 9, then allways leave blank 5 pixels on top (so . is not confused with ').
topCropping = startTop;
for (int y = bmp.Height - 1; y > 3; y--)
{
int difference = 0;
bool allTransparent = true;
for (int x = 1; x < bmp.Width - 1; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
difference++;
if (difference >= maxDifferentPixelsOnLine)
{
allTransparent = false;
break;
}
}
}
if (allTransparent == false)
return Copy(bmp, new Rectangle(0, startTop, bmp.Width - 1, y - startTop + 1));
}
return bmp;
}
public static List<ImageSplitterItem> SplitVertical(Bitmap bmp)
{
return SplitVertical(new NikseBitmap(bmp));
}
public static List<ImageSplitterItem> SplitVertical(Bitmap bmp, int lineMinHeight)
{
return SplitVertical(new NikseBitmap(bmp), lineMinHeight);
}
public static List<ImageSplitterItem> SplitVertical(NikseBitmap bmp)
{ // split into lines
int startY = 0;
int size = 0;
var parts = new List<ImageSplitterItem>();
for (int y = 0; y < bmp.Height; y++)
{
bool allTransparent = true;
for (int x = 0; x < bmp.Width; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
allTransparent = false;
break;
}
}
if (allTransparent)
{
if (size > 2 && size < 6)
{
size++; // at least 5 pixels, like top of 'i'
}
else
{
if (size > 2)
{
NikseBitmap part = Copy(bmp, new Rectangle(0, startY, bmp.Width, size+1));
// part.Save("c:\\line_0_to_width.bmp");
parts.Add(new ImageSplitterItem(0, startY, part));
// bmp.Save("c:\\original.bmp");
}
size = 0;
startY = y;
}
}
else
{
size++;
}
}
if (size > 2)
{
NikseBitmap part = Copy(bmp, new Rectangle(0, startY, bmp.Width, size+1));
parts.Add(new ImageSplitterItem(0, startY, part));
}
return parts;
}
public static List<ImageSplitterItem> SplitVertical(NikseBitmap bmp, int lineMinHeight)
{ // split into lines
int startY = 0;
int size = 0;
var parts = new List<ImageSplitterItem>();
for (int y = 0; y < bmp.Height; y++)
{
bool allTransparent = true;
for (int x = 0; x < bmp.Width; x++)
{
Color c = bmp.GetPixel(x, y);
if (c.A != 0)
{
allTransparent = false;
break;
}
}
if (allTransparent)
{
if (size > 2 && size <= lineMinHeight)
{
size++; // at least 5 pixels, like top of 'i'
}
else
{
if (size > 2)
{
NikseBitmap part = Copy(bmp, new Rectangle(0, startY, bmp.Width, size + 1));
// part.Save("c:\\line_0_to_width.bmp");
parts.Add(new ImageSplitterItem(0, startY, part));
// bmp.Save("c:\\original.bmp");
}
size = 0;
startY = y;
}
}
else
{
size++;
}
}
if (size > 2)
{
NikseBitmap part = Copy(bmp, new Rectangle(0, startY, bmp.Width, size + 1));
parts.Add(new ImageSplitterItem(0, startY, part));
}
return parts;
}
public static int IsBitmapsAlike(Bitmap bmp1, Bitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
public static int IsBitmapsAlike(FastBitmap bmp1, Bitmap bmp2)
{
int different = 0;
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
Color c1 = bmp1.GetPixel(x, y);
Color c2 = bmp1.GetPixel(x, y);
if (!IsColorClose(c1, c2, 20))
different++;
}
}
return different;
}
private static List<ImageSplitterItem> SplitHorizontal(ImageSplitterItem verticalItem, int xOrMorePixelsMakesSpace)
{ // split line into letters
NikseBitmap bmp = verticalItem.NikseBitmap;
var parts = new List<ImageSplitterItem>();
int size = 0;
int startX = 0;
int lastEndX = 0;
int y = 0;
bool spaceJustAdded = false;
for (int x = 0; x < bmp.Width - 1; x++)
{
bool allTransparent = IsVerticalLineTransparent(bmp, ref y, x);
// check if line is transparent and cursive
bool cursiveOk = false;
int tempY = 0;
if (allTransparent == false &&
size > 5 &&
y > 3 &&
x < bmp.Width-2 &&
!IsVerticalLineTransparent(bmp, ref tempY, x + 1))
{
//Add space?
if (lastEndX > 0 && lastEndX + xOrMorePixelsMakesSpace < startX)
{
int cleanCount = 0;
for (int j = lastEndX; j < startX; j++)
{
int y1 = j;
if (IsVerticalLineTransparent2(bmp, ref y1, j))
cleanCount++;
}
if (cleanCount > 0 && !spaceJustAdded)
{
parts.Add(new ImageSplitterItem(" "));
spaceJustAdded = true;
}
}
var cursivePoints = new List<Point>();
cursiveOk = IsCursiveVerticalLineTransparent(bmp, size, y, x, cursivePoints);
if (cursiveOk)
{
// make letter image
int end = x + 1 - startX;
if (startX > 0)
{
startX--;
end++;
}
NikseBitmap b1 = Copy(bmp, new Rectangle(startX, 0, end, bmp.Height));
// b1.Save(@"d:\temp\cursive.bmp"); // just for debugging
// make non-black/transparent stuff from other letter transparent
foreach (Point p in cursivePoints)
{
for (int fixY = p.Y; fixY < bmp.Height; fixY++)
b1.SetPixel(p.X - startX, fixY, Color.Transparent);
}
RemoveBlackBarRight(b1);
// b1.Save(@"d:\temp\cursive-cleaned.bmp"); // just for debugging
// crop and save image
int addY;
b1 = CropTopAndBottom(b1, out addY);
parts.Add(new ImageSplitterItem(startX, verticalItem.Y + addY, b1));
spaceJustAdded = false;
size = 0;
startX = x + 1;
lastEndX = x;
}
}
if (!cursiveOk)
{
if (allTransparent)
{
if (size > 0)
{
if (size > 1)
{
//Add space?
if (lastEndX > 0 && lastEndX + xOrMorePixelsMakesSpace < startX)
{
int cleanCount = 0;
for (int j = lastEndX; j < startX; j++)
{
int y1=j;
if (IsVerticalLineTransparent2(bmp, ref y1, j))
cleanCount++;
}
if (cleanCount > 2 && !spaceJustAdded)
{
parts.Add(new ImageSplitterItem(" "));
spaceJustAdded = true;
}
}
if (startX > 0)
startX--;
lastEndX = x;
int end = x + 1 - startX;
NikseBitmap part = Copy(bmp, new Rectangle(startX, 0, end, bmp.Height));
RemoveBlackBarRight(part);
int addY;
// part.Save("c:\\before" + startX.ToString() + ".bmp"); // just for debugging
part = CropTopAndBottom(part, out addY);
// part.Save("c:\\after" + startX.ToString() + ".bmp"); // just for debugging
parts.Add(new ImageSplitterItem(startX, verticalItem.Y + addY, part));
spaceJustAdded = false;
// part.Save(@"d:\temp\cursive.bmp"); // just for debugging
}
size = 0;
}
startX = x + 1;
}
else
{
size++;
}
}
}
if (size > 0)
{
if (lastEndX > 0 && lastEndX + xOrMorePixelsMakesSpace < startX && !spaceJustAdded)
parts.Add(new ImageSplitterItem(" "));
if (startX > 0)
startX--;
lastEndX = bmp.Width-1;
int end = lastEndX + 1 - startX;
NikseBitmap part = Copy(bmp, new Rectangle(startX, 0, end, bmp.Height - 1));
int addY;
part = CropTopAndBottom(part, out addY);
parts.Add(new ImageSplitterItem(startX, verticalItem.Y + addY, part));
//part.Save(@"d:\temp\cursive.bmp"); // just for debugging
}
return parts;
}
private static void RemoveBlackBarRight(NikseBitmap bmp)
{
int xRemoveBlackBar = bmp.Width-1;
for (int yRemoveBlackBar = 0; yRemoveBlackBar < bmp.Height; yRemoveBlackBar++)
{
Color c = bmp.GetPixel(xRemoveBlackBar, yRemoveBlackBar);
if (c.A == 0 || IsColorClose(c, Color.Black, 280))
{
if (bmp.GetPixel(xRemoveBlackBar - 1, yRemoveBlackBar).A == 0)
bmp.SetPixel(xRemoveBlackBar, yRemoveBlackBar, Color.Transparent);
}
}
}
private static bool IsCursiveVerticalLineTransparent(NikseBitmap bmp, int size, int y, int x, List<Point> cursivePoints)
{
bool cursiveOk = true;
int newY = y;
int newX = x;
while (cursiveOk && newY < bmp.Height - 1)
{
Color c0 = bmp.GetPixel(newX, newY);
if (c0.A == 0 || IsColorClose(c0, Color.Black, 280))
{
newY++;
}
else
{
Color c1 = bmp.GetPixel(newX - 1, newY - 1);
Color c2 = bmp.GetPixel(newX - 1, newY);
if ((c1.A == 0 || IsColorClose(c1, Color.Black, 280)) && // still dark color...
(c2.A == 0 || IsColorClose(c2, Color.Black, 280)))
{
cursivePoints.Add(new Point(newX, newY));
if (newX > 1)
newX--;
else
cursiveOk = false;
newY++;
}
else
{
cursiveOk = false;
}
}
if (newX < x - size)
cursiveOk = false;
}
return cursiveOk;
}
private static bool IsVerticalLineTransparent(NikseBitmap bmp, ref int y, int x)
{
bool allTransparent = true;
for (y = 0; y < bmp.Height - 1; y++)
{
Color c = bmp.GetPixel(x, y);
if (c.A == 0 || //c.ToArgb() == transparentColor.ToArgb() ||
IsColorClose(c, Color.Black, 280)) // still dark color...
{
}
else
{
allTransparent = false;
break;
}
}
return allTransparent;
}
private static bool IsVerticalLineTransparent2(NikseBitmap bmp, ref int y, int x)
{
bool allTransparent = true;
for (y = 0; y < bmp.Height - 1; y++)
{
int a = bmp.GetAlpha(x, y);
if (a == 0) // still dark color...
{
}
else
{
allTransparent = false;
break;
}
}
return allTransparent;
}
public static List<ImageSplitterItem> SplitBitmapToLetters(NikseBitmap bmp, int xOrMorePixelsMakesSpace, bool rightToLeft, bool topToBottom)
{
var list = new List<ImageSplitterItem>();
// split into seperate lines
List<ImageSplitterItem> verticalBitmaps = SplitVertical(bmp, xOrMorePixelsMakesSpace);
if (!topToBottom)
verticalBitmaps.Reverse();
// split into letters
int lineCount = 0;
foreach (ImageSplitterItem b in verticalBitmaps)
{
if (lineCount > 0)
list.Add(new ImageSplitterItem(Environment.NewLine));
var line = new List<ImageSplitterItem>();
foreach (ImageSplitterItem item in SplitHorizontal(b, xOrMorePixelsMakesSpace))
{
item.ParentY = item.Y;
line.Add(item);
}
if (rightToLeft)
line.Reverse();
foreach (ImageSplitterItem item in line)
list.Add(item);
lineCount++;
}
return list;
}
public static List<ImageSplitterItem> SplitBitmapToLetters(List<ImageSplitterItem> verticalBitmaps, int xOrMorePixelsMakesSpace, bool rightToLeft, bool topToBottom)
{
var list = new List<ImageSplitterItem>();
if (!topToBottom)
verticalBitmaps.Reverse();
// split into letters
int lineCount = 0;
foreach (ImageSplitterItem b in verticalBitmaps)
{
if (lineCount > 0)
list.Add(new ImageSplitterItem(Environment.NewLine));
var line = new List<ImageSplitterItem>();
foreach (ImageSplitterItem item in SplitHorizontal(b, xOrMorePixelsMakesSpace))
{
item.ParentY = item.Y;
line.Add(item);
}
if (rightToLeft)
line.Reverse();
foreach (ImageSplitterItem item in line)
list.Add(item);
lineCount++;
}
return list;
}
internal static unsafe int IsBitmapsAlike(NikseBitmap bmp1, NikseBitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
internal static unsafe int IsBitmapsAlike(ManagedBitmap bmp1, NikseBitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
internal static unsafe int IsBitmapsAlike(ManagedBitmap bmp1, Bitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
internal static unsafe int IsBitmapsAlike(NikseBitmap bmp1, ManagedBitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
internal static unsafe int IsBitmapsAlike(Bitmap bmp1, NikseBitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
NikseBitmap nbmp1 = new NikseBitmap(bmp1);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(nbmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
internal static unsafe int IsBitmapsAlike(NikseBitmap bmp1, Bitmap bmp2)
{
int different = 0;
int maxDiff = (int)(bmp1.Width * bmp1.Height / 5.0);
for (int x = 1; x < bmp1.Width; x++)
{
for (int y = 1; y < bmp1.Height; y++)
{
if (!IsColorClose(bmp1.GetPixel(x, y), bmp2.GetPixel(x, y), 20))
{
different++;
}
}
if (different > maxDiff)
return different + 10;
}
return different;
}
}
}

View File

@ -734,6 +734,7 @@
<Compile Include="Logic\BluRaySup\PaletteInfo.cs" />
<Compile Include="Logic\BluRaySup\ToolBox.cs" />
<Compile Include="Logic\BmpReader.cs" />
<Compile Include="Logic\NikseBitmapImageSplitter.cs" />
<Compile Include="Logic\DetectEncoding\EncodingTools.cs" />
<Compile Include="Logic\DetectEncoding\Multilang\CMLangConvertCharset.cs" />
<Compile Include="Logic\DetectEncoding\Multilang\CMLangConvertCharsetClass.cs" />