OmniAICreator/Qiita-1.07M huggingface dataset:
AVAssetExportSessionで多数の動画を合成するときにハマッたお話

## AVAssetExportSessionの罠？

拙作のアプリ[ふぉとむぐ](https://itunes.apple.com/jp/app/ふぉとむぐ/id1251727875?mt=8)では、`AVAssetExportSession`を用いて多数の動画を合成する機能を実装したのですが、そこで思わぬ罠にはまってしまいました。

はじめに結果を申し上げると、この内容をApple Developer Technical Supportに報告したところ、iOS 10.3 の時点では不具合(というより制限？)のため、回避策を試して欲しいとのことでした。

ただ回答で来た方法ではうまくいかなったため、これをアレンジして回避することができたので、ここにその方法をまとめることにしました。

### 起こった問題

従来は動画の合成を行う際、下記の図のようにしていました。

![old.png](https://qiita-image-store.s3.amazonaws.com/0/25727/2a051470-4a77-d628-501e-e59e7e6d4b79.png)

* 各入力動画(`AVAsset`)から`AVAssetTrack`を取り出し、その都度`AVCompositionTrack`を追加
(つまり動画の数だけ`AVCompositionTrack`を生成していた)
* 各`AVCompositionTrack`に対応する`AVVideoCompositionLayerInstruction`を生成し、TransformやOpacityRampを適用
* ひとつの`AVVideoCompositionInstruction`に、各入力動画の対応する`AVVideoCompositionLayerInstruction`を設定し、これを書き出す

このような方法で動画の合成を行うと、 **多数の動画を入力したとき以下のエラーで書き出しに失敗します！**

> Error Domain=AVFoundationErrorDomain Code=-11839 "Cannot Decode" UserInfo={NSUnderlyingError=0x174247020 {Error Domain=NSOSStatusErrorDomain Code=-12913 "(null)"}, NSLocalizedFailureReason=The decoder required for this media is busy., NSLocalizedRecoverySuggestion=Stop any other actions that decode media and try again., NSLocalizedDescription=Cannot Decode}

(iPhone 6sでは15〜16個の動画合成で発生。シミュレータでは発生しない)

エラー内容とAppleからの回答から、`AVCompositionTrack`はビデオデコーダのリソースを抑えたまま解放しない問題があるらしく、多量にインスタンス化するとリソース不足でエラーが起きてしまうようです。

### 解決策

お察しのとおり、`AVCompositionTrack`を使い回して、必要以上に生成しなければ解決できます。
Appleからの回答では、2つの`AVCompositionTrack`を交互に使えばいいとのことでしたがうまくいかなかったため、以下の図のようにしました。

![new.png](https://qiita-image-store.s3.amazonaws.com/0/25727/d38c9747-8345-89d4-6c70-a10e2752241c.png)

* `AVCompositionTrack`を3つ用意する
    * Main: トランジション時間にかからない、各動画単独再生のトラック
    * Transition Source: トランジション中の遷移元となる動画用トラック
    * Transition Destination: トランジション中の遷移先となる動画用トラック
* `AVVideoCompositionInstruction`はトランジション時間ごとに別々に用意する
    * 非トランジション区間はMainトラックに追加した`AVVideoCompositionLayerInsturction`のみ参照
    * トランジション区間はSource, Destinationトラック2つの`AVVideoCompositionLayerInsturction`を参照

## その他・注意しておきたいところ

`AVAssetExportSession`では他にも、こんなところが躓きやすい...

### export中のエラー

時間の指定が間違っていないか確認しましょう。

* `AVVideoCompositionInstruction`の`timeRange`は"空白の区間"があってはいけない。つまり`prevInstruction.timeRange.end == instruction.timeRange.start`である必要がある
* `AVVideoCompositionInstruction`の`timeRange`と、`insertTimeRange()`で追加した動画の位置と長さは一致していなければならない(おそらく)

### exportは成功したけど動画が真っ黒

`AVVideoCompositionLayerInstruction`のTransformを正しく設定しないとイイ位置に来てくれません。

* Live Photosから取り出した`AVAssetTrack`の`preferredTransform.tx, ty`は画像解像度に準拠しない値になっていることがある
(Live Photos動画の解像度とフレームレートが、リリース当初と最近で仕様が違うため？)
* 出力解像度を変える(スケーリングする)場合、CropRectangleを指定しないとスケールしない場合がある
Carthageでライブラリインストール


Carthageでライブラリをインストール手順について記載します。
今回は例として、ローカルDBライブラリ `Realm` をインストールします。

※Realm
https://realm.io/docs/swift/latest/

#### 環境

macOS 10.12.5 (Sierra)
Xcode v8.3.3
Homebrew 1.2.1
Carthage 0.20.1

### 事前説明

##### Carthageとは

Swift製のライブラリ管理ツール。
ライブラリを事前にビルドし、フレームワークを作成してくれるので、コンパイル時間を短くしてくれる。

※ CocoaPodsとの違い
CocoaPodsも同じくライブラリ管理ツール。都度ライブラリをビルド・更新するCocoaPodsに対し、Carthageは事前にビルドしてフレームワーク作成をするので、コンパイル時間が短くなる。個人的にはCarthageの方がおすすめ。

### 手順

1. 準備：homebrewインストール
2. 準備：carthageインストール
3. cartfileを作成
4. ライブラリインストール
5. Xcodeの設定

### 1. 準備：homebrewインストール

homebrewとは、Mac OS X オペレーティング・システム上でソフトウェアの導入を単純化するパッケージ管理システム。要は、homebrewを使うと、様々な便利パッケージなどをインストールできる。

※補足：homebrewメリット

- 依存関係でインストールされるソフトが少ない。インストールしたいパッケージに不要なソフトがついでにインストールされてしまう、ということが少ない。
- 極力Macに入っているものを使ってくれる。パッケージ導入時のシステムへの負担や、インストールにかかる時間が比較的少なく済む。
- スーパーユーザでコマンドを実行する必要がない。

##### インストール方法

[Homebrewの公式ページ](http://brew.sh/)に書かれているコマンドを叩く。

```ruby
$ /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
```

注意：fishshellなどを用いていて上記のコマンドが叩けない場合がある。その際は `bash`と打って、bashに切り替える。

### 2. 準備：carthageインストール

##### インストール方法

homebrewインストール後、下記コマンドを叩く。

```ruby
$ brew install carthage
```

### 3. cartfileを作成

carthageは、Cartfileに記載されたライブラリをインストールする仕様である。
まず、Cartfileを自分で作成する。例えば `$ touch Cartfile` コマンドで。

次にCartfileを編集する。 vimを使うなら、 `$ vi Cartfile` コマンド。
下記を記載しよう。

```vim
github "realm/realm-cocoa"
```

ここに書くものは、ライブラリのgithubトップページのReadmeに基本的に記載されているので、そちらを参照にする。
ここで、バージョンはコミット番号を指定したりできるが、今回は省略。

### 4. ライブラリインストール

Cartfileの作業が完了したら、carthageのupdateを実行する。
ライブラリのバイナリを生成するので、少々時間がかかる。

```ruby
$ carthage update
$ carthage update --platform ios # os指定したい場合はコレ
```

これでライブラリのインストール自体は完了。次にXcodeの設定をする。
もしgitでソース管理している場合、バイナリをpushしてしまうとgitが壊れることがあるので要注意。 `Carthage/` 配下にあるファイルはgitignoreしておいた方がよい。

### 5. Xcodeの設定

2つ設定する必要がある。

- Linked Frameworks and Libraries にライブラリ追加
- Build Phasesに追加

##### Linked Frameworks and Libraries にライブラリ追加

`起動したApplication` > `TARGETS` > `Generalタブ` > `Linked Frameworks and Libraries` にライブラリのframeworkを追加する。

今回は、 `Carthage/Build/iOS/` 配下にある `Realm.framework` と `RealmSwift.framework` を追加しよう。drag-and-dropで追加できる。

これで、RealmDBを利用できるようになる。

##### Build Phasesに追加

アプリケーションを申請する際に、iTunesConnectの不具合を回避するために、この手順は必須。

`起動したApplication` > `TARGETS` > `Build Phasesタブ` にある `+` ボタンをクリック、 `New Run Script Phase`をクリックしてRun Scriptを追加する。

黒背景部分に下記を記載する。どのライブラリでも共通。

```
/usr/local/bin/carthage copy-frameworks
```

Iput Filesに追加するライブラリ情報を下記のように記載する。

```
$(SRCROOT)/Carthage/Build/iOS/Realm.framework 
$(SRCROOT)/Carthage/Build/iOS/RealmSwift.framework
```

### まとめ、補足

これでRealmライブラリの導入が完了です。コード上で `import RealmSwift` ができるはずです。もしできなかったらXcodeを再起動しましょう。

ちなみに、git上にライブラリのバイナリをアップロードしないことがおすすめなので、複数人でgit利用している場合は各々で `carthage update` しないといけなかったり。その場合、ライブラリのバージョンを揃えないといけなかったり。

その説明は、また別の機会に。
eclipseでJava Streamの改行をいい感じに

# 手順
1. ウィンドウ -> 設定 を開く
1. Java -> コード・スタイル -> フォーマッター よりアクティブなプロファイルの編集ボタン押下
1. 行折り返しタブ選択
1. 関数呼び出し -> 修飾呼び出し選択
1. 修飾呼び出しの設定
    * 行の折り返しポリシーを 必要時以外は最初の要素以外の全ての要素を折り返す にする
    * 行が最大行幅より短くても矯正分割にチェックを付ける
    * インデント・ポリシー を 1つごとにインデント にする
すると いい感じ になります。


************************************************************
# 参考リンク
[stackoverflow](https://stackoverflow.com/questions/6275785/wrapping-chained-method-calls-on-a-separate-line-in-eclipse-for-java)
異体字同一視検索を実装メモ


## 環境
C#、Linq to Entity、SQL Serverです。

## はじめに
以下を参考にさせていただきました。（感謝）
[karak 異体字同一視検索](http://www.karak.jp/chinese/variants.html)

## 異体字とは

http://d.hatena.ne.jp/keyword/%B0%DB%C2%CE%BB%FA

標準の字体と同じ意味・発音を持つが、表記に差異がある文字のこと。手書きによる個人差から生じたもの、新字・旧字（簡体・繁体）の違いによるものがある。

## 目的
峰さん、嶺さん、峯さん、いっぱいいますね。
いざ検索しようとして、みねってどんな字だったっけ？全然ヒットしない！
という事もあろうかと思います。
同様に浜さん、濱さん、濵さん、なかなか検索ヒットできません。

さらにたとえば濵嵜（はまざき）さんという人を検索したい場合、なかなか変換ではでてこないですし、ひらがなも、はまざき・はまさき　どっちだったけ？となりがちです。

という時に、「浜」でも「濱」「濵」さんが検索ヒットできるように異体字を同一視して検索できるように実装しました。

## 異体字辞書の作成
まずは異体字の辞書を用意しました。
DB化するか悩んだのですが、漢字であるしほぼ変わらないであろうことからコードに書いてます。
具体的には以下のような感じです。

```csharp
var variants = new List<KeyValuePair<string, string>>()
{
    new KeyValuePair<string, string>("濱", "濱|頻|濵|浜|滨"),
    new KeyValuePair<string, string>("浜", "浜|濵|濱"),
    new KeyValuePair<string, string>("領", "領|阾|袊|嶺|岭|领"),
    new KeyValuePair<string, string>("岭", "岭|領|岺|嶺"),
    new KeyValuePair<string, string>("嶺", "嶺|領|岭"),
    ...
}
```

## 検索用文字列の変換
浜で検索した場合に正規表現で検索したいので、
浜→[浜|濵|濱]と変換します。

たとえば濵嵜（はまざき）さんという人を検索したい場合は検索ワードとしては以下で正規表現で検索するといい感じになりそうです。
 [浜|濵|濱][崎|隑|陭|徛|﨑|㟢|碕|埼|嵜]

浜崎 → [浜|濵|濱][崎|隑|陭|徛|﨑|㟢|碕|埼|嵜]　という変換は文字列を1文字ずつ先ほどの辞書を元に変換します。

```csharp

        public static string get(string word)
        {
            var result = "";

            //異体字一覧（辞書）を取得する
            var vari = Dictionaly.GetDictionaly();

            //文字列を1文字ずつに分割して処理する
            foreach (char c in word)
            {
                //文字が異体字リストにあれば、異体字を取得する。
                //ex. 浜 →  [浜|濵|濱]
                var f = vari.FirstOrDefault(x => x.Key == c.ToString());

                //[]で囲む
                if (f.Key != null)
                {
                    result += "[" + f.Value + "]";
                }
                else
                {
                    result += c;
                }

            }

            //結果を返す
            return result;
        }

```

## 検索

Linq to Entityに投げ込みます。

Linq to Entityでは正規表現をそのまま検索できないので、SqlFunctionsを使います。
SqlFunctionsはSystem.Data.Objects.SqlClientにあります。

```csharp
using System.Data.Objects.SqlClient;

//regStringsが検索ワード（[浜|濵|濱][崎|隑|陭|徛|﨑|㟢|碕|埼|嵜]）等
var query = from c in db.Entity
    where SqlFunctions.PatIndex("%" + regStrings + "%", c.Modid) == 1
    select c;
    
```


# 参考

・[異体字データベース](https://github.com/cjkvi/cjkvi-variants)

・[Linq to Entityでの正規表現について（stackoverflow）](https://stackoverflow.com/questions/40234780/c-sharp-linq-how-to-check-if-variable-starts-with-m-where-is-numeric)


他にも検索の幅を増やしたい場合には、LinqKit等を使えばより柔軟になりそうです。
GitLab導入してみた

# 背景
GitHub+hogehogeでの開発が主流になっている昨今、自社ではBacklogのみで
ソース管理やプロジェクト管理、課題管理などをやっていた。
けれど、社外に公開したくない情報やソースも時たま出てきていて、申し訳程度にある
社内専用のGitBucketを活用していた。

# 転機
ある時、社内のGitBucketを使いたいなと思って、アクセスすると画面が一向に表示されない。
原因調査のために、sshでログインしたいけどログインID・Passを誰も覚えていなかったので、
仕方なく、新しくGitサーバーを立てようと思った。

# 選定
GitのOSSといってもGitBucketくらいしか知らなかったので、幾つかの記事を参考にして、
最終的にGitLabを導入した。
選定基準として以下の要素を考えていた。
```
　・Github likeであること。　←これかなり大事だった！
　・他サービスとの連携がしやすいこと。　←後々の開発にも継続運用可能！
　・UIがリッチで、つい使いたくなること。　
　・導入が容易なこと。
　・継続して開発されていること。
```
上記の条件で合致したのは、GitBucketとGitLab。
最終判断としては、[この記事](http://knowledge.sakura.ad.jp/tech/3005/)を参考にしたのと、
もともとGitBucketを使っていたので、今回は新しいものに挑戦したくなり、GitLabにした。

# 導入方法
サーバーはCentOS7.1。導入方法は、[GitLabの公式ドキュメント](https://about.gitlab.com/installation/#centos-7)を参考にしたが、ものすごく簡単だった。

# 導入してみて
導入したが、予想通りいい感じでGithubライクな開発手法が適用できる。さらに、プライベートリポジトリが無料なことで、
公開したくないプライベートソースもソース管理できるので、開発好きなエンジニアたまらないのではないかと。

また、masterのプロテクト機能やユーザー・グループごとのアクセス権限管理などBacklogでは出来ない
細かな機能もデフォルトで付いているので、正しく運用されればモダンな開発スタイルが確立できると思われる。

ただ、これまでGithubを用いた開発を行っていないため、画面の操作性であったり細かな機能に対して煩わしさを
覚える可能性は高い。

これはどうしても慣れることが大事なので、積極的に活用していきたいと思う。
電子署名のサンプルコード（JAVA）

```java:サンプルプログラム
import java.security.InvalidKeyException;
import java.security.Key;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.SecureRandom;
import java.security.Signature;
import java.security.SignatureException;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 * ECDSA 160bitで署名と署名の検証を行うサンプル
 */
public class ECDSASignature {

    public static void main(String argv[]){
        signatureTest();
    }
    
    public static void signatureTest(){

        /**
         * キーペアを発行
         */
        KeyPairGenerator keyPairGenerator = null;
        try {
            keyPairGenerator = KeyPairGenerator.getInstance("EC");
        } catch (NoSuchAlgorithmException ex) {
            return;
        }
        SecureRandom secureRandom = new SecureRandom();
        keyPairGenerator.initialize(160, secureRandom);
        KeyPair pair = keyPairGenerator.generateKeyPair();
        Key publicKey = pair.getPublic();
        Key privateKey = pair.getPrivate();        
        
        // とりあえず、ただの文字列で
        String hako = "Qiitaは、プログラマのための技術情報共有サービスです。";
        
        /**
         * 秘密鍵で署名を行う（ECDSA 160bit）
         */
        byte[] sign = null;
        try {
            Signature signatureSign = null;
            signatureSign = Signature.getInstance("NONEwithECDSA");
            signatureSign.initSign((PrivateKey)privateKey, secureRandom);
            signatureSign.update(hako.getBytes());
            sign = signatureSign.sign();
            
            System.out.println("sign: " + new String(sign));

        } catch (InvalidKeyException | NoSuchAlgorithmException | SignatureException ex) {
            Logger.getLogger(ECDSASignature.class.getName()).log(Level.SEVERE, null, ex);
        }
        
        /**
         * 公開鍵で署名の検証を行う
         */
        Signature signatureVerify = null;
        try {
            signatureVerify = Signature.getInstance("NONEwithECDSA");
            signatureVerify.initVerify((PublicKey)publicKey);
            signatureVerify.update(hako.getBytes());
            boolean verifyResult = signatureVerify.verify(sign);
            System.out.println(verifyResult ? "署名OK" : "署名NG");
            
        } catch (NoSuchAlgorithmException | InvalidKeyException | SignatureException e) {
            Logger.getLogger(ECDSASignature.class.getName()).log(Level.SEVERE, null, e);
        }
        
    }

}
```

```Text:実行結果
sign: （ 省略 ）
署名OK
```
ebiten でフィールド移動（改良版）

[以前にも同じような記事](http://qiita.com/zenwerk/items/be659825635430ca3d3b)を書きましたが、動作を改善と実装をシンプルにした改善版を作りました。

## 概要
フィールド移動に関しては、前回の記事の[概要](http://qiita.com/zenwerk/items/be659825635430ca3d3b#%E3%83%95%E3%82%A3%E3%83%BC%E3%83%AB%E3%83%89%E3%81%AE%E7%A7%BB%E5%8B%95)と同じで、描画用に対象物のオフセット座標を計算する処理が必要になります。
このオフセット計算処理を行う処理をカメラという構造体として実装します。

## コード
- 全体のコードは以下です。
	- https://github.com/zenwerk/ebiten-example/tree/master/camera

### 最初の実装
- 捉えたいオブジェクトをカメラの中心に捉える実装です
	- [Link](https://github.com/zenwerk/ebiten-example/blob/e6288cf3759d56381fb57716e494a9aeddc97eb8/camera/camera/camera.go#L14-L18)

```go
// SimpleMove は対象物を常に中心に捉える
func (c *Camera) SimpleMove(x, y int) {
	// x,y座標に常に画面の半分の座標の値をオフセットとして与える
	c.X = (c.Width / 2) - x
	c.Y = (c.Height / 2) - y
}
```

カメラの座標(=オフセット座標)に常に画面範囲の半分を加え続けることで、常に対象物を中心に捉えるようにしています。

### 実行結果

![2dcamera_simple.gif](https://qiita-image-store.s3.amazonaws.com/0/4428/4f9cf073-dc23-2289-ccae-684a13cac284.gif "2dcamera_simple.gif")

### 問題点
最初の実装は、とても簡単なのですが、実行結果から分かるようにフィールドの端に到達すると、端に空白領域が表示されてしまいます。
フィールドの端として意図した実装をしていても、対象物を常に中心に捉えるため、カメラのオフセット座標がフィールドの端の座標を越えてしまうからです。

イメージとしては以下のようになります。

![simple_camera.png](https://qiita-image-store.s3.amazonaws.com/0/4428/18282d4d-a4f2-79f6-a099-c3074173e3f0.png "simple_camera.png")

キャラクターが画面端に移動した際に、赤色の空白領域が発生していしまいます。

### 改善した実装
最初の実装で発生した、画面端の空白領域を生まないためには、カメラのオフセットが実装者が想定してる画面端の座標に到達したらオフセットの値を更新しない、という処理が必要になります。

動作イメージとしては以下のようになります。

![improved_camera.png](https://qiita-image-store.s3.amazonaws.com/0/4428/0ff1d922-05ed-19f2-2280-a533bd523ee4.png "improved_camera.png")

動作イメージにあるように、オフセットの最大値は表示領域の縦横の値とフィールドの縦横の値の差分になります。この最大値を超えてしまうと、空白領域が生まれてしまいます。

#### 実装
- 上記の点を考慮した実装は以下です。
	- [Link](https://github.com/zenwerk/ebiten-example/blob/e6288cf3759d56381fb57716e494a9aeddc97eb8/camera/camera/camera.go#L20-L44)

```go
// Move は対象物を常に中心に捉えるが, 画面端に到達した場合はカメラを移動しない
func (c *Camera) Move(x, y int) {
	maxXOffset := -(c.MaxWidth - c.Width)
	maxYOffset := -(c.MaxHeight - c.Height)

	restX := (c.Width / 2) - x
	restY := (c.Height / 2) - y

	// オフセット値の調整
	if restX > 0 {
		c.X = 0
	} else if restX < maxXOffset {
		c.X = maxXOffset
	} else {
		c.X = restX
	}

	if restY > 0 {
		c.Y = 0
	} else if restY < maxYOffset {
		c.Y = maxYOffset
	} else {
		c.Y = restY
	}
}
```

#### 実行結果

![2dcamera_offsetlimit.gif](https://qiita-image-store.s3.amazonaws.com/0/4428/e9e0f472-c0c8-4bc8-174c-d6d3536889c1.gif "2dcamera_offsetlimit.gif")

空白領域が生まれなくなりました。

## まとめ
この手の処理は実装してみると簡単ですが、考えを整理するのが大変でした。

## 参考文献
- [StackOverflow - Add scrolling to a platformer in pygame](https://stackoverflow.com/a/14357169)
	- 実装と考え方はほぼこの記事から来ています
	- 実装コードも python から単純に Go(ebiten) にポートしただけです
ebiten で衝突判定（改良版）

[以前にも同じような記事](http://qiita.com/zenwerk/items/e1d372842a6cfb53af7e)を書きましたが、衝突判定部分のコードが煩雑＋動作がおかしい部分があったので書き直しました。

## コード
- 全体は以下
	- https://github.com/zenwerk/ebiten-example/tree/master/collision

#### 衝突判定関数
- 2つの画像(四角形)a, b の座標が交差しているか判断します

```go
func (p *Player) Intersect(block *Block) bool {
	ax, ay := p.X, p.Y
	aw, ah := p.Image.Size()

	bx, by := block.X, block.Y
	bw, bh := block.Image.Size()

	// aの左上 < bの右下 かつ aの右下 > bの左上
	return (ax < bx+bw && ay < by+bh) && (ax+aw > bx && ay+ah > by)
}
```

#### 移動判定関数
- キャラクターが移動しているときに、衝突した際の動作
	- 以前のコードでは衝突判定と移動判定が混ざっていたため煩雑になっていた
	- 移動判定はX軸, Y軸でそれぞれ別に行う必要がある
		- そうしないと斜め移動の衝突時におかしな動作をする

```go
func (p *Player) Move(blocks []*Block) {
	var dx, dy int
	if ebiten.IsKeyPressed(ebiten.KeyLeft) {
		dx -= 2
	}
	if ebiten.IsKeyPressed(ebiten.KeyRight) {
		dx += 2
	}
	if ebiten.IsKeyPressed(ebiten.KeyUp) {
		dy -= 2
	}
	if ebiten.IsKeyPressed(ebiten.KeyDown) {
		dy += 2
	}

	if p.X != 0 {
		p.moveX(dx, blocks)
	}
	if p.Y != 0 {
		p.moveY(dy, blocks)
	}
}

func (p *Player) moveX(dx int, blocks []*Block) {
	p.X += dx
	// 衝突判定
	for _, b := range blocks {
		if !p.Intersect(b) {
			continue
		}
		// 右に移動して衝突
		if dx > 0 {
			// プレイヤーの右端の座標がブロックの左端座標になるようにする
			p.X = b.X - p.Width()
		}
		// 左に移動して衝突
		if dx < 0 {
			// プレイヤーの左端の座標がブロックの右端座標になるようにする
			p.X = b.X + b.Width()
		}
	}
}

func (p *Player) moveY(dy int, blocks []*Block) {
	p.Y += dy
	// 衝突判定
	for _, b := range blocks {
		if !p.Intersect(b) {
			continue
		}
		// 下に移動して衝突
		if dy > 0 {
			// プレイヤーの下端の座標がブロックの上端座標になるようにする
			p.Y = b.Y - p.Height()
		}
		// 上に移動して衝突
		if dy < 0 {
			// プレイヤーの上端の座標がブロックの下端座標になるようにする
			p.Y = b.Y + b.Height()
		}
	}
}
```

## 実行結果
![2dcollision.gif](https://qiita-image-store.s3.amazonaws.com/0/4428/d8678a1d-37b6-c8ba-2e2a-43814ea010b0.gif "2dcollision.gif")

## まとめ
前の実装よりスッキリしわかりやすくなりました。

## 参考文献
- [Rect Collision Response](http://www.pygame.org/project-Rect+Collision+Response-1061-.html)
Delphi で Android 端末のバッテリーレベルを特定する

バッテリーの充電レベルを知りたいことってありますよね。
Android では [BatteryManager](https://developer.android.com/reference/android/os/BatteryManager.html?hl=ja) によってバッテリーに関する情報がインテントでブロードキャストされています。

充電レベルを調べるには、バッテリーレベル(level)と、段階(scale)を取り出して、％を計算します。
このコードは、Android Developersのトレーニング記事[「バッテリー レベルと充電状態を監視する」](https://developer.android.com/training/monitoring-device-state/battery-monitoring.html?hl=ja)を参考にしています。

##サンプルコード
フォーム上にボタンとリストボックスを置き

- ボタンを押すと充電レベルを検出する
- 検出した％の値をリストボックスに書き出す

という処理を記述しています。(10.2 Tokyo, Nexus 5, Android 5.1.1で確認)

```delphi
unit Unit1;

interface

uses
  System.SysUtils, System.Types, System.UITypes, System.Classes, System.Variants,
  FMX.Types, FMX.Controls, FMX.Forms, FMX.Graphics, FMX.Dialogs,
  FMX.Controls.Presentation, FMX.StdCtrls, FMX.Layouts, FMX.ListBox,
  Androidapi.Helpers, Androidapi.JNI.GraphicsContentViewText,
  Androidapi.JNI.JavaTypes
  ;

type
  TForm1 = class(TForm)
    ListBox1: TListBox;
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { private 宣言 }
  public
    { public 宣言 }
  end;

var
  Form1: TForm1;

implementation

{$R *.fmx}

procedure TForm1.Button1Click(Sender: TObject);
var
  ifl: JIntentFilter;
  ctx: JContext;
  bStatus: JIntent;
  level, scale: Integer;
begin
  // 現在の充電状態を特定(バッテリーステータス インテントを取得)
  ifl := TJintentFilter.JavaClass.init(TJIntent.JavaClass.ACTION_BATTERY_CHANGED);
  ctx := TAndroidHelper.Context;
  bStatus := ctx.registerReceiver(nil, ifl);

  // BatteryManager.EXTRA_LEVEL の実態は levelという文字列
  // BatteryManager.EXTRA_SCALE の実態は scaleという文字列
  level := bStatus.getIntExtra(StringToJString('level'), -1);
  scale := bStatus.getIntExtra(StringToJstring('scale'), -1);

  ListBox1.Items.Add('Battery');
  // 充電状態の %を計算
  ListBox1.Items.Add(IntToStr((100*level) div scale));
end;

end.

```
Navigation Drawer上にRecyclerViewやViewPagerを設定しているときに、横スクロールの動きをいい感じにするTips

DrawerLayout上にRecyclerViewやViewPagerを設定しても、横方向のスクロールはDrawerを閉じる動きが優先され、縦方向のスクロールやTabの切り替えなどが閉じる動きに引っ張られ、気持ちよく操作出来ません。

下記の設定で、DrawerLayout上で横スクロール操作した時に発生するDrawerを閉じる動きを殺すことが出来ます。
Drawerを閉じる操作も、Drawerの外側から横スクロールすることで可能です。

```Java
    // DrawerLayoutを設定しているActivityなどで
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        DrawerLayout.DrawerListener drawerListener = new DrawerLayout.DrawerListener() {
            @Override
            public void onDrawerSlide(View drawerView, float slideOffset) {
            }

            @Override
            public void onDrawerOpened(View drawerView) {
                // 開いた直後のドロア上の横スクロールを無効化
                mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_OPEN);
            }

            @Override
            public void onDrawerClosed(View drawerView) {
                // 閉じた時, 横スクロールを有効化
                mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_UNDEFINED);
            }

            @Override
            public void onDrawerStateChanged(int newState) {
                // ドロアが開いている状態で状態に変化があり,再度ドロアが開いた状態になったとき, ドロア上の横スクロールを無効化
                if (newState == DrawerLayout.STATE_IDLE && mDrawerLayout.isDrawerOpen(Gravity.LEFT)) {
                    mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_OPEN);
                }
            }
        };

        mDrawerLayout.addDrawerListener(drawerListener);
        mDrawerLayout.setOnTouchListener((v, event) -> {
            // ドロアの外側に触れた時, 横スクロールを有効化
            if (mDrawerLayout.isDrawerOpen(Gravity.LEFT) && event.getAction() == MotionEvent.ACTION_DOWN) {
                mDrawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_UNDEFINED);
            }
            return false;
        });
    }

```
いまさら CentOS7系を触ってみる

# ほんにいまさら
家に立てるサーバ、、といっても自分メモ程度のwebをひっそり運用してはや１０数年ｗ
いっとき Fedora で運用するもメンテナンス更新期限が短い事をしらず毎年OSを更新してたときもありますが、CentOS6系 に乗り換えてからそういう煩わしいことから多少は解放されたと思ったら、CentOS6 も メンテナンス更新期限 2020年という（東京オリンピックか！）ことで、そろそろ 7系も触っていないとなーと重い腰をあげつつある今日このごろ
※vagrantで触ってるだけだけどねｗ

# とりあえずりんく
分かり易い感じのサイトが沢山あるのでそのリンク

> [CentOS7で使われているsystemctlについて少しまとめた](http://qiita.com/tukiyo3/items/092fc32318bd3d1a0846)
> [RHEL6→RHEL7で変更された主要コマンドまとめ](https://oss.sios.com/yorozu-blog/rhel6-rhel7change)
> [CentOS6とCentOS7の比較表](http://qiita.com/sion_cojp/items/115e1671fcbc8f214aee)
> [【まとめ】CentOS7とCentOS6以前のバージョンとの違いとは？](https://eng-entrance.com/linux-distribution-centos7)
rubyにおけるクラスとインスタンスについて

# クラスとインスタンスについて

クラスが設計図でその設計図から作られるものがインスタンスになります。クラスに情報を付加してインスタンスを生成することもできます。


# classの定義方法

```ruby:test

class Menu
end

```

これでクラスの定義はできます。ただし、下記注意。

* class名は大文字で始める

# classの構成要素

## returnとputsの違い

returnは値を返し、putsは出力をする。

## インスタンス変数

```ruby:test

class Foo
  def initialize # Foo.new したら呼ばれるメソッド
    @var = "val"
  end
  def puts_var
    puts @var
  end
  def var=(var) # attr_writer :var するのと同じ
    @var = var # @var と var は別の変数
  end
end

f = Foo.new
f.puts_val # => val

f.var = "bar"
f.puts_val # => bar


```

インスタンス変数は@で定義される。


## attr_accessorについて

```ruby:test

class Menu
  attr_accessor :name
  attr_accessor :price
end

```

上記のようにクラスに対して変数で情報を付与することができます。

* attr_accessor – セッタとゲッタを共に定義する
* attr_reader – ゲッタのみを定義する
* attr_writer – セッタのみを定義する

### インスタンスメソッド内でインスタンス変数を扱う場合

```ruby:test

class Menu
 def show_name
  puts "#{self.name}"
 end
end
menu1 = Menu.new
menu1.name = "太郎"
menu1.show_name

```
上記のようにselfでインスタンスを指すことができる。self=menu1=Menuになっている。

## クラスとインスタンスのメソッド

### クラスメソッド

```ruby:test

class Menu
  def self.info
   puts "hogehoge"
  end
  class << self
    def info2
      puts "hoge2"
    end
  end
  define_singleton_method(:info3){
    puts "hoge3"
  }
  extend Module.new{
    def info4
      puts "hoge4"
    end
  }
end
Menu.info
Menu.info2
Menu.info3
Menu.info4

```

#### initializeメソッド


```ruby:test

class Menu
 def initialize
  puts "hogehoge"
 end
end
Menu.info
# 出力 hogehoge
```



クラスからインスタンスを生成した際に自動で行なわれるメソッド。


### インスタンスメソッド

```ruby:test

class Menu
 def info
  puts "hogehoge"
 end
end
menu1 = Menu.new
menu1.info

```

### クラスメソッドとインスタンスメソッドの使い分け

クラスメソッド、インスタンスメソッド、どちらを使っても出力内容は変わらないことがありますが基本はクラス自身のメソッド、共通のメソッドはクラスメソッド、個々のものはインスタンスメソッドで管理しておくとあとで変更した際に楽そう。

## クラスの継承について

クラスは親クラスから子クラスを作り、一部の仕様を共有したクラスを複数作れる。

```ruby:test

class 小クラス < 親クラス

end

```
* 親クラス（super class）
* 子クラス(sub class)
SmartGit > bug? > 複数のファイルがUntrackedになった

WIP (Work in progress)

```txt:動作環境
Windows 7 Pro (32bit)
SmartGit Version 17.0.4 #10132
```

featureブランチを切って作業して、masterにマージをする、ということを繰り返していた。

ふと気づくと２つのファイルがUntrackedになっている。

新しく切ったfeatureブランチではUntrackedになっており、マージ前のmasterではソースとして含まれている。

ブランチを切った時にビルドが中途半端だったのだろうか。
(２つのファイルはビルドが正常終了した時に生成されるファイル?）。

これらのファイルはリポジトリに加えなくても良い気もするが、はっきりとは理解していないため加えている。
IntelliJでファイルを違うファイルにマッピングしてしまったときの解決方法

IntelliJってファイルを作るときに拡張子をつけてないとこんな画面がでて、ファイルのタイプを指定してね。って言われるのですが
<img width="520" alt="Screen Shot 2017-08-01 at 09.06.06.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/32856/a52c5f04-4cb4-6c66-6ef7-7eb55b9d3489.jpeg">

ここで例えば、hoge.javaというファイルをJavaのパッケージではないフォルダにコピーするときなどに、このダイアログが出て、Textにしてしまったとします。
そうすると、hoge.javaはTextファイルという情報がIntelliJに登録されてしまい、一旦削除して、再作成してもTextファイルとして認識されてしまいますし、hoge.javaというファイルを作ろうとすると"intellij mapped to not java"みたいなエラーが出てファイルを作れなくなってしまいます。

この場合はIntelliJの設定を開いて、"File Types"で検索するか、Editor > File Typesで
ファイルタイプを選択し、登録されたパターンを削除することで解決できます。
<img width="835" alt="Screen Shot 2017-08-01 at 09.12.29.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/32856/f0351c5b-5d7c-2c83-1522-3ec11962260a.jpeg">
Windows10 IoT CoreをHyper-Vで仮想化

`I wrote it in English in the comment section.`

##◆はじめに
**※2017/08/06 Windows10 IoT Core仮想化の現実解はHyper-VでもVirtualboxでもVMware Workstation Playerでもなく「VMware WorkStation Pro」だったため、後日VMwareでの仮想化手順を別記する予定。**

流行のIoT用マイコンボードを趣味で買うほどお金が無いため仮想化にトライ。無事成功。
全ての環境を無償で手に入れてVisual Studio2017 community＋C#でプログラム作ってリモートデバッグして遊べる。

ちなみに、下記サイトの方法ではNICを認識しない。かつ、Virtualboxを前提としている。
https://www.newventuresoftware.com/blog/running-windows-10-iot-core-in-a-virtual-machine

こんなサイトもある。が、MinnowBoard Maxのイメージ、かつVmwareを前提としている。
https://mmateev.wordpress.com/2017/02/05/how-to-simulate-iot-gateway-using-vmware-workstation/

以下、あえてIntel Jouleのイメージで実施。

##◆Windows10 IoT Core仮想化の前提環境
１．ホストマシン・・・Windows10 Pro x64 (Hyper-v機能の有効化必要、Virtualboxとの同時使用不可、管理者コマンドプロンプトから「bcdedit /set hypervisorlaunchtype auto」実行でHyper-vモードへ切り替え可能)
２．USB Wi-Fiドングル(例：BUFFALO WLI-UC-GNME Amazonで800円)→PC内蔵のWi-Fiとは別の通信ルート確保が必要となることがある。ホストがSurfaceであればドングルがなくても構成可能なことを確認済み。当方の使用ホストは、NEC LAVIE Hybrid-Zero MEM:4GB, CPU:Core i5
３．USB Wi-Fiドングルのドライバがあらかじめホストマシンにインストール済みであり、ルータと通信可能(インターネット通信)な状態であること

※たぶんIoT Core x86/x64ベースの64bitイメージなら同じ手順でいけると思う
※~~試していないが、おそらくARMでもいけると思う~~ → 2017/8/5 ARMはダメだった。。。

##◆Windows10 IoT Core仮想化の手順
１．Microsoft の公式ページからIoT Core インストールファイルISOをダウンロードしてPCにマウントし、中身のMSIをホストにインストールする（自分はBuild 16247のISOでトライ）
２．C:\Program Files (x86)\Microsoft IoT\FFU\xxx　にFFUイメージ「flash.ffu」が生成される
３．ImgMountをダウンロードしてデスクトップに解凍する（ImgMount.exe）https://forum.xda-developers.com/showthread.php?t=2066903
４．管理者としてコマンドプロンプトを起動し、「CD C:\Program Files (x86)\Microsoft IoT\FFU\xxx」を実行
５．C:\Users\　(username)\Desktop\ImgMount\ImgMount.exe .\flash.ffuを実行
６．コントロールパネル→管理ツール→コンピュータの管理→ディスクの管理
７．flash.ffuのイメージをマウント(５．)した結果増えた「ディスクn」を右クリック→VHDの取り外し
８．取り外しを選んだ瞬間に表示されるダイアログ内に表示されているパスをコピーし、notepadに張り付けて退避しておく
９．Hyper-vを起動→右側ペインの「仮想スイッチマネージャ」をクリック
10．「新しい仮想ネットワークスイッチ」が選択された状態で、「仮想スイッチの作成」ペインの「外部」を選択して、仮想スイッチの作成ボタンをクリック
11．「仮想スイッチのプロパティ」ペインで、「名前：」に「VirtualBridge」(好きな名前で良い)を入力、「接続の種類」に「外部ネットワーク」を選択、リストからUSB Wi-Fiドングルを選択、管理オペレーティングシステムにこのネットワークアダプタの共有を許可する、にチェックＯＮ
12．Hyper-v右側ペインの「ディスクの編集」をクリック
13．「仮想ハードディスクファイルの場所を指定してください。」で参照ボタンクリック、８．で控えたパスを指定（フルパス）して次へ
14．「変換」を指定して次へ
15．「VHDX」を指定して次へ
16．「容量可変」を指定して次へ
17．「名前：」欄に表示されているパスの末尾に任意のファイル名(例)「xxx.vhdx」を追加入力
18．「名前：」欄のフルパスをnotepadに退避して次へ
19．「完了」ボタンクリック

20．Hyper-v右側ペインの「新規」をクリック→「仮想マシン」をクリック
21．次へ
22．「名前：」に好きなマシン名を入力して次へ
23．「第２世代」を選択して次へ
24．メモリサイズを適当に変更（1024MBでＯＫ）
25．「接続：」リストから「VirtualBridge」を選択して次へ
26．「既存の仮想ハードディスクを使用する」を選択し、「場所：」に18. で退避したフルパスを入力
27．完了ボタンクリック

##◆ffuイメージの展開先例
C:\Program Files (x86)\Microsoft IoT\FFU\xxx

##◆おわりに
次はBluetoothドングルの追加とI2Cセンサーのリモートデバッグにトライしようと思う。

##◆次の記事
Windows10 IoT CoreをVMwareで仮想化 へ続く
http://qiita.com/PINTO/items/43d3f0540adea08013e9
BlueBoard（LPC1768）のI2CとSPI

秋月のBlueBoardでmbedを動かしてるんだけど、I2CとSPIが動くか確認してみた。
mbedで出てるピンが使えるのは当然なんだけど、mbedでは出てないピンでも動くんだろか？
で、mbedライブラリのソースを見たら、しっかりとアサインされてました。
http://nora66.com/mbed/mbed-src.html#2017/08/01orange
うむ～mbed立派であります。
GithubへPushした際の「Connection refused」エラーについて

##エラー内容詳細
pushすると結果表示がされず3～5分たった後に以下エラー出現

```
fatal: unable to access 'https://github.com/hogehoge/test.git/'
: Failed to connect to github.com port 443: Connection refused
```

##解決法：Proxyを設定する
自分の場合Proxyの設定された社内環境からpushしていたため
以下のようにGitでProxyの設定をしたところ解決した。

```
git config --global http.proxy http://proxy.hogehoge.co.jp:8080
```

##参考にしたサイト
https://github.com/npm/npm/issues/10037
http://qiita.com/tunepolo/items/296c2639e0b750de41c6
[クイズ]javascriptと仲良くなるための一歩　第１３話「文字と数」

#問題

```js
'x' * 0
//=> ?
+'x'
//=> ?
```

:mouse:
:cow:
:tiger:
:rabbit:
:dragon_face:
:snake:
:horse:
:sheep:
:monkey_face:
:bird:
:dog:
:boar:
:mouse:
:cow:
:tiger:
:rabbit:
:dragon_face:
:snake:
:horse:
:sheep:
:monkey_face:
:bird:
:dog:
:boar:

#答え

```js
'x' * 0
//=> NaN
+'x'
//=> NaN
```

`*0`や`+`で、数字として変換されて処理しようとします。
その結果、xは数字で表せないので`NaN`となります。
Recovering from Optane Failure

This is a rough translation of [https://www.douban.com/note/626762420/].

One of my machine with Intel Optane Memory installed failed to upgrade to Windows 10 15063.447.
The machine stuck in a boot and BSoD loop, then it tried to boot into WinRE by itself and the result was different kinds of BSoD.

Tries to resolve the failure:

1. Prepare a boot drive with WinPE  
sadly I failed to inject Intel RST Driver to the boot.wim with DISM++. the optane drive device was not present.
2. Disable Fast Boot & Secure Boot
3. Find the switch in the BIOS settings to disable Optane (Deconcatenate the Optane from HDD)  
Intel Rapid Storage Technology -> Deconcatenate  
Preserve user data on deconcatenation (Choose Enabled)  
Are you sure you want to perform deconcatenation (Choose Yes)  
Start deconcatenation  
Wait (needs about 15min? no progress, must wait patiently :) )
4. Switch the storage mode to AHCI ***(important!)***
5. Boot into WinPE & Reset the EFI partition  
mountvol Z: /S; format z: /fs:fat32; bcdboot c:\windows /s z: /f UEFI
6. Boot into Safe Mode (Press F8? repeatedly)
7. Re-enable Optane after the system is recovered  
 You may want to check the file integrity with:
 Dism /Online /Cleanup-Image /RestoreHealth; sfc /scannow
Angularで画面分割を試す 【超初心者】

Webサイトの画面はいくつものファイルで構成されていることがよくあります。
１つのファイルで画面が作られていれば画面を移動するたびに全てのソースを入れ替える必要がありますが、
・ヘッダー
・サイドバー
・メイン
・フッター
とファイルが別れて構成されていれば、サイト内での移動はメインのファイルのみを別ページのものに変えればいいだけなので通信料も低く、表示速度も速いです。

AngularではWebサイトの１パーツごとにクラス分けしてコーディングが可能です。
そのやり方をメモしていきたいと思います。

まずAngular-cliでng new アプリ名をしたところからスタートしていきます。

```:ターミナル
kuniatsu$ ng new アプリ名

```


```:フォルダツリー

.
├── e2e
├── node_modules
├── src
│   ├── app
│   │   ├── app.component.css
│   │   ├── app.component.html
│   │   ├── app.component.ts
│   │   ├── app.component.spec.ts
│   │   └── app.module.ts
│   ├── assets
│   └── environments
├── .angular-cli.json
├── package.json
.
.
※関係ないファイルは省略しています。
```
##component作成

まず、componentを２つ作ります。



```:ターミナル
kuniatsu$ ng g component one
kuniatsu$ ng g component two

```
現在フォルダ構成はこの形です。


```:フォルダツリー

.
├── e2e
├── node_modules
├── src
│   ├── app
│   │   ├── one//追加
│   │   │   ├── one.component.css
│   │   │   ├── one.component.html
│   │   │   ├── one.component.ts
│   │   │   └── one.component.spec.ts
│   │   ├── two//追加
│   │   │   ├── two.component.css
│   │   │   ├── two.component.html
│   │   │   ├── two.component.ts
│   │   │   └── two.component.spec.ts
│   │   ├── app.component.css
│   │   ├── app.component.html
│   │   ├── app.component.ts
│   │   ├── app.component.spec.ts
│   │   └── app.module.ts
│   ├── assets
│   └── environments
├── .angular-cli.json
├── package.json
.
.
※関係ないファイルは省略しています。
```

新しく作ったcomponentが表示されるようにします。
作ったcomponentを表示するにはselectorの名前のタグを使います。
selectorの確認はcomponent.tsを見ます。

```ts:one.component.ts
import { Component, OnInit } from '@angular/core';
@Component({
  selector: 'app-one',//←確認
  templateUrl: './one.component.html',
  styleUrls: ['./one.component.css']
})
export class OneComponent implements OnInit {
  constructor() { }
  ngOnInit() {
  }

}

```

selector名を確認したらselector名のタグをapp.component.htmlに貼り付けます。

```html:app.component.html
main
<hr />
<app-one></app-one>
```

<img width="479" alt="スクリーンショット 2017-07-30 23.40.43.png" src="https://qiita-image-store.s3.amazonaws.com/0/98758/25868949-a7e5-25b3-943a-6e2e9a5f3d01.png">

app.component.htmlの中に書いた<app-one>が展開されていることがわかります。
twoも同じようにしておきます。

```html:app.component.html
main
<hr />
<app-one></app-one>
<hr />
<app-two></app-two>
```
<img width="563" alt="スクリーンショット 2017-07-30 23.43.39.png" src="https://qiita-image-store.s3.amazonaws.com/0/98758/bb77ab64-376b-8fa7-d3a4-b4e66ed175f3.png">

これで3つのコンポーネントが表示されるようになりました。
・app.component
・one.component
・two.component

あとは、各Componentの内容を充実させて好きにスタイリングすれば画面分割は完成です。
【swift3.0】NSMutableAttributedStringで文字の色を部分的に切り替える


文字の途中の色を変えたい場合

![B9UVg.png](https://qiita-image-store.s3.amazonaws.com/0/64334/0628ab52-7adf-2b12-42ac-14f35814e99e.png)

```swift:
var myString:NSString = "I AM KIRIT MODI"
var myMutableString = NSMutableAttributedString()
override func viewDidLoad() {

    myMutableString = NSMutableAttributedString(string: myString, attributes: [NSFontAttributeName:UIFont(name: "Georgia", size: 18.0)!])
    myMutableString.addAttribute(NSForegroundColorAttributeName, value: UIColor.redColor(), range: NSRange(location:2,length:4))
    // set label Attribute
    labName.attributedText = myMutableString
    super.viewDidLoad()
}
```

もっと分割したいときは条件を追加していけば良い。

![eHVh1.png](https://qiita-image-store.s3.amazonaws.com/0/64334/1591c593-0906-48a9-749e-414b944ed86b.png)

```swift:
 myMutableString.addAttribute(NSForegroundColorAttributeName, value: UIColor.greenColor(), range: NSRange(location:10,length:5))
```


実際に使うときには自分で細かい条件は変更した。



```swift:
var myMutableString = NSMutableAttributedString()
var myString = "文章文章文章文章文章文章文章文章文章文章文章文章文章文章文章"
myMutableString = NSMutableAttributedString(string: myString, attributes: [NSFontAttributeName:UIFont.hiraginoSans(ofSize: 12)])
myMutableString.addAttribute(NSForegroundColorAttributeName, value: Color.gray, range: NSRange(location:7,length:9))
profileLabel.attributedText = myMutableString

```

スタイルを変えたりするのは条件部分を変えれば良い。


#参考
https://stackoverflow.com/questions/27728466/use-multiple-font-colors-in-a-single-label-swift
Qtでシグナルをブロックする方法

## はじめに
「QSpinBox の valueChanged シグナルと任意のスロットを接続して処理していたけど、このプッシュボタンでスピンボックスの値を変更した時はシグナルを発行して欲しくない」という感じで、特定の処理の時だけシグナルを発行して欲しくないとき、どうやったらシグナルの発行を抑えられるのか調べてみました。

## QSignalBlocker を使う方法
QSignalBlocker のコンストラクタにシグナルの発行を抑えたいオブジェクトを渡してやります。

```cpp
const QSignalBlocker blocker(ui->spinBox);
```
QSignalBlocker のインスタンスを作ると、このインスタンスが生きているうちは、引数に渡したオブジェクトのシグナルは抑えられます。

破棄されたタイミングで、オブジェクトのシグナルのブロック状態は QSignalBlocker のコンストラクタが実行される前の状態に戻されます。

## QObject::blockSignals を使う方法
QObject::blockSignals(bool block) を使った方法は以下のようになります。

```cpp
const bool wasBlocked = ui->spinBox->blockSignals(true);
/* 何らかの処理 */
ui->spinBox->blockSignals(wasBlocked);
```

blockSignals に true を渡してやると、そのオブジェクトのシグナルは抑えられます。この時、 blockSignals は今現在のシグナルのブロックの状態を返すのでとっておいて、用が済んだらこれを使って元に戻して上げます。

## サンプル
スピンボックスのアップダウンボタンで値を変えた時はシグナルを発行して、自前で用意したプッシュボタン（＋、ー）で変更した時はシグナルを発行しないサンプルをGitHubに上げておきました。

[GitHub - SignalBlockTest](https://github.com/tatsuteb/SignalBlockTest)
![screen_shot.png](https://qiita-image-store.s3.amazonaws.com/0/141789/1ed96e12-01ae-cb03-a291-743a20f75636.png)

## 参考
[Qt Documentation - QSignalBlocker Class](http://doc.qt.io/qt-5/qsignalblocker.html#details)
[Qt Documentation - QObject Class (blockSignal)](http://doc.qt.io/qt-5/qobject.html#blockSignals)
Google Forms で連結した集計シート（Google Spreadsheets ファイル）から改めてグラフを描く

#はじめに

Google Forms の回答の概要で表示される円グラフはレポート等へ引用しづらいですよね。かといって一旦数値として集計するのは面倒です。

ざっとネット検索しても見つからなかったのですが、アンケートにより生成されるような形式のシートから、特に何も考えず「項目の数を集計しつつグラフ化」できる機能が存在したのでメモを残します。

#もしも

コピペ等で引用する方法を知っている人は、ぜひ教えてください。よろしくお願いします。

#昔話

2016-07 頃に Chrome で上述「回答の概要」を範囲選択しての印刷を使って PDF 化したものを、別途作成した PDF と連結してレポート作成したのですが、2017-07 に試したら「回答の概要」が適切に PDF 出来ませんでした。グラフが切れたり等。残念。

#Google Spreadsheets で「項目の数を集計しつつグラフ化」

非常に拍子抜けですが、単に１列から範囲選択して、グラフ挿入、グラフエディタで「列xを集計」にチェックを入れるだけです。

![サンプル](https://qiita-image-store.s3.amazonaws.com/0/150857/c004a2f8-3964-a288-3bd9-d4a40a975d61.png)


#公式情報

円グラフ（Pie Chart）のヘルプだと（日英とも）「２列にデータ入れろ、ラベルと値だ」とだけ書いてあります。そうじゃない使い方が書いてあるようには見えません。

見える人、ぜひ教えてください。よろしくお願いします。
Python3でアルファベットのリストを表示する

備忘。
競技用プログラミングとかで使えそうなので認めておく。

```python:alphabet_list.py
print([chr(ord('a') + i) for i in range(26)])

#=> ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z']
```
IoTゲートウェイを購入するときに確認したいこと


* ハードウェアの性能     (CPU、メモリ、ストレージなど)
* 同梱ミドルウェアの確認 (Oracle JDKのように有料ソフトが入っていると嬉しい) 
* 対応しているSIMの種類      (サイズ、PDPタイプ、LTE/3G等)
* 設置場所における安全基準など(耐久性や体温性など)
* 量産方法                   (自前でできるのか、メーカーに依頼するのか、簡単なのかなど)
* ユーザサポートの充実度  (問い合わせができるか、瑕疵担保、何らかのオプションがあるか等)
* 電波強度の確認ができる (ログファイルで確認できる、LEDランプで確認できる、Web画面で確認できる)
A3RTを使って遊んでみる（Text Suggest編）

少し前から気になっていたリクルートテクノロジーズ社が公開しているAPIを試してみた。
とりあえず「Text Suggest API」のみ。

##環境
Cloud9上（最近の個人的流行）

##インストール
```
pip install requests
pip install pya3rt
```

##サンプルコード
```suggest.py
# -*- coding: utf-8 -*-
import pya3rt

apikey = "{Your API Key}"
api = pya3rt.TextSuggestClient(apikey)

pd = "武士道とは"
sug_dict = api.text_suggest(previous_description=pd)

print(pd + sug_dict["suggestion"][0])
````

さてさて、有名なフレーズが完成するのを期待してコードを流してみた。
結果は、、、、
「武士道とは、大きなビルがあります。」

うーん、なんだか現代風な文章となってしまった。


##なぜか詰まったこと
上記のコードを実行するとなぜかエラーとなった。
エラー内容は以下の通り。

```
File "/usr/local/lib/python3.5/dist-packages/pya3rt/text_suggest.py", line 17, in request
response = requests.get(endpoint, params)
TypeError: get() takes 1 positional argument but 2 were given
```
「getの引数が多いぜ」と言われているので、該当ソースを見たところ、

```
response = requests.get(endpoint, params)
```

確かに多い、ということで、以下のように修正して動作させた。

```
response = requests.get(endpoint, params=params)
```

##オフィシャルサイト
https://a3rt.recruit-tech.co.jp/product/textSuggestAPI/
Azureスキルトレーニングをやってみた

今回は初めての人でもAzureを適切に知ることができる「Azureスキルトレーニング」の紹介をします。

#Azureスキルトレーニング
Azureスキルトレーニングには、アプリケーション開発のコースや、自動化のワークロードなどのシナリオに対応するトレーニングがあるようです。たくさんのコースがありますね。

https://www.microsoft.com/ja-jp/learning/azure-skills-training.aspx

![00.PNG](https://qiita-image-store.s3.amazonaws.com/0/32580/18e1b182-864c-f032-892d-92f37e2073c2.png)

今回はAzureを適切に使えるようになるためにも、Architecting Microsoft Azure Solutionsコースを選んでみます。

# Architecting Microsoft Azure Solutionsコース

このコースでは、ソリューションデザインのスキルを学ぶために、Microsoft Azureでの実装を学びます。パブリッククラウドとハイブリッドクラウドのデザインするためのトレードオフ知り、どのように設計したらよいか勉強するようです。

https://openedx.microsoft.com/courses/course-v1:Microsoft+DEV205Bx+2017_T2/about

試験70-534のMicrosoft Azureソリューションのアーキテクチャ認定試験にも関係しているトレーニングのようですので、認定試験を予定している方は一石二鳥ですね。

内容をざざっと紹介すると以下のようになります。クラウドのデザインパターンやWeb Appsを使うなど、Azureのソリューションを知ることができます。

- クラウドインフラストラクチャと開発のためのデザイン原則
- App Service Web Appsのデザイン
- Azure Resource Managerの紹介
- Application Storageとデータアクセスのデザイン
- リソースの保護
- Microsoft Azureとネットワークのデザイン
- モニタリング手法と管理のデザイン
- ビジネス継続手法のデザイン

# 実際に動かすためのチュートリアルや動画による説明も

コースは文章による説明のほか、実際にコマンドを実行したりするためのチュートリアルが含まれています。動画による説明では、英語のスクリプトが右側に表示され、更に音声のスピードも変えることができます。英語が聞き取れなくても、音声のスピードを遅くすることもできますし、スクリプトで確認することもできます。

![01.PNG](https://qiita-image-store.s3.amazonaws.com/0/32580/a3d664b5-6342-3b2b-5e77-bd6ae2e4d39c.png)

英語教材にも使えそうですね。。。Azureを勉強しながら英語の勉強ができるとは思っていませんでした。

# さいごに

Azureスキルトレーニングは、実践で使うための基礎を勉強することができますが、Azureの認定資格を取るためにも使えそうです。あとは、英語の勉強にも使えそうですので、是非、皆さんも試してみてはいかがでしょうか。
mod-wsgiをapache2.2から2.4に変更する際にやったこと


## ■  mod-rewriteを有効に

http://qiita.com/u-akihiro/items/c7a5bb38c34858d00c2a

```
sudo a2enmod rewrite
```

---

## ■ ソケットファイルのパスを変更

下記のエラーが出るのでパスを変更する。

```
No such file or directory: mod_wsgi
Couldn't bind unix domain socket '/etc/apache2/run/..sock
```

* ファイルパスを下記のように変更

```
WSGISocketPrefix ${APACHE_RUN_DIR}/wsgi
```

* 設定を反映

```
source /etc/apache2/envvars 
```

* オプションの設定ミス

```
Invalid option to WSGI daemon process definition
```

* 下記を削除。

```
eviction-timeout=0
response-buffer-size=0
```

### ● それぞれの項目の意味

* graceful-timeout
アイドル状態になっているかどうかを確認するために、
処理停止が発生してからプロセスを停止せず、待機する時間。

* eviction-timeout
graceful restartを使用した際に、受付中のプロセスがある場合に
プロセスを停止せずに待機させる時間。

設定されていない場合は、graceful-timeoutが使われる。

* response-buffer-size=nnn
apacheの子プロセスがWsgiアプリからの応答を受け付けるときのバッファのサイズ。

https://modwsgi.readthedocs.io/en/develop/configuration-directives/WSGIDaemonProcess.html
UnityでImageEffectをかける方法

UnityでImageEffect（ポストプロセス）をかける方法を備忘録的に簡単にまとめます。

Projectフォルダを右クリックして`Create => Shader => Image Effect Shader`からShaderを作ります。
名前はデフォルトのImage Effect Shaderが色を反転するエフェクトをかけるものなのでInvertにしておきます。

作成したInvertシェーダー上で右クリックして、`Create => Material`からマテリアルを作成します。これも名前をInvertにしておきます。
作成したInvertマテリアルのShaderが`Hidden/Invert`になっていることをインスペクターから確認してください。

以下のスクリプトをCameraに追加して、インスペクターからスクリプトのmaterialプロパティをさきほど作成したInvertマテリアルにします。

```csharp:ImageEffect.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ImageEffect : MonoBehaviour {

	public Material material;

	void OnRenderImage(RenderTexture src, RenderTexture dest) {
		Graphics.Blit (src, dest, material);
	}
}
```

これで、プログラムを実行すると以下のようになり、Game画面で色が反転しているのが確認できます。

<img width="557" alt="invert.png" src="https://qiita-image-store.s3.amazonaws.com/0/61569/11daaf21-dc71-a964-4deb-4363d3317646.png">
jenkinsでprofileがうまく更新されないときの解決方法

### 環境
- AWS
- windows7

### この記事を読んでわかること
jenkinsの乗っているEC2をまるっとコピーして、別VPCで起動したときに設定変更がうまくいかずにはまったときにどう対処したか

----

### 前提条件
- jenkinsにGUIでアクセスできている
    - 適切なアクセス権の付与
    - URLの設定変更など　（後で詳しく書きます）
- jenkinsの乗っているEC2にssh接続できる

## cliで設定してみる

```ruby:aws_cli
$ aws configure
AWS Access Key ID [None]: AKIA****************
AWS Secret Access Key [None]: ****************************************
Default region name [None]: ap-northeast-1
Default output format [None]: json
```

## profile名を指定して設定してみる

```ruby:aws_cli
$ aws configure --profile user2
AWS Access Key ID [None]: AKIA****************
AWS Secret Access Key [None]: ****************************************
Default region name [None]: ap-northeast-1
Default output format [None]: json
```

- 上記のように設定できる
- しかし、上記の設定が反映されない場合がある（原因わからず）
    - aws configureしたときに新しい設定が上書きされない

## 対策
- 直接configファイルとcredencialsファイルを書いてあげる
- 場所
    - `cd /var/lib/.aws/config`
    - `cd /var/lib/.aws/credencials`

- configファイル

```ruby:config
[profile test]
output = json
region = ap-northeast-1
```

- credencialsファイル(なければ手動で作る)

```ruby:credencials
[profile test]
aws_access_key_id = AKIA****************
aws_secret_access_key = ****************************************
```

## 設定の確認方法

```ruby:
$ aws configure list
      Name                    Value             Type    Location
      ----                    -----             ----    --------
   profile                <not set>             None    None
access_key     ********************              env    
secret_key     ********************              env    
    region                <not set>             None    None

```
Jupyter + Matplotlib > 横軸の表記がscientific exponential notation(例: 1e7)になるのを抑止する > ax1.get_xaxis().get_major_formatter().set_scientific(False)

```txt:動作環境
GeForce GTX 1070 (8GB)
ASRock Z170M Pro4S [Intel Z170chipset]
Ubuntu 16.04 LTS desktop amd64
TensorFlow v1.1.0
cuDNN v5.1 for Linux
CUDA v8.0
Python 3.5.2
IPython 6.0.0 -- An enhanced Interactive Python.
gcc (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
GNU bash, version 4.3.48(1)-release (x86_64-pc-linux-gnu)
```

TensorFlowの学習step数を増やしたことにより、グラフの横軸の表記が`1e7`のような[scientific exponential notation](https://en.wikipedia.org/wiki/Scientific_notation)になってしまうようになった。

![qiita.png](https://qiita-image-store.s3.amazonaws.com/0/32870/edce5597-3c48-e7f7-fd3a-a6ce896a4658.png)

元の数字の表記方法は以下で見つけました。
https://stackoverflow.com/questions/14711655/how-to-prevent-numbers-being-changed-to-exponential-form-in-python-matplotlib-fi

```py
ax1.get_xaxis().get_major_formatter().set_scientific(False)
```

Jupyter code.

```py:check_result_170722.ipynb
%matplotlib inline

# learning [Exr,Exi,Eyr,Eyi,Ezr,Ezi] from ADDA
# Jul. 31, 2017

import numpy as np
import matplotlib.pyplot as plt


def moving_average(a, n=3) :
    # from
    # https://stackoverflow.com/questions/14313510/how-to-calculate-moving-average-using-numpy
    ret = np.cumsum(a, dtype=float)
    ret[n:] = ret[n:] - ret[:-n]
    return ret[n - 1:] / n


def add_lineplot(filepath, ax1, alabel):
    data1 = np.loadtxt(filepath, delimiter=',')
    input1 = data1[:,0]
    output1 = data1[:,1]

    # moving average
    NUM_AVERAGE = 500
    output1 = moving_average(output1, n=NUM_AVERAGE)
    for loop in range(NUM_AVERAGE - 1):
        output1 = np.append(output1, 1e-7)  # dummy

    ax1.plot(input1, output1, label=alabel)
    
fig = plt.figure(figsize=(10,10),dpi=200)
ax1 = fig.add_subplot(2,1,1)
ax1.grid(True)
ax1.set_xlabel('step')
ax1.set_ylabel('loss')
ax1.set_yscale('log')
#ax1.set_xlim([0, 3000000])
ax1.set_xlim([0e6, 3e7])  # Jul. 31, 2017
ax1.set_ylim([1e-5, 1.0])

#--- learning rate=0.001, batch_size=4
FILE_PATH1 = 'RES_170728_t0716//log_learn.170727_t2308'
#--- learning rate=0.0001, batch_size=4
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0720'
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0751'
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0821'
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0850'
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0921'
#FILE_PATH1 = 'RES_170728_t2119/log_learn.170728_t0951'
#FILE_PATH2 = 'RES_170728_t2119/log_learn.170728_t1050'
#--- batch_size=2
FILE_PATH2 = 'RES_170729_t0744//log_learn.170728_t2311'
#--- batch_size=20
#FILE_PATH3 = 'RES_170728_t2311/log_learn.170728_t2208'

# for [10x30x100] 2017/07/29 18:45
FILE_PATH3 = 'log_learn.170731_t2045'

# for learning rage=0.001, 30x100x100
add_lineplot(FILE_PATH2, ax1, alabel="batch size=2")
add_lineplot(FILE_PATH1, ax1, alabel="batch size=4")
add_lineplot(FILE_PATH3, ax1, alabel="batch size=2")

ax1.legend()

ax1.get_xaxis().get_major_formatter().set_scientific(False)

```

![qiita.png](https://qiita-image-store.s3.amazonaws.com/0/32870/ba6713ee-f6a7-4069-d6d1-6096e013d562.png)

step=3e7の頃にはlossは`1e-6`になるだろう(hopefully)。
Vue + Typescript + Element + fuseboxの開発環境構築

# 更新

## 2018/12/02

この記事を書いたあといろいろ試しましたが、Nuxtがオススメです。
超絶かんたんにセットアップできます。
Server side renderingが超絶簡単にできるので、SEOにも有利です。

# 概要

以下のライブラリを使って、フロントエンドUI開発環境を整えてみました。結論だけ知りたい方は[サンプルアプリ](https://github.com/contribu/element-ui-sample)を見てください。この記事には、この構成にいたった経緯やハマりポイントを書きます。

- [fusebox](http://fuse-box.org/)
   - webpackのようなもの。typescriptとの相性が良く、webpackより速い。 
- [vue](https://jp.vuejs.org/index.html)
   - Javascriptフレームワーク
- [Element](http://element.eleme.io/#/en-US)
   - vueのコンポーネント集
- [typescript](https://www.typescriptlang.org/)

サンプルアプリ: https://github.com/contribu/element-ui-sample

# 経緯やハマりポイント

## スピード重視でfuseboxを選んだ

Webpackとfuseboxどちらが良いのか？ソースコード更新後ビルドが終わるまでに、Webpackは数十秒かかります。一方でfuseboxは数十msで終わります。Webpackは.vue内で\<style\>が使えますが、cssは.vueで管理しないほうが保守性が良い気がしたので、そこはメリットとして弱いと判断しました。webpackはソースコードを更新すると、ブラウザのリロードまで自動でやってくれますが、そもそもビルドに数十秒かかると意味が無いです。結論、スピード重視でfuseboxにしました。

| | 速度 | .vue内で\<style\>を使えるか？ | ホットリロード |
|---|:-:|:-:|:-:|
| Webpack | 数十秒 | **使える** | **ブラウザ自動リロード** |
| fusebox (採用) | **数十ms** | 使えない | ブラウザ手動リロード |


## Vue.use(ElementUI)が動かない

以下の修正で解決しました。治る理由は良く分かっていないです。
- https://github.com/contribu/element-ui-sample/blob/965023ec3faeb9bf1a5ca7e56b5bf0eeb5f87b42/src/index.ts#L3-L66
- https://github.com/contribu/element-ui-sample/blob/965023ec3faeb9bf1a5ca7e56b5bf0eeb5f87b42/src/index.ts#L72-L139

参考リンク
- http://element.eleme.io/#/en-US/component/quickstart#on-demand

## element-uiのテーマや.scssがロードされない

[この修正で解決しました。](https://github.com/contribu/element-ui-sample/blob/965023ec3faeb9bf1a5ca7e56b5bf0eeb5f87b42/fuse.js#L8-L19)治る理由は良く分かっていないです。

## vagrant経由だとfuse.watch()が効かない

[この修正で解決しました。](https://github.com/contribu/element-ui-sample/blob/965023ec3faeb9bf1a5ca7e56b5bf0eeb5f87b42/fuse.js#L31)

```js
fuse.run({
    chokidar: {
        usePolling: true,
    },
});
```

参考リンク
- fuseboxのchokidarオプション: http://fuse-box.org/page/development#chokidar-options
- chokidarのusePollingオプション: https://github.com/paulmillr/chokidar#performance

## vagrant経由だとnpm installが失敗する

こちらで解決しました -> https://medium.com/@dtinth/isolating-node-modules-in-vagrant-9e646067b36

```bash
cd /path/to/element-ui-sample
mkdir ~/element-ui-sample_node_modules # synced_folderの外
mkdir ./node_modules # synced_folderの中
sudo mount --bind ~/element-ui-sample_node_modules /path/to/element-ui-sample/node_modules
```
sympyで「なぜ三角形の内角の和は180度？」を証明できなかった

(参考)なぜ三角形の内角の和は180度？
http://qiita.com/tomo64/items/d25c0435dfcc62154a43

```python
from sympy import *
var('x1 y1 x2 y2 x3 y3')
# P1=Point(x1,y1)
# P2=Point(x2,y2)
# P3=Point(x3,y3)
# print( Polygon(P1,P2,P3).angles[P2] + Polygon(P2,P3,P1).angles[P3]  + Polygon(P3,P1,P2).angles[P1])
# ValueError: Can't determine orientation
x1=0
y1=0
x2=100
y2=0
x3=100
y3=100
P1=Point(x1,y1)
P2=Point(x2,y2)
P3=Point(x3,y3)
print( Polygon(P1,P2,P3).angles[P2] + Polygon(P2,P3,P1).angles[P3]  + Polygon(P3,P1,P2).angles[P1])
# pi
```
Xcode8系でAlcatrazをインストールする

# xcode 8系でAlcatrazのエラーにコケた時の対処法

### はじめに

xcodeのプラグインマネージャのAlcatrazを入れても、windowのメニューに表示されず詰まったので、メモ。



xcode8系は以下のやり方で、インストールからwindowのメニューの表示まで出来るようになります。
> xcodeは終了しておく


```
// Alcatrazのインストール
$ curl -fsSL https://raw.githubusercontent.com/supermarin/Alcatraz/deploy/Scripts/install.sh | sh

$ sudo gem install update_xcode_plugins

$ update_xcode_plugins --unsafe-unsign
```

xcodeを起動するとAlcatrazをロードするのか聞かれるので、「Load bundle」を選択。
以上で「window」メニューに「Package Manager」が追加されます。