/*! * pixDisplayWriteFormat() * * Input: pix (1, 2, 4, 8, 16, 32 bpp) * reduction (-1 to reset/erase; 0 to disable; * otherwise this is a reduction factor) * format (IFF_PNG or IFF_JFIF_JPEG) * Return: 0 if OK; 1 on error * * Notes: * (1) This writes files if reduction > 0. These can be displayed using * pixDisplayMultiple("/tmp/junk_write_display*"); * (2) All previously written files can be erased by calling with * reduction < 0; the value of pixs is ignored. * (3) If reduction > 1 and depth == 1, this does a scale-to-gray * reduction. * (4) This function uses a static internal variable to number * output files written by a single process. Behavior * with a shared library may be unpredictable. * (5) Output file format is as follows: * format == IFF_JFIF_JPEG: * png if d < 8 or d == 16 or if the output pix * has a colormap. Otherwise, output is jpg. * format == IFF_PNG: * png (lossless) on all images. * (6) For 16 bpp, the choice of full dynamic range with log scale * is the best for displaying these images. Alternative outputs are * pix8 = pixMaxDynamicRange(pixt, L_LINEAR_SCALE); * pix8 = pixConvert16To8(pixt, 0); // low order byte * pix8 = pixConvert16To8(pixt, 1); // high order byte */ l_int32 pixDisplayWriteFormat(PIX *pixs, l_int32 reduction, l_int32 format) { char buffer[L_BUF_SIZE]; l_float32 scale; PIX *pixt, *pix8; static l_int32 index = 0; /* caution: not .so or thread safe */ PROCNAME("pixDisplayWriteFormat"); if (reduction == 0) return 0; if (reduction < 0) { index = 0; /* reset; this will cause erasure at next call to write */ return 0; } if (format != IFF_JFIF_JPEG && format != IFF_PNG) return ERROR_INT("invalid format", procName, 1); if (!pixs) return ERROR_INT("pixs not defined", procName, 1); if (index == 0) { snprintf(buffer, L_BUF_SIZE, "rm -f /tmp/junk_write_display.*.png /tmp/junk_write_display.*.jpg"); system(buffer); } index++; if (reduction == 1) pixt = pixClone(pixs); else { scale = 1. / (l_float32)reduction; if (pixGetDepth(pixs) == 1) pixt = pixScaleToGray(pixs, scale); else pixt = pixScale(pixs, scale, scale); } if (pixGetDepth(pixt) == 16) { pix8 = pixMaxDynamicRange(pixt, L_LOG_SCALE); snprintf(buffer, L_BUF_SIZE, "/tmp/junk_write_display.%03d.png", index); pixWrite(buffer, pix8, IFF_PNG); pixDestroy(&pix8); } else if (pixGetDepth(pixt) < 8 || pixGetColormap(pixt) || format == IFF_PNG) { snprintf(buffer, L_BUF_SIZE, "/tmp/junk_write_display.%03d.png", index); pixWrite(buffer, pixt, IFF_PNG); } else { snprintf(buffer, L_BUF_SIZE, "/tmp/junk_write_display.%03d.jpg", index); pixWrite(buffer, pixt, format); } pixDestroy(&pixt); return 0; }
main(int argc, char **argv) { char *filein, *fileout; l_int32 d; l_float32 scalex, scaley; PIX *pixs, *pixd; static char mainName[] = "scaletest1"; if (argc != 5) return ERROR_INT(" Syntax: scaletest1 filein scalex scaley fileout", mainName, 1); filein = argv[1]; scalex = atof(argv[2]); scaley = atof(argv[3]); fileout = argv[4]; if ((pixs = pixRead(filein)) == NULL) return ERROR_INT("pixs not made", mainName, 1); /* choose type of scaling operation */ #if 1 pixd = pixScale(pixs, scalex, scaley); #elif 0 pixd = pixScaleLI(pixs, scalex, scaley); #elif 0 pixd = pixScaleSmooth(pixs, scalex, scaley); #elif 0 pixd = pixScaleAreaMap(pixs, scalex, scaley); #elif 0 pixd = pixScaleBySampling(pixs, scalex, scaley); #else pixd = pixScaleToGray(pixs, scalex); #endif d = pixGetDepth(pixd); #if 1 if (d <= 8) pixWrite(fileout, pixd, IFF_PNG); else pixWrite(fileout, pixd, IFF_JFIF_JPEG); #else pixWrite(fileout, pixd, IFF_PNG); #endif pixDestroy(&pixs); pixDestroy(&pixd); return 0; }
/*! * pixSaveTiledOutline() * * Input: pixs (1, 2, 4, 8, 32 bpp) * pixa (the pix are accumulated here) * scalefactor (0.0 to disable; otherwise this is a scale factor) * newrow (0 if placed on the same row as previous; 1 otherwise) * space (horizontal and vertical spacing, in pixels) * linewidth (width of added outline for image; 0 for no outline) * dp (depth of pixa; 8 or 32 bpp; only used on first call) * Return: 0 if OK, 1 on error. * * Notes: * (1) Before calling this function for the first time, use * pixaCreate() to make the @pixa that will accumulate the pix. * This is passed in each time pixSaveTiled() is called. * (2) @scalefactor scales the input image. After scaling and * possible depth conversion, the image is saved in the input * pixa, along with a box that specifies the location to * place it when tiled later. Disable saving the pix by * setting @scalefactor == 0.0. * (3) @newrow and @space specify the location of the new pix * with respect to the last one(s) that were entered. * (4) @dp specifies the depth at which all pix are saved. It can * be only 8 or 32 bpp. Any colormap is removed. This is only * used at the first invocation. * (5) This function uses two variables from call to call. * If they were static, the function would not be .so or thread * safe, and furthermore, there would be interference with two or * more pixa accumulating images at a time. Consequently, * we use the first pix in the pixa to store and obtain both * the depth and the current position of the bottom (one pixel * below the lowest image raster line when laid out using * the boxa). The bottom variable is stored in the input format * field, which is the only field available for storing an int. */ l_int32 pixSaveTiledOutline(PIX *pixs, PIXA *pixa, l_float32 scalefactor, l_int32 newrow, l_int32 space, l_int32 linewidth, l_int32 dp) { l_int32 n, top, left, bx, by, bw, w, h, depth, bottom; BOX *box; PIX *pix1, *pix2, *pix3, *pix4; PROCNAME("pixSaveTiledOutline"); if (scalefactor == 0.0) return 0; if (!pixs) return ERROR_INT("pixs not defined", procName, 1); if (!pixa) return ERROR_INT("pixa not defined", procName, 1); n = pixaGetCount(pixa); if (n == 0) { bottom = 0; if (dp != 8 && dp != 32) { L_WARNING("dp not 8 or 32 bpp; using 32\n", procName); depth = 32; } else { depth = dp; } } else { /* extract the depth and bottom params from the first pix */ pix1 = pixaGetPix(pixa, 0, L_CLONE); depth = pixGetDepth(pix1); bottom = pixGetInputFormat(pix1); /* not typical usage! */ pixDestroy(&pix1); } /* Remove colormap if it exists; otherwise a copy. This * guarantees that pix4 is not a clone of pixs. */ pix1 = pixRemoveColormapGeneral(pixs, REMOVE_CMAP_BASED_ON_SRC, L_COPY); /* Scale and convert to output depth */ if (scalefactor == 1.0) { pix2 = pixClone(pix1); } else if (scalefactor > 1.0) { pix2 = pixScale(pix1, scalefactor, scalefactor); } else if (scalefactor < 1.0) { if (pixGetDepth(pix1) == 1) pix2 = pixScaleToGray(pix1, scalefactor); else pix2 = pixScale(pix1, scalefactor, scalefactor); } pixDestroy(&pix1); if (depth == 8) pix3 = pixConvertTo8(pix2, 0); else pix3 = pixConvertTo32(pix2); pixDestroy(&pix2); /* Add black outline */ if (linewidth > 0) pix4 = pixAddBorder(pix3, linewidth, 0); else pix4 = pixClone(pix3); pixDestroy(&pix3); /* Find position of current pix (UL corner plus size) */ if (n == 0) { top = 0; left = 0; } else if (newrow == 1) { top = bottom + space; left = 0; } else if (n > 0) { pixaGetBoxGeometry(pixa, n - 1, &bx, &by, &bw, NULL); top = by; left = bx + bw + space; } pixGetDimensions(pix4, &w, &h, NULL); bottom = L_MAX(bottom, top + h); box = boxCreate(left, top, w, h); pixaAddPix(pixa, pix4, L_INSERT); pixaAddBox(pixa, box, L_INSERT); /* Save the new bottom value */ pix1 = pixaGetPix(pixa, 0, L_CLONE); pixSetInputFormat(pix1, bottom); /* not typical usage! */ pixDestroy(&pix1); return 0; }
/*! * \brief pixDisplayWriteFormat() * * \param[in] pix 1, 2, 4, 8, 16, 32 bpp * \param[in] reduction -1 to erase and reset; 0 to disable; * otherwise this is a reduction factor * \param[in] format IFF_DEFAULT or IFF_PNG * \return 0 if OK; 1 on error * * <pre> * Notes: * (1) This writes files with pathnames "/tmp/lept/display/file.*" * if reduction \> 0. These can be collected into a pdf using * pixDisplayMultiple(); * (2) Before writing a set of files, call * pixDisplayWrite(NULL, -1); * This erases any previously written files in that directory. * (3) If reduction \> 1 and depth == 1, this does a scale-to-gray * reduction. * (4) This function uses a static internal variable to number * output files written by a single process. Behavior * with a shared library may be unpredictable. * (5) Output file format is as follows: * format == IFF_DEFAULT: * png if d \< 8 or d == 16 or if the output pix * has a colormap. Otherwise, output is jpg. * format == IFF_PNG: * png (lossless) on all images. * (6) For 16 bpp, the choice of full dynamic range with log scale * is the best for displaying these images. Alternative outputs are * pix8 = pixMaxDynamicRange(pixt, L_LINEAR_SCALE); * pix8 = pixConvert16To8(pixt, 0); // low order byte * pix8 = pixConvert16To8(pixt, 1); // high order byte * </pre> */ l_int32 pixDisplayWriteFormat(PIX *pixs, l_int32 reduction, l_int32 format) { char buf[L_BUF_SIZE]; char *fname; l_float32 scale; PIX *pix1, *pix2; static l_int32 index = 0; /* caution: not .so or thread safe */ PROCNAME("pixDisplayWriteFormat"); if (reduction == 0) return 0; if (reduction < 0) { /* initialize */ lept_rmdir("lept/display"); index = 0; return 0; } if (!pixs) return ERROR_INT("pixs not defined", procName, 1); if (format != IFF_DEFAULT && format != IFF_PNG) { L_INFO("invalid format; using default\n", procName); format = IFF_DEFAULT; } if (index == 0) lept_mkdir("lept/display"); index++; if (reduction == 1) { pix1 = pixClone(pixs); } else { scale = 1. / (l_float32)reduction; if (pixGetDepth(pixs) == 1) pix1 = pixScaleToGray(pixs, scale); else pix1 = pixScale(pixs, scale, scale); } if (pixGetDepth(pix1) == 16) { pix2 = pixMaxDynamicRange(pix1, L_LOG_SCALE); snprintf(buf, L_BUF_SIZE, "file.%03d.png", index); fname = genPathname("/tmp/lept/display", buf); pixWrite(fname, pix2, IFF_PNG); pixDestroy(&pix2); } else if (pixGetDepth(pix1) < 8 || pixGetColormap(pix1) || format == IFF_PNG) { snprintf(buf, L_BUF_SIZE, "file.%03d.png", index); fname = genPathname("/tmp/lept/display", buf); pixWrite(fname, pix1, IFF_PNG); } else { snprintf(buf, L_BUF_SIZE, "file.%03d.jpg", index); fname = genPathname("/tmp/lept/display", buf); pixWrite(fname, pix1, format); } LEPT_FREE(fname); pixDestroy(&pix1); return 0; }
/*! * pixSaveTiledOutline() * * Input: pixs (1, 2, 4, 8, 32 bpp) * pixa (the pix are accumulated here) * reduction (0 to disable; otherwise this is a reduction factor) * newrow (0 if placed on the same row as previous; 1 otherwise) * space (horizontal and vertical spacing, in pixels) * linewidth (width of added outline for image; 0 for no outline) * dp (depth of pixa; 8 or 32 bpp; only used on first call) * Return: 0 if OK, 1 on error. * * Notes: * (1) Before calling this function for the first time, use * pixaCreate() to make the @pixa that will accumulate the pix. * This is passed in each time pixSaveTiled() is called. * (2) @reduction is the integer reduction factor for the input * image. After reduction and possible depth conversion, * the image is saved in the input pixa, along with a box * that specifies the location to place it when tiled later. * Disable saving the pix by setting reduction == 0. * (3) @newrow and @space specify the location of the new pix * with respect to the last one(s) that were entered. * (4) @dp specifies the depth at which all pix are saved. It can * be only 8 or 32 bpp. Any colormap is removed. This is only * used at the first invocation. * (5) This function uses two variables from call to call. * If they were static, the function would not be .so or thread * safe, and furthermore, there would be interference with two or * more pixa accumulating images at a time. Consequently, * we use the first pix in the pixa to store and obtain both * the depth and the current position of the bottom (one pixel * below the lowest image raster line when laid out using * the boxa). The bottom variable is stored in the input format * field, which is the only field available for storing an int. */ l_int32 pixSaveTiledOutline(PIX *pixs, PIXA *pixa, l_int32 reduction, l_int32 newrow, l_int32 space, l_int32 linewidth, l_int32 dp) { l_int32 n, top, left, bx, by, bw, w, h, depth, bottom; l_float32 scale; BOX *box; PIX *pix, *pixt1, *pixt2, *pixt3; PROCNAME("pixSaveTiledOutline"); if (reduction == 0) return 0; if (!pixs) return ERROR_INT("pixs not defined", procName, 1); if (!pixa) return ERROR_INT("pixa not defined", procName, 1); n = pixaGetCount(pixa); if (n == 0) { bottom = 0; if (dp != 8 && dp != 32) { L_WARNING("dp not 8 or 32 bpp; using 32", procName); depth = 32; } else depth = dp; } else { /* extract the depth and bottom params from the first pix */ pix = pixaGetPix(pixa, 0, L_CLONE); depth = pixGetDepth(pix); bottom = pixGetInputFormat(pix); /* not typical usage! */ pixDestroy(&pix); } /* Scale and convert to output depth */ if (reduction == 1) pixt1 = pixClone(pixs); else { scale = 1. / (l_float32)reduction; if (pixGetDepth(pixs) == 1) pixt1 = pixScaleToGray(pixs, scale); else pixt1 = pixScale(pixs, scale, scale); } if (depth == 8) pixt2 = pixConvertTo8(pixt1, 0); else pixt2 = pixConvertTo32(pixt1); pixDestroy(&pixt1); /* Add black outline */ if (linewidth > 0) pixt3 = pixAddBorder(pixt2, linewidth, 0); else pixt3 = pixClone(pixt2); pixDestroy(&pixt2); /* Find position of current pix (UL corner plus size) */ if (n == 0) { top = 0; left = 0; } else if (newrow == 1) { top = bottom + space; left = 0; } else if (n > 0) { pixaGetBoxGeometry(pixa, n - 1, &bx, &by, &bw, NULL); top = by; left = bx + bw + space; } pixGetDimensions(pixt3, &w, &h, NULL); bottom = L_MAX(bottom, top + h); box = boxCreate(left, top, w, h); pixaAddPix(pixa, pixt3, L_INSERT); pixaAddBox(pixa, box, L_INSERT); /* Save the new bottom value */ pix = pixaGetPix(pixa, 0, L_CLONE); pixSetInputFormat(pix, bottom); /* not typical usage! */ pixDestroy(&pix); return 0; }
/*! * pixaDisplayTiledAndScaled() * * Input: pixa * outdepth (output depth: 1, 8 or 32 bpp) * tilewidth (each pix is scaled to this width) * ncols (number of tiles in each row) * background (0 for white, 1 for black; this is the color * of the spacing between the images) * spacing (between images, and on outside) * border (width of additional black border on each image; * use 0 for no border) * Return: pix of tiled images, or null on error * * Notes: * (1) This can be used to tile a number of renderings of * an image that are at different scales and depths. * (2) Each image, after scaling and optionally adding the * black border, has width 'tilewidth'. Thus, the border does * not affect the spacing between the image tiles. The * maximum allowed border width is tilewidth / 5. */ PIX * pixaDisplayTiledAndScaled(PIXA *pixa, l_int32 outdepth, l_int32 tilewidth, l_int32 ncols, l_int32 background, l_int32 spacing, l_int32 border) { l_int32 x, y, w, h, wd, hd, d; l_int32 i, n, nrows, maxht, ninrow, irow, bordval; l_int32 *rowht; l_float32 scalefact; PIX *pix, *pixn, *pixt, *pixb, *pixd; PIXA *pixan; PROCNAME("pixaDisplayTiledAndScaled"); if (!pixa) return (PIX *)ERROR_PTR("pixa not defined", procName, NULL); if (outdepth != 1 && outdepth != 8 && outdepth != 32) return (PIX *)ERROR_PTR("outdepth not in {1, 8, 32}", procName, NULL); if (border < 0 || border > tilewidth / 5) border = 0; if ((n = pixaGetCount(pixa)) == 0) return (PIX *)ERROR_PTR("no components", procName, NULL); /* Normalize scale and depth for each pix; optionally add border */ pixan = pixaCreate(n); bordval = (outdepth == 1) ? 1 : 0; for (i = 0; i < n; i++) { if ((pix = pixaGetPix(pixa, i, L_CLONE)) == NULL) continue; pixGetDimensions(pix, &w, &h, &d); scalefact = (l_float32)(tilewidth - 2 * border) / (l_float32)w; if (d == 1 && outdepth > 1 && scalefact < 1.0) pixt = pixScaleToGray(pix, scalefact); else pixt = pixScale(pix, scalefact, scalefact); if (outdepth == 1) pixn = pixConvertTo1(pixt, 128); else if (outdepth == 8) pixn = pixConvertTo8(pixt, FALSE); else /* outdepth == 32 */ pixn = pixConvertTo32(pixt); pixDestroy(&pixt); if (border) pixb = pixAddBorder(pixn, border, bordval); else pixb = pixClone(pixn); pixaAddPix(pixan, pixb, L_INSERT); pixDestroy(&pix); pixDestroy(&pixn); } if ((n = pixaGetCount(pixan)) == 0) { /* should not have changed! */ pixaDestroy(&pixan); return (PIX *)ERROR_PTR("no components", procName, NULL); } /* Determine the size of each row and of pixd */ wd = tilewidth * ncols + spacing * (ncols + 1); nrows = (n + ncols - 1) / ncols; if ((rowht = (l_int32 *)CALLOC(nrows, sizeof(l_int32))) == NULL) return (PIX *)ERROR_PTR("rowht array not made", procName, NULL); maxht = 0; ninrow = 0; irow = 0; for (i = 0; i < n; i++) { pix = pixaGetPix(pixan, i, L_CLONE); ninrow++; pixGetDimensions(pix, &w, &h, NULL); maxht = L_MAX(h, maxht); if (ninrow == ncols) { rowht[irow] = maxht; maxht = ninrow = 0; /* reset */ irow++; } pixDestroy(&pix); } if (ninrow > 0) { /* last fencepost */ rowht[irow] = maxht; irow++; /* total number of rows */ } nrows = irow; hd = spacing * (nrows + 1); for (i = 0; i < nrows; i++) hd += rowht[i]; pixd = pixCreate(wd, hd, outdepth); if ((background == 1 && outdepth == 1) || (background == 0 && outdepth != 1)) pixSetAll(pixd); /* Now blit images to pixd */ x = y = spacing; irow = 0; for (i = 0; i < n; i++) { pix = pixaGetPix(pixan, i, L_CLONE); pixGetDimensions(pix, &w, &h, NULL); if (i && ((i % ncols) == 0)) { /* start new row */ x = spacing; y += spacing + rowht[irow]; irow++; } pixRasterop(pixd, x, y, w, h, PIX_SRC, pix, 0, 0); x += tilewidth + spacing; pixDestroy(&pix); } pixaDestroy(&pixan); FREE(rowht); return pixd; }
int main(int argc, char **argv) { char bufname[256]; l_int32 i, w, h; l_float32 *mat1, *mat2, *mat3, *mat1i, *mat2i, *mat3i, *matdinv; l_float32 matd[9], matdi[9]; BOXA *boxa, *boxa2; PIX *pix, *pixs, *pixb, *pixg, *pixc, *pixcs; PIX *pixd, *pix1, *pix2, *pix3; PIXA *pixa; PTA *ptas, *ptad; L_REGPARAMS *rp; if (regTestSetup(argc, argv, &rp)) return 1; pix = pixRead("feyn.tif"); pixs = pixScale(pix, 0.22, 0.22); pixDestroy(&pix); #if ALL /* Test invertability of sequential. */ fprintf(stderr, "Test invertability of sequential\n"); pixa = pixaCreate(0); for (i = 0; i < 3; i++) { pixb = pixAddBorder(pixs, ADDED_BORDER_PIXELS, 0); MakePtas(i, &ptas, &ptad); pix1 = pixAffineSequential(pixb, ptad, ptas, 0, 0); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 0,3,6 */ pixaAddPix(pixa, pix1, L_INSERT); pix2 = pixAffineSequential(pix1, ptas, ptad, 0, 0); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 1,4,7 */ pixaAddPix(pixa, pix2, L_INSERT); pixd = pixRemoveBorder(pix2, ADDED_BORDER_PIXELS); pixXor(pixd, pixd, pixs); regTestWritePixAndCheck(rp, pixd, IFF_PNG); /* 2,5,8 */ pixaAddPix(pixa, pixd, L_INSERT); pixDestroy(&pixb); ptaDestroy(&ptas); ptaDestroy(&ptad); } pix1 = pixaDisplayTiledInColumns(pixa, 3, 1.0, 20, 3); pix2 = pixScaleToGray(pix1, 0.2); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 9 */ pixDisplayWithTitle(pix2, 0, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixaDestroy(&pixa); #endif #if ALL /* Test invertability of sampling */ fprintf(stderr, "Test invertability of sampling\n"); pixa = pixaCreate(0); for (i = 0; i < 3; i++) { pixb = pixAddBorder(pixs, ADDED_BORDER_PIXELS, 0); MakePtas(i, &ptas, &ptad); pix1 = pixAffineSampledPta(pixb, ptad, ptas, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 10,13,16 */ pixaAddPix(pixa, pix1, L_INSERT); pix2 = pixAffineSampledPta(pix1, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 11,14,17 */ pixaAddPix(pixa, pix2, L_INSERT); pixd = pixRemoveBorder(pix2, ADDED_BORDER_PIXELS); pixXor(pixd, pixd, pixs); regTestWritePixAndCheck(rp, pixd, IFF_PNG); /* 12,15,18 */ pixaAddPix(pixa, pixd, L_INSERT); pixDestroy(&pixb); ptaDestroy(&ptas); ptaDestroy(&ptad); } pix1 = pixaDisplayTiledInColumns(pixa, 3, 1.0, 20, 3); pix2 = pixScaleToGray(pix1, 0.2); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 19 */ pixDisplayWithTitle(pix2, 200, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixs); pixaDestroy(&pixa); #endif #if ALL /* Test invertability of interpolation on grayscale */ fprintf(stderr, "Test invertability of grayscale interpolation\n"); pix = pixRead("feyn.tif"); pixg = pixScaleToGray3(pix); pixDestroy(&pix); pixa = pixaCreate(0); for (i = 0; i < 3; i++) { pixb = pixAddBorder(pixg, ADDED_BORDER_PIXELS / 3, 255); MakePtas(i, &ptas, &ptad); pix1 = pixAffinePta(pixb, ptad, ptas, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix1, IFF_JFIF_JPEG); /* 20,23,26 */ pixaAddPix(pixa, pix1, L_INSERT); pix2 = pixAffinePta(pix1, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix2, IFF_JFIF_JPEG); /* 21,24,27 */ pixaAddPix(pixa, pix2, L_INSERT); pixd = pixRemoveBorder(pix2, ADDED_BORDER_PIXELS / 3); pixXor(pixd, pixd, pixg); pixInvert(pixd, pixd); regTestWritePixAndCheck(rp, pixd, IFF_JFIF_JPEG); /* 22,25,28 */ pixaAddPix(pixa, pixd, L_INSERT); pixDestroy(&pixb); ptaDestroy(&ptas); ptaDestroy(&ptad); } pix1 = pixaDisplayTiledInColumns(pixa, 3, 1.0, 20, 3); pix2 = pixScale(pix1, 0.2, 0.2); regTestWritePixAndCheck(rp, pix2, IFF_JFIF_JPEG); /* 29 */ pixDisplayWithTitle(pix2, 400, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixg); pixaDestroy(&pixa); #endif #if ALL /* Test invertability of interpolation on color */ fprintf(stderr, "Test invertability of color interpolation\n"); pixa = pixaCreate(0); pixc = pixRead("test24.jpg"); pixcs = pixScale(pixc, 0.3, 0.3); for (i = 0; i < 3; i++) { pixb = pixAddBorder(pixcs, ADDED_BORDER_PIXELS / 4, 0xffffff00); MakePtas(i, &ptas, &ptad); pix1 = pixAffinePta(pixb, ptad, ptas, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix1, IFF_JFIF_JPEG); /* 30,33,36 */ pixaAddPix(pixa, pix1, L_INSERT); pix2 = pixAffinePta(pix1, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix2, IFF_JFIF_JPEG); /* 31,34,37 */ pixaAddPix(pixa, pix2, L_INSERT); pixd = pixRemoveBorder(pix2, ADDED_BORDER_PIXELS / 4); pixXor(pixd, pixd, pixcs); pixInvert(pixd, pixd); regTestWritePixAndCheck(rp, pixd, IFF_JFIF_JPEG); /* 32,35,38 */ pixaAddPix(pixa, pixd, L_INSERT); pixDestroy(&pixb); ptaDestroy(&ptas); ptaDestroy(&ptad); } pix1 = pixaDisplayTiledInColumns(pixa, 3, 1.0, 20, 3); pix2 = pixScale(pix1, 0.25, 0.25); regTestWritePixAndCheck(rp, pix2, IFF_JFIF_JPEG); /* 39 */ pixDisplayWithTitle(pix2, 600, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixc); pixaDestroy(&pixa); #endif #if ALL /* Comparison between sequential and sampling */ fprintf(stderr, "Compare sequential with sampling\n"); pix = pixRead("feyn.tif"); pixs = pixScale(pix, 0.22, 0.22); pixDestroy(&pix); MakePtas(3, &ptas, &ptad); pixa = pixaCreate(0); /* Use sequential transforms */ pix1 = pixAffineSequential(pixs, ptas, ptad, ADDED_BORDER_PIXELS, ADDED_BORDER_PIXELS); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 40 */ pixaAddPix(pixa, pix1, L_INSERT); /* Use sampled transform */ pix2 = pixAffineSampledPta(pixs, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 41 */ pixaAddPix(pixa, pix2, L_COPY); /* Compare the results */ pixXor(pix2, pix2, pix1); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 42 */ pixaAddPix(pixa, pix2, L_INSERT); pix1 = pixaDisplayTiledInColumns(pixa, 3, 1.0, 20, 3); pix2 = pixScale(pix1, 0.5, 0.5); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 43 */ pixDisplayWithTitle(pix2, 800, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixs); pixaDestroy(&pixa); ptaDestroy(&ptas); ptaDestroy(&ptad); #endif #if ALL /* Test with large distortion */ fprintf(stderr, "Test with large distortion\n"); MakePtas(4, &ptas, &ptad); pixa = pixaCreate(0); pix = pixRead("feyn.tif"); pixg = pixScaleToGray6(pix); pixDestroy(&pix); pix1 = pixAffineSequential(pixg, ptas, ptad, 0, 0); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 44 */ pixaAddPix(pixa, pix1, L_COPY); pix2 = pixAffineSampledPta(pixg, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 45 */ pixaAddPix(pixa, pix2, L_COPY); pix3 = pixAffinePta(pixg, ptas, ptad, L_BRING_IN_WHITE); regTestWritePixAndCheck(rp, pix3, IFF_PNG); /* 46 */ pixaAddPix(pixa, pix3, L_INSERT); pixXor(pix1, pix1, pix2); pixInvert(pix1, pix1); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 47 */ pixaAddPix(pixa, pix1, L_INSERT); pixXor(pix2, pix2, pix3); pixInvert(pix2, pix2); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 48 */ pixaAddPix(pixa, pix2, L_INSERT); pix1 = pixaDisplayTiledInColumns(pixa, 5, 1.0, 20, 3); pix2 = pixScale(pix1, 0.8, 0.8); regTestWritePixAndCheck(rp, pix2, IFF_PNG); /* 49 */ pixDisplayWithTitle(pix2, 1000, 100, NULL, rp->display); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixg); pixaDestroy(&pixa); ptaDestroy(&ptas); ptaDestroy(&ptad); #endif #if ALL /* Set up pix and boxa */ fprintf(stderr, "Test affine transforms and inverses on pix and boxa\n"); pixa = pixaCreate(0); pix = pixRead("lucasta.1.300.tif"); pixTranslate(pix, pix, 70, 0, L_BRING_IN_WHITE); pix1 = pixCloseBrick(NULL, pix, 14, 5); pixOpenBrick(pix1, pix1, 1, 2); boxa = pixConnComp(pix1, NULL, 8); pixs = pixConvertTo32(pix); pixGetDimensions(pixs, &w, &h, NULL); pixc = pixCopy(NULL, pixs); RenderHashedBoxa(pixc, boxa, 113); regTestWritePixAndCheck(rp, pixc, IFF_PNG); /* 50 */ pixaAddPix(pixa, pixc, L_INSERT); pixDestroy(&pix); pixDestroy(&pix1); /* Set up an affine transform in matd, and apply it to boxa */ mat1 = createMatrix2dTranslate(SHIFTX, SHIFTY); mat2 = createMatrix2dScale(SCALEX, SCALEY); mat3 = createMatrix2dRotate(w / 2, h / 2, ROTATION); l_productMat3(mat3, mat2, mat1, matd, 3); boxa2 = boxaAffineTransform(boxa, matd); /* Set up the inverse transform --> matdi */ mat1i = createMatrix2dTranslate(-SHIFTX, -SHIFTY); mat2i = createMatrix2dScale(1.0/ SCALEX, 1.0 / SCALEY); mat3i = createMatrix2dRotate(w / 2, h / 2, -ROTATION); l_productMat3(mat1i, mat2i, mat3i, matdi, 3); /* Invert the original affine transform --> matdinv */ affineInvertXform(matd, &matdinv); if (rp->display) { fprintf(stderr, " Affine transform, applied to boxa\n"); for (i = 0; i < 9; i++) { if (i && (i % 3 == 0)) fprintf(stderr, "\n"); fprintf(stderr, " %7.3f ", matd[i]); } fprintf(stderr, "\n Inverse transform, by composing inverse parts"); for (i = 0; i < 9; i++) { if (i % 3 == 0) fprintf(stderr, "\n"); fprintf(stderr, " %7.3f ", matdi[i]); } fprintf(stderr, "\n Inverse transform, by inverting affine xform"); for (i = 0; i < 6; i++) { if (i % 3 == 0) fprintf(stderr, "\n"); fprintf(stderr, " %7.3f ", matdinv[i]); } fprintf(stderr, "\n"); } /* Apply the inverted affine transform --> pixs */ pixd = pixAffine(pixs, matdinv, L_BRING_IN_WHITE); RenderHashedBoxa(pixd, boxa2, 513); regTestWritePixAndCheck(rp, pixd, IFF_PNG); /* 51 */ pixaAddPix(pixa, pixd, L_INSERT); pix1 = pixaDisplayTiledInColumns(pixa, 2, 1.0, 30, 2); regTestWritePixAndCheck(rp, pix1, IFF_PNG); /* 52 */ pixDisplayWithTitle(pix1, 1200, 100, NULL, rp->display); pixDestroy(&pix1); pixaDestroy(&pixa); pixDestroy(&pixs); boxaDestroy(&boxa); boxaDestroy(&boxa2); lept_free(mat1); lept_free(mat2); lept_free(mat3); lept_free(mat1i); lept_free(mat2i); lept_free(mat3i); lept_free(matdinv); #endif return regTestCleanup(rp); }
main(int argc, char **argv) { l_int32 h; l_float32 scalefactor; BOX *box; BOXA *boxa1, *boxa2; BOXAA *baa; PIX *pix1, *pix2, *pix3, *pix4, *pix5, *pix6, *pix7, *pix8, *pix9; L_REGPARAMS *rp; if (regTestSetup(argc, argv, &rp)) return 1; lept_rmdir("segtest"); lept_mkdir("segtest"); baa = boxaaCreate(5); /* Image region input. */ pix1 = pixRead("wet-day.jpg"); pix2 = pixScaleToSize(pix1, WIDTH, 0); pixWrite("/tmp/segtest/0.jpg", pix2, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/0.jpg"); /* 0 */ box = boxCreate(105, 161, 620, 872); /* image region */ boxa1 = boxaCreate(1); boxaAddBox(boxa1, box, L_INSERT); boxaaAddBoxa(baa, boxa1, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); /* Compute image region at w = 2 * WIDTH */ pix1 = pixRead("candelabrum-11.jpg"); pix2 = pixScaleToSize(pix1, WIDTH, 0); pix3 = pixConvertTo1(pix2, 100); pix4 = pixExpandBinaryPower2(pix3, 2); /* w = 2 * WIDTH */ pix5 = pixGenHalftoneMask(pix4, NULL, NULL, 1); pix6 = pixMorphSequence(pix5, "c20.1 + c1.20", 0); pix7 = pixMaskConnComp(pix6, 8, &boxa1); pix8 = pixReduceBinary2(pix7, NULL); /* back to w = WIDTH */ pix9 = pixBackgroundNormSimple(pix2, pix8, NULL); pixWrite("/tmp/segtest/1.jpg", pix9, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/1.jpg"); /* 1 */ boxa2 = boxaTransform(boxa1, 0, 0, 0.5, 0.5); /* back to w = WIDTH */ boxaaAddBoxa(baa, boxa2, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pix3); pixDestroy(&pix4); pixDestroy(&pix5); pixDestroy(&pix6); pixDestroy(&pix7); pixDestroy(&pix8); pixDestroy(&pix9); boxaDestroy(&boxa1); /* Use mask to find image region */ pix1 = pixRead("lion-page.00016.jpg"); pix2 = pixScaleToSize(pix1, WIDTH, 0); pixWrite("/tmp/segtest/2.jpg", pix2, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/2.jpg"); /* 2 */ pix3 = pixRead("lion-mask.00016.tif"); pix4 = pixScaleToSize(pix3, WIDTH, 0); boxa1 = pixConnComp(pix4, NULL, 8); boxaaAddBoxa(baa, boxa1, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pix3); pixDestroy(&pix4); /* Compute image region at full res */ pix1 = pixRead("rabi.png"); scalefactor = (l_float32)WIDTH / (l_float32)pixGetWidth(pix1); pix2 = pixScaleToGray(pix1, scalefactor); pixWrite("/tmp/segtest/3.jpg", pix2, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/3.jpg"); /* 3 */ pix3 = pixGenHalftoneMask(pix1, NULL, NULL, 0); pix4 = pixMorphSequence(pix3, "c20.1 + c1.20", 0); boxa1 = pixConnComp(pix4, NULL, 8); boxa2 = boxaTransform(boxa1, 0, 0, scalefactor, scalefactor); boxaaAddBoxa(baa, boxa2, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pix3); pixDestroy(&pix4); boxaDestroy(&boxa1); /* Page with no image regions */ pix1 = pixRead("lucasta-47.jpg"); pix2 = pixScaleToSize(pix1, WIDTH, 0); boxa1 = boxaCreate(1); pixWrite("/tmp/segtest/4.jpg", pix2, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/4.jpg"); /* 4 */ boxaaAddBoxa(baa, boxa1, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); /* Page that is all image */ pix1 = pixRead("map1.jpg"); pix2 = pixScaleToSize(pix1, WIDTH, 0); pixWrite("/tmp/segtest/5.jpg", pix2, IFF_JFIF_JPEG); regTestCheckFile(rp, "/tmp/segtest/5.jpg"); /* 5 */ h = pixGetHeight(pix2); box = boxCreate(0, 0, WIDTH, h); boxa1 = boxaCreate(1); boxaAddBox(boxa1, box, L_INSERT); boxaaAddBoxa(baa, boxa1, L_INSERT); pixDestroy(&pix1); pixDestroy(&pix2); /* Save the boxaa file */ boxaaWrite("/tmp/segtest/seg.baa", baa); regTestCheckFile(rp, "/tmp/segtest/seg.baa"); /* 6 */ /* Do the conversion */ l_pdfSetDateAndVersion(FALSE); convertSegmentedFilesToPdf("/tmp/segtest", ".jpg", 100, L_G4_ENCODE, 140, baa, 75, 0.6, "Segmentation Test", "/tmp/pdfseg.7.pdf"); regTestCheckFile(rp, "/tmp/pdfseg.7.pdf"); /* 7 */ boxaaDestroy(&baa); return regTestCleanup(rp); }
main(int argc, char **argv) { PIX *pixs; l_int32 d; static char mainName[] = "scaletest2"; if (argc != 2) return ERROR_INT(" Syntax: scaletest2 filein", mainName, 1); if ((pixs = pixRead(argv[1])) == NULL) return ERROR_INT("pixs not made", mainName, 1); d = pixGetDepth(pixs); #if 1 /* Integer scale-to-gray functions */ if (d == 1) { PIX *pixd; pixd = pixScaleToGray2(pixs); pixWrite("/tmp/s2g_2x", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray3(pixs); pixWrite("/tmp/s2g_3x", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray4(pixs); pixWrite("/tmp/s2g_4x", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray6(pixs); pixWrite("/tmp/s2g_6x", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray8(pixs); pixWrite("/tmp/s2g_8x", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray16(pixs); pixWrite("/tmp/s2g_16x", pixd, IFF_PNG); pixDestroy(&pixd); } #endif #if 1 /* Various non-integer scale-to-gray, compared with * with different ways of getting similar results */ if (d == 1) { PIX *pixt, *pixd; pixd = pixScaleToGray8(pixs); pixWrite("/tmp/s2g_8.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray(pixs, 0.124); pixWrite("/tmp/s2g_124.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixScaleToGray(pixs, 0.284); pixWrite("/tmp/s2g_284.png", pixd, IFF_PNG); pixDestroy(&pixd); pixt = pixScaleToGray4(pixs); pixd = pixScaleBySampling(pixt, 284./250., 284./250.); pixWrite("/tmp/s2g_284.2.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixt = pixScaleToGray4(pixs); pixd = pixScaleGrayLI(pixt, 284./250., 284./250.); pixWrite("/tmp/s2g_284.3.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixt = pixScaleBinary(pixs, 284./250., 284./250.); pixd = pixScaleToGray4(pixt); pixWrite("/tmp/s2g_284.4.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixt = pixScaleToGray4(pixs); pixd = pixScaleGrayLI(pixt, 0.49, 0.49); pixWrite("/tmp/s2g_42.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixt = pixScaleToGray4(pixs); pixd = pixScaleSmooth(pixt, 0.49, 0.49); pixWrite("/tmp/s2g_4sm.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixt = pixScaleBinary(pixs, .16/.125, .16/.125); pixd = pixScaleToGray8(pixt); pixWrite("/tmp/s2g_16.png", pixd, IFF_PNG); pixDestroy(&pixt); pixDestroy(&pixd); pixd = pixScaleToGray(pixs, .16); pixWrite("/tmp/s2g_16.2.png", pixd, IFF_PNG); pixDestroy(&pixd); } #endif #if 1 /* Antialiased (smoothed) reduction, along with sharpening */ if (d != 1) { PIX *pixt1, *pixt2; startTimer(); pixt1 = pixScaleSmooth(pixs, 0.154, 0.154); fprintf(stderr, "fast scale: %5.3f sec\n", stopTimer()); pixDisplayWithTitle(pixt1, 0, 0, "smooth scaling", DISPLAY); pixWrite("/tmp/smooth1.png", pixt1, IFF_PNG); pixt2 = pixUnsharpMasking(pixt1, 1, 0.3); pixWrite("/tmp/smooth2.png", pixt2, IFF_PNG); pixDisplayWithTitle(pixt2, 200, 0, "sharp scaling", DISPLAY); pixDestroy(&pixt1); pixDestroy(&pixt2); } #endif #if 1 /* Test a large range of scale-to-gray reductions */ if (d == 1) { l_int32 i; l_float32 scale; PIX *pixd; for (i = 2; i < 15; i++) { scale = 1. / (l_float32)i; startTimer(); pixd = pixScaleToGray(pixs, scale); fprintf(stderr, "Time for scale %7.3f: %7.3f sec\n", scale, stopTimer()); pixDisplayWithTitle(pixd, 75 * i, 100, "scaletogray", DISPLAY); pixDestroy(&pixd); } for (i = 8; i < 14; i++) { scale = 1. / (l_float32)(2 * i); startTimer(); pixd = pixScaleToGray(pixs, scale); fprintf(stderr, "Time for scale %7.3f: %7.3f sec\n", scale, stopTimer()); pixDisplayWithTitle(pixd, 100 * i, 600, "scaletogray", DISPLAY); pixDestroy(&pixd); } } #endif #if 1 /* Test the same range of scale-to-gray mipmap reductions */ if (d == 1) { l_int32 i; l_float32 scale; PIX *pixd; for (i = 2; i < 15; i++) { scale = 1. / (l_float32)i; startTimer(); pixd = pixScaleToGrayMipmap(pixs, scale); fprintf(stderr, "Time for scale %7.3f: %7.3f sec\n", scale, stopTimer()); pixDisplayWithTitle(pixd, 75 * i, 100, "scale mipmap", DISPLAY); pixDestroy(&pixd); } for (i = 8; i < 12; i++) { scale = 1. / (l_float32)(2 * i); startTimer(); pixd = pixScaleToGrayMipmap(pixs, scale); fprintf(stderr, "Time for scale %7.3f: %7.3f sec\n", scale, stopTimer()); pixDisplayWithTitle(pixd, 100 * i, 600, "scale mipmap", DISPLAY); pixDestroy(&pixd); } } #endif #if 1 /* Test several methods for antialiased reduction, * along with sharpening */ if (d != 1) { PIX *pixt1, *pixt2, *pixt3, *pixt4, *pixt5, *pixt6, *pixt7; l_float32 SCALING = 0.27; l_int32 SIZE = 7; l_int32 smooth; l_float32 FRACT = 1.0; smooth = SIZE / 2; startTimer(); pixt1 = pixScaleSmooth(pixs, SCALING, SCALING); fprintf(stderr, "fast scale: %5.3f sec\n", stopTimer()); pixDisplayWithTitle(pixt1, 0, 0, "smooth scaling", DISPLAY); pixWrite("/tmp/sm_1.png", pixt1, IFF_PNG); pixt2 = pixUnsharpMasking(pixt1, 1, 0.3); pixDisplayWithTitle(pixt2, 150, 0, "sharpened scaling", DISPLAY); startTimer(); pixt3 = pixBlockconv(pixs, smooth, smooth); pixt4 = pixScaleBySampling(pixt3, SCALING, SCALING); fprintf(stderr, "slow scale: %5.3f sec\n", stopTimer()); pixDisplayWithTitle(pixt4, 200, 200, "sampled scaling", DISPLAY); pixWrite("/tmp/sm_2.png", pixt4, IFF_PNG); startTimer(); pixt5 = pixUnsharpMasking(pixs, smooth, FRACT); pixt6 = pixBlockconv(pixt5, smooth, smooth); pixt7 = pixScaleBySampling(pixt6, SCALING, SCALING); fprintf(stderr, "very slow scale + sharp: %5.3f sec\n", stopTimer()); pixDisplayWithTitle(pixt7, 500, 200, "sampled scaling", DISPLAY); pixWrite("/tmp/sm_3.jpg", pixt7, IFF_JFIF_JPEG); pixDestroy(&pixt1); pixDestroy(&pixt2); pixDestroy(&pixt3); pixDestroy(&pixt4); pixDestroy(&pixt5); pixDestroy(&pixt6); pixDestroy(&pixt7); } #endif #if 1 /* Test the color scaling function, comparing the * special case of scaling factor 2.0 with the * general case. */ if (d == 32) { PIX *pix1, *pix2, *pixd; NUMA *nar, *nag, *nab, *naseq; GPLOT *gplot; startTimer(); pix1 = pixScaleColorLI(pixs, 2.00001, 2.0); fprintf(stderr, " Time with regular LI: %7.3f\n", stopTimer()); pixWrite("/tmp/color1.jpg", pix1, IFF_JFIF_JPEG); startTimer(); pix2 = pixScaleColorLI(pixs, 2.0, 2.0); fprintf(stderr, " Time with 2x LI: %7.3f\n", stopTimer()); pixWrite("/tmp/color2.jpg", pix2, IFF_JFIF_JPEG); pixd = pixAbsDifference(pix1, pix2); pixGetColorHistogram(pixd, 1, &nar, &nag, &nab); naseq = numaMakeSequence(0., 1., 256); gplot = gplotCreate("/tmp/plot_absdiff", GPLOT_X11, "Number vs diff", "diff", "number"); gplotSetScaling(gplot, GPLOT_LOG_SCALE_Y); gplotAddPlot(gplot, naseq, nar, GPLOT_POINTS, "red"); gplotAddPlot(gplot, naseq, nag, GPLOT_POINTS, "green"); gplotAddPlot(gplot, naseq, nab, GPLOT_POINTS, "blue"); gplotMakeOutput(gplot); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixd); numaDestroy(&naseq); numaDestroy(&nar); numaDestroy(&nag); numaDestroy(&nab); gplotDestroy(&gplot); } #endif #if 1 /* Test the gray LI scaling function, comparing the * special cases of scaling factor 2.0 and 4.0 with the * general case */ if (d == 8 || d == 32) { PIX *pixt, *pix0, *pix1, *pix2, *pixd; NUMA *nagray, *naseq; GPLOT *gplot; if (d == 8) pixt = pixClone(pixs); else pixt = pixConvertRGBToGray(pixs, 0.33, 0.34, 0.33); pix0 = pixScaleGrayLI(pixt, 0.5, 0.5); #if 1 startTimer(); pix1 = pixScaleGrayLI(pix0, 2.00001, 2.0); fprintf(stderr, " Time with regular LI 2x: %7.3f\n", stopTimer()); startTimer(); pix2 = pixScaleGrayLI(pix0, 2.0, 2.0); fprintf(stderr, " Time with 2x LI: %7.3f\n", stopTimer()); #else startTimer(); pix1 = pixScaleGrayLI(pix0, 4.00001, 4.0); fprintf(stderr, " Time with regular LI 4x: %7.3f\n", stopTimer()); startTimer(); pix2 = pixScaleGrayLI(pix0, 4.0, 4.0); fprintf(stderr, " Time with 2x LI: %7.3f\n", stopTimer()); #endif pixWrite("/tmp/gray1", pix1, IFF_JFIF_JPEG); pixWrite("/tmp/gray2", pix2, IFF_JFIF_JPEG); pixd = pixAbsDifference(pix1, pix2); nagray = pixGetGrayHistogram(pixd, 1); naseq = numaMakeSequence(0., 1., 256); gplot = gplotCreate("/tmp/g_absdiff", GPLOT_X11, "Number vs diff", "diff", "number"); gplotSetScaling(gplot, GPLOT_LOG_SCALE_Y); gplotAddPlot(gplot, naseq, nagray, GPLOT_POINTS, "gray"); gplotMakeOutput(gplot); pixDestroy(&pixt); pixDestroy(&pix0); pixDestroy(&pix1); pixDestroy(&pix2); pixDestroy(&pixd); numaDestroy(&naseq); numaDestroy(&nagray); gplotDestroy(&gplot); } #endif pixDestroy(&pixs); return 0; }
main(int argc, char **argv) { char *infile; PIX *pixs, *pixg, *pixc, *pixd; static char mainName[] = "morphseq_reg"; if (argc != 1) return ERROR_INT(" Syntax: morphseq_reg", mainName, 1); pixs = pixRead("feyn.tif"); /* 1 bpp */ pixd = pixMorphSequence(pixs, SEQUENCE1, -1); pixDestroy(&pixd); pixd = pixMorphSequence(pixs, SEQUENCE1, DISPLAY_SEPARATION); pixWrite("/tmp/morphseq1.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixMorphCompSequence(pixs, SEQUENCE2, -2); pixDestroy(&pixd); pixd = pixMorphCompSequence(pixs, SEQUENCE2, DISPLAY_SEPARATION); pixWrite("/tmp/morphseq2.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixMorphSequenceDwa(pixs, SEQUENCE2, -3); pixDestroy(&pixd); pixd = pixMorphSequenceDwa(pixs, SEQUENCE2, DISPLAY_SEPARATION); pixWrite("/tmp/morphseq3.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixMorphCompSequenceDwa(pixs, SEQUENCE2, -4); pixDestroy(&pixd); pixd = pixMorphCompSequenceDwa(pixs, SEQUENCE2, DISPLAY_SEPARATION); pixWrite("/tmp/morphseq4.png", pixd, IFF_PNG); pixDestroy(&pixd); /* 8 bpp */ pixg = pixScaleToGray(pixs, 0.25); pixd = pixGrayMorphSequence(pixg, SEQUENCE3, -5, 150); pixDestroy(&pixd); pixd = pixGrayMorphSequence(pixg, SEQUENCE3, DISPLAY_SEPARATION, 150); pixWrite("/tmp/morphseq5.png", pixd, IFF_PNG); pixDestroy(&pixd); pixd = pixGrayMorphSequence(pixg, SEQUENCE4, -6, 300); pixWrite("/tmp/morphseq6.png", pixd, IFF_PNG); pixDestroy(&pixd); /* 32 bpp */ pixc = pixRead("wyom.jpg"); pixd = pixColorMorphSequence(pixc, SEQUENCE5, -7, 150); pixDestroy(&pixd); pixd = pixColorMorphSequence(pixc, SEQUENCE5, DISPLAY_SEPARATION, 450); pixWrite("/tmp/morphseq7.png", pixd, IFF_PNG); pixDestroy(&pixc); pixDestroy(&pixd); /* Syntax error handling */ fprintf(stderr, " ------------ Error messages follow ------------------\n"); pixd = pixMorphSequence(pixs, BAD_SEQUENCE, 50); /* fails; returns null */ pixd = pixGrayMorphSequence(pixg, BAD_SEQUENCE, 50, 0); /* this fails */ pixDestroy(&pixg); pixDestroy(&pixs); return 0; }