quasar-ui-danx 0.4.79 → 0.4.81

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "quasar-ui-danx",
3
- "version": "0.4.79",
3
+ "version": "0.4.81",
4
4
  "author": "Dan <dan@flytedesk.com>",
5
5
  "description": "DanX Vue / Quasar component library",
6
6
  "license": "MIT",
@@ -27,7 +27,8 @@
27
27
  :class="filePreviewClass"
28
28
  :style="styleSize"
29
29
  :file="file"
30
- :related-files="file.transcodes || uploadedFiles"
30
+ :show-transcodes="showTranscodes"
31
+ :related-files="uploadedFiles"
31
32
  downloadable
32
33
  :removable="!readonly && !disabled"
33
34
  @remove="onRemove(file)"
@@ -92,6 +93,7 @@ const props = withDefaults(defineProps<{
92
93
  addIconClass?: string;
93
94
  filePreviewClass?: string;
94
95
  filePreviewBtnSize?: string;
96
+ showTranscodes?: boolean;
95
97
  }>(), {
96
98
  modelValue: null,
97
99
  field: null,
@@ -1,64 +1,66 @@
1
1
  <template>
2
- <QBtn
3
- :loading="isSaving"
4
- class="shadow-none py-0"
5
- :class="buttonClass"
6
- :disable="disabled"
7
- @click="()=> onAction()"
8
- >
9
- <div class="flex items-center flex-nowrap">
10
- <component
11
- :is="icon || typeOptions.icon"
12
- class="transition-all"
13
- :class="resolvedIconClass"
14
- />
15
- <div
16
- v-if="label || label === 0"
17
- class="ml-2"
18
- :class="labelClass"
19
- >
20
- {{ label }}
21
- </div>
22
- <slot />
23
- </div>
24
- <QTooltip
25
- v-if="tooltip"
26
- class="whitespace-nowrap"
27
- :class="tooltipClass"
28
- >
29
- <slot name="tooltip">
30
- {{ tooltip }}
31
- </slot>
32
- </QTooltip>
33
- <QMenu
34
- v-if="isConfirming"
35
- :model-value="true"
36
- >
37
- <div class="p-4 bg-slate-600">
38
- <div>{{ confirmText }}</div>
39
- <div class="flex items-center flex-nowrap mt-2">
40
- <div class="flex-grow">
41
- <ActionButton
42
- type="cancel"
43
- color="gray"
44
- @click="isConfirming = false"
45
- />
46
- </div>
47
- <ActionButton
48
- type="confirm"
49
- color="green"
50
- @click="()=> onAction(true)"
51
- />
52
- </div>
53
- </div>
54
- </QMenu>
55
- </QBtn>
2
+ <QBtn
3
+ :loading="isSaving"
4
+ class="shadow-none py-0"
5
+ :class="buttonClass"
6
+ :disable="disabled"
7
+ @click="()=> onAction()"
8
+ >
9
+ <div class="flex items-center flex-nowrap">
10
+ <component
11
+ :is="icon || typeOptions.icon"
12
+ class="transition-all"
13
+ :class="resolvedIconClass"
14
+ />
15
+ <div
16
+ v-if="label || label === 0"
17
+ class="ml-2"
18
+ :class="labelClass"
19
+ >
20
+ {{ label }}
21
+ </div>
22
+ <slot />
23
+ </div>
24
+ <QTooltip
25
+ v-if="tooltip"
26
+ class="whitespace-nowrap"
27
+ :class="tooltipClass"
28
+ >
29
+ <slot name="tooltip">
30
+ {{ tooltip }}
31
+ </slot>
32
+ </QTooltip>
33
+ <QMenu
34
+ v-if="isConfirming"
35
+ :model-value="true"
36
+ >
37
+ <div class="p-4 bg-slate-600">
38
+ <div>{{ confirmText }}</div>
39
+ <div class="flex items-center flex-nowrap mt-2">
40
+ <div class="flex-grow">
41
+ <ActionButton
42
+ type="cancel"
43
+ color="gray"
44
+ @click="isConfirming = false"
45
+ />
46
+ </div>
47
+ <ActionButton
48
+ type="confirm"
49
+ color="green"
50
+ @click="()=> onAction(true)"
51
+ />
52
+ </div>
53
+ </div>
54
+ </QMenu>
55
+ </QBtn>
56
56
  </template>
57
57
  <script setup lang="ts">
58
58
  import {
59
+ FaSolidArrowRotateRight as RestartIcon,
59
60
  FaSolidArrowsRotate as RefreshIcon,
60
61
  FaSolidCircleCheck as ConfirmIcon,
61
62
  FaSolidCircleXmark as CancelIcon,
63
+ FaSolidCodeMerge as MergeIcon,
62
64
  FaSolidCopy as CopyIcon,
63
65
  FaSolidFileExport as ExportIcon,
64
66
  FaSolidFileImport as ImportIcon,
@@ -75,8 +77,8 @@ import { computed, ref } from "vue";
75
77
  import { ActionTarget, ResourceAction } from "../../../types";
76
78
 
77
79
  export interface ActionButtonProps {
78
- type?: "trash" | "create" | "edit" | "copy" | "folder" | "play" | "stop" | "pause" | "refresh" | "confirm" | "cancel" | "export" | "import" | "minus";
79
- color?: "red" | "blue" | "sky" | "sky-invert" | "green" | "green-invert" | "lime" | "white" | "gray" | "yellow" | "orange";
80
+ type?: "trash" | "create" | "edit" | "copy" | "folder" | "play" | "stop" | "pause" | "refresh" | "restart" | "confirm" | "cancel" | "export" | "import" | "minus" | "merge";
81
+ color?: "red" | "blue" | "blue-invert" | "sky" | "sky-invert" | "green" | "green-invert" | "lime" | "white" | "gray" | "yellow" | "orange";
80
82
  size?: "xxs" | "xs" | "sm" | "md" | "lg";
81
83
  icon?: object | string;
82
84
  iconClass?: string;
@@ -154,6 +156,8 @@ const colorClass = computed(() => {
154
156
  return "text-green-300 bg-green-900 hover:bg-green-800";
155
157
  case "blue":
156
158
  return "text-blue-900 bg-blue-300 hover:bg-blue-400";
159
+ case "blue-invert":
160
+ return "text-blue-300 bg-blue-900 hover:bg-blue-800";
157
161
  case "sky":
158
162
  return "text-sky-900 bg-sky-300 hover:bg-sky-400";
159
163
  case "sky-invert":
@@ -199,10 +203,14 @@ const typeOptions = computed(() => {
199
203
  return { icon: StopIcon };
200
204
  case "pause":
201
205
  return { icon: PauseIcon };
206
+ case "restart":
207
+ return { icon: RestartIcon };
202
208
  case "refresh":
203
209
  return { icon: RefreshIcon };
204
210
  case "minus":
205
211
  return { icon: MinusIcon };
212
+ case "merge":
213
+ return { icon: MergeIcon };
206
214
  default:
207
215
  return { icon: EditIcon };
208
216
  }
@@ -6,7 +6,7 @@
6
6
  <template v-if="computedImage">
7
7
  <div
8
8
  class="grow h-full"
9
- @click="showPreview = true"
9
+ @click="onShowPreview"
10
10
  >
11
11
  <div
12
12
  v-if="isVideo"
@@ -143,8 +143,9 @@
143
143
 
144
144
  <script setup lang="ts">
145
145
  import { DocumentTextIcon as TextFileIcon, DownloadIcon, PlayIcon } from "@heroicons/vue/outline";
146
- import { computed, ComputedRef, onMounted, ref } from "vue";
147
- import { download, FileUpload, uniqueBy } from "../../../helpers";
146
+ import { computed, ComputedRef, ref, shallowRef } from "vue";
147
+ import { danxOptions } from "../../../config";
148
+ import { download, uniqueBy } from "../../../helpers";
148
149
  import { ImageIcon, PdfIcon, TrashIcon as RemoveIcon } from "../../../svg";
149
150
  import { UploadedFile } from "../../../types";
150
151
  import { FullScreenCarouselDialog } from "../Dialogs";
@@ -171,6 +172,7 @@ export interface FilePreviewProps {
171
172
  disabled?: boolean;
172
173
  square?: boolean;
173
174
  btnSize?: "xs" | "sm" | "md" | "lg";
175
+ showTranscodes?: boolean;
174
176
  }
175
177
 
176
178
  const emit = defineEmits(["remove"]);
@@ -207,10 +209,11 @@ const computedImage: ComputedRef<UploadedFile | null> = computed(() => {
207
209
  return null;
208
210
  });
209
211
 
212
+ const transcodes = shallowRef(props.file?.transcodes || null);
210
213
  const isUploading = computed(() => !props.file || props.file?.progress !== undefined);
211
214
  const statusMessage = computed(() => isUploading.value ? "Uploading..." : transcodingStatus.value?.message);
212
215
  const previewableFiles: ComputedRef<(UploadedFile | null)[] | null> = computed(() => {
213
- return props.relatedFiles?.length > 0 ? uniqueBy([computedImage.value, ...props.relatedFiles], filesHaveSameUrl) : [computedImage.value];
216
+ return props.relatedFiles?.length > 0 ? uniqueBy([computedImage.value, ...(props.showTranscodes ? (transcodes.value || []) : props.relatedFiles)], filesHaveSameUrl) : [computedImage.value];
214
217
  });
215
218
 
216
219
  function filesHaveSameUrl(a: UploadedFile, b: UploadedFile) {
@@ -253,13 +256,6 @@ const transcodingStatus = computed(() => {
253
256
  return status;
254
257
  });
255
258
 
256
- // Check for an active transcode and make sure the file is being polled for updates
257
- onMounted(() => {
258
- if (transcodingStatus.value) {
259
- (new FileUpload([])).waitForTranscode(props.file);
260
- }
261
- });
262
-
263
259
  const isConfirmingRemove = ref(false);
264
260
  function onRemove() {
265
261
  if (!isConfirmingRemove.value) {
@@ -271,6 +267,15 @@ function onRemove() {
271
267
  emit("remove");
272
268
  }
273
269
  }
270
+
271
+ async function onShowPreview() {
272
+ showPreview.value = true;
273
+
274
+ if (props.showTranscodes && props.file && !transcodes.value) {
275
+ const file = await danxOptions.value.fileUpload.refreshFile(props.file.id) as UploadedFile;
276
+ transcodes.value = file.transcodes || [];
277
+ }
278
+ }
274
279
  </script>
275
280
 
276
281
  <style module="cls" lang="scss">
@@ -13,7 +13,6 @@ import {
13
13
  import { resolveFileLocation } from "./files";
14
14
  import { FlashMessages } from "./FlashMessages";
15
15
  import { storeObject } from "./objectStore";
16
- import { sleep } from "./utils";
17
16
 
18
17
 
19
18
  export class FileUpload {
@@ -231,7 +230,6 @@ export class FileUpload {
231
230
  // Fire the file complete callbacks
232
231
  this.fireCompleteCallback(fileUpload, storedFile);
233
232
  this.checkAllComplete();
234
- await this.waitForTranscode(storedFile);
235
233
  } catch (error: any) {
236
234
  this.errorHandler(e, fileUpload.file, error);
237
235
  }
@@ -293,20 +291,6 @@ export class FileUpload {
293
291
  return false;
294
292
  }
295
293
 
296
- /**
297
- * Keeps refreshing the file while there is transcoding in progress
298
- */
299
- async waitForTranscode(file: UploadedFile) {
300
- // Only allow waiting for transcode 1 time per file
301
- if (!file.meta || file.meta.is_waiting_transcode) return;
302
- file.meta.is_waiting_transcode = true;
303
- let currentFile: UploadedFile | null = file;
304
- while (currentFile && this.isTranscoding(currentFile)) {
305
- await sleep(1000);
306
- currentFile = await this.refreshFile(currentFile);
307
- }
308
- }
309
-
310
294
  /**
311
295
  * Start uploading all files
312
296
  */