2.8 分段控制器——UISegmentedControl

UISegmentedControl用于管理和实现一组内容的切换逻辑,如几个并列关系的界面之间的相互切换。UISegmentedControl常见于导航栏的标题视图中,因其小巧的外表和简洁的接口风格,在原生和第三方应用中都十分常见。

2.8.1 UISegmentedControl基本属性的应用

首先,使用Xcode开发工具创建一个名为UISegmentedControlTest的工程,在ViewController.m的viewDidLoad方法中添加如下代码。

Swift语言版本:

            override func viewDidLoad() {
                super.viewDidLoad()
                let seg = UISegmentedControl(items: ["one", "", "three", "four"])
                seg.frame = CGRect(x: 20, y: 100, width: 280, height: 30)
                seg.setImage(UIImage(named: "image")? .withRenderingMode(.alwaysOriginal), forSegmentAt: 1)
                seg.setContentOffset(CGSize(width: 10, height: 10), forSegmentAt: 1)
                seg.isMomentary = true
                self.view.addSubview(seg)
            }

Objective-C语言版本:

        - (void)viewDidLoad {
            [super viewDidLoad];
            UISegmentedControl * seg = [[UISegmentedControl alloc]initWithItems: @[@"one", @"", @"three",@"four"]];
            seg.frame = CGRectMake(20, 100, 280, 30);
            [seg setImage:[[UIImage imageNamed:@"image"] imageWithRenderingMode:
    UIImageRenderingModeAlwaysOriginal] forSegmentAtIndex:1];
            [seg setContentOffset:CGSizeMake(10, 10) forSegmentAtIndex:0];
            seg.momentary=NO;
            [self.view addSubview:seg];
        }

代码中使用带item数组参数的构造方法初始化UISegmentedControl对象,这个方法中需要传入一个标题数组,数组中字符串的个数和内容决定了UISegmentedControl控件中按钮的个数和标题。setImage方法用于设置某个按钮的图案,其中按钮的编号Index从0开始计。setContentOffset方法设置其中某个按钮内容的位置偏移。UISegmentedControl的isMomentary属性默认为布尔值假,控件为切换按钮模式,如果设置为布尔值真,控件就为触发按钮模式。运行工程,效果如图2-28所示。

图2-28 UISegmentedControl

提示 UISegmenedControl在切换按钮模式时,当用户点击一个按钮后,此按钮会一直保持选中状态,直到用户切换为另一个为止,而在触发按钮模式中,用户手指离开屏幕后,按钮将不保持选中状态。

2.8.2 对UISegmentedControl中的按钮进行增、删、改操作

UIsegmentedControl对象中的按钮除了在初始化时可以进行创建外,在程序运行过程中也可以进行动态的添加、删除和修改操作,UISegmentedControl中有如下方法可供开发者使用。

Swift语言版本:

        seg.insertSegment(withTitle: "new", at: 2, animated: true)
        seg.removeSegment(at: 1, animated: true)
        seg.setTitle("replace", forSegmentAt: 1)
        seg.removeAllSegments()

Objective-C语言版本:

        [seg insertSegmentWithTitle:@"new" atIndex:2 animated:YES];
        [seg removeSegmentAtIndex:1 animated:YES];
        [seg setTitle:@"replace" forSegmentAtIndex:1];
        [seg removeAllSegments];

insertSegment方法用于在UISegmentedControl当前按钮组中插入一个新的标题按钮,第1个参数是设置按钮的标题文字,第2个参数是设置插入的位置,第3个参数是设置是否带动画效果,与这个方法对应的还有一个插入方法用于插入一个图片按钮;removeSegment方法可以在已有的按钮中移除一个;setTitle方法可以重新设置一个按钮的标题,与之对应的setImage方法可以重新设置一个按钮的图片;removeAllSegments方法将移除所有的按钮。

2.8.3 UISegmentedControl中按钮宽度的自适应

UISegmentedControl控件中的按钮宽度默认是平均分的,如果某个按钮的标题长度超出了宽度的范围,就会被自动截断,如图2-29所示。

图2-29 UISegmentedControl按钮标题文字被截断

开发者可以手动对UISegmentedControl中的每个按钮的宽度进行设置,以便设置按钮宽度与其文字相适应,示例代码如下,效果如图2-30所示。

图2-30 自定义UISegmentedContrl按钮宽度

Swift语言版本:

    seg.setWidth(130, forSegmentAt: 3)

Objective-C语言版本:

    [seg setWidth:130 forSegmentAtIndex:3];

上面的方法可以对UISegmentedControl中按钮宽度进行设置,但是有一个致命的缺点,开发者可能并不知道这个按钮上面标题文字所占的宽度,如果使用强制计算的方法,就会徒增许多代码量。幸运的是,UISegmentedControl中还提供了一个属性,可以让UISegmentedControl自己计算其中按钮需要的宽度,让其进行宽度的自适应,代码如下。

Swift语言版本:

    seg.apportionsSegmentWidthsByContent = true

Objective-C语言版本:

    seg.apportionsSegmentWidthsByContent=YES;

将apportionsSegmentWidthsByContent属性设置为布尔值真,UISegmentedControl控件中的按钮宽度将进行自适应。

提示 UISegmentedControl添加触发方法也是通过addTarget方法设置的,需要监听的触发动作和UIPageControl控件一致,为valueChanged。