SVN8.COM - SVN中文技术网

投递文章 投稿指南 SVN中文技术网公告:技术交流诚聘优秀版主最新公告
搜索: 您的位置主页>JAVA技术>Socket编程>Java调用Delphi DLL实例(直接调和通过C++调两种方法)

Java调用Delphi DLL实例(直接调和通过C++调两种方法)

SVN技术网 www.svn8.com 2008-09-24 22:26:58   来源:   作者:  评论:0 点击:
这段时间客户在上一个触摸屏查询的项目,这个项目是包给另一个公司做的,但里面的一些业务逻辑需要用到我们原有的一个DLL,于是就有了这次Java和Delphi的邂逅。。。

     关于Delphi的DLL,先前在VB、PB这些开发工具中调用都是没有问题的,但是在Java中还没有做过,于是先请教了一下Mr Google,据说是直接调可能有问题,最好在中间用C++转一下,下面就先讲Java->C++->Delphi这种方法:

一、Java->C++->Delphi

1、Delphi中的代码很简单:

 

  1. function search(name: pchar): pchar; stdcall;
  2. begin
  3.   result := pchar('hello '+name);
  4. end;
  5. exports
  6.   search;

2、Java中新建一个类DllTest

  1. public class DllTest {
  2.     public native static String get(String name);   
  3.       
  4.     static {   
  5.         System.loadLibrary("DllTest");   
  6.     }   
  7.   
  8.         public static void main(String[] args) {   
  9.         // TODO 
  10.             DllTest test = new DllTest();    
  11.             String ret = test.get("yf");
  12.             System.out.println(ret);
  13.             System.out.println("success!!");   
  14.     }   
  15. }

编译生成class文件后,到命令行,该文件所在目录

  javah -classpath . -jni DllTest

生成DllTest.h头文件,这个在C++中要用的

 

3、接下来就该C++出场了

首先在C++中新建一个DLL的工程DllTest,接着把刚才生成的DllTest.h、jni.h(jdkinclude)、jni_md.h(jdkincludewin32)、StdAfx.h(代码后附)都拷到DllTest目录下面,DllTest.h的代码如下:

  1. /* DO NOT EDIT THIS FILE - it is machine generated */
  2. #include "jni.h"
  3. /* Header for class DllTest */
  4. #ifndef _Included_DllTest
  5. #define _Included_DllTest
  6. #ifdef __cplusplus
  7. extern "C" {
  8. #endif
  9. /*
  10.  * Class:     DllTest
  11.  * Method:    get
  12.  * Signature: (Ljava/lang/String;)Ljava/lang/String;
  13.  */
  14. JNIEXPORT jstring JNICALL Java_DllTest_get
  15.   (JNIEnv *, jclass, jstring Name);
  16. #ifdef __cplusplus
  17. }
  18. #endif
  19. #endif

StdAfx.h代码如下:

  1. // stdafx.h : include file for standard system include files,
  2. //  or project specific include files that are used frequently, but
  3. //      are changed infrequently
  4. //
  5. #if !defined(AFX_STDAFX_H__AEAE6431_AB02_4D9C_84D7_11491AAF82FF__INCLUDED_)
  6. #define AFX_STDAFX_H__AEAE6431_AB02_4D9C_84D7_11491AAF82FF__INCLUDED_
  7. #if _MSC_VER > 1000
  8. #pragma once
  9. #endif // _MSC_VER > 1000
  10. // Insert your headers here
  11. #define WIN32_LEAN_AND_MEAN     // Exclude rarely-used stuff from Windows headers
  12. #include <windows.h>
  13. // TODO: reference additional headers your program requires here
  14. //{{AFX_INSERT_LOCATION}}
  15. // Microsoft Visual C++ will insert additional declarations immediately before the previous line.
  16. #endif // !defined(AFX_STDAFX_H__AEAE6431_AB02_4D9C_84D7_11491AAF82FF__INCLUDED_)

新建一个DT.cpp文件,代码如下:

 

  1. #include "StdAfx.h" 
  2. #include "stdlib.h" 
  3. #include "DllTest.h" 
  4. HINSTANCE hDLL;
  5. typedef char* (__stdcall *SEARCH)(const char* name);
  6. SEARCH search;
  7.  jstring   windowsToJstring(   JNIEnv*   env,  const char*   str   )   
  8.   {   
  9. /*      AFX_MANAGE_STATE(AfxGetStaticModuleState());   */
  10.       jstring   rtn   =   0;   
  11.       int   slen   =   strlen(str);   
  12.       wchar_t*   buffer   =   0;   
  13.       if(   slen   ==   0   )   
  14.           rtn   =   env->NewStringUTF(str);   //UTF   ok   since   empty   string    
  15.       else   
  16.       {   
  17.           int   length   =   MultiByteToWideChar(   CP_ACP,   0,   (LPCSTR)str,   slen,   NULL,   0   );   
  18.           buffer   =   (wchar_t*)malloc(   length*2   +   1   );   
  19.           if(   MultiByteToWideChar(   CP_ACP,   0,   (LPCSTR)str,   slen,   (LPWSTR)buffer,   length   )   >0   )   
  20.               rtn   =   env->NewString(   (jchar*)buffer,   length   );   
  21.       }   
  22.       if(   buffer   )   
  23.         free(   buffer   );   
  24.       return   rtn;   
  25.   }
  26. // This is an example of an exported function. 
  27. jstring JNICALL Java_DllTest_get(JNIEnv *env, jobject cl, jstring Name)
  28. {
  29.     char buf[6]= "error"
  30.     const char* name; 
  31.     const char* ret;
  32.     name = env->GetStringUTFChars(Name, NULL); 
  33.     jstring err = env->NewStringUTF(buf);
  34.     
  35.     if (NULL == (hDLL = LoadLibrary("simple.dll"))){
  36.         MessageBox(0,"Error to load simple.dll!","标题",MB_OKCANCEL );
  37.         return err;
  38.     }
  39.     search = (SEARCH)GetProcAddress(HMODULE(hDLL),"search"); 
  40.     if (FARPROC(search) == FARPROC(NULL)){
  41.         MessageBox(0,"Error to get procedure's address!","标题",MB_OKCANCEL );
  42.         return err;
  43.     }
  44.     ret = search(name);
  45.   return env->NewStringUTF(ret); 
  46. //    return windowsToJstring(env,ret);
  47. }

 windowsToJstring这个函数是为了解决中文乱码的问题

 

用Release生产DllTest.dll文件,并拷贝到jdk的bin目录,就可以用DllTest.class测试了;

 

 

二、Java->Delphi

之后,又发现直接调也可以成功,不解。。。

Delphi的Dll还是同一个,另外还需要JNativeCpp.dll和JNative.jar

 

Java的代码修改如下:

  1.     public static void main(String[] args) {
  2.         TestNative test = new TestNative();
  3.         JNative jn = null;
  4.         String str = "";
  5.         try {
  6.             jn = new JNative("simple","search");
  7.             jn.setRetVal(Type.STRING);
  8.             jn.setParameter(0,Type.STRING,"yf");
  9.             jn.invoke();
  10.             str = jn.getRetVal();
  11.             System.out.println(str);
  12.         } catch (NativeException e) {
  13.             e.printStackTrace();
  14.         } catch (IllegalAccessException e) {
  15.             e.printStackTrace();
  16.         }finally{
  17.             if(null != jn){
  18.                 try {
  19.                     jn.dispose();//
  20.                     jn = null;
  21.                 } catch (NativeException e) {
  22.                     jn = null;
  23.                 } catch (IllegalAccessException e) {
  24.                     jn = null;
  25.                 }
  26.             }
  27.         }
  28.     }

这样也是调用成功的!



技术交流 录入:SVN中文技术网[www.svn8.com]
Tags:  
责任编辑:
  • 请文明参与讨论,禁止漫骂攻击。 用户名:新注册) 密码: 匿名:
    评论总数:0 [ 查看全部 ] 网友评论
    关于我们 - 联系我们 - 广告服务 - RSS订阅 - 网站地图 - 返回顶部