I'm using ToUnicodeEx
function to translate the virtual key code of a pressed key to its unicode character,
This is the function definition:
<DllImport("user32.dll", CharSet:=CharSet.Auto, ExactSpelling:=True, CallingConvention:=CallingConvention.Winapi)>
Friend Shared Function ToUnicodeEx(
ByVal wVirtKey As UInteger,
ByVal wScanCode As UInteger,
ByVal lpKeyState As Byte(),
<Out, MarshalAs(UnmanagedType.LPWStr)>
ByVal pwszBuff As StringBuilder,
ByVal cchBuff As Integer,
ByVal wFlags As UInteger,
ByVal dwhkl As IntPtr
) As Integer
End Function
The function works perfect for my culture es-ES with my keyboard layout 3082, however, if instead specifying 3082 I try the code below specifying a 1033 keyboard layout to simulate a key pres for en-US culture, or whatever any other keyboard layout different than 3082, then ToUnicodeEx
function will fail and returns 0, where a return value of 0 means this:
The specified virtual key has no translation for the current state of the keyboard. Nothing was written to the buffer specified by pwszBuff.
Dim buf As New StringBuilder(256)
Dim keyboardState As Byte() = New Byte(255) {}
If shift Then
keyboardState(CInt(Keys.ShiftKey)) = &HFF
End If
If altGr Then
keyboardState(CInt(Keys.ControlKey)) = &HFF
keyboardState(CInt(Keys.Menu)) = &HFF
End If
InputDevice.NativeMethods.ToUnicodeEx(CUInt(Keys.A), 0UI, keyboardState, buf, 256, 0UI,
New IntPtr(1033))
What I'm doing wrong?, How I can fix it?
Experimenting, reasearching, and with some fails, I found in the .Net framework class library the best and easier solution that does not involves P/Invoking.
Just knowing a culturename, like en-US or es-ES with the Systwm.Windows.Forms.InputLanguage
class we can retrieve the handle of the layout (the HKL)
InputLanguage.FromCulture(New CultureInfo("en-US")).Handle
Then, that value can be set for the dwHKL
parameter of the ToUnicodeEx
function, and it works perfect!.