如何创建定义基线的自定义UIView?

时间:2013-05-06 20:48:42

标签: uiview autolayout

使用NSLayoutConstraint类,可以创建基于视图基线(NSLayoutAttributeBaseline)的约束。但是,我没有看到任何描述UIView如何实际为自动布局系统提供基线值的文档。

如果我想创建一个定义基线的自定义UIView子类,我该怎么做? NSView定义了一个baselineOffsetFromBottom方法,我假设它在某种程度上涉及到OS X,但这在iOS中是如何工作的?

4 个答案:

答案 0 :(得分:10)

来自UIView文档:

  

viewForBaselineLayout

     

返回用于满足基线约束的视图。

     

- (UIView *)viewForBaselineLayout

     

返回值

     

约束系统应该使用的视图来满足基线约束

答案 1 :(得分:8)

我刚刚使用Hopper反汇编程序查看iOS 8.1中的UILabel,它实现了方法_baselineOffsetFromBottom_firstBaselineOffsetFromTop,这些方法又被-[UIView nsli_lowerAttribute:intoExpression:withCoefficient:forConstraint:]调用,因此UIKit具有私有性类似于OS X的方法,它们只是不向公众公开。

_baselineOffsetFromBottom_firstBaselineOffsetFromTop由UIView(返回0),UILabel和UITextView实现。还有一个名为_UIGlintyStringView的类,它实现了_baselineOffsetFromBottom;没有其他UIKit类有这些方法。

当视图的基线发生变化时,它会执行以下操作:

__UITagLayoutConstraintsForConstantChangeForSelectedAttributes(self, __UILayoutAttributeIsBaselineAttribute)

似乎没有什么特别的东西不能暴露给公众;或许他们不觉得有需要或想要阻止人们写自己的标签。 UILabel是一个相当复杂的类,涉及自定义CoreAnimation层(_UILabelLayer)和大量技巧,包括相当多的可访问性支持代码。

答案 2 :(得分:3)

如果不方便与视图对齐,则也可以覆盖基线值之一,即firstBaselineOffsetFromTop。例如,下面的代码将第一个基线设置为视图的一半:

override var firstBaselineOffsetFromTop: CGFloat {
    return bounds.midY
}

编辑:不好,那是MacOS。我认为iOS等效项是firstBaselineAnchor,它返回一个NSLayoutYAxisAnchor对象。我尚未对此进行测试,但是我希望这会产生类似的效果:

override var firstBaselineAnchor: NSLayoutYAxisAnchor {
    return NSLayoutYAxisAnchor.anchorWithOffset(bounds.midY)
}

答案 3 :(得分:1)

     for i in range(5):
         exec("list_%d = []" % (i+1))

已弃用,因此您必须使用

viewForBaselineLayout 

示例

viewForFirstBaselineLayout