心灵微语 世界上的一队小小的漂泊者呀,请留下你们的足印在我的文字里。 Troupe of little vagrants of the world, leave your footprints in my words. 使用情况:PLC一次需要传递大量数据给HMI;反之亦然! 当然了,这也是WinCC的一个小漏洞,就是在Tags点数有限的情况下,可以使用这种方法来扩展点数。 提醒:此方式下。PLC与HMI只能使用“字节”进行交互。 以下重点阐述“浮点数”交互的问题!关于“DINT”或“INT”,大家可以参照“浮点数”的交互方式。其实“浮点数”交互时,依据的也就是“DINT”型数据。 举例:REAL:A(保留小数点后两位) DINT:B 推导:B=REAL_To_DINT(A*100.0) A= DINT_To_REAL(B)/100.0 通过上述,我们很容易得出一个结论:可以操作的“浮点数”范围应限制在“-21474836.48~21474836.47”内,也就是其扩大100倍后,在一个“DINT”范围内。 这里建议大家将“浮点数”范围限制在“-20000000.00~20000000.00”,当超出范围时,HMI和PLC中应有相应的防护、报警措施。(以下文中并没有具体给出防护、报警措施) 数据交互时,为了保证数据的有效性,①这里还简单的做了一下“和校验”,当然亦可以扩展其他的校验方式。(校验必须要有)②还需要增加检验 “PLC与HMI”是否断线从而保证交互数据的有效性! “PLC与HMI”之间断线判断方法: PLC发送递增数据至HMI,判断“当前周期数据”与“上一周期数据”是否不一样: ①“不相等”,即通讯正常; ②“相等”,且持续“一段时间”(5~10秒),即通讯异常! 反之:HMI发送递增数据至PLC,判断方法和上面一样! 一、数据方向: ---PLC To HMI(HMI From PLC) 1、PLC工作: PLC创建“DB1”数据块,注意创建的数据类型是“DINT”;
将浮点数转换为双整数,并存入DB1中。(这里将要传递的数据,逐一转换后,存入DB1中) 定义:REAL:A(保留小数点后两位) DINT:B 推导:B= REAL_To_DINT(A*100.0)
PLC中计算和校验,注意这里的数据类型是”DINT”和“DWORD”。 提供给HMI做判断!
2、HMI工作: 创建“原始数据类型”变量,这里建议:一个“原始数据类型”变量最多可以有400个字节,即100个“REAL”数据或“DINT” 数据 若想交互更多数据,可以新建多个“原始数据类型”变量。 但一定要注意传输量限制(小于16K)。
创建显示用的“内部变量”
创建脚本程序 //*************************************************************************************** // Define Variable定义变量 // Define Read Variable BYTE Read_A [400] ; // HMI From PLC ReallyVariable DWORD Read_B [100] ; // Change Type Variable LONG Read_C [100] ; // Change Type Variable FLOAT Read_D [100] ; // HMI Variable DWORD Read_E , Read_F ; // Public Variable INT i , j ; // Read Program // HMI Read PLC读取数据 GetTagRaw ( "Read_Raw0" , Read_A , 400 ) ; // HMI From PLC Really Variable拼装数据 for(i=0;i<100;i++) { j = i * 4 ; Read_B [ i ] = ( DWORD ) ( ( Read_A [ j ] * 16777216 ) +( Read_A [ j + 1 ] * 65536 ) + ( Read_A [ j + 2 ] * 256 ) + Read_A [ j + 3 ] ); } // Change Variable Type数据类型转换和数据校验计算 // Value Check Read_E =0 ; for ( i = 0 ; i < 100 ; i++ ) { Read_E = Read_E + Read_B [ i ] ; // Value Check Read_C [ i ] = ( LONG ) Read_B [ i ] ; // Change Variable Type Read_D [ i ] = ( ( FLOAT ) Read_C [ i ] ) / 100.0; // ChangeVariable Type } Read_F = Read_E ^ 0xFFFFFFFF ; // Value Check // Gain PLC Variable数据写入“内部变量”中 SetTagFloat ( "Read0" ,Read_D [ 0 ] ) ; SetTagFloat ( "Read1" ,Read_D [ 1 ] ) ; SetTagFloat ( "Read2" ,Read_D [ 2 ] ) ; SetTagFloat ( "Read3" ,Read_D [ 3 ] ) ; SetTagFloat ( "Read4" ,Read_D [ 4 ] ) ; // ......此处省略 SetTagFloat ( "Read95" ,Read_D [ 95 ] ) ; SetTagFloat ( "Read96" ,Read_D [ 96 ] ) ; SetTagFloat ( "Read97" ,Read_D [ 97 ] ) ; SetTagFloat ( "Read98" ,Read_D [ 98 ] ) ; SetTagFloat ( "Read99" ,Read_D [ 99 ] ) ; 以下是数据校验判断(判断来至PLC的校验数据) if ( ( Read_E == GetTagDWord( "Read_Check1" ) )& ( Read_F == GetTagDWord( "Read _Check2" ) ) ) { SetTagBit ( "Read_Good" , 1 ) ; SetTagBit ( "Read_Bad" , 0 ) ; } else { SetTagBit ( "Read_Good" , 0 ) ; SetTagBit ( "Read_Bad" , 1 ) ; } //*************************************************************************************** 扩展: 当需要交互更多数据时,若想交互500个“浮点数”。只需要增加以下部分:(以下为举例) (以下程序为了可读性,定义的变量较多,当然也可以适当的减少!) /*************************************************************************************** // Define Variable定义变量 // Define Read Variable BYTE Read_A0 [400] ; BYTE Read_A1 [400] ; BYTE Read_A2 [400] ; BYTE Read_A3 [400] ; BYTE Read_A4 [400] ; DWORD Read_B0 [100] ; DWORD Read_B1 [100] ; DWORD Read_B2 [100] ; DWORD Read_B3 [100] ; DWORD Read_B4 [100] ; LONG Read_C0 [100] ; LONG Read_C1 [100] ; LONG Read_C2 [100] ; LONG Read_C3 [100] ; LONG Read_C4 [100] ; FLOAT Read_D0 [100] ; FLOAT Read_D1 [100] ; FLOAT Read_D2 [100] ; FLOAT Read_D3 [100] ; FLOAT Read_D4 [100] ; DWORD Read_E , Read_F ; // Public Variable INT i , j ; // Read Program // HMI Read PLC读取数据 GetTagRaw ( "Read_Raw0" , Read_A0 , 400 ) ; GetTagRaw ( "Read_Raw1" , Read_A1 , 400 ) ; GetTagRaw ( "Read_Raw2" , Read_A2 , 400 ) ; GetTagRaw ( "Read_Raw3" , Read_A3 , 400 ) ; GetTagRaw ( "Read_Raw4" , Read_A4 , 400 ) ; // HMI From PLC Really Variable拼装数据 for(i=0;i<100;i++) { j = i * 4 ;
|