Proyectos de Subversion Moodle

Rev

| Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
/* global ns */
2
/**
3
 * Construct a library selector.
4
 *
5
 * @param {Array} libraries
6
 * @param {String} defaultLibrary
7
 * @param {Object} defaultParams
8
 * @returns {ns.LibrarySelector}
9
 */
10
ns.LibrarySelector = function (libraries, defaultLibrary, defaultParams) {
11
  var that = this;
12
 
13
  this.libraries = libraries;
14
 
15
  H5P.EventDispatcher.call(this);
16
 
17
  try {
18
    this.defaultParams = JSON.parse(defaultParams);
19
    if (!(this.defaultParams instanceof Object)) {
20
      throw true;
21
    }
22
  }
23
  catch (event) {
24
    // Content parameters are broken. Reset. (This allows for broken content to be reused without deleting it)
25
    this.defaultParams = {};
26
  }
27
 
28
  this.defaultLibrary = this.currentLibrary = defaultLibrary;
29
  this.defaultLibraryParameterized = defaultLibrary ? defaultLibrary.replace('.', '-').toLowerCase() : undefined;
30
 
31
  //Add tutorial and example link:
32
  this.$tutorialUrl = ns.$(
33
    '<a class="h5p-tutorial-url" target="_blank">' +
34
      '<span class="h5p-tutorial-url-label">' +
35
        ns.t('core', 'tutorial') +
36
      '</span>' +
37
    '</a>'
38
  ).hide();
39
  this.$exampleUrl = ns.$(
40
    '<a class="h5p-example-url" target="_blank">' +
41
      '<span class="h5p-example-url-label">' +
42
        ns.t('core', 'example') +
43
      '</span>' +
44
    '</a>'
45
  ).hide();
46
 
47
  // Create confirm dialog
48
  var changeLibraryDialog = new H5P.ConfirmationDialog({
49
    headerText: H5PEditor.t('core', 'changeLibrary'),
50
    dialogText: H5PEditor.t('core', 'confirmChangeLibrary')
51
  }).appendTo(document.body);
52
 
53
  if (H5PIntegration.hubIsEnabled) {
54
    this.selector = new ns.SelectorHub(libraries, defaultLibrary, changeLibraryDialog);
55
  }
56
  else {
57
    this.selector = new ns.SelectorLegacy(libraries, defaultLibrary, changeLibraryDialog);
58
  }
59
 
60
  this.$selector = ns.$(this.selector.getElement());
61
 
62
  /**
63
   * @private
64
   * @param {object} library
65
   */
66
  var librarySelectHandler = function (library) {
67
    that.currentLibrary = library.uberName;
68
    that.loadSemantics(library.uberName, that.selector.getParams(), that.selector.getMetadata());
69
 
70
    that.$tutorialUrl.attr('href', library.tutorialUrl ? library.tutorialUrl : '#').toggle(!!library.tutorialUrl);
71
    that.$exampleUrl.attr('href', library.exampleUrl ? library.exampleUrl : '#').toggle(!!library.exampleUrl);
72
  };
73
 
74
  /**
75
   * Event handler for loading a new library editor
76
   * @private
77
   */
78
  var loadLibrary = function () {
79
    that.trigger('editorload', that.selector.currentLibrary);
80
    that.selector.getSelectedLibrary(librarySelectHandler);
81
  };
82
 
83
  /**
84
   * Confirm replace if there is content selected
85
   *
86
   * @param {number} top Offset
87
   * @param {function} next Next callback
88
   */
89
  this.confirmPasteError = function (message, top, next) {
90
    // Confirm changing library
91
    var confirmReplace = new H5P.ConfirmationDialog({
92
      headerText: H5PEditor.t('core', 'pasteError'),
93
      dialogText: message,
94
      cancelText: ' ',
95
      confirmText: H5PEditor.t('core', 'ok')
96
    }).appendTo(document.body);
97
    confirmReplace.on('confirmed', next);
98
    confirmReplace.show(top);
99
  };
100
 
101
  // Change library on confirmation
102
  changeLibraryDialog.on('confirmed', loadLibrary);
103
 
104
  // Revert selector on cancel
105
  changeLibraryDialog.on('canceled', function () {
106
    that.selector.resetSelection(that.currentLibrary, that.defaultParams, that.form.metadata, true);
107
  });
108
 
109
  // First time a library is selected in the editor
110
  this.selector.on('selected', loadLibrary);
111
 
112
  this.selector.on('resize', function () {
113
    that.trigger('resize');
114
  });
115
 
116
  this.on('select', loadLibrary);
117
  H5P.externalDispatcher.on('datainclipboard', this.updateCopyPasteButtons.bind(this));
118
  this.selector.on('paste', this.pasteContent.bind(this));
119
};
120
 
121
// Extends the event dispatcher
122
ns.LibrarySelector.prototype = Object.create(H5P.EventDispatcher.prototype);
123
ns.LibrarySelector.prototype.constructor = ns.LibrarySelector;
124
 
125
/**
126
 * Sets the current library
127
 *
128
 * @param {string} library
129
 */
130
ns.LibrarySelector.prototype.setLibrary = function (library) {
131
  this.trigger('select');
132
};
133
 
134
/**
135
 * Append the selector html to the given container.
136
 *
137
 * @param {jQuery} $element
138
 * @returns {undefined}
139
 */
140
ns.LibrarySelector.prototype.appendTo = function ($element) {
141
  var self = this;
142
  this.$parent = $element;
143
 
144
  this.$selector.appendTo($element);
145
  this.$tutorialUrl.appendTo($element);
146
  this.$exampleUrl.appendTo($element);
147
 
148
  if (window.localStorage) {
149
    var $buttons = ns.$(ns.createCopyPasteButtons()).appendTo($element);
150
 
151
    // Hide copy paste until library is selected:
152
    $buttons.addClass('hidden');
153
    self.on('editorloaded', function () {
154
      $buttons.removeClass('hidden');
155
    });
156
 
157
    this.$copyButton = $buttons.find('.h5peditor-copy-button').click(function () {
158
      H5P.clipboardify({
159
        library: self.getCurrentLibrary(),
160
        params: self.getParams(),
161
        metadata: self.getMetadata()
162
      });
163
      ns.attachToastTo(
164
        self.$copyButton.get(0),
165
        H5PEditor.t('core', 'copiedToClipboard'), {
166
          position: {
167
            horizontal: 'center',
168
            vertical: 'above',
169
            noOverflowX: true
170
          }
171
        }
172
      );
173
    });
174
    this.$pasteButton = $buttons.find('.h5peditor-paste-button')
175
      .click(self.pasteContent.bind(this));
176
 
177
    self.updateCopyPasteButtons();
178
  }
179
};
180
 
181
/**
182
 * Update state of copy and paste buttons dependent on what is currently in
183
 * the clipboard
184
 */
185
ns.LibrarySelector.prototype.updateCopyPasteButtons = function () {
186
  if (!window.localStorage) {
187
    return;
188
  }
189
 
190
  // Check if content type is supported here
191
  const pasteCheck = ns.canPastePlus(H5P.getClipboard(), this.libraries);
192
  const canPaste = pasteCheck.canPaste;
193
 
194
  this.$copyButton
195
    .prop('disabled', false)
196
    .toggleClass('disabled', false);
197
 
198
  this.$pasteButton
199
    .text(ns.t('core', 'pasteAndReplaceButton'))
200
    .attr('title', canPaste ? ns.t('core', 'pasteAndReplaceFromClipboard') : pasteCheck.description)
201
    .toggleClass('disabled', !canPaste)
202
    .prop('disabled', !canPaste);
203
 
204
  this.selector.setCanPaste && this.selector.setCanPaste(canPaste, !canPaste ? pasteCheck.description : undefined);
205
};
206
 
207
/**
208
 * Sets the current library
209
 *
210
 * @param {string} library
211
 */
212
ns.LibrarySelector.prototype.pasteContent = function () {
213
  var self = this;
214
  var clipboard = H5P.getClipboard();
215
 
216
  ns.confirmReplace(self.getCurrentLibrary(), self.$parent.offset().top, function () {
217
    self.selector.resetSelection(clipboard.generic.library, clipboard.generic.params, clipboard.generic.metadata, false);
218
    self.setLibrary();
219
  });
220
};
221
 
222
/**
223
 * Display loading message and load library semantics.
224
 *
225
 * @param {String} library
226
 * @param {Object} params Pass in params to semantics
227
 * @returns {unresolved}
228
 */
229
ns.LibrarySelector.prototype.loadSemantics = function (library, params, metadata) {
230
  var that = this;
231
 
232
  if (this.form !== undefined) {
233
    // Remove old form.
234
    this.form.remove();
235
  }
236
 
237
  if (library === '-') {
238
    // No library chosen.
239
    this.$parent.attr('class', 'h5peditor');
240
    return;
241
  }
242
  this.$parent.attr('class', 'h5peditor ' + library.split(' ')[0].toLowerCase().replace('.', '-') + '-editor');
243
 
244
  // Display loading message
245
  var $loading = ns.$('<div class="h5peditor-loading h5p-throbber">' + ns.t('core', 'loading') + '</div>').appendTo(this.$parent);
246
 
247
  this.$selector.attr('disabled', true);
248
 
249
  ns.resetLoadedLibraries();
250
  ns.loadLibrary(library, function (semantics) {
251
    if (!semantics) {
252
      that.form = ns.$('<div/>', {
253
        'class': 'h5p-errors',
254
        text: H5PEditor.t('core', 'noSemantics'),
255
        insertAfter: $loading
256
      });
257
    }
258
    else {
259
      var overrideParams = {};
260
      if (params) {
261
        overrideParams = params;
262
        that.defaultParams = overrideParams;
263
      }
264
      else if (library === that.defaultLibrary || library === that.defaultLibraryParameterized) {
265
        overrideParams = that.defaultParams;
266
      }
267
 
268
      if (!metadata) {
269
        metadata = overrideParams.metadata;
270
      }
271
      const defaultLanguage = metadata && metadata.defaultLanguage
272
        ? metadata.defaultLanguage
273
        : null;
274
      that.form = new ns.Form(
275
        library,
276
        ns.libraryCache[library].languages,
277
        defaultLanguage
278
      );
279
      that.form.replace($loading);
280
      that.form.currentLibrary = library;
281
      that.form.processSemantics(semantics, overrideParams, metadata);
282
      that.updateCopyPasteButtons();
283
    }
284
 
285
    that.$selector.attr('disabled', false);
286
    $loading.remove();
287
    that.trigger('editorloaded', library);
288
  });
289
};
290
 
291
/**
292
 * Returns currently selected library
293
 *
294
 * @returns {string} Currently selected library
295
 */
296
ns.LibrarySelector.prototype.getCurrentLibrary = function () {
297
  return this.currentLibrary;
298
};
299
 
300
/**
301
 * Return params needed to start library.
302
 */
303
ns.LibrarySelector.prototype.getParams = function () {
304
  if (this.form === undefined) {
305
    return;
306
  }
307
 
308
  // Only return if all fields has validated.
309
  //var valid = true;
310
 
311
  if (this.form.metadataForm.children !== undefined) {
312
    for (var i = 0; i < this.form.metadataForm.children.length; i++) {
313
      if (this.form.metadataForm.children[i].validate() === false) {
314
        //valid = false;
315
      }
316
    }
317
  }
318
 
319
  if (this.form.children !== undefined) {
320
    for (var i = 0; i < this.form.children.length; i++) {
321
      if (this.form.children[i].validate() === false) {
322
        //valid = false;
323
      }
324
    }
325
  }
326
 
327
  //return valid ? this.form.params : false;
328
  return this.form.params; // TODO: Switch to the line above when we are able to tell the user where the validation fails
329
};
330
 
331
/**
332
 * Get the metadata of the main form.
333
 *
334
 * @return {object} Metadata object.
335
 */
336
ns.LibrarySelector.prototype.getMetadata = function () {
337
  if (this.form === undefined) {
338
    return;
339
  }
340
 
341
  return this.form.metadata;
342
};
343
 
344
/**
345
 *
346
 * @param content
347
 * @param library
348
 * @returns {H5PEditor.Presave} Result after processing library and content
349
 */
350
ns.LibrarySelector.prototype.presave = function (content, library) {
351
  return (new ns.Presave).process(library, content);
352
};