UISegmentedControlのボタンの色を任意に変える
下記の例では「Month」と「All」、「Timeline」と「Tag」をそれぞれ排他的に選択させたいが、UISegmentedControlでは複数のグループには分割できない。それぞれのボタンに色をつけることでそれを擬似的に表現したい。

初期状態では「Month」「Timeline」がそれぞれ選択されている。

「All」をタッチすると、「Month」の色が消えて、「All」に色がつく。「Timeline」と「Tag」に変化はない。

さらに「Tag」をタッチすると、同様にボタンの色が変化する。
以下、コード。
- (void)viewWillAppear:(BOOL)animated {
navigationSegment = [[UISegmentedControl alloc] initWithItems:nil];
navigationSegment.segmentedControlStyle = UISegmentedControlStyleBar;
navigationSegment.momentary = YES;
//initialize UISegmentedControl
//UISegmentedControlの初期化
[navigationSegment insertSegmentWithTitle:NSLocalizedString(@"month", @"Month") atIndex:0 animated:NO];
[navigationSegment insertSegmentWithTitle:NSLocalizedString(@"all", @"All") atIndex:1 animated:NO];
[navigationSegment insertSegmentWithTitle:NSLocalizedString(@"sorttime",@"Timeline") atIndex:2 animated:NO];
[navigationSegment insertSegmentWithTitle:NSLocalizedString(@"sorttag",@"Tag") atIndex:3 animated:NO];
[navigationSegment insertSegmentWithImage:[UIImage imageNamed: @"mail2.png"] atIndex:4 animated:NO];
//call controlPressed when UISegmentedControl is pushed
//UISegmentedControlが押されたら、controlPressedメソッドを呼ぶ
[navigationSegment addTarget:self action:@selector(controlPressed:) forControlEvents:UIControlEventValueChanged];
//Initial value: Month and Timeline is ON.
//初期値はMonthがON,TimelineがON
tagOrTime = TIMELINE_FLAG_ON;
allOrMonth = MONTH_FLAG_ON;
//When view is displayed, objectAtIndex(es) are 0, 1, 2, 3, and 4 from the left.
//viewが表示されたときは、objectAtIndexは左から0,1,2,3,4。
[[[navigationSegment subviews] objectAtIndex:0] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
[[[navigationSegment subviews] objectAtIndex:1] setTintColor:nil];
[[[navigationSegment subviews] objectAtIndex:2] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
[[[navigationSegment subviews] objectAtIndex:3] setTintColor:nil];
}
- (void)controlPressed:(id)sender{
int index = navigationSegment.selectedSegmentIndex;
if(index == 2){
tagOrTime = TIMELINE_FLAG_ON;
}else if(index == 3){
tagOrTime = TAG_FLAG_ON;
}else if(index == 0){
allOrMonth = MONTH_FLAG_ON;
}else if(index == 1){
allOrMonth = ALL_FLAG_ON;
}else if(index == 4){
....
}
//Since the turn of Subview of UISegmentedControl changes irregularly, it rearranges from the left.
//UISegmentedControlのSubviewの順番がなぜかコロコロ変わってしまうので、左から並び替える。
NSArray *sortedViews = [navigationSegment.subviews sortedArrayUsingFunction:compareViewsByOrigin context:NULL];
//A flag is changed according to the button pushed now.
//現在押されているボタンに従って、フラグを変更する。
if (tagOrTime == TAG_FLAG_ON) {
[[sortedViews objectAtIndex:2] setTintColor:nil];
[[sortedViews objectAtIndex:3] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
} else {
[[sortedViews objectAtIndex:3] setTintColor:nil];
[[sortedViews objectAtIndex:2] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
}
if (allOrMonth == ALL_FLAG_ON) {
[[sortedViews objectAtIndex:0] setTintColor:nil];
[[sortedViews objectAtIndex:1] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
} else {
[[sortedViews objectAtIndex:1] setTintColor:nil];
[[sortedViews objectAtIndex:0] setTintColor:[UIColor colorWithRed: 0/255.0 green:32/255.0 blue:128/255.0 alpha:0.2]];
}
// Remove all original segments from the control
// 一旦Subviewをすべて削除
for (id view in navigationSegment.subviews) {
[view removeFromSuperview];
}
// Append sorted and colored segments to the control
// 色を変えたsubviewを付け替える
for (id view in sortedViews) {
[navigationSegment addSubview:view];
}
}
//subviews sort function
//ソート関数
NSInteger static compareViewsByOrigin(id sp1, id sp2, void *context)
{
// UISegmentedControl segments use UISegment objects (private API). But we can safely cast them to UIView objects.
float v1 = ((UIView *)sp1).frame.origin.x;
float v2 = ((UIView *)sp2).frame.origin.x;
if (v1 < v2)
return NSOrderedAscending;
else if (v1 > v2)
return NSOrderedDescending;
else
return NSOrderedSame;
}
Thank you, https://goddess-gate.com/dc2/index.php/post/454