effective_bootstrap 0.2.3 → 0.2.4
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +12 -0
- data/app/assets/javascripts/effective_bootstrap.js +1 -0
- data/app/assets/javascripts/effective_percent/initialize.js.coffee +39 -0
- data/app/assets/javascripts/effective_percent/input.js +1 -0
- data/app/assets/javascripts/effective_price/initialize.js.coffee +11 -2
- data/app/helpers/effective_bootstrap_helper.rb +8 -4
- data/app/models/effective/form_builder.rb +4 -0
- data/app/models/effective/form_inputs/collection_input.rb +17 -18
- data/app/models/effective/form_inputs/date_field.rb +1 -1
- data/app/models/effective/form_inputs/datetime_field.rb +29 -16
- data/app/models/effective/form_inputs/percent_field.rb +33 -0
- data/app/models/effective/form_inputs/price_field.rb +3 -8
- data/app/models/effective/form_inputs/select.rb +39 -4
- data/lib/effective_bootstrap/version.rb +1 -1
- metadata +5 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: dbcd85ec412ee04f3a0cd56458b24a615c7bc0b7
|
4
|
+
data.tar.gz: a4e5e7b632e4d5c486e68fd3acabf6f1e72bcd61
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e808ddfb63187adf28e906b459e2387b38f69f5d47c9f0b9bece57b588c8d47559693f413b9fcbc2df3fb731bd11c329f9602b5591c852e0744907f04bbe04ba
|
7
|
+
data.tar.gz: 132f566a29c1cb27b8bba080e8fa14c90dc15deb08d5df4c4ebb93f8e8933b814afd6b72f562d9dc8ccbb2af1c33096c5794084ad68130de1d8c00a9483baa97
|
data/README.md
CHANGED
@@ -255,6 +255,18 @@ More info is available here:
|
|
255
255
|
|
256
256
|
http://eonasdan.github.io/bootstrap-datetimepicker/Events/
|
257
257
|
|
258
|
+
## Custom percent_field
|
259
|
+
|
260
|
+
This custom form input uses no 3rd party jQuery plugins.
|
261
|
+
|
262
|
+
It displays a percentage formatted value `100` or `12.500` but posts the "percentage as integer" value of `100000` or `12500` to the server.
|
263
|
+
|
264
|
+
It's like the price field, but 3 digits instead of 2.
|
265
|
+
|
266
|
+
```haml
|
267
|
+
= f.percent_field :percent
|
268
|
+
```
|
269
|
+
|
258
270
|
## Custom price_field
|
259
271
|
|
260
272
|
This custom form input uses no 3rd party jQuery plugins.
|
@@ -8,6 +8,7 @@
|
|
8
8
|
//= require ./effective_checks/input
|
9
9
|
//= require ./effective_editor/input
|
10
10
|
//= require ./effective_file/input
|
11
|
+
//= require ./effective_percent/input
|
11
12
|
//= require ./effective_phone/input
|
12
13
|
//= require ./effective_price/input
|
13
14
|
//= require ./effective_radio/input
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# Prevent non-currency buttons from being pressed
|
2
|
+
$(document).on 'keydown', "input[type='text'].effective_percent", (event) ->
|
3
|
+
allowed = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '-', '.']
|
4
|
+
|
5
|
+
if event.key && event.key.length == 1 && event.metaKey == false && allowed.indexOf(event.key) == -1
|
6
|
+
event.preventDefault()
|
7
|
+
|
8
|
+
# Assign the hidden input a value of 100x value
|
9
|
+
$(document).on 'change keyup', "input[type='text'].effective_percent", (event) ->
|
10
|
+
$input = $(event.target)
|
11
|
+
value = $input.val()
|
12
|
+
|
13
|
+
unless value == ''
|
14
|
+
value = (parseFloat(value || 0.00) * 1000.00).toFixed(0)
|
15
|
+
|
16
|
+
$input.siblings("input[type='hidden']").first().val(value)
|
17
|
+
|
18
|
+
# Format the value for display as percentage
|
19
|
+
$(document).on 'change', "input[type='text'].effective_percent", (event) ->
|
20
|
+
$input = $(event.target)
|
21
|
+
value = $input.siblings("input[type='hidden']").first().val()
|
22
|
+
max = 100000 # 100% is our max value
|
23
|
+
|
24
|
+
unless value == ''
|
25
|
+
value = parseInt(value || 0)
|
26
|
+
|
27
|
+
if value > max # 100% is our max value
|
28
|
+
value = max
|
29
|
+
$input.siblings("input[type='hidden']").first().val(max)
|
30
|
+
|
31
|
+
if value < -max # -100% is our min value
|
32
|
+
value = -max
|
33
|
+
$input.siblings("input[type='hidden']").first().val(-max)
|
34
|
+
|
35
|
+
value = (value / 1000.0) if value != 0
|
36
|
+
value = value.toFixed(3).toString()
|
37
|
+
value = value.replace('.000', '') if value.endsWith('.000')
|
38
|
+
|
39
|
+
$input.val(value)
|
@@ -0,0 +1 @@
|
|
1
|
+
//= require ./initialize
|
@@ -10,7 +10,7 @@ $(document).on 'change keyup', "input[type='text'].effective_price", (event) ->
|
|
10
10
|
$input = $(event.target)
|
11
11
|
value = $input.val().replace(/,/g, '')
|
12
12
|
|
13
|
-
unless
|
13
|
+
unless value == ''
|
14
14
|
value = (parseFloat(value || 0.00) * 100.00).toFixed(0)
|
15
15
|
|
16
16
|
$input.siblings("input[type='hidden']").first().val(value)
|
@@ -19,10 +19,19 @@ $(document).on 'change keyup', "input[type='text'].effective_price", (event) ->
|
|
19
19
|
$(document).on 'change', "input[type='text'].effective_price", (event) ->
|
20
20
|
$input = $(event.target)
|
21
21
|
value = $input.siblings("input[type='hidden']").first().val()
|
22
|
+
max = 2000000000
|
22
23
|
|
23
|
-
unless
|
24
|
+
unless value == ''
|
24
25
|
value = parseInt(value || 0)
|
25
26
|
|
27
|
+
if value > max # 20 million is our max value
|
28
|
+
value = max
|
29
|
+
$input.siblings("input[type='hidden']").first().val(max)
|
30
|
+
|
31
|
+
if value < -max # -20 million is our min value
|
32
|
+
value = -max
|
33
|
+
$input.siblings("input[type='hidden']").first().val(-max)
|
34
|
+
|
26
35
|
if isNaN(value) == false && value != ''
|
27
36
|
value = (value / 100.0) if value != 0
|
28
37
|
|
@@ -13,9 +13,11 @@ module EffectiveBootstrapHelper
|
|
13
13
|
# variations can be :dropup, :dropleft, :dropright
|
14
14
|
# split can be true, false
|
15
15
|
# right is to right align things
|
16
|
-
def dropdown(variation: nil, split: true,
|
16
|
+
def dropdown(variation: nil, split: true, btn_class: nil, right: false, &block)
|
17
17
|
raise 'expected a block' unless block_given?
|
18
18
|
|
19
|
+
btn_class = btn_class.presence || 'btn-outline-primary'
|
20
|
+
|
19
21
|
@_dropdown_link_tos = []; yield
|
20
22
|
|
21
23
|
return @_dropdown_link_tos.first if @_dropdown_link_tos.length <= 1
|
@@ -23,7 +25,7 @@ module EffectiveBootstrapHelper
|
|
23
25
|
retval = if split
|
24
26
|
first = @_dropdown_link_tos.first
|
25
27
|
menu = content_tag(:div, @_dropdown_link_tos[1..-1].join.html_safe, class: ['dropdown-menu', ('dropdown-menu-right' if right)].compact.join(' '))
|
26
|
-
split = content_tag(:button, class: "btn #{
|
28
|
+
split = content_tag(:button, class: "btn #{btn_class} dropdown-toggle dropdown-toggle-split", type: 'button', 'data-toggle': 'dropdown', 'aria-haspopup': true, 'aria-expanded': false) do
|
27
29
|
content_tag(:span, 'Toggle Dropdown', class: 'sr-only')
|
28
30
|
end
|
29
31
|
|
@@ -59,15 +61,17 @@ module EffectiveBootstrapHelper
|
|
59
61
|
concat link_to(label, path, options)
|
60
62
|
end
|
61
63
|
|
62
|
-
#
|
64
|
+
# Works with dots do and dropdown do
|
63
65
|
def dropdown_link_to(label, path, options = {})
|
66
|
+
btn_class = options.delete(:btn_class).presence || 'btn-outline-primary'
|
67
|
+
|
64
68
|
unless @_dropdown_link_tos
|
65
69
|
options[:class] = [options[:class], 'dropdown-item'].compact.join(' ')
|
66
70
|
return link_to(label, path, options)
|
67
71
|
end
|
68
72
|
|
69
73
|
if @_dropdown_link_tos.length == 0
|
70
|
-
options[:class] = [options[:class], 'btn
|
74
|
+
options[:class] = [options[:class], 'btn', btn_class].compact.join(' ')
|
71
75
|
else
|
72
76
|
options[:class] = [options[:class], 'dropdown-item'].compact.join(' ')
|
73
77
|
end
|
@@ -77,6 +77,10 @@ module Effective
|
|
77
77
|
Effective::FormInputs::PasswordField.new(name, options, builder: self).to_html { super(name, options) }
|
78
78
|
end
|
79
79
|
|
80
|
+
def percent_field(name, options = {})
|
81
|
+
Effective::FormInputs::PercentField.new(name, options, builder: self).to_html
|
82
|
+
end
|
83
|
+
|
80
84
|
def phone_field(name, options = {})
|
81
85
|
Effective::FormInputs::PhoneField.new(name, options, builder: self).to_html { super(name, options) }
|
82
86
|
end
|
@@ -36,8 +36,8 @@ module Effective
|
|
36
36
|
include_blank = options[:input].delete(:include_blank)
|
37
37
|
|
38
38
|
@collection_options = {
|
39
|
-
checked: (checked || selected || passed_value || value),
|
40
|
-
selected: (selected || checked || passed_value || value),
|
39
|
+
checked: (checked || selected || passed_value || polymorphic_value || value),
|
40
|
+
selected: (selected || checked || passed_value || polymorphic_value || value),
|
41
41
|
include_blank: include_blank
|
42
42
|
}.compact
|
43
43
|
end
|
@@ -80,38 +80,36 @@ module Effective
|
|
80
80
|
def assign_options_collection!
|
81
81
|
collection = options[:input].delete(:collection)
|
82
82
|
|
83
|
-
grouped = collection.kind_of?(Hash) && collection.values.
|
83
|
+
grouped = collection.kind_of?(Hash) && collection.values.first.respond_to?(:to_a)
|
84
84
|
|
85
85
|
if grouped? && !grouped && collection.present?
|
86
86
|
raise "Grouped collection expecting a Hash {'Posts' => Post.all, 'Events' => Event.all} or a Hash {'Posts' => [['Post A', 1], ['Post B', 2]], 'Events' => [['Event A', 1], ['Event B', 2]]}"
|
87
87
|
end
|
88
88
|
|
89
|
-
if grouped
|
90
|
-
collection
|
89
|
+
if polymorphic? && !grouped && collection.present?
|
90
|
+
raise "Polymorphic collection expecting a Hash {'Posts' => Post.all, 'Events' => Event.all}"
|
91
91
|
end
|
92
92
|
|
93
|
-
|
94
|
-
if
|
95
|
-
collection.
|
96
|
-
|
97
|
-
|
93
|
+
@options_collection = (
|
94
|
+
if polymorphic?
|
95
|
+
collection.inject({}) { |h, (k, group)| h[k] = group.map { |obj| [obj.to_s, "#{obj.class.model_name}_#{obj.id}"] }; h }
|
96
|
+
elsif grouped
|
97
|
+
collection.inject({}) { |h, (k, group)| h[k] = group.map { |obj| obj }; h }
|
98
98
|
else
|
99
|
-
collection.
|
99
|
+
collection.map { |obj| obj }
|
100
100
|
end
|
101
|
-
|
102
|
-
|
103
|
-
@options_collection = collection.to_a
|
101
|
+
)
|
104
102
|
end
|
105
103
|
|
106
104
|
def assign_options_collection_methods!
|
107
105
|
options[:input].reverse_merge!(
|
108
|
-
if
|
106
|
+
if polymorphic?
|
109
107
|
{ group_method: :last, group_label_method: :first, option_key_method: :second, option_value_method: :first }
|
110
108
|
elsif grouped?
|
111
109
|
{ group_method: :last, group_label_method: :first, option_key_method: :second, option_value_method: :first }
|
112
|
-
elsif options_collection
|
110
|
+
elsif options_collection.first.kind_of?(Array)
|
113
111
|
{ label_method: :first, value_method: :second }
|
114
|
-
elsif options_collection
|
112
|
+
elsif options_collection.first.kind_of?(ActiveRecord::Base)
|
115
113
|
{ label_method: :to_s, value_method: :id }
|
116
114
|
else
|
117
115
|
{ label_method: :to_s, value_method: :to_s }
|
@@ -128,7 +126,8 @@ module Effective
|
|
128
126
|
end
|
129
127
|
|
130
128
|
def polymorphic_value
|
131
|
-
|
129
|
+
return nil unless polymorphic?
|
130
|
+
"#{value.class.model_name}_#{value.id}" if value
|
132
131
|
end
|
133
132
|
|
134
133
|
def polymorphic_type_value
|
@@ -10,7 +10,7 @@ module Effective
|
|
10
10
|
end
|
11
11
|
|
12
12
|
def input_js_options
|
13
|
-
{ format: format, showTodayButton: false, showClear: false, useCurrent: 'hour', disabledDates: disabled_dates.presence }.compact
|
13
|
+
{ format: format, showTodayButton: false, showClear: false, useCurrent: 'hour', disabledDates: disabled_dates.presence, minDate: min_date.presence, maxDate: max_date.presence }.compact
|
14
14
|
end
|
15
15
|
|
16
16
|
def input_group_options
|
@@ -10,7 +10,7 @@ module Effective
|
|
10
10
|
end
|
11
11
|
|
12
12
|
def input_js_options
|
13
|
-
{ format: format, sideBySide: true, showTodayButton: false, showClear: false, useCurrent: 'hour', disabledDates: disabled_dates.presence }.compact
|
13
|
+
{ format: format, sideBySide: true, showTodayButton: false, showClear: false, useCurrent: 'hour', disabledDates: disabled_dates.presence, minDate: min_date.presence, maxDate: max_date.presence }.compact
|
14
14
|
end
|
15
15
|
|
16
16
|
def input_group_options
|
@@ -37,22 +37,17 @@ module Effective
|
|
37
37
|
|
38
38
|
def disabled_dates
|
39
39
|
return @disabled_dates unless @disabled_dates.nil?
|
40
|
+
@disabled_dates ||= Array(options.delete(:disabledDates)).map { |obj| parse_object_date(obj) }.flatten.compact
|
41
|
+
end
|
42
|
+
|
43
|
+
def max_date
|
44
|
+
return @max_date unless @max_date.nil?
|
45
|
+
@max_date = parse_object_date(options.delete(:maxDate))
|
46
|
+
end
|
40
47
|
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
obj.strftime('%F')
|
45
|
-
elsif obj.kind_of?(Range) && obj.first.respond_to?(:strftime)
|
46
|
-
[obj.first].tap do |dates|
|
47
|
-
dates << (dates.last + 1.day) until (dates.last + 1.day) > obj.last
|
48
|
-
end
|
49
|
-
elsif obj.kind_of?(String)
|
50
|
-
obj
|
51
|
-
else
|
52
|
-
raise 'unexpected disabledDates data. Expected a DateTime, Range of DateTimes or String'
|
53
|
-
end
|
54
|
-
end.flatten.compact
|
55
|
-
)
|
48
|
+
def min_date
|
49
|
+
return @min_date unless @min_date.nil?
|
50
|
+
@min_date = parse_object_date(options.delete(:minDate))
|
56
51
|
end
|
57
52
|
|
58
53
|
def not_date_linked?
|
@@ -65,6 +60,24 @@ module Effective
|
|
65
60
|
@am_pm = options.key?(:am_pm) ? options.delete(:am_pm) : true
|
66
61
|
end
|
67
62
|
|
63
|
+
private
|
64
|
+
|
65
|
+
def parse_object_date(obj)
|
66
|
+
if obj.respond_to?(:strftime)
|
67
|
+
obj.strftime('%F')
|
68
|
+
elsif obj.kind_of?(Range) && obj.first.respond_to?(:strftime)
|
69
|
+
[obj.first].tap do |dates|
|
70
|
+
dates << (dates.last + 1.day) until (dates.last + 1.day) > obj.last
|
71
|
+
end
|
72
|
+
elsif obj.kind_of?(String)
|
73
|
+
obj
|
74
|
+
elsif obj.nil?
|
75
|
+
obj
|
76
|
+
else
|
77
|
+
raise "unexpected date object #{obj}. Expected a DateTime, Range of DateTimes or String"
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
68
81
|
end
|
69
82
|
end
|
70
83
|
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module Effective
|
2
|
+
module FormInputs
|
3
|
+
class PercentField < Effective::FormInput
|
4
|
+
|
5
|
+
def build_input(&block)
|
6
|
+
@builder.hidden_field(name, value: percent_to_integer, id: tag_id + '_value_as_integer') +
|
7
|
+
@template.text_field_tag(name, percent_to_s, options[:input].merge(id: tag_id, name: nil))
|
8
|
+
end
|
9
|
+
|
10
|
+
def input_group_options
|
11
|
+
{ input_group: { class: 'input-group' }, prepend: content_tag(:span, icon('percent'), class: 'input-group-text') }
|
12
|
+
end
|
13
|
+
|
14
|
+
def input_html_options
|
15
|
+
{ class: 'form-control effective_percent', autocomplete: 'off' }
|
16
|
+
end
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
def percent_to_integer
|
21
|
+
return nil unless value
|
22
|
+
value.kind_of?(Integer) ? value : ('%.3f' % (value / 1000.0))
|
23
|
+
end
|
24
|
+
|
25
|
+
def percent_to_s
|
26
|
+
return nil unless value
|
27
|
+
str = value.kind_of?(Integer) ? ('%.3f' % (value / 1000.0)) : value.to_s
|
28
|
+
str.gsub('.000', '')
|
29
|
+
end
|
30
|
+
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -12,26 +12,21 @@ module Effective
|
|
12
12
|
end
|
13
13
|
|
14
14
|
def input_html_options
|
15
|
-
{ class: 'form-control effective_price',
|
15
|
+
{ class: 'form-control effective_price', autocomplete: 'off' }
|
16
16
|
end
|
17
17
|
|
18
18
|
private
|
19
19
|
|
20
20
|
def price
|
21
|
-
return
|
21
|
+
return nil unless value
|
22
22
|
value.kind_of?(Integer) ? value : ('%.2f' % (value / 100.0))
|
23
23
|
end
|
24
24
|
|
25
25
|
def currency
|
26
|
-
return
|
26
|
+
return nil unless value
|
27
27
|
value.kind_of?(Integer) ? ('%.2f' % (value / 100.0)) : value
|
28
28
|
end
|
29
29
|
|
30
|
-
def include_blank? # default false
|
31
|
-
return @include_blank unless @include_blank.nil?
|
32
|
-
@include_blank = (options.delete(:include_blank) || false)
|
33
|
-
end
|
34
|
-
|
35
30
|
end
|
36
31
|
end
|
37
32
|
end
|
@@ -5,9 +5,10 @@
|
|
5
5
|
module Effective
|
6
6
|
module FormInputs
|
7
7
|
class Select < CollectionInput
|
8
|
+
INCLUDE_NULL = 'Blank (null)'
|
8
9
|
|
9
10
|
def build_input(&block)
|
10
|
-
html = if
|
11
|
+
html = if polymorphic?
|
11
12
|
@builder.grouped_collection_select(polymorphic_id_method, options_collection, group_method, group_label_method, option_key_method, option_value_method, collection_options, html_options)
|
12
13
|
elsif grouped?
|
13
14
|
@builder.grouped_collection_select(name, options_collection, group_method, group_label_method, option_key_method, option_value_method, collection_options, html_options)
|
@@ -32,7 +33,7 @@ module Effective
|
|
32
33
|
theme: 'bootstrap',
|
33
34
|
minimumResultsForSearch: 6,
|
34
35
|
width: 'style',
|
35
|
-
placeholder: (
|
36
|
+
placeholder: (options.delete(:placeholder) || 'Please choose'),
|
36
37
|
allowClear: (true if include_blank?),
|
37
38
|
tokenSeparators: ([',', ';', '\n', '\t'] if tags?),
|
38
39
|
tags: (true if tags?),
|
@@ -47,16 +48,50 @@ module Effective
|
|
47
48
|
'effective_select',
|
48
49
|
'form-control',
|
49
50
|
('polymorphic' if polymorphic?),
|
50
|
-
('grouped' if grouped?),
|
51
|
+
('grouped' if (grouped? || polymorphic?)),
|
51
52
|
('hide-disabled' if hide_disabled?),
|
52
53
|
('tags-input' if tags?),
|
53
54
|
].compact.join(' ')
|
54
55
|
|
55
|
-
{ class: classes, multiple: (true if multiple?), include_blank: (true if include_blank?) }.compact
|
56
|
+
{ class: classes, multiple: (true if multiple?), include_blank: (true if include_blank?), include_null: include_null }.compact
|
57
|
+
end
|
58
|
+
|
59
|
+
def assign_options_collection!
|
60
|
+
super
|
61
|
+
|
62
|
+
return unless include_null
|
63
|
+
|
64
|
+
# Check for singles - transform the array
|
65
|
+
if options_collection.kind_of?(Array) && !options_collection.first.respond_to?(:to_a) # [:admin, :member]
|
66
|
+
@options_collection = options_collection.map { |obj| [obj, obj] }
|
67
|
+
end
|
68
|
+
|
69
|
+
if options_collection.kind_of?(Array) && options_collection.first.respond_to?(:to_a)
|
70
|
+
options_collection.push(['---------------', '-', disabled: 'disabled'])
|
71
|
+
options_collection.push([include_null, 'nil'])
|
72
|
+
end
|
73
|
+
|
74
|
+
if options_collection.kind_of?(Hash)
|
75
|
+
options_collection[include_null] = [[include_null, 'nil']]
|
76
|
+
end
|
77
|
+
|
78
|
+
options_collection
|
56
79
|
end
|
57
80
|
|
58
81
|
private
|
59
82
|
|
83
|
+
def include_null
|
84
|
+
return @include_null unless @include_null.nil?
|
85
|
+
|
86
|
+
obj = options.delete(:include_null)
|
87
|
+
|
88
|
+
@include_null = case obj
|
89
|
+
when nil then false
|
90
|
+
when true then INCLUDE_NULL
|
91
|
+
else obj
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
60
95
|
def include_blank?
|
61
96
|
return @include_blank unless @include_blank.nil?
|
62
97
|
@include_blank = (options.key?(:include_blank) ? options.delete(:include_blank) : true) && !multiple?
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: effective_bootstrap
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Code and Effect
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-10-
|
11
|
+
date: 2018-10-31 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -387,6 +387,8 @@ files:
|
|
387
387
|
- app/assets/javascripts/effective_editor/quill.js
|
388
388
|
- app/assets/javascripts/effective_file/initialize.js.coffee
|
389
389
|
- app/assets/javascripts/effective_file/input.js
|
390
|
+
- app/assets/javascripts/effective_percent/initialize.js.coffee
|
391
|
+
- app/assets/javascripts/effective_percent/input.js
|
390
392
|
- app/assets/javascripts/effective_phone/initialize.js.coffee
|
391
393
|
- app/assets/javascripts/effective_phone/input.js
|
392
394
|
- app/assets/javascripts/effective_phone/jquery.maskedInput.js
|
@@ -440,6 +442,7 @@ files:
|
|
440
442
|
- app/models/effective/form_inputs/form_group.rb
|
441
443
|
- app/models/effective/form_inputs/number_field.rb
|
442
444
|
- app/models/effective/form_inputs/password_field.rb
|
445
|
+
- app/models/effective/form_inputs/percent_field.rb
|
443
446
|
- app/models/effective/form_inputs/phone_field.rb
|
444
447
|
- app/models/effective/form_inputs/price_field.rb
|
445
448
|
- app/models/effective/form_inputs/radios.rb
|