Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
364 views
in Technique[技术] by (71.8m points)

xib第一次加载尺寸不正确

问题描述

使用Xib构建了视图A。根据设计需求,B是A的子视图。

这边想在A的layoutSubview方法中,根据业务数据模型动态创建B视图(通过加载B的xib文件),同时获取A的实际尺寸来给B的frame赋值

问题就在于:

在interface builder里看A视图的尺寸是 100 x 100
App运行后第一次加载,在A的layoutSubview里获取的尺寸(self.bounds.width)也确实是 100 x 100
但真正显示到屏幕上后,A的尺寸根据机器的实际屏幕尺寸做了resize,变成了 95 x 95例如,这就导致了后续B视图的布局异常

然而后续再次在A的layoutSubview里获取的尺寸就恒定是 95 x 95了,也就是第一次获取到的尺寸和实际显示尺寸不相等,导致视图第一次显示出来总是布局异常(但后续没有问题)

问题出现的环境背景及自己尝试过哪些方法

视图A是用xib构建的,其中子视图B的宽高使用了AspectRatio,宽度等于实际屏幕-56,也就是说B的宽高是根据实际设备屏幕的尺寸来决定的。

相关代码

`
override func layoutSubviews() {

super.layoutSubviews()

refreshUI()

}

func refreshUI() {

if toolData == nil {

return

}

//先清除之前的

for subView in subItemContainerView.subviews {

subView.removeFromSuperview()

}

itemViewArr.removeAll()

plusViewArr.removeAll()
///就是下面这个h,第一次加载是xib文件中的100,后续就恒定变成某个值例如95,应该是autolayout计算过后的值。这边期望第一次就能获取到resize后的值,保证布局正确。

let h:CGFloat = subItemContainerView.frame.height

let w:CGFloat = h * (ST_375_NEED_ITEM_WIDTH / ST_375_NEED_ITEM_HEIGHT)

let midX:CGFloat = subItemContainerView.bounds.midX

let midY:CGFloat = subItemContainerView.bounds.midY

for subItem in toolData!.needStuffArr {

let itemV = ZSNeedItemView.loadFromXib() as! ZSNeedItemView

// let itemV = UIView()

// itemV.backgroundColor = .red

itemV.imageView?.image = UIImage(named: subItem.imgName)

itemV.titleLabel?.attributedText = ZSNeedItemView.desc(ofNeedItemAndCount: subItem)

subItemContainerView.addSubview(itemV)

itemV.sizeToFit()

itemV.frame = CGRect(x: 0, y: 0, width: w, height: h)

itemV.center = CGPoint(x: midX, y: midY)

itemViewArr.append(itemV)

if subItem != toolData?.needStuffArr.last {

//需要加 + 图片

let plusImgView = UIImageView(image: UIImage(named: "item_plus"))

plusImgView.frame = CGRect(x: 0, y: 0, width: PLUS_IMG_WIDTH, height: PLUS_IMG_HEIGHT)

plusImgView.center = CGPoint(x: midX, y: midY)

subItemContainerView.addSubview(plusImgView);

plusViewArr.append(plusImgView)

}

}

}

`

你期待的结果是什么?实际看到的错误信息又是什么?

这边期望第一次就能获取到xib文件 resize后的真实尺寸值,保证布局正确。

实际看到的错误是,第一次展示A视图,布局总是轻微异常,后续再次加载布局正常(猜是已经resize过了)

补充: 目前这边暂时想到的workaround方法就是,app加载的时候,先把A视图加载到window一次,设置成alpha = 0, 然后再快速remove掉,这样就回避掉了第一次加载布局异常。But,这个方法非常的nasty,求elegant一点的方法。


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)
等待大神解答

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

2.1m questions

2.1m answers

60 comments

56.8k users

...