2

我有兩個活動:主活動其他活動。在MainActivity片段啓動OtherActivity,但是當我按後退按鈕,在頂部,它返回我的MainActivity取而代之的是推出了OtherActivity的片段。從另一個活動返回後返回到MainActivity的片段?

最終結果是最終用戶被髮送回主屏幕而不是他們正在使用的片段。

這是我的清單。我已經設置MainActivity是的OtherActivity父:

<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=".OtherActivity" 
     android:parentActivityName="com.example.test.MainActivity" > 
    </activity> 

MainActivity,當用戶點擊一個按鈕,它加載列表片段:

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

    // ... 

    button.findViewById(R.id.events).setOnClickListener(new View.OnClickListener() { 

     Fragment ef = new MyItemsFragment(); 
     FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); 
     fragmentTransaction.addToBackStack(null); 
     fragmentTransaction.replace(R.id.content, ef, "my_fragment"); 
     fragmentTransaction.commit(); 
    }); 

} 

public void callOtherActivity() { 
    Intent i = new Intent(this, OtherActivity.class); 
    this.startActivity(i); 
} 

當項目在List Fragment中單擊,它啓動OtherActivity。很多代碼都是由android studio自動生成的。我改變了一些。在MyItemsRecyclerViewAdapter

@Override 
public void onBindViewHolder(final ViewHolder holder, int position) { 
    holder.mItem = mValues.get(position); 

    holder.mView.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      if (null != mListener) { 
       // Notify the active callbacks interface (the activity, if the 
       // fragment is attached to one) that an item has been selected. 
       mListener.onEventFragmentInteraction(holder.mItem); 

       MainActivity ma = (MainActivity) holder.mView.getContext(); 
       ma.callOtherActivity(); 

      } 
     } 
    }); 
} 

通知它調用,這是在MainActivity定義,將推出OtherActivity當點擊列表中的片段的項目。

這是OtherActivity

public class OtherActivity extends AppCompatActivity { 

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

} 

現在,當我點擊在OtherActivity後退箭頭按鈕,該應用程序將只顯示MainActivity,而不是名單片段用戶上次看到。

如何確保從OtherActivity返回時,用戶將再次看到列表片段以獲得更好的用戶體驗?

編輯:似乎有關於'後退'按鈕的混淆。也許他們是一樣的,但我在談論切換活動時的那個。它不是用於退出應用程序的後退按鈕。 See image

+0

嘗試在調用片段時刪除addToBackStack(null),並參見 –

+0

從清單文件中刪除android:parentActivityName =「com.example.test.MainActivity」並嘗試。無論您何時單擊後退按鈕,它都會基本啓動MainActivity新鮮activity.Please讓我知道如果我是錯的。 –

+0

只有一個「後退」按鈕,通常用於導航後退堆棧。我認爲你的更新是說你指的是「向上」按鈕。 https://developer.android.com/training/appbar/up-action。html – Kuffs

回答

0

只要刪除此行fragmentTransaction.addToBackStack(null);

0

你可以使用getSupportFragmentManager()getBackStackEntryCount()。方法在MainActivity的onBackPressed方法中。 OnClick底部系統後退按鈕。 按照下面的方法。

@Override 
public void onBackPressed() {  
int backstack = getSupportFragmentManager().getBackStackEntryCount(); 
if (backstack > 0) { 
     getSupportFragmentManager().popBackStack(); 
    } else { 
      super.onBackPressed(); 
      System.exit(0); 
     }} 

在片段中,按下頂部的後退按鈕。 試試這個, 在onCreate方法或片段調用這個默認的方法

setHasOptionsMenu(true); 

的onCreateView方法,然後覆蓋下面的方法:

@Override 
public boolean onOptionsItemSelected(MenuItem item) { 
    switch (item.getItemId()) { 
     case android.R.id.home: 
      getFragmentManager().popBackStack(); 
      break; 
     } 
     return super.onOptionsItemSelected(item); 
} 
0

您可以使用活動的結果,這個開始其他活動,併爲一旦你想完成OtherActivity只是做setResult,MainActivity會收到這個結果,並在那裏做下列

if (getSupportFragmentManager().getBackStackEntryCount() > 0) { 
     getSupportFragmentManager().popBackStack(); 
    } 

的代碼會是這樣的MainActivity

public void callOtherActivity() { 
    Intent i = new Intent(this, OtherActivity.class); 
    startActivityForResult(i, 1); 
} 

和OtherActivity的下面方法onBackPress調用。

Intent returnIntent = new Intent(); 
returnIntent.putExtra("result",result); 
setResult(Activity.RESULT_OK,returnIntent); 
finish(); 

現在在MainActivity onActivityresult

@Override 
    protected void onActivityResult(int requestCode, int resultCode, Intent data) { 
     if (requestCode == 1) { 
if (getSupportFragmentManager().getBackStackEntryCount() > 0) { 
      getSupportFragmentManager().popBackStack(); 
     } 
    } 
} 
0

當你開始一個新的活動,現有一個堆疊,所以你可以找回以後這樣的,當你按返回鍵。

按下返回鍵後,活動重新啓動。這是重要的部分。它不僅與上次使用時完全一樣。這意味着您作爲開發人員必須注意將活動恢復到您希望的狀態。任何碎片已經處於正確的狀態,但是當您的活動重新啓動時,您必須注意不要覆蓋該狀態。

在你的情況下,我懷疑你的MainActivity代碼是不加區分地重新初始化你的片段,而不是檢查片段是否已經存在了這個特定的活動,然後纔有條件地初始化它們。

很難肯定地說,因爲您的問題中沒有包含任何代碼。檢查在MainActivity中顯示片段的代碼。在顯示它們之前,你是否檢查是否有可見的碎片?如果不是,你應該是。

例如,下面的Activity中的代碼首先檢查一個片段是否已經顯示,然後再添加一個片段。實質上,第一次運行時,將不會有碎片,因此existing將爲空,並且將創建並顯示新的碎片。

當你開始一個新的OtherActivity等,然後用Back鍵返回到這個活動後,existing將不再爲空,因爲Fragment系統已經將任何現有的片段恢復回你的容器。所以我們實際上什麼都不做。

@Override 
protected void onCreate(Bundle b) { 
    super.onCreate(b); 

    Fragment existing = getSupportFragmentManager().findFragmentById(R.id.content); 

    if (existing == null) { 
     Fragment newFragment = new MyFragment(); 
     getSupportFragmentManager().beginTransaction() 
       .replace(R.id.content, newFragment) 
       .commit(); 
    } 

} 

希望這個很清楚。

+1

該片段已經加載了數據,所以我有'fragmentTransaction.addToBackStack(null);'。當主活動從其他活動返回後重新啓動時,我能不能從後臺堆棧恢復此操作嗎? – doejoe

+0

'R.id.content'實際上是主要活動的內容。這應該是片段,所以'.findFragmentByTag(「my_fragment」)',因爲我點擊按鈕後在交易中爲它創建了一個標籤?但是如果它存在,我如何使用它的現有數據加載它?如果沒有任何東西存在,您的示例將重新創建片段。 – doejoe

+0

我的建議(和代碼示例)相當籠統,因爲您沒有包含任何片段創建代碼。這可能是相關的,也可能不是,但這是我見過的人常犯的一個錯誤,你對問題的描述聽起來像是一個可能的原因。 – Kuffs