|
|
@ -577,6 +577,62 @@ void cv::Laplacian( InputArray _src, OutputArray _dst, int ddepth, int ksize, |
|
|
|
ddepth = sdepth; |
|
|
|
ddepth = sdepth; |
|
|
|
_dst.create( _src.size(), CV_MAKETYPE(ddepth, cn) ); |
|
|
|
_dst.create( _src.size(), CV_MAKETYPE(ddepth, cn) ); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#if defined HAVE_IPP && !defined HAVE_IPP_ICV_ONLY |
|
|
|
|
|
|
|
if ((ksize == 3 || ksize == 5) && ((borderType & BORDER_ISOLATED) != 0 || !_src.isSubmatrix()) && |
|
|
|
|
|
|
|
((stype == CV_8UC1 && ddepth == CV_16S) || (ddepth == CV_32F && stype == CV_32FC1))) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
int iscale = saturate_cast<int>(scale), idelta = saturate_cast<int>(delta); |
|
|
|
|
|
|
|
bool floatScale = std::fabs(scale - iscale) > DBL_EPSILON, needScale = iscale != 1; |
|
|
|
|
|
|
|
bool floatDelta = std::fabs(delta - idelta) > DBL_EPSILON, needDelta = delta != 0; |
|
|
|
|
|
|
|
int borderTypeNI = borderType & ~BORDER_ISOLATED; |
|
|
|
|
|
|
|
Mat src = _src.getMat(), dst = _dst.getMat(); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (src.data != dst.data) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
Ipp32s bufsize; |
|
|
|
|
|
|
|
IppStatus status = (IppStatus)-1; |
|
|
|
|
|
|
|
IppiSize roisize = { src.cols, src.rows }; |
|
|
|
|
|
|
|
IppiMaskSize masksize = ksize == 3 ? ippMskSize3x3 : ippMskSize5x5; |
|
|
|
|
|
|
|
IppiBorderType borderTypeIpp = ippiGetBorderType(borderTypeNI); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#define IPP_FILTER_LAPLACIAN(ippsrctype, ippdsttype, ippfavor) \ |
|
|
|
|
|
|
|
do \
|
|
|
|
|
|
|
|
{ \
|
|
|
|
|
|
|
|
if (borderTypeIpp >= 0 && ippiFilterLaplacianGetBufferSize_##ippfavor##_C1R(roisize, masksize, &bufsize) >= 0) \
|
|
|
|
|
|
|
|
{ \
|
|
|
|
|
|
|
|
Ipp8u * buffer = ippsMalloc_8u(bufsize); \
|
|
|
|
|
|
|
|
status = ippiFilterLaplacianBorder_##ippfavor##_C1R((const ippsrctype *)src.data, (int)src.step, (ippdsttype *)dst.data, \
|
|
|
|
|
|
|
|
(int)dst.step, roisize, masksize, borderTypeIpp, 0, buffer); \
|
|
|
|
|
|
|
|
ippsFree(buffer); \
|
|
|
|
|
|
|
|
} \
|
|
|
|
|
|
|
|
} while ((void)0, 0) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (sdepth == CV_8U && ddepth == CV_16S && !floatScale && !floatDelta) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
IPP_FILTER_LAPLACIAN(Ipp8u, Ipp16s, 8u16s); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (needScale && status >= 0) |
|
|
|
|
|
|
|
status = ippiMulC_16s_C1IRSfs((Ipp16s)iscale, (Ipp16s *)dst.data, (int)dst.step, roisize, 0); |
|
|
|
|
|
|
|
if (needDelta && status >= 0) |
|
|
|
|
|
|
|
status = ippiAddC_16s_C1IRSfs((Ipp16s)idelta, (Ipp16s *)dst.data, (int)dst.step, roisize, 0); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
else if (sdepth == CV_32F && ddepth == CV_32F) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
IPP_FILTER_LAPLACIAN(Ipp32f, Ipp32f, 32f); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (needScale && status >= 0) |
|
|
|
|
|
|
|
status = ippiMulC_32f_C1IR((Ipp32f)scale, (Ipp32f *)dst.data, (int)dst.step, roisize); |
|
|
|
|
|
|
|
if (needDelta && status >= 0) |
|
|
|
|
|
|
|
status = ippiAddC_32f_C1IR((Ipp32f)delta, (Ipp32f *)dst.data, (int)dst.step, roisize); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (status >= 0) |
|
|
|
|
|
|
|
return; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
#undef IPP_FILTER_LAPLACIAN |
|
|
|
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
#ifdef HAVE_TEGRA_OPTIMIZATION |
|
|
|
#ifdef HAVE_TEGRA_OPTIMIZATION |
|
|
|
if (scale == 1.0 && delta == 0) |
|
|
|
if (scale == 1.0 && delta == 0) |
|
|
|
{ |
|
|
|
{ |
|
|
|