/** @module */
'use strict';
var ParsoidExtApi = module.parent.parent.require('./extapi.js').versionCheck('^0.11.0');
const { DOMDataUtils, DOMUtils, JSUtils, Util } = ParsoidExtApi;
/**
* @class
*/
class Traditional {
constructor() {
this.mode = 'traditional';
this.scale = 1;
this.padding = { thumb: 30, box: 5, border: 8 };
}
MODE() { return this.mode; }
SCALE() { return this.scale; }
PADDING() { return this.padding; }
appendAttr(ul, k, v) {
var val = ul.getAttribute(k) || '';
if (val) { val += ' '; }
ul.setAttribute(k, val + v);
}
ul(opts, doc) {
var ul = doc.createElement('ul');
var cl = 'gallery mw-gallery-' + this.MODE();
ul.setAttribute('class', cl);
Object.keys(opts.attrs).forEach((k) => {
this.appendAttr(ul, k, opts.attrs[k]);
});
doc.body.appendChild(ul);
this.perRow(opts, ul);
this.setAdditionalOptions(opts, ul);
return ul;
}
perRow(opts, ul) {
if (opts.imagesPerRow > 0) {
var padding = this.PADDING();
var total = opts.imageWidth + padding.thumb + padding.box + padding.border;
total *= opts.imagesPerRow;
this.appendAttr(ul, 'style', [
'max-width: ' + total + 'px;',
'_width: ' + total + 'px;',
].join(' '));
}
}
setAdditionalOptions(opts, ul) {}
caption(opts, doc, ul, caption) {
var li = doc.createElement('li');
li.setAttribute('class', 'gallerycaption');
DOMUtils.migrateChildrenBetweenDocs(caption, li);
li.setAttribute('data-parsoid', caption.getAttribute('data-parsoid'));
// The data-mw attribute *shouldn't* exist, since this caption
// should be a <body>. But let's be safe and copy it anyway.
li.setAttribute('data-mw', caption.getAttribute('data-mw'));
ul.appendChild(doc.createTextNode('\n'));
ul.appendChild(li);
}
dimensions(opts) {
return `${opts.imageWidth}x${opts.imageHeight}px`;
}
scaleMedia(opts, wrapper) {
return opts.imageWidth;
}
thumbWidth(width) {
return width + this.PADDING().thumb;
}
thumbHeight(height) {
return height + this.PADDING().thumb;
}
thumbStyle(width, height) {
var style = [`width: ${this.thumbWidth(width)}px;`];
if (this.MODE() === 'traditional') {
style.push(`height: ${this.thumbHeight(height)}px;`);
}
return style.join(' ');
}
boxWidth(width) {
return this.thumbWidth(width) + this.PADDING().box;
}
boxStyle(width, height) {
return `width: ${this.boxWidth(width)}px;`;
}
galleryText(doc, box, gallerytext, width) {
var div = doc.createElement('div');
div.setAttribute('class', 'gallerytext');
if (gallerytext) {
DOMUtils.migrateChildrenBetweenDocs(gallerytext, div);
div.setAttribute('data-parsoid', gallerytext.getAttribute('data-parsoid'));
// The data-mw attribute *shouldn't* exist, since this gallerytext
// should be a <figcaption>. But let's be safe and copy it anyway.
div.setAttribute('data-mw', gallerytext.getAttribute('data-mw'));
}
box.appendChild(div);
}
line(opts, doc, ul, o) {
var width = this.scaleMedia(opts, o.thumb);
var height = opts.imageHeight;
var box = doc.createElement('li');
box.setAttribute('class', 'gallerybox');
box.setAttribute('style', this.boxStyle(width, height));
var thumb = doc.createElement('div');
thumb.setAttribute('class', 'thumb');
thumb.setAttribute('style', this.thumbStyle(width, height));
var wrapper = doc.createElement('figure-inline');
wrapper.setAttribute('typeof', o.rdfaType);
DOMDataUtils.setDataParsoid(wrapper, Util.clone(DOMDataUtils.getDataParsoid(o.thumb)));
DOMDataUtils.setDataMw(wrapper, Util.clone(DOMDataUtils.getDataMw(o.thumb)));
// Store temporarily, otherwise these get clobbered after rendering by
// the call to `DOMDataUtils.visitAndLoadDataAttribs()` in `toDOM`.
DOMDataUtils.storeDataAttribs(wrapper);
DOMUtils.migrateChildrenBetweenDocs(o.thumb, wrapper);
thumb.appendChild(wrapper);
box.appendChild(thumb);
this.galleryText(doc, box, o.gallerytext, width);
ul.appendChild(doc.createTextNode('\n'));
ul.appendChild(box);
}
render(env, opts, caption, lines) {
var doc = env.createDocument();
var ul = this.ul(opts, doc);
if (caption) {
this.caption(opts, doc, ul, caption);
}
lines.forEach(l => this.line(opts, doc, ul, l));
ul.appendChild(doc.createTextNode('\n'));
return doc;
}
}
/**
* @class
* @extends ~Traditional
*/
class NoLines extends Traditional {
constructor() {
super();
this.mode = 'nolines';
this.padding = { thumb: 0, box: 5, border: 4 };
}
}
/**
* @class
* @extends ~Traditional
*/
class Slideshow extends Traditional {
constructor() {
super();
this.mode = 'slideshow';
}
setAdditionalOptions(opts, ul) {
ul.setAttribute('data-showthumbnails', opts.showthumbnails ? "1" : "");
}
perRow() {}
}
/**
* @class
* @extends ~Traditional
*/
class Packed extends Traditional {
constructor() {
super();
this.mode = 'packed';
this.scale = 1.5;
this.padding = { thumb: 0, box: 2, border: 8 };
}
perRow() {}
dimensions(opts) {
return `x${Math.ceil(opts.imageHeight * this.SCALE())}px`;
}
scaleMedia(opts, wrapper) {
var elt = wrapper.firstChild.firstChild;
var width = parseInt(elt.getAttribute('width'), 10);
if (Number.isNaN(width)) {
width = opts.imageWidth;
} else {
width /= this.SCALE();
}
elt.setAttribute('width', Math.ceil(width));
elt.setAttribute('height', opts.imageHeight);
return width;
}
galleryText(doc, box, gallerytext, width) {
if (!/packed-(hover|overlay)/.test(this.MODE())) {
Traditional.prototype.galleryText.call(this, doc, box, gallerytext, width);
return;
}
if (!gallerytext) {
return;
}
var div = doc.createElement('div');
div.setAttribute('class', 'gallerytext');
DOMUtils.migrateChildrenBetweenDocs(gallerytext, div);
div.setAttribute('data-parsoid', gallerytext.getAttribute('data-parsoid'));
// The data-mw attribute *shouldn't* exist, since this gallerytext
// should be a <figcaption>. But let's be safe and copy it anyway.
div.setAttribute('data-mw', gallerytext.getAttribute('data-mw'));
var wrapper = doc.createElement('div');
wrapper.setAttribute('class', 'gallerytextwrapper');
wrapper.setAttribute('style', `width: ${Math.ceil(width - 20)}px;`);
wrapper.appendChild(div);
box.appendChild(wrapper);
}
}
/**
* @class
* @extends ~Packed
*/
class PackedHover extends Packed {
constructor() {
super();
this.mode = 'packed-hover';
}
}
/**
* @class
* @extends ~Packed
*/
class PackedOverlay extends Packed {
constructor() {
super();
this.mode = 'packed-overlay';
}
}
/** @namespace */
var modes = JSUtils.mapObject({
traditional: new Traditional(),
nolines: new NoLines(),
slideshow: new Slideshow(),
packed: new Packed(),
'packed-hover': new PackedHover(),
'packed-overlay': new PackedOverlay(),
});
if (typeof module === 'object') {
module.exports = modes;
}