Android 地图视图';s onDestroy()导致UninitializedPropertyAccessException

Android 地图视图';s onDestroy()导致UninitializedPropertyAccessException,android,google-maps,kotlin,google-maps-android-api-2,Android,Google Maps,Kotlin,Google Maps Android Api 2,谷歌地图的MapView组件有一个奇怪的问题,它导致运行时异常UninitializedPropertyAccessException在每个其他视图中的第二次配置更改(设备旋转)后引发异常,MapView方法被覆盖的视图除外。因此,在处理com.google.android.gms.maps.MapView生命周期的MyMapViewFragment中,不会引发此错误,配置更改工作正常 当我旋转设备时,问题会出现在每个其他视图中,调用该设备时会破坏com.google.android.gms.m

谷歌地图的MapView组件有一个奇怪的问题,它导致运行时异常UninitializedPropertyAccessException在每个其他视图中的第二次配置更改(设备旋转)后引发异常,MapView方法被覆盖的视图除外。因此,在处理
com.google.android.gms.maps.MapView
生命周期的
MyMapViewFragment
中,不会引发此错误,配置更改工作正常

当我旋转设备时,问题会出现在每个其他视图中,调用该设备时会破坏
com.google.android.gms.maps.MapView

override fun onDestroy() {
    super.onDestroy()
    googleMapView.onDestroy()
}
第二次旋转设备会导致Google MapView.onDestroy()上的UninitializedPropertyAccessException(未初始化MapView)。MyMapViewFragment的代码:

class MyMapViewFragment : Fragment(), OnMapReadyCallback {

   private lateinit var googleMapView: com.google.android.gms.maps.MapView
   private lateinit var googleMap : GoogleMap

  override fun onCreateView(
    inflater: LayoutInflater, container: ViewGroup?,
    savedInstanceState: Bundle?
  ): View? {
    var view = inflater.inflate(R.layout.fragment_map_view, container, false)
    googleMapView = view.findViewById(R.id.mapView2)
    googleMapView.onCreate(savedInstanceState)
    googleMapView.getMapAsync(this)
    bottomNavigationView = requireActivity().findViewById(R.id.bottomNavigation)
    mountainCustomInfoWindow.visibility = View.INVISIBLE
    bottomNavigationView.visibility = View.VISIBLE
    return view
 }

  override fun onMapReady(map: GoogleMap) {
    googleMap = map
  }
  override fun onPause() {
     super.onPause()
     googleMapView.onPause()
  }
  override fun onResume() {
     super.onResume()
     googleMapView.onResume()
  }
  override fun onDestroy() {
     super.onDestroy()
     googleMapView.onDestroy()
  }
  override fun onLowMemory() {
     super.onLowMemory()
     googleMapView.onLowMemory()
  }
}
堆栈跟踪:

Process: com.hiker, PID: 25388
java.lang.RuntimeException: Unable to destroy activity {com.hiker/com.hiker.presentation.MainActivity}: kotlin.UninitializedPropertyAccessException: lateinit property googleMapView has not been initialized
    at android.app.ActivityThread.performDestroyActivity(ActivityThread.java:4605)
    at android.app.ActivityThread.handleDestroyActivity(ActivityThread.java:4623)
    at android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:4897)
    at android.app.ActivityThread.-wrap19(Unknown Source:0)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1702)
    at android.os.Handler.dispatchMessage(Handler.java:105)
    at android.os.Looper.loop(Looper.java:164)
    at android.app.ActivityThread.main(ActivityThread.java:6944)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:327)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1374)
 Caused by: kotlin.UninitializedPropertyAccessException: lateinit property googleMapView has not been initialized
    at com.hiker.presentation.map.MapView.onDestroy(MapView.kt:173)
    at androidx.fragment.app.Fragment.performDestroy(Fragment.java:2830)
    at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1028)
    at androidx.fragment.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManagerImpl.java:1238)
    at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1310)
    at androidx.fragment.app.FragmentManagerImpl.dispatchStateChange(FragmentManagerImpl.java:2659)
    at androidx.fragment.app.FragmentManagerImpl.dispatchDestroy(FragmentManagerImpl.java:2644)
    at androidx.fragment.app.Fragment.performDestroy(Fragment.java:2825)
    at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1028)
    at androidx.fragment.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManagerImpl.java:1238)
    at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1303)
    at androidx.fragment.app.FragmentManagerImpl.dispatchStateChange(FragmentManagerImpl.java:2659)
    at androidx.fragment.app.FragmentManagerImpl.dispatchDestroy(FragmentManagerImpl.java:2644)
    at androidx.fragment.app.FragmentController.dispatchDestroy(FragmentController.java:329)
    at androidx.fragment.app.FragmentActivity.onDestroy(FragmentActivity.java:366)
    at androidx.appcompat.app.AppCompatActivity.onDestroy(AppCompatActivity.java:210)
    at android.app.Activity.performDestroy(Activity.java:7479)
    at android.app.Instrumentation.callActivityOnDestroy(Instrumentation.java:1255)
    at android.app.ActivityThread.performDestroyActivity(ActivityThread.java:4592)
更多的猜测:
lateinit
属性要求在对其执行任何其他操作之前初始化该属性。我们在本例中使用它,因为我们只能在
onCreateView
中初始化它,而不能在构造函数中初始化它。您确实在初始化
onCreateView
的第二行上的
googleMapView

但是,如果,
view.findViewById(R.id.mapView2)
将返回
null
,则实际上可能无法正确初始化它。如果布局
fragment\u map\u视图中没有id为
mapView2
的元素,则会出现这种情况。因此,请验证是否确实存在地图视图


另一种可能发生的情况是,如果片段实际上没有附加到视图层次结构,而是在活动中实例化和注册。当活动被销毁时,它会销毁片段并调用未初始化对象上的方法。这里的实际情况


(有关解决方案,请参见注释)。

您能发布完整的stacktrace吗?当然,在问题中添加了stacktrace。我将
com.hiker.presentation.map.MapView
命名为
MyMapViewFragment
,因为在我看来,Clarity就像是在
onCreateView
之前调用了
onDestroy
,这确实很奇怪。如何将片段添加到活动中?是的,您是正确的,配置更改时不会调用onCreateView。我正在使用带有导航图的导航组件,
com.hiker.presentation.map.MapView
是我的起始视图。在我的主要活动中,我有BottomNavigationView,它负责切换视图。我刚刚添加了一个答案,另外还有一个潜在问题。所以,如果您愿意的话,您可以接受它。我发现,当我在TripView上旋转设备时,会发生以下流程:MapView.onDestroy()->MainActivity.onCreate()->MapView.onCreate()->TripView.onCreate()。奇怪的是,调用了MapView.onCreate(),但为什么呢?此片段与TripView没有依赖关系。当我第二次旋转设备,然后第一次旋转MapView.onDestroy()时,应用程序崩溃。。