From fd89925920a1aebe61950203094995b2933c5424 Mon Sep 17 00:00:00 2001
From: rlazarini <remi.lazarini@cea.fr>
Date: Wed, 2 Oct 2024 14:34:20 +0200
Subject: [PATCH] [Ivette] add modal

---
 ivette/src/dome/renderer/data/states.ts |  2 +-
 ivette/src/dome/renderer/dialogs.tsx    |  7 ++++++
 ivette/src/dome/renderer/dome.tsx       | 32 ++++++++++++++++++++++---
 ivette/src/dome/renderer/style.css      | 27 +++++++++++++++++++++
 4 files changed, 64 insertions(+), 4 deletions(-)

diff --git a/ivette/src/dome/renderer/data/states.ts b/ivette/src/dome/renderer/data/states.ts
index fab86e0e57d..fa2d5174b86 100644
--- a/ivette/src/dome/renderer/data/states.ts
+++ b/ivette/src/dome/renderer/data/states.ts
@@ -32,7 +32,7 @@
 import Emitter from 'events';
 import React from 'react';
 import isEqual from 'react-fast-compare';
-import { Debug } from 'dome';
+import { Debug } from 'dome/system';
 
 const D = new Debug('State');
 
diff --git a/ivette/src/dome/renderer/dialogs.tsx b/ivette/src/dome/renderer/dialogs.tsx
index a1bff13059e..ebcebbd2eda 100644
--- a/ivette/src/dome/renderer/dialogs.tsx
+++ b/ivette/src/dome/renderer/dialogs.tsx
@@ -28,6 +28,7 @@
 
 import * as filepath from 'path';
 import { ipcRenderer } from 'electron';
+import { modal } from 'dome';
 import * as System from 'dome/system';
 
 // --------------------------------------------------------------------------
@@ -304,3 +305,9 @@ export async function showOpenDir(
 }
 
 // --------------------------------------------------------------------------
+// --- Modal
+// --------------------------------------------------------------------------
+export function showModal(val: React.ReactNode): void { modal.setValue(val); }
+export function closeModal(): void { showModal(undefined); }
+
+// --------------------------------------------------------------------------
diff --git a/ivette/src/dome/renderer/dome.tsx b/ivette/src/dome/renderer/dome.tsx
index 38c44963ee9..8bb7597f502 100644
--- a/ivette/src/dome/renderer/dome.tsx
+++ b/ivette/src/dome/renderer/dome.tsx
@@ -45,7 +45,7 @@ import { createRoot } from 'react-dom/client';
 import { ipcRenderer } from 'electron';
 
 import SYS, * as System from 'dome/system';
-import { State } from './data/states';
+import { State, GlobalState, useGlobalState } from './data/states';
 import * as Json from 'dome/data/json';
 import * as Settings from 'dome/data/settings';
 
@@ -320,6 +320,31 @@ export function setTitle(title: string): void {
   ipcRenderer.send('dome.ipc.window.title', title);
 }
 
+// --------------------------------------------------------------------------
+// --- Window Modal
+// --------------------------------------------------------------------------
+
+export const modal = new GlobalState<React.ReactNode | undefined>(undefined);
+
+function Modal(): JSX.Element | null {
+  const [ modalContent, setModalContent ] = useGlobalState(modal);
+
+  if(modalContent === undefined) return null;
+  return (
+    <div
+      className="dome-xModal-overlay"
+      onClick={() => setModalContent(undefined)}
+    >
+      <div
+        className="dome-xModal"
+        onClick={(event) => event.stopPropagation()}
+      >
+        {modalContent}
+      </div>
+    </div>
+  );
+}
+
 // --------------------------------------------------------------------------
 // --- Window Container
 // --------------------------------------------------------------------------
@@ -329,8 +354,9 @@ function setContainer(
 ): void {
   Settings.synchronize();
   const appNode = setContextAppNode();
-  if (appNode)
-    createRoot(appNode).render(<Component />);
+  if (appNode) {
+    createRoot(appNode).render(<><Component /><Modal /></>);
+  }
   else
     // eslint-disable-next-line no-console
     console.error('[Dome] root element #root not found.');
diff --git a/ivette/src/dome/renderer/style.css b/ivette/src/dome/renderer/style.css
index ad640de4533..a0800a53d14 100644
--- a/ivette/src/dome/renderer/style.css
+++ b/ivette/src/dome/renderer/style.css
@@ -211,3 +211,30 @@ input[type="checkbox"]:checked {
 }
 
 /* -------------------------------------------------------------------------- */
+/* --- Modal                                                              --- */
+/* -------------------------------------------------------------------------- */
+.dome-xModal {
+  position: absolute;
+  display: flex;
+  flex-direction: column;
+  top: 50%;
+  left: 50%;
+  transform: translate(-50%, -50%);
+  border: solid var(--border) 2px;
+  border-radius: 10px;
+  background-color: var(--background);
+  max-width: calc(100% - 100px);
+  max-height: calc(100% - 50px);
+  overflow: hidden;
+}
+
+.dome-xModal-overlay {
+  z-index: 100;
+  position: fixed;
+  top: 0;
+  left: 0;
+  right: 0;
+  bottom: 0;
+  background-color: rgba(50, 50, 50, .4);
+}
+/* -------------------------------------------------------------------------- */
-- 
GitLab