cm-admin 0.1.0 → 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +12 -0
- data/.rspec +3 -0
- data/.travis.yml +6 -0
- data/Gemfile +7 -1
- data/Gemfile.lock +121 -0
- data/LICENSE.txt +21 -0
- data/README.md +20 -21
- data/app/assets/images/logo.png +0 -0
- data/app/assets/stylesheets/cm_admin/base/auth.scss +73 -0
- data/app/assets/stylesheets/cm_admin/base/common.scss +237 -0
- data/app/assets/stylesheets/cm_admin/base/filters.scss +200 -0
- data/app/assets/stylesheets/cm_admin/base/form.scss +197 -0
- data/app/assets/stylesheets/cm_admin/base/main-nav.scss +47 -0
- data/app/assets/stylesheets/cm_admin/base/navbar.scss +65 -0
- data/app/assets/stylesheets/cm_admin/base/quicksearch.scss +76 -0
- data/app/assets/stylesheets/cm_admin/base/scaffold.scss +96 -0
- data/app/assets/stylesheets/cm_admin/base/show.scss +76 -0
- data/app/assets/stylesheets/cm_admin/base/sidebar.scss +225 -0
- data/app/assets/stylesheets/cm_admin/base/table.scss +320 -0
- data/app/assets/stylesheets/cm_admin/base/tabs.scss +26 -0
- data/{lib/generators/cm_admin/templates/assets/stylesheets/application.css.scss → app/assets/stylesheets/cm_admin/cm_admin.css.scss} +12 -16
- data/app/assets/stylesheets/cm_admin/components/_alerts.scss +101 -0
- data/app/assets/stylesheets/cm_admin/components/_buttons.scss +135 -0
- data/app/assets/stylesheets/cm_admin/components/_dropdown-popup.scss +153 -0
- data/app/assets/stylesheets/cm_admin/components/_input.scss +274 -0
- data/app/assets/stylesheets/cm_admin/components/_modal.scss +34 -0
- data/app/assets/stylesheets/cm_admin/components/_range.scss +31 -0
- data/app/assets/stylesheets/cm_admin/components/_status-tag.scss +68 -0
- data/app/assets/stylesheets/cm_admin/components/index.scss +7 -0
- data/app/assets/stylesheets/cm_admin/dependency/bootstrap.min.css +7 -0
- data/app/assets/stylesheets/cm_admin/helpers/_mixins.scss +20 -0
- data/app/assets/stylesheets/cm_admin/helpers/_variable.scss +87 -0
- data/app/assets/stylesheets/cm_admin/helpers/index.scss +2 -0
- data/app/controllers/cm_admin/application_controller.rb +11 -0
- data/app/controllers/cm_admin/exports_controller.rb +16 -0
- data/app/controllers/cm_admin/static_controller.rb +12 -0
- data/app/helpers/cm_admin/application_helper.rb +11 -0
- data/app/helpers/cm_admin/custom_helper.rb +4 -0
- data/app/javascript/packs/cm_admin/application.js +22 -0
- data/app/javascript/packs/cm_admin/filters.js +347 -0
- data/app/javascript/packs/cm_admin/quick_search.js +67 -0
- data/app/javascript/packs/cm_admin/scaffolds.js +43 -0
- data/app/javascript/stylesheets/cm_admin/application.scss +3 -0
- data/app/views/cm_admin/main/_associated_table.html.slim +60 -0
- data/app/views/cm_admin/main/_cm_pagy_nav.html.slim +23 -0
- data/app/views/cm_admin/main/_filters.html.slim +1 -0
- data/app/views/cm_admin/main/_nested_fields.html.slim +7 -0
- data/app/views/cm_admin/main/_nested_table_form.html.slim +6 -0
- data/app/views/cm_admin/main/_table.html.slim +60 -0
- data/app/views/cm_admin/main/_tabs.html.slim +5 -0
- data/app/views/cm_admin/main/_top_navbar.html.slim +25 -0
- data/app/views/cm_admin/main/associated_index.html.slim +6 -0
- data/app/views/cm_admin/main/associated_show.html.slim +6 -0
- data/app/views/cm_admin/main/dashboard.html.slim +1 -0
- data/app/views/cm_admin/main/edit.html.slim +19 -0
- data/app/views/cm_admin/main/index.html.slim +12 -0
- data/app/views/cm_admin/main/new.html.slim +22 -0
- data/app/views/cm_admin/main/show.html.slim +12 -0
- data/app/views/cm_admin/static/error_401.html.slim +4 -0
- data/app/views/layouts/_left_sidebar_nav.html.slim +34 -0
- data/app/views/layouts/_quick_links.html.slim +25 -0
- data/app/views/layouts/cm_admin.html.slim +41 -0
- data/app/views/layouts/static.html.slim +18 -0
- data/bin/webpack +18 -0
- data/bin/webpack-dev-server +18 -0
- data/cm_admin.gemspec +21 -31
- data/config/.DS_Store +0 -0
- data/config/initializers/active_record_extension.rb +9 -0
- data/config/routes.rb +19 -0
- data/config/webpack/development.js +5 -0
- data/config/webpack/environment.js +13 -0
- data/config/webpack/production.js +5 -0
- data/config/webpack/test.js +5 -0
- data/config/webpacker.yml +92 -0
- data/lib/cm_admin/constants.rb +33 -0
- data/lib/cm_admin/engine.rb +38 -0
- data/lib/cm_admin/model.rb +152 -0
- data/lib/cm_admin/models/action.rb +36 -0
- data/lib/cm_admin/models/actions/blocks.rb +25 -0
- data/lib/cm_admin/models/blocks.rb +19 -0
- data/lib/cm_admin/models/cm_show_section.rb +20 -0
- data/lib/cm_admin/models/column.rb +61 -0
- data/lib/cm_admin/models/controller_method.rb +75 -0
- data/lib/cm_admin/models/dsl_method.rb +122 -0
- data/lib/cm_admin/models/export.rb +54 -0
- data/lib/cm_admin/models/field.rb +15 -0
- data/lib/cm_admin/models/filter.rb +95 -0
- data/lib/cm_admin/models/form_field.rb +21 -0
- data/lib/cm_admin/models/tab.rb +13 -0
- data/lib/cm_admin/utils.rb +67 -0
- data/lib/cm_admin/version.rb +1 -1
- data/lib/cm_admin/view_helpers/column_field_helper.rb +29 -0
- data/lib/cm_admin/view_helpers/field_display_helper.rb +65 -0
- data/lib/cm_admin/view_helpers/filter_helper.rb +190 -0
- data/lib/cm_admin/view_helpers/form_field_helper.rb +33 -0
- data/lib/cm_admin/view_helpers/form_helper.rb +65 -0
- data/lib/cm_admin/view_helpers/manage_column_popup_helper.rb +75 -0
- data/lib/cm_admin/view_helpers/navigation_helper.rb +34 -0
- data/lib/cm_admin/view_helpers/page_info_helper.rb +57 -0
- data/lib/cm_admin/view_helpers.rb +74 -0
- data/lib/cm_admin.rb +33 -2
- data/lib/generators/cm_admin/install_generator.rb +11 -13
- data/lib/tasks/webpack_install.rake +63 -0
- data/package.json +23 -0
- data/postcss.config.js +12 -0
- data/tmp/cache/webpacker/last-compilation-digest-development +1 -0
- data/yarn.lock +6933 -0
- metadata +155 -42
- data/lib/generators/cm_admin/USAGE +0 -8
- data/lib/generators/cm_admin/templates/assets/images/same-logo.png +0 -0
- data/lib/generators/cm_admin/templates/assets/stylesheets/_variable.scss +0 -11
- data/lib/generators/cm_admin/templates/assets/stylesheets/alignment.scss +0 -111
- data/lib/generators/cm_admin/templates/assets/stylesheets/devise.scss +0 -98
- data/lib/generators/cm_admin/templates/assets/stylesheets/form.scss +0 -131
- data/lib/generators/cm_admin/templates/assets/stylesheets/products.scss +0 -21
- data/lib/generators/cm_admin/templates/assets/stylesheets/scaffold.scss +0 -241
- data/lib/generators/cm_admin/templates/assets/stylesheets/table.scss +0 -90
- data/lib/generators/cm_admin/templates/assets/stylesheets/user.scss +0 -25
- data/lib/generators/cm_admin/templates/layouts/_navbar.html.slim +0 -9
- data/lib/generators/cm_admin/templates/layouts/_side_navbar.html.slim +0 -16
- data/lib/generators/cm_admin/templates/layouts/application.html.slim +0 -25
- data/lib/generators/cm_admin/templates/layouts/initializer.rb +0 -2
- data/lib/generators/cm_admin/templates/views/_filters.html.slim +0 -0
- data/lib/generators/cm_admin/templates/views/_form.erb +0 -38
- data/lib/generators/cm_admin/templates/views/_table.erb +0 -14
- data/lib/generators/cm_admin/templates/views/index.erb +0 -11
- data/lib/generators/cm_admin/templates/views/show.erb +0 -8
- data/lib/generators/cm_admin/view_generator.rb +0 -57
@@ -0,0 +1,22 @@
|
|
1
|
+
require("@rails/ujs").start()
|
2
|
+
require("turbolinks").start()
|
3
|
+
require("@rails/activestorage").start()
|
4
|
+
require("stylesheets/cm_admin/application")
|
5
|
+
require("jquery")
|
6
|
+
require("moment")
|
7
|
+
require("bootstrap")
|
8
|
+
require('flatpickr')
|
9
|
+
require('./scaffolds.js')
|
10
|
+
require('./quick_search.js')
|
11
|
+
require('./filters.js')
|
12
|
+
|
13
|
+
import jQuery from 'jquery'
|
14
|
+
window.$ = jQuery
|
15
|
+
window.jQuery = jQuery
|
16
|
+
|
17
|
+
require("@nathanvda/cocoon")
|
18
|
+
import "@fortawesome/fontawesome-free/css/all"
|
19
|
+
import "daterangepicker"
|
20
|
+
|
21
|
+
|
22
|
+
|
@@ -0,0 +1,347 @@
|
|
1
|
+
var currentRequest = null;
|
2
|
+
|
3
|
+
// Main method which will structure the existing filter values with the newly
|
4
|
+
// applied filter. Send and receive the value from the backend.
|
5
|
+
var getFilteredData = function(filterType, filterValue, filterColumn=null) {
|
6
|
+
var url = window.location.pathname
|
7
|
+
|
8
|
+
// Based on the value changed for recent filter generate the filterParams hash
|
9
|
+
var filterParams = {};
|
10
|
+
if (filterColumn) {
|
11
|
+
filterParams[filterType] = {};
|
12
|
+
filterParams[filterType][filterColumn] = filterValue
|
13
|
+
} else {
|
14
|
+
filterParams[filterType] = filterValue
|
15
|
+
}
|
16
|
+
|
17
|
+
// TODO add sort params in the queryString
|
18
|
+
// page params is reinitialized to 1 when any new filter value is applied so
|
19
|
+
// that it won't throw the error when the user doesn't have sufficent data
|
20
|
+
// to display on the table.
|
21
|
+
var queryString = {
|
22
|
+
filters: filterParams,
|
23
|
+
page: 1
|
24
|
+
};
|
25
|
+
|
26
|
+
// Generate the queryString by concatenating the filterParams and
|
27
|
+
// searchParams that are already applied, if searchParams are present.
|
28
|
+
var searchParams = window.location.search
|
29
|
+
if (searchParams.length > 0) {
|
30
|
+
// Delete the previous applied value for multi_select filter from the
|
31
|
+
// searchParams as altering the array with new and old value will create
|
32
|
+
// more complicated logic. The new value is passed and structured in
|
33
|
+
// filterParams and will be concadinated with the searchParams post deletion
|
34
|
+
if (filterType == 'multi_select') {
|
35
|
+
searchParams = getParamsAsObject(searchParams)
|
36
|
+
if (searchParams['filters'][filterType] != undefined) {
|
37
|
+
delete(searchParams['filters'][filterType][filterColumn])
|
38
|
+
}
|
39
|
+
searchParams = jQuery.param(searchParams)
|
40
|
+
}
|
41
|
+
filterParams = jQuery.param(queryString)
|
42
|
+
var availableParams = searchParams + '&' + filterParams
|
43
|
+
queryString = getParamsAsObject(availableParams)
|
44
|
+
}
|
45
|
+
|
46
|
+
return currentRequest = $.ajax(url, {
|
47
|
+
type: 'GET',
|
48
|
+
data: queryString,
|
49
|
+
beforeSend: function() {
|
50
|
+
if (currentRequest !== null) {
|
51
|
+
currentRequest.abort();
|
52
|
+
}
|
53
|
+
},
|
54
|
+
success: function(data) {
|
55
|
+
var queryParam = jQuery.param(queryString)
|
56
|
+
window.history.pushState("", "", url + '?' + queryParam);
|
57
|
+
$('.index-page__table-container').html(data);
|
58
|
+
},
|
59
|
+
error: function(jqxhr, textStatus, errorThrown) {
|
60
|
+
console.log(errorThrown, textStatus);
|
61
|
+
}
|
62
|
+
});
|
63
|
+
}
|
64
|
+
|
65
|
+
$(document).on('change', '[data-behaviour="filter"]', function(e) {
|
66
|
+
var filterType = $(this).data('filter-type')
|
67
|
+
var filterColumn = $(this).data('db-column')
|
68
|
+
|
69
|
+
if (filterType == 'range') {
|
70
|
+
var rangeElements = $(this).parent().children()
|
71
|
+
var filterValue = $(rangeElements[0]).val() + ' to ' + $(rangeElements[1]).val()
|
72
|
+
} else {
|
73
|
+
var filterValue = $(this).val()
|
74
|
+
}
|
75
|
+
|
76
|
+
$(this).parents(':nth(1)').children(':first').children(':nth(1)').text(filterValue)
|
77
|
+
$(this).parents(':nth(1)').children(':first').children(':last').removeClass('hidden')
|
78
|
+
|
79
|
+
unhideClearFilterBtn(filterValue)
|
80
|
+
getFilteredData(filterType, filterValue, filterColumn)
|
81
|
+
});
|
82
|
+
|
83
|
+
$(document).on('keyup', '[data-behaviour="input-search"]', function(e) {
|
84
|
+
e.stopPropagation();
|
85
|
+
|
86
|
+
var searchValue = $(this).val();
|
87
|
+
unhideClearFilterBtn(searchValue)
|
88
|
+
getFilteredData('search', searchValue)
|
89
|
+
});
|
90
|
+
|
91
|
+
$(document).on('click', '[data-behaviour="filter-option"]', function(e) {
|
92
|
+
var filterType = $(this).data('filter-type')
|
93
|
+
var filterColumn = $(this).data('db-column')
|
94
|
+
|
95
|
+
// Clear the search value post selection and regenerate the dropdown elements.
|
96
|
+
var searchInputElement = $(this).parents(':nth(1)').children(':first').children()
|
97
|
+
searchInputElement.val('')
|
98
|
+
CmFilter.dropdown_search(searchInputElement)
|
99
|
+
|
100
|
+
unhideFilter(filterType, filterColumn)
|
101
|
+
});
|
102
|
+
|
103
|
+
var unhideFilter = function(filterType, filterColumn) {
|
104
|
+
var filterInputElement = $('[data-behaviour="filter-input"][data-filter-type=' + filterType + '][data-db-column='+ filterColumn + ']')
|
105
|
+
|
106
|
+
filterInputElement.parent().removeClass('hidden');
|
107
|
+
filterInputElement.click()
|
108
|
+
};
|
109
|
+
|
110
|
+
// Search inside the dropdowns
|
111
|
+
$(document).on('keyup', '[data-behaviour="dropdown-filter-search"]', function(e) {
|
112
|
+
CmFilter.dropdown_search($(this))
|
113
|
+
});
|
114
|
+
|
115
|
+
// Method to decode the encoded nested and/or complex hash and convert it to
|
116
|
+
// object that is used for filters while sending the data to the backend.
|
117
|
+
var getParamsAsObject = function (query) {
|
118
|
+
query = query.substring(query.indexOf('?') + 1);
|
119
|
+
|
120
|
+
var re = /([^&=]+)=?([^&]*)/g;
|
121
|
+
var decodeRE = /\+/g;
|
122
|
+
|
123
|
+
var decode = function (str) {
|
124
|
+
return decodeURIComponent(str.replace(decodeRE, " "));
|
125
|
+
};
|
126
|
+
|
127
|
+
var params = {}, e;
|
128
|
+
while (e = re.exec(query)) {
|
129
|
+
var k = decode(e[1]), v = decode(e[2]);
|
130
|
+
if (k.substring(k.length - 2) === '[]') {
|
131
|
+
k = k.substring(0, k.length - 2);
|
132
|
+
(params[k] || (params[k] = [])).push(v);
|
133
|
+
}
|
134
|
+
else params[k] = v;
|
135
|
+
}
|
136
|
+
|
137
|
+
var assign = function (obj, keyPath, value) {
|
138
|
+
var lastKeyIndex = keyPath.length - 1;
|
139
|
+
for (var i = 0; i < lastKeyIndex; ++i) {
|
140
|
+
var key = keyPath[i];
|
141
|
+
if (!(key in obj))
|
142
|
+
obj[key] = {}
|
143
|
+
obj = obj[key];
|
144
|
+
}
|
145
|
+
obj[keyPath[lastKeyIndex]] = value;
|
146
|
+
}
|
147
|
+
|
148
|
+
for (var prop in params) {
|
149
|
+
var structure = prop.split('[');
|
150
|
+
if (structure.length > 1) {
|
151
|
+
var levels = [];
|
152
|
+
structure.forEach(function (item, i) {
|
153
|
+
var key = item.replace(/[?[\]\\ ]/g, '');
|
154
|
+
levels.push(key);
|
155
|
+
});
|
156
|
+
assign(params, levels, params[prop]);
|
157
|
+
delete(params[prop]);
|
158
|
+
}
|
159
|
+
}
|
160
|
+
return params;
|
161
|
+
};
|
162
|
+
|
163
|
+
$(document).on('click', '[data-behaviour="filter-input"]', function(e) {
|
164
|
+
var filterType = $(this).data('filter-type')
|
165
|
+
var filterColumn = $(this).data('db-column')
|
166
|
+
|
167
|
+
var filterElement = $('[data-behaviour="filter"][data-filter-type=' + filterType + '][data-db-column=' + filterColumn +']')
|
168
|
+
|
169
|
+
if (filterType == 'range') {
|
170
|
+
filterElement.parent().toggleClass('hidden')
|
171
|
+
} else if (filterType == 'multi_select') {
|
172
|
+
$(this).parent().children(':last').toggleClass('hidden')
|
173
|
+
} else if (filterType == 'date') {
|
174
|
+
filterElement.click()
|
175
|
+
}
|
176
|
+
})
|
177
|
+
|
178
|
+
// Remove all the applied filters and reload the page
|
179
|
+
$(document).on('click', '.clear-btn', function(e) {
|
180
|
+
window.location.href = window.location.href.split("?")[0]
|
181
|
+
})
|
182
|
+
|
183
|
+
var unhideClearFilterBtn = function(filterValue) {
|
184
|
+
if (filterValue) {
|
185
|
+
$('.clear-btn').removeClass('hidden')
|
186
|
+
}
|
187
|
+
}
|
188
|
+
|
189
|
+
// Selecting options for single and multi select filters
|
190
|
+
$(document).on('click', '[data-behaviour="select-option"]', function(e) {
|
191
|
+
var filterType = $(this).data('filter-type')
|
192
|
+
var filterColumn = $(this).data('db-column')
|
193
|
+
|
194
|
+
if (filterType == 'single_select') {
|
195
|
+
var filterValue = $(this).data('value')
|
196
|
+
if (!this.classList.contains('selected')) {
|
197
|
+
if (this.parentNode.querySelector('.list-item.selected') != null) {
|
198
|
+
this.parentNode.querySelector('.list-item.selected').classList.remove('selected');
|
199
|
+
}
|
200
|
+
$(this).addClass('selected')
|
201
|
+
}
|
202
|
+
|
203
|
+
$(this).parents(':nth(4)').children(':first').children(':nth(1)').text(filterValue)
|
204
|
+
$(this).parents(':nth(4)').children(':first').children(':last').removeClass('hidden')
|
205
|
+
|
206
|
+
// Clear the search value post selection and regenerate the dropdown elements.
|
207
|
+
var searchInputElement = $(this).parents(':nth(1)').children(':first').children()
|
208
|
+
searchInputElement.val('')
|
209
|
+
CmFilter.dropdown_search(searchInputElement)
|
210
|
+
|
211
|
+
unhideClearFilterBtn(filterValue)
|
212
|
+
getFilteredData(filterType, filterValue, filterColumn)
|
213
|
+
}
|
214
|
+
else if (filterType == 'multi_select') {
|
215
|
+
var parentChip = $(this).parent().siblings(':first')
|
216
|
+
var checkboxElement = $(this).find('.cm-checkbox')
|
217
|
+
checkboxElement.prop('checked', !checkboxElement.prop('checked'))
|
218
|
+
var checkedCount = $(this).parent().find('.cm-checkbox').filter(':checked').length
|
219
|
+
|
220
|
+
if (checkboxElement.prop('checked')) {
|
221
|
+
var chip = $('<div class="chip"></div>')
|
222
|
+
var firstSpan = $('<span></span>').text($(this).data('value'))
|
223
|
+
var secondSpan = $('<span data-behaviour="selected-chip"><i class="fa fa-times"></i></span>')
|
224
|
+
parentChip.prepend(chip.append(firstSpan).append(secondSpan))
|
225
|
+
} else {
|
226
|
+
var chipElement = parentChip.find('.chip')
|
227
|
+
for(var i = 0; i < chipElement.length; i++) {
|
228
|
+
if ($(chipElement[i]).text() == $(this).data('value')) {
|
229
|
+
$(chipElement[i]).remove()
|
230
|
+
break
|
231
|
+
}
|
232
|
+
}
|
233
|
+
}
|
234
|
+
|
235
|
+
if (checkedCount > 0) {
|
236
|
+
parentChip.addClass('search-with-chips').removeClass('search-area')
|
237
|
+
$(this).parents(':nth(1)').children(':last').addClass('active')
|
238
|
+
} else {
|
239
|
+
parentChip.addClass('search-area').removeClass('search-with-chips')
|
240
|
+
$(this).parents(':nth(1)').children(':last').removeClass('active')
|
241
|
+
}
|
242
|
+
}
|
243
|
+
});
|
244
|
+
|
245
|
+
// Apply button for multi select filters
|
246
|
+
$(document).on('click', '.apply-area', function(e) {
|
247
|
+
var filterInputElement = $(this).parents(':nth(3)').children(':first')
|
248
|
+
var filterType = filterInputElement.data('filter-type')
|
249
|
+
var filterColumn = filterInputElement.data('db-column')
|
250
|
+
var filterValue = []
|
251
|
+
|
252
|
+
var selectFilterElement = $('[data-behaviour="select-option"][data-filter-type=' + filterType + '][data-db-column=' + filterColumn + ']')
|
253
|
+
var checkedElements = selectFilterElement.find('.cm-checkbox').filter(':checked')
|
254
|
+
|
255
|
+
if (checkedElements.length > 0) {
|
256
|
+
for(var i = 0; i < checkedElements.length; i++) {
|
257
|
+
filterValue.push($(checkedElements[i]).parent().data('value'))
|
258
|
+
}
|
259
|
+
|
260
|
+
truncatedFilterValue = filterValue[0]
|
261
|
+
if (filterValue.length > 1) {
|
262
|
+
truncatedFilterValue += ' + ' + (filterValue.length - 1) + ' more'
|
263
|
+
}
|
264
|
+
|
265
|
+
filterInputElement.children(':nth(1)').text(truncatedFilterValue)
|
266
|
+
filterInputElement.children(':last').removeClass('hidden')
|
267
|
+
selectFilterElement.parents(':nth(3)').addClass('hidden')
|
268
|
+
|
269
|
+
// Clear the search value post selection and regenerate the dropdown elements.
|
270
|
+
var searchInputElement = $(this).parent().children(':first').children(':last')
|
271
|
+
searchInputElement.val('')
|
272
|
+
CmFilter.dropdown_search(searchInputElement)
|
273
|
+
|
274
|
+
unhideClearFilterBtn(filterValue)
|
275
|
+
getFilteredData(filterType, filterValue, filterColumn)
|
276
|
+
}
|
277
|
+
});
|
278
|
+
|
279
|
+
// Remove single applied filter.
|
280
|
+
$(document).on('click', '.filter-chip-remove', function(e) {
|
281
|
+
var url = window.location.pathname
|
282
|
+
var filterType = $(this).parent().data('filter-type')
|
283
|
+
var filterColumn = $(this).parent().data('db-column')
|
284
|
+
|
285
|
+
var searchParams = window.location.search
|
286
|
+
if (searchParams.length > 0) {
|
287
|
+
queryString = getParamsAsObject(searchParams)
|
288
|
+
if (queryString['filters'][filterType] != undefined) {
|
289
|
+
delete(queryString['filters'][filterType][filterColumn])
|
290
|
+
var queryParam = jQuery.param(queryString)
|
291
|
+
window.history.pushState("", "", url + '?' + queryParam);
|
292
|
+
window.location.reload()
|
293
|
+
}
|
294
|
+
}
|
295
|
+
});
|
296
|
+
|
297
|
+
$(document).on('click', '[data-behaviour="selected-chip"]', function(e) {
|
298
|
+
var filterType = $(this).parents(':nth(5)').find('.filter-chip').data('filter-type')
|
299
|
+
var filterColumn = $(this).parents(':nth(5)').find('.filter-chip').data('db-column')
|
300
|
+
var filterValue = $(this).siblings().text()
|
301
|
+
|
302
|
+
var selectElement = $('[data-behaviour="select-option"][data-filter-type=' + filterType + '][data-db-column=' + filterColumn + ']')
|
303
|
+
$(this).parent().remove()
|
304
|
+
|
305
|
+
for(var i = 0; i < selectElement.length; i++) {
|
306
|
+
if ($(selectElement[i]).data('value') == filterValue) {
|
307
|
+
var checkboxElement = $(selectElement[i]).find('.cm-checkbox')
|
308
|
+
checkboxElement.prop('checked', !checkboxElement.prop('checked'))
|
309
|
+
break
|
310
|
+
}
|
311
|
+
}
|
312
|
+
|
313
|
+
var checkedCount = $(selectElement).find('.cm-checkbox').filter(':checked').length
|
314
|
+
if (checkedCount < 1) {
|
315
|
+
$(selectElement).parent().siblings(':first').addClass('search-area').removeClass('search-with-chips')
|
316
|
+
$(selectElement).parent().siblings(':last').removeClass('active')
|
317
|
+
}
|
318
|
+
})
|
319
|
+
|
320
|
+
CmFilter = {
|
321
|
+
// Generate or remove elements of the dropdown based on the search value.
|
322
|
+
dropdown_search: function(element) {
|
323
|
+
var filter = element.val().toUpperCase();
|
324
|
+
var dropdownElements = element.parents(':nth(1)').find('.list-area').children();
|
325
|
+
for (var i = 0; i < dropdownElements.length; i++) {
|
326
|
+
txtValue = $(dropdownElements[i]).children().text();
|
327
|
+
if (txtValue.toUpperCase().indexOf(filter) > -1) {
|
328
|
+
$(dropdownElements[i]).css('display', 'flex');
|
329
|
+
} else {
|
330
|
+
$(dropdownElements[i]).css('display', 'none');
|
331
|
+
}
|
332
|
+
}
|
333
|
+
},
|
334
|
+
quick_input_search: function(element) {
|
335
|
+
var filter = element.val().toUpperCase();
|
336
|
+
var searchElements = element.parents(':nth(3)').find('.list-area').children();
|
337
|
+
searchElements.removeClass('visible').addClass('hidden')
|
338
|
+
console.log("Filter is ", filter)
|
339
|
+
console.log("Search elements are ", searchElements)
|
340
|
+
for (var i = 0; i < searchElements.length; i++) {
|
341
|
+
txtValue = $(searchElements[i]).children().text();
|
342
|
+
if (txtValue.toUpperCase().indexOf(filter) > -1) {
|
343
|
+
$(searchElements[i]).removeClass('hidden').addClass('visible');
|
344
|
+
}
|
345
|
+
}
|
346
|
+
}
|
347
|
+
}
|
@@ -0,0 +1,67 @@
|
|
1
|
+
$(document).on("keydown", function(e) {
|
2
|
+
if (e.keyCode == 75 && e.metaKey) {
|
3
|
+
$('#quickSearchModal').modal('show')
|
4
|
+
}
|
5
|
+
});
|
6
|
+
|
7
|
+
var liSelected;
|
8
|
+
$(document).on('keydown', function(e){
|
9
|
+
var sel_item = $('.search-results-container > a.visible');
|
10
|
+
if ($('#quickSearchModal').hasClass('show')) {
|
11
|
+
var selected;
|
12
|
+
if(e.which === 40){
|
13
|
+
if(liSelected){
|
14
|
+
liSelected.removeClass('active-item');
|
15
|
+
next = liSelected.next();
|
16
|
+
if(next.length > 0){
|
17
|
+
liSelected = next.addClass('active-item');
|
18
|
+
selected = next.text();
|
19
|
+
|
20
|
+
}else{
|
21
|
+
liSelected = sel_item.eq(0).addClass('active-item');
|
22
|
+
selected = sel_item.eq(0).text();
|
23
|
+
}
|
24
|
+
}else{
|
25
|
+
liSelected = sel_item.eq(0).addClass('active-item');
|
26
|
+
selected = sel_item.eq(0).text();
|
27
|
+
}
|
28
|
+
}else if(e.which === 38){
|
29
|
+
if(liSelected){
|
30
|
+
liSelected.removeClass('active-item');
|
31
|
+
next = liSelected.prev();
|
32
|
+
if(next.length > 0){
|
33
|
+
liSelected = next.addClass('active-item');
|
34
|
+
selected = next.text();
|
35
|
+
|
36
|
+
}else{
|
37
|
+
|
38
|
+
liSelected = sel_item.last().addClass('active-item');
|
39
|
+
selected = sel_item.last().text()
|
40
|
+
}
|
41
|
+
}else{
|
42
|
+
liSelected = sel_item.last().addClass('active-item');
|
43
|
+
selected = sel_item.last().text()
|
44
|
+
}
|
45
|
+
}
|
46
|
+
if(liSelected && e.which === 13) {
|
47
|
+
console.log("Selected item id ", liSelected)
|
48
|
+
href = liSelected.attr('href')
|
49
|
+
window.location = href
|
50
|
+
}
|
51
|
+
}
|
52
|
+
});
|
53
|
+
|
54
|
+
$(document).on('keyup', '[data-behaviour="quick-input-search"]', function(e) {
|
55
|
+
if ($(this).val().length > 0) {
|
56
|
+
$('.clear-search').removeClass('hidden')
|
57
|
+
} else {
|
58
|
+
$('.clear-search').addClass('hidden')
|
59
|
+
}
|
60
|
+
CmFilter.quick_input_search($(this))
|
61
|
+
});
|
62
|
+
|
63
|
+
$(document).on('click', '.clear-search', function(){
|
64
|
+
$('#quick-search-input').val('')
|
65
|
+
$('.clear-search').addClass('hidden')
|
66
|
+
CmFilter.quick_input_search($('#quick-search-input'))
|
67
|
+
});
|
@@ -0,0 +1,43 @@
|
|
1
|
+
$(document).ready(function(e) {
|
2
|
+
$('.select-2').select2();
|
3
|
+
flatpickr("[data-behaviour='date-only']", {})
|
4
|
+
flatpickr("[data-behaviour='date-time']", {
|
5
|
+
enableTime: true
|
6
|
+
})
|
7
|
+
flatpickr("[data-behaviour='filter'][data-filter-type='date']", {
|
8
|
+
mode: 'range'
|
9
|
+
})
|
10
|
+
Sortable.create($('.columns-list')[0],{
|
11
|
+
handle: '.dragger',
|
12
|
+
animation: 150
|
13
|
+
});
|
14
|
+
});
|
15
|
+
|
16
|
+
$(document).on("keypress keyup blur", "[data-behaviour='decimal-only'], [data-behaviour='filter'][data-filter-type='range']", function (e) {
|
17
|
+
var charCode = (e.which) ? e.which : e.keyCode
|
18
|
+
if (charCode > 31 && (charCode != 46 &&(charCode < 48 || charCode > 57)))
|
19
|
+
return false;
|
20
|
+
return true;
|
21
|
+
});
|
22
|
+
|
23
|
+
$(document).on("keypress keyup blur", "[data-behaviour='integer-only']", function (event) {
|
24
|
+
$(this).val($(this).val().replace(/[^\d].+/, ""));
|
25
|
+
if ((event.which < 48 || event.which > 57)) {
|
26
|
+
event.preventDefault();
|
27
|
+
}
|
28
|
+
});
|
29
|
+
|
30
|
+
$(document).on('click', '.row-action-cell', function(e) {
|
31
|
+
e.stopPropagation();
|
32
|
+
if ($(this).hasClass('opacity-1')) {
|
33
|
+
$('.row-action-cell').removeClass('opacity-1')
|
34
|
+
} else {
|
35
|
+
$('.row-action-cell').removeClass('opacity-1')
|
36
|
+
$(this).addClass('opacity-1');
|
37
|
+
}
|
38
|
+
if ($(this).find('.table-export-popup').hasClass('hidden')) {
|
39
|
+
return $(this).find('.table-export-popup').removeClass('hidden');
|
40
|
+
} else {
|
41
|
+
return $(this).find('.table-export-popup').addClass('hidden');
|
42
|
+
}
|
43
|
+
});
|
@@ -0,0 +1,60 @@
|
|
1
|
+
.admin-table-index
|
2
|
+
.table-top
|
3
|
+
p.table-top__total-count = "#{@associated_ar_object.pagy.count} #{@associated_model.ar_model.table_name} found"
|
4
|
+
.table-top__column-action
|
5
|
+
button.secondary-btn.column-btn data-target="#columnActionModal" data-toggle="modal" type="button"
|
6
|
+
span
|
7
|
+
i.fa.fa-columns.bolder
|
8
|
+
span
|
9
|
+
i.fa.fa-angle-down
|
10
|
+
|
11
|
+
.new-admin-table.scrollable
|
12
|
+
table.cm-table
|
13
|
+
thead.cm-table__header
|
14
|
+
tr.header-row
|
15
|
+
th.check-box-space
|
16
|
+
span
|
17
|
+
input.cm-checkbox type="checkbox"
|
18
|
+
- @model.available_fields[@action.name.to_sym].each do |column|
|
19
|
+
th = column.header
|
20
|
+
tbody.cm-table__body
|
21
|
+
- @associated_ar_object.data.each do |ar_object|
|
22
|
+
tr.body-row
|
23
|
+
td.check-box-space
|
24
|
+
span
|
25
|
+
input.cm-checkbox type="checkbox"
|
26
|
+
- @model.available_fields[@action.name.to_sym].each do |column|
|
27
|
+
td
|
28
|
+
span class="#{column.cm_css_class}" = show_field_value(ar_object, column)
|
29
|
+
td.row-action-cell
|
30
|
+
.row-action-tool
|
31
|
+
button.secondary-btn.tool-btn type="button"
|
32
|
+
span
|
33
|
+
i.fa.fa-bars.bolder
|
34
|
+
span
|
35
|
+
i.fa.fa-angle-down
|
36
|
+
.popup-card.table-export-popup.hidden
|
37
|
+
.popup-option
|
38
|
+
a href="#{page_url('edit', ar_object)}"
|
39
|
+
| Edit
|
40
|
+
/ .cm-pagination
|
41
|
+
/ .cm-pagination__lhs Showing 1 to 15 out of 104
|
42
|
+
/ .cm-pagination__rhs
|
43
|
+
/ span.page-move-btn.disabled
|
44
|
+
/ i.fa.fa-angle-double-left.bolder.f14
|
45
|
+
/ span.page-move-btn.disabled
|
46
|
+
/ i.fa.fa-chevron-left.bolder
|
47
|
+
/ span.page-num-btn.active 1
|
48
|
+
/ span.page-num-btn 2
|
49
|
+
/ span.page-num-btn 3
|
50
|
+
/ span.page-num-btn 4
|
51
|
+
/ span.page-num-btn 5
|
52
|
+
/ span.page-move-btn
|
53
|
+
/ i.fa.fa-chevron-right.bolder
|
54
|
+
/ span.page-move-btn
|
55
|
+
/ i.fa.fa-angle-double-right.bolder.f14
|
56
|
+
|
57
|
+
.cm-pagination
|
58
|
+
.cm-pagination__lhs Showing #{@associated_ar_object.pagy.from} to #{@associated_ar_object.pagy.to} out of #{@associated_ar_object.pagy.count}
|
59
|
+
.cm-pagination__rhs
|
60
|
+
== render partial: 'cm_admin/main/cm_pagy_nav', locals: { pagy: @associated_ar_object.pagy }
|
@@ -0,0 +1,23 @@
|
|
1
|
+
- link = pagy_link_proc(pagy)
|
2
|
+
|
3
|
+
nav.pagy_nav.pagination role="navigation" aria-label="pager"
|
4
|
+
|
5
|
+
- if pagy.prev
|
6
|
+
span ==> link.call(pagy.prev, '<', 'aria-label="previous" class="page-move-btn"')
|
7
|
+
- else
|
8
|
+
span ==> link.call('#', '<', 'class="page-move-btn disabled"')
|
9
|
+
|
10
|
+
- pagy.series.each do |item| # series example: [1, :gap, 7, 8, "9", 10, 11, :gap, 36]
|
11
|
+
- if item.is_a?(Integer) # page link
|
12
|
+
span ==> link.call(item, item, 'class="page-num-btn"')
|
13
|
+
|
14
|
+
- elsif item.is_a?(String) # current page
|
15
|
+
span ==> link.call(item, item, 'class="page-num-btn active"')
|
16
|
+
|
17
|
+
- elsif item == :gap # page gap
|
18
|
+
span.page.gap ==> pagy_t('pagy.nav.gap')
|
19
|
+
|
20
|
+
- if pagy.next
|
21
|
+
span == link.call(pagy.next, '>', 'aria-label="next" class="page-move-btn"')
|
22
|
+
- else
|
23
|
+
span ==> link.call('#', '>', 'class="page-move-btn disabled"')
|
@@ -0,0 +1 @@
|
|
1
|
+
= generate_filters(filters)
|
@@ -0,0 +1,7 @@
|
|
1
|
+
.nested-fields
|
2
|
+
- @model.available_fields[action_name.to_sym][assoc_name].each do |field|
|
3
|
+
= f.label field.field_name, class: 'field-label'
|
4
|
+
br
|
5
|
+
= input_field_for_column(f, field)
|
6
|
+
- if @reflections.select {|x| x if x.name == assoc_name}.first.macro == :has_many
|
7
|
+
= link_to_remove_association "remove #{assoc_name}", f
|
@@ -0,0 +1,6 @@
|
|
1
|
+
#tasks
|
2
|
+
= f.fields_for table_name do |record|
|
3
|
+
= render partial: '/cm_admin/main/nested_fields', locals: { f: record, assoc_name: table_name }
|
4
|
+
- if @reflections.select {|x| x if x.name == table_name}.first.macro == :has_many
|
5
|
+
.links
|
6
|
+
= link_to_add_association "add #{table_name}", f, table_name, partial: '/cm_admin/main/nested_fields', render_options: {locals: { assoc_name: table_name }}
|
@@ -0,0 +1,60 @@
|
|
1
|
+
.admin-table-index
|
2
|
+
.table-top
|
3
|
+
p.table-top__total-count = "#{@ar_object.pagy.count} #{@model.ar_model.table_name} found"
|
4
|
+
.table-top__column-action
|
5
|
+
button.secondary-btn.column-btn data-bs-target="#columnActionModal" data-bs-toggle="modal"
|
6
|
+
span
|
7
|
+
i.fa.fa-columns.bolder
|
8
|
+
span
|
9
|
+
i.fa.fa-angle-down
|
10
|
+
|
11
|
+
.new-admin-table.scrollable
|
12
|
+
table.cm-table
|
13
|
+
thead.cm-table__header
|
14
|
+
tr.header-row
|
15
|
+
th.check-box-space
|
16
|
+
span
|
17
|
+
input.cm-checkbox type="checkbox"
|
18
|
+
- @model.available_fields[:index].each do |column|
|
19
|
+
th = column.header
|
20
|
+
tbody.cm-table__body
|
21
|
+
- @ar_object.data.each do |ar_object|
|
22
|
+
tr.body-row
|
23
|
+
td.check-box-space
|
24
|
+
span
|
25
|
+
input.cm-checkbox type="checkbox"
|
26
|
+
- @model.available_fields[:index].each do |column|
|
27
|
+
td
|
28
|
+
span class="#{column.cm_css_class}" = show_field_value(ar_object, column)
|
29
|
+
td.row-action-cell
|
30
|
+
.row-action-tool
|
31
|
+
button.secondary-btn.tool-btn type="button"
|
32
|
+
span
|
33
|
+
i.fa.fa-bars.bolder
|
34
|
+
span
|
35
|
+
i.fa.fa-angle-down
|
36
|
+
.popup-card.table-export-popup.hidden
|
37
|
+
.popup-option
|
38
|
+
a href="#{page_url('edit', ar_object)}"
|
39
|
+
| Edit
|
40
|
+
/ .cm-pagination
|
41
|
+
/ .cm-pagination__lhs Showing 1 to 15 out of 104
|
42
|
+
/ .cm-pagination__rhs
|
43
|
+
/ span.page-move-btn.disabled
|
44
|
+
/ i.fa.fa-angle-double-left.bolder.f14
|
45
|
+
/ span.page-move-btn.disabled
|
46
|
+
/ i.fa.fa-chevron-left.bolder
|
47
|
+
/ span.page-num-btn.active 1
|
48
|
+
/ span.page-num-btn 2
|
49
|
+
/ span.page-num-btn 3
|
50
|
+
/ span.page-num-btn 4
|
51
|
+
/ span.page-num-btn 5
|
52
|
+
/ span.page-move-btn
|
53
|
+
/ i.fa.fa-chevron-right.bolder
|
54
|
+
/ span.page-move-btn
|
55
|
+
/ i.fa.fa-angle-double-right.bolder.f14
|
56
|
+
|
57
|
+
.cm-pagination
|
58
|
+
.cm-pagination__lhs Showing #{@ar_object.pagy.from} to #{@ar_object.pagy.to} out of #{@ar_object.pagy.count}
|
59
|
+
.cm-pagination__rhs
|
60
|
+
== render partial: 'cm_admin/main/cm_pagy_nav', locals: { pagy: @ar_object.pagy }
|
@@ -0,0 +1,5 @@
|
|
1
|
+
ul.nav.nav-pills
|
2
|
+
- @model.available_tabs.each do |nav_item|
|
3
|
+
li.nav-item
|
4
|
+
- nav_item_action_name = nav_item.custom_action.present? ? nav_item.custom_action : 'show'
|
5
|
+
= link_to nav_item.nav_item_name.to_s.titleize, "/cm_admin/#{@model.name.underscore.pluralize}/#{@ar_object.id}/#{nav_item.custom_action}", class: "nav-link #{ nav_item_action_name == action_name ? 'active' : ''}"
|