Module: Protege::Components::FormsHelper
- Included in:
- ComponentsHelper
- Defined in:
- app/helpers/protege/components/forms_helper.rb
Overview
Form-building UI elements shared across engine views.
Split out of ComponentsHelper so each module stays focused; FormsHelper
owns the input styling constants and the field/select/checkbox builders that
wrap Rails form helpers in Protege's design system.
Colors use CSS custom properties (--surface, --border, --text, --text-faint) defined in tailwind/application.css so dark mode works via a single .dark class toggle.
Constant Summary collapse
- FORM_INPUT =
Tailwind classes applied to text inputs, selects, and textareas.
'block w-full rounded-sm px-2.5 py-1.5 text-sm shadow-sm ' \ 'focus:border-amber-500 focus:outline-none focus:ring-1 focus:ring-amber-500'
- FORM_LABEL =
Tailwind classes applied to field labels.
'block text-sm font-medium mb-1'- FORM_CHECKBOX =
Tailwind classes applied to checkboxes.
'h-4 w-4 rounded text-amber-600 focus:ring-amber-500'
Instance Method Summary collapse
-
#form_checkbox(form, field, label: nil) ⇒ ActiveSupport::SafeBuffer
Render a labelled checkbox wired to a form builder.
-
#form_checklist(form, field, collection, label: nil, hint: nil, value: :to_s, text: :to_s) ⇒ ActiveSupport::SafeBuffer
Render a labelled checklist — one checkbox per item, backed by an array attribute, wired to a form builder.
-
#form_email_address(record, domains) ⇒ ActiveSupport::SafeBuffer
Render the split prefix/domain email-address control for a persona.
-
#form_errors(record) ⇒ ActiveSupport::SafeBuffer
Render a record's validation errors as a styled list, or nothing when valid.
-
#form_field(form, field, label: nil, hint: nil, **input_attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled text field with an optional hint, wired to a form builder.
-
#form_input_style ⇒ String
Build the inline style applied to form controls so they track the theme.
-
#form_select(form, field, choices, label: nil, prompt: nil, selected: nil, **attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled select wired to a form builder.
-
#form_text_area(form, field, label: nil, hint: nil, fill: false, **input_attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled textarea with an optional hint, wired to a form builder.
Instance Method Details
#form_checkbox(form, field, label: nil) ⇒ ActiveSupport::SafeBuffer
Render a labelled checkbox wired to a form builder.
123 124 125 126 127 128 |
# File 'app/helpers/protege/components/forms_helper.rb', line 123 def form_checkbox(form, field, label: nil) tag.div(class: 'flex items-center gap-3') do form.check_box(field, class: FORM_CHECKBOX, style: 'border: 1px solid var(--border)') + form.label(field, label, class: 'text-sm font-medium') end end |
#form_checklist(form, field, collection, label: nil, hint: nil, value: :to_s, text: :to_s) ⇒ ActiveSupport::SafeBuffer
Render a labelled checklist — one checkbox per item, backed by an array attribute, wired to a
form builder. Rails' collection_check_boxes emits the hidden blank field for us, so unchecking
every box submits an empty array (clearing the attribute) instead of omitting it.
142 143 144 145 146 147 148 149 150 151 152 153 154 |
# File 'app/helpers/protege/components/forms_helper.rb', line 142 def form_checklist(form, field, collection, label: nil, hint: nil, value: :to_s, text: :to_s) tag.div do (label ? tag.label(label, class: FORM_LABEL) : ''.html_safe) + form_hint(hint) + tag.div(class: 'space-y-2 pt-1') do form.collection_check_boxes(field, collection, value, text) do |b| b.label(class: 'flex items-center gap-3 text-sm') do b.check_box(class: FORM_CHECKBOX, style: 'border: 1px solid var(--border)') + b.text end end end end end |
#form_email_address(record, domains) ⇒ ActiveSupport::SafeBuffer
Render the split prefix/domain email-address control for a persona.
When domains exist, render a prefix text box, an @ separator, and a domain
select preselected to the record's current domain; otherwise prompt the
operator to add a domain first.
87 88 89 90 91 92 93 94 |
# File 'app/helpers/protege/components/forms_helper.rb', line 87 def form_email_address(record, domains) tag.div do tag.label('Email address', class: FORM_LABEL) + tag.div(class: 'flex items-center gap-2') do domains.any? ? email_address_fields(record, domains) : email_address_empty end end end |
#form_errors(record) ⇒ ActiveSupport::SafeBuffer
Render a record's validation errors as a styled list, or nothing when valid.
34 35 36 37 38 39 40 41 42 |
# File 'app/helpers/protege/components/forms_helper.rb', line 34 def form_errors(record) return ''.html_safe unless record.errors.any? tag.div(class: 'rounded-lg border border-red-200 bg-red-50 px-4 py-3 text-sm text-red-700') do tag.ul(class: 'list-disc pl-4 space-y-1') do safe_join(record.errors..map { || tag.li() }) end end end |
#form_field(form, field, label: nil, hint: nil, **input_attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled text field with an optional hint, wired to a form builder.
52 53 54 55 56 57 58 |
# File 'app/helpers/protege/components/forms_helper.rb', line 52 def form_field(form, field, label: nil, hint: nil, **input_attrs) tag.div do form.label(field, label, class: FORM_LABEL) + form.text_field(field, class: FORM_INPUT, style: form_input_style, **input_attrs) + form_hint(hint) end end |
#form_input_style ⇒ String
Build the inline style applied to form controls so they track the theme.
26 27 28 |
# File 'app/helpers/protege/components/forms_helper.rb', line 26 def form_input_style 'background: var(--surface); border: 1px solid var(--border); color: var(--text)' end |
#form_select(form, field, choices, label: nil, prompt: nil, selected: nil, **attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled select wired to a form builder.
71 72 73 74 75 76 |
# File 'app/helpers/protege/components/forms_helper.rb', line 71 def form_select(form, field, choices, label: nil, prompt: nil, selected: nil, **attrs) tag.div do form.label(field, label, class: FORM_LABEL) + form.select(field, choices, { prompt:, selected: }, class: FORM_INPUT, style: form_input_style, **attrs) end end |
#form_text_area(form, field, label: nil, hint: nil, fill: false, **input_attrs) ⇒ ActiveSupport::SafeBuffer
Render a labelled textarea with an optional hint, wired to a form builder.
106 107 108 109 110 111 112 113 114 115 |
# File 'app/helpers/protege/components/forms_helper.rb', line 106 def form_text_area(form, field, label: nil, hint: nil, fill: false, **input_attrs) input_attrs[:rows] ||= 3 size_class = fill ? 'flex-1 min-h-0 resize-none' : 'resize-y min-h-[6rem]' tag.div(class: fill ? 'flex min-h-0 flex-1 flex-col' : nil) do (label ? form.label(field, label, class: FORM_LABEL) : ''.html_safe) + form.text_area(field, class: "#{FORM_INPUT} font-mono #{size_class}", style: form_input_style, **input_attrs) + form_hint(hint) end end |