diff --git a/commons.h b/commons.h
index 03af550a8..71efe693e 100644
--- a/commons.h
+++ b/commons.h
@@ -62,6 +62,7 @@ extern struct dec_data {
extern struct {
float syellow[NSMAX];
float ref[3457];
+ float filter[3457];
} spectra_;
extern struct {
diff --git a/lib/refspectrum.f90 b/lib/refspectrum.f90
index 73f13acc3..a3b356a7d 100644
--- a/lib/refspectrum.f90
+++ b/lib/refspectrum.f90
@@ -1,4 +1,4 @@
-subroutine refspectrum(id2,brefspec)
+subroutine refspectrum(id2,brefspec,buseref,fname)
! Input:
! id2 i*2 Raw 16-bit integer data, 12000 Hz sample rate
@@ -6,24 +6,41 @@ subroutine refspectrum(id2,brefspec)
parameter (NFFT=6912,NH=NFFT/2)
integer*2 id2(NH)
- logical brefspec,brefspec0
- real x(NFFT)
- real s(0:NH)
- complex cx(0:NH)
- common/spectra/syellow(6827),ref(0:NH)
+ logical*1 brefspec,buseref
+
+ real x0(0:NH-1) !Input samples
+ real x1(0:NH-1) !Output samples (delayed by one block)
+ real x0s(0:NH-1) !Saved upper half of input samples
+ real x1s(0:NH-1) !Saved upper half of output samples
+ real x(0:NFFT-1) !Work array
+ real*4 w(0:NFFT-1) !Window function
+ real*4 s(0:NH) !Average spectrum
+ real*4 fil(0:NH)
+ logical first,firstuse
+ complex cx(0:NH) !Complex frequency-domain work array
+ character*(*) fname
+ common/spectra/syellow(6827),ref(0:NH),filter(0:NH)
equivalence(x,cx)
- data nsave/0/,brefspec0/.false./
-! save brefspec0,nsave,ref
+ data first/.true./,firstuse/.true./
save
+ if(first) then
+ pi=4.0*atan(1.0)
+ do i=0,NFFT-1
+ ww=sin(i*pi/NFFT)
+ w(i)=ww*ww/NFFT
+ enddo
+ nsave=0
+ s=0.0
+ filter=1.0
+ x0s=0.
+ x1s=0.
+ first=.false.
+ endif
+
if(brefspec) then
- if(.not.brefspec0) then
- nsave=0
- s=0.
- endif
-
- x(1:NH)=0.001*id2
- x(NH+1:)=0.0
+ x(0:NH-1)=0.001*id2
+ x(NH:NFFT-1)=0.0
call four2a(x,NFFT,1,-1,0) !r2c FFT
do i=1,NH
@@ -31,27 +48,80 @@ subroutine refspectrum(id2,brefspec)
enddo
nsave=nsave+1
- if(mod(nsave,34).eq.0) then !About 9.8 sec
+ fac0=0.9
+ if(mod(nsave,4).eq.0) then
df=12000.0/NFFT
- ia=nint(500.0/df)
- ib=nint(2500.0/df)
- call pctile(s(ia),ib-ia+1,50,xmed)
- db0=db(xmed)
-! nhadd=10
- open(16,file='refspec.dat',status='unknown')
+ ia=nint(1000.0/df)
+ ib=nint(2000.0/df)
+ avemid=sum(s(ia:ib))/(ib-ia+1)
+ do i=0,NH
+ fil(i)=0.
+ filter(i)=-60.0
+ if(s(i).gt.0.0) then
+ fil(i)=sqrt(avemid/s(i))
+ endif
+ enddo
+
+ ia=nint(240.0/df)
+ fac=fac0
+ do i=ia,1,-1
+ fac=fac*fac0
+ fil(i)=fac*fil(i)
+ enddo
+
+ ib=nint(4000.0/df)
+ fac=fac0
+ do i=ib,NH
+ fac=fac*fac0
+ fil(i)=fac*fil(i)
+ enddo
+
+ do iter=1,1000 !### ??? ###
+ call smo121(fil,NH)
+ enddo
+
+ do i=0,NH
+ filter(i)=-60.0
+ if(s(i).gt.0.0) filter(i)=20.0*log10(fil(i))
+ enddo
+
+! open(16,file='refspec.dat',status='unknown')
+ open(16,file=fname,status='unknown')
do i=1,NH
freq=i*df
-! ia=max(1,i-nhadd)
-! ib=min(NH,i+nhadd)
-! smo=sum(s(ia:ib))/(ib-ia+1)
- ref(i)=db(s(i)) - db0
- write(16,1000) freq,s(i),ref(i)
-1000 format(f10.3,e12.3,f12.6)
+ ref(i)=db(s(i)/avemid)
+ write(16,1000) freq,s(i),ref(i),fil(i),filter(i)
+1000 format(f10.3,e12.3,f12.6,e12.3,f12.6)
enddo
close(16)
endif
+ return
endif
- brefspec0=brefspec
+
+ if(buseref) then
+ if(firstuse) then
+! open(16,file='refspec.dat',status='unknown')
+ fil=1.0
+ open(16,file=fname,status='old',err=10)
+ do i=1,NH
+ read(16,1000,err=10,end=10) freq,s(i),ref(i),fil(i),filter(i)
+ enddo
+10 close(16)
+ firstuse=.false.
+ endif
+ x0=id2
+ x(0:NH-1)=x0s !Previous 2nd half to new 1st half
+ x(NH:NFFT-1)=x0 !New 2nd half
+ x0s=x0 !Save the new 2nd half
+ x=w*x !Apply window
+ call four2a(x,NFFT,1,-1,0) !r2c FFT (to frequency domain)
+ cx=fil*cx
+ call four2a(cx,NFFT,1,1,-1) !c2r FFT (back to time domain)
+ x1=x1s + x(0:NH-1) !Add previous segment's 2nd half
+ id2=nint(x1)
+ x1s=x(NH:NFFT-1) !Save the new 2nd half
+ endif
+
return
end subroutine refspectrum
diff --git a/lib/symspec.f90 b/lib/symspec.f90
index d7f015953..ba5cc28af 100644
--- a/lib/symspec.f90
+++ b/lib/symspec.f90
@@ -30,7 +30,7 @@ subroutine symspec(shared_data,k,ntrperiod,nsps,ingain,nminw,pxdb,s, &
complex cx(0:MAXFFT3/2)
integer nch(7)
- common/spectra/syellow(NSMAX),ref(0:3456)
+ common/spectra/syellow(NSMAX),ref(0:3456),filter(0:3456)
data rms/999.0/,k0/99999999/,nfft3z/0/
data nch/1,2,4,9,18,36,72/
equivalence (xc,cx)
diff --git a/mainwindow.cpp b/mainwindow.cpp
index 89451cd68..2aaf1a997 100644
--- a/mainwindow.cpp
+++ b/mainwindow.cpp
@@ -99,7 +99,8 @@ extern "C" {
void hash_calls_(char calls[], int* ih9, int len);
void degrade_snr_(short d2[], int* n, float* db, float* bandwidth);
void wav12_(short d2[], short d1[], int* nbytes, short* nbitsam2);
- void refspectrum_(short int d2[], bool* brefspec);
+ void refspectrum_(short int d2[], bool* brefspec, bool* buseref,
+ const char* c_fname, int len);
}
int volatile itone[NUM_ISCAT_SYMBOLS]; //Audio tones for all Tx symbols
@@ -874,7 +875,12 @@ void MainWindow::dataSink(qint64 frames)
static float df3;
int k (frames);
- if(m_bRefSpec) refspectrum_(&dec_data.d2[k-3456],&m_bRefSpec);
+ QString fname {QDir::toNativeSeparators(m_dataDir.absoluteFilePath ("refspec.dat"))};
+ QByteArray bafname = fname.toLatin1();
+ const char *c_fname = bafname.data();
+ int len=fname.length();
+ m_bUseRef=m_wideGraph->useRef();
+ refspectrum_(&dec_data.d2[k-3456],&m_bRefSpec,&m_bUseRef,c_fname,len);
if(m_diskData) {
dec_data.params.ndiskdat=1;
@@ -4043,7 +4049,7 @@ void MainWindow::band_changed (Frequency f)
if (f + m_wideGraph->nStartFreq () > m_freqNominal + ui->TxFreqSpinBox->value ()
|| f + m_wideGraph->nStartFreq () + m_wideGraph->fSpan () <=
m_freqNominal + ui->TxFreqSpinBox->value ()) {
- qDebug () << "start f:" << m_wideGraph->nStartFreq () << "span:" << m_wideGraph->fSpan () << "DF:" << ui->TxFreqSpinBox->value ();
+// qDebug () << "start f:" << m_wideGraph->nStartFreq () << "span:" << m_wideGraph->fSpan () << "DF:" << ui->TxFreqSpinBox->value ();
// disable auto Tx if "blind" QSY outside of waterfall
ui->stopTxButton->click (); // halt any transmission
auto_tx_mode (false); // disable auto Tx
@@ -5344,6 +5350,7 @@ void MainWindow::fastPick(int x0, int x1, int y)
void MainWindow::on_actionSave_reference_spectrum_triggered()
{
+ if(!m_monitoring) on_monitorButton_clicked (true);
m_bRefSpec=true;
}
diff --git a/mainwindow.h b/mainwindow.h
index c92e14f30..626436587 100644
--- a/mainwindow.h
+++ b/mainwindow.h
@@ -426,6 +426,7 @@ private:
bool m_bFastDecodeCalled;
bool m_bDoubleClickAfterCQnnn;
bool m_bRefSpec;
+ bool m_bUseRef;
float m_pctZap;
char m_msg[100][80];
diff --git a/plotter.cpp b/plotter.cpp
index 7518aee00..282c8cd37 100644
--- a/plotter.cpp
+++ b/plotter.cpp
@@ -176,7 +176,9 @@ void CPlotter::draw(float swide[], bool bScroll) //dr
if(m_bReference) { //Reference (red)
float df_ref=12000.0/6912.0;
int j=FreqfromX(i)/df_ref + 0.5;
- y2=gain2d*spectra_.ref[j] + m_plot2dZero;
+ y2=spectra_.ref[j] + m_plot2dZero;
+ if(gain2d>1.5) y2=spectra_.filter[j] + m_plot2dZero;
+
}
if(i==iz-1) painter2D.drawPolyline(LineBuf,j);
diff --git a/widegraph.cpp b/widegraph.cpp
index 43a5c536d..546804239 100644
--- a/widegraph.cpp
+++ b/widegraph.cpp
@@ -51,6 +51,8 @@ WideGraph::WideGraph(QSettings * settings, QWidget *parent) :
m_bFlatten=m_settings->value("Flatten",true).toBool();
ui->cbFlatten->setChecked(m_bFlatten);
ui->widePlot->setFlatten(m_bFlatten);
+ m_bRef=m_settings->value("UseRef",false).toBool();
+ ui->cbRef->setChecked(m_bRef);
ui->widePlot->setBreadth(m_settings->value("PlotWidth",1000).toInt());
ui->bppSpinBox->setValue(n);
m_nsmo=m_settings->value("SmoothYellow",1).toInt();
@@ -130,6 +132,7 @@ void WideGraph::saveSettings() //saveS
m_settings->setValue ("UserPalette", QVariant::fromValue (m_userPalette.colours ()));
m_settings->setValue ("Fmin", m_fMin);
m_settings->setValue("Flatten",m_bFlatten);
+ m_settings->setValue("UseRef",m_bRef);
m_settings->endGroup ();
}
@@ -377,9 +380,22 @@ void WideGraph::on_paletteComboBox_activated (QString const& palette) //palet
void WideGraph::on_cbFlatten_toggled(bool b) //Flatten On/Off
{
m_bFlatten=b;
+ if(m_bRef and m_bFlatten) {
+ m_bRef=false;
+ ui->cbRef->setChecked(false);
+ }
ui->widePlot->setFlatten(m_bFlatten);
}
+void WideGraph::on_cbRef_toggled(bool b)
+{
+ m_bRef=b;
+ if(m_bRef and m_bFlatten) {
+ m_bFlatten=false;
+ ui->cbFlatten->setChecked(false);
+ }
+}
+
void WideGraph::on_adjust_palette_push_button_clicked (bool) //Adjust Palette
{
try
@@ -404,6 +420,11 @@ bool WideGraph::flatten() //Flatten
return m_bFlatten;
}
+bool WideGraph::useRef() //Flatten
+{
+ return m_bRef;
+}
+
void WideGraph::on_gainSlider_valueChanged(int value) //Gain
{
ui->widePlot->setPlotGain(value);
diff --git a/widegraph.h b/widegraph.h
index 3cfa6783f..4fdce40ed 100644
--- a/widegraph.h
+++ b/widegraph.h
@@ -40,6 +40,7 @@ public:
void setModeTx(QString modeTx);
void setLockTxFreq(bool b);
bool flatten();
+ bool useRef();
void setTol(int n);
int smoothYellow();
void setRxBand(QString band);
@@ -68,6 +69,7 @@ private slots:
void on_fStartSpinBox_valueChanged(int n);
void on_paletteComboBox_activated(const QString &palette);
void on_cbFlatten_toggled(bool b);
+ void on_cbRef_toggled(bool b);
void on_adjust_palette_push_button_clicked (bool);
void on_gainSlider_valueChanged(int value);
void on_zeroSlider_valueChanged(int value);
@@ -99,6 +101,7 @@ private:
bool m_lockTxFreq;
bool m_bFlatten;
+ bool m_bRef;
bool m_bHaveTransmitted; //Set true at end of a WSPR transmission
QString m_mode;
diff --git a/widegraph.ui b/widegraph.ui
index dd31f7a24..d3433792a 100644
--- a/widegraph.ui
+++ b/widegraph.ui
@@ -562,14 +562,14 @@
-
- Flat
+ Flatten
-
- Ref
+ Ref Spec