@hashtagcms/admin-ui-kit 1.0.6

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.
Files changed (79) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +83 -0
  3. package/dist/admin-ui-kit.min.css +14 -0
  4. package/dist/admin-ui-kit.min.js +2 -0
  5. package/dist/admin-ui-kit.min.js.LICENSE.txt +175 -0
  6. package/package.json +53 -0
  7. package/packages/components/README.md +92 -0
  8. package/packages/components/package.json +28 -0
  9. package/packages/components/src/action-bar.vue +237 -0
  10. package/packages/components/src/category-platform.vue +97 -0
  11. package/packages/components/src/category-settings.vue +815 -0
  12. package/packages/components/src/cms-module-dropdown.vue +78 -0
  13. package/packages/components/src/downlods.vue +21 -0
  14. package/packages/components/src/file-uploader.vue +188 -0
  15. package/packages/components/src/frontend-module-creator.vue +599 -0
  16. package/packages/components/src/global-site-button.vue +94 -0
  17. package/packages/components/src/homepage.vue +1087 -0
  18. package/packages/components/src/html-slot.vue +23 -0
  19. package/packages/components/src/image-gallery.vue +144 -0
  20. package/packages/components/src/index.js +53 -0
  21. package/packages/components/src/info-boxes.vue +68 -0
  22. package/packages/components/src/info-popup.vue +121 -0
  23. package/packages/components/src/language-button.vue +80 -0
  24. package/packages/components/src/language-copier.vue +177 -0
  25. package/packages/components/src/left-nav.vue +159 -0
  26. package/packages/components/src/library/copy-paste.vue +186 -0
  27. package/packages/components/src/library/info-box.vue +102 -0
  28. package/packages/components/src/library/left-menu-show-hide.vue +47 -0
  29. package/packages/components/src/library/loader.vue +141 -0
  30. package/packages/components/src/library/modal-box.vue +136 -0
  31. package/packages/components/src/library/split-button.vue +127 -0
  32. package/packages/components/src/library/timer-button.vue +43 -0
  33. package/packages/components/src/library/toast-box.vue +53 -0
  34. package/packages/components/src/menu-sorter.vue +265 -0
  35. package/packages/components/src/module-creator.vue +650 -0
  36. package/packages/components/src/module-permission.vue +334 -0
  37. package/packages/components/src/pagination.vue +125 -0
  38. package/packages/components/src/platform-button.vue +118 -0
  39. package/packages/components/src/search-bar.vue +144 -0
  40. package/packages/components/src/site-button.vue +42 -0
  41. package/packages/components/src/site-cloner.vue +150 -0
  42. package/packages/components/src/sitewise-copier.vue +234 -0
  43. package/packages/components/src/sitewise-data.vue +347 -0
  44. package/packages/components/src/sorter.vue +239 -0
  45. package/packages/components/src/tabular-view.vue +824 -0
  46. package/packages/components/src/title-bar.vue +76 -0
  47. package/packages/components/src/top-nav.vue +96 -0
  48. package/packages/helpers/README.md +88 -0
  49. package/packages/helpers/package.json +20 -0
  50. package/packages/helpers/src/admin-config.js +9 -0
  51. package/packages/helpers/src/common.js +89 -0
  52. package/packages/helpers/src/dashboard.js +16 -0
  53. package/packages/helpers/src/editor.js +163 -0
  54. package/packages/helpers/src/error-message-handler.js +50 -0
  55. package/packages/helpers/src/event-bus.js +4 -0
  56. package/packages/helpers/src/form.js +4 -0
  57. package/packages/helpers/src/fx.js +106 -0
  58. package/packages/helpers/src/humanize.js +14 -0
  59. package/packages/helpers/src/map.js +3 -0
  60. package/packages/styles/README.md +37 -0
  61. package/packages/styles/package.json +15 -0
  62. package/packages/styles/src/_action-bar.scss +35 -0
  63. package/packages/styles/src/_admin.scss +22 -0
  64. package/packages/styles/src/_animate.scss +1579 -0
  65. package/packages/styles/src/_badges.scss +34 -0
  66. package/packages/styles/src/_category-list.scss +14 -0
  67. package/packages/styles/src/_common.scss +163 -0
  68. package/packages/styles/src/_info-box.scss +96 -0
  69. package/packages/styles/src/_left-nav.scss +59 -0
  70. package/packages/styles/src/_loader.scss +82 -0
  71. package/packages/styles/src/_menu-sorter.scss +39 -0
  72. package/packages/styles/src/_model-creator.scss +48 -0
  73. package/packages/styles/src/_module-permission.scss +25 -0
  74. package/packages/styles/src/_page-manager.scss +63 -0
  75. package/packages/styles/src/_popover-modal.scss +20 -0
  76. package/packages/styles/src/_table-grid.scss +39 -0
  77. package/packages/styles/src/_toast.scss +20 -0
  78. package/packages/styles/src/_variables.scss +37 -0
  79. package/packages/styles/src/app.scss +2 -0
@@ -0,0 +1,347 @@
1
+ <template>
2
+ <div class="col col-4">
3
+ <div class="card border-0">
4
+ <div class="card-header">
5
+ <h5 class="card-title m-0" style="line-height: inherit">
6
+ Available {{ title }}
7
+ <span class="badge text-bg-secondary">{{ total }}</span>
8
+ <button
9
+ type="button"
10
+ title="Add Selected"
11
+ @click="doAction('add')"
12
+ class="hand pull-right btn btn-sm btn-primary"
13
+ >
14
+ Add Selected
15
+ </button>
16
+ </h5>
17
+ </div>
18
+ <div class="card-body p-2">
19
+ <div class="card-subtitle mb-2 text-muted" v-if="total > 0">
20
+ <label class="inline"
21
+ ><input
22
+ type="checkbox"
23
+ @click="selectAllData('table', $event.target)"
24
+ />
25
+ Select All</label
26
+ >
27
+ </div>
28
+ <div class="panel-sub-heading" style="padding: 4px" v-if="showSearch">
29
+ <div class="input-group">
30
+ <input
31
+ type="text"
32
+ placeholder="Search"
33
+ class="form-control"
34
+ aria-describedby="basic-addon3"
35
+ v-model="searchKey"
36
+ />
37
+ </div>
38
+ </div>
39
+ <ul class="list-group">
40
+ <li v-for="(data, index) in filterData()" class="list-group-item">
41
+ <label class="normal">
42
+ <input type="checkbox" v-model="data.selected" />
43
+ {{ getLabel(data) }}
44
+ </label>
45
+ </li>
46
+ </ul>
47
+ </div>
48
+ </div>
49
+ </div>
50
+
51
+ <div class="col col-4">
52
+ <div class="card border-0">
53
+ <div class="card-body p-0" v-if="message.length > 0">
54
+ <small
55
+ :class="alertCss"
56
+ v-html="message"
57
+ style="display: block"
58
+ ></small>
59
+ </div>
60
+ <div class="card-header">
61
+ <h5 class="card-title text-success m-0" style="line-height: inherit">
62
+ Added {{ title }}
63
+ <span class="badge text-bg-secondary">{{ selectedTotal }}</span>
64
+ <button
65
+ title="Remove Selected"
66
+ @click="doAction('remove')"
67
+ class="btn btn-sm btn-danger pull-right"
68
+ >
69
+ Remove Selected
70
+ </button>
71
+ </h5>
72
+ </div>
73
+ <div class="card-body">
74
+ <div v-if="selectedTotal > 0" class="card-subtitle mb-2 text-muted">
75
+ <label class="inline"
76
+ ><input
77
+ type="checkbox"
78
+ @click="selectAllData('sitewise', $event.target)"
79
+ />
80
+ Select All</label
81
+ >
82
+ </div>
83
+ <ul class="list-group">
84
+ <li v-for="(data, index) in siteData" class="list-group-item">
85
+ <label class="normal">
86
+ <input type="checkbox" v-model="data.selected" />
87
+ {{ getLabelForSite(data) }}
88
+ </label>
89
+ </li>
90
+ </ul>
91
+ </div>
92
+ </div>
93
+ </div>
94
+ </template>
95
+
96
+ <script>
97
+ import AdminConfig from "@hashtagcms/helpers/admin-config";
98
+
99
+ import { Loader, Toast } from "@hashtagcms/helpers/common";
100
+
101
+ export default {
102
+ mounted() {
103
+ //console.log(this.siteData);
104
+ // console.log(this.allData.data[0]);
105
+ //console.log(this.cuurent);
106
+ // this.initData();
107
+ },
108
+ created() {
109
+ //this.initData();
110
+ },
111
+
112
+ props: [
113
+ "dataMessage",
114
+ "dataAllData",
115
+ "dataSiteData",
116
+ "dataCurrentKey",
117
+ "dataSiteId",
118
+ "dataDefaultActionForSave",
119
+ "dataAlertCss",
120
+ "dataControllerName",
121
+ ],
122
+ data() {
123
+ return {
124
+ siteData:
125
+ typeof this.dataSiteData == "undefined" || this.dataSiteData === ""
126
+ ? []
127
+ : JSON.parse(this.dataSiteData),
128
+ allData:
129
+ typeof this.dataAllData == "undefined" || this.dataAllData === ""
130
+ ? []
131
+ : JSON.parse(this.dataAllData),
132
+ currentKey: this.dataCurrentKey,
133
+ searchKey: "",
134
+ siteId: parseInt(this.dataSiteId),
135
+ message: typeof this.dataMessage == "undefined" ? "" : this.dataMessage,
136
+ defaultActionForSave:
137
+ typeof this.dataDefaultActionForSave === "undefined"
138
+ ? "saveSettings"
139
+ : this.dataDefaultActionForSave,
140
+ alertCss:
141
+ typeof this.dataAlertCss == "undefined" || this.dataAlertCss === ""
142
+ ? "alert alert-info"
143
+ : this.dataAlertCss,
144
+ controllerName:
145
+ typeof this.dataControllerName === "undefined"
146
+ ? "site"
147
+ : this.dataControllerName,
148
+ };
149
+ },
150
+ computed: {
151
+ title() {
152
+ return this.allData.label;
153
+ },
154
+ total() {
155
+ return this.allData.data ? this.allData.data.length : 0;
156
+ },
157
+ selectedTotal() {
158
+ return this.siteData == null ? 0 : this.siteData.length;
159
+ },
160
+ showSearch() {
161
+ //return true;
162
+ return this.allData.data && this.allData.data.length > 10;
163
+ },
164
+ },
165
+ methods: {
166
+ saveNow(url, data) {
167
+ Loader.show(this, "Please wait. Making Changes...");
168
+ return new Promise((resolve, reject) => {
169
+ axios
170
+ .post(url, data)
171
+ .then((response) => {
172
+ resolve(response);
173
+ })
174
+ .catch((error) => {
175
+ reject(error.response);
176
+ })
177
+ .finally(() => {
178
+ Loader.hide(this);
179
+ });
180
+ });
181
+ },
182
+ doAction(action = "add") {
183
+ let $this = this;
184
+ //if action is add use left data to copy/reference to the right side
185
+ let currentData = action === "add" ? this.allData.data : this.siteData;
186
+ let ids = [];
187
+ let selectedArr = [];
188
+
189
+ if (currentData && currentData.length > 0) {
190
+ currentData.forEach(function (current) {
191
+ if (current.selected === true) {
192
+ ids.push(current.id);
193
+ selectedArr.push(current);
194
+ }
195
+ });
196
+
197
+ //if action is method/function. means it is being called from another component
198
+ if (typeof this.defaultActionForSave === "function") {
199
+ this.defaultActionForSave(action, currentData, selectedArr, ids);
200
+ return false;
201
+ }
202
+
203
+ if (ids.length > 0) {
204
+ let postParams = {};
205
+ postParams.key = this.currentKey;
206
+ postParams.ids = ids;
207
+ postParams.site_id = this.siteId;
208
+ postParams.action = action;
209
+ this.saveNow(
210
+ AdminConfig.admin_path(
211
+ this.controllerName + "/" + this.defaultActionForSave,
212
+ ),
213
+ postParams,
214
+ )
215
+ .then(function (res) {
216
+ feedback(res);
217
+ })
218
+ .catch(function (res) {
219
+ console.error("error: ", res);
220
+ Toast.show(
221
+ $this,
222
+ res?.data?.message || "I don't know what went wrong.",
223
+ 5000,
224
+ );
225
+ });
226
+ }
227
+ }
228
+
229
+ function hasInArr(element, onwhat, value) {
230
+ return element[onwhat] === value;
231
+ }
232
+ //console.log(ids);
233
+ function feedback(res) {
234
+ console.log(res);
235
+ if (action === "add") {
236
+ //console.log("adding");
237
+ //console.log(selectedArr);
238
+ selectedArr.forEach(function (current) {
239
+ let id = current.id;
240
+
241
+ let found = $this.siteData.findIndex(function (c) {
242
+ return c.id === id;
243
+ });
244
+
245
+ if (found === -1) {
246
+ $this.siteData.push(current);
247
+ }
248
+ });
249
+ } else {
250
+ //remove from right side
251
+ selectedArr.forEach(function (current) {
252
+ let id = current.id;
253
+
254
+ let found = $this.siteData.findIndex(function (c) {
255
+ return c.id === id;
256
+ });
257
+
258
+ if (found !== -1) {
259
+ $this.siteData.splice(found, 1);
260
+ }
261
+ });
262
+ }
263
+ }
264
+ },
265
+ selectAllData(dataType, holder) {
266
+ let $this = this;
267
+ let currentData =
268
+ dataType === "table" ? this.allData.data : this.siteData;
269
+ let selected = holder.checked;
270
+ if (currentData && currentData.length > 0) {
271
+ currentData.forEach(function (current) {
272
+ //$this.$set(current, "selected", selected);
273
+ current.selected = selected;
274
+ });
275
+ }
276
+ },
277
+ getLabel(data) {
278
+ let label = "";
279
+ if (data.lang) {
280
+ label = typeof data.lang.name == "undefined" ? "" : data.lang.name;
281
+ } else {
282
+ label = data.name || data.alias || "";
283
+ }
284
+ return label;
285
+ },
286
+ getLabelForSite(data) {
287
+ //console.log(data);
288
+
289
+ if (typeof data.name != "undefined" || typeof data.alias != "undefined") {
290
+ return data.name || data.alias;
291
+ } else if (data.lang) {
292
+ return typeof data.lang.name == "undefined" ? "" : data.lang.name;
293
+ }
294
+
295
+ //Lang data can be found from the source too. Borrow it from left side if right side does not have it.
296
+ //fallback - get from source/left side data compare id or link_rewrite
297
+
298
+ if (this.allData.data && this.allData.data.length > 0) {
299
+ let index = this.allData.data.findIndex(function (current) {
300
+ return (
301
+ current.id === data.id ||
302
+ (typeof data.link_rewrite != "undefined" &&
303
+ data.link_rewrite === current.link_rewrite)
304
+ );
305
+ });
306
+
307
+ return index === -1 ? "" : this.getLabel(this.allData.data[index]);
308
+ }
309
+
310
+ return "";
311
+ },
312
+ filterData() {
313
+ let $this = this;
314
+
315
+ let data = [];
316
+
317
+ let key = this.searchKey;
318
+
319
+ if (key !== "" && key != null) {
320
+ key = key.toLowerCase();
321
+
322
+ return this.allData.data.filter(function (current) {
323
+ return (
324
+ $this.getLabel(current).toLowerCase().includes(key) ||
325
+ current.id === key
326
+ );
327
+ });
328
+ } else {
329
+ //console.log("data ", this.allData.data);
330
+ return this.allData.data;
331
+ }
332
+ },
333
+ setData(key, data) {
334
+ //this.allData[key] = data;
335
+ //console.log(key, data);
336
+ this.allData[key] = data;
337
+ //this.$set(this.allData, key, data);
338
+ },
339
+ setSiteData(data) {
340
+ //this.allData[key] = data;
341
+ this.siteData = {};
342
+ this.siteData = data;
343
+ //this.$set(this, 'siteData', data);
344
+ },
345
+ },
346
+ };
347
+ </script>
@@ -0,0 +1,239 @@
1
+ <template>
2
+ <div class="sortElem" @click="showHide($event)">
3
+ <ul id="sortableField">
4
+ <li
5
+ v-for="current in allData"
6
+ class="parent"
7
+ v-if="current.module_pid == 0"
8
+ >
9
+ <h3>
10
+ <a>
11
+ <i
12
+ v-if="hasChild(current)"
13
+ class="js_more fa fa-ellipsis-v pull-right adjustMore"
14
+ ></i>
15
+ <span class="text">{{ current.name }}</span>
16
+ </a>
17
+ </h3>
18
+ <ul v-if="hasChild(current)">
19
+ <li v-for="child in current.child">
20
+ <a>
21
+ <span class="text">{{ child.name }}</span>
22
+ </a>
23
+ </li>
24
+ </ul>
25
+ </li>
26
+ </ul>
27
+ </div>
28
+ </template>
29
+
30
+ <script>
31
+ import AdminConfig from "@hashtagcms/helpers/admin-config";
32
+
33
+ import Sortable from "sortablejs";
34
+ import { Toast } from "@hashtagcms/helpers/common";
35
+ import Form from "@hashtagcms/helpers/form";
36
+
37
+ export default {
38
+ mounted() {
39
+ this.enableSorting();
40
+ console.log(this.controllerName);
41
+ },
42
+
43
+ props: ["dataAllModules", "dataControllerName"],
44
+
45
+ data() {
46
+ return {
47
+ allData:
48
+ this.dataAllModules && this.dataAllModules != "null"
49
+ ? JSON.parse(this.dataAllModules)
50
+ : [],
51
+ sortable: null,
52
+ sortingInterval: -1,
53
+ updateIndexUrl: AdminConfig.admin_path(
54
+ this.controllerName + "/updateIndex",
55
+ ),
56
+ lastTarget: "",
57
+ };
58
+ },
59
+ computed: {
60
+ controllerName() {
61
+ let cName =
62
+ typeof this.dataControllerName == "undefined"
63
+ ? ""
64
+ : this.dataControllerName.toLocaleLowerCase();
65
+ return cName.replace(/\s/g, "");
66
+ },
67
+ },
68
+ methods: {
69
+ hasChild(data) {
70
+ return data.child.length > 0;
71
+ },
72
+ hideAll() {
73
+ var $this = this;
74
+ document.querySelectorAll(".sortElem .parent").forEach(function (i) {
75
+ i.classList.remove("active");
76
+ });
77
+ },
78
+ showHide(event) {
79
+ let ele = event.target;
80
+ if (ele.parentElement.parentElement.parentElement != this.lastTarget) {
81
+ this.hideAll();
82
+ if (ele.classList.contains("js_more")) {
83
+ event.preventDefault();
84
+ ele.parentElement.parentElement.parentElement.classList.add(
85
+ "active",
86
+ "animated",
87
+ "fadeIn",
88
+ );
89
+ }
90
+ this.lastTarget = ele.parentElement.parentElement.parentElement;
91
+ } else {
92
+ if (
93
+ ele.parentElement.parentElement.parentElement.classList.contains(
94
+ "active",
95
+ )
96
+ ) {
97
+ ele.parentElement.parentElement.parentElement.classList.remove(
98
+ "active",
99
+ );
100
+ } else {
101
+ ele.parentElement.parentElement.parentElement.classList.add("active");
102
+ }
103
+ }
104
+ },
105
+ getActiveCss(controller_name, data) {
106
+ return this.isActive(controller_name, data) ? "active" : "";
107
+ },
108
+ isActive(controller_name, data) {
109
+ if (this.controllerName == controller_name) {
110
+ return true;
111
+ }
112
+
113
+ if (data && data.child && data.child.length > 0) {
114
+ var controllerName = this.controllerName;
115
+ return data.child.find(function (c) {
116
+ return c.controller_name == controllerName;
117
+ });
118
+ }
119
+ },
120
+ enableSorting() {
121
+ this.$nextTick(function () {
122
+ if (this.sortable != null) {
123
+ this.sortable.destroy();
124
+ }
125
+ var el = document.getElementById("sortableField");
126
+ this.sortable = Sortable.create(el, {
127
+ onEnd: this.sortingCallback,
128
+ onStart: this.cancelSortingCallback,
129
+ });
130
+ });
131
+ },
132
+ cancelSortingCallback() {
133
+ if (this.sortingInterval != -1) {
134
+ clearInterval(this.sortingInterval);
135
+ }
136
+ },
137
+ sortingCallback(evt) {
138
+ var text = "";
139
+ var $this = this;
140
+ var data = [];
141
+ // console.log(evt);
142
+ document
143
+ .querySelectorAll(".sortElem .parent")
144
+ .forEach(function (i, index) {
145
+ var text = i.children[0].children[0].innerText;
146
+ var indx = index;
147
+ for (var a = 0; a < $this.allData.length; a++) {
148
+ if (
149
+ $this.allData[a].module_pid == 0 &&
150
+ $this.allData[a].name == text
151
+ ) {
152
+ data[a] = {};
153
+ data[a].id = $this.allData[a].id;
154
+ data[a].position = index;
155
+ data[a].name = $this.allData[a].name;
156
+ }
157
+ }
158
+ });
159
+ // console.log(data);
160
+ this.updateIndex(data);
161
+ this.cancelSortingCallback();
162
+ },
163
+ submit(requestType, url, data) {
164
+ return new Promise((resolve, reject) => {
165
+ axios[requestType](url, data)
166
+ .then((response) => {
167
+ this.onSuccess(response);
168
+ })
169
+ .catch((error) => {
170
+ this.onFailure(error.response);
171
+ });
172
+ });
173
+ },
174
+ updateIndex(data) {
175
+ this.submit("post", this.updateIndexUrl, data)
176
+ .then((response) => this.onSuccess(response))
177
+ .catch((response) => this.onFailure(response));
178
+ },
179
+ onSuccess(res) {
180
+ Toast.show(this, "Modules Sorted.");
181
+ },
182
+ onFailure(res) {
183
+ console.log(res);
184
+ },
185
+ },
186
+ };
187
+ </script>
188
+
189
+ <style>
190
+ .sortElem {
191
+ margin-top: 15px;
192
+ }
193
+
194
+ .sortElem .parent {
195
+ list-style: none;
196
+ border: 1px solid #cacaca;
197
+ background: #fff;
198
+ }
199
+
200
+ .sortElem .parent h3 {
201
+ font-size: 16px;
202
+ margin: 0;
203
+ }
204
+
205
+ .sortElem ul {
206
+ padding: 0;
207
+ }
208
+
209
+ .sortElem .parent a {
210
+ padding: 10px;
211
+ color: #666;
212
+ display: block;
213
+ }
214
+
215
+ .sortElem .parent ul {
216
+ display: none;
217
+ }
218
+
219
+ .sortElem .parent.active ul {
220
+ display: block;
221
+ background: #ffff;
222
+ border-top: 1px solid #cacaca;
223
+ }
224
+
225
+ .sortElem .parent.active ul li {
226
+ list-style: none;
227
+ margin-left: 15px;
228
+ line-height: normal;
229
+ }
230
+
231
+ .sortElem .parent.active ul li a span {
232
+ color: #000;
233
+ font-weight: bold;
234
+ }
235
+
236
+ .sortElem .parent.sortable-chosen {
237
+ background: #f4f4f4;
238
+ }
239
+ </style>