java jni SendMessageA WM_KEYDOWN dont work ( - winapi

public interface User32Extra extends User32 {
User32Extra INSTANCE = (User32Extra) Native.loadLibrary("user32", User32Extra.class, W32APIOptions.DEFAULT_OPTIONS);
public HWND FindWindow(String string, String string1);
long SendMessageA(HWND hWnd, int msg, WPARAM wPAram, LPARAM lParam);
}
public class ecbot {
//http://msdn.microsoft.com/en-us/library/windows/desktop/ms645607(v=vs.85).aspx
private static int WM_KEYDOWN = 256;
public static void main(String[] args) {
HWND hWnd = User32.INSTANCE.FindWindow("Notepad", null);
System.out.println(hWnd.toString());
LPARAM lParam1 = new LPARAM(1);
LPARAM lParam0 = new LPARAM(0);
for (int i = 0; i < 1000; i++) {
WinDef.WPARAM wParam = new WinDef.WPARAM(i);
User32Extra.INSTANCE.SendMessageA(hWnd, WM_KEYDOWN, wParam, lParam1);
User32Extra.INSTANCE.SendMessageA(hWnd, WM_KEYDOWN, wParam, lParam0);
User32Extra.INSTANCE.SendMessageA(hWnd, WM_KEYDOWN, wParam, null);
}
}
}
I'm trying to send messages to key presses, looking for the right window handle but that message is not getting .... Why?((

Related

Turn off the monitor in windows

I need to turn off my monitor in code. I googled and found some code that should do it, but when I run this, nothing at all happens, and I just get a 0 WinAPI result. What am I doing wrong?
class Program
{
[DllImport("user32.dll")]
static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll")]
private static extern IntPtr GetDesktopWindow();
const int SC_MONITORPOWER = 0xF170;
const int WM_SYSCOMMAND = 0x0112;
const int MONITOR_OFF = 2;
static void Main(string[] args)
{
Console.WriteLine(
SendMessage(
GetDesktopWindow(),
WM_SYSCOMMAND,
(IntPtr) SC_MONITORPOWER,
(IntPtr) MONITOR_OFF));
Console.WriteLine("Hello World!");
}
}
From Fumbling around in the dark and stumbling across the wrong solution:
the desktop window is a very special window and as a rule should be avoided, since it won't behave like windows created by applications. In particular, the author tried to post a message to the desktop window. This used to work in the historically open world of the window manager, but security and robustness concerns have come to take priority over compatibility.
The real solution is to create your own window and send it the message, anything else is a hack.
If you don't mind hacks, at least try to find a suitable window:
[DllImport("user32.dll", SetLastError = false)]
public static extern IntPtr GetForegroundWindow();
[DllImport("user32.dll")]
static extern IntPtr PostMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);
const int SC_MONITORPOWER = 0xF170;
const int WM_SYSCOMMAND = 0x0112;
const int MONITOR_OFF = 2;
static void Main(string[] args)
{
IntPtr w;
for (; IntPtr.Zero == (w = GetForegroundWindow());) System.Threading.Thread.Sleep(1000);
PostMessage(w, WM_SYSCOMMAND, (IntPtr) SC_MONITORPOWER, (IntPtr) MONITOR_OFF);
}
And because it is a hack there are where times it might not work. The window you are borrowing might be destroyed before you post the message. You might not have the right to send messages to it (UAC). Or it might decide to not pass this message to DefWindowProc.
Another slightly better hack is to create a temporary window:
[DllImport("user32.dll")]
static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll")]
static extern int DestroyWindow(IntPtr hWnd);
[DllImport("user32.dll", SetLastError=true)]
public static extern IntPtr CreateWindowEx(uint dwExStyle, string lpClassName, IntPtr cap, uint dwStyle, int x, int y, int nWidth, int nHeight, IntPtr hWndParent, IntPtr hMenu, IntPtr hInstance, IntPtr lpParam);
const int SC_MONITORPOWER = 0xF170;
const int WM_SYSCOMMAND = 0x0112;
const int MONITOR_OFF = 2;
static void Main(string[] args)
{
IntPtr w = CreateWindowEx(0, "Button", IntPtr.Zero, 0, 0, 0, 0, 0, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);
if (w != IntPtr.Zero)
{
SendMessage(w, WM_SYSCOMMAND, (IntPtr) SC_MONITORPOWER, (IntPtr) MONITOR_OFF);
DestroyWindow(w);
}
}
This is still somewhat of a hack because it never actually pumps messages.

Why does a custom Window Procedure stop processing window messages?

I'm trying to configure a custom window procedure and it works. However, after a while, the window stops reacting to any input. It seems that the more rendering is going on in a scene, the sooner the window gets broken.
This even happens if my custom window procedure simply calls the default window.
Reproducer:
package com.example;
import com.sun.jna.Native;
import com.sun.jna.Pointer;
import com.sun.jna.platform.win32.BaseTSD;
import com.sun.jna.platform.win32.User32;
import com.sun.jna.platform.win32.WinDef.HWND;
import com.sun.jna.platform.win32.WinUser;
import com.sun.jna.win32.W32APIOptions;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.ProgressIndicator;
import javafx.stage.Stage;
import static com.sun.jna.platform.win32.WinUser.GWL_WNDPROC;
public class CustomWndProc {
public static void main(String[] args) {
CustomFrameApplication.launch(CustomFrameApplication.class, args);
}
public static class CustomFrameApplication extends Application {
#Override
public void start(Stage primaryStage) {
primaryStage.setScene(new Scene(new ProgressIndicator(ProgressIndicator.INDETERMINATE_PROGRESS)));
primaryStage.show();
HWND hwnd = new HWND();
hwnd.setPointer(User32.INSTANCE.GetActiveWindow().getPointer());
BaseTSD.LONG_PTR defaultWindowProc = User32.INSTANCE.GetWindowLongPtr(hwnd, GWL_WNDPROC);
WinUser.WindowProc windowProc = (hwnd1, uMsg, wParam, lParam) ->
User32Ex.INSTANCE.CallWindowProc(defaultWindowProc, hwnd1, uMsg, wParam, lParam);
User32Ex.INSTANCE.SetWindowLongPtr(hwnd, GWL_WNDPROC, windowProc);
}
}
public interface User32Ex extends User32 {
User32Ex INSTANCE = Native.load("user32", User32Ex.class, W32APIOptions.DEFAULT_OPTIONS);
Pointer SetWindowLongPtr(HWND hWnd, int nIndex, WindowProc wndProc);
LRESULT CallWindowProc(LONG_PTR proc, HWND hWnd, int uMsg, WPARAM uParam, LPARAM lParam);
}
}
Give it a few seconds or minutes and you won't be able to move, minimize, maximize or close the window anymore.
If you want guaranteed freeze, use a WebView instead of a ProgressIndicator:
WebView webView = new WebView();
webView.getEngine().load("https://www.google.com");
primaryStage.setScene(new Scene(webView));
I wondered if it has something to do that my code runs in the JavaFX Application thread (leading to some race condition) but I assume so does the default window procedure (how can I verify?).
I'm trying to build a JavaFX application that uses a custom frame.
Using JNA 5.5.0.
I think this is the right way to do it, but maybe I'm wrong..
I got the Information from:
Why my JNA using application doesn't react in a right way?
import com.sun.jna.LastErrorException;
import com.sun.jna.Native;
import com.sun.jna.platform.win32.BaseTSD;
import com.sun.jna.platform.win32.User32;
import com.sun.jna.platform.win32.WinDef;
import com.sun.jna.platform.win32.WinDef.HWND;
import com.sun.jna.win32.W32APIOptions;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.ProgressIndicator;
import javafx.stage.Stage;
public class CustomWndProc {
public static void main(String[] args) {
CustomFrameApplication.launch(CustomFrameApplication.class, args);
}
public static class CustomFrameApplication extends Application {
private BaseTSD.LONG_PTR baseWndProc;
public User32Ex.WNDPROC listener = new User32Ex.WNDPROC() {
public WinDef.LRESULT callback(HWND hWnd, int uMsg, WinDef.WPARAM uParam,
WinDef.LPARAM lParam) {
// TODO handle the window message
// calling the base WndProc
return User32Ex.INSTANCE.CallWindowProc(baseWndProc, hWnd, uMsg, uParam, lParam);
}
};
#Override
public void start(Stage primaryStage) {
primaryStage.setScene(new Scene(new ProgressIndicator(ProgressIndicator.INDETERMINATE_PROGRESS)));
primaryStage.show();
HWND hwnd = new HWND();
hwnd.setPointer(User32.INSTANCE.GetActiveWindow().getPointer());
this.baseWndProc = User32Ex.INSTANCE.GetWindowLongPtr(hwnd, User32Ex.GWL_WNDPROC);
User32Ex.INSTANCE.SetWindowLongPtr(hwnd, User32Ex.GWL_WNDPROC, this.listener);
}
}
public interface User32Ex extends User32 {
User32Ex INSTANCE = Native.load("user32", User32Ex.class, W32APIOptions.DEFAULT_OPTIONS);
interface WNDPROC extends StdCallCallback {
LRESULT callback(HWND hWnd, int uMsg, WPARAM uParam, LPARAM lParam);
}
LONG_PTR GetWindowLongPtr(HWND hWnd, int nIndex) throws LastErrorException;
LRESULT CallWindowProc(LONG_PTR proc, HWND hWnd, int uMsg, WPARAM uParam, WinDef.LPARAM lParam) throws LastErrorException;
LONG_PTR SetWindowLongPtr(HWND hWnd, int nIndex, WNDPROC wndProc) throws LastErrorException;
}
}

C# Outlook 2013 Add-In Keyboard Events

I'm working on a custom shortcut but I'm facing the problem, that the key events do not fire when outlook 2013 is focused (with 2007 & 2010 it's working fine). So far, I've tried different solutions. This one seems to be the best so far, the following code is a global hook.
[DllImport("user32.dll")]
static extern IntPtr SetWindowsHookEx(int idHook, LowLevelKeyboardProc callback, IntPtr hInstance, uint threadId);
[DllImport("user32.dll")]
static extern bool UnhookWindowsHookEx(IntPtr hInstance);
[DllImport("user32.dll")]
static extern IntPtr CallNextHookEx(IntPtr idHook, int nCode, int wParam, IntPtr lParam);
[DllImport("kernel32.dll")]
static extern IntPtr LoadLibrary(string lpFileName);
private delegate IntPtr LowLevelKeyboardProc(int nCode, IntPtr wParam, IntPtr lParam);
const int WH_KEYBOARD_LL = 13;
const int WM_KEYDOWN = 0x100;
private LowLevelKeyboardProc _proc = hookProc;
private static IntPtr hhook = IntPtr.Zero;
public void SetHook()
{
IntPtr hInstance = LoadLibrary("User32");
hhook = SetWindowsHookEx(WH_KEYBOARD_LL, _proc, hInstance, 0);
}
public static IntPtr hookProc(int code, IntPtr wParam, IntPtr lParam)
{
Debug.WriteLine("key event triggered");
//...
return CallNextHookEx(hhook, code, (int)wParam, lParam);
}

get all handles

How can I get all handles of a window via Win32? I found this code but I don't know how is it work!
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool EnumChildWindows(IntPtr hwndParent, EnumWindowsProc lpEnumFunc, IntPtr lParam);
private List<IntPtr> GetChildWindows(IntPtr parent)
{
List<IntPtr> result = new List<IntPtr>();
GCHandle listHandle = GCHandle.Alloc(result);
try
{
EnumWindowProc childProc = new EnumWindowProc(EnumWindow);
EnumChildWindows(parent, childProc, GCHandle.ToIntPtr(listHandle));
}
finally
{
if (listHandle.IsAllocated)
listHandle.Free();
}
return result;
}

How can I get the localized name of a 'special' windows folder (Recycle bin etc.)?

I'm trying to find out the 'correct' windows API for finding out the localized name of 'special' folders, specifically the Recycle Bin. I want to be able to prompt the user with a suitably localized dialog box asking them if they want to send files to the recycle bin or delete them directly.
I've found lots on the internet (and on Stackoverflow) about how to do the actual deletion, and it seems simple enough, I just really want to be able to have the text localized.
Read this article for code samples and usage:
http://www.codeproject.com/KB/winsdk/SpecialFolders.aspx
Also there is an article on MSDN that helps you Identify the Location of Special Folders with API Calls
I actually didn't find the CodeProject article terribly helpful, so I thought I'd answer this question with the actual code that I used to retrieve the localized name of the recycle bin.
This sample also tries to behave correctly with regard to freeing resources. Any comments are welcome, especially if you spot an error with my resource management!
public static string GetLocalizedRecycleBinName()
{
IntPtr relative_pidl, parent_ptr, absolute_pidl;
PInvoke.SHGetFolderLocation(IntPtr.Zero, PInvoke.CSIDL.BitBucket,
IntPtr.Zero, 0, out absolute_pidl);
try
{
PInvoke.SHBindToParent(absolute_pidl,
ref PInvoke.Guids.IID_IShellFolder,
out parent_ptr, out relative_pidl);
PInvoke.IShellFolder shell_folder =
Marshal.GetObjectForIUnknown(parent_ptr)
as PInvoke.IShellFolder;
// Release() for this object is called at finalization
if (shell_folder == null)
return Strings.RecycleBin;
PInvoke.STRRET strret = new PInvoke.STRRET();
StringBuilder sb = new StringBuilder(260);
shell_folder.GetDisplayNameOf(relative_pidl, PInvoke.SHGNO.Normal,
out strret);
PInvoke.StrRetToBuf(ref strret, relative_pidl, sb, 260);
string name = sb.ToString();
return String.IsNullOrEmpty(name) ? Strings.RecycleBin : name;
}
finally { PInvoke.ILFree(absolute_pidl); }
}
static class PInvoke
{
[DllImport("shell32.dll")]
public static extern int SHGetFolderLocation(IntPtr hwndOwner,
CSIDL nFolder, IntPtr hToken, uint dwReserved, out IntPtr ppidl);
[DllImport("shell32.dll")]
public static extern int SHBindToParent(IntPtr lpifq, [In] ref Guid riid,
out IntPtr ppv, out IntPtr pidlLast);
[DllImport("shlwapi.dll")]
public static extern Int32 StrRetToBuf(ref STRRET pstr, IntPtr pidl,
StringBuilder pszBuf, uint cchBuf);
[DllImport("shell32.dll")]
public static extern void ILFree([In] IntPtr pidl);
[ComImport]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
[Guid("000214E6-0000-0000-C000-000000000046")]
public interface IShellFolder
{
[PreserveSig]
Int32 CompareIDs(Int32 lParam, IntPtr pidl1, IntPtr pidl2);
void ParseDisplayName(IntPtr hwnd, IntPtr pbc, String pszDisplayName,
UInt32 pchEaten, out IntPtr ppidl, UInt32 pdwAttributes);
void EnumObjects(IntPtr hwnd, int grfFlags,
out IntPtr ppenumIDList);
void BindToObject(IntPtr pidl, IntPtr pbc, [In] ref Guid riid,
out IntPtr ppv);
void BindToStorage(IntPtr pidl, IntPtr pbc, [In] ref Guid riid,
out IntPtr ppv);
void CreateViewObject(IntPtr hwndOwner, [In] ref Guid riid,
out IntPtr ppv);
void GetAttributesOf(UInt32 cidl,
[MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 0)]
IntPtr[] apidl, ref uint rgfInOut);
void GetUIObjectOf(IntPtr hwndOwner, UInt32 cidl,
[MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 1)]
IntPtr[] apidl, [In] ref Guid riid, UInt32 rgfReserved,
out IntPtr ppv);
void GetDisplayNameOf(IntPtr pidl, SHGNO uFlags, out STRRET pName);
void SetNameOf(IntPtr hwnd, IntPtr pidl, string pszName,
int uFlags, out IntPtr ppidlOut);
}
public enum CSIDL
{
BitBucket = 0x000a,
}
public enum SHGNO
{
Normal = 0x0000, ForParsing = 0x8000,
}
[StructLayout(LayoutKind.Explicit, Size = 520)]
public struct STRRETinternal
{
[FieldOffset(0)] public IntPtr pOleStr;
[FieldOffset(0)] public IntPtr pStr;
[FieldOffset(0)] public uint uOffset;
}
[StructLayout(LayoutKind.Sequential)]
public struct STRRET
{
public uint uType;
public STRRETinternal data;
}
public class Guids
{
public static Guid IID_IShellFolder =
new Guid("{000214E6-0000-0000-C000-000000000046}");
}
}

Resources