Android - 以编程方式从片段容器访问片段视图

时间:2017-01-16 07:44:30

标签: android android-fragments android-coordinatorlayout

在MainActivity的onCreate中,我使用FrameLayout在MainFragment的xml布局中用DragSelectRecyclerView替换了xml布局中的FragmentManager片段容器。以下代码显示了这一点:

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

    getFragmentManager().beginTransaction()
            .replace(R.id.fragmentContainer, new MainFragment())
            .commit();
}

MainActivity的xml:

    <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"
    tools:context="com.gra.app.activities.MainActivity">

    <FrameLayout
        android:id="@+id/fragmentContainer"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:clipToPadding="false"
        android:paddingTop="?attr/actionBarSize" />

    <android.support.design.widget.AppBarLayout
        android:id="@+id/appbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:layout_behavior=".utilities.AppBarLayoutBackgroundAlphaBehavior">

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:background="?attr/colorPrimary"
            android:theme="@style/ThemeOverlay.AppCompat.ActionBar" />
    </android.support.design.widget.AppBarLayout>
</android.support.design.widget.CoordinatorLayout>

MainFragment的xml:

<com.afollestad.dragselectrecyclerview.DragSelectRecyclerView 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:id="@+id/recyclerView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scrollbars="vertical"
app:dsrv_autoScrollEnabled="true"
app:dsrv_autoScrollHotspotHeight="56dp"
tools:context="com.gra.app.fragments.MainFragment" />

有没有办法以编程方式访问DragSelectRecyclerViewFrameLayout的实例?

原因是我需要让MainActivity的xml中的AppBarLayout依赖于MainFragment的DragSelectRecyclerView,这样我就可以根据

淡入/淡出AppBarLayout

DragSelectRecyclerView.getVerticalScrollbarPosition()

通过

CoordinatorLayout.Behavior<AppBarLayout>

这是可能的还是我应该在MainActivity的xml中移动DragSelectRecyclerView

3 个答案:

答案 0 :(得分:2)

我建议你在MainFragment中有一个公共方法 -

public float getVerticalScrollbarPosition(){
    return DragSelectRecyclerView.getVerticalScrollbarPosition();
}

将MainActivity的onCreate方法更新为此 -

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    MainFragment mainFragment = new MainFragment();
    getFragmentManager().beginTransaction()
            .replace(R.id.fragmentContainer, mainFragment)
            .commit();
}

现在在MainActivity中,您可以在任何地方访问该方法以获取值并相应淡入/淡出AppBarLayout -

mainFragment.getVerticalScrollbarPosition();

这就是应该如何处理片段和活动之间的沟通 - https://developer.android.com/guide/components/fragments.html#CommunicatingWithActivity

答案 1 :(得分:2)

您可以直接在主要活动的xml布局中设置片段,如

<RelativeLayout
    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">

    <fragment android:id="@+id/fragment"
          android:name="some.package.MainFragment"
          android:layout_width="match_parent"
          android:layout_height="match_parent"/>
</RelativeLayout>

然后通过

在活动的onCreate方法中获取DragSelectRecyclerView的实例
DragSelectRecyclerView recyclerView = (DragSelectRecyclerView) findViewById(R.id.recyclerView)

或者您只需将Fragment中的DragSelectRecyclerView设置为Activity:

@Override
public void onActivityCreated(@Nullable Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);
    DragSelectRecyclerView dragSelectRecyclerView = (DragSelectRecyclerView) getView().findViewById(R.id.recyclerView);
    Activity activity = getActivity();
    if (activity != null && activity instanceof MainActivity) {
        ((MainActivity) activity).setDragSelectRecyclerView(dragSelectRecyclerView);
    }
}

在这两种情况下,请确保在碎片消失后重置变量。

@Override
public void onDestroyView() {
    super.onDestroyView();
    Activity activity = getActivity();
    if (activity != null && activity instanceof MainActivity) {
        ((MainActivity) activity).setDragSelectRecyclerView(null);
    }
}

答案 2 :(得分:0)

您可以尝试在片段事务中设置tag,然后通过在事务期间设置的tag检索片段及其视图。

你可以这样做:

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

    getFragmentManager().beginTransaction()
            .replace(R.id.fragmentContainer, new MainFragment(),"tag")     //Adding tag here
            .commit();
}

然后您可以通过以下方式检索该片段内的recyclerview:

    View fragmentView = getFragmentManager().findFragmentByTag("tag").getView();
DragSelectRecyclerView recyclerView = (DragSelectRecyclerView)fragmentView.findViewById(R.id.recyclerView) //use the view

View fragmentView = getFragmentManager().findFragmentByTag("tag").getView();可能会根据片段状态的状态返回null。所以你需要注意那个。