根据微软拼音输入法得到拼音的例子: Option Explicit Private Const IME_ESC_MAX_KEY = &H1005 Private Const IME_ESC_IME_NAME = &H1006 Private Const GCL_REVERSECONVERSION = &H2 Private Declare Function GetKeyboardLayoutList Lib "user32" (ByVal nBuff As Long, lpList As Long) As Long Private Declare Function ImmEscape Lib "imm32.dll" Alias "ImmEscapeA" (ByVal hkl As Long, ByVal himc As Long, ByVal un As Long, lpv As Any) As Long Private Declare Function ImmGetConversionList Lib "imm32.dll" Alias "ImmGetConversionListA" (ByVal hkl As Long, ByVal himc As Long, ByVal lpsz As String, lpCandidateList As Any, ByVal dwBufLen As Long, ByVal uFlag As Long) As Long Private Declare Function IsDBCSLeadByte Lib "kernel32" (ByVal bTestChar As Byte) As Long Public Function GetChineseSpell(Chinese As String, Optional Delimiter As String = " ", Optional IMEName As String = "微软拼音输入法", Optional BufferSize As Long = 255) As String If VBA.Len(VBA.Trim(Chinese)) > 0 Then Dim i As Long Dim s As String s = VBA.Space(BufferSize) Dim IMEInstalled As Boolean Dim j As Long Dim a() As Long ReDim a(BufferSize) As Long j = GetKeyboardLayoutList(BufferSize, a(LBound(a)))
For i = LBound(a) To LBound(a) + j - 1 If ImmEscape(a(i), 0, IME_ESC_IME_NAME, ByVal s) Then If VBA.Trim(IMEName) = VBA.Replace(VBA.Trim(s), VBA.Chr(0), "") Then IMEInstalled = True Exit For End If End If Next i If IMEInstalled Then 'Stop Chinese = VBA.Trim(Chinese) Dim sChar As String Dim Buffer0() As Byte 'Dim Buffer() As Byte Dim bBuffer0() As Byte Dim bBuffer() As Byte Dim k As Long Dim l As Long Dim m As Long For j = 0 To VBA.Len(Chinese) - 1 sChar = VBA.Mid(Chinese, j + 1, 1) Buffer0 = VBA.StrConv(sChar, vbFromUnicode) If IsDBCSLeadByte(Buffer0(0)) Then k = ImmEscape(a(i), 0, IME_ESC_MAX_KEY, Null) If k Then l = ImmGetConversionList(a(i), 0, sChar, 0, 0, GCL_REVERSECONVERSION) If l Then s = VBA.Space(BufferSize) If ImmGetConversionList(a(i), 0, sChar, ByVal s, l, GCL_REVERSECONVERSION) Then
bBuffer0 = VBA.StrConv(s, vbFromUnicode) ReDim bBuffer(k * 2 - 1) For m = bBuffer0(24) To bBuffer0(24) + k * 2 - 1 bBuffer(m - bBuffer0(24)) = bBuffer0(m) Next m sChar = VBA.Trim(VBA.StrConv(bBuffer, vbUnicode)) If VBA.InStr(sChar, vbNullChar) Then sChar = VBA.Trim(VBA.Left(sChar, VBA.InStr(sChar, vbNullChar) - 1)) End If sChar = VBA.Left(sChar, VBA.Len(sChar) - 1) & VBA.IIf(j < VBA.Len(Chinese) - 1, Delimiter, "")
End If
End If End If End If GetChineseSpell = GetChineseSpell & sChar Next j Else
End If
End If End FunctionPrivate Sub Command1_Click() VBA.MsgBox GetChineseSpell("你好") End Sub
你要整个拼音还是首字符?如果只是要首字符,这个就行了: Private Function TransToPY(AWord As String) As String If AWord = "" Then Exit Function Dim TmpStr As String, i As Long On Error GoTo MyError i = Asc(AWord) If i >= &HB0A1 And i <= &HB0C4 Then TmpStr = "A" If i >= &HB0C5 And i <= &HB2C0 Then TmpStr = "B" If i >= &HB2C1 And i <= &HB4ED Then TmpStr = "C" If i >= &HB4EE And i <= &HB6E9 Then TmpStr = "D" If i >= &HB6EA And i <= &HB7A1 Then TmpStr = "E" If i >= &HB7A2 And i <= &HB8C0 Then TmpStr = "F" If i >= &HB8C1 And i <= &HB9FD Then TmpStr = "G" If i >= &HB9FE And i <= &HBBF6 Then TmpStr = "H" If i >= &HBBF7 And i <= &HBFA5 Then TmpStr = "J" If i >= &HBFA6 And i <= &HC0AB Then TmpStr = "K" If i >= &HC0AC And i <= &HC2E7 Then TmpStr = "L" If i >= &HC2E8 And i <= &HC4C2 Then TmpStr = "M" If i >= &HC4C3 And i <= &HC5B5 Then TmpStr = "N" If i >= &HC5B6 And i <= &HC5BD Then TmpStr = "O" If i >= &HC5BE And i <= &HC6D9 Then TmpStr = "P" If i >= &HC6DA And i <= &HC8BA Then TmpStr = "Q" If i >= &HC8BB And i <= &HC8F5 Then TmpStr = "R" If i >= &HC8F6 And i <= &HCBF9 Then TmpStr = "S" If i >= &HCBFA And i <= &HCDD9 Then TmpStr = "T" If i >= &HCDDA And i <= &HCEF3 Then TmpStr = "W" If i >= &HCEF4 And i <= &HD1B8 Then TmpStr = "X" If i >= &HD1B9 And i <= &HD4D0 Then TmpStr = "Y" If i >= &HD4D1 And i <= &HD7F9 Then TmpStr = "Z" If i > 0 And i < 128 Then TmpStr = UCase(Chr(i)) TransToPY = TmpStr MyError: End Function
Option Explicit
Private Const IME_ESC_MAX_KEY = &H1005
Private Const IME_ESC_IME_NAME = &H1006
Private Const GCL_REVERSECONVERSION = &H2
Private Declare Function GetKeyboardLayoutList Lib "user32" (ByVal nBuff As Long, lpList As Long) As Long
Private Declare Function ImmEscape Lib "imm32.dll" Alias "ImmEscapeA" (ByVal hkl As Long, ByVal himc As Long, ByVal un As Long, lpv As Any) As Long
Private Declare Function ImmGetConversionList Lib "imm32.dll" Alias "ImmGetConversionListA" (ByVal hkl As Long, ByVal himc As Long, ByVal lpsz As String, lpCandidateList As Any, ByVal dwBufLen As Long, ByVal uFlag As Long) As Long
Private Declare Function IsDBCSLeadByte Lib "kernel32" (ByVal bTestChar As Byte) As Long
Public Function GetChineseSpell(Chinese As String, Optional Delimiter As String = " ", Optional IMEName As String = "微软拼音输入法", Optional BufferSize As Long = 255) As String
If VBA.Len(VBA.Trim(Chinese)) > 0 Then
Dim i As Long
Dim s As String
s = VBA.Space(BufferSize)
Dim IMEInstalled As Boolean
Dim j As Long
Dim a() As Long
ReDim a(BufferSize) As Long
j = GetKeyboardLayoutList(BufferSize, a(LBound(a)))
For i = LBound(a) To LBound(a) + j - 1
If ImmEscape(a(i), 0, IME_ESC_IME_NAME, ByVal s) Then
If VBA.Trim(IMEName) = VBA.Replace(VBA.Trim(s), VBA.Chr(0), "") Then
IMEInstalled = True
Exit For
End If
End If
Next i
If IMEInstalled Then
'Stop
Chinese = VBA.Trim(Chinese)
Dim sChar As String
Dim Buffer0() As Byte
'Dim Buffer() As Byte
Dim bBuffer0() As Byte
Dim bBuffer() As Byte
Dim k As Long
Dim l As Long
Dim m As Long
For j = 0 To VBA.Len(Chinese) - 1
sChar = VBA.Mid(Chinese, j + 1, 1)
Buffer0 = VBA.StrConv(sChar, vbFromUnicode)
If IsDBCSLeadByte(Buffer0(0)) Then
k = ImmEscape(a(i), 0, IME_ESC_MAX_KEY, Null)
If k Then
l = ImmGetConversionList(a(i), 0, sChar, 0, 0, GCL_REVERSECONVERSION)
If l Then
s = VBA.Space(BufferSize)
If ImmGetConversionList(a(i), 0, sChar, ByVal s, l, GCL_REVERSECONVERSION) Then
bBuffer0 = VBA.StrConv(s, vbFromUnicode)
ReDim bBuffer(k * 2 - 1)
For m = bBuffer0(24) To bBuffer0(24) + k * 2 - 1
bBuffer(m - bBuffer0(24)) = bBuffer0(m)
Next m
sChar = VBA.Trim(VBA.StrConv(bBuffer, vbUnicode))
If VBA.InStr(sChar, vbNullChar) Then
sChar = VBA.Trim(VBA.Left(sChar, VBA.InStr(sChar, vbNullChar) - 1))
End If
sChar = VBA.Left(sChar, VBA.Len(sChar) - 1) & VBA.IIf(j < VBA.Len(Chinese) - 1, Delimiter, "")
End If
End If
End If
End If
GetChineseSpell = GetChineseSpell & sChar
Next j
Else
End If
End If
End FunctionPrivate Sub Command1_Click()
VBA.MsgBox GetChineseSpell("你好")
End Sub
我先说说文本编码的发展:
Unicode 2.0时为了支持东亚象形文字,成立CJK委员会
Unicode 3.0时发现东亚象形文字远远超过16位空间,于是提出代理对概念(可以用两个wchar存放一个字符,既有的字符16bit、有的字符32bit),将编码空间改成21位
Unicode 4.0索性将编码空间定义为31位,提出UTF-8、UTF-16、UTF-32等一系列编码方案GB2312-1980标准在1993年被GB13000-1993代替
GB13000-1993也在2000年被GB18030-2000代替1993年的GB13000-1993标准是为了兼容CJK字汇,收录了CJK兼容区和CJK扩展区A,简体繁体均收录,共2万多字
2000年的GB18030-2000标准是为了兼容Unicode 4.0,允许4字节编码,编码空间增加260万
注意CJK是“中日韩”的缩写到1998年出VB6时
Microsoft早已支持GB13000-1993标准
所以支持日文显示
对于简体中文系统:
Windows95支持GB13000-1993
Windows98从内核上支持GB13000-1993
Windows2000支持GB18030-2000,但由于其4字节编码很不符合习惯,所以一般情况下还是用GB13000-1993
其实1993出的GB13000-1993已经很变态了
居然支持简体中文、繁体中文、日文、朝鲜文汉字四种语言(注意是朝鲜文中使用的汉字,不是朝鲜文)
现在认识到中国政府有多么认真做事了吧
不像台湾
(20世纪)70年代提出个Big5
到了现在还没更新
仍只支持繁体汉字
中国唯一就是教育行业存在问题
仍是(20世纪)80年代老教材讲ASCII与GB2312-1980
很多人不知道GB13000-1993这个居然被淘汰了的超强汉字标准
(没办法,GB18030-2000更变态)
Private Function TransToPY(AWord As String) As String
If AWord = "" Then Exit Function
Dim TmpStr As String, i As Long
On Error GoTo MyError
i = Asc(AWord)
If i >= &HB0A1 And i <= &HB0C4 Then TmpStr = "A"
If i >= &HB0C5 And i <= &HB2C0 Then TmpStr = "B"
If i >= &HB2C1 And i <= &HB4ED Then TmpStr = "C"
If i >= &HB4EE And i <= &HB6E9 Then TmpStr = "D"
If i >= &HB6EA And i <= &HB7A1 Then TmpStr = "E"
If i >= &HB7A2 And i <= &HB8C0 Then TmpStr = "F"
If i >= &HB8C1 And i <= &HB9FD Then TmpStr = "G"
If i >= &HB9FE And i <= &HBBF6 Then TmpStr = "H"
If i >= &HBBF7 And i <= &HBFA5 Then TmpStr = "J"
If i >= &HBFA6 And i <= &HC0AB Then TmpStr = "K"
If i >= &HC0AC And i <= &HC2E7 Then TmpStr = "L"
If i >= &HC2E8 And i <= &HC4C2 Then TmpStr = "M"
If i >= &HC4C3 And i <= &HC5B5 Then TmpStr = "N"
If i >= &HC5B6 And i <= &HC5BD Then TmpStr = "O"
If i >= &HC5BE And i <= &HC6D9 Then TmpStr = "P"
If i >= &HC6DA And i <= &HC8BA Then TmpStr = "Q"
If i >= &HC8BB And i <= &HC8F5 Then TmpStr = "R"
If i >= &HC8F6 And i <= &HCBF9 Then TmpStr = "S"
If i >= &HCBFA And i <= &HCDD9 Then TmpStr = "T"
If i >= &HCDDA And i <= &HCEF3 Then TmpStr = "W"
If i >= &HCEF4 And i <= &HD1B8 Then TmpStr = "X"
If i >= &HD1B9 And i <= &HD4D0 Then TmpStr = "Y"
If i >= &HD4D1 And i <= &HD7F9 Then TmpStr = "Z"
If i > 0 And i < 128 Then TmpStr = UCase(Chr(i))
TransToPY = TmpStr
MyError:
End Function
微软拼音还算做得比较好,支持绝大多数GB13000-1993编码中的字(很多输入法只支持那个六千字的GB2312-1980)至于GB18030-2000
虽然它是最新汉字标准
但绝大多数人连GB13000-1993的两万多字还未消化可以考虑自己买本《康熙字典》,再自己手动输入……估计输完后你头发都白了所以想100%得到拼音,至少在这几年内是不可能的
也看懂了
但是就是懒得去写对应的vb代码……