📄 lmscopedlg.cpp
字号:
//***************************************************************************
//
// lmscopeDlg.cpp : implementation file
//
//***************************************************************************
#include "stdafx.h"
#define PACKED
#pragma pack(1)
#include "usb_protocol.h"
#pragma pack()
#include "scope_control.h"
#include "lmscope.h"
#include "WaveformDisplay.h"
#include "lmscopeDlg.h"
#include "DisplayOptions.h"
#include "hlp\ctrlhlp.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
//***************************************************************************
//
// Control ID to help topic ID mappings.
//
//***************************************************************************
static DWORD g_pdwHelpIDs[] =
{
IDC_CHANNEL1_FIND, HIDC_CHANNEL1_FIND,
IDC_CHANNEL2_FIND, HIDC_CHANNEL2_FIND,
IDC_CHANNEL1_SCALE, HIDC_CHANNEL1_SCALE,
IDC_CHANNEL2_SCALE, HIDC_CHANNEL2_SCALE,
IDC_CHANNEL1_POS, HIDC_CHANNEL1_POS,
IDC_CHANNEL2_POS, HIDC_CHANNEL2_POS,
IDC_TRIGGER_TYPE, HIDC_TRIGGER_TYPE,
IDC_ENABLE_CH2, HIDC_ENABLE_CH2,
IDC_TRIGGER_CH1, HIDC_TRIGGER_CH1,
IDC_TRIGGER_CH2, HIDC_TRIGGER_CH2,
IDC_START_STOP, HIDC_START_STOP,
IDC_CAPTURE, HIDC_CAPTURE,
IDC_TRIGGER_LEVEL, HIDC_TRIGGER_LEVEL,
IDC_TIMEBASE, HIDC_TIMEBASE,
IDC_TRIGGER_POS, HIDC_TRIGGER_POS,
IDC_WAVEFORM, HIDC_WAVEFORM,
IDOK, HIDOK,
IDC_CH1_MIN, HIDC_CH1_MIN,
IDC_CH1_MAX, HIDC_CH1_MAX,
IDC_CH1_MEAN, HIDC_CH1_MEAN,
IDC_CH2_MIN, HIDC_CH2_MIN,
IDC_CH2_MAX, HIDC_CH2_MAX,
IDC_CH2_MEAN, HIDC_CH2_MEAN,
//
// Ids for which there is no context-sensitive help.
//
IDC_CH1_TEXT1, -1,
IDC_CH1_TEXT2, -1,
IDC_CH2_TEXT1, -1,
IDC_CH2_TEXT2, -1,
IDC_CHANNEL1_POS_TEXT, -1,
IDC_CHANNEL2_POS_TEXT, -1,
IDC_TRIGGER_LEVEL_TEXT, -1,
IDC_STATIC, -1,
0, -1,
0,0
};
//***************************************************************************
//
// A number larger than the largest control ID that we want to show context
// sensitive help for. This helps guard against error message boxes if people
// right click on the application status bar.
//
//***************************************************************************
#define CTRL_ID_MAX 5000
//***************************************************************************
//
// Initialization values for the voltage scale combo boxes.
//
//***************************************************************************
const DWORD g_pdwVoltages[] =
{
100, 200, 500, 1000, 2000, 5000, 10000
};
//***************************************************************************
//
// Initialization values for the timebase combo box.
//
//***************************************************************************
const DWORD g_pdwTimebases[] =
{
2, 5, 10, 25, 50, 100, 250, 500, 1000, 2500, 5000, 10000, 25000, 50000
};
//***************************************************************************
//
// Ping timer parameters. When connected, we ping the device every 2 seconds
// to ensure that the connection is still active.
//
//***************************************************************************
#define PING_TIMER 1
#define PING_FREQUENCY_MS 2000
//***************************************************************************
//
// Macro to round a number to the nearest multiple of another number.
//
//***************************************************************************
#define ROUND(num, mult) ((((num) + ((mult) / 2)) / (mult)) * (mult))
typedef struct
{
int iStringID;
DWORD dwValue;
} tComboEntry;
//***************************************************************************
//
// Initialization values for the trigger type combo box.
//
//***************************************************************************
tComboEntry g_psTriggers[] =
{
{IDS_RISING, SCOPE_TRIGGER_TYPE_RISING},
{IDS_FALLING, SCOPE_TRIGGER_TYPE_FALLING},
{IDS_LEVEL, SCOPE_TRIGGER_TYPE_LEVEL},
{IDS_ALWAYS, SCOPE_TRIGGER_TYPE_ALWAYS}
};
//
// Macro to reverse the sense of a slider value. Windows insists that vertical
// sliders have their minimum value at the top position and this is not well
// suited to our model.
//
#define REVERSE_SLIDER(pos, max, min) ((max) - ((pos) - (min)))
static UINT BASED_CODE indicators[] =
{
ID_INDICATOR_STATUS
};
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialog
{
public:
CAboutDlg();
// Dialog Data
enum { IDD = IDD_ABOUTBOX };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
// Implementation
protected:
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
{
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
END_MESSAGE_MAP()
// ClmscopeDlg dialog
ClmscopeDlg::ClmscopeDlg(CWnd* pParent /*=NULL*/)
: CDialog(ClmscopeDlg::IDD, pParent)
, m_TriggerLevel(_T(""))
, m_Channel2Pos(_T(""))
, m_Channel1Pos(_T(""))
, m_Ch1Min(_T(""))
, m_Ch1Max(_T(""))
, m_Ch1Mean(_T(""))
, m_Ch2Min(_T(""))
, m_Ch2Max(_T(""))
, m_Ch2Mean(_T(""))
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void ClmscopeDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
DDX_Control(pDX, IDC_CHANNEL1_POS, m_cChannel1PosSlider);
DDX_Control(pDX, IDC_CHANNEL2_POS, m_cChannel2PosSlider);
DDX_Control(pDX, IDC_TRIGGER_LEVEL, m_cTriggerLevelSlider);
DDX_Control(pDX, IDC_TRIGGER_POS, m_cTriggerPosSlider);
DDX_Control(pDX, IDC_CHANNEL1_SCALE, m_cChannel1Scale);
DDX_Control(pDX, IDC_CHANNEL2_SCALE, m_cChannel2Scale);
DDX_Control(pDX, IDC_ENABLE_CH2, m_cChannel2Enable);
DDX_Control(pDX, IDC_CHANNEL1_FIND, m_cFindChannel1);
DDX_Control(pDX, IDC_CHANNEL2_FIND, m_cFindChannel2);
DDX_Control(pDX, IDC_TIMEBASE, m_cTimebase);
DDX_Control(pDX, IDC_CAPTURE, m_cOneShot);
DDX_Control(pDX, IDC_CHANNEL1_POS_TEXT, m_cChannel1Pos);
DDX_Control(pDX, IDC_CHANNEL2_POS_TEXT, m_cChannel2Pos);
DDX_Control(pDX, IDC_START_STOP, m_cStopStart);
DDX_Control(pDX, IDC_TRIGGER_TYPE, m_cTriggerType);
DDX_Control(pDX, IDC_CH1_MIN, m_cCh1Min);
DDX_Control(pDX, IDC_CH1_MAX, m_cCh1Max);
DDX_Control(pDX, IDC_CH1_MEAN, m_cCh1Mean);
DDX_Control(pDX, IDC_CH2_MIN, m_cCh2Min);
DDX_Control(pDX, IDC_CH2_MAX, m_cCh2Max);
DDX_Control(pDX, IDC_CH2_MEAN, m_cCh2Mean);
DDX_Control(pDX, IDC_TRIGGER_CH1, m_cTriggerCh1);
DDX_Control(pDX, IDC_TRIGGER_CH2, m_cTriggerCh2);
DDX_Control(pDX, IDC_TRIGGER_LEVEL_TEXT, m_cTriggerLevel);
DDX_Text(pDX, IDC_TRIGGER_LEVEL_TEXT, m_TriggerLevel);
DDX_Text(pDX, IDC_CHANNEL2_POS_TEXT, m_Channel2Pos);
DDX_Text(pDX, IDC_CHANNEL1_POS_TEXT, m_Channel1Pos);
DDX_Text(pDX, IDC_CH1_MIN, m_Ch1Min);
DDX_Text(pDX, IDC_CH1_MAX, m_Ch1Max);
DDX_Text(pDX, IDC_CH1_MEAN, m_Ch1Mean);
DDX_Text(pDX, IDC_CH2_MIN, m_Ch2Min);
DDX_Text(pDX, IDC_CH2_MAX, m_Ch2Max);
DDX_Text(pDX, IDC_CH2_MEAN, m_Ch2Mean);
DDX_Control(pDX, IDC_WAVEFORM, m_cWaveform);
}
BEGIN_MESSAGE_MAP(ClmscopeDlg, CDialog)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_HSCROLL()
ON_WM_VSCROLL()
ON_WM_QUERYDRAGICON()
//}}AFX_MSG_MAP
ON_BN_CLICKED(IDC_START_STOP, &ClmscopeDlg::OnBnClickedStartStop)
ON_BN_CLICKED(IDC_CAPTURE, &ClmscopeDlg::OnBnClickedCapture)
ON_BN_CLICKED(IDC_CHANNEL2_FIND, &ClmscopeDlg::OnBnClickedChannel2Find)
ON_BN_CLICKED(IDC_CHANNEL1_FIND, &ClmscopeDlg::OnBnClickedChannel1Find)
ON_BN_CLICKED(IDC_ENABLE_CH2, &ClmscopeDlg::OnBnClickedEnableCh2)
ON_CBN_SELCHANGE(IDC_CHANNEL1_SCALE, &ClmscopeDlg::OnCbnSelchangeChannel1Scale)
ON_CBN_SELCHANGE(IDC_CHANNEL2_SCALE, &ClmscopeDlg::OnCbnSelchangeChannel2Scale)
ON_CBN_SELCHANGE(IDC_TRIGGER_TYPE, &ClmscopeDlg::OnCbnSelchangeTriggerType)
ON_CBN_SELCHANGE(IDC_TIMEBASE, &ClmscopeDlg::OnCbnSelchangeTimebase)
ON_BN_CLICKED(IDC_TRIGGER_CH1, &ClmscopeDlg::OnBnClickedTriggerCh1)
ON_BN_CLICKED(IDC_TRIGGER_CH2, &ClmscopeDlg::OnBnClickedTriggerCh2)
ON_MESSAGE(WM_SCOPE_NO_DRIVER, &ClmscopeDlg::OnScopeNoDriver)
ON_MESSAGE(WM_SCOPE_DEVICE_AVAILABLE, &ClmscopeDlg::OnScopeDeviceAvailable)
ON_MESSAGE(WM_SCOPE_DEVICE_CONNECTED, &ClmscopeDlg::OnScopeDeviceConnected)
ON_MESSAGE(WM_SCOPE_DEVICE_DISCONNECTED, &ClmscopeDlg::OnScopeDeviceDisconnected)
ON_MESSAGE(WM_SCOPE_DATA, &ClmscopeDlg::OnScopeData)
ON_MESSAGE(WM_SCOPE_PING_RESPONSE, &ClmscopeDlg::OnScopePingResponse)
ON_MESSAGE(WM_SCOPE_STARTED, &ClmscopeDlg::OnScopeStarted)
ON_MESSAGE(WM_SCOPE_STOPPED, &ClmscopeDlg::OnScopeStopped)
ON_MESSAGE(WM_SCOPE_TIMEBASE_CHANGED, &ClmscopeDlg::OnScopeTimebaseChanged)
ON_MESSAGE(WM_SCOPE_TRIGGER_LEVEL_CHANGED, &ClmscopeDlg::OnScopeTriggerLevelChanged)
ON_MESSAGE(WM_SCOPE_TRIGGER_TYPE_CHANGED, &ClmscopeDlg::OnScopeTriggerTypeChanged)
ON_MESSAGE(WM_SCOPE_TRIGGER_POS_CHANGED, &ClmscopeDlg::OnScopeTriggerPosChanged)
ON_MESSAGE(WM_SCOPE_CHANNEL2, &ClmscopeDlg::OnScopeChannel2)
ON_MESSAGE(WM_SCOPE_POS_CHANGED, &ClmscopeDlg::OnScopePositionChanged)
ON_MESSAGE(WM_SCOPE_SCALE_CHANGED, &ClmscopeDlg::OnScopeScaleChanged)
ON_BN_CLICKED(IDOK, &ClmscopeDlg::OnBnClickedOk)
ON_WM_TIMER()
ON_WM_CTLCOLOR()
ON_WM_CONTEXTMENU()
ON_WM_HELPINFO()
END_MESSAGE_MAP()
// ClmscopeDlg message handlers
//***************************************************************************
//
// Called during dialog initialization.
//
//***************************************************************************
BOOL ClmscopeDlg::OnInitDialog()
{
CRect rect;
CDialog::OnInitDialog();
//
// Check that all menu IDs are valid for use in the system menu.
//
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
ASSERT((IDM_SAVEASBMP & 0xFFF0) == IDM_SAVEASBMP);
ASSERT(IDM_SAVEASBMP < 0xF000);
ASSERT((IDM_SAVEASCSV & 0xFFF0) == IDM_SAVEASCSV);
ASSERT(IDM_SAVEASCSV < 0xF000);
ASSERT((IDM_DISPLAYOPTS & 0xFFF0) == IDM_DISPLAYOPTS);
ASSERT(IDM_DISPLAYOPTS < 0xF000);
ASSERT((IDM_SHOWHELP & 0xFFF0) == IDM_SHOWHELP);
ASSERT(IDM_SHOWHELP < 0xF000);
//
// Remember that the "Save As" menu entries are disabled.
//
m_bSaveItemsEnabled = FALSE;
//
// Clear our keep-alive counters.
//
m_iPingResponse = 0;
m_iPingCount = 0;
m_bPingResponseReceived = TRUE;
m_bReconnecting = FALSE;
//
// Add our entries to the system menu.
//
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
CString strEntry;
//
// Add a separator to the bottom of the existing menu.
//
pSysMenu->AppendMenu(MF_SEPARATOR);
//
// Add the "Save as bitmap" menu item.
//
strEntry.LoadString(IDS_SAVEASBMP);
if(!strEntry.IsEmpty())
{
pSysMenu->AppendMenu(MF_STRING, IDM_SAVEASBMP, strEntry);
pSysMenu->EnableMenuItem(IDM_SAVEASBMP, MF_GRAYED);
}
//
// Add the "Save as spreadsheet" menu item.
//
strEntry.LoadString(IDS_SAVEASCSV);
if(!strEntry.IsEmpty())
{
pSysMenu->AppendMenu(MF_STRING, IDM_SAVEASCSV, strEntry);
pSysMenu->EnableMenuItem(IDM_SAVEASCSV, MF_GRAYED);
}
//
// Add the "Display options" menu item.
//
strEntry.LoadString(IDS_DISPLAY_OPTS);
if(!strEntry.IsEmpty())
{
pSysMenu->AppendMenu(MF_STRING, IDM_DISPLAYOPTS, strEntry);
}
//
// Add a separator to the menu.
//
pSysMenu->AppendMenu(MF_SEPARATOR);
//
// Add the "LMScope Help..." menu item.
//
strEntry.LoadString(IDS_SHOWHELP);
if (!strEntry.IsEmpty())
{
pSysMenu->AppendMenu(MF_STRING, IDM_SHOWHELP, strEntry);
}
//
// Add the "About" menu item.
//
strEntry.LoadString(IDS_ABOUTBOX);
if (!strEntry.IsEmpty())
{
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strEntry);
}
}
//
// Initialize the two brushes we use for control background colors.
//
m_cBlackBrush.CreateSolidBrush(SCOPE_COLOR_BACKGROUND);
m_cGreyBrush.CreateSolidBrush(SCOPE_COLOR_DLG_BACKGROUND);
m_cYellowBrush.CreateSolidBrush(SCOPE_COLOR_CHANNEL_1);
m_cVioletBrush.CreateSolidBrush(SCOPE_COLOR_CHANNEL_2);
//
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog.
//
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
//
// Initialize status bar
//
m_csbStatusBar.Create(this); //We create the status bar
m_csbStatusBar.SetIndicators(indicators,1); //Set the number of panes
GetClientRect(&rect);
//
//Size the status bar to the width of the window
//
m_csbStatusBar.SetPaneInfo(0,ID_INDICATOR_STATUS,
SBPS_NORMAL,rect.Width());
//
// Draw the status bar on the screen.
//
RepositionBars(AFX_IDW_CONTROLBAR_FIRST,AFX_IDW_CONTROLBAR_LAST,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -