[PHP-DEV] [PATCH] Image sharpening function for ext/gd

Ask a Question related to PHP Development, Design and Development.

  1. #1

    Default [PHP-DEV] [PATCH] Image sharpening function for ext/gd

    --Apple-Mail-22--962413191
    Content-Transfer-Encoding: 7bit
    Content-Type: text/plain;
    charset=US-ASCII;
    format=flowed

    Hello,

    I was surprised to find that, although the GD image-handling functions
    shipped with PHP do many useful things very well, there's no function
    to sharpen an image. I found a few posts bemoaning this absence, and
    therefore attach a patch which adds the function

    int imagesharpen ( resource im, int pct )

    It performs the sharpening in-place. pct is the degree of sharpening to
    be applied: 0 does nothing; 100 gives a quite noticeable effect. Values
    >100 can be used for stronger sharpening. Negative values are treated
    as 0.

    The routine only sharpens truecolor images, as it rarely makes sense to
    attempt the operation on palletted images.

    It's a simple linear sharpening routine using a 3x3 kernel, rather than
    the more flexible, but slower, unsharp masking approach used in e.g.
    Photoshop, Imagemagick. However it's very effective at making resampled
    photographic images (such as thumbnails) look a little more crisp.

    I've built and tested it using gcc 3.3 under Mac OS X 10.3.1. There's
    nothing I'd expect to be platform-dependent in it. The attached patch
    is against php4-STABLE-200311202030, but it should work with most
    varieties of php-4.3.4, as the new code is fairly self-contained.

    This is my first patch for PHP. Is there anything else I should do,
    beyond posting it here?

    Many thanks,


    Paul.

    --
    Paul Troughton [url]http://paul.troughton.org/[/url]
    mobile +44 7866 041144 home +44 1223 366900


    --Apple-Mail-22--962413191
    Content-Type: text/plain; charset=us-ascii

    --
    PHP Internals - PHP Runtime Development Mailing List
    To unsubscribe, visit: [url]http://www.php.net/unsub.php[/url]
    --Apple-Mail-22--962413191--
    Paul Troughton Guest

  2. Similar Questions and Discussions

    1. [PHP-DEV] [PATCH] proposal for new function (str_type)
      --------------Boundary-00=_VW2QKJOKCJDXG0I3P9SL Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 8bit On Friday 21...
    2. [PHP-DEV] [PATCH] proposal for new function (str_type)
      --------------Boundary-00=_JUYP82W7BQFNR975SEQ4 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 8bit Hi everyone, ...
    3. [PHP-DEV] Patch providing new function apache_get_scoreboard()
      --------------020304030003010600010706 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 8bit Hello, ...
    4. sharpening (and unsharpmask)
      I don't have the time (or energy) to individually and manually sharpen all my images. If I use unsharp mask, is there an ideal setting for all three...
    5. What's best for image sharpening?
      Without much effort I found several image sharpening "programs" that all claim to be the best and work in some unique way. In addition to unsharpen...
  3. #2

    Default Re: [PHP-DEV] [PATCH] Image sharpening function for ext/gd


    There's new function in PHP 5 CVS, imagefilter(),
    I'd guess this would be good addition into that one..

    --Jani


    On Mon, 24 Nov 2003, Paul Troughton wrote:
    >Hello,
    >
    >I was surprised to find that, although the GD image-handling functions
    >shipped with PHP do many useful things very well, there's no function
    >to sharpen an image. I found a few posts bemoaning this absence, and
    >therefore attach a patch which adds the function
    >
    > int imagesharpen ( resource im, int pct )
    >
    >It performs the sharpening in-place. pct is the degree of sharpening to
    >be applied: 0 does nothing; 100 gives a quite noticeable effect. Values
    > >100 can be used for stronger sharpening. Negative values are treated
    >as 0.
    >
    >The routine only sharpens truecolor images, as it rarely makes sense to
    >attempt the operation on palletted images.
    >
    >It's a simple linear sharpening routine using a 3x3 kernel, rather than
    >the more flexible, but slower, unsharp masking approach used in e.g.
    >Photoshop, Imagemagick. However it's very effective at making resampled
    >photographic images (such as thumbnails) look a little more crisp.
    >
    >I've built and tested it using gcc 3.3 under Mac OS X 10.3.1. There's
    >nothing I'd expect to be platform-dependent in it. The attached patch
    >is against php4-STABLE-200311202030, but it should work with most
    >varieties of php-4.3.4, as the new code is fairly self-contained.
    >
    >This is my first patch for PHP. Is there anything else I should do,
    >beyond posting it here?
    >
    >Many thanks,
    >
    >
    >Paul.
    >
    >
    --
    PHP Internals - PHP Runtime Development Mailing List
    To unsubscribe, visit: [url]http://www.php.net/unsub.php[/url]

    Jani Taskinen Guest

  4. #3

    Default Re: [PHP-DEV] [PATCH] Image sharpening function for ext/gd

    --Apple-Mail-23--957482105
    Content-Transfer-Encoding: 7bit
    Content-Type: text/plain;
    charset=US-ASCII;
    format=flowed

    Second attempt at posting, this time hopefully with the patch as a MIME
    type that won't be stripped...

    On Nov 24, 2003, at 15:09, Paul Troughton wrote:
    > Hello,
    >
    > I was surprised to find that, although the GD image-handling functions
    > shipped with PHP do many useful things very well, there's no function
    > to sharpen an image. I found a few posts bemoaning this absence, and
    > therefore attach a patch which adds the function
    >
    > int imagesharpen ( resource im, int pct )
    >
    > It performs the sharpening in-place. pct is the degree of sharpening
    > to be applied: 0 does nothing; 100 gives a quite noticeable effect.
    > Values >100 can be used for stronger sharpening. Negative values are
    > treated as 0.
    >
    > The routine only sharpens truecolor images, as it rarely makes sense
    > to attempt the operation on palletted images.
    >
    > It's a simple linear sharpening routine using a 3x3 kernel, rather
    > than the more flexible, but slower, unsharp masking approach used in
    > e.g. Photoshop, Imagemagick. However it's very effective at making
    > resampled photographic images (such as thumbnails) look a little more
    > crisp.
    >
    > I've built and tested it using gcc 3.3 under Mac OS X 10.3.1. There's
    > nothing I'd expect to be platform-dependent in it. The attached patch
    > is against php4-STABLE-200311202030, but it should work with most
    > varieties of php-4.3.4, as the new code is fairly self-contained.
    >
    > This is my first patch for PHP. Is there anything else I should do,
    > beyond posting it here?
    >
    > Many thanks,
    >
    >
    > Paul.
    >
    > --
    > Paul Troughton [url]http://paul.troughton.org/[/url]
    > mobile +44 7866 041144 home +44 1223 366900

    --Apple-Mail-23--957482105
    Content-Transfer-Encoding: 7bit
    Content-Type: text/plain;
    x-unix-mode=0644;
    name="php-4.3.4-sharpen.txt"
    Content-Disposition: attachment;
    filename=php-4.3.4-sharpen.txt

    diff -c3prb php4-STABLE-200311202030/ext/gd/gd.c php-4.3.4-mod-pt/ext/gd/gd.c
    *** php4-STABLE-200311202030/ext/gd/gd.c Wed Nov 19 16:06:33 2003
    --- php-4.3.4-mod-pt/ext/gd/gd.c Thu Nov 20 00:59:58 2003
    *************** function_entry gd_functions[] = {
    *** 166,171 ****
    --- 166,172 ----
    PHP_FE(imagerotate, NULL)
    PHP_FE(imageantialias, NULL)
    #endif
    + PHP_FE(imagesharpen, NULL)

    #if HAVE_GD_IMAGESETTILE
    PHP_FE(imagesettile, NULL)
    *************** PHP_FUNCTION(imageantialias)
    *** 3852,3857 ****
    --- 3855,3884 ----
    }
    /* }}} */
    #endif
    +
    + /* {{{ proto int imagesharpen(int im, int pct)
    + Sharpen a GD image
    + Added by Paul Troughton 2003-11-19 */
    + PHP_FUNCTION(imagesharpen)
    + {
    + zval **IM, **PCT;
    + gdImagePtr im;
    + int pct;
    +
    + if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &IM, &PCT) == FAILURE) {
    + ZEND_WRONG_PARAM_COUNT();
    + }
    +
    + ZEND_FETCH_RESOURCE(im, gdImagePtr, IM, -1, "Image", le_gd);
    + convert_to_long_ex(PCT);
    + pct = Z_LVAL_PP(PCT);
    +
    + gdImageSharpen(im, pct);
    + RETURN_TRUE;
    +
    + }
    + /* }}} */
    +

    #endif /* HAVE_LIBGD */

    diff -c3prb php4-STABLE-200311202030/ext/gd/libgd/gd.c php-4.3.4-mod-pt/ext/gd/libgd/gd.c
    *** php4-STABLE-200311202030/ext/gd/libgd/gd.c Tue Nov 4 02:06:49 2003
    --- php-4.3.4-mod-pt/ext/gd/libgd/gd.c Thu Nov 20 22:15:15 2003
    *************** int gdImageColorClosestAlpha (gdImagePtr
    *** 255,261 ****
    gd = im->green[i] - g;
    bd = im->blue[i] - b;
    /* gd 2.02: whoops, was - b (thanks to David Marwood) */
    ! ad = im->alpha[i] - a;
    dist = rd * rd + gd * gd + bd * bd + ad * ad;
    if (first || (dist < mindist)) {
    mindist = dist;
    --- 255,261 ----
    gd = im->green[i] - g;
    bd = im->blue[i] - b;
    /* gd 2.02: whoops, was - b (thanks to David Marwood) */
    ! ad = im->blue[i] - a;
    dist = rd * rd + gd * gd + bd * bd + ad * ad;
    if (first || (dist < mindist)) {
    mindist = dist;
    *************** void gdImageGetClip (gdImagePtr im, int
    *** 3365,3368 ****
    --- 3365,3486 ----
    *y1P = im->cy1;
    *x2P = im->cx2;
    *y2P = im->cy2;
    + }
    +
    +
    + /* Called by gdImageSharpen to avoid excessive code repetition
    + Added on 2003-11-19 by
    + Paul Troughton (paul<dot>troughton<at>ieee<dot>org)
    + Given filter coefficents and colours of three adjacent pixels, returns new colour for centre pixel
    + */
    +
    + int gdImageSharpen_Sub (int pc, int c, int nc, float inner_coeff, float outer_coeff) {
    + float red, green, blue, alpha;
    +
    + red = inner_coeff * gdTrueColorGetRed (c) + outer_coeff * (gdTrueColorGetRed (pc) + gdTrueColorGetRed (nc));
    + green = inner_coeff * gdTrueColorGetGreen (c) + outer_coeff * (gdTrueColorGetGreen (pc) + gdTrueColorGetGreen (nc));
    + blue = inner_coeff * gdTrueColorGetBlue (c) + outer_coeff * (gdTrueColorGetBlue (pc) + gdTrueColorGetBlue (nc));
    + alpha = gdTrueColorGetAlpha (c);
    +
    + /* Clamping, as can overshoot bounds in either direction */
    + if (red > 255.0f) {
    + red = 255.0f;
    + }
    + if (green > 255.0f) {
    + green = 255.0f;
    + }
    + if (blue > 255.0f) {
    + blue = 255.0f;
    + }
    + if (red < 0.0f) {
    + red = 0.0f;
    + }
    + if (green < 0.0f) {
    + green = 0.0f;
    + }
    + if (blue < 0.0f) {
    + blue = 0.0f;
    + }
    +
    + return gdTrueColorAlpha ((int) red, (int) green, (int) blue, (int) alpha);
    + }
    +
    + /*
    + * Sharpen function added on 2003-11-19
    + * by Paul Troughton (paul<dot>troughton<at>ieee<dot>org)
    + * Simple 3x3 convolution kernel
    + * Makes use of seperability
    + * Faster, but less flexible, than full-blown unsharp masking
    + * pct is sharpening percentage, and can be greater than 100
    + * Silently does nothing to non-truecolor images
    + * Silently does nothing for pct<0, as not a useful blurring function
    + * Leaves transparency/alpha-channel untouched
    + */
    +
    + void gdImageSharpen (gdImagePtr im, int pct)
    + {
    + int x, y;
    + int sx, sy;
    + float inner_coeff, outer_coeff;
    +
    + sx = im->sx;
    + sy = im->sy;
    +
    + /* Must sum to 1 to avoid overall change in brightness.
    + * Scaling chosen so that pct=100 gives 1-D filter [-1 6 -1]/4,
    + * resulting in a 2-D filter [1 -6 1; -6 36 -6; 1 -6 1]/16,
    + * which gives noticeable, but not excessive, sharpening
    + */
    +
    + outer_coeff = -pct / 400.0;
    + inner_coeff = 1 - 2 * outer_coeff;
    +
    + /* Don't try to do anything with non-truecolor images, as pointless,
    + * nor for pct<=0, as small kernel size leads to nasty artefacts when blurring
    + */
    + if ( (im->trueColor) && (pct>0) ) {
    +
    + /* First pass, 1-D convolution column-wise */
    + for (x = 0; x < sx; x++) {
    +
    + /* pc is colour of previous pixel; c of the current pixel and nc of the next */
    + int pc, c, nc;
    +
    + /* Replicate edge pixel at image boundary */
    + pc = gdImageGetPixel (im, x, 0);
    +
    + /* Stop looping before last pixel to avoid conditional within loop */
    + for (y = 0; y < sy-1; y++) {
    +
    + c = gdImageGetPixel (im, x, y);
    +
    + nc = gdImageGetTrueColorPixel (im, x, y+1);
    +
    + /* Update centre pixel to new colour */
    + gdImageSetPixel(im, x, y, gdImageSubSharpen (pc, c, nc, inner_coeff, outer_coeff) );
    +
    + /* Save original colour of current pixel for next time round */
    + pc = c;
    + }
    +
    + /* Deal with last pixel, replicating current pixel at image boundary */
    + c = gdImageGetPixel (im, x, y);
    + gdImageSetPixel(im, x, y, gdImageSharpen_Sub (pc, c, c, inner_coeff, outer_coeff) );
    + }
    +
    + /* Second pass, 1-D convolution row-wise */
    + for (y = 0; y < sy; y++) {
    + int pc, c, nc;
    + pc = gdImageGetPixel (im, 0, y);
    + for (x = 0; x < sx-1; x++) {
    + int c, nc;
    + c = gdImageGetPixel (im, x, y);
    + nc = gdImageGetTrueColorPixel (im, x+1, y);
    + gdImageSetPixel(im, x, y, gdImageSharpen_Sub (pc, c, nc, inner_coeff, outer_coeff) );
    + pc = c;
    + }
    + c = gdImageGetPixel (im, x, y);
    + gdImageSetPixel(im, x, y, gdImageSubSharpen (pc, c, c, inner_coeff, outer_coeff) );
    + }
    + }
    }
    diff -c3prb php4-STABLE-200311202030/ext/gd/libgd/gd.h php-4.3.4-mod-pt/ext/gd/libgd/gd.h
    *** php4-STABLE-200311202030/ext/gd/libgd/gd.h Wed Apr 9 04:05:40 2003
    --- php-4.3.4-mod-pt/ext/gd/libgd/gd.h Wed Nov 19 17:18:59 2003
    *************** void gdImageAlphaBlending(gdImagePtr im,
    *** 537,542 ****
    --- 537,553 ----
    void gdImageAntialias(gdImagePtr im, int antialias);
    void gdImageSaveAlpha(gdImagePtr im, int saveAlphaArg);

    + /*
    + * Sharpen function added on 2003-11-19
    + * by Paul Troughton (paul<dot>troughton<at>ieee<dot>org)
    + * Simple 3x3 convolution kernel
    + * Makes use of seperability
    + * Faster, but less flexible, than full-blown unsharp masking
    + * pct is sharpening percentage
    + * Leaves transparency/alpha-channel untouched
    + */
    + void gdImageSharpen (gdImagePtr im, int pct);
    +
    /* Macros to access information about images. */

    /* Returns nonzero if the image is a truecolor image,
    diff -c3prb php4-STABLE-200311202030/ext/gd/php_gd.h php-4.3.4-mod-pt/ext/gd/php_gd.h
    *** php4-STABLE-200311202030/ext/gd/php_gd.h Mon Mar 31 10:05:59 2003
    --- php-4.3.4-mod-pt/ext/gd/php_gd.h Thu Nov 20 22:24:09 2003
    *************** PHP_FUNCTION(imagerotate);
    *** 108,113 ****
    --- 108,115 ----
    PHP_FUNCTION(imageantialias);
    #endif

    + PHP_FUNCTION(imagesharpen);
    +
    PHP_FUNCTION(imagesetthickness);
    PHP_FUNCTION(imagecopymergegray);
    PHP_FUNCTION(imagesetbrush);

    --Apple-Mail-23--957482105
    Content-Transfer-Encoding: 7bit
    Content-Type: text/plain;
    charset=US-ASCII;
    format=flowed





    --Apple-Mail-23--957482105
    Content-Type: text/plain; charset=us-ascii

    --
    PHP Internals - PHP Runtime Development Mailing List
    To unsubscribe, visit: [url]http://www.php.net/unsub.php[/url]
    --Apple-Mail-23--957482105--
    Paul Troughton Guest

Posting Permissions

  • You may not post new threads
  • You may post replies
  • You may not post attachments
  • You may not edit your posts

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139