diff --git a/Pane.swift b/Pane.swift index 030a239..3e2f117 100644 --- a/Pane.swift +++ b/Pane.swift @@ -101,8 +101,10 @@ class ShowTitle: NSObject, ObservableObject { @Published var chapVisible = false } + struct Pane: View { @ObservedObject var paneConnector: PaneConnector + @ObservedObject var scrollDelegate: ScrollDelegate @StateObject var showTitle = ShowTitle() // @State var chapVisible = false @@ -202,12 +204,11 @@ struct Pane: View { let reactive = self.refresh } - // if self.paneConnector != nil { - // let reactive = self.paneConnector - // } + scrollView.canCancelContentTouches = false + scrollView.delegate = scrollDelegate - DispatchQueue.main.async { - if paneConnector.setScrollOffset != nil { + DispatchQueue.main.async { + if paneConnector.setScrollOffset != nil { scrollView.contentOffset.y = scrollView.contentOffset.y + paneConnector.setScrollOffset! paneConnector.setScrollOffset = nil diff --git a/gloss/ContentView.swift b/gloss/ContentView.swift index 20414a2..9eccaa9 100644 --- a/gloss/ContentView.swift +++ b/gloss/ContentView.swift @@ -215,6 +215,7 @@ func makeVerseView(seg: SegDenorm) -> some View { } class PaneConnector: NSObject, ObservableObject { + var showOverlay: Bool = false @Published var refresh: Bool = false @Published var vertSep = CGFloat(20) @@ -225,9 +226,27 @@ class PaneConnector: NSObject, ObservableObject { @Published var scrollOffset = CGFloat() @Published var hasMoved = false var setScrollOffset: CGFloat? + @Published var disableScroll = false + } +class ScrollDelegate: NSObject, ObservableObject, UIScrollViewDelegate { + @Published var isScrolling = false + + func scrollViewWillBeginDragging(_: UIScrollView) { + print("pop started scroll") + isScrolling.toggle() + } + + func scrollViewDidEndDragging(_: UIScrollView, willDecelerate _: Bool) { + print("pop ended scroll") + isScrolling.toggle() + } +} + + + struct ContentView: View { // this is for the whole view swiping @State var mainSwipe = CGSize.zero @@ -236,6 +255,7 @@ struct ContentView: View { @State var selection = 0 @StateObject var paneConnector = PaneConnector() + @StateObject var scrollDelegate = ScrollDelegate() @State var refresh: Bool = false @@ -248,6 +268,8 @@ struct ContentView: View { @State var dragOffset = CGFloat(0) + @GestureState var dragGestureActive = CGSize.zero + enum SwipeStartState { case center case right @@ -271,10 +293,13 @@ struct ContentView: View { init() { UITableView.appearance().backgroundColor = UIColor(Color(red: 0.2, green: 0.2, blue: 0.2)) _selectedRibbon = Query(SelectedRibbonRequest()) + } + var body: some View { + var fontSize = CGFloat(15) var scale = 0.65 var height = CGFloat(50) @@ -327,6 +352,7 @@ struct ContentView: View { // Top pane Pane(paneConnector: paneConnector, + scrollDelegate: scrollDelegate, selectedRibbon: selectedRibbon, width: geometry.size.width - 15, height: geometry.size.height + 20, @@ -340,7 +366,7 @@ struct ContentView: View { // .onChanged { gesture in // paneConnector.vertSep = paneConnector.vertSep - gesture.translation.height // } - // ) + // // // Bottom pane // ScrollViewReader { _ in @@ -372,9 +398,14 @@ struct ContentView: View { .offset(x: 20, y: 0) .offset(x: pulledOut.width) .offset(x: mainSwipe.width) - .gesture( - DragGesture() + .highPriorityGesture( + DragGesture(minimumDistance: 30) + .updating($dragGestureActive) { value, state, _ in + print("pop here") + state = value.translation + } .onChanged { value in + print("pop changed") // Calculate the offset let margin = CGFloat(30) @@ -392,50 +423,46 @@ struct ContentView: View { print("start swipe meow: \(startSwipeState)") } - if newOffset > 0 { - startSwipeDir = .right - } else { - startSwipeDir = .left - } - - - // Apply resistance if out of bounds - var maxOffsetRight: CGFloat = 110 - var maxOffsetLeft: CGFloat = 200 - - - if startSwipeState == .right { - if startSwipeDir == .right { - maxOffsetRight = .zero - maxOffsetLeft = .zero - } else if startSwipeDir == .left { - maxOffsetRight = CGFloat(110) - maxOffsetLeft = CGFloat(-30) - } - } else if startSwipeState == .left { - - if startSwipeDir == .left { - maxOffsetLeft = .zero - maxOffsetRight = .zero - } else if startSwipeDir == .right { - maxOffsetLeft = CGFloat(200) - maxOffsetRight = CGFloat(10) - } + if newOffset > 0 { + startSwipeDir = .right + } else { + startSwipeDir = .left } - if newOffset + pulledOut.width < -maxOffsetLeft { - if startSwipeState == .right && startSwipeDir == .left { - newOffset = -maxOffsetLeft + rubberBandEffect(newOffset + maxOffsetLeft) - pulledOut.width - } else { - newOffset = -maxOffsetLeft + rubberBandEffect(newOffset + maxOffsetLeft) - } + // Apply resistance if out of bounds + var maxOffsetRight: CGFloat = 150 + var maxOffsetLeft: CGFloat = -200 - } else if newOffset + pulledOut.width > maxOffsetRight { - if startSwipeState == .left, startSwipeDir == .right { - newOffset = maxOffsetRight + rubberBandEffect(newOffset - maxOffsetRight) - pulledOut.width - } else { - newOffset = maxOffsetRight + rubberBandEffect(newOffset - maxOffsetRight) - } + // if startSwipeState == .right { + // if startSwipeDir == .right { + // maxOffsetRight = .zero + // maxOffsetLeft = .zero + // } else if startSwipeDir == .left { + // maxOffsetRight = CGFloat(110) + // maxOffsetLeft = CGFloat(-30) + // } + // } else if startSwipeState == .left { + + // if startSwipeDir == .left { + // maxOffsetLeft = .zero + // maxOffsetRight = .zero + // } else if startSwipeDir == .right { + // maxOffsetLeft = CGFloat(200) + // maxOffsetRight = CGFloat(10) + // } + // } + + if newOffset > maxOffsetRight, pulledOut.width == 0 { + // newOffset = maxOffsetRight + rubberBandEffect(newOffset) + newOffset = maxOffsetRight + rubberBandEffect(newOffset - maxOffsetRight) + } + + if newOffset > 0, pulledOut.width > 0 { + newOffset = rubberBandEffect(newOffset) + } + + if newOffset < maxOffsetLeft, pulledOut.width == 0 { + newOffset = maxOffsetLeft + rubberBandEffect(newOffset) } self.mainSwipe.width = newOffset @@ -443,83 +470,129 @@ struct ContentView: View { // dragOffset is what is used to make the text be readable // with the right pane being visible - // if mainSwipe.width < -margin && pulledOut.width <= 0 { - - if mainSwipe.width < -margin && pulledOut.width <= 0 { + if mainSwipe.width < -margin, pulledOut.width <= 0 { dragOffset = margin + mainSwipe.width + pulledOut.width } - if mainSwipe.width > 0 && pulledOut.width < 0 { + if mainSwipe.width > 0, pulledOut.width < 0 { dragOffset = margin + mainSwipe.width + pulledOut.width } } .onEnded { _ in - var finalSwipe = CGFloat(0) - let swipeLeftFinal = CGFloat(-200) - let swipeRightFinal = CGFloat(110) - - let margin = CGFloat(30) - var setDragOffset = CGFloat(0) - - if startSwipeState == .center { - if startSwipeDir == .right { - finalSwipe = swipeRightFinal - } else { - finalSwipe = swipeLeftFinal - setDragOffset = margin + swipeLeftFinal - } - } else if startSwipeState == .right { - finalSwipe = .zero - - if startSwipeDir == .left { - finalSwipe = .zero - } else { - finalSwipe = swipeRightFinal - } - } else if startSwipeState == .left { - - if startSwipeDir == .left { - finalSwipe = swipeLeftFinal - setDragOffset = margin + swipeLeftFinal - } else { - finalSwipe = .zero - } - } - - startSwipeState = nil - startSwipeDir = nil - - print("foo") - - // if mainSwipe.width < 0 && pulledOut.width > 0 { - // setPulledOutWith = CGFloat(0) - // } else if mainSwipe.width > 0 && pulledOut.width < 0 { - // setPulledOutWith = CGFloat(0) - - // } else if (mainSwipe.width < 0 && pulledOut.width < 0) || - // (mainSwipe.width < 0 && pulledOut.width == 0) { - // setPulledOutWith = pulledOutRight - // setDragOffset = margin + setPulledOutWith - // } else if abs(mainSwipe.width + pulledOut.width) > 30 { - // setPulledOutWith = pulledOutLeft - // } - - withAnimation(.spring(response: 0.2)) { - pulledOut.width = finalSwipe - dragOffset = setDragOffset - mainSwipe = .zero - } + onDragEnded() } - ) + ) + .onChange(of: scrollDelegate.isScrolling) { value in + print ("pop reset change") + // if scrollDelegate.isScrolling == true { + Task { + mainSwipe.width = 0 + } + // } + } } } .background(Color(red: 0.1, green: 0.1, blue: 0.1)) } + + func onDragEnded() { + print("pop ended") + paneConnector.disableScroll = false + var finalSwipe = CGFloat(0) + let swipeLeftFinal = CGFloat(-200) + let swipeRightFinal = CGFloat(110) + + let margin = CGFloat(30) + var setDragOffset = CGFloat(0) + + if startSwipeState == .center { + if startSwipeDir == .right { + finalSwipe = swipeRightFinal + } else { + finalSwipe = swipeLeftFinal + setDragOffset = margin + swipeLeftFinal + } + } else if startSwipeState == .right { + finalSwipe = .zero + + if startSwipeDir == .left { + finalSwipe = .zero + } else { + finalSwipe = swipeRightFinal + } + } else if startSwipeState == .left { + if startSwipeDir == .left { + finalSwipe = swipeLeftFinal + setDragOffset = margin + swipeLeftFinal + } else { + finalSwipe = .zero + } + } + + startSwipeState = nil + startSwipeDir = nil + + print("foo") + + // if mainSwipe.width < 0 && pulledOut.width > 0 { + // setPulledOutWith = CGFloat(0) + // } else if mainSwipe.width > 0 && pulledOut.width < 0 { + // setPulledOutWith = CGFloat(0) + + // } else if (mainSwipe.width < 0 && pulledOut.width < 0) || + // (mainSwipe.width < 0 && pulledOut.width == 0) { + // setPulledOutWith = pulledOutRight + // setDragOffset = margin + setPulledOutWith + // } else if abs(mainSwipe.width + pulledOut.width) > 30 { + // setPulledOutWith = pulledOutLeft + // } + + withAnimation(.spring(response: 0.2)) { + pulledOut.width = finalSwipe + dragOffset = setDragOffset + mainSwipe = .zero + } + } + + + + // let hackyPinch = MagnificationGesture(minimumScaleDelta: 0.0) + // .onChanged({ delta in + // onDragEnded() + // }) + // .onEnded({ delta in + // onDragEnded() + // }) + + // let hackyRotation = RotationGesture(minimumAngleDelta: Angle(degrees: 0.0)) + // .onChanged({ delta in + // onDragEnded() + // }) + // .onEnded({ delta in + // onDragEnded() + // }) + + // let hackyPress = LongPressGesture(minimumDuration: 0.0, maximumDistance: 0.0) + // .onChanged({ _ in + // onDragEnded() + // }) + // .onEnded({ delta in + // onDragEnded() + // }) + + + func handleVisibilityChanged2(_: String, change _: VisibilityChange, tracker _: VisibilityTracker) {} func rubberBandEffect(_ offset: CGFloat) -> CGFloat { - let resistance: CGFloat = 0.55 - return resistance * pow(abs(offset), 0.7) * (offset < 0 ? -1 : 1) + let resistance: CGFloat = 0.05 + return 4 * log(offset + 1) + // return resistance * pow(abs(offset), 1) * (offset < 0 ? -1 : 1) + } + + private func dragCancelled() { + print("pop dragCancelled") + mainSwipe = .zero } }