使用auto layout自定义flipBar

原创 2016年05月30日 10:46:17

最近有在看一本关于auto layout的书,受益匪浅,然后突然想到我要解决的一个问题其实正好可以用到这个auto layout的技巧,现在进行一个讲解


我们之前看新闻、视频等的软件,常看到过这样的功能(如图蓝椭圆内)

      

      


我最早做这个功能的时候,是通过计算frame相应的值进行布局。其实这样很low,尤其如果button所对应的内容不一定时,计算就简直了,后来看了auto layout,觉得可以试一试使用它。

在这里主要涉及到俩个知识点,1.几何约束。2.内容约束


先晒代码,在做解释


#define buttonTag 1000


@interface ViewController ()

@property(nonatomic,strong)UIScrollView *scrollView;

@property(nonatomic,strong)NSArray *buttonContents;


@end


@implementation ViewController


- (void)viewDidLoad {

    [super viewDidLoad];

    

    self.buttonContents = @[@"button1",@"longButton2",@"longlongButton3",@"btn",@"b",@"这是一个超长button",@"这个button更长更长更更长"];

    self.scrollView = [[UIScrollView alloc] initWithFrame:CGRectZero];

    self.scrollView.translatesAutoresizingMaskIntoConstraints = NO;

    [self.view addSubview:self.scrollView];



    UIButton *btn;

    for (int i = 0; i < self.buttonContents.count; i++) {

        btn = [UIButton buttonWithType:UIButtonTypeRoundedRect];

        btn.translatesAutoresizingMaskIntoConstraints = NO;

        [btn setTitle:self.buttonContents[i] forState:UIControlStateNormal];

        btn.tag = buttonTag+i;

        [btn addTarget:self action:@selector(clickBtn:) forControlEvents:UIControlEventTouchUpInside];

        [self.scrollView addSubview:btn];


        [self.scrollView addConstraint:[NSLayoutConstraint constraintWithItem:btn attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1.0 constant:btn.intrinsicContentSize.width+10.0]];

        if (i == 0) {

            [self.scrollView addConstraint:[NSLayoutConstraint constraintWithItem:btn attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self.scrollView attribute:NSLayoutAttributeTop multiplier:1.0 constant:0]];

            [self.scrollView addConstraint:[NSLayoutConstraint constraintWithItem:btn attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self.scrollView attribute:NSLayoutAttributeLeft multiplier:1.0 constant:10]];

            

        }else{

            UIButton *preBtn = [self.scrollView viewWithTag:999+i];

            [self.scrollView addConstraint:[NSLayoutConstraint constraintWithItem:btn attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:preBtn attribute:NSLayoutAttributeTop multiplier:1.0 constant:0]];

            [self.scrollView addConstraint:[NSLayoutConstraint constraintWithItem:btn attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:preBtn attribute:NSLayoutAttributeRight multiplier:1.0 constant:0]];

        }

        [btn layoutIfNeeded];

    }

    

    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.scrollView attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0]];

    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.scrollView attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeWidth multiplier:1.0 constant:0]];

    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.scrollView attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeTop multiplier:1.0 constant:100]];

    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.scrollView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:btn attribute:NSLayoutAttributeHeight multiplier:1.0 constant:0]];

    self.scrollView.contentSize = CGSizeMake(btn.frame.origin.x+btn.frame.size.width, btn.frame.size.height);

    

    

}



- (void)clickBtn:(id)sender{

    UIButton *btn = (UIButton *)sender;

    

    NSString *buttonContent = self.buttonContents[btn.tag - buttonTag];

    NSLog(@"button title is %@",buttonContent);

}




最终结果如上图,图中区域可以左右滑动显示更多内容


flipBar只需要俩个控件,1.UIScrollView. 2.UIButton

如果有需要,你完全可以自定义一个UIButton


1.首先需要初始化scrollView,注意不需要指定frame的具体值


2.其次涉及到translatesAutoresizingMaskIntoConstraints属性,它的默认值是YES.其中开发文档中是这样描述它

If this property’s value is YES, the system creates a set of constraints that duplicate the behavior specified by the view’s autoresizing mask. This also lets you modify the view’s size and location using the view’s framebounds, or center properties, allowing you to create a static, frame-based layout within Auto Layout.

Note that the autoresizing mask constraints fully specify the view’s size and position; therefore, you cannot add additional constraints to modify this size or position without introducing conflicts. If you want to use Auto Layout to dynamically calculate the size and position of your view, you must set this property to NO, and then provide a non ambiguous, nonconflicting set of constraints for the view.

By default, the property is set to YES for any view you programmatically create. If you add views in Interface Builder, the system automatically sets this property to NO.


如果属性值是YES,重复被viewautoresizing mask指定的行为。也就是让你通过frameboundcenter等属性来修改视图的sizelocation,允许您用auto layout创建静态,框架布局。

注意autoresizing mask约束完全指定视图的sizeposition;因此,你在不引入冲突的情况下不能添加额外约束来修改size或者position(言外之意,属性设置YES,只要修改size或者position就会带来冲突)。如果你想要使用Auto Layout来动态的计算你视图的sizeposition,你必须设置此属性为NO,并且提供一系列不模棱两可的,无冲突的的视图约束。

编程方式创建视图,属性默认值是YES。如果在IB中添加views,系统自动设置属性为NO.


所以如果是动态计算sizeposition,就需要设置属性值是NO,之后的button也会将此属性设置为NO


3.一定要先addSubView:,才能设置一系列的约束,否则一定会报错


4.通过for的方式添加button,添加的button也不需要设置frame,因为在设置translatesAutoresizingMaskIntoConstraintsNO时,button会自动根据内容设置其它的大小

但在内容约束的基础上,我们往往希望内别逗挤在一起,所以在此处设置了内容约束基础上扩宽10PX,你可以按照自己喜好设置


5.然后,其实第一个button是有点不太一样的,它的几何约束是以scrollView为基础的,而剩下的button都是以前面的button为基础,具体你可以参照代码


6.layoutIfNeeded的应用,其中,使用这个属性的话,就自动布局,最明显的反应就是frame值不是0了,在下面也有很好的使用


7.接下来auto layout 约束scrollview,然后设置它的contentSize,其中主要利用了最后一个button的frame值


flipBar大概就是这样


对代码做了一些改进后的demo地址:https://github.com/xiujiePei/PXJSlidButtonBar


版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

Auto Layout 使用心得(三)—— 自定义 cell 并使用 Auto Layout

此系列文章代码仓库在 https://github.com/johnlui/AutoLayout ,有不明白的地方可以参考我的 Auto Layout 设置哦,下载到本地打开就可以了。 简介...

android自定义粘性控件,综合使用measure,layout,onTouchEvent,onInterceptTouchEvent等方法

android自定义粘性控件,综合使用measure,layout,onTouchEvent,onInterceptTouchEvent等方法

安卓-使用layout_weight属性自定义标题栏布局

今天使用android:layout_weight这个属性来实现一个标题栏的布局。线上效果图: 布局文件如下: <LinearLayout xmlns:android="http://s...

android 使用自定义layout作为导航栏

一个人瞎摸索android,一直依靠百度,被百度的结果坑了无数次,但拯救了更多次。 希望做一个导航栏,像IOS那样,百度了一下,android 导航栏,看了一些简单的实现,使用layout来做,的确很...

自定义layout

  • 2016-12-25 15:47
  • 3.24MB
  • 下载

iOS 8 Auto Layout界面自动布局系列2-使用Xcode的Interface Builder添加布局约束

上一篇文章《iOS 8界面自动布局系列-1》简要介绍了iOS界面布局方式的前世今生。本篇文章将详细介绍如何使用自动布局实现不同屏幕尺寸的适配。添加自动布局约束(下文简称约束)有以下三种方式:使用Xco...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)