-
Notifications
You must be signed in to change notification settings - Fork 8
/
Copy pathinterp2.cpp
110 lines (93 loc) · 4.05 KB
/
interp2.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
// interp2.cpp
//
// Copyright (C) Jongwoo Lim.
// All rights reserved.
//
//////////////////////////////////////////////////////////////////////
#include "mex.h"
#include <math.h>
//#include "cvbase/cvimage.h"
#define ARR(A,r,c,nr,nc) (((r)<0 || (r)>=(nr) || (c)<0 || (c)>=(nc))? 0 : (A)[(c)*(nr)+(r)])
inline double interp(double *img, int w, int h, double x, double y)
{
register int x0 = (int) x, y0 = (int) y, x1 = x0+1, y1 = y0+1;
register double rx0 = x-x0, rx1 = 1-rx0, ry = y-y0;
return ((rx1*ARR(img,y0,x0,h,w) + rx0*ARR(img,y0,x1,h,w))*(1-ry) +
(rx1*ARR(img,y1,x0,h,w) + rx0*ARR(img,y1,x1,h,w))*ry);
}
//-----------------------------------------------------------------------------
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
// check inputs
if (nrhs < 3 || nrhs > 6)
mexErrMsgTxt("invalid number of inputs: [x,y,]z,xi,yi[,method]");
if (nlhs != 1)
mexErrMsgTxt("invalid number of outputs: zi");
const char *_argin[] = { "x","y","z","xi","yi","method" };
const char **argin = (nrhs < 4)? &_argin[2] : _argin;
char buf[1024];
// Check input data
const mxArray *X = NULL, *Y = NULL, *Z, *XI, *YI;
if (nrhs < 4)
Z = prhs[0], XI = prhs[1], YI = prhs[2];
else
X = prhs[0], Y = prhs[1], Z = prhs[2], XI = prhs[3], YI = prhs[4];
if (nrhs == 4 || nrhs == 6)
nrhs--; // Ignore method
for (int ri = 0; ri < nrhs; ri++) {
if (!prhs[ri])
{ sprintf(buf,"invalid mxArray(%s)", argin[ri]); mexErrMsgTxt(buf); }
if (!mxIsDouble(prhs[ri]))
{ sprintf(buf,"data must be double (%s)", argin[ri]); mexErrMsgTxt(buf); }
}
if (mxGetNumberOfDimensions(Z) != 2)
mexErrMsgTxt("invalid Z dimension: should be 2");
// Need to check whether dims of X,Y,Z matche
if (mxGetNumberOfElements(XI) != mxGetNumberOfElements(YI))
mexErrMsgTxt("XI and YI does not match");
// Build output data
const int *dimz = mxGetDimensions(Z), *dim = mxGetDimensions(XI);
int ndim = mxGetNumberOfDimensions(XI);
register double dx = -1, dy = -1, sx = 1, sy = 1;
if (nrhs >= 4) {
int nx = mxGetNumberOfElements(X), ny = mxGetNumberOfElements(Y);
double *pX = mxGetPr(X), *pY = mxGetPr(Y);
if (nx == dimz[1] && ny == dimz[0])
dx = -pX[0], sx = (dimz[1]-1)/(pX[nx-1]-pX[0]),
dy = -pY[0], sy = (dimz[0]-1)/(pY[ny-1]-pY[0]);
else if (nx == ny && ny == mxGetNumberOfElements(Z))
dx = -pX[0], sx = (dimz[1]-1)/(pX[(dimz[1]-1)*dimz[0]]-pX[0]),
dy = -pY[0], sy = (dimz[0]-1)/(pY[dimz[0]-1]-pY[0]);
else
mexErrMsgTxt("X and Y do not match with Z");
}
if (mxIsComplex(Z)) {
mxArray *ZI = plhs[0] = mxCreateNumericArray(ndim, dim, mxDOUBLE_CLASS, mxCOMPLEX);
// Load input data and fill output array
double *pZr = mxGetPr(Z), *pZi = mxGetPi(Z), *pXI = mxGetPr(XI), *pYI = mxGetPr(YI);
double *pZIr = mxGetPr(ZI), *pZIi = mxGetPi(ZI);
// cvImage<double> imgr(pZr, dimz[0], dimz[1]), imgi(pZi, dimz[0], dimz[1]);
int h = dimz[0], w = dimz[1];
for (int i = 0, n = mxGetNumberOfElements(XI); i < n; i++) {
pZIr[i] = interp(pZr, w,h, sx*(pXI[i]+dx), sy*(pYI[i]+dy));
pZIi[i] = interp(pZi, w,h, sx*(pXI[i]+dx), sy*(pYI[i]+dy));
// cvtPoint<double> p(sy*(pYI[i]+dy),sx*(pXI[i]+dx));
// pZIr[i] = imgr.interp<double,double>(p);
// pZIi[i] = imgi.interp<double,double>(p);
}
}
else {
mxArray *ZI = plhs[0] = mxCreateNumericArray(ndim, dim, mxDOUBLE_CLASS, mxREAL);
// Load input data and fill output array
double *pZ = mxGetPr(Z), *pXI = mxGetPr(XI), *pYI = mxGetPr(YI);
double *pZI = mxGetPr(ZI);
// cvImage<double> img(pZ, dimz[0], dimz[1]);
int h = dimz[0], w = dimz[1];
for (int i = 0, n = mxGetNumberOfElements(XI); i < n; i++) {
pZI[i] = interp(pZ, w,h, sx*(pXI[i]+dx), sy*(pYI[i]+dy));
// cvtPoint<double> p(sy*(pYI[i]+dy),sx*(pXI[i]+dx));
// pZI[i] = img.interp<double,double>(p);
}
}
}
//-----------------------------------------------------------------------------