lesli_view 0.1.0 → 1.0.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 +4 -4
- data/lib/lesli_view/charts/bar.rb +41 -0
- data/lib/lesli_view/charts/general.html.erb +97 -0
- data/lib/lesli_view/charts/general.rb +71 -0
- data/lib/lesli_view/charts/line.rb +41 -0
- data/lib/lesli_view/{element → components}/header.html.erb +10 -2
- data/lib/lesli_view/{element → components}/header.rb +4 -3
- data/lib/lesli_view/components/header.scss +69 -0
- data/lib/lesli_view/components/panel.html.erb +37 -0
- data/lib/lesli_view/{element/form.rb → components/panel.rb} +8 -12
- data/lib/lesli_view/components/panel.scss +37 -0
- data/lib/lesli_view/components/tabs.html.erb +35 -0
- data/lib/lesli_view/components/tabs.rb +58 -0
- data/lib/lesli_view/components/tabs_spec.rb +0 -0
- data/lib/lesli_view/components/timeline.html.erb +23 -0
- data/lib/lesli_view/components/timeline.rb +45 -0
- data/lib/lesli_view/components/timeline.scss +218 -0
- data/lib/lesli_view/{element → components}/toolbar.rb +1 -1
- data/lib/lesli_view/components/toolbar.scss +54 -0
- data/lib/lesli_view/elements/avatar.html.erb +7 -0
- data/lib/lesli_view/elements/avatar.rb +76 -0
- data/lib/lesli_view/elements/avatar.scss +50 -0
- data/lib/lesli_view/elements/button.html.erb +24 -0
- data/lib/lesli_view/{element → elements}/button.rb +26 -5
- data/lib/lesli_view/elements/empty.html.erb +8 -0
- data/lib/lesli_view/elements/empty.rb +40 -0
- data/lib/lesli_view/elements/table.html.erb +48 -0
- data/lib/lesli_view/{element → elements}/table.rb +29 -21
- data/lib/lesli_view/elements/table.scss +153 -0
- data/lib/lesli_view/forms/builder.rb +47 -0
- data/lib/lesli_view/forms/builder_horizontal.rb +25 -0
- data/lib/lesli_view/forms/fields.rb +144 -0
- data/lib/lesli_view/forms/fieldset.rb +15 -0
- data/lib/lesli_view/forms/form.scss +87 -0
- data/lib/lesli_view/forms/inputs.rb +46 -0
- data/lib/lesli_view/layout/container.html.erb +5 -3
- data/lib/lesli_view/version.rb +2 -1
- data/lib/lesli_view.rb +27 -5
- data/readme.md +29 -32
- metadata +39 -17
- data/lib/lesli_view/element/button.html.erb +0 -12
- data/lib/lesli_view/element/form.html.erb +0 -10
- data/lib/lesli_view/element/table.full.rb +0 -43
- data/lib/lesli_view/element/table.html.erb +0 -39
- data/lib/lesli_view/element/table.html.full.erb +0 -101
- data/lib/lesli_view/lesli_view.scss +0 -3
- /data/lib/lesli_view/{element → components}/toolbar.html.erb +0 -0
@@ -0,0 +1,218 @@
|
|
1
|
+
|
2
|
+
.lesli-timelines {
|
3
|
+
|
4
|
+
.lesli-timeline {
|
5
|
+
line-height: 1.4em;
|
6
|
+
list-style: none;
|
7
|
+
margin: 0;
|
8
|
+
padding: 0;
|
9
|
+
width: 100%;
|
10
|
+
}
|
11
|
+
.lesli-timeline h1,
|
12
|
+
.lesli-timeline h2,
|
13
|
+
.lesli-timeline h3,
|
14
|
+
.lesli-timeline h4,
|
15
|
+
.lesli-timeline h5,
|
16
|
+
.lesli-timeline h6 {
|
17
|
+
line-height: inherit;
|
18
|
+
}
|
19
|
+
|
20
|
+
/*----- TIMELINE ITEM -----*/
|
21
|
+
.lesli-timeline-item {
|
22
|
+
padding-left: 40px;
|
23
|
+
position: relative;
|
24
|
+
}
|
25
|
+
.lesli-timeline-item:last-child {
|
26
|
+
padding-bottom: 0;
|
27
|
+
}
|
28
|
+
|
29
|
+
/*----- TIMELINE INFO -----*/
|
30
|
+
.lesli-timeline-info {
|
31
|
+
font-size: 12px;
|
32
|
+
font-weight: 700;
|
33
|
+
letter-spacing: 3px;
|
34
|
+
margin: 0 0 0.5em 0;
|
35
|
+
text-transform: uppercase;
|
36
|
+
white-space: nowrap;
|
37
|
+
}
|
38
|
+
|
39
|
+
/*----- TIMELINE MARKER -----*/
|
40
|
+
.lesli-timeline-marker {
|
41
|
+
position: absolute;
|
42
|
+
top: 0;
|
43
|
+
bottom: 0;
|
44
|
+
left: 0;
|
45
|
+
width: 15px;
|
46
|
+
}
|
47
|
+
.lesli-timeline-marker:before {
|
48
|
+
background: #ff6b6b;
|
49
|
+
border: 3px solid transparent;
|
50
|
+
border-radius: 100%;
|
51
|
+
content: "";
|
52
|
+
display: block;
|
53
|
+
height: 15px;
|
54
|
+
position: absolute;
|
55
|
+
top: 4px;
|
56
|
+
left: 0;
|
57
|
+
width: 15px;
|
58
|
+
transition: background 0.3s ease-in-out, border 0.3s ease-in-out;
|
59
|
+
}
|
60
|
+
.lesli-timeline-marker:after {
|
61
|
+
content: "";
|
62
|
+
width: 3px;
|
63
|
+
background: #ccd5db;
|
64
|
+
display: block;
|
65
|
+
position: absolute;
|
66
|
+
top: 24px;
|
67
|
+
bottom: 0;
|
68
|
+
left: 6px;
|
69
|
+
}
|
70
|
+
.lesli-timeline-item:last-child .lesli-timeline-marker:after {
|
71
|
+
content: none;
|
72
|
+
}
|
73
|
+
|
74
|
+
.lesli-timeline-item:not(.period):hover .lesli-timeline-marker:before {
|
75
|
+
background: transparent;
|
76
|
+
border: 3px solid #ff6b6b;
|
77
|
+
}
|
78
|
+
|
79
|
+
/*----- TIMELINE CONTENT -----*/
|
80
|
+
.lesli-timeline-content {
|
81
|
+
padding-bottom: 40px;
|
82
|
+
}
|
83
|
+
.lesli-timeline-content p:last-child {
|
84
|
+
margin-bottom: 0;
|
85
|
+
}
|
86
|
+
|
87
|
+
/*----- TIMELINE PERIOD -----*/
|
88
|
+
.period {
|
89
|
+
padding: 0;
|
90
|
+
}
|
91
|
+
.period .lesli-timeline-info {
|
92
|
+
display: none;
|
93
|
+
}
|
94
|
+
.period .lesli-timeline-marker:before {
|
95
|
+
background: transparent;
|
96
|
+
content: "";
|
97
|
+
width: 15px;
|
98
|
+
height: auto;
|
99
|
+
border: none;
|
100
|
+
border-radius: 0;
|
101
|
+
top: 0;
|
102
|
+
bottom: 30px;
|
103
|
+
position: absolute;
|
104
|
+
border-top: 3px solid #ccd5db;
|
105
|
+
border-bottom: 3px solid #ccd5db;
|
106
|
+
}
|
107
|
+
.period .lesli-timeline-marker:after {
|
108
|
+
content: "";
|
109
|
+
height: 32px;
|
110
|
+
top: auto;
|
111
|
+
}
|
112
|
+
.period .lesli-timeline-content {
|
113
|
+
padding: 40px 0 70px;
|
114
|
+
}
|
115
|
+
.period .timeline-title {
|
116
|
+
margin: 0;
|
117
|
+
}
|
118
|
+
|
119
|
+
/*----------------------------------------------
|
120
|
+
MOD: TIMELINE SPLIT
|
121
|
+
----------------------------------------------*/
|
122
|
+
@media (min-width: 768px) {
|
123
|
+
.lesli-timeline-split .timeline, .timeline-centered .lesli-timeline {
|
124
|
+
display: table;
|
125
|
+
}
|
126
|
+
.lesli-timeline-split .lesli-timeline-item, .timeline-centered .lesli-timeline-item {
|
127
|
+
display: table-row;
|
128
|
+
padding: 0;
|
129
|
+
}
|
130
|
+
.lesli-timeline-split .lesli-timeline-info, .timeline-centered .lesli-timeline-info,
|
131
|
+
.lesli-timeline-split .lesli-timeline-marker,
|
132
|
+
.timeline-centered .lesli-timeline-marker,
|
133
|
+
.lesli-timeline-split .lesli-timeline-content,
|
134
|
+
.timeline-centered .lesli-timeline-content,
|
135
|
+
.lesli-timeline-split .period .lesli-timeline-info {
|
136
|
+
display: table-cell;
|
137
|
+
vertical-align: top;
|
138
|
+
}
|
139
|
+
.lesli-timeline-split .lesli-timeline-marker, .timeline-centered .lesli-timeline-marker {
|
140
|
+
position: relative;
|
141
|
+
}
|
142
|
+
.lesli-timeline-split .lesli-timeline-content, .timeline-centered .lesli-timeline-content {
|
143
|
+
padding-left: 30px;
|
144
|
+
}
|
145
|
+
.lesli-timeline-split .lesli-timeline-info, .timeline-centered .lesli-timeline-info {
|
146
|
+
padding-right: 30px;
|
147
|
+
}
|
148
|
+
.lesli-timeline-split .period .timeline-title, .timeline-centered .period .timeline-title {
|
149
|
+
position: relative;
|
150
|
+
left: -45px;
|
151
|
+
}
|
152
|
+
}
|
153
|
+
|
154
|
+
/*----------------------------------------------
|
155
|
+
MOD: TIMELINE CENTERED
|
156
|
+
----------------------------------------------*/
|
157
|
+
@media (min-width: 992px) {
|
158
|
+
.timeline-centered,
|
159
|
+
.timeline-centered .lesli-timeline-item,
|
160
|
+
.timeline-centered .lesli-timeline-info,
|
161
|
+
.timeline-centered .lesli-timeline-marker,
|
162
|
+
.timeline-centered .lesli-timeline-content {
|
163
|
+
display: block;
|
164
|
+
margin: 0;
|
165
|
+
padding: 0;
|
166
|
+
}
|
167
|
+
.timeline-centered .lesli-timeline-item {
|
168
|
+
padding-bottom: 40px;
|
169
|
+
overflow: hidden;
|
170
|
+
}
|
171
|
+
.timeline-centered .lesli-timeline-marker {
|
172
|
+
position: absolute;
|
173
|
+
left: 50%;
|
174
|
+
margin-left: -7.5px;
|
175
|
+
}
|
176
|
+
.timeline-centered .lesli-timeline-info,
|
177
|
+
.timeline-centered .lesli-timeline-content {
|
178
|
+
width: 50%;
|
179
|
+
}
|
180
|
+
.timeline-centered > .lesli-timeline-item:nth-child(odd) .lesli-timeline-info {
|
181
|
+
float: left;
|
182
|
+
text-align: right;
|
183
|
+
padding-right: 30px;
|
184
|
+
}
|
185
|
+
.timeline-centered > .lesli-timeline-item:nth-child(odd) .lesli-timeline-content {
|
186
|
+
float: right;
|
187
|
+
text-align: left;
|
188
|
+
padding-left: 30px;
|
189
|
+
}
|
190
|
+
.timeline-centered > .lesli-timeline-item:nth-child(even) .lesli-timeline-info {
|
191
|
+
float: right;
|
192
|
+
text-align: left;
|
193
|
+
padding-left: 30px;
|
194
|
+
}
|
195
|
+
.timeline-centered > .lesli-timeline-item:nth-child(even) .lesli-timeline-content {
|
196
|
+
float: left;
|
197
|
+
text-align: right;
|
198
|
+
padding-right: 30px;
|
199
|
+
}
|
200
|
+
.timeline-centered > .lesli-timeline-item.period .lesli-timeline-content {
|
201
|
+
float: none;
|
202
|
+
padding: 0;
|
203
|
+
width: 100%;
|
204
|
+
text-align: center;
|
205
|
+
}
|
206
|
+
.timeline-centered .lesli-timeline-item.period {
|
207
|
+
padding: 50px 0 90px;
|
208
|
+
}
|
209
|
+
.timeline-centered .period .lesli-timeline-marker:after {
|
210
|
+
height: 30px;
|
211
|
+
bottom: 0;
|
212
|
+
top: auto;
|
213
|
+
}
|
214
|
+
.timeline-centered .period .timeline-title {
|
215
|
+
left: auto;
|
216
|
+
}
|
217
|
+
}
|
218
|
+
}
|
@@ -0,0 +1,54 @@
|
|
1
|
+
/*
|
2
|
+
|
3
|
+
Lesli
|
4
|
+
|
5
|
+
Copyright (c) 2023, Lesli Technologies, S. A.
|
6
|
+
|
7
|
+
This program is free software: you can redistribute it and/or modify
|
8
|
+
it under the terms of the GNU General Public License as published by
|
9
|
+
the Free Software Foundation, either version 3 of the License, or
|
10
|
+
(at your option) any later version.
|
11
|
+
|
12
|
+
This program is distributed in the hope that it will be useful,
|
13
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
GNU General Public License for more details.
|
16
|
+
|
17
|
+
You should have received a copy of the GNU General Public License
|
18
|
+
along with this program. If not, see http://www.gnu.org/licenses/.
|
19
|
+
|
20
|
+
Lesli · Ruby on Rails SaaS development platform.
|
21
|
+
|
22
|
+
Made with ♥ by https://www.lesli.tech
|
23
|
+
Building a better future, one line of code at a time.
|
24
|
+
|
25
|
+
@contact hello@lesli.tech
|
26
|
+
@website https://www.lesli.tech
|
27
|
+
@license GPLv3 http://www.gnu.org/licenses/gpl-3.0.en.html
|
28
|
+
|
29
|
+
// · ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~
|
30
|
+
// ·
|
31
|
+
*/
|
32
|
+
|
33
|
+
|
34
|
+
// ·
|
35
|
+
//@import "../../scss/component";
|
36
|
+
|
37
|
+
|
38
|
+
// ·
|
39
|
+
.lesli-toolbar {
|
40
|
+
|
41
|
+
// General styles
|
42
|
+
input,
|
43
|
+
.select select {
|
44
|
+
border-radius: 6px;
|
45
|
+
border: 1px solid lesli-css-color(silver);
|
46
|
+
}
|
47
|
+
|
48
|
+
// search input
|
49
|
+
input::placeholder {
|
50
|
+
color: lesli-css-color(silver, 500);
|
51
|
+
opacity: 1;
|
52
|
+
}
|
53
|
+
|
54
|
+
}
|
@@ -0,0 +1,7 @@
|
|
1
|
+
<figure class="lesli-element-avatar has-background-grey-lighter" style="<%= avatar_style %>">
|
2
|
+
<% if image %>
|
3
|
+
<img src="<%= image %>" alt="Avatar image">
|
4
|
+
<% else %>
|
5
|
+
<span class="has-text-weight-bold <%= font_size %>"><%= letter %></span>
|
6
|
+
<% end %>
|
7
|
+
</figure>
|
@@ -0,0 +1,76 @@
|
|
1
|
+
=begin
|
2
|
+
|
3
|
+
Lesli
|
4
|
+
|
5
|
+
Copyright (c) 2025, Lesli Technologies, S. A.
|
6
|
+
|
7
|
+
This program is free software: you can redistribute it and/or modify
|
8
|
+
it under the terms of the GNU General Public License as published by
|
9
|
+
the Free Software Foundation, either version 3 of the License, or
|
10
|
+
(at your option) any later version.
|
11
|
+
|
12
|
+
This program is distributed in the hope that it will be useful,
|
13
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
GNU General Public License for more details.
|
16
|
+
|
17
|
+
You should have received a copy of the GNU General Public License
|
18
|
+
along with this program. If not, see http://www.gnu.org/licenses/.
|
19
|
+
|
20
|
+
Lesli · Ruby on Rails SaaS Development Framework.
|
21
|
+
|
22
|
+
Made with ♥ by LesliTech
|
23
|
+
Building a better future, one line of code at a time.
|
24
|
+
|
25
|
+
@contact hello@lesli.tech
|
26
|
+
@website https://www.lesli.tech
|
27
|
+
@license GPLv3 http://www.gnu.org/licenses/gpl-3.0.en.html
|
28
|
+
|
29
|
+
// · ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~
|
30
|
+
// ·
|
31
|
+
=end
|
32
|
+
module LesliView
|
33
|
+
module Elements
|
34
|
+
class Avatar < ViewComponent::Base
|
35
|
+
attr_reader :image, :name, :size, :letter, :font_size, :avatar_style
|
36
|
+
|
37
|
+
def initialize(image: nil, name: "", size: "medium")
|
38
|
+
@image = image
|
39
|
+
@name = name
|
40
|
+
@size = size
|
41
|
+
@letter = ""
|
42
|
+
@font_size = ""
|
43
|
+
@avatar_style = ""
|
44
|
+
calculate_size
|
45
|
+
get_letter unless @image
|
46
|
+
end
|
47
|
+
|
48
|
+
private
|
49
|
+
|
50
|
+
# Calculate the size of the avatar and set styles accordingly
|
51
|
+
def calculate_size
|
52
|
+
case size
|
53
|
+
when "small"
|
54
|
+
@font_size = "is-size-5"
|
55
|
+
@avatar_style = "height: 60px; width: 60px;"
|
56
|
+
when "medium"
|
57
|
+
@font_size = "is-size-3"
|
58
|
+
@avatar_style = "height: 120px; width: 120px;"
|
59
|
+
when "large"
|
60
|
+
@font_size = "is-size-1"
|
61
|
+
@avatar_style = "height: 180px; width: 180px;"
|
62
|
+
else
|
63
|
+
raise ArgumentError, "Invalid size: #{size}"
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
# Calculate the initials based on the name
|
68
|
+
def get_letter
|
69
|
+
return @letter = "" if name.strip.empty?
|
70
|
+
|
71
|
+
words = name.strip.split(/\s+/)
|
72
|
+
@letter = words.first(2).map { |word| word[0].upcase }.join
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
/*
|
2
|
+
|
3
|
+
Lesli
|
4
|
+
|
5
|
+
Copyright (c) 2023, Lesli Technologies, S. A.
|
6
|
+
|
7
|
+
This program is free software: you can redistribute it and/or modify
|
8
|
+
it under the terms of the GNU General Public License as published by
|
9
|
+
the Free Software Foundation, either version 3 of the License, or
|
10
|
+
(at your option) any later version.
|
11
|
+
|
12
|
+
This program is distributed in the hope that it will be useful,
|
13
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
GNU General Public License for more details.
|
16
|
+
|
17
|
+
You should have received a copy of the GNU General Public License
|
18
|
+
along with this program. If not, see http://www.gnu.org/licenses/.
|
19
|
+
|
20
|
+
Lesli · Ruby on Rails SaaS development platform.
|
21
|
+
|
22
|
+
Made with ♥ by https://www.lesli.tech
|
23
|
+
Building a better future, one line of code at a time.
|
24
|
+
|
25
|
+
@contact hello@lesli.tech
|
26
|
+
@website https://www.lesli.tech
|
27
|
+
@license GPLv3 http://www.gnu.org/licenses/gpl-3.0.en.html
|
28
|
+
|
29
|
+
// · ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~
|
30
|
+
// ·
|
31
|
+
*/
|
32
|
+
|
33
|
+
.lesli-element-avatar {
|
34
|
+
display: flex;
|
35
|
+
justify-content: center;
|
36
|
+
align-items: center;
|
37
|
+
border-radius: 50%;
|
38
|
+
background-color: lesli-css-color(silver, 100);
|
39
|
+
|
40
|
+
& > img {
|
41
|
+
width: 100%;
|
42
|
+
height: 100%;
|
43
|
+
object-fit: cover;
|
44
|
+
border-radius: 50%;
|
45
|
+
}
|
46
|
+
|
47
|
+
& > span {
|
48
|
+
color: lesli-css-color(silver, 700);
|
49
|
+
}
|
50
|
+
}
|
@@ -0,0 +1,24 @@
|
|
1
|
+
<% tag_name = url.present? ? :a : :button %>
|
2
|
+
|
3
|
+
<% attributes = {
|
4
|
+
class: button_classes,
|
5
|
+
data: {}
|
6
|
+
} %>
|
7
|
+
|
8
|
+
<% attributes[:href] = url if url.present? %>
|
9
|
+
<% attributes[:data][:turbo_frame] = "_top" if url.present? %>
|
10
|
+
|
11
|
+
<%# Add Alpine.js properties %>
|
12
|
+
<% attributes[:"x-data"] = "" if dispatch %>
|
13
|
+
<% attributes[:"@click"] = "$dispatch('#{ dispatch }')" if dispatch %>
|
14
|
+
|
15
|
+
<%= content_tag(tag_name, **attributes) do %>
|
16
|
+
<% if icon %>
|
17
|
+
<span class="icon <%= 'is-small' if small %>">
|
18
|
+
<span class="material-icons"><%= icon %></span>
|
19
|
+
</span>
|
20
|
+
<% end %>
|
21
|
+
<% unless icon_only? %>
|
22
|
+
<span><%= label %></span>
|
23
|
+
<% end %>
|
24
|
+
<% end %>
|
@@ -33,11 +33,30 @@ Building a better future, one line of code at a time.
|
|
33
33
|
=end
|
34
34
|
|
35
35
|
module LesliView
|
36
|
-
module
|
36
|
+
module Elements
|
37
37
|
class Button < ViewComponent::Base
|
38
|
-
attr_reader :icon, :loading, :solid, :info, :success, :warning, :danger, :small
|
38
|
+
attr_reader :label, :url, :icon, :loading, :solid, :info, :success, :warning, :danger, :small, :type, :dispatch
|
39
39
|
|
40
|
-
|
40
|
+
# Adds two numbers together.
|
41
|
+
# @param [Integer] a The first number.
|
42
|
+
# @param [Integer] b The second number.
|
43
|
+
# @return [Integer] The sum of the two numbers.
|
44
|
+
def initialize(
|
45
|
+
label=nil,
|
46
|
+
url:nil,
|
47
|
+
icon: nil,
|
48
|
+
loading: false,
|
49
|
+
solid: false,
|
50
|
+
info: false,
|
51
|
+
success: false,
|
52
|
+
warning: false,
|
53
|
+
danger: false,
|
54
|
+
small: false,
|
55
|
+
type: "button",
|
56
|
+
dispatch:nil
|
57
|
+
)
|
58
|
+
@label = label
|
59
|
+
@url = url
|
41
60
|
@icon = icon
|
42
61
|
@loading = loading
|
43
62
|
@solid = solid
|
@@ -46,6 +65,8 @@ module LesliView
|
|
46
65
|
@warning = warning
|
47
66
|
@danger = danger
|
48
67
|
@small = small
|
68
|
+
@type = type
|
69
|
+
@dispatch = dispatch
|
49
70
|
end
|
50
71
|
|
51
72
|
def button_classes
|
@@ -64,8 +85,8 @@ module LesliView
|
|
64
85
|
"is-primary"
|
65
86
|
end
|
66
87
|
|
67
|
-
def icon_only?
|
68
|
-
icon && !
|
88
|
+
def icon_only?
|
89
|
+
icon && !label
|
69
90
|
end
|
70
91
|
end
|
71
92
|
end
|
@@ -0,0 +1,8 @@
|
|
1
|
+
|
2
|
+
<div class="lesli-empty has-text-centered">
|
3
|
+
<svg width="184" height="184" viewBox="0 0 184 184" fill="none" xmlns="http://www.w3.org/2000/svg">
|
4
|
+
<path d="M145.271 90.6522H142.735V89.528C142.735 83.9793 138.222 79.4655 132.673 79.4655H85.7357C84.255 79.4655 82.1132 78.0942 81.4922 76.7515L76.1878 65.2544C74.1523 60.8499 68.9629 57.5293 64.1128 57.5293H39.7012C34.1524 57.5293 29.6387 62.043 29.6387 67.5918V151.809C29.6387 157.358 34.1524 161.872 39.7012 161.872H53.3459C53.5357 161.883 53.7139 161.932 53.9065 161.932H112.945V153.307H108.831H53.9065C53.7197 153.307 53.6219 153.278 53.5587 153.247C53.527 153.232 53.4897 153.215 53.481 153.206C53.458 153.181 53.412 153.045 53.4609 152.772L63.1985 101.419C63.4027 100.338 64.6849 99.2772 65.7803 99.2772H134.11H142.735H145.271C145.553 99.2772 145.679 99.349 145.697 99.3749C145.714 99.4008 145.766 99.533 145.714 99.809L142.735 115.524L135.979 151.159C135.775 152.24 134.493 153.301 133.395 153.301H121.964V161.926H133.395C138.621 161.926 143.48 157.904 144.455 152.767L154.189 101.413C154.713 98.6648 154.037 95.9163 152.341 93.8693C150.645 91.8281 148.069 90.6522 145.271 90.6522ZM134.11 90.6522H65.7832C60.5593 90.6522 55.7005 94.6743 54.7259 99.8119L44.9883 151.168C44.856 151.864 44.8043 152.56 44.8244 153.247H39.7012C38.922 153.247 38.2637 152.588 38.2637 151.809V67.5918C38.2637 66.8127 38.922 66.1543 39.7012 66.1543H64.1128C65.5934 66.1543 67.7353 67.5257 68.3563 68.8683L73.6607 80.3654C75.6962 84.7699 80.8855 88.0905 85.7357 88.0905H132.673C133.452 88.0905 134.11 88.7489 134.11 89.528V90.6522Z" fill="#BDBDBD"/>
|
5
|
+
<path d="M145.7 50.5227L153.201 43.0219C154.805 41.4176 154.739 38.7525 153.054 37.0677C151.369 35.383 148.704 35.3197 147.1 36.9211L139.599 44.422L132.098 36.9211C130.494 35.3169 127.829 35.383 126.144 37.0677C124.459 38.7525 124.396 41.4176 125.997 43.0219L133.498 50.5227L125.997 58.0236C124.393 59.6279 124.459 62.293 126.144 63.9777C127.829 65.6625 130.494 65.7257 132.098 64.1244L139.599 56.6235L147.1 64.1244C148.704 65.7286 151.369 65.6625 153.054 63.9777C154.739 62.293 154.802 59.6279 153.201 58.0236L145.7 50.5227Z" fill="#BDBDBD"/>
|
6
|
+
</svg>
|
7
|
+
<p class="has-text-grey"><%= @text %></p>
|
8
|
+
</div>
|
@@ -0,0 +1,40 @@
|
|
1
|
+
=begin
|
2
|
+
|
3
|
+
Lesli
|
4
|
+
|
5
|
+
Copyright (c) 2025, Lesli Technologies, S. A.
|
6
|
+
|
7
|
+
This program is free software: you can redistribute it and/or modify
|
8
|
+
it under the terms of the GNU General Public License as published by
|
9
|
+
the Free Software Foundation, either version 3 of the License, or
|
10
|
+
(at your option) any later version.
|
11
|
+
|
12
|
+
This program is distributed in the hope that it will be useful,
|
13
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
14
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
15
|
+
GNU General Public License for more details.
|
16
|
+
|
17
|
+
You should have received a copy of the GNU General Public License
|
18
|
+
along with this program. If not, see http://www.gnu.org/licenses/.
|
19
|
+
|
20
|
+
Lesli · Ruby on Rails SaaS Development Framework.
|
21
|
+
|
22
|
+
Made with ♥ by LesliTech
|
23
|
+
Building a better future, one line of code at a time.
|
24
|
+
|
25
|
+
@contact hello@lesli.tech
|
26
|
+
@website https://www.lesli.tech
|
27
|
+
@license GPLv3 http://www.gnu.org/licenses/gpl-3.0.en.html
|
28
|
+
|
29
|
+
// · ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~ ~·~
|
30
|
+
// ·
|
31
|
+
=end
|
32
|
+
module LesliView
|
33
|
+
module Elements
|
34
|
+
class Empty < ViewComponent::Base
|
35
|
+
def initialize(text: "No data found")
|
36
|
+
@text = text
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
<div class="lesli-table-container table-container">
|
2
|
+
<table id="<%= id %>" class="table is-fullwidth lesli-table mb-5 <%= class_name %>">
|
3
|
+
<% unless headless %>
|
4
|
+
<thead>
|
5
|
+
<tr>
|
6
|
+
<% columns.each do |column| %>
|
7
|
+
<th
|
8
|
+
width="<%= column[:width] %>"
|
9
|
+
class="<%= table_header_class(column) %>"
|
10
|
+
data-action="click->table#sort"
|
11
|
+
data-field="<%= column[:field] %>">
|
12
|
+
<% if column[:sort] %>
|
13
|
+
<span class="icon-text">
|
14
|
+
<span><%= column[:label] %></span>
|
15
|
+
<span class="icon">
|
16
|
+
<span class="material-icons"><%= column[:field] == @current_sort ? (current_sort_dir(column) == "asc" ? "arrow_upward" : "arrow_downward") : "sort" %></span>
|
17
|
+
</span>
|
18
|
+
</span>
|
19
|
+
<% else %>
|
20
|
+
<%= column[:label] %>
|
21
|
+
<% end %>
|
22
|
+
</th>
|
23
|
+
<% end %>
|
24
|
+
</tr>
|
25
|
+
</thead>
|
26
|
+
<% end %>
|
27
|
+
<tbody>
|
28
|
+
<% if records %>
|
29
|
+
<% records.each_with_index do |record, i| %>
|
30
|
+
<tr>
|
31
|
+
<% columns.each do |column| %>
|
32
|
+
<td class="<%= table_body_class(column) %>">
|
33
|
+
<% if link %>
|
34
|
+
<%= link_to(record[column[:field]] || "", link.call(record), class: "link", data: { turbo_frame: '_top' }) %>
|
35
|
+
<% else %>
|
36
|
+
<%= record[column[:field]] %>
|
37
|
+
<% end %>
|
38
|
+
</td>
|
39
|
+
<% end %>
|
40
|
+
</tr>
|
41
|
+
<% end %>
|
42
|
+
<% end %>
|
43
|
+
<% rows.each do |row| %>
|
44
|
+
<%= row %>
|
45
|
+
<% end %>
|
46
|
+
</tbody>
|
47
|
+
</table>
|
48
|
+
</div>
|
@@ -1,6 +1,4 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
=begin
|
1
|
+
=begin
|
4
2
|
|
5
3
|
Lesli
|
6
4
|
|
@@ -33,11 +31,13 @@ Building a better future, one line of code at a time.
|
|
33
31
|
=end
|
34
32
|
|
35
33
|
module LesliView
|
36
|
-
module
|
34
|
+
module Elements
|
37
35
|
class Table < ViewComponent::Base
|
38
36
|
attr_reader :id, :class_name, :pagination, :loading, :headless, :columns, :records, :link
|
39
37
|
|
40
|
-
|
38
|
+
renders_many :rows, "TableRow"
|
39
|
+
|
40
|
+
def initialize(columns: nil, records: nil, id: nil, class_name: "is-striped", pagination: nil, loading: false, headless: false, link: nil)
|
41
41
|
@id = id
|
42
42
|
@class_name = class_name
|
43
43
|
@pagination = pagination
|
@@ -56,22 +56,30 @@ module LesliView
|
|
56
56
|
column[:field] == "id" || column[:align] == "center" ? "has-text-centered" : ""
|
57
57
|
end
|
58
58
|
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
59
|
+
class TableRow < ViewComponent::Base
|
60
|
+
renders_many :cells, "TableData"
|
61
|
+
|
62
|
+
def initialize(css_class: "")
|
63
|
+
@css_class = css_class
|
64
|
+
end
|
65
|
+
|
66
|
+
def call
|
67
|
+
# safe_joins ensure multiple <td> elements render correctly
|
68
|
+
content_tag(:tr, safe_join(cells), class:@css_class)
|
69
|
+
end
|
70
|
+
|
71
|
+
class TableData < ViewComponent::Base
|
72
|
+
attr_reader :css_class
|
73
|
+
|
74
|
+
def initialize(css_class: "")
|
75
|
+
@css_class = css_class
|
76
|
+
end
|
77
|
+
|
78
|
+
def call
|
79
|
+
content_tag :td, content, class: css_class
|
80
|
+
end
|
81
|
+
end
|
74
82
|
end
|
75
|
-
end
|
83
|
+
end
|
76
84
|
end
|
77
85
|
end
|