关于vc上位机 的cserialport类的问题(已解决)
本帖最后由 FSL_TICS_ZP 于 2014-7-2 21:57 编辑// practise4Dlg.cpp : implementation file
//
#include "stdafx.h"
#include "practise4.h"
#include "practise4Dlg.h"
//
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialog
{
public:
CAboutDlg();
// Dialog Data
//{{AFX_DATA(CAboutDlg)
enum { IDD = IDD_ABOUTBOX };
//}}AFX_DATA
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CAboutDlg)
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
//}}AFX_VIRTUAL
// Implementation
protected:
//{{AFX_MSG(CAboutDlg)
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
{
//{{AFX_DATA_INIT(CAboutDlg)
//}}AFX_DATA_INIT
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CAboutDlg)
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
//{{AFX_MSG_MAP(CAboutDlg)
// No message handlers
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CPractise4Dlg dialog
CPractise4Dlg::CPractise4Dlg(CWnd* pParent /*=NULL*/)
: CDialog(CPractise4Dlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CPractise4Dlg)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
// Note that LoadIcon does not require a subsequent DestroyIcon in Win32
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void CPractise4Dlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CPractise4Dlg)
DDX_Control(pDX, IDC_COMBO1, m_combo1);
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CPractise4Dlg, CDialog)
//{{AFX_MSG_MAP(CPractise4Dlg)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_BUTTON1, OnButton1)
ON_BN_CLICKED(IDC_BUTTON2, OnButton2)
ON_BN_CLICKED(IDC_BUTTON3, OnButton3)
ON_BN_CLICKED(IDC_BUTTON4, OnButton4)
ON_BN_CLICKED(IDC_exit, Onexit)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CPractise4Dlg message handlers
BOOL CPractise4Dlg::OnInitDialog()
{
CDialog::OnInitDialog();
// Add "About..." menu item to system menu.
// IDM_ABOUTBOX must be in the system command range.
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
CString strAboutMenu;
strAboutMenu.LoadString(IDS_ABOUTBOX);
if (!strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// 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
// TODO: Add extra initialization here
//自己添加代码
m_combo1.SetCurSel(1); //选择第二个串口
GetDlgItem(IDC_BUTTON3)->EnableWindow(m_openflag);
GetDlgItem(IDC_BUTTON4)->EnableWindow(m_openflag);
// port1.InitPort()
return TRUE;// return TRUEunless you set the focus to a control
}
void CPractise4Dlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialog::OnSysCommand(nID, lParam);
}
}
// If you add a minimize button to your dialog, you will need the code below
//to draw the icon.For MFC applications using the document/view model,
//this is automatically done for you by the framework.
void CPractise4Dlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
// Center icon in client rectangle
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}
// The system calls this to obtain the cursor to display while the user drags
//the minimized window.
HCURSOR CPractise4Dlg::OnQueryDragIcon()
{
return (HCURSOR) m_hIcon;
}
void CPractise4Dlg::OnButton1()
{
char buf={'a'};
if(!m_bSerialPortOpened) //检查串口是否打开
{
AfxMessageBox("串口没有打开");
return;
}
// TODO: Add your control notification handler code here
port1.WriteToPort(buf);
}
void CPractise4Dlg::OnButton2()
{
// TODO: Add your control notification handler code here
char buf1={'b'};
if(!m_bSerialPortOpened) //检查串口是否打开
{
AfxMessageBox("串口没有打开");
return;
}
// TODO: Add your control notification handler code here
port1.WriteToPort(buf1);
}
void CPractise4Dlg::OnButton3()
{
// TODO: Add your control notification handler code here
int nPort=m_combo1.GetCurSel()+1; //得到串口号,想想为什么要加1
if(port1.InitPort(this, nPort, 9600,'N',8,1,EV_RXFLAG | EV_RXCHAR,512))
{
port1.StartMonitoring();
m_bSerialPortOpened=TRUE;
m_unPort=nPort;
}
else
{
AfxMessageBox("没有发现此串口或被占用");
m_bSerialPortOpened=FALSE;
}
GetDlgItem(IDC_BUTTON3)->EnableWindow(!m_bSerialPortOpened);
GetDlgItem(IDC_BUTTON4)->EnableWindow(m_bSerialPortOpened);
}
void CPractise4Dlg::OnButton4()
{
// TODO: Add your control notification handler code here
port1.ClosePort();//关闭串口
m_bSerialPortOpened=FALSE;
GetDlgItem(IDC_BUTTON3)->EnableWindow(!m_bSerialPortOpened);
GetDlgItem(IDC_BUTTON4)->EnableWindow(m_bSerialPortOpened);
}
void CPractise4Dlg::Onexit()
{
// TODO: Add your control notification handler code here
CDialog::OnCancel();
}
不能先说问题再贴代码吗? 目前我想实现上位机去控制我的LED灯,我按钮1点亮 按钮2熄灭
现在出现的问题是我打开串口后,然后点亮led是可以的,但是再点熄灭就不行了,
必须关闭串口以后再重新打开串口点按钮2才可以熄灭,请问是我的上位机的问题还是我下位机的问题,还是cserialport这个类的问题,请教各位了! 下位机我是用stm8ss208的单片机,
下位机我贴下我的代码
#include <iostm8s208rb.h>
#include "main.h"
uint buf,m;
_Bool flag_led1,flag_led2;
#define adc_enable() ADC_CR1|=0x01
#define adc_disable() ADC_CR1&=~0x01
voidadc_init(void) //adc初始化
{
adc_disable();
ADC_CSR=0x00;
ADC_CR2=0x18;
ADC_CR1=0x03;
asm("nop"); asm("nop");asm("nop"); asm("nop"); asm("nop"); asm("nop");
adc_enable();
}
unsigned longadc_get(uchar mux) //得到adc转换后的
{
uchardataH, dataL;
uintvalue = 0;
// adc_init();
ADC_CSR|=(mux&0x0f);//选择通道
while(!((ADC_CSR&0x80)==0x80)); //等待转换完成
ADC_CSR&=~0x80; //软件清零
asm("nop"); asm("nop");asm("nop"); asm("nop"); asm("nop"); asm("nop");
dataL = ADC_DRL; //读取寄存器数据
dataH = ADC_DRH; //右对齐数据
value = dataH*256+dataL;
returnvalue;
}
ulongSort_detection(uchar mux) //中值滤波
{
uchar i,j,k;
ulong tmp,adc_buf;
for(i=0;i<5;i++)
{
adc_buf = adc_get(mux);
asm("nop"); asm("nop");asm("nop"); asm("nop"); asm("nop"); asm("nop");
}
for(j=4;j>0;j--) //冒泡排序
{
for(k=0;k<j;k++)
{
if(adc_buf>adc_buf)
{
tmp = adc_buf;
adc_buf = adc_buf;
adc_buf = tmp;
}
}
}
returnadc_buf; //函数返回值为数组中间值
}
void Key_init()
{
PF_DDR_DDR3=0;
PD_DDR_DDR0=0;
PD_DDR_DDR2=0;
PD_DDR_DDR3=0;
PF_CR1_C13=1;
PD_CR1_C10=1;
PD_CR1_C12=1;
PD_CR1_C13=1;
}
void Led_init()
{
PC_DDR_DDR1=1;
PF_DDR_DDR6=1;
PF_DDR_DDR5=1;
PF_DDR_DDR4=1;
PC_CR1_C11=1;
PF_CR1_C16=1;
PF_CR1_C15=1;
PF_CR1_C14=1;
}
void Uart_init()
{
UART1_BRR2 = 0x00; //9600bps @2M
UART1_BRR1 = 0x0D; //9600bps @2M
UART1_CR3 = 0x00;//1位停止位,不开启同步模式
UART1_CR2 = 0x2C;// 使能发送和接收功能,并开启接收中断
UART1_CR1 = 0x00;//8位数据,不使用奇偶效验,并且使能UART1
}
void send_char(char buf)
{
UART1_DR = buf;//发送TxBuffer1数组的字符
while((UART1_SR & 0x80) == 0x00);//查询发送缓冲区的字节是否已经发送出去
}
uchar Get_char()
{
uchar b;
b=UART1_DR;
while((UART1_SR & 0x80) == 0x00);//查询发送缓冲区的字节是否已经发送出去
return b;
}
void send_string(char *buf)
{
while(*buf)
{
send_char(*(buf++));
}
}
void Timer4_init()
{
TIM4_ARR=255;//计数到255后产生溢出
TIM4_PSCR=0x07;//128分频,即2M/128=15.625KHz(相当于计数器周期为64uS)
TIM4_IER=0X01;//禁止中断
TIM4_EGR=0x01;//允许产生更新事件
TIM4_CR1=0X01;//启动定时器
}
void Device_inti()
{
Key_init();
adc_init();
Led_init();
Uart_init();
Timer4_init();
LED1=1;
LED2=1;
LED3=1;
LED4=1;
asm("rim");// 开全局中断
}
void Ad_handle()
{
if(m>=50)
{
m=0;
send_char(buf%10000/1000+48);
send_char(buf%1000/100+48);
send_char(buf%100/10+48);
send_char(buf%10/1+48);
send_char(0x0a);
}
}
void main()
{
Device_inti();
while(1)
{
buf=adc_get(9)*3.22;
// Ad_handle();
if(KEY1==0)
{
if(m>=10)
{
m=0;
send_string("hello STM8");
}
while(KEY1==0);
}
}
}
#pragma vector=20
__interrupt void Uart1_IRQHandler(void)
{
ucharuartbuf;
uartbuf=Get_char();
send_string("iget it \n");
switch(uartbuf)
{
case 'a':
//flag_led1=1;
LED1=0;
break;
case 'b':
// flag_led2=1;
LED1=1;
break;
default :break;
}
return;
}
#pragma vector=25
__interrupt void Timer1_IRQHandler(void)
{
TIM4_SR = 0x00; // 清除更新标志
m++;
return;
}
没有人能帮你编程的,别人只能帮你理一下思路,根本不会有人去看你的那么长的代码! 发送的2个按钮函数,将 char类型改为 static char看看,
因为是异步传输,很可能WriteToPort的时候,数组生命周期已经结束。 wangpengcheng 发表于 2014-6-6 13:50
没有人能帮你编程的,别人只能帮你理一下思路,根本不会有人去看你的那么长的代码! ...
这话说的,我只是不知道问题在哪?
这代码是我昨天就敲完,今天验证的时候出现这个问题了! dhw5qq 发表于 2014-6-6 15:30
这话说的,我只是不知道问题在哪?
这代码是我昨天就敲完,今天验证的时候出现这个问题了! ...
单步调试,设断点,printf等好多种调试方法,先把问题点确认! 68336016 发表于 2014-6-6 14:06
发送的2个按钮函数,将 char类型改为 static char看看,
因为是异步传输,很可能WriteToPort的时候,数组生 ...
查了vc的书,好像一个控件在处理消息以后需要返回,可能是没有返回,导致程序无法响应按钮2 dhw5qq 发表于 2014-6-6 20:05
查了vc的书,好像一个控件在处理消息以后需要返回,可能是没有返回,导致程序无法响应按钮2 ...
别管书上怎么说,有没有按我说的试试,只需要敲 12个字母而已。 试过了,还是不行,我问了我们老师,他说你需要清空缓冲区数据! 在上位机程序中设置一个数组变量,如char m_cSendbuf, 然后每次发送都是先 m_cSendbuf = 'a'或'b',然后WriteToPort(m_cSendbuf,1),试试看。还不行就把按钮消息中只设置m_cSendbuf,然后设一个BOOL值作为标志,将WriteToPort的执行放到一个定时器中,多执行WriteToPort几次,不信还收不到! 这个类我使用很久了,特地又试一次,毫无问题。 68336016 发表于 2014-6-8 02:31
这个类我使用很久了,特地又试一次,毫无问题。
我知道跟这个串口类没有关系,可能我的思路出问题了,我再试试吧!按照楼上的
页:
[1]