rapp-users
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Rapp-users] Morphological functions


From: Douglas Medeiros
Subject: Re: [Rapp-users] Morphological functions
Date: Tue, 18 Sep 2018 13:10:03 -0300

Thanks a lot for your help Johan.
I think I finally got it.

I confess I still not understanding the code at all, specially because the complex pointers arithmetic, but it's working for me. Some pieces of the code below, mainly the code which initializes the buffers, I've copied from "rapp_test_morph_bin.c" in rapp installation "test" folder. I'm sharing it so I believe can help others.

/*
  Performs a limiarization and then dilates an u8 image, out_8u stores the resulting dilated binarized u8 image.
  width and height are always 640x480; The resulting image, in "out_8u" has the dilated image pixels.
*/
void rapp_pgs_test(unsigned char *img_8u, int width, int height, unsigned char *out_8u)
{
    uint8_t *pat_buf = NULL;  /* Pattern buffer                */
    uint8_t *pad_buf = NULL;  /* Source buffer with padding    */
    uint8_t *src_buf = NULL;  /* Source buffer                 */
    uint8_t *dst_buf = NULL;  /* Destination buffer            */
    uint8_t *ref_buf = NULL;  /* Reference buffer              */
    void    *work    = NULL;  /* Working buffer (scratch)      */
    int      src_dim;         /* Source buffer dimension       */
    int      dst_dim;         /* Destination buffer dimension  */
    int      pad_len;         /* Padded source buffer in bytes */
    int      se_square_size = 4; // size of the morph structuring element
    int      size    = MIN(width, height);
    int      minxpixpad = MIN( se_square_size / 2, 16);
    int      minypixpad = MIN( se_square_size / 2, 16);
    int      minxpad = rapp_align((minxpixpad + 7) / 8);
    int      pos;
    bool     ok = false;

    /* Allocate the buffers */
    dst_dim = rapp_align((width + 7) / 8);
    src_dim = dst_dim + 2*minxpad;
    pat_buf = (uint8_t*)rapp_malloc(height*dst_dim, 0);
    pad_len = (height + 2*minypixpad)*src_dim;
    pad_buf = (uint8_t*)rapp_malloc(pad_len, 0);
    src_buf = &pad_buf[minypixpad*src_dim + minxpad];
    dst_buf = (uint8_t*)rapp_malloc(height*dst_dim, 0);
    ref_buf = (uint8_t*)rapp_malloc(height*dst_dim, 0);
    work    = (uint8_t*)rapp_malloc(rapp_morph_worksize_bin(width, height), 0);

    rapp_thresh_gt_u8(src_buf, src_dim, img_8u, width, width, height, 100);//binarizes the u8 image int an binary image buffer.

    rapp_morph_dilate_rect_bin(dst_buf, dst_dim, src_buf, src_dim, width, height,  se_square_size se_square_size, work);

    rapp_type_bin_to_u8(out_8u, width, dst_buf, dst_dim, width, height);//out_8u can be easyly encapsulated into an Opencv Mat

    rapp_free(pat_buf);
    rapp_free(pad_buf);
    rapp_free(dst_buf);
    rapp_free(ref_buf);
    rapp_free(work);
}

Em dom, 12 de ago de 2018 às 14:13, Johan Almbladh <address@hidden> escreveu:
Hi Douglas,

I think you might have not initialised the padding pixels around the source image properly. All spatial filter functions, convolutional and morphological, assume that the source image is padded with the proper values. The functions reads the padding pixels outside the source image area as it computes the edge pixels in the destination image. It is up to the caller to allocate sufficient padding and initialise those pixels properly. Please also note that binary images are stored as 1 bit per pixel and not 8 bits.

For binary morphological operations, the padding is initialised using the functions rapp_pad_const_bin() or rapp_pad_clamp_bin(), depending on what boundary conditions you want. In your case the process would be as follows.

1. Allocate a larger buffer to hold the binary threshold image + the necessary padding.
2. Threshold the source image, letting the function write to the actual image area within the larger buffer allocated above.
3. Initialise the padding pixels properly. The required size of the padding depends on the structuring element size.
4. Perform the desired morphological operation on the binary source image.

The recommended practice is to always use pixel buffers with enough padding outside the real image area in order to avoid copying data for operations where padding is needed.

Unfortunately there are not much sample code snippets available, but the docs are quite extensive and should contain everything you need. Please see the sections on padding, pixel buffer semantics and morphological filters for details.

Best regards,
Johan

On Wed, Aug 8, 2018 at 5:53 PM, Douglas Medeiros <address@hidden> wrote:
Hello,

I'm working on a project that uses morphological function in order to make an object detection. We recently discovered RAPP and how suitable for embedded processing it could be.
I´ve faced some difficulties because of the (hard) documentation (no samples!), but until now I can use the threshold and Gaussian filters, but the dilate and erode functions I was unsuccessful. The binary image buffer is obtained by using rapp_malloc, actually the binary image is the exact output of the threshold function (rapp_thresh_gt_u8), but the resulting image of the dilate function (rapp_morph_dilate_rect_bin) is a kind of messy.

I'm not sure whether the images are misaligned or the source binary images buffers are not being initialized properly. Hope people here could help me on this.

The images are all grayscale, 640x480. Normally our dilate and erode operation use rectangle structural component with both width and height 15 pixels.

Thanks vary much in advance.

Doug.


reply via email to

[Prev in Thread] Current Thread [Next in Thread]