Exemplo n.º 1
0
int16_t BLOCK_LINE_IT::get_line(             //get a line
                              int16_t y,     //line to get
                              int16_t &xext  //output extent
                             ) {
  ICOORD bleft;                  //bounding box
  ICOORD tright;                 //of block & rect

                                 //get block box
  block->bounding_box (bleft, tright);
  if (y < bleft.y () || y >= tright.y ()) {
    //              block->print(stderr,false);
    BADBLOCKLINE.error ("BLOCK_LINE_IT::get_line", ABORT, "Y=%d", y);
  }

                                 //get rectangle box
  rect_it.bounding_box (bleft, tright);
                                 //inside rectangle
  if (y >= bleft.y () && y < tright.y ()) {
                                 //width of line
    xext = tright.x () - bleft.x ();
    return bleft.x ();           //start of line
  }
  for (rect_it.start_block (); !rect_it.cycled_rects (); rect_it.forward ()) {
                                 //get rectangle box
    rect_it.bounding_box (bleft, tright);
                                 //inside rectangle
    if (y >= bleft.y () && y < tright.y ()) {
                                 //width of line
      xext = tright.x () - bleft.x ();
      return bleft.x ();         //start of line
    }
  }
  LOSTBLOCKLINE.error ("BLOCK_LINE_IT::get_line", ABORT, "Y=%d", y);
  return 0;                      //dummy to stop warning
}
Exemplo n.º 2
0
void ELIST2::assign_to_sublist(                            //to this list
                               ELIST2_ITERATOR *start_it,  //from list start
                               ELIST2_ITERATOR *end_it) {  //from list end
  const ERRCODE LIST_NOT_EMPTY =
    "Destination list must be empty before extracting a sublist";

  if (!empty ())
    LIST_NOT_EMPTY.error ("ELIST2.assign_to_sublist", ABORT, NULL);

  last = start_it->extract_sublist (end_it);
}
Exemplo n.º 3
0
ScrollView::Color check_path_legal(                  //certify outline
                        CRACKEDGE *start  //start of loop
                       ) {
  int lastchain;              //last chain code
  int chaindiff;               //chain code diff
  inT32 length;                  //length of loop
  inT32 chainsum;                //sum of chain diffs
  CRACKEDGE *edgept;             //current point
  const ERRCODE ED_ILLEGAL_SUM = "Illegal sum of chain codes";

  length = 0;
  chainsum = 0;                  //sum of chain codes
  edgept = start;
  lastchain = edgept->prev->stepdir; //previous chain code
  do {
    length++;
    if (edgept->stepdir != lastchain) {
                                 //chain code difference
      chaindiff = edgept->stepdir - lastchain;
      if (chaindiff > 2)
        chaindiff -= 4;
      else if (chaindiff < -2)
        chaindiff += 4;
      chainsum += chaindiff;     //sum differences
      lastchain = edgept->stepdir;
    }
    edgept = edgept->next;
  }
  while (edgept != start && length < edges_maxedgelength);

  if ((chainsum != 4 && chainsum != -4)
  || edgept != start || length < MINEDGELENGTH) {
    if (edgept != start) {
      long_edges++;
      return ScrollView::YELLOW;
    }
    else if (length < MINEDGELENGTH) {
      short_edges++;
      return ScrollView::MAGENTA;
    }
    else {
      ED_ILLEGAL_SUM.error ("check_path_legal", TESSLOG, "chainsum=%d",
        chainsum);
      return ScrollView::GREEN;
    }
  }
                                 //colour on inside
  return chainsum < 0 ? ScrollView::BLUE : ScrollView::RED;
}
Exemplo n.º 4
0
void ELIST::assign_to_sublist(                           //to this list
                              ELIST_ITERATOR *start_it,  //from list start
                              ELIST_ITERATOR *end_it) {  //from list end
  const ERRCODE LIST_NOT_EMPTY =
    "Destination list must be empty before extracting a sublist";

  #ifndef NDEBUG
  if (!this)
    NULL_OBJECT.error ("ELIST::assign_to_sublist", ABORT, NULL);
  #endif

  if (!empty ())
    LIST_NOT_EMPTY.error ("ELIST.assign_to_sublist", ABORT, NULL);

  last = start_it->extract_sublist (end_it);
}
Exemplo n.º 5
0
void LLSQ::remove(double x, double y) {          // delete an element
  if (total_weight <= 0.0)                       // illegal
    EMPTY_LLSQ.error("LLSQ::remove", ABORT, NULL);
  total_weight--;                           // count elements
  sigx -= x;                     // update accumulators
  sigy -= y;
  sigxx -= x * x;
  sigxy -= x * y;
  sigyy -= y * y;
}
Exemplo n.º 6
0
/**********************************************************************
 * error
 *
 * Print an error message and continue, exit or abort according to action.
 * Makes use of error messages and numbers in a common place.
 *
 **********************************************************************/
void ERRCODE::error(             // handle error
const char *caller,              // name of caller
TessErrorLogCode action,         // action to take
const char *format, ...          // special message
) const {
  va_list args;                  // variable args
  char msg[MAX_MSG];
  char *msgptr = msg;

  if (caller != nullptr)
                                 //name of caller
    msgptr += sprintf (msgptr, "%s:", caller);
                                 //actual message
  msgptr += sprintf (msgptr, "Error:%s", message);
  if (format != nullptr) {
    msgptr += sprintf (msgptr, ":");
    va_start(args, format);  //variable list
    #ifdef _WIN32
                                 //print remainder
    msgptr += _vsnprintf (msgptr, MAX_MSG - 2 - (msgptr - msg), format, args);
    msg[MAX_MSG - 2] = '\0';     //ensure termination
    strcat (msg, "\n");
    #else
                                 //print remainder
    msgptr += vsprintf (msgptr, format, args);
                                 //no specific
    msgptr += sprintf (msgptr, "\n");
    #endif
    va_end(args);
  }
  else
                                 //no specific
    msgptr += sprintf (msgptr, "\n");

  // %s is needed here so msg is printed correctly!
  fprintf(stderr, "%s", msg);

  int* p = nullptr;
  switch (action) {
    case DBG:
    case TESSLOG:
      return;                    //report only
    case TESSEXIT:
      //err_exit();
    case ABORT:
      // Create a deliberate segv as the stack trace is more useful that way.
      if (!*p)
        abort();
    default:
      BADERRACTION.error ("error", ABORT, nullptr);
  }
}
Exemplo n.º 7
0
VARIABLES_WINDOW *ASSOCIATION_LIST::lookup(           //find assoc
                                           WINDOW fd  //Window handle
                                          ) {
  ASSOC_IT it(&associations); 

  if (!it.empty ()) {
    for (it.mark_cycle_pt (); !it.cycled_list (); it.forward ()) {
      if (fd == it.data ()->fd)
        return it.data ()->var_win;
    }
  }
  NOT_ASSOCIATED.error ("ASSOCIATION_LIST::lookup", ABORT, NULL);
  return NULL;
}
Exemplo n.º 8
0
void ASSOCIATION_LIST::remove(           // delete assoc
                              WINDOW fd  //Window handle
                             ) {
  ASSOC_IT it(&associations); 

  if (!it.empty ()) {
    for (it.mark_cycle_pt (); !it.cycled_list (); it.forward ()) {
      if (fd == it.data ()->fd) {
        it.extract ();
        return;
      }
    }
  }
  NOT_ASSOCIATED.error ("ASSOCIATION_LIST::remove", ABORT, NULL);
}
Exemplo n.º 9
0
void QLSQ::remove(           //delete an element
                  double x,  //xcoord
                  double y   //ycoord
                 ) {
  if (n <= 0)
                                 //illegal
    EMPTY_QLSQ.error ("QLSQ::remove", ABORT, NULL);
  n--;                           //count elements
  sigx -= x;                     //update accumulators
  sigy -= y;
  sigxx -= x * x;
  sigxy -= x * y;
  sigyy -= y * y;
  sigxxx -= (long double) x *x * x;
  sigxxy -= (long double) x *x * y;
  sigxxxx -= (long double) x *x * x * x;
}
Exemplo n.º 10
0
/**********************************************************************
 * error
 *
 * Print an error message and continue, exit or abort according to action.
 * Makes use of error messages and numbers in a common place.
 *
 **********************************************************************/
void
ERRCODE::error (                 //handle error
const char *caller,              //name of caller
inT8 action,                     //action to take
const char *format, ...          //special message
) const
{
  va_list args;                  //variable args
  char msg[MAX_MSG];
  char *msgptr = msg;

  if (caller != NULL)
                                 //name of caller
    msgptr += sprintf (msgptr, "%s:", caller);
                                 //actual message
  msgptr += sprintf (msgptr, "Error:%s", message);
  if (format != NULL) {
    msgptr += sprintf (msgptr, ":");
    va_start(args, format);  //variable list
    #ifdef __MSW32__
                                 //print remainder
    msgptr += _vsnprintf (msgptr, MAX_MSG - 2 - (msgptr - msg), format, args);
    msg[MAX_MSG - 2] = '\0';     //ensure termination
    strcat (msg, "\n");
    #else
                                 //print remainder
    msgptr += vsprintf (msgptr, format, args);
                                 //no specific
    msgptr += sprintf (msgptr, "\n");
    #endif
    va_end(args);
  }
  else
                                 //no specific
    msgptr += sprintf (msgptr, "\n");

  fprintf(stderr, msg);
  /*if ((strstr (message, "File") != NULL) ||
    (strstr (message, "file") != NULL))
  else if ((strstr (message, "List") != NULL) ||
    (strstr (message, "list") != NULL))
  else if ((strstr (message, "Memory") != NULL) ||
    (strstr (message, "memory") != NULL))
    global_abort_code = MEMORY_ABORT;
  else
    global_abort_code = NO_ABORT_CODE;
    */

  int* p = NULL;
  switch (action) {
    case DBG:
    case TESSLOG:
      return;                    //report only
    case TESSEXIT:
      //err_exit();
    case ABORT:
      // Create a deliberate segv as the stack trace is more useful that way.
      if (!*p)
        abort();
    default:
      BADERRACTION.error ("error", ABORT, NULL);
  }
}
Exemplo n.º 11
0
ELIST2_LINK *ELIST2_ITERATOR::extract_sublist(                              //from this current
                                              ELIST2_ITERATOR *other_it) {  //to other current
  #ifndef NDEBUG
  const ERRCODE BAD_EXTRACTION_PTS =
    "Can't extract sublist from points on different lists";
  const ERRCODE DONT_EXTRACT_DELETED =
    "Can't extract a sublist marked by deleted points";
  #endif
  const ERRCODE BAD_SUBLIST = "Can't find sublist end point in original list";

  ELIST2_ITERATOR temp_it = *this;
  ELIST2_LINK *end_of_new_list;

  #ifndef NDEBUG
  if (!other_it)
    BAD_PARAMETER.error ("ELIST2_ITERATOR::extract_sublist", ABORT,
      "other_it NULL");
  if (!list)
    NO_LIST.error ("ELIST2_ITERATOR::extract_sublist", ABORT, NULL);
  if (list != other_it->list)
    BAD_EXTRACTION_PTS.error ("ELIST2_ITERATOR.extract_sublist", ABORT, NULL);
  if (list->empty ())
    EMPTY_LIST.error ("ELIST2_ITERATOR::extract_sublist", ABORT, NULL);

  if (!current || !other_it->current)
    DONT_EXTRACT_DELETED.error ("ELIST2_ITERATOR.extract_sublist", ABORT,
      NULL);
  #endif

  ex_current_was_last = other_it->ex_current_was_last = FALSE;
  ex_current_was_cycle_pt = FALSE;
  other_it->ex_current_was_cycle_pt = FALSE;

  temp_it.mark_cycle_pt ();
  do {                           //walk sublist
    if (temp_it.cycled_list ())  //can't find end pt
      BAD_SUBLIST.error ("ELIST2_ITERATOR.extract_sublist", ABORT, NULL);

    if (temp_it.at_last ()) {
      list->last = prev;
      ex_current_was_last = other_it->ex_current_was_last = TRUE;
    }

    if (temp_it.current == cycle_pt)
      ex_current_was_cycle_pt = TRUE;

    if (temp_it.current == other_it->cycle_pt)
      other_it->ex_current_was_cycle_pt = TRUE;

    temp_it.forward ();
  }
                                 //do INCLUSIVE list
  while (temp_it.prev != other_it->current);

                                 //circularise sublist
  other_it->current->next = current;
                                 //circularise sublist
  current->prev = other_it->current;
  end_of_new_list = other_it->current;

                                 //sublist = whole list
  if (prev == other_it->current) {
    list->last = NULL;
    prev = current = next = NULL;
    other_it->prev = other_it->current = other_it->next = NULL;
  }
  else {
    prev->next = other_it->next;
    other_it->next->prev = prev;

    current = other_it->current = NULL;
    next = other_it->next;
    other_it->prev = prev;
  }
  return end_of_new_list;
}
Exemplo n.º 12
0
void ELIST2_ITERATOR::exchange(                              //positions of 2 links
                               ELIST2_ITERATOR *other_it) {  //other iterator
  const ERRCODE DONT_EXCHANGE_DELETED =
    "Can't exchange deleted elements of lists";

  ELIST2_LINK *old_current;

  #ifndef NDEBUG
  if (!list)
    NO_LIST.error ("ELIST2_ITERATOR::exchange", ABORT, NULL);
  if (!other_it)
    BAD_PARAMETER.error ("ELIST2_ITERATOR::exchange", ABORT, "other_it NULL");
  if (!(other_it->list))
    NO_LIST.error ("ELIST2_ITERATOR::exchange", ABORT, "other_it");
  #endif

  /* Do nothing if either list is empty or if both iterators reference the same
  link */

  if ((list->empty ()) ||
    (other_it->list->empty ()) || (current == other_it->current))
    return;

  /* Error if either current element is deleted */

  if (!current || !other_it->current)
    DONT_EXCHANGE_DELETED.error ("ELIST2_ITERATOR.exchange", ABORT, NULL);

  /* Now handle the 4 cases: doubleton list; non-doubleton adjacent elements
  (other before this); non-doubleton adjacent elements (this before other);
  non-adjacent elements. */

                                 //adjacent links
  if ((next == other_it->current) ||
  (other_it->next == current)) {
                                 //doubleton list
    if ((next == other_it->current) &&
    (other_it->next == current)) {
      prev = next = current;
      other_it->prev = other_it->next = other_it->current;
    }
    else {                       //non-doubleton with
                                 //adjacent links
                                 //other before this
      if (other_it->next == current) {
        other_it->prev->next = current;
        other_it->current->next = next;
        other_it->current->prev = current;
        current->next = other_it->current;
        current->prev = other_it->prev;
        next->prev = other_it->current;

        other_it->next = other_it->current;
        prev = current;
      }
      else {                     //this before other
        prev->next = other_it->current;
        current->next = other_it->next;
        current->prev = other_it->current;
        other_it->current->next = current;
        other_it->current->prev = prev;
        other_it->next->prev = current;

        next = current;
        other_it->prev = other_it->current;
      }
    }
  }
  else {                         //no overlap
    prev->next = other_it->current;
    current->next = other_it->next;
    current->prev = other_it->prev;
    next->prev = other_it->current;
    other_it->prev->next = current;
    other_it->current->next = next;
    other_it->current->prev = prev;
    other_it->next->prev = current;
  }

  /* update end of list pointer when necessary (remember that the 2 iterators
    may iterate over different lists!) */

  if (list->last == current)
    list->last = other_it->current;
  if (other_it->list->last == other_it->current)
    other_it->list->last = current;

  if (current == cycle_pt)
    cycle_pt = other_it->cycle_pt;
  if (other_it->current == other_it->cycle_pt)
    other_it->cycle_pt = cycle_pt;

  /* The actual exchange - in all cases*/

  old_current = current;
  current = other_it->current;
  other_it->current = old_current;
}