我想在我的应用中实现新的Android导航组件。据我所知,默认情况下,基本上用于承载片段(NavHostFragment)的片段使用FrameLayout。但是,不幸的是,FrameLayout对窗口插入一无所知,因为它是在Android 4.4之前开发的。因此,我想知道如何创建自己的NavHostFragment,它将使用CoordinatorLayout作为根元素在视图层次结构中传递窗口插图。
要用CoordinatorLayout替换FrameLayout,您可以创建自定义NavHostFrament并覆盖onCreateView
方法。
NavHostFragment内部]:
@Nullable @Override public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { FrameLayout frameLayout = new FrameLayout(inflater.getContext()); // When added via XML, this has no effect (since this FrameLayout is given the ID // automatically), but this ensures that the View exists as part of this Fragment's View // hierarchy in cases where the NavHostFragment is added programmatically as is required // for child fragment transactions frameLayout.setId(getId()); return frameLayout; }
您可以看到,FrameLayout是通过编程方式创建的,在返回ID之前已设置其ID。
CustomNavHostFragment
:,您无需将NavHostFragment的默认class CustomNavHostFragment : NavHostFragment() { override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? { // change it to CoordinatorLayout val view = CoordinatorLayout(inflater.context) view.id = id return view } }
但是
FrameLayout
替换为CoordinatorLayout
。根据Ian Lake的answer,您还可以实现ViewCompat.setOnApplyWindowInsetsListener()来拦截对窗口插图的调用并进行必要的调整。coordinatorLayout?.let {
ViewCompat.setOnApplyWindowInsetsListener(it) { v, insets ->
ViewCompat.onApplyWindowInsets(
v, insets.replaceSystemWindowInsets(
insets.systemWindowInsetLeft, 0,
insets.systemWindowInsetRight, insets.systemWindowInsetBottom
)
)
insets // return original insets to pass them down in view hierarchy or remove this line if you want to pass modified insets down the stream.
// or
// insets.consumeSystemWindowInsets()
}
}