Search code examples
swiftswiftuiinsertfuncdot

SwiftUI Insert a field name received from a function following "."


I get a field name from a function. How to insert that field name following dot "."

  1. Model
struct User: Identifiable {
        let username: String
        let fullName: String
        var description: String = ""
    }
  1. Get a field name from a title
extension User {
    func get_field_name(key: String?) -> String {
        var default_field = ""
        guard let key = key else { return default_field }
        let field: [String: String] = [
            "Name" : "fullName",
            "Username" : "username",
            "Bio" : "description"
        ]
        return field[key] ?? default_field
    }
}
  1. Expect.

Example if "item.title" is "Name" then

let user: User
Text(item.title) //OK - Name
Text(user.get_field_name(key: item.title)) //OK - fullName
Text(user.???) //??? How to insert field name following "."
  1. Purpose

I use it in the pic below

enter image description here

Thank you so much for your answer.


Solution

  • I think you are looking for key paths.

    Change get_field_name to:

    func getUserKeyPath(key: String?) -> KeyPath<User, String>? {
        guard let key = key else { return nil }
        let field: [_: KeyPath<User, _>] = [
            "Name" : \.fullName,
            "Username" : \.username,
            "Bio" : \.description
        ]
        return field[key]
    }
    

    Then you can do:

    if let keyPath = getFieldKeyPath(key: item.title) {
        Text(user[keyPath: keyPath])
    } else {
        // handle the case when item.title does not match any property name in User
    }
    

    You can also do this in a single expression if you want to show a default string in the Text when item.title does not match any property name:

    Text(getFieldKeyPath(key: "Name").map { user[keyPath: $0] } ?? "Unknown")