cvscanlines.cpp.svn-base
来自「非结构化路识别」· SVN-BASE 代码 · 共 2,039 行 · 第 1/4 页
SVN-BASE
2,039 行
/*M///////////////////////////////////////////////////////////////////////////////////////
//
// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
//
// By downloading, copying, installing or using the software you agree to this license.
// If you do not agree to this license, do not download, install,
// copy or use the software.
//
//
// Intel License Agreement
// For Open Source Computer Vision Library
//
// Copyright (C) 2000, Intel Corporation, all rights reserved.
// Third party copyrights are property of their respective owners.
//
// Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met:
//
// * Redistribution's of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistribution's in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// * The name of Intel Corporation may not be used to endorse or promote products
// derived from this software without specific prior written permission.
//
// This software is provided by the copyright holders and contributors "as is" and
// any express or implied warranties, including, but not limited to, the implied
// warranties of merchantability and fitness for a particular purpose are disclaimed.
// In no event shall the Intel Corporation or contributors be liable for any direct,
// indirect, incidental, special, exemplary, or consequential damages
// (including, but not limited to, procurement of substitute goods or services;
// loss of use, data, or profits; or business interruption) however caused
// and on any theory of liability, whether in contract, strict liability,
// or tort (including negligence or otherwise) arising in any way out of
// the use of this software, even if advised of the possibility of such damage.
//
//M*/
#include "_cv.h"
#include "_cvvm.h"
//#define REAL_ZERO(x) ( (x) < 1e-8 && (x) > -1e-8)
static CvStatus
icvGetNormalVector3( CvMatrix3 * Matrix, float *v )
{
/* return vector v that is any 3-vector perpendicular
to all the row vectors of Matrix */
double *solutions = 0;
double M[3 * 3];
double B[3] = { 0.f, 0.f, 0.f };
int i, j, res;
if( Matrix == 0 || v == 0 )
return CV_NULLPTR_ERR;
for( i = 0; i < 3; i++ )
{
for( j = 0; j < 3; j++ )
M[i * 3 + j] = (double) (Matrix->m[i][j]);
} /* for */
res = icvGaussMxN( M, B, 3, 3, &solutions );
if( res == -1 )
return CV_BADFACTOR_ERR;
if( res > 0 && solutions )
{
v[0] = (float) solutions[0];
v[1] = (float) solutions[1];
v[2] = (float) solutions[2];
res = 0;
}
else
res = 1;
if( solutions )
icvFree( &solutions );
if( res )
return CV_BADFACTOR_ERR;
else
return CV_NO_ERR;
} /* icvgetNormalVector3 */
/*=====================================================================================*/
static CvStatus
icvMultMatrixVector3( CvMatrix3 * m, float *src, float *dst )
{
if( m == 0 || src == 0 || dst == 0 )
return CV_NULLPTR_ERR;
dst[0] = m->m[0][0] * src[0] + m->m[0][1] * src[1] + m->m[0][2] * src[2];
dst[1] = m->m[1][0] * src[0] + m->m[1][1] * src[1] + m->m[1][2] * src[2];
dst[2] = m->m[2][0] * src[0] + m->m[2][1] * src[1] + m->m[2][2] * src[2];
return CV_NO_ERR;
} /* icvMultMatrixVector3 */
/*=====================================================================================*/
static CvStatus
icvMultMatrixTVector3( CvMatrix3 * m, float *src, float *dst )
{
if( m == 0 || src == 0 || dst == 0 )
return CV_NULLPTR_ERR;
dst[0] = m->m[0][0] * src[0] + m->m[1][0] * src[1] + m->m[2][0] * src[2];
dst[1] = m->m[0][1] * src[0] + m->m[1][1] * src[1] + m->m[2][1] * src[2];
dst[2] = m->m[0][2] * src[0] + m->m[1][2] * src[1] + m->m[2][2] * src[2];
return CV_NO_ERR;
} /* icvMultMatrixTVector3 */
/*=====================================================================================*/
static CvStatus
icvCrossLines( float *line1, float *line2, float *cross_point )
{
float delta;
if( line1 == 0 && line2 == 0 && cross_point == 0 )
return CV_NULLPTR_ERR;
delta = line1[0] * line2[1] - line1[1] * line2[0];
if( REAL_ZERO( delta ))
return CV_BADFACTOR_ERR;
cross_point[0] = (-line1[2] * line2[1] + line1[1] * line2[2]) / delta;
cross_point[1] = (-line1[0] * line2[2] + line1[2] * line2[0]) / delta;
cross_point[2] = 1;
return CV_NO_ERR;
} /* icvCrossLines */
/*======================================================================================*/
CvStatus
icvMakeScanlines( CvMatrix3 * matrix,
CvSize imgSize,
int *scanlines_1, int *scanlines_2, int *lens_1, int *lens_2, int *numlines )
{
CvStatus error;
error = icvGetCoefficient( matrix, imgSize, scanlines_2, scanlines_1, numlines );
/* Make Length of scanlines */
if( scanlines_1 == 0 && scanlines_2 == 0 )
return error;
icvMakeScanlinesLengths( scanlines_1, *numlines, lens_1 );
icvMakeScanlinesLengths( scanlines_2, *numlines, lens_2 );
matrix = matrix;
return CV_NO_ERR;
} /* icvMakeScanlines */
/*======================================================================================*/
CvStatus
icvMakeScanlinesLengths( int *scanlines, int numlines, int *lens )
{
int index;
int x1, y1, x2, y2, dx, dy;
int curr;
curr = 0;
for( index = 0; index < numlines; index++ )
{
x1 = scanlines[curr++];
y1 = scanlines[curr++];
x2 = scanlines[curr++];
y2 = scanlines[curr++];
dx = abs( x1 - x2 ) + 1;
dy = abs( y1 - y2 ) + 1;
lens[index] = MAX( dx, dy );
}
return CV_NO_ERR;
}
/*======================================================================================*/
CvStatus
icvMakeAlphaScanlines( int *scanlines_1,
int *scanlines_2,
int *scanlines_a, int *lens, int numlines, float alpha )
{
int index;
int x1, y1, x2, y2;
int curr;
int dx, dy;
int curr_len;
curr = 0;
curr_len = 0;
for( index = 0; index < numlines; index++ )
{
x1 = (int) (scanlines_1[curr] * alpha + scanlines_2[curr] * (1.0 - alpha));
scanlines_a[curr++] = x1;
y1 = (int) (scanlines_1[curr] * alpha + scanlines_2[curr] * (1.0 - alpha));
scanlines_a[curr++] = y1;
x2 = (int) (scanlines_1[curr] * alpha + scanlines_2[curr] * (1.0 - alpha));
scanlines_a[curr++] = x2;
y2 = (int) (scanlines_1[curr] * alpha + scanlines_2[curr] * (1.0 - alpha));
scanlines_a[curr++] = y2;
dx = abs( x1 - x2 ) + 1;
dy = abs( y1 - y2 ) + 1;
lens[curr_len++] = MAX( dx, dy );
}
return CV_NO_ERR;
}
/*======================================================================================*/
/* //////////////////////////////////////////////////////////////////////////////////// */
CvStatus
icvGetCoefficient( CvMatrix3 * matrix,
CvSize imgSize, int *scanlines_1, int *scanlines_2, int *numlines )
{
float l_epipole[3];
float r_epipole[3];
CvMatrix3 *F;
CvMatrix3 Ft;
CvStatus error;
int i, j;
F = matrix;
l_epipole[2] = -1;
r_epipole[2] = -1;
if( F == 0 )
{
error = icvGetCoefficientDefault( matrix,
imgSize, scanlines_1, scanlines_2, numlines );
return error;
}
for( i = 0; i < 3; i++ )
for( j = 0; j < 3; j++ )
Ft.m[i][j] = F->m[j][i];
error = icvGetNormalVector3( &Ft, l_epipole );
if( error == CV_NO_ERR && !REAL_ZERO( l_epipole[2] ) && !REAL_ZERO( l_epipole[2] - 1 ))
{
l_epipole[0] /= l_epipole[2];
l_epipole[1] /= l_epipole[2];
l_epipole[2] = 1;
} /* if */
error = icvGetNormalVector3( F, r_epipole );
if( error == CV_NO_ERR && !REAL_ZERO( r_epipole[2] ) && !REAL_ZERO( r_epipole[2] - 1 ))
{
r_epipole[0] /= r_epipole[2];
r_epipole[1] /= r_epipole[2];
r_epipole[2] = 1;
} /* if */
if( REAL_ZERO( l_epipole[2] - 1 ) && REAL_ZERO( r_epipole[2] - 1 ))
{
error = icvGetCoefficientStereo( matrix,
imgSize,
l_epipole,
r_epipole, scanlines_1, scanlines_2, numlines );
if( error == CV_NO_ERR )
return CV_NO_ERR;
}
else
{
if( REAL_ZERO( l_epipole[2] ) && REAL_ZERO( r_epipole[2] ))
{
error = icvGetCoefficientOrto( matrix,
imgSize, scanlines_1, scanlines_2, numlines );
if( error == CV_NO_ERR )
return CV_NO_ERR;
}
}
error = icvGetCoefficientDefault( matrix, imgSize, scanlines_1, scanlines_2, numlines );
return error;
} /* icvlGetCoefficient */
/*===========================================================================*/
CvStatus
icvGetCoefficientDefault( CvMatrix3 * matrix,
CvSize imgSize, int *scanlines_1, int *scanlines_2, int *numlines )
{
int curr;
int y;
*numlines = imgSize.height;
if( scanlines_1 == 0 && scanlines_2 == 0 )
return CV_NO_ERR;
curr = 0;
for( y = 0; y < imgSize.height; y++ )
{
scanlines_1[curr] = 0;
scanlines_1[curr + 1] = y;
scanlines_1[curr + 2] = imgSize.width - 1;
scanlines_1[curr + 3] = y;
scanlines_2[curr] = 0;
scanlines_2[curr + 1] = y;
scanlines_2[curr + 2] = imgSize.width - 1;
scanlines_2[curr + 3] = y;
curr += 4;
}
matrix = matrix;
return CV_NO_ERR;
} /* icvlGetCoefficientDefault */
/*===========================================================================*/
CvStatus
icvGetCoefficientOrto( CvMatrix3 * matrix,
CvSize imgSize, int *scanlines_1, int *scanlines_2, int *numlines )
{
float l_start_end[4], r_start_end[4];
CvStatus error;
CvMatrix3 *F;
F = matrix;
if( F->m[0][2] * F->m[1][2] < 0 )
{ /* on left / */
if( F->m[2][0] * F->m[2][1] < 0 )
{ /* on right / */
error = icvGetStartEnd1( F, imgSize, l_start_end, r_start_end );
}
else
{ /* on right \ */
error = icvGetStartEnd2( F, imgSize, l_start_end, r_start_end );
} /* if */
}
else
{ /* on left \ */
if( F->m[2][0] * F->m[2][1] < 0 )
{ /* on right / */
error = icvGetStartEnd3( F, imgSize, l_start_end, r_start_end );
}
else
{ /* on right \ */
error = icvGetStartEnd4( F, imgSize, l_start_end, r_start_end );
} /* if */
} /* if */
if( error != CV_NO_ERR )
return error;
if( fabs( l_start_end[0] - l_start_end[2] ) > fabs( r_start_end[0] - r_start_end[2] ))
{
error = icvBuildScanlineLeft( F,
imgSize,
scanlines_1, scanlines_2, l_start_end, numlines );
}
else
{
error = icvBuildScanlineRight( F,
imgSize,
scanlines_1, scanlines_2, r_start_end, numlines );
} /* if */
return error;
} /* icvlGetCoefficientOrto */
/*===========================================================================*/
CvStatus
icvGetStartEnd1( CvMatrix3 * matrix, CvSize imgSize, float *l_start_end, float *r_start_end )
{
CvMatrix3 *F;
int width, height;
float l_diagonal[3];
float r_diagonal[3];
float l_point[3], r_point[3], epiline[3];
CvStatus error = CV_OK;
F = matrix;
width = imgSize.width - 1;
height = imgSize.height - 1;
l_diagonal[0] = (float) 1 / width;
l_diagonal[1] = (float) 1 / height;
l_diagonal[2] = -1;
r_diagonal[0] = (float) 1 / width;
r_diagonal[1] = (float) 1 / height;
r_diagonal[2] = -1;
r_point[0] = (float) width;
r_point[1] = 0;
r_point[2] = 1;
icvMultMatrixVector3( F, r_point, epiline );
error = icvCrossLines( l_diagonal, epiline, l_point );
assert( error == CV_NO_ERR );
if( l_point[0] >= 0 && l_point[0] <= width )
{
l_start_end[0] = l_point[0];
l_start_end[1] = l_point[1];
r_start_end[0] = r_point[0];
r_start_end[1] = r_point[1];
}
else
{
if( l_point[0] < 0 )
{
l_point[0] = 0;
l_point[1] = (float) height;
l_point[2] = 1;
icvMultMatrixTVector3( F, l_point, epiline );
error = icvCrossLines( r_diagonal, epiline, r_point );
assert( error == CV_NO_ERR );
if( r_point[0] >= 0 && r_point[0] <= width )
{
l_start_end[0] = l_point[0];
l_start_end[1] = l_point[1];
r_start_end[0] = r_point[0];
r_start_end[1] = r_point[1];
}
else
return CV_BADFACTOR_ERR;
}
else
{ /* if( l_point[0] > width ) */
l_point[0] = (float) width;
l_point[1] = 0;
l_point[2] = 1;
icvMultMatrixTVector3( F, l_point, epiline );
error = icvCrossLines( r_diagonal, epiline, r_point );
assert( error == CV_NO_ERR );
if( r_point[0] >= 0 && r_point[0] <= width )
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?