最初に
サポートライブラリの後任となる AndroidX ライブラリですが、
マイナーバージョンが上がると内部的なクラス関係がけっこう変更されています。
標準ライブラリと言っても良い AndroidX ですが 1.1.0 では以下のアップデートが行われました。
2項目の AppCompatActivity について
この中の AppCompatActivity についてピックアップします。
AppCompatActivity が Fragment 1.1.0 を介して、
Activity 1.0.0 の ComponentActivity から推移的に拡張されるようになりました。
推移的に拡張... ←どうもイメージ掴みにくいですね。
元々 appcompat は、フラグメント機能を持つ androidx.fragment:fragment に依存していました。
こちらの内部バージョンが上がり、
そのフラグメント内で新たに androidx.activity に依存するように なりました。
androidx.fragment | androidx.activity | |
---|---|---|
appcompat:1.0.0 | 1.0.0 | - |
appcompat:1.1.0 | 1.1.0 | 1.0.0 |
なにが変わるのか
AppCompactAcitivty の継承関係 に変更が入りました。
【1.0.0】
AppCompatActivity
+- androidx.fragment.app.FragmentActivity
+- androidx.core.app.ComponentActivity
+- android.app.Activity
【1.1.0】
AppCompatActivity
+- androidx.fragment.app.FragmentActivity
+- androidx.activity.ComponentActivity
+- androidx.core.app.ComponentActivity
+- android.app.Activity
1.1.0 では androidx.activity.ComponentActivity が新規に追加され、FrameActivity のスーパークラスのパッケージ自体が別物になっています。
これにより、
・サードパーティ製のライブラリが appcompat:1.1.0
・自分のプロジェクトを appcompat:1.0.0
という状況で開発を行っていると... ライブラリ側にandroidx.activity.ComponentActivity を参照するコードがあると、ビルドが通らなくなります。
ライブラリ側から見たら、aar 作成時には認識していたクラスが「いざリンクしよう!」としたら無くなったので当然ですね。
対策は?
この場合、サポートライブラリ時代と同じように
configurations.all {
resolutionStrategy.eachDependency { DependencyResolveDetails details ->
if (details.requested.group == 'androidx.appcompat') {
details.useVersion '1.1.0'
}
}
}
上記のように 1.1.0 とのリンクを明示することで、動作は可能です。
ダウングレードの注意
なおライブラリ側をダウングレードさせるのは危険なのでご注意ください。
appcompact では他にも ActionBarOverlayLayout.onNestedScroll() の引数が追加 されており( 1.0.0 にない I/F が追加 )、ライブラリ開発者がこの I/F で開発を行っていた場合に 1.0.0 と強制リンクを行うと、ビルドは成功し何となく動きます(※)
※インスタンス化する程度ではクラッシュしませんでした。
このとき考えられる弊害としては、
実際のリンクは 1.0.0 と行っているため、新しい I/F が呼ばれず古い onNestedScroll() が呼ばれることになり、ライブラリ開発者が想定していたロジックが呼ばれず... 気づきにくいバグ事象となります。
アップグレードする場合は、appcompact の変更点を確認してからするのが確実です。
参考
appcompat:1.1.0 について
activity:1.0.0 について
fragment:1.1.0 について