Trang 1 trên 1

Cách dùng API unicode thay đổi đối số (String, Long, Any)

Đã gửi: T.Bảy 19/11/2011 10:50 am
gửi bởi truongphu
Tên bài viết: Cách dùng API unicode thay đổi đối số (String, Long, Any)
Tác giả: truongphu
Cấp độ bài viết: Can bản
Tóm tắt: Cách dùng API unicode thay đổi đối số (String, Long, Any)



Ta xét hàm API TextOut: (ANSI)
Private Declare Function TextOut Lib "gdi32" Alias "TextOutA" (ByVal hdc As Long, ByVal x As Long, ByVal y As Long, ByVal lpString As String, ByVal nCount As Long) As Long

Bỏ qua 3 đối số đầu hDc (số mặt vẽ, x và y vị trí)
2 đối số sau; lpString As String = chuỗi và nCount As Long = số ký tự chuỗi

Giờ chuyển qua dùng unicode, ta phải truy xuất từ TextOutW
và đối số lpString sẽ được khai báo tùy định dạng biến ta dùng: chuỗi, mảng byte hay địa chỉ chuỗi (con trỏ)
lpString như vậy sẽ được khai hoặc String, Any hay Long.
Code như sau:

  1. Private Declare Function AAA Lib "gdi32.dll" Alias "TextOutW" _
  2. (ByVal hdc As Long, ByVal x As Long, ByVal y As Long, _
  3.  lpString As Any, ByVal nCount As Long) As Long
  4. ' Khi dùng mang byte thì loai bo "ByVal" tai lpString As Any (Byref)
  5.  
  6. Private Declare Function LLL Lib "gdi32.dll" Alias "TextOutW" _
  7. (ByVal hdc As Long, ByVal x As Long, ByVal y As Long, _
  8.  ByVal lpString As Long, ByVal nCount As Long) As Long
  9.  
  10. Private Declare Function SSS Lib "gdi32.dll" Alias "TextOutW" _
  11. (ByVal hdc As Long, ByVal x As Long, ByVal y As Long, _
  12.  ByVal lpString As String, ByVal nCount As Long) As Long
  13.  
  14. Dim Chuôi$, Result&
  15.  
  16. Private Sub Form_Paint()
  17.     Chuôi = "Ti" & ChrW(7871) & "ng Vi" & ChrW(7879) & "t Unicode bi" & ChrW(&H1EC3) & "u hi" & ChrW(&H1EC7) & "n t" & ChrW(&H1ED1) & "t."
  18. End Sub
  19.  
  20. Private Sub Command1_Click() ' lpString As Long
  21.    Result = LLL(Me.hdc, 24, 10, StrPtr(Chuôi), Len(Chuôi))
  22. End Sub
  23.  
  24. Private Sub Command2_Click() ' lpString As String
  25.    Result = SSS(Me.hdc, 24, 50, StrConv(Chuôi, vbUnicode), Len(Chuôi))
  26. End Sub
  27.  
  28. Private Sub Command3_Click() ' lpString As Any
  29.    Dim ZZ() As Byte: ZZ = Chuôi
  30.     Result = AAA(Me.hdc, 24, 90, ZZ(0), Len(Chuôi))
  31.     Result = AAA(Picture1.hdc, 12, 5, ZZ(0), Len(Chuôi))
  32. End Sub
  33.  



Ở trên, hàm TextOut có đối số nCount As Long = số ký tự chuỗi, một số hàm khác không có đối số nầy. Ta thử xét hàm RemoveDirectory.
Chuyển qua unicode, ta dùng code như sau:

  1. Private Declare Function RemoveDirectory Lib "kernel32" Alias "RemoveDirectoryW" (ByVal lpPathName As Long) As Long
  2. Private Declare Function XoaFolder Lib "kernel32" Alias "RemoveDirectoryW" (ByVal lpPathName As String) As Long
  3.  
  4. Private Sub Command1_Click() ' Xóa folder tiêng viêt unicode,
  5. ' folder phai không có gì = rô~ng
  6. Set PathFolder = CreateObject("Shell.Application") _
  7. .BrowseForFolder(0, "Select a folder:", 0)
  8. If Not PathFolder Is Nothing Then RemoveDirectory StrPtr(PathFolder.Self.Path)
  9. End Sub
  10.  
  11.  
  12. Private Sub Command2_Click()
  13. ' folder phai không có gì = rô~ng
  14. Set PathFolder = CreateObject("Shell.Application") _
  15. .BrowseForFolder(0, "Select a folder:", 0)
  16. If Not PathFolder Is Nothing Then XoaFolder StrConv(PathFolder.Self.Path, vbUnicode)
  17. End Sub

Re: Cách dùng API unicode thay đổi đối số (String, Long, Any

Đã gửi: CN 20/11/2011 12:10 pm
gửi bởi OKMimo
theo mình nếu sử dụng textoutw mà truyền đối số cuối cùng là len(chuoi) là sai, mình thấy msdn nói vậy mà

Re: Cách dùng API unicode thay đổi đối số (String, Long, Any

Đã gửi: CN 20/11/2011 11:26 pm
gửi bởi truongphu
a! không để ý, hóa ra có một bạn đọc "sửa sai", rồi đánh giá thấp "uy tín" của tôi nữa chứ! gê thật!
OKMimo đã viết:theo mình nếu sử dụng textoutw mà truyền đối số cuối cùng là len(chuoi) là sai, mình thấy msdn nói vậy mà

Nói vậy nghĩa là sao? bạn phải trích dẫn cụ thể bởi tôi nghi rằng bạn học chưa kỹ: hoặc học một cách máy móc áp dụng không đúng, hoặc bạn nhớ lẫn lộn đâu đó...
Học là phải biết thông hiểu vấn đề và vận dụng, chứ học theo kiểu bạn: "nghe nói thế..." là biết thế mà chẳng hiểu sao cả thì làm sao mà tiến?

1- bạn có học ở đâu trích hàm TextOutW mà gọi chúng là function AAA, LLL hay SSS không? chắc bạn chưa thấy, nhưng điều đó là được phép, tôi đặt tên để dễ nhớ: A=Array, L=Long, S=String.
2- bạn có để ý đối số cuối quy định không? ByVal nCount As Long, nghĩa là bạn đưa vào vị trí đấy một số Long là chạy êm, hà cớ gì mà giới hạn cái nầy sai hay đúng?
3- phải phân biệt Len và LenB, có lẽ msdn nói như thế mới có ý nghĩa. Mà bạn đã biết Len và LenB khác nhau thế nào không?

Túm lại, bạn học thêm Len và LenB nhé. Và cũng nên load các project trên để làm tài liệu...
.

FindWindow vớu unicode Title (thay đối số)

Đã gửi: CN 03/06/2012 9:13 pm
gửi bởi truongphu
byun.over đã viết:Làm sao để FindWindowEx được unicode vậy
gửi bởi byun.over » Hôm nay 6:44 pm

posting.php?mode=reply&f=7&t=23293#pr125256

Câu hỏi nầy hay đấy!
FindWindowEx hay FindWindow cũng từa tựa giống nhau. (FindWindowEx có thêm 2 đối số hWnd = Long ở trước).
Ta xét FindWindow cho dễ.

Khai báo thông thường:
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long


Trong câu khai báo trên, FindWindow là từ ta có thể đặt một tên khác tùy thích; quan trọng là "FindWindowA", nghĩa là truy xuất thư viện user32 lấy ra "FindWindowA" không hổ trợ unicode (ký tự A ở sau).

* Để làm việc với unicode, ta sửa lại "FindWindowA" thành "FindWindowW"

Mã: Chọn hết

Private Declare Function FindWindow Lib "user32" Alias "FindWindowW" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long


Khai báo như thế sẽ chưa làm việc được vì chuỗi unicode không được nhận ra!
Xem ví dụ code sau:
- Mở Notepad có tên là Bướm Hồng, Titlte sẽ là "Bướm Hồng - Notepad"

Mã: Chọn hết

Private Sub Command1_Click()
Dim h As Long, tt As String
tt = "B" & ChrW(432) & ChrW(7899) & "m H" & ChrW(7891) & "ng - Notepad"
h = FindWindow(vbNullString, tt)
MsgBox h
End Sub


Kết quả h = 0

* Ta phải dùng thêm hàm StrPtr để tìm địa chỉ chuỗi unicode trong bộ nhớ. Hàm StrPtr trả về số Long; do đó ta sửa tiếp câu khai báo hàm API như sau:
ByVal lpWindowName As String thành ByVal lpWindowName As Long
  1. Private Declare Function FindWindowUNICODE Lib "user32" Alias "FindWindowW" (ByVal lpClassName As String, ByVal lpWindowName As Long) As Long


  1. Private Sub Command2_Click()
  2. Dim h As Long, tt As Long
  3. tt = StrPtr("B" & ChrW(432) & ChrW(7899) & "m H" & ChrW(7891) & "ng - Notepad")
  4. h = FindWindowUNICODE(vbNullString, tt)
  5. MsgBox h
  6. End Sub


lần sau, kết quả đương nhiên ok
Project:

Re: Cách dùng API unicode thay đổi đối số (String, Long, Any

Đã gửi: T.Hai 04/06/2012 8:36 am
gửi bởi byun.over
quá hay. thanks bác truongphu

Re: Cách dùng API unicode thay đổi đối số (String, Long, Any

Đã gửi: T.Hai 04/06/2012 3:29 pm
gửi bởi bimio9
Thanks Bác T Phú!