Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/matomo-org/matomo.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'node_modules/materialize-css/js/materialbox.js')
-rw-r--r--node_modules/materialize-css/js/materialbox.js453
1 files changed, 453 insertions, 0 deletions
diff --git a/node_modules/materialize-css/js/materialbox.js b/node_modules/materialize-css/js/materialbox.js
new file mode 100644
index 0000000000..f682db54ff
--- /dev/null
+++ b/node_modules/materialize-css/js/materialbox.js
@@ -0,0 +1,453 @@
+(function($, anim) {
+ 'use strict';
+
+ let _defaults = {
+ inDuration: 275,
+ outDuration: 200,
+ onOpenStart: null,
+ onOpenEnd: null,
+ onCloseStart: null,
+ onCloseEnd: null
+ };
+
+ /**
+ * @class
+ *
+ */
+ class Materialbox extends Component {
+ /**
+ * Construct Materialbox instance
+ * @constructor
+ * @param {Element} el
+ * @param {Object} options
+ */
+ constructor(el, options) {
+ super(Materialbox, el, options);
+
+ this.el.M_Materialbox = this;
+
+ /**
+ * Options for the modal
+ * @member Materialbox#options
+ * @prop {Number} [inDuration=275] - Length in ms of enter transition
+ * @prop {Number} [outDuration=200] - Length in ms of exit transition
+ * @prop {Function} onOpenStart - Callback function called before materialbox is opened
+ * @prop {Function} onOpenEnd - Callback function called after materialbox is opened
+ * @prop {Function} onCloseStart - Callback function called before materialbox is closed
+ * @prop {Function} onCloseEnd - Callback function called after materialbox is closed
+ */
+ this.options = $.extend({}, Materialbox.defaults, options);
+
+ this.overlayActive = false;
+ this.doneAnimating = true;
+ this.placeholder = $('<div></div>').addClass('material-placeholder');
+ this.originalWidth = 0;
+ this.originalHeight = 0;
+ this.originInlineStyles = this.$el.attr('style');
+ this.caption = this.el.getAttribute('data-caption') || '';
+
+ // Wrap
+ this.$el.before(this.placeholder);
+ this.placeholder.append(this.$el);
+
+ this._setupEventHandlers();
+ }
+
+ static get defaults() {
+ return _defaults;
+ }
+
+ static init(els, options) {
+ return super.init(this, els, options);
+ }
+
+ /**
+ * Get Instance
+ */
+ static getInstance(el) {
+ let domElem = !!el.jquery ? el[0] : el;
+ return domElem.M_Materialbox;
+ }
+
+ /**
+ * Teardown component
+ */
+ destroy() {
+ this._removeEventHandlers();
+ this.el.M_Materialbox = undefined;
+
+ // Unwrap image
+ $(this.placeholder)
+ .after(this.el)
+ .remove();
+
+ this.$el.removeAttr('style');
+ }
+
+ /**
+ * Setup Event Handlers
+ */
+ _setupEventHandlers() {
+ this._handleMaterialboxClickBound = this._handleMaterialboxClick.bind(this);
+ this.el.addEventListener('click', this._handleMaterialboxClickBound);
+ }
+
+ /**
+ * Remove Event Handlers
+ */
+ _removeEventHandlers() {
+ this.el.removeEventListener('click', this._handleMaterialboxClickBound);
+ }
+
+ /**
+ * Handle Materialbox Click
+ * @param {Event} e
+ */
+ _handleMaterialboxClick(e) {
+ // If already modal, return to original
+ if (this.doneAnimating === false || (this.overlayActive && this.doneAnimating)) {
+ this.close();
+ } else {
+ this.open();
+ }
+ }
+
+ /**
+ * Handle Window Scroll
+ */
+ _handleWindowScroll() {
+ if (this.overlayActive) {
+ this.close();
+ }
+ }
+
+ /**
+ * Handle Window Resize
+ */
+ _handleWindowResize() {
+ if (this.overlayActive) {
+ this.close();
+ }
+ }
+
+ /**
+ * Handle Window Resize
+ * @param {Event} e
+ */
+ _handleWindowEscape(e) {
+ // ESC key
+ if (e.keyCode === 27 && this.doneAnimating && this.overlayActive) {
+ this.close();
+ }
+ }
+
+ /**
+ * Find ancestors with overflow: hidden; and make visible
+ */
+ _makeAncestorsOverflowVisible() {
+ this.ancestorsChanged = $();
+ let ancestor = this.placeholder[0].parentNode;
+ while (ancestor !== null && !$(ancestor).is(document)) {
+ let curr = $(ancestor);
+ if (curr.css('overflow') !== 'visible') {
+ curr.css('overflow', 'visible');
+ if (this.ancestorsChanged === undefined) {
+ this.ancestorsChanged = curr;
+ } else {
+ this.ancestorsChanged = this.ancestorsChanged.add(curr);
+ }
+ }
+ ancestor = ancestor.parentNode;
+ }
+ }
+
+ /**
+ * Animate image in
+ */
+ _animateImageIn() {
+ let animOptions = {
+ targets: this.el,
+ height: [this.originalHeight, this.newHeight],
+ width: [this.originalWidth, this.newWidth],
+ left:
+ M.getDocumentScrollLeft() +
+ this.windowWidth / 2 -
+ this.placeholder.offset().left -
+ this.newWidth / 2,
+ top:
+ M.getDocumentScrollTop() +
+ this.windowHeight / 2 -
+ this.placeholder.offset().top -
+ this.newHeight / 2,
+ duration: this.options.inDuration,
+ easing: 'easeOutQuad',
+ complete: () => {
+ this.doneAnimating = true;
+
+ // onOpenEnd callback
+ if (typeof this.options.onOpenEnd === 'function') {
+ this.options.onOpenEnd.call(this, this.el);
+ }
+ }
+ };
+
+ // Override max-width or max-height if needed
+ this.maxWidth = this.$el.css('max-width');
+ this.maxHeight = this.$el.css('max-height');
+ if (this.maxWidth !== 'none') {
+ animOptions.maxWidth = this.newWidth;
+ }
+ if (this.maxHeight !== 'none') {
+ animOptions.maxHeight = this.newHeight;
+ }
+
+ anim(animOptions);
+ }
+
+ /**
+ * Animate image out
+ */
+ _animateImageOut() {
+ let animOptions = {
+ targets: this.el,
+ width: this.originalWidth,
+ height: this.originalHeight,
+ left: 0,
+ top: 0,
+ duration: this.options.outDuration,
+ easing: 'easeOutQuad',
+ complete: () => {
+ this.placeholder.css({
+ height: '',
+ width: '',
+ position: '',
+ top: '',
+ left: ''
+ });
+
+ // Revert to width or height attribute
+ if (this.attrWidth) {
+ this.$el.attr('width', this.attrWidth);
+ }
+ if (this.attrHeight) {
+ this.$el.attr('height', this.attrHeight);
+ }
+
+ this.$el.removeAttr('style');
+ this.originInlineStyles && this.$el.attr('style', this.originInlineStyles);
+
+ // Remove class
+ this.$el.removeClass('active');
+ this.doneAnimating = true;
+
+ // Remove overflow overrides on ancestors
+ if (this.ancestorsChanged.length) {
+ this.ancestorsChanged.css('overflow', '');
+ }
+
+ // onCloseEnd callback
+ if (typeof this.options.onCloseEnd === 'function') {
+ this.options.onCloseEnd.call(this, this.el);
+ }
+ }
+ };
+
+ anim(animOptions);
+ }
+
+ /**
+ * Update open and close vars
+ */
+ _updateVars() {
+ this.windowWidth = window.innerWidth;
+ this.windowHeight = window.innerHeight;
+ this.caption = this.el.getAttribute('data-caption') || '';
+ }
+
+ /**
+ * Open Materialbox
+ */
+ open() {
+ this._updateVars();
+ this.originalWidth = this.el.getBoundingClientRect().width;
+ this.originalHeight = this.el.getBoundingClientRect().height;
+
+ // Set states
+ this.doneAnimating = false;
+ this.$el.addClass('active');
+ this.overlayActive = true;
+
+ // onOpenStart callback
+ if (typeof this.options.onOpenStart === 'function') {
+ this.options.onOpenStart.call(this, this.el);
+ }
+
+ // Set positioning for placeholder
+ this.placeholder.css({
+ width: this.placeholder[0].getBoundingClientRect().width + 'px',
+ height: this.placeholder[0].getBoundingClientRect().height + 'px',
+ position: 'relative',
+ top: 0,
+ left: 0
+ });
+
+ this._makeAncestorsOverflowVisible();
+
+ // Set css on origin
+ this.$el.css({
+ position: 'absolute',
+ 'z-index': 1000,
+ 'will-change': 'left, top, width, height'
+ });
+
+ // Change from width or height attribute to css
+ this.attrWidth = this.$el.attr('width');
+ this.attrHeight = this.$el.attr('height');
+ if (this.attrWidth) {
+ this.$el.css('width', this.attrWidth + 'px');
+ this.$el.removeAttr('width');
+ }
+ if (this.attrHeight) {
+ this.$el.css('width', this.attrHeight + 'px');
+ this.$el.removeAttr('height');
+ }
+
+ // Add overlay
+ this.$overlay = $('<div id="materialbox-overlay"></div>')
+ .css({
+ opacity: 0
+ })
+ .one('click', () => {
+ if (this.doneAnimating) {
+ this.close();
+ }
+ });
+
+ // Put before in origin image to preserve z-index layering.
+ this.$el.before(this.$overlay);
+
+ // Set dimensions if needed
+ let overlayOffset = this.$overlay[0].getBoundingClientRect();
+ this.$overlay.css({
+ width: this.windowWidth + 'px',
+ height: this.windowHeight + 'px',
+ left: -1 * overlayOffset.left + 'px',
+ top: -1 * overlayOffset.top + 'px'
+ });
+
+ anim.remove(this.el);
+ anim.remove(this.$overlay[0]);
+
+ // Animate Overlay
+ anim({
+ targets: this.$overlay[0],
+ opacity: 1,
+ duration: this.options.inDuration,
+ easing: 'easeOutQuad'
+ });
+
+ // Add and animate caption if it exists
+ if (this.caption !== '') {
+ if (this.$photocaption) {
+ anim.remove(this.$photoCaption[0]);
+ }
+ this.$photoCaption = $('<div class="materialbox-caption"></div>');
+ this.$photoCaption.text(this.caption);
+ $('body').append(this.$photoCaption);
+ this.$photoCaption.css({ display: 'inline' });
+
+ anim({
+ targets: this.$photoCaption[0],
+ opacity: 1,
+ duration: this.options.inDuration,
+ easing: 'easeOutQuad'
+ });
+ }
+
+ // Resize Image
+ let ratio = 0;
+ let widthPercent = this.originalWidth / this.windowWidth;
+ let heightPercent = this.originalHeight / this.windowHeight;
+ this.newWidth = 0;
+ this.newHeight = 0;
+
+ if (widthPercent > heightPercent) {
+ ratio = this.originalHeight / this.originalWidth;
+ this.newWidth = this.windowWidth * 0.9;
+ this.newHeight = this.windowWidth * 0.9 * ratio;
+ } else {
+ ratio = this.originalWidth / this.originalHeight;
+ this.newWidth = this.windowHeight * 0.9 * ratio;
+ this.newHeight = this.windowHeight * 0.9;
+ }
+
+ this._animateImageIn();
+
+ // Handle Exit triggers
+ this._handleWindowScrollBound = this._handleWindowScroll.bind(this);
+ this._handleWindowResizeBound = this._handleWindowResize.bind(this);
+ this._handleWindowEscapeBound = this._handleWindowEscape.bind(this);
+
+ window.addEventListener('scroll', this._handleWindowScrollBound);
+ window.addEventListener('resize', this._handleWindowResizeBound);
+ window.addEventListener('keyup', this._handleWindowEscapeBound);
+ }
+
+ /**
+ * Close Materialbox
+ */
+ close() {
+ this._updateVars();
+ this.doneAnimating = false;
+
+ // onCloseStart callback
+ if (typeof this.options.onCloseStart === 'function') {
+ this.options.onCloseStart.call(this, this.el);
+ }
+
+ anim.remove(this.el);
+ anim.remove(this.$overlay[0]);
+
+ if (this.caption !== '') {
+ anim.remove(this.$photoCaption[0]);
+ }
+
+ // disable exit handlers
+ window.removeEventListener('scroll', this._handleWindowScrollBound);
+ window.removeEventListener('resize', this._handleWindowResizeBound);
+ window.removeEventListener('keyup', this._handleWindowEscapeBound);
+
+ anim({
+ targets: this.$overlay[0],
+ opacity: 0,
+ duration: this.options.outDuration,
+ easing: 'easeOutQuad',
+ complete: () => {
+ this.overlayActive = false;
+ this.$overlay.remove();
+ }
+ });
+
+ this._animateImageOut();
+
+ // Remove Caption + reset css settings on image
+ if (this.caption !== '') {
+ anim({
+ targets: this.$photoCaption[0],
+ opacity: 0,
+ duration: this.options.outDuration,
+ easing: 'easeOutQuad',
+ complete: () => {
+ this.$photoCaption.remove();
+ }
+ });
+ }
+ }
+ }
+
+ M.Materialbox = Materialbox;
+
+ if (M.jQueryLoaded) {
+ M.initializeJqueryWrapper(Materialbox, 'materialbox', 'M_Materialbox');
+ }
+})(cash, M.anime);