cm-admin 0.2.0 → 0.4.2
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/.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 +8 -19
- data/app/assets/images/logo.png +0 -0
- data/{lib/generators/cm_admin/templates/assets/stylesheets → app/assets/stylesheets/cm_admin}/base/auth.scss +4 -6
- data/app/assets/stylesheets/cm_admin/base/common.scss +237 -0
- data/app/assets/stylesheets/cm_admin/base/filters.scss +200 -0
- data/{lib/generators/cm_admin/templates/assets/stylesheets → app/assets/stylesheets/cm_admin}/base/form.scss +83 -11
- 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/app/assets/stylesheets/cm_admin/cm_admin.css.scss +26 -0
- 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 +3 -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 -46
- data/lib/generators/cm_admin/USAGE +0 -8
- data/lib/generators/cm_admin/templates/assets/images/cm.png +0 -0
- data/lib/generators/cm_admin/templates/assets/stylesheets/application.css.scss +0 -33
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/_variable.scss +0 -14
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/input-styles.scss +0 -72
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/main-nav.scss +0 -79
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/scaffold.scss +0 -95
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/show.scss +0 -88
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/sidebar.scss +0 -69
- data/lib/generators/cm_admin/templates/assets/stylesheets/base/table.scss +0 -246
- data/lib/generators/cm_admin/templates/layouts/_navbar.html.slim +0 -8
- data/lib/generators/cm_admin/templates/layouts/_side_navbar.html.slim +0 -12
- data/lib/generators/cm_admin/templates/layouts/application.html.slim +0 -20
- data/lib/generators/cm_admin/templates/layouts/initializer.rb +0 -2
- data/lib/generators/cm_admin/templates/views/_form.erb +0 -67
- data/lib/generators/cm_admin/templates/views/_table.erb +0 -22
- data/lib/generators/cm_admin/templates/views/edit.erb +0 -10
- data/lib/generators/cm_admin/templates/views/index.erb +0 -11
- data/lib/generators/cm_admin/templates/views/new.erb +0 -10
- data/lib/generators/cm_admin/templates/views/reset_password.erb +0 -12
- data/lib/generators/cm_admin/templates/views/show.erb +0 -18
- data/lib/generators/cm_admin/templates/views/sign_in.erb +0 -18
- data/lib/generators/cm_admin/view_generator.rb +0 -78
|
@@ -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' : ''}"
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
.cm-navbar
|
|
2
|
+
.cm-navbar__lhs
|
|
3
|
+
.bread-crumb-area
|
|
4
|
+
= yield :bread_crumb
|
|
5
|
+
.nav-title-area
|
|
6
|
+
p.title-text = action_title
|
|
7
|
+
p.title-sub-text = action_description
|
|
8
|
+
- if @model.current_action.name == 'index'
|
|
9
|
+
.cm-navbar__rhs
|
|
10
|
+
.export-container
|
|
11
|
+
.dropdown
|
|
12
|
+
button.secondary-btn data-bs-toggle='dropdown'
|
|
13
|
+
span
|
|
14
|
+
i.fa.fa-arrow-down
|
|
15
|
+
span
|
|
16
|
+
| Export
|
|
17
|
+
span
|
|
18
|
+
i.fa.fa-angle-down
|
|
19
|
+
ul.dropdown-menu.export-popup
|
|
20
|
+
li
|
|
21
|
+
.popup-option.pointer data-bs-toggle='modal' data-bs-target='#exportmodal'
|
|
22
|
+
span Export
|
|
23
|
+
|
|
24
|
+
a.primary-btn.ml-2 href="#{page_url('new')}"
|
|
25
|
+
| Add
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
| This is the dashboard page
|