你好,欢迎来到电脑编程技巧与维护杂志社! 杂志社简介广告服务读者反馈编程社区  
合订本订阅
 
 
您的位置:杂志经典 / 网络与通信
4.2 测量数据的接收处理及其程序设计
 

一、引言

在高等院校、科研院所等单位的教学、科研活动中,经常需要测量超低频信号的波形和非周期信号的波形,但往往因为价格较低的通用示波器不具有上述功能,而具有这些功能的数字示波器或专用摸拟示波器价格昂贵,致使教学、科研受到了影响。

运用单片机技术和VB6设计的测量系统,不但具有上述功能,而且还能指示波形上任意点的值,还能送大屏幕显示(便于教学演示),尤其经费支出很少(利用单位现有微机和大屏幕,实现一机多用)。基本设计思想为:利用价格低而性能好的单片机(如AT89系列)和具有采样保持器的快速A/D实现数据采集,用VB6通信控件收发数据、用VB6设计用户界面、用VB6处理数据(标度变换、插值后绘制波形、显示波形上鼠标单击处的值等)。本文重点研究测量数据的接收、处理和程序设计。

二、界面设计

用户界面(见下图所示)是在微型计算机屏幕上显示用于控制测量的按钮和输入输出信息,用鼠标进行操作控制。下表为用户界面使用的主要控件的属性和用途。


用户界面

 

主要控件的属性和用途

 控件

 属性

设置值

控件用途

Form1

Caption

 

形成面板,Paint事件建坐标系,Load事件初始化控件属性值

Picture1

Caption

 

Line方法画线,Pset方法画点,Print方法显示信息,MouseDown事件计算单击处的值。

Option1

Caption

Style

暂停

Graphical

便于读取波形上任意点的值

Option2

Caption

Style

测量

Graphical

Click事件绘制波形

Command1

Caption

停止

Click事件停止测量

Combo1

List

Style

0.1,1,10,100

DropDown

从列表中选择横坐标每厘米表示的时间值(ms, Click事件重绘波形。

Combo2

List

Style

0.01,0.1,1,10,100

DropDown

从列表中选择纵坐标每厘米表示的电压值(V, Click事件重绘波形。

Combo3

List

Style

10,100,1000,10000

DropDown

从列表中选择采样的时间间隔(μs), 并通过Click事件向单片机发送采样信息。

MSComm1

 

用代码设置

收发数据

 

三、数据的接收与处理

1.数据的接收

    运用VB6提供的串行通信控件接收数据,其优点是数据的接收与处理互不影响,这一功能可由通信控件的OnComm事件实现。若把通信控件的Rthreshold属性设置为单片机每次发送给PC机的字节数,则只有当串口接收缓冲区接收到规定的字节数时,才发生OnComm事件,对OnComm事件编写代码,就可进行标度变换并存入数组中,以供绘图过程使用。在发生OnComm事件之前,串口接收缓冲区自动逐个接收数据,同时VB6执行其它代码,如对刚接收的一批数据进行插值、绘制波形等。

2.标度变换

被测模拟信号经A/D转换后,变成了相应的二进制码,不同的A/D器件对数字量的编码方法不同,对于双极性输入的A/D(为测量双极性模拟信号,应选用双极性输入的A/D),通常采用的编码方法为:符号-数值双极性码和偏移二进制双极性码。对于单字节的偏移二进制双极性码,00H对应模拟信号的最大值,80H对应模拟信号的0值,FFH对应模拟信号的最小值(负值)。显然,这些数码虽然与模拟信号有一一对应关系,但并不等于模拟值,因此必须把偏移二进制双极性码所代表的模拟量大小表示出来,常称之为标度变换。经研究,偏移二进制双极性码的标度变换公式为

      ­­­­­­­­­­­=1- ­­NB / 2­­­­­­n-1­.V­­­­max

式中,N­­B表示偏移二进制双极性码(对应的十进制值),­­­A表示N­­B代表的模拟值,n为偏移二进制双极性码的位数,­­­max­­A/D的最大输入模拟值。若被测模拟信号经分压后接入A/D,则还需再乘上分压系数。

3.插值与绘制波形

采集的数据个数毕竟有限,为了把这些数据进行标度变换后绘制成波形,必须把变换后的数据进行插值,建立插值函数,再根据插值函数计算出大量数值,用描点法在坐标系中绘制波形。

当用等间隔法采样时,拉格郎日三点插值的插值函数为

u=[0.5(t-t­1)(t-t­2)u­0 -(t-t­0)(t-t­2)u1+0.5(t-t­0)(t-t­1)u2 ]/tm­­­2

式中,u0t=t0时的u值,u1t=t1时的u值,u2t=t2时的u值,tm为采样时间间隔。时间单位为ms,电压单位为v

    当采集数据较多时,采用分组插值法,能较好地反映被测信号的波形。

4.计算波形上鼠标单击处的值

    当把鼠标指针指向波形上某点且按下鼠标键时,鼠标指针当前的坐标值自动保存在xy中,利用xy和坐标原点oldx oldy值及纵横轴每厘米代表的值,就可计算出波形上单击处的值。计算公式为

     u=(oldy-y).Val(Combo2.Text)

     t=(x-oldx).Val(Combo1.Text)

四、程序设计

实现上述功能的核心代码如下:

'声明通用变量

Public oldx As Single, oldy As Single

Private y() As Single

'绘制波形(拉格郎日三点插值,多点时分段)

Private Sub buo()

Dim n As Integer, i As Integer, j As Integer

Dim j1 As Integer, j2 As Integer, t As Single

Dim tm As Single, tm2 As Single

Dim tm3 As Single, u As Single

lp:

If Option2.Value = True Then '按下"测量"时绘制波形

Picture1.AutoRedraw = False  '绘制的波形可被清除

Picture1.Cls                 '清除上次绘制的波形

tm = Val(Combo3.Text) / 1000

tm2 = tm ^ 2                 'tm­­­­­­2tm2

tm3 = tm / 1000

n = UBound(y)                '引用y()数组上界

If n >= 3 Then       '测量数据3个以上时才绘制波形

n = Int((n - 1) / 2) '分组插值组数

For i = 1 To n       '建立n个插值函数绘制波形

j = 2 * (i - 1) + 1

j1 = j + 1: j2 = j + 2

t0 = (j - 1) * tm: t1 = j * tm: t2 = (j + 1) * tm

For t = t0 To t2 Step tm3 '建立第i个插值函数绘波形

u = (t - t1) * (t - t2) * y(j) * 0.5

u = u - (t - t0) * (t - t2) * y(j1)

u = u + (t - t0) * (t - t1) * y(j2) * 0.5

u = u / tm2

Picture1.PSet (t / Val(Combo1.Text) + oldx, _

oldy - u / Val(Combo2.Text)), QBColor(9)

DoEvents         '可响应其它控件发生的事件

Next t

Next i

GoTo lp

Else

Picture1.Print "无测量数据"

Exit Sub

End If

End If

End Sub

Private Sub Combo1_Click()

Call buo     '改变横轴值/div,重绘制波形

End Sub

Private Sub Combo2_Click()

Call buo    '改变纵轴值/div,重绘制波形

End Sub

'向单片机发送采样信息

Private Sub Combo3_Click()

Dim out(0) As Byte, fa As Single

fa = Val(Combo3.Text)

Select Case fa

Case 10          '采样间隔为10微秒时发送1

out(0) = &H1

Case 100        '采样间隔为100微秒时发送2

out(0) = &H2

Case 1000      '采样间隔为1000微秒时发送4

out(0) = &H4

Case 10000    '采样间隔为10000微秒时发送8

out(0) = &H8

End Select

MSComm1.Output = out   '向单片机发送信息

End Sub

Private Sub Command1_Click()

End                '停止测量

End Sub

'初始化

Private Sub Form_Load()

With MSComm1             '串口初始化

.InBufferSize = 1024     '接收缓冲区1024字节

.OutBufferSize = 512     '输出缓冲区512字节

.CommPort = 1            '串口1

.Settings = "9600,n,8,1" '波特率9600,1个停止位,无校验

.Handshaking = comNone   '无协议

.InputLen = 0            '获得接收缓冲区的所有内容

.InputMode = comInputModeBinary '以二进制格式访问

.RThreshold = 100        '接收缓冲区可接收的字节数

.PortOpen = True         '打开串口

End With

ReDim y(0)               '定义y()动态数组

Combo1.Text = 1          '纵横轴初值:1/div

Combo2.Text = 1

Combo3.Text = 100        '采样间隔初值

End Sub

'建立图片框内的坐标系统

Private Sub Form_Paint()

With Picture1   '使图片框大小随窗体尺寸自动改变

.Top = 200

.Left = 300

.Width = Me.ScaleWidth - 600

.Height = Me.ScaleHeight - 1800

.ScaleMode = 7           '以厘米为单位

oldx = .ScaleWidth / 2   '图片框中心坐标

oldy = .ScaleHeight / 2

.AutoRedraw = True       '使坐标系不被CLS清除

Picture1.Line (oldx, 0)-(oldx, .ScaleHeight), _

RGB(255, 0, 0)           '画纵轴

Picture1.Line (0, oldy)-(.ScaleWidth, oldy), _

RGB(255, 0, 0)           '画横轴

End With

For xt = -14 To 14        '画横轴厘米刻度线

If xt <> 0 Then

Picture1.Line (oldx + xt, oldy - 0.2)-(oldx _

+ xt, oldy), RGB(255, 0, 0)

End If

Next

For xt = -14 To 14 Step 0.1 '画横轴毫米刻度线

If xt <> 0 Then

Picture1.Line (oldx + xt, oldy - 0.1)-(oldx + _

xt, oldy), RGB(255, 0, 0)

End If

Next

For yt = -9 To 9           '画纵轴厘米刻度线

If yt <> 0 Then

Picture1.Line (oldx, oldy + yt)-(oldx + 0.2, _

oldy + yt), RGB(255, 0, 0)

End If

Next

For yt = -9 To 9 Step 0.1  '画纵轴毫米刻度线

If yt <> 0 Then

Picture1.CurrentX = oldx - 0.4

Picture1.CurrentY = oldy + st - 0.1

Picture1.Line (oldx, oldy + yt)-(oldx + 0.1, _

oldy + yt), RGB(255, 0, 0)

End If

Next

End Sub

'把串口接收的数据送y()数组

Private Sub MSComm1_OnComm()

If MSComm1.CommEvent = comEvReceive Then

Dim yy() As Byte, n As Integer

k = MSComm1.InBufferCount '串口接收的字节数送K

yy = MSComm1.Input '把串口接收的所有字节送yy()

ReDim y(0)

y(0) = yy(0)       '取出被测摸拟量被衰减的倍数

For i = 2 To k

n = UBound(y)             '当前y()数组上界

ReDim Preserve y(n + 1)   '数组y()增加1个元素

y(n + 1) = yy(i - 1)  'Byte型数据转换为Sigle

y(n + 1) = -y(0) * (y(n + 1) / 128 - 1) * 5 '标度变换

Next

End If

End Sub

Private Sub Option2_Click()

Call buo       '按下“测量”按钮时绘制波形

End Sub

'计算、显示波形上任一点的值

Private Sub Picture1_MouseDown(Button As Integer, _

Shift As Integer, x As Single, y As Single)

x = (x - oldx) * Val(Combo1.Text) '计算单击处的值

y = (oldy - y) * Val(Combo2.Text)

Picture1.Line (0, 0)-(3, 2), _

Picture1.BackColor, BF           '清除该矩形区

Picture1.CurrentX = 0            '移动光标

Picture1.CurrentY = 0

Picture1.Print "该点数据:"

Picture1.Print "t="; x; "ms"     '显示t

Picture1.Print "u="; y; "v"      '显示u

End Sub

 

五、结语

VB6收发数据、设计用户界面、处理数据(标度变换、插值后绘制波形、显示波形上鼠标单击处的值等)及其程序设计的方法,有一定的理论和实用价值,也可应用于其他编程语言。

 

  推荐精品文章

·2024年2月目录 
·2024年1月目录
·2023年12月目录
·2023年11月目录
·2023年10月目录
·2023年9月目录 
·2023年8月目录 
·2023年7月目录
·2023年6月目录 
·2023年5月目录
·2023年4月目录 
·2023年3月目录 
·2023年2月目录 
·2023年1月目录 

  联系方式
TEL:010-82561037
Fax: 010-82561614
QQ: 100164630
Mail:gaojian@comprg.com.cn

  友情链接
 
Copyright 2001-2010, www.comprg.com.cn, All Rights Reserved
京ICP备14022230号-1,电话/传真:010-82561037 82561614 ,Mail:gaojian@comprg.com.cn
地址:北京市海淀区远大路20号宝蓝大厦E座704,邮编:100089