熱線支持的過程中有時會遇到一些客戶提出要在 WinCC 項目運行時,在畫面中捕捉到鼠標的坐標值。多年的熱線支持養(yǎng)成的習(xí)慣總是會驅(qū)使我考慮一下用戶要這個坐標值干嘛用呢?當然,問客戶是最直接的,得到最多的回答就是希望獲取這個坐標的目的在于:當在 WinCC 畫面中點擊設(shè)備圖標時彈出設(shè)備的子畫面,希望彈出子畫面的坐標根據(jù)鼠標的坐標來自動確定,而不是在腳本中寫為固定的常數(shù)。當然答案也不全是這個,也有比較特殊用途的。
其實為解決客戶自動確定彈出子畫面窗口坐標位置的這個問題無需大費周章,WinCC 的鼠標事件中其實就已經(jīng)包含了鼠標坐標值。當然也并不是所有鼠標事件中都包含,首先來看一下 WinCC 按鈕中都有哪些鼠標事件:
- 單擊鼠標
- 按左鍵
- 釋放左鍵
- 按右鍵
- 釋放左鍵
那哪些事件能夠簡單的獲取到鼠標坐標值呢?
很簡單,只要隨意打開一個按鈕事件的動作腳本編輯器就能知道。
單擊鼠標 C 動作:
按左鍵 C 動作:
按右鍵 VBS 動作:
細心的朋友應(yīng)該從截圖中就已經(jīng)找到答案了。除了單擊鼠標動作事件中沒有提供鼠標坐標值,其它動作事件中都已經(jīng)默認提供了鼠標坐標值,也就是截圖紅框中的 x 和 y 。
為什么唯獨單擊鼠標事件沒有提供鼠標坐標值呢?這是因為單擊鼠標指的是鼠標按下并釋放的一個完整過程,當鼠標指針在一個可操作對象上按下鼠標左鍵時,這個過程并未完成,此時如果想放棄操作只需要在按住左鍵不釋放而將鼠標移動至可操作對象范圍之外再釋放,相當于就放棄了此次單擊操作。所以 WinCC 只提供了鼠標按下以及釋放時的鼠標坐標值就已經(jīng)能完全滿足需要了。
清楚了這一點,其實接下來要實現(xiàn)彈出窗口自動確定坐標的功能也就很容易實現(xiàn)了。首先簡單測試一下如何通過 C 腳本以及 VB 腳本來獲取并輸出鼠標的 x 和 y 坐標值,然后再應(yīng)用到實際需求中即可。
首先在畫面中添加兩個按鈕以及一個應(yīng)用程序窗口(窗口內(nèi)容:全局腳本;模板:GSC Diagnostics)。
1.鼠標按左鍵時 C 腳本獲取并輸出 x 和 y 坐標值:
在按鈕“C 獲取 x,y 坐標”的“按左鍵”事件中編寫腳本
void OnLButtonDown(
char* lpszPictureName, char* lpszObjectName, char* lpszPropertyName, UINT nFlags, int x, int y)
{
printf("C 獲取的 x y 坐標:X: %d Y: %d\r\n", x, y);
}
2.鼠標按左鍵時 VB 腳本獲取并輸出 x 和 y 坐標值:
在按鈕“VBS 獲取 x,y 坐標”的“按左鍵”事件中編寫腳本
Sub OnLButtonDown(ByVal Item, ByVal Flags, ByVal x, ByVal y)
HMIRuntime.Trace "VBS 獲取的 x y 坐標:" & " X: " & x & " Y: " & y & vbCrlf
End Sub
激活 WinCC 運行系統(tǒng)后,在畫面中鼠標分別按下兩個按鈕后,應(yīng)用程序窗口中將會輸出鼠標按下時的 x,y 坐標值。
接下來就可以應(yīng)用到實際需求中了。將剛才的兩個按鈕當作設(shè)備圖標,當按下兩個按鈕時自動根據(jù)鼠標位置彈出子畫面窗口(以 VBS 為例)。
1.添加并編輯一個子畫面(DeviceDetail.pdl)
2.主畫面中添加一個畫面窗口(對象名稱:SubPic)
3.給兩個按鈕編重新編寫 VB 腳本
激活運行后,分別按下兩個按鈕時,彈出窗口則會自動根據(jù)鼠標按下時的坐標位置彈出
以上方法都是由鼠標動作事件來獲取鼠標坐標值,如果希望在鼠標移動而不執(zhí)行鼠標動作事件時也實時獲取鼠標位置是否可行呢?答案是肯定的,通過強大的 C 腳本也是可以實現(xiàn)的,方法如下:
在 C 全局動作中添加一個全局動作,并將觸發(fā)器設(shè)置為周期 250 ms
當項目激活運行后,在應(yīng)用程序窗口中就可以看到實時變化的鼠標坐標值。
通過這種方法也可以做出一些特殊的效果,例如導(dǎo)航菜單根據(jù)鼠標位置的自動彈出及隱藏。