当我在更新观察到的对象时遇到了一些问题,我跟随了this lecture.我有一个@ObservedObject
,叫做EmojiMemoryGame
,有一个MemoryGame<String>
变量,叫做model
."MemoryGame是一个存储一系列卡片的 struct ,每个卡片都有一个Bool
变量,用于存储卡片是否正面朝上.
My ContentView
是一个在屏幕上显示网格中每张卡的视图.当用户点击卡时,viewModel.choose(card)
切换卡的isFaceUp
变量;问题是,这不会导致卡在屏幕上翻转.这是我在ContentView.swift
中的代码:
struct ContentView: View {
@ObservedObject var viewModel: EmojiMemoryGame
var body: some View {
ScrollView {
LazyVGrid(columns: [GridItem(.adaptive(minimum: 89))]) {
ForEach(viewModel.cards) { card in
CardView(card: card)
.aspectRatio(2/3, contentMode: .fit)
.onTapGesture {
viewModel.choose(card)
}
}
}
}
.foregroundColor(.red)
.padding(.horizontal)
}
}
struct CardView: View {
let card: MemoryGame<String>.Card
var body: some View {
ZStack {
let shape = RoundedRectangle(cornerRadius: 20)
if card.isFaceUp {
shape
.fill()
.foregroundColor(.white)
shape
.strokeBorder(lineWidth: 3)
Text(card.content)
.font(.largeTitle)
} else {
shape
.fill()
}
}
}
}
然而,如果我只是将CardView
中的代码直接复制/粘贴到ContentView
的主体中(见下文),那么代码就会像预期的那样工作,因此我不确定这里到底发生了什么.
struct ContentView: View {
@ObservedObject var viewModel: EmojiMemoryGame
var body: some View {
ScrollView {
LazyVGrid(columns: [GridItem(.adaptive(minimum: 89))]) {
ForEach(viewModel.cards) { card in
ZStack {
let shape = RoundedRectangle(cornerRadius: 20)
if card.isFaceUp {
shape
.fill()
.foregroundColor(.white)
shape
.strokeBorder(lineWidth: 3)
Text(card.content)
.font(.largeTitle)
} else {
shape
.fill()
}
}
.aspectRatio(2/3, contentMode: .fit)
.onTapGesture {
viewModel.choose(card)
}
}
}
}
.foregroundColor(.red)
.padding(.horizontal)
}
}
编辑:这是我的EmojiMemoryGame.swift
:
class EmojiMemoryGame: ObservableObject {
static let emojis = ["????", "????", "????????️", "????", "????", "????", "????", "????", "????", "????", "????", "????", "????", "????", "????", "????????", "????", "????", "????", "????"]
static func createMemoryGame() -> MemoryGame<String> {
MemoryGame<String>(numberOfPairsOfCards: 4) { pairIndex in
emojis[pairIndex]
}
}
@Published var model: MemoryGame<String> = createMemoryGame()
var cards: Array<MemoryGame<String>.Card> {
return model.cards
}
func choose(_ card: MemoryGame<String>.Card) {
model.choose(card)
}
}
和MemoryGame.swift
:
struct MemoryGame<CardContent> where CardContent: Equatable {
struct Card: Identifiable, Equatable {
var isFaceUp: Bool = false
var isMatched: Bool = false
var content: CardContent
var id: Int
static func == (lhs: MemoryGame<CardContent>.Card, rhs: MemoryGame<CardContent>.Card) -> Bool {
lhs.id == rhs.id
}
}
private(set) var cards: Array<Card>
init(numberOfPairsOfCards: Int, createCardContent: (Int) -> CardContent) {
cards = Array<Card>()
// add numberOfPairsOfCards * 2 cards to cards array
for pairIndex in 0..<numberOfPairsOfCards {
let content: CardContent = createCardContent(pairIndex)
cards.append(Card(content: content, id: pairIndex*2))
cards.append(Card(content: content, id: pairIndex*2 + 1))
}
}
mutating func choose(_ card: Card) {
let chosenIndex = cards.firstIndex(of: card)
cards[chosenIndex!].isFaceUp.toggle()
}
}