Eureka: SegmentedRow stretches its UISegmentedControl rather than sizeToFit()

Created on 23 Mar 2017  路  6Comments  路  Source: xmartlabs/Eureka

iOS: 10.0+
Xcode: 8.2.1
Eureka: 2.0.1

I am currently having trouble getting the SegmentedRow to hug its values, rather than spread itself across the row:
Screenshot

The values of these SegmentedRow's are always ["true", "false"], which is a pretty short string, so I'd like them to .sizeToFit().

At first I thought there was a constraint of a fixed spacing between the trailing edge of the UILabel and the leading edge of the UISegmentedControl, but I could only find a constraint about its minimum width:

dynamicConstraints.append(NSLayoutConstraint(item: segmentedControl, attribute: .width, relatedBy: .greaterThanOrEqual, toItem: contentView, attribute: .width, multiplier: 0.3, constant: 0.0))

For now, the only possible solution I could find was #480. But it involves giving it a fixed width, which isn't a great auto-layout solution for obvious reasons.

Any ideas on how to resolve this?

awaiting response

Most helpful comment

Hey @Laptopmini, actually the segmentedControl is constrained to get as much width as it can, see here.

One thing i can think of is changing it's horizontal contentHuggingPriority to something high that in your case would result in it's width to match it's intrinsic content size and the titleLabel taking the space that is left.

<<< SegmentedRow<String>("persist_row"){
    $0.title = "Persist"
    $0.options = ["true", "false"]
}.cellSetup { cell, row in
    cell.segmentedControl.setContentHuggingPriority(UILayoutPriorityDefaultHigh, for: .horizontal)
}

image

All 6 comments

Hey @Laptopmini, actually the segmentedControl is constrained to get as much width as it can, see here.

One thing i can think of is changing it's horizontal contentHuggingPriority to something high that in your case would result in it's width to match it's intrinsic content size and the titleLabel taking the space that is left.

<<< SegmentedRow<String>("persist_row"){
    $0.title = "Persist"
    $0.options = ["true", "false"]
}.cellSetup { cell, row in
    cell.segmentedControl.setContentHuggingPriority(UILayoutPriorityDefaultHigh, for: .horizontal)
}

image

Looks like the problem can be solved with last comment.

Closing this due to lack of response

Thanks for the answer. Works like a charm.

<<< SegmentedRow<String>("persist_row"){
    $0.title = "Persist"
    $0.options = ["true", "false"]
}.cellSetup { cell, _ in
    cell.segmentedControl.setContentHuggingPriority(.defaultHigh, for: .horizontal)
}

updated for Swift 4.1

FYI, I finding also adding this does an even better job of shrinking each segment to a minimum, if you really want to minimize the overall width of the SegmentedControl:

cell.segmentedControl.setContentHuggingPriority(.defaultHigh, for: .horizontal)
cell.segmentedControl.apportionsSegmentWidthsByContent = true

Also FYI, you can use the following for a fixed width:

<<< SegmentedRow<String>("persist_row"){
    $0.title = "Persist"
    $0.options = ["true", "false"]
}.cellSetup { cell, _ in
    cell.segmentedControl.widthAnchor.constraint(equalToConstant: 200).isActive = true
}
Was this page helpful?
0 / 5 - 0 ratings