rails_bootstrap_form 0.4.2 → 0.5.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5874a38745d73c1b0bb05c751711cdc380be8684c71187069e07224e9d40333a
4
- data.tar.gz: ffe2043c13700e6015d7741b51550c52642098c412f29b1921a7e98ed20ec9cf
3
+ metadata.gz: 75f1c7df21987622c3341031991186ceff26dc21f48c301ee2017fb47dd1074a
4
+ data.tar.gz: e84fbf45f5bcff4bfad1904253c5e549fa616ebc9d646b762facb78cca121ce7
5
5
  SHA512:
6
- metadata.gz: 657b116576955954f11ecd923cd61277613bd732d7b986effe3d5b908ed38531549413baa47436167fd7d675fb5aab709863cc53bfb19f99d4a39abb2148de63
7
- data.tar.gz: '09d24eb35c72a56c834d0031ce85152e1a0241a1d4614dc69ebb5bc820b45780380d80132a9c882086b6524d8bb9fd5826d41c339f45bd87b335fcb0ceb97eeb'
6
+ metadata.gz: ee6cf0a877cff1e96ccc3e95495c331f41c5af536a23332b58669a10f6c6db6c3f1dc9f5fd3cd2fc2e51c0040380e18a7477231f4b108d306593dfc1f6844fa7
7
+ data.tar.gz: 39f8e46ae208727fd81127cb3c8de3f32878c16b957ff21fc882f6a250e7972bd00f573dd4dd6a958140d7564e57a4e70e1a86eb30c484e73b3ab42ece3a2bb5
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- rails_bootstrap_form (0.4.2)
4
+ rails_bootstrap_form (0.5.1)
5
5
 
6
6
  GEM
7
7
  remote: http://rubygems.org/
@@ -1,8 +1,8 @@
1
1
  label.is-invalid, .invalid-feedback {
2
- color: var(--bs-danger);
2
+ color: var(--bs-form-invalid-color);
3
3
  }
4
4
  label.required::after {
5
- color: var(--bs-danger);
5
+ color: var(--bs-form-invalid-color);
6
6
  content: "*";
7
7
  padding-left: .25rem;
8
8
  top: -2px;
@@ -3,6 +3,8 @@
3
3
  # -*- warn_indent: true -*-
4
4
 
5
5
  class Address < ApplicationRecord
6
+ validates :street, :city, :country_id, presence: true
7
+
6
8
  belongs_to :user
7
9
  belongs_to :country
8
10
 
@@ -4,7 +4,15 @@
4
4
 
5
5
  class User < ApplicationRecord
6
6
  validates :name, presence: true, length: {in: 2..50}
7
- validates :email, presence: true
7
+ validates :terms, acceptance: true
8
+ validates :email,
9
+ :password,
10
+ :mobile_number,
11
+ :birth_date,
12
+ :favorite_color,
13
+ :fruit_id,
14
+ :skill_ids,
15
+ presence: true
8
16
 
9
17
  has_one :address, dependent: :destroy
10
18
 
@@ -9,19 +9,16 @@
9
9
  <%= form.text_field :password, autocomplete: "new-password" %>
10
10
  <%= form.phone_field :mobile_number %>
11
11
  <%= form.date_field :birth_date %>
12
- <%= form.check_box :terms %>
12
+ <%= form.check_box :terms, bootstrap_form: {switch: false}, required: true %>
13
13
  <%= form.range_field :excellence %>
14
14
  <%= form.url_field :blog_url %>
15
+ <%= form.collection_radio_buttons :fruit_id, ::Fruit.all, :id, :name, {bootstrap_form: {layout: :inline}, checked: form.object.fruit_id} %>
15
16
  <%= form.color_field :favorite_color %>
16
- <%= form.select :fruit_id, options_for_select(::Fruit.pluck(:name, :id), form.object.fruit_id),
17
- {include_blank: "Select Favorite Fruit"} %>
18
- <%= form.collection_check_boxes :skill_ids, ::Skill.all, :id, :name do |b| %>
19
- <%= b.check_box + b.text %>
20
- <% end %>
17
+ <%= form.collection_check_boxes :skill_ids, ::Skill.all, :id, :name, {bootstrap_form: {layout: :inline}} %>
21
18
  <%= form.fields_for :address, include_id: false do |address_form| %>
22
19
  <%= address_form.text_area :street %>
23
20
  <%= address_form.text_field :state %>
24
- <%= address_form.grouped_collection_select :city, ::Country.all, :cities, :name, :id, :name %>
21
+ <%= address_form.grouped_collection_select :city, ::Country.all, :cities, :name, :id, :name, {include_blank: "Select city"} %>
25
22
  <%= address_form.text_field :postal_code %>
26
23
  <%= address_form.select :country_id, options_for_select(::Country.pluck(:name, :id), address_form.object.country_id),
27
24
  {include_blank: "Select Country", bootstrap_form: {}} %>
@@ -42,7 +42,10 @@
42
42
  },
43
43
  help_texts: {
44
44
  user: {
45
- email: "Please use official email address"
45
+ email: "Please use official email address",
46
+ terms: "You must first accept terms and conditions in order to continue",
47
+ skill_ids: "Select your strong skills",
48
+ fruit_id: "Select your favorite fruit"
46
49
  }
47
50
  },
48
51
  }
@@ -25,10 +25,6 @@ module RailsBootstrapForm
25
25
  options[:html].reverse_merge!(RailsBootstrapForm.config.default_form_attributes)
26
26
  end
27
27
 
28
- def control_specific_class(field_tag_name)
29
- "rails-bootstrap-forms-#{field_tag_name.to_s.tr("_", "-")}"
30
- end
31
-
32
- private :apply_default_form_options, :control_specific_class
28
+ private :apply_default_form_options
33
29
  end
34
30
  end
@@ -86,6 +86,10 @@ module RailsBootstrapForm
86
86
  # Default is `form-control-plaintext`.
87
87
  attr_accessor :static_field_class
88
88
 
89
+ # Option to control whether the check box should look like bootstrap switches.
90
+ # Default is `false`.
91
+ attr_accessor :switch
92
+
89
93
  def initialize(options = {})
90
94
  set_defaults
91
95
  set_bootstrap_form_options(options)
@@ -146,6 +150,8 @@ module RailsBootstrapForm
146
150
  @floating = false
147
151
 
148
152
  @static_field_class = "form-control-plaintext"
153
+
154
+ @switch = false
149
155
  end
150
156
 
151
157
  private :set_defaults
@@ -0,0 +1,66 @@
1
+ # -*- encoding: utf-8 -*-
2
+ # -*- frozen_string_literal: true -*-
3
+ # -*- warn_indent: true -*-
4
+
5
+ module RailsBootstrapForm
6
+ module Components
7
+ module CheckBox
8
+ extend ActiveSupport::Concern
9
+
10
+ def self.included(base_class)
11
+ def check_box_label(attribute, checked_value, options, bootstrap_options, &block)
12
+ unless bootstrap_options.skip_label
13
+ label_options = {
14
+ class: check_box_label_class(attribute, bootstrap_options, options)
15
+ }
16
+ label_options[:for] = options[:id] if options[:id].present?
17
+
18
+ label_name = if options[:multiple]
19
+ check_box_value(attribute, checked_value)
20
+ else
21
+ attribute
22
+ end
23
+
24
+ label_text = check_box_label_text(attribute, options, bootstrap_options, &block)
25
+
26
+ label(label_name, label_text, label_options)
27
+ end
28
+ end
29
+
30
+ def check_box_label_text(attribute, options, bootstrap_options, &block)
31
+ block ? capture(&block) : label_text(attribute, bootstrap_options)
32
+ end
33
+
34
+ def check_box_value(attribute, value)
35
+ # label's `for` attribute needs to match checkbox tag's id,
36
+ # IE sanitized value, IE
37
+ # https://github.com/rails/rails/blob/5-0-stable/actionview/lib/action_view/helpers/tags/base.rb#L123-L125
38
+ "#{attribute}_#{value.to_s.gsub(/\s/, "_").gsub(/[^-[[:word:]]]/, "").mb_chars.downcase}"
39
+ end
40
+
41
+ def check_box_classes(attribute, options)
42
+ classes = Array(options[:class]) << "form-check-input"
43
+ classes << "is-invalid" if is_invalid?(attribute)
44
+ classes.flatten.compact
45
+ end
46
+
47
+ def check_box_label_class(attribute, bootstrap_options, options)
48
+ classes = Array("form-check-label") << bootstrap_options.additional_label_class
49
+ classes << "required" if is_field_required?(attribute, options) && !bootstrap_options.inline?
50
+ classes << "is-invalid" if is_invalid?(attribute)
51
+ classes << bootstrap_options.hide_class if bootstrap_options.hide_label
52
+ classes.flatten.compact
53
+ end
54
+
55
+ def check_box_wrapper_class(bootstrap_options)
56
+ classes = Array("form-check")
57
+ classes << "form-switch" if bootstrap_options.switch
58
+ classes << "form-check-inline" if bootstrap_options.inline?
59
+ classes.flatten.compact
60
+ end
61
+
62
+ private :check_box_label, :check_box_classes, :check_box_label_class, :check_box_wrapper_class
63
+ end
64
+ end
65
+ end
66
+ end
@@ -13,7 +13,7 @@ module RailsBootstrapForm
13
13
 
14
14
  help_text = (bootstrap_options.help_text || scoped_help_text(attribute))
15
15
 
16
- tag.span(help_text, class: "form-text text-muted") if help_text.present?
16
+ tag.div(help_text, class: "form-text text-muted") if help_text.present?
17
17
  end
18
18
 
19
19
  def object_class
@@ -8,12 +8,12 @@ module RailsBootstrapForm
8
8
  extend ActiveSupport::Concern
9
9
 
10
10
  def self.included(base_class)
11
- def label(attribute, bootstrap_options)
11
+ def draw_label(attribute, bootstrap_options)
12
12
  unless bootstrap_options.skip_label
13
13
  label_class = label_classes(attribute, bootstrap_options)
14
14
  label_text = label_text(attribute, bootstrap_options)
15
15
 
16
- super(attribute, label_text, class: label_class)
16
+ label(attribute, label_text, class: label_class)
17
17
  end
18
18
  end
19
19
 
@@ -29,7 +29,7 @@ module RailsBootstrapForm
29
29
  bootstrap_options.label_text || object&.class.try(:human_attribute_name, attribute)
30
30
  end
31
31
 
32
- private :label, :label_classes, :label_text
32
+ private :draw_label, :label_classes, :label_text
33
33
  end
34
34
  end
35
35
  end
@@ -0,0 +1,62 @@
1
+ # -*- encoding: utf-8 -*-
2
+ # -*- frozen_string_literal: true -*-
3
+ # -*- warn_indent: true -*-
4
+
5
+ module RailsBootstrapForm
6
+ module Components
7
+ module RadioButton
8
+ extend ActiveSupport::Concern
9
+
10
+ def self.included(base_class)
11
+ def radio_button_label(attribute, value, options, bootstrap_options)
12
+ unless bootstrap_options.skip_label
13
+ label_options = {
14
+ value: value,
15
+ class: radio_button_label_class(attribute, bootstrap_options, options)
16
+ }
17
+ label_options[:for] = options[:id] if options[:id].present?
18
+
19
+ label_name = if options[:multiple]
20
+ radio_button_value(attribute, checked_value)
21
+ else
22
+ attribute
23
+ end
24
+
25
+ label_text = label_text(attribute, bootstrap_options)
26
+
27
+ label(label_name, label_text, label_options)
28
+ end
29
+ end
30
+
31
+ def radio_button_value(attribute, value)
32
+ # label's `for` attribute needs to match checkbox tag's id,
33
+ # IE sanitized value, IE
34
+ # https://github.com/rails/rails/blob/5-0-stable/actionview/lib/action_view/helpers/tags/base.rb#L123-L125
35
+ "#{attribute}_#{value.to_s.gsub(/\s/, "_").gsub(/[^-[[:word:]]]/, "").mb_chars.downcase}"
36
+ end
37
+
38
+ def radio_button_classes(attribute, options)
39
+ classes = Array(options[:class]) << "form-check-input"
40
+ classes << "is-invalid" if is_invalid?(attribute)
41
+ classes.flatten.compact
42
+ end
43
+
44
+ def radio_button_label_class(attribute, bootstrap_options, options)
45
+ classes = Array("form-check-label") << bootstrap_options.additional_label_class
46
+ classes << "required" if is_field_required?(attribute, options) && !bootstrap_options.inline?
47
+ classes << "is-invalid" if is_invalid?(attribute)
48
+ classes << bootstrap_options.hide_class if bootstrap_options.hide_label
49
+ classes.flatten.compact
50
+ end
51
+
52
+ def radio_button_wrapper_class(bootstrap_options)
53
+ classes = Array("form-check")
54
+ classes << "form-check-inline" if bootstrap_options.inline?
55
+ classes.flatten.compact
56
+ end
57
+
58
+ private :radio_button_label, :radio_button_classes, :radio_button_label_class, :radio_button_wrapper_class
59
+ end
60
+ end
61
+ end
62
+ end
@@ -10,10 +10,14 @@ module RailsBootstrapForm
10
10
  autoload :Labels
11
11
  autoload :RequiredField
12
12
  autoload :Errors
13
+ autoload :CheckBox
14
+ autoload :RadioButton
13
15
 
14
16
  include HelpText
15
17
  include Labels
16
18
  include RequiredField
17
19
  include Errors
20
+ include CheckBox
21
+ include RadioButton
18
22
  end
19
23
  end
@@ -13,7 +13,7 @@ module RailsBootstrapForm
13
13
  end
14
14
 
15
15
  def field_wrapper(attribute, bootstrap_options, options, &block)
16
- label = label(attribute, bootstrap_options)
16
+ label = draw_label(attribute, bootstrap_options)
17
17
  help_text = help_text(attribute, bootstrap_options)
18
18
 
19
19
  if bootstrap_options.floating
@@ -0,0 +1,24 @@
1
+ # -*- encoding: utf-8 -*-
2
+ # -*- frozen_string_literal: true -*-
3
+ # -*- warn_indent: true -*-
4
+
5
+ module RailsBootstrapForm
6
+ module Inputs
7
+ module Base
8
+ extend ActiveSupport::Concern
9
+
10
+ def self.included(base_class)
11
+ def collection_input_checked?(checked, obj, input_value)
12
+ checked == input_value || Array(checked).try(:include?, input_value) ||
13
+ checked == obj || Array(checked).try(:include?, obj)
14
+ end
15
+
16
+ def control_specific_class(field_tag_name)
17
+ "rails-bootstrap-forms-#{field_tag_name.to_s.tr("_", "-")}"
18
+ end
19
+
20
+ private :collection_input_checked?, :control_specific_class
21
+ end
22
+ end
23
+ end
24
+ end
@@ -5,6 +5,12 @@
5
5
  module RailsBootstrapForm
6
6
  module Inputs
7
7
 
8
+ extend ActiveSupport::Autoload
9
+
10
+ autoload :Base
11
+
12
+ include Base
13
+
8
14
  FIELD_HELPERS = %i[
9
15
  text_field
10
16
  url_field
@@ -120,5 +126,97 @@ module RailsBootstrapForm
120
126
 
121
127
  text_field(attribute, static_options)
122
128
  end
129
+
130
+ def check_box(attribute, options = {}, checked_value = "1", unchecked_value = "0", &block)
131
+ bootstrap_options = bootstrap_form_options.scoped(options.delete(:bootstrap_form))
132
+
133
+ options[:class] = check_box_classes(attribute, options)
134
+
135
+ check_box_field = super(attribute, options, checked_value, unchecked_value)
136
+ check_box_help_text = help_text(attribute, bootstrap_options)
137
+
138
+ check_box_label = check_box_label(attribute, checked_value, options, bootstrap_options, &block)
139
+
140
+ check_box_html = tag.div(class: check_box_wrapper_class(bootstrap_options)) do
141
+ concat(check_box_field)
142
+ concat(check_box_label)
143
+ concat(check_box_help_text) unless bootstrap_options.inline?
144
+ concat(generate_error(attribute)) if is_invalid?(attribute) && !bootstrap_options.inline?
145
+ end
146
+
147
+ check_box_html
148
+ end
149
+
150
+ def radio_button(attribute, value, options = {})
151
+ bootstrap_options = bootstrap_form_options.scoped(options.delete(:bootstrap_form))
152
+
153
+ options[:class] = radio_button_classes(attribute, options)
154
+
155
+ radio_button_field = super(attribute, value, options)
156
+ radio_button_help_text = help_text(attribute, bootstrap_options)
157
+
158
+ radio_button_label = radio_button_label(attribute, value, options, bootstrap_options)
159
+
160
+ radio_button_html = tag.div(class: radio_button_wrapper_class(bootstrap_options)) do
161
+ concat(radio_button_field)
162
+ concat(radio_button_label)
163
+ concat(radio_button_help_text) unless bootstrap_options.inline?
164
+ concat(generate_error(attribute)) if is_invalid?(attribute) && !bootstrap_options.inline?
165
+ end
166
+
167
+ radio_button_html
168
+ end
169
+
170
+ def collection_check_boxes(attribute, collection, value_method, text_method, options = {}, html_options = {}, &block)
171
+ options[:multiple] = true
172
+
173
+ inputs = ActiveSupport::SafeBuffer.new
174
+
175
+ collection.each do |object|
176
+ input_value = value_method.respond_to?(:call) ? value_method.call(object) : object.send(value_method)
177
+ input_options = {
178
+ bootstrap_form: {
179
+ label_text: text_method.respond_to?(:call) ? text_method.call(object) : object.send(text_method)
180
+ }
181
+ }.deep_merge!(options)
182
+
183
+ inputs << check_box(attribute, input_options, input_value, nil)
184
+ end
185
+
186
+ if options.delete(:include_hidden) { true }
187
+ inputs.prepend hidden_field(attribute, value: "", multiple: true)
188
+ end
189
+
190
+ field_wrapper_builder(attribute, options, html_options) do
191
+ concat(tag.div(class: control_specific_class(:collection_check_boxes)) do
192
+ concat(inputs)
193
+ end)
194
+ end
195
+ end
196
+
197
+ def collection_radio_buttons(attribute, collection, value_method, text_method, options = {}, html_options = {}, &block)
198
+ inputs = ActiveSupport::SafeBuffer.new
199
+
200
+ collection.each do |object|
201
+ input_value = value_method.respond_to?(:call) ? value_method.call(object) : object.send(value_method)
202
+ input_options = {
203
+ bootstrap_form: {
204
+ label_text: text_method.respond_to?(:call) ? text_method.call(object) : object.send(text_method)
205
+ }
206
+ }.deep_merge!(options)
207
+
208
+ if (checked = input_options[:checked])
209
+ input_options[:checked] = collection_input_checked?(checked, object, object.send(value_method))
210
+ end
211
+
212
+ inputs << radio_button(attribute, input_value, input_options)
213
+ end
214
+
215
+ field_wrapper_builder(attribute, options, html_options) do
216
+ concat(tag.div(class: control_specific_class(:collection_radio_buttons)) do
217
+ concat(inputs)
218
+ end)
219
+ end
220
+ end
123
221
  end
124
222
  end
@@ -3,6 +3,6 @@
3
3
  # -*- warn_indent: true -*-
4
4
 
5
5
  module RailsBootstrapForm
6
- VERSION = "0.4.2".freeze
6
+ VERSION = "0.5.1".freeze
7
7
  REQUIRED_RAILS_VERSION = "~> 7.0".freeze
8
8
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rails_bootstrap_form
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.2
4
+ version: 0.5.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Harshal LADHE (shivam091)
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2023-05-16 00:00:00.000000000 Z
11
+ date: 2023-05-20 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: generator_spec
@@ -111,15 +111,18 @@ files:
111
111
  - lib/rails_bootstrap_form/bootstrap_form_builder.rb
112
112
  - lib/rails_bootstrap_form/bootstrap_form_options.rb
113
113
  - lib/rails_bootstrap_form/components.rb
114
+ - lib/rails_bootstrap_form/components/check_box.rb
114
115
  - lib/rails_bootstrap_form/components/errors.rb
115
116
  - lib/rails_bootstrap_form/components/help_text.rb
116
117
  - lib/rails_bootstrap_form/components/labels.rb
118
+ - lib/rails_bootstrap_form/components/radio_button.rb
117
119
  - lib/rails_bootstrap_form/components/required_field.rb
118
120
  - lib/rails_bootstrap_form/configuration.rb
119
121
  - lib/rails_bootstrap_form/engine.rb
120
122
  - lib/rails_bootstrap_form/field_wrapper_builder.rb
121
123
  - lib/rails_bootstrap_form/input_group_builder.rb
122
124
  - lib/rails_bootstrap_form/inputs.rb
125
+ - lib/rails_bootstrap_form/inputs/base.rb
123
126
  - lib/rails_bootstrap_form/version.rb
124
127
  - sig/rails_bootstrap_form.rbs
125
128
  homepage: https://github.com/shivam091/rails_bootstrap_form