- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有一个由许多 ScrollView 组成的 Gallery,每个 ScrollView 都占据了整个屏幕。问题是 ScrollViews 的 onTouchEvent 返回 true,因此阻止 DOM 中的任何其他 View 处理相同的事件(在 ScrollView 级别处理后被吞没)。结果画廊不再滚动。另一方面,如果我像这样覆盖 onTouchEvent:
@Override
public boolean onTouchEvent(MotionEvent ev) {
super.onTouchEvent(ev);
return false; // <<<<<<<<<<<<<<<<<
}
然后 Gallery 收到要处理的 on 事件,但 SrollView 不再滚动。反正你输了!还是你?
这个问题听起来令人费解,但我敢肯定,如果你过去偶然发现了它,你会立即认出它,因为它是一个该死的问题!
谢谢
最佳答案
这是我尝试使用垂直 ScrollViews
的图库。
它使用自己的 GestureDetector
实例,并为它提供来自 onInterceptTouchEvent
的 MotionEvents
。
当手势检测器识别到滚动时,我们确定它是水平还是垂直并锁定方向,直到手势完成。这避免了对角线滚动。
如果是水平滚动,onInterceptTouchEvent
将返回 true,以便将来的运动事件转到继承的 Gallery.onTouchEvent
以进行实际滚动。
Gallery
自己的手势检测器(Gallery.java
中的mGestureDetector
)不会获取所有运动事件,因此有时会报告巨大的突发事件导致画廊跳来跳去的卷轴。我做了一个讨厌的 hack 来丢弃那些。
代码:
import android.content.Context;
import android.util.AttributeSet;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.widget.Gallery;
public class BetterGallery extends Gallery {
/* This gets set when we detect horizontal scrolling */
private boolean scrollingHorizontally = false;
/* This gets set during vertical scrolling. We use this to avoid detecting
* horizontal scrolling when vertical scrolling is already in progress
* and vice versa. */
private boolean scrollingVertically = false;
/* Our own gesture detector, Gallery's mGestureDetector is private.
* We'll feed it with motion events from `onInterceptTouchEvent` method. */
private GestureDetector mBetterGestureDetector;
public BetterGallery(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
mBetterGestureDetector = new GestureDetector(new BetterGestureListener());
}
public BetterGallery(Context context, AttributeSet attrs) {
super(context, attrs);
mBetterGestureDetector = new GestureDetector(new BetterGestureListener());
}
public BetterGallery(Context context) {
super(context);
mBetterGestureDetector = new GestureDetector(new BetterGestureListener());
}
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
float velocityY) {
// Limit velocity so we don't fly over views
return super.onFling(e1, e2, 0, velocityY);
}
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
// Documentation on this method's contract:
// http://developer.android.com/reference/android/view/ViewGroup.html#onInterceptTouchEvent(android.view.MotionEvent)
// Reset our scrolling flags if ACTION_UP or ACTION_CANCEL
switch (ev.getAction()) {
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_CANCEL:
scrollingHorizontally = false;
scrollingVertically = false;
}
// Feed our gesture detector
mBetterGestureDetector.onTouchEvent(ev);
// Intercept motion events if horizontal scrolling is detected
return scrollingHorizontally;
}
@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
// Hack: eat jerky scrolls caused by stale state in mGestureDetector
// which we cannot directly access
if (Math.abs(distanceX) > 100) return false;
return super.onScroll(e1, e2, distanceX, distanceY);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
// Reset our scrolling flags if ACTION_UP or ACTION_CANCEL
switch(event.getAction()) {
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_CANCEL:
scrollingHorizontally = false;
scrollingVertically = false;
}
super.onTouchEvent(event);
return scrollingHorizontally;
}
private class BetterGestureListener implements GestureDetector.OnGestureListener {
@Override
public boolean onDown(MotionEvent arg0) {
return false;
}
@Override
public boolean onFling(MotionEvent arg0, MotionEvent arg1, float arg2, float arg3) {
return false;
}
@Override
public void onLongPress(MotionEvent arg0) {
}
@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
if (scrollingHorizontally || scrollingVertically) {
// We already know we're scrolling, ignore this callback.
// This avoids changing scrollingHorizontally / scrollingVertically
// flags mid-scroll.
return false;
}
scrollingHorizontally |= Math.abs(distanceX) > Math.abs(distanceY);
// It's a scroll, and if it's not horizontal, then it has to be vertical
scrollingVertically = !scrollingHorizontally;
return false;
}
@Override
public void onShowPress(MotionEvent arg0) {
}
@Override
public boolean onSingleTapUp(MotionEvent arg0) {
return false;
}
}
}
警告:类(class)名称中的“Better”一词可能具有误导性!
更新:
忘记说了,我还设置了将它的 onTouchEvent
转发到 gallery 的 Activity:
@Override
public boolean onTouchEvent(MotionEvent event) {
return mGallery.onTouchEvent(event);
}
更新 2:
我对这段代码做了一些改进并将其发布在 bitbucket 上.还有一个示例应用程序。它表明此小部件与作为子级的 ListView 存在问题:-/
更新 3:
从 Gallery
切换到 HorizontalScrollView
作为我的自定义小部件的基类。 More on this here . Flings 工作,ListViews 和 ExpandableListViews 作为 child 工作,在 Android 1.6、2.2、2.3.4 上测试。它的行为现在非常接近谷歌应用程序的行为,IMO。
更新 4:
Google 已发布 ViewPager !
关于android - ScrollView 和 Gallery 干扰,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5012545/
我正在尝试创建一个类似于 BBC 新闻 native 应用程序的布局(使用known.js);一个垂直的ScrollView,其中有许多水平的ScrollView。我已经“工作”到了一切都渲染并且水平
我正在尝试创建一个类似于 BBC 新闻 native 应用程序的布局(使用known.js);一个垂直的ScrollView,其中有许多水平的ScrollView。我已经“工作”到了一切都渲染并且水平
我已经为以下问题寻找了很多答案,但没有找到合适的解决方案(也不是“不可能”)。我不想要双向 ScrollView! 我想要的只是拥有这样的东西: 如果我这样做(具有所需的布局属性),我会得到我的
我想使用 famo.us 标准 Scrollview但是有一个以不同速度滚动的背景图像以产生视差效果。 我想知道是否有一种方法可以连接到事件流,或者以某种方式将 Scrollviews 位置通过管道传
初始化程序中有一个带有 ScrollView(alwaysBounceVertical: false) 的属性,但我似乎找不到它了。 有谁知道如何禁用 SwiftUI ScrollView 上的垂直弹
在你说之前 “Google 说不要这样做” 请阅读我的所有问题!! 布局: ScrollView -> RelativeLayout -> ScrollView -> RelativeLayout 第
我想在 Windows 7 上创建一种体验(使用触摸),我可以在其中拥有一个只能垂直滚动的外部 ScrollViewer(它是屏幕的大小)。在那个 ScrollViewer 中,我将有几个其他的 Sc
我知道 Google 的人要求我们不要将 Scrollable View 放在另一个 Scrollable View 中,但他们是否有任何官方声明指示我们不要这样做? 最佳答案 试试这个 注意:这里
更新Xcode11 beta3后,我发现scrollview内部 View 的阴影会在边界处被切断,但在Xcode11 beta2中还可以。我只是使用底部填充来修复它,但我认为这不是一个好的解决方案。
我的 wpf 应用程序的结构如下: 我的目标是,如果 DataGrid 超过屏幕的高度来使用它自己的 Scrollviewer。目前只使用外部的 S
我在其他应用程序中使用了 ScrollView,只添加了 style={styles.container}与风格。然而,在这个应用程序中,我正在创建我的风格 alignItems:'flex-star
这是我的布局 xml。 ... 我已经尝试过此链接中的解决方案: ScrollView Inside ScrollVie
有没有办法在 nativescript 的 ScrollView 上隐藏滚动指示器?我试过 scrollBars='none' 和 css overflow='hidden' 但它不能同时工作。谢谢
所以我有一个 ScrollView ,里面有一个 TextView 。当文本的String长于屏幕宽度时,它只是在下一行中移动。我想通过在 ScrollView 中添加 HorizontalScr
我正在尝试在 android 的水平 ScrollView 中创建一个水平 ScrollView 。第一个水平 ScrollView 工作正常。当我尝试滚动时,第二个水平 ScrollView 不起作
我在同一布局中创建了两个 ScrollView。你可以说一个平行的 ScrollView 。我想手动滚动一个 ScrollView ,作为响应,另一个 ScrollView 应该以完全相同的方式滚动。
我在 android 中设计 UI,我在另一个 HorizontalScrollView 中有一个 HorizontalScrollView。但是,子 HorizontalScrollVi
我在另一个 ScrollView 中有 ScrollView 。我想滚动内部 ScrollView ,但外部 ScrollView 只滚动。如何解决这个问题? 谢谢。 最佳答案 sv01 =
我有两个 UIScrollView,如果用户在 ScrollView 中滚动,我想让另一个 ScrollView 也滚动。我已经阅读了一个解决方案,涉及将 pangesturerecognizer 从
我以编程方式创建了 UIScrollView 并向其中添加了多个 button。 它运行良好,没有任何问题。 但我需要通过复制先前 ScrollView 的内容来创建另一个 ScrollView 。
我是一名优秀的程序员,十分优秀!