@windward/core 0.9.1 → 0.10.0

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/CHANGELOG.md CHANGED
@@ -1,5 +1,8 @@
1
1
  # Changelog
2
2
 
3
+ ### Release [0.10.0] created - 2025-01-03
4
+
5
+
3
6
  ### Hotfix [0.9.1] created - 2024-12-10
4
7
 
5
8
 
@@ -59,26 +59,19 @@
59
59
  "
60
60
  ></TextEditor>
61
61
  </v-container>
62
- <v-container>
63
- <v-img
64
- v-if="block.metadata.config.items[itemIndex].file"
65
- :aria-describedby="
62
+ <v-container
63
+ v-if="
64
+ block.metadata.config.items[itemIndex].fileConfig
65
+ .asset
66
+ "
67
+ >
68
+ <ImageAssetViewer
69
+ v-model="
66
70
  block.metadata.config.items[itemIndex]
67
- .ariaDescribedBy
68
- "
69
- :alt="
70
- getImageAlt(
71
- block.metadata.config.items[itemIndex].file,
72
- block.metadata.config.items[itemIndex]
73
- .altText
74
- )
75
- "
76
- :src="
77
- getImagePublicUrl(
78
- block.metadata.config.items[itemIndex].file
79
- )
71
+ .fileConfig
80
72
  "
81
- ></v-img>
73
+ :assets="block.assets"
74
+ ></ImageAssetViewer>
82
75
  </v-container>
83
76
  </v-expansion-panel-content>
84
77
  </v-expansion-panel>
@@ -89,6 +82,7 @@
89
82
  <script>
90
83
  import _ from 'lodash'
91
84
  import Crypto from '~/helpers/Crypto'
85
+ import ImageAssetViewer from '~/components/Content/ImageAssetViewer.vue'
92
86
  import TextEditor from '~/components/Text/TextEditor'
93
87
  import TextViewer from '~/components/Text/TextViewer'
94
88
  import BaseContentBlock from '~/components/Content/Blocks/BaseContentBlock'
@@ -98,6 +92,7 @@ export default {
98
92
  components: {
99
93
  TextEditor,
100
94
  TextViewer,
95
+ ImageAssetViewer,
101
96
  },
102
97
  extends: BaseContentBlock,
103
98
  beforeMount() {
@@ -118,9 +113,7 @@ export default {
118
113
  header: '',
119
114
  expand: false,
120
115
  content: '',
121
- file: null,
122
- altText: '',
123
- ariaDescribedBy: '',
116
+ fileConfig: {},
124
117
  }
125
118
  this.block.metadata.config.items = []
126
119
  this.block.metadata.config.items.push(defaultObject)
@@ -27,7 +27,7 @@
27
27
  @click="item.active = !item.active"
28
28
  >
29
29
  <v-avatar
30
- v-if="item.iconImage && item.icon"
30
+ v-if="item.iconImage && item.fileConfig"
31
31
  class="clickable--image"
32
32
  :rounded="
33
33
  block.metadata.config.display.round_icon
@@ -36,7 +36,12 @@
36
36
  "
37
37
  size="100%"
38
38
  >
39
- <v-img :src="getImagePublicUrl(item.iconAsset)" />
39
+ <ImageAssetViewer
40
+ v-model="item.fileConfig"
41
+ :assets="block.assets"
42
+ class="image-asset-viewer"
43
+ :inherit-sizing="true"
44
+ ></ImageAssetViewer>
40
45
  </v-avatar>
41
46
  <v-icon
42
47
  v-else-if="isIcon(item.icon)"
@@ -77,11 +82,13 @@ import _ from 'lodash'
77
82
  import he from 'he'
78
83
  import BaseContentBlock from '~/components/Content/Blocks/BaseContentBlock'
79
84
  import TextViewer from '~/components/Text/TextViewer'
85
+ import ImageAssetViewer from '~/components/Content/ImageAssetViewer.vue'
80
86
 
81
87
  export default {
82
88
  name: 'ClickableIcons',
83
89
  components: {
84
90
  TextViewer,
91
+ ImageAssetViewer,
85
92
  },
86
93
  extends: BaseContentBlock,
87
94
  beforeMount() {
@@ -295,4 +302,8 @@ button.button-icon.button-icon--rounded {
295
302
  font-size: 2.5rem;
296
303
  }
297
304
  }
305
+ .image-asset-viewer {
306
+ height: inherit;
307
+ width: inherit;
308
+ }
298
309
  </style>
@@ -7,30 +7,9 @@
7
7
  {{ block.metadata.config.description }}
8
8
  </p>
9
9
 
10
- <v-card v-if="render && !hasSource">
11
- <v-card-title>
12
- <v-icon class="mr-2">mdi-cloud-question</v-icon>
13
- {{
14
- $t(
15
- 'windward.core.components.content.blocks.video.not_configured_title'
16
- )
17
- }}
18
- </v-card-title>
19
- <v-card-text>{{
20
- $t('windward.core.components.content.blocks.video.edit_prompt')
21
- }}</v-card-text>
22
- </v-card>
23
-
24
- <v-skeleton-loader
25
- v-if="!render && !hasSource"
26
- type="image, image, list-item-avatar"
27
- class="reload-skeleton"
28
- ></v-skeleton-loader>
29
-
30
10
  <VuetifyPlayer
31
- v-if="hasSource"
32
11
  :language="$i18n && $i18n.locale ? $i18n.locale : 'en-US'"
33
- :type="block.metadata.config.type"
12
+ type="auto"
34
13
  :playlist="linkedPlaylist"
35
14
  :autoplay="block.metadata.config.attributes.autoplay"
36
15
  :autopictureinpicture="
@@ -59,9 +38,31 @@
59
38
  block.metadata.config.attributes.playlistautoadvance
60
39
  "
61
40
  :playbackrates="block.metadata.config.attributes.playbackrates"
41
+ :captions-autoscroll.sync="captionsAutoscroll"
42
+ :captions-paragraph-view.sync="captionsParagraphView"
43
+ :captions-visible.sync="captionsVisible"
44
+ flat
62
45
  @seeking="onSeeking"
63
46
  @timeupdate="onTimeupdate"
64
- />
47
+ >
48
+ <template #no-source>
49
+ <v-card>
50
+ <v-card-title class="justify-center">
51
+ <v-icon class="mr-2">mdi-cloud-question</v-icon>
52
+ {{
53
+ $t(
54
+ 'windward.core.components.content.blocks.video.not_configured_title'
55
+ )
56
+ }}
57
+ </v-card-title>
58
+ <v-card-text>{{
59
+ $t(
60
+ 'windward.core.components.content.blocks.video.edit_prompt'
61
+ )
62
+ }}</v-card-text>
63
+ </v-card>
64
+ </template>
65
+ </VuetifyPlayer>
65
66
  <!-- display first note in the playlist for now -->
66
67
  <v-alert
67
68
  v-if="notes.length > 0"
@@ -78,10 +79,11 @@
78
79
 
79
80
  <script>
80
81
  import _ from 'lodash'
82
+ import he from 'he'
81
83
  import VuetifyPlayer from '@mindedge/vuetify-player'
84
+ import AuthUserRepository from '~/models/repositories/AuthUserRepository'
82
85
  import BaseContentBlock from '~/components/Content/Blocks/BaseContentBlock'
83
86
  import TextViewer from '~/components/Text/TextViewer'
84
- import he from 'he'
85
87
 
86
88
  export default {
87
89
  name: 'ContentBlockVideo',
@@ -214,6 +216,58 @@ export default {
214
216
  })
215
217
  return playlist
216
218
  },
219
+ captionsAutoscroll: {
220
+ get() {
221
+ const user = new AuthUserRepository(this.$nuxt)
222
+
223
+ return user.getPreference('video.captions-autoscroll', true)
224
+ },
225
+ set(v) {
226
+ try {
227
+ const user = new AuthUserRepository(this.$nuxt)
228
+ user.setPreference('video.captions-autoscroll', v)
229
+ user.save()
230
+ } catch (e) {
231
+ console.error('Could not save user video preference!')
232
+ console.error(e)
233
+ }
234
+ },
235
+ },
236
+ captionsParagraphView: {
237
+ get() {
238
+ const user = new AuthUserRepository(this.$nuxt)
239
+ return user.getPreference(
240
+ 'video.captions-paragraph-view',
241
+ false
242
+ )
243
+ },
244
+ set(v) {
245
+ try {
246
+ const user = new AuthUserRepository(this.$nuxt)
247
+ user.setPreference('video.captions-paragraph-view', v)
248
+ user.save()
249
+ } catch (e) {
250
+ console.error('Could not save user video preference!')
251
+ console.error(e)
252
+ }
253
+ },
254
+ },
255
+ captionsVisible: {
256
+ get() {
257
+ const user = new AuthUserRepository(this.$nuxt)
258
+ return user.getPreference('video.captions-visible', false)
259
+ },
260
+ set(v) {
261
+ try {
262
+ const user = new AuthUserRepository(this.$nuxt)
263
+ user.setPreference('video.captions-visible', v)
264
+ user.save()
265
+ } catch (e) {
266
+ console.error('Could not save user video preference!')
267
+ console.error(e)
268
+ }
269
+ },
270
+ },
217
271
  },
218
272
  data() {
219
273
  return {
@@ -224,7 +278,7 @@ export default {
224
278
  description: '',
225
279
  // Default settings for new blocks
226
280
  // This will be overridden in beforeMount()
227
- type: 'video', // Allowed video|audio. In audio mode the player has a max-height of 40px
281
+ type: 'auto', // Allowed auto|video|audio. In audio mode the player has a max-height of 40px. Auto will switch between the other types when needed
228
282
  attributes: {
229
283
  autoplay: false, // Autoplay on load. It's in the spec but DON'T USE THIS
230
284
  autopictureinpicture: false, // Start with picture in picture mode
@@ -98,53 +98,16 @@
98
98
  )
99
99
  }}
100
100
  </h4>
101
- <v-text-field
102
- v-model="
103
- block.metadata.config.items[index].altText
104
- "
105
- class="pt-3 pb-3"
106
- :hide-details="true"
107
- dense
108
- outlined
109
- :label="
110
- $t(
111
- 'windward.core.shared.settings.alt_image'
112
- )
113
- "
114
- :disabled="render"
115
- ></v-text-field>
116
- <v-text-field
101
+ <ImageAssetSettings
117
102
  v-model="
118
103
  block.metadata.config.items[index]
119
- .ariaDescribedBy
104
+ .fileConfig
120
105
  "
121
- class="pt-3 pb-3"
122
- :hide-details="true"
123
- dense
124
- outlined
125
- :label="
126
- $t(
127
- 'windward.core.shared.settings.aria_described'
128
- )
129
- "
130
- :disabled="render"
131
- ></v-text-field>
132
- <ContentBlockAsset
133
- v-model="
134
- block.metadata.config.items[index].file
135
- "
136
- mimes="image/png,image/jpeg"
137
106
  :assets.sync="block.assets"
138
- outlined
139
- >
140
- <template #title>
141
- {{
142
- $t(
143
- 'windward.core.components.settings.image.place_image'
144
- )
145
- }}
146
- </template>
147
- </ContentBlockAsset>
107
+ hide-background
108
+ hide-decorative
109
+ hide-modal
110
+ ></ImageAssetSettings>
148
111
  </v-container>
149
112
  </v-container>
150
113
  </template>
@@ -181,12 +144,14 @@ import BaseContentSettings from '~/components/Content/Settings/BaseContentSettin
181
144
  import TextEditor from '~/components/Text/TextEditor'
182
145
  import SortableExpansionPanel from '~/components/Core/SortableExpansionPanel.vue'
183
146
  import Uuid from '~/helpers/Uuid'
147
+ import ImageAssetSettings from '~/components/Content/Settings/ImageAssetSettings.vue'
184
148
 
185
149
  export default {
186
150
  name: 'AccordionSettings',
187
151
  components: {
188
152
  TextEditor,
189
153
  SortableExpansionPanel,
154
+ ImageAssetSettings,
190
155
  },
191
156
  extends: BaseContentSettings,
192
157
  beforeMount() {
@@ -219,9 +184,7 @@ export default {
219
184
  header: '',
220
185
  expand: false,
221
186
  content: '',
222
- file: null,
223
- altText: '',
224
- ariaDescribedBy: '',
187
+ fileConfig: {},
225
188
  }
226
189
  this.block.metadata.config.items = []
227
190
  this.block.metadata.config.items.push(defaultObject)
@@ -260,9 +223,7 @@ export default {
260
223
  header: '',
261
224
  expand: false,
262
225
  content: '',
263
- file: null,
264
- altText: '',
265
- ariaDescribedBy: '',
226
+ fileConfig: {},
266
227
  }
267
228
  this.block.metadata.config.items.push(default_item)
268
229
  this.block.metadata.config.selectedPanels =
@@ -87,8 +87,8 @@
87
87
  @click:close="onRemoveElement"
88
88
  >
89
89
  <template #header="{ item }">
90
- <v-avatar v-if="item.iconImage && item.iconAsset">
91
- <v-img :src="getImagePublicUrl(item.iconAsset)" />
90
+ <v-avatar v-if="item.iconImage && item.fileConfig">
91
+ <v-img :src="getImagePublicUrl(item.fileConfig.asset)" />
92
92
  </v-avatar>
93
93
  <v-icon
94
94
  v-else-if="
@@ -146,29 +146,19 @@
146
146
  :rules="validation.iconRules"
147
147
  :disabled="render"
148
148
  ></TextIconPicker>
149
-
150
- <ContentBlockAsset
149
+ <ImageAssetSettings
151
150
  v-if="
152
151
  block.metadata.config.items[index].iconImage
153
152
  "
154
153
  v-model="
155
- block.metadata.config.items[index].iconAsset
154
+ block.metadata.config.items[index]
155
+ .fileConfig
156
156
  "
157
157
  :assets.sync="block.assets"
158
- class="mb-4"
159
- mimes="image/jpeg,image/png,image/gif"
160
- :disabled="render"
161
- outlined
162
- @click:file="onFileSelect($event, index)"
163
- >
164
- <template #title>
165
- {{
166
- $t(
167
- 'windward.core.components.settings.image.place_image'
168
- )
169
- }}
170
- </template>
171
- </ContentBlockAsset>
158
+ hide-background
159
+ hide-decorative
160
+ hide-modal
161
+ ></ImageAssetSettings>
172
162
  <v-text-field
173
163
  v-model="
174
164
  block.metadata.config.items[index].title
@@ -234,6 +224,7 @@ import TextIconPicker from '~/components/Core/TextIconPicker.vue'
234
224
  import ColorPicker from '~/components/Core/ColorPicker.vue'
235
225
  import SortableExpansionPanel from '~/components/Core/SortableExpansionPanel.vue'
236
226
  import ContentBlockAsset from '~/components/Content/ContentBlockAsset.vue'
227
+ import ImageAssetSettings from '~/components/Content/Settings/ImageAssetSettings.vue'
237
228
 
238
229
  export default {
239
230
  name: 'ClickableIconsSettings',
@@ -243,6 +234,7 @@ export default {
243
234
  TextIconPicker,
244
235
  ColorPicker,
245
236
  ContentBlockAsset,
237
+ ImageAssetSettings,
246
238
  },
247
239
  extends: BaseContentSettings,
248
240
  data() {
@@ -311,7 +303,7 @@ export default {
311
303
  onAddElement() {
312
304
  const defaultObject = {
313
305
  icon: '',
314
- iconAsset: null,
306
+ fileConfig: {},
315
307
  iconImage: false,
316
308
  title: '',
317
309
  body: '<p></p>',
@@ -336,7 +328,7 @@ export default {
336
328
  onClickToggleIconImage(index) {
337
329
  // We're switching between images / text. Clear the relevant fields
338
330
  this.block.metadata.config.items[index].icon = ''
339
- this.block.metadata.config.items[index].iconAsset = null
331
+ this.block.metadata.config.items[index].fileConfig = null
340
332
  },
341
333
  onFileSelect(file, index) {
342
334
  // file = null when you remove a file
@@ -113,7 +113,7 @@
113
113
  :disabled="render"
114
114
  @click:close="editTerm(verified)"
115
115
  >
116
- <TextViewer v-model="verified.term"></TextViewer>
116
+ <ContentViewer v-model="verified.term"></ContentViewer>
117
117
  </v-chip>
118
118
  </v-card-text>
119
119
  </v-card>
@@ -136,7 +136,9 @@
136
136
  :disabled="render"
137
137
  @click:close="addGlossaryTerm(unVerified)"
138
138
  >
139
- <TextViewer v-model="unVerified.term"></TextViewer>
139
+ <ContentViewer
140
+ v-model="unVerified.term"
141
+ ></ContentViewer>
140
142
  </v-chip>
141
143
  </v-card-text>
142
144
  </v-card>
@@ -198,18 +200,18 @@
198
200
  import { mapGetters, mapMutations } from 'vuex'
199
201
  import GlossaryHelper from '../../helpers/GlossaryHelper'
200
202
  import CourseGlossaryForm from '../utils/glossary/CourseGlossaryForm.vue'
203
+ import ContentViewer from '../utils/ContentViewer.vue'
201
204
  import DialogBox from '~/components/Core/DialogBox.vue'
202
205
  import Course from '~/models/Course'
203
206
  import BaseContentSettings from '~/components/Content/Settings/BaseContentSettings.js'
204
207
  import TextEditor from '~/components/Text/TextEditor'
205
- import TextViewer from '~/components/Text/TextViewer.vue'
206
208
  export default {
207
209
  name: 'TextEditorSettings',
208
210
  components: {
209
211
  DialogBox,
210
212
  TextEditor,
211
213
  CourseGlossaryForm,
212
- TextViewer,
214
+ ContentViewer,
213
215
  },
214
216
  extends: BaseContentSettings,
215
217
  data() {
@@ -21,7 +21,7 @@
21
21
  {{
22
22
  sourceDescription ||
23
23
  $t(
24
- 'windward.core.components.settings.video.video.configure_blurb'
24
+ 'windward.core.components.settings.video.media.configure_blurb'
25
25
  )
26
26
  }}
27
27
  </template>
@@ -146,9 +146,9 @@
146
146
  :disabled="render"
147
147
  @change:source="
148
148
  (file, rawFile) =>
149
- onAdSourceSelect(file, rawFile, 0)
149
+ onAdSourceSelect(file, rawFile, 100)
150
150
  "
151
- @change:track="onAdTrackSelect($event, 0)"
151
+ @change:track="onAdTrackSelect($event, 100)"
152
152
  ></SourcePicker>
153
153
  </v-tab-item>
154
154
  </v-tabs-items>
@@ -575,6 +575,11 @@ export default {
575
575
  return ads.length
576
576
  },
577
577
  onRemovePlaylistItem() {
578
+ // If there's still items in the playlist then decrement it down to the previous item
579
+ if (this.playlistIndex > 0) {
580
+ this.playlistPaginator--
581
+ }
582
+
578
583
  if (this.block.metadata.config.playlist.length > 1) {
579
584
  this.block.metadata.config.playlist.splice(
580
585
  this.playlistIndex,
@@ -11,7 +11,7 @@
11
11
  <label v-if="label" class="editor-label">{{ label }}</label>
12
12
  </slot>
13
13
  <Editor
14
- :id="id"
14
+ :id="editorId"
15
15
  :key="seed + (isDarkTheme ? '-theme-dark' : '-theme-light')"
16
16
  v-model="text"
17
17
  initial-value=""
@@ -121,6 +121,7 @@ export default {
121
121
  props: {
122
122
  value: { type: String, required: true, default: '' },
123
123
  id: { type: String, required: false, default: '' },
124
+ dataKey: { type: String, required: false, default: '' }, // used as a unique key for testing
124
125
  height: { type: Number, required: false, default: null },
125
126
  menubar: {
126
127
  type: String,
@@ -152,12 +153,26 @@ export default {
152
153
  computed: {
153
154
  dataCy() {
154
155
  return (
156
+ this.dataKey ||
155
157
  this.id ||
156
158
  this.label.toLowerCase().replaceAll(/[^a-z0-9]/g, '-') ||
157
159
  this.hint.toLowerCase().replaceAll(/[^a-z0-9]/g, '-') ||
158
160
  _.get(this, '$parent.$parent.$options.name', '')
159
161
  )
160
162
  },
163
+ editorId() {
164
+ // If the id is not empty then make sure it's unique
165
+ // TinyMCE fails to load if an id is duplicated. Also duplicate ids are just bad in general
166
+ if (this.id) {
167
+ const duplicates = document.querySelectorAll(`#${this.id}`)
168
+
169
+ return duplicates.length === 0
170
+ ? this.id
171
+ : this.id + '-' + this.seed
172
+ } else {
173
+ return ''
174
+ }
175
+ },
161
176
  isDarkTheme() {
162
177
  return this.$vuetify.theme.isDark
163
178
  },
@@ -194,7 +209,7 @@ export default {
194
209
  },
195
210
  autoresize_min_height: 100,
196
211
  autoresize_max_height: 1000,
197
- autoresize_bottom_margin: 0,
212
+ autoresize_bottom_margin: 1,
198
213
  plugins: [
199
214
  'autoresize',
200
215
  'advlist',
@@ -1,25 +1,25 @@
1
1
  <template>
2
2
  <div
3
+ v-click-outside="onClickOutside"
3
4
  class="glossary-word"
4
5
  :class="{ active: show }"
5
- v-click-outside="onClickOutside"
6
6
  @click="show = !show"
7
7
  >
8
8
  <v-tooltip
9
- top
10
9
  v-model="show"
10
+ top
11
11
  :open-on-hover="false"
12
12
  color="primary"
13
13
  max-width="768px"
14
14
  z-index="10"
15
15
  >
16
16
  <template #activator="{ on }">
17
- <span v-on="on">
17
+ <span tabindex="0" v-on="on">
18
18
  <slot name="term"></slot>
19
19
  </span>
20
20
  </template>
21
21
  <div>
22
- <div v-if="this.$slots['definition']">
22
+ <div v-if="$slots['definition']">
23
23
  <h6 class="text-capitalize">
24
24
  <slot name="term"></slot>
25
25
  {{
@@ -33,7 +33,7 @@
33
33
  <slot name="definition"></slot>
34
34
  </p>
35
35
  </div>
36
- <div v-if="this.$slots['alternate_forms']">
36
+ <div v-if="$slots['alternate_forms']">
37
37
  <h4 class="text-capitalize">
38
38
  <slot name="term"></slot>
39
39
  {{
@@ -46,7 +46,7 @@
46
46
  <p><slot name="alternate_forms"></slot></p>
47
47
  </div>
48
48
 
49
- <div v-if="this.$slots['related_terms']">
49
+ <div v-if="$slots['related_terms']">
50
50
  <h4 class="text-capitalize">
51
51
  {{
52
52
  $t(
@@ -1,4 +1,4 @@
1
1
  export default {
2
- not_configured_title: 'Video not configured',
2
+ not_configured_title: 'Media not configured',
3
3
  edit_prompt: 'Edit this block to get started',
4
4
  }
@@ -1,11 +1,11 @@
1
1
  export default {
2
- title: 'Video Title',
2
+ title: 'Media Title',
3
3
  sources: 'Sources',
4
4
  place_source: 'Place Video or Audio',
5
5
  playback: 'Playback',
6
6
  no_sources: 'No Sources Configured',
7
- default_filename: 'Video',
8
- playlist: 'Videos in Playlist',
7
+ default_filename: 'Media',
8
+ playlist: 'Media in Playlist',
9
9
  playlist_name: 'Name in Playlist',
10
10
  playlist_name_source_required:
11
11
  'Select a source before naming this playlist item',
@@ -16,6 +16,10 @@ export default {
16
16
  'When enabled, the selected media will use captions linked on the file, managed in the file manager. When disabled, the selected media will have its own unique captions that is not shared globally on the file.',
17
17
  inherit_missing_captions:
18
18
  'No global captions are available for this source. Please set them in the file settings',
19
+ media: {
20
+ configure_blurb:
21
+ 'Upload a media file (.mp4, .webm, .mp3, .ogg), pick one from the file manager, or add via the public URL',
22
+ },
19
23
  video: {
20
24
  title: 'Video File',
21
25
  configure_blurb:
@@ -29,7 +33,7 @@ export default {
29
33
  playback_rates: 'Playback Rates',
30
34
  rewind: 'Allow 10 Second Rewind',
31
35
  playsinline: 'Disable fullscreen and force inline viewing',
32
- captionsmenu: 'Show the interactive captions menu',
36
+ captionsmenu: 'Show the transcript menu',
33
37
  playlistmenu:
34
38
  'Show playlist menu (Requires more than 1 video selected to show)',
35
39
  playlistautoadvance: 'Auto-advance the playlist on media end',
@@ -11,7 +11,7 @@ export default {
11
11
  clickable_icons: 'Clickable Icons Settings',
12
12
  scenario_choice: 'Scenario Choice',
13
13
  accordion: 'Accordion Settings',
14
- video: 'Video Settings',
14
+ video: 'Video / Audio Settings',
15
15
  table: 'Table Settings',
16
16
  math: 'Math Settings',
17
17
  feedback: 'Feedback Settings',
@@ -1,5 +1,5 @@
1
1
  export default {
2
- not_configured_title: 'Video no configurado',
2
+ not_configured_title: 'Medios no configurados',
3
3
  edit_prompt:
4
4
  "Para comenzar a manipular el bloque,haga clic en el botón 'Editar'.",
5
5
  }
@@ -1,11 +1,11 @@
1
1
  export default {
2
- title: 'Título del vídeo',
2
+ title: 'Título del medio',
3
3
  sources: 'Fuentes',
4
4
  place_source: 'Colocar video o audio',
5
5
  playback: 'Reproducción',
6
6
  no_sources: 'No hay fuentes configuradas',
7
- default_filename: 'Vídeo',
8
- playlist: 'Vídeos en lista de reproducción',
7
+ default_filename: 'Medios de comunicación',
8
+ playlist: 'Medios en lista de reproducción',
9
9
  playlist_name: 'Nombre en lista de reproducción',
10
10
  playlist_name_source_required:
11
11
  'Seleccione una fuente antes de nombrar este elemento de la lista de reproducción',
@@ -16,6 +16,10 @@ export default {
16
16
  'Cuando está habilitado, el contenido multimedia seleccionado utilizará subtítulos vinculados al archivo, administrados en el administrador de archivos. Cuando está deshabilitado, el contenido multimedia seleccionado tendrá sus propios subtítulos exclusivos que no se comparten globalmente en el archivo.',
17
17
  inherit_missing_captions:
18
18
  'No hay subtítulos globales disponibles para esta fuente. Establézcalos en la configuración del archivo',
19
+ media: {
20
+ configure_blurb:
21
+ 'Sube un archivo multimedia (.mp4, .webm, .mp3, .ogg), elige uno del administrador de archivos o agrégalo a través de la URL pública',
22
+ },
19
23
  video: {
20
24
  title: 'Archivo de vídeo',
21
25
  configure_blurb:
@@ -30,7 +34,7 @@ export default {
30
34
  rewind: 'Permitir rebobinado de 10 segundos',
31
35
  playsinline:
32
36
  'Deshabilitar pantalla completa y forzar visualización en línea',
33
- captionsmenu: 'Mostrar el interactivo menú de subtítulos',
37
+ captionsmenu: 'Mostrar el menú de transcripción',
34
38
  playlistmenu:
35
39
  'Mostrar menú de lista de reproducción (requiere más de 1 video seleccionado para mostrar)',
36
40
  playlistautoadvance:
@@ -13,7 +13,7 @@ export default {
13
13
  'Configuración de iconos en los que se puede hacer clic',
14
14
  scenario_choice: 'Elección de escenario',
15
15
  accordion: 'Configuración de acordeón',
16
- video: 'Configuración de vídeo',
16
+ video: 'Configuración de video/audio',
17
17
  table: 'Configuración de la tabla',
18
18
  math: 'Configuración matemática',
19
19
  feedback: 'Configuración de comentarios',
@@ -1,4 +1,4 @@
1
1
  export default {
2
- not_configured_title: 'Video inte konfigurerad',
2
+ not_configured_title: 'Media inte konfigurerad',
3
3
  edit_prompt: 'Redigera detta block för att komma igång',
4
4
  }
@@ -1,11 +1,11 @@
1
1
  export default {
2
- title: 'Videotitel',
2
+ title: 'Media Titel',
3
3
  sources: 'Källor',
4
4
  place_source: 'Placera video eller ljud',
5
5
  playback: 'Uppspelning',
6
6
  no_sources: 'Inga källor konfigurerade',
7
- default_filename: 'Video',
8
- playlist: 'Videos in Playlist',
7
+ default_filename: 'Media',
8
+ playlist: 'Media i spellistan',
9
9
  playlist_name: 'Namn i spellista',
10
10
  playlist_name_source_required:
11
11
  'Välj en källa innan du namnger detta spellistaobjekt',
@@ -16,6 +16,10 @@ export default {
16
16
  'När det är aktiverat kommer det valda mediet att använda bildtexter länkade på filen, hanterade i filhanteraren. När det är inaktiverat kommer det valda mediet att ha sina egna unika bildtexter som inte delas globalt på filen.',
17
17
  inherit_missing_captions:
18
18
  'Inga globala bildtexter är tillgängliga för den här källan. Ange dem i filinställningarna',
19
+ media: {
20
+ configure_blurb:
21
+ 'Ladda upp en mediefil (.mp4, .webm, .mp3, .ogg), välj en från filhanteraren eller lägg till via den offentliga webbadressen',
22
+ },
19
23
  video: {
20
24
  title: 'Videofil',
21
25
  configure_blurb:
@@ -29,7 +33,7 @@ export default {
29
33
  playback_rates: 'Uppspelningshastigheter',
30
34
  rewind: 'Tillåt 10 sekunders spola tillbaka',
31
35
  playsinline: 'Inaktivera helskärm och tvinga inline-visning',
32
- captionsmenu: 'Visa det interaktiva bildtextmeny',
36
+ captionsmenu: 'Visa avskriftsmenyn',
33
37
  playlistmenu:
34
38
  'Visa spellistameny (kräver mer än 1 video vald för att visa)',
35
39
  playlistautoadvance: 'Avancera spellistan automatiskt på mediaänden',
@@ -11,7 +11,7 @@ export default {
11
11
  clickable_icons: 'Inställningar för klickbara ikoner',
12
12
  scenario_choice: 'Scenarioval',
13
13
  accordion: 'Accordion Settings',
14
- video: 'Videoinställningar',
14
+ video: 'Video/ljudinställningar',
15
15
  table: 'Tabellinställningar',
16
16
  math: 'Matematiska inställningar',
17
17
  feedback: 'Feedback-inställningar',
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@windward/core",
3
- "version": "0.9.1",
3
+ "version": "0.10.0",
4
4
  "description": "Windward UI Core Plugins",
5
5
  "main": "plugin.js",
6
6
  "scripts": {
@@ -21,7 +21,7 @@
21
21
  "license": "MIT",
22
22
  "homepage": "https://bitbucket.org/mindedge/windward-ui-plugin-core#readme",
23
23
  "dependencies": {
24
- "@mindedge/vuetify-player": "^0.3.1",
24
+ "@mindedge/vuetify-player": "^0.4.1",
25
25
  "@tinymce/tinymce-vue": "^3.2.8",
26
26
  "accessibility-scanner": "^0.0.1",
27
27
  "eslint": "^8.11.0",
@@ -2,7 +2,7 @@
2
2
  <v-row justify="center" align="center">
3
3
  <v-col cols="12">
4
4
  <div class="d-flex mb-5">
5
- <h2 class="mr-auto flex-grow-1">
5
+ <h2 class="mr-auto flex-grow-1" tabindex="0">
6
6
  {{ $t('windward.core.pages.glossary.title') }}
7
7
  </h2>
8
8
  </div>
@@ -31,17 +31,13 @@ describe('AccordionSettings', () => {
31
31
  header: '',
32
32
  expand: false,
33
33
  content: '',
34
- file: null,
35
- altText: '',
36
- ariaDescribedBy: '',
34
+ fileConfig: {},
37
35
  },
38
36
  {
39
37
  header: '',
40
38
  expand: false,
41
39
  content: '',
42
- file: null,
43
- altText: '',
44
- ariaDescribedBy: '',
40
+ fileConfig: {},
45
41
  },
46
42
  ])
47
43
  })
@@ -17,4 +17,49 @@ describe('ClickableIconsSettings', () => {
17
17
  })
18
18
  expect(wrapper.vm).toBeTruthy()
19
19
  })
20
+
21
+ test('can add an clickable icon', () => {
22
+ const wrapper = shallowMount(ClickableIconsSettings, {
23
+ propsData: {
24
+ tag: 'core-clickable-icons-settings',
25
+ },
26
+ mocks: defaultMocks,
27
+ })
28
+ wrapper.vm.onAddElement()
29
+ expect(wrapper.vm.$data.block.metadata.config.items).toEqual([
30
+ {
31
+ icon: '',
32
+ fileConfig: {},
33
+ iconImage: false,
34
+ title: '',
35
+ body: '<p></p>',
36
+ color: {
37
+ class: '',
38
+ },
39
+ active: false,
40
+ },
41
+ {
42
+ icon: '',
43
+ fileConfig: {},
44
+ iconImage: false,
45
+ title: '',
46
+ body: '<p></p>',
47
+ color: {
48
+ class: '',
49
+ },
50
+ active: false,
51
+ },
52
+ ])
53
+ })
54
+
55
+ test('can remove an clickable icon', () => {
56
+ const wrapper = shallowMount(ClickableIconsSettings, {
57
+ propsData: {
58
+ tag: 'core-clickable-icons-settings',
59
+ },
60
+ mocks: defaultMocks,
61
+ })
62
+ wrapper.vm.onRemoveElement(0)
63
+ expect(wrapper.vm.$data.block.metadata.config.items).toEqual([])
64
+ })
20
65
  })
@@ -70,6 +70,10 @@ class mockBaseModel extends mockModel {
70
70
  })
71
71
  }
72
72
 
73
+ getPreference() {
74
+ return null
75
+ }
76
+
73
77
  integrations() {
74
78
  return this
75
79
  }