我有一个UILabel对象正在动画,上下移动。我使用Swift 3在Xcode 8.3中编码。用户可以平移此对象并拖动到一个位置以获得一些点。我正在使用touchesXXX
手势处理平移/拖动。然而,当我点击并让它立即行进时,由于某种原因,这个物体在其位置上方垂直跳跃,我现在无法弄清楚为什么一周...
当我启用一些调试时,我只能看到touchesBegan
被调用(touchesMoved
没有按预期调用,touchesEnded
对我来说都不是意外的。如果我手动禁用对象上的动画,它会按预期工作,并且该对象可以毫不费力地进行平移,并且显然没有对象跳转。
以下是相关代码的摘录:
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
let touch = touches.first
let touchLocation = touch!.location(in: self.view)
if self.optOneLbl.layer.presentation()!.hitTest(touchLocation) != nil {
//pauseLayer(self.optOneLbl.layer) <<<<< comment #1
//optOneLbl.translatesAutoresizingMaskIntoConstraints = true <<<<< comment #2
optOneLbl.center = touchLocation
}
}
override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
let touch = touches.first
let touchLocation = touch!.location(in: self.view)
var sender: UILabel
if self.optOneLbl.layer.presentation()!.hitTest(touchLocation) != nil {
self.optOneLbl.center = touchLocation
sender = self.optOneLbl
}
// identify which letter was overlapped
var overlappedView : UILabel
if (sender.frame.contains(letter1.center)) {
...
}
else {
return
}
}
override func touchesEnded(_ touches: Set<UITouch>, with event: UIEvent?) {
super.touchesEnded(touches, with: event)
}
在阅读了对其他SO问题的回复后,我认为按照上面touchesBegan
中的评论#1触摸时,以编程方式禁用标签动画可能会有所帮助,但问题仍然存在。此外,我认为可能是自动布局导致这种奇怪的跳跃。所以,我根据评论#2启用了translatesAutoresizingMaskIntoConstraints
,但它也没有帮助。
任何人都能看到我处理错误的地方? 谢谢你的阅读!
编辑:
根据@ agibson007请求,我添加动画代码提取以供参考:
UIView.animate(withDuration: 12.0, delay: 0.0, options: [ .allowUserInteraction, .curveLinear, .autoreverse, .repeat ], animations: {
self.optOneLbl.center = CGPoint(x: self.optOneLbl.center.x, y: screenSize.midY*1.1)
})
答案 0 :(得分:1)
更改标签的位置后,您需要删除/重置动画。动画不知道您更新了值并且尝试从头开始保持在相同的byValue范围内。这是更新动画的工作示例。
import UIKit
class ViewController: UIViewController {
var optOneLbl = UILabel()
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
optOneLbl = UILabel(frame: CGRect(x: 20, y: 50, width: self.view.bounds.width - 40, height: 40))
optOneLbl.textAlignment = .center
optOneLbl.text = "I Will Be Moving Up and Down"
optOneLbl.textColor = .white
optOneLbl.backgroundColor = .blue
self.view.addSubview(optOneLbl)
//starts it in the beginnning with a y
fireAnimation(toY: self.view.bounds.midY*1.1)
}
func fireAnimation(toY:CGFloat) {
UIView.animate(withDuration: 12.0, delay: 0.0, options: [ .allowUserInteraction, .curveLinear, .autoreverse, .repeat ], animations: {
self.optOneLbl.center = CGPoint(x: self.optOneLbl.center.x, y:toY)
})
}
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
let touch = touches.first
let touchLocation = touch!.location(in: self.view)
if self.optOneLbl.layer.presentation()!.hitTest(touchLocation) != nil {
//re
optOneLbl.layer.removeAllAnimations()
optOneLbl.center = touchLocation
}
}
override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
let touch = touches.first
let touchLocation = touch!.location(in: self.view)
var sender: UILabel
if self.optOneLbl.layer.presentation()!.hitTest(touchLocation) != nil {
self.optOneLbl.center = touchLocation
sender = self.optOneLbl
}
}
override func touchesEnded(_ touches: Set<UITouch>, with event: UIEvent?) {
super.touchesEnded(touches, with: event)
//restart animation after finished and change the Y if you want.
// you could change duration or whatever
fireAnimation(toY: self.view.bounds.height - optOneLbl.bounds.height)
}
}
答案 1 :(得分:0)
您可以使用UIPanGestureRecognizer实现相同目的。在您的标签上添加平移手势,并将标签移动到平底锅上
@IBAction func handlePan(_ gestureRecognizer: UIPanGestureRecognizer) {
if gestureRecognizer.state == .began || gestureRecognizer.state == .changed {
let translation = gestureRecognizer.translation(in: self.view)
yourLabel!.center = CGPoint(x: yourLabel!.center.x + translation.x, y: yourLabel!.center.y + translation.y)
gestureRecognizer.setTranslation(CGPoint.zero, in: self.view)
}
}
您可以从故事板向您的UILabel添加gesturerecognizer,或在viewDidLoad中以编程方式添加
let gestureRecognizer = UIPanGestureRecognizer(target: self, action: #selector(handlePan))
yourLabel.addGestureRecognizer(gestureRecognizer)
使用Pan手势作为您不必跟进touchesXX方法的优势。为什么你的观点正在向上移动,我认为你可能会在其他地方重置你的标签框架。手势也有可能与触摸相冲突。由于这两种情况在您的代码中都不明显,我们需要更多代码来确认相同的内容。