Upgrade to Pro — share decks privately, control downloads, hide ads and more …

ScrollView scroll,decelerating - iOS SDK UIkit

notoroid
September 25, 2021

ScrollView scroll,decelerating - iOS SDK UIkit

札幌iPhoneアプリ開発懇談会(Devsap) 2021年9月25日勉強会資料

notoroid

September 25, 2021
Tweet

More Decks by notoroid

Other Decks in Programming

Transcript

  1. 6*4DSPMM7JFX  J04ͷ࢖͍ͪ͝͝ͷྑ͞Λܾఆ͚ͮͨ6*ύʔπ w J04 J1IPOF04 ͷࠒ͔Βଘࡏ w Ϣʔβʔͷλονૢ࡞ʹ௥ਵ͢ΔεΫϩʔϧ w

    ίϯςϯπ຤୺·Ͱ౸ୡͨ͠ࡍͷό΢ϯε w Ԡ༻6*ଟ਺ w 8,8FC7JFXɺ6*5BCMF7JFXɺ6*$PMMFDUJPO7JFX w աڈʹ͸.BQ΋࢖༻
  2. 6*4DSPMM7JFX  J04ͷ࢖͍ͪ͝͝ͷྑ͞Λܾఆ͚ͮͨ6*ύʔπ w ΞϓϦ։ൃͰ΋ෳࡶͳ࢓૊Έ w εΫϩʔϧίϯςϯπͷ෯ߴ͞ͷऔѻ͕೥ʑมԽ w "VUP4J[JOHˠ$POTUSBJOUˠ"ODIPSͱ೥ʑ੔ཧ w

    ίϯςϯπྖҬͷτϥϒϧ w J04ʙεςʔλεόʔྖҬมߋΛ΋Ζʹड͚Δ w εςʔλεόʔ͔ΒϊονྖҬ΁ͱมԽ w ෳ਺ϓϩύςΟͷ૊Έ߹ΘͤͰڍಈ͕มԽ w %FMFHBUFͰͷදࣔྖҬ੍ޚͷϊ΢ϋ΢ඞཁ
  3. 6*4DSPMM7JFX%FMFHBUF 6*4DSPMM7JFX಺ͰͷΠϕϯτΛัଊ͢ΔEFMFHBUF w 4DSPMMΠϕϯτ w εΫϩʔϧ։࢝ऴྃΠϕϯτ w ར༻ऀ6*ଆͷશͯͷεΫϩʔϧΠϕϯτ͕ൃੜ w ζʔϜ։࢝ऴྃΠϕϯτ

    w %FDFMFSBUJOH։࢝ऴྃΠϕϯτ w Ϣʔβʔͷૢ࡞ޙʹό΢ϯυಈ࡞ͷ։࢝ऴྃΛ௨஌ w εΫϩʔϧΛτοϓʹҠಈ͢Δ͔ͷΠϕϯτ εςʔλεྖҬͷλ οϓ
  4. 6*4DSPMM7JFX%FMFHBUF  4DSPMMͱ%FDFMFSBUJOHͷؔ܎ w 4DSPMMΠϕϯτ w Ϣʔβʔ͕λονૢ࡞Ͱ w %FDFMFSBUJOHΠϕϯτ w

    Ճ଎౓͋Γͷλονૢ࡞ޙʹɺ4DSPMM7JFX͕ຊདྷ͋Δ΂͖Ґஔ ʹίϯςϯπ͕໭Δ·ͰͷΠϕϯτ w %FDFMFSBUJOH͕ऴྃ͢Δ·Ͱը໘্ͷಈ͖͸ࢭ·Βͳ͍
  5. extension InfiniteLoopHeaderView: UIScrollViewDelegate { … // Decelerating΁ͷରԠ func scrollViewDidEndDecelerating(_ scrollView:

    UIScrollView) { // εΫϩʔϧҐஔͷਖ਼نԽ͕ߦΘΕ͍ͯͳ͍৔߹ guard scrollNormalizedPosition != 0 else { return } // ίϯςϯπͷதԝҐஔΛऔಘ let scrollViewCenter = scrollView.superview!.convert(scrollView.center, to: contentView) // தԝҐஔؚ͕·ΕΔۣܗ৘ใΛݩʹϔομʔཁૉͷΠϯσοΫεΛܭࢉ var targetIndex: Int = -1 for index in 0..<(leftOverrun + elementCount + rightOverrun) { let hitTestRect = CGRect(origin: CGPoint(x: CGFloat(index) * scrollView.bounds.width, y: 0), size: scrollView.bounds.size) if hitTestRect.contains(scrollViewCenter) { targetIndex = index } } // ಘΒΕͨΠϯσοΫεΛݩʹΠϯσοΫε৘ใΛਖ਼نԽ let position = targetIndex - leftOverrun let loopIndex = (elementCount + ( (position) % elementCount)) % elementCount selectedIndex = loopIndex // ͜͜ͰεΫϩʔϧॲཧΛϓϩςΫτ͢Δ(scrollNormalizedPosition͕มߋ͞Εͯ͠·͏ՄೳੑΛආ͚ΔͨΊ) skipDidScroll = true self.scrollView.contentOffset = CGPoint(x: self.scrollView.bounds.width * CGFloat(centerForFiniteLoop() + selectedIndex), y: 0) skipDidScroll = false scrollNormalizedPosition = 0 centerXConstraint.constant = 0 } }
  6. extension InfiniteLoopHeaderView: UIScrollViewDelegate { … // εΫϩʔϧ΁ͷରԠ func scrollViewDidScroll(_ scrollView:

    UIScrollView) { // skipDidScroll͞Ε͍ͯΔ৔߹͸scrollViewDidEndDecelerating Ͱͷ guard skipDidScroll != true else { return } // ScrollViewͷcontentOffsetͱscrollNormalizedPosition͔ΒҐஔΛಘΔ let plainPosition = Int(ceil( (scrollView.contentOffset.x / scrollView.bounds.width) - CGFloat(centerForFiniteLoop()) + CGFloat(scrollNormalizedPosition) ) ) if plainPosition <= leftSafeArea { // ϔομʔࠨͷ҆શྖҬΛ௒͍͑ͯͨ৔߹͸scrollNormalizedPosition ʹҐஔΛ֨ೲ͠contentView ͷҐஔΛͣΒ͢ scrollNormalizedPosition = scrollNormalizedPosition + -plainPosition + (elementCount - visibleColumnNumber) centerXConstraint.constant = CGFloat(-scrollNormalizedPosition) * scrollView.bounds.width } else if plainPosition >= rightSafeArea { // ϔομʔӈͷ҆શྖҬΛ௒͍͑ͯͨ৔߹͸scrollNormalizedPosition ʹҐஔΛ֨ೲ͠contentView ͷҐஔΛͣΒ͢ scrollNormalizedPosition = scrollNormalizedPosition + -plainPosition centerXConstraint.constant = CGFloat(-scrollNormalizedPosition) * scrollView.bounds.width } else { // ͦͷଞͷ৔߹͸௨ৗॲཧɻબ୒ΠϯσοΫεΛมߋ let lIndex = (elementCount + (plainPosition % elementCount)) % elementCount selectedIndex = lIndex } } }