Enum с изображениями для соответствия JSON - PullRequest
0 голосов
/ 27 апреля 2020

У меня есть enum States, сопоставление с изображениями, которые я сохранил в своей папке .xcassets:

 enum States: String {

    case AL, AR, etc

    var image: UIImage {
    switch self {
    case .AL: return UIImage(named: "Alabama")!
    case .AR: return UIImage(named: "Arkansas")!

    }
   }
  }

Структура программы:

struct Programs: Codable, Identifiable {

        enum CodingKeys: CodingKey {
        case programName, programState
      }

      var id = UUID()
      var programName: String
      var programState: String

      func mapToStates() -> States? {
        return States(rawValue: programState)
        }
      }
    }

Программа JSON:

{
"programName": "Alabama Time",
"programState": "AL",
}

Использование его с SwiftUI в ProgramRow:

    struct ProgramRow: View {
        var programData: Programs

        var body: some View {
        VStack(alignment: .leading) {
        HStack {
        Image(uiImage: States.AL.image) <-- use here, right now static value

        VStack(alignment: .leading) {
        Text(programData.programName)
        }
       }.padding()
     }
    }
   }

Мой вопрос заключается в том, как лучше всего проверить возвращенный JSON и показать изображение состояния, соответствующее тому, что возвращается из JSON

Ответы [ 3 ]

1 голос
/ 30 апреля 2020

Более эффективное решение с NSLocalizedString. Он работает как словарь и отображает одно значение в другое.

  • Создайте новый strings файл и назовите его States.strings

  • Заполните файл (синтаксис имеет решающее значение)

    "AL" = "Alabama";
    "AR" = "Arkansas";
    
    etc
    
  • Удалить enum

  • Заменить mapToStates() на

    var image : UIImage {
        let imageName = NSLocalizedString(programState, tableName:"States", comment: "")
        return UIImage(named: imageName)!
    }
    

И использовать это

Image(uiImage: programData.image) 
0 голосов
/ 27 апреля 2020

Прежде всего, вы должны исправить свой enum. Добавить регистр etc в switch:

enum States: String {
    case AL, AR, etc

    var image: UIImage? {
        switch self {
        case .AL:
            return UIImage(named: "Alabama")
        case .AR:
            return UIImage(named: "Arkansas")
        case .etc:
            return nil
        }
    }
}

Вы можете использовать кодируемую модель:

struct Programs: Codable {
    var programName: String
    var programState: String

    func mapToStates() -> States? {
        return States(rawValue: programState ?? "")
    }
}

И получить свое состояние из строки json:

do {
    let programs = try JSONDecoder().decode(Programs.self, from: jsonString.data(using: .utf8) ?? Data())
    guard let state = programs.mapToStates() else { return }
    // Use state
} catch {
    print(error)
}

В вашем коде это должно выглядеть так:

struct ProgramRow: View {
    var programData: Programs

    var body: some View {
        VStack(alignment: .leading) {
            HStack {
                Image(uiImage: programData.mapToStates()?.image ?? UIImage())

                VStack(alignment: .leading) {
                    Text(programData.programName)
                }
            }.padding()
        }
    }
}
0 голосов
/ 27 апреля 2020

Если вы хотите проанализировать все это JSON, вы можете сделать это:

//In my case, I'm using SwiftyJSON
import SwiftyJSON

class Program {
  let name: String
  let state: States

  init(from json: JSON) {
    guard 
      let name = json["programName"].string,
      let state = States(rawValue: json["programState"].string ?? "")
      else { return nil }
    self.name = name
    self.state = state
  }
}

Затем вы должны сопоставить свой ответ с Program:


let response: JSON = ... //get response

guard let program = Program(from: response) else { return }

//use program.
myImageView.image = program.state.image
...