title: How to switch views in SwiftUI interactively based on a pan gesture or scroll view position?
body: <p>In an UIKit app I've built I used to have this effect where a scroll view would control the animation of enabling/disabling specific constraints in a view by using an UIPropertyAnimator and manipulating it's <code>fractionComplete</code> property. This allowed the animation to follow the scroll view's progression.</p>
  <p>In SwiftUI I do not control constraints anymore but rather I change the whole view hierarchy based on a <code>@State</code> variable (for eg, the view I want to transition between 2 states has a property called <code>isExpanded</code>).</p>
  <p>This simple transition is easily done with SwiftUI's <code>withAnimation</code> by simply toggling the bool value that I need. Using the <code>matchedGeometryEffect(id:in:properties:anchor:isSource:)</code> I can easily have elements move from/to the correct positions.</p>
  <p>What I am trying to figure out is how can I basically <em>pause</em> and then control the progression of the animation so that the transition between my start and end state is controlled via a pan gesture or, like I used to do it in UIKit, via a <code>ScrollView</code>.</p>
  <p>Here's a basic example of my SwiftUI code:</p>
  <pre><code>struct MyTwoStatesView: View {
      
      @Namespace var namespace
      @State var isExpanded: Bool = true
      
      var body: some View {
          ZStack {
              RoundedRectangle(cornerRadius: 4)
                  .fill(Color.gray)
              if isExpanded {
                  ExpandedStateView(namespace: namespace)
              }
              else {
                  CollapsedStateView(namespace: namespace)
              }
          }
          .fixedSize(horizontal: false, vertical: true)
          .onTapGesture {
              withAnimation {
                  isExpanded.toggle()
              }
          }
      }
  }
  </code></pre>
  <p>And here's the effect that the final animation has:
  <a href="https://i.stack.imgur.com/bHjds.gif" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/bHjds.gif" alt="enter image description here" /></a></p>
  <hr />
  <p><strong>Later edit:</strong>
  Here's a gist for the &quot;full&quot; example: <a href="https://gist.github.com/zeusent/39f58827519d9bfda63271a9cb24d6b6" rel="nofollow noreferrer">https://gist.github.com/zeusent/39f58827519d9bfda63271a9cb24d6b6</a></p>