📄 winpskview.cpp
字号:
// WinPSKView.cpp : implementation of the CWinPSKView class
//
//////////////////////////////////////////////////////////////////////
//
#include "stdafx.h"
#include "WinPSK.h"
#include "Macrodlg.h"
#include "WinPSKDoc.h"
#include "WinPSKView.h"
#include "MainFrm.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define FFT_SAMPLERATE 8000
#define FFT_SIZE 2048
#define SOUNCARD_NUM -1
#define SEARCH_RANGE 45
#define DLLSTAT_OFF -1 //DLL status/error codes
#define DLLSTAT_RX 0
#define DLLSTAT_TX 1
#define DLLSTAT_CPUSLOW 2
#define DLLSTAT_TXFINISHING 3
#define ID_TIMER 1
#define SATMODE (1<<7)
/////////////////////////////////////////////////////////////////////////////
// CWinPSKView
IMPLEMENT_DYNCREATE(CWinPSKView, CFormView)
BEGIN_MESSAGE_MAP(CWinPSKView, CFormView)
//{{AFX_MSG_MAP(CWinPSKView)
ON_WM_DESTROY()
ON_NOTIFY(TCN_SELCHANGE, IDC_DISPLAYTAB, OnSelchangeDisplaytab)
ON_WM_LBUTTONDOWN()
ON_WM_MOUSEMOVE()
ON_NOTIFY(UDN_DELTAPOS, IDC_ZOOM, OnDeltaposZoom)
ON_NOTIFY(UDN_DELTAPOS, IDC_RXFREQSPIN, OnDeltaposRxFreqspin)
ON_WM_LBUTTONDBLCLK()
ON_BN_CLICKED(IDC_SLOWAVE, OnSlowave)
ON_BN_CLICKED(IDC_AFC, OnAfc)
ON_BN_CLICKED(IDC_TRBUTTON, OnTrbutton)
ON_BN_CLICKED(IDC_BPSK, OnBpsk)
ON_BN_CLICKED(IDC_QPSK, OnQpsk)
ON_WM_TIMER()
ON_BN_CLICKED(IDC_NET, OnNet)
ON_COMMAND(ID_EDIT_PASTE, OnEditPaste)
ON_COMMAND(ID_EDIT_COPY, OnEditCopy)
ON_COMMAND(ID_EDIT_CUT, OnEditCut)
ON_COMMAND(ID_EDIT_UNDO, OnEditUndo)
ON_UPDATE_COMMAND_UI(ID_EDIT_COPY, OnUpdateEditCopy)
ON_UPDATE_COMMAND_UI(ID_EDIT_CUT, OnUpdateEditCut)
ON_UPDATE_COMMAND_UI(ID_EDIT_PASTE, OnUpdateEditPaste)
ON_UPDATE_COMMAND_UI(ID_EDIT_UNDO, OnUpdateEditUndo)
ON_COMMAND(ID_EDIT_CLEAR, OnEditClear)
ON_UPDATE_COMMAND_UI(ID_EDIT_CLEAR, OnUpdateEditClear)
ON_WM_CONTEXTMENU()
ON_EN_KILLFOCUS(IDC_RXFREQ, OnKillfocusRxfreq)
ON_EN_SETFOCUS(IDC_RXFREQ, OnSetfocusRxfreq)
ON_EN_KILLFOCUS(IDC_TXFREQ, OnKillfocusTxfreq)
ON_NOTIFY(UDN_DELTAPOS, IDC_TXFREQSPIN, OnDeltaposTxfreqspin)
ON_EN_SETFOCUS(IDC_TXFREQ, OnSetfocusTxfreq)
ON_BN_CLICKED(IDC_M1BUTTON, OnM1button)
ON_BN_CLICKED(IDC_M2BUTTON, OnM2button)
ON_BN_CLICKED(IDC_M3BUTTON, OnM3button)
ON_BN_CLICKED(IDC_M4BUTTON, OnM4button)
ON_BN_CLICKED(IDC_M5BUTTON, OnM5button)
ON_BN_CLICKED(IDC_M6BUTTON, OnM6button)
ON_BN_CLICKED(IDC_M7BUTTON, OnM7button)
ON_BN_CLICKED(IDC_M8BUTTON, OnM8button)
ON_BN_CLICKED(IDC_M9BUTTON, OnM9button)
ON_BN_CLICKED(IDC_M10BUTTON, OnM10button)
ON_BN_CLICKED(IDC_AUTOTXTSEL, OnAutotxtsel)
ON_BN_CLICKED(IDC_CLRQSO, OnClrqso)
ON_BN_CLICKED(IDC_DECFNSET, OnDecfnset)
ON_BN_CLICKED(IDC_INCFNSET, OnIncfnset)
ON_BN_CLICKED(IDC_SETHOME, OnSethome)
ON_WM_RBUTTONDOWN()
ON_BN_CLICKED(IDC_RUN, OnRun)
ON_BN_CLICKED(IDC_TXFMODE, OnTxFreqMode)
ON_BN_CLICKED(IDC_PSK3163, OnPsk3163)
//}}AFX_MSG_MAP
ON_NOTIFY_EX( TTN_NEEDTEXT, 0, OnToolTipNotify )
ON_MESSAGE( MSG_DATARDY, OnDataRdy)
ON_MESSAGE( MSG_PSKCHARRDY, OnCharRdy)
ON_MESSAGE( MSG_STATUSCHANGE, OnStatusChange)
ON_MESSAGE( MSG_IMDRDY, OnIMDRdy)
ON_MESSAGE( MSG_CLKERROR, OnClkError)
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CWinPSKView construction/destruction
/////////////////////////////////////////////////////////////////////////////
CWinPSKView::CWinPSKView()
: CFormView(CWinPSKView::IDD)
{
//{{AFX_DATA_INIT(CWinPSKView)
m_fSlowAve = FALSE;
m_UseAFC = FALSE;
m_TXNet = FALSE;
m_AutoTxtSel = TRUE;
m_RxFreq = 1000;
m_TxDisp = 1000;
m_PSKMode = 0;
m_XMaxCStr = _T("");
m_XMinCStr = _T("");
m_ZoomTxt = _T("");
m_PSK63 = FALSE;
//}}AFX_DATA_INIT
m_pCPlotData = NULL;
m_fRxFreqEditing = FALSE;
m_fTxFreqEditing = FALSE;
m_pSquelchCtrl = NULL;
m_SearchRange = SEARCH_RANGE;
m_IMDDispDelay = 0;
m_ProgramState = STATE_RX;
m_ScreenInitialized = FALSE;
m_DLLRunning = FALSE;
m_NewChannel = 0;
}
CWinPSKView::~CWinPSKView()
{
}
/////////////////////////////////////////////////////////////////////////////
void CWinPSKView::DoDataExchange(CDataExchange* pDX)
{
CFormView::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CWinPSKView)
DDX_Control(pDX, IDC_TXFMODE, m_TxFreqModeCtrl);
DDX_Control(pDX, IDC_RUN, m_RunCtrl);
DDX_Control(pDX, IDC_DEBUGTXT2, m_DebugCtrl2);
DDX_Control(pDX, IDC_DEBUGTXT1, m_DebugCtrl1);
DDX_Check(pDX, IDC_SLOWAVE, m_fSlowAve);
DDX_Check(pDX, IDC_AFC, m_UseAFC);
DDX_Check(pDX, IDC_NET, m_TXNet);
DDX_Check(pDX, IDC_AUTOTXTSEL, m_AutoTxtSel);
DDX_Text(pDX, IDC_RXFREQ, m_RxFreq);
DDX_Text(pDX, IDC_TXFREQ, m_TxDisp);
DDX_Radio(pDX, IDC_BPSK, m_PSKMode);
DDX_Control(pDX, IDC_XMAXTXT, m_XMaxCntrl);
DDX_Control(pDX, IDC_MACROSETTXT, m_MacroSetTxtCtrl);
DDX_Control(pDX, IDC_QPSK, m_QPSKCtrl);
DDX_Control(pDX, IDC_TRBUTTON, m_TRCntrl);
DDX_Control(pDX, IDC_XMINTXT, m_XMinCntrl);
DDX_Control(pDX, IDC_DISPLAYTAB, m_DispTabCtrl);
DDX_Text(pDX, IDC_XMAXTXT, m_XMaxCStr);
DDX_Text(pDX, IDC_XMINTXT, m_XMinCStr);
DDX_Text(pDX, IDC_ZOOMTXT, m_ZoomTxt);
DDX_Check(pDX, IDC_PSK3163, m_PSK63);
//}}AFX_DATA_MAP
DDX_Control(pDX, IDC_M1BUTTON, m_MTitleCtrl[0]); //F1 to F10 keys
DDX_Control(pDX, IDC_M2BUTTON, m_MTitleCtrl[1]);
DDX_Control(pDX, IDC_M3BUTTON, m_MTitleCtrl[2]);
DDX_Control(pDX, IDC_M4BUTTON, m_MTitleCtrl[3]);
DDX_Control(pDX, IDC_M5BUTTON, m_MTitleCtrl[4]);
DDX_Control(pDX, IDC_M6BUTTON, m_MTitleCtrl[5]);
DDX_Control(pDX, IDC_M7BUTTON, m_MTitleCtrl[6]);
DDX_Control(pDX, IDC_M8BUTTON, m_MTitleCtrl[7]);
DDX_Control(pDX, IDC_M9BUTTON, m_MTitleCtrl[8]);
DDX_Control(pDX, IDC_M10BUTTON, m_MTitleCtrl[9]);
}
BOOL CWinPSKView::PreCreateWindow(CREATESTRUCT& cs)
{
return CFormView::PreCreateWindow(cs);
}
/////////////////////////////////////////////////////////////////////////////
// Called to initialize the main FormView object.
/////////////////////////////////////////////////////////////////////////////
void CWinPSKView::OnInitialUpdate()
{
CSize size;
CFormView::OnInitialUpdate();
EnableToolTips(TRUE);
// save off original mouse cursor
m_hOrigCursor = (HCURSOR)::GetClassLong(GetSafeHwnd(),GCL_HCURSOR);
// get the system cross cursor for use when mouse goes over the plot
m_hCross = AfxGetApp()->LoadStandardCursor(IDC_CROSS);
m_TRCntrl.SetIcon(AfxGetApp()->LoadIcon(IDI_TRRCV));
CWinPSKDoc* pDoc = (CWinPSKDoc*) GetDocument();
ASSERT_VALID( pDoc);
if (pDoc != NULL)
{
// See if need to Keep program "ON Top" of all others.
CMainFrame* pFrm=(CMainFrame*)AfxGetMainWnd();
pFrm->StayOnTop();
// create "theircall" edit box
CRect cr;
CWnd* pWnd = GetDlgItem( IDC_THEIRCALL );
ASSERT_VALID(pWnd);
pWnd->GetWindowRect( cr );
ScreenToClient( cr);
if(!pDoc->m_pTheirCallEdit)
{
pDoc->m_pTheirCallEdit = new CTheirCallCtrl;
pDoc->m_pTheirCallEdit->Create( WS_VISIBLE | WS_BORDER | WS_CHILD |
WS_GROUP , cr, this, IDC_RICHEDIT3);
}
// create "theirname" edit box
pWnd = GetDlgItem( IDC_THEIRNAME );
ASSERT_VALID(pWnd);
pWnd->GetWindowRect( cr );
ScreenToClient( cr);
if(!pDoc->m_pTheirNameEdit)
{
pDoc->m_pTheirNameEdit = new CTheirNameCtrl;
pDoc->m_pTheirNameEdit->Create( WS_VISIBLE | WS_BORDER | WS_CHILD |
WS_GROUP , cr, this, IDC_RICHEDIT4);
}
// create "TextGrab" edit box
pWnd = GetDlgItem( IDC_TEXTGRAB );
ASSERT_VALID(pWnd);
pWnd->GetWindowRect( cr );
ScreenToClient( cr);
if(!pDoc->m_pTextGrabEdit)
{
pDoc->m_pTextGrabEdit = new CTextGrabCtrl;
pDoc->m_pTextGrabEdit->Create( WS_VISIBLE | WS_BORDER | WS_CHILD |
WS_GROUP | ES_AUTOHSCROLL, cr, this, IDC_RICHEDIT5);
}
//instantiate display data plotting and processing objects
if(!m_pCPlotData)
{
m_pCPlotData = new CPlotData(); //initialize Data plotting resources
ASSERT(m_pCPlotData);
}
//
pDoc->m_pWinPSKView = this; //store this view ptr in Document class
pWnd = GetDlgItem( IDC_PLOTAREA );
ASSERT_VALID(pWnd); //give ciew client area to Plot object
pWnd->GetClientRect( cr );
m_PlotWidth = cr.right;
m_pCPlotData->SetPlotSize(cr);
CString str;
str = _T("WinPsk 2.13 -- ") + pDoc->m_pSettings->m_sMyCall;
AfxGetMainWnd()->SetWindowText( str );
if(!m_pSquelchCtrl)
{
m_pSquelchCtrl = new CSquelchCtrl();
ASSERT_VALID(m_pSquelchCtrl);
}
CRect r;
GetDlgItem(IDC_SQUELCH)->GetWindowRect(r);
ScreenToClient(r);
BOOL res = m_pSquelchCtrl->Create( "",WS_VISIBLE|WS_CHILD|WS_DLGFRAME,
r, this, IDC_SQUELCH, (PCALLBACKFUNCT)SquelchThreshCallback);
m_pSquelchCtrl->SetThreshold( pDoc->m_pSettings->m_SQThreshold);
fnSetSquelchThreshold(pDoc->m_pSettings->m_SQThreshold,
pDoc->m_pSettings->m_SquelchSpeed, RX_CHAN);
m_pSquelchCtrl->SetLevel(0);
// Initialize controls to values in "pDoc->m_Settings"
if( pDoc->m_pSettings->m_TxOffsetMode)
{
m_TxDisp = pDoc->m_pSettings->m_TxFreqOffset;
m_TxFreqModeCtrl.SetWindowText( _T("TxOffset") );
}
else
{
m_TxDisp = pDoc->m_pSettings->m_TxFreq;
m_TxFreqModeCtrl.SetWindowText( _T("Tx Freq") );
}
m_PSKMode = pDoc->m_pSettings->m_ModType;
m_PSK63 = pDoc->m_pSettings->m_PSK63Mode;
if(pDoc->m_pSettings->m_UseLSB)
m_QPSKCtrl.SetWindowText(_T("QPSK (lsb)"));
else
m_QPSKCtrl.SetWindowText(_T("QPSK (usb)"));
m_UseAFC = pDoc->m_pSettings->m_UseAFC;
m_TXNet = pDoc->m_pSettings->m_TXNet;
m_fSlowAve = pDoc->m_pSettings->m_fSlowAve;
m_AutoTxtSel = pDoc->m_pSettings->m_AutoTxtSel;
pDoc->m_pSettings->m_MacroSet--;
OnIncfnset();
if( (pDoc->m_pSettings->m_TabSel == FFT_DISPVIEW ) ||
(pDoc->m_pSettings->m_TabSel == WATERFALL_DISPVIEW ) )
{
m_ZoomOK = TRUE;
m_pCPlotData->SetPlotCursorIndex( pDoc->m_pSettings->
m_PlotViewState[pDoc->m_pSettings->m_TabSel].xcur );
m_pCPlotData->SetZoom( pDoc->m_pSettings->
m_PlotViewState[pDoc->m_pSettings->m_TabSel].zoom,TRUE,
pDoc->m_pSettings->m_FreqMin,
pDoc->m_pSettings->m_FreqMax );
}
else
{
m_ZoomOK = FALSE;
m_pCPlotData->SetZoom( 1, FALSE,
pDoc->m_pSettings->m_FreqMin,
pDoc->m_pSettings->m_FreqMax );
}
UpdatePlotInfo(PLOT_CHNG_ZOOM);
UpdatePlotInfo(PLOT_CHNG_FREQ);
// Add plot display TAB control initialization here
TC_ITEM tci;
tci.mask = TCIF_TEXT;
str = _T("Spectrum");
tci.pszText = (LPSTR)(LPCTSTR)str;
tci.cchTextMax = str.GetLength();
m_DispTabCtrl.InsertItem(FFT_DISPVIEW, &tci);
str = _T("Waterfall");
tci.pszText = (LPSTR)(LPCTSTR)str;
tci.cchTextMax = str.GetLength();
m_DispTabCtrl.InsertItem(WATERFALL_DISPVIEW, &tci);
str = _T("Input");
tci.pszText = (LPSTR)(LPCTSTR)str;
tci.cchTextMax = str.GetLength();
m_DispTabCtrl.InsertItem(INPUT_DISPVIEW, &tci);
str = _T("Data Sync");
tci.pszText = (LPSTR)(LPCTSTR)str;
tci.cchTextMax = str.GetLength();
m_DispTabCtrl.InsertItem(SYNC_DISPVIEW, &tci);
m_DispTabCtrl.SetCurSel(pDoc->m_pSettings->m_TabSel);
m_TimerID = SetTimer( ID_TIMER, 500, NULL); //start up status timer
if( m_TimerID == 0)
AfxMessageBox( _T("Can't Start Status Timer"),MB_OK );
//
INT tmp = 0;
if(pDoc->m_pSettings->m_PSK63Mode)
tmp |= PSK63MODE;
if( pDoc->m_pSettings->m_ModType == BPSK_MODE )
{
fnSetRXPSKMode( BPSK_MODE|tmp, RX_CHAN);
}
else
{
if(pDoc->m_pSettings->m_UseLSB)
fnSetRXPSKMode( IQPSK_MODE|tmp, RX_CHAN);
else
fnSetRXPSKMode( QPSK_MODE|tmp, RX_CHAN);
}
if(pDoc->m_pSettings->m_UseAFC)
{
fnSetAFCLimit(pDoc->m_pSettings->m_AFCLimit, RX_CHAN);
m_SearchRange = SEARCH_RANGE;
}
else
{
fnSetAFCLimit( 0, RX_CHAN);
m_SearchRange = 0;
}
fnSetClockErrorAdjustment(pDoc->m_pSettings->m_ClockAdj);
fnSetCWIDString((PCHAR)(LPCTSTR)pDoc->m_CWIdString );
if(pDoc->m_pSettings->m_PTTPort)
fnSetComPort(pDoc->m_pSettings->m_PTTPort, 3);
else
fnSetComPort(0, 0);
if(pDoc->m_pSettings->m_TxOffsetMode)
fnSetTXFrequency( pDoc->m_pSettings->m_TxFreq +
pDoc->m_pSettings->m_TxFreqOffset );
else
fnSetTXFrequency( pDoc->m_pSettings->m_TxFreq );
fnSetRXFrequency( pDoc->m_pSettings->m_RxFreq , 0, RX_CHAN);
m_RunCtrl.SetIcon(AfxGetApp()->LoadIcon(IDI_START));
m_TRCntrl.EnableWindow(FALSE);
pDoc->m_FilePercentDone = -1;
if( (pDoc->m_pSettings->m_IOMode&(IOM_WAVEIN|IOM_WAVELOG|IOM_WAVETX) )
== 0 )
{
StartDLL(pDoc); //autostart if no wave files are involved
}
}
m_ScreenInitialized = FALSE;
}
void CWinPSKView::StartDLL(CWinPSKDoc *pDoc)
{
INT err;
LONG length;
INT Mode = pDoc->m_pSettings->m_IOMode;
CHAR errstr[50];
pDoc->m_FilePercentDone = -1;
if(!m_DLLRunning)
{
if( Mode&IOM_WAVEIN)
{
err = fnSetInputWavePath((PCHAR)(LPCTSTR)pDoc->m_pSettings->m_InPathName,
&length,
pDoc->m_pSettings->m_InWaveOffset);
if(err!=0)
{
fnGetErrorString( errstr );
AfxMessageBox( errstr);
return;
}
}
if( Mode&(IOM_WAVELOG|IOM_WAVETX))
{
err = fnSetOutputWavePath((PCHAR)(LPCTSTR)pDoc->m_pSettings->m_OutPathName,
pDoc->m_pSettings->m_OutWaveTimeLimit*60,
pDoc->m_pSettings->m_AppendMode);
if(err!=0)
{
fnGetErrorString( errstr );
AfxMessageBox( errstr);
return;
}
}
err = fnStartSoundCardEx( m_hWnd, pDoc->m_pSettings->m_SoundcardNum, RX_CHAN+1, Mode );
if( err )
{
fnGetErrorString( errstr );
AfxMessageBox( errstr);
if(err==21) //default soundcardnumber if can't open
{
pDoc->m_pSettings->m_SoundcardNum = -1;
err = fnStartSoundCardEx( m_hWnd, pDoc->m_pSettings->m_SoundcardNum, RX_CHAN+1, Mode );
}
if(err)
{
fnStopSoundCard();
m_RunCtrl.SetIcon(AfxGetApp()->LoadIcon(IDI_START));
m_TRCntrl.EnableWindow(FALSE);
m_DLLRunning = FALSE;
return;
// ExitProcess(0);
}
}
fnAbortTX();
pDoc->m_pXmitEdit->ClearAll();
m_DLLRunning = TRUE;
}
m_RunCtrl.SetIcon(AfxGetApp()->LoadIcon(IDI_STOP));
m_TRCntrl.EnableWindow(TRUE);
}
void CWinPSKView::StopDLL()
{
if(m_DLLRunning)
{
fnStopSoundCard();
m_DLLRunning = FALSE;
OnStatusChange(DLL_RX_STATUS, 0);
}
m_RunCtrl.SetIcon(AfxGetApp()->LoadIcon(IDI_START));
m_TRCntrl.EnableWindow(FALSE);
}
/////////////////////////////////////////////////////////////////////////////
// Called to release all the View object resources.
/////////////////////////////////////////////////////////////////////////////
void CWinPSKView::OnDestroy()
{
CWinPSKDoc* pDoc = (CWinPSKDoc*) GetDocument();
KillTimer(m_TimerID);
if(m_pCPlotData)
{
delete m_pCPlotData;
m_pCPlotData = NULL;
}
if (pDoc != NULL)
{
if(pDoc->m_pTheirCallEdit)
{
delete pDoc->m_pTheirCallEdit;
pDoc->m_pTheirCallEdit = NULL;
}
}
if( m_pSquelchCtrl )
{
delete m_pSquelchCtrl;
m_pSquelchCtrl = NULL;
}
CFormView::OnDestroy();
}
/////////////////////////////////////////////////////////////////////////////
// CWinPSKView diagnostics
/////////////////////////////////////////////////////////////////////////////
#ifdef _DEBUG
void CWinPSKView::AssertValid() const
{
CFormView::AssertValid();
}
void CWinPSKView::Dump(CDumpContext& dc) const
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -