1

I can't figure out why my ForEach loop is making my views not scale correctly inside their parent view. If I comment out the ForEach loop and uncomment //.frame(width: geometry.size.width, height: 10) the RoundedRectangle is scaled correctly in its parent view, but when using the ForEach loop my views flow off the screen. I have double checked that CGFloat((sleepOrAwakeSpan.seconds / DataStore.sleepOrAwakeSpans.map { $0.endTime.timeIntervalSince($0.startTime) }.reduce(0, +))) total = 100. So I know the geometry is correct, and I know my expected % of the geometry is correct, what could cause the addition of the ForEach to make it flow off screen?

struct AsleepTimeView: View {

    @EnvironmentObject var dataStore: DataStore

     static let sleepTimeFormat: DateFormatter = {
        let formatter = DateFormatter()
        formatter.dateStyle = .none
        formatter.timeStyle = .short
        return formatter
     }()
    
    
    var body: some View {
        Color.clear.overlay(
        GeometryReader { geometry in
            VStack(alignment: .center) {
                HStack {
                    ForEach(DataStore.sleepOrAwakeSpans) { sleepOrAwakeSpan in    
                            RoundedRectangle(cornerRadius: 5)
                                .frame(width: geometry.size.width * CGFloat((sleepOrAwakeSpan.seconds / DataStore.sleepOrAwakeSpans.map { $0.endTime.timeIntervalSince($0.startTime) }.reduce(0, +))), height: 10)
                                //.frame(width: geometry.size.width, height: 10)
                                .foregroundColor(sleepOrAwakeSpan.asleep == false ? TrackerConstants.scaleLevel6Color : TrackerConstants.scaleLevel2Color)
                                //.foregroundColor(.red)
                                                 
                    }
                 
                }
            }
            
            
            })     // end of overlay
      
    }
}
GarySabo
  • 5,806
  • 5
  • 49
  • 124

1 Answers1

1

In your question, you say that you've double checked that the total = 100. But, if you're using it like a percentage, you'd want it to be 1.0, not 100 (so that everything adds up to 1.0 * width).

Secondly, HStack has built-in default spacing. Try using HStack(spacing: 0)

jnpdx
  • 45,847
  • 6
  • 64
  • 94
  • thank you! Yes sorry I meant 100% i.e. 1.0, yes HStack(spacing: 0) does work to center it within it's parent without overlapping, however I would like a bit more space between the views, how can I add say 2 or 5 spacing – GarySabo Apr 05 '21 at 19:40
  • 1
    If you want spacing, you'd have to build that into your equation -- so the width would be the `(totalWidth - totaSpacing) * percentage`. You'd find the total spacing by multiplying the individual spacing by the number of views - 1. – jnpdx Apr 05 '21 at 19:43