UNPKG

@react95/core

Version:
127 lines (126 loc) 3.95 kB
import React, { forwardRef, useState, useEffect } from "react"; import { Frame } from "../Frame/Frame.mjs"; import { Clock } from "./Clock.mjs"; import { WindowButton } from "./WindowButton.mjs"; import { Logo } from "@react95/icons"; import { truncate } from "./TaskBar.css.mjs"; import { useModal } from "../shared/use-modal.mjs"; import { ModalEvents } from "../shared/modal-types.mjs"; const TaskBar = forwardRef( ({ list, className }, ref) => { const [showList, toggleShowList] = useState(false); const [activeStart, toggleActiveStart] = useState(false); const [modalWindows, setModalWindows] = React.useState([]); const [activeWindow, setActiveWindow] = useState(); const { minimize, restore, focus, subscribe } = useModal(); useEffect(() => { const addModal = (window) => { if (!window.id) { console.warn("Modal added without ID"); return; } setModalWindows((prevModals) => { if (prevModals.some((modal) => modal.id === window.id)) { return prevModals; } return [...prevModals, window]; }); }; const removeModal = (data) => { setModalWindows((prevModals) => { const filteredModals = prevModals.filter( (modal) => modal.id !== data.id ); const lastModal = filteredModals.at(-1); if (activeWindow === data.id && lastModal) { focus(lastModal.id); } return filteredModals; }); }; const updateVisibleModal = ({ id }) => { setActiveWindow(id); }; const unsubscribeAdd = subscribe(ModalEvents.AddModal, addModal); const unsubscribeRemove = subscribe(ModalEvents.RemoveModal, removeModal); const unsubscribeVisibility = subscribe( ModalEvents.ModalVisibilityChanged, updateVisibleModal ); return () => { unsubscribeAdd(); unsubscribeRemove(); unsubscribeVisibility(); }; }, [activeWindow, subscribe, focus]); return /* @__PURE__ */ React.createElement( Frame, { position: "fixed", bottom: "0px", left: "0px", right: "0px", display: "flex", justifyContent: "space-between", h: "28px", w: "100%", padding: "$2", zIndex: "$taskbar", backgroundColor: "$material", boxShadow: "$out", ref, className }, showList && /* @__PURE__ */ React.createElement( Frame, { position: "absolute", bottom: "28px", onClick: () => { toggleActiveStart(false); toggleShowList(false); } }, list ), /* @__PURE__ */ React.createElement( WindowButton, { small: true, icon: /* @__PURE__ */ React.createElement(Logo, { variant: "32x32_4" }), active: activeStart, onClick: () => { toggleActiveStart(!activeStart); toggleShowList(!showList); } }, "Start" ), /* @__PURE__ */ React.createElement(Frame, { w: "100%", paddingLeft: "$0", ml: "$2", display: "flex" }, modalWindows.map( ({ icon, title, hasButton, id }) => hasButton && /* @__PURE__ */ React.createElement( WindowButton, { key: id, icon, active: id === activeWindow, onClick: () => { if (id === activeWindow) { minimize(id); setActiveWindow(void 0); } else { restore(id); focus(id); } }, small: false }, /* @__PURE__ */ React.createElement("div", { className: truncate }, title) ) )), /* @__PURE__ */ React.createElement(Clock, null) ); } ); export { TaskBar };