1
0
mirror of https://github.com/beestat/app.git synced 2025-05-24 02:14:03 -04:00
beestat/js/component/modal.js
Jon Ziebell c3891ffff8 Added 3D viewer to Visualize
Added 3D viewer to Visualize
2022-08-18 21:40:35 -04:00

266 lines
6.7 KiB
JavaScript

/**
* Modal
*/
beestat.component.modal = function() {
beestat.component.apply(this, arguments);
};
beestat.extend(beestat.component.modal, beestat.component);
beestat.component.modal.prototype.decorate_ = function() {
var self = this;
var mask = $.createElement('div')
.style({
'position': 'fixed',
'top': '0',
'left': '0',
'width': '100%',
'height': '100%',
'vertical-align': 'middle',
'transition': 'background 200ms ease'
});
$('body').appendChild(mask);
var modal = $.createElement('div');
beestat.style.set(
modal,
{
'max-width': '700px',
'padding': beestat.style.size.gutter,
'position': 'absolute',
'top': '100px',
'left': '50%',
'transform': 'translateX(-50%)',
'width': '100%',
'transition': 'transform 200ms ease'
},
{
'(max-width: 900px)': {
'top': '0px'
}
}
);
modal.style('transform', 'translateX(-50%) scale(0)');
mask.appendChild(modal);
this.modal_content_ = $.createElement('div');
beestat.style.set(
this.modal_content_,
{
'background': '#fff',
'padding': beestat.style.size.gutter,
'color': beestat.style.color.bluegray.dark,
'max-height': 'calc(100vh - ' + (200 + (beestat.style.size.gutter * 2)) + 'px)',
'overflow': 'auto',
'border-radius': beestat.style.size.border_radius,
'min-height': '200px'
},
{
'(max-width: 900px)': {
'max-height': 'calc(100vh - ' + (beestat.style.size.gutter * 2) + 'px)'
}
}
);
modal.appendChild(this.modal_content_);
this.mask_ = mask;
this.modal_ = modal;
/*
* Blur the body
* Fade in the mask
* Overpop the modal
*/
this.timeout_1_ = window.setTimeout(function() {
$('body').firstElementChild()
.style('filter', 'blur(3px)');
mask.style('background', 'rgba(0, 0, 0, 0.5)');
modal.style('transform', 'translateX(-50%) scale(1.05)');
}, 0);
// Pop the modal back to normal size
this.timeout_2_ = window.setTimeout(function() {
modal.style('transform', 'translateX(-50%) scale(1)');
}, 250);
// Escape to close
$(window).addEventListener('keydown.modal', function(e) {
if (e.which === 27) {
self.dispose();
}
});
// Click the mask to close
$(window).addEventListener('click.modal', function(e) {
if (e.target === mask[0]) {
self.dispose();
}
});
this.decorate_header_(this.modal_content_);
this.decorate_contents_(this.modal_content_);
this.decorate_buttons_(this.modal_content_);
};
/**
* Close the currently open modal.
*/
beestat.component.modal.prototype.dispose = function() {
if (this.rendered_ === true) {
var self = this;
window.clearTimeout(this.timeout_1_);
window.clearTimeout(this.timeout_2_);
this.modal_.style('transform', 'translateX(-50%) scale(0)');
this.mask_.style('background', 'rgba(0, 0, 0, 0)');
$('body').firstElementChild()
.style('filter', '');
window.setTimeout(function() {
self.modal_.parentNode().removeChild(self.modal_);
self.mask_.parentNode().removeChild(self.mask_);
delete self.mask_;
delete self.modal_;
}, 200);
$(window).removeEventListener('keydown.modal');
$(window).removeEventListener('click.modal');
this.rendered_ = false;
}
};
/**
* Overridden rerender function which just brazenly deletes content and writes
* it again. RIP event listeners. Had to do this since modal rendering does
* all the fancy animation and that is not desirable when rerendering.
*/
beestat.component.modal.prototype.rerender = function() {
if (this.rendered_ === true) {
this.modal_content_.innerHTML('');
this.decorate_header_(this.modal_content_);
this.decorate_contents_(this.modal_content_);
this.decorate_buttons_(this.modal_content_);
}
};
/**
* Decorate the header bar with the title and close icon.
*
* @param {rocket.Elements} parent
*/
beestat.component.modal.prototype.decorate_header_ = function(parent) {
var row = $.createElement('div')
.style({
'display': 'flex',
'align-items': 'center'
});
parent.appendChild(row);
var column_title = $.createElement('div')
.style({
'flex': '1'
});
row.appendChild(column_title);
this.decorate_title_(column_title);
var column_close = $.createElement('div')
.style({
'flex': '0 0 50px',
'text-align': 'right'
});
row.appendChild(column_close);
this.decorate_close_(column_close);
};
/**
* Decorate the title of the modal.
*
* @param {rocket.Elements} parent
*/
beestat.component.modal.prototype.decorate_title_ = function(parent) {
var title = this.get_title_();
if (title !== undefined) {
parent.appendChild($.createElement('div')
.innerHTML(title)
.style({
'font-weight': beestat.style.font_weight.bold,
'font-size': beestat.style.font_size.extra_large,
'white-space': 'nowrap',
'overflow': 'hidden',
'text-overflow': 'ellipsis'
}));
}
};
/**
* Decorate the close button.
*
* @param {rocket.Elements} parent
*/
beestat.component.modal.prototype.decorate_close_ = function(parent) {
var self = this;
var close = new beestat.component.tile()
.set_type('pill')
.set_shadow(false)
.set_icon('close')
.set_text_color(beestat.style.color.gray.dark)
.set_background_hover_color(beestat.style.color.gray.light)
.addEventListener('click', function() {
self.dispose();
});
close.render(parent);
};
/**
* Decorate the contents of the modal.
*/
beestat.component.modal.prototype.decorate_contents_ = function() {
// Stub
};
/**
* Get the buttons that go on the bottom of this modal.
*
* @return {[beestat.component.button]} The buttons.
*/
beestat.component.modal.prototype.get_buttons_ = function() {
return [];
};
/**
* Decorate the buttons on the bottom right of the modal.
*
* @param {rocket.Elements} parent
*/
beestat.component.modal.prototype.decorate_buttons_ = function(parent) {
var buttons = this.get_buttons_();
if (buttons.length > 0) {
var container = $.createElement('div')
.style({
'margin-top': beestat.style.size.gutter,
'text-align': 'right'
});
parent.appendChild(container);
var tile_group = new beestat.component.tile_group();
buttons.forEach(function(button) {
tile_group.add_tile(button);
});
tile_group.render(container);
}
};
/**
* Get the title of the modal.
*/
beestat.component.modal.prototype.get_title_ = function() {
// Stub
};