wordrec/pieces.cpp

Go to the documentation of this file.
00001 
00020 /*----------------------------------------------------------------------
00021           I n c l u d e s
00022 ----------------------------------------------------------------------*/
00023 #include "pieces.h"
00024 #include "plotseg.h"
00025 #include "hideedge.h"
00026 #include "wordclass.h"
00027 #include "freelist.h"
00028 #include "blobs.h"
00029 #include "matchtab.h"
00030 
00031 /*----------------------------------------------------------------------
00032           M a c r o s
00033 ----------------------------------------------------------------------*/
00034 /* ================== */
00038 #define set_bounds_entry(array,index,top_left,bot_right)  \
00039 ((array)[index].topleft  = (top_left),                  \
00040 (array)[index].botright = (bot_right))                 \
00041 
00042 
00043 /* ================== */
00047 #define get_bounds_entry(array,index,top_left,bot_right)  \
00048 ((top_left)  = (array)[index].topleft,                  \
00049 (bot_right) = (array)[index].botright)                 \
00050 
00051 
00052 /*----------------------------------------------------------------------
00053           F u n c t i o n s
00054 ----------------------------------------------------------------------*/
00055 /* ================== */
00061 void break_pieces(TBLOB *blobs, SEAMS seams, INT16 start, INT16 end) { 
00062   TESSLINE *outline = blobs->outlines;
00063   TBLOB *next_blob;
00064   INT16 x;
00065 
00066   for (x = start; x < end; x++)
00067     reveal_seam ((SEAM *) array_value (seams, x));
00068 
00069   next_blob = blobs->next;
00070 
00071   while (outline && next_blob) {
00072     if (outline->next == next_blob->outlines) {
00073       outline->next = NULL;
00074       outline = next_blob->outlines;
00075       next_blob = next_blob->next;
00076     }
00077     else {
00078       outline = outline->next;
00079     }
00080   }
00081 }
00082 
00083 
00084 /* ================== */
00089 void join_pieces(TBLOB *piece_blobs, SEAMS seams, INT16 start, INT16 end) { 
00090   TBLOB *next_blob;
00091   TBLOB *blob;
00092   INT16 x;
00093   TESSLINE *outline;
00094   SEAM *seam;
00095 
00096   for (x = 0, blob = piece_blobs; x < start; x++)
00097     blob = blob->next;
00098   next_blob = blob->next;
00099   outline = blob->outlines;
00100   if (!outline)
00101     return;
00102 
00103   while (x < end) {
00104     seam = (SEAM *) array_value (seams, x);
00105     if (x - seam->widthn >= start && x + seam->widthp < end)
00106       hide_seam(seam); 
00107     while (outline->next)
00108       outline = outline->next;
00109     outline->next = next_blob->outlines;
00110     next_blob = next_blob->next;
00111 
00112     x++;
00113   }
00114 }
00115 
00116 
00117 /* ================== */
00122 void hide_seam(SEAM *seam) { 
00123   if (seam == NULL || seam->split1 == NULL)
00124     return;
00125   hide_edge_pair (seam->split1->point1, seam->split1->point2);
00126 
00127   if (seam->split2 == NULL)
00128     return;
00129   hide_edge_pair (seam->split2->point1, seam->split2->point2);
00130 
00131   if (seam->split3 == NULL)
00132     return;
00133   hide_edge_pair (seam->split3->point1, seam->split3->point2);
00134 }
00135 
00136 
00137 /* ================== */
00142 void hide_edge_pair(EDGEPT *pt1, EDGEPT *pt2) { 
00143   EDGEPT *edgept;
00144 
00145   edgept = pt1;
00146   do {
00147     hide_edge(edgept); 
00148     edgept = edgept->next;
00149   }
00150   while (!exact_point (edgept, pt2) && edgept != pt1);
00151   if (edgept == pt1) {
00152     /*              cprintf("Hid entire outline at (%d,%d)!!\n",
00153        edgept->pos.x,edgept->pos.y);                                */
00154   }
00155   edgept = pt2;
00156   do {
00157     hide_edge(edgept); 
00158     edgept = edgept->next;
00159   }
00160   while (!exact_point (edgept, pt1) && edgept != pt2);
00161   if (edgept == pt2) {
00162     /*              cprintf("Hid entire outline at (%d,%d)!!\n",
00163        edgept->pos.x,edgept->pos.y);                                */
00164   }
00165 }
00166 
00167 
00168 /* ================== */
00173 void reveal_seam(SEAM *seam) { 
00174   if (seam == NULL || seam->split1 == NULL)
00175     return;
00176   reveal_edge_pair (seam->split1->point1, seam->split1->point2);
00177 
00178   if (seam->split2 == NULL)
00179     return;
00180   reveal_edge_pair (seam->split2->point1, seam->split2->point2);
00181 
00182   if (seam->split3 == NULL)
00183     return;
00184   reveal_edge_pair (seam->split3->point1, seam->split3->point2);
00185 }
00186 
00187 
00188 /* ================== */
00193 void reveal_edge_pair(EDGEPT *pt1, EDGEPT *pt2) { 
00194   EDGEPT *edgept;
00195 
00196   edgept = pt1;
00197   do {
00198     reveal_edge(edgept); 
00199     edgept = edgept->next;
00200   }
00201   while (!exact_point (edgept, pt2) && edgept != pt1);
00202   if (edgept == pt1) {
00203     /*              cprintf("Hid entire outline at (%d,%d)!!\n",
00204        edgept->pos.x,edgept->pos.y);                                */
00205   }
00206   edgept = pt2;
00207   do {
00208     reveal_edge(edgept); 
00209     edgept = edgept->next;
00210   }
00211   while (!exact_point (edgept, pt1) && edgept != pt2);
00212   if (edgept == pt2) {
00213     /*              cprintf("Hid entire outline at (%d,%d)!!\n",
00214        edgept->pos.x,edgept->pos.y);                                */
00215   }
00216 }
00217 
00218 
00219 /* ================== */
00224 void bounds_of_piece(BOUNDS_LIST bounds,
00225                      INT16 start,
00226                      INT16 end,
00227                      TPOINT *extreme_tl,
00228                      TPOINT *extreme_br) {
00229   TPOINT topleft;
00230   TPOINT botright;
00231   INT16 x;
00232 
00233   get_bounds_entry(bounds, start, *extreme_tl, *extreme_br); 
00234 
00235   for (x = start + 1; x <= end; x++) {
00236     get_bounds_entry(bounds, x, topleft, botright); 
00237 
00238     extreme_tl->x = min (topleft.x, extreme_tl->x);
00239     extreme_tl->y = max (topleft.y, extreme_tl->y);
00240     extreme_br->x = max (botright.x, extreme_br->x);
00241     extreme_br->y = min (botright.y, extreme_br->y);
00242   }
00243 }
00244 
00245 
00246 /* ================== */
00253 CHOICES classify_piece(TBLOB *pieces,
00254                        SEAMS seams,
00255                        INT16 start,
00256                        INT16 end,
00257                        INT32 fx,
00258                        STATE *this_state,
00259                        STATE *best_state,
00260                        INT32 pass,
00261                        INT32 blob_index) {
00262   STATE current_state;
00263   CHOICES choices;
00264   TBLOB *pblob;
00265   TBLOB *blob;
00266   TBLOB *nblob;
00267   INT16 x;
00268   SEARCH_STATE chunk_groups;
00269 
00270   set_n_ones (&current_state, array_count (seams));
00271 
00272   join_pieces(pieces, seams, start, end); 
00273   for (blob = pieces, pblob = NULL, x = 0; x < start; x++) {
00274     pblob = blob;
00275     blob = blob->next;
00276   }
00277   for (nblob = blob->next; x < end; x++)
00278     nblob = nblob->next;
00279   choices = classify_blob (pblob, blob, nblob, NULL, fx, "pieces:", White,
00280     this_state, best_state, pass, blob_index);
00281 
00282   break_pieces(blob, seams, start, end); 
00283 #ifndef GRAPHICS_DISABLED
00284   if (display_segmentations > 2) {
00285     chunk_groups = bin_to_chunks (&current_state, array_count (seams));
00286     display_segmentation(pieces, chunk_groups); 
00287     window_wait(segm_window); 
00288     memfree(chunk_groups); 
00289   }
00290 #endif
00291 
00292   return (choices);
00293 }
00294 
00295 
00296 /* ================== */
00304 CHOICES get_piece_rating(MATRIX ratings,
00305                          TBLOB *blobs,
00306                          SEAMS seams,
00307                          INT16 start,
00308                          INT16 end,
00309                          INT32 fx,
00310                          STATE *this_state,
00311                          STATE *best_state,
00312                          INT32 pass,
00313                          INT32 blob_index) {
00314   CHOICES choices;
00315 
00316   choices = matrix_get (ratings, start, end);
00317   if (choices == NOT_CLASSIFIED) {
00318     choices =
00319       classify_piece(blobs,
00320                      seams,
00321                      start,
00322                      end,
00323                      fx,
00324                      this_state,
00325                      best_state,
00326                      pass,
00327                      blob_index);
00328     matrix_put(ratings, start, end, choices); 
00329   }
00330   return (choices);
00331 }
00332 
00333 
00334 /* ================== */
00339 BOUNDS_LIST record_blob_bounds(TBLOB *blobs) { 
00340   TBLOB *blob;
00341   BOUNDS_LIST bounds;
00342   TPOINT topleft;
00343   TPOINT botright;
00344   INT16 x = 0;
00345 
00346   bounds = (BOUNDS_LIST) memalloc (count_blobs (blobs) * sizeof (BOUNDS));
00347 
00348   iterate_blobs(blob, blobs) { 
00349     blob_bounding_box(blob, &topleft, &botright); 
00350     set_bounds_entry(bounds, x, topleft, botright); 
00351     x++;
00352   }
00353   return (bounds);
00354 }
00355 
00356 
00357 /* ================== */
00365 MATRIX record_piece_ratings(TBLOB *blobs) { 
00366   BOUNDS_LIST bounds;
00367   INT16 num_blobs;
00368   INT16 x;
00369   INT16 y;
00370   TPOINT tp_topleft;
00371   TPOINT tp_botright;
00372   unsigned int topleft;
00373   unsigned int botright;
00374   MATRIX ratings;
00375   CHOICES choices;
00376 
00377   bounds = record_blob_bounds (blobs);
00378   num_blobs = count_blobs (blobs);
00379   ratings = create_matrix (num_blobs);
00380 
00381   for (x = 0; x < num_blobs; x++) {
00382     for (y = x; y < num_blobs; y++) {
00383       bounds_of_piece(bounds, x, y, &tp_topleft, &tp_botright); 
00384       topleft = *(unsigned int *) &tp_topleft;
00385       botright = *(unsigned int *) &tp_botright;
00386       choices = get_match_by_bounds (topleft, botright);
00387       if (choices != NIL) {
00388         matrix_put(ratings, x, y, choices); 
00389       }
00390     }
00391   }
00392   memfree(bounds); 
00393   return (ratings);
00394 }

Generated on Wed Feb 28 19:49:13 2007 for Tesseract by  doxygen 1.5.1