如何获取当前显示的片段?

时间:2012-02-15 13:49:03

标签: android android-layout android-intent android-fragments

我在Android中玩片段。

我知道我可以使用以下代码更改片段:

FragmentManager fragMgr = getSupportFragmentManager();
FragmentTransaction fragTrans = fragMgr.beginTransaction();

MyFragment myFragment = new MyFragment(); //my custom fragment

fragTrans.replace(android.R.id.content, myFragment);
fragTrans.addToBackStack(null);
fragTrans.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
fragTrans.commit();

我的问题是,在Java文件中,如何获取当前显示的Fragment实例?

53 个答案:

答案 0 :(得分:419)

在交易中添加片段时,您应该使用标记。

fragTrans.replace(android.R.id.content, myFragment, "MY_FRAGMENT");

...稍后如果要检查片段是否可见:

MyFragment myFragment = (MyFragment)getFragmentManager().findFragmentByTag("MY_FRAGMENT");
if (myFragment != null && myFragment.isVisible()) {
   // add your code here
}

另见http://developer.android.com/reference/android/app/Fragment.html

答案 1 :(得分:364)

我知道这是一个老帖子,但之前也遇到了麻烦。找到了一个在onBackStackChanged()监听功能

中执行此操作的解决方案
  @Override
    public void onBackPressed() {
        super.onBackPressed();

         Fragment f = getActivity().getFragmentManager().findFragmentById(R.id.fragment_container);
      if(f instanceof CustomFragmentClass) 
        // do something with f
        ((CustomFragmentClass) f).doSomething();

    }

这对我有用,因为我不想遍历每个片段,我必须找到一个可见的片段。希望它也可以帮助其他人。

答案 2 :(得分:139)

这是我的解决方案,我觉得它很方便用于低碎片方案

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

答案 3 :(得分:75)

每当你展示片段时,你必须将它贴在backstack中:

FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.setTransition(FragmentTransaction.TRANSIT_ENTER_MASK);       
ft.add(R.id.primaryLayout, fragment, tag);
ft.addToBackStack(tag);
ft.commit();        

然后,当您需要获取当前片段时,您可以使用此方法:

public BaseFragment getActiveFragment() {
    if (getSupportFragmentManager().getBackStackEntryCount() == 0) {
        return null;
    }
    String tag = getSupportFragmentManager().getBackStackEntryAt(getSupportFragmentManager().getBackStackEntryCount() - 1).getName();
    return (BaseFragment) getSupportFragmentManager().findFragmentByTag(tag);
}

答案 4 :(得分:21)

我用来查找当前显示片段的是以下代码。它很简单,现在对我有用。它在包含片段的活动中运行

    FragmentManager fragManager = this.getSupportFragmentManager();
    int count = this.getSupportFragmentManager().getBackStackEntryCount();
    Fragment frag = fragManager.getFragments().get(count>0?count-1:count);

答案 5 :(得分:14)

reactive方式:

Observable.from(getSupportFragmentManager().getFragments())
    .filter(fragment -> fragment.isVisible())
    .subscribe(fragment1 -> {
        // Do something with it
    }, throwable1 -> {
        // 
    });

答案 6 :(得分:11)

我的方法基于try / catch,如下所示:

MyFragment viewer = null;
    if(getFragmentManager().findFragmentByTag(MY_TAG_FRAGMENT) instanceOf MyFragment){
    viewer = (MyFragment) getFragmentManager().findFragmentByTag(MY_TAG_FRAGMENT);
}

但可能有更好的方法......

答案 7 :(得分:8)

如果您使用的是AndroidX Navigation

val currentFragment = findNavController(R.id.your_navhost).?currentDestination

有关此导航组件的更多信息: https://developer.android.com/guide/navigation/navigation-getting-started

答案 8 :(得分:8)

嗯,这个问题得到了很多观点和关注,但仍然没有包含 我最简单的解决方案 - 使用getFragments()。

int/unsigned

答案 9 :(得分:7)

有点晚了,但是对于任何有兴趣的人: 如果您知道FragmentManager中所需片段的索引,只需获取对它的引用并检查isMenuVisible()函数!在这里:

getSupportFragmentManager().getFragments().get(0).isMenuVisible()

如果true对用户可见,等等!

答案 10 :(得分:7)

1)

ft.replace(R.id.content_frame, fragment, **tag**).commit();

2)

FragmentManager fragmentManager = getSupportFragmentManager();
Fragment currentFragment = fragmentManager.findFragmentById(R.id.content_frame);

3)

if (currentFragment.getTag().equals(**"Fragment_Main"**))
{
 //Do something
}
else
if (currentFragment.getTag().equals(**"Fragment_DM"**))
{
//Do something
}

答案 11 :(得分:5)

findFragmentById()中有一个名为SupportFragmentManager的方法。我在活动容器中使用它,如:

public Fragment currentFragment(){
    return getSupportFragmentManager().findFragmentById(R.id.activity_newsfeed_frame);
}

这就是获取当前Fragment的方法。如果您有自定义Fragment并且需要检查Fragment是什么,我通常会使用instanceof

if (currentFragment() instanceof MyFrag){
    // Do something here
}

答案 12 :(得分:5)

科特琳的方式;

val currentFragment = supportFragmentManager.fragments.last()

答案 13 :(得分:5)

受到 Tainy 的回答的启发,这是我的两分钱。从大多数其他实现中修改很少。

private Fragment getCurrentFragment() {
    FragmentManager fragmentManager = myActivity.getSupportFragmentManager();
    int stackCount = fragmentManager.getBackStackEntryCount();
    if( fragmentManager.getFragments() != null ) return fragmentManager.getFragments().get( stackCount > 0 ? stackCount-1 : stackCount );
    else return null;
}

"myActivity"替换为&#34;此&#34;如果是您当前的活动或使用您的活动参考。

答案 14 :(得分:4)

如果到达这里并且您正在使用科特林:

var fragment = supportFragmentManager.findFragmentById(R.id.fragment_container)

R.id.fragment_containerid在其fragment上出现的activity

或者,如果您需要更好的解决方案:

supportFragmentManager.findFragmentById(R.id.content_main)?.let {
    // the fragment exists

    if (it is FooFragment) {
        // The presented fragment is FooFragment type
    }
}

答案 15 :(得分:4)

您可以查询哪些片段已加载到您的“活动”内容框架中,并检索片段类或片段的简单名称&#39; (作为一个字符串)。

public String getCurrentFragment(){
     return activity.getSupportFragmentManager().findFragmentById(R.id.content_frame).getClass().getSimpleName();
}

用法:

Log.d(TAG, getCurrentFragment());

输出:

D/MainActivity: FragOne

答案 16 :(得分:4)

Sev's answer适用于您点击后退按钮或以其他方式更改后台堆栈时。

但是,我做了一些略有不同的事情。我在基础Fragment及其派生的片段上设置了一个backstack change listener,这段代码在监听器中:

Fragment f = getActivity().getSupportFragmentManager().findFragmentById(R.id.container);

if (f.getClass().equals(getClass())) {
    // On back button, or popBackStack(),
    // the fragment that's becoming visible executes here,
    // but not the one being popped, or others on the back stack

    // So, for my case, I can change action bar bg color per fragment
}

答案 17 :(得分:4)

这是获取当前片段的简单方法..

getFragmentManager().addOnBackStackChangedListener(new FragmentManager.OnBackStackChangedListener() {
  @Override public void onBackStackChanged() {
    currentFragment = fragmentManager.findFragmentById(R.id.content);
    if (currentFragment !=  null && (currentFragment instanceof LoginScreenFragment)) {
      logout.setVisibility(View.GONE);
    } else {
      logout.setVisibility(View.VISIBLE);
    }
  }
});

答案 18 :(得分:4)

简便的方法:

Fragment fr=getSupportFragmentManager().findFragmentById(R.id.fragment_container);
String fragmentName = fr.getClass().getSimpleName();

答案 19 :(得分:3)

签出此解决方案。它为我工作,以获取当前的片段。

if(getSupportFragmentManager().getBackStackEntryCount() > 0){
        android.support.v4.app.Fragment f = 
         getSupportFragmentManager().findFragmentById(R.id.fragment_container);
        if(f instanceof ProfileFragment){
            Log.d(TAG, "Profile Fragment");
        }else if(f instanceof SavedLocationsFragment){
            Log.d(TAG, "SavedLocations Fragment");
        }else if(f instanceof AddLocationFragment){
            Log.d(TAG, "Add Locations Fragment");
        }

答案 20 :(得分:3)

如果您从父活动中获取片段的当前实例,则可以

findFragmentByID(R.id.container);

这实际上是在视图中填充的当前片段实例。我遇到过同样的问题。我不得不加载相同的片段两次,一个在backstack上。

以下方法无效。它只是得到一个带有标签的Fragment。不要在这种方法上浪费你的时间。我确信它有它的用途,但要获得同一片段的最新版本不是其中之一。

findFragmentByTag()

答案 21 :(得分:3)

这对我有用。我希望这会对某人有所帮助。

答案 22 :(得分:2)

这是Kotlin解决方案:

if ( this.getSupportFragmentManager().getBackStackEntryCount()>0 ) {
    var fgmt = this.getSupportFragmentManager().fragments[this.getSupportFragmentManager().getBackStackEntryCount()-1]
    if( fgmt is FgmtClassName ) {
        (fgmt as FgmtClassName).doSth()
    }
}

简化方式:

with ( this.getSupportFragmentManager() ) {
    if ( getBackStackEntryCount()>0 ) {
        var fgmt = fragments[getBackStackEntryCount()-1]
        if ( fgmt is FgmtClassName ) {
            (fgmt as FgmtClassName).doSth()
        }
    }
}

答案 23 :(得分:2)

以上30个答案中没有一个对我完全有效。但这是有效的答案:

在使用导航组件时使用Kotlin:

fun currentVisibleFragment(): Fragment? {
    return supportFragmentManager.fragments.first()?.getChildFragmentManager()?.getFragments()?.get(0)
}

答案 24 :(得分:2)

final FragmentManager fm=this.getSupportFragmentManager();
final Fragment fragment=fm.findFragmentByTag("MY_FRAGMENT");

if(fragment != null && fragment.isVisible()){
      Log.i("TAG","my fragment is visible");
}
else{
      Log.i("TAG","my fragment is not visible");
}

答案 25 :(得分:1)

这应该有效 -

val visibleFragment = supportFragmentManager.fragments.findLast { fgm -> fgm.isVisible }
Timber.d("backStackIterator: visibleFragment: $visibleFragment")

答案 26 :(得分:1)

我遇到了类似的问题,我想知道按下后退键时最后显示的片段。我使用了一个非常简单的解决方案,对我有用。每次我打开一个片段,在onCreate()方法中,我在我的单例中设置一个变量(用你的片段名称替换“myFragment”)

MySingleton.currentFragment = myFragment.class;

变量在单例中声明为

public static Class currentFragment = null; 

然后在onBackPressed()中检查

    if (MySingleton.currentFragment == myFragment.class){
        // do something
        return;
    }
    super.onBackPressed();

确保调用super.onBackPressed();在“返回”之后,否则应用程序将处理后退密钥,在我的情况下导致应用程序终止。

答案 27 :(得分:1)

对于滚动片段,当您使用ViewPager类的实例时,假设mVeiwPager,您可以调用mViewPager.getCurrentItem()来获取当前片段的int数。

在MainLayout.xml中

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true"
    android:orientation="vertical"
    tools:context="unidesign.photo360.MainActivity">

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:fitsSystemWindows="false"
        android:theme="@style/AppTheme.AppBarOverlay"
        app:expanded="false">

        <android.support.v7.widget.Toolbar
            android:id="@+id/main_activity_toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            app:popupTheme="@style/AppTheme.PopupOverlay"
            app:title="@string/app_name">

        </android.support.v7.widget.Toolbar>

    </android.support.design.widget.AppBarLayout>


    <android.support.v4.view.ViewPager
        android:id="@+id/view_pager"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

    </android.support.v4.view.ViewPager>
    
</android.support.design.widget.CoordinatorLayout>

MainActivity.kt中的

class MainActivity : AppCompatActivity() {
    
        lateinit var mViewPager: ViewPager
        lateinit var pageAdapter: PageAdapter
        
//      ...
    
        override fun onCreate(savedInstanceState: Bundle?) {
            super.onCreate(savedInstanceState)
            setContentView(R.layout.activity_main)
            
            pageAdapter = PageAdapter(supportFragmentManager)
            mViewPager = findViewById(R.id.view_pager)
//          ...
            }
            
        override fun onResume() {
          super.onResume()
          var currentFragment = pageAdapter.getItem(mViewPager.currentItem)
//         ...
          }

答案 28 :(得分:1)

您也可以使用logcat中的URL轻松完成此操作,该URL将您重定向到当前片段源代码的源代码。首先,您需要在主机活动(例如-

)中添加 OnBackStackChangedListener
activity.getChildFragmentManager().addOnBackStackChangedListener(backStackListener);

OnBackStackChangedListener 实现是-

    public FragmentManager.OnBackStackChangedListener backStackListener = () -> {

    String simpleName = "";
    String stackName = getStackTopName().trim();

    if (Validator.isValid(stackName) && stackName.length() > 0) {

      simpleName = stackName.substring(Objects.requireNonNull(stackName).lastIndexOf('.') + 1).trim();

      List<Fragment >
       fragmentList = getChildFragmentManager().getFragments();
      Fragment myCurrentFragment;

      for (int i = 0; i < fragmentList.size(); i++) {
       myCurrentFragment= fragmentList.get(i);
       if (myCurrentFragment.getClass().getSimpleName().equals(simpleName)) {
        //Now you get the current displaying fragment assigned in myCurrentFragment.
        break;
       }
       myFragment = null;
      }
     }


     //The code below is for the source code redirectable logcat which would be optional for you.
     StackTraceElement stackTraceElement = new StackTraceElement(simpleName, "", simpleName + ".java", 50);
     String fileName = stackTraceElement.getFileName();
     if (fileName == null) fileName = "";
     final String info = "Current Fragment is:" + "(" + fileName + ":" +
     stackTraceElement.getLineNumber() + ")";
     Log.d("now", info + "\n\n");
    };

getStackTopName()方法是-

public String getStackTopName() {
    FragmentManager.BackStackEntry backEntry = null;
    FragmentManager fragmentManager = getChildFragmentManager();
    if (fragmentManager != null) {
        if (getChildFragmentManager().getBackStackEntryCount() > 0)
            backEntry = getChildFragmentManager().getBackStackEntryAt(
                    getChildFragmentManager().getBackStackEntryCount() - 1
            );
    }
    return backEntry != null ? backEntry.getName() : null;
}

答案 29 :(得分:1)

在主要活动中,当新片段附加到活动时,将调用onAttachFragment(片段片段)方法。在此方法中,您可以获取当前片段的实例。但是,当从backstack弹出一个片段时,即当按下后退按钮以将顶部片段放在堆栈顶部时,不会调用onAttachFragment方法。我仍在寻找一种回调方法,当一个片段在活动中变得可见时,该方法在主要活动中被触发。

答案 30 :(得分:1)

如果您使用的是Jetpack导航库:

import requests from bs4 import BeautifulSoup import pandas as pd params = { "pos": "all", "stats": "bat", "type": "fangraphsdc" } data = { 'RadScriptManager1_TSM': 'ProjectionBoard1$dg1', "__EVENTTARGET": "ProjectionBoard1$dg1", '__EVENTARGUMENT': 'FireCommand:ProjectionBoard1$dg1$ctl00;PageSize;1000', '__VIEWSTATEGENERATOR': 'C239D6F0', '__SCROLLPOSITIONX': '0', '__SCROLLPOSITIONY': '1366', "ProjectionBoard1_tsStats_ClientState": "{\"selectedIndexes\":[\"0\"],\"logEntries\":[],\"scrollState\":{}}", "ProjectionBoard1_tsPosition_ClientState": "{\"selectedIndexes\":[\"0\"],\"logEntries\":[],\"scrollState\":{}}", "ProjectionBoard1$rcbTeam": "All+Teams", "ProjectionBoard1_rcbTeam_ClientState": "", "ProjectionBoard1$rcbLeague": "All", "ProjectionBoard1_rcbLeague_ClientState": "", "ProjectionBoard1_tsProj_ClientState": "{\"selectedIndexes\":[\"5\"],\"logEntries\":[],\"scrollState\":{}}", "ProjectionBoard1_tsUpdate_ClientState": "{\"selectedIndexes\":[],\"logEntries\":[],\"scrollState\":{}}", "ProjectionBoard1$dg1$ctl00$ctl02$ctl00$PageSizeComboBox": "30", "ProjectionBoard1_dg1_ctl00_ctl02_ctl00_PageSizeComboBox_ClientState": "", "ProjectionBoard1$dg1$ctl00$ctl03$ctl01$PageSizeComboBox": "1000", "ProjectionBoard1_dg1_ctl00_ctl03_ctl01_PageSizeComboBox_ClientState": "{\"logEntries\":[],\"value\":\"1000\",\"text\":\"1000\",\"enabled\":true,\"checkedIndices\":[],\"checkedItemsTextOverflows\":false}", "ProjectionBoard1_dg1_ClientState": "" } def main(url): with requests.Session() as req: r = req.get(url, params=params) soup = BeautifulSoup(r.content, 'html.parser') data['__VIEWSTATE'] = soup.find("input", id="__VIEWSTATE").get("value") data['__EVENTVALIDATION'] = soup.find( "input", id="__EVENTVALIDATION").get("value") r = req.post(url, params=params, data=data) df = pd.read_html(r.content, attrs={ 'id': 'ProjectionBoard1_dg1_ctl00'})[0] df.drop(df.columns[1], axis=1, inplace=True) print(df) df.to_csv("data.csv", index=False) main("https://www.fangraphs.com/projections.aspx")

答案 31 :(得分:1)

科特林比这里暴露的方法更安全

supportFragmentManager.fragments.lastOrNull()?.let { currentFragment ->
               
      //Do something here
 }

答案 32 :(得分:1)

我最近不得不这样做

public Fragment getCurrentFragment() {
     return fragmentManager.findFragmentById(R.id.container);
}

最后我得到了这个容器的最后一个片段。

答案 33 :(得分:0)

  SupportFragmentManager.BeginTransaction().Replace(Resource.Id.patientFrameHome, test, "Test").CommitAllowingStateLoss();  

var fragment = SupportFragmentManager.FindFragmentByTag("Test") as V4Fragment;

  if (fragment == null && fragment.IsVisiable is true)
{
}

答案 34 :(得分:0)

非常简单,不需要编写太多代码     yourFragment.isAdded() 要么     yourFragment.isVisible();

我更喜欢iFyreed(),它们都返回boolean值,如果在if条件下使用它,则必须在onCreate()中初始化您的片段,否则会得到空点异常。

答案 35 :(得分:0)

谁在 2021 年搜索它 只需这样做:(R.id.fragment 是您的容器的 id)

    val activeFragment  = this.supportFragmentManager.findFragmentById(R.id.fragment)?.childFragmentManager?.primaryNavigationFragment

    if (activeFragment is DetailFragment){
        (activeFragment as DetailFragment).onPermissionResult(permissionGranted)
    }

答案 36 :(得分:0)

我发现findFragmentByTag不太方便。如果您的String currentFragmentTag或父Activity中有Fragment,则需要将其保存在onSaveInstanceState中并在onCreate中进行恢复。即使这样做,在重新创建Activity时,onAttachFragment也会在onCreate之前调用,因此您不能在currentFragmentTag中使用onAttachFragment(例如,更新一些基于currentFragmentTag的视图,因为它可能尚未还原。

我使用以下代码:

Fragment getCurrentFragment() {
    List<Fragment> fragments = getSupportFragmentManager().getFragments();
    if(fragments.isEmpty()) {
        return null;
    }
    return fragments.get(fragments.size()-1);
}

FragmentManager的文档指出

  

列表中片段的顺序是添加或附加片段的顺序。

当您需要根据当前片段类型进行操作时,只需使用getCurrentFragment() instance of MyFragment而不是currentFragmentTag.equals("my_fragment_tag")

请注意,getCurrentFragment()中的onAttachFragment不会得到附件Fragment,而是前一个附件。

答案 37 :(得分:0)

如果getFragmentManager()不起作用,则尝试使用getSupportFragmentManager()并在加载片段时添加一个标签。

String fn = "/resources/files/censusTemplates/SimpleStandardTemplate.xlsm";

    try {
        InputStream inputStream = new URL("file:///"  + fn).openStream();

答案 38 :(得分:0)

getSupportFragmentManager().findFragmentById(R.id.content_frame).getClass().getSimpleName();

嗯,我想这是对这个问题最直接的答案。 我希望这会有所帮助。

答案 39 :(得分:0)

如果您嵌套了片段,例如viewpagers中的viewpagers等 并且您想获取所有嵌套的片段。

感谢Matt Mombrea answer的一些调整版本。

private List<Fragment> getVisibleFragments(List<Fragment> searchFragments, List<Fragment> visibleFragments) {
    if (searchFragments != null && searchFragments.size() > 0) {
        for (Fragment fragment : searchFragments) {
            List<Fragment> nestedFragments = new ArrayList<>();
            List<Fragment> childFMFragments = fragment.getChildFragmentManager().getFragments();
            List<Fragment> fmFragments = fragment.getFragmentManager().getFragments();
            fmFragments.retainAll(childFMFragments);
            nestedFragments.addAll(childFMFragments);
            nestedFragments.addAll(fmFragments);
            getVisibleFragments(nestedFragments, visibleFragments);
            if (fragment != null && fragment.isVisible()) {
                visibleFragments.add(fragment);
            }
        }
    }
    return visibleFragments;
}

这是用法:

List<Fragment> allVisibleFragments = getVisibleFragments(searchFragments, visibleFragments);

例如:

List<Fragment> visibleFragments = new ArrayList<>();
List<Fragment> searchFragments = MainActivity.this.getSupportFragmentManager().getFragments();
Toast.makeText(this, ""+getVisibleFragments(searchFragments, visibleFragments), Toast.LENGTH_LONG).show();

答案 40 :(得分:0)

我最近不得不这样做,这里没有一个答案真的适合这种情况。

如果您确信只有一个片段是可见的(全屏显示),那么您真的想查找后端堆栈顶部的内容。例如,作为Kotlin的{​​{1}}:

Fragment

并像这样使用它:

import androidx.fragment.app.Fragment

fun Fragment.setVisibilityChangeListener(clazz: Class<out Fragment>, listener: (Boolean) -> Unit) {
    fragmentManager?.run {
        addOnBackStackChangedListener {
            val topFragmentTag = getBackStackEntryAt(backStackEntryCount - 1).name
            val topFragment = findFragmentByTag(topFragmentTag)
            listener(topFragment != null && topFragment::class.java == clazz)
        }
    }
}

答案 41 :(得分:0)

如果您使用支持库v13,则此问题已修复,您只需覆盖:

@Override
public void setUserVisibleHint(boolean isVisibleToUser)
{
    // TODO Auto-generated method stub
    super.setUserVisibleHint(isVisibleToUser);
}

问题是,你不能混合两者,因为片段与版本4的片段类不兼容。

如果您不使用V4支持lib,请将setPrimaryItem方法覆盖到FragmentStatePagerAdapter。

我用它来更新大名单中的Actionbat标题。

答案 42 :(得分:0)

我也坚持这一点。我最终做了什么,只是声明了一系列片段:

private static PlaceholderFragment[] arrFrg;

(在我的例子中是PlaceholderFragment)并将所有thsess Fragemnts打包到这个数组中而没有标记:)

        public static PlaceholderFragment newInstance(int sectionNumber) {
            final PlaceholderFragment fragment = new PlaceholderFragment();
            Bundle args = new Bundle();
            args.putInt(ARG_SECTION_NUMBER, sectionNumber);
            fragment.setArguments(args);
            arrFrg[sectionNumber] = fragment;

            return fragment;
}

然后您可以轻松访问当前显示的片段:

arrFrg[mViewPager.getCurrentItem()];

据我所知,这可能不是最佳解决方案,但它对我来说非常有用:)

答案 43 :(得分:0)

这是最好的方式:

       android.app.Fragment currentFragment=getFragmentManager().findFragmentById(R.id.main_container);
            if(currentFragment!=null)
            {
                String[] currentFragmentName = currentFragment.toString().split("\\{");
                if (currentFragmentName[0].toString().equalsIgnoreCase("HomeSubjectFragment"))
                {
                    fragment = new HomeStagesFragment();
                    tx = getSupportFragmentManager().beginTransaction();
                    tx.replace(R.id.main_container, fragment);
                    tx.addToBackStack(null);
                    tx.commit();
                }
                else if(currentFragmentName[0].toString().equalsIgnoreCase("HomeStagesFragment"))
                {
                    new AlertDialog.Builder(this)
                            .setMessage("Are you sure you want to exit?")
                            .setCancelable(false)
                            .setPositiveButton("Yes", new DialogInterface.OnClickListener() {
                                public void onClick(DialogInterface dialog, int id) {
                                    finish();
                                }
                            })
                            .setNegativeButton("No", null)
                            .show();
                }

            }

别忘了在标题中定义:

private Fragment fragment;
FragmentTransaction tx;

答案 44 :(得分:0)

好吧,我想你想知道你在哪个片段中 我想有一种解决方案我不认为它是最好的 但它的确有效 首先

你应该创建它扩展Fragment

的父片段
public class Fragment2 extends Fragment {
    private static position;
    public static int getPosition() {
        return position;
    }

    public static void setPosition(int position) {
        FragmentSecondParent.position = position;
    }
}

第二

你应该在每个片段和onCreateView

中的每次写入中扩展它
setPosition(//your fragmentposition here)

<强>第三

你想要获取当前片段

写这个

Fragment2 fragment= (Fragment2) getSupportFragmentManager()
    .findFragmentById(R.id.fragment_status);

int position = fragment.getPosition();
if(//position condition)
{
    //your code here
}

答案 45 :(得分:0)

也许最简单的方法是:

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;
}

它对我有用

答案 46 :(得分:0)

您好我知道这是一个非常古老的问题,但我想分享我自己的解决方案..

为了获得用户浏览的片段列表,我创建了一个帮助类:

public class MyHelperClass{

    private static ArrayList<Fragment> listFragment = new ArrayList<>();

    public static void addFragment(Fragment f){
        if(!existFragment(f)) {
            listFragment.add(f);
        }
    }
    public static void removeFragment(){
        if(listFragment.size()>0)
            listFragment.remove(listFragment.size()-1);
    }
    public static Fragment getCurrentFragment(){
        return listFragment.get(listFragment.size()-1);
    }
    public static int sizeFragments(){
        return listFragment.size();
    }
    private static Boolean existFragment(Fragment f){
        Boolean ret = false;
        for(Fragment fragment : listFragment){
            if (fragment.getClass() == f.getClass()){
                ret = true;
            }
        }
        return ret;
    }

进入主Activity,我重写onAttachFragment方法

@Override
public void onAttachFragment(Fragment f) {
    super.onAttachFragment(f);

    MyHelperClass.addFragment(f);
}

而且,我重写了onBackPressed Method:

@Override
public void onBackPressed() {
        General.removeFragment();
        if(General.sizeFragments()>0){
            Fragment fragment = null;
            Class fragmentClass = General.getCurrentFragment().getClass();

            try {
                fragment = (Fragment) fragmentClass.newInstance();
                fragment.setArguments(General.getCurrentFragment().getArguments());
            } catch (Exception e) {
                e.printStackTrace();
            }

            fragmentManager.beginTransaction().replace(R.id.flContent, fragment).commit();
        }else{
            super.onBackPressed();
        }
}

所以通过这种方式你可以随时使用MyHelperClass.getCurrentFragment()获取活动片段

我希望这对任何人都有帮助

问候

答案 47 :(得分:0)

您可以添加一个类变量selectedFragment,每次更改片段时都会更新变量。

public Fragment selectedFragment;
public void changeFragment(Fragment newFragment){
    FragmentManager fragMgr = getSupportFragmentManager();
    FragmentTransaction fragTrans = fragMgr.beginTransaction();
    fragTrans.replace(android.R.id.content, newFragment);
    fragTrans.addToBackStack(null);
    fragTrans.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
    fragTrans.commit();
    //here you update the variable
    selectedFragment = newFragment;
}

然后你可以在任何你想要的地方使用selectedFragment

答案 48 :(得分:0)

在这些情况下,使用事件总线(如OttoEventBusRxJava Bus)尤其方便。

虽然这种方法并不一定会将当前可见的片段作为对象传递给你(虽然它也可以完成,但它会导致更长的调用链),但它允许你对当前可见的片段执行操作(知道当前可见的片段通常是你想做的事情。

  1. 确保您尊重片段生命周期并在适当的时间注册/取消注册事件总线
  2. 在您需要知道当前可见片段并执行一组操作的位置。用活动巴士拍摄活动。
  3. 所有已注册到总线的可见片段都将执行必要的操作。

答案 49 :(得分:0)

您可以使用以下代码获取当前片段

FragmentClass f = (FragmentClass)viewPager.getAdapter().instantiateItem(viewPager, viewPager.getCurrentItem());

答案 50 :(得分:0)

请尝试这种方法.....

private Fragment getCurrentFragment(){
    FragmentManager fragmentManager = getSupportFragmentManager();
    String fragmentTag = fragmentManager.getBackStackEntryAt(fragmentManager.getBackStackEntryCount() - 1).getName();
    Fragment currentFragment = getSupportFragmentManager()
.findFragmentByTag(fragmentTag);
    return currentFragment;
}

答案 51 :(得分:0)

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

这对我有用。在遍历片段列表之前,需要执行空检查。可能存在堆栈中没有加载片段的情况。

可以将返回的片段与要放入堆栈的片段进行比较。

答案 52 :(得分:0)

有点奇怪,但我查看了FragmentManager $ FragmentManagerImpl,以下内容适用于我:

public static Fragment getActiveFragment(Activity activity, int index)
{
    Bundle bundle = new Bundle();
    String key = "i";
    bundle.putInt(key,index);
    Fragment fragment=null;
    try
    {
        fragment = activity.getFragmentManager().getFragment(bundle, key);
    } catch(Exception e){}
    return fragment;
}

获取第一个活动片段使用0作为索引