检测 UIScrollView 外部的点击
我根据这种技术实现了分页滚动 ( iOS 开发. 如何扩展 UIScrollView 的滚动事件响应区域? )并且它按预期工作。
我正在滚动的视图包含几个按钮,我希望不仅能够单击滚动视图中居中/分页的按钮,还能够单击滚动视图左侧和右侧的按钮。我找不到任何方法来解决这个问题,但我还不是真正的 iOS 绝地武士,希望你们中的一个是:)
因此,从屏幕上可以看到,UIScrollView大约是窗口宽度的三分之一,UIScrollView的内容大小要大得多:大约1500px并包含许多以编程方式添加的按钮。该解决方案的最酷之处以及实际起作用的部分是按钮: 1)分页到滚动视图中 2) 在滚动视图外部可见(因为滚动视图的“剪辑子视图”未选中) 3) 按钮在 uiscrollview 内部可见时可单击。
但行不通的只是这样: - 当前位于窗口外部的按钮在单击它们时不会收到“它们的”点击,而是将事件转发到底层(窗口的白色部分)视图。
I've implemented a paged scroll according to this technique
( iOS develop. How to extend UIScrollView's scroll event responding area? ) and it works just as intended.
The view that I'm scrolling is containing a couple of buttons and I want to be able to click not only those that are centered/paged into the scrollview but also those to the left and to the right of it. I cannot find any way to solve this but I'm not really an iOS-Jedi yet, hoping one of you are though :)
So as you can see from the screenie the UIScrollView is about a third of the width of the window, the contentsize of the UIScrollView is much larger: about 1500px and contains a lot of buttons added programmatically. The cool thing with this solution, and the part that actually works, is that the buttons:
1) are paged into the scrollview
2) are visible outside the scrollview (since "clip subviews" is unchecked for the scrollview) 3) the buttons are clickable when visible inside the uiscrollview.
BUT what doesn't work is simply this:
- the buttons currently being outside of the window does not receive "their" clicks when clicking on them, the events are instead forwarded to the underlaying (the white part of the window) view.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
所以,
我终于设法解决了这个难题,解决方案分为两个
部分。正如您所记得的那样,问题是点击事件没有传输到
UIScrollView 外部(可见)的按钮。事实证明,点击是由底层视图捕获的,并且可以通过稍微改变关于谁被击中的规则来操纵他们找到目标的方式,从而欺骗事件传递到你想要的地方。不太确定这是否应该这样做,但它解决了我的问题...... :)
1)第一个必须重写底部视图中的以下方法
以便在适当的时候返回滚动视图而不是其本身。
2)scrollView 必须重写两个方法以将点击移交给其包含的对象。
非常
感谢您的评论和愿意提供帮助。
我嗬
So,
I finally managed to solve this puzzle and the solution is divided into two
parts. The problem was, as you way recall, that the click events did not travel to the
buttons that were(visible) outside the UIScrollView. It turned out that the clicks were captured by the underlying view and that it is possible to manipulate their way to finding their target by bending the rules a bit regarding who got hit and thereby tricking the events to get passed where you want them. Not really sure if this is how it should be done but it solved my problem.. . :)
1) First one must override the following method in the bottom view
so that it returns the scrollview instead of itself when appropriate.
2) The scrollView must override TWO methods to hand over the clicks to its contained objects.
and
Thanks a lot for you comments and willingness to help.
I ho
受到@tommys提到的答案的启发,事实证明,通过重写UIView的hinTest方法并返回scrollView,您实际上可以将此UIView的滑动分离到scrollView。
所以这个UIView的作用就像是scrollView的扩展滚动区域,想法就在这里。如果将 UIView 遮罩覆盖在滚动视图上并且与窗口大小相同,则在窗口内的任意位置滑动都会使滚动视图滚动。
这是示例 ExtensionScrollArea
Inspired by the answer @tommys mentioned, it turns out that by overriding the hinTest method of a UIView and return the scrollView instead, you actually can detach the swiping of this UIView to the scrollView.
So this UIView is acting like an extension scroll area of the scrollView, the idea is here. If you make the UIView mask over the scrollView and same size of the window, then swiping anywhere inside the window makes the scrollView scroll.
Here is the example, ExtensionScrollArea
这是我的版本:
在容器中进行命中测试
(*) 如果您正在移动或以其他方式隐藏视图,例如,如果您有多个视图,每个视图都有自己的滚动视图,则此标记线非常重要。如果您没有此行,则可能会将所有触摸定向到屏幕外滚动视图!
在滚动视图中覆盖
(在容器的 hitTest 中,您可以在默认行为的 if 语句中排除其他帧):)
Here's my version:
hit test in container
(*) This marked line is important if you are moving about or otherwise hiding your view, for instance if you have multiple views, each with their own scrollviews. If you don't have this line, you may be directing all your touches to an off-screen scrollview!
override in scrollview
(in the hitTest of the container, you can exclude additional frames within the if statement for default behaviour) :)