Isaac Isaac - 5 months ago 20
Android Question

How to call a method of MainActivity by a class that extends Button

I want to call a method showMessage() which is defined in my main activity from a TestButton class that extend Button. The code I use below throw a null pointer exception. I am not sure how to solve this. Can you please help me?

MainActivity

public class MainActivity extends MultiTouchActivity {

TestButton btn;
@Override
public void onCreate(final Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
btn = (TestButton)findViewById(R.id.button4);
btn.setOnTouchListener(this);
}
public void showMessage()
{
Toast.makeText(this, "hello", Toast.LENGTH_SHORT).show();
}


TestButton class

public class TestButton extends Button {

MainActivity m;
public TestButton(final Context context, final AttributeSet attrs)
{
super(context, attrs);

// TODO Auto-generated constructor stub
}

@Override
public boolean onTouchEvent(final MotionEvent event)
{
if (event.getAction() == MotionEvent.ACTION_UP)
{
m = new MultitouchtestActivity();
m.showMessage();
}
return super.onTouchEvent(event);
}


}

EDIT
Thank you @ΦXoce 웃 Пepeúpa this solve my issue but I made a little bit changes.

btn.setCallback(this); from btn.setCallback();


and

public void setCallback(final ICallback iCallback)

Answer

2 things:

  1. m = new MultitouchtestActivity(); is not the way ANDROID wants you to create ACtivities.. so you have more chances to breack your code than doing something right by calling the constructor directly..
  2. On the other hand trying to call a method from the Activity inside of a button class is forcing you to make circle-dependencies... now your Activity needs a button and your button needs an Activity..(not a good approach)

How to solve it

Implement a callback like doing:

interface ICallback{
    void showMessage();
}

public class MainActivity extends MultiTouchActivity implements ICallback{

TestButton btn;

@Override
public void onCreate(final Bundle savedInstanceState)
{
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);
    btn = (TestButton)findViewById(R.id.button4);
    btn.setOnTouchListener(this);
    //register here the callback
    btn.setCallback(this);
}

@Override
public void showMessage()
{
    Toast.makeText(this, "hello", Toast.LENGTH_SHORT).show();
}

public class TestButton extends Button {

MainActivity m;
ICallback iCallback;
public setCallback(final ICallback iCallback)
{
    this.iCallback = iCallback; 
}
public TestButton(final Context context, final AttributeSet attrs)
{
    super(context, attrs);

    // TODO Auto-generated constructor stub
}

@Override
public boolean onTouchEvent(final MotionEvent event)
{
    if (event.getAction() == MotionEvent.ACTION_UP)
    {
        iCallback.showMessage();
    }
    return super.onTouchEvent(event);
}
}
Comments