예제 #1
0
// Threshold the given grey or color image into the tesseract global
// image ready for recognition. Requires thresholds and hi_value
// produced by OtsuThreshold above.
void TessBaseAPI::ThresholdRect(const unsigned char* imagedata,
                                int bytes_per_pixel,
                                int bytes_per_line,
                                int left, int top,
                                int width, int height,
                                const int* thresholds,
                                const int* hi_values) {
  IMAGELINE line;
  page_image.create(width, height, 1);
  line.init(width);
  // For each line in the image, fill the IMAGELINE class and put it into the
  // Tesseract global page_image. Note that Tesseract stores images with the
  // bottom at y=0 and 0 is black, so we need 2 kinds of inversion.
  const unsigned char* data = imagedata + top*bytes_per_line +
                              left*bytes_per_pixel;
  for (int y = height - 1 ; y >= 0; --y) {
    const unsigned char* pix = data;
    for (int x = 0; x < width; ++x, pix += bytes_per_pixel) {
      line.pixels[x] = 1;
      for (int ch = 0; ch < bytes_per_pixel; ++ch) {
        if (hi_values[ch] >= 0 &&
            (pix[ch] > thresholds[ch]) == (hi_values[ch] == 0)) {
          line.pixels[x] = 0;
          break;
        }
      }
    }
    page_image.put_line(0, y, width, &line, 0);
    data += bytes_per_line;
  }
}
예제 #2
0
void read_tiff_image(TIFF* tif, IMAGE* image) {
  tdata_t buf;
  uint32 image_width, image_height;
  uint16 photometric;
  inT16 bpp;
  inT16 samples_per_pixel = 0;
  TIFFGetField(tif, TIFFTAG_IMAGEWIDTH, &image_width);
  TIFFGetField(tif, TIFFTAG_IMAGELENGTH, &image_height);
  TIFFGetField(tif, TIFFTAG_BITSPERSAMPLE, &bpp);
  TIFFGetField(tif, TIFFTAG_SAMPLESPERPIXEL, &samples_per_pixel);
  TIFFGetField(tif, TIFFTAG_PHOTOMETRIC, &photometric);
  if (samples_per_pixel > 1)
    bpp *= samples_per_pixel;
  // Tesseract's internal representation is 0-is-black,
  // so if the photometric is 1 (min is black) then high-valued pixels
  // are 1 (white), otherwise they are 0 (black).
  uinT8 high_value = photometric == 1;
  image->create(image_width, image_height, bpp);
  IMAGELINE line;
  line.init(image_width);

  buf = _TIFFmalloc(TIFFScanlineSize(tif));
  int bytes_per_line = (image_width*bpp + 7)/8;
  uinT8* dest_buf = image->get_buffer();
  // This will go badly wrong with one of the more exotic tiff formats,
  // but the majority will work OK.
  for (int y = 0; y < image_height; ++y) {
    TIFFReadScanline(tif, buf, y);
    memcpy(dest_buf, buf, bytes_per_line);
    dest_buf += bytes_per_line;
  }
  if (high_value == 0)
    invert_image(image);
  _TIFFfree(buf);
}
예제 #3
0
// Dump the internal binary image to a PGM file.
void TessBaseAPI::DumpPGM(const char* filename) {
  IMAGELINE line;
  line.init(page_image.get_xsize());
  FILE *fp = fopen(filename, "w");
  fprintf(fp, "P5 " INT32FORMAT " " INT32FORMAT " 255\n", page_image.get_xsize(),
          page_image.get_ysize());
  for (int j = page_image.get_ysize()-1; j >= 0 ; --j) {
    page_image.get_line(0, j, page_image.get_xsize(), &line, 0);
    for (int i = 0; i < page_image.get_xsize(); ++i) {
      uinT8 b = line.pixels[i] ? 255 : 0;
      fwrite(&b, 1, 1, fp);
    }
  }
  fclose(fp);
}
DLLSYM void block_edges(                      //get edges in a block
                        IMAGE *t_image,       //threshold image
                        PDBLK *block,         //block in image
                        ICOORD page_tr        //corner of page
                       ) {
  uinT8 margin;                  //margin colour
  inT16 x;                       //line coords
  inT16 y;                       //current line
  ICOORD bleft;                  //bounding box
  ICOORD tright;
  ICOORD block_bleft;            //bounding box
  ICOORD block_tright;
  int xindex;                    //index to pixel
  BLOCK_LINE_IT line_it = block; //line iterator
  IMAGELINE bwline;              //thresholded line
                                 //lines in progress
  CRACKEDGE **ptrline = new CRACKEDGE*[t_image->get_xsize()+1];
  block->bounding_box (bleft, tright); // block box
  block_bleft = bleft;
  block_tright = tright;
  for (x = tright.x () - bleft.x (); x >= 0; x--)
    ptrline[x] = NULL;           //no lines in progress

  bwline.init (t_image->get_xsize());

  margin = WHITE_PIX;

  for (y = tright.y () - 1; y >= bleft.y () - 1; y--) {
    if (y >= block_bleft.y () && y < block_tright.y ()) {
      t_image->get_line (bleft.x (), y, tright.x () - bleft.x (), &bwline,
        0);
      make_margins (block, &line_it, bwline.pixels, margin, bleft.x (),
        tright.x (), y);
    }
    else {
      x = tright.x () - bleft.x ();
      for (xindex = 0; xindex < x; xindex++)
        bwline.pixels[xindex] = margin;
    }
    line_edges (bleft.x (), y, tright.x () - bleft.x (),
      margin, bwline.pixels, ptrline);
  }

  free_crackedges(free_cracks);  //really free them
  free_cracks = NULL;
    delete [] ptrline;
  }
예제 #5
0
////////////DEBAYAN//Deskew begins//////////////////////
void deskew(float angle,int srcheight, int srcwidth)
{
  //angle=4;        //45° for example 
  IMAGE tempimage;
  
  
  IMAGELINE line;
  //Convert degrees to radians 
  float radians=(2*3.1416*angle)/360; 
  
  float cosine=(float)cos(radians); 
  float sine=(float)sin(radians); 
  
  float Point1x=(srcheight*sine); 
  float Point1y=(srcheight*cosine); 
  float Point2x=(srcwidth*cosine-srcheight*sine); 
  float Point2y=(srcheight*cosine+srcwidth*sine); 
  float Point3x=(srcwidth*cosine); 
  float Point3y=(srcwidth*sine); 
  
  float minx=min(0,min(Point1x,min(Point2x,Point3x))); 
  float miny=min(0,min(Point1y,min(Point2y,Point3y))); 
  float maxx=max(Point1x,max(Point2x,Point3x)); 
  float maxy=max(Point1y,max(Point2y,Point3y)); 
  
  int DestWidth=(int)ceil(fabs(maxx)-minx); 
  int DestHeight=(int)ceil(fabs(maxy)-miny); 
  
  tempimage.create(DestWidth,DestHeight,1);
  line.init(DestWidth);
  
  for(int i=0;i<DestWidth;i++){ //A white line of length=DestWidth
	line.pixels[i]=1;
  }
  
  for(int y=0;y<DestHeight;y++){ //Fill the Destination image with white, else clipmatra wont work
	tempimage.put_line(0,y,DestWidth,&line,0);
  }
  line.init(DestWidth);
  
  
  
  for(int y=0;y<DestHeight;y++) //Start filling the destination image pixels with corresponding source image pixels
  { 
	for(int x=0;x<DestWidth;x++) 
	{ 
	  int Srcx=(int)((x+minx)*cosine+(y+miny)*sine); 
	  int Srcy=(int)((y+miny)*cosine-(x+minx)*sine); 
	  if(Srcx>=0&&Srcx<srcwidth&&Srcy>=0&& 
		 Srcy<srcheight) 
	  { 
		line.pixels[x]= 
		  page_image.pixel(Srcx,Srcy); 
	  } 
	} 
	tempimage.put_line(0,y,DestWidth,&line,0);	
  } 
  
  //tempimage.write("tempimage.tif");
  page_image=tempimage;//Copy deskewed image to global page image, so it can be worked on further
	tempimage.destroy(); 
  //page_image.write("page_image.tif");
  
}