見出し画像

スタンフォード式iOSアプリ開発講座の宿題もやってみた①

レクチャー2にはハンズオン講座以外に、プログラミング課題もあったので実践しました。このページでは、実践した内容を振り返りたいと思います。

プログラミング課題の内容

課題は全部で10のステップになっています。

1. レクチャー1と2で示したように、Memorizeゲームを動作させます。
どこかからコピー&ペーストせずに、すべてのコードを入力してください。

2. 画面下の⊖と⊕のボタンを外します。

3. 画面上部に「Memorize!(記憶せよ)」というタイトルを追加します。

4. タップすると、すべてのカードが選択したテーマに合った絵文字を含む新しいカードに入れ替わるようにする「テーマ選択」ボタンを、少なくとも3つUIに追加します。
テーマの1つとして、講義で使用した車両を使用しても構いませんが、全く新しいテーマを作成しても構いません。

5. 各テーマに含まれるカードは、8枚以下であってはいけません。

6. テーマボタンを押したときに表示されるカードは、ランダムな順番になっていること。
つまり、テーマを選ぶたびにカードがシャッフルされるようにします。

7. テーマボタンには、「テーマを表す画像」と「テーマを説明するテキスト」が縦に重ねて表示されること。

8. テーマボタンの画像部分に、テーマを連想させるSFシンボルを使用します。

9. テーマボタンの説明文に、「カードの絵文字に使用したフォント」よりも小さいサイズを使用します。

10. どのiPhoneでも、縦と横で動作するUIであることを確認します。

すべてのステップは、レクチャー1と2の内容を理解していることが前提となっているようです。順を追って実装していけば、それほど難しくはありませんでした。

完成したコード全体

課題には、「コードを上手に記述することは意識しなくても良い」というアドバイスがありました。まだ、講座の序盤なので、後から学ぶべきスキルだからでしょう。
すべてのステップを実装したコードは、以下のようになりました。

import SwiftUI

struct ContentView: View {
   let faces    = ["😀", "😅", "🥲", "😊", "😎", "😍", "😡", "🥺", "🥶", "🤮"]
   let animals  = ["🐶", "🐹", "🐻", "🐨", "🐯", "🐼", "🐵", "🦁"]
   let vehicles = ["🚗", "🚌", "🏎", "🚓", "🚕", "🚒", "🚛", "🚜",
                   "🚍", "🚡", "🚟", "🚃", "🚞", "🚝", "🚄", "🚅",
                   "✈️", "🛰", "🛩", "🚀", "🛸", "⛵️", "🛶", "🚤"]
   
   @State var emojis = ["🚗", "🚌", "🏎", "🚓", "🚕", "🚒", "🚛", "🚜",
                        "🚍", "🚡", "🚟", "🚃", "🚞", "🚝", "🚄", "🚅",
                        "✈️", "🛰", "🛩", "🚀", "🛸", "⛵️", "🛶", "🚤"]
   @State var emojiCount = 20
   
   var body: some View {
       VStack {
           Text("Memorize!")
               .font(.largeTitle)
               .fontWeight(.bold)
           ScrollView {
               LazyVGrid(columns: [GridItem(.adaptive(minimum: 65.0))]) {
                   ForEach(emojis[0..<emojiCount], id: \.self) { emoji in
                       CardView(content: emoji)
                           .aspectRatio(2/3, contentMode: .fit)
                   }
               }
           }
           .foregroundColor(.red)
           Spacer()
           HStack {
               Spacer()
               theme1
               Spacer()
               theme2
               Spacer()
               theme3
               Spacer()
           }
           .font(.largeTitle)
           .padding(.horizontal)
       }
       .padding(.horizontal)
   }
       
   var theme1: some View {
       Button(action: {
           emojiCount = vehicles.count
           emojis = vehicles.shuffled()
       }, label: {
           VStack {
                Image(systemName: "car")
                Text("Vehicles")
                    .font(.subheadline)
            }
       })
    }
   
   var theme2: some View {
       Button(action: {
           emojiCount = faces.count
           emojis = faces.shuffled()
       }, label: {
           VStack {
               Image(systemName: "face.smiling")
               Text("Faces")
                   .font(.subheadline)
           }
       })
   }
   
   var theme3: some View {
       Button(action: {
           emojiCount = animals.count
           emojis = animals.shuffled()
       }, label: {
           VStack {
               Image(systemName: "hare")
               Text("Animals")
                   .font(.subheadline)
           }
       })
   }
}

struct CardView: View {
   var content: String
   @State var isFaceUp: Bool = true
   
   var body: some View {
       ZStack {
           let shape = RoundedRectangle(cornerRadius: 20.0)
           if isFaceUp {
               shape.fill().foregroundColor(.white)
               shape.strokeBorder(lineWidth: 3.0)
               Text(content).font(.largeTitle)
           } else {
               shape.fill()
           }
       }
       .onTapGesture {
           isFaceUp = !isFaceUp
       }
   }
}
struct ContentView_Previews: PreviewProvider {
   static var previews: some View {
       ContentView()
   }
}




いいなと思ったら応援しよう!