Skip to content

Commit

Permalink
Add the ability to use translations
Browse files Browse the repository at this point in the history
closes #2
  • Loading branch information
yuki24 committed Mar 13, 2024
1 parent 63facbf commit 626f271
Show file tree
Hide file tree
Showing 3 changed files with 186 additions and 15 deletions.
41 changes: 27 additions & 14 deletions app/helpers/shoelace/form_helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,9 @@ def render(&block)
options = @options.stringify_keys
options["value"] = options.fetch("value") { value_before_type_cast }
add_default_name_and_id(options)
label = options.delete('label').presence || @method_name.humanize

@template_object.content_tag('sl-switch', @method_name.to_s.humanize, options, &block)
@template_object.content_tag('sl-switch', label, options, &block)
end
end

Expand Down Expand Up @@ -123,6 +124,7 @@ def render(&block)
options = @options.stringify_keys
options["value"] = @checked_value
options["checked"] = true if input_checked?(options)
label = options.delete("label") || @method_name.humanize

if options["multiple"]
add_default_name_and_id_for_value(@checked_value, options)
Expand All @@ -136,7 +138,7 @@ def render(&block)
sl_checkbox_tag = if block_given?
@template_object.content_tag('sl-checkbox', '', options, &block)
else
@template_object.content_tag('sl-checkbox', @method_name.to_s.humanize, options)
@template_object.content_tag('sl-checkbox', label || @method_name.to_s.humanize, options)
end

if include_hidden
Expand Down Expand Up @@ -181,8 +183,9 @@ def render_collection(&block)
html_options = @html_options.stringify_keys
html_options["value"] = value
add_default_name_and_id(html_options)
html_options["label"] = @options[:label].presence || @method_name.humanize

@template_object.content_tag('sl-radio-group', html_options.with_defaults(label: @method_name.humanize)) { super(&block) }
@template_object.content_tag('sl-radio-group', html_options) { super(&block) }
end

def hidden_field
Expand All @@ -206,59 +209,69 @@ class ShoelaceFormBuilder < ActionView::Helpers::FormBuilder #:nodoc:
url: :url
}.each do |field_type, field_class|
# def email_field(method, **options, &block)
# ShoelaceInputField.new(:email, object_name, method, @template, options.with_defaults(label: method.to_s.humanize)).render(&block)
# ShoelaceInputField.new(:email, object_name, method, @template, options.with_defaults(label: label_text(method))).render(&block)
# end
eval <<-RUBY, nil, __FILE__, __LINE__ + 1
def #{field_type}_field(method, **options, &block)
ShoelaceInputField.new(:#{field_class}, object_name, method, @template, options.with_defaults(object: @object, label: method.to_s.humanize)).render(&block)
ShoelaceInputField.new(:#{field_class}, object_name, method, @template, options.with_defaults(object: @object, label: label_text(method))).render(&block)
end
RUBY
end

def color_field(method, **options)
ShoelaceColorPicker.new(object_name, method, @template, options.with_defaults(object: @object)).render
ShoelaceColorPicker.new(object_name, method, @template, options.with_defaults(object: @object, label: label_text(method))).render
end
alias color_picker color_field

def range_field(method, **options)
ShoelaceRange.new(object_name, method, @template, options.with_defaults(object: @object, label: method.to_s.humanize)).render
ShoelaceRange.new(object_name, method, @template, options.with_defaults(object: @object, label: label_text(method))).render
end
alias range range_field

def switch_field(method, **options, &block)
ShoelaceSwitch.new(object_name, method, @template, options.with_defaults(object: @object)).render(&block)
if block_given?
ShoelaceSwitch.new(object_name, method, @template, options.with_defaults(object: @object)).render(&block)
else
ShoelaceSwitch.new(object_name, method, @template, options.with_defaults(object: @object, label: label_text(method))).render(&block)
end
end
alias switch switch_field

def text_area(method, **options, &block)
ShoelaceTextArea.new(object_name, method, @template, options.with_defaults(object: @object, label: method.to_s.humanize, resize: 'auto')).render(&block)
ShoelaceTextArea.new(object_name, method, @template, options.with_defaults(object: @object, label: label_text(method), resize: 'auto')).render(&block)
end

def check_box(method, options = {}, checked_value = "1", unchecked_value = "0", &block)
ShoelaceCheckBox.new(object_name, method, @template, checked_value, unchecked_value, options.merge(object: @object)).render(&block)
ShoelaceCheckBox.new(object_name, method, @template, checked_value, unchecked_value, options.with_defaults(label: label_text(method)).merge(object: @object)).render(&block)
end

def select(method, choices = nil, options = {}, html_options = {}, &block)
ShoelaceSelect.new(object_name, method, @template, choices, options.with_defaults(object: @object), html_options.with_defaults(label: method.to_s.humanize), &block).render
ShoelaceSelect.new(object_name, method, @template, choices, options.with_defaults(object: @object), html_options.with_defaults(label: label_text(method)), &block).render
end

def collection_select(method, collection, value_method, text_method, options = {}, html_options = {}, &block)
ShoelaceCollectionSelect.new(object_name, method, @template, collection, value_method, text_method, options.with_defaults(object: @object), html_options.with_defaults(label: method.to_s.humanize), &block).render
ShoelaceCollectionSelect.new(object_name, method, @template, collection, value_method, text_method, options.with_defaults(object: @object), html_options.with_defaults(label: label_text(method)), &block).render
end

def grouped_collection_select(method, collection, group_method, group_label_method, option_key_method, option_value_method, options = {}, html_options = {})
ShoelaceGroupedCollectionSelect.new(object_name, method, @template, collection, group_method, group_label_method, option_key_method, option_value_method, options.with_defaults(object: @object), html_options.with_defaults(label: method.to_s.humanize)).render
ShoelaceGroupedCollectionSelect.new(object_name, method, @template, collection, group_method, group_label_method, option_key_method, option_value_method, options.with_defaults(object: @object), html_options.with_defaults(label: label_text(method))).render
end

def collection_radio_buttons(method, collection, value_method, text_method, options = {}, html_options = {}, &block)
ShoelaceCollectionRadioButtons.new(object_name, method, @template, collection, value_method, text_method, options.with_defaults(object: @object), html_options).render(&block)
ShoelaceCollectionRadioButtons.new(object_name, method, @template, collection, value_method, text_method, options.with_defaults(object: @object, label: label_text(method)), html_options).render(&block)
end

def submit(value = nil, options = {})
value, options = nil, value if value.is_a?(Hash)

@template.sl_submit_tag(value || submit_default_value, **options)
end

private

def label_text(method, tag_value = nil)
::ActionView::Helpers::Tags::Label::LabelBuilder.new(@template, object_name, method, object, tag_value).to_s
end
end

DEFAULT_FORM_PARAMETERS = { builder: ShoelaceFormBuilder }
Expand Down
2 changes: 1 addition & 1 deletion test/helpers/form_helper_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -149,7 +149,7 @@ class FormHelperTest < ActionView::TestCase
test "#color_field" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.color_field(:name)
<sl-color-picker name="user[name]" id="user_name"></sl-color-picker>
<sl-color-picker name="user[name]" id="user_name" label="Name"></sl-color-picker>
HTML
end
end
Expand Down
158 changes: 158 additions & 0 deletions test/helpers/translation_test.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,158 @@
# frozen_string_literal: true
require 'test_helper'

require_relative '../../app/helpers/shoelace/form_helper'

class TranslationTest < ActionView::TestCase
include ActionView::Helpers::TranslationHelper
include Shoelace::FormHelper

setup do
I18n.backend.store_translations :en,
helpers: {
label: {
user: { name: "Full Name" }
}
}

view_paths = ActionController::Base.view_paths
view_paths.each(&:clear_cache)
@view = ::ActionView::Base.with_empty_template_cache.with_view_paths(view_paths, {})
end

teardown do
I18n.backend.reload!
end

test "Form helpers should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.text_field(:name)
<sl-input label="Full Name" type="text" name="user[name]" id="user_name"></sl-input>
HTML
end
end

test "#color_field should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.color_field(:name)
<sl-color-picker name="user[name]" id="user_name" label="Full Name"></sl-color-picker>
HTML
end
end

test "#range_field should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.range_field(:name)
<sl-range label="Full Name" name="user[name]" id="user_name"></sl-range>
HTML
end
end

test "#switch_field should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.switch_field(:name)
<sl-switch name="user[name]" id="user_name">Full Name</sl-switch>
HTML
end
end

test "#text_area should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.text_area(:name)
<sl-textarea label="Full Name" resize="auto" name="user[name]" id="user_name"></sl-textarea>
HTML
end
end

test "#check_box should respect label translations" do
sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.check_box(:name)
<input name="user[name]" type="hidden" value="0" autocomplete="off" />
<sl-checkbox value="1" name="user[name]" id="user_name">Full Name</sl-checkbox>
HTML
end
end

test "#selec should respect label translationst" do
users = {
"Yuki Nishijima" => 1,
"Matz" => 2,
"Koichi Sasada" => 3
}

sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.select(:name, users)
<sl-select label="Full Name" name="user[name]" id="user_name">
<sl-option value="1">Yuki Nishijima</sl-option>
<sl-option value="2">Matz</sl-option>
<sl-option value="3">Koichi Sasada</sl-option>
</sl-select>
HTML
end
end

test "#collection_select should respect label translations" do
users = {
1 => "Yuki Nishijima",
2 => "Matz",
3 => "Koichi Sasada",
}

sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.collection_select(:name, users, :first, :last)
<sl-select label="Full Name" name="user[name]" id="user_name">
<sl-option value="1">Yuki Nishijima</sl-option>
<sl-option value="2">Matz</sl-option>
<sl-option value="3">Koichi Sasada</sl-option>
</sl-select>
HTML
end
end

test "#grouped_collection_select should respect label translations" do
users = [
OpenStruct.new(
group_name: "Main maintainers",
members: [
OpenStruct.new(id: 1, name: "Matz"),
OpenStruct.new(id: 2, name: "Koichi Sasada"),
]
),
OpenStruct.new(
group_name: "Default gem maintainers",
members: [OpenStruct.new(id: 3, name: "Yuki Nishijima")]
),
]

sl_form_for(User.new(name: "2"), url: "/") do |form|
assert_dom_equal <<~HTML, form.grouped_collection_select(:name, users, :members, :group_name, :id, :name)
<sl-select label="Full Name" name="user[name]" id="user_name" value="2">
<small>Main maintainers</small>
<sl-option value="1">Matz</sl-option>
<sl-option value="2" checked="checked">Koichi Sasada</sl-option>
<sl-divider></sl-divider>
<small>Default gem maintainers</small>
<sl-option value="3">Yuki Nishijima</sl-option>
</sl-select>
HTML
end
end

test "#collection_radio_buttons should respect label translations" do
users = {
1 => "Yuki Nishijima",
2 => "Matz",
3 => "Koichi Sasada",
}

sl_form_for(User.new, url: "/") do |form|
assert_dom_equal <<~HTML, form.collection_radio_buttons(:name, users, :first, :last)
<sl-radio-group label="Full Name" name="user[name]" id="user_name">
<sl-radio value="1" id="user_name_1">Yuki Nishijima</sl-radio>
<sl-radio value="2" id="user_name_2">Matz</sl-radio>
<sl-radio value="3" id="user_name_3">Koichi Sasada</sl-radio>
</sl-radio-group>
HTML
end
end
end

0 comments on commit 626f271

Please sign in to comment.