layoutSubviews何時調用的問題


今天跟旺才兄學習了一下UIView的setNeedsDisplay和setNeedsLayout方法。首先兩個方法都是異步執行的。而setNeedsDisplay會調用自動調用drawRect方法,這樣可以拿到UIGraphicsGetCurrentContext,就可以畫畫了。而setNeedsLayout會默認調用layoutSubViews,就可以處理子視圖中的一些數據。
宗上所訴,setNeedsDisplay方便繪圖,而layoutSubViews方便出來數據。
\

ipad橫豎屏切換解決方案
2011年08月01日 星期一 10:09
由於ipad的橫豎屏不同,所以好的應用,橫豎屏的頁面布局也不一樣。那么就需要橫豎屏的整體解決方案。先看一個橫豎屏布局不一樣的界面。

上面兩張圖是來自同一個界面的橫豎版的截屏。可以看出,橫豎版顯示的內容相同,但是界面布局不同。要實現上述布局,主要是運用UIView中 layoutSubviews方法。當UIView設置為自動適配屏幕時,當用戶旋轉設備的時候,會調用layoutSubviews方法,我們只需重寫 這個方法,然后判斷用戶屏幕的方向。在調整每個空間的位置即可。

下面是實現上述界面的最簡單的原型:

首先分析可以知道左面是圖片,右面是一個圖片加文字的視圖。下面就實現一個左面視圖右面是一個圖加一段字的事例。
事例的截圖如下:

其中右面的文字和綠色部分是用一個子視圖封裝的。
整個布局是我在主視圖中添加了一個ContentView視圖,在ContentView視圖中添加了一個ArticleView視圖。
其中ArticleView和ContentView的xib文件都打開了


在ContentView中重寫layoutSubviews方法,然后根據stausbar的方向判斷當前視圖的橫豎屏。具體代碼:
-(void)layoutSubviews{
[super layoutSubviews];
UIDeviceOrientation interfaceOrientation=[[UIApplication sharedApplication] statusBarOrientation];
if (interfaceOrientation == UIDeviceOrientationPortrait || interfaceOrientation == UIDeviceOrientationPortraitUpsideDown) {
//翻轉為豎屏時
[self setVerticalFrame];
}else if (interfaceOrientation==UIDeviceOrientationLandscapeLeft || interfaceOrientation == UIDeviceOrientationLandscapeRight) {
//翻轉為橫屏時
[self setHorizontalFrame];
}
}

-(void)setVerticalFrame
{
NSLog(@"豎屏");
[titleLable setFrame:CGRectMake(283, 0, 239, 83)];
[leftView setFrame:CGRectMake(38, 102, 384, 272)];
[rightView setFrame:CGRectMake(450, 102, 282, 198)];
}

-(void)setHorizontalFrame
{
NSLog(@"橫屏");
[titleLable setFrame:CGRectMake(183, 0, 239, 83)];
[leftView setFrame:CGRectMake(168, 122, 384, 272)];
[rightView setFrame:CGRectMake(650, 122, 282, 198)];
}

在具體的橫豎屏方法中,從新設置各個組件的坐標即可。

接下來在ContentView中添加ArticleView視圖。
-(id)initWithCoder:(NSCoder *)aDecoder
{
if ((self = [super initWithCoder:aDecoder])) {

NSArray *arrayContentView =[[NSBundle mainBundle] loadNibNamed:@"ArticleView" owner:self options:nil];
rightView=[arrayContentView objectAtIndex:0];
[self addSubview:rightView];
}
return self;
}

由於我用的是xib,所以初始化方法為initWithCoder,在這個中添加新的視圖。

同樣在ArticleView中設置橫豎屏相應空間的坐標即可。
-(void)layoutSubviews{
[super layoutSubviews];
UIDeviceOrientation interfaceOrientation=[[UIApplication sharedApplication] statusBarOrientation];
CGRect rect=self.frame;
rect.size.width=282;
rect.size.height=198;
[self setFrame:rect];
if (interfaceOrientation == UIDeviceOrientationPortrait || interfaceOrientation == UIDeviceOrientationPortraitUpsideDown) {
//翻轉為豎屏時
[self setVerticalFrame];
}else if (interfaceOrientation==UIDeviceOrientationLandscapeLeft || interfaceOrientation == UIDeviceOrientationLandscapeRight) {
//翻轉為橫屏時
[self setHorizontalFrame];
}
}

-(void)setVerticalFrame
{
NSLog(@"豎屏");
[contentView setFrame:CGRectMake(12, 6, 250, 125)];
[textLable setFrame:CGRectMake(50, 139, 182, 39)];
}

-(void)setHorizontalFrame
{
NSLog(@"橫屏");
[contentView setFrame:CGRectMake(12, 6, 106, 158)];
[textLable setFrame:CGRectMake(135, 11, 147, 39)];
}

 

layoutSubviews何時調用的問題

layoutSubviews何時調用的問題,這個方法是當你需要在調整subview的大小的時候需要重寫(我這個翻譯不嚴謹,以下是原文:You should override this method only if the autoresizing behaviors of the subviews do not offer the behavior you want.),但有時候經常指望它被調用的時候沒被調用,不希望它被調用的時候被調用了,搞的很上火。根據國外社區一個人帖子,做了總結性翻譯。

layoutSubviews在以下情況下會被調用:

1、init初始化不會觸發layoutSubviews
2、addSubview會觸發layoutSubviews
3、設置view的Frame會觸發layoutSubviews,當然前提是frame的值設置前后發生了變化
4、滾動一個UIScrollView會觸發layoutSubviews
5、旋轉Screen會觸發父UIView上的layoutSubviews事件
6、改變一個UIView大小的時候也會觸發父UIView上的layoutSubviews事件


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM