Nakajijapan

生きるのに必死です。

2015年 振り返り

これを書いている時はまだ2015ですが、出す頃には2016になってるんだろうな。

さて、2015年振り返ってみることにしよう。 今年は自分が部署移動して来て仕事が怒涛に前に進んでいったというイメージが強い。日々自分もそこで奮闘していた。 モバイルエンジニアとして活動してから2年ちょっと経過したのかと思う。(実際は趣味で2012年からやり始めているから結構経過していた) その中でもこの1年はさらに濃いものだったと思う。

仕事

モバイルでは初の複数人開発を経験した。今まで一人で開発してきての急な複数人開発で不安なものがあった。 まぁスクラムをある程度体系化していたのとメンバーとのコミュニケーションもそれなりにとれていたのでコンテキスト が大幅にずれることはなかったのでうまく仕事を回せていけた。その甲斐もあって、この1年間でいろんな問題が通常の3倍のスピードで改善されていった。 来年もさらに改善活動は続けていくのだが、それだけでは圧倒的なプロダクトになっていかないので自分たちは自分達なりにそのプロダクトをどうしていくべきを考えて いかなければいけない。自分としては改善活動と合わせて、技術をさらに深掘りしていくのと、デザインやマーケティングをもっと学んで違ったアプローチでプロダクト をよくしていく活動もしていこうと思う。

発表

以前自分がどのようにしてエンジニアとして成長しているのかというのを自己紹介という名目で発表した。 今年はまさにそれを体現している一年となったかもしれない。ただ、変わっていたのは個人プロダクトから 会社のプロダクト経由でたくさんの挑戦や学びを得たというところだろうか。

スライド

小さいものから大きいものまであるが自分の成長サイクルの一環としてできているので今後も継続していきたい。 ただ、やや個人的なもの多かったので大規模なもの、さらに技術的に濃いことを踏み込んで話せていければさらに自分の成長につながっていいのではないかと思ったので実践していくぞ!

OSS

ここ数年間でOSS活動が自然とできるようになった感じがする。 このアクティビティを見るとやるときとやらないときの差が大きかったが、まぁこれはこれでいいだろう。 この一年は以下の内容が主だった。

  • プライベート・仕事にかかわらず抽象化できるところは、依存性を取り除いてプラグイン化していった。
  • 興味のあるインタラクションがあったらそれを実装にまで落とし込んでプラグインまで昇華させていった。
  • その他便利ツールの作成

この行動は良いことだと思うので来年も継続して行っていきたい。

まとめ

今年1年間はエンジニアとして成長できるサイクル・楽しくできる環境を作れたのでまぁ良かったのではないかと思っている。 来年もさらに激動な1年になるので、その大波に自分も乗っていけるようにさらに成長していくぞ!!!!すごい勢いで!!!!!! (来年の目標は来年書くって言いながら今年になってた!!!!!)

Potatotips #24に参加してきた

potatotips (iOS/Android開発Tips共有会) 第24回にブログ枠として参加してきたのでそのメモに綴ります! 今回はGoodpatchさん主催での開催となりました。

iOSでテーマ(着せ替え)機能を実装した時のTips

Goodpatchの重田さん

  • UIAppearanceの話

tvOSでWebSocketを使う

デジタルサーカスの長谷川さん

  • Apple TVの話
  • AppleTVのサーバ通信
  • WEB API?
    • もっとリアルタイムにしたい
  • APNs?
  • WebSocket?
    • Starscreamが良かった
      • Pure Swift!

iOS7をサポート対象外にして開発を健全化する

@shoby さん

  • iOS 7をサポート対象外にして健全にする
  • ユーザにOSのアップデートを促す
  • 最終互換バージョンを提供する
  • 著名なアプリが対象外にしている!!!!!

xcconfigで複数ターゲットのビルド設定をまとめる

@k_katsumi さん

  • Univy targets for multiple platforms into one target
  • メルカリは言語ごとにターゲット作ってる
  • 複数管理する方法
  • keychainaccess
    • v2.1 コピーすればios7でも使える
  • どうやるか
    • configuration file使ってる
      • base.xcconfig
        • 全部デプロイ面とターゲットを利用している
      • Debug.xcconfig
      • Release.xcconfig
  • *で設定すると便利
  • BuildSettingExtractor使うと便利

Enhancements with 3D Touch

Goodpatch の @roothybrid7 さん

  • Enhancements with 3D touch
  • 導入した話
  • なぜ?
    • プロトタイプのプレビューをすぐみたい
  • 3D touch
    • Home Screen
    • Quick Actions
    • Peek and Pop
  • Blurによりうきあがる量いいの指定
  • タッチしたポイント(location)から算出

On Demand Resourcesを意識したコンテンツ制作

ユビレジの @nolili さん

  • try!
  • 昔のアプリをtvOS対応した話
  • サーバのリソース入れ替えよう!! –> ダメ
  • 住めてのアセットがそれ追っていること
  • 適切なタグが振られていること
  • どこでユーザをまあたせていいのか
    • 初回起動時にオフラインのユーザがどの段階までコンテンツにアクセスrすrのかSubmit時の意トラブル発覚は辛い
    • TestFlightでテストする
  • ドキュメントあるからそこみるといい

What’s new in Swift3

@TachibanaKaoru さん

  • Swiftの話
    • try! Swiftの紹介
  • Swift Evolution
  • 今後のSwiftのレビューを振り返る
  • Swift 2.2
  • 春にリリースされるバグ修正、実装の品質向上
  • コード互換性あり
  • 3.0リリースに見据えてwarningを表示するようになる
  • 3.0
    • 2016年秋に出る予定
    • 3.0で対応しないこと
    • Proposalレポジトリ

enumrate

ネクスト の @mo_to_44 さん

  • enumarateはどう実装されているのか
  • .gyb
  • Generate Your Boilerplate
  • Swiftのプロジェクトで使われいてるテンプレート形式
  • GeneratorTypeプロトコル
  • EnumerateSequence

感想

  • ブログ枠だったけど次回はトーク枠で参加したいですね。
  • 企画・主催してくださったグッドパッチさんに鬼感謝です!!!!!!
  • Goodpatchさんのアドベントカレンダーがあるようです!

次回

次回開催はFringe81さんでpotatotipsを行うそうです!!!!

Technology of Etsy

初めまして, @nakajijapanです。

この記事はiOS Adovent Calendar 2015の16日目の記事になります。

今日のネタはEtsyの気になるインタラクションがあったので試してみようと思ったのですが、ネットを探してもなかったものなので見よう見まねで作成してみました。 どんなインタラクションかというと作品のの個数を決めるときにドラムロールで選択するのが通常だと思うのですが、Etsyの場合は一工夫しているようで以下のような インタラクションを実現しています。

カートで在庫や作品の色を決めるときに表現されます。

  • transitionで現在の画面を多少縮小させる
  • 画面の半分までTableViewが表示される
    • Cellをタップしたら閉じる
  • NavigationBarのような部分をパンすることで最後までTableViewが表示されるようになる
    • パンしている間、縮小した画面はそれに合わせてリアルタイムに変化する

これは、少ない選択肢の時はTableViewを半分だけ表示すれば事足りるのだが、その半分におさまらない場合はパンすることでさらに見ることができるようになるという仕組み?かと思います。 これがいいのは、ユーザの細かいフェーズでインタラクションを実現できることだと思います。

  • 選択肢が少ない場合は半分だけ表示されれば、画面遷移を完全にすることなく選択できる
    • 後ろにタップした画面を表示させることで何のための選択肢なのか視覚的に伝えることができる
  • 選択肢が多かったとしても、メジャーに選択されるものを最初の半分で表示させといて、それ以外にも選択する必要がある場合は完全に広げることで選択が可能になる
    • 上記と同じなのだが、さらに本当にもっと他の選択肢が必要になった時にのみに全体表示せるようにしている

試してみたこと

では、このインタラクションを見てどのように実装してくのかを考えたときに真っ先に思いついたのがUIPercentDrivenInteractiveTransitionを利用した方法です。 これはあるViewControllerからあるViewControllerへ遷移する時のアニメーションを手動で管理する方法です。通常のアニメーションだと最初から最後まで一貫して 行われてしまうのですがUIPercentDrivenInteractiveTransitionを利用することで、例えばパンしている間は、画面を閉じるアニメーションをリアルタイムに制御できるようになるということです。アニメーション自体はUIViewControllerAnimatorTransitioningプロトコルを利用したアニメーションクラスを実装することで実現できます。 しかし、これだと画面を開くときに最初は通常のアニメーションを行い途中で止めて、途中からUIPercentDrivenInteractiveTransitionを利用してパンしながらリアルタイムにアニメーションをすることができませんでした。

どのように作成したの

では、どう実現させたかというと遷移前のViewController.viewに遷移先のViewController.viewをaddSubviewすることで実現できました。いたってシンプル。 あとリアルタイムに背景を形状を変化させる処理は以下のようにして実装しました。

1
2
3
4
5
6
7
8
9
10
11
12
func transitionBackgroundView(degree: CGFloat, location:CGPoint) {

    let overlayView = self.parentView!.viewWithTag(920)!
    let imageView = overlayView.viewWithTag(910) as! UIImageView
    let scale = self.map(location.y, inMin: 0, inMax: UIScreen.mainScreen().bounds.height, outMin: 0.90, outMax: 1.0)
    let transform : CATransform3D = CATransform3DMakeScale(scale, scale, 1)
    imageView.layer.removeAllAnimations()
    imageView.layer.transform = transform
    imageView.setNeedsLayout()
    imageView.layoutIfNeeded()

}

イベントはUIPanGestureRecognizerを利用すれば実現できます。

1
2
let panGestureRecognizer = UIPanGestureRecognizer(target: self, action: "pan:")
self.navigationBar.addGestureRecognizer(panGestureRecognizer)

実際以下のような感じになりました。

まとめ

今回はEtsyの気になるインタラクションを真似して実装してみるという実験を行う話でした。 もちろん、これが正しいとは限らないんですが、別の手段があれば是非教えて欲しいものです。 とりあえず、技術的にはできるようになったしこれはこれでよしとしたいと思います。今回ソースは まだ公開できないのですが今年中にはCocoaPodsにして出そうかと思います。

Teiten 1.3.0にバージョンアップ - 動画をアーカイブできるようにした

Teitenのバージョンアップを行いました。

バージョンアップ内容は以下の内容です。

  • 動画にその時の時間を加えました。
  • 指定された時間ごとに3秒動画を撮ってそれを結合できるようにしました。

もっと監視っぷりを高めたくこの更新を行いました。

処理内容

  • 動画を保存する
  • 保存された動画を結合する
  • 動画には録画された時間帯を表示させておく

動画を保存する

今まで出力に

  • AVCaptureStillImageOutput

を利用していたが新たな出力先に

  • AVCaptureMovieFileOutput

を登録した。

保存された動画を結合する

以前自分が作成したプラグインNKJMovieComposerでさくっと実装した

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
let movieComposition = NKJMovieComposer()
movieComposition.videoComposition.renderSize = CGSize(width: self.size.width, height: self.size.height)

for i in 0..<self.files.count {

    let beforeTimeDuration = movieComposition.currentTimeDuration
    let moviePath = self.files[i]

    // movie
    let movieURL = NSURL(fileURLWithPath: moviePath)
    //let layerInstruction = movieComposition.addVideo(movieURL)
    _ = movieComposition.addVideo(movieURL)

    (snip...)
}

動画には録画された時間帯を表示させておく

時間帯は動画ファイルのメタ情報から取得できるのでそれを利用する。あとは動画が切り替わるごとにその文字列を切り替えればいい。 動画上にCALayerを敷いてそこで文字列を表示するのにCATextLayerを使ってアニメーションさせればしたいこは実現できた。

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
// today
let dateFormatter = NSDateFormatter()
dateFormatter.dateFormat = "yyyy/MM/dd HH:mm"

// text layer
let textLayer = CATextLayer()
textLayer.frame = CGRect(x: self.size.width - 400.0 - 10.0, y: 10.0, width: 400.0, height: 52.0)
textLayer.string = dateFormatter.stringFromDate(self.dates[i])
textLayer.fontSize = 48.0
textLayer.alignmentMode = kCAAlignmentRight
textLayer.foregroundColor = NSColor.whiteColor().CGColor
textLayer.shouldRasterize = true
textLayer.opacity = 0.0
layerRoot.addSublayer(textLayer)

// animation
let offsetTimeDuration = CMTimeSubtract(movieComposition.currentTimeDuration, beforeTimeDuration)
let animation = CABasicAnimation(keyPath: "opacity")
animation.beginTime     = (i == 0) ? AVCoreAnimationBeginTimeAtZero : CMTimeGetSeconds(beforeTimeDuration)
animation.duration      = CMTimeGetSeconds(offsetTimeDuration)
animation.repeatCount   = 1
animation.autoreverses  = false
animation.fromValue     = NSNumber(float: 1.0)
animation.toValue       = NSNumber(float: 1.0)
animation.removedOnCompletion = false
textLayer.addAnimation(animation, forKey:"hide")

最後はそのアニメーションをAVVideoCompositionCoreAnimationToolを使ってVideo Compositionに登録する。

1
2
// animation
movieComposition.videoComposition.animationTool = AVVideoCompositionCoreAnimationTool(postProcessingAsVideoLayer: layerVideo, inLayer: layerRoot)

これで上記にある動画は実現できた。

まとめ

今回は既存の知識で何とかできたのでそれほど技術的に達成感はないものの、動画ネタはまだ自分の中でまだまだ冷めてないことがわかった。また、何か面白そうなことがあれば試していきたいと思う。 監視最高。