20210728のSwiftに関する記事は9件です。

横にスクロールするUICollectionViewのCell

完成形はこちら 機能説明 横にスライドするUICollectionViewのCellをタップすると色がUIColor.systemTealに変わります。 コードと簡単説明 collectionViewを横にスライドできるようにするには、UICollectionViewFlowLayout()のインスタンス.scrollDirection = .horizontalを設定します。 今回は、UICollectionViewのCellをタッチした時の処理を追加しています。その為には、func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {}を使用します。 ViewController import UIKit class ViewController: UIViewController { @IBOutlet weak var collectionView: UICollectionView! let collectionViewFlowLayout = UICollectionViewFlowLayout() //インスタンス作成 override func viewDidLoad() { super.viewDidLoad() collectionView.delegate = self collectionView.dataSource = self } override func viewWillAppear(_ animated: Bool) { super.viewWillAppear(animated) collectionViewFlowLayout.sectionInset = UIEdgeInsets(top: 5, left: 5, bottom: 5, right: 5) collectionViewFlowLayout.scrollDirection = .horizontal //ここで、横にスクロールに変更してます collectionView.collectionViewLayout = collectionViewFlowLayout } } extension ViewController: UICollectionViewDelegate,UICollectionViewDataSource,UICollectionViewDelegateFlowLayout{ func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return 10 } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "Cell", for: indexPath) return cell } func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { return CGSize(width: collectionView.frame.size.width / 4 - 10, height: collectionView.frame.size.width / 4 - 10) } func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) { let selectCell = collectionView.cellForItem(at: indexPath)! selectCell.backgroundColor = UIColor.systemTeal } } 終わり 最近、長くなったif文を短く出来ないか、考えるのが楽しくて楽しくて。 ご指摘、ご質問などありましたら、コメントまでお願い致します。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

swift Custom Keyboard Extension

自分用メモです カスタムキーボードを作成する際に躓いたポイントを忘れないように残しておきます 躓きポイント ios14.3に統一 Bundle Identiferを「com.〜」にする 参考になる記事
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

swift カスタムキーボード

自分用メモです カスタムキーボードを作成する際に躓いたポイントを忘れないように残しておきます 躓きポイント ios14.3に統一 Bundle Identiferを「com.〜」にする 参考になる記事
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Swift メモリ管理

Swiftのメモリ管理 Swiftはメモリ管理する際はARC(Automatic Reference Counting)という方法になっている. ARCとは オブジェクトが他のオブジェクトから参照されている数を参照カウントとしてゲットしてきて、この参照カウントを追跡してインスタンスを解放をするかどうか判断する。 この参照カウントが一つでもあるとオブジェクトが破棄されることはなくインスタンスは解放されない。 0になった際にオブジェクトは破棄されてガーベジコレクタにいく。 Swiftではオブジェクトが参照した際はデフォルトで強参照になっている。 解放されたかどうかを確かめるには deinitを使用する。解放されたprintされる。 書き方 class Fish { var name: String init(name: String) { self.name = name } // デイニシャライザを定義する deinit { print("deinit!") } } 強参照の循環、循環参照 参照型同士のオブジェクトが参照しあっていると循環参照になり、参照カウントが絶対に1にならないようになってしまう。 class Fish { var animal: Animal? init() {} deinit { print("Fishクラスのインスタンスが解放されました") } } class Animal { var fish: Fish? init() {} deinit { print("Animalクラスのインスタンスが解放されました") } } AnimalクラスとFishクラスが参照しあっているため、どんなに少なくても参照カウントが1となり、メモリが解放されることはなくなってしまう。 また循環参照は別名、強参照の循環とも言われる。 循環参照の解決 手段は2つ 1weak(storyboardでよくみるあれ) 2unowned class Fish { // 弱参照させる weak var animal: Animal? init() {} deinit { print("Fishクラスのインスタンスが解放されました") } } var、letの前にweakをつけることで弱参照にし、参照カウント煮含めないようにする。参照しあっているオブジェクトが他にいなければカウントがゼロになり解放される。 weakに対してunownedはクラスがオプショナル型ではなくnilであることを許容しない場合に使う。 class Fish { var animal: Animal? init() {} deinit { print("Fishクラスのインスタンスが解放されました") } } class Animal { unowned var fish: Fish//nilを許容しない init() {} deinit { print("Animalクラスのインスタンスが解放されました") } } クロージャー内の循環参照 クロージャーもインスタンスなのでクロージャー内でインスタンスを利用する場合は循環参照になる class Animal { let name: String init(name: String) { self.name = name } lazy var getInfo: () -> String = { [weak self] in return "\(self.name)" // selfの参照カウントが+1になり解放されない } } Animal→getInfo,getInfo→Animal(self)で循環参照してしまっていたため[weak self]をつける(キャプチャリストという)ことで弱参照にできる。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Swift】mutatingとは

概要 mutatingは構造体のストアドプロパティの値を変更する為に、再代入することを示す明示的なキーワードです。その為参照型であるクラスには使用せず、再代入を必要とする値型のみに使用します。 使用例 前述した通り、値型である構造体のストアドプロパティに変更を加えるとエラーになります。参照型であるクラスの場合はエラーにはなりません。 struct numberStruct { var number: Int init(number: Int){ self.number = number } func plus() { self.number += 1 // コンパイルエラー } } class numberClass { var number: Int init(number: Int) { self.number = number } func plus() { self.number += 1 // クラスの場合エラーにならない } } mutatingを使用することで値を変更することができます。 struct numberStruct { var number: Int init(number: Int){ self.number = number } mutating func plus() { self.number += 1 } }
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[Swift]SKStoreReviewController.requestReview()がiOS14から非推奨になった件について

SKStoreReviewController.requestReview() レビューをユーザーに促す場合に使われていたコード。 iOS14以降は非推奨となった。 SKStoreReviewController.requestReview() 一行で書けていたのに残念? 公式によると requestReview(in:)を使いなさいとのこと。 iOS14以降の書き方 if let scene = UIApplication.shared.connectedScenes.first as? UIWindowScene { SKStoreReviewController.requestReview(in: scene) } このように書けば良さそう! お知らせ 現在、iOS開発案件を業務委託で募集中です(副業)。TwitterDMご依頼をお待ちしています。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

カスタムフォントはメインターゲットに入れないと反映されない

結論 EmbeddedFrameworkによってターゲットを分けているプロジェクトで カスタムフォントを使用する場合には メインターゲットにフォントファイルを入れなければいけません。 メイン以外のターゲット配下にファイルを入れて、 そのターゲットのinfo.plistにファイルを紐付けても、 使用することはできません。 言いたいことは以上なのですが、FontBookを使ったカスタムフォントの導入方法も備忘のために記述します。 カスタムフォントの導入方法 今回はHiraKakuStdN-W8を追加します。 FontBookから必要なフォントファイルを取得する Xcodeでカスタムフォントを使用するには.ttf、.otf形式のファイルをXcodeに組み込む必要があります。 デフォルトでMacに入っているFontBookを開き、お目当てのHiraKakuStdN-W8はヒラギノ角ゴのW8にあたるので、 それを検索して右クリックするとFinderからフォントファイルの在り処を調べることができます。 FontBook経由でなくてもデフォルトでMacで使えるフォント(例えばBigSurの場合はこちら)は /System/Library/Fonts/配下にあるはずなのでこちらにアクセスしてフォントファイルを取得してきてもOKです。 .ttcを.otfに変換する transfonterを使いました。 アップロードして変換後のファイルをダウンロードするだけです。 新フォントをXcodeに組み込む .otf形式に変換したフォントファイルをメインターゲット配下の任意のフォルダに格納します XcodeのProject > メインターゲットを選択 > Build Phases > Copy Bundle Resources に追加した.otfファイルが追加されていることを確認します(なければ追加してください) info.plistのFonts provided by applicationを追加して、新たに加えたhoge.otfファイルのファイル名を記述します StroyBoard、xibから使用する 上記まで問題なくできていれば普通に使用するだけです。 before after ちなみにメインターゲットに入れていないと、 xib上ではフォントは変更されているのに、実機かシミュレータでは反映されません。 ご注意を。 コードから使用する Xcodeから使用できるフォントはUIFont.familyNamesが持っているので、以下のコードからprintできます。 for family: String in UIFont.familyNames { print(family) for names: String in UIFont.fontNames(forFamilyName: family) { print("== \(names)") } } // 出力(抜粋) // Hiragino Sans // == HiraginoSans-W3 // == HiraginoSans-W6 // == HiraginoSans-W7 // == HiraKakuStdN-W8 もともと入っていたHiraginoSans-W3、HiraginoSans-W6、HiraginoSans-W7に加えて HiraKakuStdN-W8が追加されています また、メインターゲットにフォントファイルが入っていない場合こちらも出力されません。 このfamilyNameを使って以下のようにコードからも設定できます let hirakakuStdW8Font = UIFont(name: "HiraKakuStdN-W8", size: 24)! 結論(再掲) EmbeddedFrameworkによってターゲットを分けているプロジェクトで カスタムフォントを使用する場合には メインターゲットにフォントファイルを入れなければいけません。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

プログラミング言語別文法早見表(基礎)

1.変数 *値を更新できる箱 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 変数名=値 let 変数名=値 var 変数名=直 $変数名=値 例 money=100 let money=100 var money=100 money=100 2.定数 *値を更新できない箱 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 変数と差異なし const 変数名=値 let 変数名=直 $変数名=値4 例 const=100 const tax=100 let tax=100 tax=100 3.四則演算子 *基本的に同じ 四則演算子 項目 + ー × ÷ 余り 書き方 + - * / % 例 price + tax apple - orange price * count price / tax price % tax インクリメント演算子(足し算) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 なし ++; なし $++; 例 なし const y = x++; なし $num++; インクリメント演算子(引き算) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 なし --; なし --; 例 なし const y = x--; なし $num--; 4.配列 配列(記入方法) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 配列名 = [値1, 値2, 値3] 配列名 = [値1, 値2, 値3] 配列名 = [値1, 値2, 値3] 配列名 = [値1, 値2, 値3] 例 array = [1,2,3] const fruits = ['りんご', 'バナナ'] let fruits = ['りんご', 'バナナ'] $fruits = ['りんご', 'バナナ'] 配列(追加方法) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 配列名[順番] = 値 配列名[順番] = 値配列名.push('値') 配列名.append(値) $配列名[] = "値" 例 array[4] = "e" array[4] = "e" list1.append("品川") $stack[] = "ぶどう"; 配列(削除方法) 後で更新 配列(抽出方法) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 配列名[順番] 配列名[順番] 配列名[順番] $配列名[順番] 例 print 配列名[順番] print 配列名[順番] なし print $配列名[順番] 5.配列 ハッシュ 配列(記入方法) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 配列名 = {"キー" => 値,"キー" => 値} 配列名 = ["キー": 値, "キー": 値] $配列名 = ["キー"=> 値, "キー"=> 値]; 例 hash = {"Lemon" => 100, "Orange" => 150} let dictionary = ["りんご": 青森, "バナナ": フィリピン] $hash = ["Lemon" => 100, "Orange" => 150]; 配列(追加方法) 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 配列名[キー] = 値 配列名[キー] = 値 $配列名[キー] = "値" 例 hash["Banana"] = 90 fruits["いちご"] = 300 $stack["フルーツ"] = "ぶどう";  繰り返し文 for 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 for 変数 in オブジェクト do 実行する処理1 end for (初期化式; 条件式; 変化式){ 実行する処理1;} for 変数 in 開始値 ..< 終了値 {実行する処理1} for(初期値; 条件式; 変化式){実行する処理1} 例 for num in 1..3 doprint("num = ", num, "¥n")endprint("End") for (let i = 0; i < 5; i++) { console.log((i + 1) + '回目の処理です');} for i in 1..<10 {print("i: (i)")} for($i=0;$i<5;$i++){echo $i;}  while  関数 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 def メソッドの名前 やりたい処理endメソッドの名前 function 関数名(変数) {やりたい処理}関数名(変数名) func 関数名 (引数1:引数1の型, ...) -> 戻り値の型 {やりたい処理return 戻り値}関数名(変数) function 関数名(変数){処理内容return 返り値関数名(変数名)} 例 def hello puts "Hello World!"endhello function square(number){{return number * number;}] let arrayData = [3, 5, 8, 10]for data in arrayData{print("data: (data)")} <?phpfunction goaisatsu() {$message = 'Hello world!'; return $message;}echo goaisatsu(); ?> 条件分岐 IF 項目 RUBY JAVASCRIPT SWIFT PHP 書き方 if 条件式1 then処理elsif 条件式2 then処理2elsedo 処理3end if (条件式1) {実行1}else if(条件式2){条件式2} if 条件式1 {処理1} else if 条件式2 {条件式2} else {処理3} if(条件){処理1}else{条件が偽であれば実行}else{条件が偽であれば実行} 例 a = 1if a > 3 thenputs "a is greater than 3"end var num = 70;if (num > 80) {console.log("numは80より大きいです。");} else if (num >= 60) {console.log("numは60~80の間です。"); } else {console.log("numは60未満です。");} var num = 5if ( num > 10 ) {print("10以上です")} else if ( num < 10 ) {print("10未満です")} else {print("それ以外");} $score = 90;if($score >= 80){echo “合格です!おめでとうございます!”;}else($score < 80){echo “不合格です!がんばりましょう!”} クラス 項目 RUBY JAVASCRIPT SWIFT PHP 書き方(作成方法) class クラス名{//プロパティの宣言public $変数名 = 値;//メソッドの宣言public function メソッド名(){メソッド内処理...} 書き方(生成方法) $クラスオブジェクト = new クラス名(); 書き方(作成方法) echo $生成->変数名; 例(作成方法) class SampleClass{//プロパティの宣言public $var = 'This is Sample Class.';} 例(生成方法) $sample = new SampleClass(); 例(出力方法) echo $sample->var;
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Could not initialize Amplify: PluginError: Unable to decode configuration

ある日突然、以下のようなエラーが出て、時間を溶かしたのでメモを残します。 Could not initialize Amplify: PluginError: Unable to decode configuration Recovery suggestion: Make sure the plugin configuration is JSONValue 同じようなエラーが発生した人によってissueが立てられていたのですが、Amplifyでpushを忘れているからという理由でした。 amplify statusでのリソースの状態は正しかったため、まさかと思っていたのですが、、 というのも、 こちらの記事を参考にBackend.swiftを作成し、使うリソース(AuthとApi、Storage)をまとめて初期化しています。 Backend.swift import UIKit import Amplify import AmplifyPlugins class Backend { static let shared = Backend() static func initialize() -> Backend { return .shared } private init() { // initialize amplify do { try Amplify.add(plugin: AWSCognitoAuthPlugin()) try Amplify.add(plugin: AWSAPIPlugin(modelRegistration: AmplifyModels())) try Amplify.add(plugin: AWSS3StoragePlugin()) try Amplify.configure() print("Initialized Amplify") } catch { print("Could not initialize Amplify: \(error)") } } } しかし、Amplifyを新しく作り直した際に、Storageはとりあえず使わないから、とaddしていなかった。 にもかかわらず、Backend.swiftでStorageの初期化も行おうとしているためエラーが出ていたようです。 あっちゃあ。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む