M. Carlo Bramini
M. Carlo Bramini

Reputation: 2532

StartActivity from different context

I've got a main class and a separete class (OnClickBtn.java) in which I want to keep just the button methos. I would like to start new activities not from the main class but from the OnClickBtn.java.

I've run the program but it crashes at launch. I guess that my main issue is related to the code for the Intent object "Intent int_btnOpenA =new Intent(objContex, ActivityA.class)"

This is my code, MainActivity.java:

 package com.example.and2dtest;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends Activity {
//START***VIEW LIST E BOTTONI
    TextView txtView01;
    Button btnOpenA;
    Button btnOpenB;
    EditText editText1;

    OnClickBtn btnMethods=new OnClickBtn(this);
//END***VIEW LIST E BOTTONI

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
//Start***set buttons views
        txtView01=(TextView)findViewById(R.id.txtView01);
        btnOpenA=(Button)findViewById(R.id.btnOpenA);
        btnOpenB=(Button)findViewById(R.id.btnOpenB);
        editText1=(EditText)findViewById(R.id.editText1);   

        btnOpenA.setOnClickListener(btnMethods);
        btnOpenB.setOnClickListener(btnMethods);
//end***set buttons views
    }




    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }



}

this is the OnClickBtn.java class:

package com.example.and2dtest;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;

public class OnClickBtn extends Activity implements OnClickListener {
MainActivity objContex;

    public OnClickBtn(MainActivity cont){
    objContex=cont;
    }

    Intent int_btnOpenA =new Intent(objContex, ActivityA.class); //<<THIS CAUSES CRASH!

    @Override
    public void onClick(View v) {
        switch(v.getId()){
        case R.id.btnOpenA:
            Log.d("ZR", "in case btnOpenA");
            //this.startActivity(int_btnOpenA);  //<-clearly This Wont Start
            break;
        case R.id.btnOpenB:
            Log.d("ZR","in case btnOpenB");
            //do something
            break;

        }   
    }


}

how can I make it work, keeping the startActivity method not in the main activity?

Thanks, Luther

Ok I've been messing with the code and the following seems to work, ActivityA gets started not from MainActivity.java but from OnClickBtn.java, as I was trying to do. This is the code:

MainActivity.java:

package com.example.and2dtest;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class MainActivity extends Activity {
//START***VIEW LIST E BOTTONI
    TextView txtView01;
    Button btnOpenA;
    Button btnOpenB;
    EditText editText1;


//END***VIEW LIST E BOTTONI

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        OnClickBtn btnMethods=new OnClickBtn(this);
//Start***set buttons views
        txtView01=(TextView)findViewById(R.id.txtView01);
        btnOpenA=(Button)findViewById(R.id.btnOpenA);
        btnOpenB=(Button)findViewById(R.id.btnOpenB);
        editText1=(EditText)findViewById(R.id.editText1);   

        btnOpenA.setOnClickListener(btnMethods);
        btnOpenB.setOnClickListener(btnMethods);
//end***set buttons views
    }




    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }



}

OnClickBtn.java:

package com.example.and2dtest;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;

public class OnClickBtn implements OnClickListener {
Context objContext;

    public OnClickBtn(Context con){
    //v=view;
    objContext=con;
    }

    //Intent int_btnOpenA =new Intent(objContext, ActivityA.class);

    @Override
    public void onClick(View v) {
        switch(v.getId()){
        case R.id.btnOpenA:
            Log.d("ZR", "in case btnOpenA");
            Intent int_btnOpenA =new Intent(objContext, ActivityA.class);
            objContext.startActivity(int_btnOpenA);
            break;
        case R.id.btnOpenB:
            Log.d("ZR","in case btnOpenB");
            //do something
            break;

        }   
    }


}

ActivityA.java:

package com.example.and2dtest;

import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;

public class ActivityA extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_activity);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.activity, menu);
        return true;
    }

}

Upvotes: 1

Views: 6098

Answers (6)

reis_eliel
reis_eliel

Reputation: 328

Try it like this:

(just change "btnOpenA.setOnClickListener(btnMethods);" and "btnOpenB.setOnClickListener(btnMethods);" for this two and forget the button class)


    btnOpenA.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(final View view) {
            final Intent intent = new Intent(MainActivity.this, ActivityA.class);
            SensorActivity.this.startActivity(intent);
        }
    });


    btnOpenB.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(final View view) {
            final Intent intent = new Intent(MainActivity.this, ActivityB.class);
            SensorActivity.this.startActivity(intent);
        }
    });

EDIT: If you want that button class badly, you can try this:

(Register the listeners using this "listener class" nested class inside your activity, or change it to public and put it on a different file and then register the listeners using this "listener class". Context will still be related to the MainActivity.)

private final class OnClickBtn implements OnClickListener {
    @Override
    public void onClick(final View view) {

        if( view.getId() == R.id.btnOpenA ){

            final Context context = view.getContext();
            final Intent intent = new Intent(context, ActivityA.class);
            view.getContext().startActivity(intent);
        }
        else if( view.getId() == R.id.btnOpenB ){

            final Context context = view.getContext();
            final Intent intent = new Intent(context, ActivityB.class);
            view.getContext().startActivity(intent);
        }
    }
}

Upvotes: 0

Saif Hamed
Saif Hamed

Reputation: 1094

Try this:

Intent int_btnOpenA;
public OnClickBtn(MainActivity cont){
 int_btnOpenA=new Intent(cont, ActivityA.class);
}

Upvotes: 0

codeMagic
codeMagic

Reputation: 44571

As others have said, it is not good to instantiate an Activity in this way and won't work. They don't have a user-defined constructor. They should only be instantiated with an Intent.

What you can do is implements OnClickListener in your click class. There you override and put your code in there.

Here is an answer that demonstrates that.

If you want them to be reusable and have the same functionality in each Activity then you can place them in a BaseActivity which you will extend in the other Activities.

This is explained a little more in this SO answer

Upvotes: 1

Dale Wilson
Dale Wilson

Reputation: 9434

Give MainActiviy a constructor that takes a Context as the argument. Save that Context (or use it to getActivityContext() for use when you receive the button click.

This is a common technique in Android. You will see many objects that take a Context as an argument to their constructor.

Also, as Alécio said in his answer, MainActivity should not extend Activity. Any attempt to use it as an activity is likely to fail.

Upvotes: 0

Al&#233;cio Carvalho
Al&#233;cio Carvalho

Reputation: 13667

you can't instantiate an activity yourself. Although OnClickBtn is extending an Activity, it is not functioning as an Activity.

Upvotes: 0

nomachinez
nomachinez

Reputation: 521

Try setting btnMethods in your onCreate() method instead of at the class level.

.....

OnClickBtn btnMethods;

.....

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    btnMethods = new OnClickBtn(this);
    ......
}

Upvotes: 0

Related Questions