用JNI调用C去获取窗口WINDOW HANDLE ID,使用C++的时候老是出错,不知道是什么地方错了
------------------------------------------------------
//MyWindow.java
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.awt.peer.*;
import sun.awt.*;public class MyWindow extends Canvas
{
static
{
// Load the library that contains the JNI code.
System.loadLibrary("MyWindow");
} // native entry point for initializing the IE control.
public native static void initialize(int hwnd, String strURL); // native entry point for resizing
public native static void resizeControl(int hwnd, int nWidth, int nHeight);
public native static int getNativeWindowHandle(Canvas canvas);
public void addNotify()
{
super.addNotify();
m_hWnd = getNativeWindowHandle(this);
initialize(m_hWnd, m_strURL);
} String m_strURL = "http://www.163.com";
int m_hWnd = 0; public static void main( String[] argv )
{
Frame f = new Frame();
f.setLayout(new BorderLayout());
f.setTitle("Internet Explorer inside Java Canvas");
MyWindow w = new MyWindow();
if(argv.length>0)
w.m_strURL = argv[0]; String strText = "URL:" + w.m_strURL;
f.add(w,BorderLayout.CENTER);
f.add(new Label(strText),BorderLayout.NORTH);
f.setBounds(300,300,500,300);
f.setVisible(true);
} public void setSize( int width, int height )
{
super.setSize(width,height);
if(m_hWnd!=0)
resizeControl(m_hWnd, width, height);
} public void setSize( Dimension d )
{
super.setSize(d);
if(m_hWnd!=0)
resizeControl(m_hWnd, d.width, d.height);
} public void setBounds( int x, int y, int width, int height )
{
super.setBounds(x,y,width,height);
if(m_hWnd!=0)
resizeControl(m_hWnd, width, height);
} public void setBounds( Rectangle r )
{
super.setBounds(r);
if(m_hWnd!=0)
resizeControl(m_hWnd, r.width, r.height);
}
}
--------------------------------------------------------------
-----------------------
//MyWindow.cpp
#include <jni.h>
#include <jawt.h>
#include <afxwin.h>
#include <windows.h>
#include "MyWindow.h"
#include "jawt_md.h"
//#include <assert.h>
#include <process.h>// Includes for ATL
#pragma comment(lib,"atl.lib")
#include <atldef.h>
#define _ATL_DLL_IMPL
#include <atliface.h>
#include <atlbase.h>
#include <exdisp.h>// Structure for Thread Parameters.
typedef struct {
char szURL[1024];
HWND hwnd;
} ThreadParam;// Helper functions.
VOID CreateIEControl(ThreadParam *);
static void WINAPIV StartATL(LPVOID);
JNIEXPORT jint JNICALL Java_MyWindow_getNativeWindowHandle
(JNIEnv *env, jobject jobj, jobject window)
{JAWT awt;
awt.version = JAWT_VERSION_1_3;
jboolean result = JAWT_GetAWT(env, &awt);if (result == JNI_FALSE)
return 0;JAWT_DrawingSurface* ds = awt.GetDrawingSurface(env, window);if (ds == 0)
return 0;jint lock = ds->Lock(ds);if ((lock & JAWT_LOCK_ERROR) != 0)
return 0;JAWT_DrawingSurfaceInfo* dsi = ds->GetDrawingSurfaceInfo(ds);if (dsi == 0)
return 0;JAWT_Win32DrawingSurfaceInfo* dsiwin = (JAWT_Win32DrawingSurfaceInfo*) dsi->platformInfo;jint ret = reinterpret_cast<jint>(dsiwin->hwnd);ds->FreeDrawingSurfaceInfo(dsi);
ds->Unlock(ds);
awt.FreeDrawingSurface(ds);return ret;
}// native method for initializing the control.
JNIEXPORT void JNICALL Java_MyWindow_initialize
(JNIEnv *pEnv, jobject, jint hwndIn, jstring string)
{
// Fill up the params.
const char *str = pEnv->GetStringUTFChars(string, 0);
ThreadParam *pThreadParam = new ThreadParam;
pThreadParam->hwnd = (HWND) hwndIn;
strcpy(pThreadParam->szURL,str);
pEnv->ReleaseStringUTFChars(string, str); // Launch the Thread.
_beginthread(StartATL, 0, pThreadParam);
}// Thread for creating the control
void WINAPIV StartATL(LPVOID lpVoid)
{
ThreadParam *pThreadParam = (ThreadParam *)lpVoid;
CreateIEControl(pThreadParam);
delete pThreadParam;
MSG msg;
// Windows message loop.
while(GetMessage(&msg, NULL, NULL, NULL))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}// Creates IE control
VOID CreateIEControl(ThreadParam *pThreadParam)
{
AtlAxWinInit();
printf("Create AtlAxWin Begin...[0x%x][%s]\n",pThreadParam->hwnd,pThreadParam->szURL);
// In the 2nd Param you can use ProgID or UUID of any activex control.
HWND hwndChild = ::CreateWindow("AtlAxWin",
"http://www.microsoft.com",
WS_CHILD|WS_VISIBLE,
0,0,0,0,
pThreadParam->hwnd,NULL,
::GetModuleHandle(NULL),
NULL); IUnknown *pUnk = NULL;
AtlAxGetControl(hwndChild,&pUnk);
printf("Create AtlAxWin Done...[0x%x]\n",pUnk); // get an interface to set the URL.
CComPtr<IWebBrowser2> spBrowser;
pUnk->QueryInterface(IID_IWebBrowser2, (void**)&spBrowser);
if (spBrowser)
{
CComVariant ve;
CComVariant vurl(pThreadParam->szURL);
#pragma warning(disable: 4310) // cast truncates constant value
spBrowser->put_Visible(VARIANT_TRUE);
#pragma warning(default: 4310) // cast truncates constant value
spBrowser->Navigate2(&vurl, &ve, &ve, &ve, &ve);
}
}// native method for handling resizes.
JNIEXPORT void JNICALL Java_MyWindow_resizeControl
(JNIEnv *, jobject, jint hwndIn, jint width, jint height)
{
HWND hwnd = (HWND) hwndIn;
RECT rc;
if(hwnd!=NULL)
{
::GetWindowRect(hwnd,&rc);
HWND hwndChild = GetWindow(hwnd, GW_CHILD);
printf("got resize (0x%x,%d,%d)\n",hwndChild,width,height);
::SetWindowPos(hwndChild,NULL,0,0,rc.right-rc.left,rc.bottom-rc.top,SWP_NOZORDER|SWP_NOACTIVATE|SWP_SHOWWINDOW|SWP_NOMOVE);
}
}
--------------------------------我按照上面的做了.在java里面报这个错是什么意思,要怎么解决呢
java.lang.UnsatisfiedLinkError: getNativeWindowHandle
at MyWindow.getNativeWindowHandle(Native Method)
at MyWindow.addNotify(MyWindow.java:27)
at java.awt.Container.addNotify(Container.java:2049)
at java.awt.Window.addNotify(Window.java:418)
at java.awt.Frame.addNotify(Frame.java:482)
at java.awt.Window.show(Window.java:459)
at java.awt.Component.show(Component.java:1133)
at java.awt.Component.setVisible(Component.java:1088)
at MyWindow.main(MyWindow.java:48)
------------------------------------------------------
//MyWindow.java
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.awt.peer.*;
import sun.awt.*;public class MyWindow extends Canvas
{
static
{
// Load the library that contains the JNI code.
System.loadLibrary("MyWindow");
} // native entry point for initializing the IE control.
public native static void initialize(int hwnd, String strURL); // native entry point for resizing
public native static void resizeControl(int hwnd, int nWidth, int nHeight);
public native static int getNativeWindowHandle(Canvas canvas);
public void addNotify()
{
super.addNotify();
m_hWnd = getNativeWindowHandle(this);
initialize(m_hWnd, m_strURL);
} String m_strURL = "http://www.163.com";
int m_hWnd = 0; public static void main( String[] argv )
{
Frame f = new Frame();
f.setLayout(new BorderLayout());
f.setTitle("Internet Explorer inside Java Canvas");
MyWindow w = new MyWindow();
if(argv.length>0)
w.m_strURL = argv[0]; String strText = "URL:" + w.m_strURL;
f.add(w,BorderLayout.CENTER);
f.add(new Label(strText),BorderLayout.NORTH);
f.setBounds(300,300,500,300);
f.setVisible(true);
} public void setSize( int width, int height )
{
super.setSize(width,height);
if(m_hWnd!=0)
resizeControl(m_hWnd, width, height);
} public void setSize( Dimension d )
{
super.setSize(d);
if(m_hWnd!=0)
resizeControl(m_hWnd, d.width, d.height);
} public void setBounds( int x, int y, int width, int height )
{
super.setBounds(x,y,width,height);
if(m_hWnd!=0)
resizeControl(m_hWnd, width, height);
} public void setBounds( Rectangle r )
{
super.setBounds(r);
if(m_hWnd!=0)
resizeControl(m_hWnd, r.width, r.height);
}
}
--------------------------------------------------------------
-----------------------
//MyWindow.cpp
#include <jni.h>
#include <jawt.h>
#include <afxwin.h>
#include <windows.h>
#include "MyWindow.h"
#include "jawt_md.h"
//#include <assert.h>
#include <process.h>// Includes for ATL
#pragma comment(lib,"atl.lib")
#include <atldef.h>
#define _ATL_DLL_IMPL
#include <atliface.h>
#include <atlbase.h>
#include <exdisp.h>// Structure for Thread Parameters.
typedef struct {
char szURL[1024];
HWND hwnd;
} ThreadParam;// Helper functions.
VOID CreateIEControl(ThreadParam *);
static void WINAPIV StartATL(LPVOID);
JNIEXPORT jint JNICALL Java_MyWindow_getNativeWindowHandle
(JNIEnv *env, jobject jobj, jobject window)
{JAWT awt;
awt.version = JAWT_VERSION_1_3;
jboolean result = JAWT_GetAWT(env, &awt);if (result == JNI_FALSE)
return 0;JAWT_DrawingSurface* ds = awt.GetDrawingSurface(env, window);if (ds == 0)
return 0;jint lock = ds->Lock(ds);if ((lock & JAWT_LOCK_ERROR) != 0)
return 0;JAWT_DrawingSurfaceInfo* dsi = ds->GetDrawingSurfaceInfo(ds);if (dsi == 0)
return 0;JAWT_Win32DrawingSurfaceInfo* dsiwin = (JAWT_Win32DrawingSurfaceInfo*) dsi->platformInfo;jint ret = reinterpret_cast<jint>(dsiwin->hwnd);ds->FreeDrawingSurfaceInfo(dsi);
ds->Unlock(ds);
awt.FreeDrawingSurface(ds);return ret;
}// native method for initializing the control.
JNIEXPORT void JNICALL Java_MyWindow_initialize
(JNIEnv *pEnv, jobject, jint hwndIn, jstring string)
{
// Fill up the params.
const char *str = pEnv->GetStringUTFChars(string, 0);
ThreadParam *pThreadParam = new ThreadParam;
pThreadParam->hwnd = (HWND) hwndIn;
strcpy(pThreadParam->szURL,str);
pEnv->ReleaseStringUTFChars(string, str); // Launch the Thread.
_beginthread(StartATL, 0, pThreadParam);
}// Thread for creating the control
void WINAPIV StartATL(LPVOID lpVoid)
{
ThreadParam *pThreadParam = (ThreadParam *)lpVoid;
CreateIEControl(pThreadParam);
delete pThreadParam;
MSG msg;
// Windows message loop.
while(GetMessage(&msg, NULL, NULL, NULL))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}// Creates IE control
VOID CreateIEControl(ThreadParam *pThreadParam)
{
AtlAxWinInit();
printf("Create AtlAxWin Begin...[0x%x][%s]\n",pThreadParam->hwnd,pThreadParam->szURL);
// In the 2nd Param you can use ProgID or UUID of any activex control.
HWND hwndChild = ::CreateWindow("AtlAxWin",
"http://www.microsoft.com",
WS_CHILD|WS_VISIBLE,
0,0,0,0,
pThreadParam->hwnd,NULL,
::GetModuleHandle(NULL),
NULL); IUnknown *pUnk = NULL;
AtlAxGetControl(hwndChild,&pUnk);
printf("Create AtlAxWin Done...[0x%x]\n",pUnk); // get an interface to set the URL.
CComPtr<IWebBrowser2> spBrowser;
pUnk->QueryInterface(IID_IWebBrowser2, (void**)&spBrowser);
if (spBrowser)
{
CComVariant ve;
CComVariant vurl(pThreadParam->szURL);
#pragma warning(disable: 4310) // cast truncates constant value
spBrowser->put_Visible(VARIANT_TRUE);
#pragma warning(default: 4310) // cast truncates constant value
spBrowser->Navigate2(&vurl, &ve, &ve, &ve, &ve);
}
}// native method for handling resizes.
JNIEXPORT void JNICALL Java_MyWindow_resizeControl
(JNIEnv *, jobject, jint hwndIn, jint width, jint height)
{
HWND hwnd = (HWND) hwndIn;
RECT rc;
if(hwnd!=NULL)
{
::GetWindowRect(hwnd,&rc);
HWND hwndChild = GetWindow(hwnd, GW_CHILD);
printf("got resize (0x%x,%d,%d)\n",hwndChild,width,height);
::SetWindowPos(hwndChild,NULL,0,0,rc.right-rc.left,rc.bottom-rc.top,SWP_NOZORDER|SWP_NOACTIVATE|SWP_SHOWWINDOW|SWP_NOMOVE);
}
}
--------------------------------我按照上面的做了.在java里面报这个错是什么意思,要怎么解决呢
java.lang.UnsatisfiedLinkError: getNativeWindowHandle
at MyWindow.getNativeWindowHandle(Native Method)
at MyWindow.addNotify(MyWindow.java:27)
at java.awt.Container.addNotify(Container.java:2049)
at java.awt.Window.addNotify(Window.java:418)
at java.awt.Frame.addNotify(Frame.java:482)
at java.awt.Window.show(Window.java:459)
at java.awt.Component.show(Component.java:1133)
at java.awt.Component.setVisible(Component.java:1088)
at MyWindow.main(MyWindow.java:48)
出错。即使是返回一个数字,也不会返回成功。我对C++了解不多,比较恐慌。不得不用JNI