获取当前片段对象

时间:2011-07-19 15:47:16

标签: android android-fragments

main.xml我有

  <FrameLayout
        android:id="@+id/frameTitle"
        android:padding="5dp"
        android:layout_height="wrap_content"
        android:layout_width="fill_parent"
        android:background="@drawable/title_bg">
            <fragment
              android:name="com.fragment.TitleFragment"
              android:id="@+id/fragmentTag"
              android:layout_width="fill_parent"
              android:layout_height="wrap_content" />

  </FrameLayout>

我正在设置像这样的片段对象

FragmentManager fragmentManager = activity.getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
Fragment newFragment = new FragmentType1();
fragmentTransaction.replace(R.id.frameTitle, casinodetailFragment, "fragmentTag");

// fragmentTransaction.addToBackStack(null);
fragmentTransaction.commit();

它在不同的时间设置不同类型的Fragment对象(FragmentType2,FragmentType3,...)。现在,在某个时间点,我需要确定当前存在哪个对象。

简短我需要做以下事情:

Fragment currentFragment = //what is the way to get current fragment object in FrameLayout R.id.frameTitle

我尝试了以下

TitleFragment titleFragmentById = (TitleFragment) fragmentManager.findFragmentById(R.id.frameTitle);

    TitleFragment titleFragmentByTag = (TitleFragment) fragmentManager.findFragmentByTag("fragmentTag");

但是两个对象(titleFragmentById和titleFragmentByTag)都是null
我错过了什么吗? 我正在使用Compatibility Package, r3并正在开发API level 7

如果我们使用findFragmentById()findFragmentByTag()设置片段,

fragmentTransaction.replacefragmentTransaction.add将有效,但如果我们将对象设置为xml,则会return null就像我在main.xml中所做的那样。我想我的XML文件中缺少一些东西。

18 个答案:

答案 0 :(得分:246)

  

现在在某些时候我需要确定目前哪个对象

findFragmentById()上致电FragmentManager,确定R.id.frameTitle容器中的哪个片段。

答案 1 :(得分:99)

试试这个,

Fragment currentFragment = getActivity().getFragmentManager().findFragmentById(R.id.fragment_container);

这将给你当前片段,然后你可以将它与片段类进行比较并做你的事情。

    if (currentFragment instanceof NameOfYourFragmentClass) {
     Log.v(TAG, "find the current fragment");
  }

答案 2 :(得分:37)

我认为您可以使用 onAttachFragment 事件来捕获哪个片段处于活动状态。

@Override
public void onAttachFragment(Fragment fragment) {
    // TODO Auto-generated method stub
    super.onAttachFragment(fragment);

    Toast.makeText(getApplicationContext(), String.valueOf(fragment.getId()), Toast.LENGTH_SHORT).show();

}

答案 3 :(得分:11)

我认为你应该这样做:

Fragment currentFragment = fragmentManager.findFragmentByTag("fragmentTag");

原因是你将标签“fragmentTag”设置为你添加的最后一个片段(当你调用replace时)。

答案 4 :(得分:9)

可能会迟到但我希望它可以帮助其他人,同时@CommonsWare也会发布正确答案。

FragmentManager fm = getSupportFragmentManager();
Fragment fragment_byID = fm.findFragmentById(R.id.fragment_id);
//OR
Fragment fragment_byTag = fm.findFragmentByTag("fragment_tag");

答案 5 :(得分:9)

您可以获取片段列表并查看最后一个片段。

    FragmentManager fm = getSupportFragmentManager();
    List<Fragment> fragments = fm.getFragments();
    Fragment lastFragment = fragments.get(fragments.size() - 1);

但有时(当您向后导航时)列表大小保持不变,但最后一些元素为空。所以在列表中我迭代到最后一个非null片段并使用它。

    FragmentManager fm = getSupportFragmentManager();
    if (fm != null) {
        List<Fragment> fragments = fm.getFragments();
        for(int i = fragments.size() - 1; i >= 0; i--){
            Fragment fragment = fragments.get(i);
            if(fragment != null) {
                // found the current fragment

                // if you want to check for specific fragment class
                if(fragment instanceof YourFragmentClass) {
                    // do something
                }
                break;
            }
        }
    }

答案 6 :(得分:9)

这是最简单的解决方案,对我有用。

1。)你添加你的片段

ft.replace(R.id.container_layout, fragment_name, "fragment_tag").commit();

2)。

FragmentManager fragmentManager = getSupportFragmentManager();

Fragment currentFragment = fragmentManager.findFragmentById(R.id.container_layout);

if(currentFragment.getTag().equals("fragment_tag"))

{

 //Do something

}

else

{

//Do something

}

答案 7 :(得分:6)

也许最简单的方法是:

public MyFragment getVisibleFragment(){
    FragmentManager fragmentManager = MainActivity.this.getSupportFragmentManager();
    List<Fragment> fragments = fragmentManager.getFragments();
    for(Fragment fragment : fragments){
        if(fragment != null && fragment.getUserVisibleHint())
            return (MyFragment)fragment;
    }
    return null;
}

它对我有用

答案 8 :(得分:4)

我知道已经有一段时间了,但我会在这里,以防它帮助某人。

到目前为止正确答案是(和选定的)来自CommonsWare的那个。我遇到了与发布相同的问题,以下

MyFragmentClass fragmentList = 
            (MyFragmentClass) getSupportFragmentManager().findFragmentById(R.id.fragementID);

继续返回null。我的错误非常愚蠢,在我的xml文件中:

<fragment
    android:tag="@+id/fragementID"
    android:name="com.sf.lidgit_android.content.MyFragmentClass"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
/>

错误在于我有 android:tag INSTEAD OF android:id

答案 9 :(得分:4)

您可以在父级活动类中创建字段:

public class MainActivity extends AppCompatActivity {

    public Fragment fr;

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

}

然后在每个片段类中:

public class SomeFragment extends Fragment {

@Override
    public View onCreateView(LayoutInflater inflater,
                             ViewGroup container, Bundle savedInstanceState) {

        ((MainActivity) getActivity()).fr = this;
}

你的&#39; fr&#39;字段是当前片段对象

它也在使用popBackStack()

答案 10 :(得分:2)

如果您正在使用BackStack ......并且仅在使用后台堆栈时,请尝试以下操作:

rivate Fragment returnToPreviousFragment() {

    FragmentManager fm = getSupportFragmentManager();

    Fragment topFrag = null;

    int idx = fm.getBackStackEntryCount();
    if (idx > 1) {
        BackStackEntry entry = fm.getBackStackEntryAt(idx - 2);
        topFrag = fm.findFragmentByTag(entry.getName());
    }

    fm.popBackStack();

    return topFrag;
}

答案 11 :(得分:2)

@Hammer响应对我有用,我用来控制一个浮动动作按钮

final FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(final View view) {
            android.app.Fragment currentFragment = getFragmentManager().findFragmentById(R.id.content_frame);
            Log.d("VIE",String.valueOf(currentFragment));
            if (currentFragment instanceof PerfilFragment) {
                PerfilEdit(view, fab);
            }
        }
});

答案 12 :(得分:2)

  1. 使用onStart方法检查(活动容器中的哪个片段);

    @Override
    protected void onStart() {
    super.onStart();
    Fragment fragmentCurrent = getSupportFragmentManager.findFragmentById(R.id.constraintLayout___activity_main___container);
    }
    
  2. 一些检查:

    if (fragmentCurrent instanceof MenuFragment) 
    

答案 13 :(得分:0)

如果您要在活动的XML布局中定义片段,请在Activity中确保在致电setContentView()之前致电findFragmentById()

答案 14 :(得分:0)

如果要从AbstractActivity扩展,则可以使用getFragments()方法:

for (Fragment f : getFragments()) {
    if (f instanceof YourClass) {
        // do stuff here
    }
}

答案 15 :(得分:0)

这将为您提供当前的片段类名称->

String fr_name = getSupportFragmentManager().findFragmentById(R.id.fragment_container).getClass().getSimpleName();

答案 16 :(得分:0)

您可以检查当前由哪个片段加载

        supportFragmentManager.addOnBackStackChangedListener {
        val myFragment = supportFragmentManager.fragments.last()

        if (null != myFragment && myFragment is HomeFragment) {
            //HomeFragment is visible or currently loaded
        } else {
            //your code
        }
    }

答案 17 :(得分:0)

我最近参与了一个涉及多个片段的活动,因此想分享我在这里使用的方法:

首先,我声明了一个函数 getCurrentFragment() 返回我,是的,你猜对了,当前片段,哈哈。

private fun getCurrentFragment(): Fragment? {
    return supportFragmentManager.findFragmentById(R.id.fragmentContainerView)
}

然后我覆盖活动中的 onBackPressed 函数以定义片段内的导航。假设,如果用户在片段 3 中并按回,我想显示片段 2,所以我做了这样的事情来实现这一点

override fun onBackPressed() {
        if (getCurrentFragment() is Fragment3) {
            showFragment2()
        } else {
            super.onBackPressed()
        }
    }

在 showFragment2() 中我做了这样的事情:

private fun showFragment2() {
        val fragment = Fragment2.newInstance()
        supportFragmentManager.commit {
            replace(R.id.FragmentContainerView, fragment, "Add a tag here")
        }
    }

我认为这应该给那些正在寻找如何在 Activity 中浏览片段的人提供更好的想法。