Search code examples
javawinapijna

How to implement Win32 macro MAKEINTRESOURCE


Hi can you help with implementation macro MAKEINTRESOURCEW. When I view to the header file I found this:

#define MAKEINTRESOURCEW(i) ((LPWSTR)((ULONG_PTR)((WORD)(i))))

I need this functionality for my program where I am implementing the IContextMenu functionality to view explorer context menu. In all my items which I have tested I can get command string with function GetCommandString. But in one item I don't get the command string. And the item is Edit with Notepad++. So I have found in documentation that in the lpverb in structure CMINVOKECOMMANDINFOEX use the id of the item with macro MAKEINTRESOURCE.

But now I don't know how to invoke the command with id of this item and replace this macro.

This is my java code:

Memory numberVerb = new Memory(Native.POINTER_SIZE);
numberVerb.setLong(0, 109);

CMINVOKECOMMANDINFOEX cmInvokeCommandEx = new CMINVOKECOMMANDINFOEX();          
cmInvokeCommandEx.cbSize = cmInvokeCommandEx.size();                            
cmInvokeCommandEx.fMask = 0x00004000;                                           
cmInvokeCommandEx.hwnd = null;                                                                         
cmInvokeCommandEx.lpVerbW = new WTypes.LPWSTR(numberVerb);                      
cmInvokeCommandEx.lpVerb = new WTypes.LPSTR(verb);                              
cmInvokeCommandEx.lpParameters = null;                                          
cmInvokeCommandEx.lpParametersW = null;                                         
cmInvokeCommandEx.lpDirectory = new WTypes.LPSTR(parentDir.getAbsolutePath());  
cmInvokeCommandEx.lpDirectoryW = new WTypes.LPWSTR(parentDir.getAbsolutePath());
cmInvokeCommandEx.nShow = 5;                                                    
cmInvokeCommandEx.dwHotKey = 0;                                                 
cmInvokeCommandEx.hIcon = Pointer.NULL;                                         
cmInvokeCommandEx.lpTitle = null;                                               
cmInvokeCommandEx.lpTitleW = null;                                              
cmInvokeCommandEx.ptInvoke = point;                                             
cmInvokeCommandEx.write();                                                      
                                                                            
hResult = contextMenu2.InvokeCommand(cmInvokeCommandEx.getPointer());           

Solution

  • I have found the solution of this problem. I am upgrading my code for this:

    result = User32Ex.INSTANCE.GetMenuItemInfoW(hMenu.getPointer(), 4, true, menuiteminfow.getPointer());
    if (!result.booleanValue()) {
       int errorCode = Native.getLastError();
       System.out.println("Error Code: " + errorCode);
       return false;
    }
    
    CMINVOKECOMMANDINFOEX cmInvokeCommandEx = new CMINVOKECOMMANDINFOEX();          
    cmInvokeCommandEx.cbSize = cmInvokeCommandEx.size();                            
    cmInvokeCommandEx.fMask = 0x00004000;                                           
    cmInvokeCommandEx.hwnd = null;                                                                         
    cmInvokeCommandEx.lpVerbW = new WTypes.LPWSTR(new Pointer(menuiteminfow.wId - 1));                      
    cmInvokeCommandEx.lpVerb = new WTypes.LPSTR(new Pointer(menuiteminfow.wId - 1));                              
    cmInvokeCommandEx.lpParameters = null;                                          
    cmInvokeCommandEx.lpParametersW = null;                                         
    cmInvokeCommandEx.lpDirectory = new WTypes.LPSTR(parentDir.getAbsolutePath());  
    cmInvokeCommandEx.lpDirectoryW = new WTypes.LPWSTR(parentDir.getAbsolutePath());
    cmInvokeCommandEx.nShow = 5;                                                    
    cmInvokeCommandEx.dwHotKey = 0;                                                 
    cmInvokeCommandEx.hIcon = Pointer.NULL;                                         
    cmInvokeCommandEx.lpTitle = null;                                               
    cmInvokeCommandEx.lpTitleW = null;                                              
    cmInvokeCommandEx.ptInvoke = point;                                             
    cmInvokeCommandEx.write();                                                      
                                                                            
    hResult = contextMenu2.InvokeCommand(cmInvokeCommandEx.getPointer());
    

    The key change is that when you want invoke command threw the id and not the command you must define the wId to the lpVerb variable and not to the lpVerbW or both. Because the lpVerbW is for the unicode string command only.