5
\$\begingroup\$

I've started some experimentation in Java and LWJGL (via Slick), and it seems very solid. However, I have some legacy code that requires a HWND integer as a parameter. I'm not sure how I'd be able to get this, or if LWJGL would be able to report this for me. Any help?

\$\endgroup\$
4
\$\begingroup\$

An hWnd is a Windows API window handle. Here's an example that shows how to get it for an AWT component and does some other stuff (from here):

JNIEXPORT jlong JNICALL Java_test_Transparency_getWindowHandle
  (JNIEnv * env, jclass cls, jobject component)
{
   JAWT awt;
   JAWT_DrawingSurface* ds;
   JAWT_DrawingSurfaceInfo* dsi;
   JAWT_Win32DrawingSurfaceInfo* dsi_win;
   jint dsLock;
   jboolean result = JNI_FALSE;

   // Get the AWT
   awt.version = JAWT_VERSION_1_4;
   result = JAWT_GetAWT(env, &awt);

   if ( result == JNI_FALSE )
   {
      printf( "%s:%i -  JAWT_GetAWT() failed.\n", __FILE__, __LINE__ );
      return 0;
   }

   // Get the drawing surface
   ds = awt.GetDrawingSurface(env, component);

   if ( ds == NULL )
   {
      printf( "%s:%i -  GetDrawingSurface() failed.\n", __FILE__, __LINE__ );
      return 0;
   }

   dsLock = ds->Lock(ds);

   // Get the drawing surface info
   dsi = ds->GetDrawingSurfaceInfo(ds);

   // Get the platform-specific drawing info
   dsi_win = (JAWT_Win32DrawingSurfaceInfo*)dsi->platformInfo;

   HWND handle = dsi_win->hwnd;

   ds->FreeDrawingSurfaceInfo(dsi);
   ds->Unlock(ds);
   awt.FreeDrawingSurface(ds);

   return (jlong)handle;
}
\$\endgroup\$
2
  • \$\begingroup\$ I'll take a look and see if LWJGL uses AWT, I'm not too sure (and I'm not very familiar with LWJGL as of yet). \$\endgroup\$ – ThatsGobbles Dec 14 '10 at 1:13
  • \$\begingroup\$ But hopefully it gives you an idea. Get the drawing area, then the platform window info, then the hWnd. \$\endgroup\$ – Matthew Read Dec 14 '10 at 1:18
1
\$\begingroup\$

I actually coded this up before I noticed that long org.lwjgl.WindowsSysImplementation.getHwnd() (also private) contains essentially the same code (Although it runs it as a privileged action). Note that the answer from Matthew Read does (what appears to be at first glance, anyway) the same thing as long org.lwjgl.opengl.WindowsDisplay(Canvas)

I figured this was cleaner because it uses reflection to get the HWND used directly by LWJGL, instead of guessing the window/canvas/etc/ it uses, as well as not being native, so you can reduce native errors as much as possible. I didn't put much error checking into this, but you should be able to edit it to have as much or as little as you want.

protected long getLWJGLHwnd() throws Exception {
    //long org.lwjgl.opengl.WindowsDisplay.getHwnd()
    try {
        Method methImpl = Display.class.getDeclaredMethod("getImplementation");
        methImpl.setAccessible(true); //Make it accessible, since it is private
        Object impl = methImpl.invoke(null); //Static with no parameters, type not visible anyway so keep as object
        Class clsWinDisplay = Class.forName("org.lwjgl.opengl.WindowsDisplay"); //Not visible, so can't use constant WindowsDisplay.class
        if(!clsWinDisplay.isInstance(impl)) throw new Exception("The current platform must be Windows!"); //Throw on non-windows host
        Method methHwnd = clsWinDisplay.getDeclaredMethod("getHwnd");
        methHwnd.setAccessible(true);
        Long value = (Long) methHwnd.invoke(impl);
        return value;
    } catch (ClassNotFoundException | NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException e){
        e.printStackTrace();
        return 0;
    }
}

If it means anything to anyone, before I found I could do this, I was just using EnumWindows to cycle through the windows, and get the one with the right PID/name combination, but thats another question.

\$\endgroup\$
1
  • 1
    \$\begingroup\$ Hey! Welcome to GDSE! I edited your answer to make it 'time agnostic'. It does not matter that the question is old, if the answer is relevant, it's all good. And referring to other answers as "above, below, accepted" can lead to confusion if your answer gets popular and/or accepted :) \$\endgroup\$ – Vaillancourt Nov 19 '16 at 15:43

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.