Pragmatic ball boy

iOSを中心にやってる万年球拾いの老害エンジニアメモ

iOS

iOSのFrameworkのVersionについて

iOS

Frameworkにはversionがいくつかあってそれらの違いの雑な説明です。 その1 ひとつはお馴染みのinfo.plistに書くやつ これはちょっと省きます その2 Umbrella Headerに書いてあるやつ FOUNDATION_EXPORT double FwVersionNumber; FOUNDATION_EXPORT const un…

AutolayoutでレイアウトしたViewを外して元に戻す

InterfaceBuilderやStoryboardでAutolayoutを使って配置したViewをremoveFromSuperviewしてから、 再度addSubviewしたい!ということがたまにあります。 普通にremoveFromSuperviewしてaddSubviewすると元には戻りません。 なぜならremoveFromSuperviewした…

独自のNotification名を追加

独自のNotification名を追加する場合はこんな書き方がよいような気がします。 extension Notification.Name { struct AppName { public static let DidLogin = Notification.Name(rawValue: "com.example.appname.didLogin") } } 通知名の文字列には通知名の…

CircleCIでipaファイルを作ろうとするとExport Failedする

ローカルではarchiveからipaにexportできるのにCircleCIだとExport Failedになる場合の対処法です。 原因としてはCircleCIの環境変数が悪さをしているようで、以下のをunsetすればなおりました unset BUNDLE_BIN_PATH unset BUNDLE_GEMFILE unset BUNDLE_ORI…

SwiftでKVOするときはObjective-Cのプロパティ名を使う

当たり前といえば当たり前なんですが、 iOSのKVO(addObserver(_:forKeyPath:options:context:))はObjective-CのNSObjectのメソッドなので、指定するkeyPathはObjective-Cのプロパティ名じゃないとだめです。 例えばUIViewのisHiddenをKVOしたい場合は↓のよう…

TwitterKitを使ってログインするときの注意点

TwitterKitを使ってログインするときの注意点を2点 1. Twitterアカウントを登録しているかで挙動が変わる TwitterKitを使ってTwitterログインするときに、TwitterのアカウントをiOSに設定しているかどうかで挙動が変わります。 (2017年1月時点) iOSの設定…

Swiftでの複数にデリゲート multicast delegate

Swiftにはweak reference arrayがないので、NSHashTableを利用します protocol SampleDelegate : class { func sampleDelegateDidFinish() } class SampleClass { let delegates = NSHashTable<AnyObject>() // AnyObjectをSampleDelegateにするとSwift3時点ではコンパ</anyobject>…

Xcode8.2からコマンドラインでシミュレータの動画が撮れる

Xcode8.2でコマンドラインでシミュレータの動画が撮れるようになって便利に スクリーンショット xcrun simctl io booted screenshot. To take a video, run the command 動画 xcrun simctl io booted recordVideo <filename>.<file extension> 実行すると Recording... (Press CTL+C to</file></filename>…

popToRootViewControllerで画面を消すとviewWillDisappearでnavigationControllerがnilになる

現象が伝えにくいので、図に表すと以下のような感じで、 TabbarController内にNavigationControllerをもたせた状態で、いくつかViewControllerをPushViewControllerします。 そして、2つ以上PushViewControllerした状態で一番上のViewControllerのナビバーを…

Swift3.0.1で若干変わったIntなどの数値型⇔AnyObjectのcast

Xcode8(Swift3.0.0)だと↓のテストは通るんですが、 import XCTest @testable import TypeTest class TypeTests: XCTestCase { func testType_WhenIntToAnyObject() { let intValue = ["hoge": Int(1) as AnyObject] XCTAssertTrue(intValue["hoge"] is Int) …

CGRectの新旧書き方対応表

古 新 CGRectGetWidth( rect ) rect.width CGRectGetHeight( rect ) rect.height CGRectGetMinX( rect ) rect.minX CGRectGetMidX( rect ) rect.midX CGRectGetMaxX( rect ) rect.maxX CGRectGetMinY( rect ) rect.minY CGRectGetMidY( rect ) rect.midY CGR…

Xcode8でテストが実行できない Could not determine bundle identifier for TEST_HOST

Xcode8でxcodebuildでtestを走らせると以下のようなエラーがでてテストが実行できなくなりました xcodebuild: error: Failed to build workspace XXX with scheme XXX. Reason: Could not determine bundle identifier for XXXTests's TEST_HOST: どうもTEST…

動画のフォトアルバムへの保存

動画のフォトアルバムへの保存 iOS8まで import AssetsLibrary ... ALAssetsLibrary().writeVideoAtPathToSavedPhotosAlbum(filePathURL) { _ in // 完了後の処理 } iOS9以降 import Photos ... PHPhotoLibrary.sharedPhotoLibrary().performChanges( { PHAs…

UITableViewCellのセパレーターを消す

セルのセパレーター消すやつ override func awakeFromNib() { separatorInset = UIEdgeInsets(top: 0, left: bounds.width, bottom: 0, right: 0) }

RxSwiftでTableView その3

RxTableViewSectionedReloadDataSourceでは複数Sectionに対応できましたが、 Section単位でreloadData()がされてしまっていました。 今回はRxTableViewSectionedAnimatedDataSourceを使ってみます RxTableViewSectionedAnimatedDataSource ViewControllerはR…

RxSwiftでTableView その2

rx_itemsWithCellIdentifierではSection1つしかダメでした。 複数Sectionを使う方法としていくつかあるっぽいのですが、 まずRXTableViewSectionedReloadDataSourceを使ってみます。 RXTableViewSectionedReloadDataSource これはRxSwiftには含まれておらず…

RxSwiftでTableView その1

RxSwiftでTableViewとdatasourceをbindingさせる方法はいくつかあるようなので1つずつ見ていきます。 今回はrx_itemsWithCellIdentifilerを使ってみます。 rx_itemsWithCellIdentifier 単にSectionが1つのリストをTableViewに表示するだけであればrx_itemsWi…

SwiftLint

Swiftでコーディング規約に沿っているかチェックするツールにSwiftLintというのがあるのでつかってみました。 SwiftLintではコーディング規約としてGithubのSwift style guildeを使っています。 使い方 $ brew install swiftlint XcodeでSwiftLintをかけるプ…

RxSwiftでログイン画面のサンプル実装

ユーザー名とパスワードを規定の文字数以上入力するとログインボタンが有効になるViewControllerをRxSwiftを使って実装してみました。 SwiftBondしか使ったことなく初めてRxSwiftを使ってみた感想としては、RxSwiftのほうが似たようなものがたくさんあり学習…

iOSでSlackのWebSocket疎通まで

やること iOSからSlackのWebSocketを使ってメッセージのやり取りをできる状態にする 事前準備 redirect urlを用意せずにモバイルアプリ単体でアクセストークンを取得するのは無理っぽいのでとりあえずテスト用のを使う テスト用のアクセストークンの取得 htt…

久しぶりにcocoapodsを使ってはまったところ

cocoapods 1.0.1 The dependency xxx is not used in any concrete target. Podfileの書き方がcocoapods 1.0系になって変わったらしく Podfileを $ pod init で生成すると # Uncomment this line to define a global platform for your project # platform :…

Crashlyticsにクラッシュレポートが送信されない

普通はFabricで手順通りにやってればクラッシュレポートは送信されるはずなんですが、なぜか送信されないってことがありました。 answersとかは動いているのでFabric自体はちゃんと取り込まれてるのになぜだ・・と思って調べたら troubleshootingに書いてあ…

3D Touch Peak, Popの使い方

1. 3D Touchの発火元となるviewの登録 UIViewControllerのregisterForPreviewingWithDelegateというメソッドを使って、3D Touchに反応するViewと、3D Touchが発生した際にハンドリングするdelegateを登録します。 override func viewDidLoad() { super.viewD…

iOS9のクイックアクション対応

ホーム画面のアプリアイコンを3D Touchすると実行されるクイックアクションの実装方法です。 Info.plistの変更 UIApplicationShortcutItemsを追加します。 例 Info.plist <key>UIApplicationShortcutItems</key> <array> <dict> <key>UIApplicationShortcutItemIconType</key> <string>UIApplicationShor</string></dict></array>…

SwiftでUnitTest時に環境変数で分岐させる

テスト対象を@testable import XXXXを使ってimportした場合に、テスト対象のコードをテスト時だけ分岐させて特定の処理を行わないようにしたりしたい場合の対処方法です。 方法としては、環境変数がセットされているかどうかでテストかどうかを判定します。 …

dynamic frameworkを使ってるプロジェクトでコマンドラインでipaファイル作成

Swiftでサブプロジェクトのモジュールをdynamic frameworkで取り込む場合にコマンドラインでipaファイルを作成する手順です。 環境:Xcode7.1 従来のやりかたではできなかったのでメモしておきます 発生した問題 以前Objective-Cでstatic libraryでやってい…

UnitTestでNSUserDefaultsに保存したデータを消す方法

UnitTestだとremoveObjectForKeyや NSUserDefaults.standardUserDefaults().removeObjectForKey("key") resetStandartUserDefaultsを呼んでもデータが消えません NSUserDefaults.resetStandardUserDefaults() 解決方法 setObjectでnilを突っ込む NSUserDefau…

Swift Bond v4

Swift BondがSwift2.0に対応し、更にインターフェースが大きくかわりv4としてmasterに統合されました。 主な変更点としては、 クラス名を刷新 これまではBond、Dynamicといった意味不明なクラス名がObservable, EventProducerに変わりわかりやすくなりました…

Swift2でArrayにArrayをinsertする

これまではsplice:atIndexでしたが items.splice(insertItems, atIndex: items.endIndex) Swift2(beta6以降)からinsertContentsOf:atに変わりました items.insertContentsOf(insertItems, at: 1) 例 var items = ["a", "b", "c"] let insertItems = ["1", "2…

iPadのマルチタスク(SlideOver, SplitView)対応

iOS9からiPadでmultitaskingが使えるようになります。 SlideOverはiPad Air以降、SplitViewはiPad Air2以降で利用できます。 SlideOver, SplitViewに対応したアプリの作成方法 新規で作成する場合 Xcode7で新しいプロジェクトを作ると特に何もしなくてもよい…