讓CEGUI的Editbox控件支持複製,粘貼

讓CEGUI的Editbox控件支持複製,粘貼。鑑於CEGUI內部,集成太多的東西,不利於維護,因此對windows Clipboard 的API函數的控制,放在客戶端實現,同時CEGUI只負責Ctrl+C,Ctrl+V被按下的時候,發出相應的消息即可。

但這樣就又引出了新的問題:負責處理該事件的回調函數在lua中,對utf8編碼的處理比較煩,關鍵是沒有相應的字符串函數供你調用;回想一下,C++中的insert(),erase(),length()用的這麼舒心,你該感概庫的強大作用了吧!

沒關係,自己動手豐衣足食嘛!首先搞懂UTF8的編碼規則:

  • 字符的第一個字節範圍: 0x00—0x7F(0-127),或者 0xC2—0xF4(194-244);

  • 0xC0, 0xC1,0xF5—0xFF(192, 193 和 245-255)不會出現在UTF8編碼中

  • 0x80—0xBF(128-191)只會出現在第二個及隨後的編碼中(針對多字節編碼,如漢字)

這樣我們可以利用lua強大的模式匹配,來實現我們要的效果,關鍵的處理有這麼兩個:

  • local _, count = string.gsub(str, "[^\128-\193]", ""),用來得到str中的字符數

  • for uchar in string.gfind(str, "[%z\1-\127\194-\244][\128-\191]*") do tab[#tab+1] = uchar end,用來把str中的每個字符映射到tab中

另外附上windows Clipboard的相關API:

{%highlight c++%} if(OpenClipboard(0)) { EmptyClipboard(); HGLOBAL clipbuffer = GlobalAlloc(GMEMDDESHARE, info.length()+1); char buffer = (char)GlobalLock(clipbuffer); strcpy(buffer, info.cstr()); GlobalUnlock(clipbuffer); SetClipboardData(CFTEXT,clipbuffer); CloseClipboard(); } //---------------------------------------------------------------------------- if (!IsClipboardFormatAvailable(CFTEXT) || !OpenClipboard(0)) { return false; } HGLOBAL hMem = GetClipboardData(CF_TEXT); if (hMem != NULL) { LPTSTR lpStr = (LPTSTR)GlobalLock(hMem); if (lpStr != NULL) { content = std::string((char*)lpStr); GlobalUnlock(hMem); } else content = ""; } else content = ""; CloseClipboard(); {%endhighlight%}

對付一般的應用,這樣做足夠了;如果高手路過,能有更好的解決方案,歡迎賜教!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章