diff --git a/dist/photoviewer.common.js b/dist/photoviewer.common.js
index fd0be02..dcabdbd 100644
--- a/dist/photoviewer.common.js
+++ b/dist/photoviewer.common.js
@@ -5,7 +5,7 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
@@ -1263,6 +1263,7 @@ function fadeIn(speed, callback) {
var methods = {
isPlainObject: isPlainObject,
isArray: isArray,
+ isFunction: isFunction,
noop: noop
};
var fnMethods = {
@@ -1390,7 +1391,9 @@ var DEFAULTS = {
// Whether to set modal css `position: fixed`
positionFixed: true,
// Init modal position `{top: 0, right: 0, bottom: 0, left: 0}`
- initModalPos: null
+ initModalPos: null,
+ // Error message when image could not be loaded
+ errorMsg: ''
};
var document = window.document;
@@ -2003,6 +2006,8 @@ var PhotoViewer = /*#__PURE__*/function () {
left: null,
top: null
});
+ // Store previous index
+ _defineProperty(this, "prevIndex", null);
// Used for time comparison
_defineProperty(this, "_lastTimestamp", 0);
this.init(items, options);
@@ -2059,7 +2064,7 @@ var PhotoViewer = /*#__PURE__*/function () {
key: "_createTemplate",
value: function _createTemplate() {
var photoviewerHTML = "
\n
\n
\n
\n ").concat(this._createBtns(this.options.headerToolbar), "\n
\n ").concat(this._createTitle(), "\n
\n
\n
\n
\n
\n
\n ").concat(this._createBtns(this.options.footerToolbar), "\n
\n
\n
\n
");
- return photoviewerHTML;
+ return photoviewerHTML.replace(/>\s+<');
}
}, {
key: "_build",
@@ -2087,10 +2092,6 @@ var PhotoViewer = /*#__PURE__*/function () {
this.$prev = $photoviewer.find(CLASS_NS + '-button-prev');
this.$next = $photoviewer.find(CLASS_NS + '-button-next');
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
-
// Reset the modal `z-index` of multiple instances
this.$photoviewer.css('z-index', PUBLIC_VARS['zIndex']);
if (this.options.positionFixed) {
@@ -2307,44 +2308,51 @@ var PhotoViewer = /*#__PURE__*/function () {
if (!this.imageLoaded) {
// Loader end
this.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Remove init classes after image loaded
- this.$stage.removeClass('stage-ready');
- this.$image.removeClass('image-ready');
+ // The class must be removed after image loaded
+ this.$stage.removeClass(NS + '-align-center');
// Add init animation for image
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.fadeIn();
}
this.imageLoaded = true;
+ this._triggerHook('changed', [this, this.index]);
}
}
}, {
key: "_loadImage",
- value: function _loadImage(index, fn, err) {
+ value: function _loadImage(index) {
var _this$images$index,
+ _this$images$index2,
_this4 = this;
- var imgSrc = (_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src;
- if (!imgSrc) {
- return;
- }
+ // Flag for both image loaded and animation finished
+ this.imageLoaded = false;
+ this._triggerHook('beforeChange', [this, this.prevIndex]);
+ this._removeErrorMsg();
- // Reset the image src
+ // Reset the image src and rotation status
this.$image.removeAttr('style').attr('src', '');
this.isRotated = false;
this.rotationDegree = 0;
- this.imageLoaded = false;
// Loader start
this.$photoviewer.append(""));
-
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
+ // Used for centering image
+ this.$stage.addClass(NS + '-align-center');
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.hide();
}
+
+ // The image src must be a string
+ var imgSrc = ((_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src) == null ? '' : this.images[index].src.toString();
+
+ // Get image with src
this.$image.attr('src', imgSrc);
+ var title = ((_this$images$index2 = this.images[index]) === null || _this$images$index2 === void 0 ? void 0 : _this$images$index2.title) || getImageNameFromUrl(imgSrc);
+ if (this.options.title) {
+ this.$title.html(title);
+ }
+ this.$image.attr('alt', title);
preloadImage(imgSrc, function (img) {
// Store the original image size
_this4.imageData = {
@@ -2356,59 +2364,49 @@ var PhotoViewer = /*#__PURE__*/function () {
} else {
_this4._setModalSize();
}
-
- // Callback of the image loaded successfully
- if (fn) {
- fn.call();
- }
}, function () {
// Loader end
_this4.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Callback of the image loading failed
- if (err) {
- err.call();
- }
+ _this4._triggerHook('changed', [_this4, index]);
+ _this4._setErrorMsg();
});
- if (this.options.title && imgSrc) {
- this._setImageTitle(imgSrc);
+ }
+ }, {
+ key: "_setErrorMsg",
+ value: function _setErrorMsg() {
+ var errorMsg = D.isFunction(this.options.errorMsg) ? this.options.errorMsg(this, this.index) : this.options.errorMsg;
+ if (errorMsg) {
+ this.$stage.append("").concat(errorMsg, ""));
+ this.$image.addClass(NS + '-image-error');
}
}
}, {
- key: "_setImageTitle",
- value: function _setImageTitle(url) {
- var title = this.images[this.index].title || getImageNameFromUrl(url);
- this.$title.html(title);
+ key: "_removeErrorMsg",
+ value: function _removeErrorMsg() {
+ this.$stage.find(CLASS_NS + '-error-msg').remove();
+ this.$image.removeClass(NS + '-image-error');
}
}, {
key: "jump",
value: function jump(step) {
- this._triggerHook('beforeChange', [this, this.index]);
-
- // Only allow to change image after the modal animation has finished
+ // Allow to change image only after the modal animation has finished
var now = Date.now();
if (now - this._lastTimestamp >= this.options.animationDuration) {
- this.index = this.index + step;
- this.jumpTo(this.index);
+ var newIndex = this.index + step;
+ this.jumpTo(newIndex);
this._lastTimestamp = now;
}
}
}, {
key: "jumpTo",
value: function jumpTo(index) {
- var _this5 = this;
- index = index % this.images.length;
- if (index >= 0) {
- index = index % this.images.length;
- } else if (index < 0) {
- index = (this.images.length + index) % this.images.length;
+ this.prevIndex = this.index;
+ var newIndex = index % this.images.length;
+ if (newIndex <= 0) {
+ newIndex = (newIndex + this.images.length) % this.images.length;
}
- this.index = index;
- this._loadImage(index, function () {
- _this5._triggerHook('changed', [_this5, index]);
- }, function () {
- _this5._triggerHook('changed', [_this5, index]);
- });
+ this.index = newIndex;
+ this._loadImage(this.index);
}
}, {
key: "_wheel",
@@ -2699,54 +2697,54 @@ var PhotoViewer = /*#__PURE__*/function () {
}, {
key: "_addEvents",
value: function _addEvents() {
- var _this6 = this;
+ var _this5 = this;
this.$close.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.close();
+ _this5.close();
});
this.$stage.on(WHEEL_EVENT + EVENT_NS, function (e) {
- _this6._wheel(e);
+ _this5._wheel(e);
});
this.$zoomIn.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(_this6.options.ratioThreshold * 3);
+ _this5.zoom(_this5.options.ratioThreshold * 3);
});
this.$zoomOut.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(-_this6.options.ratioThreshold * 3);
+ _this5.zoom(-_this5.options.ratioThreshold * 3);
});
this.$actualSize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoomTo(1);
+ _this5.zoomTo(1);
});
this.$prev.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(-1);
+ _this5.jump(-1);
});
this.$next.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(1);
+ _this5.jump(1);
});
this.$rotateLeft.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(-90);
+ _this5.rotate(-90);
});
this.$rotateRight.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(90);
+ _this5.rotate(90);
});
this.$maximize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.toggleMaximize();
+ _this5.toggleMaximize();
});
this.$fullscreen.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.fullscreen();
+ _this5.fullscreen();
});
this.$photoviewer.on(KEYDOWN_EVENT + EVENT_NS, function (e) {
- _this6._keydown(e);
+ _this5._keydown(e);
});
$W.on(RESIZE_EVENT + EVENT_NS, debounce(function () {
- return _this6.resize();
+ return _this5.resize();
}, 500));
}
}, {
key: "_addCustomButtonEvents",
value: function _addCustomButtonEvents() {
- var _this7 = this;
+ var _this6 = this;
var _loop = function _loop(btnKey) {
- _this7.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
- _this7.options.customButtons[btnKey].click.apply(_this7, [_this7, e]);
+ _this6.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
+ _this6.options.customButtons[btnKey].click.apply(_this6, [_this6, e]);
});
};
for (var btnKey in this.options.customButtons) {
diff --git a/dist/photoviewer.css b/dist/photoviewer.css
index 1d7ee7c..b9f4da7 100644
--- a/dist/photoviewer.css
+++ b/dist/photoviewer.css
@@ -5,7 +5,7 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
@@ -133,17 +133,6 @@
background-color: #fff;
overflow: hidden;
}
-.photoviewer-stage.stage-ready {
- text-align: center;
- font-size: 0;
-}
-.photoviewer-stage.stage-ready::before {
- content: "";
- display: inline-block;
- height: 100%;
- vertical-align: middle;
- overflow: hidden;
-}
.photoviewer-image {
position: absolute;
@@ -151,12 +140,6 @@
min-width: auto;
max-width: none;
}
-.photoviewer-image.image-ready {
- position: static;
- max-width: 100%;
- max-height: 100%;
- vertical-align: middle;
-}
.photoviewer-footer {
position: absolute;
@@ -167,6 +150,31 @@
text-align: center;
}
+.photoviewer-align-center {
+ text-align: center;
+}
+.photoviewer-align-center::before {
+ content: "";
+ display: inline-block;
+ height: 100%;
+ vertical-align: middle;
+ overflow: hidden;
+}
+.photoviewer-align-center .photoviewer-image {
+ position: static;
+ max-width: 100%;
+ max-height: 100%;
+ vertical-align: middle;
+}
+
+.photoviewer-image-error {
+ display: none;
+}
+
+.photoviewer-error-msg {
+ vertical-align: middle;
+}
+
[dir=rtl] .photoviewer-button-prev,
[dir=rtl] .photoviewer-button-next {
-ms-transform: rotate(180deg);
diff --git a/dist/photoviewer.esm.js b/dist/photoviewer.esm.js
index 5aff7c5..a49b6cc 100644
--- a/dist/photoviewer.esm.js
+++ b/dist/photoviewer.esm.js
@@ -5,7 +5,7 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
@@ -1261,6 +1261,7 @@ function fadeIn(speed, callback) {
var methods = {
isPlainObject: isPlainObject,
isArray: isArray,
+ isFunction: isFunction,
noop: noop
};
var fnMethods = {
@@ -1388,7 +1389,9 @@ var DEFAULTS = {
// Whether to set modal css `position: fixed`
positionFixed: true,
// Init modal position `{top: 0, right: 0, bottom: 0, left: 0}`
- initModalPos: null
+ initModalPos: null,
+ // Error message when image could not be loaded
+ errorMsg: ''
};
var document = window.document;
@@ -2001,6 +2004,8 @@ var PhotoViewer = /*#__PURE__*/function () {
left: null,
top: null
});
+ // Store previous index
+ _defineProperty(this, "prevIndex", null);
// Used for time comparison
_defineProperty(this, "_lastTimestamp", 0);
this.init(items, options);
@@ -2057,7 +2062,7 @@ var PhotoViewer = /*#__PURE__*/function () {
key: "_createTemplate",
value: function _createTemplate() {
var photoviewerHTML = "\n
\n
\n
\n ").concat(this._createBtns(this.options.headerToolbar), "\n
\n ").concat(this._createTitle(), "\n
\n
\n
\n
\n
\n
\n ").concat(this._createBtns(this.options.footerToolbar), "\n
\n
\n
\n
");
- return photoviewerHTML;
+ return photoviewerHTML.replace(/>\s+<');
}
}, {
key: "_build",
@@ -2085,10 +2090,6 @@ var PhotoViewer = /*#__PURE__*/function () {
this.$prev = $photoviewer.find(CLASS_NS + '-button-prev');
this.$next = $photoviewer.find(CLASS_NS + '-button-next');
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
-
// Reset the modal `z-index` of multiple instances
this.$photoviewer.css('z-index', PUBLIC_VARS['zIndex']);
if (this.options.positionFixed) {
@@ -2305,44 +2306,51 @@ var PhotoViewer = /*#__PURE__*/function () {
if (!this.imageLoaded) {
// Loader end
this.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Remove init classes after image loaded
- this.$stage.removeClass('stage-ready');
- this.$image.removeClass('image-ready');
+ // The class must be removed after image loaded
+ this.$stage.removeClass(NS + '-align-center');
// Add init animation for image
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.fadeIn();
}
this.imageLoaded = true;
+ this._triggerHook('changed', [this, this.index]);
}
}
}, {
key: "_loadImage",
- value: function _loadImage(index, fn, err) {
+ value: function _loadImage(index) {
var _this$images$index,
+ _this$images$index2,
_this4 = this;
- var imgSrc = (_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src;
- if (!imgSrc) {
- return;
- }
+ // Flag for both image loaded and animation finished
+ this.imageLoaded = false;
+ this._triggerHook('beforeChange', [this, this.prevIndex]);
+ this._removeErrorMsg();
- // Reset the image src
+ // Reset the image src and rotation status
this.$image.removeAttr('style').attr('src', '');
this.isRotated = false;
this.rotationDegree = 0;
- this.imageLoaded = false;
// Loader start
this.$photoviewer.append(""));
-
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
+ // Used for centering image
+ this.$stage.addClass(NS + '-align-center');
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.hide();
}
+
+ // The image src must be a string
+ var imgSrc = ((_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src) == null ? '' : this.images[index].src.toString();
+
+ // Get image with src
this.$image.attr('src', imgSrc);
+ var title = ((_this$images$index2 = this.images[index]) === null || _this$images$index2 === void 0 ? void 0 : _this$images$index2.title) || getImageNameFromUrl(imgSrc);
+ if (this.options.title) {
+ this.$title.html(title);
+ }
+ this.$image.attr('alt', title);
preloadImage(imgSrc, function (img) {
// Store the original image size
_this4.imageData = {
@@ -2354,59 +2362,49 @@ var PhotoViewer = /*#__PURE__*/function () {
} else {
_this4._setModalSize();
}
-
- // Callback of the image loaded successfully
- if (fn) {
- fn.call();
- }
}, function () {
// Loader end
_this4.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Callback of the image loading failed
- if (err) {
- err.call();
- }
+ _this4._triggerHook('changed', [_this4, index]);
+ _this4._setErrorMsg();
});
- if (this.options.title && imgSrc) {
- this._setImageTitle(imgSrc);
+ }
+ }, {
+ key: "_setErrorMsg",
+ value: function _setErrorMsg() {
+ var errorMsg = D.isFunction(this.options.errorMsg) ? this.options.errorMsg(this, this.index) : this.options.errorMsg;
+ if (errorMsg) {
+ this.$stage.append("").concat(errorMsg, ""));
+ this.$image.addClass(NS + '-image-error');
}
}
}, {
- key: "_setImageTitle",
- value: function _setImageTitle(url) {
- var title = this.images[this.index].title || getImageNameFromUrl(url);
- this.$title.html(title);
+ key: "_removeErrorMsg",
+ value: function _removeErrorMsg() {
+ this.$stage.find(CLASS_NS + '-error-msg').remove();
+ this.$image.removeClass(NS + '-image-error');
}
}, {
key: "jump",
value: function jump(step) {
- this._triggerHook('beforeChange', [this, this.index]);
-
- // Only allow to change image after the modal animation has finished
+ // Allow to change image only after the modal animation has finished
var now = Date.now();
if (now - this._lastTimestamp >= this.options.animationDuration) {
- this.index = this.index + step;
- this.jumpTo(this.index);
+ var newIndex = this.index + step;
+ this.jumpTo(newIndex);
this._lastTimestamp = now;
}
}
}, {
key: "jumpTo",
value: function jumpTo(index) {
- var _this5 = this;
- index = index % this.images.length;
- if (index >= 0) {
- index = index % this.images.length;
- } else if (index < 0) {
- index = (this.images.length + index) % this.images.length;
+ this.prevIndex = this.index;
+ var newIndex = index % this.images.length;
+ if (newIndex <= 0) {
+ newIndex = (newIndex + this.images.length) % this.images.length;
}
- this.index = index;
- this._loadImage(index, function () {
- _this5._triggerHook('changed', [_this5, index]);
- }, function () {
- _this5._triggerHook('changed', [_this5, index]);
- });
+ this.index = newIndex;
+ this._loadImage(this.index);
}
}, {
key: "_wheel",
@@ -2697,54 +2695,54 @@ var PhotoViewer = /*#__PURE__*/function () {
}, {
key: "_addEvents",
value: function _addEvents() {
- var _this6 = this;
+ var _this5 = this;
this.$close.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.close();
+ _this5.close();
});
this.$stage.on(WHEEL_EVENT + EVENT_NS, function (e) {
- _this6._wheel(e);
+ _this5._wheel(e);
});
this.$zoomIn.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(_this6.options.ratioThreshold * 3);
+ _this5.zoom(_this5.options.ratioThreshold * 3);
});
this.$zoomOut.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(-_this6.options.ratioThreshold * 3);
+ _this5.zoom(-_this5.options.ratioThreshold * 3);
});
this.$actualSize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoomTo(1);
+ _this5.zoomTo(1);
});
this.$prev.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(-1);
+ _this5.jump(-1);
});
this.$next.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(1);
+ _this5.jump(1);
});
this.$rotateLeft.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(-90);
+ _this5.rotate(-90);
});
this.$rotateRight.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(90);
+ _this5.rotate(90);
});
this.$maximize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.toggleMaximize();
+ _this5.toggleMaximize();
});
this.$fullscreen.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.fullscreen();
+ _this5.fullscreen();
});
this.$photoviewer.on(KEYDOWN_EVENT + EVENT_NS, function (e) {
- _this6._keydown(e);
+ _this5._keydown(e);
});
$W.on(RESIZE_EVENT + EVENT_NS, debounce(function () {
- return _this6.resize();
+ return _this5.resize();
}, 500));
}
}, {
key: "_addCustomButtonEvents",
value: function _addCustomButtonEvents() {
- var _this7 = this;
+ var _this6 = this;
var _loop = function _loop(btnKey) {
- _this7.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
- _this7.options.customButtons[btnKey].click.apply(_this7, [_this7, e]);
+ _this6.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
+ _this6.options.customButtons[btnKey].click.apply(_this6, [_this6, e]);
});
};
for (var btnKey in this.options.customButtons) {
diff --git a/dist/photoviewer.js b/dist/photoviewer.js
index 3868956..915f4a5 100644
--- a/dist/photoviewer.js
+++ b/dist/photoviewer.js
@@ -5,7 +5,7 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
@@ -1267,6 +1267,7 @@
var methods = {
isPlainObject: isPlainObject,
isArray: isArray,
+ isFunction: isFunction,
noop: noop
};
var fnMethods = {
@@ -1394,7 +1395,9 @@
// Whether to set modal css `position: fixed`
positionFixed: true,
// Init modal position `{top: 0, right: 0, bottom: 0, left: 0}`
- initModalPos: null
+ initModalPos: null,
+ // Error message when image could not be loaded
+ errorMsg: ''
};
var document = window.document;
@@ -2007,6 +2010,8 @@
left: null,
top: null
});
+ // Store previous index
+ _defineProperty(this, "prevIndex", null);
// Used for time comparison
_defineProperty(this, "_lastTimestamp", 0);
this.init(items, options);
@@ -2063,7 +2068,7 @@
key: "_createTemplate",
value: function _createTemplate() {
var photoviewerHTML = "\n
\n
\n
\n ").concat(this._createBtns(this.options.headerToolbar), "\n
\n ").concat(this._createTitle(), "\n
\n
\n
\n
\n
\n
\n ").concat(this._createBtns(this.options.footerToolbar), "\n
\n
\n
\n
");
- return photoviewerHTML;
+ return photoviewerHTML.replace(/>\s+<');
}
}, {
key: "_build",
@@ -2091,10 +2096,6 @@
this.$prev = $photoviewer.find(CLASS_NS + '-button-prev');
this.$next = $photoviewer.find(CLASS_NS + '-button-next');
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
-
// Reset the modal `z-index` of multiple instances
this.$photoviewer.css('z-index', PUBLIC_VARS['zIndex']);
if (this.options.positionFixed) {
@@ -2311,44 +2312,51 @@
if (!this.imageLoaded) {
// Loader end
this.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Remove init classes after image loaded
- this.$stage.removeClass('stage-ready');
- this.$image.removeClass('image-ready');
+ // The class must be removed after image loaded
+ this.$stage.removeClass(NS + '-align-center');
// Add init animation for image
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.fadeIn();
}
this.imageLoaded = true;
+ this._triggerHook('changed', [this, this.index]);
}
}
}, {
key: "_loadImage",
- value: function _loadImage(index, fn, err) {
+ value: function _loadImage(index) {
var _this$images$index,
+ _this$images$index2,
_this4 = this;
- var imgSrc = (_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src;
- if (!imgSrc) {
- return;
- }
+ // Flag for both image loaded and animation finished
+ this.imageLoaded = false;
+ this._triggerHook('beforeChange', [this, this.prevIndex]);
+ this._removeErrorMsg();
- // Reset the image src
+ // Reset the image src and rotation status
this.$image.removeAttr('style').attr('src', '');
this.isRotated = false;
this.rotationDegree = 0;
- this.imageLoaded = false;
// Loader start
this.$photoviewer.append(""));
-
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
+ // Used for centering image
+ this.$stage.addClass(NS + '-align-center');
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.hide();
}
+
+ // The image src must be a string
+ var imgSrc = ((_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src) == null ? '' : this.images[index].src.toString();
+
+ // Get image with src
this.$image.attr('src', imgSrc);
+ var title = ((_this$images$index2 = this.images[index]) === null || _this$images$index2 === void 0 ? void 0 : _this$images$index2.title) || getImageNameFromUrl(imgSrc);
+ if (this.options.title) {
+ this.$title.html(title);
+ }
+ this.$image.attr('alt', title);
preloadImage(imgSrc, function (img) {
// Store the original image size
_this4.imageData = {
@@ -2360,59 +2368,49 @@
} else {
_this4._setModalSize();
}
-
- // Callback of the image loaded successfully
- if (fn) {
- fn.call();
- }
}, function () {
// Loader end
_this4.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Callback of the image loading failed
- if (err) {
- err.call();
- }
+ _this4._triggerHook('changed', [_this4, index]);
+ _this4._setErrorMsg();
});
- if (this.options.title && imgSrc) {
- this._setImageTitle(imgSrc);
+ }
+ }, {
+ key: "_setErrorMsg",
+ value: function _setErrorMsg() {
+ var errorMsg = D.isFunction(this.options.errorMsg) ? this.options.errorMsg(this, this.index) : this.options.errorMsg;
+ if (errorMsg) {
+ this.$stage.append("").concat(errorMsg, ""));
+ this.$image.addClass(NS + '-image-error');
}
}
}, {
- key: "_setImageTitle",
- value: function _setImageTitle(url) {
- var title = this.images[this.index].title || getImageNameFromUrl(url);
- this.$title.html(title);
+ key: "_removeErrorMsg",
+ value: function _removeErrorMsg() {
+ this.$stage.find(CLASS_NS + '-error-msg').remove();
+ this.$image.removeClass(NS + '-image-error');
}
}, {
key: "jump",
value: function jump(step) {
- this._triggerHook('beforeChange', [this, this.index]);
-
- // Only allow to change image after the modal animation has finished
+ // Allow to change image only after the modal animation has finished
var now = Date.now();
if (now - this._lastTimestamp >= this.options.animationDuration) {
- this.index = this.index + step;
- this.jumpTo(this.index);
+ var newIndex = this.index + step;
+ this.jumpTo(newIndex);
this._lastTimestamp = now;
}
}
}, {
key: "jumpTo",
value: function jumpTo(index) {
- var _this5 = this;
- index = index % this.images.length;
- if (index >= 0) {
- index = index % this.images.length;
- } else if (index < 0) {
- index = (this.images.length + index) % this.images.length;
+ this.prevIndex = this.index;
+ var newIndex = index % this.images.length;
+ if (newIndex <= 0) {
+ newIndex = (newIndex + this.images.length) % this.images.length;
}
- this.index = index;
- this._loadImage(index, function () {
- _this5._triggerHook('changed', [_this5, index]);
- }, function () {
- _this5._triggerHook('changed', [_this5, index]);
- });
+ this.index = newIndex;
+ this._loadImage(this.index);
}
}, {
key: "_wheel",
@@ -2703,54 +2701,54 @@
}, {
key: "_addEvents",
value: function _addEvents() {
- var _this6 = this;
+ var _this5 = this;
this.$close.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.close();
+ _this5.close();
});
this.$stage.on(WHEEL_EVENT + EVENT_NS, function (e) {
- _this6._wheel(e);
+ _this5._wheel(e);
});
this.$zoomIn.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(_this6.options.ratioThreshold * 3);
+ _this5.zoom(_this5.options.ratioThreshold * 3);
});
this.$zoomOut.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(-_this6.options.ratioThreshold * 3);
+ _this5.zoom(-_this5.options.ratioThreshold * 3);
});
this.$actualSize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoomTo(1);
+ _this5.zoomTo(1);
});
this.$prev.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(-1);
+ _this5.jump(-1);
});
this.$next.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(1);
+ _this5.jump(1);
});
this.$rotateLeft.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(-90);
+ _this5.rotate(-90);
});
this.$rotateRight.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(90);
+ _this5.rotate(90);
});
this.$maximize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.toggleMaximize();
+ _this5.toggleMaximize();
});
this.$fullscreen.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.fullscreen();
+ _this5.fullscreen();
});
this.$photoviewer.on(KEYDOWN_EVENT + EVENT_NS, function (e) {
- _this6._keydown(e);
+ _this5._keydown(e);
});
$W.on(RESIZE_EVENT + EVENT_NS, debounce(function () {
- return _this6.resize();
+ return _this5.resize();
}, 500));
}
}, {
key: "_addCustomButtonEvents",
value: function _addCustomButtonEvents() {
- var _this7 = this;
+ var _this6 = this;
var _loop = function _loop(btnKey) {
- _this7.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
- _this7.options.customButtons[btnKey].click.apply(_this7, [_this7, e]);
+ _this6.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
+ _this6.options.customButtons[btnKey].click.apply(_this6, [_this6, e]);
});
};
for (var btnKey in this.options.customButtons) {
diff --git a/dist/photoviewer.min.css b/dist/photoviewer.min.css
index 09b2c14..865a6d9 100644
--- a/dist/photoviewer.min.css
+++ b/dist/photoviewer.min.css
@@ -5,12 +5,12 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
* Copyright (c) 2018-present nzbin
* Released under MIT License
- */.photoviewer-modal{position:absolute;z-index:1090;width:320px;height:320px;color:#333;background-color:rgba(255,255,255,.9);border:1px solid rgba(0,0,0,.6);border-radius:6px;box-shadow:0 2px 10px 2px rgba(0,0,0,.3);outline:none}.photoviewer-modal:focus-visible{outline:thick solid rgba(0,0,0,.2)}.photoviewer-inner{position:absolute;top:0;left:0;right:0;bottom:0}.photoviewer-maximized{position:fixed;top:0;right:0;bottom:0;left:0;width:auto;height:auto}.photoviewer-maximized.photoviewer-modal{border-width:0;border-radius:0}.photoviewer-maximized .photoviewer-header{border-radius:0}.photoviewer-maximized .photoviewer-resizable-handle{display:none}.photoviewer-button{display:inline-block;min-width:40px;height:40px;box-sizing:border-box;font-size:16px;line-height:1;background:none;border-width:0;color:inherit;cursor:pointer;outline:none}.photoviewer-button:hover{color:#111}.photoviewer-button:focus{background-color:rgba(0,0,0,.1)}.photoviewer-button svg{display:inline-block;font-size:inherit;width:1em;height:1em;overflow:visible;vertical-align:-0.125em}.photoviewer-header{position:relative;z-index:2;height:30px;border-radius:5px 5px 0 0;overflow:hidden}.photoviewer-header .photoviewer-toolbar{float:right}[dir=rtl] .photoviewer-header .photoviewer-toolbar{float:left}.photoviewer-header .photoviewer-button{height:30px}.photoviewer-header .photoviewer-button:hover{background-color:rgba(0,0,0,.1)}.photoviewer-header .photoviewer-button-close:hover{color:#fff;background-color:#ff4545}.photoviewer-title{padding:8px 10px;font-size:14px;line-height:1;white-space:nowrap;text-overflow:ellipsis;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;overflow:hidden}.photoviewer-stage{position:absolute;top:30px;right:0;bottom:40px;left:0;z-index:1;border-top:1px solid rgba(0,0,0,.6);border-bottom:1px solid rgba(0,0,0,.6);background-color:#fff;overflow:hidden}.photoviewer-stage.stage-ready{text-align:center;font-size:0}.photoviewer-stage.stage-ready::before{content:"";display:inline-block;height:100%;vertical-align:middle;overflow:hidden}.photoviewer-image{position:absolute;display:inline-block;min-width:auto;max-width:none}.photoviewer-image.image-ready{position:static;max-width:100%;max-height:100%;vertical-align:middle}.photoviewer-footer{position:absolute;bottom:0;z-index:2;width:100%;height:40px;text-align:center}[dir=rtl] .photoviewer-button-prev,[dir=rtl] .photoviewer-button-next{-ms-transform:rotate(180deg);transform:rotate(180deg)}.photoviewer-resizable-handle{position:absolute;z-index:10}.photoviewer-resizable-handle-e{top:0;right:-5px;bottom:0;left:auto;width:10px;cursor:e-resize}.photoviewer-resizable-handle-s{top:auto;right:0;bottom:-5px;left:0;height:10px;cursor:s-resize}.photoviewer-resizable-handle-w{top:0;right:auto;bottom:0;left:-5px;width:10px;cursor:w-resize}.photoviewer-resizable-handle-n{top:-5px;right:0;bottom:auto;left:0;height:10px;cursor:n-resize}.photoviewer-resizable-handle-se{top:auto;right:-5px;bottom:-5px;left:auto;width:10px;height:10px;cursor:se-resize}.photoviewer-resizable-handle-sw{top:auto;right:auto;bottom:-5px;left:-5px;width:10px;height:10px;cursor:sw-resize}.photoviewer-resizable-handle-nw{top:-5px;right:auto;bottom:auto;left:-5px;width:10px;height:10px;cursor:nw-resize}.photoviewer-resizable-handle-ne{top:-5px;right:-5px;bottom:auto;left:auto;width:10px;height:10px;cursor:ne-resize}:-webkit-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-webkit-full-screen .photoviewer-header,:-webkit-full-screen .photoviewer-footer,:-webkit-full-screen .photoviewer-resizable-handle{display:none}:-webkit-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-moz-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-moz-full-screen .photoviewer-header,:-moz-full-screen .photoviewer-footer,:-moz-full-screen .photoviewer-resizable-handle{display:none}:-moz-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-ms-fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-ms-fullscreen .photoviewer-header,:-ms-fullscreen .photoviewer-footer,:-ms-fullscreen .photoviewer-resizable-handle{display:none}:-ms-fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:full-screen .photoviewer-header,:full-screen .photoviewer-footer,:full-screen .photoviewer-resizable-handle{display:none}:full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-webkit-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-ms-fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-webkit-full-screen .photoviewer-header, :-webkit-full-screen .photoviewer-footer, :-webkit-full-screen .photoviewer-resizable-handle{display:none}:-ms-fullscreen .photoviewer-header, :-ms-fullscreen .photoviewer-footer, :-ms-fullscreen .photoviewer-resizable-handle{display:none}:fullscreen .photoviewer-header,:fullscreen .photoviewer-footer,:fullscreen .photoviewer-resizable-handle{display:none}:-webkit-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-ms-fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}::backdrop{background-color:#000}::-ms-backdrop{background-color:#000}.is-grab{cursor:move;cursor:grab}.is-grabbing{cursor:move;cursor:grabbing}.photoviewer-loader{position:absolute;top:30px;left:0;right:0;bottom:40px;z-index:2;text-align:center;color:#333}.photoviewer-loader::before{content:"";position:relative;display:inline-block;width:36px;height:36px;box-sizing:border-box;border-width:5px;border-style:solid;border-color:rgba(0,0,0,.5) rgba(0,0,0,.5) rgba(0,0,0,.5) rgba(255,255,255,.5);border-radius:100%;vertical-align:middle;animation:photoviewerLoading 1s infinite linear}.photoviewer-loader::after{content:"";display:inline-block;width:0;height:100%;vertical-align:middle;overflow:hidden}@keyframes photoviewerLoading{0%{transform:rotateZ(0deg) translate3d(0, 0, 0)}100%{transform:rotateZ(360deg) translate3d(0, 0, 0)}}
+ */.photoviewer-modal{position:absolute;z-index:1090;width:320px;height:320px;color:#333;background-color:rgba(255,255,255,.9);border:1px solid rgba(0,0,0,.6);border-radius:6px;box-shadow:0 2px 10px 2px rgba(0,0,0,.3);outline:none}.photoviewer-modal:focus-visible{outline:thick solid rgba(0,0,0,.2)}.photoviewer-inner{position:absolute;top:0;left:0;right:0;bottom:0}.photoviewer-maximized{position:fixed;top:0;right:0;bottom:0;left:0;width:auto;height:auto}.photoviewer-maximized.photoviewer-modal{border-width:0;border-radius:0}.photoviewer-maximized .photoviewer-header{border-radius:0}.photoviewer-maximized .photoviewer-resizable-handle{display:none}.photoviewer-button{display:inline-block;min-width:40px;height:40px;box-sizing:border-box;font-size:16px;line-height:1;background:none;border-width:0;color:inherit;cursor:pointer;outline:none}.photoviewer-button:hover{color:#111}.photoviewer-button:focus{background-color:rgba(0,0,0,.1)}.photoviewer-button svg{display:inline-block;font-size:inherit;width:1em;height:1em;overflow:visible;vertical-align:-0.125em}.photoviewer-header{position:relative;z-index:2;height:30px;border-radius:5px 5px 0 0;overflow:hidden}.photoviewer-header .photoviewer-toolbar{float:right}[dir=rtl] .photoviewer-header .photoviewer-toolbar{float:left}.photoviewer-header .photoviewer-button{height:30px}.photoviewer-header .photoviewer-button:hover{background-color:rgba(0,0,0,.1)}.photoviewer-header .photoviewer-button-close:hover{color:#fff;background-color:#ff4545}.photoviewer-title{padding:8px 10px;font-size:14px;line-height:1;white-space:nowrap;text-overflow:ellipsis;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;overflow:hidden}.photoviewer-stage{position:absolute;top:30px;right:0;bottom:40px;left:0;z-index:1;border-top:1px solid rgba(0,0,0,.6);border-bottom:1px solid rgba(0,0,0,.6);background-color:#fff;overflow:hidden}.photoviewer-image{position:absolute;display:inline-block;min-width:auto;max-width:none}.photoviewer-footer{position:absolute;bottom:0;z-index:2;width:100%;height:40px;text-align:center}.photoviewer-align-center{text-align:center}.photoviewer-align-center::before{content:"";display:inline-block;height:100%;vertical-align:middle;overflow:hidden}.photoviewer-align-center .photoviewer-image{position:static;max-width:100%;max-height:100%;vertical-align:middle}.photoviewer-image-error{display:none}.photoviewer-error-msg{vertical-align:middle}[dir=rtl] .photoviewer-button-prev,[dir=rtl] .photoviewer-button-next{-ms-transform:rotate(180deg);transform:rotate(180deg)}.photoviewer-resizable-handle{position:absolute;z-index:10}.photoviewer-resizable-handle-e{top:0;right:-5px;bottom:0;left:auto;width:10px;cursor:e-resize}.photoviewer-resizable-handle-s{top:auto;right:0;bottom:-5px;left:0;height:10px;cursor:s-resize}.photoviewer-resizable-handle-w{top:0;right:auto;bottom:0;left:-5px;width:10px;cursor:w-resize}.photoviewer-resizable-handle-n{top:-5px;right:0;bottom:auto;left:0;height:10px;cursor:n-resize}.photoviewer-resizable-handle-se{top:auto;right:-5px;bottom:-5px;left:auto;width:10px;height:10px;cursor:se-resize}.photoviewer-resizable-handle-sw{top:auto;right:auto;bottom:-5px;left:-5px;width:10px;height:10px;cursor:sw-resize}.photoviewer-resizable-handle-nw{top:-5px;right:auto;bottom:auto;left:-5px;width:10px;height:10px;cursor:nw-resize}.photoviewer-resizable-handle-ne{top:-5px;right:-5px;bottom:auto;left:auto;width:10px;height:10px;cursor:ne-resize}:-webkit-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-webkit-full-screen .photoviewer-header,:-webkit-full-screen .photoviewer-footer,:-webkit-full-screen .photoviewer-resizable-handle{display:none}:-webkit-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-moz-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-moz-full-screen .photoviewer-header,:-moz-full-screen .photoviewer-footer,:-moz-full-screen .photoviewer-resizable-handle{display:none}:-moz-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-ms-fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-ms-fullscreen .photoviewer-header,:-ms-fullscreen .photoviewer-footer,:-ms-fullscreen .photoviewer-resizable-handle{display:none}:-ms-fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:full-screen .photoviewer-header,:full-screen .photoviewer-footer,:full-screen .photoviewer-resizable-handle{display:none}:full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-webkit-full-screen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-ms-fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:fullscreen{top:0 !important;right:0 !important;bottom:0 !important;left:0 !important;width:100% !important;height:100% !important;background-color:rgba(0,0,0,0);border-width:0;border-radius:0}:-webkit-full-screen .photoviewer-header, :-webkit-full-screen .photoviewer-footer, :-webkit-full-screen .photoviewer-resizable-handle{display:none}:-ms-fullscreen .photoviewer-header, :-ms-fullscreen .photoviewer-footer, :-ms-fullscreen .photoviewer-resizable-handle{display:none}:fullscreen .photoviewer-header,:fullscreen .photoviewer-footer,:fullscreen .photoviewer-resizable-handle{display:none}:-webkit-full-screen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:-ms-fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}:fullscreen .photoviewer-stage{top:0;right:0;bottom:0;left:0;border-width:0;background-color:#000}::backdrop{background-color:#000}::-ms-backdrop{background-color:#000}.is-grab{cursor:move;cursor:grab}.is-grabbing{cursor:move;cursor:grabbing}.photoviewer-loader{position:absolute;top:30px;left:0;right:0;bottom:40px;z-index:2;text-align:center;color:#333}.photoviewer-loader::before{content:"";position:relative;display:inline-block;width:36px;height:36px;box-sizing:border-box;border-width:5px;border-style:solid;border-color:rgba(0,0,0,.5) rgba(0,0,0,.5) rgba(0,0,0,.5) rgba(255,255,255,.5);border-radius:100%;vertical-align:middle;animation:photoviewerLoading 1s infinite linear}.photoviewer-loader::after{content:"";display:inline-block;width:0;height:100%;vertical-align:middle;overflow:hidden}@keyframes photoviewerLoading{0%{transform:rotateZ(0deg) translate3d(0, 0, 0)}100%{transform:rotateZ(360deg) translate3d(0, 0, 0)}}
/*# sourceMappingURL=photoviewer.min.css.map */
\ No newline at end of file
diff --git a/dist/photoviewer.min.js b/dist/photoviewer.min.js
index 7d74f64..197c31e 100644
--- a/dist/photoviewer.min.js
+++ b/dist/photoviewer.min.js
@@ -5,11 +5,11 @@
* / ____/ __ / /_/ / / / / /_/ /| |/ // // /___ | |/ |/ / /___/ _, _/
* /_/ /_/ /_/\____/ /_/ \____/ |___/___/_____/ |__/|__/_____/_/ |_|
*
- * photoviewer - v3.9.2
+ * photoviewer - v3.10.0
* A JS plugin to view images just like in Windows.
* https://nzbin.github.io/photoviewer/
*
* Copyright (c) 2018-present nzbin
* Released under MIT License
*/
-!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).PhotoViewer=e()}(this,function(){"use strict";function A(t,e){for(var i=0;i]*>/,Y=/^<(\w+)\s*\/?>(?:<\/\1>|)$/,X=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,q=/^(?:body|html)$/i,Z=["val","css","html","text","data","width","height","offset"],t=w.createElement("table"),W=w.createElement("tr"),U={tr:w.createElement("tbody"),tbody:t,thead:t,tfoot:t,td:W,th:W,"*":w.createElement("div")},K=/^[\w-]*$/,Q={},G=Q.toString,J=w.createElement("div"),l=Array.isArray||function(t){return"[object Array]"===Object.prototype.toString.call(t)},b=w.documentElement.contains?function(t,e){return t!==e&&t.contains(e)}:function(t,e){for(;e=e&&e.parentNode;)if(e===t)return!0;return!1};function h(t){return null==t?String(t):Q[G.call(t)]||"object"}function s(t){return"string"==typeof t}function c(t){return"function"==h(t)}function a(t){return null!=t&&t==t.window}function tt(t){return null!=t&&t.nodeType==t.DOCUMENT_NODE}function r(t){return"object"==h(t)}function u(t){return r(t)&&!a(t)&&Object.getPrototypeOf(t)==Object.prototype}function et(t){var e=!!t&&"length"in t&&t.length,i=h(t);return"function"!=i&&!a(t)&&("array"==i||0===e||"number"==typeof e&&0$2>")),void 0===e&&(e=N.test(t)&&RegExp.$1),(s=U[e=e in U?e:"*"]).innerHTML=""+t,o=H.each(y.call(s.childNodes),function(){s.removeChild(this)})),u(i)&&(n=H(o),H.each(i,function(t,e){-1{var e=t.e+"."+t.ns.split(" ").join(".");xt(i,e,t.fn,t.sel)})}var n,s,a,r;null!=this.parentNode&&this.parentNode.removeChild(this)})},empty:function(){return this.each(function(){this.innerHTML=""})},html:function(i){return 0 in arguments?this.each(function(t){var e=this.innerHTML;H(this).empty().append(p(this,i,t,e))}):0 in this?this[0].innerHTML:null},width:function(t){return rt.call(this,"width",t)},height:function(t){return rt.call(this,"height",t)},scrollTop:function(t){var e;if(this.length)return e="scrollTop"in this[0],void 0===t?e?this[0].scrollTop:(a(this[0])?this[0]:this[0].defaultView).pageYOffset:this.each(e?function(){this.scrollTop=t}:function(){this.scrollTo(this.scrollX,t)})},scrollLeft:function(t){var e;if(this.length)return e="scrollLeft"in this[0],void 0===t?e?this[0].scrollLeft:(a(this[0])?this[0]:this[0].defaultView).pageXOffset:this.each(e?function(){this.scrollLeft=t}:function(){this.scrollTo(t,this.scrollY)})},offset:function(o){var t;return o?this.each(function(t){var e=H(this),t=p(this,o,t,e.offset()),i=e.offsetParent().offset(),t={top:t.top-i.top,left:t.left-i.left};"static"==e.css("position")&&(t.position="relative"),e.css(t)}):this.length?w.documentElement===this[0]||b(w.documentElement,this[0])?{left:(t=this[0].getBoundingClientRect()).left+window.pageXOffset,top:t.top+window.pageYOffset,width:Math.round(t.width),height:Math.round(t.height)}:{top:0,left:0}:null},offsetParent:function(){return this.map(function(){for(var t=this.offsetParent||w.body;t&&!q.test(t.nodeName)&&"static"==H(t).css("position");)t=t.offsetParent;return t})},position:function(){var t,e,i,o;if(this.length)return t=this[0],i=this.offsetParent(),o=q.test(i[0].nodeName)?{top:0,left:0}:i.offset(),"fixed"===H(t).css("position")?e=t.getBoundingClientRect():(e=this.offset(),o.top+=parseFloat(H(i[0]).css("border-top-width"))||0,o.left+=parseFloat(H(i[0]).css("border-left-width"))||0),{top:e.top-o.top-parseFloat(H(t).css("margin-top"))||0,left:e.left-o.left-parseFloat(H(t).css("margin-left"))||0}},on:function(u,d,f,p,g){var m,v,i=this;return u&&!s(u)?(H.each(u,function(t,e){i.on(t,d,f,e,g)}),i):(s(d)||c(p)||!1===p||(p=f,f=d,d=void 0),void 0!==p&&!1!==f||(p=f,f=void 0),!1===p&&(p=lt),i.each(function(t,i){var o,e,n,s,a,r,h,l,c;g&&(m=function(t){return xt(i,t.type,p),p.apply(this,arguments)}),e=u,n=p,s=f,r=(v=(a=d)?function(t){var e=H(t.target).closest(d,i).get(0);if(e&&e!==i)return t=H.extend(function(t){var e,i={originalEvent:t};for(e in t)pt.test(e)||void 0===t[e]||(i[e]=t[e]);return mt(i,t)}(t),{currentTarget:e,liveFired:i}),(m||p).apply(e,[t].concat(y.call(arguments,1)))}:v)||m,l=z(o=i),c=x[l]||(x[l]=[]),e.split(/\s/).forEach(function(t){if("ready"==t)return H(w).ready(n);var e=vt(t),i=(e.fn=n,e.sel=a,e.e in ft&&(n=function(t){t=t.relatedTarget;if(!t||t!==this&&!b(this,t))return e.fn.apply(this,arguments)}),(e.del=r)||n);e.proxy=function(t){var e;if(!(t=mt(t)).isImmediatePropagationStopped())return t.data=s,!1===(e=i.apply(o,null==t._args?[t]:[t].concat(t._args)))&&(t.preventDefault(),t.stopPropagation()),e},e.i=c.length,c.push(e),"addEventListener"in o&&o.addEventListener(bt(e.e),e.proxy,yt(e,h))})}))},off:function(t,i,e){var o=this;return t&&!s(t)?(H.each(t,function(t,e){o.off(t,i,e)}),o):(s(i)||c(e)||!1===e||(e=i,i=void 0),!1===e&&(e=lt),o.each(function(){xt(this,t,e,i)}))},show:function(t,e){return Pt.call(this),void 0===t?t=0:this.css("opacity",0),St(this,t,1,"1,1",e)},hide:function(t,e){return void 0===t?Rt.call(this):(i=e,St(this,t,0,"0,0",function(){Rt.call(H(this)),i&&i.call(this)}));var i},anim:function(t,e,i,o,n){var s,a,r,h={},l="",c=this,u=H.fx.transitionEnd,d=!1;if(void 0===e&&(e=H.fx.speeds._default/1e3),void 0===n&&(n=0),H.fx.off&&(e=0),"string"==typeof t)h[Ht]=t,h[Et]=e+"s",h[kt]=n+"s",h[Vt]=i||"linear",u=H.fx.animationEnd;else{for(s in a=[],t)Dt.test(s)?l+=s+"("+t[s]+") ":(h[s]=t[s],a.push(s.replace(/([A-Z])/g,"-$1").toLowerCase()));l&&(h[$t]=l,a.push($t)),0\n \n ',maximize:'',close:'',zoomIn:'',zoomOut:'',prev:'',next:'',fullscreen:'',actualSize:'',rotateLeft:'',rotateRight:''},i18n:{minimize:"Minimize",maximize:"Maximize (Alt+X)",close:"Close (Q)",zoomIn:"Zoom-in (+)",zoomOut:"Zoom-out (-)",prev:"Prev (←)",next:"Next (→)",fullscreen:"Fullscreen (F)",actualSize:"Actual-size (Ctrl+Alt+0)",rotateLeft:"Rotate-left (Ctrl+,)",rotateRight:"Rotate-right (Ctrl+.)"},multiInstances:!0,initAnimation:!0,animationDuration:400,animationEasing:"ease-in-out",fixedModalPos:!1,zIndex:1090,dragHandle:null,callbacks:{beforeOpen:H.noop,opened:H.noop,beforeClose:H.noop,closed:H.noop,beforeChange:H.noop,changed:H.noop},index:0,progressiveLoading:!0,appendTo:"body",customButtons:{},positionFixed:!0,initModalPos:null}),It=window.document;function Ot(t,e,i,o){var n=o?t.h:t.w,o=o?t.w:t.h;(o>e.h||n>e.w)&&i.addClass("is-grab"),o<=e.h&&n<=e.w&&i.removeClass("is-grab")}function jt(){return"ontouchstart"in window||window.DocumentTouch&&It instanceof window.DocumentTouch}function $(t){return/^(?:body|html)$/i.test(t.nodeName)}function T(i,t){return t.reduce(function(t,e){return t+parseFloat(i.css(e))},0)}function E(t){return"border-box"===t.css("box-sizing")}function Ft(t,e,i,o,n){return n?Math.min(i/e,o/t,1):Math.min(i/t,o/e,1)}var C=H(window),V=H(It),L="click",Bt=jt()?"touchstart":"mousedown",k=jt()?"touchmove":"mousemove",D=jt()?"touchend":"mouseup",P="photoviewer",_="."+P,R="."+P,S={isMoving:!1,isResizing:!1,zIndex:0};var Nt="html, body, .".concat(P,"-modal, .").concat(P,"-stage, .").concat(P,"-button, .").concat(P,"-resizable-handle");var Yt="html, body, .".concat(P,"-modal, .").concat(P,"-stage, .").concat(P,"-button");t=function(){function i(t,e){if(!(this instanceof i))throw new TypeError("Cannot call a class as a function");n(this,"isOpened",!1),n(this,"isMaximized",!1),n(this,"isRotated",!1),n(this,"rotationDegree",0),n(this,"imageData",{}),n(this,"modalData",{width:null,height:null,left:null,top:null}),n(this,"_lastTimestamp",0),this.init(t,e)}var t,e,o;return t=i,(e=[{key:"init",value:function(t,e){this.options=H.extend(!0,{},At,e),e&&H.isArray(e.footerToolbar)&&(this.options.footerToolbar=e.footerToolbar),e&&H.isArray(e.headerToolbar)&&(this.options.headerToolbar=e.headerToolbar),S.zIndex=(0===S.zIndex?this.options:S).zIndex,this.open(),this.images=t,this.index=this.options.index,this._loadImage(this.index),this.options.draggable&&this.draggable(this.$photoviewer,this.dragHandle,_+"-button"),this.options.movable&&this.movable(this.$stage,this.$image),this.options.resizable&&this.resizable(this.$photoviewer,this.$stage,this.$image,this.options)}},{key:"_createBtns",value:function(t){var o=this,n=["minimize","maximize","close","zoomIn","zoomOut","prev","next","fullscreen","actualSize","rotateLeft","rotateRight"],s="";return H.each(t,function(t,e){var i="".concat(P,"-button ").concat(P,"-button-").concat(e);0<=n.indexOf(e)?s+='"):o.options.customButtons[e]&&(s+='"))}),s}},{key:"_createTitle",value:function(){return this.options.title?''):""}},{key:"_createTemplate",value:function(){return'\n
\n \n
\n
\n
\n \n
\n
")}},{key:"_build",value:function(){var t=this._createTemplate(),t=H(t);this.$photoviewer=t,this.$stage=t.find(_+"-stage"),this.$title=t.find(_+"-title"),this.$image=t.find(_+"-image"),this.$close=t.find(_+"-button-close"),this.$maximize=t.find(_+"-button-maximize"),this.$minimize=t.find(_+"-button-minimize"),this.$zoomIn=t.find(_+"-button-zoomIn"),this.$zoomOut=t.find(_+"-button-zoomOut"),this.$actualSize=t.find(_+"-button-actualSize"),this.$fullscreen=t.find(_+"-button-fullscreen"),this.$rotateLeft=t.find(_+"-button-rotateLeft"),this.$rotateRight=t.find(_+"-button-rotateRight"),this.$prev=t.find(_+"-button-prev"),this.$next=t.find(_+"-button-next"),this.$stage.addClass("stage-ready"),this.$image.addClass("image-ready"),this.$photoviewer.css("z-index",S.zIndex),this.options.positionFixed&&this.$photoviewer.css({position:"fixed"}),this.options.dragHandle&&this.options.dragHandle!==_+"-modal"?this.dragHandle=this.$photoviewer.find(this.options.dragHandle):this.dragHandle=this.$photoviewer,H(this.options.appendTo).eq(0).append(this.$photoviewer),this._stageEdgeValue={horizontal:T(this.$stage,["left","right","border-left-width","border-right-width"]),vertical:T(this.$stage,["top","bottom","border-top-width","border-bottom-width"])},this._modalEdgeValue={horizontal:T(this.$photoviewer,["padding-left","padding-right","border-left-width","border-right-width"]),vertical:T(this.$photoviewer,["padding-top","padding-bottom","border-top-width","border-bottom-width"])},this._addEvents(),this._addCustomButtonEvents()}},{key:"open",value:function(){this._triggerHook("beforeOpen",this),!this.options.multiInstances&&0')),this.$stage.addClass("stage-ready"),this.$image.addClass("image-ready"),this.options.initAnimation&&!this.options.progressiveLoading&&this.$image.hide(),this.$image.attr("src",t),o=t,n=function(t){r.imageData={originalWidth:t.width,originalHeight:t.height},r.isMaximized||r.isOpened&&r.options.fixedModalPos?r._setImageSize():r._setModalSize(),e&&e.call()},s=function(){r.$photoviewer.find(_+"-loader").remove(),i&&i.call()},(a=new Image).onload=function(){n(a)},a.onerror=function(){s(a)},a.src=o,this.options.title)&&t&&this._setImageTitle(t)}},{key:"_setImageTitle",value:function(t){t=this.images[this.index].title||t.replace(/^.*?\/*([^/?]*)\.[a-z]+(\?.+|$)/gi,"$1");this.$title.html(t)}},{key:"jump",value:function(t){this._triggerHook("beforeChange",[this,this.index]);var e=Date.now();e-this._lastTimestamp>=this.options.animationDuration&&(this.index=this.index+t,this.jumpTo(this.index),this._lastTimestamp=e)}},{key:"jumpTo",value:function(t){var e=this;0<=(t%=this.images.length)?t%=this.images.length:t<0&&(t=(this.images.length+t)%this.images.length),this.index=t,this._loadImage(t,function(){e._triggerHook("changed",[e,t])},function(){e._triggerHook("changed",[e,t])})}},{key:"_wheel",value:function(t){t.preventDefault();var e=1,e=(t.deltaY?e=0this.options.maxRatio||t')),i=H('')),n=H('')),s=H('')),h=H('')),c=H('')),u=H('')),d=H('')),f={e:e,s:n,se:h,n:s,w:i,nw:d,ne:u,sw:c},p=(o.append(e,i,n,s,h,c,u,d),0),g=0,m={w:0,h:0,x:0,y:0},v={w:0,h:0,x:0,y:0},w={w:0,h:0,x:0,y:0},y=0,b=0,x=0,z="",M=t.modalWidth,$=t.modalHeight,T=function(t,e,i){var o=-e+m.w>M?e+m.x:m.x+m.w-M,n=-i+m.h>$?i+m.y:m.y+m.h-$;return{e:{width:Math.max(e+m.w,M)},s:{height:Math.max(i+m.h,$)},se:{width:Math.max(e+m.w,M),height:Math.max(i+m.h,$)},w:{width:Math.max(-e+m.w,M),left:o},n:{height:Math.max(-i+m.h,$),top:n},nw:{width:Math.max(-e+m.w,M),height:Math.max(-i+m.h,$),top:n,left:o},ne:{width:Math.max(e+m.w,M),height:Math.max(-i+m.h,$),top:n},sw:{width:Math.max(-e+m.w,M),height:Math.max(i+m.h,$),left:o}}[t]},C=function(t,e,i){var o=e+m.w>M?v.w-b+e-y:M-(m.w-v.w)-b-y,n=i+m.h>$?v.h-x+i+y:$-(m.h-v.h)-x+y,e=-e+m.w>M?v.w-b-e-y:M-(m.w-v.w)-b-y,i=-i+m.h>$?v.h-x-i+y:$-(m.h-v.h)-x+y,s=l.position().left,a=l.position().top,r=(0]*>/,Y=/^<(\w+)\s*\/?>(?:<\/\1>|)$/,X=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,q=/^(?:body|html)$/i,Z=["val","css","html","text","data","width","height","offset"],t=w.createElement("table"),W=w.createElement("tr"),U={tr:w.createElement("tbody"),tbody:t,thead:t,tfoot:t,td:W,th:W,"*":w.createElement("div")},K=/^[\w-]*$/,Q={},G=Q.toString,J=w.createElement("div"),l=Array.isArray||function(t){return"[object Array]"===Object.prototype.toString.call(t)},b=w.documentElement.contains?function(t,e){return t!==e&&t.contains(e)}:function(t,e){for(;e=e&&e.parentNode;)if(e===t)return!0;return!1};function h(t){return null==t?String(t):Q[G.call(t)]||"object"}function s(t){return"string"==typeof t}function c(t){return"function"==h(t)}function a(t){return null!=t&&t==t.window}function tt(t){return null!=t&&t.nodeType==t.DOCUMENT_NODE}function r(t){return"object"==h(t)}function u(t){return r(t)&&!a(t)&&Object.getPrototypeOf(t)==Object.prototype}function et(t){var e=!!t&&"length"in t&&t.length,i=h(t);return"function"!=i&&!a(t)&&("array"==i||0===e||"number"==typeof e&&0$2>")),void 0===e&&(e=N.test(t)&&RegExp.$1),(s=U[e=e in U?e:"*"]).innerHTML=""+t,o=E.each(y.call(s.childNodes),function(){s.removeChild(this)})),u(i)&&(n=E(o),E.each(i,function(t,e){-1{var e=t.e+"."+t.ns.split(" ").join(".");xt(i,e,t.fn,t.sel)})}var n,s,a,r;null!=this.parentNode&&this.parentNode.removeChild(this)})},empty:function(){return this.each(function(){this.innerHTML=""})},html:function(i){return 0 in arguments?this.each(function(t){var e=this.innerHTML;E(this).empty().append(p(this,i,t,e))}):0 in this?this[0].innerHTML:null},width:function(t){return rt.call(this,"width",t)},height:function(t){return rt.call(this,"height",t)},scrollTop:function(t){var e;if(this.length)return e="scrollTop"in this[0],void 0===t?e?this[0].scrollTop:(a(this[0])?this[0]:this[0].defaultView).pageYOffset:this.each(e?function(){this.scrollTop=t}:function(){this.scrollTo(this.scrollX,t)})},scrollLeft:function(t){var e;if(this.length)return e="scrollLeft"in this[0],void 0===t?e?this[0].scrollLeft:(a(this[0])?this[0]:this[0].defaultView).pageXOffset:this.each(e?function(){this.scrollLeft=t}:function(){this.scrollTo(t,this.scrollY)})},offset:function(o){var t;return o?this.each(function(t){var e=E(this),t=p(this,o,t,e.offset()),i=e.offsetParent().offset(),t={top:t.top-i.top,left:t.left-i.left};"static"==e.css("position")&&(t.position="relative"),e.css(t)}):this.length?w.documentElement===this[0]||b(w.documentElement,this[0])?{left:(t=this[0].getBoundingClientRect()).left+window.pageXOffset,top:t.top+window.pageYOffset,width:Math.round(t.width),height:Math.round(t.height)}:{top:0,left:0}:null},offsetParent:function(){return this.map(function(){for(var t=this.offsetParent||w.body;t&&!q.test(t.nodeName)&&"static"==E(t).css("position");)t=t.offsetParent;return t})},position:function(){var t,e,i,o;if(this.length)return t=this[0],i=this.offsetParent(),o=q.test(i[0].nodeName)?{top:0,left:0}:i.offset(),"fixed"===E(t).css("position")?e=t.getBoundingClientRect():(e=this.offset(),o.top+=parseFloat(E(i[0]).css("border-top-width"))||0,o.left+=parseFloat(E(i[0]).css("border-left-width"))||0),{top:e.top-o.top-parseFloat(E(t).css("margin-top"))||0,left:e.left-o.left-parseFloat(E(t).css("margin-left"))||0}},on:function(u,d,f,p,g){var m,v,i=this;return u&&!s(u)?(E.each(u,function(t,e){i.on(t,d,f,e,g)}),i):(s(d)||c(p)||!1===p||(p=f,f=d,d=void 0),void 0!==p&&!1!==f||(p=f,f=void 0),!1===p&&(p=lt),i.each(function(t,i){var o,e,n,s,a,r,h,l,c;g&&(m=function(t){return xt(i,t.type,p),p.apply(this,arguments)}),e=u,n=p,s=f,r=(v=(a=d)?function(t){var e=E(t.target).closest(d,i).get(0);if(e&&e!==i)return t=E.extend(function(t){var e,i={originalEvent:t};for(e in t)pt.test(e)||void 0===t[e]||(i[e]=t[e]);return mt(i,t)}(t),{currentTarget:e,liveFired:i}),(m||p).apply(e,[t].concat(y.call(arguments,1)))}:v)||m,l=z(o=i),c=x[l]||(x[l]=[]),e.split(/\s/).forEach(function(t){if("ready"==t)return E(w).ready(n);var e=vt(t),i=(e.fn=n,e.sel=a,e.e in ft&&(n=function(t){t=t.relatedTarget;if(!t||t!==this&&!b(this,t))return e.fn.apply(this,arguments)}),(e.del=r)||n);e.proxy=function(t){var e;if(!(t=mt(t)).isImmediatePropagationStopped())return t.data=s,!1===(e=i.apply(o,null==t._args?[t]:[t].concat(t._args)))&&(t.preventDefault(),t.stopPropagation()),e},e.i=c.length,c.push(e),"addEventListener"in o&&o.addEventListener(bt(e.e),e.proxy,yt(e,h))})}))},off:function(t,i,e){var o=this;return t&&!s(t)?(E.each(t,function(t,e){o.off(t,i,e)}),o):(s(i)||c(e)||!1===e||(e=i,i=void 0),!1===e&&(e=lt),o.each(function(){xt(this,t,e,i)}))},show:function(t,e){return Pt.call(this),void 0===t?t=0:this.css("opacity",0),Rt(this,t,1,"1,1",e)},hide:function(t,e){return void 0===t?St.call(this):(i=e,Rt(this,t,0,"0,0",function(){St.call(E(this)),i&&i.call(this)}));var i},anim:function(t,e,i,o,n){var s,a,r,h={},l="",c=this,u=E.fx.transitionEnd,d=!1;if(void 0===e&&(e=E.fx.speeds._default/1e3),void 0===n&&(n=0),E.fx.off&&(e=0),"string"==typeof t)h[Et]=t,h[Ht]=e+"s",h[Vt]=n+"s",h[kt]=i||"linear",u=E.fx.animationEnd;else{for(s in a=[],t)Dt.test(s)?l+=s+"("+t[s]+") ":(h[s]=t[s],a.push(s.replace(/([A-Z])/g,"-$1").toLowerCase()));l&&(h[$t]=l,a.push($t)),0\n \n ',maximize:'',close:'',zoomIn:'',zoomOut:'',prev:'',next:'',fullscreen:'',actualSize:'',rotateLeft:'',rotateRight:''},i18n:{minimize:"Minimize",maximize:"Maximize (Alt+X)",close:"Close (Q)",zoomIn:"Zoom-in (+)",zoomOut:"Zoom-out (-)",prev:"Prev (←)",next:"Next (→)",fullscreen:"Fullscreen (F)",actualSize:"Actual-size (Ctrl+Alt+0)",rotateLeft:"Rotate-left (Ctrl+,)",rotateRight:"Rotate-right (Ctrl+.)"},multiInstances:!0,initAnimation:!0,animationDuration:400,animationEasing:"ease-in-out",fixedModalPos:!1,zIndex:1090,dragHandle:null,callbacks:{beforeOpen:E.noop,opened:E.noop,beforeClose:E.noop,closed:E.noop,beforeChange:E.noop,changed:E.noop},index:0,progressiveLoading:!0,appendTo:"body",customButtons:{},positionFixed:!0,initModalPos:null,errorMsg:""}),It=window.document;function Ot(t,e,i,o){var n=o?t.h:t.w,o=o?t.w:t.h;(o>e.h||n>e.w)&&i.addClass("is-grab"),o<=e.h&&n<=e.w&&i.removeClass("is-grab")}function Ft(){return"ontouchstart"in window||window.DocumentTouch&&It instanceof window.DocumentTouch}function $(t){return/^(?:body|html)$/i.test(t.nodeName)}function T(i,t){return t.reduce(function(t,e){return t+parseFloat(i.css(e))},0)}function H(t){return"border-box"===t.css("box-sizing")}function jt(t,e,i,o,n){return n?Math.min(i/e,o/t,1):Math.min(i/t,o/e,1)}var C=E(window),k=E(It),L="click",Bt=Ft()?"touchstart":"mousedown",V=Ft()?"touchmove":"mousemove",D=Ft()?"touchend":"mouseup",P="photoviewer",_="."+P,S="."+P,R={isMoving:!1,isResizing:!1,zIndex:0};var Nt="html, body, .".concat(P,"-modal, .").concat(P,"-stage, .").concat(P,"-button, .").concat(P,"-resizable-handle");var Yt="html, body, .".concat(P,"-modal, .").concat(P,"-stage, .").concat(P,"-button");t=function(){function i(t,e){if(!(this instanceof i))throw new TypeError("Cannot call a class as a function");n(this,"isOpened",!1),n(this,"isMaximized",!1),n(this,"isRotated",!1),n(this,"rotationDegree",0),n(this,"imageData",{}),n(this,"modalData",{width:null,height:null,left:null,top:null}),n(this,"prevIndex",null),n(this,"_lastTimestamp",0),this.init(t,e)}var t,e,o;return t=i,(e=[{key:"init",value:function(t,e){this.options=E.extend(!0,{},At,e),e&&E.isArray(e.footerToolbar)&&(this.options.footerToolbar=e.footerToolbar),e&&E.isArray(e.headerToolbar)&&(this.options.headerToolbar=e.headerToolbar),R.zIndex=(0===R.zIndex?this.options:R).zIndex,this.open(),this.images=t,this.index=this.options.index,this._loadImage(this.index),this.options.draggable&&this.draggable(this.$photoviewer,this.dragHandle,_+"-button"),this.options.movable&&this.movable(this.$stage,this.$image),this.options.resizable&&this.resizable(this.$photoviewer,this.$stage,this.$image,this.options)}},{key:"_createBtns",value:function(t){var o=this,n=["minimize","maximize","close","zoomIn","zoomOut","prev","next","fullscreen","actualSize","rotateLeft","rotateRight"],s="";return E.each(t,function(t,e){var i="".concat(P,"-button ").concat(P,"-button-").concat(e);0<=n.indexOf(e)?s+='"):o.options.customButtons[e]&&(s+='"))}),s}},{key:"_createTitle",value:function(){return this.options.title?''):""}},{key:"_createTemplate",value:function(){return'\n
\n \n
\n
\n
\n \n
\n
").replace(/>\s+<")}},{key:"_build",value:function(){var t=this._createTemplate(),t=E(t);this.$photoviewer=t,this.$stage=t.find(_+"-stage"),this.$title=t.find(_+"-title"),this.$image=t.find(_+"-image"),this.$close=t.find(_+"-button-close"),this.$maximize=t.find(_+"-button-maximize"),this.$minimize=t.find(_+"-button-minimize"),this.$zoomIn=t.find(_+"-button-zoomIn"),this.$zoomOut=t.find(_+"-button-zoomOut"),this.$actualSize=t.find(_+"-button-actualSize"),this.$fullscreen=t.find(_+"-button-fullscreen"),this.$rotateLeft=t.find(_+"-button-rotateLeft"),this.$rotateRight=t.find(_+"-button-rotateRight"),this.$prev=t.find(_+"-button-prev"),this.$next=t.find(_+"-button-next"),this.$photoviewer.css("z-index",R.zIndex),this.options.positionFixed&&this.$photoviewer.css({position:"fixed"}),this.options.dragHandle&&this.options.dragHandle!==_+"-modal"?this.dragHandle=this.$photoviewer.find(this.options.dragHandle):this.dragHandle=this.$photoviewer,E(this.options.appendTo).eq(0).append(this.$photoviewer),this._stageEdgeValue={horizontal:T(this.$stage,["left","right","border-left-width","border-right-width"]),vertical:T(this.$stage,["top","bottom","border-top-width","border-bottom-width"])},this._modalEdgeValue={horizontal:T(this.$photoviewer,["padding-left","padding-right","border-left-width","border-right-width"]),vertical:T(this.$photoviewer,["padding-top","padding-bottom","border-top-width","border-bottom-width"])},this._addEvents(),this._addCustomButtonEvents()}},{key:"open",value:function(){this._triggerHook("beforeOpen",this),!this.options.multiInstances&&0')),this.$stage.addClass(P+"-align-center"),this.options.initAnimation&&!this.options.progressiveLoading&&this.$image.hide(),null==(null==(s=this.images[t])?void 0:s.src)?"":this.images[t].src.toString()),a=(this.$image.attr("src",s),(null==(a=this.images[t])?void 0:a.title)||s.replace(/^.*?\/*([^/?]*)\.[a-z]+(\?.+|$)/gi,"$1"));this.options.title&&this.$title.html(a),this.$image.attr("alt",a),a=s,e=function(t){n.imageData={originalWidth:t.width,originalHeight:t.height},n.isMaximized||n.isOpened&&n.options.fixedModalPos?n._setImageSize():n._setModalSize()},i=function(){n.$photoviewer.find(_+"-loader").remove(),n._triggerHook("changed",[n,t]),n._setErrorMsg()},(o=new Image).onload=function(){e(o)},o.onerror=function(){i(o)},o.src=a}},{key:"_setErrorMsg",value:function(){var t=E.isFunction(this.options.errorMsg)?this.options.errorMsg(this,this.index):this.options.errorMsg;t&&(this.$stage.append('').concat(t,"")),this.$image.addClass(P+"-image-error"))}},{key:"_removeErrorMsg",value:function(){this.$stage.find(_+"-error-msg").remove(),this.$image.removeClass(P+"-image-error")}},{key:"jump",value:function(t){var e=Date.now();e-this._lastTimestamp>=this.options.animationDuration&&(t=this.index+t,this.jumpTo(t),this._lastTimestamp=e)}},{key:"jumpTo",value:function(t){this.prevIndex=this.index;t%=this.images.length;t<=0&&(t=(t+this.images.length)%this.images.length),this.index=t,this._loadImage(this.index)}},{key:"_wheel",value:function(t){t.preventDefault();var e=1,e=(t.deltaY?e=0this.options.maxRatio||t')),i=E('')),n=E('')),s=E('')),h=E('')),c=E('')),u=E('')),d=E('')),f={e:e,s:n,se:h,n:s,w:i,nw:d,ne:u,sw:c},p=(o.append(e,i,n,s,h,c,u,d),0),g=0,m={w:0,h:0,x:0,y:0},v={w:0,h:0,x:0,y:0},w={w:0,h:0,x:0,y:0},y=0,b=0,x=0,z="",M=t.modalWidth,$=t.modalHeight,T=function(t,e,i){var o=-e+m.w>M?e+m.x:m.x+m.w-M,n=-i+m.h>$?i+m.y:m.y+m.h-$;return{e:{width:Math.max(e+m.w,M)},s:{height:Math.max(i+m.h,$)},se:{width:Math.max(e+m.w,M),height:Math.max(i+m.h,$)},w:{width:Math.max(-e+m.w,M),left:o},n:{height:Math.max(-i+m.h,$),top:n},nw:{width:Math.max(-e+m.w,M),height:Math.max(-i+m.h,$),top:n,left:o},ne:{width:Math.max(e+m.w,M),height:Math.max(-i+m.h,$),top:n},sw:{width:Math.max(-e+m.w,M),height:Math.max(i+m.h,$),left:o}}[t]},C=function(t,e,i){var o=e+m.w>M?v.w-b+e-y:M-(m.w-v.w)-b-y,n=i+m.h>$?v.h-x+i+y:$-(m.h-v.h)-x+y,e=-e+m.w>M?v.w-b-e-y:M-(m.w-v.w)-b-y,i=-i+m.h>$?v.h-x-i+y:$-(m.h-v.h)-x+y,s=l.position().left,a=l.position().top,r=(0\n \n
\n
\n ").concat(this._createBtns(this.options.headerToolbar), "\n
\n ").concat(this._createTitle(), "\n
\n
\n
\n
\n
\n
\n ").concat(this._createBtns(this.options.footerToolbar), "\n
\n
\n
\n ");
- return photoviewerHTML;
+ return photoviewerHTML.replace(/>\s+<');
}
}, {
key: "_build",
@@ -2091,10 +2096,6 @@
this.$prev = $photoviewer.find(CLASS_NS + '-button-prev');
this.$next = $photoviewer.find(CLASS_NS + '-button-next');
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
-
// Reset the modal `z-index` of multiple instances
this.$photoviewer.css('z-index', PUBLIC_VARS['zIndex']);
if (this.options.positionFixed) {
@@ -2311,44 +2312,51 @@
if (!this.imageLoaded) {
// Loader end
this.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Remove init classes after image loaded
- this.$stage.removeClass('stage-ready');
- this.$image.removeClass('image-ready');
+ // The class must be removed after image loaded
+ this.$stage.removeClass(NS + '-align-center');
// Add init animation for image
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.fadeIn();
}
this.imageLoaded = true;
+ this._triggerHook('changed', [this, this.index]);
}
}
}, {
key: "_loadImage",
- value: function _loadImage(index, fn, err) {
+ value: function _loadImage(index) {
var _this$images$index,
+ _this$images$index2,
_this4 = this;
- var imgSrc = (_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src;
- if (!imgSrc) {
- return;
- }
+ // Flag for both image loaded and animation finished
+ this.imageLoaded = false;
+ this._triggerHook('beforeChange', [this, this.prevIndex]);
+ this._removeErrorMsg();
- // Reset the image src
+ // Reset the image src and rotation status
this.$image.removeAttr('style').attr('src', '');
this.isRotated = false;
this.rotationDegree = 0;
- this.imageLoaded = false;
// Loader start
this.$photoviewer.append(""));
-
- // Add init classes before image loaded
- this.$stage.addClass('stage-ready');
- this.$image.addClass('image-ready');
+ // Used for centering image
+ this.$stage.addClass(NS + '-align-center');
if (this.options.initAnimation && !this.options.progressiveLoading) {
this.$image.hide();
}
+
+ // The image src must be a string
+ var imgSrc = ((_this$images$index = this.images[index]) === null || _this$images$index === void 0 ? void 0 : _this$images$index.src) == null ? '' : this.images[index].src.toString();
+
+ // Get image with src
this.$image.attr('src', imgSrc);
+ var title = ((_this$images$index2 = this.images[index]) === null || _this$images$index2 === void 0 ? void 0 : _this$images$index2.title) || getImageNameFromUrl(imgSrc);
+ if (this.options.title) {
+ this.$title.html(title);
+ }
+ this.$image.attr('alt', title);
preloadImage(imgSrc, function (img) {
// Store the original image size
_this4.imageData = {
@@ -2360,59 +2368,49 @@
} else {
_this4._setModalSize();
}
-
- // Callback of the image loaded successfully
- if (fn) {
- fn.call();
- }
}, function () {
// Loader end
_this4.$photoviewer.find(CLASS_NS + '-loader').remove();
-
- // Callback of the image loading failed
- if (err) {
- err.call();
- }
+ _this4._triggerHook('changed', [_this4, index]);
+ _this4._setErrorMsg();
});
- if (this.options.title && imgSrc) {
- this._setImageTitle(imgSrc);
+ }
+ }, {
+ key: "_setErrorMsg",
+ value: function _setErrorMsg() {
+ var errorMsg = D.isFunction(this.options.errorMsg) ? this.options.errorMsg(this, this.index) : this.options.errorMsg;
+ if (errorMsg) {
+ this.$stage.append("").concat(errorMsg, ""));
+ this.$image.addClass(NS + '-image-error');
}
}
}, {
- key: "_setImageTitle",
- value: function _setImageTitle(url) {
- var title = this.images[this.index].title || getImageNameFromUrl(url);
- this.$title.html(title);
+ key: "_removeErrorMsg",
+ value: function _removeErrorMsg() {
+ this.$stage.find(CLASS_NS + '-error-msg').remove();
+ this.$image.removeClass(NS + '-image-error');
}
}, {
key: "jump",
value: function jump(step) {
- this._triggerHook('beforeChange', [this, this.index]);
-
- // Only allow to change image after the modal animation has finished
+ // Allow to change image only after the modal animation has finished
var now = Date.now();
if (now - this._lastTimestamp >= this.options.animationDuration) {
- this.index = this.index + step;
- this.jumpTo(this.index);
+ var newIndex = this.index + step;
+ this.jumpTo(newIndex);
this._lastTimestamp = now;
}
}
}, {
key: "jumpTo",
value: function jumpTo(index) {
- var _this5 = this;
- index = index % this.images.length;
- if (index >= 0) {
- index = index % this.images.length;
- } else if (index < 0) {
- index = (this.images.length + index) % this.images.length;
+ this.prevIndex = this.index;
+ var newIndex = index % this.images.length;
+ if (newIndex <= 0) {
+ newIndex = (newIndex + this.images.length) % this.images.length;
}
- this.index = index;
- this._loadImage(index, function () {
- _this5._triggerHook('changed', [_this5, index]);
- }, function () {
- _this5._triggerHook('changed', [_this5, index]);
- });
+ this.index = newIndex;
+ this._loadImage(this.index);
}
}, {
key: "_wheel",
@@ -2703,54 +2701,54 @@
}, {
key: "_addEvents",
value: function _addEvents() {
- var _this6 = this;
+ var _this5 = this;
this.$close.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.close();
+ _this5.close();
});
this.$stage.on(WHEEL_EVENT + EVENT_NS, function (e) {
- _this6._wheel(e);
+ _this5._wheel(e);
});
this.$zoomIn.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(_this6.options.ratioThreshold * 3);
+ _this5.zoom(_this5.options.ratioThreshold * 3);
});
this.$zoomOut.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoom(-_this6.options.ratioThreshold * 3);
+ _this5.zoom(-_this5.options.ratioThreshold * 3);
});
this.$actualSize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.zoomTo(1);
+ _this5.zoomTo(1);
});
this.$prev.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(-1);
+ _this5.jump(-1);
});
this.$next.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.jump(1);
+ _this5.jump(1);
});
this.$rotateLeft.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(-90);
+ _this5.rotate(-90);
});
this.$rotateRight.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.rotate(90);
+ _this5.rotate(90);
});
this.$maximize.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.toggleMaximize();
+ _this5.toggleMaximize();
});
this.$fullscreen.on(CLICK_EVENT + EVENT_NS, function () {
- _this6.fullscreen();
+ _this5.fullscreen();
});
this.$photoviewer.on(KEYDOWN_EVENT + EVENT_NS, function (e) {
- _this6._keydown(e);
+ _this5._keydown(e);
});
$W.on(RESIZE_EVENT + EVENT_NS, debounce(function () {
- return _this6.resize();
+ return _this5.resize();
}, 500));
}
}, {
key: "_addCustomButtonEvents",
value: function _addCustomButtonEvents() {
- var _this7 = this;
+ var _this6 = this;
var _loop = function _loop(btnKey) {
- _this7.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
- _this7.options.customButtons[btnKey].click.apply(_this7, [_this7, e]);
+ _this6.$photoviewer.find(CLASS_NS + '-button-' + btnKey).on(CLICK_EVENT + EVENT_NS, function (e) {
+ _this6.options.customButtons[btnKey].click.apply(_this6, [_this6, e]);
});
};
for (var btnKey in this.options.customButtons) {
diff --git a/package.json b/package.json
index 9a84013..aa2ee4a 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "photoviewer",
- "version": "3.9.2",
+ "version": "3.10.0",
"description": "A JS plugin to view images just like in Windows.",
"main": "src/js/photoviewer.js",
"types": "types/index.d.ts",