Applies to: desktop apps only
Synthesizes keystrokes, mouse motions, and button clicks.
Syntax
UINT WINAPI SendInput( __in UINT nInputs, __in LPINPUT pInputs, __in int cbSize );
Parameters
- nInputs [in]
-
Type: UINT
The number of structures in the pInputs array.
- pInputs [in]
-
Type: LPINPUT
An array of INPUT structures. Each structure represents an event to be inserted into the keyboard or mouse input stream.
- cbSize [in]
-
Type: int
The size, in bytes, of an INPUT structure. If cbSize is not the size of an INPUT structure, the function fails.
Return value
Type: UINT
The function returns the number of events that it successfully inserted into the keyboard or mouse input stream. If the function returns zero, the input was already blocked by another thread. To get extended error information, call GetLastError.
This function fails when it is blocked by UIPI. Note that neither GetLastError nor the return value will indicate the failure was caused by UIPI blocking.
Remarks
This function is subject to UIPI. Applications are permitted to inject input only into applications that are at an equal or lesser integrity level.
The SendInput function inserts the events in the INPUT structures serially into the keyboard or mouse input stream. These events are not interspersed with other keyboard or mouse input events inserted either by the user (with the keyboard or mouse) or by calls to keybd_event, mouse_event, or other calls to SendInput.
This function does not reset the keyboard's current state. Any keys that are already pressed when the function is called might interfere with the events that this function generates. To avoid this problem, check the keyboard's state with the GetAsyncKeyState function and correct as necessary.
Because the touch keyboard uses the surrogate macros defined in winnls.h to send input to the system, a listener on the keyboard event hook must decode input originating from the touch keyboard. For more information, see Surrogates and Supplementary Characters.
Requirements
|
Minimum supported client | Windows 2000 Professional |
|---|---|
|
Minimum supported server | Windows 2000 Server |
|
Header |
|
|
Library |
|
|
DLL |
|
See also
- Reference
- INPUT
- GetAsyncKeyState
- keybd_event
- mouse_event
- Conceptual
- Keyboard Input
- Surrogates and Supplementary Characters
Send comments about this topic to Microsoft
Build date: 3/6/2012
Module SendInput
Const ShiftKey As Short = 16
Const ControlKey As Short = 17
Const AltKey As Short = 18
Public Function GetKeyboardCode(ByVal value As Char) As Int32
Dim scan = BitConverter.GetBytes(NativeMethods.VkKeyScan(value))
Return CInt(scan(0))
End Function
Public Function SendStringKeys(ByVal data As String) As Boolean
If data Is Nothing Then Throw New ArgumentNullException("data")
Dim tempList = New List(Of tagINPUT)
For Each item As Char In data
Dim scan = BitConverter.GetBytes(NativeMethods.VkKeyScan(item))
Select Case scan(1)
Case Is = 1 'Contain Shift
tempList.Add(GetKeyDownStructure(ShiftKey))
tempList.Add(GetKeyDownStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(ShiftKey))
Case Is = 2 ' Contain Ctrl
tempList.Add(GetKeyDownStructure(ControlKey))
tempList.Add(GetKeyDownStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(ControlKey))
Case Is = 4 ' Contain Alt
tempList.Add(GetKeyDownStructure(AltKey))
tempList.Add(GetKeyDownStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(AltKey))
Case Else
tempList.Add(GetKeyDownStructure(CShort(scan(0))))
tempList.Add(GetKeyUpStructure(CShort(scan(0))))
End Select
Next
Dim objSend = tempList.ToArray
Dim nInput = CUInt(objSend.Count)
Return nInput = NativeMethods.SendInput(CUInt(objSend.Count), objSend, Marshal.SizeOf(GetType(tagINPUT)))
End Function
Public Function SendKeyPress(ByVal key As Int32) As Boolean
If ValidateKeyCode(key) = False Then Throw New ArgumentOutOfRangeException("key")
Dim objSend() As tagINPUT = {GetKeyDownStructure(CShort(key)), GetKeyUpStructure(CShort(key))}
Dim nInput = CUInt(objSend.Count)
Return nInput = NativeMethods.SendInput(CUInt(objSend.Count), objSend, Marshal.SizeOf(GetType(tagINPUT)))
End Function
Public Function SendKeyUp(ByVal key As Int32) As Boolean
If ValidateKeyCode(key) = False Then Throw New ArgumentOutOfRangeException("key")
Dim objSend = New tagINPUT(0) {GetKeyUpStructure(CShort(key))}
Dim nInput = CUInt(objSend.Count)
Return nInput = NativeMethods.SendInput(CUInt(objSend.Count), objSend, Marshal.SizeOf(GetType(tagINPUT)))
End Function
Public Function SendKeyDown(ByVal key As Int32) As Boolean
If ValidateKeyCode(key) = False Then Throw New ArgumentOutOfRangeException("key")
Dim objSend = New tagINPUT(0) {GetKeyDownStructure(CShort(key))}
Dim nInput = CUInt(objSend.Count)
Return nInput = NativeMethods.SendInput(CUInt(objSend.Count), objSend, Marshal.SizeOf(GetType(tagINPUT)))
End Function
Private Function GetKeyDownStructure(ByVal key As Short) As tagINPUT
Dim retVal = New tagINPUT With {.dwType = INPUTTYPE.KEYBOARD}
With retVal.union.ki
.dwExtraInfo = Nothing
.dwFlags = 0
.time = 0
.wScan = 0
.wVk = key
End With
Return retVal
End Function
Private Function GetKeyUpStructure(ByVal key As Short) As tagINPUT
Dim retVal = New tagINPUT With {.dwType = INPUTTYPE.KEYBOARD}
With retVal.union.ki
.dwExtraInfo = Nothing
.dwFlags = KEYEVENTF.KEYUP
.time = 0
.wScan = 0
.wVk = key
End With
Return retVal
End Function
Public Function ValidateKeyCode(ByVal key As Int32) As Boolean
If key < 1 OrElse key > 254 Then Return False
Return True
End Function
#Region "Structures"
<StructLayout(LayoutKind.Sequential)>
Friend Structure tagHARDWAREINPUT
Public uMsg As Int32
Public wParamL As Int16
Public wParamH As Int16
End Structure
<StructLayout(LayoutKind.Sequential)>
Friend Structure tagKEYBDINPUT
Public wVk As Int16
Public wScan As Int16
Public dwFlags As KEYEVENTF
Public time As UInt32
Public dwExtraInfo As UIntPtr
End Structure
<StructLayout(LayoutKind.Sequential)>
Friend Structure tagMOUSEINPUT
Public dx As Int32
Public dy As Int32
Public mouseData As Int32
Public dwFlags As MOUSEEVENTF
Public time As UInt32
Public dwExtraInfo As UIntPtr
End Structure
<StructLayout(LayoutKind.Sequential)>
Friend Structure tagINPUT
Public dwType As INPUTTYPE
Public union As UnionTag
<StructLayout(LayoutKind.Explicit)>
Public Structure UnionTag
<FieldOffset(0)> Public mi As tagMOUSEINPUT
<FieldOffset(0)> Public ki As tagKEYBDINPUT
<FieldOffset(0)> Public hi As tagHARDWAREINPUT
End Structure
End Structure
#End Region
#Region "Enumerations"
Friend Enum INPUTTYPE As UInt32
MOUSE = 0
KEYBOARD = 1
HARDWARE = 2
End Enum
<Flags()>
Friend Enum MOUSEEVENTF As UInt32
MOVE = &H1 ' mouse move
LEFTDOWN = &H2 ' left button down
LEFTUP = &H4 ' left button up
RIGHTDOWN = &H8 ' right button down
RIGHTUP = &H10 ' right button up
MIDDLEDOWN = &H20 ' middle button down
MIDDLEUP = &H40 ' middle button up
XDOWN = &H80 ' x button down
XUP = &H100 ' x button down
WHEEL = &H800 ' wheel button rolled
HWHEEL = &H1000 ' hwheel button rolled
MOVE_NOCOALESCE = &H2000 ' do not coalesce mouse moves
VIRTUALDESK = &H4000 ' map to entire virtual desktop
ABSOLUTE = &H8000 ' absolute move
End Enum
<Flags()>
Friend Enum KEYEVENTF As UInt32
EXTENDEDKEY = &H1
KEYUP = &H2
UNICODE = &H4
SCANCODE = &H8
End Enum
#End Region
Private NotInheritable Class NativeMethods
Private Sub New()
End Sub
Private Const WinUser As String = "user32.dll"
<DllImport(WinUser, EntryPoint:="SendInput", SetLastError:=True)>
Public Shared Function SendInput(<[In]()> ByVal nInput As UInt32,
<[In](), MarshalAs(UnmanagedType.LPArray, ArraySubtype:=UnmanagedType.Struct, SizeParamindex:=0)> ByVal pInputs() As tagINPUT,
<[In]()> ByVal cbInput As Int32) As UInt32
End Function
<DllImport(WinUser, EntryPoint:="VkKeyScan", SetLastError:=True)>
Public Shared Function VkKeyScan(<[In]()> ByVal ch As Char) As UInt16
End Function
End Class
End Module
/****************** replicated structs for mouse, keys and hardware. ******************/
[StructLayout(LayoutKind.Sequential)]
internal struct MOUSEINPUT
{
public int dx;
public int dy;
public int mouseData;
public int dwFlags;
public int time;
public IntPtr dwExtraInfo;
} ;
[StructLayout(LayoutKind.Sequential)]
internal struct KEYBDINPUT
{
public short wVk;
public short wScan;
public int dwFlags;
public int time;
public IntPtr dwExtraInfo;
} ;
[StructLayout(LayoutKind.Sequential)]
internal struct HARDWAREINPUT
{
public int uMsg;
public short wParamL;
public short wParamH;
}
/****************** then a struct of structs for the union (each in its place): ******************/
[StructLayout(LayoutKind.Explicit)]
internal struct UNION
{
[FieldOffset(0)] public MOUSEINPUT mouseInput;
[FieldOffset(1)] public KEYBDINPUT keyboardInput;
[FieldOffset(2)] public HARDWAREINPUT hardwareInput;
} ;
/****************** Then Passing in the INPUT struct by ref ******************/
[StructLayout(LayoutKind.Sequential)]
internal struct INPUT
{
public int type;
public UNION union;
} ;
Declare Type myTypeDim type As LongBegin UnionCase type = 1 Then 'This is a checked predicateDim field1_1 As MyType1Case type = 2 Then 'This is another checked predicateDim field2_1, field2_2 As MyType2Dim field2_3 As LongEnd UnionEnd MyType
type As Long
mi As MOUSEINPUT
ki As KEYBDINPUT
hi As HARDWAREINPUTEnd Type
WORD vkCode = 0x36; // '6'
INPUT keyEvent = {0};
keyEvent.type = INPUT_KEYBOARD;
keyEvent.ki.wVk = vkCode;
keyEvent.ki.wScan = MapVirtualKeyEx(vkCode, 0, (HKL)0xf0010413);
SendInput(1, &keyEvent, sizeof(keyEvent));
///////////////////////////////////////////////
This code gives the '^6' char combination instead of '6'.
Private Type INPUT_MOUSE_DATA
type As Long
mi As MOUSEINPUT
End Type
Private Type INPUT_KEYBD_DATA
type As Long
ki As KEYBDINPUT
End Type
Private Type INPUT_HW_DATA
type As Long
hi As HARDWAREINPUT
End Type