iOS11 UIToolBar Contentview iOS11 UIToolBar Contentview ios ios

iOS11 UIToolBar Contentview


To solve the problem for iOS11 (compatible with lower versions) you only needto make layoutSubview right after UIToolBar was added as a subview to UI hierarchy.

In this case _UIToolbarContentView lowers to the first subview of UIToolBar, and you canadd all your subviews higher as before.

For example in ObjC,

    UIToolbar *toolbar = [UIToolbar new];    [self addSubview: toolbar];    [toolbar layoutIfNeeded];    <here one can add all subviews needed>

The same problem happens with slacktextviewcontroller


I have solved this problem in my case. I rewrite the layoutSubviews method in subclass of UIToobar and change the userInteractionEnable of _UIToolbarContentView into NO.

- (void)layoutSubviews {    [super layoutSubviews];    NSArray *subViewArray = [self subviews];    for (id view in subViewArray) {        if ([view isKindOfClass:(NSClassFromString(@"_UIToolbarContentView"))]) {            UIView *testView = view;            testView.userInteractionEnabled = NO;         }     }}


You can just use the hitTest(_:with:) method.

  1. First, create a property contentView in UIToolbar:

    open private(set) var contentView: UIView = UIView()
  2. Then, make the contentView's frame the same as the UIToolbar's. For example:

    contentView.frame = boundscontentView.autoresizingMask = [.flexibleWidth, .flexibleHeight]addSubview(contentView)
  3. Finally, override the hitTest(_:with:) method:

    open override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {    if self.point(inside: point, with: event) {        if let hitTestView = contentView.hitTest(point, with: event) {            return hitTestView        } else {            return self        }    } else {        return nil    }}

In this situation, if you want to customize a toolbar by simply adding additional views, you should add them to the contentView so they will be positioned appropriately.