Ошибка Kotlin: Кинжал не поддерживает инъекцию в частные поля
Я использую в kotlin активность ViewPager, и я хочу, чтобы в Kotlin Fragment использовалась инъекция кинжала. У меня есть Ошибка: Кинжал не поддерживает инъекцию в частные поля. В Java Fragment работает инъекция кинжала. Почему я не могу ввести кинжал в котлинскую дальность?
в моей котлинской деятельности
mPagerAdapter = object : FragmentPagerAdapter(supportFragmentManager) {
private val mFragments = arrayOf(KotlinFragment(), JavaFragment())
private val mFragmentNames = arrayOf(getString(R.string.cashdocuments), getString(R.string.action_absmysql))
override fun getItem(position: Int): Fragment {
return mFragments[position]
}
override fun getCount(): Int {
return mFragments.size
}
override fun getPageTitle(position: Int): CharSequence {
return mFragmentNames[position]
}
}
мой фрагмент котлина
class KotlinFragment : Fragment() {
@Inject
internal var mSharedPreferences: SharedPreferences? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
(activity.application as SamfantozziApp).dgaeacomponent().inject(this)
}
override fun onCreateView(inflater: LayoutInflater?, container: ViewGroup?,
savedInstanceState: Bundle?): View? {
super.onCreateView(inflater, container, savedInstanceState)
val rootView = inflater!!.inflate(R.layout.activity_absserver, container, false)
return rootView
}
}
сообщение gradle build
Ответы
Ответ 1
Случайно я наткнулся на свой собственный ответ и должен признаться, что на самом деле он не работает (по крайней мере, для моего случая использования). Пожалуйста, обратите внимание на ответ Авилио, который тоже работал для меня: замените internal
с lateinit
.
Старый ответ
Удалите internal
модификатор. Для доступа к аннотированному полю кинггеру требуется, по крайней мере, пакетный доступ. internal
модификатор Kotlin не является заменой модификатора доступа к частному доступу Java.
Подробное объяснение различий между модификаторами в Java и Kotlin относится к эпизоду фрагментированного подкаста № 101 - "Изучение Kotlin - модификаторы видимости, внутренний модификатор, модули", а также официальные документы.
Ответ 2
У вас есть ошибка здесь:
@Inject
internal var mSharedPreferences: SharedPreferences? = null
Это выглядит, как вы добавили @Inject
аннотацию к KotlinFragment
класса
Пожалуйста, измените его на это, и он будет работать:
var mSharedPreferences: SharedPreferences? = null
@Inject set
Вот ссылка на документацию: https://kotlinlang.org/docs/reference/annotations.html
Ответ 3
У меня была такая же ошибка, даже при удалении внутреннего ключевого слова. Таким образом, я заменил внутреннее с lateinit, и это сработало.
Ответ 4
Как просто вы можете это сделать, измените эту строку
@Inject
internal var mSharedPreferences: SharedPreferences? = null
к
@set:Inject
internal var mSharedPreferences: SharedPreferences? = null
эта работа как прелесть в моем случае.
Ответ 5
@Inject
lateinit var mSharedPreferences: SharedPreferences
Кроме того, это сработало и для поздней инициализации переменной
Ответ 6
Удалите internal
модификатор. И мне также пришлось объявить lateinit
и удалить lateinit
.
Ответ 7
Вы определили приложение fun inject(fragment: KotlinFragment)
в своем ApplicationComponent
? Потому что похоже, что ваше сообщение об ошибке говорит именно это.
EDIT: возможно, вы не предоставили SharedPreferences
в своем модуле следующим образом:
@Module
public class AndroidModule {
private final TimrApplication application;
public AndroidModule(TimrApplication application) {
this.application = application;
}
@Provides
SharedPreferences provideSharedPreferences(){
return PreferenceManager.getDefaultSharedPreferences(application);
}
}
Ответ 8
Я следовал вышеупомянутому совету не делать поле внутренним. Но этого было недостаточно. Kapt все еще конвертирует var в private во время компиляции.
Мне пришлось добавить аннотацию @JvmField
, чтобы она лучше себя вел.
Ответ, который я нашел, был здесь:https://discuss.kotlinlang.org/t/kapt-converting-public-fields-to-private-during-compilation/11757