satis 2.1.39 → 2.1.41
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -1
- data/Rakefile +0 -4
- data/app/assets/stylesheets/satis/application.css +2 -0
- data/app/components/satis/call_to_action/component.css +11 -0
- data/app/components/satis/call_to_action/component.html.slim +25 -0
- data/app/components/satis/call_to_action/component.rb +24 -0
- data/app/components/satis/card/component.rb +1 -1
- data/app/components/satis/link_button/component.css +11 -0
- data/app/components/satis/link_button/component.html.slim +11 -0
- data/app/components/satis/link_button/component.rb +17 -0
- data/app/components/satis/tab/component.rb +2 -2
- data/app/javascript/satis/controllers/fields_for_controller.js +79 -7
- data/app/views/shared/_fields_for.html.slim +16 -2
- data/lib/satis/helpers/container.rb +11 -10
- data/lib/satis/version.rb +1 -1
- data/lib/satis.rb +6 -5
- metadata +8 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 3eec0a994c04e1229ba122c0c5b8443e24405834a7fa461a4606edd1d21fcc46
|
4
|
+
data.tar.gz: 38216df0a8fbaa32b085a04386b0cb50703ff191f4e25a20ec92f09505756256
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9de946bcc30083902717763eaa4be4ddad6cd2103486c3fa94680ceff2ff07d4a0a0be3e913c5060d6c16f25e82b856749d46c9f659164010075ed95f28f44f1
|
7
|
+
data.tar.gz: 395f70551a7b09aa4f9eaadcebcba2e2fcdd11eb4a586142cfb4e51c8ac153637fe012c6558f6dc49aecc246a0e053724ea87a166e6c36e0630ffd0f4310fc62
|
data/.gitignore
CHANGED
data/Rakefile
CHANGED
@@ -1,6 +1,7 @@
|
|
1
1
|
@import '../../../components/satis/appearance_switcher/component.css';
|
2
2
|
@import '../../../components/satis/breadcrumbs/component.css';
|
3
3
|
@import '../../../components/satis/card/component.css';
|
4
|
+
@import '../../../components/satis/call_to_action/component.css';
|
4
5
|
@import '../../../components/satis/color_picker/component.css';
|
5
6
|
@import '../../../components/satis/date_time_picker/component.css';
|
6
7
|
@import '../../../components/satis/dialog/component.css';
|
@@ -9,6 +10,7 @@
|
|
9
10
|
@import '../../../components/satis/flash_messages/component.css';
|
10
11
|
@import '../../../components/satis/input/component.css';
|
11
12
|
@import '../../../components/satis/input_array/component.css';
|
13
|
+
@import '../../../components/satis/link_button/component.css';
|
12
14
|
@import '../../../components/satis/map/component.css';
|
13
15
|
@import '../../../components/satis/menu/component.css';
|
14
16
|
@import '../../../components/satis/page/component.css';
|
@@ -0,0 +1,25 @@
|
|
1
|
+
.sts-call-to-action class=style
|
2
|
+
.px-6.py-12.sm:px-6.sm:py-16.lg:px-8
|
3
|
+
.mx-auto.max-w-2xl.text-center
|
4
|
+
h2.text-balance.text-4xl.font-semibold.tracking-tight.text-gray-900.sm:text-5xl.dark:text-white
|
5
|
+
= title
|
6
|
+
p.mx-auto.mt-6.max-w-xl.text-pretty.text-lg/8.text-gray-600
|
7
|
+
= description
|
8
|
+
.mt-10.flex.items-center.justify-center.gap-x-6
|
9
|
+
- actions.each do |action|
|
10
|
+
= action
|
11
|
+
|
12
|
+
/.bg-primary-600.rounded-md
|
13
|
+
.px-6.py-24.sm:px-6.sm:py-32.lg:px-8
|
14
|
+
.mx-auto.max-w-2xl.text-center
|
15
|
+
h2.text-balance.text-4xl.font-semibold.tracking-tight.text-white.sm:text-5xl
|
16
|
+
| Boost your productivity. Start using our app today.
|
17
|
+
p.mx-auto.mt-6.max-w-xl.text-pretty.text-lg/8.text-primary-200
|
18
|
+
| Incididunt sint fugiat pariatur cupidatat consectetur sit cillum anim id veniam aliqua proident excepteur commodo do ea.
|
19
|
+
.mt-10.flex.items-center.justify-center.gap-x-6
|
20
|
+
a.rounded-md.bg-white.px-3.5.py-2.5.text-sm.font-semibold.text-primary-600.shadow-sm.hover:bg-primary-50.focus-visible:outline.focus-visible:outline-2.focus-visible:outline-offset-2.focus-visible:outline-white[href="#"]
|
21
|
+
| Get started
|
22
|
+
a.text-sm.font-semibold.leading-6.text-white[href="#"]
|
23
|
+
| Learn more
|
24
|
+
span[aria-hidden="true"]
|
25
|
+
| →
|
@@ -0,0 +1,24 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Satis
|
4
|
+
module CallToAction
|
5
|
+
class Component < Satis::ApplicationComponent
|
6
|
+
renders_many :actions, LinkButton::Component
|
7
|
+
|
8
|
+
attr_reader :identifier, :title, :description, :style
|
9
|
+
|
10
|
+
def initialize(identifier = nil,
|
11
|
+
icon: nil,
|
12
|
+
title: nil,
|
13
|
+
description: nil,
|
14
|
+
style: :regular)
|
15
|
+
super
|
16
|
+
|
17
|
+
@identifier = identifier
|
18
|
+
@title = title
|
19
|
+
@description = description
|
20
|
+
@style = style
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -27,7 +27,7 @@ module Satis
|
|
27
27
|
super
|
28
28
|
|
29
29
|
if identifier.blank?
|
30
|
-
|
30
|
+
Satis::Deprecation.warn('Calling sts.card with the id parameter will become mandatory')
|
31
31
|
end
|
32
32
|
|
33
33
|
@identifier = identifier
|
@@ -0,0 +1,11 @@
|
|
1
|
+
a.sts-link-button.button {
|
2
|
+
@apply rounded-md px-3.5 py-2.5 text-sm font-semibold text-white shadow-sm focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600;
|
3
|
+
}
|
4
|
+
|
5
|
+
a.sts-link-button.primary {
|
6
|
+
@apply bg-primary-600 hover:bg-primary-500 dark:bg-white dark:text-primary-600;
|
7
|
+
}
|
8
|
+
|
9
|
+
a.sts-link-button.link {
|
10
|
+
@apply mt-1 text-sm font-semibold leading-6 text-gray-600;
|
11
|
+
}
|
@@ -0,0 +1,11 @@
|
|
1
|
+
- if type == :primary
|
2
|
+
a.sts-link-button.button.primary href=url
|
3
|
+
= title
|
4
|
+
- if type == :button
|
5
|
+
a.sts-link-button.button href=url
|
6
|
+
= title
|
7
|
+
- if type == :link
|
8
|
+
a.sts-link-button.link href=url
|
9
|
+
= title
|
10
|
+
- if icon
|
11
|
+
i.ml-2 aria-hidden="true" class=icon
|
@@ -0,0 +1,17 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Satis
|
4
|
+
module LinkButton
|
5
|
+
class Component < Satis::ApplicationComponent
|
6
|
+
attr_reader :title, :url, :icon, :type, :class_names
|
7
|
+
# renders_many :items
|
8
|
+
def initialize(type, title: nil, icon: nil, url: nil)
|
9
|
+
@type = type.to_sym
|
10
|
+
@title = title
|
11
|
+
@icon = icon
|
12
|
+
@url = url
|
13
|
+
@class_names = class_names
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -36,12 +36,12 @@ module Satis
|
|
36
36
|
# FIXME: Obsolete these
|
37
37
|
if tab_menu.present?
|
38
38
|
@menu ||= tab_menu
|
39
|
-
|
39
|
+
Satis::Deprecation.warn('Calling tab with the tab_menu parameter, use menu instead')
|
40
40
|
end
|
41
41
|
|
42
42
|
if selected_tab_index.present?
|
43
43
|
@selected_tab_index = selected_tab_index # use selected
|
44
|
-
|
44
|
+
Satis::Deprecation.warn('Calling tab with the selected_tab_index parameter, use selected instead')
|
45
45
|
end
|
46
46
|
|
47
47
|
@block = block
|
@@ -7,6 +7,7 @@ export default class FieldsForController extends ApplicationController {
|
|
7
7
|
super.connect()
|
8
8
|
|
9
9
|
this.boundMonitorChanges = this.monitorChanges.bind(this)
|
10
|
+
this.boundMouseMove = this.mouseMove.bind(this)
|
10
11
|
this.addNewLine()
|
11
12
|
}
|
12
13
|
|
@@ -20,30 +21,81 @@ export default class FieldsForController extends ApplicationController {
|
|
20
21
|
})
|
21
22
|
|
22
23
|
let tmpNode = event.target.closest(".nested-fields")
|
24
|
+
this.setupNewChild(tmpNode)
|
25
|
+
|
26
|
+
this.addNewLine()
|
27
|
+
|
28
|
+
window.scrollBy(0, this.element.querySelector(".nested-fields").clientHeight)
|
29
|
+
}
|
30
|
+
|
31
|
+
setupNewChild(tmpNode) {
|
23
32
|
tmpNode.classList.remove("template")
|
24
33
|
tmpNode.querySelectorAll(".association").forEach((item) => {
|
25
34
|
if (item.classList.contains("hidden")) {
|
26
|
-
item.
|
35
|
+
if (!item.querySelector("a[data-action='click->satis-fields-for#cloneAssociation']")) {
|
36
|
+
item.classList.remove("hidden")
|
37
|
+
}
|
27
38
|
} else {
|
28
|
-
item.
|
39
|
+
if (!item.querySelector("a[data-action='click->satis-fields-for#cloneAssociation']")) {
|
40
|
+
item.remove()
|
41
|
+
} else {
|
42
|
+
item.classList.add("hidden")
|
43
|
+
}
|
29
44
|
}
|
30
45
|
})
|
31
46
|
|
32
47
|
// Simply replace every child node's attributes value, replacing TEMPLATE
|
33
|
-
let
|
48
|
+
let templateId = new Date().valueOf()
|
49
|
+
let templateName = tmpNode.querySelector("span.temp-name").getAttribute("temp_name")
|
50
|
+
tmpNode.querySelector("span.temp-id").setAttribute("temp_id", templateId)
|
34
51
|
tmpNode.querySelectorAll("*").forEach((node) => {
|
35
52
|
for (let attribute of node.attributes) {
|
36
|
-
attribute.value = attribute.value.replace(/TEMPLATE/g,
|
53
|
+
attribute.value = attribute.value.replace(/TEMPLATE-NAME/g, `[${templateName}][${templateId}]`)
|
54
|
+
attribute.value = attribute.value.replace(/TEMPLATE-ID/g, `${templateName}_${templateId}`)
|
55
|
+
|
56
|
+
attribute.value = attribute.value.replace(/TEMPLATE/g, templateId)
|
37
57
|
}
|
38
58
|
})
|
39
59
|
|
40
60
|
tmpNode.querySelectorAll("template").forEach((node) => {
|
41
|
-
node.innerHTML = node.innerHTML.replace(/TEMPLATE/g,
|
61
|
+
node.innerHTML = node.innerHTML.replace(/TEMPLATE-NANE/g, `[${templateName}][${templateId}]`)
|
62
|
+
node.innerHTML = node.innerHTML.replace(/TEMPLATE-ID/g, `${templateName}_${templateId}`)
|
63
|
+
|
64
|
+
node.innerHTML = node.innerHTML.replace(/TEMPLATE/g, templateId)
|
42
65
|
})
|
43
66
|
|
44
|
-
this.
|
67
|
+
tmpNode.addEventListener("mousemove", this.boundMouseMove)
|
68
|
+
}
|
45
69
|
|
46
|
-
|
70
|
+
cloneAssociation(event) {
|
71
|
+
event.preventDefault()
|
72
|
+
|
73
|
+
let item = event.target.closest(".nested-fields")
|
74
|
+
let templateId = item.querySelector("span.temp-id").getAttribute("temp_id")
|
75
|
+
let templateName = item.querySelector("span.temp-name").getAttribute("temp_name")
|
76
|
+
|
77
|
+
let clonedItem = item.cloneNode(true)
|
78
|
+
|
79
|
+
clonedItem.querySelectorAll("*").forEach((node) => {
|
80
|
+
for (let attribute of node.attributes) {
|
81
|
+
attribute.value = attribute.value.replaceAll(`[${templateName}][${templateId}]`, "TEMPLATE-NAME")
|
82
|
+
attribute.value = attribute.value.replaceAll(`${templateName}_${templateId}`, "TEMPLATE-ID")
|
83
|
+
}
|
84
|
+
})
|
85
|
+
|
86
|
+
//this.insertionPointTarget.appendChild(clonedItem)
|
87
|
+
this.insertionPointTarget.insertBefore(
|
88
|
+
clonedItem,
|
89
|
+
this.insertionPointTarget.childNodes[this.insertionPointTarget.childNodes.length - 1]
|
90
|
+
)
|
91
|
+
|
92
|
+
clonedItem
|
93
|
+
.querySelector("a[data-action='click->satis-fields-for#removeAssociation']")
|
94
|
+
?.parentElement.classList.remove("hidden")
|
95
|
+
clonedItem
|
96
|
+
.querySelector("a[data-action='click->satis-fields-for#cloneAssociation']")
|
97
|
+
?.parentElement.classList.add("hidden")
|
98
|
+
this.setupNewChild(clonedItem)
|
47
99
|
}
|
48
100
|
|
49
101
|
addNewLine() {
|
@@ -59,6 +111,26 @@ export default class FieldsForController extends ApplicationController {
|
|
59
111
|
}, 500)
|
60
112
|
}
|
61
113
|
|
114
|
+
mouseMove(event) {
|
115
|
+
let item = event.target.closest(".nested-fields")
|
116
|
+
|
117
|
+
if (event.altKey) {
|
118
|
+
item
|
119
|
+
.querySelector("a[data-action='click->satis-fields-for#removeAssociation']")
|
120
|
+
?.parentElement.classList.add("hidden")
|
121
|
+
item
|
122
|
+
.querySelector("a[data-action='click->satis-fields-for#cloneAssociation']")
|
123
|
+
?.parentElement.classList.remove("hidden")
|
124
|
+
} else {
|
125
|
+
item
|
126
|
+
.querySelector("a[data-action='click->satis-fields-for#removeAssociation']")
|
127
|
+
?.parentElement.classList.remove("hidden")
|
128
|
+
item
|
129
|
+
.querySelector("a[data-action='click->satis-fields-for#cloneAssociation']")
|
130
|
+
?.parentElement.classList.add("hidden")
|
131
|
+
}
|
132
|
+
}
|
133
|
+
|
62
134
|
monitorChanges(event) {
|
63
135
|
if (event?.detail?.src == "satis-dropdown") {
|
64
136
|
// Skip events caused by the initial load of a satis-dropdown
|
@@ -5,9 +5,12 @@
|
|
5
5
|
- if template_object
|
6
6
|
template data-satis-fields-for-target='template'
|
7
7
|
= form.rails_fields_for collection, template_object, child_index: 'TEMPLATE' do |nested_form|
|
8
|
+
- items_name_parts = nested_form.object_name.split(']').map{|x| x.gsub('[', '')}
|
8
9
|
.nested-fields.template.py-2.field-for-bg
|
9
10
|
= nested_form.input :id, as: :hidden
|
10
11
|
= nested_form.input :_destroy, as: :hidden
|
12
|
+
span.hidden.temp-id temp_id=items_name_parts[-1]
|
13
|
+
span.hidden.temp-name temp_name=items_name_parts[-2]
|
11
14
|
.grid.grid-cols-12.gap-4
|
12
15
|
.col-span-11.fields
|
13
16
|
= yield(nested_form)
|
@@ -15,18 +18,29 @@
|
|
15
18
|
.h-full.w-1.border-r.border-dashed.dark:border-gray-700
|
16
19
|
a.text-primary-600.nested-fields_action href="#" data-action='click->satis-fields-for#addAssociation'
|
17
20
|
i.fal.fa-plus
|
21
|
+
.hidden.col-span-1.flex.justify-center.items-center.association
|
22
|
+
.h-full.w-1.border-r.border-dashed
|
23
|
+
a.text-primary-600.nested-fields_action href="#" data-action='click->satis-fields-for#cloneAssociation'
|
24
|
+
i.fa-light.fa-copy
|
18
25
|
.hidden.col-span-1.flex.justify-center.items-center.association
|
19
26
|
.h-full.w-1.border-r.border-dashed.dark:border-gray-700
|
20
27
|
a.text-primary-600.nested-fields_action href="#" data-action='click->satis-fields-for#removeAssociation'
|
21
28
|
i.fal.fa-trash
|
22
29
|
|
23
|
-
= form.
|
24
|
-
|
30
|
+
= form.fields_for collection do |nested_form|
|
31
|
+
- items_name_parts = nested_form.object_name.split(']').map{|x| x.gsub('[', '')}
|
32
|
+
.nested-fields.field-for-bg.py-2 data-action='mousemove->satis-fields-for#mouseMove'
|
25
33
|
= nested_form.input :id, as: :hidden
|
26
34
|
= nested_form.input :_destroy, as: :hidden
|
35
|
+
span.hidden.temp-id temp_id=items_name_parts[-1]
|
36
|
+
span.hidden.temp-name temp_name=items_name_parts[-2]
|
27
37
|
.grid.grid-cols-12.gap-4
|
28
38
|
.col-span-11
|
29
39
|
= yield(nested_form)
|
40
|
+
.hidden.col-span-1.flex.justify-center.items-center.association
|
41
|
+
.h-full.w-1.border-r.border-dashed
|
42
|
+
a.text-primary-600.nested-fields_action href="#" data-action='click->satis-fields-for#cloneAssociation'
|
43
|
+
i.fa-light.fa-copy
|
30
44
|
.col-span-1.flex.justify-center.items-center
|
31
45
|
.h-full.w-1.border-r.border-dashed.dark:border-gray-700
|
32
46
|
a.text-primary-600.nested-fields_action href="#" data-action='click->satis-fields-for#removeAssociation'
|
@@ -12,6 +12,7 @@ module Satis
|
|
12
12
|
add_helper :avatar, Satis::Avatar::Component
|
13
13
|
add_helper :breadcrumbs, Satis::Breadcrumbs::Component
|
14
14
|
add_helper :card, Satis::Card::Component
|
15
|
+
add_helper :call_to_action, Satis::CallToAction::Component
|
15
16
|
add_helper :editor, Satis::Editor::Component
|
16
17
|
add_helper :flash_messages, Satis::FlashMessages::Component
|
17
18
|
add_helper :info, Satis::Info::Component
|
@@ -35,19 +36,19 @@ module Satis
|
|
35
36
|
@browser ||= Browser.new(action_view.request.user_agent)
|
36
37
|
end
|
37
38
|
|
38
|
-
def form_for(name, *args, &
|
39
|
-
options = args.extract_options!.deep_merge!(html: {
|
39
|
+
def form_for(name, *args, &)
|
40
|
+
options = args.extract_options!.deep_merge!(html: {data: {}})
|
40
41
|
form_options_defaults!(options)
|
41
42
|
update_form_data_options!(options[:html][:data], options)
|
42
43
|
args << options.merge(builder: Satis::Forms::Builder)
|
43
|
-
action_view.form_for(name, *args, &
|
44
|
+
action_view.form_for(name, *args, &)
|
44
45
|
end
|
45
46
|
|
46
|
-
def form_with(model: nil, scope: nil, url: nil, format: nil, **options, &
|
47
|
+
def form_with(model: nil, scope: nil, url: nil, format: nil, **options, &)
|
47
48
|
options = options.reverse_merge(builder: Satis::Forms::Builder, class: "").deep_merge!(data: {})
|
48
49
|
form_options_defaults!(options)
|
49
50
|
update_form_data_options!(options[:data], options)
|
50
|
-
action_view.form_with(model: model, scope: scope, url: url, format: format, **options, &
|
51
|
+
action_view.form_with(model: model, scope: scope, url: url, format: format, **options, &)
|
51
52
|
end
|
52
53
|
|
53
54
|
def form_options_defaults!(options)
|
@@ -71,11 +72,11 @@ module Satis
|
|
71
72
|
original_args = args.dup
|
72
73
|
options = args.extract_options!
|
73
74
|
instance = if options.key? :variant
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
75
|
+
variant_component = component.to_s.sub(/::Component$/, "::#{options[:variant].to_s.camelize}::Component").safe_constantize
|
76
|
+
(variant_component || component).new(*original_args, **kwargs)
|
77
|
+
else
|
78
|
+
component.new(*original_args, **kwargs)
|
79
|
+
end
|
79
80
|
instance.original_view_context = action_view
|
80
81
|
action_view.render(instance, &block)
|
81
82
|
end
|
data/lib/satis/version.rb
CHANGED
data/lib/satis.rb
CHANGED
@@ -1,15 +1,16 @@
|
|
1
|
-
require
|
2
|
-
require
|
3
|
-
require
|
4
|
-
require
|
1
|
+
require "satis/version"
|
2
|
+
require "satis/engine"
|
3
|
+
require "satis/configuration"
|
4
|
+
require "satis/active_record_helpers"
|
5
5
|
|
6
6
|
Browser::Base.include(Browser::Aliases)
|
7
7
|
|
8
8
|
module Satis
|
9
9
|
extend Configurable
|
10
10
|
|
11
|
-
|
11
|
+
Deprecation = ActiveSupport::Deprecation.new("2.2", "Satis")
|
12
12
|
|
13
|
+
class << self
|
13
14
|
def confirm_before_leave?
|
14
15
|
return false if config.nil?
|
15
16
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: satis
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.1.
|
4
|
+
version: 2.1.41
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tom de Grunt
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2024-
|
11
|
+
date: 2024-11-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: browser
|
@@ -759,6 +759,9 @@ files:
|
|
759
759
|
- app/components/satis/breadcrumbs/crumb.slim
|
760
760
|
- app/components/satis/calendar_month/component.html.slim
|
761
761
|
- app/components/satis/calendar_month/component.rb
|
762
|
+
- app/components/satis/call_to_action/component.css
|
763
|
+
- app/components/satis/call_to_action/component.html.slim
|
764
|
+
- app/components/satis/call_to_action/component.rb
|
762
765
|
- app/components/satis/card/component.css
|
763
766
|
- app/components/satis/card/component.html.slim
|
764
767
|
- app/components/satis/card/component.rb
|
@@ -804,6 +807,9 @@ files:
|
|
804
807
|
- app/components/satis/input_array/component.html.slim
|
805
808
|
- app/components/satis/input_array/component.rb
|
806
809
|
- app/components/satis/input_array/component_controller.js
|
810
|
+
- app/components/satis/link_button/component.css
|
811
|
+
- app/components/satis/link_button/component.html.slim
|
812
|
+
- app/components/satis/link_button/component.rb
|
807
813
|
- app/components/satis/map/component.css
|
808
814
|
- app/components/satis/map/component.html.slim
|
809
815
|
- app/components/satis/map/component.rb
|