cvsmooth.cpp.svn-base

来自「非结构化路识别」· SVN-BASE 代码 · 共 1,957 行 · 第 1/5 页

SVN-BASE
1,957
字号

        rows[ker_y] = saved_row;

        /* rotate buffer */
        {
            int *t = rows[0];

            CV_COPY( rows, rows + 1, ker_height - 1, i );
            rows[i] = t;
            crows--;
            dst += dstStep;
        }
    }
    while( ++y < dst_height );

    roiSize->height = y;
    state->crows = crows;

    return CV_OK;
}


IPCVAPI( CvStatus,
     icvBlur_8s16s_C1R, ( const char* src, int srcStep,
                          short* dst, int dstStep, CvSize * roiSize,
                          CvFilterState* state, int stage ));

IPCVAPI_IMPL( CvStatus,
     icvBlur_8s16s_C1R, ( const char* pSrc, int srcStep,
                          short* dst, int dstStep, CvSize * roiSize,
                          CvFilterState* state, int stage ))
{
    char* src = (char*)pSrc;
    int width = roiSize->width;
    int src_height = roiSize->height;
    int dst_height = src_height;
    int x, y = 0, i;

    int ker_x = state->ker_x;
    int ker_y = state->ker_y;
    int ker_width = state->ker_width;
    int ker_height = state->ker_height;
    int ker_right = ker_width - ker_x;

    int crows = state->crows;
    int **rows = (int**)(state->rows);
    short *tbufw = (short*)(state->tbuf);
    int   *sumbuf = (int*)((char*)state->tbuf + state->buffer_step);
    int *trow, *trow2;

    int channels = state->channels;
    int ker_x_n = ker_x * channels;
    int ker_width_n = ker_width * channels;
    int ker_right_n = ker_right * channels;
    int width_n = width * channels;

    int is_small_width = width < MAX( ker_x, ker_right );
    int starting_flag = 0;
    int width_rest = width_n & (CV_MORPH_ALIGN - 1);

    /* initialize cyclic buffer when starting */
    if( stage == CV_WHOLE || stage == CV_START )
    {
        for( i = 0; i < ker_height; i++ )
            rows[i] = (int*)(state->buffer + state->buffer_step * i);

        crows = ker_y;
        if( stage != CV_WHOLE )
            dst_height -= ker_height - ker_y - 1;
        starting_flag = 1;
    }

    if( stage == CV_END )
        dst_height += ker_height - ker_y - 1;

    dstStep /= sizeof(dst[0]);

    do
    {
        int need_copy = is_small_width | (y == 0);
        char *tsrc;
        int *tdst;
        short *tdst2;
        int *saved_row = rows[ker_y];

        /* fill cyclic buffer - horizontal filtering */
        for( ; crows < ker_height; crows++ )
        {
            tsrc = src - ker_x_n;
            tdst = rows[crows];

            if( src_height-- <= 0 )
            {
                if( stage != CV_WHOLE && stage != CV_END )
                    break;
                /* duplicate last row */
                trow = rows[crows - 1];
                CV_COPY( tdst, trow, width_n, x );
                continue;
            }

            need_copy |= src_height == 1;

            if( ker_width > 1 )
            {
                char* tbuf = (char*)tbufw;

                if( need_copy )
                {
                    tsrc = tbuf - ker_x_n;
                    CV_COPY( tbuf, src, width_n, x );
                }
                else
                {
                    CV_COPY( tbuf - ker_x_n, src - ker_x_n, ker_x_n, x );
                    CV_COPY( tbuf, src + width_n, ker_right_n, x );
                }

                {
                    /* make replication borders */
                    char pix = tsrc[ker_x];
                    int t0 = 0;

                    CV_SET( tsrc, pix, ker_x, x );

                    pix = tsrc[width + ker_x - 1];
                    CV_SET( tsrc + width + ker_x, pix, ker_right, x );

                    for( i = 0; i < ker_width_n - 1; i++ )
                        t0 += tsrc[i];

                    /* horizontal blurring */
                    for( i = ker_width_n; i < width_n + ker_width_n; i++ )
                    {
                        t0 += tsrc[i-1];
                        tdst[i-ker_width_n] = t0;
                        t0 -= tsrc[i - ker_width_n];
                    }
                }

                if( !need_copy )
                {
                    /* restore borders */
                    CV_COPY( src - ker_x_n, tbuf - ker_x_n, ker_x_n, x );
                    CV_COPY( src + width_n, tbuf, ker_right_n, x );
                }
            }
            else
            {
                CV_COPY( tdst, tsrc + ker_x_n, width_n, x );
            }

            if( crows < ker_height )
                src += srcStep;
        }

        if( starting_flag )
        {
            starting_flag = 0;

            for( x = 0; x < width_n; x++ )
            {
                int t = rows[ker_y][x];
                for( i = 0; i < ker_y; i++ ) // copy border
                    rows[i][x] = t;

                t *= ker_y;
                for( i = ker_y; i < ker_height - 1; i++ ) // accumulate initial sum
                    t += rows[i][x];
                sumbuf[x] = t;
            }
        }

        /* vertical convolution */
        if( crows != ker_height )
            break;

        tdst2 = dst;

        if( width_rest )
        {
            need_copy = width_n < CV_MORPH_ALIGN || y == dst_height - 1;

            if( need_copy )
                tdst2 = tbufw;
            else
                CV_COPY( tbufw + width_n, dst + width_n, CV_MORPH_ALIGN, x );
        }

        trow = rows[0];
        trow2 = rows[ker_height-1];

        for( x = 0; x < width_n; x += CV_MORPH_ALIGN )
        {
            int val0, val1;

            val0 = sumbuf[x];
            val1 = sumbuf[x+1];
            
            val0 += trow2[x];
            val1 += trow2[x+1];

            tdst2[x] = (short)val0;
            tdst2[x+1] = (short)val1;

            sumbuf[x] = val0 - trow[x];
            sumbuf[x+1] = val1 - trow[x+1];

            val0 = sumbuf[x+2];
            val1 = sumbuf[x+3];
            
            val0 += trow2[x+2];
            val1 += trow2[x+3];

            tdst2[x+2] = (short)val0;
            tdst2[x+3] = (short)val1;

            sumbuf[x+2] = val0 - trow[x+2];
            sumbuf[x+3] = val1 - trow[x+3];
        }

        if( width_rest )
        {
            if( need_copy )
                CV_COPY( dst, tbufw, width_n, x );
            else
                CV_COPY( dst + width_n, tbufw + width_n, CV_MORPH_ALIGN, x );
        }

        rows[ker_y] = saved_row;

        /* rotate buffer */
        {
            int *t = rows[0];

            CV_COPY( rows, rows + 1, ker_height - 1, i );
            rows[i] = t;
            crows--;
            dst += dstStep;
        }
    }
    while( ++y < dst_height );

    roiSize->height = y;
    state->crows = crows;

    return CV_OK;
}


IPCVAPI( CvStatus,
     icvBlur_32f_CnR, ( const float* src, int srcStep,
                        float* dst, int dstStep, CvSize * roiSize,
                        CvFilterState* state, int stage ));

IPCVAPI_IMPL( CvStatus,
     icvBlur_32f_CnR, ( const float* pSrc, int srcStep,
                        float* dst, int dstStep, CvSize * roiSize,
                        CvFilterState* state, int stage ))
{
    float* src = (float*)pSrc;
    int width = roiSize->width;
    int src_height = roiSize->height;
    int dst_height = src_height;
    int x, y = 0, i;

    int ker_x = state->ker_x;
    int ker_y = state->ker_y;
    int ker_width = state->ker_width;
    int ker_height = state->ker_height;
    int ker_right = ker_width - ker_x;

    int crows = state->crows;
    float **rows = (float**)(state->rows);
    float *tbuf = (float*)(state->tbuf);
    float *sumbuf = (float*)((char*)state->tbuf + state->buffer_step);
    float *trow, *trow2;

    int channels = state->channels;
    int ker_x_n = ker_x * channels;
    int ker_width_n = ker_width * channels;
    int ker_right_n = ker_right * channels;
    int width_n = width * channels;

    int is_small_width = width < MAX( ker_x, ker_right );
    int starting_flag = 0;
    int width_rest = width_n & (CV_MORPH_ALIGN - 1);
    float scale = (float)(1./state->divisor);
    int no_scale = state->divisor == 1;

    srcStep /= sizeof(float);
    dstStep /= sizeof(float);

    /* initialize cyclic buffer when starting */
    if( stage == CV_WHOLE || stage == CV_START )
    {
        for( i = 0; i < ker_height; i++ )
            rows[i] = (float*)(state->buffer + state->buffer_step * i);

        crows = ker_y;
        if( stage != CV_WHOLE )
            dst_height -= ker_height - ker_y - 1;
        starting_flag = 1;
    }

    if( stage == CV_END )
        dst_height += ker_height - ker_y - 1;

    do
    {
        int need_copy = is_small_width | (y == 0);
        float *tsrc;
        float *tdst;
        float *tdst2;
        float *saved_row = rows[ker_y];

        /* fill cyclic buffer - horizontal filtering */
        for( ; crows < ker_height; crows++ )
        {
            tsrc = src - ker_x_n;
            tdst = rows[crows];

            if( src_height-- <= 0 )
            {
                if( stage != CV_WHOLE && stage != CV_END )
                    break;
                /* duplicate last row */
                trow = rows[crows - 1];
                CV_COPY( tdst, trow, width_n, x );
                continue;
            }

            need_copy |= src_height == 1;

            if( ker_width > 1 )
            {
                if( need_copy )
                {
                    tsrc = tbuf - ker_x_n;
                    CV_COPY( tbuf, src, width_n, x );
                }
                else
                {
                    CV_COPY( tbuf - ker_x_n, src - ker_x_n, ker_x_n, x );
                    CV_COPY( tbuf, src + width_n, ker_right_n, x );
                }

                if( channels == 1 )
                {
                    /* make replication borders */
                    float pix = tsrc[ker_x];
                    float t0 = 0;

                    CV_SET( tsrc, pix, ker_x, x );

                    pix = tsrc[width + ker_x - 1];
                    CV_SET( tsrc + width + ker_x, pix, ker_right, x );

                    for( i = 0; i < ker_width_n - 1; i++ )
                        t0 += tsrc[i];

                    /* horizontal blurring */
                    for( i = ker_width_n; i < width_n + ker_width_n; i++ )
                    {
                        t0 += tsrc[i-1];
                        tdst[i-ker_width_n] = t0;
                        t0 -= tsrc[i - ker_width_n];
                    }
                }
                else if( channels == 3 )
                {
                    /* make replication borders */
                    CvRGB32f pix = ((CvRGB32f *)tsrc)[ker_x];
                    float t0 = 0, t1 = 0, t2 = 0;

                    CV_SET( (CvRGB32f *) tsrc, pix, ker_x, x );

                    pix = ((CvRGB32f *) tsrc)[width + ker_x - 1];
                    CV_SET( (CvRGB32f *) tsrc + width + ker_x, pix, ker_right, x );

                    for( i = 0; i < ker_width_n - 3; i += 3 )
                    {
                        t0 += tsrc[i];
                        t1 += tsrc[i+1];
                        t2 += tsrc[i+2];
                    }

                    /* horizontal blurring */
                    for( i = ker_width_n; i < width_n + ker_width_n; i += 3 )
                    {
                        t0 += tsrc[i-3];
                        t1 += tsrc[i-2];

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?