When do intent extras become null between activiti

2019-03-03 22:59发布

问题:

I'm having problems receiving intent extras between activities.

In my MainActivity I start a Gallery activity to chose video files on external SD card:

public class MainMenu extends Activity {
    //Button change video
    Button video_change;
    //Extra for changing video content
    Bundle extras;
    //Intent for Gallery view activity
    Intent intent;

    @Override
    protected void onCreate(final Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
     //...
     intent = new Intent(getApplicationContext(),GalleryView.class);

     video_change.setOnClickListener(new View.OnClickListener() {

                  @Override
                  public void onClick(View v) {

                      Uri mUri = null;
                      try {
                          Field mUriField = VideoView.class.getDeclaredField("mUri");
                          mUriField.setAccessible(true);
                          mUri = (Uri) mUriField.get(myVideoView);          
                      } catch(Exception e) {
                          //TODO: Something here
                      }
                      String string = mUri.toString();
                      intent.putExtra("old_video",string);
                      startActivity(intent);            
                  }
              });
      }

    @Override
    public synchronized void onResume() {
        super.onResume();
        if (Config.DEBUG)
            Log.d(CLASS_NAME, "+ ON RESUME +");
        try {
            extras = intent.getExtras();
            if (extras != null){
                Log.d("++ ON RESUME ++","Found Extra!");
                String newvideo = extras.getString("new_video");
                Log.d("++ ON RESUME ++","NEW VIDEO: "+ newvideo);
                Uri tempuri = Uri.parse(newvideo);
                myVideoView.setVideoURI(tempuri);         
            }
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        View decorView = getWindow().getDecorView();
        decorView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE
                | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
                | View.SYSTEM_UI_FLAG_FULLSCREEN
                | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);
    }
  }

Then in my GalleryView activity:

public class GalleryView extends Activity {

    ImageView back_button;
    ListView videolist;
    List<String> videos = new ArrayList<String>();
    private File[] videoFiles;
    //private Cursor videocursor;
    //private int video_column_index;
    int x=0;
     @Override
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
         setContentView(R.layout.gallery);
         back_button = (ImageView) findViewById(R.id.back_button);
         videolist = (ListView) findViewById(R.id.listview);

         start_listview();

         ArrayAdapter adapter = new ArrayAdapter<String>(this,R.layout.activity_listview,videos);
         videolist.setAdapter(adapter);

         videolist.setOnItemClickListener(new OnItemClickListener(){
              @Override
              public void onItemClick(AdapterView<?> adapter, View v, int position, long arg3) {
                    String value = (String)adapter.getItemAtPosition(position); 
                    Log.d("VALUE: ",value);
                    Intent i = new Intent(getApplicationContext(),MainMenu.class);
                    // Send the file path
                    i.putExtra("new_video", value);
                    startActivity(i);
              }
         });

         back_button.setOnClickListener(new OnClickListener() {
           //videolist.setAdapter(new VideoAdapter(getApplicationContext()));
            @Override
            public void onClick(View v) {
           //videolist.setOnItemClickListener(videogridlistener);
                Intent intent = new Intent(getApplicationContext(),MainMenu.class);
                Bundle extras = getIntent().getExtras();
                String newString = extras.getString("old_video");
                intent.putExtra("new_video", newString);
                startActivity(intent);

            }
         });
     }

    public void start_listview() {

        String path = ("/storage/extsd/Videos/");
        File directory = new File(path);
        videoFiles = directory.listFiles();
        try {
            for (File f : videoFiles) {
                Log.d("FILE: ", f.toString());
                String file = f.toString();
                Uri tempuri = Uri.fromFile(f);
                videos.add(file);
            }
            //Set the visibility of the progress bar to false.
            findViewById(R.id.relativelayout_progress).setVisibility(View.GONE);
        } catch (Exception e) {
            // TODO: handle exception
        }
    }
}

The problem is, I when I return back to the MainMenu activity, I the extra is found, but is null! From logcat:

MainMenu           + ON RESUME +
++ ON RESUME ++    Found Extra!
++ ON RESUME ++    NEWVIDEO: null

Even if I put the extras = intent.getExtras() call in the onCreate, it never gets called because it never passes the extras != null check


HOW I FIXED IT (THANKS TO STEFAN'S ANSWER)

So my MAIN problem was that my Main Activity was always being set to the background whenever I started the new Gallery Activity. My manifest file dictated that it would do a android:launchMode="singleTask" on the Main Activity. So, somehow when the Main Activity was re-started, the intent was never truly passed since the app was always running in the background and never passed the intent extras. So I tried the onNewIntent() method call and tried the piece of code in there to receive the extras, and it worked! Thanks again to Stefan!

回答1:

What you are doing is to call the MainActivity again after opening the gallery. Depending on the flags used in your manifest, that might cause that your main activity is not launched a second tim, but that your initial main activity is unpaused and raised to foreground.

If this is the case, due to the activity lifecycle, onCreate(...)will not be called again, but you can check if the following method is called:

@Override
protected void onNewIntent(Intent intent) {
    super.onNewIntent(intent);
    //TODO: check here if your intent extras arrive and log, then debug
}