artberri
artberri

Reputation: 1357

How to call Java method (custom class) with an interface typed parameter in Nativescript

I'm creating a Nativescript plugin. It includes a custom Android Library (AAR) and I want to use it from the Typescript code. When I run a demo (in device or emulator) I get a TypeError: sender.registerListener is not a function error when calling this registerListener method, which is weird because I'm able to call other methods of the same object.

I think that it could be because I am not implementing properly the interface required as parameter. I think that I can explain it better with code:

Sender.java: the public class I will use in Typescript:

package com.berriart.android.myplugin;

public class Sender {
    public static final String TAG = "Sender";

    private Context _context = null;

    public Sender(Context context) {
        _context = context;
    }

    public void send(final String messagePath, final String messageToSend) {
        if (Log.isLoggable(TAG, Log.INFO)) {
            Log.i(TAG, "Send call: " + messagePath + " " + messageToSend);
        }
    }

    public void registerListener(MessageListener listener) {
        if (Log.isLoggable(TAG, Log.INFO)) {
            Log.i(TAG, "registerListener");
        }
    }

    // Other code here
}

MessageListener.java: the interface that must be implemented by the registerListener parameter:

package com.berriart.android.myplugin;

public interface MessageListener {
    void receive(String messagePath, String messageReceived);
}

This is the Typescript (Nativescript) code of the plugin ( to ):

import * as app from "tns-core-modules/application";

export class WearMessaging {
    public static send(messagePath: string, messageToSend: string) {
        let sender = new com.berriart.android.myplugin.Sender(app.android.context);

        sender.send(messagePath, messageToSend);
    }

    public static registerListener(receiveCallback: (messagePath: string, messageReceived: string) => void) {
        let messageListener = new com.berriart.android.myplugin.MessageListener({
            receive: receiveCallback
        });
        let sender = new com.berriart.android.myplugin.Sender(app.android.context);
        sender.registerListener(messageListener);
    }
}

If I include WearMessaging.send("/demo", "Hola"); in my nativescript application it compiles and run properly, it's call the Java method successfuly. But if I run:

WearMessaging.registerListener((messagePath: string, messageReceived: string) => {
  console.log(messagePath);
  console.log(messageReceived);
});

The application stops at run time and throws: TypeError: sender.registerListener is not a function refering to the myplugin.android.ts file.

I'm getting crazy trying to make this work, so, let me know if you have any clue. As I say I think that is because I'm missing something when implementing the interface and because the parameter type do not match them method is not being recognized, but maybe I'm wrong.

Here you can see some official doc: https://docs.nativescript.org/runtimes/android/generator/extend-class-interface

Thanks in advance.

Upvotes: 1

Views: 1321

Answers (1)

artberri
artberri

Reputation: 1357

Ok, I solved it :S

It seems that the incremental build was doing something wrong. After deleting manually the build files of the demo everything went fine:

rm -rf platforms/android/build/*
rm -rf platforms/android/app/build/*
# Then build & deploy again

So, question code seems to be fine if you need to do something similar.

Upvotes: 0

Related Questions