如何向 UIView 添加大小调整手柄?
How can I add sizing handles to a UIView?
我正在尝试根据用户请求在运行时动态创建视图(UIImageView 和 UITextView),然后允许用户移动和调整它们的大小。除了调整大小,我的一切都很好。我尝试使用捏合手势识别器,但发现它对于我想要的东西来说太笨拙了。因此,我想使用大小调整手柄。我相信我可以在每个手柄上放置一个平移手势识别器,并在其中一个手柄移动时调整视图框架。
问题是,我不太确定如何创建大小调整手柄。我会指出我尝试过的所有事情,但说实话,我不太确定从哪里开始。我有一些想法...
1) 可能用coregraphics在角和边上画方框或圆圈?我会创建一个新层并在上面绘制它们吗?不确定。
2) 在每个角上贴一个方框或圆圈的小图像?
3) XIB 文件已经放置了句柄?
任何建议表示赞赏。我只需要指出正确的方向。
编辑:像 Apple 在 Pages 中使用的东西就完美了!
首先,我建议为 UIView 创建一个自定义 View 子类,您将处理此处的所有行为。我们称它为 ResizableView。
在自定义视图中,您需要为这些角点绘制图层或视图,并将 PangestureRecognized 添加到 them.Then 您可以在用户拖动它们时使用 recognizer.locationInView()
跟踪这些点的位置,用来计算View.Here比例的代码可以参考:
func rotateViewPanGesture(recognizer: UIPanGestureRecognizer) {
touchLocation = recognizer.locationInView(self.superview)
let center = CalculateFunctions.CGRectGetCenter(self.frame)
switch recognizer.state {
case .Began:
initialBounds = self.bounds
initialDistance = CalculateFunctions.CGpointGetDistance(center, point2: touchLocation!)
case .Changed:
//Finding scale between current touchPoint and previous touchPoint
let scale = sqrtf(Float(CalculateFunctions.CGpointGetDistance(center, point2: touchLocation!)) / Float(initialDistance!))
let scaleRect = CalculateFunctions.CGRectScale(initialBounds!, wScale: CGFloat(scale), hScale: CGFloat(scale))
self.bounds = scaleRect
self.refresh()
case:.Ended:
self.refresh()
default:break
循序渐进
touchLocation
Pangesture 的位置
center
是ResizableView的中心
initialBounds
是PanGesture开始时ResizableView的初始边界。
initailDistance
是用户拖动的点的 touchPoint 的 ResizableView 中心之间的距离。
然后可以计算scale
给定initialDistance
,center
,touch location
现在您已经根据需要缩放了视图。你还需要相应地刷新这些角点的位置,这就是refresh()
的原因,你需要自己实现。
计算函数
我倾向于定义一些 helpFunctions 来帮助我计算。
CalculateFunctions.CGPointGetDistance
用于计算视图中心到触摸位置的距离
CalculateFunctions.CGRectScale
return 给定您刚刚计算的比例的缩放 CGRect。
CalculateFunctions.CGRectGetCenter
return CGRect
的中心点
这只是一个粗略的想法。其实还有很多库可以参考。
一些建议:
- SPUserResizableView
这正是您想要的 ResizableView,但它是用 ObjC 编写的,并且已经很长时间没有更新了。不过你可以参考一下。
- JLStickerTextView 这可能不太符合你的要求,因为它是文本(编辑,调整大小,用一根手指旋转)但是,这个是用 Swift 写的,一个很好的例子你.
如有任何问题,随时post it.Good 运气:-)
我正在尝试根据用户请求在运行时动态创建视图(UIImageView 和 UITextView),然后允许用户移动和调整它们的大小。除了调整大小,我的一切都很好。我尝试使用捏合手势识别器,但发现它对于我想要的东西来说太笨拙了。因此,我想使用大小调整手柄。我相信我可以在每个手柄上放置一个平移手势识别器,并在其中一个手柄移动时调整视图框架。
问题是,我不太确定如何创建大小调整手柄。我会指出我尝试过的所有事情,但说实话,我不太确定从哪里开始。我有一些想法...
1) 可能用coregraphics在角和边上画方框或圆圈?我会创建一个新层并在上面绘制它们吗?不确定。
2) 在每个角上贴一个方框或圆圈的小图像?
3) XIB 文件已经放置了句柄?
任何建议表示赞赏。我只需要指出正确的方向。
编辑:像 Apple 在 Pages 中使用的东西就完美了!
首先,我建议为 UIView 创建一个自定义 View 子类,您将处理此处的所有行为。我们称它为 ResizableView。
在自定义视图中,您需要为这些角点绘制图层或视图,并将 PangestureRecognized 添加到 them.Then 您可以在用户拖动它们时使用 recognizer.locationInView()
跟踪这些点的位置,用来计算View.Here比例的代码可以参考:
func rotateViewPanGesture(recognizer: UIPanGestureRecognizer) {
touchLocation = recognizer.locationInView(self.superview)
let center = CalculateFunctions.CGRectGetCenter(self.frame)
switch recognizer.state {
case .Began:
initialBounds = self.bounds
initialDistance = CalculateFunctions.CGpointGetDistance(center, point2: touchLocation!)
case .Changed:
//Finding scale between current touchPoint and previous touchPoint
let scale = sqrtf(Float(CalculateFunctions.CGpointGetDistance(center, point2: touchLocation!)) / Float(initialDistance!))
let scaleRect = CalculateFunctions.CGRectScale(initialBounds!, wScale: CGFloat(scale), hScale: CGFloat(scale))
self.bounds = scaleRect
self.refresh()
case:.Ended:
self.refresh()
default:break
循序渐进
touchLocation
Pangesture 的位置
center
是ResizableView的中心
initialBounds
是PanGesture开始时ResizableView的初始边界。
initailDistance
是用户拖动的点的 touchPoint 的 ResizableView 中心之间的距离。
然后可以计算scale
给定initialDistance
,center
,touch location
现在您已经根据需要缩放了视图。你还需要相应地刷新这些角点的位置,这就是refresh()
的原因,你需要自己实现。
计算函数
我倾向于定义一些 helpFunctions 来帮助我计算。
CalculateFunctions.CGPointGetDistance
用于计算视图中心到触摸位置的距离
CalculateFunctions.CGRectScale
return 给定您刚刚计算的比例的缩放 CGRect。
CalculateFunctions.CGRectGetCenter
return CGRect
这只是一个粗略的想法。其实还有很多库可以参考。 一些建议:
- SPUserResizableView 这正是您想要的 ResizableView,但它是用 ObjC 编写的,并且已经很长时间没有更新了。不过你可以参考一下。
- JLStickerTextView 这可能不太符合你的要求,因为它是文本(编辑,调整大小,用一根手指旋转)但是,这个是用 Swift 写的,一个很好的例子你.
如有任何问题,随时post it.Good 运气:-)