|
tesseract 3.04.01
|
00001 00002 // File: tesseractclass.cpp 00003 // Description: The Tesseract class. It holds/owns everything needed 00004 // to run Tesseract on a single language, and also a set of 00005 // sub-Tesseracts to run sub-languages. For thread safety, *every* 00006 // variable that was previously global or static (except for 00007 // constant data, and some visual debugging flags) has been moved 00008 // in here, directly, or indirectly. 00009 // This makes it safe to run multiple Tesseracts in different 00010 // threads in parallel, and keeps the different language 00011 // instances separate. 00012 // Some global functions remain, but they are isolated re-entrant 00013 // functions that operate on their arguments. Functions that work 00014 // on variable data have been moved to an appropriate class based 00015 // mostly on the directory hierarchy. For more information see 00016 // slide 6 of "2ArchitectureAndDataStructures" in 00017 // https://drive.google.com/file/d/0B7l10Bj_LprhbUlIUFlCdGtDYkE/edit?usp=sharing 00018 // Some global data and related functions still exist in the 00019 // training-related code, but they don't interfere with normal 00020 // recognition operation. 00021 // Author: Ray Smith 00022 // Created: Fri Mar 07 08:17:01 PST 2008 00023 // 00024 // (C) Copyright 2008, Google Inc. 00025 // Licensed under the Apache License, Version 2.0 (the "License"); 00026 // you may not use this file except in compliance with the License. 00027 // You may obtain a copy of the License at 00028 // http://www.apache.org/licenses/LICENSE-2.0 00029 // Unless required by applicable law or agreed to in writing, software 00030 // distributed under the License is distributed on an "AS IS" BASIS, 00031 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00032 // See the License for the specific language governing permissions and 00033 // limitations under the License. 00034 // 00036 00037 // Include automatically generated configuration file if running autoconf. 00038 #ifdef HAVE_CONFIG_H 00039 #include "config_auto.h" 00040 #endif 00041 00042 #include "tesseractclass.h" 00043 00044 #include "allheaders.h" 00045 #ifndef NO_CUBE_BUILD 00046 #include "cube_reco_context.h" 00047 #endif 00048 #include "edgblob.h" 00049 #include "equationdetect.h" 00050 #include "globals.h" 00051 #ifndef NO_CUBE_BUILD 00052 #include "tesseract_cube_combiner.h" 00053 #endif 00054 00055 namespace tesseract { 00056 00057 Tesseract::Tesseract() 00058 : BOOL_MEMBER(tessedit_resegment_from_boxes, false, 00059 "Take segmentation and labeling from box file", 00060 this->params()), 00061 BOOL_MEMBER(tessedit_resegment_from_line_boxes, false, 00062 "Conversion of word/line box file to char box file", 00063 this->params()), 00064 BOOL_MEMBER(tessedit_train_from_boxes, false, 00065 "Generate training data from boxed chars", this->params()), 00066 BOOL_MEMBER(tessedit_make_boxes_from_boxes, false, 00067 "Generate more boxes from boxed chars", this->params()), 00068 BOOL_MEMBER(tessedit_dump_pageseg_images, false, 00069 "Dump intermediate images made during page segmentation", 00070 this->params()), 00071 // The default for pageseg_mode is the old behaviour, so as not to 00072 // upset anything that relies on that. 00073 INT_MEMBER( 00074 tessedit_pageseg_mode, PSM_SINGLE_BLOCK, 00075 "Page seg mode: 0=osd only, 1=auto+osd, 2=auto, 3=col, 4=block," 00076 " 5=line, 6=word, 7=char" 00077 " (Values from PageSegMode enum in publictypes.h)", 00078 this->params()), 00079 INT_INIT_MEMBER(tessedit_ocr_engine_mode, tesseract::OEM_TESSERACT_ONLY, 00080 "Which OCR engine(s) to run (Tesseract, Cube, both)." 00081 " Defaults to loading and running only Tesseract" 00082 " (no Cube,no combiner)." 00083 " Values from OcrEngineMode enum in tesseractclass.h)", 00084 this->params()), 00085 STRING_MEMBER(tessedit_char_blacklist, "", 00086 "Blacklist of chars not to recognize", this->params()), 00087 STRING_MEMBER(tessedit_char_whitelist, "", 00088 "Whitelist of chars to recognize", this->params()), 00089 STRING_MEMBER(tessedit_char_unblacklist, "", 00090 "List of chars to override tessedit_char_blacklist", 00091 this->params()), 00092 BOOL_MEMBER(tessedit_ambigs_training, false, 00093 "Perform training for ambiguities", this->params()), 00094 INT_MEMBER(pageseg_devanagari_split_strategy, 00095 tesseract::ShiroRekhaSplitter::NO_SPLIT, 00096 "Whether to use the top-line splitting process for Devanagari " 00097 "documents while performing page-segmentation.", 00098 this->params()), 00099 INT_MEMBER(ocr_devanagari_split_strategy, 00100 tesseract::ShiroRekhaSplitter::NO_SPLIT, 00101 "Whether to use the top-line splitting process for Devanagari " 00102 "documents while performing ocr.", 00103 this->params()), 00104 STRING_MEMBER(tessedit_write_params_to_file, "", 00105 "Write all parameters to the given file.", this->params()), 00106 BOOL_MEMBER(tessedit_adaption_debug, false, 00107 "Generate and print debug" 00108 " information for adaption", 00109 this->params()), 00110 INT_MEMBER(bidi_debug, 0, "Debug level for BiDi", this->params()), 00111 INT_MEMBER(applybox_debug, 1, "Debug level", this->params()), 00112 INT_MEMBER(applybox_page, 0, "Page number to apply boxes from", 00113 this->params()), 00114 STRING_MEMBER(applybox_exposure_pattern, ".exp", 00115 "Exposure value follows" 00116 " this pattern in the image filename. The name of the image" 00117 " files are expected to be in the form" 00118 " [lang].[fontname].exp[num].tif", 00119 this->params()), 00120 BOOL_MEMBER(applybox_learn_chars_and_char_frags_mode, false, 00121 "Learn both character fragments (as is done in the" 00122 " special low exposure mode) as well as unfragmented" 00123 " characters.", 00124 this->params()), 00125 BOOL_MEMBER(applybox_learn_ngrams_mode, false, 00126 "Each bounding box" 00127 " is assumed to contain ngrams. Only learn the ngrams" 00128 " whose outlines overlap horizontally.", 00129 this->params()), 00130 BOOL_MEMBER(tessedit_display_outwords, false, "Draw output words", 00131 this->params()), 00132 BOOL_MEMBER(tessedit_dump_choices, false, "Dump char choices", 00133 this->params()), 00134 BOOL_MEMBER(tessedit_timing_debug, false, "Print timing stats", 00135 this->params()), 00136 BOOL_MEMBER(tessedit_fix_fuzzy_spaces, true, 00137 "Try to improve fuzzy spaces", this->params()), 00138 BOOL_MEMBER(tessedit_unrej_any_wd, false, 00139 "Don't bother with word plausibility", this->params()), 00140 BOOL_MEMBER(tessedit_fix_hyphens, true, "Crunch double hyphens?", 00141 this->params()), 00142 BOOL_MEMBER(tessedit_redo_xheight, true, "Check/Correct x-height", 00143 this->params()), 00144 BOOL_MEMBER(tessedit_enable_doc_dict, true, 00145 "Add words to the document dictionary", this->params()), 00146 BOOL_MEMBER(tessedit_debug_fonts, false, "Output font info per char", 00147 this->params()), 00148 BOOL_MEMBER(tessedit_debug_block_rejection, false, "Block and Row stats", 00149 this->params()), 00150 BOOL_MEMBER(tessedit_enable_bigram_correction, true, 00151 "Enable correction based on the word bigram dictionary.", 00152 this->params()), 00153 BOOL_MEMBER(tessedit_enable_dict_correction, false, 00154 "Enable single word correction based on the dictionary.", 00155 this->params()), 00156 INT_MEMBER(tessedit_bigram_debug, 0, 00157 "Amount of debug output for bigram correction.", 00158 this->params()), 00159 BOOL_MEMBER(enable_noise_removal, true, 00160 "Remove and conditionally reassign small outlines when they" 00161 " confuse layout analysis, determining diacritics vs noise", 00162 this->params()), 00163 INT_MEMBER(debug_noise_removal, 0, "Debug reassignment of small outlines", 00164 this->params()), 00165 // Worst (min) certainty, for which a diacritic is allowed to make the 00166 // base 00167 // character worse and still be included. 00168 double_MEMBER(noise_cert_basechar, -8.0, 00169 "Hingepoint for base char certainty", this->params()), 00170 // Worst (min) certainty, for which a non-overlapping diacritic is allowed 00171 // to make the base character worse and still be included. 00172 double_MEMBER(noise_cert_disjoint, -1.0, 00173 "Hingepoint for disjoint certainty", this->params()), 00174 // Worst (min) certainty, for which a diacritic is allowed to make a new 00175 // stand-alone blob. 00176 double_MEMBER(noise_cert_punc, -3.0, 00177 "Threshold for new punc char certainty", this->params()), 00178 // Factor of certainty margin for adding diacritics to not count as worse. 00179 double_MEMBER(noise_cert_factor, 0.375, 00180 "Scaling on certainty diff from Hingepoint", 00181 this->params()), 00182 INT_MEMBER(noise_maxperblob, 8, "Max diacritics to apply to a blob", 00183 this->params()), 00184 INT_MEMBER(noise_maxperword, 16, "Max diacritics to apply to a word", 00185 this->params()), 00186 INT_MEMBER(debug_x_ht_level, 0, "Reestimate debug", this->params()), 00187 BOOL_MEMBER(debug_acceptable_wds, false, "Dump word pass/fail chk", 00188 this->params()), 00189 STRING_MEMBER(chs_leading_punct, "('`\"", "Leading punctuation", 00190 this->params()), 00191 STRING_MEMBER(chs_trailing_punct1, ").,;:?!", "1st Trailing punctuation", 00192 this->params()), 00193 STRING_MEMBER(chs_trailing_punct2, ")'`\"", "2nd Trailing punctuation", 00194 this->params()), 00195 double_MEMBER(quality_rej_pc, 0.08, 00196 "good_quality_doc lte rejection limit", this->params()), 00197 double_MEMBER(quality_blob_pc, 0.0, 00198 "good_quality_doc gte good blobs limit", this->params()), 00199 double_MEMBER(quality_outline_pc, 1.0, 00200 "good_quality_doc lte outline error limit", this->params()), 00201 double_MEMBER(quality_char_pc, 0.95, 00202 "good_quality_doc gte good char limit", this->params()), 00203 INT_MEMBER(quality_min_initial_alphas_reqd, 2, "alphas in a good word", 00204 this->params()), 00205 INT_MEMBER(tessedit_tess_adaption_mode, 0x27, 00206 "Adaptation decision algorithm for tess", this->params()), 00207 BOOL_MEMBER(tessedit_minimal_rej_pass1, false, 00208 "Do minimal rejection on pass 1 output", this->params()), 00209 BOOL_MEMBER(tessedit_test_adaption, false, "Test adaption criteria", 00210 this->params()), 00211 BOOL_MEMBER(tessedit_matcher_log, false, "Log matcher activity", 00212 this->params()), 00213 INT_MEMBER(tessedit_test_adaption_mode, 3, 00214 "Adaptation decision algorithm for tess", this->params()), 00215 BOOL_MEMBER(test_pt, false, "Test for point", this->params()), 00216 double_MEMBER(test_pt_x, 99999.99, "xcoord", this->params()), 00217 double_MEMBER(test_pt_y, 99999.99, "ycoord", this->params()), 00218 INT_MEMBER(paragraph_debug_level, 0, "Print paragraph debug info.", 00219 this->params()), 00220 BOOL_MEMBER(paragraph_text_based, true, 00221 "Run paragraph detection on the post-text-recognition " 00222 "(more accurate)", 00223 this->params()), 00224 INT_MEMBER(cube_debug_level, 0, "Print cube debug info.", this->params()), 00225 STRING_MEMBER(outlines_odd, "%| ", "Non standard number of outlines", 00226 this->params()), 00227 STRING_MEMBER(outlines_2, "ij!?%\":;", "Non standard number of outlines", 00228 this->params()), 00229 BOOL_MEMBER(docqual_excuse_outline_errs, false, 00230 "Allow outline errs in unrejection?", this->params()), 00231 BOOL_MEMBER(tessedit_good_quality_unrej, true, 00232 "Reduce rejection on good docs", this->params()), 00233 BOOL_MEMBER(tessedit_use_reject_spaces, true, "Reject spaces?", 00234 this->params()), 00235 double_MEMBER(tessedit_reject_doc_percent, 65.00, 00236 "%rej allowed before rej whole doc", this->params()), 00237 double_MEMBER(tessedit_reject_block_percent, 45.00, 00238 "%rej allowed before rej whole block", this->params()), 00239 double_MEMBER(tessedit_reject_row_percent, 40.00, 00240 "%rej allowed before rej whole row", this->params()), 00241 double_MEMBER(tessedit_whole_wd_rej_row_percent, 70.00, 00242 "Number of row rejects in whole word rejects" 00243 "which prevents whole row rejection", 00244 this->params()), 00245 BOOL_MEMBER(tessedit_preserve_blk_rej_perfect_wds, true, 00246 "Only rej partially rejected words in block rejection", 00247 this->params()), 00248 BOOL_MEMBER(tessedit_preserve_row_rej_perfect_wds, true, 00249 "Only rej partially rejected words in row rejection", 00250 this->params()), 00251 BOOL_MEMBER(tessedit_dont_blkrej_good_wds, false, 00252 "Use word segmentation quality metric", this->params()), 00253 BOOL_MEMBER(tessedit_dont_rowrej_good_wds, false, 00254 "Use word segmentation quality metric", this->params()), 00255 INT_MEMBER(tessedit_preserve_min_wd_len, 2, 00256 "Only preserve wds longer than this", this->params()), 00257 BOOL_MEMBER(tessedit_row_rej_good_docs, true, 00258 "Apply row rejection to good docs", this->params()), 00259 double_MEMBER(tessedit_good_doc_still_rowrej_wd, 1.1, 00260 "rej good doc wd if more than this fraction rejected", 00261 this->params()), 00262 BOOL_MEMBER(tessedit_reject_bad_qual_wds, true, 00263 "Reject all bad quality wds", this->params()), 00264 BOOL_MEMBER(tessedit_debug_doc_rejection, false, "Page stats", 00265 this->params()), 00266 BOOL_MEMBER(tessedit_debug_quality_metrics, false, 00267 "Output data to debug file", this->params()), 00268 BOOL_MEMBER(bland_unrej, false, "unrej potential with no chekcs", 00269 this->params()), 00270 double_MEMBER(quality_rowrej_pc, 1.1, 00271 "good_quality_doc gte good char limit", this->params()), 00272 BOOL_MEMBER(unlv_tilde_crunching, true, 00273 "Mark v.bad words for tilde crunch", this->params()), 00274 BOOL_MEMBER(hocr_font_info, false, "Add font info to hocr output", 00275 this->params()), 00276 BOOL_MEMBER(crunch_early_merge_tess_fails, true, "Before word crunch?", 00277 this->params()), 00278 BOOL_MEMBER(crunch_early_convert_bad_unlv_chs, false, 00279 "Take out ~^ early?", this->params()), 00280 double_MEMBER(crunch_terrible_rating, 80.0, "crunch rating lt this", 00281 this->params()), 00282 BOOL_MEMBER(crunch_terrible_garbage, true, "As it says", this->params()), 00283 double_MEMBER(crunch_poor_garbage_cert, -9.0, 00284 "crunch garbage cert lt this", this->params()), 00285 double_MEMBER(crunch_poor_garbage_rate, 60, 00286 "crunch garbage rating lt this", this->params()), 00287 double_MEMBER(crunch_pot_poor_rate, 40, "POTENTIAL crunch rating lt this", 00288 this->params()), 00289 double_MEMBER(crunch_pot_poor_cert, -8.0, "POTENTIAL crunch cert lt this", 00290 this->params()), 00291 BOOL_MEMBER(crunch_pot_garbage, true, "POTENTIAL crunch garbage", 00292 this->params()), 00293 double_MEMBER(crunch_del_rating, 60, "POTENTIAL crunch rating lt this", 00294 this->params()), 00295 double_MEMBER(crunch_del_cert, -10.0, "POTENTIAL crunch cert lt this", 00296 this->params()), 00297 double_MEMBER(crunch_del_min_ht, 0.7, "Del if word ht lt xht x this", 00298 this->params()), 00299 double_MEMBER(crunch_del_max_ht, 3.0, "Del if word ht gt xht x this", 00300 this->params()), 00301 double_MEMBER(crunch_del_min_width, 3.0, 00302 "Del if word width lt xht x this", this->params()), 00303 double_MEMBER(crunch_del_high_word, 1.5, 00304 "Del if word gt xht x this above bl", this->params()), 00305 double_MEMBER(crunch_del_low_word, 0.5, 00306 "Del if word gt xht x this below bl", this->params()), 00307 double_MEMBER(crunch_small_outlines_size, 0.6, "Small if lt xht x this", 00308 this->params()), 00309 INT_MEMBER(crunch_rating_max, 10, "For adj length in rating per ch", 00310 this->params()), 00311 INT_MEMBER(crunch_pot_indicators, 1, 00312 "How many potential indicators needed", this->params()), 00313 BOOL_MEMBER(crunch_leave_ok_strings, true, "Don't touch sensible strings", 00314 this->params()), 00315 BOOL_MEMBER(crunch_accept_ok, true, "Use acceptability in okstring", 00316 this->params()), 00317 BOOL_MEMBER(crunch_leave_accept_strings, false, 00318 "Don't pot crunch sensible strings", this->params()), 00319 BOOL_MEMBER(crunch_include_numerals, false, "Fiddle alpha figures", 00320 this->params()), 00321 INT_MEMBER(crunch_leave_lc_strings, 4, 00322 "Don't crunch words with long lower case strings", 00323 this->params()), 00324 INT_MEMBER(crunch_leave_uc_strings, 4, 00325 "Don't crunch words with long lower case strings", 00326 this->params()), 00327 INT_MEMBER(crunch_long_repetitions, 3, 00328 "Crunch words with long repetitions", this->params()), 00329 INT_MEMBER(crunch_debug, 0, "As it says", this->params()), 00330 INT_MEMBER(fixsp_non_noise_limit, 1, 00331 "How many non-noise blbs either side?", this->params()), 00332 double_MEMBER(fixsp_small_outlines_size, 0.28, "Small if lt xht x this", 00333 this->params()), 00334 BOOL_MEMBER(tessedit_prefer_joined_punct, false, 00335 "Reward punctation joins", this->params()), 00336 INT_MEMBER(fixsp_done_mode, 1, "What constitues done for spacing", 00337 this->params()), 00338 INT_MEMBER(debug_fix_space_level, 0, "Contextual fixspace debug", 00339 this->params()), 00340 STRING_MEMBER(numeric_punctuation, ".,", 00341 "Punct. chs expected WITHIN numbers", this->params()), 00342 INT_MEMBER(x_ht_acceptance_tolerance, 8, 00343 "Max allowed deviation of blob top outside of font data", 00344 this->params()), 00345 INT_MEMBER(x_ht_min_change, 8, 00346 "Min change in xht before actually trying it", this->params()), 00347 INT_MEMBER(superscript_debug, 0, 00348 "Debug level for sub & superscript fixer", this->params()), 00349 double_MEMBER( 00350 superscript_worse_certainty, 2.0, 00351 "How many times worse " 00352 "certainty does a superscript position glyph need to be for " 00353 "us to try classifying it as a char with a different " 00354 "baseline?", 00355 this->params()), 00356 double_MEMBER( 00357 superscript_bettered_certainty, 0.97, 00358 "What reduction in " 00359 "badness do we think sufficient to choose a superscript " 00360 "over what we'd thought. For example, a value of 0.6 means " 00361 "we want to reduce badness of certainty by at least 40%", 00362 this->params()), 00363 double_MEMBER(superscript_scaledown_ratio, 0.4, 00364 "A superscript scaled down more than this is unbelievably " 00365 "small. For example, 0.3 means we expect the font size to " 00366 "be no smaller than 30% of the text line font size.", 00367 this->params()), 00368 double_MEMBER(subscript_max_y_top, 0.5, 00369 "Maximum top of a character measured as a multiple of " 00370 "x-height above the baseline for us to reconsider whether " 00371 "it's a subscript.", 00372 this->params()), 00373 double_MEMBER(superscript_min_y_bottom, 0.3, 00374 "Minimum bottom of a character measured as a multiple of " 00375 "x-height above the baseline for us to reconsider whether " 00376 "it's a superscript.", 00377 this->params()), 00378 BOOL_MEMBER(tessedit_write_block_separators, false, 00379 "Write block separators in output", this->params()), 00380 BOOL_MEMBER(tessedit_write_rep_codes, false, "Write repetition char code", 00381 this->params()), 00382 BOOL_MEMBER(tessedit_write_unlv, false, "Write .unlv output file", 00383 this->params()), 00384 BOOL_MEMBER(tessedit_create_txt, false, "Write .txt output file", 00385 this->params()), 00386 BOOL_MEMBER(tessedit_create_hocr, false, "Write .html hOCR output file", 00387 this->params()), 00388 BOOL_MEMBER(tessedit_create_pdf, false, "Write .pdf output file", 00389 this->params()), 00390 STRING_MEMBER(unrecognised_char, "|", 00391 "Output char for unidentified blobs", this->params()), 00392 INT_MEMBER(suspect_level, 99, "Suspect marker level", this->params()), 00393 INT_MEMBER(suspect_space_level, 100, 00394 "Min suspect level for rejecting spaces", this->params()), 00395 INT_MEMBER(suspect_short_words, 2, 00396 "Don't suspect dict wds longer than this", this->params()), 00397 BOOL_MEMBER(suspect_constrain_1Il, false, "UNLV keep 1Il chars rejected", 00398 this->params()), 00399 double_MEMBER(suspect_rating_per_ch, 999.9, "Don't touch bad rating limit", 00400 this->params()), 00401 double_MEMBER(suspect_accept_rating, -999.9, "Accept good rating limit", 00402 this->params()), 00403 BOOL_MEMBER(tessedit_minimal_rejection, false, 00404 "Only reject tess failures", this->params()), 00405 BOOL_MEMBER(tessedit_zero_rejection, false, "Don't reject ANYTHING", 00406 this->params()), 00407 BOOL_MEMBER(tessedit_word_for_word, false, 00408 "Make output have exactly one word per WERD", this->params()), 00409 BOOL_MEMBER(tessedit_zero_kelvin_rejection, false, 00410 "Don't reject ANYTHING AT ALL", this->params()), 00411 BOOL_MEMBER(tessedit_consistent_reps, true, 00412 "Force all rep chars the same", this->params()), 00413 INT_MEMBER(tessedit_reject_mode, 0, "Rejection algorithm", 00414 this->params()), 00415 BOOL_MEMBER(tessedit_rejection_debug, false, "Adaption debug", 00416 this->params()), 00417 BOOL_MEMBER(tessedit_flip_0O, true, "Contextual 0O O0 flips", 00418 this->params()), 00419 double_MEMBER(tessedit_lower_flip_hyphen, 1.5, 00420 "Aspect ratio dot/hyphen test", this->params()), 00421 double_MEMBER(tessedit_upper_flip_hyphen, 1.8, 00422 "Aspect ratio dot/hyphen test", this->params()), 00423 BOOL_MEMBER(rej_trust_doc_dawg, false, 00424 "Use DOC dawg in 11l conf. detector", this->params()), 00425 BOOL_MEMBER(rej_1Il_use_dict_word, false, "Use dictword test", 00426 this->params()), 00427 BOOL_MEMBER(rej_1Il_trust_permuter_type, true, "Don't double check", 00428 this->params()), 00429 BOOL_MEMBER(rej_use_tess_accepted, true, "Individual rejection control", 00430 this->params()), 00431 BOOL_MEMBER(rej_use_tess_blanks, true, "Individual rejection control", 00432 this->params()), 00433 BOOL_MEMBER(rej_use_good_perm, true, "Individual rejection control", 00434 this->params()), 00435 BOOL_MEMBER(rej_use_sensible_wd, false, "Extend permuter check", 00436 this->params()), 00437 BOOL_MEMBER(rej_alphas_in_number_perm, false, "Extend permuter check", 00438 this->params()), 00439 double_MEMBER(rej_whole_of_mostly_reject_word_fract, 0.85, 00440 "if >this fract", this->params()), 00441 INT_MEMBER(tessedit_image_border, 2, "Rej blbs near image edge limit", 00442 this->params()), 00443 STRING_MEMBER(ok_repeated_ch_non_alphanum_wds, "-?*\075", 00444 "Allow NN to unrej", this->params()), 00445 STRING_MEMBER(conflict_set_I_l_1, "Il1[]", "Il1 conflict set", 00446 this->params()), 00447 INT_MEMBER(min_sane_x_ht_pixels, 8, "Reject any x-ht lt or eq than this", 00448 this->params()), 00449 BOOL_MEMBER(tessedit_create_boxfile, false, "Output text with boxes", 00450 this->params()), 00451 INT_MEMBER(tessedit_page_number, -1, 00452 "-1 -> All pages" 00453 " , else specifc page to process", 00454 this->params()), 00455 BOOL_MEMBER(tessedit_write_images, false, 00456 "Capture the image from the IPE", this->params()), 00457 BOOL_MEMBER(interactive_display_mode, false, "Run interactively?", 00458 this->params()), 00459 STRING_MEMBER(file_type, ".tif", "Filename extension", this->params()), 00460 BOOL_MEMBER(tessedit_override_permuter, true, "According to dict_word", 00461 this->params()), 00462 INT_MEMBER(tessdata_manager_debug_level, 0, 00463 "Debug level for" 00464 " TessdataManager functions.", 00465 this->params()), 00466 STRING_MEMBER(tessedit_load_sublangs, "", 00467 "List of languages to load with this one", this->params()), 00468 BOOL_MEMBER(tessedit_use_primary_params_model, false, 00469 "In multilingual mode use params model of the" 00470 " primary language", 00471 this->params()), 00472 double_MEMBER(min_orientation_margin, 7.0, 00473 "Min acceptable orientation margin", this->params()), 00474 BOOL_MEMBER(textord_tabfind_show_vlines, false, "Debug line finding", 00475 this->params()), 00476 BOOL_MEMBER(textord_use_cjk_fp_model, FALSE, "Use CJK fixed pitch model", 00477 this->params()), 00478 BOOL_MEMBER(poly_allow_detailed_fx, false, 00479 "Allow feature extractors to see the original outline", 00480 this->params()), 00481 BOOL_INIT_MEMBER(tessedit_init_config_only, false, 00482 "Only initialize with the config file. Useful if the " 00483 "instance is not going to be used for OCR but say only " 00484 "for layout analysis.", 00485 this->params()), 00486 BOOL_MEMBER(textord_equation_detect, false, "Turn on equation detector", 00487 this->params()), 00488 BOOL_MEMBER(textord_tabfind_vertical_text, true, 00489 "Enable vertical detection", this->params()), 00490 BOOL_MEMBER(textord_tabfind_force_vertical_text, false, 00491 "Force using vertical text page mode", this->params()), 00492 double_MEMBER( 00493 textord_tabfind_vertical_text_ratio, 0.5, 00494 "Fraction of textlines deemed vertical to use vertical page " 00495 "mode", 00496 this->params()), 00497 double_MEMBER( 00498 textord_tabfind_aligned_gap_fraction, 0.75, 00499 "Fraction of height used as a minimum gap for aligned blobs.", 00500 this->params()), 00501 INT_MEMBER(tessedit_parallelize, 0, "Run in parallel where possible", 00502 this->params()), 00503 BOOL_MEMBER(preserve_interword_spaces, false, 00504 "Preserve multiple interword spaces", this->params()), 00505 BOOL_MEMBER(include_page_breaks, FALSE, 00506 "Include page separator string in output text after each " 00507 "image/page.", 00508 this->params()), 00509 STRING_MEMBER(page_separator, "\f", 00510 "Page separator (default is form feed control character)", 00511 this->params()), 00512 00513 // The following parameters were deprecated and removed from their 00514 // original 00515 // locations. The parameters are temporarily kept here to give Tesseract 00516 // users a chance to updated their [lang].traineddata and config files 00517 // without introducing failures during Tesseract initialization. 00518 // TODO(ocr-team): remove these parameters from the code once we are 00519 // reasonably sure that Tesseract users have updated their data files. 00520 // 00521 // BEGIN DEPRECATED PARAMETERS 00522 BOOL_MEMBER(textord_tabfind_vertical_horizontal_mix, true, 00523 "find horizontal lines such as headers in vertical page mode", 00524 this->params()), 00525 INT_MEMBER(tessedit_ok_mode, 5, "Acceptance decision algorithm", 00526 this->params()), 00527 BOOL_INIT_MEMBER(load_fixed_length_dawgs, true, 00528 "Load fixed length dawgs" 00529 " (e.g. for non-space delimited languages)", 00530 this->params()), 00531 INT_MEMBER(segment_debug, 0, "Debug the whole segmentation process", 00532 this->params()), 00533 BOOL_MEMBER(permute_debug, 0, "Debug char permutation process", 00534 this->params()), 00535 double_MEMBER(bestrate_pruning_factor, 2.0, 00536 "Multiplying factor of" 00537 " current best rate to prune other hypotheses", 00538 this->params()), 00539 BOOL_MEMBER(permute_script_word, 0, 00540 "Turn on word script consistency permuter", this->params()), 00541 BOOL_MEMBER(segment_segcost_rating, 0, 00542 "incorporate segmentation cost in word rating?", 00543 this->params()), 00544 double_MEMBER(segment_reward_script, 0.95, 00545 "Score multipler for script consistency within a word. " 00546 "Being a 'reward' factor, it should be <= 1. " 00547 "Smaller value implies bigger reward.", 00548 this->params()), 00549 BOOL_MEMBER(permute_fixed_length_dawg, 0, 00550 "Turn on fixed-length phrasebook search permuter", 00551 this->params()), 00552 BOOL_MEMBER(permute_chartype_word, 0, 00553 "Turn on character type (property) consistency permuter", 00554 this->params()), 00555 double_MEMBER(segment_reward_chartype, 0.97, 00556 "Score multipler for char type consistency within a word. ", 00557 this->params()), 00558 double_MEMBER(segment_reward_ngram_best_choice, 0.99, 00559 "Score multipler for ngram permuter's best choice" 00560 " (only used in the Han script path).", 00561 this->params()), 00562 BOOL_MEMBER(ngram_permuter_activated, false, 00563 "Activate character-level n-gram-based permuter", 00564 this->params()), 00565 BOOL_MEMBER(permute_only_top, false, "Run only the top choice permuter", 00566 this->params()), 00567 INT_MEMBER(language_model_fixed_length_choices_depth, 3, 00568 "Depth of blob choice lists to explore" 00569 " when fixed length dawgs are on", 00570 this->params()), 00571 BOOL_MEMBER(use_new_state_cost, FALSE, 00572 "use new state cost heuristics for segmentation state" 00573 " evaluation", 00574 this->params()), 00575 double_MEMBER(heuristic_segcost_rating_base, 1.25, 00576 "base factor for adding segmentation cost into word rating." 00577 "It's a multiplying factor, the larger the value above 1, " 00578 "the bigger the effect of segmentation cost.", 00579 this->params()), 00580 double_MEMBER(heuristic_weight_rating, 1.0, 00581 "weight associated with char rating in combined cost of" 00582 "state", 00583 this->params()), 00584 double_MEMBER(heuristic_weight_width, 1000.0, 00585 "weight associated with width evidence in combined cost of" 00586 " state", 00587 this->params()), 00588 double_MEMBER(heuristic_weight_seamcut, 0.0, 00589 "weight associated with seam cut in combined cost of state", 00590 this->params()), 00591 double_MEMBER(heuristic_max_char_wh_ratio, 2.0, 00592 "max char width-to-height ratio allowed in segmentation", 00593 this->params()), 00594 BOOL_MEMBER(enable_new_segsearch, true, 00595 "Enable new segmentation search path.", this->params()), 00596 double_MEMBER(segsearch_max_fixed_pitch_char_wh_ratio, 2.0, 00597 "Maximum character width-to-height ratio for" 00598 " fixed-pitch fonts", 00599 this->params()), 00600 // END DEPRECATED PARAMETERS 00601 00602 backup_config_file_(NULL), 00603 pix_binary_(NULL), 00604 cube_binary_(NULL), 00605 pix_grey_(NULL), 00606 pix_thresholds_(NULL), 00607 source_resolution_(0), 00608 textord_(this), 00609 right_to_left_(false), 00610 scaled_color_(NULL), 00611 scaled_factor_(-1), 00612 deskew_(1.0f, 0.0f), 00613 reskew_(1.0f, 0.0f), 00614 most_recently_used_(this), 00615 font_table_size_(0), 00616 #ifndef NO_CUBE_BUILD 00617 cube_cntxt_(NULL), 00618 tess_cube_combiner_(NULL), 00619 #endif 00620 equ_detect_(NULL) { 00621 } 00622 00623 Tesseract::~Tesseract() { 00624 Clear(); 00625 end_tesseract(); 00626 sub_langs_.delete_data_pointers(); 00627 #ifndef NO_CUBE_BUILD 00628 // Delete cube objects. 00629 if (cube_cntxt_ != NULL) { 00630 delete cube_cntxt_; 00631 cube_cntxt_ = NULL; 00632 } 00633 if (tess_cube_combiner_ != NULL) { 00634 delete tess_cube_combiner_; 00635 tess_cube_combiner_ = NULL; 00636 } 00637 #endif 00638 } 00639 00640 void Tesseract::Clear() { 00641 pixDestroy(&pix_binary_); 00642 pixDestroy(&cube_binary_); 00643 pixDestroy(&pix_grey_); 00644 pixDestroy(&pix_thresholds_); 00645 pixDestroy(&scaled_color_); 00646 deskew_ = FCOORD(1.0f, 0.0f); 00647 reskew_ = FCOORD(1.0f, 0.0f); 00648 splitter_.Clear(); 00649 scaled_factor_ = -1; 00650 for (int i = 0; i < sub_langs_.size(); ++i) 00651 sub_langs_[i]->Clear(); 00652 } 00653 00654 void Tesseract::SetEquationDetect(EquationDetect* detector) { 00655 equ_detect_ = detector; 00656 equ_detect_->SetLangTesseract(this); 00657 } 00658 00659 // Clear all memory of adaption for this and all subclassifiers. 00660 void Tesseract::ResetAdaptiveClassifier() { 00661 ResetAdaptiveClassifierInternal(); 00662 for (int i = 0; i < sub_langs_.size(); ++i) { 00663 sub_langs_[i]->ResetAdaptiveClassifierInternal(); 00664 } 00665 } 00666 00667 // Clear the document dictionary for this and all subclassifiers. 00668 void Tesseract::ResetDocumentDictionary() { 00669 getDict().ResetDocumentDictionary(); 00670 for (int i = 0; i < sub_langs_.size(); ++i) { 00671 sub_langs_[i]->getDict().ResetDocumentDictionary(); 00672 } 00673 } 00674 00675 void Tesseract::SetBlackAndWhitelist() { 00676 // Set the white and blacklists (if any) 00677 unicharset.set_black_and_whitelist(tessedit_char_blacklist.string(), 00678 tessedit_char_whitelist.string(), 00679 tessedit_char_unblacklist.string()); 00680 // Black and white lists should apply to all loaded classifiers. 00681 for (int i = 0; i < sub_langs_.size(); ++i) { 00682 sub_langs_[i]->unicharset.set_black_and_whitelist( 00683 tessedit_char_blacklist.string(), tessedit_char_whitelist.string(), 00684 tessedit_char_unblacklist.string()); 00685 } 00686 } 00687 00688 // Perform steps to prepare underlying binary image/other data structures for 00689 // page segmentation. 00690 void Tesseract::PrepareForPageseg() { 00691 textord_.set_use_cjk_fp_model(textord_use_cjk_fp_model); 00692 pixDestroy(&cube_binary_); 00693 cube_binary_ = pixClone(pix_binary()); 00694 // Find the max splitter strategy over all langs. 00695 ShiroRekhaSplitter::SplitStrategy max_pageseg_strategy = 00696 static_cast<ShiroRekhaSplitter::SplitStrategy>( 00697 static_cast<inT32>(pageseg_devanagari_split_strategy)); 00698 for (int i = 0; i < sub_langs_.size(); ++i) { 00699 ShiroRekhaSplitter::SplitStrategy pageseg_strategy = 00700 static_cast<ShiroRekhaSplitter::SplitStrategy>( 00701 static_cast<inT32>(sub_langs_[i]->pageseg_devanagari_split_strategy)); 00702 if (pageseg_strategy > max_pageseg_strategy) 00703 max_pageseg_strategy = pageseg_strategy; 00704 // Clone the cube image to all the sub langs too. 00705 pixDestroy(&sub_langs_[i]->cube_binary_); 00706 sub_langs_[i]->cube_binary_ = pixClone(pix_binary()); 00707 pixDestroy(&sub_langs_[i]->pix_binary_); 00708 sub_langs_[i]->pix_binary_ = pixClone(pix_binary()); 00709 } 00710 // Perform shiro-rekha (top-line) splitting and replace the current image by 00711 // the newly splitted image. 00712 splitter_.set_orig_pix(pix_binary()); 00713 splitter_.set_pageseg_split_strategy(max_pageseg_strategy); 00714 if (splitter_.Split(true)) { 00715 ASSERT_HOST(splitter_.splitted_image()); 00716 pixDestroy(&pix_binary_); 00717 pix_binary_ = pixClone(splitter_.splitted_image()); 00718 } 00719 } 00720 00721 // Perform steps to prepare underlying binary image/other data structures for 00722 // OCR. The current segmentation is required by this method. 00723 // Note that this method resets pix_binary_ to the original binarized image, 00724 // which may be different from the image actually used for OCR depending on the 00725 // value of devanagari_ocr_split_strategy. 00726 void Tesseract::PrepareForTessOCR(BLOCK_LIST* block_list, 00727 Tesseract* osd_tess, OSResults* osr) { 00728 // Find the max splitter strategy over all langs. 00729 ShiroRekhaSplitter::SplitStrategy max_ocr_strategy = 00730 static_cast<ShiroRekhaSplitter::SplitStrategy>( 00731 static_cast<inT32>(ocr_devanagari_split_strategy)); 00732 for (int i = 0; i < sub_langs_.size(); ++i) { 00733 ShiroRekhaSplitter::SplitStrategy ocr_strategy = 00734 static_cast<ShiroRekhaSplitter::SplitStrategy>( 00735 static_cast<inT32>(sub_langs_[i]->ocr_devanagari_split_strategy)); 00736 if (ocr_strategy > max_ocr_strategy) 00737 max_ocr_strategy = ocr_strategy; 00738 } 00739 // Utilize the segmentation information available. 00740 splitter_.set_segmentation_block_list(block_list); 00741 splitter_.set_ocr_split_strategy(max_ocr_strategy); 00742 // Run the splitter for OCR 00743 bool split_for_ocr = splitter_.Split(false); 00744 // Restore pix_binary to the binarized original pix for future reference. 00745 ASSERT_HOST(splitter_.orig_pix()); 00746 pixDestroy(&pix_binary_); 00747 pix_binary_ = pixClone(splitter_.orig_pix()); 00748 // If the pageseg and ocr strategies are different, refresh the block list 00749 // (from the last SegmentImage call) with blobs from the real image to be used 00750 // for OCR. 00751 if (splitter_.HasDifferentSplitStrategies()) { 00752 BLOCK block("", TRUE, 0, 0, 0, 0, pixGetWidth(pix_binary_), 00753 pixGetHeight(pix_binary_)); 00754 Pix* pix_for_ocr = split_for_ocr ? splitter_.splitted_image() : 00755 splitter_.orig_pix(); 00756 extract_edges(pix_for_ocr, &block); 00757 splitter_.RefreshSegmentationWithNewBlobs(block.blob_list()); 00758 } 00759 // The splitter isn't needed any more after this, so save memory by clearing. 00760 splitter_.Clear(); 00761 } 00762 00763 } // namespace tesseract