どうも、フリーランスのITエンジニア兼ブロガー兼投資家のKerubitoです。
Swiftで「撮影した写真のファイル保存する」アプリを作ってみました。
環境は以下の通りです。
・Swiftバージョン:5
・Xcodeバージョン:11.2.1
・使用デバイス:iPhone8(13.2.2)
プロジェクトの作成
Xcodeを立ち上げ、「Create a new Xcode project」をクリックします。
次はプロジェクトのタイプを選択します。
「Single View Application」をクリックします。
あとはアプリやデベロッパーの名称、言語、対象デバイスを設定します。
カメラ機能の実装
まずは写真を撮影するためのカメラ機能を実装します。
1 2 3 4 5 6 7 | override func viewDidAppear(_ animated: Bool) { super.viewDidAppear(animated) let pc = UIImagePickerController() pc.sourceType = .camera pc.delegate = self present(pc, animated: true, completion: nil) } |
ViewControllerのviewDidAppearにて強制的にカメラを起動しちゃいます。
忘れていけないのは、カメラを使うためにはplistに「Privacy - Camera Usage Description」を追加してやる必要がありますね。
それと撮影完了のdelegateも追加。
1 2 3 4 5 6 7 8 9 | extension ViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate { func imagePickerControllerDidCancel(_ picker: UIImagePickerController) { dismiss(animated: true) } func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) { self.dismiss(animated: true) } } |
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any])が撮影完了時に呼ばれるdelegate。
func imagePickerControllerDidCancel(_ picker: UIImagePickerController) {はキャンセルすると呼ばれます。
UIImageからJpegファイルを生成する
メインの処理であるUIImageからJpegファイルを生成するところを実装します。
1 2 3 4 5 6 7 8 9 10 11 12 | extension UIImage { internal func saveJpegFile (_ path: URL, _ fileName: String) -> Bool{ let jpgImageData = self.jpegData(compressionQuality: 1.0) let fileURL = path.appendingPathComponent(fileName) do { try jpgImageData!.write(to: fileURL) } catch { return false } return true } } |
ここではUIImageのextensionとして実装しています。
let jpgImageData = self.jpegData(compressionQuality: 1.0)
にてUIImageからJpegデータに変換。
try jpgImageData!.write(to: fileURL)
にてJpegデータからファイルを作成しています。
撮影した写真からJpegファイルを作成
最後に写真撮影とJpegファイルの作成を繋げます。
1 2 3 4 5 6 7 8 | func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) { let image = info["UIImagePickerControllerOriginalImage"] as! UIImage let path = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0] let fileName = "sample.jpg" if !image.saveJpegFile(path, fileName) { } self.dismiss(animated: true) } |
撮影完了のdelegate内にてUIImageのsaveJpegFileを呼び出します。
let image = info["UIImagePickerControllerOriginalImage"] as! UIImageでは撮影にて作成されたUIImageを取り出しています。
最終的にはアプリ領域内のdocument直下にsample.jpgとして撮影された写真が保存されます。
全体ソース
最後に全体ソースです。
ViewController.swift
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 | import UIKit class ViewController: UIViewController { override func viewDidLoad() { super.viewDidLoad() // Do any additional setup after loading the view. } override func viewDidAppear(_ animated: Bool) { super.viewDidAppear(animated) let pc = UIImagePickerController() pc.sourceType = .camera pc.delegate = self present(pc, animated: true, completion: nil) } } extension ViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate { func imagePickerControllerDidCancel(_ picker: UIImagePickerController) { dismiss(animated: true) } func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) { let image = info["UIImagePickerControllerOriginalImage"] as! UIImage let path = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0] let fileName = "sample.jpg" if !image.saveJpegFile(path, fileName) { } self.dismiss(animated: true) } } |
UIImageExtensions.swift
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | import Foundation import UIKit extension UIImage { internal func saveJpegFile (_ path: URL, _ fileName: String) -> Bool{ let jpgImageData = self.jpegData(compressionQuality: 1.0) let fileURL = path.appendingPathComponent(fileName) do { try jpgImageData!.write(to: fileURL) } catch { return false } return true } } |
ソースはgithubにもあげていますので試してみたい方は以下からどうぞ。