oOEric
oOEric

Reputation: 1079

Can't show the whole string in a list using SwiftUI

When you open the sample project:

Press a row once first and a plus button will be appeared. After tap plus button once, a plus character will be appended to the row. If I tap the button for many times, the ++++ string will show +... (shown in the image below). I didn't expect this, I expect that the row height will be increased automatically so whole string can be shown. What should I do to fix it?

enter image description here

If I tap the plus button for 5-6 times, the row height will be increased automatically as expected.

enter image description here

Major project code in the sample project:

ContentView.swift

struct ContentView: View {
    
    @EnvironmentObject var userData: UserData
    
    var body: some View {

        HStack {
            List {
                ForEach(userData.subtasks) { subtask in
                    SubtaskRowNextToCard(subtaskModel: subtask)
                }
            }
            
            if userData.currentSubtask != nil {
                SubtaskCard()
                    .padding(.all)
            }
        }
        .onAppear {
                        
            for _ in 0..<20 {
                appendASubtask()
            }
            
        }
        
    }
    
    func appendASubtask() {
        let aSubtask = SubtaskModel(
        score: ""
        )
        
        userData.subtasks.append(aSubtask)
    }
    
}

SubtaskModel.swift

import Foundation
import SwiftUI

class SubtaskModel: ObservableObject, Identifiable {
    @Published var score: String = ""
    
    init(
        score: String
    ) {
        self.score = score
    }
}

SubtaskRowNextToCard.swift

struct SubtaskRowNextToCard: View {
    
    @ObservedObject var subtaskModel: SubtaskModel
    @EnvironmentObject var userData: UserData
    
    @State var scoreWithRound: String = ""
    
    var body: some View {
        
        Button(action: {
            userData.currentSubtask = subtaskModel
        }) {
            Text(scoreWithRound)
        }
        .onAppear {
            updateScore()
        }
        .onReceive(NotificationCenter.default.publisher(for: NSNotification.Name.init("changedCurrentSubtask"))) { obj in
            updateScore()
        }
        
    }
    
    func updateScore() {
        scoreWithRound = subtaskModel.score
    }
    
}

SubtaskCard.swift

struct SubtaskCard: View {
    
    @EnvironmentObject var userData: UserData
        
    var body: some View {
        
        Button(action: {
            print("+ button was tapped")
            appendScore(newScore: "+")
        }) {
            Image(systemName: "plus.circle.fill")
        }
        .buttonStyle(PlainButtonStyle())
        
    }
    
    func appendScore(newScore: String) {
        if let subtaskModel = userData.currentSubtask {
            subtaskModel.score = subtaskModel.score + newScore + " "
                        
            NotificationCenter.default.post(name: NSNotification.Name.init("changedCurrentSubtask"), object: nil, userInfo: nil)
        }
    }
}

Upvotes: 0

Views: 302

Answers (1)

RTXGamer
RTXGamer

Reputation: 3712

Add .fixedSize(horizontal: false, vertical: true) and it wont truncate the text anymore:

  ForEach(userData.subtasks) { subtask in
                    SubtaskRowNextToCard(subtaskModel: subtask).fixedSize(horizontal: false, vertical: true)
                }

EDIT: For the dynamic height fix:

Replace Text with TextEditor and you won't notice the flickering:

Text(scoreWithRound)

to

TextEditor(text: $scoreWithRound).allowsHitTesting(false)

Upvotes: 1

Related Questions