安卓谷歌地图 |两指滚动

标签 android google-maps scroll conditional custom-scrolling

我正在使用 Google map ,

我的情况是我在 ScrollView 中有一个 map fragment ,如果用户只触摸一个手指 map 不工作,我只需要用两根手指滚动 map 和正常的 ScrollView 应该工作。

这是我到目前为止尝试过的 -

transparent_image.setOnTouchListener(new View.OnTouchListener() {

                @Override
                public boolean onTouch(View v, MotionEvent event) {
                    int action = event.getAction();
                    switch (action & MotionEvent.ACTION_MASK) {
                        case MotionEvent.ACTION_POINTER_DOWN:
                            showMessage("Double finger ACTION_POINTER_DOWN");

                            googleMap.getUiSettings().setScrollGesturesEnabled(false);
                            scroll_view.requestDisallowInterceptTouchEvent(true);
                            return true;
                        case MotionEvent.ACTION_POINTER_UP:
                            showMessage("Double finger ACTION_POINTER_UP");

                            googleMap.getUiSettings().setScrollGesturesEnabled(true);

                            scroll_view.requestDisallowInterceptTouchEvent(false);

                            return true;

                        default:
                            return true;
                    }
                }
            });

最佳答案

您可以在以下情况下实现 native Android 应用程序的行为:

1) 当用户将两根手指放在MapFragment 上时,禁用ScrollView 滚动并启用GoogleMap 滚动;

2) 在其他情况下启用ScrollView 滚动并禁用GoogleMap 滚动。

要根据条件禁用/启用ScrollView 滚动,您需要扩展ScrollView 并覆盖onTouchEvent() 方法以返回 false 当某些条件匹配时,例如 this answerJosep Earl :

public class LockableScrollView extends ScrollView {

    private boolean mScrollable = true;

    public LockableScrollView(Context context) {
        super(context);
    }

    public LockableScrollView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public LockableScrollView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    public void setScrollingEnabled(boolean enabled) {
        mScrollable = enabled;
    }

    public boolean isScrollable() {
        return mScrollable;
    }

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        switch (ev.getAction()) {
            case MotionEvent.ACTION_DOWN:
                // if we can scroll pass the event to the superclass
                if (mScrollable) return super.onTouchEvent(ev);
                // only continue to handle the touch event if scrolling enabled
                return mScrollable; // mScrollable is always false at this point
            default:
                return super.onTouchEvent(ev);
        }
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev) {
        // Don't do anything with intercepted touch events if
        // we are not scrollable
        if (!mScrollable) return false;
        else return super.onInterceptTouchEvent(ev);
    }
}

GoogleMap 启用/禁用滚动手势您可以轻松调用 GoogleMap.getUiSettings( ) 对象并确定两根手指在 MapFragment 上的触摸,您可以使用基于 this answer 的方法社区维基:

public class TouchableWrapper extends FrameLayout {

    private LockableScrollView mLockableScroll;
    private GoogleMap mGoogleMap;

    public TouchableWrapper(Context context) {
        super(context);
    }

    public void setGoogleMapAndScroll(GoogleMap googleMap, LockableScrollView lockableScroll) {
        mGoogleMap = googleMap;
        mLockableScroll = lockableScroll;
    }


    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {

        switch (event.getAction() & MotionEvent.ACTION_MASK) {

            case MotionEvent.ACTION_DOWN:
                mGoogleMap.getUiSettings().setScrollGesturesEnabled(false);
                // UPDATE: add below line to disable zoom gesture
                mGoogleMap.getUiSettings().setZoomGesturesEnabled(false);
                mLockableScroll.setScrollingEnabled(true);
            break;

            case MotionEvent.ACTION_POINTER_DOWN:
                mLockableScroll.setScrollingEnabled(false);
                mGoogleMap.getUiSettings().setScrollGesturesEnabled(true);
                // UPDATE: add below line to enable zoom gesture
                mGoogleMap.getUiSettings().setZoomGesturesEnabled(true);

            break;

            case MotionEvent.ACTION_POINTER_UP:
                // UPDATE: add below line to disable zoom gesture
                mGoogleMap.getUiSettings().setZoomGesturesEnabled(false);
                mGoogleMap.getUiSettings().setScrollGesturesEnabled(false);
                mLockableScroll.setScrollingEnabled(true);
            break;

            case MotionEvent.ACTION_UP:
                // UPDATE: add below line to disable zoom gesture
                mGoogleMap.getUiSettings().setZoomGesturesEnabled(false);
                mGoogleMap.getUiSettings().setScrollGesturesEnabled(false);
                mLockableScroll.setScrollingEnabled(true);
            break;
        }
        return super.dispatchTouchEvent(event);
    }
}

MapFragment 在这种情况下可以是这样的:

public class MultiTouchMapFragment extends MapFragment {
    public View mOriginalContentView;
    public TouchableWrapper mTouchView;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup parent, Bundle savedInstanceState) {
        mOriginalContentView = super.onCreateView(inflater, parent, savedInstanceState);
        mTouchView = new TouchableWrapper(getActivity());
        mTouchView.addView(mOriginalContentView);
        return mTouchView;
    }

    @Override
    public View getView() {
        return mOriginalContentView;
    }
}

MainActivity 这样(不需要在 map 上添加标记 - 它只是为了测试):

public class MainActivity extends AppCompatActivity implements OnMapReadyCallback {
    private LockableScrollView mLockableScrollView;
    private MultiTouchMapFragment mapFragment;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        mLockableScrollView = (LockableScrollView) findViewById(R.id.lockable_scroll);
        mapFragment = (MultiTouchMapFragment) getFragmentManager()
                .findFragmentById(R.id.map_fragment);
        mapFragment.getMapAsync(this);
    }

    @Override
    public void onMapReady(GoogleMap googleMap) {
        LatLng marker = new LatLng(48, 38);
        googleMap.addMarker(new MarkerOptions().position(marker).title("Scroll"));
        googleMap.getUiSettings().setAllGesturesEnabled(false);

        mapFragment.mTouchView.setGoogleMapAndScroll(googleMap, mLockableScrollView);
    }
}

最后,例如 MainActivityactivity_main.xml 可以是这样的:

<[your_package_name].LockableScrollView
    android:id="@+id/lockable_scroll"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">

        <ImageView
            android:layout_width="match_parent"
            android:layout_height="300dp"
            android:src="@mipmap/ic_launcher"/>

        <fragment
            android:id="@+id/map_fragment"
            android:name="[your_package_name].MultiTouchMapFragment"
            android:layout_width="match_parent"
            android:layout_height="300dp"/>

        <ImageView
            android:layout_width="match_parent"
            android:layout_height="300dp"
            android:src="@mipmap/ic_launcher"/>

    </LinearLayout>

</[your_package_name].LockableScrollView>

就是这样。

关于安卓谷歌地图 |两指滚动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46320667/

相关文章:

android - 应用内结算,无法让 RESULT_DEVELOPER_ERROR 消失

java - 等待更新程序单例

ios - 可以在 GMSPanoramaView 中为 GMSMarkers 设置动画

java - 在java中解析google geocode结果 - 找不到JSONArray [0](它在那里)

javascript - 请帮我解决这个平滑的 float 卷轴

android - 是否有适用于 Android 的电子表格小部件?

android - 磁场的绝对强度: Android

ios - 如何修复我的自定义标记的大小和颜色

jquery - 将滚动从整个页面更改为单个 div

css - 将一个图像滚动到另一个 css