更新除背景底色算法,提高效能

This commit is contained in:
yangjiaxuan 2023-12-04 17:54:50 +08:00
parent 57082a9efe
commit b1b5ed44e0
3 changed files with 24 additions and 100 deletions

View File

@ -1,17 +1,11 @@
#include "ImageApplyFadeBackGroundColor.h" #include "ImageApplyFadeBackGroundColor.h"
#include "ImageProcess_Public.h"
CImageApplyFadeBackGroudColor::CImageApplyFadeBackGroudColor(int threshold, int offset, int range) CImageApplyFadeBackGroudColor::CImageApplyFadeBackGroudColor(int threshold, int offset, int range)
: m_threshold(threshold) : m_threshold(threshold)
, m_offset(offset) , m_offset(offset)
, m_range(range) , m_range(range)
{ {
memset(m_table1, 255, 768);
memset(m_table1, 0, m_threshold * 3);
memset(m_table2, 255, 256 * 3);
for (size_t i = 0; i < 256; i++)
m_table2[i] = i;
} }
CImageApplyFadeBackGroudColor::~CImageApplyFadeBackGroudColor() CImageApplyFadeBackGroudColor::~CImageApplyFadeBackGroudColor()
@ -48,98 +42,33 @@ void CImageApplyFadeBackGroudColor::apply(cv::Mat& pDib, int side)
cv::add(pDib, cv::Scalar::all(255 + m_offset) - mean_bgr, pDib, mask); cv::add(pDib, cv::Scalar::all(255 + m_offset) - mean_bgr, pDib, mask);
#else #else
#if 0
fadeBackground(pDib.data, pDib.cols, pDib.rows, pDib.step, m_threshold, m_offset, m_range); fadeBackground(pDib.data, pDib.cols, pDib.rows, pDib.step, m_threshold, m_offset, m_range);
#else
fadeBackground(pDib, m_threshold, m_offset, m_range);
#endif
#endif #endif
} }
/// <summary> void CImageApplyFadeBackGroudColor::fadeBackground(cv::Mat& image, int threshold, int offset, int range)
/// 除文稿底色算法仅支持24位图像
/// </summary>
/// <param name="data">图像数据头指针</param>
/// <param name="bytesPerLine">每行数据大小</param>
/// <param name="height">图像高度</param>
/// <param name="threshold">阈值参考值为100</param>
/// <param name="offset">文稿底色增亮偏移量默认为0。值越大背景越白反之越暗</param>
void CImageApplyFadeBackGroudColor::fadeBackground(unsigned char* data, int width, int height, int bytesPerLine, int threshold, int offset, int range)
{ {
memset(m_table1, 255, 768); cv::Mat resizeMat;
memset(m_table1, 0, threshold * 3); cv::resize(image, resizeMat, cv::Size(200, 200));
memset(m_table2, 255, 256 * 3); cv::Mat mask;
cv::cvtColor(resizeMat, mask, cv::COLOR_BGR2GRAY);
cv::threshold(mask, mask, threshold, 255, cv::THRESH_BINARY);
for (uint i = 0; i < 256; i++) cv::Scalar bgc = hg::getBackGroundColor(resizeMat, mask, threshold);
m_table2[i] = i;
int hist_bgr[3][256] = { 0 }; std::vector<int> low, up;
for (size_t i = 0; i < 3; i++)
unsigned char* mask = new unsigned char[width * height];
unsigned char* ptr_data = data;
unsigned char* ptr_mask = mask;
unsigned char b = 0;
for (uint i = 0; i < height; i++, ptr_data += bytesPerLine, ptr_mask += width)
for (uint j = 0, x = 0; j < width; j++, x += 3)
{
b = m_table1[ptr_data[x] + ptr_data[x + 1] + ptr_data[x + 2]];
ptr_mask[j] = b;
for (uint k = 0; k < 3; k++)
hist_bgr[k][ptr_data[x + k] & b]++;
}
int max_vals[3] = { 0 };
int max_indexes[3] = { 0 };
for (uint i = 1; i < 256; i++)
for (uint j = 0; j < 3; j++)
if (hist_bgr[j][i] > max_vals[j])
{
max_vals[j] = hist_bgr[j][i];
max_indexes[j] = i;
}
uchar table_rgb[3][256] = { 0 };
for (uint i = 0; i < 3; i++)
{ {
int start = cv::max(max_indexes[i] - range, 0); low.push_back(cv::max((int)bgc[i] - range, 0));
int end = cv::min(max_indexes[i] + range, 255); up.push_back(cv::min((int)bgc[i] + range, 255));
memset(table_rgb[i] + start, 255, cv::min(end - start + 1, 256 - start));
} }
ptr_data = data; cv::inRange(image, low, up, mask);
ptr_mask = mask; cv::add(image, cv::Scalar::all(offset), image, mask);
for (uint i = 0; i < height; i++, ptr_data += bytesPerLine, ptr_mask += width)
for (uint j = 0, x = 0; j < width; j++, x += 3)
ptr_mask[j] &= table_rgb[0][ptr_data[x]] & table_rgb[1][ptr_data[x + 1]] & table_rgb[2][ptr_data[x + 2]];
unsigned char offset_rgb[3];
for (uint i = 0; i < 3; i++)
offset_rgb[i] = cv::min(255 + offset - max_indexes[i], 255);
#if 1
ptr_data = data;
ptr_mask = mask;
for (uint i = 0; i < height; i++, ptr_data += bytesPerLine, ptr_mask += width)
for (uint j = 0, x = 0; j < width; j++, x += 3)
for (uint k = 0; k < 3; k++)
ptr_data[x + k] = m_table2[(int)ptr_data[x + k] + (offset_rgb[k] & ptr_mask[j])];
#else
for (uint c = 0; c < 3; c++)
{
ptr_data = data + c;
ptr_mask = mask;
for (uint y = 0; y < height; y++)
{
int ptr_x = 0;
for (uint x = 0; x < width; x++)
{
ptr_data[ptr_x] = m_table2[(int)ptr_data[ptr_x] + (offset_rgb[c] & ptr_mask[x])];
ptr_x += 3;
}
ptr_data += bytesPerLine;
ptr_mask += width;
}
}
#endif
delete[] mask;
} }
void CImageApplyFadeBackGroudColor::apply(std::vector<cv::Mat>& mats, bool isTwoSide) void CImageApplyFadeBackGroudColor::apply(std::vector<cv::Mat>& mats, bool isTwoSide)

View File

@ -15,7 +15,8 @@
* 2022/03/08 v3.4 BUG * 2022/03/08 v3.4 BUG
* 2022/10/22 v3.5 使opencv ROI的内存机制 * 2022/10/22 v3.5 使opencv ROI的内存机制
* 2023/11/22 v3.6 BUG * 2023/11/22 v3.6 BUG
* v3.6 * 2023/12/01 v3.7
* v3.7
* ==================================================== * ====================================================
*/ */
@ -26,7 +27,6 @@
#include "ImageApply.h" #include "ImageApply.h"
class CImageApplyAdjustColors;
class GIMGPROC_LIBRARY_API CImageApplyFadeBackGroudColor : public CImageApply class GIMGPROC_LIBRARY_API CImageApplyFadeBackGroudColor : public CImageApply
{ {
public: public:
@ -43,25 +43,20 @@ public:
virtual void apply(std::vector<cv::Mat>& mats, bool isTwoSide); virtual void apply(std::vector<cv::Mat>& mats, bool isTwoSide);
private: private:
/// <summary> /// <summary>
/// 除文稿底色算法仅支持24位图像 /// 除文稿底色算法仅支持24位图像
/// </summary> /// </summary>
/// <param name="data">图像数据头指针</param> /// <param name="image">图像</param>
/// <param name="width">图像宽度</param>
/// <param name="height">图像高度</param>
/// <param name="bytesPerLine">每行数据大小</param>
/// <param name="threshold">阈值。区分文稿和黑色背景。取值范围[0, 255],参考值为100</param> /// <param name="threshold">阈值。区分文稿和黑色背景。取值范围[0, 255],参考值为100</param>
/// <param name="offset">文稿底色增亮偏移量默认为0。值越大背景越白反之越暗</param> /// <param name="offset">文稿底色增亮偏移量默认为0。值越大背景越白反之越暗</param>
/// <param name="range">背景色彩的浮动范围。要求大于等于1。值越大范围越大更多的色彩被判定为底色并除色。参考值40</param> /// <param name="range">背景色彩的浮动范围。要求大于等于1。值越大范围越大更多的色彩被判定为底色并除色。参考值40</param>
void fadeBackground(unsigned char* data, int width, int height, int bytesPerLine, int threshold, int offset, int range); void fadeBackground(cv::Mat& image, int threshold, int offset, int range);
private: private:
int m_threshold; int m_threshold;
int m_offset; int m_offset;
int m_range; int m_range;
uchar m_table1[768];
uchar m_table2[768];
uchar m_table_rgb[3][256];
}; };
#endif // !IMAGE_APPLY_FADE_BACKGROUND_COLOR_H #endif // !IMAGE_APPLY_FADE_BACKGROUND_COLOR_H

View File

@ -739,7 +739,7 @@ namespace hg_imgproc
mats_.clear(); mats_.clear();
CImageApplyFadeBackGroudColor fade(20, 100, img_conf_.fadebackrange); CImageApplyFadeBackGroudColor fade(20, 255, img_conf_.fadebackrange);
for(size_t i = 0; i < mats.size();i++) for(size_t i = 0; i < mats.size();i++)
{ {
fade.apply(mats[i],img_conf_.is_duplex); fade.apply(mats[i],img_conf_.is_duplex);