应用程序崩溃 "back" 映射片段
App crash by "back" to maps fragment
我在开发我的第一个应用程序时遇到了 "back" 功能的问题。
当我打开应用程序并在菜单中单击另一个片段(2,3 或 4)并按下后退按钮时,应用程序崩溃了。当我启动应用程序并单击菜单中的 2 > 3 > 4
(按此顺序)并按下后退按钮时,我返回到 3 > 2 > crash
。当我返回包含 google 地图的 mainFragment 时,应用程序崩溃。
我认为我的问题与此片段中的 googlemap 有关(要导航回的片段),因为当我在 xml 的错误行之前设置 2 时该视图并再次 运行,错误行号为 +2。当我注释掉这个片段时,后退按钮工作正常。
通过导航到我调用的新片段:
fragmentTransaction.replace(R.id.fr_content_container, new NewsFragment()).addToBackStack(null).commit();
我得到的错误是
04-01 14:26:39.679 19054-19054/aaeu.app E/AndroidRuntime: FATAL EXCEPTION: main
Process: aaeu.app, PID: 19054
android.view.InflateException: Binary XML file line #7: Binary XML file line #7: Error inflating class fragment
at android.view.LayoutInflater.inflate(LayoutInflater.java:539)
at android.view.LayoutInflater.inflate(LayoutInflater.java:423)
at aaeu.app.presentationlayer.tab_AlertMapsOverview.onCreateView(mapsFragment.java:52)
.....................
mapsFragment 的 XML 是:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="2"
android:name="com.google.android.gms.maps.SupportMapFragment"
android:id="@+id/mapwhere" />
</RelativeLayout>
地图片段代码为:
private SupportMapFragment mMapFragment;
private AlertManager mAlertManager;
private GoogleMap mGoogleMap;
HashMap<Marker, Alert> mMarkerMap;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mAlertManager = new AlertManager(getContext());
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.overview_maps_alert_tab, container, false);
ButterKnife.bind(this, view);
loadMap();
return view;
}
private void loadMap() {
mMapFragment = (SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.mapwhere);
if (mMapFragment == null) {
FragmentManager fragmentManager = getFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
mMapFragment = SupportMapFragment.newInstance();
fragmentTransaction.replace(R.id.mapwhere, mMapFragment).commit();
}
if (mMapFragment != null) {
mMapFragment.getMapAsync(new OnMapReadyCallback() {
@Override
public void onMapReady(GoogleMap googleMap) {
if (googleMap != null) {
googleMap.getUiSettings().setAllGesturesEnabled(true);
LatLng marker_latlng = new LatLng(55.042684, 14.125549);
CameraPosition cameraPosition = new CameraPosition.Builder().target(marker_latlng).zoom(3.0f).build();
CameraUpdate cameraUpdate = CameraUpdateFactory.newCameraPosition(cameraPosition);
googleMap.moveCamera(cameraUpdate);
setGoogleMap(googleMap);
}
}
});
}
}
private void setGoogleMap(GoogleMap googleMap) {
this.mGoogleMap = googleMap;
}
// This method is called by the asynctask who downloads the alerts
@Override
public void UpdateAlerts(List<Alert> alerts) {
mMarkerMap = new HashMap<Marker, Alert>();
try {
for (Alert alert : alerts) {
MarkerOptions marker = new MarkerOptions();
marker.position(alert.Location.get(0));
marker.title(alert.GetFullName());
Marker m = mGoogleMap.addMarker(marker);
mMarkerMap.put(m, alert);
}
mGoogleMap.setOnMarkerClickListener(
new GoogleMap.OnMarkerClickListener() {
@Override
public boolean onMarkerClick(Marker marker) {
startDetailView(marker);
return false;
}
}
);
}
catch (NullPointerException e)
{
Log.i("tab_AlertMapsOverview","No missings to create markers for or set clicklisteners on. Are there missings in the configured Areas?");
}
}
在这个问题附近我也有一个小问题。当我有 3 个片段时,1、2 和 3。当我(例如)从 activity 1 开始并导航到 2 > 3 > 2 > 3 时,我需要向后推 4 次才能回到 1。是可以使用一种 "tree" 系统进行后退导航。所以我总是升一级?也许这澄清了我的意思。
我认为目前的情况也远非最佳,因为碎片在 RAM 中仍然处于活动状态?还是我错了?
我也遇到了同样的问题。在浪费了很多时间寻找解决方案之后,我最终做的是,我从 xml 中删除了片段标签。将 FrameLayout 放在那里,每当我想添加该片段时,我都会使用片段事务添加它。这对我有用。
问题的原因是,每当调用该片段的 onCreateView() 时,xml 文件都会膨胀,从而膨胀该片段。这将导致多个片段具有相同的 id,从而导致此异常。
用这个替换你的 onBackPressed...
@Override
public void onBackPressed() {
// if there is a fragment and the back stack of this fragment is not empty,
// then emulate 'onBackPressed' behaviour, because in default, it is not working
FragmentManager fm = getSupportFragmentManager();
for (Fragment frag : fm.getFragments()) {
if (frag.isVisible()) {
FragmentManager childFm = frag.getChildFragmentManager();
if (childFm.getBackStackEntryCount() > 0) {
childFm.popBackStack();
return;
}
}
}
super.onBackPressed();
}
我在开发我的第一个应用程序时遇到了 "back" 功能的问题。
当我打开应用程序并在菜单中单击另一个片段(2,3 或 4)并按下后退按钮时,应用程序崩溃了。当我启动应用程序并单击菜单中的 2 > 3 > 4
(按此顺序)并按下后退按钮时,我返回到 3 > 2 > crash
。当我返回包含 google 地图的 mainFragment 时,应用程序崩溃。
我认为我的问题与此片段中的 googlemap 有关(要导航回的片段),因为当我在 xml 的错误行之前设置 2 时该视图并再次 运行,错误行号为 +2。当我注释掉这个片段时,后退按钮工作正常。
通过导航到我调用的新片段:
fragmentTransaction.replace(R.id.fr_content_container, new NewsFragment()).addToBackStack(null).commit();
我得到的错误是
04-01 14:26:39.679 19054-19054/aaeu.app E/AndroidRuntime: FATAL EXCEPTION: main
Process: aaeu.app, PID: 19054
android.view.InflateException: Binary XML file line #7: Binary XML file line #7: Error inflating class fragment
at android.view.LayoutInflater.inflate(LayoutInflater.java:539)
at android.view.LayoutInflater.inflate(LayoutInflater.java:423)
at aaeu.app.presentationlayer.tab_AlertMapsOverview.onCreateView(mapsFragment.java:52)
.....................
mapsFragment 的 XML 是:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<fragment
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="2"
android:name="com.google.android.gms.maps.SupportMapFragment"
android:id="@+id/mapwhere" />
</RelativeLayout>
地图片段代码为:
private SupportMapFragment mMapFragment;
private AlertManager mAlertManager;
private GoogleMap mGoogleMap;
HashMap<Marker, Alert> mMarkerMap;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mAlertManager = new AlertManager(getContext());
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.overview_maps_alert_tab, container, false);
ButterKnife.bind(this, view);
loadMap();
return view;
}
private void loadMap() {
mMapFragment = (SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.mapwhere);
if (mMapFragment == null) {
FragmentManager fragmentManager = getFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
mMapFragment = SupportMapFragment.newInstance();
fragmentTransaction.replace(R.id.mapwhere, mMapFragment).commit();
}
if (mMapFragment != null) {
mMapFragment.getMapAsync(new OnMapReadyCallback() {
@Override
public void onMapReady(GoogleMap googleMap) {
if (googleMap != null) {
googleMap.getUiSettings().setAllGesturesEnabled(true);
LatLng marker_latlng = new LatLng(55.042684, 14.125549);
CameraPosition cameraPosition = new CameraPosition.Builder().target(marker_latlng).zoom(3.0f).build();
CameraUpdate cameraUpdate = CameraUpdateFactory.newCameraPosition(cameraPosition);
googleMap.moveCamera(cameraUpdate);
setGoogleMap(googleMap);
}
}
});
}
}
private void setGoogleMap(GoogleMap googleMap) {
this.mGoogleMap = googleMap;
}
// This method is called by the asynctask who downloads the alerts
@Override
public void UpdateAlerts(List<Alert> alerts) {
mMarkerMap = new HashMap<Marker, Alert>();
try {
for (Alert alert : alerts) {
MarkerOptions marker = new MarkerOptions();
marker.position(alert.Location.get(0));
marker.title(alert.GetFullName());
Marker m = mGoogleMap.addMarker(marker);
mMarkerMap.put(m, alert);
}
mGoogleMap.setOnMarkerClickListener(
new GoogleMap.OnMarkerClickListener() {
@Override
public boolean onMarkerClick(Marker marker) {
startDetailView(marker);
return false;
}
}
);
}
catch (NullPointerException e)
{
Log.i("tab_AlertMapsOverview","No missings to create markers for or set clicklisteners on. Are there missings in the configured Areas?");
}
}
在这个问题附近我也有一个小问题。当我有 3 个片段时,1、2 和 3。当我(例如)从 activity 1 开始并导航到 2 > 3 > 2 > 3 时,我需要向后推 4 次才能回到 1。是可以使用一种 "tree" 系统进行后退导航。所以我总是升一级?也许这澄清了我的意思。
我也遇到了同样的问题。在浪费了很多时间寻找解决方案之后,我最终做的是,我从 xml 中删除了片段标签。将 FrameLayout 放在那里,每当我想添加该片段时,我都会使用片段事务添加它。这对我有用。
问题的原因是,每当调用该片段的 onCreateView() 时,xml 文件都会膨胀,从而膨胀该片段。这将导致多个片段具有相同的 id,从而导致此异常。
用这个替换你的 onBackPressed...
@Override
public void onBackPressed() {
// if there is a fragment and the back stack of this fragment is not empty,
// then emulate 'onBackPressed' behaviour, because in default, it is not working
FragmentManager fm = getSupportFragmentManager();
for (Fragment frag : fm.getFragments()) {
if (frag.isVisible()) {
FragmentManager childFm = frag.getChildFragmentManager();
if (childFm.getBackStackEntryCount() > 0) {
childFm.popBackStack();
return;
}
}
}
super.onBackPressed();
}