I have a problem with the lifecycle of the activities on android. I am trying to return back from my second activity to my first one. It actually my code is doing that, not the way it supposed to do it. I have "back button" on the top left corner and when I hit it - it goes through onDestroy() and onCreate() methods of my MainActivity. But if I use the back button on my phone - everything is OK(it goes just trough onResume() method) Can someone explain me - where my code is wrong?
in MainActivity.java:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater menuInflater = getMenuInflater();
menuInflater.inflate(R.menu.settings_menu, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.action_settings) {
Intent intent = new Intent(MainActivity.this, SettingsActivity.class);
startActivity(intent);
return true;
}
return super.onOptionsItemSelected(item);
}
in my SettingsActivity.java:
package com.example.garagedoor;
import android.os.Bundle;
import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AppCompatActivity;
import androidx.preference.PreferenceFragmentCompat;
public class SettingsActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.settings_activity);
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.settings, new SettingsFragment())
.commit();
ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
actionBar.setDisplayHomeAsUpEnabled(true);
}
}
public static class SettingsFragment extends PreferenceFragmentCompat {
#Override
public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
setPreferencesFromResource(R.xml.root_preferences, rootKey);
}
}
}
in AndroidManifest.xml:
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".SettingsActivity"
android:label="#string/title_activity_settings"
android:parentActivityName=".MainActivity">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".MainActivity"/>
</activity>
You need to add
android:launchMode="singleTop"
to the manifest entry for MainActivity. See the following questions:
ActionBar up navigation recreates parent activity instead of onResume
How can I return to a parent activity correctly?
Your problem is probably about the task stack. I am not sure what actionbar button do but i think you should either use
#Override public void onBackPressed()
in SettingsActivity or start the SettingsActivity with Intent flags like here:
https://developer.android.com/guide/components/activities/tasks-and-back-stack
Hope this helps.
Related
I added a Toolbar to my Activity with back arrow like this:
Toolbar myToolbar = (Toolbar) findViewById(R.id.my_toolbar);
setSupportActionBar(myToolbar);
//add back arrow - but it doesn't go back, nothing happens when I click it
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
But when I click the back arrow, it doesn't go back to previous page
add this lines:
#Override
public boolean onSupportNavigateUp() {
onBackPressed();
return true;
}
#Override
public void onBackPressed() {
super.onBackPressed();
finish(); // or your code
}
You need to override onCreateOptionsMenu() and onOptionsItemSelected() just like this:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.your_id, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
onBackPressed();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
Don't forget to replace R.menu.your_id with your id as name suggest.
With suggested answers you might want to add parentActivity in your Android manifest.xml
<application ... >
...
<!-- The main/home activity (it has no parent activity) -->
<activity
android:name="com.example.myfirstapp.MainActivity" ...>
...
</activity>
<!-- A child of the main activity -->
<activity
android:name="com.example.myfirstapp.DisplayMessageActivity"
android:label="#string/title_activity_display_message"
android:parentActivityName="com.example.myfirstapp.MainActivity" >
<!-- The meta-data element is needed for versions lower than 4.1 -->
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="com.example.myfirstapp.MainActivity" />
</activity>
Docs: Android developers
I did some research one this Exception but none of these answers here helped me. So what I need to do is when I click a list item, it moves to another activity but I end up getting the same annoying Exception. It tells to look into Android Manifest file but everything is alright there!
Here is my code
Intent:
#Override
public void onItemClick(AdapterView<?> adapterView, View view, int position, long id) {
String strItemTextView = mForecastAdapter.getItem(position);
Intent intent = new Intent(getActivity(), DetailActivity.class);
intent.putExtra(Intent.EXTRA_TEXT, strItemTextView);
startActivity(intent);
}
And Android Manifest file:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.android.sunshine2">
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:label="#string/app_name"
android:supportsRtl="true"
android:theme="#style/AppTheme">
<activity
android:name="com.example.android.sunshine2.MainActivity"
android:label="#string/app_name"
android:theme="#style/AppTheme.NoActionBar">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name="com.example.android.sunshine2.DetailActivity"
android:label="#string/title_activity_detail"
android:parentActivityName="com.example.android.sunshine2.MainActivity"
android:theme="#style/AppTheme.NoActionBar">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="com.example.android.sunshine2.MainActivity" />
</activity>
</application>
</manifest>
UPDATE:
Here is my code for DetailActivity:
package com.example.android.sunshine2;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v7.app.ActionBarActivity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
public class DetailActivity extends ActionBarActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_detail);
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction()
.add(R.id.container, new PlaceholderFragment())
.commit();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.detail, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
/**
* A placeholder fragment containing a simple view.
*/
public static class PlaceholderFragment extends Fragment {
public PlaceholderFragment() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_detail, container, false);
return rootView;
}
}
}
I get an exception like this:
android.content.ActivityNotFoundException: Unable to find explicit activity class {com.example.android.sunshine2/com.example.android.sunshine2.DetailActivity}; have you declared this activity in your AndroidManifest.xml?
And it points to this line of the code:
intent.putExtra(Intent.EXTRA_TEXT, strItemTextView);
UPDATE #2:
Now things are getting really weird. If I use relative path for activity name BUT leave a full path for a Parent activity name (Code snippet of manifest file):
<activity
android:name=".DetailActivity" // <!--Activity I wanna go to (relative path)-->
android:label="#string/title_activity_detail"
android:parentActivityName="com.example.android.sunshine2.MainActivity"
android:theme="#style/AppTheme.NoActionBar">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="com.example.android.sunshine2.MainActivity" /><!--Full path-->
</activity>
I get the same Exception but this time it points to this line of code:
startActivity(intent);
UPDATE #3:
Please take a look at the comment I managed to fix my problem
You already have a declared package in your manifest:
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.android.sunshine2">
So as far as I remember you should just declare your activity in manifest with relative path only:
<activity
android:name=".DetailActivity"
android:label="#string/title_activity_detail"
android:parentActivityName=".MainActivity"
android:theme="#style/AppTheme.NoActionBar">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="com.example.android.sunshine2.MainActivity" />
</activity>
can you try below code
Intent intent = new Intent(view.getContext(), DetailActivity.class);
intent.putExtra(Intent.EXTRA_TEXT, strItemTextView);
So I managed to fix my problem. Since I am just learning on Udacity, after 2days of no answers I decided to look into the their solution. The problem is that their tutorials are about 1 year old and since then Android Studio was updated quite a lot. When you are creating a new project with fragment on the latest version of Android studio, for a layout you get three files:
activity_main.xml
content_main.xml
fragment_main.xml
As in previous versions of Android Studio, you wold only get two files:
activity_main.xml
fragment_main.xml
So what I did was I deleted content_main.xml and voilà. It worked!
That was really weird and I am marking this question as answered and I hope it will help for other users as well!
I have setup an activity to be executed from a menu button. The activity is started and briefly appears and then crashes. I have added added activity to manifest file. Code poseted below. I have recently switched form Eclipse to Android Studio and still learning the changes.
<?xml version="1.0" encoding="utf-8"?>
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
<application
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<activity
android:name=".MainActivity"
android:label="#string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".Titles_Edit_Activity"
android:label="#string/title_activity_titles__edit_"
android:theme="#style/Theme.AppCompat">
</activity>
</application>
This is the logcat message:
08-13 11:13:45.841 15302-15302/com.example.jerry.els2015 D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x0002
Menu trigger in MainActivity
public void setup(MenuItem menuItem){
Log.d("TAG", "Setting ");
startActivity(new Intent(this,Titles_Edit_Activity.class));
}
XML for Tiles_Edit_Activity
package com.example.jerry.els2015;
import android.app.Activity;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.view.Menu;
import android.view.MenuItem;
public class Titles_Edit_Activity extends ActionBarActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_titles__edit_);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_titles__edit_, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
}
I found the issue on the activity. I setup menu and back button to finish and exit the system so bluetooth will be killed. I removed these option and was able to execute the new activity.
#Override
protected void onDestroy() {
super.onDestroy();
// finish();
// System.exit(0);
}
#Override
protected void onStop() {
super.onStop();
// finish();
// System.exit(0);
}
try other way for startactivity, ex;
Intent intent = new Intent(MainActivity.this, Titles_Edit_Activity.class);
startActivity(intent);
I found the issue on the activity. I setup menu and back button to finish and exit the system so bluetooth will be killed. I removed these option and was able to execute the new activity.
#Override
protected void onDestroy() {
super.onDestroy();
finish();
System.exit(0);
}
#Override
protected void onStop() {
super.onStop();
// finish();
// System.exit(0);
}
The scenario I have consists of 3 activities:
1- Homepage
2-Login
3-Register
The thing is now Home page has 2 buttons one login and one for homepage , and the login activity should be called from either this button or from inside register after I am done registering ,also both login and register activities inflate 2 different fragments.
The problem : Login activity doesnt start , instead it sometimes just blinks with the layout it should inflate for a split second and then backs to the previous activity whichever one it is , also when I replaced the login activity with another activity it started normally with no problems
Any idea what that might be.
NOTE: I'm not getting any errors or so
Signin Activity code:
package engezni.Activties;
import android.annotation.TargetApi;
import android.app.ActionBar;
import android.app.Activity;
import android.os.Build;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.WindowManager;
import android.widget.FrameLayout;
import android.widget.TextView;
import Fragments.SigninFragment;
import engezni.Activties.R;
public class SignInScreen extends Activity {
FrameLayout frameLayout;
SigninFragment signinFragment;
TextView signinScreen;
#TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2)
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_sign_in_screen);
this.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
getActionBar().setCustomView(R.layout.custom_action_bar);
getActionBar().setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
/*Setting text to the textview in the xml actionbar layout */
signinScreen = (TextView) findViewById(R.id.actionbarTitleOrderScreen);
signinScreen.setText("Sign In");
getActionBar().setDisplayHomeAsUpEnabled(true);
getActionBar().setHomeButtonEnabled(true);
getActionBar().setDisplayShowHomeEnabled(false);
getActionBar().setBackgroundDrawable(getResources().getDrawable(R.drawable.actionbar));
getActionBar().setHomeAsUpIndicator(getResources().getDrawable(R.drawable.backlogo));
frameLayout=(FrameLayout)findViewById(R.id.signin_framelayout);
signinFragment=new SigninFragment();
if (findViewById(R.id.signin_framelayout) != null) {
if (savedInstanceState != null) {
return;
}
signinFragment.setArguments(getIntent().getExtras());
getFragmentManager().beginTransaction().add(R.id.signin_framelayout, signinFragment).commit();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.sign_in_screen, menu);
onBackPressed();
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
}
And then here is the manifest
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<activity
android:name=".SplashScreen"
android:label="#string/app_name"
android:screenOrientation="portrait"
android:theme="#android:style/Theme.Light.NoTitleBar.Fullscreen" >
>
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".HomeScreen"
android:label="#string/title_activity_home_screen"
android:screenOrientation="portrait" >
</activity>
<activity
android:name=".SignInScreen"
android:label="#string/title_activity_sign_in_screen"
android:screenOrientation="portrait" >
</activity>
<activity
android:name=".RegisterScreen"
android:label="#string/title_activity_register_screen"
android:screenOrientation="portrait" >
</activity>
<activity
android:name=".MyActivity"
android:label="#string/title_activity_my" >
</activity>
</application>
Problem:
getMenuInflater().inflate(R.menu.sign_in_screen, menu);
onBackPressed();
When the onCreateOptionsMenu is called that is where you go back to the last activity because you called onBackPressed which will destroy your current activity.
solution:
remove the onBackPressed
I am new to android app development. I am practicing some basics with a simple app. I was able to launch an activity from my app's home screen, however, when I try to launch a third
activity from activity2 using the same method, the app fails to work.
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_fish);
Button anthiasButton = (Button)findViewById(R.id.anthiasButton);
anthiasButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View arg0) {
Intent intent = new Intent(FishActivity.this, AnthiasActivity.class);
startActivity(intent);
}
});
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction()
.add(R.id.container, new PlaceholderFragment()).commit();
}
}
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.kdc.reeffishguide"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="19" />
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<activity
android:name="com.kdc.reeffishguide.MainActivity"
android:label="#string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name="com.kdc.reeffishguide.FishActivity"
android:label="#string/title_activity_fish" >
</activity>
<activity
android:name="com.kdc.reeffishguide.CoralActivity"
android:label="#string/title_activity_coral" >
</activity>
<activity
android:name="com.kdc.reeffishguide.InvertsActivity"
android:label="#string/title_activity_inverts" >
</activity>
<activity
android:name="com.kdc.reeffishguide.AnthiasActivity"
android:label="#string/title_activity_anthias" >
</activity>
</application>
</manifest>
I am trying to open AnthiasActivity from FishActivity. No errors or warnings are given in eclipse, but when I run the app and click on FishActivity the app closes. When I delete the portion of code in fish activity that is responsible for launching anthias Activity, fish activity opens, but obviously I cannot get to Anthias Activity
package com.kdc.reeffishguide;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.app.ActionBar;
import android.support.v4.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.os.Build;
public class AnthiasActivity extends ActionBarActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_anthias);
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction()
.add(R.id.container, new PlaceholderFragment()).commit();
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.anthias, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
/**
* A placeholder fragment containing a simple view.
*/
public static class PlaceholderFragment extends Fragment {
public PlaceholderFragment() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_anthias,
container, false);
return rootView;
}
}
}
here are the logcat errors.
04-12 19:24:32.427: E/QcrilMsgTunnelSocket(22517): IOExceptionjava.io.IOException: No such file or directoryReason: No such file or directory
04-12 19:24:36.421: E/QcrilMsgTunnelSocket(22517): IOExceptionjava.io.IOException: No such file or directoryReason: No such file or directory
04-12 19:24:40.425: E/QcrilMsgTunnelSocket(22517): IOExceptionjava.io.IOException: No such file or directoryReason: No such file or directory