Ask Your Question
0

What exactly does code in Canny do?

asked 2016-07-12 22:22:23 -0600

LiquidSquid gravatar image

Hi,

I'm trying to modify the Canny function to output both edges and also a mask which flags each edge pixel with 1,2,3,4 (corresponding to the 4 edge directions used by Canny). I've found the code which I belive to be responsible for this, however I need some help understanding this code:

Here is a bit of code from modules/gpu/src/cuda/canny.cu in the the function calcMapKernel:

__global__ void calcMapKernel(const PtrStepSzi dx, const PtrStepi dy, PtrStepi map, const float low_thresh, const float high_thresh)
{
    const int CANNY_SHIFT = 15;
    //0.4142135623730950488016887242097 = tan(pi/8), this is the angles
    const int TG22 = (int)(0.4142135623730950488016887242097*(1<<CANNY_SHIFT) + 0.5);

    const int x = blockIdx.x * blockDim.x + threadIdx.x;
    const int y = blockIdx.y * blockDim.y + threadIdx.y;

    if (x == 0 || x >= dx.cols - 1 || y == 0 || y >= dx.rows - 1)
        return;

    int dxVal = dx(y, x);
    int dyVal = dy(y, x);

    const int s = (dxVal ^ dyVal) < 0 ? -1 : 1;
    const float m = tex2D(tex_mag, x, y);

    dxVal = ::abs(dxVal);
    dyVal = ::abs(dyVal);

    // 0 - the pixel can not belong to an edge
    // 1 - the pixel might belong to an edge
    // 2 - the pixel does belong to an edge
    int edge_type = 0;

    if (m > low_thresh)
    {
        //what do these 2 lines do?
        const int tg22x = dxVal * TG22;
        const int tg67x = tg22x + ((dxVal + dxVal) << CANNY_SHIFT);

        dyVal <<= CANNY_SHIFT;

        //I guess these if blocks determine where the pixel is part of a edge using it's direction
        if (dyVal < tg22x)
        {
            if (m > tex2D(tex_mag, x - 1, y) && m >= tex2D(tex_mag, x + 1, y))
                edge_type = 1 + (int)(m > high_thresh);
        }
        else if(dyVal > tg67x)
        {
            if (m > tex2D(tex_mag, x, y - 1) && m >= tex2D(tex_mag, x, y + 1))
                edge_type = 1 + (int)(m > high_thresh);
        }
        else
        {
            if (m > tex2D(tex_mag, x - s, y - 1) && m >= tex2D(tex_mag, x + s, y + 1))
                edge_type = 1 + (int)(m > high_thresh);
        }
    }

    map(y, x) = edge_type;
}

What exactly are these lines doing? :

const int tg22x = dxVal * TG22;
const int tg67x = tg22x + ((dxVal + dxVal) << CANNY_SHIFT);

Thanks!

edit retag flag offensive close merge delete

1 answer

Sort by ยป oldest newest most voted
1

answered 2016-07-13 12:59:00 -0600

B4silio gravatar image

updated 2016-07-13 13:00:33 -0600

Not an expert but from the look of it it seems like a nice trick for high computational efficiency:

  • Precompute a costly operation tan(pi/8)
  • Use some bit shifting ( << operation) to do comparisons using int insteand of floats

it seems to be deciding which type of comparison it needs to do with the if (dyVal < tg22x) lines and then goes and check the next pixels in the derivatives images (dx and dy).

 if (dyVal < tg22x) // this is for horizontal edges
    {
        if (m > tex2D(tex_mag, x - 1, y) && m >= tex2D(tex_mag, x + 1, y)) {
            edge_type = 1 + (int)(m > high_thresh);
            // flag = 1;
        }
    }
    else if(dyVal > tg67x) // this for vertical ones
    {
        if (m > tex2D(tex_mag, x, y - 1) && m >= tex2D(tex_mag, x, y + 1)) {
            edge_type = 1 + (int)(m > high_thresh);
            // flag = 2;
        }
    }
    else // diagonals (uses s to switch direction of the diagonal)
    {
        if (m > tex2D(tex_mag, x - s, y - 1) && m >= tex2D(tex_mag, x + s, y + 1)) {
            edge_type = 1 + (int)(m > high_thresh);
            // flag = s > 0 ? 3 : 4;
        }
    }
    // mask(x,y) = flag;

Bottom line, that's where you need to set your flags.

For clarification, you wont be able to tell the "direction" in the sense of right to left vs left to right, just vertical, horizontal and two diagonal directions.

Hope this helps!

edit flag offensive delete link more

Question Tools

1 follower

Stats

Asked: 2016-07-12 19:50:37 -0600

Seen: 362 times

Last updated: Jul 13 '16