实现类似QQ微信视频的iOS小窗口自由拖动

实现效果:小窗口拖动,注意是仅当拖动小窗口时候才移动,触摸小窗口外部不移动

hitTest: 方法同样接受一个CGPoint类型参数,而不是BOOL类型,它返回图层本身,或者包含这个坐标点的叶子节点图层。直接获得位于点击事件响应链条最前沿的子图层或自身,不需要一层一层用-conrainsPoint:去判断

如果说小窗口视图没有非常复杂的视图的结构的话,采用以下的方法

触摸事件开始,主要做点击区域判断


- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
    [super touchesBegan:touches withEvent:event];
    
    UITouch *touch = [touches anyObject];
    
    CGPoint point = [touch locationInView:self.view];
    
    CALayer *touchedLayer = [self.view.layer hitTest:point];
    
    if(touchedLayer == self.smallView.layer){
        self.isMoving = YES;
    }
}

拖动过程,计算偏移

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{
    [super touchesMoved:touches withEvent:event];
    
    if(!self.isMoving){
        return;
    }
    
    UITouch *touch = [touches anyObject];
    
    CGPoint current = [touch locationInView:self.view];
    CGPoint previous = [touch previousLocationInView:self.view];
    
    CGPoint center = self.smallView.center;
    
    CGPoint offset = CGPointMake(current.x - previous.x, current.y - previous.y);
    
    self.smallView.center = CGPointMake(center.x + offset.x, center.y + offset.y);
}

拖动结束

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{
    [super touchesEnded:touches withEvent:event];
    
    self.isMoving = NO;
}

相对而言的,如果说小窗口有比较复杂的视图结构,比如说有多级子视图,这时候上面的方法久不合适了

原因:-touchesBegan:方法中CALayer *touchedLayer = [self.view.layer hitTest:point]; 会直接获取顶层的图层,也就是位于响应链最前沿的视图的图层,所以这时候再进行图层判断if(touchedLayer == self.smallView.layer){ 就不合适了!

-containsPoint: 接受一个在本图层坐标系下的CGPoint,如果这个点在图层frame范围内就返回YES

这时候就就应该采用如下的方式


- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
    [super touchesBegan:touches withEvent:event];
    
    UITouch *touch = [touches anyObject];
    
    CGPoint point = [touch locationInView:self.view];
    
    //Converts the point from the specified layer’s coordinate system to the receiver’s coordinate system.
    point = [self.catEarView.layer convertPoint:point fromLayer:self.view.layer];
    
    if([self.catEarView.layer containsPoint:point]){
        self.isMoving = YES;
    }
}

你可能感兴趣的:(实现类似QQ微信视频的iOS小窗口自由拖动)