2013-03-25 30 views
0

我试图从DLL D2D1.dll映射函数D2D1CreateFactory。从那里我想创建一个Direct2D Java映射,但这是无关紧要的。我至今有这样的:来自D2D1的Java JNA映射D2D1CreateFactory

public WinNT.HRESULT D2D1CreateFactory(int factoryType, REFIID riid, ID2D1Factory.ByReference ppIFactory); 

的ID2D1Factory看起来是这样的:

public class ID2D1Factory extends IUnknown { 

    public ID2D1Factory() { } 

    public ID2D1Factory(Pointer pvInstance) { 
     super(pvInstance); 
    } 

} 

当我尝试使用下面的代码来运行我的代码,“java.lang.Error的:无效的内存访问”是抛出(打开JNA.setProtected()时)。

的代码运行:

ID2D1Factory.ByReference ref= new ID2D1Factory.ByReference(); 
D2D1.INSTANCE.D2D1CreateFactory(0, new REFIID(new IID("06152247-6f50-465a-9245-118bfd3b6007").toByteArray()), ref); 

我不知道为什么。有什么我做错了吗?

编辑:感谢technomage我能够得到正确的方法声明。该方法应该声明如下:

public WinNT.HRESULT D2D1CreateFactory(int factoryType, REFIID riid, D2D1_FACTORY_OPTIONS opts, PointerByReference pref); 

的D2D1_FACTORY_OPTIONS结构映射如下:

public static class D2D1_FACTORY_OPTIONS extends Structure { 
    public int debugLevel; 
    protected List<String> getFieldOrder() { 
     return Arrays.asList(new String[] { "debugLevel" }); 
    } 
    public D2D1_FACTORY_OPTIONS() {} 
    public D2D1_FACTORY_OPTIONS(int size) { 
     super(new Memory(size)); 
    } 
    public D2D1_FACTORY_OPTIONS(Pointer memory) { 
     super(memory); 
     read(); 
    } 
} 

最后,该代码段调用的方法:

D2D1_FACTORY_OPTIONS opts = new D2D1_FACTORY_OPTIONS(); 
PointerByReference pp = new PointerByReference(); 
D2D1.INSTANCE.D2D1CreateFactory(0, new REFIID(new IID("06152247-6f50-465a-9245-118bfd3b6007").toByteArray()), opts, pp); 

回答

2

this referenceD2D1CreateFactory需要指针类型作为第三和第四个参数(您只声明了三个参数)。

假设您插入选项指针(简单的struct *),您的最终参数需要为PointerByReference,因为该函数将“返回”您提供的地址中的指针值。

然后可以使用PointerByReference.getValue()初始化新ID2D1Factory实例(在这种情况下,Structure.ByReference是多余的,因为默认情况下,所有结构作为函数参数为struct *由JNA除非另有明确定义处理)。

public WinNT.HRESULT D2D1CreateFactory(int factoryType, REFIID riid, D2D1_FACTORY_OPTIONS options, ID2D1Factory ppIFactory); 

public class D2D1_FACTORY_OPTIONS extends Structure { ... } 

D2D1_FACTORY_OPTIONS options = ...; 
PointerByReference pref = new PointerByReference(); 

D2D1.INSTANCE.D2D1CreateFactory(0, new REFIID(...), options, pref); 
ID2D1Factory factory = new ID2D1Factory(pref.getValue()); 

而且不要忘记调用Structure.read()ID2D1Factory(Pointer)构造函数。

+0

非常感谢。我会试试这个结果并回来告诉其他用户。 – 2013-03-25 18:53:08