There were a lot of elements previously, like `Em`, `H1`, and a lot more, that took a string as the first argument previously. This was weird when you wanted to mix elements to output html like `<strong><em>…</em></strong>` or `<h1>Something <em>something</em> something</h1>`. gomponents is not an HTML validator, so I want people to be able to use elements however they please, also without text content.
This also means that all elements now have the same API.
This makes it clearer that the helpers return a `Node` of any kind, and that the type is not important.
This also streamlines the API, as attribute helpers already return just `Node`.
`a`, `form`, `img`, `input`, `label`, `option`, `progress`, `select`, and `textarea` are now just regular elements (without helper parameters), because:
- Sometimes the use case doesn't fit (`a` as anchor without href, for example)
- There's no reason these are special among the others, so streamlining them makes sense
Also added new attributes `action`, `alt`, `for`, `method` that I had somehow missed.
This makes it easier to use dot-imports.
Also updated the readme and examples with new usage, and move the `Classes` helper into the `components` package.
The `Placer` interface was a weird interface that tried to abstract away nodes being elements or attributes, but it doesn't really make sense. Now `Nodes` just have a `NodeType`.
Previously, elements of kind void and empty elements generally would be rendered auto-closing (with a final `/` character in the start tag), which is allowed sometimes but arguably wrong. See https://dev.w3.org/html5/spec-LC/syntax.html#end-tags
This created problems with for example `textarea` and `script`, which cannot be auto-closing, or the browser renders it wrong.
Also clarified in the docs that this library outputs HTML5.
Fixes#42.
The Render function has been changed to take a `Writer` instead of returning a string. This makes it possible to generate documents without having the whole content in memory.
This also removes the `gomponents.Write` function, which is now redundant.
Furthermore, the `el.Document` function has been changed to only take one child, as multiple children never make sense for it. (It's not even a child, more a sibling.)
Just concatenating the strings is much faster.
Before:
```
make benchmark
go test -bench=.
goos: darwin
goarch: amd64
pkg: github.com/maragudk/gomponents
BenchmarkAttr/boolean_attributes-8 8194791 139 ns/op
BenchmarkAttr/name-value_attributes-8 5143292 229 ns/op
PASS
ok github.com/maragudk/gomponents 2.841s
```
After:
```
make benchmark
go test -bench=.
goos: darwin
goarch: amd64
pkg: github.com/maragudk/gomponents
BenchmarkAttr/boolean_attributes-8 16755404 67.0 ns/op
BenchmarkAttr/name-value_attributes-8 10208625 116 ns/op
PASS
ok github.com/maragudk/gomponents 2.702s
```
This change adds a lot of element helpers, and refactors:
- helpers into simple, text, and other helpers
- most tests into table-driven tests, so they're easier to read
Thanks to @oderwat for pushing me to improve the tests. 😉
When implemented, the `Place` method of the `Placer` interface tells `Render` in `El` where to put a Node. This is relevant for helpers that want to be rendered like attributes, inside the parent element.
Fixes the bug where `attr.Classes` was rendered outside the element.
Especially add elements that are either used in every document, that nearly always have text content, or that are almost always used with certain attributes.