java.lang.NullPointerException: отсутствует необходимое представление с идентификатором:
Android Studio 3.6
в app/build.gradle:
android {
viewBinding.enabled = true
Вот мой xml:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/bluetoothBottonMainContainer"
android:layout_width="0dp"
android:layout_height="104dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<View
android:id="@+id/viewPointNotSelect"
android:layout_width="16dp"
android:layout_height="16dp"
android:background="@drawable/circle_transparent"
app:layout_constraintBottom_toBottomOf="@+id/separator"
app:layout_constraintEnd_toStartOf="@+id/separator"
app:layout_constraintTop_toTopOf="parent" />
и еще один xml unclude prev. xml:
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/bottonContainer"
android:layout_width="0dp"
android:layout_height="104dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent">
<include
android:id="@+id/qrBottonContainer"
layout="@layout/qr_bottom_container"
android:layout_width="0dp"
android:layout_height="wrap_content"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent" />
вот моя деятельность:
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = QrBluetoothSwipeActivityBinding.inflate(layoutInflater)
setContentView(binding.root)
}
приложение создается и запускается. Приятно.
Теперь я двигаю id - android:id="@+id/bluetoothBottonMainContainer"
во внешний контейнер следующим образом:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/bluetoothBottonMainContainer"
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="0dp"
android:layout_height="104dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<View
android:id="@+id/viewPointNotSelect"
android:layout_width="16dp"
android:layout_height="16dp"
android:background="@drawable/circle_transparent"
app:layout_constraintBottom_toBottomOf="@+id/separator"
app:layout_constraintEnd_toStartOf="@+id/separator"
app:layout_constraintTop_toTopOf="parent" />
приложение построено, но при запуске я получаю ошибку выполнения в этой строке:
binding = QrBluetoothSwipeActivityBinding.inflate(layoutInflater)
ошибка:
10-25 11:11:51.290 E/AndroidRuntime(14128): FATAL EXCEPTION: main
10-25 11:11:51.290 E/AndroidRuntime(14128): Process: com.myproject.debug, PID: 14128
10-25 11:11:51.290 E/AndroidRuntime(14128): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.myproject.debug/com.myproject.ui.actviity.QRBluetoothSwipeActivity}: java.lang.NullPointerException: Missing required view with ID: bluetoothBottonMainContainer
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2416)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2476)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread.-wrap11(ActivityThread.java)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1344)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.os.Handler.dispatchMessage(Handler.java:102)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.os.Looper.loop(Looper.java:148)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread.main(ActivityThread.java:5417)
10-25 11:11:51.290 E/AndroidRuntime(14128): at java.lang.reflect.Method.invoke(Native Method)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
10-25 11:11:51.290 E/AndroidRuntime(14128): Caused by: java.lang.NullPointerException: Missing required view with ID: bluetoothBottonMainContainer
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.myproject.databinding.BluetoothBottomContainerBinding.bind(BluetoothBottomContainerBinding.java:114)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.myproject.databinding.QrBluetoothSwipeActivityBinding.bind(QrBluetoothSwipeActivityBinding.java:76)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.myproject.databinding.QrBluetoothSwipeActivityBinding.inflate(QrBluetoothSwipeActivityBinding.java:62)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.myproject.databinding.QrBluetoothSwipeActivityBinding.inflate(QrBluetoothSwipeActivityBinding.java:52)
10-25 11:11:51.290 E/AndroidRuntime(14128): at com.myproject.ui.actviity.QRBluetoothSwipeActivity.onCreate(QRBluetoothSwipeActivity.kt:31)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.Activity.performCreate(Activity.java:6251)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1107)
10-25 11:11:51.290 E/AndroidRuntime(14128): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2369)
10-25 11:11:51.290 E/AndroidRuntime(14128): ... 9 more
10-25 11:11:51.291 W/ActivityManager( 780): Force finishing activity com.myproject.debug/com.myproject.ui.actviity.QRBluetoothSwipeActivity
10-25 11:11:51.307 I/Icing (11529): Indexing done com.google.android.gms-apps
33 ответа
Если кто-то получает это с
TabLayout
и
ViewBinding
включен, то вы могли установить идентификатор для. Удаление идентификатора из
TabItem
решил проблему для меня.
Пожалуйста, проверьте, возможно, у вас одинаковые файлы макета в разных модулях.
Я столкнулся с этой проблемой, но в моем случае проблема заключается в include
флаг. Обходной путь, который я нашел, состоит в том, чтобы сделать идентификатор представления таким же, как идентификатор корневого представления включенного макета.
activity_layout.xml
<LinearLayout>
<include android:id="@+id/widget1" layout="@layout/my_widget" />
</LinearLayout>
my_wideget.xml
<LinearLayout
android:id="@+id/widget1">
</LinearLayout>
Остерегайтесь, если вы используете
<merge>
внутри вашего включенного XML-макета логика иная, как указано здесь:
Подробное изучение привязки представления Android
Если мы попытаемся дать этому идентификатор, привязка представления не будет генерировать идентификатор в классе привязки, поэтому мы не сможем получить доступ к представлению, как это было в случае обычного включения.
В этом случае у нас есть PlaceholderBinding, который является автоматически сгенерированным классом для placeholder.xml (наш<merge>
макет файла). Мы должны назвать этоbind()
и передайте корневое представление макета, в который мы его включили.
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<include layout="@layout/placeholder" />
</androidx.constraintlayout.widget.ConstraintLayout>
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
binding = FragmentOrderBinding.inflate(layoutInflater, container, false)
placeholderBinding = PlaceholderBinding.bind(binding.root)
placeholderBinding.tvPlaceholder.text = getString(R.string.please_wait)
return binding.root
}
Обновить
Это должно быть исправлено в последних бета-версиях и версиях Android Studio Carnary.
Тем не менее существует проблема при использовании привязки вида с элементами вкладок макета вкладки материала, о которой здесь сообщается и которая еще не исправлена.
Это ошибка в View Binding, о которой сообщается в системе отслеживания проблем в следующих местах.
Вы также можете получить эту ошибку, если неправильно привяжете ячейку к представлению в recyclerView. Если вы привяжете представление к неправильному макету, вы получите сообщение об ошибке о том, что оно не может найти ожидаемые дочерние представления.
Это ставило меня в тупик на долгое время.
Решение состоит в том, чтобы убедиться, что макет, который вы привязываете к представлению, совпадает с макетом ViewBinding.
Вам следует удалить идентификатор TabItem и использовать API TabLayout для получения элемента. Этот способ обхода работает, если вы используете Material Design.
проверьте это: ответ Github
В моем случае в другом модуле был другой файл с таким же именем.
У меня был item_view.xml в модуле A и item_view.xml в модуле B, поэтому привязка данных не могла их различить.
Я изменил имя одного из них, и это исправлено.
В моем случае я удалил идентификатор внутри включенного макета, и он работает правильно!
main.xml
<RelativeLayout>
....
<include
include="@layout/included_layout"
android:id="@+id/view_included_layout"/>
</RelativeLayout>
include_layout.xml
` <LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/top_level_layout"> <!-- Remove this id -->
....
</LinearLayout>
`
Моя версия Android Studio - 3.6.2, а версия build.gradle - 3.6.1
Решение - удалить идентификатор основного контейнера. И поместите в другой контейнер внутри родителя.
1.- Макет
<include
android:id="@+id/example"
layout="@layout/account_current_payment_card"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
2.- Включить макет
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
xmlns:app="http://schemas.android.com/apk/res-auto">
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/example2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintTop_toTopOf="parent">
</androidx.constraintlayout.widget.ConstraintLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
Это происходит со мной прямо сейчас. Я просто заметил, что это произошло потому, что в моих файлах xml их можно вызывать: Activity_main.xml / Activity_other.xml. У меня был виджет (в данном случае кнопка) с тем же идентификатором (+id / bttNext)
(это означает, что у activity_main.xml и Activity_other раньше была кнопка с одинаковым +id)
как только я тестирую свое приложение на устройстве:
java.lang.NullPointerException: отсутствует необходимое представление с идентификатором:
появившийся
как только я изменил кнопку + id второй активности (скажем, переименовал bttNext1) aspp работал нормально
Подводя итог: избегайте использования одного и того же идентификатора в кнопках (и других виджетах), не имеет значения, если они находятся в разных действиях
Я пробовал много способов, но все не сработало.
Наконец, проблема в том, что в другом модуле есть XML с таким же именем.
просто удалите каталог .gradle и активируйте кеши / перезапустите проект, сохраните резервную копию проекта. Я столкнулся с той же проблемой, решенной этим методом.
Для меня проблема заключалась в том, что я все еще использовал версию Android 3.x, но использовал новую версию Gradle 4.0.0.
Нажал "О программе-> Проверить наличие обновлений", обновил Android Studio, и ошибки больше нет.
Я встречаю ту же ошибку. Чтобы избежать этой ошибки, вы можете добавить представление оболочки в свой "внешний контейнер".
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/bluetoothBottonMainContainer"
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="0dp"
android:layout_height="104dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<View
android:id="@+id/viewPointNotSelect"
android:layout_width="16dp"
android:layout_height="16dp"
android:background="@drawable/circle_transparent"
app:layout_constraintBottom_toBottomOf="@+id/separator"
app:layout_constraintEnd_toStartOf="@+id/separator"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
Я получал ошибку, потому что в моем случае mainapp
иmodule
такая же планировка(layout_calling_waiting
) с разными видами, которые не удалось найти в макете приложения. Таким образом, ошибка waas давала.
Получил эту проблему с пользовательским представлением, где ошибочно взят
this
вместо того
super
constructor(context: Context, attrs: AttributeSet?) : this(context,attrs) { //<-Change this to super
}
Эта ошибка также может произойти, если вы по ошибке используете XML-макет для фрагмента, но используете другой для привязки. Я делал, когда обнаружил ошибку
class LoginFragment :Fragment(R.layout.login_fragment) {
private val binding by viewBinding(LoginFragmentNewBinding::bind)//here I am referring to a new xml file called login_fragment_new which is different from the one in the Fragment's constructor (i.e login_fragment)
}
и с помощью того же файла xml исправил это для меня.
Я столкнулся с той же проблемой, и я решил ее, удалив эту строку в макете.
tools:context=".ui.SplashScreenActivity
В моем случае эта проблема была связана с одинаковыми именами файлов xml в разных модулях.
Почему возникла проблема:
У меня было 2 файла xml с одинаковым именем (item_tag.xml
) в разных модулях (app
,landing
). Компилятор не знает, какой из них нужно использовать, и я получил ошибку во время выполнения (каждый раз, когда я открывал экран с этимbinding
).
Решение:
Я переименовал файл xml, и один из них сталitem_landing_tag.xml
(и был сгенерированItemLandingTagBinding
класс вместоItemTagBinding
).
Надеюсь, это поможет кому-то :)
Get RootView() возвращает включенный макет и может вносить в него изменения
Для моей базы
my_main_layout.xml
было -
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
<ScrollView style="@style/ScrollViewContainerStyle">
<include
android:id="@+id/include_1"
layout="@layout/layout"></include>
<include
android:id="@+id/include_1"
layout="@layout/layout"></include>
<include
android:id="@+id/include_1"
layout="@layout/layout"></include>
</include></layout>
</ScrollView>
И мой включенный
layout.xml
было -
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="@+id/tv_title"
tools:text="This is a tile" />
</LinearLayout>
Я просто решил свою проблему, обернув ее
<layout>
-
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
tools:visibility="visible">
<TextView
android:id="@+id/tv_title"
tools:text="This is a tile" />
</LinearLayout>
</layout>
Решил это с помощью: Invalidate Caches and Clean Project.
В моем случае я скопировал некоторые виджеты из одного макета в другой, после чего изменил идентификаторы (чтобы идентификаторы не повторялись).
Отладочная сборка работала корректно, но при попытке запустить выпускную сборку выдавалось исключение.
Может быть уже поздно, но. Для всех, кто сталкивался с этим вопросом. Я сначала попробовал все, что видел здесь, но безуспешно. Я обнаружил, что использование идентификаторов кейсов змейки решает проблему. У меня был идентификатор tabContainer, и он вызывал NPE. Переименование его в tab_container устранило ошибку для меня.
У меня тоже была эта проблема, но, по-видимому, это было именно то, на что указывала ошибка, нулевой указатель, представление было «потреблено» моим пользовательским контейнером представления, который принимал только первое дочернее представление после infaltion и следующее представление с идентификатором, указанным ошибка была удалена из иерархии, поэтому программа просмотра не могла их связать.
Та же проблема, но только в пользовательской активности просмотра я установил правильные атрибуты.
В котлине:
class CanvasNew @JvmOverloads constructor(context: Context, attrs: AttributeSet? = null):View(context,attrs){
Мое решение было похожим, но немного другим, у меня было включение в мой диалог
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:minHeight="@dimen/complete_programme_min_height"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<include
android:id="@+id/include" <!-- Removing this line worked -->
layout="@layout/background_triangle_medium_violet_gradient" />
Решение может быть:
init {
id = context.obtainStyledAttributes(attrs, intArrayOf(android.R.attr.id)).let { typedArray ->
val value = typedArray.getResourceId(0, View.NO_ID)
typedArray.recycle()
value
}
val inflater = context.getSystemService(Context.LAYOUT_INFLATER_SERVICE) as LayoutInflater
binding = AnyBinding.inflate(inflater, this)
}
У меня были разные макеты для телефонов и планшетов, и в одном из макетов отсутствовал идентификатор представления, его добавление решило проблему.
Вsrc/main/res/layout-sw600dp/fragment_satellite.xml
У меня была точка зрения:
....
<FrameLayout
android:id="@+id/container"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginBottom="@dimen/row005"
/>
....
но не было представления с таким же идентификатором@+id/container
, поэтому добавив его вsrc/main/res/layout/fragment_satellite.xml
решил проблему.
Запустите свой код с противоположным { minifyEnabled }
Если так сейчас:
debug {
minifyEnabled false
}
Затем запустите так:
debug {
minifyEnabled true
}
Или наоборот.