Question

There are several ways that Andorid aka-native code (Java code) could be integrated into Xamarin project. Official ways are listed in this article.

We are trying to use a Java Library Binding approach discribed in the article. Our test andoid library is published on Github for this question specifically.

We've created it in Android Developer tools setting it as Java Android Library. It is built in Eclipse into a .jar format that tutorial on Xamarin site assumes to be sufficient.

If we are trying to bind .jar into our project in Visual Studio, the Object Explorer will show us the binding asseblie's namespace, but in code, even though the assembly is referenced, we can't access the methods and classes in the namespace, decleared in our test java android lib..

On the other hand, when we take almost any .jar, which is an android library on the internet (for example this one), we can bind it and access it's methods without a problem.

Please compare two .jar and if possible, let me know what is wrong with our test android library on github, that causes our namespace to be unavailable from code.

Was it helpful?

Solution

I read the same Binding a Java Library article you did, went through the instructions, and had no build errors. When I attempted to use the classes from my jar file, intellisense was not recognizing anything. Then I read the follow-on article on API Metadata Reference. This got me thinking that perhaps I should try editing the Transforms/Metadata.xml file. After editing that briefly to include a rename of the package, Visual studio allowed (after a compile) a reference to a class from the jar file. I then attempted to call a method from the class, and again, got another compiler error. So, I went back into the Metadata.xml file and added an entry to rename the method in question. I edited my code to call the renamed method, and Visual Studio compiled fine. I integrated this call into a unit test case, and it passed!

From my reading, it didn't seem necessary to edit the Metadata.xml file, but at least in my experience it seemed necessary. It uses XPATH on the obj/Release/api.xml file (as stated in API Metadata Reference). From that article there were examples for renaming both package & method names, so it wasn't much work for me to insert into my Metadata.xml file. In addition, I downloaded the OsmBindingDroidExample from the Binding a Java Library article and checked out their Metadata.xml file as well.

Here's my XML for reference as well:

<metadata>
  <attr path="/api/package[@name='com.abc.def']" name="managedName">MyRenamedPackage</attr>
  <attr path="/api/package[@name='com.abc.def']/class[@name='MyClass']/method[@name='originalJavaMethod']" name="managedName">RenamedDotNetMethod</attr>
</metadata>

So, now in my .NET code, I could write:

MyRenamedPackage.MyClass.RenamedDotNetMethod(...);

Hope this helps!

EDIT:

I've gotten a bit more familiar with the Xamarin toolkit, and have an update to make using this easier.

In order to limit the involvement of code that needs to interact with the jar methods, Xamarin allows you to create C# classes in the Additions folder. So, I created a wrapper class that exposes the methods in a managed C# class that other projects can access. Since it's C# there's no complaints from Visual Studio.

Here's what a wrapper class would look like going with my earlier example (obviously you'd pick a name more meaningful to the task at hand):

public class InovcationWrapper
{
    public static void InvokeMethod(...)
    {
        MyRenamedPackage.MyClass.RenamedDotNetMethod(...);
    }
}

Then in your project code, you'd have full intellisense if you just call your wrapper class:

InvocationWrapper.InvokeMethod(...);

This makes it much easier to work with and limits the amount of red squiggles to be ignored in your code. Hope this helps!

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top