mirror of
https://github.com/acaloiaro/frm
synced 2026-07-21 18:29:12 +00:00
82 lines
2.7 KiB
Text
82 lines
2.7 KiB
Text
package fields
|
|
|
|
import (
|
|
"fmt"
|
|
|
|
"github.com/acaloiaro/frm/types"
|
|
)
|
|
|
|
// SingleChoice is a form input type allowing only a single choice (radio)
|
|
templ SingleChoice(field types.FormField) {
|
|
@LabeledField(field) {
|
|
<div class="w-full">
|
|
<div class="join w-full">
|
|
for _, option := range field.SortedOptions() {
|
|
<label class="join-item h-auto flex-grow shrink btn has-[:checked]:bg-sky-400 first:border-x-0 last:border-r-0 border-y-0 border-black bg-sky-50 py-3">
|
|
<!-- the input field is hidden with opacity, width, and height, but available for HTML validation when 'required' -->
|
|
<input
|
|
class="opacity-0 w-0 h-0"
|
|
type="radio"
|
|
id={ field.ID.String() }
|
|
name={ field.ID.String() }
|
|
aria-label={ option.Label }
|
|
value={ option.Value }
|
|
if field.Required {
|
|
required
|
|
}
|
|
_={ fmt.Sprintf("on change trigger field_change(field_id: '%s', value: my.value)", field.ID.String()) }
|
|
/>
|
|
{ option.Label }
|
|
</label>
|
|
}
|
|
</div>
|
|
if len(field.OptionLabels) > 0 {
|
|
<div class="flex flex-grow w-full text-center text-gray-400">
|
|
for _, label := range field.OptionLabels {
|
|
<div class="w-full first:text-left last:text-right">{ label }</div>
|
|
}
|
|
</div>
|
|
}
|
|
</div>
|
|
<div
|
|
id={ fmt.Sprintf("errors-%s", field.ID.String()) }
|
|
class="text-red-400"
|
|
></div>
|
|
}
|
|
}
|
|
|
|
// SingleChoiceSpaced is a form input type allowing only a single choice (radio), spaced out
|
|
templ SingleChoiceSpaced(field types.FormField) {
|
|
@LabeledField(field) {
|
|
<div class="w-full">
|
|
<div class="grid grid-cols-1 xl:grid-cols-2 gap-8">
|
|
for _, option := range field.SortedOptions() {
|
|
<label
|
|
class="flex gap-2 w-auto h-auto btn bg-sky-50 has-[:checked]:bg-sky-400 has-[:checked]:border-sky-500 py-3"
|
|
>
|
|
<span>{ option.Label }</span>
|
|
<span class="grow"></span>
|
|
<input
|
|
type="radio"
|
|
class="peer opacity-0 w-0 h-0"
|
|
name={ field.ID.String() }
|
|
aria-label={ option.Label }
|
|
value={ option.Value }
|
|
if field.Required {
|
|
required
|
|
}
|
|
_={ fmt.Sprintf("on change trigger field_change(field_id: '%s', value: my.value)", field.ID.String()) }
|
|
/>
|
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="currentColor" class="size-7 invisible peer-checked:visible bg-sky-200 rounded-full p-1">
|
|
<path fill-rule="evenodd" d="M19.916 4.626a.75.75 0 0 1 .208 1.04l-9 13.5a.75.75 0 0 1-1.154.114l-6-6a.75.75 0 0 1 1.06-1.06l5.353 5.353 8.493-12.74a.75.75 0 0 1 1.04-.207Z" clip-rule="evenodd"></path>
|
|
</svg>
|
|
</label>
|
|
}
|
|
</div>
|
|
</div>
|
|
<div
|
|
id={ fmt.Sprintf("errors-%s", field.ID.String()) }
|
|
class="text-red-400"
|
|
></div>
|
|
}
|
|
}
|