1

这是这种情况:

我有一个包含三个片段的 PagerAdapter 活动。此活动允许您更改屏幕方向。

其中一个片段使用 osmdroid 库创建了 mapView,并且保留了该片段 ( setRetainInstance(true) )。在每次更改方向时,都会再次触发 onCreateView 事件:

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {
    fragmentView = (LinearLayout) inflater.inflate(R.layout.main,
            container, false);

    mapView = (MapView) fragmentView.findViewById(R.id.practice_mapview);

    mapView.setBuiltInZoomControls(true);
    mapView.setMultiTouchControls(true);
    mapView.setTileSource(TileSourceFactory.MAPNIK);
    mapView.setUseSafeCanvas(true);
    setHardwareAccelerationOff();

    mapController = (MapController) mapView.getController();

    [...]

    mLocationOverlay = new MyLocationOverlay(getActivity(), mapView);
    mLocationOverlay.setDrawAccuracyEnabled(true);

    [...]

    mapView.invalidate();

    return fragmentView;
}

开始时一切正常,但是当我旋转手机时,会再次执行语句“ mLLocationOverlay = new MyLocationOverlay(getActivity(), mapView); ”,这意味着当您关闭应用程序时,GPS 图标永远不会消失。

如果您不旋转手机,该图标会在应用程序关闭时消失。

这就是我在 onPause 事件中的内容:

@Override
public void onPause() {
    mLocationOverlay.disableCompass();

    if (this.getActivity().isFinishing()) {
        disableMyLocation();    
        releaseLocationOverlay();
    }

    cleanMapViewCache();
}

private void disableMyLocation() {
    if (mLocationOverlay.isMyLocationEnabled() == true)
        mLocationOverlay.disableMyLocation();

    if (mLocationOverlay.isFollowLocationEnabled() == true)
        mLocationOverlay.disableFollowLocation();
}

private void releaseLocationOverlay() {
    if (mLocationOverlay != null) {
        mapView.getOverlays().remove(mLocationOverlay);
        mLocationOverlay = null;
    }
}

private void cleanMapViewCache() {
    mapView.getTileProvider().clearTileCache();
    System.gc();
}

Si en el eventto onCreateView hago este sencillo control el problema desaparece:

如果我把这个控件放在 onCreateView 事件中,问题就消失了:

if (this.getActivity().isFinishing())
    mLocationOverlay = new MyLocationOverlay(getActivity(), mapView);

但是,除其他外,我无法再居中:

mapController.animateTo(mLocationOverlay.getMyLocation());

任何想法?有什么我做错了吗?

如果您需要更多代码,则无需多说。谢谢!

4

1 回答 1

0

这里有两件事:

1)我对您的代码的理解是,mLocationOverlay当方向改变时会重新创建它,但不会关闭其旧实例,从而导致 aLocationListener保持活动并链接到 GPS。

而不是这样做onCreate()

// this is a copypaste of your workaround code but that prevents the map from moving
if (this.getActivity().isFinishing())
    mLocationOverlay = new MyLocationOverlay(getActivity(), mapView);

尝试做:

if (mLocationOverlay != null) {
    uninitialize(); // see below
    mLocationOverlay = new MyLocationOverlay(getActivity(), mapView);
 }

然后,改变你onPause()的方式:

public void onPause() {
    uninitialize();
}

并创建此方法:

private void uninitialize() {
    // What follows is your former onPause() code:
    mLocationOverlay.disableCompass();

    if (this.getActivity().isFinishing()) {
        disableMyLocation();    
        releaseLocationOverlay();
    }

    cleanMapViewCache();
}

所有这些都需要优化/重构。例如,我不确定cleanMapViewCache()在更改设备方向时调用是否有用。

2)另外,非常重要的是,不要让你的前者mapController从一个方向转移到另一个方向:当你MapView重新初始化时onCreate(),你的控制器也应该重新初始化。这可能就是地图不再移动的原因:控制器引用 this 的前一个实例MapView而不是当前实例。

这一切都行得通吗?不要犹豫让我知道,如果需要,我会编辑我的答案。

于 2014-07-22T11:40:52.113 回答