Loopy Carousel: Submission to the SwiftUI Series **Workarounds** challenge

Overview

Loopy Carousel

Submission to the SwiftUI Series Workarounds challenge.

Loopy Carousel

Workaround details

In order to create the illusion of looping through the cards/images infinitely, we create two additional copies of the original deck and we tape them toghether making a 3x-length strip.

When the user taps on a card we reposition the strip using a calculated offset so that we are always set around the middle of the tape. We do this explicitely without animation. The goal is for the user not to notice any visual changes at all during this phase.

Finally we transition in the direction of the target card by moving the offset one more time, this time using withAnimation(). The animation will create the carousel effect by sliding while scaling the card at the center.

Relevant snippets

All the relevant code is in the ContentView source.

The layout consists of an outer, fixed HStack which wraps an inner, shifting HStack containing all the cards.

HStack(spacing: 0) {
  HStack(spacing: Self.spacing) {
      ForEach(0 ..< loopCount, id: \.self) { i in
      Card(content: cardLabels[i % cardLabels.count], isSelected: .constant(current == i))
        .onTapGesture { onSelect(i) }
    }
  }
  .offset(x: offset)
}
.clipped()

Some calculated properties help us render the deck and determine the current offset.

private var loopCount: Int {
  cardLabels.count * 3
}

private var cardWidth: CGFloat {
  Card.normalWidth + Self.spacing
}

private var evenShift: CGFloat {
  loopCount.isMultiple(of: 2)
  ? -cardWidth / 2
  : 0
}

private var offset: CGFloat {
  cardWidth * CGFloat(loopCount / 2 - current) + evenShift
}

Our handler for the tap action does the work of preparing the view before triggering the animated transition.

private func onSelect(_ index: Int) -> () {
  let jump = abs(current - index)
  if (index >= cardLabels.count * 2) {
    current = cardLabels.count + (index % cardLabels.count) - jump
    withAnimation { current += jump }
  } else if (index < cardLabels.count) {
    current = cardLabels.count + (index % cardLabels.count) + jump
    withAnimation { current -= jump }
  } else {
    withAnimation { current = index }
  }
}
You might also like...
This is a project about Swift Student Challenge - WWDC22 [Submitted] Detailed walk through video link below.
This is a project about Swift Student Challenge - WWDC22 [Submitted] Detailed walk through video link below.

Oh My Flag The App Oh My Flag helps students get familiar with flags. It is both educating and entertaining with the design of multi-module and intera

Accepted in WWDC22 Swift Student Challenge. This is an app dedicated to my grandfather.

WWDC22 Introduction Accepted in WWDC22 Swift Student Challenge. This is an app dedicated to my grandfather. In short, Grandpa's Farm is an app in whic

Swift playground teaching basics of buffer overflow vulnerability and ARM64 assembly by exploiting vulnerable app on ARM64 emulator (WWDC22 Swift Student Challenge Winner)
Swift playground teaching basics of buffer overflow vulnerability and ARM64 assembly by exploiting vulnerable app on ARM64 emulator (WWDC22 Swift Student Challenge Winner)

Pwnground Project overview Pwnground is a project created as my submission for WWDC22 Swift Student Challenge (winner). It is an interactive Swift Pla

🎲 100% SwiftUI 2.0, classic 2048 game [SwiftUI 2.0, iOS 14.0+, iPadOS 14.0+, macOS 11.0+, Swift 5.3].
🎲 100% SwiftUI 2.0, classic 2048 game [SwiftUI 2.0, iOS 14.0+, iPadOS 14.0+, macOS 11.0+, Swift 5.3].

swiftui-2048 If you like the project, please give it a star ⭐ It will show the creator your appreciation and help others to discover the repo. ✍️ Abou

A simple SwiftUI Application to demonstrate creation of UI using SwiftUI.
A simple SwiftUI Application to demonstrate creation of UI using SwiftUI.

WatchShop_UI A simple SwiftUI Application to demonstrate creation of UI using SwiftUI. How to run the project ? Fork the project. Run the project usin

E-commerce app built in SwiftUI. Built in the course SwiftUI Masterclass in Udemy.
E-commerce app built in SwiftUI. Built in the course SwiftUI Masterclass in Udemy.

Touchdown-SwiftUI E-commerce app built in SwiftUI. Built in the course SwiftUI Masterclass in Udemy. Main components and concepts used: @EnvironmentOb

A multiplatform SwiftUI project demonstrating various SwiftUI features.

WikiDemo A multiplatform SwiftUI project demonstrating various SwiftUI features, including creating a master-detail interface. It's a multiplatform ve

SwiftUI Projects from Udemy SwiftUI Masterclass

SwiftUI Masterclass Repos: AsyncImage (N/A) Fructus (finished): an app for getting information about different fruits. Data comes from json files. Afr

Best architecture for SwiftUI + CombineBest architecture for SwiftUI + Combine

Best architecture for SwiftUI + Combine The content of the presentation: First of the proposed architectures - MVP + C Second of the proposed architec

Owner
Diego Lavalle
Mad computer scientist. Builder-of-Apps. Early adopter #SwiftUI @swift-you-and-i @swiftuilib
Diego Lavalle
My WWDC21 Swift Student Challenge Submission

Swift3D A 3D framework for everyone. I love SwiftUI. I have been using it constantly since it came out in 2019 and its power and ease of use are what

Christian 191 Sep 23, 2022
My WWDC22 Swift Student Challenge submission [Submitted]

WWDC22 Swift Student Challenge Submission An educational iPad app teaching some fundamental rules of typography in a fun and interactive way. Created

null 11 Nov 3, 2022
My WWDC 2022 swift student challenge submission - GradientDescend

GradientDescend Welcome to GradientDescend! This is my submission for the WWDC 2022 Swift Student Challenge. If you'd like, you can check out Gradient

Ryan Du 10 Oct 9, 2022
This is my copy of the "Ultimate Portfolio Project" tutorial series in Hacking with Swift+.

UltimatePortfolio This is my version of the "Ultimate Portfolio Project" tutorial series in Hacking with Swift+. I What have I learned in this series?

Justin Holt 0 Jun 16, 2022
Challenge: Throwback with SwiftUI 🕺🏻

Challenge: Throwback with SwiftUI ???? https://developer.apple.com/news/?id=5qbbn6ut Built using: SF Symbols & LazyVGrid for the toolbar Reference ima

An Trinh 6 Apr 6, 2022
DiceChallenge - Hacking with SwiftUI Challenge - Dice simulator

Some Dices Hacking with SwiftUI challenge turned into a real app available at th

Alex Oliveira 0 Jan 11, 2022
WWDC22 Challenge: SwiftUI navigation hotdish

Challenge: SwiftUI navigation hotdish See this challenge definition at: Challenge: SwiftUI navigation hotdish Proposed solution The new SwiftUI versio

Zebra 1 Jun 11, 2022
Swift Playgrounds desenvolvido para o Swift Student Challenge da WWDC 21

Pile Up Swift Playgrounds desenvolvido para o Swift Student Challenge da WWDC 21 Descrição Pile Up é um quebra cabeça cujo objetivo é empilhar os bloc

Beatriz Sato 3 Jun 5, 2021
My project for WWDC21 Swift Student Challenge!

Art with Times Table An interactive book that shows the figures that are generated when times tables are drawn inside a circle. This project was appro

Lucas Claro 10 Dec 30, 2022
null 1 Jan 27, 2022