waveterm/frontend/app/workspace/workspace.tsx

103 lines
3.3 KiB
TypeScript
Raw Normal View History

// Copyright 2024, Command Line Inc.
// SPDX-License-Identifier: Apache-2.0
import { ModalsRenderer } from "@/app/modals/modalsrenderer";
2024-06-18 06:50:33 +02:00
import { TabBar } from "@/app/tab/tabbar";
import { TabContent } from "@/app/tab/tabcontent";
import { atoms, createBlock } from "@/store/global";
import * as util from "@/util/util";
2024-05-28 21:12:28 +02:00
import * as jotai from "jotai";
import * as React from "react";
2024-05-28 21:12:28 +02:00
import { CenteredDiv } from "../element/quickelems";
import "./workspace.less";
2024-06-22 00:15:38 +02:00
const iconRegex = /^[a-z0-9-]+$/;
2024-06-26 18:31:43 +02:00
const Widgets = React.memo(() => {
const settingsConfig = jotai.useAtomValue(atoms.settingsConfigAtom);
const newWidgetModalVisible = React.useState(false);
2024-08-20 02:21:44 +02:00
const helpWidget: WidgetsConfigType = {
icon: "circle-question",
label: "help",
blockdef: {
meta: {
2024-08-20 02:21:44 +02:00
view: "help",
},
2024-08-20 02:21:44 +02:00
},
};
const showHelp = settingsConfig?.["widget:showhelp"] ?? true;
const showDivider = settingsConfig?.defaultwidgets?.length > 0 && settingsConfig?.widgets?.length > 0;
return (
<div className="workspace-widgets">
{settingsConfig?.defaultwidgets?.map((data, idx) => <Widget key={`defwidget-${idx}`} widget={data} />)}
{showDivider ? <div className="widget-divider" /> : null}
{settingsConfig?.widgets?.map((data, idx) => <Widget key={`widget-${idx}`} widget={data} />)}
{showHelp ? (
<>
<div className="widget-spacer" />
<Widget key="help" widget={helpWidget} />
</>
) : null}
</div>
);
});
2024-08-20 02:21:44 +02:00
async function handleWidgetSelect(blockDef: BlockDef) {
createBlock(blockDef);
}
2024-08-20 02:21:44 +02:00
function isIconValid(icon: string): boolean {
if (util.isBlank(icon)) {
return false;
2024-06-22 00:15:38 +02:00
}
2024-08-20 02:21:44 +02:00
return icon.match(iconRegex) != null;
}
2024-06-22 00:15:38 +02:00
2024-08-20 02:21:44 +02:00
function getIconClass(icon: string): string {
if (!isIconValid(icon)) {
2024-08-22 20:30:18 +02:00
return "fa fa-regular fa-browser fa-fw";
2024-06-22 00:15:38 +02:00
}
2024-08-20 02:21:44 +02:00
return `fa fa-solid fa-${icon} fa-fw`;
}
2024-06-22 00:15:38 +02:00
2024-08-20 02:21:44 +02:00
const Widget = React.memo(({ widget }: { widget: WidgetsConfigType }) => {
return (
2024-08-20 02:21:44 +02:00
<div
className="widget"
onClick={() => handleWidgetSelect(widget.blockdef)}
title={widget.description || widget.label}
>
<div className="widget-icon" style={{ color: widget.color }}>
<i className={getIconClass(widget.icon)}></i>
</div>
2024-08-20 02:21:44 +02:00
{!util.isBlank(widget.label) ? <div className="widget-label">{widget.label}</div> : null}
</div>
);
2024-06-26 18:31:43 +02:00
});
2024-06-26 18:31:43 +02:00
const WorkspaceElem = React.memo(() => {
const windowData = jotai.useAtomValue(atoms.waveWindow);
const activeTabId = windowData?.activetabid;
const ws = jotai.useAtomValue(atoms.workspace);
return (
<div className="workspace">
2024-06-26 18:31:43 +02:00
<TabBar key={ws.oid} workspace={ws} />
<div className="workspace-tabcontent">
2024-05-28 01:33:31 +02:00
{activeTabId == "" ? (
<CenteredDiv>No Active Tab</CenteredDiv>
) : (
<>
<TabContent key={activeTabId} tabId={activeTabId} />
2024-08-22 20:30:18 +02:00
<Widgets />
<ModalsRenderer />
2024-05-28 01:33:31 +02:00
</>
)}
</div>
</div>
);
2024-06-26 18:31:43 +02:00
});
export { WorkspaceElem as Workspace };