Leptonica  1.83.1
Image processing and image analysis suite
warper.c File Reference
#include <math.h>
#include "allheaders.h"

Go to the source code of this file.

Macros

#define USE_SIN_TABLE   0
 

Functions

static l_float64 * generateRandomNumberArray (l_int32 size)
 
static l_int32 applyWarpTransform (l_float32 xmag, l_float32 ymag, l_float32 xfreq, l_float32 yfreq, l_float64 *randa, l_int32 nx, l_int32 ny, l_int32 xp, l_int32 yp, l_float32 *px, l_float32 *py)
 
PIXpixSimpleCaptcha (PIX *pixs, l_int32 border, l_int32 nterms, l_uint32 seed, l_uint32 color, l_int32 cmapflag)
 
PIXpixRandomHarmonicWarp (PIX *pixs, l_float32 xmag, l_float32 ymag, l_float32 xfreq, l_float32 yfreq, l_int32 nx, l_int32 ny, l_uint32 seed, l_int32 grayval)
 
PIXpixWarpStereoscopic (PIX *pixs, l_int32 zbend, l_int32 zshiftt, l_int32 zshiftb, l_int32 ybendt, l_int32 ybendb, l_int32 redleft)
 
PIXpixStretchHorizontal (PIX *pixs, l_int32 dir, l_int32 type, l_int32 hmax, l_int32 operation, l_int32 incolor)
 
PIXpixStretchHorizontalSampled (PIX *pixs, l_int32 dir, l_int32 type, l_int32 hmax, l_int32 incolor)
 
PIXpixStretchHorizontalLI (PIX *pixs, l_int32 dir, l_int32 type, l_int32 hmax, l_int32 incolor)
 
PIXpixQuadraticVShear (PIX *pixs, l_int32 dir, l_int32 vmaxt, l_int32 vmaxb, l_int32 operation, l_int32 incolor)
 
PIXpixQuadraticVShearSampled (PIX *pixs, l_int32 dir, l_int32 vmaxt, l_int32 vmaxb, l_int32 incolor)
 
PIXpixQuadraticVShearLI (PIX *pixs, l_int32 dir, l_int32 vmaxt, l_int32 vmaxb, l_int32 incolor)
 
PIXpixStereoFromPair (PIX *pix1, PIX *pix2, l_float32 rwt, l_float32 gwt, l_float32 bwt)
 

Variables

static const l_float32 DefaultRedWeight = 0.0
 
static const l_float32 DefaultGreenWeight = 0.7
 
static const l_float32 DefaultBlueWeight = 0.3
 

Detailed Description


     High-level captcha interface
         PIX               *pixSimpleCaptcha()

     Random sinusoidal warping
         PIX               *pixRandomHarmonicWarp()

     Helper functions
         static l_float64  *generateRandomNumberArray()
         static l_int32     applyWarpTransform()

     Version using a LUT for sin
         PIX               *pixRandomHarmonicWarpLUT()
         static l_int32     applyWarpTransformLUT()
         static l_int32     makeSinLUT()
         static l_float32   getSinFromLUT()

     Stereoscopic warping
         PIX               *pixWarpStereoscopic()

     Linear and quadratic horizontal stretching
         PIX               *pixStretchHorizontal()
         PIX               *pixStretchHorizontalSampled()
         PIX               *pixStretchHorizontalLI()

     Quadratic vertical shear
         PIX               *pixQuadraticVShear()
         PIX               *pixQuadraticVShearSampled()
         PIX               *pixQuadraticVShearLI()

     Stereo from a pair of images
         PIX               *pixStereoFromPair()

Definition in file warper.c.

Function Documentation

◆ applyWarpTransform()

static l_int32 applyWarpTransform ( l_float32  xmag,
l_float32  ymag,
l_float32  xfreq,
l_float32  yfreq,
l_float64 *  randa,
l_int32  nx,
l_int32  ny,
l_int32  xp,
l_int32  yp,
l_float32 *  px,
l_float32 *  py 
)
static

applyWarpTransform()

Notes: (1) Uses the internal sin function.

Definition at line 259 of file warper.c.

◆ pixQuadraticVShear()

PIX* pixQuadraticVShear ( PIX pixs,
l_int32  dir,
l_int32  vmaxt,
l_int32  vmaxb,
l_int32  operation,
l_int32  incolor 
)

pixQuadraticVShear()

Parameters
[in]pixs1, 8 or 32 bpp
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]vmaxtmax vertical displacement at edge and at top
[in]vmaxbmax vertical displacement at edge and at bottom
[in]operationL_SAMPLED or L_INTERPOLATED
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched, or NULL on error
Notes:
     (1) This gives a quadratic bending, upward or downward, as you
         move to the left or right.
     (2) If dir == L_WARP_TO_LEFT, the right edge is unchanged, and
         the left edge pixels are moved maximally up or down.
     (3) Parameters vmaxt and vmaxb control the maximum amount of
         vertical pixel shear at the top and bottom, respectively.
         If vmaxt > 0, the vertical displacement of pixels at the
         top is downward.  Likewise, if vmaxb > 0, the vertical
         displacement of pixels at the bottom is downward.
     (4) If operation == L_SAMPLED, the dest pixels are taken from
         the nearest src pixel.  Otherwise, we use linear interpolation
         between pairs of sampled pixels.
     (5) This is for quadratic shear.  For uniform (linear) shear,
         use the standard shear operators.

Definition at line 1005 of file warper.c.

References L_BRING_IN_BLACK, L_BRING_IN_WHITE, L_INTERPOLATED, L_SAMPLED, L_WARP_TO_LEFT, L_WARP_TO_RIGHT, pixCopy(), pixGetDimensions(), pixQuadraticVShearLI(), and pixQuadraticVShearSampled().

Referenced by pixWarpStereoscopic().

◆ pixQuadraticVShearLI()

PIX* pixQuadraticVShearLI ( PIX pixs,
l_int32  dir,
l_int32  vmaxt,
l_int32  vmaxb,
l_int32  incolor 
)

pixQuadraticVShearLI()

Parameters
[in]pixs8 or 32 bpp, or colormapped
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]vmaxtmax vertical displacement at edge and at top
[in]vmaxbmax vertical displacement at edge and at bottom
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched, or NULL on error
Notes:
     (1) See pixQuadraticVShear() for details.

Definition at line 1161 of file warper.c.

References pixGetDimensions().

Referenced by pixQuadraticVShear().

◆ pixQuadraticVShearSampled()

PIX* pixQuadraticVShearSampled ( PIX pixs,
l_int32  dir,
l_int32  vmaxt,
l_int32  vmaxb,
l_int32  incolor 
)

pixQuadraticVShearSampled()

Parameters
[in]pixs1, 8 or 32 bpp
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]vmaxtmax vertical displacement at edge and at top
[in]vmaxbmax vertical displacement at edge and at bottom
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched, or NULL on error
Notes:
     (1) See pixQuadraticVShear() for details.

Definition at line 1057 of file warper.c.

References L_BRING_IN_BLACK, L_BRING_IN_WHITE, L_WARP_TO_LEFT, L_WARP_TO_RIGHT, pixCopy(), pixCreateTemplate(), pixGetData(), pixGetDimensions(), and pixSetBlackOrWhite().

Referenced by pixQuadraticVShear().

◆ pixRandomHarmonicWarp()

PIX* pixRandomHarmonicWarp ( PIX pixs,
l_float32  xmag,
l_float32  ymag,
l_float32  xfreq,
l_float32  yfreq,
l_int32  nx,
l_int32  ny,
l_uint32  seed,
l_int32  grayval 
)

pixRandomHarmonicWarp()

Parameters
[in]pixs8 bpp; no colormap
[in]xmag,ymagmaximum magnitude of x and y distortion
[in]xfreq,yfreqmaximum magnitude of x and y frequency
[in]nx,nynumber of x and y harmonic terms
[in]seedof random number generator
[in]grayvalcolor brought in from the outside; 0 for black, 255 for white
Returns
pixd 8 bpp; no colormap, or NULL on error
Notes:
     (1) To generate the warped image p(x',y'), set up the transforms
         that are in getWarpTransform().  For each (x',y') in the
         dest, the warp function computes the originating location
         (x, y) in the src.  The differences (x - x') and (y - y')
         are given as a sum of products of sinusoidal terms.  Each
         term is multiplied by a maximum amplitude (in pixels), and the
         angle is determined by a frequency and phase, and depends
         on the (x', y') value of the dest.  Random numbers with
         a variable input seed are used to allow the warping to be
         unpredictable.  A linear interpolation is used to find
         the value for the source at (x, y); this value is written
         into the dest.
     (2) This can be used to generate 'captcha's, which are somewhat
         randomly distorted images of text.  A typical set of parameters
         for a captcha are:
                   xmag = 4.0     ymag = 6.0
                   xfreq = 0.10   yfreq = 0.13
                   nx = 3         ny = 3
         Other examples can be found in prog/warptest.c.

Definition at line 183 of file warper.c.

References pixGetDimensions().

Referenced by pixSimpleCaptcha().

◆ pixSimpleCaptcha()

PIX* pixSimpleCaptcha ( PIX pixs,
l_int32  border,
l_int32  nterms,
l_uint32  seed,
l_uint32  color,
l_int32  cmapflag 
)

pixSimpleCaptcha()

Parameters
[in]pixs8 bpp; no colormap
[in]borderadded white pixels on each side
[in]ntermsnumber of x and y harmonic terms
[in]seedof random number generator
[in]colorfor colorizing; in 0xrrggbb00 format; use 0 for black
[in]cmapflag1 for colormap output; 0 for rgb
Returns
pixd 8 bpp cmap or 32 bpp rgb, or NULL on error
Notes:
     (1) This uses typical default values for generating captchas.
         The magnitudes of the harmonic warp are typically to be
         smaller when more terms are used, even though the phases
         are random.  See, for example, prog/warptest.c.

Definition at line 111 of file warper.c.

References pixAddBorder(), pixColorizeGray(), pixConvertTo8(), pixDestroy(), and pixRandomHarmonicWarp().

◆ pixStereoFromPair()

PIX* pixStereoFromPair ( PIX pix1,
PIX pix2,
l_float32  rwt,
l_float32  gwt,
l_float32  bwt 
)

pixStereoFromPair()

Parameters
[in]pix132 bpp rgb
[in]pix232 bpp rgb
[in]rwt,gwt,bwtweighting factors used for each component in pix1 to determine the output red channel
Returns
pixd stereo enhanced, or NULL on error
Notes:
     (1) pix1 and pix2 are a pair of stereo images, ideally taken
         concurrently in the same plane, with some lateral translation.
     (2) The output red channel is determined from pix1.
         The output green and blue channels are taken from the green
         and blue channels, respectively, of pix2.
     (3) The weights determine how much of each component in pix1
         goes into the output red channel.  The sum of weights
         must be 1.0.  If it's not, we scale the weights to
         satisfy this criterion.
     (4) The most general pixel mapping allowed here is:
           rval = rwt * r1 + gwt * g1 + bwt * b1  (from pix1)
           gval = g2   (from pix2)
           bval = b2   (from pix2)
     (5) The simplest method is to use rwt = 1.0, gwt = 0.0, bwt = 0.0,
         but this causes unpleasant visual artifacts with red in the image.
         Use of green and blue from pix1 in the red channel,
         instead of red, tends to fix that problem.

Definition at line 1312 of file warper.c.

◆ pixStretchHorizontal()

PIX* pixStretchHorizontal ( PIX pixs,
l_int32  dir,
l_int32  type,
l_int32  hmax,
l_int32  operation,
l_int32  incolor 
)

pixStretchHorizontal()

Parameters
[in]pixs1, 8 or 32 bpp
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]typeL_LINEAR_WARP or L_QUADRATIC_WARP
[in]hmaxhorizontal displacement at edge
[in]operationL_SAMPLED or L_INTERPOLATED
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched/compressed, or NULL on error
Notes:
     (1) If hmax > 0, this is an increase in the coordinate value of
         pixels in pixd, relative to the same pixel in pixs.
     (2) If dir == L_WARP_TO_LEFT, the pixels on the right edge of
         the image are not moved. So, for example, if hmax > 0
         and dir == L_WARP_TO_LEFT, the pixels in pixd are
         contracted toward the right edge of the image, relative
         to those in pixs.
     (3) If type == L_LINEAR_WARP, the pixel positions are moved
         to the left or right by an amount that varies linearly with
         the horizontal location.
     (4) If operation == L_SAMPLED, the dest pixels are taken from
         the nearest src pixel.  Otherwise, we use linear interpolation
         between pairs of sampled pixels.

Definition at line 725 of file warper.c.

Referenced by pixWarpStereoscopic().

◆ pixStretchHorizontalLI()

PIX* pixStretchHorizontalLI ( PIX pixs,
l_int32  dir,
l_int32  type,
l_int32  hmax,
l_int32  incolor 
)

pixStretchHorizontalLI()

Parameters
[in]pixs1, 8 or 32 bpp
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]typeL_LINEAR_WARP or L_QUADRATIC_WARP
[in]hmaxhorizontal displacement at edge
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched/compressed, or NULL on error
Notes:
     (1) See pixStretchHorizontal() for details.

Definition at line 871 of file warper.c.

References L_BRING_IN_BLACK, L_BRING_IN_WHITE, L_LINEAR_WARP, L_QUADRATIC_WARP, L_WARP_TO_LEFT, L_WARP_TO_RIGHT, pixCreateTemplate(), pixGetData(), pixGetDimensions(), and pixSetBlackOrWhite().

◆ pixStretchHorizontalSampled()

PIX* pixStretchHorizontalSampled ( PIX pixs,
l_int32  dir,
l_int32  type,
l_int32  hmax,
l_int32  incolor 
)

pixStretchHorizontalSampled()

Parameters
[in]pixs1, 8 or 32 bpp
[in]dirL_WARP_TO_LEFT or L_WARP_TO_RIGHT
[in]typeL_LINEAR_WARP or L_QUADRATIC_WARP
[in]hmaxhorizontal displacement at edge
[in]incolorL_BRING_IN_WHITE or L_BRING_IN_BLACK
Returns
pixd stretched/compressed, or NULL on error
Notes:
     (1) See pixStretchHorizontal() for details.

Definition at line 775 of file warper.c.

References L_BRING_IN_BLACK, L_BRING_IN_WHITE, L_LINEAR_WARP, L_QUADRATIC_WARP, L_WARP_TO_LEFT, L_WARP_TO_RIGHT, pixCreateTemplate(), pixGetData(), pixGetDimensions(), and pixSetBlackOrWhite().

◆ pixWarpStereoscopic()

PIX* pixWarpStereoscopic ( PIX pixs,
l_int32  zbend,
l_int32  zshiftt,
l_int32  zshiftb,
l_int32  ybendt,
l_int32  ybendb,
l_int32  redleft 
)

pixWarpStereoscopic()

Parameters
[in]pixsany depth, colormap ok
[in]zbendhorizontal separation in pixels of red and cyan at the left and right sides, that gives rise to quadratic curvature out of the image plane
[in]zshifttuniform pixel translation difference between red and cyan, that pushes the top of the image plane away from the viewer (zshiftt > 0) or towards the viewer (zshiftt < 0)
[in]zshiftbuniform pixel translation difference between red and cyan, that pushes the bottom of the image plane away from the viewer (zshiftb > 0) or towards the viewer (zshiftb < 0)
[in]ybendtmultiplicative parameter for in-plane vertical displacement at the left or right edge at the top: y = ybendt * (2x/w - 1)^2
[in]ybendbsame as ybendt, except at the left or right edge at the bottom
[in]redleft1 if the red filter is on the left; 0 otherwise
Returns
pixd 32 bpp, or NULL on error
Notes:
     (1) This function splits out the red channel, mucks around with
         it, then recombines with the unmolested cyan channel.
     (2) By using a quadratically increasing shift of the red
         pixels horizontally and away from the vertical centerline,
         the image appears to bend quadratically out of the image
         plane, symmetrically with respect to the vertical center
         line.  A positive value of zbend causes the plane to be
         curved away from the viewer.  We use linearly interpolated
         stretching to avoid the appearance of kinks in the curve.
     (3) The parameters zshiftt and zshiftb tilt the image plane
         about a horizontal line through the center, and at the
         same time move that line either in toward the viewer or away.
         This is implemented by a combination of horizontal shear
         about the center line (for the tilt) and horizontal
         translation (to move the entire plane in or out).
         A positive value of zshiftt moves the top of the plane
         away from the viewer, and a positive value of zshiftb
         moves the bottom of the plane away.  We use linear interpolated
         shear to avoid visible vertical steps in the tilted image.
     (4) The image can be bent in the plane and about the vertical
         centerline.  The centerline does not shift, and the
         parameter ybend gives the relative shift at left and right
         edges, with a downward shift for positive values of ybend.
     (6) When writing out a steroscopic (red/cyan) image in jpeg,
         first call pixSetChromaSampling(pix, 0) to get sufficient
         resolution in the red channel.
     (7) Typical values are:
            zbend = 20
            zshiftt = 15
            zshiftb = -15
            ybendt = 30
            ybendb = 0
         If the disparity z-values are too large, it is difficult for
         the brain to register the two images.
     (8) This function has been cleverly reimplemented by Jeff Breidenbach.
         The original implementation used two 32 bpp rgb images,
         and merged them at the end.  The result is somewhat faded,
         and has a parameter "thresh" that controls the amount of
         color in the result.  (The present implementation avoids these
         two problems, skipping both the colorization and the alpha
         blending at the end, and is about 3x faster)
         The basic operations with 32 bpp are as follows:
              // Immediate conversion to 32 bpp
           Pix *pixt1 = pixConvertTo32(pixs);
              // Do vertical shear
           Pix *pixr = pixQuadraticVerticalShear(pixt1, L_WARP_TO_RIGHT,
                                                 ybendt, ybendb,
                                                 L_BRING_IN_WHITE);
              // Colorize two versions, toward red and cyan
           Pix *pixc = pixCopy(NULL, pixr);
           l_int32 thresh = 150;  // if higher, get less original color
           pixColorGray(pixr, NULL, L_PAINT_DARK, thresh, 255, 0, 0);
           pixColorGray(pixc, NULL, L_PAINT_DARK, thresh, 0, 255, 255);
              // Shift the red pixels; e.g., by stretching
           Pix *pixrs = pixStretchHorizontal(pixr, L_WARP_TO_RIGHT,
                                             L_QUADRATIC_WARP, zbend,
                                             L_INTERPOLATED,
                                             L_BRING_IN_WHITE);
              // Blend the shifted red and unshifted cyan 50:50
           Pix *pixg = pixCreate(w, h, 8);
           pixSetAllArbitrary(pixg, 128);
           pixd = pixBlendWithGrayMask(pixrs, pixc, pixg, 0, 0);

Definition at line 580 of file warper.c.

References boxCreate(), COLOR_BLUE, COLOR_GREEN, COLOR_RED, L_BRING_IN_WHITE, L_INTERPOLATED, L_QUADRATIC_WARP, L_WARP_TO_LEFT, L_WARP_TO_RIGHT, PIX_SRC, pixClipRectangle(), pixClone(), pixConvertTo32(), pixCreate(), pixDestroy(), pixGetDimensions(), pixGetRGBComponent(), pixQuadraticVShear(), pixRasterop(), pixStretchHorizontal(), and pixTranslate().