[iphone] iOS 11 iPhone X 시뮬레이터 UITabBar 아이콘과 제목이 서로를 덮고 위에 렌더링됩니다.

UITabBar 구성 요소와 관련하여 iPhone X 시뮬레이터에 문제가 있습니까?

내 아이콘과 제목을 서로 렌더링하는 것처럼 보입니다. 내가 빠진 것이 확실하지 않은 경우 iPhone 8 시뮬레이터에서 실행 한 것과 실제 장치가 그림과 같이 잘 보입니다. 스토리 보드.

아이폰 X :

iPhone X UITabBar 버그

아이폰 8

아이폰 8 UITabBar 작동



답변

viewDidLayoutSubviews의 UITabBar에서 invalidateIntrinsicContentSize를 호출하여 문제를 해결할 수있었습니다.

-(void)viewDidLayoutSubviews
{
    [super viewDidLayoutSubviews];
    [self.tabBar invalidateIntrinsicContentSize];
}

참고 : 탭 막대의 아래쪽은 안전 영역이 아니라 기본보기의 아래쪽에 포함되어야하며 탭 막대에는 높이 제한이 없어야합니다.


답변

VoidLess가 제공 한 답변은 TabBar 문제를 부분적으로 만 해결합니다. 탭 막대 내에서 레이아웃 문제를 해결하지만 탭 막대를 숨기는 뷰 컨트롤러를 사용하는 경우 애니메이션 중에 탭 막대가 잘못 렌더링됩니다 (재생하는 것이 가장 좋습니다. 제자리에서 렌더링되는 탭바 참조). 다음 코드는 두 가지 문제를 모두 해결합니다. 잘 했어.

class SafeAreaFixTabBar: UITabBar {

var oldSafeAreaInsets = UIEdgeInsets.zero

@available(iOS 11.0, *)
override func safeAreaInsetsDidChange() {
    super.safeAreaInsetsDidChange()

    if oldSafeAreaInsets != safeAreaInsets {
        oldSafeAreaInsets = safeAreaInsets

        invalidateIntrinsicContentSize()
        superview?.setNeedsLayout()
        superview?.layoutSubviews()
    }
}

override func sizeThatFits(_ size: CGSize) -> CGSize {
    var size = super.sizeThatFits(size)
    if #available(iOS 11.0, *) {
        let bottomInset = safeAreaInsets.bottom
        if bottomInset > 0 && size.height < 50 && (size.height + bottomInset < 90) {
            size.height += bottomInset
        }
    }
    return size
}

override var frame: CGRect {
    get {
        return super.frame
    }
    set {
        var tmp = newValue
        if let superview = superview, tmp.maxY !=
        superview.frame.height {
            tmp.origin.y = superview.frame.height - tmp.height
        }

        super.frame = tmp
        }
    }
}

오브젝티브 -C 코드 :

@implementation VSTabBarFix {
    UIEdgeInsets oldSafeAreaInsets;
}


- (void)awakeFromNib {
    [super awakeFromNib];

    oldSafeAreaInsets = UIEdgeInsetsZero;
}


- (void)safeAreaInsetsDidChange {
    [super safeAreaInsetsDidChange];

    if (!UIEdgeInsetsEqualToEdgeInsets(oldSafeAreaInsets, self.safeAreaInsets)) {
        [self invalidateIntrinsicContentSize];

        if (self.superview) {
            [self.superview setNeedsLayout];
            [self.superview layoutSubviews];
        }
    }
}

- (CGSize)sizeThatFits:(CGSize)size {
    size = [super sizeThatFits:size];

    if (@available(iOS 11.0, *)) {
        float bottomInset = self.safeAreaInsets.bottom;
        if (bottomInset > 0 && size.height < 50 && (size.height + bottomInset < 90)) {
            size.height += bottomInset;
        }
    }

    return size;
}


- (void)setFrame:(CGRect)frame {
    if (self.superview) {
        if (frame.origin.y + frame.size.height != self.superview.frame.size.height) {
            frame.origin.y = self.superview.frame.size.height - frame.size.height;
        }
    }
    [super setFrame:frame];
}


@end


답변

문제를 해결할 수있는 방법이 있습니다.

UITabBar를 UIView 안에 넣으십시오.

이것은 실제로 나를 위해 일하고 있습니다.

또는 자세한 내용 은이 링크 를 참조하십시오.


답변

우선 UITabBar sizeThatFits(_)safeArea에 대한

extension UITabBar {
    static let height: CGFloat = 49.0

    override open func sizeThatFits(_ size: CGSize) -> CGSize {
        guard let window = UIApplication.shared.keyWindow else {
            return super.sizeThatFits(size)
        }
        var sizeThatFits = super.sizeThatFits(size)
        if #available(iOS 11.0, *) {
            sizeThatFits.height = UITabBar.height + window.safeAreaInsets.bottom
        } else {
            sizeThatFits.height = UITabBar.height
        }
        return sizeThatFits
    }
}


답변

나는 이것을 추가했다. viewWillAppearUITabBarController제공된 답변 중 어느 것도 나를 위해 일하지 않았기 때문에 내 custom에 했습니다.

tabBar.invalidateIntrinsicContentSize()
tabBar.superview?.setNeedsLayout()
tabBar.superview?.layoutSubviews()


답변

나는 같은 문제가 있었다.

여기에 이미지 설명을 입력하십시오

UITabBar의 하단 제약 조건에서 0이 아닌 상수를 안전 영역으로 설정하면 :

여기에 이미지 설명을 입력하십시오

예상대로 작동하기 시작합니다 …

여기에 이미지 설명을 입력하십시오

그것이 내가 한 유일한 변화이며 그것이 왜 효과가 있는지 전혀 알지 못하지만 누군가가 알고 싶다면 알고 싶습니다.


답변

탭 막대를 아래쪽에서 1 포인트 이동하면 나에게 도움이되었습니다.

물론 어떤 식 으로든 채워야하지만 텍스트 / 아이콘이 올바르게 배치되어 간격이 생깁니다.