📄 demo.c
字号:
UCHAR mBCD;
if ( iChar >= '0' && iChar <= '9' ) mBCD = iChar -'0';
else if ( iChar >= 'A' && iChar <= 'F' ) mBCD = iChar - 'A' + 0x0a;
else if ( iChar >= 'a' && iChar <= 'f' ) mBCD = iChar - 'a' + 0x0a;
else mBCD = 0xff;
return( mBCD );
}
// 同步按键显示,键被按下时显示◎,否则显示键号
void mSyncKeyboard(
HWND iDialog, // 主对话框
UINT iKeyCode ) // 输入的按键值,00H-3FH则键被按下,0FFH则按下的键被释放
{
// 以下方法只适用于IDC_K0至IDC_K63完全有序的情况
static UINT mKeyNo=0;
UCHAR mKeyBuffer[8];
if ( iKeyCode == 0xff ) // 释放刚按下的键
{
sprintf( mKeyBuffer, "%0d", mKeyNo ); // 键号字符串
SetDlgItemText( iDialog, IDC_K0 + mKeyNo, mKeyBuffer ); // 恢复显示键号
}
else // 键被按下
{
mKeyNo = iKeyCode & 0x3f ; // 键号0-63
SetDlgItemText( iDialog, IDC_K0 + mKeyNo, "◎" ); // 00H-3FH键被按下则显示◎
}
// 下面是另一种直接方法,代码较多
/*
switch( iKey )
{
case 0x00:
SetDlgItemText( iDialog, IDC_K0, "◎" );
break;
case 0x01:
SetDlgItemText( iDialog, IDC_K1, "◎" );
break;
......
case 0x3f:
SetDlgItemText( iDialog, IDC_K63, "◎" );
break;
case 0xff:
SetDlgItemText( iDialog, ???, "??" );
break;
}
*/
}
// 中断服务程序是由CH375驱动程序中断后通过DLL在应用层模拟调用的
VOID CALLBACK mInterruptEvent( // 中断服务程序
PUCHAR iBuffer ) // 指向一个缓冲区,提供当前的中断特征数据
{
// iBuffer指向一个8个字节的缓冲区,该缓冲区中的内容是由单片机用CMD_WR_USB_DATA5命令写入CH375的数据
// CH375产生中断后,产生一个消息通知主程序
if ( iBuffer[0] == 1 ) // 检查中断特征数据
{
mKeyCode = iBuffer[1] & 0x3f; // 返回的键值,则单片机存放在中断特征数据缓冲区的第2字节
PostMessage( mSaveDialogMain, WM_COMMAND, IDC_INT_PRESS, 0 ); // 中断特征数据1则键被按下
}
else if ( iBuffer[0] == 2 ) PostMessage( mSaveDialogMain, WM_COMMAND, IDC_INT_RELEASE, 0 ); // 中断特征数据2则键被释放
// 如果使用中断特征数据,则根据该数据作相应的处理
/*
switch( iBuffer[0] )
{
case 1: 中断特征数据为1
case 2: 中断特征数据为2
.....
case 6: 中断特征数据为6
}
*/
}
VOID CALLBACK NotifyRoutine ( // 设备事件通知回调程序
ULONG iEventStatus ) // 设备事件和当前状态: 0=设备拔出事件, 3=设备插入事件
{
//在中断程序中对系统资源不能操作太多,所以将插拔事件处理通过PostMessage()放到IDC_INT_DEVARRIVAL中处理
if(iEventStatus==CH375_DEVICE_ARRIVAL)
SendMessage( mSaveDialogMain, WM_COMMAND, IDC_INT_DEVARRIVAL, 0 ); //将设备插入消息发送到窗体进行处理
else if(iEventStatus==CH375_DEVICE_REMOVE)
SendMessage( mSaveDialogMain, WM_COMMAND, IDC_INT_DEVREMOVAL, 0 ); //将设备拔出消息发送到窗体进行处理
return;
}
VOID devarrival() //设备插入处理程序
{
char i;
if(!openflag)
{
if ( CH375OpenDevice( mIndex ) == INVALID_HANDLE_VALUE ) /* 设备插入打开设备 */
{
MessageBox( mSaveDialogMain, "无法打开CH372/CH375设备", mCaptionInform, MB_ICONSTOP | MB_OK );
return;
}
else
openflag=TRUE;
CH375SetTimeout( mIndex, 3000, 3000 ); // 设置USB数据读写的超时,超过3000mS未完成读写将强制返回,避免一直等待下去
Testcommunication();
CH375SetExclusive( mIndex, FALSE ); // 临时设置共享使用当前CH375设备,因为下面设置中断服务程序时需要使用当前这个CH375设备
CH375SetIntRoutine( mIndex, mInterruptEvent ); //设置中断
Sleep( 50 ); // 主程序休息50mS,以等待上一个操作CH375SetIntRoutine创建线程并由该线程再次打开CH375,否则下一个操作CH375SetExclusive将导致创建的线程无法打开CH375
CH375SetExclusive( mIndex, TRUE ); // 设置独占使用当前CH375设备,在此之后其它应用程序不能同时使用当前这个CH375设备,实际是无法再打开CH375设备
}
//设备打开,输入按钮可用,设备没打开,输入按钮禁用
for(i=0;i<8;i++){
Arrivalflag=TRUE; //忽略数据输入对话框
mBufferLength = GetDlgItemText( mSaveDialogMain, IDC_N1+i, mEnterBuffer, 4 ); // 取LED按钮上显示的字符
//软件与EVT数码管显示同步
SendMessage(mSaveDialogMain,WM_COMMAND,IDC_N1+i,0); //发送当前窗体数码管按钮IDC_N1..IDC_N8的显示值
//输入按钮可用
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_N1+i),TRUE);
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_FlashLed1+i),TRUE); //闪烁按钮
}
SendMessage(mSaveDialogMain,WM_COMMAND,IDC_FlashLed1,0); //发送当前窗体数码管闪烁控制状态
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_SetSegLight),TRUE); //设置段位显示按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_SetShowPara),TRUE); //设置显示参数按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_LeftShift),TRUE); //字左移按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_RightShift),TRUE); //字右移按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_CMD1),TRUE); //输入命令码按钮
SetDlgItemText(mSaveDialogMain,IDC_devstatue,"**CH372/CH375设备已插上"); //设备插拔状态显示
}
VOID devremoval() //设备拔出处理程序
{
char i;
if(openflag)
{
CH375CloseDevice( mIndex ); // 退出程序前必须关闭CH375设备
openflag=FALSE;
}
for(i=0;i<8;i++){
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_N1+i),FALSE); //LED
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_FlashLed1+i),FALSE); //闪烁按钮
}
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_SetSegLight),FALSE); //设置段位显示按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_SetShowPara),FALSE); //设置显示参数按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_LeftShift),FALSE); //字左移按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_RightShift),FALSE); //字右移按钮
EnableWindow(GetDlgItem(mSaveDialogMain,IDC_CMD1),FALSE); //输入命令码按钮
SetDlgItemText(mSaveDialogMain,IDC_devstatue,"**CH372/CH375设备已拔出");//设备插拔状态显示
}
VOID Testcommunication()
{
mCOMMAND_PACKET mDemoReq;
UINT mLength;
mDemoReq.mCommandCode = DEF_CMD_TEST_DATA; // 测试命令,将PC机发来的所有数据取反后返回
mDemoReq.mCommandCodeNot = ~ DEF_CMD_TEST_DATA;
mDemoReq.mParameter[0] = 0x5a; // 任意的测试数据,返回后将按位取反
mDemoReq.mParameter[1] = 0x96; // 任意的测试数据,返回后将按位取反
mDemoReq.mParameter[2] = 0xf3; // 任意的测试数据,返回后将按位取反
mDemoReq.mParameter[3] = 0x4c; // 任意的测试数据,返回后将按位取反
mDemoReq.mParameter[4] = 0x39; // 任意的测试数据,返回后将按位取反
mLength = CONST_CMD_LEN; // 命令包的长度
if ( CH375WriteData( mIndex, &mDemoReq, &mLength ) ) // 通过CH375发送命令数据,成功
{
mLength = mCH375_PACKET_LENGTH;
if ( CH375ReadData( mIndex, &mDemoReq, &mLength ) ) // 通过CH375接收应答数据,成功
{
if ( mLength == CONST_CMD_LEN )
{
if ( mDemoReq.mCommandCode != (UCHAR)~ DEF_CMD_TEST_DATA || mDemoReq.mParameter[0] != (UCHAR)~ 0x5a || mDemoReq.mParameter[1] != (UCHAR)~ 0x96 )
MessageBox( mSaveDialogMain, "通过USB传输的数据有错误", mCaptionInform, MB_OK | MB_ICONERROR );
}
else MessageBox( mSaveDialogMain, "CH375数据测试返回的长度错误", mCaptionInform, MB_OK | MB_ICONERROR );
}
else
MessageBox( mSaveDialogMain, "CH375ReadData 失败", mCaptionInform, MB_OK | MB_ICONERROR );
}
else
MessageBox( mSaveDialogMain, "CH375WriteData 失败", mCaptionInform, MB_OK | MB_ICONERROR );
}
UINT mDownloadData( UCHAR *iBuffer, UINT iLength )
{
mCOMMAND_PACKET mDemoReq;
UINT mLength;
if ( iLength > 4096 )
{
MessageBox( mSaveDialogMain, "单次下传数据长度超过4096字节", mCaptionInform, MB_OK | MB_ICONERROR );
return( FALSE );
}
mDemoReq.mCommandCode = DEF_CMD_DOWN_DATA; // 连续下传数据块
mDemoReq.mCommandCodeNot = ~ DEF_CMD_DOWN_DATA;
mDemoReq.mBufferID = ACCESS_MCS51_XRAM; // 读写51单片机的外部RAM(本演示板的单片机没有外部RAM,所以无法演示)
mDemoReq.mBufferAddr = 0x8200; // 指定外部RAM缓冲区起始地址,该例是将数据下传到起始地址为0X8200的外部RAM
mDemoReq.mLength = iLength; // 传输数据总长度
mLength = CONST_CMD_LEN; // 命令包的长度
if ( CH375WriteData( mIndex, &mDemoReq, &mLength ) ) // 通过CH375发送命令包,成功
{
mLength = iLength; // 数据块的长度,一次下传不超过4096字节
if ( ( mLength % 64 ) == CONST_CMD_LEN ) mLength ++; // 防止数据包的长度与命令包的长度相同,如果相同,则多发送一个无效数据
if ( CH375WriteData( mIndex, iBuffer, &mLength ) ) // 通过CH375发送数据,成功
return( mLength );
else MessageBox( mSaveDialogMain, "CH375WriteData 下传数据失败", mCaptionInform, MB_OK | MB_ICONERROR );
}
else MessageBox( mSaveDialogMain, "CH375WriteData 发送命令失败,DEF_CMD_DOWN_DATA", mCaptionInform, MB_OK | MB_ICONERROR );
return( 0 );
}
UINT mUploadData( UCHAR *iBuffer, UINT iLength )
{
mCOMMAND_PACKET mDemoReq;
UINT mLength;
if ( iLength > 4096 )
{
MessageBox( mSaveDialogMain, "单次上传数据长度超过4096字节", mCaptionInform, MB_OK | MB_ICONERROR );
return( FALSE );
}
mDemoReq.mCommandCode = DEF_CMD_CLEAR_UP; // 连续上传数据块之前进行同步,实际是让单片机清除上传缓冲区的已有内容
mDemoReq.mCommandCodeNot = ~ DEF_CMD_CLEAR_UP;
mLength = CONST_CMD_LEN; // 命令包的长度
if ( CH375WriteData( mIndex, &mDemoReq, &mLength ) ) // 通过CH375发送命令包,成功
{
mDemoReq.mCommandCode = DEF_CMD_UP_DATA; // 连续上传数据块
mDemoReq.mCommandCodeNot = ~ DEF_CMD_UP_DATA;
mDemoReq.mBufferID = ACCESS_MCS51_XRAM; // 读写51单片机的外部RAM(本演示板的单片机没有外部RAM,所以无法演示)
mDemoReq.mBufferAddr = 0x8200; // 指定外部RAM缓冲区起始地址,该例是将从起始地址为0X8200的外部RAM上传数据
mDemoReq.mLength = iLength; // 传输数据总长度
mLength = CONST_CMD_LEN; // 命令包的长度
if ( CH375WriteData( mIndex, &mDemoReq, &mLength ) ) // 通过CH375发送命令包,成功
{
mLength = iLength; // 数据块的长度,一次上传不超过4096字节
if ( CH375ReadData( mIndex, iBuffer, &mLength ) ) // 通过CH375接收数据,成功
return( mLength );
else MessageBox( mSaveDialogMain, "CH375ReadData 上传数据失败", mCaptionInform, MB_OK | MB_ICONERROR );
}
else MessageBox( mSaveDialogMain, "CH375WriteData 发送命令失败,DEF_CMD_UP_DATA", mCaptionInform, MB_OK | MB_ICONERROR );
}
else MessageBox( mSaveDialogMain, "CH375WriteData 发送命令失败,DEF_CMD_CLEAR_UP", mCaptionInform, MB_OK | MB_ICONERROR );
return( 0 );
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -