2017-03-15 67 views
1

我對Fragment.isVisible()應該如何工作感到困惑。即使在Activity.create()中添加了片段,即使使用FragmentManager.commitNow()Fragment.isVisible()也會返回false。Fragment.isVisible()即使在添加了片段並且可見時也會返回false

Fragment.isVisible()即使在onResume()中也返回錯誤。但是,當點擊一個UI按鈕時,返回的值是正確的。

public class MainActivity extends AppCompatActivity implements View.OnClickListener { 

public final static String TAG = "HideFragmentOnChange"; 

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

    ((Button)findViewById(R.id.my_button)).setOnClickListener(this); 

    if(savedInstanceState == null){ 
     Fragment fragmentA = new FragmentA(); 

     Log.d(TAG, "onCreate: Before FragmentTransaction FragA: " + (fragmentA.isVisible() ? "visible" : "not visible")); 

     getSupportFragmentManager().beginTransaction() 
       .add(R.id.fragment_container, fragmentA, "fragA") 
       .commitNow(); 

     Log.d(TAG, "onCreate: After FragmentTransaction FragA: " + (fragmentA.isVisible() ? "visible" : "not visible")); 

    } 

    this.runOnUiThread(new Runnable(){ 
     @Override 
     public void run() { 
      Fragment fragA = getSupportFragmentManager().findFragmentByTag("fragA"); 
      Log.d(TAG, "runOnUiThread after onCreate(): FragA: " + (fragA.isVisible() ? "visible" : "not visible")); 
     } 
    }); 
} 

@Override 
protected void onResume() { 
    super.onResume(); 

    Fragment fragA = getSupportFragmentManager().findFragmentByTag("fragA"); 
    Log.d(TAG, "onResume: FragA: " + (fragA.isVisible() ? "visible" : "not visible")); 

    this.runOnUiThread(new Runnable(){ 
     @Override 
     public void run() { 
      Fragment fragA = getSupportFragmentManager().findFragmentByTag("fragA"); 
      Log.d(TAG, "runOnUiThread after onResume(): FragA: " + (fragA.isVisible() ? "visible" : "not visible")); 
     } 
    }); 
} 

@Override 
public void onClick(View v) { 
    Fragment fragmentA = getSupportFragmentManager().findFragmentByTag("fragA"); 
    Log.d(TAG, "onClick(): FragA: " + (fragmentA.isVisible() ? "visible" : "not visible")); 
} 

}

我最初以爲也許是因爲主線程一直沒有尚未運行的機會和FragmentTransaction不充分和適當地提交到以後的點。但是,撥打runOnUiThread不會更改返回值isVisible()

我附上日誌以供參考。

03-15 17:22:34.978 14094-14094/ D/HideFragmentOnChange: onCreate: Before FragmentTransaction FragA: not visible 
03-15 17:22:34.990 14094-14094/ D/HideFragmentOnChange: onCreate: After FragmentTransaction FragA: not visible 
03-15 17:22:34.991 14094-14094/ D/HideFragmentOnChange: runOnUiThread after onCreate(): FragA: not visible 
03-15 17:22:34.996 14094-14094/ D/HideFragmentOnChange: onResume: FragA: not visible 
03-15 17:22:34.996 14094-14094/ D/HideFragmentOnChange: runOnUiThread after onResume(): FragA: not visible 
03-15 17:22:56.683 14094-14094/ D/HideFragmentOnChange: onClick(): FragA: visible 

爲什麼Fragment.isVisible()似乎有這麼大的延遲返回正確的值?

我正在使用支持庫25.2並支持庫碎片,儘管本機碎片產生了相同的行爲。

回答

0

你必須記住,碎片也有他自己的生命週期。你基本上是在過早地調用它。如果

Fragment#isVisible

返回真,如果片段是當前用戶可見的片段是視爲可見。這意味着:(1)已被添加,(2)已將其視圖附加到窗口,並且(3)未隱藏。

看到這個SO發佈有關活動的整個生命週期/片段 When is onAttach called during the Fragment LifeCycle?

1

您可以使用setUserVisibleHint

形式的Documentation

設置的提示,系統是否該片段的用戶界面當前爲 對用戶可見。此提示默認爲true,並跨片段實例狀態保存和恢復持久 。

要使用它:

private static boolean isVisible; 

@Override 
public void setUserVisibleHint(boolean isVisibleToUser) { 
    super.setUserVisibleHint(isVisibleToUser); 
    isVisible = isVisibleToUser; 

    if (isVisible) { 
     Log.d("TAG", "this fragment is visible"); 
    } else { 
     Log.d("TAG", "this fragment is invisible"); 
    } 
} 
1

沒有爲片段的方法:

 getUserVisibleHint(); 

可以在official document找到更多信息。

它在片段對用戶可見時給出「true」,當它不可見時給出「false」。

享受!

+0

這個工作,非常感謝!!!!!! –

0

我注意到,在打開一個片段和經歷所有的生命週期 (onAttach,的onCreate,在onStart等),要求從可見性的onResume()()將返回。但是,如果您只停止片段(即按Home按鈕),isVisible()將返回true。 結論:保持類布爾標誌:

private mFirstTimeVisible = true; 

,並在下面的onResume檢查使用它:

@Override 
    public void onResume() { 
     super.onResume(); 
     if (mFistTimeVisible || isVisible()) { 
      //your code... 
     } 
     mFistTimeVisible = false; 
    } 
相關問題