Tesseract  3.02
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
tesseract::TextlineProjection Class Reference

#include <textlineprojection.h>

Public Member Functions

 TextlineProjection (int resolution)
 
 ~TextlineProjection ()
 
void ConstructProjection (TO_BLOCK *input_block, const FCOORD &rotation, Pix *nontext_map)
 
void PlotGradedBlobs (BLOBNBOX_LIST *blobs, ScrollView *win)
 
void MoveNonTextlineBlobs (BLOBNBOX_LIST *blobs, BLOBNBOX_LIST *small_blobs) const
 
void DisplayProjection () const
 
int DistanceOfBoxFromPartition (const TBOX &box, const ColPartition &part, const DENORM *denorm, bool debug) const
 
int DistanceOfBoxFromBox (const TBOX &from_box, const TBOX &to_box, bool horizontal_textline, const DENORM *denorm, bool debug) const
 
int VerticalDistance (bool debug, int x, int y1, int y2) const
 
int HorizontalDistance (bool debug, int x1, int x2, int y) const
 
bool BoxOutOfHTextline (const TBOX &box, const DENORM *denorm, bool debug) const
 
int EvaluateColPartition (const ColPartition &part, const DENORM *denorm, bool debug) const
 
int EvaluateBox (const TBOX &box, const DENORM *denorm, bool debug) const
 

Detailed Description

Definition at line 33 of file textlineprojection.h.

Constructor & Destructor Documentation

tesseract::TextlineProjection::TextlineProjection ( int  resolution)
explicit

Definition at line 41 of file textlineprojection.cpp.

42  : x_origin_(0), y_origin_(0), pix_(NULL) {
43  // The projection map should be about 100 ppi, whatever the input.
44  scale_factor_ = IntCastRounded(resolution / 100.0);
45  if (scale_factor_ < 1) scale_factor_ = 1;
46 }
int IntCastRounded(double x)
Definition: helpers.h:121
#define NULL
Definition: host.h:144
tesseract::TextlineProjection::~TextlineProjection ( )

Definition at line 47 of file textlineprojection.cpp.

47  {
48  pixDestroy(&pix_);
49 }

Member Function Documentation

bool tesseract::TextlineProjection::BoxOutOfHTextline ( const TBOX box,
const DENORM denorm,
bool  debug 
) const

Definition at line 338 of file textlineprojection.cpp.

340  {
341  int grad1 = 0;
342  int grad2 = 0;
343  EvaluateBoxInternal(box, denorm, debug, &grad1, &grad2, NULL, NULL);
344  int worst_result = MIN(grad1, grad2);
345  int total_result = grad1 + grad2;
346  if (total_result >= 6) return false; // Strongly in textline.
347  // Medium strength: if either gradient is negative, it is likely outside
348  // the body of the textline.
349  if (worst_result < 0)
350  return true;
351  return false;
352 }
#define NULL
Definition: host.h:144
#define MIN(x, y)
Definition: ndminx.h:28
void tesseract::TextlineProjection::ConstructProjection ( TO_BLOCK input_block,
const FCOORD rotation,
Pix *  nontext_map 
)

Definition at line 58 of file textlineprojection.cpp.

60  {
61  pixDestroy(&pix_);
62  TBOX image_box(0, 0, pixGetWidth(nontext_map), pixGetHeight(nontext_map));
63  x_origin_ = 0;
64  y_origin_ = image_box.height();
65  int width = (image_box.width() + scale_factor_ - 1) / scale_factor_;
66  int height = (image_box.height() + scale_factor_ - 1) / scale_factor_;
67 
68  pix_ = pixCreate(width, height, 8);
69  ProjectBlobs(&input_block->blobs, rotation, image_box, nontext_map);
70  ProjectBlobs(&input_block->large_blobs, rotation, image_box, nontext_map);
71  Pix* final_pix = pixBlockconv(pix_, 1, 1);
72 // Pix* final_pix = pixBlockconv(pix_, 2, 2);
73  pixDestroy(&pix_);
74  pix_ = final_pix;
75 }
BLOBNBOX_LIST blobs
Definition: blobbox.h:735
Definition: rect.h:29
BLOBNBOX_LIST large_blobs
Definition: blobbox.h:739
void tesseract::TextlineProjection::DisplayProjection ( ) const

Definition at line 117 of file textlineprojection.cpp.

117  {
118  int width = pixGetWidth(pix_);
119  int height = pixGetHeight(pix_);
120  Pix* pixc = pixCreate(width, height, 32);
121  int src_wpl = pixGetWpl(pix_);
122  int col_wpl = pixGetWpl(pixc);
123  uinT32* src_data = pixGetData(pix_);
124  uinT32* col_data = pixGetData(pixc);
125  for (int y = 0; y < height; ++y, src_data += src_wpl, col_data += col_wpl) {
126  for (int x = 0; x < width; ++x) {
127  int pixel = GET_DATA_BYTE(src_data, x);
128  l_uint32 result;
129  if (pixel <= 17)
130  composeRGBPixel(0, 0, pixel * 15, &result);
131  else if (pixel <= 145)
132  composeRGBPixel(0, (pixel - 17) * 2, 255, &result);
133  else
134  composeRGBPixel((pixel - 145) * 2, 255, 255, &result);
135  col_data[x] = result;
136  }
137  }
138 #if 0
139  // TODO(rays) uncomment when scrollview can display non-binary images.
140  ScrollView* win = new ScrollView("Projection", 0, 0,
141  width, height, width, height);
142  win->Image(pixc, 0, 0);
143  win->Update();
144 #else
145  pixWrite("projection.png", pixc, IFF_PNG);
146 #endif
147  pixDestroy(&pixc);
148 }
static void Update()
Definition: scrollview.cpp:710
void Image(struct Pix *image, int x_pos, int y_pos)
Definition: scrollview.cpp:768
unsigned int uinT32
Definition: host.h:103
int tesseract::TextlineProjection::DistanceOfBoxFromBox ( const TBOX from_box,
const TBOX to_box,
bool  horizontal_textline,
const DENORM denorm,
bool  debug 
) const

Definition at line 194 of file textlineprojection.cpp.

198  {
199  // The parallel_gap is the horizontal gap between a horizontal textline and
200  // the box. Analogous for vertical.
201  int parallel_gap = 0;
202  // start_pt is the box end of the line to be modified for curved space.
203  TPOINT start_pt;
204  // end_pt is the partition end of the line to be modified for curved space.
205  TPOINT end_pt;
206  if (horizontal_textline) {
207  parallel_gap = from_box.x_gap(to_box) + from_box.width();
208  start_pt.x = (from_box.left() + from_box.right()) / 2;
209  end_pt.x = start_pt.x;
210  if (from_box.top() - to_box.top() >= to_box.bottom() - from_box.bottom()) {
211  start_pt.y = from_box.top();
212  end_pt.y = MIN(to_box.top(), start_pt.y);
213  } else {
214  start_pt.y = from_box.bottom();
215  end_pt.y = MAX(to_box.bottom(), start_pt.y);
216  }
217  } else {
218  parallel_gap = from_box.y_gap(to_box) + from_box.height();
219  if (from_box.right() - to_box.right() >= to_box.left() - from_box.left()) {
220  start_pt.x = from_box.right();
221  end_pt.x = MIN(to_box.right(), start_pt.x);
222  } else {
223  start_pt.x = from_box.left();
224  end_pt.x = MAX(to_box.left(), start_pt.x);
225  }
226  start_pt.y = (from_box.bottom() + from_box.top()) / 2;
227  end_pt.y = start_pt.y;
228  }
229  // The perpendicular gap is the max vertical distance gap out of:
230  // top of from_box to to_box top and bottom of from_box to to_box bottom.
231  // This value is then modified for curved projection space.
232  // Analogous for vertical.
233  int perpendicular_gap = 0;
234  // If start_pt == end_pt, then the from_box lies entirely within the to_box
235  // (in the perpendicular direction), so we don't need to calculate the
236  // perpendicular_gap.
237  if (start_pt.x != end_pt.x || start_pt.y != end_pt.y) {
238  if (denorm != NULL) {
239  // Denormalize the start and end.
240  denorm->DenormTransform(start_pt, &start_pt);
241  denorm->DenormTransform(end_pt, &end_pt);
242  }
243  if (abs(start_pt.y - end_pt.y) >= abs(start_pt.x - end_pt.x)) {
244  perpendicular_gap = VerticalDistance(debug, start_pt.x, start_pt.y,
245  end_pt.y);
246  } else {
247  perpendicular_gap = HorizontalDistance(debug, start_pt.x, end_pt.x,
248  start_pt.y);
249  }
250  }
251  // The parallel_gap weighs less than the perpendicular_gap.
252  return perpendicular_gap + parallel_gap / kParaPerpDistRatio;
253 }
int HorizontalDistance(bool debug, int x1, int x2, int y) const
#define NULL
Definition: host.h:144
inT16 left() const
Definition: rect.h:67
inT16 width() const
Definition: rect.h:104
const int kParaPerpDistRatio
void DenormTransform(const TPOINT &pt, TPOINT *original) const
Definition: normalis.cpp:233
inT16 right() const
Definition: rect.h:74
inT16 y
Definition: blobs.h:68
int VerticalDistance(bool debug, int x, int y1, int y2) const
inT16 x
Definition: blobs.h:67
Definition: blobs.h:53
int y_gap(const TBOX &box) const
Definition: rect.h:218
inT16 top() const
Definition: rect.h:53
int x_gap(const TBOX &box) const
Definition: rect.h:210
#define MIN(x, y)
Definition: ndminx.h:28
#define MAX(x, y)
Definition: ndminx.h:24
inT16 height() const
Definition: rect.h:97
inT16 bottom() const
Definition: rect.h:60
int tesseract::TextlineProjection::DistanceOfBoxFromPartition ( const TBOX box,
const ColPartition part,
const DENORM denorm,
bool  debug 
) const

Definition at line 154 of file textlineprojection.cpp.

157  {
158  // Compute a partition box that uses the median top/bottom of the blobs
159  // within and median left/right for vertical.
160  TBOX part_box = part.bounding_box();
161  if (part.IsHorizontalType()) {
162  part_box.set_top(part.median_top());
163  part_box.set_bottom(part.median_bottom());
164  } else {
165  part_box.set_left(part.median_left());
166  part_box.set_right(part.median_right());
167  }
168  // Now use DistanceOfBoxFromBox to make the actual calculation.
169  return DistanceOfBoxFromBox(box, part_box, part.IsHorizontalType(),
170  denorm, debug);
171 }
void set_right(int x)
Definition: rect.h:77
int DistanceOfBoxFromBox(const TBOX &from_box, const TBOX &to_box, bool horizontal_textline, const DENORM *denorm, bool debug) const
Definition: rect.h:29
void set_bottom(int y)
Definition: rect.h:63
void set_top(int y)
Definition: rect.h:56
void set_left(int x)
Definition: rect.h:70
int tesseract::TextlineProjection::EvaluateBox ( const TBOX box,
const DENORM denorm,
bool  debug 
) const

Definition at line 410 of file textlineprojection.cpp.

411  {
412  return EvaluateBoxInternal(box, denorm, debug, NULL, NULL, NULL, NULL);
413 }
#define NULL
Definition: host.h:144
int tesseract::TextlineProjection::EvaluateColPartition ( const ColPartition part,
const DENORM denorm,
bool  debug 
) const

Definition at line 359 of file textlineprojection.cpp.

361  {
362  if (part.IsSingleton())
363  return EvaluateBox(part.bounding_box(), denorm, debug);
364  // Test vertical orientation.
365  TBOX box = part.bounding_box();
366  // Use the partition median for left/right.
367  box.set_left(part.median_left());
368  box.set_right(part.median_right());
369  int vresult = EvaluateBox(box, denorm, debug);
370 
371  // Test horizontal orientation.
372  box = part.bounding_box();
373  // Use the partition median for top/bottom.
374  box.set_top(part.median_top());
375  box.set_bottom(part.median_bottom());
376  int hresult = EvaluateBox(box, denorm, debug);
377  if (debug) {
378  tprintf("Partition hresult=%d, vresult=%d from:", hresult, vresult);
379  part.bounding_box().print();
380  part.Print();
381  }
382  return hresult >= -vresult ? hresult : vresult;
383 }
void set_right(int x)
Definition: rect.h:77
Definition: rect.h:29
DLLSYM void tprintf(const char *format,...)
Definition: tprintf.cpp:41
int EvaluateBox(const TBOX &box, const DENORM *denorm, bool debug) const
void set_bottom(int y)
Definition: rect.h:63
void set_top(int y)
Definition: rect.h:56
void set_left(int x)
Definition: rect.h:70
int tesseract::TextlineProjection::HorizontalDistance ( bool  debug,
int  x1,
int  x2,
int  y 
) const

Definition at line 306 of file textlineprojection.cpp.

307  {
308  x1 = ImageXToProjectionX(x1);
309  x2 = ImageXToProjectionX(x2);
310  y = ImageYToProjectionY(y);
311  if (x1 == x2) return 0;
312  int wpl = pixGetWpl(pix_);
313  int step = x1 < x2 ? 1 : -1;
314  uinT32* data = pixGetData(pix_) + y * wpl;
315  int prev_pixel = GET_DATA_BYTE(data, x1);
316  int distance = 0;
317  int right_way_steps = 0;
318  for (int x = x1; x != x2; x += step) {
319  int pixel = GET_DATA_BYTE(data, x + step);
320  if (debug)
321  tprintf("At (%d,%d), pix = %d, prev=%d\n",
322  x + step, y, pixel, prev_pixel);
323  if (pixel < prev_pixel)
324  distance += kWrongWayPenalty;
325  else if (pixel > prev_pixel)
326  ++right_way_steps;
327  else
328  ++distance;
329  prev_pixel = pixel;
330  }
331  return distance * scale_factor_ +
332  right_way_steps * scale_factor_ / kWrongWayPenalty;
333 }
const int kWrongWayPenalty
DLLSYM void tprintf(const char *format,...)
Definition: tprintf.cpp:41
unsigned int uinT32
Definition: host.h:103
void tesseract::TextlineProjection::MoveNonTextlineBlobs ( BLOBNBOX_LIST *  blobs,
BLOBNBOX_LIST *  small_blobs 
) const

Definition at line 100 of file textlineprojection.cpp.

101  {
102  BLOBNBOX_IT it(blobs);
103  BLOBNBOX_IT small_it(small_blobs);
104  for (it.mark_cycle_pt(); !it.cycled_list(); it.forward()) {
105  BLOBNBOX* blob = it.data();
106  const TBOX& box = blob->bounding_box();
107  bool debug = AlignedBlob::WithinTestRegion(2, box.left(),
108  box.bottom());
109  if (BoxOutOfHTextline(box, NULL, debug) && !blob->UniquelyVertical()) {
110  blob->ClearNeighbours();
111  small_it.add_to_end(it.extract());
112  }
113  }
114 }
const TBOX & bounding_box() const
Definition: blobbox.h:208
#define NULL
Definition: host.h:144
inT16 left() const
Definition: rect.h:67
Definition: rect.h:29
bool BoxOutOfHTextline(const TBOX &box, const DENORM *denorm, bool debug) const
void ClearNeighbours()
Definition: blobbox.h:476
static bool WithinTestRegion(int detail_level, int x, int y)
bool UniquelyVertical() const
Definition: blobbox.h:383
inT16 bottom() const
Definition: rect.h:60
void tesseract::TextlineProjection::PlotGradedBlobs ( BLOBNBOX_LIST *  blobs,
ScrollView win 
)

Definition at line 78 of file textlineprojection.cpp.

79  {
80  #ifndef GRAPHICS_DISABLED
81  BLOBNBOX_IT it(blobs);
82  for (it.mark_cycle_pt(); !it.cycled_list(); it.forward()) {
83  BLOBNBOX* blob = it.data();
84  const TBOX& box = blob->bounding_box();
85  bool bad_box = BoxOutOfHTextline(box, NULL, false);
86  if (blob->UniquelyVertical())
87  win->Pen(ScrollView::YELLOW);
88  else
89  win->Pen(bad_box ? ScrollView::RED : ScrollView::BLUE);
90  win->Rectangle(box.left(), box.bottom(), box.right(), box.top());
91  }
92  win->Update();
93  #endif // GRAPHICS_DISABLED
94 }
void Pen(Color color)
Definition: scrollview.cpp:721
const TBOX & bounding_box() const
Definition: blobbox.h:208
#define NULL
Definition: host.h:144
inT16 left() const
Definition: rect.h:67
Definition: rect.h:29
inT16 right() const
Definition: rect.h:74
bool BoxOutOfHTextline(const TBOX &box, const DENORM *denorm, bool debug) const
static void Update()
Definition: scrollview.cpp:710
void Rectangle(int x1, int y1, int x2, int y2)
Definition: scrollview.cpp:601
inT16 top() const
Definition: rect.h:53
bool UniquelyVertical() const
Definition: blobbox.h:383
inT16 bottom() const
Definition: rect.h:60
int tesseract::TextlineProjection::VerticalDistance ( bool  debug,
int  x,
int  y1,
int  y2 
) const

Definition at line 273 of file textlineprojection.cpp.

274  {
275  x = ImageXToProjectionX(x);
276  y1 = ImageYToProjectionY(y1);
277  y2 = ImageYToProjectionY(y2);
278  if (y1 == y2) return 0;
279  int wpl = pixGetWpl(pix_);
280  int step = y1 < y2 ? 1 : -1;
281  uinT32* data = pixGetData(pix_) + y1 * wpl;
282  wpl *= step;
283  int prev_pixel = GET_DATA_BYTE(data, x);
284  int distance = 0;
285  int right_way_steps = 0;
286  for (int y = y1; y != y2; y += step) {
287  data += wpl;
288  int pixel = GET_DATA_BYTE(data, x);
289  if (debug)
290  tprintf("At (%d,%d), pix = %d, prev=%d\n",
291  x, y + step, pixel, prev_pixel);
292  if (pixel < prev_pixel)
293  distance += kWrongWayPenalty;
294  else if (pixel > prev_pixel)
295  ++right_way_steps;
296  else
297  ++distance;
298  prev_pixel = pixel;
299  }
300  return distance * scale_factor_ +
301  right_way_steps * scale_factor_ / kWrongWayPenalty;
302 }
const int kWrongWayPenalty
DLLSYM void tprintf(const char *format,...)
Definition: tprintf.cpp:41
unsigned int uinT32
Definition: host.h:103

The documentation for this class was generated from the following files: