AppCompat 如何膨胀未明确使用 AppCompat 小部件的布局?

BLu*_*NiX 3 java android android-appcompat layout-inflater

我在使用 AppCompat 时突然想到,我一直在使用类似的东西,Button而不是android.support.v7.widget.AppCompatButton在我的布局 XML 文件中。我做了一个测试,通过view.getClass().getSimpleName()并确认即使我Button在 XML 中将它声明为 a ,正在加载的类实际上是AppCompatButton.

这是如何工作的,在引擎盖下?

BLu*_*NiX 6

在研究这个话题的过程中,为了正确提问,我自己发现了答案。

使用时AppCompatActivity,会发生一些有趣的事情:

  1. ALayoutInflater.Factory应用于默认值LayoutInflater,通过setFactoryAppDelegateImplAppCompat 中的类实现该Factory接口,并根据 API 级别选择其中一个作为工厂委托。还有一个稍微不同的Factory2,针对以后的 API。
  2. 当您的视图从 XML 膨胀时,视图类的名称被传递到Factory'screateView方法,该方法有机会覆盖创建的实际视图。
  3. 根据 中的字符串的硬编码哈希表检查视图的名称AppCompatViewInflater,如果找到匹配项,则视图由委托膨胀,而不是默认膨胀器。

  • 您甚至可以覆盖主题中的充气器。AppCompat 有这个:`<item name="viewInflaterClass">androidx.appcompat.app.AppCompatViewInflater</item>`。MaterialComponents 主题使用它来注入它自己的自定义布局充气器。至少从支持库 28 开始,不知道它以前是如何工作的。 (2认同)