📄 displayroutines.cpp
字号:
RxDet->DirIphs[i] = br->ReadInt32();
RxDet->DirQphs[i] = br->ReadInt32();
RxDet->DirMag[i] = br->ReadInt32();
}
// Read the Directional Coupler error terms 12-26-2005
RxDet->CouplerPhase = br->ReadDouble();
RxDet->CouplerMagnitude = br->ReadDouble();
}
catch(System::IO::IOException* pe)
{
MessageBox::Show(S"Error trying to load Detector Calibration File.\n\r"
S"Delete the file: detector.ica and re-run Detector Calibration", pe->Message,
MessageBoxButtons::OK, MessageBoxIcon::Error);
return;
}
__finally
{
if (br)
br->Close();
if (fs)
fs->Close();
}
RxDet->calibrated = true; // loaded a valid detector calibration
TxDet->calibrated = true;
RxDet->DirCalibrated = true;
};
/// Resolve reflected measured data set to Magnitude and Phase
void CalDataSet::ResolveReflPolar(int ReflPI, int ReflPQ, int ReflMQ, int Frequency, double& rmag, double& rphs,
bool CouplerComp)
{
double magnitude, phase;
// double phasetwiddle;
// double magtwiddle;
// double magadd, phaseadd;
phase = RxDet->IQtoDegrees(ReflPI, ReflPQ);
magnitude = RxDet->MagTodBRefl(Frequency, ReflMQ);
// phasetwiddle = double(Frequency)/1000000 * 0.013 * -magnitude; // phase drift vs. magnitude
#ifdef COUPLERCAL
if(CouplerComp) // Subtract coupler V/I tracking error (in dB) if requested
{
double angle = RxDet->CouplerPhase - phase;
if (angle >180.0)
angle -= 360.0;
if (angle < -180.0)
angle += 360.0;
magnitude += (RxDet->CouplerMagnitude * sin(angle * DEGR2RAD));
}
#endif
magnitude = pow(10.0, (magnitude/20.0)); // translate db_return_loss to voltage ratio
rphs = phase; // return phase in degrees (-180..+180)
rmag = magnitude; // return linear magnitude (0..1)
// twiddle the phase by estimated amp-to-phase conversion
// rphs += phasetwiddle;
// twiddle the mag to account for -3 dbm level
//rmag *= 1.414;
// New 10-17-2005 - adjust the reflected Magnitude and Phase by the Directivity Cal
int FreqBase, FreqBaseNext; // Two adjacent cal frequency points
double FreqRemainder; // remainder of freq between cal points
int Freq = Frequency;
#ifdef DIRECTCAL
if (RxDet->DirCalibrated)
{
// Result is frequency-dependent. Interpolate the frequency between two datasets to construct
// a linear-frequency approximation of the cal data for the desired frequency.
// Every 200 KHz from 200K to 1MHz, then every 10 MHz up to 120 MHz.
// Index: 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
// Freq: 200k 300k 400k 500k 600k 700k 800k 900k 1M 10M 20M 30M 40M 50M 60M 70M 80M 90M 100M 110M
// Build interpolated dataset between two frequencies
if (Freq <= 1000000) // 1 MHZ and below
{
FreqBase = (Freq - 200000)/100000;
FreqRemainder = (double)(Freq - (FreqBase + 2) * 100000)/100000; // Remainder of frequency, value between 0..1
}
else if (Freq < 10000000) // Between 1 and 10 MHz
{
FreqBase = 8;
FreqRemainder = (double)(Freq - 1000000)/9000000;
}
else // 10 MHz to 120 MHz
{
FreqBase = (Freq / 10000000) + 8; // Base is the integer part of the frequency index
FreqRemainder = (double)(Freq - (FreqBase - 8) * 10000000)/10000000; // Remainder of frequency, value between 0..1
}
if (FreqRemainder < 0.001)
FreqBaseNext = FreqBase; // Prevent index overflow
else
FreqBaseNext = FreqBase + 1;
int I, Q, M; // Interpolate between Directivity Cal points
I = RxDet->DirIphs[FreqBase] + (int)((RxDet->DirIphs[FreqBaseNext] - RxDet->DirIphs[FreqBase]) * FreqRemainder);
Q = RxDet->DirQphs[FreqBase] + (int)((RxDet->DirQphs[FreqBaseNext] - RxDet->DirQphs[FreqBase]) * FreqRemainder);
M = RxDet->DirMag[FreqBase] + (int)((RxDet->DirMag[FreqBaseNext] - RxDet->DirMag[FreqBase]) * FreqRemainder);
double DirPhase = RxDet->IQtoDegrees(I, Q);
double DirMagnitudedB = RxDet->MagTodBRefl(Frequency, M);
double DirMagnitudeLin = pow(10.0, (DirMagnitudedB/20.0)); // translate db_return_loss to voltage ratio
AddPolar(rmag, rphs, -DirMagnitudeLin, DirPhase); // Subtract Directivity error from Reflection reading
} // End if calibrated
#endif
if (rphs > 180.0)
rphs -= 360.0;
if (rphs < -180.0)
rphs += 360.0;
return;
}
/// Resolve transmitted measured data set to Magnitude and Phase
void CalDataSet::ResolveTranPolar(int TranPI, int TranPQ, int TranMQHi, int TranMQLo, int TranMQMid, int Frequency, double& rmag, double& rphs)
{
double magnitude, phase;
phase = TxDet->IQtoDegrees(TranPI, TranPQ);
magnitude = TxDet->MagTodBTran(Frequency, TranMQHi, TranMQLo, TranMQMid);
// offset phase by 180 degrees for Trans measurements
phase += 180.0;
if (phase > 180.0)
phase -= 360.0;
if (phase < -180.0)
phase += 360.0;
magnitude = pow(10.0, (magnitude/20.0)); // translate db to voltage ratio
rmag = magnitude; // return linear magnitude (0..1)
rphs = phase; // return phase in degrees (-180..+180)
}
/// Construct Cal error terms from Cal raw data at each frequency point
void CalToErrorTerms(CalDataSet* Cal)
{
for (int i=0; i<1024; i++)
{
std::complex<double> two(2.0, 0.0);
std::complex<double> rslt(0.0, 0.0);
double realpart, imagpart;
realpart = Cal->S11shortReal[i];
imagpart = Cal->S11shortImag[i];
std::complex<double> Sshort(realpart, imagpart);
realpart = Cal->S11openReal[i];
imagpart = Cal->S11openImag[i];
std::complex<double> Sopen(realpart, imagpart);
realpart = Cal->S11termReal[i];
imagpart = Cal->S11termImag[i];
std::complex<double> Sterm(realpart, imagpart);
// Directivity error term
Cal->EdReal[i] = Cal->S11termReal[i];
Cal->EdImag[i] = Cal->S11termImag[i];
// Source mismatch error term
rslt = ((two * Sterm) - (Sshort + Sopen)) / (Sshort - Sopen);
Cal->EsReal[i] = real(rslt);
Cal->EsImag[i] = imag(rslt);
// Tracking error term
rslt = ((two * (Sopen - Sterm) * (Sshort - Sterm)) / (Sshort - Sopen));
Cal->EtReal[i] = real(rslt);
Cal->EtImag[i] = imag(rslt);
}
};
/// Convert measured S11 into actual S11 via calibration
void CorrectS11(CalDataSet* Cal, int Frequency, double measmag, double measphs, double& rsltmag, double& rsltphs)
{
// There are 1024 calibration frequencies, find the two adjacent to the measured frequency.
// Linearly interpolate (real, imag) between the two cal points
int i, j;
double delta, position;
double realpart, imagpart;
delta = (MAXCALFREQ - MINCALFREQ)/ (NUMCALPTS - 1); // frequency separation of cal points
i = (int)(((double)Frequency - MINCALFREQ) / delta); // Cal frequency directly below ours
j = i+1; // Cal frequency directly above ours
if(j >= (int)NUMCALPTS)
j = (int)NUMCALPTS - 1; // In case we are close to MAX cal frequnecy
position = (((double)Frequency - MINCALFREQ) / delta) - i ; // fractional position between i and j
// transform measured S11 into actual S11
std::complex<double> rslt;
realpart = Cal->EdReal[i] + ((Cal->EdReal[j] - Cal->EdReal[i]) * position); // interpolate
imagpart = Cal->EdImag[i] + ((Cal->EdImag[j] - Cal->EdImag[i]) * position);
std::complex<double> Ed(realpart, imagpart);
realpart = Cal->EsReal[i] + ((Cal->EsReal[j] - Cal->EsReal[i]) * position); // interpolate
imagpart = Cal->EsImag[i] + ((Cal->EsImag[j] - Cal->EsImag[i]) * position);
std::complex<double> Es(realpart, imagpart);
realpart = Cal->EtReal[i] + ((Cal->EtReal[j] - Cal->EtReal[i]) * position); // interpolate
imagpart = Cal->EtImag[i] + ((Cal->EtImag[j] - Cal->EtImag[i]) * position);
std::complex<double> Et(realpart, imagpart);
// Convert measured data to rectangular coordinates
double measreal, measimag;
double phase_radians = measphs * DEGR2RAD;
measreal = measmag * cos(phase_radians);
measimag = measmag * sin(phase_radians);
std::complex<double> S11meas(measreal, measimag);
rslt = ((S11meas - Ed) / (Es * (S11meas - Ed) + Et));
// Convert results to polar coordinates
double x = real(rslt);
double y = imag(rslt);
double fphase = atan2(y, x) * RAD2DEGR;
double fmagnitude = sqrt(x*x + y*y);
rsltmag = fmagnitude;
rsltphs = fphase;
}
/// Convert measured S21 into actual S21 via calibration
void CorrectS21(CalDataSet* Cal, int Frequency, double measmag, double measphs, double& rsltmag, double& rsltphs)
{
// There are 1024 calibration frequencies, find the two adjacent to the measured frequency.
// Linearly interpolate (real, imag) between the two cal points
int i, j;
double delta, position;
double realpart, imagpart;
delta = (MAXCALFREQ - MINCALFREQ)/ (NUMCALPTS - 1); // frequency separation of cal points
i = (int)(((double)Frequency - MINCALFREQ) / delta); // Cal frequency directly below ours
j = i+1; // Cal frequency directly above ours
if(j >= (int)NUMCALPTS)
j = (int)NUMCALPTS - 1; // In case we are close to MAX cal frequnecy
position = (((double)Frequency - MINCALFREQ) / delta) - i ; // fractional position between i and j
realpart = Cal->ThReal[i] + ((Cal->ThReal[j] - Cal->ThReal[i]) * position); // interpolate between calibration points
imagpart = Cal->ThImag[i] + ((Cal->ThImag[j] - Cal->ThImag[i]) * position);
// transform measured S21 into actual S21
std::complex<double> rslt;
std::complex<double> Th(realpart, imagpart);
// Convert measured data to rectangular coordinates
double measreal, measimag;
double phase_radians = measphs * DEGR2RAD;
measreal = measmag * cos(phase_radians);
measimag = measmag * sin(phase_radians);
std::complex<double> S21meas(measreal, measimag);
rslt = S21meas / Th;
// Convert results to polar coordinates
double x = real(rslt);
double y = imag(rslt);
double fphase = atan2(y, x) * RAD2DEGR;
double fmagnitude = sqrt(x*x + y*y);
rsltmag = fmagnitude;
rsltphs = fphase;
}
/// Load Fixture Calibration Data Set
bool LoadCalDataSet(OpenFileDialog* infile, CalDataSet* Cal)
{
FileStream* fs;
BinaryReader* br;
try
{
// Create a filestream & binary reader
fs = new FileStream(infile->FileName, FileMode::Open, FileAccess::Read);
br = new BinaryReader(fs);
// Define header to match file identifying type and version
String* recognized = new String(S"VNA Calibration Data Set Version 1.0.0");
String* header;
header = br->ReadString(); // get string header on infile
if (String::Compare(recognized, header) != 0)
{
MessageBox::Show(
S"CalDataSet file is incompatible type or version.\n\rExpecting Version 1.0.0",
S"Error", MessageBoxButtons::OK, MessageBoxIcon::Error);
br->Close();
fs->Close();
return false;
}
for (int i=0; i<1024; i++) // read in the data set
{
Cal->EdReal[i] = br->ReadDouble();
Cal->EdImag[i] = br->ReadDouble();
Cal->EsReal[i] = br->ReadDouble();
Cal->EsImag[i] = br->ReadDouble();
Cal->EtReal[i] = br->ReadDouble();
Cal->EtImag[i] = br->ReadDouble();
Cal->ThReal[i] = br->ReadDouble();
Cal->ThImag[i] = br->ReadDouble();
// debug - load in the generating dataset
Cal->S11openReal[i] = br->ReadDouble();
Cal->S11openImag[i] = br->ReadDouble();
Cal->S11shortReal[i] = br->ReadDouble();
Cal->S11shortImag[i] = br->ReadDouble();
Cal->S11termReal[i] = br->ReadDouble();
Cal->S11termImag[i] = br->ReadDouble();
}
return true;
}
catch(System::IO::FileNotFoundException * pe)
{
MessageBox::Show(String::Concat(pe->Message,
S"\n\n\rError trying to read Cal Data Set. The file cannot be found.\n\r"
S"Load a valid Fixture Calibration file in order to enable Fixture Calibration."),
S"Fixture Cal File Not Found", MessageBoxButtons::OK, MessageBoxIcon::Warning);
return false;
}
catch(System::IO::IOException* pe)
{
MessageBox::Show(String::Concat(pe->Message,
S"\n\n\rError trying to read Cal Data Set:\n\r", infile->FileName,
S"\n\n\rEither the file is corrupted or the file version is incompatible.\n\r"
S"Try creating a new Fixture Cal file, or Load a valid Fixture Calibration file\n\r"
S"in order to enable Fixture Calibration."),
S"Fixture Cal Data Error", MessageBoxButtons::OK, MessageBoxIcon::Exclamation);
return false;
}
__finally
{
if (br)
br->Close();
if (fs)
fs->Close();
}
}
/// Save Fixture Calibration Data Set
void SaveCalDataSet(SaveFileDialog* outfile, CalDataSet* Cal)
{
FileStream* fs;
BinaryWriter* bw;
try
{
// Create a filestream & binary writer
fs = new FileStream(outfile->FileName, FileMode::Create, FileAccess::Write);
bw = new BinaryWriter(fs);
// Define header to match file identifying type and version
String* recognized = new String(S"VNA Calibration Data Set Version 1.0.0");
bw->Write(recognized); // put string header on outfile
for (int i=0; i<1024; i++) // write out the data set
{
bw->Write(Cal->EdReal[i]);
bw->Write(Cal->EdImag[i]);
bw->Write(Cal->EsReal[i]);
bw->Write(Cal->EsImag[i]);
bw->Write(Cal->EtReal[i]);
bw->Write(Cal->EtImag[i]);
bw->Write(Cal->ThReal[i]);
bw->Write(Cal->ThImag[i]);
// debug - also write out the measurements
bw->Write(Cal->S11openReal[i]);
bw->Write(Cal->S11openImag[i]);
bw->Write(Cal->S11shortReal[i]);
bw->Write(Cal->S11shortImag[i]);
bw->Write(Cal->S11termReal[i]);
bw->Write(Cal->S11termImag[i]);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -