2011-05-15 116 views
15

我在視圖控制器視圖中添加了一個webview,一個titleLabel和一個coverflowView作爲其子視圖,我希望它在方向更改時更改大小。我有改變的WebView框架在此方法:UIWebView在方向更改時無法正確調整大小?

- (void)willRotateToInterfaceOrientation: (UIInterfaceOrientation)toInterfaceOrientation duration: (NSTimeInterval)duration 

其內容並調整大小時,將iPad旋轉從orientationLandscape到orientationPortrait或orientationPortrait如果我開始與縱向應用程序orientationLandscape,但它是如此奇怪的是,它的內容當我以橫向方向啓動應用程序時,請不要調整大小...但NSLog顯示框架已更改。至於titleLabel和coverflowView,它們正確調整大小。我懷疑是否是因爲css?我已經使用css根據webview的高度和寬度來控制內容的風格。任何人都可以幫助我找到原因嗎?代碼如下:

- (void)willRotateToInterfaceOrientation: (UIInterfaceOrientation)toInterfaceOrientation duration: (NSTimeInterval)duration { 
double i = 0; 
NSInteger width=self.view.frame.size.width; 
NSInteger height=self.view.frame.size.height; 
NSLog(@"view :%@",[self.view description]); 
switch (toInterfaceOrientation){ 
    case UIInterfaceOrientationPortrait: 
    {  
     NSLog(@"rotate to Portrait"); 
     if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad){ 
      self.docView.frame=CGRectMake(0, 50, width+20, height-70); 
      self.toolbar.frame=CGRectMake(0, 0,height , 50); 
      for (UIView * view in [toolbar subviews]) { 
       if ([view isKindOfClass:[UIButton class]] && view.tag==kBackButtonTag){ 
        view.frame=CGRectMake(width-60, 6, 50, 36); 

       }else if([view isKindOfClass:[UIButton class]] && view.tag==kReloadButtonTag){ 
        view.frame=CGRectMake(width-160, 6, 80,36); 
       } 
      } 
      [coverflow setFrame:CGRectMake(0, 0 , width+20, height/2-50)]; 
      [titleLabel setFrame:CGRectMake(width/2-40,height/2-100, 100, 20)]; 
      if ([[[UIDevice currentDevice]model]isEqualToString:@"iPad"]) { 
       self.viewer.frame=CGRectMake(0, 0, 768, 1004); 
      }else{ 
       self.viewer.frame=CGRectMake(0, 0, 320, 480); 
      } 
     } 
     i=0; 
    }break; 
    case UIInterfaceOrientationPortraitUpsideDown: 
    { 
     NSLog(@"rotate to PortraitUpsideDown"); 
     if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad){ 
      self.docView.frame=CGRectMake(0, 50, width+20, height-70); 
      self.toolbar.frame=CGRectMake(0, 0,height , 50); 
      for (UIView * view in [toolbar subviews]) { 
       if ([view isKindOfClass:[UIButton class]] && view.tag==kBackButtonTag) { 
        view.frame=CGRectMake(width-60, 6, 50, 36); 

       }else if([view isKindOfClass:[UIButton class]] && view.tag==kReloadButtonTag){ 
        view.frame=CGRectMake(width-160, 6, 80,36); 
       } 
      } 

      [coverflow setFrame:CGRectMake(0, 0 , width+20, height/2-50)]; 
      [titleLabel setFrame:CGRectMake(width/2-40,height/2-100, 100, 20)]; 
      if ([[[UIDevice currentDevice]model]isEqualToString:@"iPad"]) { 
       self.viewer.frame=CGRectMake(0, 0, 768, 1004); 
      }else{ 
       self.viewer.frame=CGRectMake(0, 0, 320, 480); 
      } 

     } 

     i=180; 
    } break; 
    case UIInterfaceOrientationLandscapeLeft:{ 

     NSLog(@"rotate to LandscapeLeft"); 
     if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad){ 
     //  self.coverflow.frame=CGRectMake(0, 0, height+20, width-20); 
      self.docView.frame=CGRectMake(0, 50, height+20, width-70); 
      self.toolbar.frame=CGRectMake(0, 0,height+20 , 50); 
      for (UIView * view in [toolbar subviews]) { 
       if ([view isKindOfClass:[UIButton class]] && view.tag==kBackButtonTag) { 
        view.frame=CGRectMake(height-60, 6, 50, 36); 
        NSLog(@"button %@",[view description]); 
       }else if([view isKindOfClass:[UIButton class]] && view.tag==kReloadButtonTag){ 
        view.frame=CGRectMake(height-160, 6, 80,36); 
       } 
      } 
      [coverflow setFrame:CGRectMake(0, 0 , height+20, width/2-50)]; 
      [titleLabel setFrame:CGRectMake(height/2-40,width/2-80, 100, 20)]; 
      if ([[[UIDevice currentDevice]model]isEqualToString:@"iPad"]) { 
       self.viewer.frame=CGRectMake(0, 0, 1024, 748); 
      }else{ 
       self.viewer.frame=CGRectMake(0, 0, 480, 320); 
      } 
     } 

     i = 90; 
    }break; 
    case UIInterfaceOrientationLandscapeRight:{ 
     NSLog(@"rotate to LandscapeRight"); 
     if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad){ 
     // self.coverflow.frame=CGRectMake(0, 0, height+20, width-20); 
      self.docView.frame=CGRectMake(0, 50, height+20, width-70); 
      self.toolbar.frame=CGRectMake(0, 0,height+20 , 50); 
      for (UIView * view in [toolbar subviews]) { 
       if ([view isKindOfClass:[UIButton class]] && view.tag==kBackButtonTag) { 
        view.frame=CGRectMake(height-60, 6, 50, 36); 
       } 
       else if([view isKindOfClass:[UIButton class]] && view.tag==kReloadButtonTag){ 
        view.frame=CGRectMake(height-160, 6, 80,36); 
       } 
      } 
      [coverflow setFrame:CGRectMake(0, 0 , height+20, width/2-50)]; 
      [titleLabel setFrame:CGRectMake(height/2-40,width/2-80, 100, 20)]; 
      if ([[[UIDevice currentDevice]model]isEqualToString:@"iPad"]) { 
       self.viewer.frame=CGRectMake(0, 0, 1024, 748); 
      }else{ 
       self.viewer.frame=CGRectMake(0, 0, 480, 320); 
      } 
     } 

     i = -90; 
    }break; 
} 

//[webViewController willRotateToInterfaceOrientation:toInterfaceOrientation duration:duration]; 
// [self.view setNeedsDisplay]; 
// NSLog(@"coverflowView :%@",[self.coverflow description]); 
    NSLog(@"webview :%@",[viewer description]); 
    [viewer stringByEvaluatingJavaScriptFromString:[NSString stringWithFormat:@"window.__defineGetter__('orientation',function(){return %f;});",i]]; 
    [viewer stringByEvaluatingJavaScriptFromString:@"var e = document.createEvent('Events'); e.initEvent('orientationchange', true, false); document.dispatchEvent(e); "];  
} 




- (void)viewDidLoad { 
self.view.clipsToBounds=YES; 
self.view.autoresizesSubviews=YES; 
// self.view.autoresizingMask=UIViewAutoresizingNone; 

viewer=[[UIWebView alloc]initWithFrame:self.view.bounds]; 

[self.view addSubview:viewer]; 
viewer.delegate=self; 
viewer.scalesPageToFit=NO; 
viewer.autoresizesSubviews=NO; 
viewer.autoresizingMask=UIViewAutoresizingNone; 
viewer.dataDetectorTypes=0; 
// viewer.autoresizingMask=UIViewAutoresizingFlexibleWidth |UIViewAutoresizingFlexibleHeight; 
NSLog(@"webView :%@",[viewer description]); 
// [viewer setFrame:CGRectMake(0, self.view.bounds.size.height/2 , self.view.bounds.size.width, self.view.bounds.size.height/2)]; 
// [viewer setBounds:CGRectMake(0, self.view.bounds.size.height/2 , self.view.bounds.size.width, self.view.bounds.size.height/2)]; 

UIScrollView *scroller=[viewer.subviews objectAtIndex: 0]; 
if (scroller) { 
    scroller.alwaysBounceVertical=NO; 
    scroller.bounces=NO; 
    scroller.scrollEnabled=NO; 
} 

[self viewHomePage]; 
//[self createCoverFlowView]; 
[self createPopView]; 
//[self setHomeButtonPosition]; 
//[self setSettingButtonPosition]; 

#if __IPHONE_OS_VERSION_MIN_REQUIRED > 30000 
UILongPressGestureRecognizer* longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; 
[self.view addGestureRecognizer:longPress]; 
longPress.minimumPressDuration=2.0; 
longPress.delegate = self; 
longPress.cancelsTouchesInView = NO; 
longPress.allowableMovement=20; 
[longPress release]; 

UITapGestureRecognizer* singleTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(handleSingleTap:)]; 
[self.view addGestureRecognizer:singleTap]; 
singleTap.delegate = self; 
singleTap.cancelsTouchesInView = NO; 
[singleTap release]; 
#endif 
//[viewer setOpaque:YES];  //透明 
[super viewDidLoad]; 

} 
+0

我有這個完全相同的問題。如果應用程序以縱向模式啓動。 UIWebView正確調整大小,我的CSS顯示它已更改。如果我以橫向模式啓動它,它不會再改變。 – christophercotton 2011-05-21 20:23:48

回答

1

我有類似的問題,仍然無法找到真正的解決方案。我調用UIWebView上的重新加載來解決這個問題,通過縮放頁面來適應。

[webView reload]; 
+0

不適用於www.msn.com [self.webViewMain setFrame:CGRectMake(0.0,44.0,1024.0,724.0)]; ('content','width =%d;',false);「, (self.webViewMain stringByEvaluatingJavaScriptFromString: INT)self.webViewMain.frame.size.width]]; – 2012-06-06 09:53:48

51

我花了大約兩天的時間試圖跟蹤這個問題,因爲我有完全相同的問題。我發現我的視圖是否在縱向模式下開始,可以正確調整到橫向。但是,如果我以橫向模式開始視圖,它將在縱向上保持相同的尺寸。

如果您的視圖是設備的整個寬度,只需添加以下元標記即可使用。

<meta name="viewport" content="width=device-width" /> 

但在我的情況下,我們的UIWebView是非標準尺寸。將視口設置爲device-width只會讓事情變得更糟!通過使用javascript動態設置視口,我能夠正常工作。這應該在UIWebViews父視圖的layoutSubviews期間完成。您可以在willRotateToInterfaceOrientation中執行此操作,但是我發現如果您在willRotate中執行某些大小和界面,可能無法正確設置。先試試它,看看動畫是如何工作的。

該代碼只是將視口大小設置爲當前幀大小。您正在查看的HTML必須已經有meta viewport標記(如上所述)。如果你不能編輯HTML,還有其他方式通過javascript添加它。最簡單的方法是將meta標籤添加到<head>標籤中。然後使用下面的代碼,在您正確設置幀:

// assuming your self.viewer is a UIWebView 
[self.viewer stringByEvaluatingJavaScriptFromString: 
    [NSString stringWithFormat: 
    @"document.querySelector('meta[name=viewport]').setAttribute('content', 'width=%d;', false); ", 
     (int)self.viewer.frame.size.width]]; 

您可以在其他視窗添加項目,如果你不希望用戶規模,或者你想設置的最大規模。這最終使我們的UIWebView的視圖行爲正確。

+2

終極修復感謝 – sandy 2011-06-06 14:46:57

+0

作品。我有一個UIWebView的子類,並能夠把這個修復內setFrame :. – TomSwift 2011-08-01 14:49:19

+0

@TomSwift setFrame沒有爲我工作,我使用layoutSubviews – aryaxt 2012-03-07 16:06:36

0

我也遇到了從橫向切換到縱向時UIWebView內容不能正確調整大小的問題。

打獵了一段時間之後,我發現我的回答:「我發現處理這一種方法是重裝調整大小後的內容。當我說‘

重裝,’我不是這個意思UIWebView中的內置重載功能,我的意思是實際調用loadHTMLString:baseURL :(或者最初用來加載內容的任何方法)。「 Agent Gold's post on Apple Support forum

+1

在發佈複製和粘貼樣板/逐字回答多個問題時要小心,這些問題通常會被標記爲「垃圾郵件」社區。 – Kev 2011-07-23 12:26:52

+0

感謝Kev的注意。我有意在兩個地方發帖,以便在下一個人找到答案時根據他們首先遇到的問題保存下一個人。答案似乎對兩者都適用。 – 2011-07-29 22:07:46

+1

此外,重新加載內容對許多人來說是一個不好的解決方案。特別是如果你已經有了JavaScript,並且他們的用戶已經爲頁面做了一些事情。就像顯示一組不同的項目,或者開始輸入一些東西。通過重新加載,您將導致所有這些被刪除。 – christophercotton 2012-06-08 20:02:13

1

如果別人有同樣的問題,就給個提問。

由於HTML已經呈現(我不確定這是否完全正確,可能只是webview本身中的一個錯誤),但webview無法正確調整大小。我做了重新調整web視圖的html身體寬度的方法:

- (void) resizeHtml 
{ 
    NSString *jsString = [[NSString alloc] initWithFormat:@"document.getElementsByTagName('html')[0].style.width= '%dpx'", (int) _frame.size.width]; 

    [self.webView stringByEvaluatingJavaScriptFromString:jsString]; 
    [jsString release]; 
} 

這似乎只是正常工作在iPhone上,但在iPad上我不得不這樣做

- (void) reloadHtml 
{ 
    NSString *html = [webView stringByEvaluatingJavaScriptFromString:@"document.documentElement.outerHTML"]; 

    if(html == nil || [html isEqualToString:@""] || [html length] < 100) 
     [self.webView reload]; 

    [self.webView loadHTMLString:html baseURL:[NSURL URLWithString:@"some base url"]]; 
} 

你也可以使用了[self.webview重新加載],但這將使服務器的另一個要求,我認爲這是不好的;-)

我希望這可以幫助!

+1

不確定這是最好的方法,因爲您是通過字符串將整個文檔拖過來然後重新加載它。至少人們應該知道你正在導致整個頁面重新加載。 – christophercotton 2012-01-03 05:47:27

+0

這是真的,但我似乎無法找到一個更好的解決方案時,自動縮放關閉 - 我已經嘗試過這樣做相當大的文件沒有問題 – 2012-01-03 07:03:07

1

我向upvoted @ christophercotton的反應,因爲它的工作。但是我也發現我可以在不控制webview對象的情況下修復類似這樣的問題。他的解決方案爲我的問題提供了正確的方向。

 var el = $('meta[name=viewport]'); 
    if (window.orientation == 90 || window.orientation == -90) { 
     el.attr('content', 'width=device-height'); 
    } else { 
     el.attr('content', 'width=device-width'); 
    } 

這適用於iOS。還沒有嘗試過在android中(對於那些使用PhoneGap喜歡的)。

0

我剛剛有同樣的問題。

爲我工作的解決方案是設置:

webView.scalesPageToFit = YES; 
0

我試過Christoper's answer,翻譯他的OOC碼斯威夫特,但不工作。

最後,如果屏幕大小發生變化,我必須使網頁重新加載UIWebView。這可能是一個黑客,但無論如何工作。希望這個答案可以幫助Swift開發者多多少少。以下功能屬於您的UIViewController

override func viewWillTransitionToSize(size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator) { 
    super.viewWillTransitionToSize(size, withTransitionCoordinator: coordinator) 
    coordinator.animateAlongsideTransition(nil, completion: {context in 
     self.webView.reload()    
    }) 
} 
相關問題