How to translate event driven code? - android

I'm mostly C# developer and I'm recently working on some Android project. I have to implement some custom written events in Android, but I'm not sure how to do that.
I wrote a C# code for what I want to do, so if anyone can help me with translating it into Android code, that would be appreciated.
I need to have a custom function (event), placed at MySecondClass, which can be triggered from MyFirstClass.
For example, we have the class:
private class MyFirstClass
{
private event EventHandler<MyCustomEventArgs> _myCustomEvent;
public event EventHandler<MyCustomEventArgs> MyCustomEvent
{
add { _myCustomEvent += value; }
remove { _myCustomEvent -= value; }
}
public void Initialize()
{
MySecondClass myObjectSecondClass = new MySecondClass();
this.MyCustomEvent += myObjectSecondClass.SomeMethodSecondClass;
}
public void SomeMethodFirstClass(int index)
{
//here we will trigger the event with some custom values
EventsHelper.Fire(this.MyCustomEvent, this, new MyCustomEventArgs(index));
}
}
The MyCustomEventArgs is defined as:
public class MyCustomEventArgs : EventArgs
{
public int index;
public MyCustomEventArgs(int indexVal)
{
index = indexVal;
}
}
And the the second class is defined as:
private class MySecondClass
{
public void SomeMethodSecondClass(object sender, MyCustomEventArgs e)
{
//body of the method
//we can use e.index here in the calculations
}
}
So I'm not sure how to handle with these "Event" related commends in Android.

Its all interfaces in java. No fancy complicated key word here :)
There should be an interface which the second class implements.
public interface EventHandler{
void onEventFired(EventParams e);
}
public class MyFirstClass{
EventHandler eventHandler;
public void initialize(){
eventHandler = new MySecondClass();
}
public void method(){
EventParams eventParams = new EventParams();
//fire event here
eventHandler.onEventFired(eventParams);
}
}
public class MySecondClass implements EventHandler{
#Overrride
void onEventFired(EventParams e){
//handle event here
}
}
I hope you get the idea

Related

Dagger listener/interface injection

Hello everyone I've been struggling to understand how to inject a listener to a main activtity with Dagger2, I wonder if what I'm trying to do is possible or even a right move with dagger or should I just let it like it is right now I have read that I need to create another class with the implementation of that interface but is not possible(or recommended) to inject on the mainactivity?, thanks in advance to anyone who can help me, I have everything in short as follows:
//////////////////////////////////////MainActivity.class//////////////////////////////////////
public class MainActivity extends AppCompatActivity implements CustomListener{
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//this is the object I want to inject in Dagger
LongProcess longProcess = new LongProcess(this);
longProcess.longRunningProcess();
}
#Override
public void onProcessStarted() {
Log.i(TAG, "onProcessStarted: CALLBACK!");
}
#Override
public void onProcessFailed() {
Log.e(TAG, "onProcessFailed: CALLBACK!");
}}
//////////////////////////////////////LongProcess.class//////////////////////////////////////
public class LongProcess {
private CustomListener customListener;
public LongProcess(CustomListener customListener) {
this.customListener = customListener;
}
public void longRunningProcess() {
try {
//some long process started...
customListener.onProcessStarted();
} catch (Exception e) {
//some long process failed...
customListener.onProcessFailed();
}
}
}
//////////////////////////////////////interface.java//////////////////////////////////////
public interface CustomListener {
void onProcessStarted();
void onProcessFailed();
}
You can take a look at Assisted Injection for this use case: https://dagger.dev/dev-guide/assisted-injection

Pattern to add listener to method call? Is there an example?

I have been working with a ChannelClient and saw how you could call a method and add a listener to it. It does not exactly seem like the builder pattern but I was wondering to create my own class using the same technique. Is there an example? This seems like a great way to either add a listener or not.
ChannelClient channelClient = Wearable.getChannelClient(getContext());
channelClient.openChannel(node,path).addOnSuccessListener(new OnSuccessListener<ChannelClient.Channel>() {
#Override
public void onSuccess(ChannelClient.Channel channel) {
}
});
So for my class:
public class TokenMessage {
private String name;
private int id;
public TokenMessage(int id, String name) {
this.id=id;
this.name=name;
}
public void generateCode() {
}
}
How do I add addOnSuccessListener to the method call. I assume I create a public interface in the class, but how do I add it to a method call? How do I add it to the generateCode method?
There are also addOnFailureListener and addOnCompleteListener methods which can be appended to the call as well.
ADDITION
I would want to be able to add multiple listeners and have the call to look like this:
TokenMessage tokenMessage = new TokenMessage(42,"Name");
tokenMessage.generate().addOnSuccessListener(new OnSuccessListener<int>() {
#Override
public void onSuccess(int code) {
}
}).addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(#NotNull Exception e) {
}
});
You should be able to reverse engineer what your class will look like from the requirements:
Assuming you want something like this:
TokenMessage message = new TokenMessage(42, "Name");
message.addOnSuccessListener(new TokenMessage.OnSuccessListener() {
void onSuccess() {
doSuccessfulThings();
}
}).addSomeOtherListener(...)
Then clearly you need:
A method to set a listener object that returns the same object for chaining.
Listener interfaces that you can set.
Variable to hold the interface instances in your object.
Calls to the callback methods on the interface objects based on logic of generateCode.
Then your code would look something like this:
public class TokenMessage {
interface OnSuccessListener {
void onSuccess();
}
// Other interfaces for failure etc
private String name;
private int id;
private OnSuccessListener onSuccessListener;
// Other member fields
public TokenMessage(int id, String name) {
this.id=id;
this.name=name;
}
public TokenMessage generate() {
launchTaskThatTakesALongTime();
return this
}
// Setter that returns the object for chaining
public TokenMessage addOnSuccessListener(OnSuccessListener listener) {
onSuccessListener = listener;
return this;
}
private void launchTaskThatTakesALongTime() {
// Use your preferred async / threading paradigm to run your task in the background. When they complete, invoke your listeners:
// if (success && successListener != null) {
// successListener.onSuccess()
//}
}
// Other setters for other callbacks
}

Gomobile android using callbacks

I have an library written using go mobile and it should has only one callback but when trying implement it, I get two additional methods.
#Override
public Seq.Ref ref() {
return null;
}
#Override
public void call(int i, Seq seq, Seq seq1) {}
Question is, which is right way to implement callback from go on Android Activity?
Right now i have next:
public class MainActivity extends Activity implements implements Mobile.Callback {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_register);
Mobile.Client client = Mobile.New("192.168.2.1", 9000, this);
try {
client.Connect();
} catch (Exception e) {
e.printStackTrace();
}
}
#Override
public void OnMessage(String s) {
Log.e("GO", s);
}
#Override
public Seq.Ref ref() {
return null;
}
#Override
public void call(int i, Seq seq, Seq seq1) {
}
}
Connection is established successfully but on callback to activity i getting:
panic: runtime error: invalid memory address or nil pointer dereference
If someone can help I'll be really appreciate.
What is the Go source you are binding? (The package mobile and Callback interface)
For passing the Java class that implements Go interface type, see the section "Passing target language objects to Go" of
https://godoc.org/golang.org/x/mobile/cmd/gobind
Basically, the generated Java interface type is not meant to be used directly. Instead, the Java class should extends the generated Java interface's Stub class.
Use Mobile.Callback.Stub instead of Mobile.Callback for android
...
Mobile.Client client = Mobile.New("192.168.2.1", 9000, new Callbacks());
...
class Callbacks extends Mobile.Callback.Stub {
#Override
public void OnMessage(String s) {
....
}
}

RxJava with multi network request

Here is the code:
public class HomeDetails extends Model {
public Home mHomeData;
public AD mAdData;
public HomeDetails(Api api, String url) {
api.getHome(url, createHome(), this);
api.getAd(url, createAD(), this);
}
private NetworkResponse.Listener<Home> createHome() {
return new NetworkResponse.Listener<Home>() {
#Override
public void onResponse(Home home) {
mHomeData = home;
}
};
}
private NetworkResponse.Listener<AD> createAD() {
return new NetworkResponse.Listener<AD>() {
#Override
public void onResponse(AD ad) {
mAdData = ad;
}
};
}
}
I'd like to use RxJava to help me to know when the two requests are all done. if all is done, then execute another method.
You can use Observable.create() to create the two observable for the two network calls, then you can concat() or zip() them and execute whatever you want in the onNext().

android how to make listener to a custom variable?

i've seen this thread : How to implement a listener about implement listeners.
its actually pretty simple but i don't get how exactly its done and how to implement in my own code.
i have this static variable variable: AppLoader.isInternetOn.
i want to build a listener which will listen to this variable changes and update a TextView.
should i do this: ?
build an interface:
public interface InternetStateListener {
public void onStateChange();
}
run it in my activity:
public class MyActivity extends Activity {
private InternetStateListener mListener;
setTheListener(this);
public void setTheListener(InternetStateListener listen) {
mListener = listen;
}
private void onStateChange() {
if (mListener != null) {
if (AppLoader.isInternetOn)
text.setText("on")
else
text.setText("off")
}
}
}
Your Activity does nothing special, just register itself (since the interface is implemented directly in the class) with the Other class that provides the listener.
public class MyActivity extends Activity implements InternetManager.Listener {
private TextView mText;
private InternetManager mInetMgr;
/* called just like onCreate at some point in time */
public void onStateChange(boolean state) {
if (state) {
mText.setText("on");
} else {
mText.setText("off");
}
}
public void onCreate() {
mInetMgr = new InternetManager();
mInetMgr.registerListener(this);
mInetMgr.doYourWork();
}
}
The other class has to do pretty much all the work. Besides that it has to handle the registration of listeners it has to call the onStateChange method once something happend.
public class InternetManager {
// all the listener stuff below
public interface Listener {
public void onStateChange(boolean state);
}
private Listener mListener = null;
public void registerListener (Listener listener) {
mListener = listener;
}
// -----------------------------
// the part that this class does
private boolean isInternetOn = false;
public void doYourWork() {
// do things here
// at some point
isInternetOn = true;
// now notify if someone is interested.
if (mListener != null)
mListener.onStateChange(isInternetOn);
}
}
The part that you're missing it the class that actually notifies the listener. So you would need a class (most likely a service) that runs and pings the state of the network. Then when it detects a change it should call onStateChange() in any registered listeners. Then you would call setTheListener on that service, not on your activity.
Here's a link that thoroughly describes this design pattern: http://en.wikipedia.org/wiki/Observer_pattern

Categories

Resources