ModelHandle/source/website/dialog.js
2022-07-10 19:02:29 +02:00

245 lines
6.1 KiB
JavaScript

import { AddDiv, CreateDiv } from '../engine/viewer/domutils.js';
import { AddSvgIconElement, CreateInlineColorCircle, IsHoverEnabled } from './utils.js';
let currentDialog = null;
export function CloseAllDialogs ()
{
if (currentDialog === null) {
return;
}
currentDialog.Close ();
currentDialog = null;
}
function OnCloseDialog ()
{
currentDialog = null;
}
function OnOpenDialog (dialog)
{
CloseAllDialogs ();
currentDialog = dialog;
}
class Dialog
{
constructor ()
{
this.modalDiv = CreateDiv ('ov_modal');
this.modalDiv.addEventListener ('mousemove', (ev) => {
ev.stopPropagation ();
});
this.overlayDiv = null;
this.resizeHandler = null;
this.positionCalculator = null;
this.closeHandler = null;
this.isOpen = false;
this.closeable = true;
}
GetContentDiv ()
{
return this.modalDiv;
}
SetCloseable (closeable)
{
this.closeable = closeable;
}
SetPositionCalculator (positionCalculator)
{
this.positionCalculator = positionCalculator;
}
SetCloseHandler (closeHandler)
{
this.closeHandler = closeHandler;
}
Open ()
{
if (this.isOpen) {
return;
}
OnOpenDialog (this);
this.overlayDiv = AddDiv (document.body, 'ov_modal_overlay');
document.body.appendChild (this.modalDiv);
this.resizeHandler = this.Resize.bind (this);
window.addEventListener ('resize', this.resizeHandler);
if (this.closeable) {
this.overlayDiv.addEventListener ('click', (ev) => {
ev.preventDefault ();
this.Close ();
});
this.overlayDiv.addEventListener ('mousemove', (ev) => {
ev.stopPropagation ();
});
this.overlayDiv.addEventListener ('contextmenu', (ev) => {
ev.preventDefault ();
this.Close ();
});
}
this.isOpen = true;
this.Resize ();
}
Close ()
{
if (!this.isOpen) {
return;
}
OnCloseDialog ();
window.removeEventListener ('resize', this.resizeHandler);
if (this.closeHandler !== null) {
this.closeHandler ();
}
this.modalDiv.remove ();
this.overlayDiv.remove ();
this.overlayDiv = null;
this.resizeHandler = null;
this.isOpen = false;
}
Resize ()
{
let windowWidth = window.innerWidth;
let windowHeight = window.innerHeight;
let positionX = (windowWidth - this.modalDiv.offsetWidth) / 2;
let positionY = (windowHeight - this.modalDiv.offsetHeight) / 3;
if (this.positionCalculator !== null) {
let calculatedPosition = this.positionCalculator ();
positionX = calculatedPosition.x;
positionY = calculatedPosition.y;
}
this.modalDiv.style.left = positionX + 'px';
this.modalDiv.style.top = positionY + 'px';
}
}
export class ProgressDialog extends Dialog
{
constructor ()
{
super ();
this.SetCloseable (false);
this.textDiv = null;
}
Init (text)
{
let contentDiv = this.GetContentDiv ();
contentDiv.classList.add ('ov_progress');
AddDiv (contentDiv, 'ov_progress_img', '<svg><use href="assets/images/3dviewer_net_logo.svg#logo"></use></svg>');
this.textDiv = AddDiv (contentDiv, 'ov_progress_text');
this.SetText (text);
}
SetText (text)
{
this.textDiv.innerHTML = text;
}
}
export class ButtonDialog extends Dialog
{
constructor ()
{
super ();
}
Init (title, buttons)
{
function AddButton (button, buttonsDiv)
{
let buttonDiv = AddDiv (buttonsDiv, 'ov_button ov_dialog_button', button.name);
if (button.subClass) {
buttonDiv.classList.add (button.subClass);
}
buttonDiv.addEventListener ('click', () => {
button.onClick ();
});
}
let contentDiv = this.GetContentDiv ();
contentDiv.classList.add ('ov_dialog');
AddDiv (contentDiv, 'ov_dialog_title', title);
let dialogContentDiv = AddDiv (contentDiv, 'ov_dialog_content');
let buttonsDiv = AddDiv (contentDiv, 'ov_dialog_buttons');
let buttonsInnerDiv = AddDiv (buttonsDiv, 'ov_dialog_buttons_inner');
for (let i = 0; i < buttons.length; i++) {
AddButton (buttons[i], buttonsInnerDiv);
}
return dialogContentDiv;
}
}
export class PopupDialog extends Dialog
{
constructor ()
{
super ();
}
Init (positionCalculator)
{
let contentDiv = this.GetContentDiv ();
contentDiv.classList.add ('ov_popup');
this.SetPositionCalculator (positionCalculator);
return contentDiv;
}
}
export class ListPopup extends PopupDialog
{
constructor ()
{
super ();
this.listDiv = null;
}
Init (positionCalculator)
{
let contentDiv = super.Init (positionCalculator);
this.listDiv = AddDiv (contentDiv, 'ov_popup_list ov_thin_scrollbar');
return contentDiv;
}
AddListItem (item, callbacks)
{
let listItemDiv = AddDiv (this.listDiv, 'ov_popup_list_item');
if (item.icon) {
AddSvgIconElement (listItemDiv, item.icon, 'left_inline');
}
if (item.color) {
let iconDiv = AddDiv (listItemDiv, 'ov_popup_list_item_icon');
let colorCircle = CreateInlineColorCircle (item.color);
iconDiv.appendChild (colorCircle);
}
AddDiv (listItemDiv, 'ov_popup_list_item_name', item.name);
listItemDiv.addEventListener ('click', callbacks.onClick);
if (IsHoverEnabled () && callbacks.onHoverStart && callbacks.onHoverStop) {
listItemDiv.addEventListener ('mouseover', () => {
callbacks.onHoverStart ();
});
listItemDiv.addEventListener ('mouseout', () => {
callbacks.onHoverStop ();
});
}
}
}