美文网首页iOS开发技巧iOS developer重力学
iOS UIKit动力学(四)吸附(UIAttachmentBe

iOS UIKit动力学(四)吸附(UIAttachmentBe

作者: JerryLMJ | 来源:发表于2016-11-07 18:19 被阅读1015次

    iOS UIKit力学(一)基本介绍(目录)

    导语

    吸附主要发生在:元素与锚点、元素与元素之间
    当元素与锚点连接,元素的运动依赖于锚点。
    当元素与元素连接,两个元素的运动彼此影响。
    有的吸附行为支持两个元素和一个锚点。

    除此之外,吸附还分为:刚性吸附和弹性吸附
    刚性吸附就好像两个物体间使用固定的杆连接,运动时之间的距离不变;
    而弹性吸附就好像两个物体间使用橡皮筋连接,运动时两者之间的距离会发生弹性形变。

    构造

    UIAttachmentBehavior的构造共有4种方法:

    // 元素和锚点之间的吸附
    - (instancetype)initWithItem:(id <UIDynamicItem>)item attachedToAnchor:(CGPoint)point;
    // 元素和锚点之间的吸附,offset参数设置元素吸附力作用点的偏移量
    - (instancetype)initWithItem:(id <UIDynamicItem>)item offsetFromCenter:(UIOffset)offset attachedToAnchor:(CGPoint)point NS_DESIGNATED_INITIALIZER;
    
    // 元素和元素之间的吸附 
    - (instancetype)initWithItem:(id <UIDynamicItem>)item1 attachedToItem:(id <UIDynamicItem>)item2;
    // 元素和元素之间的吸附,offset1、offset2分别是两个元素吸附力作用点的偏移量
    - (instancetype)initWithItem:(id <UIDynamicItem>)item1 offsetFromCenter:(UIOffset)offset1 attachedToItem:(id <UIDynamicItem>)item2 offsetFromCenter:(UIOffset)offset2 NS_DESIGNATED_INITIALIZER;
    
    • 元素与锚点
      蓝球(_dynamicItem1View):初始位置的center(125, 125)frame(100, 100, 50, 50),在初始位置以自由落体下落
    UIAttachmentBehavior * attachmentBehavior = 
    [[UIAttachmentBehavior alloc] initWithItem:_dynamicItem1View attachedToAnchor:CGPointMake(175, 250)];
    attachmentBehavior.length = 50;
    [_animator addBehavior:attachmentBehavior];
    

    效果如下:



    然后换用另外一个构造方法:

    UIAttachmentBehavior * attachmentBehavior = 
    [[UIAttachmentBehavior alloc] initWithItem:_dynamicItem1View offsetFromCenter:UIOffsetMake(25, 0) attachedToAnchor:CGPointMake(175, 250)];
    attachmentBehavior.length = 50;
    [_animator addBehavior:attachmentBehavior];
    

    给元素的吸附力作用点一个偏移量,向右偏移25像素(正好在蓝球的右侧边缘),再来看一下效果

    为了方便理解分别给锚点和吸附力作用点加了两颗红点,当然这两颗红点实际上是不存在的

    • 元素与元素
      蓝球(_dynamicItem1View)的初始设置不变,
      增加一个黑球(_dynamicItem2View)
    UIAttachmentBehavior * attachmentBehavior = 
    [[UIAttachmentBehavior alloc] initWithItem:_dynamicItem1View attachedToItem:_dynamicItem2View];
    attachmentBehavior.length = 100;
    [_animator addBehavior:attachmentBehavior];
    

    从效果中可以看出当蓝球黑球连接后,两个球彼此吸附,运动互相影响。
    换用另外一个构造方法:
    UIAttachmentBehavior * attachmentBehavior = 
    [[UIAttachmentBehavior alloc] initWithItem:_dynamicItem1View offsetFromCenter:UIOffsetMake(25, 0) attachedToItem:_dynamicItem2View offsetFromCenter:UIOffsetMake(-35, 0)];
    attachmentBehavior.length = 100;
    [_animator addBehavior:attachmentBehavior];
    

    分别给两个球的吸附力作用点设置一个偏移量,再来看一下效果


    属性

    • 吸附类型(只读)
    @property (readonly, nonatomic) UIAttachmentBehaviorType attachedBehaviorType;
    
    typedef NS_ENUM(NSInteger, UIAttachmentBehaviorType) {
        // 元素与元素间吸附
        UIAttachmentBehaviorTypeItems,
        // 元素与锚点间吸附
        UIAttachmentBehaviorTypeAnchor
    } NS_ENUM_AVAILABLE_IOS(7_0);
    
    • 锚点
      当吸附发生在元素和锚点之间的时候,我们可以通过anchorPoint属性获得锚点位置,如果吸附发生在元素和元素之间的时候,该属性的值为(0, 0)
    @property (readwrite, nonatomic) CGPoint anchorPoint;
    
    • 元素吸附力作用点和锚点的距离 或 两个元素吸附力作用点间的距离
      这个距离就是上面效果中的两个红色作用力点之间的距离,该属性对刚性吸附有直接影响
    @property (readwrite, nonatomic) CGFloat length;
    
    • 振动频率
      在上面的例子中基本都属于刚性吸附,除了刚性吸附之外弹性吸附也是很常用的类型,frequency属性就对弹性吸附有着直接的影响
    @property (readwrite, nonatomic) CGFloat frequency; // in Hertz
    

    frequency属性是指元素在发生弹性吸附时震动的频率,值越大,弹性运动的频率越快。
    由于物理知识有限,不能用详细的公式解释震动频率在吸附作用中的实际影响,所以只能用属性值的大小和实际效果帮助大家理解(请注意下面效果中球在围绕锚点运动时的上下震动情况):

    蓝球`frequency`值为`1000`
    黑球`frequency`值为`5`
    
    蓝球`frequency`值为`1000`
    黑球`frequency`值为`1`
    
    蓝球`frequency`值为`1000`
    黑球`frequency`值为`0.5`
    
    蓝球`frequency`值为`1000`
    黑球`frequency`值为`-1`
    
    • 弹性阻力
      damping属性是设置元素在弹性吸附时震动所受到的阻力,值越大,阻力越大,弹性运动震动的幅度越小。
    @property (readwrite, nonatomic) CGFloat damping; // 1: critical damping
    

    效果中蓝球damping值为100黑球damping值为1,其他属性完全一致。
    可以看出蓝球由于阻力大的原因向下拉伸的幅度没有黑球的幅度大,但两球最终静止时纵向位置是一样的。
    • 旋转阻力
      frictionTorque为旋转力矩,指围绕一点旋转所受的阻力,默认值0.0,值越大,阻力越大。
    @property (readwrite, nonatomic) CGFloat frictionTorque NS_AVAILABLE_IOS(9_0); // default is 0.0
    
    • 运动范围
    @property (readwrite, nonatomic) UIFloatRange attachmentRange NS_AVAILABLE_IOS(9_0); // default is UIFloatRangeInfinite
    

    类方法

    iOS 9之后新增了5个类方法,我们可以通过这5个类方法得到attachment behavior对象
    (下面这几个函数的用法只能凭官方文档和自己的理解解释一下,很有可能解释是完全错误的,希望有深谙这个几个函数用法的朋友不吝赐教)

    /*!
     item1和item2会吸附在锚点point上,而锚点point会按照axis向量指向的轴运动,从而得到一个attachment behavior对象
     item1和item2不会相对于锚点和轴旋转
     item1和item2运动的距离通过attachmentRange属性来限制
     */
    +(instancetype)slidingAttachmentWithItem:(id <UIDynamicItem>)item1 attachedToItem:(id <UIDynamicItem>)item2 attachmentAnchor:(CGPoint)point axisOfTranslation:(CGVector)axis NS_AVAILABLE_IOS(9_0);
    
    /*!
     item会吸附在锚点point上,而锚点point会按照axis向量指向的轴运动,从而得到一个attachment behavior对象
     item不会相对于锚点和轴旋转
     item运动的距离通过attachmentRange属性来限制
     */
    +(instancetype)slidingAttachmentWithItem:(id <UIDynamicItem>)item attachmentAnchor:(CGPoint)point axisOfTranslation:(CGVector)axis NS_AVAILABLE_IOS(9_0);
    
    /*!
    限制item1和item2之间的最大距离,从而得到一个attachment behavior对象
    item1和item2之间就像用一条绳子拴住,它们在运动中之间最大距离为绳子的长度
    offset1和offset2同上文中的作用力点偏移量
    item1和item2之间的最大距离的初始值为item1和item2初始位置间的距离,后续可以通过length属性修改
     */
    +(instancetype)limitAttachmentWithItem:(id <UIDynamicItem>)item1 offsetFromCenter:(UIOffset)offset1 attachedToItem:(id <UIDynamicItem>)item2 offsetFromCenter:(UIOffset)offset2 NS_AVAILABLE_IOS(9_0);
    
    /*!
    通过将item1和item2固定到锚点point上,得到一个attachment behavior对象
    item1、item2和锚点point之间的相对位置在运动中是不会发生变化的,就好像三者之间被木棍固定成为一个单元
     */
    +(instancetype)fixedAttachmentWithItem:(id <UIDynamicItem>)item1 attachedToItem:(id <UIDynamicItem>)item2 attachmentAnchor:(CGPoint)point NS_AVAILABLE_IOS(9_0);
    
    /*!
    通过将item1和item2固定到锚点point上,得到一个attachment behavior对象
    item1和item2就像通过木棍固定到锚点point上,但是item1和item2可以围绕锚点以固定半径旋转,并且item1和item2之间不发生碰撞,item1和item2的旋转同时受frictionTorque旋转力矩属性和锚点运动影响
    frictionTorque值改变必须在任何一个item旋转之前进行设置。当frictionTorque值为0时,item1和item2响应任何自由旋转脉冲
    利用attachmentRange属性设置旋转的数量
     */
    +(instancetype)pinAttachmentWithItem:(id <UIDynamicItem>)item1 attachedToItem:(id <UIDynamicItem>)item2 attachmentAnchor:(CGPoint)point NS_AVAILABLE_IOS(9_0);
    

    版权声明:出自MajorLMJ技术博客的原创作品 ,转载时必须注明出处及相应链接!

    相关文章

      网友评论

      • 小呆鸟:你好,你这种显示功能的动图是怎么弄的啊?
        JerryLMJ:@小呆鸟 LICEcap
        小呆鸟:@MajorLMJ 用的是什么软件呢?
        JerryLMJ:@小呆鸟 录的gif图片

      本文标题:iOS UIKit动力学(四)吸附(UIAttachmentBe

      本文链接:https://www.haomeiwen.com/subject/odzvuttx.html