matestack-ui-bootstrap 1.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (82) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +8 -0
  3. data/README.md +26 -0
  4. data/Rakefile +43 -0
  5. data/app/assets/images/avatar-placeholder.png +0 -0
  6. data/app/assets/images/icons/bootstrap-icons.svg +1 -0
  7. data/app/concepts/matestack/ui/bootstrap/apps/admin_template.rb +85 -0
  8. data/app/concepts/matestack/ui/bootstrap/components/accordion.rb +53 -0
  9. data/app/concepts/matestack/ui/bootstrap/components/alert.js +53 -0
  10. data/app/concepts/matestack/ui/bootstrap/components/alert.rb +34 -0
  11. data/app/concepts/matestack/ui/bootstrap/components/avatar.rb +27 -0
  12. data/app/concepts/matestack/ui/bootstrap/components/badge.rb +30 -0
  13. data/app/concepts/matestack/ui/bootstrap/components/breadcrumb.rb +46 -0
  14. data/app/concepts/matestack/ui/bootstrap/components/button.rb +54 -0
  15. data/app/concepts/matestack/ui/bootstrap/components/button_group.rb +36 -0
  16. data/app/concepts/matestack/ui/bootstrap/components/card.rb +100 -0
  17. data/app/concepts/matestack/ui/bootstrap/components/carousel.js +79 -0
  18. data/app/concepts/matestack/ui/bootstrap/components/carousel.rb +85 -0
  19. data/app/concepts/matestack/ui/bootstrap/components/chart.js +232 -0
  20. data/app/concepts/matestack/ui/bootstrap/components/chart.rb +71 -0
  21. data/app/concepts/matestack/ui/bootstrap/components/close.rb +30 -0
  22. data/app/concepts/matestack/ui/bootstrap/components/collapse.js +84 -0
  23. data/app/concepts/matestack/ui/bootstrap/components/collapse.rb +43 -0
  24. data/app/concepts/matestack/ui/bootstrap/components/dropdown.js +14 -0
  25. data/app/concepts/matestack/ui/bootstrap/components/dropdown.rb +116 -0
  26. data/app/concepts/matestack/ui/bootstrap/components/icon.rb +19 -0
  27. data/app/concepts/matestack/ui/bootstrap/components/list_group.rb +83 -0
  28. data/app/concepts/matestack/ui/bootstrap/components/modal.js +90 -0
  29. data/app/concepts/matestack/ui/bootstrap/components/modal.rb +106 -0
  30. data/app/concepts/matestack/ui/bootstrap/components/navbar.rb +120 -0
  31. data/app/concepts/matestack/ui/bootstrap/components/page_heading.rb +28 -0
  32. data/app/concepts/matestack/ui/bootstrap/components/pagination.rb +40 -0
  33. data/app/concepts/matestack/ui/bootstrap/components/popover.js +26 -0
  34. data/app/concepts/matestack/ui/bootstrap/components/popover.rb +92 -0
  35. data/app/concepts/matestack/ui/bootstrap/components/progress.rb +65 -0
  36. data/app/concepts/matestack/ui/bootstrap/components/scrollspy.rb +33 -0
  37. data/app/concepts/matestack/ui/bootstrap/components/section_card.rb +31 -0
  38. data/app/concepts/matestack/ui/bootstrap/components/spinner.rb +31 -0
  39. data/app/concepts/matestack/ui/bootstrap/components/tab_nav.rb +81 -0
  40. data/app/concepts/matestack/ui/bootstrap/components/tab_nav_content.rb +32 -0
  41. data/app/concepts/matestack/ui/bootstrap/components/toast.js +79 -0
  42. data/app/concepts/matestack/ui/bootstrap/components/toast.rb +99 -0
  43. data/app/concepts/matestack/ui/bootstrap/components/tooltip.js +26 -0
  44. data/app/concepts/matestack/ui/bootstrap/components/tooltip.rb +82 -0
  45. data/app/concepts/matestack/ui/bootstrap/content/collection/collection.rb +112 -0
  46. data/app/concepts/matestack/ui/bootstrap/content/collection/collection.scss +10 -0
  47. data/app/concepts/matestack/ui/bootstrap/content/collection/content.rb +101 -0
  48. data/app/concepts/matestack/ui/bootstrap/content/collection/filter.rb +33 -0
  49. data/app/concepts/matestack/ui/bootstrap/content/collection/paginate.rb +92 -0
  50. data/app/concepts/matestack/ui/bootstrap/content/figure.rb +7 -0
  51. data/app/concepts/matestack/ui/bootstrap/form/checkbox.rb +90 -0
  52. data/app/concepts/matestack/ui/bootstrap/form/date.js +38 -0
  53. data/app/concepts/matestack/ui/bootstrap/form/date.rb +98 -0
  54. data/app/concepts/matestack/ui/bootstrap/form/input.rb +123 -0
  55. data/app/concepts/matestack/ui/bootstrap/form/radio.rb +65 -0
  56. data/app/concepts/matestack/ui/bootstrap/form/select.haml +11 -0
  57. data/app/concepts/matestack/ui/bootstrap/form/select.rb +74 -0
  58. data/app/concepts/matestack/ui/bootstrap/form/submit.rb +20 -0
  59. data/app/concepts/matestack/ui/bootstrap/form/switch.rb +90 -0
  60. data/app/concepts/matestack/ui/bootstrap/layout/column.rb +47 -0
  61. data/app/concepts/matestack/ui/bootstrap/layout/container.rb +25 -0
  62. data/app/concepts/matestack/ui/bootstrap/layout/row.rb +15 -0
  63. data/app/concepts/matestack/ui/bootstrap/layout/sidebar.js +64 -0
  64. data/app/concepts/matestack/ui/bootstrap/layout/sidebar.rb +45 -0
  65. data/app/concepts/matestack/ui/bootstrap/layout/sidebar.scss +57 -0
  66. data/app/concepts/matestack/ui/bootstrap/pages/devise/sign_in.rb +40 -0
  67. data/app/concepts/matestack/ui/bootstrap/registry.rb +63 -0
  68. data/app/helpers/matestack/ui/bootstrap/application_helper.rb +13 -0
  69. data/app/javascript/matestack-ui-bootstrap/index.js +26 -0
  70. data/app/javascript/matestack-ui-bootstrap/stylesheets/matestack-ui-bootstrap.scss +65 -0
  71. data/app/javascript/packs/matestack-ui-bootstrap.js +2 -0
  72. data/config/routes.rb +2 -0
  73. data/config/webpack/development.js +5 -0
  74. data/config/webpack/environment.js +29 -0
  75. data/config/webpack/production.js +33 -0
  76. data/config/webpack/test.js +5 -0
  77. data/config/webpacker.yml +96 -0
  78. data/lib/matestack/ui/bootstrap.rb +27 -0
  79. data/lib/matestack/ui/bootstrap/engine.rb +26 -0
  80. data/lib/matestack/ui/bootstrap/version.rb +7 -0
  81. data/lib/tasks/matestack/ui/bootstrap_tasks.rake +66 -0
  82. metadata +137 -0
@@ -0,0 +1,7 @@
1
+ class Matestack::Ui::Bootstrap::Content::Figure < Matestack::Ui::Component
2
+
3
+ def response
4
+ # provide a bootstrap figure
5
+ end
6
+
7
+ end
@@ -0,0 +1,90 @@
1
+ class Matestack::Ui::Bootstrap::Form::Checkbox < Matestack::Ui::Core::Form::Checkbox::Checkbox
2
+
3
+ optional :form_text
4
+ optional :disabled
5
+ optional :variant
6
+
7
+ def response
8
+ if !checkbox_options.empty?
9
+ label for: attr_key, class: "form-label", text: input_label if input_label
10
+ end
11
+ if !checkbox_options.empty?
12
+ multiple_checkboxes
13
+ else
14
+ true_false_checkbox
15
+ end
16
+ render_form_text
17
+ end
18
+
19
+ private
20
+
21
+ def checkbox_wrapper(options = {}, &block)
22
+ div class: "form-check #{'form-check-inline' if variant == :inline}", attributes: options[:attributes] do
23
+ yield
24
+ end
25
+ end
26
+
27
+ def bootstrap_label(text:, for_input:)
28
+ label text: text, for: for_input, class: 'form-check-label'
29
+ end
30
+
31
+ def true_false_checkbox
32
+ checkbox_wrapper do
33
+ form_input type: :hidden, key: key, value: (false_value || 0), errors: false
34
+ input html_attributes.merge(
35
+ type: :checkbox,
36
+ id: "#{id_for_item(value)}",
37
+ name: item_name(key),
38
+ value: checked_value,
39
+ class: 'form-check-input',
40
+ disabled: disabled,
41
+ attributes: vue_attributes.merge(
42
+ ref: "input.#{attr_key}",
43
+ )
44
+ )
45
+ bootstrap_label text: input_label, for_input: id_for_item(value)
46
+ render_errors
47
+ end
48
+ end
49
+
50
+ def multiple_checkboxes
51
+ checkbox_options.to_a.each do |item|
52
+ checkbox_wrapper do
53
+ input html_attributes.merge(
54
+ type: :checkbox,
55
+ id: "#{id_for_item(item_value(item))}",
56
+ name: item_name(item),
57
+ value: item_value(item),
58
+ class: 'form-check-input',
59
+ disabled: disabled,
60
+ attributes: vue_attributes
61
+ )
62
+ bootstrap_label text: item_name(item), for_input: id_for_item(item_value(item))
63
+ render_errors if checkbox_options.to_a.last == item
64
+ end
65
+ end
66
+ end
67
+
68
+ def render_errors
69
+ unless @included_config[:errors] == false && (errors == false || errors.nil?) || errors == false
70
+ div class: 'invalid-feedback', attributes: { 'v-for': "error in #{error_key}" } do
71
+ plain '{{ error }}'
72
+ end
73
+ end
74
+ end
75
+
76
+ def input_error_class
77
+ 'is-invalid'
78
+ end
79
+
80
+ def checkbox_options
81
+ super || {}
82
+ end
83
+
84
+ def render_form_text
85
+ div id: "form_text_for_#{attr_key}", class: "form-text" do
86
+ plain form_text
87
+ end
88
+ end
89
+
90
+ end
@@ -0,0 +1,38 @@
1
+ const bootstrap = require('bootstrap')
2
+ import flatpickr from "flatpickr";
3
+
4
+ MatestackUiCore.Vue.component('matestack-ui-bootstrap-date', {
5
+ mixins: [MatestackUiCore.componentMixin],
6
+
7
+ data() {
8
+ return {};
9
+ },
10
+
11
+ methods: {
12
+
13
+ },
14
+
15
+ mounted: function() {
16
+ const self = this
17
+ let data = this.$parent.data;
18
+ flatpickr(this.$el.querySelector('.flatpickr'), {
19
+ defaultDate: this.componentConfig["init_value"],
20
+ enableTime: (this.componentConfig["enable_time"] == true)
21
+ });
22
+ for (let key in this.$refs) {
23
+ let initValue = this.$refs[key]["attributes"]["init-value"];
24
+
25
+ if (initValue) {
26
+ data[key.replace("input.", "")] = initValue["value"];
27
+ } else {
28
+ data[key.replace("input.", "")] = null;
29
+ }
30
+ }
31
+ this.$parent.data = data
32
+
33
+ //without the timeout it's somehow not working
34
+ setTimeout(function () {
35
+ self.$parent.data = data
36
+ }, 100);
37
+ }
38
+ });
@@ -0,0 +1,98 @@
1
+ class Matestack::Ui::Bootstrap::Form::Date < Matestack::Ui::Core::Component::Dynamic
2
+
3
+ include Matestack::Ui::Core::Form::Utils
4
+ include Matestack::Ui::Core::Form::HasInputHtmlAttributes
5
+ include Matestack::Ui::Core::Form::HasErrors
6
+
7
+ requires :key
8
+ optional :multiple, :init, for: { as: :input_for }, label: { as: :input_label }
9
+
10
+ optional :form_text
11
+ optional :disabled
12
+ optional :placeholder
13
+
14
+ optional :with_time
15
+
16
+ vue_js_component_name "matestack-ui-bootstrap-date"
17
+
18
+ def input_key
19
+ "$parent.data[\"#{key}\"]"
20
+ end
21
+
22
+ def error_key
23
+ "$parent.errors[\"#{key}\"]"
24
+ end
25
+
26
+ def setup
27
+ @component_config[:init_value] = init_value
28
+ @component_config[:with_time] = with_time
29
+ end
30
+
31
+ def response
32
+ div do
33
+ label for: attr_key, class: "form-label", text: input_label if input_label
34
+ input html_attributes.merge(attributes: vue_attributes).merge(bootstrap_input_attributes)
35
+ render_errors
36
+ render_form_text if form_text
37
+ end
38
+ end
39
+
40
+ def vue_attributes
41
+ (options[:attributes] || {}).merge({
42
+ id: attr_key,
43
+ "@change": change_event,
44
+ ref: "input.#{attr_key}",
45
+ 'init-value': init_value,
46
+ 'v-bind:class': "{ '#{input_error_class}': #{error_key} }",
47
+ "aria-describedby": attr_key
48
+ }).merge({ "v-model": input_key })
49
+ end
50
+
51
+ def change_event
52
+ "$parent.inputChanged('#{attr_key}');".strip
53
+ end
54
+
55
+ def custom_options_validation
56
+ raise "included form config is missing, please add ':include' to parent form component" if @included_config.nil?
57
+ end
58
+
59
+ def attr_key
60
+ super
61
+ end
62
+
63
+ private
64
+
65
+ def parse_value(value)
66
+ if [true, false].include? value
67
+ value ? 1 : 0
68
+ else
69
+ return value
70
+ end
71
+ end
72
+
73
+ def bootstrap_input_attributes
74
+ {
75
+ class: (options[:class] || "") << (" form-control flatpickr"),
76
+ disabled: disabled
77
+ }
78
+ end
79
+
80
+ def render_errors
81
+ unless @included_config[:errors] == false && (errors == false || errors.nil?) || errors == false
82
+ div class: 'invalid-feedback', attributes: { 'v-for': "error in #{error_key}" } do
83
+ plain '{{ error }}'
84
+ end
85
+ end
86
+ end
87
+
88
+ def input_error_class
89
+ 'is-invalid'
90
+ end
91
+
92
+ def render_form_text
93
+ div id: "form_text_for_#{attr_key}", class: "form-text" do
94
+ plain form_text
95
+ end
96
+ end
97
+
98
+ end
@@ -0,0 +1,123 @@
1
+ class Matestack::Ui::Bootstrap::Form::Input < Matestack::Ui::Core::Form::Input::Input
2
+
3
+ optional :form_text
4
+ optional :disabled
5
+ optional :browse_button_text
6
+ optional :placeholder
7
+ optional :variant
8
+ optional :min
9
+ optional :max
10
+ optional :step
11
+ optional :show_value
12
+
13
+ def response
14
+ div do
15
+ label for: attr_key, class: "form-label", text: input_label if input_label
16
+ case type
17
+ when :range
18
+ input html_attributes.merge(attributes: vue_attributes).merge(bootstrap_range_attributes)
19
+ if show_value
20
+ div id: attr_key, class: "form-text" do
21
+ plain "{{ data['#{attr_key}'] }}"
22
+ end
23
+ end
24
+ when :file
25
+ file_input
26
+ else
27
+ input html_attributes.merge(attributes: vue_attributes).merge(bootstrap_input_attributes)
28
+ render_errors
29
+ end
30
+ render_form_text if form_text
31
+ end
32
+ end
33
+
34
+ def vue_attributes
35
+ (options[:attributes] || {}).merge({
36
+ id: attr_key,
37
+ "@change": change_event,
38
+ ref: "input.#{attr_key}",
39
+ 'init-value': init_value,
40
+ 'v-bind:class': "{ '#{input_error_class}': #{error_key} }",
41
+ "aria-describedby": attr_key,
42
+ "step": "any"
43
+ }).merge(
44
+ type != :file ? { "#{v_model_type}": input_key } : {}
45
+ ) # file inputs are readonly, no v-model possible
46
+ end
47
+
48
+ def bootstrap_input_attributes
49
+ {
50
+ class: (options[:class] || "") << (" form-control"),
51
+ disabled: disabled
52
+ }
53
+ end
54
+
55
+ def bootstrap_range_attributes
56
+ {
57
+ class: (options[:class] || "") << (" form-range"),
58
+ disabled: disabled,
59
+ min: min,
60
+ max: max,
61
+ steps: step
62
+ }
63
+ end
64
+
65
+ def bootstrap_file_input_attributes
66
+ {
67
+ class: (options[:class] || "") << (" form-file-input"),
68
+ disabled: disabled
69
+ }
70
+ end
71
+
72
+ def form_file_wrapper_class
73
+ case variant
74
+ when :lg
75
+ (options[:class] || "") << (" form-file form-file-lg")
76
+ when :sm
77
+ (options[:class] || "") << (" form-file form-file-sm")
78
+ else
79
+ (options[:class] || "") << (" form-file")
80
+ end
81
+ end
82
+
83
+ def file_input
84
+ div class: form_file_wrapper_class do
85
+ input html_attributes.merge(attributes: vue_attributes).merge(bootstrap_file_input_attributes)
86
+ label class: "form-file-label", for: attr_key do
87
+ span class: "form-file-text", attributes: { "v-if": "data['#{attr_key}']" } do
88
+ if multiple
89
+ span attributes: { "v-for": "file in data['#{attr_key}']" } do
90
+ plain "{{ file['name'] }}"
91
+ end
92
+ else
93
+ plain "{{ data['#{attr_key}']['name'] }}"
94
+ end
95
+ end
96
+ span class: "form-file-text", attributes: { "v-if": "!data['#{attr_key}']" } do
97
+ plain placeholder || "Choose file"
98
+ end
99
+ span class: "form-file-button", text: browse_button_text || "Browse"
100
+ end
101
+ render_errors
102
+ end
103
+ end
104
+
105
+ def render_errors
106
+ unless @included_config[:errors] == false && (errors == false || errors.nil?) || errors == false
107
+ div class: 'invalid-feedback', attributes: { 'v-for': "error in #{error_key}" } do
108
+ plain '{{ error }}'
109
+ end
110
+ end
111
+ end
112
+
113
+ def input_error_class
114
+ 'is-invalid'
115
+ end
116
+
117
+ def render_form_text
118
+ div id: "form_text_for_#{attr_key}", class: "form-text" do
119
+ plain form_text
120
+ end
121
+ end
122
+
123
+ end
@@ -0,0 +1,65 @@
1
+ class Matestack::Ui::Bootstrap::Form::Radio < Matestack::Ui::Core::Form::Radio::Radio
2
+
3
+ optional :form_text
4
+ optional :disabled
5
+ optional :variant
6
+
7
+ def response
8
+ label class: "form-label", text: input_label if input_label
9
+
10
+ radio_options.to_a.each_with_index do |item, index|
11
+ div class: "form-check #{'form-check-inline' if variant == :inline}" do
12
+ input html_attributes.merge(
13
+ attributes: vue_attributes,
14
+ type: :radio,
15
+ id: "#{id_for_item(item_value(item))}",
16
+ name: item_name(item),
17
+ value: item_value(item),
18
+ class: radio_class,
19
+ disabled: disabled
20
+ )
21
+ label class: "form-check-label", text: item_label(item), for: id_for_item(item_value(item))
22
+ if index == radio_options.to_a.size - 1
23
+ render_errors
24
+ end
25
+ end
26
+ end
27
+ render_form_text if form_text
28
+
29
+ end
30
+
31
+ def radio_class
32
+ (options[:class] || "") << (" form-check-input")
33
+ end
34
+
35
+ def vue_attributes
36
+ (options[:attributes] || {}).merge({
37
+ "@change": change_event,
38
+ ref: "select.#{attr_key}",
39
+ 'init-value': init_value,
40
+ 'v-bind:class': "{ '#{input_error_class}': #{error_key} }",
41
+ 'value-type': value_type,
42
+ "#{v_model_type}": input_key,
43
+ })
44
+ end
45
+
46
+ def render_form_text
47
+ div id: "form_text_for_#{attr_key}", class: "form-text" do
48
+ plain form_text
49
+ end
50
+ end
51
+
52
+ def render_errors
53
+ unless @included_config[:errors] == false && (errors == false || errors.nil?) || errors == false
54
+ div class: 'invalid-feedback', attributes: { 'v-for': "error in #{error_key}" } do
55
+ plain '{{ error }}'
56
+ end
57
+ end
58
+ end
59
+
60
+ def input_error_class
61
+ 'is-invalid'
62
+ end
63
+
64
+
65
+ end
@@ -0,0 +1,11 @@
1
+ - if input_label
2
+ %label{ for: attr_key, class: "form-label" }= input_label
3
+
4
+ %select{ html_attributes.merge(vue_attributes) }
5
+ - if placeholder
6
+ %option{value: placeholder_value, disabled: true, selected: init_value.nil?}= placeholder
7
+ - select_options.to_a.each do |item|
8
+ %option{value: item_value(item), disabled: item_disabled(item)}= item_label(item)
9
+ = render_errors
10
+ - if form_text
11
+ = render_form_text
@@ -0,0 +1,74 @@
1
+ class Matestack::Ui::Bootstrap::Form::Select < Matestack::Ui::Core::Form::Select::Select
2
+
3
+ optional :variant
4
+ optional :size
5
+ optional :form_text
6
+
7
+ def vue_attributes
8
+ (options[:attributes] || {}).merge({
9
+ "@change": change_event,
10
+ ref: vue_ref,
11
+ 'init-value': determine_init_value,
12
+ 'v-bind:class': "{ '#{input_error_class}': #{error_key} }",
13
+ 'value-type': value_type,
14
+ 'class': form_select_class,
15
+ 'size': size_class,
16
+ 'id': attr_key,
17
+ "#{v_model_type}": input_key,
18
+ })
19
+ end
20
+
21
+ def form_select_class
22
+ case variant
23
+ when :lg
24
+ (options[:class] || "") << (" form-select form-select-lg")
25
+ when :sm
26
+ (options[:class] || "") << (" form-select form-select-sm")
27
+ else
28
+ (options[:class] || "") << (" form-select")
29
+ end
30
+ end
31
+
32
+ def size_class
33
+ size
34
+ end
35
+
36
+ def determine_init_value
37
+ if init_value
38
+ init_value
39
+ else
40
+ if multiple
41
+ []
42
+ else
43
+ nil
44
+ end
45
+ end
46
+ end
47
+
48
+ def placeholder_value
49
+ if multiple
50
+ '[]'
51
+ else
52
+ 'null'
53
+ end
54
+ end
55
+
56
+ def render_errors
57
+ unless @included_config[:errors] == false && (errors == false || errors.nil?) || errors == false
58
+ div class: 'invalid-feedback', attributes: { 'v-for': "error in #{error_key}" } do
59
+ plain '{{ error }}'
60
+ end
61
+ end
62
+ end
63
+
64
+ def input_error_class
65
+ 'is-invalid'
66
+ end
67
+
68
+ def render_form_text
69
+ div id: "form_text_for_#{attr_key}", class: "form-text" do
70
+ plain form_text
71
+ end
72
+ end
73
+
74
+ end