Commit a91b3ac6 authored by Andrey Filippov's avatar Andrey Filippov

older changes

parent 805419d8
...@@ -3,14 +3,14 @@ ...@@ -3,14 +3,14 @@
** DttRad2 - Calculate DCT types II and IV for n=2^t and n*n 2-d ** DttRad2 - Calculate DCT types II and IV for n=2^t and n*n 2-d
** also DST-IV and some other related transforms ** also DST-IV and some other related transforms
** **
** Uses algorithm described in ** Uses algorithm described in
** Plonka, Gerlind, and Manfred Tasche. "Fast and numerically stable algorithms for discrete cosine transforms." ** Plonka, Gerlind, and Manfred Tasche. "Fast and numerically stable algorithms for discrete cosine transforms."
** Linear algebra and its applications 394 (2005): 309-345. ** Linear algebra and its applications 394 (2005): 309-345.
** **
** Copyright (C) 2016 Elphel, Inc. ** Copyright (C) 2016 Elphel, Inc.
** **
** -----------------------------------------------------------------------------** ** -----------------------------------------------------------------------------**
** **
** DttRad2.java is free software: you can redistribute it and/or modify ** DttRad2.java is free software: you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by ** it under the terms of the GNU General Public License as published by
** the Free Software Foundation, either version 3 of the License, or ** the Free Software Foundation, either version 3 of the License, or
...@@ -31,33 +31,37 @@ public class DttRad2 { ...@@ -31,33 +31,37 @@ 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 [][][] 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 [][][] 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;
double [][] CN1=null; double [][] CN1=null;
double [][] SN1=null; double [][] SN1=null;
double COSPI_1_8_SQRT2 = Math.cos(Math.PI/8)*Math.sqrt(2.0); double COSPI_1_8_SQRT2 = Math.cos(Math.PI/8)*Math.sqrt(2.0);
double COSPI_3_8_SQRT2 = Math.cos(3*Math.PI/8)*Math.sqrt(2.0); double COSPI_3_8_SQRT2 = Math.cos(3*Math.PI/8)*Math.sqrt(2.0);
double sqrt2 = Math.sqrt(2.0); double sqrt2 = Math.sqrt(2.0);
double sqrt1_2 = 1/sqrt2; double sqrt1_2 = 1/sqrt2;
double [] hwindow = null; // half window double [] hwindow = null; // half window
int [][] fold_index = null; // index of the source item in 2nx2n array input to mdct_2d. int [][] fold_index = null; // index of the source item in 2nx2n array input to mdct_2d.
// First index (0..n^2-1) index in the folded array (dct-iV input) // First index (0..n^2-1) index in the folded array (dct-iV input)
// Second index(0..3) - item to add (2 vertical, 2 - horizontal) // Second index(0..3) - item to add (2 vertical, 2 - horizontal)
double [][][] fold_k = null; // First index - mode: 0 - CC 1: SC, 2: CS, 3: SS. Other indices matching fold_index items. Each is a product of 2 window coefficients and sign double [][][] fold_k = null; // First index - mode: 0 - CC 1: SC, 2: CS, 3: SS. Other indices matching fold_index items. Each is a product of 2 window coefficients and sign
int [] unfold_index = null; // index for each element of idct(2nx2n) int [] unfold_index = null; // index for each element of idct(2nx2n)
double [][] unfold_k = null; // First index - mode: 0 - CC 1: SC, 2: CS, 3: SS. Other indices matching unfold_index items. Each is a product of 2 window coefficients and sign double [][] unfold_k = null; // First index - mode: 0 - CC 1: SC, 2: CS, 3: SS. Other indices matching unfold_index items. Each is a product of 2 window coefficients and sign
public int [][] getFoldIndex(){ public int [][] getFoldIndex(){
return fold_index; return fold_index;
} }
public int [] getUnfoldIndex(){ public int [] getUnfoldIndex(){
return unfold_index; return unfold_index;
} }
public double [][][] getFoldK(){
return fold_k;
}
public DttRad2 (int maxN){ // n - maximal public DttRad2 (int maxN){ // n - maximal
setup_arrays(maxN); // always setup arrays for fast calculations setup_arrays(maxN); // always setup arrays for fast calculations
} }
...@@ -78,21 +82,21 @@ public class DttRad2 { ...@@ -78,21 +82,21 @@ public class DttRad2 {
for (int i = 0; i < y.length ; i++) y[i] *= scale; for (int i = 0; i < y.length ; i++) y[i] *= scale;
return y; return y;
} }
public double [] dst_iv(double[] x){ public double [] dst_iv(double[] x){
double [] xr= new double[x.length]; double [] xr= new double[x.length];
int j= x.length-1; int j= x.length-1;
for (int i=0; i < x.length;i++) xr[i] = x[j--]; for (int i=0; i < x.length;i++) xr[i] = x[j--];
double [] y= _dctiv_recurs(xr); double [] y= _dctiv_recurs(xr);
double scale = 1.0/Math.sqrt(x.length); double scale = 1.0/Math.sqrt(x.length);
for (int i = 0; i < y.length ; i++) { for (int i = 0; i < y.length ; i++) {
y[i] *= scale; y[i] *= scale;
scale = -scale; scale = -scale;
} }
return y; return y;
} }
// For index in dct-iv input (0..n-1) get 2 variants of index in mdct input array (0..2*n-1) // For index in dct-iv input (0..n-1) get 2 variants of index in mdct input array (0..2*n-1)
// second index : 0 - index in X array 2*n long // second index : 0 - index in X array 2*n long
// 1 - window index (0..n-1), [0] - minimal, [n-1] - max // 1 - window index (0..n-1), [0] - minimal, [n-1] - max
...@@ -111,7 +115,7 @@ public class DttRad2 { ...@@ -111,7 +115,7 @@ public class DttRad2 {
ind[0][3] = 1; ind[0][3] = 1;
ind[0][4] = n1 - x -1; ind[0][4] = n1 - x -1;
ind[0][5] = -1; // c - window derivative over shift is negative ind[0][5] = -1; // c - window derivative over shift is negative
ind[1][0] = n + n1 + x; // C: -d, S: -d ind[1][0] = n + n1 + x; // C: -d, S: -d
ind[1][1] = n1 - x - 1; ind[1][1] = n1 - x - 1;
ind[1][2] = -1; ind[1][2] = -1;
...@@ -127,7 +131,7 @@ public class DttRad2 { ...@@ -127,7 +131,7 @@ public class DttRad2 {
ind[0][3] = 1; ind[0][3] = 1;
ind[0][4] = n - x - 1; ind[0][4] = n - x - 1;
ind[0][5] = 1; // a - window derivative over shift is positive ind[0][5] = 1; // a - window derivative over shift is positive
ind[1][0] = n - x - 1; // C: -bR, S: +bR ind[1][0] = n - x - 1; // C: -bR, S: +bR
ind[1][1] = n - x - 1; ind[1][1] = n - x - 1;
ind[1][2] = -1; ind[1][2] = -1;
...@@ -170,7 +174,7 @@ public class DttRad2 { ...@@ -170,7 +174,7 @@ public class DttRad2 {
} }
for (int mode = 0; mode<4; mode++){ for (int mode = 0; mode<4; mode++){
for (int k = 0; k<4;k++) { for (int k = 0; k<4;k++) {
fold_k[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1]; fold_k[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1];
} }
} }
} }
...@@ -193,10 +197,10 @@ public class DttRad2 { ...@@ -193,10 +197,10 @@ public class DttRad2 {
System.out.println(String.format(" : %2d %2d %2d %2d", (fold_k[2][i][0]<0)?-1:1, (fold_k[2][i][1]<0)?-1:1, (fold_k[2][i][2]<0)?-1:1, (fold_k[2][i][3]<0)?-1:1)); System.out.println(String.format(" : %2d %2d %2d %2d", (fold_k[2][i][0]<0)?-1:1, (fold_k[2][i][1]<0)?-1:1, (fold_k[2][i][2]<0)?-1:1, (fold_k[2][i][3]<0)?-1:1));
System.out.println(String.format(" : %2d %2d %2d %2d", (fold_k[3][i][0]<0)?-1:1, (fold_k[3][i][1]<0)?-1:1, (fold_k[3][i][2]<0)?-1:1, (fold_k[3][i][3]<0)?-1:1)); System.out.println(String.format(" : %2d %2d %2d %2d", (fold_k[3][i][0]<0)?-1:1, (fold_k[3][i][1]<0)?-1:1, (fold_k[3][i][2]<0)?-1:1, (fold_k[3][i][3]<0)?-1:1));
} }
} }
} }
public double [][][] get_fold_2d( public double [][][] get_fold_2d(
double scale_hor, double scale_hor,
double scale_vert) double scale_vert)
...@@ -208,7 +212,7 @@ public class DttRad2 { ...@@ -208,7 +212,7 @@ public class DttRad2 {
double scale_hor, double scale_hor,
double scale_vert) double scale_vert)
{ // n - DCT and window size { // n - DCT and window size
double [] hwindow_h = new double[n]; double [] hwindow_h = new double[n];
double [] hwindow_v = new double[n]; double [] hwindow_v = new double[n];
double f = Math.PI/(2.0*n); double f = Math.PI/(2.0*n);
...@@ -232,7 +236,7 @@ public class DttRad2 { ...@@ -232,7 +236,7 @@ public class DttRad2 {
vert_k[0][1] = fi[1][2] * hwindow_v[fi[1][1]]; // use cosine sign vert_k[0][1] = fi[1][2] * hwindow_v[fi[1][1]]; // use cosine sign
vert_k[1][0] = fi[0][3] * hwindow_v[fi[0][1]]; // use sine sign vert_k[1][0] = fi[0][3] * hwindow_v[fi[0][1]]; // use sine sign
vert_k[1][1] = fi[1][3] * hwindow_v[fi[1][1]]; // use sine sign vert_k[1][1] = fi[1][3] * hwindow_v[fi[1][1]]; // use sine sign
for (int j = 0; j < n; j++ ){ for (int j = 0; j < n; j++ ){
fi = get_fold_indices(j,n); fi = get_fold_indices(j,n);
hor_ind[0] = fi[0][0]; hor_ind[0] = fi[0][0];
...@@ -241,12 +245,12 @@ public class DttRad2 { ...@@ -241,12 +245,12 @@ public class DttRad2 {
hor_k[0][1] = fi[1][2] * hwindow_h[fi[1][1]]; // use cosine sign hor_k[0][1] = fi[1][2] * hwindow_h[fi[1][1]]; // use cosine sign
hor_k[1][0] = fi[0][3] * hwindow_h[fi[0][1]]; // use sine sign hor_k[1][0] = fi[0][3] * hwindow_h[fi[0][1]]; // use sine sign
hor_k[1][1] = fi[1][3] * hwindow_h[fi[1][1]]; // use sine sign hor_k[1][1] = fi[1][3] * hwindow_h[fi[1][1]]; // use sine sign
int indx = n*i + j; int indx = n*i + j;
for (int mode = 0; mode<4; mode++){ for (int mode = 0; mode<4; mode++){
for (int k = 0; k<4;k++) { for (int k = 0; k<4;k++) {
fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1]; fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1];
} }
} }
} }
...@@ -271,7 +275,7 @@ public class DttRad2 { ...@@ -271,7 +275,7 @@ public class DttRad2 {
double ahs = Math.sin(Math.PI/n2*shift_hor); double ahs = Math.sin(Math.PI/n2*shift_hor);
double avc = Math.cos(Math.PI/n2*shift_vert); double avc = Math.cos(Math.PI/n2*shift_vert);
double avs = Math.sin(Math.PI/n2*shift_vert); double avs = Math.sin(Math.PI/n2*shift_vert);
int [][] fi; int [][] fi;
for (int i = 0; i < n; i++ ){ for (int i = 0; i < n; i++ ){
fi = get_fold_indices(i,n); fi = get_fold_indices(i,n);
...@@ -283,24 +287,24 @@ public class DttRad2 { ...@@ -283,24 +287,24 @@ public class DttRad2 {
vert_k[0][1] = fi[1][2] * vw1; // use cosine sign vert_k[0][1] = fi[1][2] * vw1; // use cosine sign
vert_k[1][0] = fi[0][3] * vw0; // use sine sign vert_k[1][0] = fi[0][3] * vw0; // use sine sign
vert_k[1][1] = fi[1][3] * vw1; // use sine sign vert_k[1][1] = fi[1][3] * vw1; // use sine sign
for (int j = 0; j < n; j++ ){ for (int j = 0; j < n; j++ ){
fi = get_fold_indices(j,n); fi = get_fold_indices(j,n);
hor_ind[0] = fi[0][0]; hor_ind[0] = fi[0][0];
hor_ind[1] = fi[1][0]; hor_ind[1] = fi[1][0];
double hw0 = ahc*hwindow[fi[0][1]] + ahs*hwindow[fi[0][4]]*fi[0][5]; double hw0 = ahc*hwindow[fi[0][1]] + ahs*hwindow[fi[0][4]]*fi[0][5];
double hw1 = ahc*hwindow[fi[1][1]] + ahs*hwindow[fi[1][4]]*fi[1][5]; double hw1 = ahc*hwindow[fi[1][1]] + ahs*hwindow[fi[1][4]]*fi[1][5];
hor_k[0][0] = fi[0][2] * hw0; // use cosine sign hor_k[0][0] = fi[0][2] * hw0; // use cosine sign
hor_k[0][1] = fi[1][2] * hw1; // use cosine sign hor_k[0][1] = fi[1][2] * hw1; // use cosine sign
hor_k[1][0] = fi[0][3] * hw0; // use sine sign hor_k[1][0] = fi[0][3] * hw0; // use sine sign
hor_k[1][1] = fi[1][3] * hw1; // use sine sign hor_k[1][1] = fi[1][3] * hw1; // use sine sign
int indx = n*i + j; int indx = n*i + j;
for (int mode = 0; mode<4; mode++){ for (int mode = 0; mode<4; mode++){
for (int k = 0; k<4;k++) { for (int k = 0; k<4;k++) {
fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1]; fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1];
} }
} }
} }
...@@ -316,7 +320,7 @@ public class DttRad2 { ...@@ -316,7 +320,7 @@ public class DttRad2 {
double shift_vert, double shift_vert,
int debugLevel) // fpga scale (1 << 17 -1) int debugLevel) // fpga scale (1 << 17 -1)
{ // n - DCT and window size { // n - DCT and window size
int n2 = 2 * n; int n2 = 2 * n;
double [][][] fold_sk = new double[4][n*n][4]; double [][][] fold_sk = new double[4][n*n][4];
int [] vert_ind = new int[2]; int [] vert_ind = new int[2];
...@@ -354,7 +358,7 @@ public class DttRad2 { ...@@ -354,7 +358,7 @@ public class DttRad2 {
vert_k[0][1] = fi[1][2] * vw1; // use cosine sign vert_k[0][1] = fi[1][2] * vw1; // use cosine sign
vert_k[1][0] = fi[0][3] * vw0; // use sine sign vert_k[1][0] = fi[0][3] * vw0; // use sine sign
vert_k[1][1] = fi[1][3] * vw1; // use sine sign vert_k[1][1] = fi[1][3] * vw1; // use sine sign
for (int j = 0; j < n; j++ ){ for (int j = 0; j < n; j++ ){
fi = get_fold_indices(j,n); fi = get_fold_indices(j,n);
hor_ind[0] = fi[0][0]; hor_ind[0] = fi[0][0];
...@@ -363,32 +367,32 @@ public class DttRad2 { ...@@ -363,32 +367,32 @@ public class DttRad2 {
// double hw1 = ahc*hwindow[fi[1][1]] + ahs*hwindow[fi[1][4]]*fi[1][5]; // double hw1 = ahc*hwindow[fi[1][1]] + ahs*hwindow[fi[1][4]]*fi[1][5];
double hw0 = wnd_hor[hor_ind[0]]; double hw0 = wnd_hor[hor_ind[0]];
double hw1 = wnd_hor[hor_ind[1]]; double hw1 = wnd_hor[hor_ind[1]];
hor_k[0][0] = fi[0][2] * hw0; // use cosine sign hor_k[0][0] = fi[0][2] * hw0; // use cosine sign
hor_k[0][1] = fi[1][2] * hw1; // use cosine sign hor_k[0][1] = fi[1][2] * hw1; // use cosine sign
hor_k[1][0] = fi[0][3] * hw0; // use sine sign hor_k[1][0] = fi[0][3] * hw0; // use sine sign
hor_k[1][1] = fi[1][3] * hw1; // use sine sign hor_k[1][1] = fi[1][3] * hw1; // use sine sign
int indx = n*i + j; int indx = n*i + j;
for (int mode = 0; mode<4; mode++){ for (int mode = 0; mode<4; mode++){
for (int k = 0; k<4;k++) { for (int k = 0; k<4;k++) {
fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1]; fold_sk[mode][indx][k] = vert_k[(mode>>1) &1][(k>>1) & 1] * hor_k[mode &1][k & 1];
} }
} }
} }
} }
return fold_sk; return fold_sk;
} }
// return index and two signs (c,s) for 1-d imdct. x is index (0..2*n-1) of the imdct array, value is sign * (idct_index+1), // return index and two signs (c,s) for 1-d imdct. x is index (0..2*n-1) of the imdct array, value is sign * (idct_index+1),
// where idct_index (0..n-1) is index in the dct-iv array // where idct_index (0..n-1) is index in the dct-iv array
private int [] get_unfold_index_signs(int x, int n){ private int [] get_unfold_index_signs(int x, int n){
int n1 = n>>1; int n1 = n>>1;
int segm = x / n1; int segm = x / n1;
x = x % n1; x = x % n1;
int [] is2 = new int[3]; int [] is2 = new int[3];
switch (segm){ switch (segm){
case 0: is2[0] = x + n1; is2[1]= 1; is2[2] = 1; return is2; // return 1+ (x + n1); case 0: is2[0] = x + n1; is2[1]= 1; is2[2] = 1; return is2; // return 1+ (x + n1);
case 1: is2[0] = n - x - 1; is2[1]= -1; is2[2] = 1; return is2; // return -(n - x); case 1: is2[0] = n - x - 1; is2[1]= -1; is2[2] = 1; return is2; // return -(n - x);
...@@ -406,18 +410,18 @@ public class DttRad2 { ...@@ -406,18 +410,18 @@ public class DttRad2 {
int [] is2_vert = get_unfold_index_signs(i,n); int [] is2_vert = get_unfold_index_signs(i,n);
double [] k_vert = {is2_vert[1]*hwindow[(i < n)?i:n2 -i -1], is2_vert[2]*hwindow[(i < n)?i:n2 -i -1]}; double [] k_vert = {is2_vert[1]*hwindow[(i < n)?i:n2 -i -1], is2_vert[2]*hwindow[(i < n)?i:n2 -i -1]};
int index_vert = is2_vert[0] * n; int index_vert = is2_vert[0] * n;
for (int j = 0; j < 2*n; j++ ){ for (int j = 0; j < 2*n; j++ ){
int [] is2_hor = get_unfold_index_signs(j,n); int [] is2_hor = get_unfold_index_signs(j,n);
int index_hor = is2_hor[0]; int index_hor = is2_hor[0];
double [] k_hor = {is2_hor[1] * hwindow[(j < n)?j:n2 -j -1], is2_hor[2] * hwindow[(j < n)?j:n2 -j -1]}; double [] k_hor = {is2_hor[1] * hwindow[(j < n)?j:n2 -j -1], is2_hor[2] * hwindow[(j < n)?j:n2 -j -1]};
unfold_index[n2*i+j]=(index_vert+index_hor); unfold_index[n2*i+j]=(index_vert+index_hor);
for (int mode = 0; mode < 4; mode++){ for (int mode = 0; mode < 4; mode++){
unfold_k[mode][n2*i+j] = k_vert[(mode>>1) &1]*k_hor[mode &1]; unfold_k[mode][n2*i+j] = k_vert[(mode>>1) &1]*k_hor[mode &1];
} }
if (n < 8) System.out.print(String.format("%4d", unfold_index[n2*i+j])); if (n < 8) System.out.print(String.format("%4d", unfold_index[n2*i+j]));
} }
if (n < 8) System.out.println(); if (n < 8) System.out.println();
} }
...@@ -426,14 +430,14 @@ public class DttRad2 { ...@@ -426,14 +430,14 @@ public class DttRad2 {
System.out.println(i+"=>"+get_unfold_index_signs(i,n)[0]+", "+get_unfold_index_signs(i,n)[1]+", "+get_unfold_index_signs(i,n)[2]); System.out.println(i+"=>"+get_unfold_index_signs(i,n)[0]+", "+get_unfold_index_signs(i,n)[1]+", "+get_unfold_index_signs(i,n)[2]);
} }
} }
} }
public double [] dttt_iv(double [] x){ public double [] dttt_iv(double [] x){
return dttt_iv(x, 0, 1 << (ilog2(x.length)/2)); return dttt_iv(x, 0, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iv(double [] x, int mode){ public double [] dttt_iv(double [] x, int mode){
return dttt_iv(x, mode, 1 << (ilog2(x.length)/2)); return dttt_iv(x, mode, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iv(double [] x, int mode, int n){ // mode 0 - dct,dct 1:dst,dct, 2: dct, dst, 3: dst,dst public double [] dttt_iv(double [] x, int mode, int n){ // mode 0 - dct,dct 1:dst,dct, 2: dct, dst, 3: dst,dst
double [] y = new double [n*n]; double [] y = new double [n*n];
...@@ -442,7 +446,7 @@ public class DttRad2 { ...@@ -442,7 +446,7 @@ public class DttRad2 {
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 = ((mode & 1)!=0)? dst_iv(line):dct_iv(line); line = ((mode & 1)!=0)? dst_iv(line):dct_iv(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++){
...@@ -495,11 +499,11 @@ public class DttRad2 { ...@@ -495,11 +499,11 @@ public class DttRad2 {
} }
return y; return y;
} }
public double [] dttt_ii(double [] x){ public double [] dttt_ii(double [] x){
return dttt_ii(x, 1 << (ilog2(x.length)/2)); return dttt_ii(x, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_ii(double [] x, int n){ public double [] dttt_ii(double [] x, int n){
...@@ -509,7 +513,7 @@ public class DttRad2 { ...@@ -509,7 +513,7 @@ public class DttRad2 {
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 = dctii_direct(line); line = dctii_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++){
...@@ -521,14 +525,14 @@ public class DttRad2 { ...@@ -521,14 +525,14 @@ public class DttRad2 {
} }
public double [] dttt_iie(double [] x){ public double [] dttt_iie(double [] x){
return dttt_iie(x,0, 1 << (ilog2(x.length)/2)); return dttt_iie(x,0, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iie(double [] x, int mode){ public double [] dttt_iie(double [] x, int mode){
return dttt_iie(x, mode, 1 << (ilog2(x.length)/2)); return dttt_iie(x, mode, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iie(double [] x, int mode, 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
...@@ -536,7 +540,7 @@ public class DttRad2 { ...@@ -536,7 +540,7 @@ public class DttRad2 {
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); 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++){
...@@ -547,12 +551,12 @@ public class DttRad2 { ...@@ -547,12 +551,12 @@ public class DttRad2 {
} }
return y; return y;
} }
public double [] dttt_iii(double [] x){ public double [] dttt_iii(double [] x){
return dttt_iii(x, 1 << (ilog2(x.length)/2)); return dttt_iii(x, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iii(double [] x, int n){ public double [] dttt_iii(double [] x, int n){
...@@ -562,7 +566,7 @@ public class DttRad2 { ...@@ -562,7 +566,7 @@ public class DttRad2 {
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 = dctiii_direct(line); line = dctiii_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++){
...@@ -574,10 +578,10 @@ public class DttRad2 { ...@@ -574,10 +578,10 @@ public class DttRad2 {
} }
public double [] dttt_iiie(double [] x){ public double [] dttt_iiie(double [] x){
return dttt_iiie(x,0, 1 << (ilog2(x.length)/2)); return dttt_iiie(x,0, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iiie(double [] x, int mode){ public double [] dttt_iiie(double [] x, int mode){
return dttt_iiie(x, mode, 1 << (ilog2(x.length)/2)); return dttt_iiie(x, mode, 1 << (ilog2(x.length)/2));
} }
public double [] dttt_iiie(double [] x, int mode, int n){ public double [] dttt_iiie(double [] x, int mode, int n){
...@@ -588,7 +592,7 @@ public class DttRad2 { ...@@ -588,7 +592,7 @@ public class DttRad2 {
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); 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++){
...@@ -599,7 +603,7 @@ public class DttRad2 { ...@@ -599,7 +603,7 @@ public class DttRad2 {
} }
return y; return y;
} }
public void set_window(){ public void set_window(){
set_window(0); set_window(0);
} }
...@@ -627,7 +631,7 @@ public class DttRad2 { ...@@ -627,7 +631,7 @@ public class DttRad2 {
set_fold_2d(len); set_fold_2d(len);
set_unfold_2d(len); set_unfold_2d(len);
} }
// get current LT window as a 2d tile (2*size * 2*size) // get current LT window as a 2d tile (2*size * 2*size)
public double [] getWin2d(){ public double [] getWin2d(){
int size = this.hwindow.length; int size = this.hwindow.length;
...@@ -638,16 +642,16 @@ public class DttRad2 { ...@@ -638,16 +642,16 @@ public class DttRad2 {
int ia1 = (size2 - i -1) * size2; int ia1 = (size2 - i -1) * size2;
for (int j=0; j< size; j++){ for (int j=0; j< size; j++){
double d = this.hwindow[i] * this.hwindow[j]; double d = this.hwindow[i] * this.hwindow[j];
rslt [ia0 + j] = d; rslt [ia0 + j] = d;
rslt [ia1 + j] = d; rslt [ia1 + j] = d;
rslt [ia0 + size2 - j -1] = d; rslt [ia0 + size2 - j -1] = d;
rslt [ia1 + size2 - j -1] = d; rslt [ia1 + size2 - j -1] = d;
} }
} }
return rslt; return rslt;
} }
// Convert 2nx2n overlapping tile to n*n for dct-iv // Convert 2nx2n overlapping tile to n*n for dct-iv
public double [] fold_tile(double [] x, int mode) { // x should be 2n*2n public double [] fold_tile(double [] x, int mode) { // x should be 2n*2n
return fold_tile(x, 1 << (ilog2(x.length/4)/2)); return fold_tile(x, 1 << (ilog2(x.length/4)/2));
...@@ -692,20 +696,20 @@ public class DttRad2 { ...@@ -692,20 +696,20 @@ public class DttRad2 {
} }
return y; return y;
} }
public double [] unfold_tile( public double [] unfold_tile(
double [] x, // x should be n*n double [] x, // x should be n*n
int mode) int mode)
{ {
return unfold_tile(x, 1 << (ilog2(x.length)/2), mode); return unfold_tile(x, 1 << (ilog2(x.length)/2), mode);
} }
public double [] unfold_tile( public double [] unfold_tile(
double [] x, // x should be 2n*2n double [] x, // x should be 2n*2n
int n, int n,
int mode) int mode)
{ {
double [] y = new double [4*n*n]; double [] y = new double [4*n*n];
for (int i = 0; i<y.length;i++) { for (int i = 0; i<y.length;i++) {
...@@ -714,7 +718,7 @@ public class DttRad2 { ...@@ -714,7 +718,7 @@ public class DttRad2 {
return y; return y;
} }
public double [] dctii_direct(double[] x){ public double [] dctii_direct(double[] x){
int n = x.length; int n = x.length;
int t = ilog2(n)-1; int t = ilog2(n)-1;
...@@ -725,7 +729,7 @@ public class DttRad2 { ...@@ -725,7 +729,7 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= CII[t][i][j]*x[j]; y[i]+= CII[t][i][j]*x[j];
} }
} }
return y; return y;
...@@ -741,13 +745,13 @@ public class DttRad2 { ...@@ -741,13 +745,13 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= CIIe[t][i][j]*x[j]; y[i]+= CIIe[t][i][j]*x[j];
} }
} }
return y; return y;
} }
public double [] dctiii_direct(double[] x){ public double [] dctiii_direct(double[] x){
// CIII=transp(CII) // CIII=transp(CII)
int n = x.length; int n = x.length;
...@@ -759,12 +763,12 @@ public class DttRad2 { ...@@ -759,12 +763,12 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= CII[t][j][i]*x[j]; y[i]+= CII[t][j][i]*x[j];
} }
} }
return y; return y;
} }
public double [] dctiiie_direct(double[] x){ public double [] dctiiie_direct(double[] x){
int n = x.length; int n = x.length;
int t = ilog2(n)-1; int t = ilog2(n)-1;
...@@ -775,12 +779,12 @@ public class DttRad2 { ...@@ -775,12 +779,12 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= CIIIe[t][i][j]*x[j]; y[i]+= CIIIe[t][i][j]*x[j];
} }
} }
return y; return y;
} }
public double [] dctiv_direct(double[] x){ public double [] dctiv_direct(double[] x){
int n = x.length; int n = x.length;
int t = ilog2(n)-1; int t = ilog2(n)-1;
...@@ -791,7 +795,7 @@ public class DttRad2 { ...@@ -791,7 +795,7 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= CIV[t][i][j]*x[j]; y[i]+= CIV[t][i][j]*x[j];
} }
} }
return y; return y;
...@@ -807,7 +811,7 @@ public class DttRad2 { ...@@ -807,7 +811,7 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= SIIe[t][i][j]*x[j]; y[i]+= SIIe[t][i][j]*x[j];
} }
} }
return y; return y;
...@@ -823,12 +827,12 @@ public class DttRad2 { ...@@ -823,12 +827,12 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= SIIIe[t][i][j]*x[j]; y[i]+= SIIIe[t][i][j]*x[j];
} }
} }
return y; 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;
...@@ -839,7 +843,7 @@ public class DttRad2 { ...@@ -839,7 +843,7 @@ public class DttRad2 {
for (int i = 0; i<n; i++) { for (int i = 0; i<n; i++) {
y[i] = 0.0; y[i] = 0.0;
for (int j = 0; j< n; j++){ for (int j = 0; j< n; j++){
y[i]+= SIV[t][i][j]*x[j]; y[i]+= SIV[t][i][j]*x[j];
} }
} }
return y; return y;
...@@ -850,7 +854,7 @@ public class DttRad2 { ...@@ -850,7 +854,7 @@ public class DttRad2 {
int l = ilog2(N)-1; int l = ilog2(N)-1;
CN1 = new double[l][]; CN1 = new double[l][];
SN1 = new double[l][]; SN1 = new double[l][];
for (int t = 0; t<CN1.length; t++) { for (int t = 0; t<CN1.length; t++) {
int n1 = 2 << t; // for N==3: 2, 4, 8 int n1 = 2 << t; // for N==3: 2, 4, 8
double pi_4n=Math.PI/(8*n1); // n1 = n/2 double pi_4n=Math.PI/(8*n1); // n1 = n/2
...@@ -860,11 +864,11 @@ public class DttRad2 { ...@@ -860,11 +864,11 @@ public class DttRad2 {
CN1[t][k] = Math.cos((2*k+1)*pi_4n); CN1[t][k] = Math.cos((2*k+1)*pi_4n);
SN1[t][k] = Math.sin((2*k+1)*pi_4n); SN1[t][k] = Math.sin((2*k+1)*pi_4n);
} }
} }
} }
private void setup_CII(int maxN){ private void setup_CII(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(CII==null) && (CII.length >= l)) return; if (!(CII==null) && (CII.length >= l)) return;
CII = new double[l][][]; // only needed for direct? Assign only when needed? CII = new double[l][][]; // only needed for direct? Assign only when needed?
...@@ -878,14 +882,14 @@ public class DttRad2 { ...@@ -878,14 +882,14 @@ public class DttRad2 {
if (j==0) ej= Math.sqrt(0.5); if (j==0) ej= Math.sqrt(0.5);
else ej = 1.0; else ej = 1.0;
for (int k = 0; k<n; k++){ for (int k = 0; k<n; k++){
CII[t][j][k] = scale * ej * Math.cos(j*(2*k+1)*pi_2n); CII[t][j][k] = scale * ej * Math.cos(j*(2*k+1)*pi_2n);
} }
} }
} }
} }
private void setup_CIIe(int maxN){ private void setup_CIIe(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(CIIe==null) && (CIIe.length >= l)) return; if (!(CIIe==null) && (CIIe.length >= l)) return;
CIIe = new double[l][][]; // only needed for direct? Assign only when needed? CIIe = new double[l][][]; // only needed for direct? Assign only when needed?
...@@ -896,14 +900,14 @@ public class DttRad2 { ...@@ -896,14 +900,14 @@ 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++){
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);
} }
} }
} }
} }
private void setup_CIIIe(int maxN){ private void setup_CIIIe(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(CIIIe==null) && (CIIIe.length >= l)) return; if (!(CIIIe==null) && (CIIIe.length >= l)) return;
CIIIe = new double[l][][]; // only needed for direct? Assign only when needed? CIIIe = new double[l][][]; // only needed for direct? Assign only when needed?
...@@ -918,15 +922,15 @@ public class DttRad2 { ...@@ -918,15 +922,15 @@ public class DttRad2 {
// if (j==0) ej= 0.5; // Math.sqrt(0.5); Should it be this? https://en.wikipedia.org/wiki/Discrete_cosine_transform#DCT-III // 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][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);
} }
} }
} }
} }
private void setup_CIV(int maxN){ private void setup_CIV(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(CIV==null) && (CIV.length >= l)) return; if (!(CIV==null) && (CIV.length >= l)) return;
CIV = new double[l][][]; CIV = new double[l][][];
...@@ -937,17 +941,17 @@ public class DttRad2 { ...@@ -937,17 +941,17 @@ public class DttRad2 {
double pi_4n=Math.PI/(4*n); double pi_4n=Math.PI/(4*n);
for (int j=0;j<n; j++){ for (int j=0;j<n; j++){
for (int k = 0; k < j; k++){ for (int k = 0; k < j; k++){
CIV[t][j][k] = CIV[t][k][j]; CIV[t][j][k] = CIV[t][k][j];
} }
for (int k = j; k<n; k++){ for (int k = j; k<n; k++){
CIV[t][j][k] = scale * Math.cos((2*j+1)*(2*k+1)*pi_4n); CIV[t][j][k] = scale * Math.cos((2*j+1)*(2*k+1)*pi_4n);
} }
} }
} }
} }
private void setup_SIIe(int maxN){ private void setup_SIIe(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(SIIe==null) && (SIIe.length >= l)) return; if (!(SIIe==null) && (SIIe.length >= l)) return;
SIIe = new double[l][][]; // only needed for direct? Assign only when needed? SIIe = new double[l][][]; // only needed for direct? Assign only when needed?
...@@ -958,14 +962,14 @@ public class DttRad2 { ...@@ -958,14 +962,14 @@ 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++){
for (int k = 0; k<n; k++){ for (int k = 0; k<n; k++){
SIIe[t][j][k] = scale * Math.sin((j+1)*(2*k+1)*pi_2n); SIIe[t][j][k] = scale * Math.sin((j+1)*(2*k+1)*pi_2n);
} }
} }
} }
} }
private void setup_SIIIe(int maxN){ private void setup_SIIIe(int maxN){
if (maxN > N) setup_arrays(maxN); if (maxN > N) setup_arrays(maxN);
int l = ilog2(N); int l = ilog2(N);
if (!(SIIIe==null) && (SIIIe.length >= l)) return; if (!(SIIIe==null) && (SIIIe.length >= l)) return;
SIIIe = new double[l][][]; // only needed for direct? Assign only when needed? SIIIe = new double[l][][]; // only needed for direct? Assign only when needed?
...@@ -980,14 +984,14 @@ public class DttRad2 { ...@@ -980,14 +984,14 @@ public class DttRad2 {
if (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; else ej = 1.0;
for (int k = 0; k<n; k++){ for (int k = 0; k<n; k++){
SIIIe[t][k][j] = scale * ej * Math.sin((j+1)*(2*k+1)*pi_2n); 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);
if (!(SIV==null) && (SIV.length >= l)) return; if (!(SIV==null) && (SIV.length >= l)) return;
SIV = new double[l][][]; SIV = new double[l][][];
...@@ -998,22 +1002,22 @@ public class DttRad2 { ...@@ -998,22 +1002,22 @@ public class DttRad2 {
double pi_4n=Math.PI/(4*n); double pi_4n=Math.PI/(4*n);
for (int j=0;j<n; j++){ for (int j=0;j<n; j++){
for (int k = 0; k < j; k++){ for (int k = 0; k < j; k++){
SIV[t][j][k] = SIV[t][k][j]; SIV[t][j][k] = SIV[t][k][j];
} }
for (int k = j; k<n; k++){ for (int k = j; k<n; k++){
SIV[t][j][k] = scale * Math.sin((2*j+1)*(2*k+1)*pi_4n); SIV[t][j][k] = scale * Math.sin((2*j+1)*(2*k+1)*pi_4n);
} }
} }
} }
} }
private int ilog2(int n){ private int ilog2(int n){
int i; int i;
for (i=0; n>1; n= n >> 1) i++; for (i=0; n>1; n= n >> 1) i++;
return i; return i;
} }
private double [] _dctii_recurs(double[] x){ private double [] _dctii_recurs(double[] x){
int n = x.length; int n = x.length;
...@@ -1059,8 +1063,8 @@ public class DttRad2 { ...@@ -1059,8 +1063,8 @@ public class DttRad2 {
} }
double [] v0 = _dctii_recurs(u0); double [] v0 = _dctii_recurs(u0);
double [] v1 = _dctii_recurs(u1); //both cos-II double [] v1 = _dctii_recurs(u1); //both cos-II
double [] w0 = new double [n1]; double [] w0 = new double [n1];
double [] w1 = new double [n1]; double [] w1 = new double [n1];
...@@ -1068,9 +1072,9 @@ public class DttRad2 { ...@@ -1068,9 +1072,9 @@ public class DttRad2 {
w1[n1-1] = sqrt2 * v1[0]; w1[n1-1] = sqrt2 * v1[0];
for (int j = 0; j< n1; j++){ for (int j = 0; j< n1; j++){
int sgn = (1 - 2* (j & 1)); int sgn = (1 - 2* (j & 1));
if (j > 0) w0[j] = v0[j] - sgn * v1[n1 - j]; if (j > 0) w0[j] = v0[j] - sgn * v1[n1 - j];
if (j < (n1-1)) w1[j] = v0[j+1] - sgn * v1[n1 - j -1]; if (j < (n1-1)) w1[j] = v0[j+1] - sgn * v1[n1 - j -1];
} }
double [] y = new double[n]; double [] y = new double[n];
for (int j = 0; j< n1; j++){ for (int j = 0; j< n1; j++){
...@@ -1079,6 +1083,6 @@ public class DttRad2 { ...@@ -1079,6 +1083,6 @@ public class DttRad2 {
} }
return y; return y;
} }
} }
...@@ -27,7 +27,7 @@ import Jama.Matrix; ...@@ -27,7 +27,7 @@ import Jama.Matrix;
import ij.ImageStack; import ij.ImageStack;
public class ImageDtt { public class ImageDtt {
static boolean FPGA_COMPARE_DATA= true; // false; // static boolean FPGA_COMPARE_DATA= false; // true; // false; //
static int FPGA_SHIFT_BITS = 7; // number of bits for fractional pixel shift static int FPGA_SHIFT_BITS = 7; // number of bits for fractional pixel shift
static int FPGA_PIXEL_BITS = 15; // bits to represent pixel data (positive) static int FPGA_PIXEL_BITS = 15; // bits to represent pixel data (positive)
static int FPGA_WND_BITS = 17; // bits to represent mclt window (positive for 18-bit signed mpy input) static int FPGA_WND_BITS = 17; // bits to represent mclt window (positive for 18-bit signed mpy input)
...@@ -979,6 +979,48 @@ public class ImageDtt { ...@@ -979,6 +979,48 @@ public class ImageDtt {
return clt_data; return clt_data;
} }
public void printSignsFPGA (
DttRad2 dtt
){
double [][][] fold_coeff = dtt.getFoldK();
int [][] fpga_fi = dtt.getFoldIndex();
// For R/B color channels (1 - 4 non-zero) show signs during folding of a single pixel contributor (4 Bayer variants) per each mode
String [] mode_names={"CC","SC", "CS","SS"};
int [] bayer_patterns = {0x1, 0x2, 0x4, 0x8}; // , 0x9, 0x6};
boolean [][][] signs = new boolean [bayer_patterns.length][4][64];
// for (int bp:bayer_patterns){
for (int ibp = 0; ibp < bayer_patterns.length; ibp++){
int bp = bayer_patterns[ibp];
System.out.println("\nPattern (row/col) "+bp+":");
System.out.println("| "+(((bp & 1) !=0) ? "X ":" ")+(((bp & 2) !=0) ? "X ":" ")+"|");
System.out.println("| "+(((bp & 4) !=0) ? "X ":" ")+(((bp & 8) !=0) ? "X ":" ")+"|");
for (int mode = 0; mode < 4; mode++){
if (mode == 0) System.out.println("DTT mode = "+mode+" ("+ mode_names[mode]+"): term sign");
else System.out.println("DTT mode = "+mode+" ("+ mode_names[mode]+"): term inverse relative to CC ");
for (int i = 0; i < 64; i++){
for (int k = 0; k < 4; k++){
int row = (fpga_fi[i][k] >> 4);
int col = (fpga_fi[i][k] & 0xf);
int indx = (row & 1) + 2 * (col & 1);
if (((1 << indx) & bp) != 0) { // only use non-zero pixels, for 1 in 4 - only one k would match
signs[ibp][mode][i] = fold_coeff[mode][i][k] < 0;
if (mode == 0) {
if (fold_coeff[mode][i][k] < 0) System.out.print("- ");
else System.out.print("+ ");
} else {
boolean sgn = signs[ibp][mode][i] ^ signs[ibp][0][i];
if (sgn) System.out.print("* ");
else System.out.print(". ");
}
// continue;
}
}
if ((i+1)%8 == 0) System.out.println();
}
}
}
}
public void generateFPGACompareData( public void generateFPGACompareData(
final double [][] image_data, // for selected subcamera final double [][] image_data, // for selected subcamera
...@@ -987,6 +1029,9 @@ public class ImageDtt { ...@@ -987,6 +1029,9 @@ public class ImageDtt {
final int width, final int width,
DttRad2 dtt DttRad2 dtt
){ ){
printSignsFPGA(dtt);
int height = image_data[0].length/width; int height = image_data[0].length/width;
double [][][] fpga_clt_data_in = new double [3][4][]; double [][][] fpga_clt_data_in = new double [3][4][];
double [][][] fpga_clt_data_out = new double [3][4][]; double [][][] fpga_clt_data_out = new double [3][4][];
...@@ -1651,9 +1696,14 @@ public class ImageDtt { ...@@ -1651,9 +1696,14 @@ public class ImageDtt {
// { 1.3, -2.7}, // { 1.3, -2.7},
// {-1.3, 2.7}, // {-1.3, 2.7},
// { 0.0, 0.0}}; // { 0.0, 0.0}};
// { 2.3, -2.7},
// {-0.3, 2.7},
// { 0.0, 0.0}};
{ 2.3, -2.7}, { 2.3, -2.7},
{-0.3, 2.7}, {-0.3, 2.7},
{ 0.0, 0.0}}; { 1.0, 0.0}};
double [][] colorCentersXY = { double [][] colorCentersXY = {
{centersXY[fpga_cam][0] + manual_offsets[0][0], centersXY[fpga_cam][1] + manual_offsets[0][1]}, // add manual offsets here {centersXY[fpga_cam][0] + manual_offsets[0][0], centersXY[fpga_cam][1] + manual_offsets[0][1]}, // add manual offsets here
......
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