フリーランスのお仕事まとめ2019
2020年に入って既に10分の1ほど過ぎてしまいましたが、2019年にやったお仕事のまとめです。
機械学習×iOS
- とある有名アプリへの機械学習モデル組み込み実装
- 実稼働中
- 実績公開OKか未確認なので控えておく
- 「まごチャンネル」の子供写真検出
【お仕事】テレビにつなぐだけで子供の写真・動画の専用チャンネルができる「まごチャンネル」に、機械学習で子供の写真を自動で選別してくれる機能ができました🎉
— Shuichi Tsutsumi (@shu223) 2019年10月21日
Core MLモデルへの変換〜機能実装をお手伝いさせていただきました。 pic.twitter.com/54OsmsgrSl
- とある広告案件向けのプロトタイプ
- 個人的には関われてめちゃくちゃ嬉しいし内容もおもしろいのだけどまだまだ公開できない
ARKit, Metal, デプス, カメラ, 画像処理関連
- とある海外のアプリの動画向けエフェクト
- 渡航費や滞在費は先方持ちで1週間海外に滞在
- MetalやARKit 3を用いた動画エフェクトの実装
- とあるカメラアプリへのデプス関連機能実装
- watchOSも使用
- アプリで3Dスキャン -> 3Dプリントデータ作成(プロトタイプ)
- とある雑誌×AR案件(プロト)
- ARKitも他のARライブラリも使わないAR
- とある海外案件でのデプス機能実装(その機能だけを実装したサンプルが成果物)
BLE関連
- とあるIoTプロダクトを利用した実証実験用プロト開発
- とある業界向けソリューションで、別の業界の現場に行けるのは楽しかった
- とあるスマートロック
- BLEのパフォーマンス改善・・・起動〜利用開始までの所要時間が数分の1に短縮された(結局要因はBLEだけではなかったが)
展示系
- ニューヨークのポスター美術館「Poster House」のサイネージ向けmacOSアプリ(BASSDRUM)
ニューヨークの美術館向けに、macOSアプリ開発を担当しました!常設なのでNYCに行く際はぜひ。 / ニューヨークのチェルシーにオープンしたアメリカ初のポスターに特化したミュージアム「Poster House」。常設サイネージ2点をBASSDRUMが開発。 https://t.co/vNKMLcRtyL
— Shuichi Tsutsumi (@shu223) 2019年7月4日
(9月には義母が手伝いに来てくれて、念願かなってNYに実際に見に行くことができた)
ニューヨークのポスター美術館Poster Houseにて、開発を担当した”Poster Machine”の実機についに対面してきました!常設ですが安定稼働してるそうです😊 pic.twitter.com/fqybYUNucL
— Shuichi Tsutsumi (@shu223) 2019年9月13日
- 「不思議な宿」のiPadアプリ(ブルーパドル)
技術書の執筆
2019年のBOOTHでの売り上げを合算してみたら、受取額ベースで約150万円。まだまだ食える程ではないが、
— Shuichi Tsutsumi (@shu223) 2020年1月16日
「興味のあることを勉強して、アウトプットする」
という以前は0円でやっていたことがここまでマネタイズできるようになったのが感慨深い...https://t.co/V9jKO8MpGL pic.twitter.com/OZhixD8pHB
2019年のひとつのテーマは「技術発信のマネタイズ」だったが少しずつ結実してきた。
新刊
- 「Depth in Depth - iOSデプス詳解」
- 2019.4.14にv1.0.0を公開、その後2回の大幅加筆
- この本自体はそんなに売れていないが、デプスが絡む仕事はめっちゃ来るので完全に黒字
- 「iOSエンジニアのためのmacOSアプリ開発入門」
- 上述のニューヨーク案件で、数年ぶりにCocoa/AppKitを触ることになって備忘録的に書き始めたもの
- 「iOS 13の新機能をざっくり把握する本」
- 今はなんと100円で売っています
「iOS 13の新機能をざっくり把握する本」の電子版をなんと!100円にしてみました。
— Shuichi Tsutsumi (@shu223) 2020年1月23日
理由:
・iOS ○と題された本は時間経過で非常に売れにくくなる
・「100円なら買う」層はどれぐらいいるのかの実験
・本が売れたときの通知がくると単純に嬉しい
・(続)https://t.co/aRqpnHp6vH
- 「Keras & Core ML Tools」
- 今一番力をいれて更新しています
- 「詳解Core ML Tools - coremltools, Keras, TensorFlow」に改題予定
既刊の更新
その他発信活動
- 「三重県立桑名工業高校」での講演
- noteの有料マガジン
- 有料バリアにより心理的安全に守られつつ日々の勉強メモを気軽に投稿するための場
- 合計143本書いた(←マガジン外の記事も含む)
2019年、#note に書いた記事143本、月平均12本。本は新刊4冊出して既刊2冊も新版出した。
— Shuichi Tsutsumi (@shu223) 2019年12月23日
興味のあることを勉強する
→ついでにサクッと発信
→本にまとめてマネタイズ
→たまに関連の仕事をいただく
というインプット&アウトプット&マネタイズサイクルを作れたのが今年最大の成果 pic.twitter.com/0HJOUhmWkV
- 単価公開note
- めちゃくちゃ売れた...技術書は3ヶ月フルコミットで書いて印税の合計50万いかないぐらいだったが、これは書くのに1時間もかかってなくてたぶん100万ぐらい売れた
- しかしこれは自分の文章力とかじゃなく10年間ひたすらものをつくり行動し発信してきた結果なので再現性はまったくないと思っている
「エンジニアと人生」というYouTubeチャンネルを始めました
「エンジニアと人生」というYouTubeチャンネルを始めました。
技術の小難しい話はおいておいて、「生き様」に焦点をあてていろんなエンジニアにお話を伺う、というコンセプトの雑談チャンネルです。
ソフトウェアエンジニアという職業は今や売り手市場で、パソコンとネットがあればどこでも仕事ができ、国や言語を超えて通用し、ブログやオープンソースで発信することでプレゼンスも向上しやすく、「生き方の選択肢が多い」職業のひとつです。エンジニアにもそうでないみなさまにも、人生の可能性を感じてワクワクしていただけるような内容にしたいと思います。
- Vol. 1
- Vol. 2
- Vol. 3
チャンネル登録していただけると嬉しいです。
ちなみに今のところはいずれも音声コンテンツです。 Voicyという音声プラットフォームで配信している内容を再編集して動画を作成しています。
- このチャンネルを始めた動機
もともとは
— Shuichi Tsutsumi (@shu223) 2020年1月12日
「色んな人の人生の話を聞くのは楽しい」
→ 自分だけ楽しむのはもったいないのでコンテンツ化しよう
→ より多くの人に聞いてもらえるよう色々なプラットフォームに横展開しよう
という文脈なので楽しめない人にまで楽しんでもらう必要はないんだけど、
(2020.2 追記)動画も始めました。
最初は音声コンテンツに静止画を貼り付けたものだけで運営してましたが、最近は動画も撮り始めました。
[2019年度版]ドラッグ&ドロップで機械学習のモデルがつくれる「Create ML」の使い方(macOS 10.15 Catalina) #WWDC19
ドラッグ&ドロップで超簡単にオリジナルの機械学習モデルがつくれてしまうCreate MLが大幅パワーアップしました。
新機能が増えたのと、使い方が若干変わった(より簡単になった)部分があるので、最新版として本記事をお送りします。
なお、NDAに配慮してスクリーンショットはAppleの公開資料および現行バージョンのもので代用することにします。
Create MLの起動方法
これまではCreate MLはまだ独立したアプリとして提供されておらず、Playgroundにコードを書いて実行してアプリケーションのUIにアクセスしていました。
しかしmacOS 10.15 Catalina / Xcode 11で提供される最新バージョンでは、独立したアプリ(Create ML.app)として提供されるようになりました。
Xcode 11のメニューから、
[Xcode] > [Open Developer Tool] > [Create ML]
を選択することで起動します。
使用方法:画像分類器(Image Classifier)
プロジェクトの作成
[File] > [New Project] を選択するとテンプレート選択画面が立ち上がるので、"Image Classifier"を選択します。
データセットを用意する
どういうデータを用意するかですが、チュートリアルによると、
- ラベルごとに最低でも10枚の画像
- ラベルごとに枚数のバランスをとること(チーターは10枚、ゾウは1000枚、みたいなことをしない)
Use at least 10 images per label for the training set, but more is always better. Also, balance the number of images for each label. For example, don’t use 10 images for Cheetah and 1000 images for Elephant.
- JPEGやPNG等、画像フォーマットはなんでもいい(UTIがpublic.imageに適合していれば)
- サイズは揃ってなくてもOK
- サイズもなんでもいいが、最低でも299x299ピクセルはあった方が良い
The images can be in any format whose uniform type identifer conforms to public.image. This includes common formats like JPEG and PNG. The images don’t have to be the same size as each other, nor do they have to be any particular size, although it’s best to use images that are at least 299x299 pixels.
あとは実際に推論を行うのと同じ状況で学習データも収集した方がいいとか、いろんな角度、ライティングの状況のデータがあった方がいい、ということが書かれています。
If possible, train with images collected in a way that’s similar to how images will be collected for prediction.
Provide images with variety. For example, use images that show animals from many different angles and in different lighting conditions. A classifier trained on nearly identical images for a given label tends to have poorer performance than one trained on a more diverse image set.
ラベルをフォルダ名にし、その配下にトレーニングデータ、テストデータを配置します。
学習&モデルの評価
データフォルダをドラッグ&ドロップします。
テスト(モデルの評価)もドラッグ&ドロップ。
オプショナルで、最大イテレーション回数を指定したり、トレーニングデータにノイズやブラーを付加したり、回転を加えたりといったパラメータを指定することもできます。
Playボタンをクリックすると、学習が開始されます。
学習が完了すると、スコアが表示されます。
モデルを保存する
学習したモデルを .mlmodel
ファイルとして保存します。
アプリに組み込む
作成した .mlmodel
ファイルをiOSアプリに組み込んで使用します。
実装方法はこちらの記事を参考にしてください。
また画像分類の .mlmodel
ファイルをドラッグ&ドロップで試せるアプリをGitHubで公開しているので、こちらもぜひ活用してください。
使用方法:音声分類器(Sound Classifier)
(続く)
関連(SoundAnalysisについてちょっと書いてます):
API Diffsから見るiOS 13の新機能 - その他諸々 #WWDC19
Vision編、CoreML公式配布モデル編、Core Image編と、巨大な新API群の端っこの方から記事を書き始めたわけですが、その後どのフレームワークについて書こうとしても調査内容が膨大になってしまってうまくまとまらず、もう眠くなってしまったのでざっくり箇条書きで書いておいて明日以降にまたじっくり調査することにします。
SoundAnalysis
Analyze streamed and file-based audio to classify it as a particular type.
うおお、SoundAnalysisめっちゃアツい!画像・動画まわりは機械学習ベースでどんどん進化してるのに音声処理は重要なのにあまり変わらないよなーと最近話してたところ。OCRといい「あったらいいな」がほとんど来てる #iOS13 #WWDC19
— Shuichi Tsutsumi (@shu223) 2019年6月3日
機械学習ベースで音を分類したりするらしい。何の音を分類してくれるのかAPIリファレンスからはわからなかったのだけど、次のドキュメントで、
The SoundAnalysis framework operates on a model that you’ve trained using a Create ML MLSoundClassifier
と書いてあって、Create MLでつくったCore MLモデルを使って音を判別するようだ。
ってことで、レイヤーとしてはVisionの音声処理版(Visionは画像処理版)と解釈しとくとよさそう。
セマンティック・セグメンテーション / AVSemanticSegmentationMatte
前からしてPortrait Matteの汎用版。Portrait Matteは人間の全身専用マスクだが、もうちょっと汎用的に領域分割するマスクが取れるようになると。
関連メソッドは前回記事にも書いた:
CoreML公式配布モデルの「DeeplabV3」がMatte抽出にあたって内部で使われているのか、別の仕組みなのかは気になる。
AVSemanticSegmentationMatte.MatteType
という構造体があり、今のところ次のような種類があるようだ。
static let hair: AVSemanticSegmentationMatte.MatteType
A matting image that segments the hair from all people in the visible field of view of an image.
static let skin: AVSemanticSegmentationMatte.MatteType
A matting image that segments the skin from all people in the visible field of view of an image.
static let teeth: AVSemanticSegmentationMatte.MatteType
A matting image that segments the teeth from all people in the visible field of view of an image.
このへんの髪・肌・歯のセグメンテーションについては前回記事にも書いた。
AVCapturePhotoOutput
に関連APIがいくつか追加されている。
var availableSemanticSegmentationMatteTypes: [AVSemanticSegmentationMatte.MatteType]
An array of semantic segmentation matte types that may be captured and delivered along with the primary photo.
var enabledSemanticSegmentationMatteTypes: [AVSemanticSegmentationMatte.MatteType]
The semantic segmentation matte types that the photo render pipeline delivers.
AVCapturePhoto
にも。
func semanticSegmentationMatte(for: AVSemanticSegmentationMatte.MatteType) -> AVSemanticSegmentationMatte?
Retrieves the semantic segmentation matte associated with this photo.
AVCaptureMultiCamSession
A subclass of AVCaptureSession that supports simultaneous capture from multiple inputs of the same media type.
"AVMultiCamPiP: Capturing from Multiple Cameras"というサンプルがあるので、あとで実行してみる。
Core Haptics
Compose and play haptic patterns to customize your iOS app's haptic feedback.
サンプルもある。
このドキュメントも興味深い。"Apple Haptic and Audio Pattern (AHAP)"なるファイルフォーマットがあるらしい。
Audio Effects
そんなに新機能を期待してなかったAudioToolboxのリファレンスを見ていたら、iOS 13+なサンプルが2つもあった。
- Creating Custom Audio Effects | Apple Developer Documentation
- Incorporating Audio Effects and Instruments | Apple Developer Documentation
どちらも"Audio Effects"関連。どのへんがiOS 13なのかまだちゃんと読んでないが、あとで見てみる。
AVSpeechSynthesisVoiceGender
以前からある音声合成機能の、合成音声に男女の区別がついた。
case female case male case unspecified
これに伴い、AVSpeechSynthesisVoice
にはgender
プロパティが追加された。
var gender: AVSpeechSynthesisVoiceGender { get }
AVSpeechSynthesizer
なんかちょこちょこと新APIがある。
var mixToTelephonyUplink: Bool var synthesizerAudioSession: AVAudioSession
func write(AVSpeechUtterance, toBufferCallback: AVSpeechSynthesizer.BufferCallback)
MKPointOfInterestCategory
MKMapView
に次のようなプロパティが追加されていて、
var pointOfInterestFilter: MKPointOfInterestFilter?
地図上の"Point of Interest"をフィルタできる。めちゃくちゃ多くの種類が定義されているので、ここでは触りだけ。
static let airport: MKPointOfInterestCategory
The point of interest category for airports.
static let amusementPark: MKPointOfInterestCategory
The point of interest category for amusement parks.
MKMultiPolygon
MapKitの新クラス。WWDCキーノートを聞きながら
このストリートビューみたいなやつMapKitにAPI追加されてSceneKitやARKitと連携できるようになってたらアツいな
— Shuichi Tsutsumi (@shu223) June 3, 2019
こんな妄想をしてたのもあって、「ポリゴン」という字面からSceneKitと連携するなにかかと一瞬期待したが、よく考えたらMKPolygon
というクラスは昔からあって、3Dメッシュ表現手法としてのポリゴンではなくて普通に本来の意味での「多角形」だった。(で、どういうものなのかはまだわかってない)
Create ML
いずれ別記事で書きたいので省略するが、つくれるモデルの種類が増えている。
Create MLって何だっけ?という方はこちらをどうぞ:
VisionKit
Visionとはまた別の新フレームワーク。ドキュメントスキャナ的なものをつくる機能を提供してくれている?
VisionKit is a small framework that lets your app use the system's document scanner. Present the document camera as a view controller, which covers the entire screen like the camera function in Notes. Implement the VNDocumentCameraViewControllerDelegate in your own view controller to receive callbacks from the document camera, such as completed scans.
watchOSのIndependent App
これめっちゃいいじゃないですか。今まで2つのApp Extensionで構成されてたのがどうなるのか気になる。プロジェクト生成してみる。
どういうプロジェクト構成になるんだろう??前はapp extension2つに分かれてたけど。
— Shuichi Tsutsumi (@shu223) June 3, 2019
On-device speech recognition
オンデバイスで音声認識。SFSpeechRecognitionRequest
に、以下のプロパティが追加されている。
var requiresOnDeviceRecognition: Bool { get set }
その他もちろん気になるフレームワーク群
(SwiftUIとかCombineとかはもちろんキャッチアップするとして)
- ARKit 3
- RealityKit
- Reality
- Core ML 3
- Metal
- MetalKit
- Metal Performance Shaders
- Natural Language
etc...
API Diffsから見るiOS 13の新機能 - Core Image #WWDC19
iOS 13の新API発掘シリーズその3です。今回はCore Image。
- API Diffsから見るiOS 13の新機能 - Vision #WWDC19 - その後のその後
- API Diffsから見るiOS 13の新機能 - CoreML公式配布モデル #WWDC19 - その後のその後
髪・肌・歯のマスク
iOS 12の"Portrait Matte"は全身セグメンテーション用のマスクだったわけですが、それの「髪・肌・歯」版が取れるようになったようです。
static let auxiliarySemanticSegmentationHairMatte: CIImageOption static let auxiliarySemanticSegmentationSkinMatte: CIImageOption static let auxiliarySemanticSegmentationTeethMatte: CIImageOption
auxiliarySemanticSegmentationHairMatte
— Shuichi Tsutsumi (@shu223) June 3, 2019
auxiliarySemanticSegmentationSkinMatte
髪の色だけ変化させる、肌の色だけ変化させる、ってことができるようになるなこれ。(ちなみにTeethMatteもあったので白い歯にもなれる)#iOS13 #WWDC19
関連: "Portrait Matte"とは?
デプスブラー
CIContext
にデプスブラーフィルタを生成するメソッドが追加。disparityImage
(視差画像)、portraitEffectsMatte
(全身セグメンテーション用マスク画像)、hairSemanticSegmentation
(髪のセグメンテーション画像)を渡せて、出力としてCIFilter
オブジェクトが返ってきます。
func depthBlurEffectFilter(for image: CIImage, disparityImage: CIImage, portraitEffectsMatte: CIImage?, hairSemanticSegmentation: CIImage?, orientation: CGImagePropertyOrientation, options: [AnyHashable : Any]? = nil) -> CIFilter?
allowLowPower
また、CIContextOption
に以下の型プロパティが追加されていました。
static let allowLowPower: CIContextOption
ドキュメントには解説がありませんが、ヘッダになにか書いてあるかも知れません。パフォーマンスかなにかを犠牲にして消費電力を抑えるオプションでしょうか?
CIFilterの各フィルタの初期化メソッド
今までは次のように文字列でフィルタ名を指定して初期化しないといけなかったのですが、
let filter = CIFilter(name: "CISepiaTone")!
iOS 13ではドーンと(たぶん)全フィルタの初期化メソッドが追加されました。
一覧は長いので本記事の末尾に載せますが、たとえば上に示したsepia toneフィルタは次のメソッドで初期化できます。
class func sepiaTone() -> CIFilter & CISepiaTone
CIImageのAVSemanticSegmentationMatteからの初期化メソッド
AVSemanticSegmentationMatteはまだ紹介してませんが、名前からしてPortraitMatteの汎用版(Portrait Matteは人間の全身専用マスクだが、もうちょっと汎用的に領域分割するマスク)で、そこからCIImageを生成するメソッドが追加されています。
init?(semanticSegmentationMatte: AVSemanticSegmentationMatte) init?(semanticSegmentationMatte: AVSemanticSegmentationMatte, options: [CIImageOption : Any]?)
パパッと既存の(≠オリジナルの)画像処理を適用するにはやっぱりCore Imageが簡単なので、これは必須ですね。
CGImageSource
を渡すイニシャライザも追加されています(今までなかったんだっけ。。?)
init(cgImageSource: CGImageSource, index: Int, options: [CIImageOption : Any]?)
AVSemanticSegmentationMatte
オブジェクトにはプロパティからアクセスできる(持っていれば)ようです。
var semanticSegmentationMatte: AVSemanticSegmentationMatte?
一色のCIImageを生成する?
ドキュメントには解説がなかったのですが、CIImageに以下のような型プロパティが追加されています。一色塗りのCIImageオブジェクトを生成するのでしょうか?
class var black: CIImage class var blue: CIImage class var clear: CIImage class var cyan: CIImage class var gray: CIImage class var green: CIImage class var magenta: CIImage class var red: CIImage class var white: CIImage class var yellow: CIImage
CIFilterに追加された初期化メソッド一覧
上で解説した、CIFilterを生成するメソッド一覧です。しれっと新たに追加されたフィルタもあるかもしれません。
class func accordionFoldTransition() -> CIFilter & CIAccordionFoldTransition class func additionCompositing() -> CIFilter & CICompositeOperation class func affineClamp() -> CIFilter & CIAffineClamp class func affineTile() -> CIFilter & CIAffineTile class func attributedTextImageGenerator() -> CIFilter & CIAttributedTextImageGenerator class func aztecCodeGenerator() -> CIFilter & CIAztecCodeGenerator class func barcodeGenerator() -> CIFilter & CIBarcodeGenerator class func barsSwipeTransition() -> CIFilter & CIBarsSwipeTransition class func bicubicScaleTransform() -> CIFilter & CIBicubicScaleTransform class func blendWithAlphaMask() -> CIFilter & CIBlendWithMask class func blendWithBlueMask() -> CIFilter & CIBlendWithMask class func blendWithMask() -> CIFilter & CIBlendWithMask class func blendWithRedMask() -> CIFilter & CIBlendWithMask class func bloom() -> CIFilter & CIBloom class func bokehBlur() -> CIFilter & CIBokehBlur class func boxBlur() -> CIFilter & CIBoxBlur class func checkerboardGenerator() -> CIFilter & CICheckerboardGenerator class func circularScreen() -> CIFilter & CICircularScreen class func cmykHalftone() -> CIFilter & CICMYKHalftone class func code128BarcodeGenerator() -> CIFilter & CICode128BarcodeGenerator class func colorBlendMode() -> CIFilter & CICompositeOperation class func colorBurnBlendMode() -> CIFilter & CICompositeOperation class func colorClamp() -> CIFilter & CIColorClamp class func colorControls() -> CIFilter & CIColorControls class func colorCrossPolynomial() -> CIFilter & CIColorCrossPolynomial class func colorCube() -> CIFilter & CIColorCube class func colorCubeWithColorSpace() -> CIFilter & CIColorCubeWithColorSpace class func colorCubesMixedWithMask() -> CIFilter & CIColorCubesMixedWithMask class func colorCurves() -> CIFilter & CIColorCurves class func colorDodgeBlendMode() -> CIFilter & CICompositeOperation class func colorInvert() -> CIFilter & CIColorInvert class func colorMap() -> CIFilter & CIColorMap class func colorMatrix() -> CIFilter & CIColorMatrix class func colorMonochrome() -> CIFilter & CIColorMonochrome class func colorPolynomial() -> CIFilter & CIColorPolynomial class func colorPosterize() -> CIFilter & CIColorPosterize class func comicEffect() -> CIFilter & CIComicEffect class func convolution3X3() -> CIFilter & CIConvolution class func convolution5X5() -> CIFilter & CIConvolution class func convolution7X7() -> CIFilter & CIConvolution class func convolution9Horizontal() -> CIFilter & CIConvolution class func convolution9Vertical() -> CIFilter & CIConvolution class func copyMachineTransition() -> CIFilter & CICopyMachineTransition class func coreMLModel() -> CIFilter & CICoreMLModel class func crystallize() -> CIFilter & CICrystallize class func darkenBlendMode() -> CIFilter & CICompositeOperation class func depthOfField() -> CIFilter & CIDepthOfField class func depthToDisparity() -> CIFilter & CIDepthToDisparity class func differenceBlendMode() -> CIFilter & CICompositeOperation class func discBlur() -> CIFilter & CIDiscBlur class func disintegrateWithMaskTransition() -> CIFilter & CIDisintegrateWithMaskTransition class func disparityToDepth() -> CIFilter & CIDisparityToDepth class func dissolveTransition() -> CIFilter & CIDissolveTransition class func dither() -> CIFilter & CIDither class func divideBlendMode() -> CIFilter & CICompositeOperation class func documentEnhancer() -> CIFilter & CIDocumentEnhancer class func dotScreen() -> CIFilter & CIDotScreen class func edgePreserveUpsample() -> CIFilter & CIEdgePreserveUpsample class func edgeWork() -> CIFilter & CIEdgeWork class func edges() -> CIFilter & CIEdges class func eightfoldReflectedTile() -> CIFilter & CIEightfoldReflectedTile class func exclusionBlendMode() -> CIFilter & CICompositeOperation class func exposureAdjust() -> CIFilter & CIExposureAdjust class func falseColor() -> CIFilter & CIFalseColor class func flashTransition() -> CIFilter & CIFlashTransition class func fourfoldReflectedTile() -> CIFilter & CIFourfoldReflectedTile class func fourfoldRotatedTile() -> CIFilter & CIFourfoldRotatedTile class func fourfoldTranslatedTile() -> CIFilter & CIFourfoldTranslatedTile class func gammaAdjust() -> CIFilter & CIGammaAdjust class func gaussianBlur() -> CIFilter & CIGaussianBlur class func gaussianGradient() -> CIFilter & CIGaussianGradient class func glideReflectedTile() -> CIFilter & CIGlideReflectedTile class func gloom() -> CIFilter & CIGloom class func hardLightBlendMode() -> CIFilter & CICompositeOperation class func hatchedScreen() -> CIFilter & CIHatchedScreen class func heightFieldFromMask() -> CIFilter & CIHeightFieldFromMask class func hexagonalPixellate() -> CIFilter & CIHexagonalPixellate class func highlightShadowAdjust() -> CIFilter & CIHighlightShadowAdjust class func hueAdjust() -> CIFilter & CIHueAdjust class func hueBlendMode() -> CIFilter & CICompositeOperation class func hueSaturationValueGradient() -> CIFilter & CIHueSaturationValueGradient class func kaleidoscope() -> CIFilter & CIKaleidoscope class func labDeltaE() -> CIFilter & CILabDeltaE class func lanczosScaleTransform() -> CIFilter & CILanczosScaleTransform class func lenticularHaloGenerator() -> CIFilter & CILenticularHaloGenerator class func lightenBlendMode() -> CIFilter & CICompositeOperation class func lineOverlay() -> CIFilter & CILineOverlay class func lineScreen() -> CIFilter & CILineScreen class func linearBurnBlendMode() -> CIFilter & CICompositeOperation class func linearDodgeBlendMode() -> CIFilter & CICompositeOperation class func linearGradient() -> CIFilter & CILinearGradient class func linearToSRGBToneCurve() -> CIFilter & CILinearToSRGBToneCurve class func luminosityBlendMode() -> CIFilter & CICompositeOperation class func maskToAlpha() -> CIFilter & CIMaskToAlpha class func maskedVariableBlur() -> CIFilter & CIMaskedVariableBlur class func maximumComponent() -> CIFilter & CIMaximumComponent class func maximumCompositing() -> CIFilter & CICompositeOperation class func median() -> CIFilter & CIMedian class func meshGenerator() -> CIFilter & CIMeshGenerator class func minimumComponent() -> CIFilter & CIMinimumComponent class func minimumCompositing() -> CIFilter & CICompositeOperation class func mix() -> CIFilter & CIMix class func modTransition() -> CIFilter & CIModTransition class func morphologyGradient() -> CIFilter & CIMorphologyGradient class func morphologyMaximum() -> CIFilter & CIMorphologyMaximum class func morphologyMinimum() -> CIFilter & CIMorphologyMinimum class func morphologyRectangleMaximum() -> CIFilter & CIMorphologyRectangleMaximum class func morphologyRectangleMinimum() -> CIFilter & CIMorphologyRectangleMinimum class func motionBlur() -> CIFilter & CIMotionBlur class func multiplyBlendMode() -> CIFilter & CICompositeOperation class func multiplyCompositing() -> CIFilter & CICompositeOperation class func noiseReduction() -> CIFilter & CINoiseReduction class func opTile() -> CIFilter & CIOpTile class func overlayBlendMode() -> CIFilter & CICompositeOperation class func pageCurlTransition() -> CIFilter & CIPageCurlTransition class func pageCurlWithShadowTransition() -> CIFilter & CIPageCurlWithShadowTransition class func paletteCentroid() -> CIFilter & CIPaletteCentroid class func palettize() -> CIFilter & CIPalettize class func parallelogramTile() -> CIFilter & CIParallelogramTile class func pdf417BarcodeGenerator() -> CIFilter & CIPDF417BarcodeGenerator class func perspectiveCorrection() -> CIFilter & CIPerspectiveCorrection class func perspectiveTile() -> CIFilter & CIPerspectiveTile class func perspectiveTransform() -> CIFilter & CIPerspectiveTransform class func perspectiveTransformWithExtent() -> CIFilter & CIPerspectiveTransformWithExtent class func photoEffectChrome() -> CIFilter & CIPhotoEffect class func photoEffectFade() -> CIFilter & CIPhotoEffect class func photoEffectInstant() -> CIFilter & CIPhotoEffect class func photoEffectMono() -> CIFilter & CIPhotoEffect class func photoEffectNoir() -> CIFilter & CIPhotoEffect class func photoEffectProcess() -> CIFilter & CIPhotoEffect class func photoEffectTonal() -> CIFilter & CIPhotoEffect class func photoEffectTransfer() -> CIFilter & CIPhotoEffect class func pinLightBlendMode() -> CIFilter & CICompositeOperation class func pixellate() -> CIFilter & CIPixellate class func pointillize() -> CIFilter & CIPointillize class func qrCodeGenerator() -> CIFilter & CIQRCodeGenerator class func radialGradient() -> CIFilter & CIRadialGradient class func randomGenerator() -> CIFilter & CIRandomGenerator class func rippleTransition() -> CIFilter & CIRippleTransition class func sRGBToneCurveToLinear() -> CIFilter & CISRGBToneCurveToLinear class func saliencyMap() -> CIFilter & CISaliencyMap class func saturationBlendMode() -> CIFilter & CICompositeOperation class func screenBlendMode() -> CIFilter & CICompositeOperation class func sepiaTone() -> CIFilter & CISepiaTone class func shadedMaterial() -> CIFilter & CIShadedMaterial class func sharpenLuminance() -> CIFilter & CISharpenLuminance class func sixfoldReflectedTile() -> CIFilter & CISixfoldReflectedTile class func sixfoldRotatedTile() -> CIFilter & CISixfoldRotatedTile class func smoothLinearGradient() -> CIFilter & CISmoothLinearGradient class func softLightBlendMode() -> CIFilter & CICompositeOperation class func sourceAtopCompositing() -> CIFilter & CICompositeOperation class func sourceInCompositing() -> CIFilter & CICompositeOperation class func sourceOutCompositing() -> CIFilter & CICompositeOperation class func sourceOverCompositing() -> CIFilter & CICompositeOperation class func spotColor() -> CIFilter & CISpotColor class func spotLight() -> CIFilter & CISpotLight class func starShineGenerator() -> CIFilter & CIStarShineGenerator class func straighten() -> CIFilter & CIStraighten class func stripesGenerator() -> CIFilter & CIStripesGenerator class func subtractBlendMode() -> CIFilter & CICompositeOperation class func sunbeamsGenerator() -> CIFilter & CISunbeamsGenerator class func supportedRawCameraModels() -> [String]! class func swipeTransition() -> CIFilter & CISwipeTransition class func temperatureAndTint() -> CIFilter & CITemperatureAndTint class func textImageGenerator() -> CIFilter & CITextImageGenerator class func thermal() -> CIFilter & CIThermal class func toneCurve() -> CIFilter & CIToneCurve class func triangleKaleidoscope() -> CIFilter & CITriangleKaleidoscope class func triangleTile() -> CIFilter & CITriangleTile class func twelvefoldReflectedTile() -> CIFilter & CITwelvefoldReflectedTile class func unsharpMask() -> CIFilter & CIUnsharpMask class func vibrance() -> CIFilter & CIVibrance class func vignette() -> CIFilter & CIVignette class func vignetteEffect() -> CIFilter & CIVignetteEffect class func whitePointAdjust() -> CIFilter & CIWhitePointAdjust class func xRay() -> CIFilter & CIXRay class func zoomBlur() -> CIFilter & CIZoomBlur
API Diffsから見るiOS 13の新機能 - CoreML公式配布モデル #WWDC19
iOS 13の新API発掘シリーズその2です。
以前の公式配布CoreMLモデルと言えば、imagenetベースの物体検出がほとんどで、あまり新鮮味のあるモデルは配布されていませんでした。
なので、自作するか、サードパーティ製のを探して使うことがほとんどでした。
・・・が、今日見てみると、楽しそうなモデルがたくさん追加されているではありませんか!
ひょっとして・・・と見てみたら、CoreMLの公式配布モデルも増えてる!
— Shuichi Tsutsumi (@shu223) June 3, 2019
・デプス推定(単眼カメラでも、既存写真からでもデプスが取得可能に)
・セグメンテーション
・YOLO(「画像内のどこにあるか」までわかる物体検出)#WWDC19 #iOS13 pic.twitter.com/UfZvOIfckv
というわけで前回のVision編に続き、本記事では(APIではありませんが)CoreMLの公式配布モデルについて見ていきます。
デプス推定
- FCRN-DepthPrediction
- Depth Estimation
redict the depth from a single image.
画像からデプスを「推定」します。つまり、単眼カメラでも、デプスデータを持っていない既存写真からも、デプスが取得できるようになる、ということです。ここからAVDepthData
を生成することもできるはずです。
・・・ということはデプスを利用する機能が実質的にデバイスを限定する機能ではなくなるといえるのではないでしょうか。今まではデプスを使う機能を提供しようにもiPhone X系とか7 Plus, 8 Plus系のハイエンドデバイスのユーザーしか使えなかったので、興味やアイデアはあってもなかなか採用しづらかったのではないかと思います。
これでついにデプス利用機能が多少は普及しそうですね。参考書籍を貼っておきます。
(もちろん今回の発表をふまえてアップデート予定です)
セグメンテーション(領域分割)
- DeeplabV3
- Image Segmentation
Segment the pixels of a camera frame or image into a predefined set of classes.
サムネイル画像によると人間のセグメンテーションのように見えますが、解説を読むと"predefined set of classes"とあり、複数のクラスに対応しているようです。
試しに.mlmodel
ファイルをダウンロードして埋め込まれているdescriptionを読んでみると、
person, dog, cat and so on
とあります。人の他に犬や猫もセグメンテーションできるようです。
関連: iOS 12のPortrait Matteがすごい/ #iOSDC 2018で登壇します - その後のその後
物体検出(YOLO)
YOLOv3
- Object Detection
YOLOv3-Tiny
- (Real-time) Object Detection
Locate and classify 80 different types of objects present in a camera frame or image.
物体を「画像内のどこにあるか」の情報を含め検出してくれるモデル。リアルタイム検出用の"Tiny"版もあります。
質問への回答を生成
- BERT-SQuAD
- Question Answering
Generate answers to questions about paragraphs of text.
公式配布モデルでは唯一の自然言語処理用。
指定したパラグラフ内のテキストに関して、質問を与えると回答を生成してくれるようです。
API Diffsから見るiOS 13の新機能 - Vision #WWDC19
iOSエンジニア諸氏のツイートを見ているとSwiftUIが圧倒的インパクトっぽい今回のWWDCですが、そのへんは識者の方々にお任せして、「その他フレームワーク」で気になった新APIを見ていきたいと思います。
まずはVision。
Visionもかなりアツい。
— Shuichi Tsutsumi (@shu223) 2019年6月3日
- VNRecognizeTextRequest(今までの文字領域検出じゃなくて文字認識、いわゆるOCR!)
- VNDetectHumanRectanglesRequest
- VNAnimalDetector(今のところイヌネコw)#iOS13 #WWDC19
"Analyzing Image Similarity with Feature Print"っていうサンプルによると、画像の類似度の計算もできるようになったっぽい
— Shuichi Tsutsumi (@shu223) 2019年6月3日
人間検出
VNDetectHumanRectanglesRequest
人間を矩形で検出。
↓はOpenCV使ったやつですが、こういうのです。
ARKitのpeople segmentationがインパクトありすぎて「矩形で検出」というのは印象薄いですが、「こういうのもあったな」と頭の片隅に置いておくといつか用途があるかもしれません。
文字認識
VNRecognizeTextRequest
文字認識。今まであった文字領域検出じゃなくて、文字認識、いわゆるOCR的なやつです。
今まで無料で使えるやつだとtesseractとSwiftOCRぐらいしか選択肢がなかったのが、ついに標準でサポート・・・!感無量です。(対応言語は後で調べる)
対応言語はsupportedRecognitionLanguages(for:revision:)
というメソッドをたたけば調べられそう。あとでやってみます。
動物検出
VNDetectAnimalRectanglesReques
VNAnimalDetector
のtype propertyとして今のところcat
とdog
が用意されており、つまりイヌネコ認識が可能となります。ペットが写ってる写真とかを判別できるようになったわけですね。
画像の類似度を計算
VNGenerateImageFeaturePrintRequest
VNFeaturePrintObservation
"Analyzing Image Similarity with Feature Print"というサンプルが公開されており、画像間の類似度が計算できるようになったようです。後でコード読んでみます。
画像分類?
VNClassifyImageRequest
画像分類は前からできたはずだけど、この新クラスは何だろう?
Image Saliency
State of the Unionでも出てきたこのキーワード。"salient"は辞書によると「顕著な」(英英では"most noticeable or important.")の意味。
VNGenerateAttentionBasedSaliencyImageRequest
Generates a heat map that identifies the parts of an image most likely to draw attention.
画像内で、もっとも注意を引く部分を特定するヒートマップを生成・・・?"draw attention"な箇所ってのがよくわかりませんね。試してみます。
VNGenerateObjectnessBasedSaliencyImageRequest
Generates a heat map that identifies the parts of an image most likely to represent objects.
画像内で、もっともオブジェクトを表している部分を特定するヒートマップを生成する。ここでいう「オブジェクト」はこちらで指定できるのでしょうか。あとでもうちょっとAPIを見てみます。
VNSaliencyImageObservation
上2つのrequestの結果として得られるクラス。VNPixelBufferObservation
を継承し、グレースケールのヒートマップデータを持つ。
var salientObjects: [VNRectangleObservation]? { get }
というプロパティを持っていて、salient Objectsの矩形を複数保持できるようになっています。
Saliencyのサンプルコードとドキュメント
この"Saliency"関連では、"Highlighting Areas of Interest in an Image Using Saliency"というサンプルコードと、"Cropping Images Using Saliency"というドキュメントがあります。