Commit ddf19dcf authored by Andrey Filippov's avatar Andrey Filippov

working on clt correlation

parent 7c36f258
...@@ -31,7 +31,9 @@ public class DttRad2 { ...@@ -31,7 +31,9 @@ public class DttRad2 {
int N = 0; int N = 0;
double [][][] CII= null; double [][][] CII= null;
double [][][] CIIe= null; // alternative matrix with all coefficients the same (non-orthogonal, but matching DFT) double [][][] CIIe= null; // alternative matrix with all coefficients the same (non-orthogonal, but matching DFT)
double [][][] CIIIe= null; // alternative matrix with k0=1/2, k(n-1) = 1/2 (non-orthogonal, but matching DFT) double [][][] CIIIe= null; // alternative matrix with k0=1/2, k(n-1) = 1/2 (non-orthogonal, but matching DFT)
double [][][] SIIe= null; // alternative matrix with all coefficients the same (non-orthogonal, but matching DFT)
double [][][] SIIIe= null; // alternative matrix with k0=1/2, k(n-1) = 1/2 (non-orthogonal, but matching DFT)
double [][][] CIV= null; double [][][] CIV= null;
double [][][] SIV= null; double [][][] SIV= null;
...@@ -378,22 +380,28 @@ public class DttRad2 { ...@@ -378,22 +380,28 @@ public class DttRad2 {
} }
public double [] dttt_iie(double [] x){ public double [] dttt_iie(double [] x){
return dttt_iie(x, 1 << (ilog2(x.length)/2)); return dttt_iie(x,0, 1 << (ilog2(x.length)/2));
}
public double [] dttt_iie(double [] x, int mode){
return dttt_iie(x, mode, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iie(double [] x, int n){ public double [] dttt_iie(double [] x, int mode, int n){
double [] y = new double [n*n]; double [] y = new double [n*n];
double [] line = new double[n]; double [] line = new double[n];
// first (horizontal) pass // first (horizontal) pass
for (int i = 0; i<n; i++){ for (int i = 0; i<n; i++){
System.arraycopy(x, n*i, line, 0, n); System.arraycopy(x, n*i, line, 0, n);
line = dctiie_direct(line); // line = dctiie_direct(line);
line = ((mode & 1)!=0)? dstiie_direct(line):dctiie_direct(line);
for (int j=0; j < n;j++) y[j*n+i] =line[j]; // transpose for (int j=0; j < n;j++) y[j*n+i] =line[j]; // transpose
} }
// second (vertical) pass // second (vertical) pass
for (int i = 0; i<n; i++){ for (int i = 0; i<n; i++){
System.arraycopy(y, n*i, line, 0, n); System.arraycopy(y, n*i, line, 0, n);
line = dctiie_direct(line); // line = dctiie_direct(line);
line = ((mode & 2)!=0)? dstiie_direct(line):dctiie_direct(line);
System.arraycopy(line, 0, y, n*i, n); System.arraycopy(line, 0, y, n*i, n);
} }
return y; return y;
...@@ -425,22 +433,27 @@ public class DttRad2 { ...@@ -425,22 +433,27 @@ public class DttRad2 {
} }
public double [] dttt_iiie(double [] x){ public double [] dttt_iiie(double [] x){
return dttt_iiie(x, 1 << (ilog2(x.length)/2)); return dttt_iiie(x,0, 1 << (ilog2(x.length)/2));
}
public double [] dttt_iiie(double [] x, int mode){
return dttt_iiie(x, mode, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iiie(double [] x, int n){ public double [] dttt_iiie(double [] x, int mode, int n){
double [] y = new double [n*n]; double [] y = new double [n*n];
double [] line = new double[n]; double [] line = new double[n];
// first (horizontal) pass // first (horizontal) pass
for (int i = 0; i<n; i++){ for (int i = 0; i<n; i++){
System.arraycopy(x, n*i, line, 0, n); System.arraycopy(x, n*i, line, 0, n);
line = dctiiie_direct(line); // line = dctiiie_direct(line);
line = ((mode & 1)!=0)? dstiiie_direct(line):dctiiie_direct(line);
for (int j=0; j < n;j++) y[j*n+i] =line[j]; // transpose for (int j=0; j < n;j++) y[j*n+i] =line[j]; // transpose
} }
// second (vertical) pass // second (vertical) pass
for (int i = 0; i<n; i++){ for (int i = 0; i<n; i++){
System.arraycopy(y, n*i, line, 0, n); System.arraycopy(y, n*i, line, 0, n);
line = dctiiie_direct(line); // line = dctiiie_direct(line);
line = ((mode & 2)!=0)? dstiiie_direct(line):dctiiie_direct(line);
System.arraycopy(line, 0, y, n*i, n); System.arraycopy(line, 0, y, n*i, n);
} }
return y; return y;
...@@ -608,6 +621,38 @@ public class DttRad2 { ...@@ -608,6 +621,38 @@ public class DttRad2 {
return y; return y;
} }
public double [] dstiie_direct(double[] x){
int n = x.length;
int t = ilog2(n)-1;
if (SIIe==null){
setup_SIIe(N); // just full size
}
double [] y = new double[n];
for (int i = 0; i<n; i++) {
y[i] = 0.0;
for (int j = 0; j< n; j++){
y[i]+= SIIe[t][i][j]*x[j];
}
}
return y;
}
public double [] dstiiie_direct(double[] x){
int n = x.length;
int t = ilog2(n)-1;
if (SIIIe==null){
setup_SIIIe(N); // just full size
}
double [] y = new double[n];
for (int i = 0; i<n; i++) {
y[i] = 0.0;
for (int j = 0; j< n; j++){
y[i]+= SIIIe[t][i][j]*x[j];
}
}
return y;
}
public double [] dstiv_direct(double[] x){ public double [] dstiv_direct(double[] x){
int n = x.length; int n = x.length;
int t = ilog2(n)-1; int t = ilog2(n)-1;
...@@ -672,11 +717,8 @@ public class DttRad2 { ...@@ -672,11 +717,8 @@ public class DttRad2 {
int n = 2 << t; // for N==3: 2, 4, 8 int n = 2 << t; // for N==3: 2, 4, 8
CIIe[t] = new double[n][n]; CIIe[t] = new double[n][n];
double scale = Math.sqrt(2.0/n); double scale = Math.sqrt(2.0/n);
// double ej;
double pi_2n=Math.PI/(2*n); double pi_2n=Math.PI/(2*n);
for (int j=0;j<n; j++){ for (int j=0;j<n; j++){
// if (j==0) ej= Math.sqrt(0.5);
// else ej = 1.0;
for (int k = 0; k<n; k++){ for (int k = 0; k<n; k++){
CIIe[t][j][k] = scale * Math.cos(j*(2*k+1)*pi_2n); CIIe[t][j][k] = scale * Math.cos(j*(2*k+1)*pi_2n);
} }
...@@ -697,10 +739,9 @@ public class DttRad2 { ...@@ -697,10 +739,9 @@ public class DttRad2 {
double pi_2n=Math.PI/(2*n); double pi_2n=Math.PI/(2*n);
for (int j=0;j < n; j++){ for (int j=0;j < n; j++){
if ((j==0) || (j == (n-1))) ej= 0.5; // Math.sqrt(0.5); if ((j==0) || (j == (n-1))) ej= 0.5; // Math.sqrt(0.5);
// if (j==0) ej= 0.5; // Math.sqrt(0.5); // if (j==0) ej= 0.5; // Math.sqrt(0.5); Should it be this? https://en.wikipedia.org/wiki/Discrete_cosine_transform#DCT-III
else ej = 1.0; else ej = 1.0;
for (int k = 0; k<n; k++){ for (int k = 0; k<n; k++){
// CIIIe[t][j][k] = scale * ej * Math.cos(j*(2*k+1)*pi_2n);
CIIIe[t][k][j] = scale * ej * Math.cos(j*(2*k+1)*pi_2n); CIIIe[t][k][j] = scale * ej * Math.cos(j*(2*k+1)*pi_2n);
} }
} }
...@@ -729,6 +770,46 @@ public class DttRad2 { ...@@ -729,6 +770,46 @@ public class DttRad2 {
} }
} }
private void setup_SIIe(int maxN){
if (maxN > N) setup_arrays(maxN);
int l = ilog2(N);
if (!(SIIe==null) && (SIIe.length >= l)) return;
SIIe = new double[l][][]; // only needed for direct? Assign only when needed?
for (int t = 0; t<SIIe.length; t++) {
int n = 2 << t; // for N==3: 2, 4, 8
SIIe[t] = new double[n][n];
double scale = Math.sqrt(2.0/n);
double pi_2n=Math.PI/(2*n);
for (int j=0;j<n; j++){
for (int k = 0; k<n; k++){
SIIe[t][j][k] = scale * Math.sin((j+1)*(2*k+1)*pi_2n);
}
}
}
}
private void setup_SIIIe(int maxN){
if (maxN > N) setup_arrays(maxN);
int l = ilog2(N);
if (!(SIIIe==null) && (SIIIe.length >= l)) return;
SIIIe = new double[l][][]; // only needed for direct? Assign only when needed?
for (int t = 0; t<SIIIe.length; t++) {
int n = 2 << t; // for N==3: 2, 4, 8
SIIIe[t] = new double[n][n];
double scale = Math.sqrt(2.0/n);
double ej;
double pi_2n=Math.PI/(2*n);
for (int j=0;j < n; j++){
// if ((j==0) || (j == (n-1))) ej= 0.5; // Math.sqrt(0.5);
if (j == (n-1)) ej= 0.5; // Math.sqrt(0.5);
else ej = 1.0;
for (int k = 0; k<n; k++){
SIIIe[t][k][j] = scale * ej * Math.sin((j+1)*(2*k+1)*pi_2n);
}
}
}
}
private void setup_SIV(int maxN){ private void setup_SIV(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
......
...@@ -1767,14 +1767,18 @@ public class EyesisCorrectionParameters { ...@@ -1767,14 +1767,18 @@ public class EyesisCorrectionParameters {
} }
} }
public static class CLTParameters { public static class CLTParameters {
public int transform_size = 8; // public int transform_size = 8; //
public int clt_window = 1; // currently only 3 types of windows - 0 (none), 1 and 2 public int clt_window = 1; // currently only 3 types of windows - 0 (none), 1 and 2
public double shift_x = 0.0; public double shift_x = 0.0;
public double shift_y = 0.0; public double shift_y = 0.0;
public int iclt_mask = 15; // which transforms to combine public int iclt_mask = 15; // which transforms to combine
public int tileX = 258; // number of kernel tile (0..163) public int tileX = 258; // number of kernel tile (0..163)
public int tileY = 133; // number of kernel tile (0..122) public int tileY = 133; // number of kernel tile (0..122)
public int dbg_mode = 0; // 0 - normal, +1 - no DCT/IDCT public int dbg_mode = 0; // 0 - normal, +1 - no DCT/IDCT
public int ishift_x = 0; // debug feature - shift source image by this pixels left
public int ishift_y = 0; // debug feature - shift source image by this pixels down
public double fat_zero = 0.0; // modify phase correlation to prevent division by very small numbers
public double corr_sigma =0.8; // LPF correlarion sigma
public CLTParameters(){} public CLTParameters(){}
public void setProperties(String prefix,Properties properties){ public void setProperties(String prefix,Properties properties){
...@@ -1786,6 +1790,10 @@ public class EyesisCorrectionParameters { ...@@ -1786,6 +1790,10 @@ public class EyesisCorrectionParameters {
properties.setProperty(prefix+"tileX", this.tileX+""); properties.setProperty(prefix+"tileX", this.tileX+"");
properties.setProperty(prefix+"tileY", this.tileY+""); properties.setProperty(prefix+"tileY", this.tileY+"");
properties.setProperty(prefix+"dbg_mode", this.dbg_mode+""); properties.setProperty(prefix+"dbg_mode", this.dbg_mode+"");
properties.setProperty(prefix+"ishift_x", this.ishift_x+"");
properties.setProperty(prefix+"ishift_y", this.ishift_y+"");
properties.setProperty(prefix+"fat_zero", this.fat_zero+"");
properties.setProperty(prefix+"corr_sigma", this.corr_sigma+"");
} }
public void getProperties(String prefix,Properties properties){ public void getProperties(String prefix,Properties properties){
if (properties.getProperty(prefix+"transform_size")!=null) this.transform_size=Integer.parseInt(properties.getProperty(prefix+"transform_size")); if (properties.getProperty(prefix+"transform_size")!=null) this.transform_size=Integer.parseInt(properties.getProperty(prefix+"transform_size"));
...@@ -1796,6 +1804,10 @@ public class EyesisCorrectionParameters { ...@@ -1796,6 +1804,10 @@ public class EyesisCorrectionParameters {
if (properties.getProperty(prefix+"tileX")!=null) this.tileX=Integer.parseInt(properties.getProperty(prefix+"tileX")); if (properties.getProperty(prefix+"tileX")!=null) this.tileX=Integer.parseInt(properties.getProperty(prefix+"tileX"));
if (properties.getProperty(prefix+"tileY")!=null) this.tileY=Integer.parseInt(properties.getProperty(prefix+"tileY")); if (properties.getProperty(prefix+"tileY")!=null) this.tileY=Integer.parseInt(properties.getProperty(prefix+"tileY"));
if (properties.getProperty(prefix+"dbg_mode")!=null) this.dbg_mode=Integer.parseInt(properties.getProperty(prefix+"dbg_mode")); if (properties.getProperty(prefix+"dbg_mode")!=null) this.dbg_mode=Integer.parseInt(properties.getProperty(prefix+"dbg_mode"));
if (properties.getProperty(prefix+"ishift_x")!=null) this.ishift_x=Integer.parseInt(properties.getProperty(prefix+"ishift_x"));
if (properties.getProperty(prefix+"ishift_y")!=null) this.ishift_y=Integer.parseInt(properties.getProperty(prefix+"ishift_y"));
if (properties.getProperty(prefix+"fat_zero")!=null) this.fat_zero=Double.parseDouble(properties.getProperty(prefix+"fat_zero"));
if (properties.getProperty(prefix+"corr_sigma")!=null) this.corr_sigma=Double.parseDouble(properties.getProperty(prefix+"corr_sigma"));
} }
public boolean showDialog() { public boolean showDialog() {
GenericDialog gd = new GenericDialog("Set DCT parameters"); GenericDialog gd = new GenericDialog("Set DCT parameters");
...@@ -1807,7 +1819,10 @@ public class EyesisCorrectionParameters { ...@@ -1807,7 +1819,10 @@ public class EyesisCorrectionParameters {
gd.addNumericField("Tile X to extract (0..163)", this.tileX, 0); gd.addNumericField("Tile X to extract (0..163)", this.tileX, 0);
gd.addNumericField("Tile Y to extract (0..122)", this.tileY, 0); gd.addNumericField("Tile Y to extract (0..122)", this.tileY, 0);
gd.addNumericField("dbg_mode: 0 - normal, +1 - no DCT/IDCT, just fold", this.dbg_mode, 0); gd.addNumericField("dbg_mode: 0 - normal, +1 - no DCT/IDCT, just fold", this.dbg_mode, 0);
gd.addNumericField("ishift_x: shift source image by this pixels left", this.ishift_x, 0);
gd.addNumericField("ishift_x: shift source image by this pixels down", this.ishift_y, 0);
gd.addNumericField("Modify phase correlation to prevent division by very small numbers", this.fat_zero, 4);
gd.addNumericField("LPF correlarion sigma ", this.corr_sigma, 3);
WindowTools.addScrollBars(gd); WindowTools.addScrollBars(gd);
gd.showDialog(); gd.showDialog();
...@@ -1819,7 +1834,11 @@ public class EyesisCorrectionParameters { ...@@ -1819,7 +1834,11 @@ public class EyesisCorrectionParameters {
this.iclt_mask= (int) gd.getNextNumber(); this.iclt_mask= (int) gd.getNextNumber();
this.tileX= (int) gd.getNextNumber(); this.tileX= (int) gd.getNextNumber();
this.tileY= (int) gd.getNextNumber(); this.tileY= (int) gd.getNextNumber();
this.dbg_mode= (int) gd.getNextNumber(); this.dbg_mode= (int) gd.getNextNumber();
this.ishift_x= (int) gd.getNextNumber();
this.ishift_y= (int) gd.getNextNumber();
this.fat_zero = gd.getNextNumber();
this.corr_sigma = gd.getNextNumber();
return true; return true;
} }
} }
......
...@@ -790,7 +790,7 @@ public class EyesisDCT { ...@@ -790,7 +790,7 @@ public class EyesisDCT {
} }
// kernels[chn].st_kernels[nc][tileY][tileX]= dtt.dttt_iii(kernels[chn].st_kernels[nc][tileY][tileX]); // kernels[chn].st_kernels[nc][tileY][tileX]= dtt.dttt_iii(kernels[chn].st_kernels[nc][tileY][tileX]);
kernels[chn].st_kernels[nc][tileY][tileX]= dtt.dttt_iiie(kernels[chn].st_kernels[nc][tileY][tileX]); kernels[chn].st_kernels[nc][tileY][tileX]= dtt.dttt_iiie(kernels[chn].st_kernels[nc][tileY][tileX]); //, 0, dct_size)
} }
// System.out.println("tileY="+tileY); // System.out.println("tileY="+tileY);
} }
......
...@@ -333,6 +333,7 @@ private Panel panel1, ...@@ -333,6 +333,7 @@ private Panel panel1,
public static boolean MODE_3D=false; // 3D-related commands public static boolean MODE_3D=false; // 3D-related commands
public PixelMapping.InterSensor.DisparityTiles DISPARITY_TILES=null; public PixelMapping.InterSensor.DisparityTiles DISPARITY_TILES=null;
public ImagePlus DBG_IMP = null; public ImagePlus DBG_IMP = null;
public ImagePlus CORRELATE_IMP = null;
public class SyncCommand{ public class SyncCommand{
public boolean isRunning= false; public boolean isRunning= false;
...@@ -487,7 +488,8 @@ private Panel panel1, ...@@ -487,7 +488,8 @@ private Panel panel1,
addButton("Setup CLT parameters", panelClt1, color_configure); addButton("Setup CLT parameters", panelClt1, color_configure);
addButton("Select CLT image", panelClt1, color_configure); addButton("Select CLT image", panelClt1, color_configure);
addButton("CLT stack", panelClt1, color_process); addButton("CLT stack", panelClt1, color_process);
addButton("CLT test 1", panelClt1, color_process); addButton("Select second CLT image", panelClt1, color_configure);
addButton("CLT correlate", panelClt1, color_process);
addButton("CLT test 2", panelClt1, color_process); addButton("CLT test 2", panelClt1, color_process);
addButton("CLT test 3", panelClt1, color_process); addButton("CLT test 3", panelClt1, color_process);
addButton("CLT test 4", panelClt1, color_process); addButton("CLT test 4", panelClt1, color_process);
...@@ -3648,6 +3650,40 @@ private Panel panel1, ...@@ -3648,6 +3650,40 @@ private Panel panel1,
DBG_IMP = imp_src; DBG_IMP = imp_src;
} }
} else if (label.equals("Select second CLT image")) {
DEBUG_LEVEL=MASTER_DEBUG_LEVEL;
// IJ.showMessage("DCT test 1");
if (!CLT_PARAMETERS.showDialog()) return;
// process selected image stack
ImagePlus imp_src = WindowManager.getCurrentImage();
if (imp_src==null){
IJ.showMessage("Error","JP4 image or Bayer image stack required");
return;
}
if (imp_src.getStackSize()<3){ // convert JP4 to image stack
EyesisCorrectionParameters.SplitParameters split_parameters = new EyesisCorrectionParameters.SplitParameters(
1, // oversample;
// Add just for mdct (N/2)
CLT_PARAMETERS.transform_size/2, // addLeft
CLT_PARAMETERS.transform_size/2, // addTop
CLT_PARAMETERS.transform_size/2, // addRight
CLT_PARAMETERS.transform_size/2 // addBottom
);
ImageStack sourceStack= bayerToStack(imp_src, // source Bayer image, linearized, 32-bit (float))
split_parameters);
CORRELATE_IMP = new ImagePlus(imp_src.getTitle()+"-SPIT_CORRELATE"
+ "", sourceStack);
if (DEBUG_LEVEL > 1) {
CORRELATE_IMP.getProcessor().resetMinAndMax();
CORRELATE_IMP.show();
}
} else {
CORRELATE_IMP = imp_src;
}
/* ======================================================================== */ /* ======================================================================== */
} else if (label.equals("CLT stack")) { } else if (label.equals("CLT stack")) {
DEBUG_LEVEL=MASTER_DEBUG_LEVEL; DEBUG_LEVEL=MASTER_DEBUG_LEVEL;
...@@ -3687,6 +3723,8 @@ private Panel panel1, ...@@ -3687,6 +3723,8 @@ private Panel panel1,
DBG_IMP.getStack(), DBG_IMP.getStack(),
0, // CLT_PARAMETERS.kernel_chn, 0, // CLT_PARAMETERS.kernel_chn,
CLT_PARAMETERS, CLT_PARAMETERS,
CLT_PARAMETERS.ishift_x, //final int shiftX, // shift image horizontally (positive - right)
CLT_PARAMETERS.ishift_y, //final int shiftY, // shift image vertically (positive - down)
THREADS_MAX, DEBUG_LEVEL, UPDATE_STATUS); THREADS_MAX, DEBUG_LEVEL, UPDATE_STATUS);
/* /*
for (int chn = 0; chn < clt_data.length; chn++) { for (int chn = 0; chn < clt_data.length; chn++) {
...@@ -3740,7 +3778,7 @@ private Panel panel1, ...@@ -3740,7 +3778,7 @@ private Panel panel1,
CLT_PARAMETERS.transform_size, // final int CLT_PARAMETERS.transform_size, // final int
CLT_PARAMETERS.clt_window, //window_type CLT_PARAMETERS.clt_window, //window_type
CLT_PARAMETERS.iclt_mask, //which of 4 to transform back CLT_PARAMETERS.iclt_mask, //which of 4 to transform back
CLT_PARAMETERS.dbg_mode, //which of 4 to transform back CLT_PARAMETERS.dbg_mode, //which of 4 to transform back
THREADS_MAX, // maximal number of threads to launch THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel) DEBUG_LEVEL); // globalDebugLevel)
} }
...@@ -3751,6 +3789,280 @@ private Panel panel1, ...@@ -3751,6 +3789,280 @@ private Panel panel1,
true, true,
DBG_IMP.getTitle()+"-ICLT-"+CLT_PARAMETERS.iclt_mask); DBG_IMP.getTitle()+"-ICLT-"+CLT_PARAMETERS.iclt_mask);
return; return;
/* ======================================================================== */
} else if (label.equals("CLT correlate")) {
DEBUG_LEVEL=MASTER_DEBUG_LEVEL;
// IJ.showMessage("DCT test 1");
if (!CLT_PARAMETERS.showDialog()) return;
// process selected image stack
if (DBG_IMP == null) {
ImagePlus imp_src = WindowManager.getCurrentImage();
if (imp_src==null){
IJ.showMessage("Error","JP4 image or Bayer image stack required");
return;
}
// ImagePlus imp2;
if (imp_src.getStackSize()<3){ // convert JP4 to image stack
EyesisCorrectionParameters.SplitParameters split_parameters = new EyesisCorrectionParameters.SplitParameters(
1, // oversample;
CLT_PARAMETERS.transform_size/2, // addLeft
CLT_PARAMETERS.transform_size/2, // addTop
CLT_PARAMETERS.transform_size/2, // addRight
CLT_PARAMETERS.transform_size/2 // addBottom
);
ImageStack sourceStack= bayerToStack(imp_src, // source Bayer image, linearized, 32-bit (float))
split_parameters);
DBG_IMP = new ImagePlus(imp_src.getTitle()+"-SPIT", sourceStack);
DBG_IMP.getProcessor().resetMinAndMax();
DBG_IMP.show();
} else {
DBG_IMP = imp_src;
}
}
if (CORRELATE_IMP == null) {
ImagePlus imp_src = WindowManager.getCurrentImage();
if (imp_src==null){
IJ.showMessage("Error","JP4 image or Bayer image stack required");
return;
}
if (imp_src.getStackSize()<3){ // convert JP4 to image stack
EyesisCorrectionParameters.SplitParameters split_parameters = new EyesisCorrectionParameters.SplitParameters(
1, // oversample;
// Add just for mdct (N/2)
CLT_PARAMETERS.transform_size/2, // addLeft
CLT_PARAMETERS.transform_size/2, // addTop
CLT_PARAMETERS.transform_size/2, // addRight
CLT_PARAMETERS.transform_size/2 // addBottom
);
ImageStack sourceStack= bayerToStack(imp_src, // source Bayer image, linearized, 32-bit (float))
split_parameters);
CORRELATE_IMP = new ImagePlus(imp_src.getTitle()+"-SPIT_CORRELATE"
+ "", sourceStack);
if (DEBUG_LEVEL > 1) {
CORRELATE_IMP.getProcessor().resetMinAndMax();
CORRELATE_IMP.show();
}
} else {
CORRELATE_IMP = imp_src;
}
}
String suffix = "-dx_"+(CLT_PARAMETERS.ishift_x+CLT_PARAMETERS.shift_x)+"_dy_"+(CLT_PARAMETERS.ishift_y+CLT_PARAMETERS.shift_y);
ImageDtt image_dtt = new ImageDtt();
String [] titles = {
"redCC", "redSC", "redCS", "redSS",
"blueCC", "blueSC", "blueCS", "blueSS",
"greenCC","greenSC","greenCS","greenSS"};
double [][][][][] clt_data = image_dtt.cltStack(
DBG_IMP.getStack(),
0, // CLT_PARAMETERS.kernel_chn,
CLT_PARAMETERS,
0, //final int shiftX, // shift image horizontally (positive - right)
0, //final int shiftY, // shift image vertically (positive - down)
THREADS_MAX, DEBUG_LEVEL, UPDATE_STATUS);
int tilesY = DBG_IMP.getHeight()/CLT_PARAMETERS.transform_size - 1;
int tilesX = DBG_IMP.getWidth()/CLT_PARAMETERS.transform_size - 1;
System.out.println("'CLT stack': tilesX="+tilesX);
System.out.println("'CLT stack': tilesY="+tilesY);
double [][] clt = new double [clt_data.length*4][];
for (int chn = 0; chn < clt_data.length; chn++) {
double [][] clt_set = image_dtt.clt_dbg(
clt_data [chn],
THREADS_MAX,
DEBUG_LEVEL);
for (int ii = 0; ii < clt_set.length; ii++) clt[chn*4+ii] = clt_set[ii];
}
// System.out.println("dct_dc.length="+dct_dc.length+" dct_ac.length="+dct_ac.length);
if (DEBUG_LEVEL > 0){
SDFA_INSTANCE.showArrays(clt,
tilesX*CLT_PARAMETERS.transform_size,
tilesY*CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-CLT+"+suffix, titles);
}
// convert second image (should be the same size)
// apply integer shift to the second image
double [][][][][] clt_data2 = image_dtt.cltStack(
CORRELATE_IMP.getStack(),
0, // CLT_PARAMETERS.kernel_chn,
CLT_PARAMETERS,
CLT_PARAMETERS.ishift_x, //final int shiftX, // shift image horizontally (positive - right)
CLT_PARAMETERS.ishift_y, //final int shiftY, // shift image vertically (positive - down)
THREADS_MAX, DEBUG_LEVEL, UPDATE_STATUS);
int tilesY2 = DBG_IMP.getHeight()/CLT_PARAMETERS.transform_size - 1;
int tilesX2 = DBG_IMP.getWidth()/CLT_PARAMETERS.transform_size - 1;
System.out.println("'CLT stack 2': tilesX="+tilesX2);
System.out.println("'CLT stack 2': tilesY="+tilesY2);
if ((tilesX2 != tilesX) || (tilesY2 != tilesY)) {
System.out.println("Imges for correlation mismatch: "+tilesX+"x"+tilesY+" != "+tilesX2+"x"+tilesY2);
return;
}
// optionally apply fractional shift to the second image
if ((CLT_PARAMETERS.shift_x != 0) || (CLT_PARAMETERS.shift_y !=0)){
for (int chn = 0; chn < clt_data.length; chn++) {
clt_data2[chn] = image_dtt.clt_shiftXY(
clt_data2[chn], // final double [][][][] dct_data, // array [tilesY][tilesX][4][dct_size*dct_size]
CLT_PARAMETERS.transform_size, // final int dct_size,
CLT_PARAMETERS.shift_x, // final double shiftX,
CLT_PARAMETERS.shift_y, // final double shiftY,
(CLT_PARAMETERS.dbg_mode >> 2) & 3, // swap order hor/vert
THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel)
}
}
clt = new double [clt_data2.length*4][];
for (int chn = 0; chn < clt_data.length; chn++) {
double [][] clt_set = image_dtt.clt_dbg(
clt_data2 [chn],
THREADS_MAX,
DEBUG_LEVEL);
for (int ii = 0; ii < clt_set.length; ii++) clt[chn*4+ii] = clt_set[ii];
}
// System.out.println("dct_dc.length="+dct_dc.length+" dct_ac.length="+dct_ac.length);
if (DEBUG_LEVEL > 0){
SDFA_INSTANCE.showArrays(clt,
tilesX*CLT_PARAMETERS.transform_size,
tilesY*CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-CLT2+"+suffix, titles);
}
double [][][][][] clt_corr = new double [clt_data.length][][][][];
for (int chn = 0; chn < clt_data.length; chn++) {
clt_corr[chn] = image_dtt.clt_correlate(
clt_data[chn], // final double [][][][] data1, // array [tilesY][tilesX][4][dct_size*dct_size]
clt_data2[chn], // final double [][][][] data2, // array [tilesY][tilesX][4][dct_size*dct_size]
CLT_PARAMETERS.transform_size, // final int dct_size,
CLT_PARAMETERS.fat_zero, // final double fat_zero, // add to denominator to modify phase correlation (same units as data1, data2)
CLT_PARAMETERS.tileX, //final int debug_tileX
CLT_PARAMETERS.tileY, //final int debug_tileY
THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel)
}
clt = new double [clt_data.length*4][];
for (int chn = 0; chn < clt_data.length; chn++) {
double [][] clt_set = image_dtt.clt_dbg(
clt_corr [chn],
THREADS_MAX,
DEBUG_LEVEL);
for (int ii = 0; ii < clt_set.length; ii++) clt[chn*4+ii] = clt_set[ii];
}
if (DEBUG_LEVEL > 0){
SDFA_INSTANCE.showArrays(clt,
tilesX*CLT_PARAMETERS.transform_size,
tilesY*CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-CORR+"+suffix, titles);
}
if (CLT_PARAMETERS.corr_sigma > 0.0){
for (int chn = 0; chn < clt_data.length; chn++) {
image_dtt.clt_lpf( // filter in-place
CLT_PARAMETERS.corr_sigma, // final double sigma,
clt_corr[chn], // final double [][][][] clt_data,
THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel)
}
clt = new double [clt_data.length*4][];
for (int chn = 0; chn < clt_corr.length; chn++) {
double [][] clt_set = image_dtt.clt_dbg(
clt_corr [chn],
THREADS_MAX,
DEBUG_LEVEL);
for (int ii = 0; ii < clt_set.length; ii++) clt[chn*4+ii] = clt_set[ii];
}
if (DEBUG_LEVEL > 0){
SDFA_INSTANCE.showArrays(clt,
tilesX*CLT_PARAMETERS.transform_size,
tilesY*CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-LPF_CORR+"+suffix, titles);
}
}
for (int chn = 0; chn < clt_corr.length; chn++) {
image_dtt.clt_dtt2( // DCCT2, DSCT2, DCST2, DSST2 - in-place
clt_corr[chn], // final double [][][][] clt_data,
THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel)
}
clt = new double [clt_corr.length*4][];
for (int chn = 0; chn < clt_data.length; chn++) {
double [][] clt_set = image_dtt.clt_dbg(
clt_corr [chn],
THREADS_MAX,
DEBUG_LEVEL);
for (int ii = 0; ii < clt_set.length; ii++) clt[chn*4+ii] = clt_set[ii];
}
if (DEBUG_LEVEL > -1){
SDFA_INSTANCE.showArrays(clt,
tilesX*CLT_PARAMETERS.transform_size,
tilesY*CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-ICORR+"+suffix, titles);
}
double [][][][] corr_tiles = new double [clt_corr.length][][][];
for (int chn = 0; chn < clt_corr.length; chn++) {
corr_tiles[chn] = image_dtt.clt_corr_quad(
clt_corr[chn],
THREADS_MAX,
DEBUG_LEVEL);
}
if (DEBUG_LEVEL > -1){
double [][] corr_rslt = new double [clt_corr.length][];
for (int chn = 0; chn < clt_corr.length; chn++) {
corr_rslt[chn] = image_dtt.corr_dbg(
corr_tiles[chn],
THREADS_MAX,
DEBUG_LEVEL);
}
String [] titles_rbg = {"red","blue","green"};
SDFA_INSTANCE.showArrays(corr_rslt,
tilesX*(2*CLT_PARAMETERS.transform_size),
tilesY*(2*CLT_PARAMETERS.transform_size),
true,
DBG_IMP.getTitle()+"-C"+suffix, titles_rbg);
}
/*
double [][] iclt_data = new double [clt_data.length][];
for (int chn=0; chn<iclt_data.length;chn++){
iclt_data[chn] = image_dtt.iclt_2d(
clt_data[chn], // scanline representation of dcd data, organized as dct_size x dct_size tiles
CLT_PARAMETERS.transform_size, // final int
CLT_PARAMETERS.clt_window, //window_type
CLT_PARAMETERS.iclt_mask, //which of 4 to transform back
CLT_PARAMETERS.dbg_mode, //which of 4 to transform back
THREADS_MAX, // maximal number of threads to launch
DEBUG_LEVEL); // globalDebugLevel)
}
SDFA_INSTANCE.showArrays(
iclt_data,
(tilesX + 1) * CLT_PARAMETERS.transform_size,
(tilesY + 1) * CLT_PARAMETERS.transform_size,
true,
DBG_IMP.getTitle()+"-ICLT-"+CLT_PARAMETERS.iclt_mask);
*/
return;
// End of buttons code // End of buttons code
} }
......
...@@ -119,9 +119,9 @@ public class ImageDtt { ...@@ -119,9 +119,9 @@ public class ImageDtt {
DttRad2 dtt0 = new DttRad2(dct_size); DttRad2 dtt0 = new DttRad2(dct_size);
dtt0.set_window(window_type); dtt0.set_window(window_type);
final double [] dciii = dtt0.dttt_iii (dc, dct_size); final double [] dciii = dtt0.dttt_iii (dc, dct_size);
final double [] dciiie = dtt0.dttt_iiie (dc, dct_size); final double [] dciiie = dtt0.dttt_iiie (dc, 0, dct_size);
if ((globalDebugLevel > 0) && (color ==2)) { if ((globalDebugLevel > 0) && (color ==2)) {
double [][]dcx = {dc,dciii,dciiie, dtt0.dttt_ii(dc, dct_size),dtt0.dttt_iie(dc, dct_size)}; double [][]dcx = {dc,dciii,dciiie, dtt0.dttt_ii(dc, dct_size),dtt0.dttt_iie(dc, 0, dct_size)};
showDoubleFloatArrays sdfa_instance0 = new showDoubleFloatArrays(); // just for debugging? showDoubleFloatArrays sdfa_instance0 = new showDoubleFloatArrays(); // just for debugging?
sdfa_instance0.showArrays(dcx, dct_size, dct_size, true, "dcx"); sdfa_instance0.showArrays(dcx, dct_size, dct_size, true, "dcx");
} }
...@@ -663,6 +663,8 @@ public class ImageDtt { ...@@ -663,6 +663,8 @@ public class ImageDtt {
final int width, final int width,
final int dct_size, final int dct_size,
final int window_type, final int window_type,
final int shiftX, // shift image horizontally (positive - right)
final int shiftY, // shift image vertically (positive - down)
final int debug_tileX, final int debug_tileX,
final int debug_tileY, final int debug_tileY,
final int debug_mode, final int debug_mode,
...@@ -707,10 +709,21 @@ public class ImageDtt { ...@@ -707,10 +709,21 @@ public class ImageDtt {
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) { for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX; tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX; tileX = nTile - tileY * tilesX;
for (int i = 0; i < n2;i++){ if ((shiftX == 0) && (shiftY == 0)){
System.arraycopy(dpixels, (tileY*width+tileX)*dct_size + i*width, tile_in, i*n2, n2); for (int i = 0; i < n2;i++){
System.arraycopy(dpixels, (tileY*width+tileX)*dct_size + i*width, tile_in, i*n2, n2);
}
} else {
int x0 = tileX * dct_size - shiftX;
if (x0 < 0) x0 = 0; // first/last will be incorrect
else if (x0 >= (width - n2)) x0 = width - n2;
for (int i = 0; i < n2;i++){
int y0 = tileY * dct_size + i - shiftY;
if (y0 < 0) y0 = 0;
else if (y0 >= height) y0 = height -1;
System.arraycopy(dpixels, y0 * width+ x0, tile_in, i*n2, n2);
}
} }
for (int dct_mode = 0; dct_mode <4; dct_mode++) { for (int dct_mode = 0; dct_mode <4; dct_mode++) {
tile_folded[dct_mode] = dtt.fold_tile(tile_in, dct_size, dct_mode); // DCCT, DSCT, DCST, DSST tile_folded[dct_mode] = dtt.fold_tile(tile_in, dct_size, dct_mode); // DCCT, DSCT, DCST, DSST
if ((debug_mode & 1) != 0) { if ((debug_mode & 1) != 0) {
...@@ -725,7 +738,9 @@ public class ImageDtt { ...@@ -725,7 +738,9 @@ public class ImageDtt {
sdfa_instance.showArrays(tile_in, n2, n2, "tile_in_x"+tileX+"_y"+tileY); sdfa_instance.showArrays(tile_in, n2, n2, "tile_in_x"+tileX+"_y"+tileY);
String [] titles = {"CC","SC","CS","SS"}; String [] titles = {"CC","SC","CS","SS"};
sdfa_instance.showArrays(tile_folded, dct_size, dct_size, true, "folded_x"+tileX+"_y"+tileY, titles); sdfa_instance.showArrays(tile_folded, dct_size, dct_size, true, "folded_x"+tileX+"_y"+tileY, titles);
sdfa_instance.showArrays(tile_out, dct_size, dct_size, true, "clt_x"+tileX+"_y"+tileY, titles); if (globalDebugLevel > 0) {
sdfa_instance.showArrays(tile_out, dct_size, dct_size, true, "clt_x"+tileX+"_y"+tileY, titles);
}
} }
} }
} }
...@@ -828,14 +843,9 @@ public class ImageDtt { ...@@ -828,14 +843,9 @@ public class ImageDtt {
final int tilesY=dct_data.length; final int tilesY=dct_data.length;
final int tilesX=dct_data[0].length; final int tilesX=dct_data[0].length;
final int nTiles = tilesY* tilesX; final int nTiles = tilesY* tilesX;
final int width= (tilesX+1)*dct_size;
final int height= (tilesY+1)*dct_size;
if (globalDebugLevel > 0) { if (globalDebugLevel > 0) {
System.out.println("clt_shift():tilesX= "+tilesX); System.out.println("clt_shift():tilesX= "+tilesX);
System.out.println("clt_shift():tilesY= "+tilesY); System.out.println("clt_shift():tilesY= "+tilesY);
System.out.println("clt_shift():width= "+width);
System.out.println("clt_shift():height= "+height);
System.out.println("clt_shift():shiftX= "+shiftX); System.out.println("clt_shift():shiftX= "+shiftX);
System.out.println("clt_shift():shiftY= "+shiftY); System.out.println("clt_shift():shiftY= "+shiftY);
} }
...@@ -849,8 +859,8 @@ public class ImageDtt { ...@@ -849,8 +859,8 @@ public class ImageDtt {
double cv = Math.cos((i+0.5)*Math.PI*shiftY/dct_size); double cv = Math.cos((i+0.5)*Math.PI*shiftY/dct_size);
double sv = Math.sin((i+0.5)*Math.PI*shiftY/dct_size); double sv = Math.sin((i+0.5)*Math.PI*shiftY/dct_size);
for (int j = 0; j < dct_size; j++){ for (int j = 0; j < dct_size; j++){
int ih = dct_size * j + i; int iv = dct_size * j + i; // 2d DTT results are stored transposed!
int iv = dct_size * i + j; int ih = dct_size * i + j;
cos_hor[ih] = ch; cos_hor[ih] = ch;
sin_hor[ih] = sh; sin_hor[ih] = sh;
cos_vert[iv] = cv; cos_vert[iv] = cv;
...@@ -876,83 +886,299 @@ public class ImageDtt { ...@@ -876,83 +886,299 @@ public class ImageDtt {
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) { for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX; tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX; tileX = nTile - tileY * tilesX;
// Horizontal shift // Horizontal shift CLT tiled data is stored in transposed way (horizontal - Y, vertical X)
if (dbg_swap_mode == 1) { for (int i = 0; i < cos_hor.length; i++) {
for (int i = 0; i < cos_hor.length; i++) { rslt[tileY][tileX][0][i] = dct_data[tileY][tileX][0][i] * cos_hor[i] - dct_data[tileY][tileX][1][i] * sin_hor[i];
rslt[tileY][tileX][0][i] = dct_data[tileY][tileX][0][i] * cos_vert[i] - dct_data[tileY][tileX][1][i] * sin_vert[i]; rslt[tileY][tileX][1][i] = dct_data[tileY][tileX][1][i] * cos_hor[i] + dct_data[tileY][tileX][0][i] * sin_hor[i] ;
rslt[tileY][tileX][1][i] = dct_data[tileY][tileX][1][i] * cos_vert[i] + dct_data[tileY][tileX][0][i] * sin_vert[i] ;
rslt[tileY][tileX][2][i] = dct_data[tileY][tileX][2][i] * cos_vert[i] - dct_data[tileY][tileX][3][i] * sin_vert[i];
rslt[tileY][tileX][3][i] = dct_data[tileY][tileX][3][i] * cos_vert[i] + dct_data[tileY][tileX][2][i] * sin_vert[i] ;
}
// Vertical shift (in-place)
for (int i = 0; i < cos_hor.length; i++) {
double tmp = rslt[tileY][tileX][0][i] * cos_hor[i] - rslt[tileY][tileX][2][i] * sin_hor[i];
rslt[tileY][tileX][2][i] = rslt[tileY][tileX][2][i] * cos_hor[i] + rslt[tileY][tileX][0][i] * sin_hor[i];
rslt[tileY][tileX][0][i] = tmp;
tmp = rslt[tileY][tileX][1][i] * cos_hor[i] - rslt[tileY][tileX][3][i] * sin_hor[i]; rslt[tileY][tileX][2][i] = dct_data[tileY][tileX][2][i] * cos_hor[i] - dct_data[tileY][tileX][3][i] * sin_hor[i];
rslt[tileY][tileX][3][i] = rslt[tileY][tileX][3][i] * cos_hor[i] + rslt[tileY][tileX][1][i] * sin_hor[i]; rslt[tileY][tileX][3][i] = dct_data[tileY][tileX][3][i] * cos_hor[i] + dct_data[tileY][tileX][2][i] * sin_hor[i] ;
rslt[tileY][tileX][1][i] = tmp; }
} // Vertical shift (in-place)
} else if (dbg_swap_mode == 0) { for (int i = 0; i < cos_hor.length; i++) {
// Horizontal shift double tmp = rslt[tileY][tileX][0][i] * cos_vert[i] - rslt[tileY][tileX][2][i] * sin_vert[i];
for (int i = 0; i < cos_hor.length; i++) { rslt[tileY][tileX][2][i] = rslt[tileY][tileX][2][i] * cos_vert[i] + rslt[tileY][tileX][0][i] * sin_vert[i];
rslt[tileY][tileX][0][i] = dct_data[tileY][tileX][0][i] * cos_hor[i] - dct_data[tileY][tileX][1][i] * sin_hor[i]; rslt[tileY][tileX][0][i] = tmp;
rslt[tileY][tileX][1][i] = dct_data[tileY][tileX][1][i] * cos_hor[i] + dct_data[tileY][tileX][0][i] * sin_hor[i];
rslt[tileY][tileX][2][i] = dct_data[tileY][tileX][2][i] * cos_hor[i] - dct_data[tileY][tileX][3][i] * sin_hor[i]; tmp = rslt[tileY][tileX][1][i] * cos_vert[i] - rslt[tileY][tileX][3][i] * sin_vert[i];
rslt[tileY][tileX][3][i] = dct_data[tileY][tileX][3][i] * cos_hor[i] + dct_data[tileY][tileX][2][i] * sin_hor[i]; rslt[tileY][tileX][3][i] = rslt[tileY][tileX][3][i] * cos_vert[i] + rslt[tileY][tileX][1][i] * sin_vert[i];
} rslt[tileY][tileX][1][i] = tmp;
// Vertical shift (in-place) }
for (int i = 0; i < cos_hor.length; i++) { }
double tmp = rslt[tileY][tileX][0][i] * cos_vert[i] - rslt[tileY][tileX][2][i] * sin_vert[i]; }
rslt[tileY][tileX][2][i] = rslt[tileY][tileX][2][i] * cos_vert[i] + rslt[tileY][tileX][0][i] * sin_vert[i]; };
rslt[tileY][tileX][0][i] = tmp; }
startAndJoin(threads);
return rslt;
}
tmp = rslt[tileY][tileX][1][i] * cos_vert[i] - rslt[tileY][tileX][3][i] * sin_vert[i]; public double [][][][] clt_correlate(
rslt[tileY][tileX][3][i] = rslt[tileY][tileX][3][i] * cos_vert[i] + rslt[tileY][tileX][1][i] * sin_vert[i]; final double [][][][] data1, // array [tilesY][tilesX][4][dct_size*dct_size]
rslt[tileY][tileX][1][i] = tmp; final double [][][][] data2, // array [tilesY][tilesX][4][dct_size*dct_size]
final int dct_size,
final double fat_zero, // add to denominator to modify phase correlation (same units as data1, data2)
final int debug_tileX,
final int debug_tileY,
final int threadsMax, // maximal number of threads to launch
final int globalDebugLevel)
{
final int tilesY=(data1.length > data2.length)?data2.length:data1.length;
final int tilesX=(data1[0].length > data2[0].length)?data2[0].length:data1[0].length;
final int nTiles = tilesY* tilesX;
if (globalDebugLevel > 0) {
System.out.println("clt_shift():tilesX= "+tilesX);
System.out.println("clt_shift():tilesY= "+tilesY);
}
/*
* {{+cc -sc -cs +ss},
* {+sc +cc -ss -cs},
* {+cs -ss +cc -sc},
* {+ss +cs +sc +cc}}
*
* T= transp({cc, sc, cs, ss})
*/
/*
final int [][] zi =
{{ 0, -1, -2, 3},
{ 1, 0, -3, -2},
{ 2, -3, 0, -1},
{ 3, 2, 1, 0}};
*/
final int [][] zi =
{{ 0, 1, 2, 3},
{-1, 0, -3, 2},
{-2, -3, 0, 1},
{ 3, -2, -1, 0}};
final int dct_len = dct_size * dct_size;
final double [][][][] rslt = new double[tilesY][tilesX][4][dct_len];
final Thread[] threads = newThreadArray(threadsMax);
final AtomicInteger ai = new AtomicInteger(0);
for (int ithread = 0; ithread < threads.length; ithread++) {
threads[ithread] = new Thread() {
public void run() {
int tileY,tileX;
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX;
for (int i = 0; i < dct_len; i++) {
double s1 = 0.0, s2=0.0;
for (int n = 0; n< 4; n++){
s1+=data1[tileY][tileX][n][i] * data1[tileY][tileX][n][i];
s2+=data2[tileY][tileX][n][i] * data2[tileY][tileX][n][i];
} }
} else if (dbg_swap_mode == 3) { double scale = 1.0 / (Math.sqrt(s1*s2) + fat_zero*fat_zero); // squared to match units
for (int i = 0; i < cos_hor.length; i++) { for (int n = 0; n<4; n++){
rslt[tileY][tileX][0][i] = dct_data[tileY][tileX][0][i] * cos_vert[i] - dct_data[tileY][tileX][1][i] * sin_vert[i]; /*
rslt[tileY][tileX][1][i] = dct_data[tileY][tileX][1][i] * cos_vert[i] + dct_data[tileY][tileX][0][i] * sin_vert[i]; if (
(tileY >= rslt.length) ||
rslt[tileY][tileX][2][i] = dct_data[tileY][tileX][2][i] * cos_vert[i] + dct_data[tileY][tileX][3][i] * sin_vert[i]; (tileX >= rslt[tileY].length) ||
rslt[tileY][tileX][3][i] = dct_data[tileY][tileX][3][i] * cos_vert[i] - dct_data[tileY][tileX][2][i] * sin_vert[i]; (n >= rslt[tileY][tileX].length) ||
(i >= rslt[tileY][tileX][n].length)) {
System.out.println("===== tileY="+tileY+" ("+tilesY+") tileX="+tileX+" ("+tilesX+") n="+n+" i="+i);
System.out.println(
" rslt.length="+rslt.length+
" rslt.length[tileY]="+rslt[tileY].length+
" rslt.length[tileY][tileX]="+rslt[tileY][tileX].length+
" rslt.length[tileY][tileX][n]="+rslt[tileY][tileX][n].length);
System.out.println("===== tileY="+tileY+" ("+tilesY+") tileX="+tileX+" ("+tilesX+") n="+n+" i="+i);
}
*/
rslt[tileY][tileX][n][i] = 0;
for (int k=0; k<4; k++){
if (zi[n][k] < 0)
rslt[tileY][tileX][n][i] -=
data1[tileY][tileX][-zi[n][k]][i] * data2[tileY][tileX][k][i];
else
rslt[tileY][tileX][n][i] +=
data1[tileY][tileX][zi[n][k]][i] * data2[tileY][tileX][k][i];
}
rslt[tileY][tileX][n][i] *= scale;
} }
// Vertical shift (in-place) }
for (int i = 0; i < cos_hor.length; i++) { if ((globalDebugLevel > 0) && (debug_tileX == tileX) && (debug_tileY == tileY)) {
double tmp = rslt[tileY][tileX][0][i] * cos_hor[i] - rslt[tileY][tileX][2][i] * sin_hor[i]; showDoubleFloatArrays sdfa_instance = new showDoubleFloatArrays(); // just for debugging?
rslt[tileY][tileX][2][i] = rslt[tileY][tileX][2][i] * cos_hor[i] + rslt[tileY][tileX][0][i] * sin_hor[i]; String [] titles = {"CC","SC","CS","SS"};
rslt[tileY][tileX][0][i] = tmp; sdfa_instance.showArrays(data1[tileY][tileX], dct_size, dct_size, true, "data1_x"+tileX+"_y"+tileY, titles);
sdfa_instance.showArrays(data2[tileY][tileX], dct_size, dct_size, true, "data2_x"+tileX+"_y"+tileY, titles);
sdfa_instance.showArrays(rslt[tileY][tileX], dct_size, dct_size, true, "rslt_x"+ tileX+"_y"+tileY, titles);
}
}
}
};
}
startAndJoin(threads);
return rslt;
}
tmp = rslt[tileY][tileX][1][i] * cos_hor[i] + rslt[tileY][tileX][3][i] * sin_hor[i]; public void clt_lpf(
rslt[tileY][tileX][3][i] = rslt[tileY][tileX][3][i] * cos_hor[i] - rslt[tileY][tileX][1][i] * sin_hor[i]; final double sigma,
rslt[tileY][tileX][1][i] = tmp; final double [][][][] clt_data,
} final int threadsMax, // maximal number of threads to launch
} else if (dbg_swap_mode == 2) { final int globalDebugLevel)
// Horizontal shift {
for (int i = 0; i < cos_hor.length; i++) { final int tilesY=clt_data.length;
rslt[tileY][tileX][0][i] = dct_data[tileY][tileX][0][i] * cos_hor[i] - dct_data[tileY][tileX][1][i] * sin_hor[i]; final int tilesX=clt_data[0].length;
rslt[tileY][tileX][1][i] = dct_data[tileY][tileX][1][i] * cos_hor[i] + dct_data[tileY][tileX][0][i] * sin_hor[i]; final int nTiles=tilesX*tilesY;
final int dct_size = (int) Math.round(Math.sqrt(clt_data[0][0][0].length));
final int dct_len = dct_size*dct_size;
final double [] filter_direct= new double[dct_len];
if (sigma == 0) {
filter_direct[0] = 1.0;
for (int i= 1; i<filter_direct.length;i++) filter_direct[i] =0;
} else {
for (int i = 0; i < dct_size; i++){
for (int j = 0; j < dct_size; j++){
filter_direct[i*dct_size+j] = Math.exp(-(i*i+j*j)/(2*sigma));
}
}
}
// normalize
double sum = 0;
for (int i = 0; i < dct_size; i++){
for (int j = 0; j < dct_size; j++){
double d = filter_direct[i*dct_size+j];
d*=Math.cos(Math.PI*i/(2*dct_size))*Math.cos(Math.PI*j/(2*dct_size));
if (i > 0) d*= 2.0;
if (j > 0) d*= 2.0;
sum +=d;
}
}
for (int i = 0; i<filter_direct.length; i++){
filter_direct[i] /= sum;
}
if (globalDebugLevel > 0) {
for (int i=0; i<filter_direct.length;i++){
System.out.println("dct_lpf_psf() "+i+": "+filter_direct[i]);
}
}
DttRad2 dtt = new DttRad2(dct_size);
final double [] filter= dtt.dttt_iiie(filter_direct);
final double [] dbg_filter= dtt.dttt_ii(filter);
for (int i=0; i < filter.length;i++) filter[i] *= 2*dct_size;
if (globalDebugLevel > 0) {
for (int i=0; i<filter.length;i++){
System.out.println("dct_lpf_psf() "+i+": "+filter[i]);
}
showDoubleFloatArrays sdfa_instance = new showDoubleFloatArrays(); // just for debugging?
double [][] ff = {filter_direct,filter,dbg_filter};
sdfa_instance.showArrays(ff, dct_size,dct_size, true, "filter_lpf");
}
final Thread[] threads = newThreadArray(threadsMax);
final AtomicInteger ai = new AtomicInteger(0);
rslt[tileY][tileX][2][i] = dct_data[tileY][tileX][2][i] * cos_hor[i] + dct_data[tileY][tileX][3][i] * sin_hor[i]; for (int ithread = 0; ithread < threads.length; ithread++) {
rslt[tileY][tileX][3][i] = dct_data[tileY][tileX][3][i] * cos_hor[i] - dct_data[tileY][tileX][2][i] * sin_hor[i]; threads[ithread] = new Thread() {
public void run() {
int tileY,tileX;
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX;
for (int n = 0; n < 4; n++){
for (int i = 0; i < filter.length; i++){
clt_data[tileY][tileX][n][i] *= filter[i];
} }
// Vertical shift (in-place) }
for (int i = 0; i < cos_hor.length; i++) { }
double tmp = rslt[tileY][tileX][0][i] * cos_vert[i] - rslt[tileY][tileX][2][i] * sin_vert[i]; }
rslt[tileY][tileX][2][i] = rslt[tileY][tileX][2][i] * cos_vert[i] + rslt[tileY][tileX][0][i] * sin_vert[i]; };
rslt[tileY][tileX][0][i] = tmp; }
startAndJoin(threads);
}
public void clt_dtt2( // transform dcct2, dsct2, dcst2, dsst2
final double [][][][] data,
final int threadsMax, // maximal number of threads to launch
final int globalDebugLevel)
{
final int tilesY=data.length;
final int tilesX=data[0].length;
final int nTiles=tilesX*tilesY;
final int dct_size = (int) Math.round(Math.sqrt(data[0][0][0].length));
final Thread[] threads = newThreadArray(threadsMax);
final AtomicInteger ai = new AtomicInteger(0);
tmp = rslt[tileY][tileX][1][i] * cos_vert[i] + rslt[tileY][tileX][3][i] * sin_vert[i]; for (int ithread = 0; ithread < threads.length; ithread++) {
rslt[tileY][tileX][3][i] = rslt[tileY][tileX][3][i] * cos_vert[i] - rslt[tileY][tileX][1][i] * sin_vert[i]; threads[ithread] = new Thread() {
rslt[tileY][tileX][1][i] = tmp; public void run() {
} DttRad2 dtt = new DttRad2(dct_size);
int tileY,tileX;
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX;
for (int quadrant = 0; quadrant < 4; quadrant++){
data[tileY][tileX][quadrant] = dtt.dttt_iie(data[tileY][tileX][quadrant], quadrant, dct_size);
} }
}
}
};
}
startAndJoin(threads);
}
public double [][][] clt_corr_quad( // combine 4 correlation quadrants after DTT2
final double [][][][] data,
final int threadsMax, // maximal number of threads to launch
final int globalDebugLevel)
{
final int tilesY=data.length;
final int tilesX=data[0].length;
final int nTiles=tilesX*tilesY;
final int dct_size = (int) Math.round(Math.sqrt(data[0][0][0].length));
final int rslt_size=dct_size*2-1;
final double [][][] rslt = new double[tilesY][tilesX][rslt_size*rslt_size];
final Thread[] threads = newThreadArray(threadsMax);
final AtomicInteger ai = new AtomicInteger(0);
for (int ithread = 0; ithread < threads.length; ithread++) {
threads[ithread] = new Thread() {
public void run() {
int tileY,tileX;
double scale = 0.25;
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX;
rslt[tileY][tileX][rslt_size*dct_size - dct_size] = scale * data[tileY][tileX][0][0]; // center
for (int j = 1; j < dct_size; j++) { // for i == 0
rslt[tileY][tileX][rslt_size*dct_size - dct_size + j] = scale * (data[tileY][tileX][0][j] + data[tileY][tileX][1][j-1]);
rslt[tileY][tileX][rslt_size*dct_size - dct_size - j] = scale * (data[tileY][tileX][0][j] - data[tileY][tileX][1][j-1]);
}
for (int i = 1; i < dct_size; i++) {
rslt[tileY][tileX][rslt_size*(dct_size + i) - dct_size] =
scale * (data[tileY][tileX][0][i*dct_size] + data[tileY][tileX][2][(i-1)*dct_size]);
rslt[tileY][tileX][rslt_size*(dct_size - i) - dct_size] =
scale * (data[tileY][tileX][0][i*dct_size] - data[tileY][tileX][2][(i-1)*dct_size]);
for (int j = 1; j < dct_size; j++) {
rslt[tileY][tileX][rslt_size*(dct_size + i) - dct_size + j] =
scale * (data[tileY][tileX][0][i* dct_size + j] +
data[tileY][tileX][1][i* dct_size + j - 1] +
data[tileY][tileX][2][(i-1)*dct_size + j] +
data[tileY][tileX][3][(i-1)*dct_size + j - 1]);
rslt[tileY][tileX][rslt_size*(dct_size + i) - dct_size - j] =
scale * ( data[tileY][tileX][0][i* dct_size + j] +
-data[tileY][tileX][1][i* dct_size + j - 1] +
data[tileY][tileX][2][(i-1)*dct_size + j] +
-data[tileY][tileX][3][(i-1)*dct_size + j - 1]);
rslt[tileY][tileX][rslt_size*(dct_size - i) - dct_size + j] =
scale * (data[tileY][tileX][0][i* dct_size + j] +
data[tileY][tileX][1][i* dct_size + j - 1] +
-data[tileY][tileX][2][(i-1)*dct_size + j] +
-data[tileY][tileX][3][(i-1)*dct_size + j - 1]);
rslt[tileY][tileX][rslt_size*(dct_size - i) - dct_size - j] =
scale * (data[tileY][tileX][0][i* dct_size + j] +
-data[tileY][tileX][1][i* dct_size + j - 1] +
-data[tileY][tileX][2][(i-1)*dct_size + j] +
data[tileY][tileX][3][(i-1)*dct_size + j - 1]);
}
}
} }
} }
}; };
...@@ -961,11 +1187,58 @@ public class ImageDtt { ...@@ -961,11 +1187,58 @@ public class ImageDtt {
return rslt; return rslt;
} }
// extract correlation result in linescan order (for visualization)
public double [] corr_dbg(
final double [][][] corr_data,
final int threadsMax, // maximal number of threads to launch
final int globalDebugLevel)
{
final int tilesY=corr_data.length;
final int tilesX=corr_data[0].length;
final int nTiles=tilesX*tilesY;
final int corr_size = (int) Math.round(Math.sqrt(corr_data[0][0].length));
final int tile_size = corr_size+1;
final int corr_len = corr_size*corr_size;
final double [] corr_data_out = new double[tilesY*tilesX*tile_size*tile_size];
System.out.println("corr_dbg(): tilesY="+tilesY+", tilesX="+tilesX+", corr_size="+corr_size+", corr_len="+corr_len);
final Thread[] threads = newThreadArray(threadsMax);
final AtomicInteger ai = new AtomicInteger(0);
for (int i=0; i<corr_data_out.length;i++) corr_data_out[i]= 0;
for (int ithread = 0; ithread < threads.length; ithread++) {
threads[ithread] = new Thread() {
public void run() {
int tileY,tileX;
for (int nTile = ai.getAndIncrement(); nTile < nTiles; nTile = ai.getAndIncrement()) {
tileY = nTile/tilesX;
tileX = nTile - tileY * tilesX;
for (int i = 0; i < corr_size;i++){
System.arraycopy(corr_data[tileY][tileX], corr_size* i, corr_data_out, ((tileY*tile_size + i) *tilesX + tileX)*tile_size , corr_size);
corr_data_out[((tileY*tile_size + i) *tilesX + tileX)*tile_size+corr_size] = (i & 1) - 0.5;
}
for (int i = 0; i < tile_size; i++){
corr_data_out[((tileY*tile_size + corr_size) *tilesX + tileX)*tile_size+i] = (i & 1) - 0.5;
}
}
}
};
}
startAndJoin(threads);
return corr_data_out;
}
public double [][][][][] cltStack( public double [][][][][] cltStack(
final ImageStack imageStack, final ImageStack imageStack,
final int subcamera, // final int subcamera, //
final EyesisCorrectionParameters.CLTParameters cltParameters, // final EyesisCorrectionParameters.CLTParameters cltParameters, //
// final EyesisDCT eyesisDCT, final int shiftX, // shift image horizontally (positive - right)
final int shiftY, // shift image vertically (positive - down)
final int threadsMax, // maximal step in pixels on the maxRadius for 1 angular step (i.e. 0.5) final int threadsMax, // maximal step in pixels on the maxRadius for 1 angular step (i.e. 0.5)
final int debugLevel, final int debugLevel,
final boolean updateStatus) // update status info final boolean updateStatus) // update status info
...@@ -1001,6 +1274,8 @@ public class ImageDtt { ...@@ -1001,6 +1274,8 @@ public class ImageDtt {
imgWidth, imgWidth,
cltParameters.transform_size, cltParameters.transform_size,
cltParameters.clt_window, cltParameters.clt_window,
shiftX,
shiftY,
cltParameters.tileX, // debug_tileX, cltParameters.tileX, // debug_tileX,
cltParameters.tileY, // debug_tileY, cltParameters.tileY, // debug_tileY,
cltParameters.dbg_mode, // debug_mode, cltParameters.dbg_mode, // debug_mode,
...@@ -1133,7 +1408,7 @@ public class ImageDtt { ...@@ -1133,7 +1408,7 @@ public class ImageDtt {
// DttRad2 dtt0 = new DttRad2(dct_size); // DttRad2 dtt0 = new DttRad2(dct_size);
// dtt0.set_window(window_type); // dtt0.set_window(window_type);
// final double [] dciii = dtt0.dttt_iii (dc, dct_size); // final double [] dciii = dtt0.dttt_iii (dc, dct_size);
// final double [] dciiie = dtt0.dttt_iiie (dc, dct_size); // final double [] dciiie = dtt0.dttt_iiie (dc, 0, dct_size);
if (globalDebugLevel > 0) { if (globalDebugLevel > 0) {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment