Closed12

Swift Catch-Up Note

Koki IbukuroKoki Ibukuro

最新のSwift 言語仕様

https://docs.swift.org/swift-book/LanguageGuide/TheBasics.html

SwiftUI

新しくやるならSwiftUIかな〜。ということで、ひとまず公式チュートリアルを全部流し見するのが、一番手っ取り早いかと。
https://developer.apple.com/tutorials/swiftui

https://blog.devgenius.io/implementing-ar-in-swiftui-without-storyboards-ec529ace7ab2

逆引きTIPS

  • Status Barを消す
// ルートのエレメントで
.statusBar(hidden: true)
  • ちっこいスペーサー
Spacer()
    .frame(height: 20)
  • ターゲットネームで処理を変える
var plistFileName = Bundle.main.infoDictionary?["CFBundleName"]
  • ターゲットごとに #if HOGEHOGE なdifineを置きたい

Build Setting → 表示レベルを Allにして、Other Swift Flagsを検索窓から探す。
目的のターゲットに -D HOGEHOGE を追加する。
from stackoverflow

  • JSONファイルから読み込み
import Foundation

var landmarks: [Landmark] = load("landmarkData.json")

func load<T: Decodable>(_ filename: String) -> T {
    let data: Data

    guard let file = Bundle.main.url(forResource: filename, withExtension: nil)
    else {
        fatalError("Couldn't find \(filename) in main bundle.")
    }

    do {
        data = try Data(contentsOf: file)
    } catch {
        fatalError("Couldn't load \(filename) from main bundle:\n\(error)")
    }

    do {
        let decoder = JSONDecoder()
        return try decoder.decode(T.self, from: data)
    } catch {
        fatalError("Couldn't parse \(filename) as \(T.self):\n\(error)")
    }
}
  • 表示されたときになんかコード実行
View()
    .onAppear {
        // run swift code
    }
  • 複数デバイスで同時にプレビュー
static var previews: some View {
        ForEach(["iPhone SE (2nd generation)", "iPhone XS Max"], id: \.self) { deviceName in
            LandmarkList()
                .previewDevice(PreviewDevice(rawValue: deviceName))
                .previewDisplayName(deviceName)
        }
    }
  • システムデフォルトのアイコンはここにたくさんあるよ。自分でデザインしないでもsystemNameで指定すれば勝手に出るよ。

https://developer.apple.com/sf-symbols/

Image(systemName: "star.fill")
     .foregroundColor(.yellow)
  • データバインディングは

ObservableObject
@Published
@EnvironmentObject

あたりのキーワードでググりつつ、この記事を見直す。
https://developer.apple.com/tutorials/swiftui/handling-user-input

Toggle(isOn: $showFavoritesOnly)
  • SwiftUIのViewの中にUIViewControllerを置く

https://developer.apple.com/tutorials/swiftui/handling-user-input

  • SwiftUIでhome buttonを非表示にするのは大変っぽい。

Hackだけど、これが一番簡単そう。
https://thwork.net/2022/03/19/swiftui_homeindicatorautohidden/

iOS16からは

Text("Goodbye home indicator, the multitask indicator on iPad, and more.")
    .persistentSystemOverlays(.hidden)

これができるぽい

  • Activity Indicator てきなやつ

ProgressView

  • SwiftUIのViewに対して、参照を持つ

https://www.hackingwithswift.com/quick-start/swiftui/how-to-store-views-as-properties

  • 色々ある@の違いについて…。わからん。

@State
@StateObject
@ObservedObject
@EnvironmentObject

https://www.hackingwithswift.com/quick-start/swiftui/whats-the-difference-between-observedobject-state-and-environmentobject

  • AppDelegateのイベントをフックしたい。

https://www.hackingwithswift.com/quick-start/swiftui/how-to-add-an-appdelegate-to-a-swiftui-app

class AppDelegate: NSObject, UIApplicationDelegate {
    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey : Any]? = nil) -> Bool {
        print("Your code here")
        return true
    }
}

@main
struct Testing_SwiftUI2App: App {

    // inject into SwiftUI life-cycle via adaptor !!!
    @UIApplicationDelegateAdaptor(AppDelegate.self) var appDelegate

    var body: some Scene {
        WindowGroup {
            ContentView()
        }
    }
}
  • 画像をURLからダウンロード

iOS15からはAsyncImageってのが使える。

https://developer.apple.com/documentation/swiftui/asyncimage

https://www.hackingwithswift.com/quick-start/swiftui/how-to-load-a-remote-image-from-a-url

  • ダークモード対応したくない!

UIUserInterfaceStyleをinfo.plistに入れる。

https://stackoverflow.com/questions/56537855/is-it-possible-to-opt-out-of-dark-mode-on-ios-13

  • Async Await をパラレルで動かす。

https://developer.apple.com/documentation/swift/withtaskgroup(of:returning:body:)
https://www.donnywals.com/running-tasks-in-parallel-with-swift-concurrencys-task-groups/

  • Singleton
class Singleton {
    static let shared: Singleton = {
        let instance = Singleton()
        // setup code
        return instance
    }()
}
  • SwiftUI作ってるときに "Extra argument in call" error

SwiftUIでは10個以上のコンポーネントを直列にならべることができないらしい。

グループ化すれば大丈夫。

https://stackoverflow.com/questions/61178868/swiftui-random-extra-argument-in-call-error

  • Info.plist のローカライズ

https://stackoverflow.com/questions/25736700/how-to-localise-a-string-inside-the-ios-info-plist-file

  • @Stateの変更を受け取る

https://developer.apple.com/documentation/swiftui/view/onchange(of:perform:)

struct PlayerView: View {
    var episode: Episode
    @State private var playState: PlayState = .paused

    var body: some View {
        VStack {
            Text(episode.title)
            Text(episode.showTitle)
            PlayButton(playState: $playState)
        }
        .onChange(of: playState) { [playState] newState in
            model.playStateDidChange(from: playState, to: newState)
        }
    }
}

Koki IbukuroKoki Ibukuro

Xcode Cloud. 2023年12月まで無料らしいんで、試してみたけど、これはまだβ版の香りがプンプンする謎挙動が多いので、GitHub Actionsの方が正解かもな。

https://developer.apple.com/xcode-cloud/

追記:一個一個みてくとエラー自体は解決可能。Web上に情報が少ないので辛みはあります。

このスクラップは2022/09/23にクローズされました