haml--haml/REFERENCE.md

273 lines
7.1 KiB
Markdown
Raw Normal View History

2015-11-21 18:21:08 +00:00
# Hamlit
Basically Hamlit is the same as Haml.
See [Haml's tutorial](http://haml.info/tutorial.html) if you are not familiar with Haml's syntax.
[REFERENCE - Haml Documentation](http://haml.info/docs/yardoc/file.REFERENCE.html)
## Supported features
See [Haml's reference](http://haml.info/docs/yardoc/file.REFERENCE.html)
for full features in original implementation.
- [ ] Using Haml
2015-11-21 18:21:08 +00:00
- [x] Rails XSS Protection
- [x] Ruby Module
- [x] Options
- [ ] Encodings
- [x] Plain Text
- [x] Escaping: \
- [ ] HTML Elements
2015-11-21 18:21:08 +00:00
- [x] Element Name: %
- [ ] Attributes: `
2015-11-21 18:21:08 +00:00
- [x] :class and :id Attributes
- [x] HTML-style Attributes: ()
- [x] Ruby 1.9-style Hashes
- [ ] Attribute Methods
- [x] Boolean Attributes
- [x] HTML5 Custom Data Attributes
- [x] Class and ID: . and #
- Implicit Div Elements
- [x] Empty (void) Tags: /
- [x] Whitespace Removal: > and <
- [x] Object Reference: []
- [x] Doctype: !!!
- [x] Comments
- [x] HTML Comments: /
- [x] Conditional Comments: /[]
- [x] Haml Comments: -#
- [x] Ruby Evaluation
- [x] Inserting Ruby: =
- [x] Running Ruby: -
- [x] Ruby Blocks
- [x] Whitespace Preservation: ~
- [x] Ruby Interpolation: #{}
- [x] Escaping HTML: &=
- [x] Unescaping HTML: !=
- [ ] Filters
- [x] :cdata
2015-11-21 18:21:08 +00:00
- [x] :coffee
- [x] :css
- [x] :erb
- [x] :escaped
- [x] :javascript
- [x] :less
- [x] :markdown
- [ ] :maruku
- [x] :plain
- [x] :preserve
- [x] :ruby
- [x] :sass
- [x] :scss
- [ ] :textile
- [ ] Custom Filters
- [x] Helper Methods
- [x] preserve
2015-11-21 18:21:08 +00:00
- [x] surround
- [x] precede
- [x] succeed
- [x] Multiline: |
- [x] Whitespace Preservation
- [ ] Helpers
## Limitations
### No Haml buffer
2015-11-28 10:44:45 +00:00
Hamlit uses `Array` as buffer for performance. So you can't touch Haml::Buffer from template when using Hamlit.
2015-11-21 18:21:08 +00:00
### Haml helpers are still in development
2015-11-28 10:44:45 +00:00
At the same time, because some methods in `Haml::Helpers` require `Haml::Buffer`, they are not supported now.
2015-11-22 11:28:11 +00:00
But some helpers are supported on Rails. Some of not-implemented methods are planned to be supported.
2015-11-21 18:21:08 +00:00
### Limited attributes hyphenation
In Haml, `%a{ foo: { bar: 'baz' } }` is rendered as `<a foo-bar='baz'></a>`, whatever foo is.
2018-10-16 11:34:47 +00:00
In Hamlit, this feature is supported only for aria and data attribute. Hamlit renders `%a{ data: { foo: 'bar' } }`
2015-11-28 10:44:45 +00:00
as `<a data-foo='bar'></a>` because it's data attribute. This design allows us to reduce work on runtime
and the idea is originally in [Faml](https://github.com/eagletmt/faml).
2015-11-21 18:21:08 +00:00
### Limited boolean attributes
2015-11-22 11:28:11 +00:00
In Haml, `%a{ foo: false }` is rendered as `<a></a>`, whatever `foo` is.
2015-11-23 17:18:32 +00:00
In Hamlit, this feature is supported for only boolean attributes, which are defined by
2015-11-22 11:28:11 +00:00
http://www.w3.org/TR/xhtml1/guidelines.html or https://html.spec.whatwg.org/.
2015-11-21 18:21:08 +00:00
The list is the same as `ActionView::Helpers::TagHelper::BOOLEAN_ATTRIBUTES`.
2018-10-16 11:34:47 +00:00
In addition, aria-\* and data-\* is also regarded as boolean.
2015-11-21 18:21:08 +00:00
2015-11-28 10:44:45 +00:00
Since `foo` is not boolean attribute, `%a{ foo: false }` is rendered as `<a foo='false'></a>`
This is the same behavior as Rails helpers. Also for `%a{ foo: nil }`,
Hamlit does not remove non-boolean attributes and render `<a foo=''></a>`
(`foo` is not removed). This design allows us to reduce string concatenation and
is the only difference between Faml and Hamlit.
2015-11-21 18:21:08 +00:00
You may be also interested in
[hamlit/hamlit-boolean\_attributes](https://github.com/hamlit/hamlit-boolean_attributes).
2015-11-21 18:21:08 +00:00
## 5 Types of Attributes
Haml has 3 types of attributes: id, class and others.
2018-10-16 11:34:47 +00:00
In addition, Hamlit treats aria/data and boolean attributes specially.
2015-11-21 18:21:08 +00:00
So there are 5 types of attributes in Hamlit.
### id attribute
Almost the same behavior as Haml, except no hyphenation and boolean support.
Arrays are flattened, falsey values are removed (but attribute itself is not removed)
and merging multiple ids results in concatenation by "\_".
2015-11-21 18:21:08 +00:00
```rb
# Input
#foo{ id: 'bar' }
%div{ id: %w[foo bar] }
%div{ id: ['foo', false, ['bar', nil]] }
%div{ id: false }
2015-11-21 18:21:08 +00:00
# Output
<div id='foo_bar'></span>
<div id='foo_bar'></span>
<div id='foo_bar'></span>
<div id=''></span>
2015-11-21 18:21:08 +00:00
```
### class attribute
Almost the same behavior as Haml, except no hyphenation and boolean support.
Arrays are flattened, falsey values are removed (but attribute itself is not removed)
and merging multiple classes results in unique alphabetical sort.
2015-11-21 18:21:08 +00:00
```rb
# Input
.d.a(class='b c'){ class: 'c a' }
%div{ class: 'd c b a' }
%div{ class: ['d', nil, 'c', [false, 'b', 'a']] }
%div{ class: false }
2015-11-21 18:21:08 +00:00
# Output
<div class='a b c d'></div>
<div class='d c b a'></div>
<div class='d c b a'></div>
<div class=''></div>
2015-11-21 18:21:08 +00:00
```
2018-10-16 11:34:47 +00:00
### aria / data attribute
2015-11-23 16:08:39 +00:00
Completely compatible with Haml, hyphenation and boolean are supported.
2015-11-21 18:21:08 +00:00
```rb
# Input
%div{ data: { disabled: true } }
%div{ data: { foo: 'bar' } }
# Output
<div data-disabled></div>
<div data-foo='bar'></div>
```
2018-10-16 11:34:47 +00:00
aria attribute works in the same way as data attribute.
2015-11-21 18:21:08 +00:00
### boolean attributes
No hyphenation but complete boolean support.
```rb
# Input
2015-11-23 15:42:58 +00:00
%div{ disabled: 'foo' }
2015-11-21 18:21:08 +00:00
%div{ disabled: true }
%div{ disabled: false }
# Output
2015-11-23 15:42:58 +00:00
<div disabled='foo'></div>
2015-11-21 18:21:08 +00:00
<div disabled></div>
<div></div>
```
List of boolean attributes is:
```
disabled readonly multiple checked autobuffer autoplay controls loop selected hidden scoped async
defer reversed ismap seamless muted required autofocus novalidate formnovalidate open pubdate
itemscope allowfullscreen default inert sortable truespeed typemustmatch
```
If you want to customize the list of boolean attributes, you can use
[hamlit/hamlit-boolean\_attributes](https://github.com/hamlit/hamlit-boolean_attributes).
"aria-\*" and "data-\*" are also regarded as boolean.
2015-11-23 15:42:58 +00:00
2015-11-21 18:21:08 +00:00
### other attributes
No hyphenation and boolean support. `false` is rendered as "false" (like Rails helpers).
2015-11-21 18:21:08 +00:00
```rb
# Input
%input{ value: true }
%input{ value: false }
# Output
<input value='true'>
<input value='false'>
```
## Engine options
| Option | Default | Feature |
|:-------|:--------|:--------|
| escape\_html | true | HTML-escape for Ruby script and interpolation. This is false in Haml. |
| escape\_attrs | true | HTML-escape for Html attributes. |
| format | :html | You can set :xhtml to change boolean attribute's format. |
| attr\_quote | `'` | You can change attribute's wrapper to `"` or something. |
### Set options for Rails
```rb
# config/initializers/hamlit.rb or somewhere
Hamlit::RailsTemplate.set_options attr_quote: '"'
```
### Set options for Sinatra
```rb
set :haml, { attr_quote: '"' }
```
## Creating a custom filter
Currently it doesn't have filter registering interface compatible with Haml.
But you can easily define and register a filter using Tilt like this.
```rb
module Hamlit
class Filters
class Es6 < TiltBase
def compile(node)
# branch with `@format` here if you want
compile_html(node)
end
private
def compile_html(node)
temple = [:multi]
temple << [:static, "<script>\n"]
temple << compile_with_tilt(node, 'es6', indent_width: 2)
temple << [:static, "\n</script>"]
temple
end
end
register :es6, Es6
end
end
```
After requiring the script, you can do:
```haml
:es6
const a = 1;
```
and it's rendered as:
```html
<script>
"use strict";
var a = 1;
</script>
```