決定版!!Haml小技まとめ！！


# 本記事のサマリ
あれ、これってhamlではどうするんだっけ？ってなった人に、hamlの基本が思い出せるようにまとめています。間違いや、素敵なtips等あれば是非教えてください。
(hamlの変換結果は、適宜見やすいように、空白や改行を入れているため、実際の変換結果と異なる場合がございますので、ご留意ください。)
英語が苦手じゃなければ、[公式リファレンス](http://haml.info/docs/yardoc/file.REFERENCE.html)を読みましょう！！


### 対象読者
hamlっていいってよく聞くけど、あんまり使ったことなくてどうしたらいいかわからない方向け。
hamlをちょいちょい使ってるけど、まだ「馴染む、馴染むぞぉぉ」ってない人向け。

### 動作確認バージョン
```sh
ruby --version
ruby 2.2.3p173 (2015-08-18 revision 51636) [x86_64-darwin15]

rails -v
Rails 4.1.1

gem list --local | grep haml
  haml (4.0.7)
  haml-rails (0.9.0, 0.4)
  html2haml (2.0.0)
```

### 経緯
hamlを使うようになったけど、まだ「馴染む、馴染むぞぉぉ」ってない中で、
いまいち、全体像が網羅的にまとまっていそうなqiita記事が見つけられなかったので、自分の勉強がてらまとめておくことにしました。

# Hamlとは？
Hamlというのは、HTML Abstraction Markup Languageの略称とのこと。html(xmlも生成できる)を生成するための、マークアップ言語です。htmlより記述量が少なくて済むことと、インデントが強制されることから、非常に綺麗に簡潔に作成することが可能です。

[公式サイト](http://haml.info)
[公式リファレンス](http://haml.info/docs/yardoc/file.REFERENCE.html)

# hamlの基本
## 「%」と「インデント」でhtmlのタグを表現しよう
```haml
%html
  %head
  %body
    Hello Haml World!!
```
こんなかんじで「%」と「インデント」というイディオムを覚えてしまいましょう。上記は、こんな風になります。

```html
<html>
  <body>
    Hello Haml World!!
  </body>
</html>
```
    
## タグだけじゃhtmlは表現できない...htmlの属性は！？？
htmlの属性は、ハッシュを利用するのがメインです。( ()を使って表現する、簡易的な方法もあるようです。)

```haml
%html
  %body
    %a{ :href => 'http://google.co.jp', :id => 'anchor1' }
      {}でくくってその中に表現するのだ！！
    %a{ href: 'http://google.co.jp', id: 'anchor2' }
      属性の指定は、こんな風にも書ける(Rubyのhash指定の文法に依存)
    %a( href='http://google.co.jp' id='anchor3')
      属性の間に、カンマをつけたくない人は、こんな風に()を使っても書ける
    %a(href='http://google.co.jp'){id: 'anchor4'}
      ただ、()の方は、スペース区切りゆえにできないこともあるので、両方書くことも許されている。
``` 
↓変換後↓

```html
<html>
  <body>
    <a href='http://google.co.jp' id='anchor1'>{}でくくってその中に表現するのだ！！</a>
    <a href='http://google.co.jp' id='anchor2'>属性の指定は、こんな風にも書ける(Rubyのhash指定の文法に依存)
    <a href='http://google.co.jp' id='anchor3'>属性の間に、カンマをつけたくない人は、こんな風に()を使っても書ける</a>
    <a href='http://google.co.jp' id='anchor4'>ただ、()の方は、スペース区切りゆえにできないこともあるので、両方書くことも許されている。</a>
  </body>
</html>
```

## 超絶よく使うclass属性とid属性は、「.」と「#」で表現できる
```haml
%span#id_value.class_value1.class_value2
  こんなかんじで#でidを指定して、.でクラスを指定する。.は複数設定可
```
↓変換後↓

```html
<span id="id_value" class="class_value1 class_value2">
  こんなかんじで#でidを指定して、.でクラスを指定する。.は複数設定可
</span>

```
  
## 超絶よく使うdivタグは、%を省略できる
```haml
%div
  こんな風にdivタグも書けるけど
.xxx
  こんな風に「.(ドット)」＋文字列と書くとxxxというクラスを指定したdivタグが生成される
#zzz
  こんな風に「#(シャープ)」＋文字列と書くとzzzというidを持ったdivタグが生成される
```
↓変換後↓
    
```html
<div>
  こんな風にdivタグも書けるけど
</div>
<div class='xxx'>
  こんな風に「.(ドット)」＋文字列と書くとxxxというクラスを指定したdivタグが生成される
</div>
<div id='zzz'>
  こんな風に「#(シャープ)」＋文字列と書くとzzzというidを持ったdivタグが生成される
</div>
```

## rubyのコードは「-」や「=」で

### ループしたい？「-」使いましょう
```haml
- 3.times do |i|
  %p #{i}

```
↓変換後↓

```html
<p>1</p>
<p>2</p>
<p>3</p>
```

### 分岐したい？「-」使いましょう
```haml
- 3.times do |i|
  %span
    - if i.odd?
      odd!!
    - else
      even!!
```
↓変換後↓

```html
<span>
  even!!
</span>
<span>
  odd!!
</span>
<span>
  even!!
</span>
```

### rubyで処理した結果を出力したい？「=」使いましょう
erbで言う所の、<%= %>に当たるのが「=」です。

```haml
= link_to 'Go To Google', 'http://google.co.jp'
```
↓結果

```html
<a href="http://google.co.jp">Go To Google</a>
```

### 変数定義したい？「-」使いましょう
```haml
- my_variable = '変数使ってみる'
= "こんな風に、#{my_variable}ことができます"
```
↓結果

```html
こんな風に、変数使ってみることができます
```

とりあえず、プログラム的なことがしたくなったら、まずは「-」使うイメージで良いと思います。
そして、結果を画面に反映したい場合は、「=」を使いましょう


## コメントは、「-#」か「/」で

### ブラウザのソースを表示で見せたいコメントは「/」
```haml
/ここはコメントです。
```
↓結果

```html
<!-- ここはコメントです。 -->
```

### ブラウザのソースを表示で見せないコメントは「-#」
```haml
-#これもコメントです。(ただし、htmlには反映されません。)
```
↓結果

```html
```
(html上は、何も見えない)      

# 応用編

## よくつかうテクニック

### htmlのエスケープをしたい場合は、「&=」
「=」で出力しようとした場合に、htmlのエスケープ(&を&ampなどに変換するやつ)をするかしないかは、hamlの設定によって挙動が変わるのですが、意図的にhtmlのエスケープをしたい場合は、「&=」を使いましょう。

`&= "I like cheese & crackers"`は、`I like cheese &amp; crackers`に変換されます。


### htmlのエスケープをしたくない場合は、「!=」
「&=」とは逆に、「!=」を使うことで、エスケープさせないように制御することが可能です。
`!= "I like cheese & crackers"`は、`I like cheese & crackers`に変換されます。


### 「-」や「=」から始まる文字列を出力したいなら\(バックスラッシュ)
```haml
1
+
1
\=
2
%br/
1
\-
1
\=
0
上記のように、=や-を行の先頭文字にしたい場合は、\(バックスラッシュ)にてエスケープする
```

```html
1+1=2
<br/>
1-1=0
上記のように、=や-を行の先頭文字にしたい場合は、\(バックスラッシュ)にてエスケープする
```

<!--
### 属性の指定は、Hashを返すメソッドでもOK

※Hashを複数渡す事もできるけど、名前がかぶる場合は気をつけて。
TODO 説明
-->

### html5のカスタムデータは、「:data」で美しくかける
属性を書くときは、Hashを利用するのがセオリーですが、Hashのキーをシンボルにする場合、-(ハイフン)が使えないという欠点があります。
一方で、html5のカスタムデータを使う場合は、属性名が「data-hogehoge」という規則になるため、相性がすこぶる悪い。
どういうことかというと
`<span data-hogehoge = 'mokemoke'/>`のように表現したい場合

`%span{data-hogehoge: 'mokemoke'}`とか
`%span{:data-hogehoge => 'mokemoke'}`とかは、エラーになる。
:data-hogehogeというのは、Rubyのシンボルというものなのですが、シンボルに「-」を含めるには、ダブルクォートでくくる必要があるため、ただしくは、以下のような記述になる

`%span{"data-hogehoge": 'mokemoke'}`とか

`%span{:"data-hogehoge" => 'mokemoke'}`

これが許せる人なら、これでも構わないのですが、個人的には美しくないなぁと感じてしまいます。
そういった人のために、ハッシュを階層化することで、Haml側では自動的に「-」区切りしてくれるようになっています。

`%span{ data: { hogehoge: 'mokemoke' } }`

`%span{ :data => { :hogehoge => 'mokemoke' } }`

のように指定することができます。

ちなみに、これは、dataだけが特別なのではなく、属性として指定するHashの階層は、ハイフンで繋げられるようです。
%span{ fuga: {hoge: { piyo: 'mokemoke' } } }
-> この場合、fuga-hoge-piyo = 'mokemoke'という属性が指定される。
特に、カスタムデータを複数指定したい場合が以下のように記述できるため、よりスマートに記述することが可能です。

`%span{"data-hoge": 'data1' , "data-fuga": 'data2' , "data-piyo": 'data3'}`

これが、
`%span{ data: { hoge: 'data1', fuga: 'data2', piyo: 'data3'} }`

こんな風に記述できて、どちらも以下のような変換結果になる。
`<span data-fuga="data2" data-hoge="data1" data-piyo="data3"></span>`

<!-- このあたりは、自分の環境だとうまく動かないので検証中。
### 空タグは、最後に「/」をつけよう。

### トリミングは,<や>で

#### >を使うと、タグの外側が改行なしに

```
%div
  %span>
    a
```

#### <を使うと、タグの内側が改行なしに


### Object Reference: []
-->

### Doctype: !!!
htmlの冒頭に記載する、
`<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">`
みたいな文を生成してくれるのが「!!!」です。いろいろあるので、詳しくは、[公式リファレンス](http://haml.info/docs/yardoc/file.REFERENCE.html)のDoctypeの章を確認してください。

### 条件付きコメントを表現しなければいけない呪いにかかっているのなら。。。
この章を見ているということは、きっとあなたは、古いIEを救ってあげる勇者さま？
hamlでも、条件付きコメントをサポートしています。
条件付きコメントを利用する場合は、「/[]」を使いましょう。
参考：[Wikipedia:条件付きコメント](https://ja.wikipedia.org/wiki/%E6%9D%A1%E4%BB%B6%E4%BB%98%E3%81%8D%E3%82%B3%E3%83%A1%E3%83%B3%E3%83%88)

```haml
/[if lt IE 9]
  %script{ type: 'text/javascript', src: 'http://html5shim.googlecode.com/svn/trunk/html5.js'
```
↓結果

```html
<!--[if lt IE 9]>
<script type="text/javascript" src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
```

<!-- あんまり使いみちなさそうなので、一旦コメントアウト
### Whitespace Preservation: ~
-->

### Helper Methods
Hamlが提供している便利なヘルパーメソッドがありますので、興味が有る方は、以下をご参照ください。
[Hamlの提供するヘルパーメソッド](http://haml.info/docs/yardoc/Haml/Helpers.html#find_and_preserve-instance_method)
(自分も調査中です。。。)

<!-- あんまり使いみちなさそうなので、一旦コメントアウト
### Multiline: |
-->

### hamlの中にhamlじゃない情報を載せる(フィルター機能)
:javascriptなどのフィルターと呼ばれる機能を利用すると、hamlではない記述方法を織り交ぜることができます。
使い方は、以下のとおりです。
①宣言する
②インデントを一段さげた部分は、それぞれのフィルターが適用される
よく使いそうなものは、こちらにまとめていますが、他にもあるので、詳しくは、[公式リファレンス](http://haml.info/docs/yardoc/file.REFERENCE.html)を参照しましょう。

### coffeescirpt、javascriptをベタ書きしたい？「:coffee」「:javascript」でできます

```haml
:coffee
  alert('coffee!!')
```
これは、以下の様なjavascriptに変換されます。

```html
<script>
  (function() {
    alert('coffee!!');
  
  }).call(this);
</script>
```

```haml
:javascript
  alert('javascript!!');
```
これは、以下の様なjavascriptに変換されます。

```html
<script>
  alert('javascript!!');
</script>
```
    

### sass,scss,cssをベタ書きしたい？「:sass」「:scss」「:css」でできます
使い方は同上、なので、省略します。

### 嘘でしょ？hamlなのに、erbで書きたいの？？「:erb」でできます
まぁ、そんな場合は、「:erb」を使いましょう
使い方は、同上なので省略します。

<!--
#### erbの方がうまく表現できるのに系の情報
-->

### マークダウン記法を使いたい！？なんてわがままな。。。「:markdown」でできます
これは、地味に嬉しいかも？
使い方は同上です。

### 「-」を使わずにrubyのコードを書きたいだって！？「:ruby」でできます
あまり、viewに複雑なことをさせるのはよくないので、これを使いたい場合は、ちょっと実験したいとかくらいにとどめておいたほうがよいと思いますが。。。
:rubyを使うと、Rubyのコードがそのまま記述ができます。

## htmlをhamlに変換したい
htmlをhamlに変換したい場合は多々あると思います。
その場合は、[html2haml](https://github.com/haml/html2haml)というgemがあれば、コマンド一発で変換してくれますので、おすすめです。
もしくは、
[htmlをhamlに変換してくれるwebサイト](http://html2haml.herokuapp.com/)を使うのもありです。
私は、前者をよく利用しています。



うん、これで自分が欲しい情報はまとまったきがする！！