UPGRADE YOUR SKILLS: Learn advanced Swift and SwiftUI on Hacking with Swift+! >>

Day 95 - Animating capsule for dice statistics

Forums > 100 Days of SwiftUI

Hi all,

near the completion of the Day 95 Consolidation VII challenge project (dice roll and stats) I decided to display simple graphs showing the occurrencies of the results for a given dice. It is pretty easy to show a capsule for each result, with a frame width normalized to be = GeometryProxy.size.width for max occurrence and 0 for min occurrence.

screenshot

What I cannot do is to animate the apearance of these capsules with an animation different from the default opacoty.

my View code is the following:

import SwiftUI

struct DiceResultsDetailedView: View {

    let dice: DiceModel

    @State private var animate = false // <--- this is to start the animation in onAppear

    var body: some View {

        VStack {

            Section(header: Text("Aggregate Statistics")) {
                Form {
                    Text("Faces: \(dice.faces).")
                    Text("Rolled: \(dice.launches) times.")
                    Text("Average result : \(dice.averageResult, specifier: "%g").")
                }
                .frame(height: 195)

            }

            Section(header: Text("Frequencies")) {
                List {
                    ForEach(0..<dice.id) { index in
                        let event = index + 1 // at Index 0 we have the total number of rolls
                        let occurrence = dice.events[event]
                        let frequency = dice.percentage(of: event)
                        let maxOccurrence = dice.maxEventOccurrence()?.occurrence

                        ZStack(alignment: .leading) {
                            if dice.launches > 0 {

                                if self.animate {
                                    GeometryReader { rowGeo in
                                        let unit = rowGeo.size.width / CGFloat(maxOccurrence!)
                                        Capsule()
                                            .foregroundColor(.red)
                                            .opacity(opacity(for: occurrence, withMax: maxOccurrence!))
                                            .frame(width: CGFloat(occurrence) * unit)

                                            //ANIMATION: COPIED FROM APPLE LANDMARK TUTORIAL

                                            .transition(.slide)
                                            .animation(.ripple(index: event))
                                    }
                                }
                            }
                            Text("\(event) : \(occurrence) times (\(frequency, specifier: "%g")%)")
                                .font(.headline)
                                .padding(.leading)
                        }
                    }
                }
                .onAppear {
                    DispatchQueue.main.asyncAfter(deadline: .now()+0.5) {
                        withAnimation {
                        self.animate = true
                        }
                    }
                }
            }
        }.navigationBarTitle(Text("\(dice.faces) sided dice stats"))
    }

    func opacity(for occurrence: Int, withMax: Int) -> Double {
        return Double(occurrence) / Double(withMax)
    }
}

// COPIED FROM APPLE LANDMARK TUTORIAL

extension Animation {
    static func ripple(index: Int) -> Animation {
        Animation.spring(dampingFraction: 0.5)
            .speed((2))
            .delay(0.03 * Double(index))
    }
}

but the Ripple animation/transition (example copied from Apple Landmark tutorial) never take efects, I always see the capsule-bars appearing with an animated opacity.

I'm obviously making a mistake in the way I setup the animation, but I can't figure out what it is...

3      

BUILD THE ULTIMATE PORTFOLIO APP Most Swift tutorials help you solve one specific problem, but in my Ultimate Portfolio App series I show you how to get all the best practices into a single app: architecture, testing, performance, accessibility, localization, project organization, and so much more, all while building a SwiftUI app that works on iOS, macOS and watchOS.

Get it on Hacking with Swift+

Sponsor Hacking with Swift and reach the world's largest Swift community!

Archived topic

This topic has been closed due to inactivity, so you can't reply. Please create a new topic if you need to.

All interactions here are governed by our code of conduct.

 
Unknown user

You are not logged in

Log in or create account
 

Link copied to your pasteboard.