phlexi-form 0.7.1 → 0.8.0
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 +4 -4
- data/lib/phlexi/form/components/concerns/accepts_choices.rb +35 -5
- data/lib/phlexi/form/components/file_input.rb +2 -0
- data/lib/phlexi/form/components/select.rb +12 -2
- data/lib/phlexi/form/grouped_choices_mapper.rb +62 -0
- data/lib/phlexi/form/{choices_mapper.rb → simple_choices_mapper.rb} +9 -9
- data/lib/phlexi/form/version.rb +1 -1
- metadata +4 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 8747d53fec5851c3ad3f78d2c60fecfea530de3b033eb074ee5f4ce41bcd3181
|
4
|
+
data.tar.gz: 51c02f430a3a81a4ee05197463a14aa9b00804c0a5b3a1837f36533b006d9860
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 7434f1529fda38b7e02318c01be2fba09a97de755c874d2319730e4118d747a20bac457e7421bb34f0280f7e405079717df55e3d5ba3f32934f51deb1ebf43d7
|
7
|
+
data.tar.gz: 7457a359784b5404fee4a86ecdce99769f7899e080b7148aaff045719d536499efb4c6103c04334675258af94b74dbd10a9acacb7f327fb3a0f5f1508223f5bd
|
@@ -9,27 +9,57 @@ module Phlexi
|
|
9
9
|
|
10
10
|
def build_attributes
|
11
11
|
super
|
12
|
-
@choice_collection = attributes.delete(:choices) || field.choices
|
13
12
|
@label_method = attributes.delete(:label_method)
|
14
13
|
@value_method = attributes.delete(:value_method)
|
14
|
+
@group_method = attributes.delete(:group_method)
|
15
|
+
@group_label_method = attributes.delete(:group_label_method)
|
15
16
|
end
|
16
17
|
|
17
18
|
def choices
|
18
|
-
@choices ||=
|
19
|
+
@choices ||= begin
|
20
|
+
collection = attributes.delete(:choices) || field.choices
|
21
|
+
build_choice_mapper(collection)
|
22
|
+
end
|
19
23
|
end
|
20
24
|
|
21
25
|
def selected?(option)
|
22
26
|
if attributes[:multiple]
|
23
|
-
|
24
|
-
|
27
|
+
field_value.any? { |item| item.to_s == option.to_s }
|
28
|
+
else
|
29
|
+
field_value.to_s == option.to_s
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def field_value
|
34
|
+
if attributes[:multiple]
|
35
|
+
Array(field.value)
|
25
36
|
else
|
26
|
-
field.value
|
37
|
+
field.value
|
27
38
|
end
|
28
39
|
end
|
29
40
|
|
30
41
|
def normalize_simple_input(input_value)
|
42
|
+
# ensure that choice is in the list
|
31
43
|
([super] & choices.values)[0]
|
32
44
|
end
|
45
|
+
|
46
|
+
def build_choice_mapper(collection)
|
47
|
+
if @group_method
|
48
|
+
GroupedChoicesMapper.new(
|
49
|
+
collection,
|
50
|
+
group_method: @group_method,
|
51
|
+
group_label_method: @group_label_method,
|
52
|
+
label_method: @label_method,
|
53
|
+
value_method: @value_method
|
54
|
+
)
|
55
|
+
else
|
56
|
+
SimpleChoicesMapper.new(
|
57
|
+
collection,
|
58
|
+
label_method: @label_method,
|
59
|
+
value_method: @value_method
|
60
|
+
)
|
61
|
+
end
|
62
|
+
end
|
33
63
|
end
|
34
64
|
end
|
35
65
|
end
|
@@ -19,8 +19,18 @@ module Phlexi
|
|
19
19
|
protected
|
20
20
|
|
21
21
|
def options
|
22
|
-
choices.
|
23
|
-
|
22
|
+
if choices.is_a?(GroupedChoicesMapper)
|
23
|
+
choices.each do |group_label, group_choices|
|
24
|
+
optgroup(label: group_label) do
|
25
|
+
group_choices.each do |value, label|
|
26
|
+
option(selected: selected?(value), value: value) { label }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
else
|
31
|
+
choices.each do |value, label|
|
32
|
+
option(selected: selected?(value), value: value) { label }
|
33
|
+
end
|
24
34
|
end
|
25
35
|
end
|
26
36
|
|
@@ -0,0 +1,62 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Phlexi
|
4
|
+
module Form
|
5
|
+
class GroupedChoicesMapper
|
6
|
+
include Enumerable
|
7
|
+
|
8
|
+
def initialize(collection, group_method:, group_label_method: :to_s, label_method: nil, value_method: nil)
|
9
|
+
@collection = collection
|
10
|
+
@group_method = group_method
|
11
|
+
@group_label_method = group_label_method
|
12
|
+
@label_method = label_method
|
13
|
+
@value_method = value_method
|
14
|
+
end
|
15
|
+
|
16
|
+
def each(&)
|
17
|
+
grouped_choices.each(&)
|
18
|
+
end
|
19
|
+
|
20
|
+
def grouped_choices
|
21
|
+
@grouped_choices ||= materialize_grouped_choices(@collection)
|
22
|
+
end
|
23
|
+
|
24
|
+
def materialize_grouped_choices(collection)
|
25
|
+
case collection
|
26
|
+
in Hash => hash
|
27
|
+
hash.transform_values { |items| to_choices_mapper(items) }
|
28
|
+
in Array => arr
|
29
|
+
array_to_grouped_hash(arr)
|
30
|
+
in Proc => proc
|
31
|
+
materialize_grouped_choices(proc.call)
|
32
|
+
else
|
33
|
+
record_collection_to_hash
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
private
|
38
|
+
|
39
|
+
def array_to_grouped_hash(array)
|
40
|
+
sample = array.first
|
41
|
+
if group_method == :last && sample.is_a?(Array) && sample.size == 2
|
42
|
+
array.each_with_object({}) do |(label, items), hash|
|
43
|
+
hash[label.to_s] = to_choices_mapper(items)
|
44
|
+
end
|
45
|
+
else
|
46
|
+
record_collection_to_hash
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
def record_collection_to_hash
|
51
|
+
@collection.group_by do |item|
|
52
|
+
group = item.public_send(@group_method)
|
53
|
+
group.public_send(@group_label_method).to_s
|
54
|
+
end.transform_values { |items| to_choices_mapper(items) }
|
55
|
+
end
|
56
|
+
|
57
|
+
def to_choices_mapper(items)
|
58
|
+
SimpleChoicesMapper.new(items, label_method: @label_method, value_method: @value_method)
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
@@ -2,31 +2,31 @@
|
|
2
2
|
|
3
3
|
module Phlexi
|
4
4
|
module Form
|
5
|
-
#
|
5
|
+
# SimpleChoicesMapper is responsible for converting a collection of objects into a hash of options
|
6
6
|
# suitable for form controls, such as `select > options`.
|
7
7
|
# Both values and labels are converted to strings.
|
8
8
|
#
|
9
9
|
# @example Basic usage
|
10
10
|
# collection = [["First", 1], ["Second", 2]]
|
11
|
-
# mapper =
|
11
|
+
# mapper = SimpleChoicesMapper.new(collection)
|
12
12
|
# mapper.each { |value, label| puts "#{value}: #{label}" }
|
13
13
|
#
|
14
14
|
# @example Using with ActiveRecord objects
|
15
15
|
# users = User.all
|
16
|
-
# mapper =
|
16
|
+
# mapper = SimpleChoicesMapper.new(users)
|
17
17
|
# mapper.each { |id, name| puts "#{id}: #{name}" }
|
18
18
|
#
|
19
19
|
# @example Array access with different value types
|
20
|
-
# mapper =
|
20
|
+
# mapper = SimpleChoicesMapper.new([["Integer", 1], ["String", "2"], ["Symbol", :three]])
|
21
21
|
# puts mapper["1"] # Output: "Integer"
|
22
22
|
# puts mapper["2"] # Output: "String"
|
23
23
|
# puts mapper["three"] # Output: "Symbol"
|
24
24
|
#
|
25
25
|
# @note This class is thread-safe as it doesn't maintain mutable state.
|
26
|
-
class
|
26
|
+
class SimpleChoicesMapper
|
27
27
|
include Enumerable
|
28
28
|
|
29
|
-
# Initializes a new
|
29
|
+
# Initializes a new SimpleChoicesMapper instance.
|
30
30
|
#
|
31
31
|
# @param collection [#call, #to_a] The collection to be mapped.
|
32
32
|
# @param label_method [Symbol, nil] The method to call on each object to get the label.
|
@@ -93,9 +93,9 @@ module Phlexi
|
|
93
93
|
else
|
94
94
|
array_to_hash(Array(collection))
|
95
95
|
end
|
96
|
-
|
97
|
-
# Rails.logger.warn("Unhandled inclusion collection type: #{e}")TODO
|
98
|
-
{}
|
96
|
+
# rescue ArgumentError
|
97
|
+
# # Rails.logger.warn("Unhandled inclusion collection type: #{e}")TODO
|
98
|
+
# {}
|
99
99
|
end
|
100
100
|
|
101
101
|
# Converts an array to a hash using detected or specified methods.
|
data/lib/phlexi/form/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: phlexi-form
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.8.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Stefan Froelich
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2025-01-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: phlex
|
@@ -205,7 +205,6 @@ files:
|
|
205
205
|
- lib/phlexi/form.rb
|
206
206
|
- lib/phlexi/form/base.rb
|
207
207
|
- lib/phlexi/form/builder.rb
|
208
|
-
- lib/phlexi/form/choices_mapper.rb
|
209
208
|
- lib/phlexi/form/components/base.rb
|
210
209
|
- lib/phlexi/form/components/belongs_to.rb
|
211
210
|
- lib/phlexi/form/components/checkbox.rb
|
@@ -231,6 +230,7 @@ files:
|
|
231
230
|
- lib/phlexi/form/components/submit_button.rb
|
232
231
|
- lib/phlexi/form/components/textarea.rb
|
233
232
|
- lib/phlexi/form/components/wrapper.rb
|
233
|
+
- lib/phlexi/form/grouped_choices_mapper.rb
|
234
234
|
- lib/phlexi/form/html.rb
|
235
235
|
- lib/phlexi/form/options/autofocus.rb
|
236
236
|
- lib/phlexi/form/options/choices.rb
|
@@ -247,6 +247,7 @@ files:
|
|
247
247
|
- lib/phlexi/form/options/required.rb
|
248
248
|
- lib/phlexi/form/options/step.rb
|
249
249
|
- lib/phlexi/form/options/validators.rb
|
250
|
+
- lib/phlexi/form/simple_choices_mapper.rb
|
250
251
|
- lib/phlexi/form/structure/field_collection.rb
|
251
252
|
- lib/phlexi/form/structure/manages_fields.rb
|
252
253
|
- lib/phlexi/form/structure/namespace.rb
|