From 2f65ee6a71747574301ab76df1230ca0001bd096 Mon Sep 17 00:00:00 2001
From: Vishnu <vishnu@hexrfactory.com>
Date: Tue, 29 Apr 2025 09:29:18 +0530
Subject: [PATCH] feat: Implement handleAddEventToProduct function and
 integrate it into EventProperties and Simulations components

---
 .../eventProperties/EventProperties.tsx       |  20 +-
 .../sidebarRight/simulation/Simulations.tsx   | 342 +++++++++---------
 .../functions/handleAddEventToProduct.ts      |  28 ++
 3 files changed, 223 insertions(+), 167 deletions(-)
 create mode 100644 app/src/modules/simulation/events/points/functions/handleAddEventToProduct.ts

diff --git a/app/src/components/layout/sidebarRight/properties/eventProperties/EventProperties.tsx b/app/src/components/layout/sidebarRight/properties/eventProperties/EventProperties.tsx
index 847d035..87d3bf6 100644
--- a/app/src/components/layout/sidebarRight/properties/eventProperties/EventProperties.tsx
+++ b/app/src/components/layout/sidebarRight/properties/eventProperties/EventProperties.tsx
@@ -1,5 +1,6 @@
 import React, { useEffect, useState } from "react";
 import {
+  useSelectedAsset,
   useSelectedEventData,
   useSelectedEventSphere,
   useSelectedProduct,
@@ -11,6 +12,7 @@ import RoboticArmMechanics from "./mechanics/roboticArmMechanics";
 import MachineMechanics from "./mechanics/machineMechanics";
 import StorageMechanics from "./mechanics/storageMechanics";
 import { AddIcon } from "../../../../icons/ExportCommonIcons";
+import { handleAddEventToProduct } from "../../../../../modules/simulation/events/points/functions/handleAddEventToProduct";
 
 const EventProperties: React.FC = () => {
   const { selectedEventData } = useSelectedEventData();
@@ -20,8 +22,10 @@ const EventProperties: React.FC = () => {
     null
   );
   const [assetType, setAssetType] = useState<string | null>(null);
-  const { products } = useProductStore();
+  const { products, addEvent } = useProductStore();
   const { selectedEventSphere } = useSelectedEventSphere();
+
+  const { selectedAsset, clearSelectedAsset } = useSelectedAsset();
   useEffect(() => {
     const event = getCurrentEventData();
     setCurrentEventData(event);
@@ -91,7 +95,19 @@ const EventProperties: React.FC = () => {
             <ul>
               {products.map((product) => (
                 <li key={product.productId}>
-                  <button>
+                  <button
+                    onClick={() =>
+                      handleAddEventToProduct({
+                        selectedAsset,
+                        addEvent,
+                        selectedProduct: {
+                          productId: product.productId,
+                          productName: product.productName,
+                        },
+                        clearSelectedAsset,
+                      })
+                    }
+                  >
                     <AddIcon />
                     {product.productName}
                   </button>
diff --git a/app/src/components/layout/sidebarRight/simulation/Simulations.tsx b/app/src/components/layout/sidebarRight/simulation/Simulations.tsx
index 926ce44..b037098 100644
--- a/app/src/components/layout/sidebarRight/simulation/Simulations.tsx
+++ b/app/src/components/layout/sidebarRight/simulation/Simulations.tsx
@@ -1,204 +1,216 @@
 import React, { useEffect, useRef } from "react";
 import {
-    AddIcon,
-    ArrowIcon,
-    RemoveIcon,
-    ResizeHeightIcon,
+  AddIcon,
+  ArrowIcon,
+  RemoveIcon,
+  ResizeHeightIcon,
 } from "../../../icons/ExportCommonIcons";
 import RenameInput from "../../../ui/inputs/RenameInput";
 import { handleResize } from "../../../../functions/handleResizePannel";
-import { useSelectedAsset, useSelectedProduct } from "../../../../store/simulation/useSimulationStore";
+import {
+  useSelectedAsset,
+  useSelectedProduct,
+} from "../../../../store/simulation/useSimulationStore";
 import { useProductStore } from "../../../../store/simulation/useProductStore";
 import { generateUUID } from "three/src/math/MathUtils";
 import RenderOverlay from "../../../templates/Overlay";
 import EditWidgetOption from "../../../ui/menu/EditWidgetOption";
 import { upsertProductOrEventApi } from "../../../../services/simulation/UpsertProductOrEventApi";
+import { handleAddEventToProduct } from "../../../../modules/simulation/events/points/functions/handleAddEventToProduct";
 
 interface Event {
-    pathName: string;
+  pathName: string;
 }
 
 interface ListProps {
-    val: Event;
+  val: Event;
 }
 
 const List: React.FC<ListProps> = ({ val }) => {
-    return (
-        <div className="process-container">
-            <div className="value">
-                {val.pathName}
-            </div>
-        </div>
-    );
+  return (
+    <div className="process-container">
+      <div className="value">{val.pathName}</div>
+    </div>
+  );
 };
 
 const Simulations: React.FC = () => {
-    const productsContainerRef = useRef<HTMLDivElement>(null);
-    const { products, addProduct, removeProduct, renameProduct, addEvent, removeEvent } = useProductStore();
-    const { selectedProduct, setSelectedProduct } = useSelectedProduct();
-    const { selectedAsset, clearSelectedAsset } = useSelectedAsset();
+  const productsContainerRef = useRef<HTMLDivElement>(null);
+  const {
+    products,
+    addProduct,
+    removeProduct,
+    renameProduct,
+    addEvent,
+    removeEvent,
+  } = useProductStore();
+  const { selectedProduct, setSelectedProduct } = useSelectedProduct();
+  const { selectedAsset, clearSelectedAsset } = useSelectedAsset();
 
-    const handleAddProduct = () => {
-        addProduct(`Product ${products.length + 1}`, generateUUID());
-    };
+  const handleAddProduct = () => {
+    addProduct(`Product ${products.length + 1}`, generateUUID());
+  };
 
-    const handleRemoveProduct = (productId: string) => {
-        const currentIndex = products.findIndex(p => p.productId === productId);
-        const isSelected = selectedProduct.productId === productId;
+  const handleRemoveProduct = (productId: string) => {
+    const currentIndex = products.findIndex((p) => p.productId === productId);
+    const isSelected = selectedProduct.productId === productId;
 
-        const updatedProducts = products.filter(p => p.productId !== productId);
+    const updatedProducts = products.filter((p) => p.productId !== productId);
 
-        if (isSelected) {
-            if (updatedProducts.length > 0) {
-                let newSelectedIndex = currentIndex;
-                if (currentIndex >= updatedProducts.length) {
-                    newSelectedIndex = updatedProducts.length - 1;
-                }
-                setSelectedProduct(
-                    updatedProducts[newSelectedIndex].productId,
-                    updatedProducts[newSelectedIndex].productName
-                );
-            } else {
-                setSelectedProduct('', '');
-            }
+    if (isSelected) {
+      if (updatedProducts.length > 0) {
+        let newSelectedIndex = currentIndex;
+        if (currentIndex >= updatedProducts.length) {
+          newSelectedIndex = updatedProducts.length - 1;
         }
+        setSelectedProduct(
+          updatedProducts[newSelectedIndex].productId,
+          updatedProducts[newSelectedIndex].productName
+        );
+      } else {
+        setSelectedProduct("", "");
+      }
+    }
 
-        removeProduct(productId);
-    };
+    removeProduct(productId);
+  };
 
-    const handleRenameProduct = (productId: string, newName: string) => {
-        renameProduct(productId, newName);
-        if (selectedProduct.productId === productId) {
-            setSelectedProduct(productId, newName);
-        }
-    };
+  const handleRenameProduct = (productId: string, newName: string) => {
+    renameProduct(productId, newName);
+    if (selectedProduct.productId === productId) {
+      setSelectedProduct(productId, newName);
+    }
+  };
 
-    const handleAddEventToProduct = () => {
-        if (selectedAsset) {
-            addEvent(selectedProduct.productId, selectedAsset);
-            // upsertProductOrEventApi({
-            //     productName: selectedProduct.productName,
-            //     productId: selectedProduct.productId,
-            //     eventDatas: selectedAsset
-            // });
-            clearSelectedAsset();
-        }
-    };
+  const handleRemoveEventFromProduct = () => {
+    if (selectedAsset) {
+      removeEvent(selectedProduct.productId, selectedAsset.modelUuid);
+      clearSelectedAsset();
+    }
+  };
 
-    const handleRemoveEventFromProduct = () => {
-        if (selectedAsset) {
-            removeEvent(selectedProduct.productId, selectedAsset.modelUuid);
-            clearSelectedAsset();
-        }
-    };
+  const selectedProductData = products.find(
+    (product) => product.productId === selectedProduct.productId
+  );
 
-    const selectedProductData = products.find(
-        (product) => product.productId === selectedProduct.productId
-    );
-
-    const events: Event[] = selectedProductData?.eventDatas.map((event) => ({
-        pathName: event.modelName,
+  const events: Event[] =
+    selectedProductData?.eventDatas.map((event) => ({
+      pathName: event.modelName,
     })) || [];
 
-    return (
-        <div className="simulations-container">
-            <div className="header">Simulations</div>
-            <div className="add-product-container">
-                <div className="actions">
-                    <div className="header">
-                        <div className="header-value">Products</div>
-                        <div className="add-button" onClick={handleAddProduct}>
-                            <AddIcon /> Add
-                        </div>
-                    </div>
-                    <div
-                        className="lists-main-container"
-                        ref={productsContainerRef}
-                        style={{ height: "120px" }}
-                    >
-                        <div className="list-container">
-                            {products.map((product, index) => (
-                                <div
-                                    key={product.productId}
-                                    className={`list-item ${selectedProduct.productId === product.productId ? "active" : ""}`}
-                                >
-                                    <div
-                                        className="value"
-                                        onClick={() => setSelectedProduct(product.productId, product.productName)}
-                                    >
-                                        <input
-                                            type="radio"
-                                            name="products"
-                                            checked={selectedProduct.productId === product.productId}
-                                            readOnly
-                                        />
-                                        <RenameInput
-                                            value={product.productName}
-                                            onRename={(newName) => handleRenameProduct(product.productId, newName)}
-                                        />
-                                    </div>
-                                    {products.length > 1 && (
-                                        <div
-                                            className="remove-button"
-                                            onClick={() => handleRemoveProduct(product.productId)}
-                                        >
-                                            <RemoveIcon />
-                                        </div>
-                                    )}
-                                </div>
-                            ))}
-                        </div>
-                        <div
-                            className="resize-icon"
-                            id="action-resize"
-                            onMouseDown={(e) => handleResize(e, productsContainerRef)}
-                        >
-                            <ResizeHeightIcon />
-                        </div>
-                    </div>
-                </div>
-
-                <div className="simulation-process">
-                    <div className="collapse-header-container">
-                        <div className="header">Events</div>
-                        <div className="arrow-container">
-                            <ArrowIcon />
-                        </div>
-                    </div>
-                    {events.map((event, index) => (
-                        <List key={index} val={event} />
-                    ))}
-                </div>
-
-                <div className="compare-simulations-container">
-                    <div className="compare-simulations-header">
-                        Need to Compare Layout?
-                    </div>
-                    <div className="content">
-                        Click <span>'Compare'</span> to review and analyze the layout differences between them.
-                    </div>
-                    <div className="input">
-                        <input type="button" value={"Compare"} className="submit" />
-                    </div>
-                </div>
+  return (
+    <div className="simulations-container">
+      <div className="header">Simulations</div>
+      <div className="add-product-container">
+        <div className="actions">
+          <div className="header">
+            <div className="header-value">Products</div>
+            <div className="add-button" onClick={handleAddProduct}>
+              <AddIcon /> Add
             </div>
-
-            {selectedAsset &&
-                <RenderOverlay>
-                    <EditWidgetOption
-                        options={['Add to Product', 'Remove from Product']}
-                        onClick={(option) => {
-                            if (option === 'Add to Product') {
-                                handleAddEventToProduct();
-                            } else {
-                                handleRemoveEventFromProduct();
-                            }
-                        }}
+          </div>
+          <div
+            className="lists-main-container"
+            ref={productsContainerRef}
+            style={{ height: "120px" }}
+          >
+            <div className="list-container">
+              {products.map((product, index) => (
+                <div
+                  key={product.productId}
+                  className={`list-item ${
+                    selectedProduct.productId === product.productId
+                      ? "active"
+                      : ""
+                  }`}
+                >
+                  <div
+                    className="value"
+                    onClick={() =>
+                      setSelectedProduct(product.productId, product.productName)
+                    }
+                  >
+                    <input
+                      type="radio"
+                      name="products"
+                      checked={selectedProduct.productId === product.productId}
+                      readOnly
                     />
-                </RenderOverlay>
-            }
+                    <RenameInput
+                      value={product.productName}
+                      onRename={(newName) =>
+                        handleRenameProduct(product.productId, newName)
+                      }
+                    />
+                  </div>
+                  {products.length > 1 && (
+                    <div
+                      className="remove-button"
+                      onClick={() => handleRemoveProduct(product.productId)}
+                    >
+                      <RemoveIcon />
+                    </div>
+                  )}
+                </div>
+              ))}
+            </div>
+            <div
+              className="resize-icon"
+              id="action-resize"
+              onMouseDown={(e) => handleResize(e, productsContainerRef)}
+            >
+              <ResizeHeightIcon />
+            </div>
+          </div>
         </div>
-    );
+
+        <div className="simulation-process">
+          <div className="collapse-header-container">
+            <div className="header">Events</div>
+            <div className="arrow-container">
+              <ArrowIcon />
+            </div>
+          </div>
+          {events.map((event, index) => (
+            <List key={index} val={event} />
+          ))}
+        </div>
+
+        <div className="compare-simulations-container">
+          <div className="compare-simulations-header">
+            Need to Compare Layout?
+          </div>
+          <div className="content">
+            Click <span>'Compare'</span> to review and analyze the layout
+            differences between them.
+          </div>
+          <div className="input">
+            <input type="button" value={"Compare"} className="submit" />
+          </div>
+        </div>
+      </div>
+
+      {selectedAsset && (
+        <RenderOverlay>
+          <EditWidgetOption
+            options={["Add to Product", "Remove from Product"]}
+            onClick={(option) => {
+              if (option === "Add to Product") {
+                handleAddEventToProduct({
+                  selectedAsset,
+                  addEvent,
+                  selectedProduct,
+                  clearSelectedAsset,
+                });
+              } else {
+                handleRemoveEventFromProduct();
+              }
+            }}
+          />
+        </RenderOverlay>
+      )}
+    </div>
+  );
 };
 
 export default Simulations;
diff --git a/app/src/modules/simulation/events/points/functions/handleAddEventToProduct.ts b/app/src/modules/simulation/events/points/functions/handleAddEventToProduct.ts
new file mode 100644
index 0000000..7943c1c
--- /dev/null
+++ b/app/src/modules/simulation/events/points/functions/handleAddEventToProduct.ts
@@ -0,0 +1,28 @@
+interface HandleAddEventToProductParams {
+    selectedAsset: any; // Replace `any` with specific type if you have it
+    addEvent: (productId: string, asset: any) => void;
+    selectedProduct: {
+        productId: string;
+        productName: string;
+        // Add other fields if needed
+    };
+    clearSelectedAsset: () => void;
+}
+
+export const handleAddEventToProduct = ({
+    selectedAsset,
+    addEvent,
+    selectedProduct,
+    clearSelectedAsset,
+}: HandleAddEventToProductParams) => {
+    console.log('selectedProduct: ', selectedProduct);
+    if (selectedAsset) {
+        addEvent(selectedProduct.productId, selectedAsset);
+        // upsertProductOrEventApi({
+        //     productName: selectedProduct.productName,
+        //     productId: selectedProduct.productId,
+        //     eventDatas: selectedAsset
+        // });
+        clearSelectedAsset();
+    }
+};