UIScrollView PagingEnabled的轉屏問題
應用支援使用者轉動手機後,UI會跟隨轉動,此時就需要對我們的頁面設定轉屏支援;如果介面中包含UIScrollView(此時要求UIScrollView的width和height是不相等的,看完本文就明白),並且UIScrollView isPagingEnable為true時,在轉屏後,UIScrollView的page滑動就會出現問題(無法滑動到正確的頁,一般情況下會滑走多個頁),如何解決,請繼續看。
1. iOS的轉屏回撥
iOS在UIController中提供了屏轉的回撥,在iOS 8.0開始使用新的版本,回撥方法的宣告如下:
// iOS 8.0 以前
func willRotateToInterfaceOrientation(_ toInterfaceOrientation: UIInterfaceOrientation, duration duration: NSTimeInterval)
func didRotateFromInterfaceOrientation(_ fromInterfaceOrientation: UIInterfaceOrientation)
// iOS 8.0 及 更高版本
func viewWillTransitionToSize(_ size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator)
經過測試發現,在iOS 8.0及更高版本里面,系統會嘗試先回撥viewWillTransitionToSize
,如果沒有重寫,則會嘗試回撥willRotateToInterfaceOrientation
。
另外,我們還可以監聽如下通知獲得轉屏感知:
UIApplicationWillChangeStatusBarOrientationNotification
UIApplicationDidChangeStatusBarOrientationNotification
2. UIScrollView的轉屏設定
UIScrollView開啟pagingEnabled,scrollView每次滑動的寬度是scrollView的width的長度,轉屏之後,scrollView滑動的寬度變化了,但是scrollView的subviews的frame和scrollView的contentSize並沒有變化,這就是出現問題的原因。
解決問題的方法很簡單,只需要在轉屏時,把scrollView的subviews的frame和scrollView的contentSize設定正確就ok了,參考程式碼如下(<i>剛開始在公開場合使用Swift,不地道的地方請各位指出~~</i>):
override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
var count = 0
for view in scrollView.subviews {
var frame = view.frame
// subview的frame修正成轉屏後,一屏的大小
frame.origin.x = CGFloat.init(integerLiteral: count) * size.width
frame.size.width = size.width
frame.size.height = size.height
view.frame = frame
count += 1
}
scrollView.contentSize = CGSize.init(width: CGFloat.init(integerLiteral: count) * size.width, height: size.height)
}
此時,再對UIScrollView進行轉屏,已經不會出現滑動錯頁的問題;回到本文開始的一個問題,如果scrollView的width和height是相等的,那麼,轉屏前後,scrollView的contentSize和subviews的frame實際不會發生變化,所以這種情況下轉屏是不會有問題的。
我們會發現,轉屏後有可能顯示的不再是之前展示的那頁,所以我們還需要使用setContentOffset
來讓正確的頁顯示出來,程式碼如下:
// 滑動到當前page的顯示位置
var offset = scrollView.contentOffset
offset.x = CGFloat.init(integerLiteral: (Int)(offset.x / scrollView.frame.width)) * size.width
scrollView.setContentOffset(offset, animated: false)
3. UIScrollView的其它問題
如果UIScrollView顯示了scrollIndicator,則scrollView的subviews會多出1個或者2個UIImageView物件,這2個物件就是scrollIndicator。
可以使用下面方法,隱藏scrollIndicator
scrollView.showsHorizontalScrollIndicator = false
scrollView.showsVerticalScrollIndicator = false
或者,在遍歷subviews時排除掉
for view in scrollView.subviews {
if !view.isKind(of: YourClass.self) {
continue
}
// 修正subview的frame
}
排除的方法還有一種,可以在新增subview的時候為view設定tag
,在for中就可以根據tag
來判斷該view是否為我們新增的view了。
相關文章
- UIScrollView自動向下偏移的問題UIView
- Android Activity跳轉閃屏問題Android
- UIScrollView載入子檢視偏移64的問題UIView
- unity 劉海屏問題Unity
- VNC FOR AIX 灰屏的問題解決VNCAI
- Ubuntu 6.06 升級到 6.10 寬屏解析度的問題(轉)Ubuntu
- UIScrollview的一些用法,解決裡面ImageView只新增不釋放的問題UIView
- 解決切換Fragment的黑色閃屏問題Fragment
- UIScrollVIewUIView
- ios手機豎屏拍照圖片旋轉90°問題解決方法iOS
- UIScrollView的基本用法UIView
- UIScrollView AutoLayoutUIView
- 理解UIScrollViewUIView
- iOS UIScrollView的基本使用iOSUIView
- Ubuntu 16.04 Vysor 破解 和黑屏問題解決+ 閃屏問題解決Ubuntu
- getParameter方法的中文問題【轉】
- 轉:Oracle的時區問題Oracle
- {HELP}sar命令的問題(轉)
- 字串轉數字的問題字串
- 有沒有人瞭解安卓錄屏不成功的問題?安卓
- 使用雙快取解決 Canvas clearRect 引起的閃屏問題快取Canvas
- UIScrollView在StoryBoard中的使用UIView
- 【轉】css解決相容的問題CSS
- 問題多多的STL實現 (轉)
- PHP中include()的使用問題 (轉)PHP
- Java的國際化問題 (轉)Java
- ORACLE在“域”上的問題【轉】Oracle
- Oracle 索引的三個問題(轉)Oracle索引
- [轉帖]XACT_ABORT 的問題
- mysql 轉義問題MySql
- java轉型問題Java
- 雙硬碟問題(轉)硬碟
- UIScrollView中使用AutoLayoutUIView
- UIScrollView 原理詳解UIView
- UIScrollView API 翻譯UIViewAPI
- UIScrollView滾動動畫UIView動畫
- 每個CIO都應該問的IT轉型問題
- FPGA的DAC轉換部分遇到的問題FPGA