Резюме
Текущее поведение
Неожиданные результаты от реализации библиотеки AAR по сравнению с исходной библиотекой в проектах Android.
super
Ключевое слово, похоже, указывает на класс деда, а не на родительский класс.
- Каким-то образом переопределяет метод прародителя, даже если тот же метод объявлен и переопределен в родительском методе.
Обе проблемы существуют только при использовании скомпилированного AAR библиотеки, то есть проблемы не существует при реализации того же проекта с использованием исходного кода библиотеки.
Ожидаемое поведение
- Я ожидал бы, что оба вызова
super
разрешат родительский класс.
- Я ожидаю, что переопределение
onCreate
переопределит метод в родительском классе, а не в прародителе.
Рабочее приложение
У меня есть приложение для Android в пакете com.example.sourceapp
Это использует и управляет исходным кодом для отдельной библиотеки, расположенной в com.example.sourcelibrary
, в которой мы будем называть ParentClass
.
классом.
В ParentClass
у меня есть два заинтересованных члена.
- Публичное логическое значение с именем
myBool
, которое начинается с ParentClass
- Метод, переопределяющий метод
android.app.Activity.onCreate
, который также переопределяется и наследуется от некоторого класса прародителя GrandparentClass
в другой библиотеке com.example.someotherlibrary
.
В моем com.example.sourceapp.MainActivity
я делаю две вещи.
- Я расширяю
com.example.sourcelibrary.ParentClass
и изменяю myBool
, содержащиеся в ParentClass
, используя super.myBool = true;
.
- Я вызываю
onCreate
через super.onCreate()
в переопределенном методе.
Оба работают как положено. При наведении курсора на super.onCreate
Android Studio указывает, что он правильно разрешается в родительский класс, как и ожидалось.
Приложение не работает
В другом проекте Android com.example.compiledapp.MainActivity
вместо зависимости от исходной библиотеки com.example.sourcelibrary
я зависел от скомпилированного (отладочного) файла AAR, созданного из той же библиотеки.
Я импортирую необходимый класс из пакета AAR вверху com.example.compiledapp.MainActivity
с import com.example.sourcelibrary.ParentClass
без каких-либо проблем с разрешением.
Позже com.example.compiledapp.MainActivity
Я использую тот же код, что и раньше, для
super.myBool = true;
super.onCreate()
, но Android Studio указывает, что не может разрешить myBool в super.myBool = true;
.
Более того, вторая строка, кажется, разрешается просто отлично, но при ближайшем рассмотрении, когда я наведу на нее курсор, Android Studio указывает, что onCreate
разрешает быть членом класса прародителя com.example.someotherlibrary.GrandparentClass
вместо родительского класса com.example.sourcelibrary.ParentClass
.
Просматривая несколько строк вверх, когда я наведите курсор мыши на переопределение onCreate
, Android Studio показывает, что я переопределяю onCreate
из класса прародителя, а не из родительского класса.
Почему / Как onCreate
пропустит родительский метод и переопределит класс прародителя?
Также похоже, что ключевое слово super
разрешается в классе прародителя, а не в родительский класс. Это единственное объяснение, которое я могу придумать, в результате чего onCreate
будет преобразовано в класс GrandparentClass, а myBool
не будет разрешено Я не думал, что так было super
.
Это нормально, и я просто неправильно понимаю нечто фундаментальное в наследовании? Может быть, я что-то не так делаю при компиляции в AAR, так что родительские переменные / методы становятся недоступными, несмотря на то, что они объявлены как public? Или, может быть, Android Studio отдает предпочтение одному пакету по сравнению с некоторыми правилами, которые мне неизвестны?
Рабочий код
package com.example.sourceapp;
import android.os.Bundle;
import com.example.sourcelibrary.ParentClass;
public class MainActivity extends ParentClass {
// Shows to Override onCreate in ParentClass
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); // super resolves to ParentClass
super.myBool = true; // super resolves to ParentClass
}
}
Не рабочий код
package com.example.compiledapp;
import android.os.Bundle;
import com.example.sourcelibrary.ParentClass;
public class MainActivity extends ParentClass {
// Shows to Override onCreate in GrandparentClass
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); // super resolves to Grandparent
super.myBool = true; // does not resolve
}
}