一、数据导出到EXCEL脚本
Sub Export(ByRef ReportName)On Error Resume NextDim ExcelApp Dim ExcelBook Dim ExcelSheetDim MSFlexGrid1 Dim i,irow,ICOLDim z,kSet MSFlexGrid1 = ScreenItems("Table")Set ExcelApp = CreateObject("Excel.Application")Set ExcelBook = ExcelApp.Workbooks.AddSet ExcelSheet = ExcelBook.Worksheets(1)ExcelApp.Visible = FalseExcelSheet.Range("A1:K1").MergeFor irow = 0 To MSFlexGrid1.Rows - 1 For ICOL = 0 To MSFlexGrid1.Cols - 1 z=MSFlexGrid1.RowsExcelSheet.Cells(irow + 1,ICOL+1)=Trim(MSFlexGrid1.TextMatrix(irow, ICOL)) Next Next ExcelSheet.Range( "A1:K"&z&"").Borders(1).Weight =2ExcelSheet.Range( "A1:K"&z&"").Borders(2).Weight =2ExcelSheet.Range( "A1:K"&z&"").Borders(3).Weight =2ExcelSheet.Range( "A1:K"&z&"").Borders(4).Weight =2ExcelSheet.Rows(1).RowHeight = 0.75/0.035ExcelSheet.Cells.EntireColumn.AutoFitExcelSheet.Rows(1).Font.Name = "宋体"ExcelSheet.Rows(1).Font.Bold = TrueExcelSheet.Rows(1).Font.Size = 16 ExcelSheet.Cells.HorizontalAlignment =3ExcelSheet.PageSetup.CenterHorizontally = 2/0.035Dim patch,filename filename=CStr(Year(Now))&"年"&CStr(Month(Now))&"月"&CStr(Day(Now))&"日"&CStr(Hour(Now))&"时"&CStr(Minute(Now))&"分"&CStr(Second(Now))&"秒" patch= "E:\"&ReportName&filename&".xlsx" ExcelApp.ActiveWorkbook.SaveAs patch ExcelApp.Workbooks.Close ExcelApp.Quit Set ExcelApp= Nothing MsgBox "数据导出成功"End Sub
二、报表查询
Function Report(ByRef ArchiveTags, ByRef TagName1, ByRef TagName2, ByRef Count, ByRef N, ByRef ReportName)'Designer :BluePanda'Version:1.1'Date:2019-07-04'接口参数:'ArchiveTags:查询的归档变量名称格式为“归档名称\归档变量名称”'TagName1:变量名称第一行(名称过长分开两行写 例如:窗前明月光此行写”窗前“)'TagName2:变量名称第二行(名称过长分开两行写 例如:窗前明月光此行写”明月光“)'Count:要查询的变量个数'N:正在查询变量的位置,如有五个变量现在查到第三个则N为2'ReportName:表格名称,表格第一行要填入的名称'使用说明'使用前需要在报表画面上建立两个DateTimePicker控件,对象名称为BeginTime与EndTime'需要添加一个MSFlexGrid控件,控件名称为Table'需要添加一个I/O域,对象名称为Number Dim tagDSNName,BeginTime,EndTime,sPro,sDsn,sSer,A '声明变量Dim sCon,conn,sSql,oRs,oCom,m,grid,j,k,l,o,p,q '声明变量On Error Resume Next '防止脚本出错,电脑卡住Set A=ScreenItems("Number") '定义变量A为画面为报表画面的对象Number,画面上显示记录数据条数的IO域 Set grid=ScreenItems("Table") '定义变量grid为画面的对象Table,画面上的表格控件Set tagDSNName=HMIRuntime.Tags("@DatasourceNameRT") '定义变量tagDSNName为变量@DatasourceNameRT,WINCC运行时数据库的名称tagDSNName.Read '读取数据库的名称的值BeginTime=DateAdd("h",-8,ScreenItems("BeginTime").Value)'查询起始时间定义,WINCC读取时时间为UTC时间,我们电脑为北京时间, '相差8个小时此处减去8小时与归档时间保持一致EndTime=DateAdd("h",-8,ScreenItems("EndTime").Value)'查询结束时间定义,WINCC读取时时间为UTC时间,我们电脑为北京时间, '相差8个小时此处减去8小时与归档时间保持一致 '判断时间输入范围是否有效,当起始时间大于结束时间时弹出窗提示并退出该函数 If EndTime-BeginTime<=0 Then '时间判断 o=MsgBox ("请选择合适的时间范围......",vbOKOnly,"错误的起始时间")'弹出提示窗口 Report=o '判断是否有窗口弹出如果弹出,将弹出窗口按钮返回值作为函数返回值 Exit Function '退出该函数End If '定义数据库连接字符串,格式为固定格式 sPro = "Provider=WinCCOLEDBProvider.1;" sDsn = "Catalog=" &tagDSNName.Value& ";" sSer = "Data Source=.\WinCC" sCon = sPro + sDsn + sSer Set conn = CreateObject("ADODB.Connection") '创建数据源的开放连接,通过此连接,您可以对一个数据库进行访问和操作 conn.ConnectionString = sCon '定义ADODB对象连接字符串 conn.CursorLocation = 3 conn.Open '打开WINCC归档数据库 '判断数据库连接状态,1为成功,0为失败,失败后退出该函数 If conn.state=0 Then '数据库连接失败 o=MsgBox ("数据库连接失败......",vbOKOnly,"数据库连接")'弹出提示窗口 conn.Close '关闭数据库连接 Set conn = Nothing '释放ADODB对象 Report=o Exit Function End If sSql = "Tag:R,("&ArchiveTags&"),'" & BeginTime & "','" & EndTime & "'," '定义数据库查询字符串格式为固定格式不可更改sSql=sSql+"'order by Timestamp ASC','TimeStep=10,1'" 'TimeStep为时间间隔单位为秒,如查询间隔一分钟将语句改为TimeStep=60Set oRs = CreateObject("ADODB.Recordset") '创建数据库记录集用来存储数据库查询出的数据 Set oCom = CreateObject("ADODB.Command") '创建数据库查询oCom.CommandType = 1 '设置查询类型为按CommandText查询Set oCom.ActiveConnection = conn '连接数据库oCom.CommandText = sSql '定义查询文本Set oRs = oCom.Execute '执行查询m = oRs.RecordCount '返回查询的记录数据的数量If m=0 Then '如果没查询到数据弹出提示窗口 o=MsgBox ("没有所需数据......",vbOKOnly,"没有相关数据") Set oRs = Nothing '将数据库记录集释放 conn.Close '关闭数据库 Set conn = Nothing Report=o Exit FunctionEnd If oRs.MoveFirst '如果查询到数据,先移动到首条记录grid.Cols=Count+2 '定义表的列为查询变量个数加2,第一列为序号第二列为日期时间grid.Rows=m+3 '定义行数量的为查询到第一个变量的记录数据的数量加3,第一行为标题grid.ColWidth(0) = 600 '设置表格控件第一列列宽(编号列)grid.ColWidth(1) = 1800 '设置表格控件第二列列宽(日期时间列)For j=2 To Count+1 '设置变量列的列宽(归档变量名称)如温度压力等 grid.ColWidth(j)=1200 Next grid.Row = 0 '选择表格第一行操作 For k = 0 To Count+1 '对第一行所有列操作 grid.Col= k '选择操作的列 grid.ColAlignment(k)=4 '设置列对齐方式为水平与垂直均居中 grid.Text = ReportName '填入报表名称 Next grid.MergeCells = 4 '合并内容相同的单元格,此处是将第一行单元格合并 grid.MergeRow(0)= True '并单元格 grid.TextMatrix(1, 0) = "编号" '设置第二行第一列单元格内容为编号 grid.TextMatrix(1, 1) = "日期时间" '设置第二行第一列单元格内容为编号 grid.TextMatrix(1, N+2) = TagName1 '设置变量名称第一行内容 grid.TextMatrix(2, N+2) = TagName2 '设置变量名称第二行内容 If N=0 Then '如果查询为第1个变量执行此操作 For l = 1 To oRs.RecordCount grid.TextMatrix(l + 2, 0) = l '将序号填入第一列 grid.TextMatrix(l + 2, 1) = DateAdd("h",8,oRs.fields(1).value) '将时间还原成本地电脑时间填充到第二列 grid.TextMatrix(l + 2,N+2) = oRs.fields(2).value '将第一个变量的查询值填充到第三列 'If Second(oRs.fields(1).value)=20 Then '此处做数据过滤用本工程无需用到 'grid.TextMatrix(p + 3, 0)= p+1 'grid.TextMatrix(p+ 3, 1) = DateAdd("h",8,oRs.fields(1).value) 'grid.TextMatrix(p+ 3,N+2) = oRs.fields(2).value 'p=p+1 'oRs.movenext 'Else oRs.movenext '移动到下一条数据记录 ' 'End If Next A.ProcessValue=m 'A.OutputValue=m 'WINCC7.X使用此条语句 '将查询到的记录数量显示在报表界面 'A.ProcessValue=p 'A.OutputValue=p 'If p=0 Then 'o=MsgBox ("没有所需数据......",vbOKOnly,"没有相关数据") 'Set oRs = Nothing 'conn.Close 'Set conn = Nothing 'Report=o 'Exit Function 'End IfElse '如果查询为第2个及以上变量执行此操作 For l = 1 To oRs.RecordCount 'If Second(oRs.fields(1).value)=20 Then grid.TextMatrix(l + 2,N+2) = oRs.fields(2).value '将第2个及以上变量的查询值依次填充到第四及以上列 'grid.TextMatrix(q+ 3,N+2) = oRs.fields(2).value 'q=q+1 'oRs.movenext 'Else oRs.movenext 'End If Next End If If N=Count-1 Then Set oRs = Nothing conn.Close Set conn = Nothing Exit FunctionEnd If End Function
下一期我将分享Wincc 数据库的操作,有兴趣的朋友可以关注一下