Swift

Swiftに関するページ
Task.initのクロージャーに[weak self]はいらない。Task.detachedとTaskGroup.addTaskも同様
iOS

Task.initのクロージャーに[weak self]はいらない。Task.detachedとTaskGroup.addTaskも同様

2022年7月29日、インプレスR&D社よりSwift Concurrencyの解説本をリリースしました。 こちらの本は一冊でSwift Concurrencyの機能をほぼ網羅したConcurrency機能の解説本です。 日本語でSwift Concurrencyを学べる解説本はまだ少ないので、Swift 5.5からの非同期処理をうまく書きたい方には必見の本となっています。 さて、せっかくリリースしたばかりなのですが、一部のサンプルコードがあまり良いコードではありませんでした。 すでにサンプルコードのリポジトリは修正済みですが、どのような修正があったのかをこの記事で説明したいと思います。
12 min read
Swift 5.5からのSwift  Concurrencyのasync/awaitの使い方
iOS

Swift 5.5からのSwift Concurrencyのasync/awaitの使い方

Swift 5.5からはSwiftの言語機能としてConcurrencyが登場しました。 これは非同期処理、並行処理のコードを簡潔かつ安全に記述できる機能です。 async/awaitを使えば、同期処理と同じような書き方で非同期処理を記述できます。 またactor型を使えばデータ競合を防ぐことができます。 この記事ではSwift 5.5からのSwift Concurrencyの機能の一つ`async/await`の使い方を解説します。
10 min read
Swift PlaygroundでConcurrencyを使う by Xcode 13.2.1
iOS

Swift PlaygroundでConcurrencyを使う by Xcode 13.2.1

Swift 5.5で登場したSwift Concurrency。 async/awaitを使うことで、並列処理を上から下に流れるように記述することができます。 どんな風に使えるかをSwift Playgroundで試そうとしたところ、Swift Playgroundではいろいろ制限があるようなのでまとめました。 検証環境 * Xcode 13.2.1 * Swift 5.5 _Concurrencyをインポートする Swift Concurrencyの機能をSwift Playgroundで使う場合、まず最初にすることは _Concurrency というフレームワークをインポートすることです。 明示的にインポートしないでConcurrencyの型を実行すると「スコープにそんな型は見つからない」とエラーになります。 手元ではコンパイルエラーにはならず、実行時にエラーが表示されました。 例えば_ConcurrencyをインポートしないでTaskを実行します。 Task.detached {} するとデバックエリアにこのようなエラーが出力されます。 error: reque
2 min read
iOS 15でNavigationBarとTabBarがデフォルトで透過される
iOS

iOS 15でNavigationBarとTabBarがデフォルトで透過される

iOS 15をXcode 13以上で開発していたところ、NavigationBarとTabBarの背景が透過されていることがわかりました。 どうやらXcode 13でビルドをした場合、iOS 15のNavigationBarとTabBarはデフォルトで背景が透過されるようです。 私のアプリでは透過ではなく、iOS 14以前と同じように背景色をつけたかったので、どう修正するのかを調べました。 開発環境 * Xcode 13.2 * iOS 15.2 NavigationBarをiOS 14以前と同じ見た目にする 背景色が透過されるようになった原因 UINavigationBarにはscrollEdgeAppearanceというプロパティがあります。 UINavigationBarAppearanceというNavigationBarの外観設定を司るクラスのインスタンスです。 Navigation ControllerがNavigation BarとScroll Viewを持っている場合で、Scroll Viewのコンテンツの端がNavigation
3 min read
VNDetectRectanglesRequestのminimumSizeについて
iOS

VNDetectRectanglesRequestのminimumSizeについて

Visionフレームワークを触っていてわからなかったことがあります。 VNDetectRectanglesRequestのminimumSizeプロパティの意味です。 minimumSizeプロパティは検出する矩形の最小サイズを指定するプロパティです。 分析する画像の矩形が指定したものよりも小さければ、分析処理をしません。 多くの矩形を分析する際は処理を軽くするために指定すると良いものです。 デフォルトが0.2になっており、0.0から1.0の値が指定できます。 let request = VNDetectRectanglesRequest() request.minimumSize = 0.2 ただこの数値の意味がわからないのです。 ドキュメント [https://developer.apple.com/documentation/vision/vndetectrectanglesrequest/2875374-minimumsize] にはこう書かれています。 > The minimum size of a rectangle to detect, as a propor
3 min read
[SwiftUI] GeometryReaderでメソッド/関数を実行したい!
iOS

[SwiftUI] GeometryReaderでメソッド/関数を実行したい!

実行環境 * Xcode 12.5 GeometryReaderでViewのサイズを取得する [SwiftUI] GeometryReaderでViewのサイズを知る [https://blog.personal-factory.com/2019/12/08/how-to-know-coorginate-space-by-geometryreader/] で解説したとおり、SwiftUIでViewのサイズを取得するにはGeometryReaderを使います。 GeometryReaderのハンドラーから渡されるGeometryProxyのインスタンスでViewのサイズがわかります。 struct LocalVariableView: View { var body: some View { GeometryReader { proxy in Text("\(proxy.frame(in: .local).debugDescription)") } } } struct LocalVariableView_
2 min read
[2021年版]XcodegenでCarthageとCocoapodsを使う最小プロジェクトを作成
iOS

[2021年版]XcodegenでCarthageとCocoapodsを使う最小プロジェクトを作成

個人アプリのプロジェクト構成をXcodegenで作り直そうかと思っています。 個人アプリはライブラリーの依存関係をCarthageとCocoapodsを使って管理していますが、Xcodegenではどういう記述でproject.ymlを書けばいいのかが検討つきませんでした。 理解を深めるために最小プロジェクトを作ることにしました。 この記事ではXcodegenでCarthageとCocoapodsを使う最小プロジェクトを解説します。 実行環境 * Xcode 12.4 * Xcodegen * Carthage: 0.37.0 * Cocoapods: ディレクトリ 今回はTryXcodegen という名前のプロジェクトを作成して、CarthageとCocoapodsでライブラリーを管理し、プロジェクト生成にXcodegenを利用します。 最終的なディレクトリ構造は次のとおりです。 主要なもののみ掲載しています。 $ tree -L 2 . ├── Cartfile ├── Cartfile.resolved ├── Carthage │ ├── Build ├
3 min read
CarthageのXcode 12エラー: This usually indicates that project itself failed to compile.を直す
iOS

CarthageのXcode 12エラー: This usually indicates that project itself failed to compile.を直す

Xcode 12でCarthageでライブラリーをビルドしようとしたら、ビルドが失敗して以下のようなエラーを出力されました。 Carthageのバージョンは0.36.0で試しています。 This usually indicates that project itself failed to compile. Please check the xcodebuild log for more details: /var/folders/jm/pyy6p95j177_btm91tj0mkdm0000gn/T/carthage-xcodebuild.WPi9jL.log > このエラーは下記issuesから引用 https://github.com/Carthage/Carthage/issues/3019 実行環境 * Xcode 12.4 * Carthage: 0.36.0 -> 0.
2 min read
Clubhouseのスーパー楕円をSwiftUIで作る
iOS

Clubhouseのスーパー楕円をSwiftUIで作る

近年流行りだした音声SNS, Clubhouse [https://www.joinclubhouse.com/]。 デザインの特徴の1つにふわっとした丸みを帯びた楕円のアイコンがあります。 これは「スーパー楕円」と言われているそうです。 丸よりも丸みを感じる!? スーパー楕円の魅力とデザイン | Spinners Inc. [https://www.spinners.work/posts/kudakurage-superellipse-desgin/] この楕円を@tokorom [https://twitter.com/tokorom]さんがUIKitで実装してました。 スーパー楕円UIをiOS+Swiftで実装する | Spinners Inc. [https://spinners.work/posts/swift-superellipse/] この記事を読んでSwiftUIでも作りたくなったので、作ってみます。 実行環境 * Xcode 12.2 * iOS 14.2 実装方針 tokoromさんと同じようにもと記事 [https://www.spinner
4 min read
SwiftUIで開閉式メニューの作り方
iOS

SwiftUIで開閉式メニューの作り方

SwiftUIで下からニュッと表示する開閉式メニューの作り方を解説します。 > この記事は私が2020年12月22日に発表した資料、 「SwiftUIで作る開閉式メニュー [https://speakerdeck.com/satotakeshi/swiftuidezuo-rukai-bi-shi-meniyu] 」を記事化したものです。 動作環境 この記事は以下の環境で動作を確認しています。 * Xcode 12.2 * iOS 14.2 開閉式メニューを作ろう 今回作る開閉式メニューの動きをgifでみてみましょう。 親Viewを作る まずは親Viewを作りましょう。 struct ContentView: View { @State var isShowMenu = false var body: some View { ZStack { Button(action: { withAnimation { isShowMenu.toggl
4 min read
SwiftUIのデータ管理 Single Source of Truth編
iOS

SwiftUIのデータ管理 Single Source of Truth編

SwiftUIでアプリを開発していると@Stateや@Bindingの使い分けについて迷ったりしていませんか? SwiftUIではデータを管理するProperty Wrapperがたくさんあります。 @State、@Binding、@StateObject、@ObservedObjectなどなどです。 Property Wrapperそれぞれの特徴を理解できれば、SwiftUIのアプリ開発がはかどるでしょう。 今回はSwiftUIのデータ管理に欠かせないSingle Source of Truthという考え方について解説します。
3 min read
UITableViewをコードで実装する最速の方法
iOS

UITableViewをコードで実装する最速の方法

UITableViewでリスト表示を実装するさい、よくやるやり方は、StoryboardやXibファイルでCellを作って、そのidentifierをView Controllerで指定する方法です。 ですが、UITableViewCell標準の表示で十分な場合にファイルが分かれるのは面倒です。 なんとかコードで済ます方法がないかと探したらありましたのでご紹介します。
2 min read
[iOS 14]WidgetでDeep Link作成
iOS

[iOS 14]WidgetでDeep Link作成

iOS 14からWidgetという機能が登場しました。これはアプリを起動しなくてもHome画面にアプリ情報をユーザーに届けられる機能です。 今回はWidgetをタップした時に特定のアプリ画面が開けるようにする、Deep Linkの作成方法について解説します。 検証環境 * Xcode 12.2 * iOS 14.2 WidgetとDeep Link Widgetをタップすると何も実装しなければ、本体アプリが起動されます。 しかし、Widgetに表示されているコンテンツと関連した画面に遷移できればユーザー体験が向上します。 そのためにはWidgetにDeep Linkを作る必要があります。 Widgetのサイズとリンクの数について まず最初にWidgetのサイズとリンクの数についてお話します。 開発者が作れるWidgetの大きさはSmall, Medium, largeの3つです。 実はWidgetはサイズによっておけるリンクの数が決まっています。 Smallサイズはひとつだけで、MediumサイズとLargeサイズは複数置くことができます。 例えば、Appleの
3 min read
[iOS 14] Widgetでカウントダウン
iOS

[iOS 14] Widgetでカウントダウン

WidgetのViewを更新するにはTimelineProviderプロトコルのgetTimelineメソッドを実装してタイムラインという何時何分にどんなデータでViewを更新するのかをあらかじめWidgetKitに伝える必要があります。 Todoアプリなどでイベントをカウントダウン表示したい場合を想定します。 毎秒更新するようにタイムラインを作成すればうまくいくかと思いきや、各アプリによってWidgetを更新できる回数は決まっています。 TimelineProviderのドキュメントにはこう書かれています。 > Each configured widget receives a limited number of refreshes every day. Several factors affect how many refreshes a widget receives, such as whether the containing app is running in the foreground or background, how frequently the widge
2 min read
iOS

[SwiftUI]半透明の色を設定する

検証環境 * Xcode 11.6 * iOS 13.6 半透明の色を設定する Colorに.opacity修飾子メソッドを実行すると色の透明度を設定することができます。 Rectangle() .foregroundColor(Color.black.opacity(0.5)) 50%の透明度で指定しています。 キャプチャはこちら。 20%ぐらいだとこのぐらい。 .foregroundColor(Color.black.opacity(0.2)) 100%だとこのぐらいの色になります。 .foregroundColor(Color.black.opacity(1)) まとめ 背景色などを半透明にしたいなと思ったときに.opacityは使えそうです。 宣伝 インプレスR&D社より、「1人でアプリを作る人を支えるSwiftUI開発レシピ」発売中です。 「SwiftUIでアプリを作る!」をコンセプトにSwiftUI自体の解説とそれを組み合わせた豊富なサンプルアプリでどんな風にアプリ実装すればいいかが理解できる本となっています。 iOS 14対
1 min read
[SwiftUI]選択可能なUIコンポーネントの作り方【ラジオボタン偏】
iOS

[SwiftUI]選択可能なUIコンポーネントの作り方【ラジオボタン偏】

前回 [SwiftUI]選択可能なUIコンポーネントの作り方【複数選択偏】 [https://blog.personal-factory.com/2020/07/11/how-to-create-selectable-ui-component-by-swiftui-in-multiple/] で複数選択ができるUIコンポーネントをSwiftUIで作る方法を解説しました。 今回はHTMLのラジオボタンのように複数あるViewの内一つのみ選択するコンポーネントを作ってみます。 まずは動きをみていきましょう。 赤、緑、青のビューがあって、赤をタップすると黒枠が追加されて選択状態ということがわかります。デバックエリアにも「selected box is red」と出力されます。 他のビュー、例えば緑をタップすると、赤のビューの黒枠は消えて、緑のビューが黒枠でおおわれるようになるというしだいです。 選択するViewのタイプを定義 ユーザーが何を選択したかを判定できるようにBoxTypeというenumを定義します。 enum BoxType: String { case unkn
4 min read
[SwiftUI]選択可能なUIコンポーネントの作り方【複数選択偏】
iOS

[SwiftUI]選択可能なUIコンポーネントの作り方【複数選択偏】

人はときにタップをしたらそのビューを選択状態にするコンポーネントが必要になることがあります。 ちょっと手こずったのでブログに作り方を残します。 今回は複数選択する場合を解説したいと思います。 実行環境 * Xcode 11.5 * iOS 13.5 複数選択可能なUIコンポーネント HTMLだとチェックボックスがいい例ですが、複数選択できるコンポーネントがあると素敵ですよね。 作ってみましょう。 赤、緑、青のViewがあって、タップするとViewに黒枠が追加されて選択状態がわかるようになります。 またコンソールにもタップされたら「red is selected」 。もう一度タップすると「red is not selected」というようなメッセージができるようにしています。 ViewModelの定義 まずはデータまわりを定義していきましょう。 MultipleSelectableViewModelというクラスを定義します。 final class MultipleSelectableViewModel: ObservableObject { @Publish
4 min read
【WWDC20】Introduction to SwiftUI の雑メモ
Swift

【WWDC20】Introduction to SwiftUI の雑メモ

WWDC20のIntroduction to SwiftUIをみました。 雑にメモを残そうと思います。 https://developer.apple.com/wwdc20/10119 * ライブラリーからdrop and dragでViewコンポーネントをeditorに入れられる * ライブラリーペインからcornerRadius modifierをキャンバスに落とす * コードに追加される * previewのresumeショートカット * ⌘+option+P * Extract Subviews * View実装が大きくなったとき使う。追加でViewのレイアウトを増やしたい。でもすでにたくさん実装していてコードが大きくなっている。 * Extract Subviewsを使ってViewを新しい型に切り分けることができる * spacer、スペースが可能な領域までできるだけ広がる。 * テキストを真ん中によせるために今回は使った。 * Detai
4 min read
【Swift Argument Parser入門】Swiftでコマンドラインツールを作る
Swift

【Swift Argument Parser入門】Swiftでコマンドラインツールを作る

2020年2月、AppleがSwift向けライブラリーArgumentParserをリリースしました。 これはSwiftでコマンドラインツールを作る際にコマンド引数を簡単に扱えるライブラリーです。 CarthageやXcodeGenなどSwift製のコマンドラインツールはたくさんありますが、いざ自分で作ろうと思ったときにこのライブラリーが役に立ちます。 この記事ではArgumentParserの使い方を解説します。 Swiftでコマンドラインツールを作成した方にぴったりの記事です。
11 min read
SwiftUIアプリをVIPERアーキテクチャーで作り画面遷移処理をまとめる
iOS

SwiftUIアプリをVIPERアーキテクチャーで作り画面遷移処理をまとめる

この記事では画面遷移処理をView実装から引き剥がす方法としてVIPERアーキテクチャを解説し、実際にSwiftUIアプリケーションに適応します。 ログイン画面やNavigation ViewのPush遷移, Tab Bar表示、アラートやモーダル表示など、アプリケーションで利用する画面遷移処理をどう扱うかをみていきましょう。
10 min read