findViewById 用于在包含的合并根元素中查看

findViewById for view inside an included merge root-element

我想在多个活动中使用一个视图。在我的例子中,它是一个 FloatingActionButton。当我通过 findViewById 搜索视图时,程序抛出 NullPointerException。如何访问 FloatingActionButton?


由于按钮应该始终相同,因此我创建了一个 XML 布局,仅在 merge 根元素中包含 FloatingActionButton 以减少使用 ìnclude.[=28 时的开销=]

floating_button.xml

<merge xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/include_merge" >

    <android.support.design.widget.FloatingActionButton
        android:id="@+id/addBloodDonation"/>

</merge>

要在我的其他 XML 布局中使用它,我使用 include 标签

XML Activitiy Layouts that should include the FloatingActionButton

<include
    android:id="@+id/include_merge"
    layout="@layout/floating_button" />

目前有效。

为了在我的所有 Activity 中具有相同的功能,我创建了一个 BaseActivity,我的其他 类 继承自该 BaseActivity,例如我的 MainActivity.

BaseActivity

public abstract class BaseActivity extends AppCompatActivity {
    public FloatingActionButton fab;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        View include_merge = findViewById(R.id.include_merge);
        fab = include_merge.findViewById(R.id.addBloodDonation);
    }
}

MainActivity (exemplarily)

public class MainActivity extends BaseActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }
}

当启动应用程序时,我在 BaseActivity 中收到一个 NullPointerException 试图找到内部元素作为 View 变量 include_merge 为空。

正如我所读 hereinclude 标签和根元素应该具有相同的 android:id。使用 merge 作为根元素时有区别吗?甚至可以将 merge 标签转换为视图。

我是否需要在 BaseActivity 中使用 setContentView,因为它的 onCreate 方法在 MainActivity 之一之前被调用?


编辑:

已将 setContentView(R.layout.activity_main); 添加到评论中提到的 BaseActivity,但仍未修复它。

您不必为 <include><merge> 标签设置 id。只需删除它以及 findViewById(R.id.include_merge)<merge> 标签表示将其所有视图添加到<include> 标签的容器中。因此没有 View 与您设置的 id。但是你可以直接找到FAB

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    fab = include_merge.findViewById(R.id.addBloodDonation);
}