This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Questions regarding Mesh Android app:

thanks for the answer on the previous post.

What I came to know from our firmware engineer was that your initial version of the Android app could not support

1. multiple subscriptions for the nodes and

2. also adding clients

But he said he read somewhere that this functionality is there in the Android library but is disabled.

Can you tell me the handlers and data structures to do these 2 things in my version of the app?

  • I can see in ModelConfigurationActivity.java where you have implemented 

    mViewModel.getExtendedMeshNode().getMeshNode();

    and

    mViewModel.sendGenericOnOff(node, .... );

    at lines 347 and 352 respectively. This gets me to the first question:

    1) Does that mean that I can get the mesh node reference I'm connected to using this piece of code from any of my Activities?

    Now, mViewModel is of type ModelConfigurationViewModel which in turn relates to ModelConfigurationRepository. This ModelConfigurationRepository, in turn, sends control messages to a mBinder which is declared in the extended class of BaseMeshRepository. Over here, mBinder is declared as MeshService.MeshServiceBinder. In the service, it looks like the Binder connects to a device and uses BleMeshManagerApi.

    2) So basically, my idea was that you can directly cut through all of the other structures and just use the mBleMeshManagerApi or MeshServiceBinder from the service to connect and send messages. Is this possible and is it the right way of doing it?

    3) Also, regarding the MeshService. I want to have control over the when the service starts and stops. How do I do that?

    4) I have an activity which connects to your MainActivity which does scanning and connection to the network in the respective fragments. Also, somewhere, (I don't know where) your MainActivity starts the MeshService. But after connecting to a Proxy node, if I press Back on MainActivity which goes to my activity, the service stops and disconnects from the proxy. I don't want it to stop and disconnect from the proxy. How do I achieve this?

    5) Now if that is solved, I want to use the mBleMeshManagerApi that the service is using. I will have to use either Binder or something of the service from my activity to send data to the mesh. How do I get the MeshService Context such that I can get the context of:

    mMeshManagerApi = new MeshManagerApi(this);

    at line 221 in the service. I guess that is only how I can use the service BleMeshManagerApi. How do I do it?

  • 1) No, that's the mesh node that is passed in to that activity from the previous activity. This will point to only the node you want to talk to. Since its a mesh network you can connect to a random one and the configure the one you click and select from the main network menu. You might want to read up on Android services. A binder is used to connect to a service from an activity.

    2) You may do that and will make it very simple to you since you are new to dagger2, viewmodels and repositories. This way you can write your own app without having to dig deep in to our source.

    3) Like I said you might want to read up on Android services.

    4) If you have gone through the code you might see in the ViewModel attached to the main activity has onCleared(), disconnects and unbinds from the service and stops it.

    5) to get the context you will have to call getApplicationContext in the service

    If you're very new to Android I would suggest you go down the acitvity and service approach (you can find lot of documentation related to services) removing all the viewmodels and repositories. The reason for using viewmodels is to use the new Architecture Components in Android which makes it very easy to handle configuration changes and lifecycle changes in Android.

    Going down the service approach is only a change in the design and you can have all the api calls related to meshmanager api within the binder in the meshservice. This way you call the meshMaangerApi methods via the binder.

  • I was trying to send data to the mesh using the method of:

    mMeshManagerApi.setGenericOnOffUnacknowledged(mMeshManagerApi.getProvisionedNodes().get(5),
                    genericOnOffServerModel,
                    new byte[]{0x00, 0x05},
                    0,
                    null,
                    null,
                    null,
                    isLightOn);

    I've declared the model as:

    GenericOnOffServerModel genericOnOffServerModel = new GenericOnOffServerModel(0x1000);

    However, I get the error of model not having a binding with an app key like below:

    java.lang.IllegalArgumentException: Please bind an app key to this model to control this model!
            at no.nordicsemi.android.meshprovisioner.MeshManagerApi.setGenericOnOffUnacknowledged(MeshManagerApi.java:881)
            at no.nordicsemi.android.nrfmeshprovisioner.MainFragment.send(MainFragment.java:72)
            at no.nordicsemi.android.nrfmeshprovisioner.MainFragment_ViewBinding$1.doClick(MainFragment_ViewBinding.java:30)

    I then used the method mentioned in MeshManagerApi as:

    mMeshManagerApi.bindAppKey(mMeshManagerApi.getProvisionedNodes().get(5),
    new byte[]{0x00, 0x05},
    genericOnOffServerModel,
    0);

    It doesn't work. Am I doing something wrong?
    Also what should I enter in AppKeyIndex? Where is this array and how do I get it?
  • Not sure entirely what you're trying to do by declaring a model. When you provision a node, the library will create all the models that are available in the node. So all you have to do is just list all the models you need by just calling node.getMeshModels(). From what I see you're creating a model in the app and turn on the same model in the app, so it does not look right to me.

    Also binding app keys works fine on our end so you must be doing something wrong in your implementation.

    Before binding an app key an app key should be added to that particular node. Hope that is done and if that's the case that app key should be bound to a specific model you want to talk to.

    So as you have done bindAppKey index should work as it is. Also When you send a bindAppKey message you should get a Model App Status and that will contain if its successful or not and is handled in the library. You can find the status codes in the specification as well.

    When it comes to app key index, you can get it from the node.getAddedAppKeys() list for that specific node. When you try to bind an appKey you need to specify the index of that particular appkeyindex. If you follow our example you should see this.

  • I have already added an app key to the generic on off server model in the node's element. If I do a:

    mMeshManagerApi.getProvisionedNodes().get(5).getAddedAppKeys();

    I can get a Map of bound app keys. I've seen that the app key is correct. That means that the app key is bound to the node.

    I could not find a getMeshModels() like you mentioned above.

    mMeshManagerApi.getProvisionedNodes().get(5).getMeshModels();

    So how can I use getMeshModels()

    Can you tell me In your code, in which file are you binding app keys to models?

Related