21 #include "config_auto.h"    66                                       gridsize * gridsize)),
    67     noise_density_(nullptr) {
    74   delete noise_density_;
    95   BLOBNBOX_IT blob_it(&blob_block->
blobs);
    96   for (blob_it.mark_cycle_pt(); !blob_it.cycled_list(); blob_it.forward()) {
    99     perimeter_area_ratio *= perimeter_area_ratio / blob->
enclosed_area();
   105   noise_density_ = ComputeNoiseDensity(debug, photo_map, &good_grid);
   109     pixWrite(
"junknoisemask.png", pix, IFF_PNG);
   112   #ifndef GRAPHICS_DISABLED   116   #endif  // GRAPHICS_DISABLED   119   MarkAndDeleteNonTextBlobs(&blob_block->
large_blobs,
   127   MarkAndDeleteNonTextBlobs(&blob_block->
large_blobs,
   132   MarkAndDeleteNonTextBlobs(&blob_block->
noise_blobs, -1,
   134   MarkAndDeleteNonTextBlobs(&blob_block->
small_blobs, -1,
   136   MarkAndDeleteNonTextBlobs(&blob_block->
blobs, -1,
   139     #ifndef GRAPHICS_DISABLED   141     #endif  // GRAPHICS_DISABLED   142     pixWrite(
"junkccphotomask.png", pix, IFF_PNG);
   143     #ifndef GRAPHICS_DISABLED   146     #endif  // GRAPHICS_DISABLED   158 IntGrid* CCNonTextDetect::ComputeNoiseDensity(
bool debug, Pix* photo_map,
   167   int height = pixGetHeight(photo_map);
   172       if (max_noise_count_ < noise + photo_offset &&
   173           noise <= max_noise_count_) {
   177         int bottom = height - y * 
gridsize();
   181           noise_density->
SetGridCell(x, y, noise + photo_offset);
   184       if (debug && noise > max_noise_count_ &&
   186         tprintf(
"At %d, %d, noise = %d, good=%d, orig=%d, thr=%d\n",
   192       if (noise > max_noise_count_ &&
   202   return noise_density;
   208 static TBOX AttemptBoxExpansion(
const TBOX& box, 
const IntGrid& noise_density,
   210   TBOX expanded_box(box);
   211   expanded_box.set_right(box.
right() + pad);
   212   if (!noise_density.AnyZeroInRect(expanded_box))
   216   if (!noise_density.AnyZeroInRect(expanded_box))
   220   if (!noise_density.AnyZeroInRect(expanded_box))
   224   if (!noise_density.AnyZeroInRect(expanded_box))
   228   if (!noise_density.AnyZeroInRect(expanded_box))
   247 void CCNonTextDetect::MarkAndDeleteNonTextBlobs(BLOBNBOX_LIST* blobs,
   248                                                 int max_blob_overlaps,
   253   BLOBNBOX_IT blob_it(blobs);
   254   BLOBNBOX_LIST dead_blobs;
   255   BLOBNBOX_IT dead_it(&dead_blobs);
   256   for (blob_it.mark_cycle_pt(); !blob_it.cycled_list(); blob_it.forward()) {
   260         (max_blob_overlaps < 0 ||
   261             !BlobOverlapsTooMuch(blob, max_blob_overlaps))) {
   263       #ifndef GRAPHICS_DISABLED   265         blob->
plot(win, ok_color, ok_color);
   266       #endif  // GRAPHICS_DISABLED   272         pixRasterop(nontext_mask, box.
left(), imageheight - box.
top(),
   275         pixDestroy(&blob_pix);
   281           box = AttemptBoxExpansion(box, *noise_density_, 
gridsize());
   284         pixRasterop(nontext_mask, box.
left(), imageheight - box.
top(),
   285                     box.
width(), box.
height(), PIX_SET, 
nullptr, 0, 0);
   287       #ifndef GRAPHICS_DISABLED   290       #endif  // GRAPHICS_DISABLED   296       delete blob->
cblob();
   297       dead_it.add_to_end(blob_it.extract());
   304 bool CCNonTextDetect::BlobOverlapsTooMuch(
BLOBNBOX* blob, 
int max_overlaps) {
   309   rsearch.StartRectSearch(box);
   310   rsearch.SetUniqueMode(
true);
   312   int overlap_count = 0;
   313   while (overlap_count <= max_overlaps &&
   314          (neighbour = rsearch.NextRectSearch()) != 
nullptr) {
   317       if (overlap_count > max_overlaps)
 const int kMaxLargeOverlapsWithMedium
 
void InsertBlobList(BLOBNBOX_LIST *blobs)
 
ScrollView * MakeWindow(int x, int y, const char *window_name)
 
const ICOORD & bleft() const
 
CCNonTextDetect(int gridsize, const ICOORD &bleft, const ICOORD &tright)
 
int16_t y() const
access_function 
 
const int kMaxMediumOverlapsWithSmall
 
int32_t enclosed_area() const
 
void plot(ScrollView *window, ScrollView::Color blob_colour, ScrollView::Color child_colour)
 
const double kMinGoodTextPARatio
 
int GridCellValue(int grid_x, int grid_y) const
 
SVEvent * AwaitEvent(SVEventType type)
 
bool AnyZeroInRect(const TBOX &rect) const
 
const int kMaxLargeOverlapsWithSmall
 
int16_t x() const
access function 
 
const int kOriginalNoiseMultiple
 
bool RectMostlyOverThreshold(const TBOX &rect, int threshold) const
 
bool major_overlap(const TBOX &box) const
 
int IntCastRounded(double x)
 
void InsertBBox(bool h_spread, bool v_spread, BLOBNBOX *bbox)
 
GridSearch< BLOBNBOX, BLOBNBOX_CLIST, BLOBNBOX_C_IT > BlobGridSearch
 
DLLSYM void tprintf(const char *format,...)
 
void SetGridCell(int grid_x, int grid_y, int value)
 
const double kPhotoOffsetFraction
 
IntGrid * CountCellElements()
 
IntGrid * NeighbourhoodSum() const
 
virtual ~CCNonTextDetect()
 
const TBOX & bounding_box() const
 
static bool BoundsWithinRect(Pix *pix, int *x_start, int *y_start, int *x_end, int *y_end)
 
BLOBNBOX_LIST large_blobs
 
Pix * ComputeNonTextMask(bool debug, Pix *photo_map, TO_BLOCK *blob_block)
 
void pad(int xpad, int ypad)
 
const double kMaxSmallNeighboursPerPix
 
Pix * ThresholdToPix(int threshold) const
 
const ICOORD & tright() const
 
BLOBNBOX_LIST small_blobs
 
BLOBNBOX_LIST noise_blobs