Add search for relationships
This commit is contained in:
parent
4fec674ac6
commit
525ca9f5c7
@ -319,7 +319,7 @@ export default function ControlPanel() {
|
|||||||
</Dropdown.Menu>
|
</Dropdown.Menu>
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
<div className="px-3 py-1 hover:bg-gray-100 rounded-md">
|
<div className="px-3 py-1 hover:bg-gray-100 rounded">
|
||||||
{category}
|
{category}
|
||||||
</div>
|
</div>
|
||||||
</Dropdown>
|
</Dropdown>
|
||||||
@ -363,7 +363,7 @@ export default function ControlPanel() {
|
|||||||
</div>
|
</div>
|
||||||
</nav>
|
</nav>
|
||||||
)}
|
)}
|
||||||
<div className="p-2 px-5 flex justify-between items-center rounded-xl bg-slate-100 my-1 mx-6 text-slate-700">
|
<div className="p-2 px-5 flex justify-between items-center rounded-xl bg-slate-100 my-1 mx-6 text-slate-700 select-none">
|
||||||
<div className="flex justify-start items-center">
|
<div className="flex justify-start items-center">
|
||||||
<Dropdown
|
<Dropdown
|
||||||
position="bottomLeft"
|
position="bottomLeft"
|
||||||
@ -396,7 +396,7 @@ export default function ControlPanel() {
|
|||||||
}
|
}
|
||||||
trigger="click"
|
trigger="click"
|
||||||
>
|
>
|
||||||
<div className="py-1 px-2 hover:bg-slate-200 rounded-md">
|
<div className="py-1 px-2 hover:bg-slate-200 rounded">
|
||||||
<i className="fa-solid fa-table-list"></i> <IconCaretdown />
|
<i className="fa-solid fa-table-list"></i> <IconCaretdown />
|
||||||
</div>
|
</div>
|
||||||
</Dropdown>
|
</Dropdown>
|
||||||
@ -435,33 +435,27 @@ export default function ControlPanel() {
|
|||||||
}
|
}
|
||||||
trigger="click"
|
trigger="click"
|
||||||
>
|
>
|
||||||
<div className="py-1 px-2 hover:bg-slate-200 rounded-md">
|
<div className="py-1 px-2 hover:bg-slate-200 rounded">
|
||||||
zoom <IconCaretdown />
|
zoom <IconCaretdown />
|
||||||
</div>
|
</div>
|
||||||
</Dropdown>
|
</Dropdown>
|
||||||
<button
|
<button
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
className="py-1 px-2 hover:bg-slate-200 rounded"
|
||||||
title="Zoom in"
|
title="Zoom in"
|
||||||
>
|
>
|
||||||
<i className="fa-solid fa-magnifying-glass-plus"></i>
|
<i className="fa-solid fa-magnifying-glass-plus"></i>
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
className="py-1 px-2 hover:bg-slate-200 rounded"
|
||||||
title="Zoom out"
|
title="Zoom out"
|
||||||
>
|
>
|
||||||
<i className="fa-solid fa-magnifying-glass-minus"></i>
|
<i className="fa-solid fa-magnifying-glass-minus"></i>
|
||||||
</button>
|
</button>
|
||||||
<Divider layout="vertical" margin="8px" />
|
<Divider layout="vertical" margin="8px" />
|
||||||
<button
|
<button className="py-1 px-2 hover:bg-slate-200 rounded" title="Undo">
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
|
||||||
title="Undo"
|
|
||||||
>
|
|
||||||
<i className="fa-solid fa-rotate-left "></i>
|
<i className="fa-solid fa-rotate-left "></i>
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button className="py-1 px-2 hover:bg-slate-200 rounded" title="Redo">
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
|
||||||
title="Redo"
|
|
||||||
>
|
|
||||||
<i className="fa-solid fa-rotate-right"></i>
|
<i className="fa-solid fa-rotate-right"></i>
|
||||||
</button>
|
</button>
|
||||||
<Divider layout="vertical" margin="8px" />
|
<Divider layout="vertical" margin="8px" />
|
||||||
@ -478,31 +472,25 @@ export default function ControlPanel() {
|
|||||||
}
|
}
|
||||||
trigger="click"
|
trigger="click"
|
||||||
>
|
>
|
||||||
<div className="py-1 px-2 hover:bg-slate-200 rounded-md">
|
<div className="py-1 px-2 hover:bg-slate-200 rounded">
|
||||||
<i className="fa-solid fa-plus"></i> <IconCaretdown />
|
<i className="fa-solid fa-plus"></i> <IconCaretdown />
|
||||||
</div>
|
</div>
|
||||||
</Dropdown>
|
</Dropdown>
|
||||||
<button
|
<button className="py-1 px-2 hover:bg-slate-200 rounded" title="Edit">
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
|
||||||
title="Edit"
|
|
||||||
>
|
|
||||||
<i className="fa-solid fa-pen-to-square"></i>
|
<i className="fa-solid fa-pen-to-square"></i>
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
className="py-1 px-2 hover:bg-slate-200 rounded"
|
||||||
title="Delete"
|
title="Delete"
|
||||||
>
|
>
|
||||||
<i className="fa-solid fa-trash"></i>
|
<i className="fa-solid fa-trash"></i>
|
||||||
</button>
|
</button>
|
||||||
<Divider layout="vertical" margin="8px" />
|
<Divider layout="vertical" margin="8px" />
|
||||||
<button
|
<button className="py-1 px-2 hover:bg-slate-200 rounded" title="Save">
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
|
||||||
title="Save"
|
|
||||||
>
|
|
||||||
<i className="fa-regular fa-floppy-disk"></i>
|
<i className="fa-regular fa-floppy-disk"></i>
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
className="py-1 px-2 hover:bg-slate-200 rounded-md"
|
className="py-1 px-2 hover:bg-slate-200 rounded"
|
||||||
title="Commit"
|
title="Commit"
|
||||||
>
|
>
|
||||||
<i className="fa-solid fa-code-branch"></i>
|
<i className="fa-solid fa-code-branch"></i>
|
||||||
|
@ -30,40 +30,32 @@ const EditorPanel = (props) => {
|
|||||||
|
|
||||||
const tabList = [
|
const tabList = [
|
||||||
{ tab: "Tables", itemKey: "1" },
|
{ tab: "Tables", itemKey: "1" },
|
||||||
{ tab: "References", itemKey: "2" },
|
{ tab: "Relationships", itemKey: "2" },
|
||||||
{ tab: "Shapes", itemKey: "3" },
|
{ tab: "Shapes", itemKey: "3" },
|
||||||
{ tab: "Editor", itemKey: "4" },
|
{ tab: "Editor", itemKey: "4" },
|
||||||
];
|
];
|
||||||
const contentList = [
|
const contentList = [
|
||||||
<div>
|
<TableOverview tables={props.tables} setTables={props.setTables} />,
|
||||||
<TableOverview tables={props.tables} setTables={props.setTables} />
|
<ReferenceOverview
|
||||||
</div>,
|
relationships={props.relationships}
|
||||||
<div>
|
setRelationships={props.setRelationships}
|
||||||
<ReferenceOverview
|
tables={props.tables}
|
||||||
relationships={props.relationships}
|
/>,
|
||||||
setRelationships={props.setRelationships}
|
<Shape />,
|
||||||
tables={props.tables}
|
<CodeMirror
|
||||||
/>
|
value={props.code}
|
||||||
</div>,
|
height="100%"
|
||||||
<div>
|
theme={myTheme}
|
||||||
<Shape />
|
extensions={[sql()]}
|
||||||
</div>,
|
onChange={(e) => {
|
||||||
<div>
|
props.setCode(e);
|
||||||
<CodeMirror
|
}}
|
||||||
value={props.code}
|
/>,
|
||||||
height="100%"
|
|
||||||
theme={myTheme}
|
|
||||||
extensions={[sql()]}
|
|
||||||
onChange={(e) => {
|
|
||||||
props.setCode(e);
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
</div>,
|
|
||||||
];
|
];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="h-screen flex overflow-clip relative">
|
<div className="h-screen flex overflow-clip relative">
|
||||||
<div className="mt-2" style={{ width: `${props.width}px` }}>
|
<div style={{ width: `${props.width}px` }}>
|
||||||
<Tabs
|
<Tabs
|
||||||
type="card"
|
type="card"
|
||||||
tabList={tabList}
|
tabList={tabList}
|
||||||
@ -72,7 +64,7 @@ const EditorPanel = (props) => {
|
|||||||
}}
|
}}
|
||||||
collapsible
|
collapsible
|
||||||
>
|
>
|
||||||
{contentList[parseInt(tab) - 1]}
|
<div className="p-2">{contentList[parseInt(tab) - 1]}</div>
|
||||||
</Tabs>
|
</Tabs>
|
||||||
<button
|
<button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
@ -151,7 +143,9 @@ const EditorPanel = (props) => {
|
|||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
className={`flex justify-center items-center p-1 h-full hover:bg-slate-300 cursor-col-resize ${props.resize? "bg-slate-300": ""}`}
|
className={`flex justify-center items-center p-1 h-full hover:bg-slate-300 cursor-col-resize ${
|
||||||
|
props.resize ? "bg-slate-300" : ""
|
||||||
|
}`}
|
||||||
onMouseDown={() => props.setResize(true)}
|
onMouseDown={() => props.setResize(true)}
|
||||||
>
|
>
|
||||||
<div className="w-1 border-x border-white h-1/6" />
|
<div className="w-1 border-x border-white h-1/6" />
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
import React from "react";
|
import React, { useState } from "react";
|
||||||
import {
|
import {
|
||||||
|
AutoComplete,
|
||||||
Collapse,
|
Collapse,
|
||||||
|
Empty,
|
||||||
Form,
|
Form,
|
||||||
Row,
|
Row,
|
||||||
Col,
|
Col,
|
||||||
@ -14,7 +16,12 @@ import {
|
|||||||
IconDeleteStroked,
|
IconDeleteStroked,
|
||||||
IconLoopTextStroked,
|
IconLoopTextStroked,
|
||||||
IconMore,
|
IconMore,
|
||||||
|
IconSearch,
|
||||||
} from "@douyinfe/semi-icons";
|
} from "@douyinfe/semi-icons";
|
||||||
|
import {
|
||||||
|
IllustrationNoContent,
|
||||||
|
IllustrationNoContentDark,
|
||||||
|
} from "@douyinfe/semi-illustrations";
|
||||||
import { Cardinality, Constraint } from "../data/data";
|
import { Cardinality, Constraint } from "../data/data";
|
||||||
|
|
||||||
export default function ReferenceOverview(props) {
|
export default function ReferenceOverview(props) {
|
||||||
@ -28,158 +35,219 @@ export default function ReferenceOverview(props) {
|
|||||||
dataIndex: "foreign",
|
dataIndex: "foreign",
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
const [refActiveIndex, setRefActiveIndex] = useState("");
|
||||||
|
const [value, setValue] = useState("");
|
||||||
|
const [filteredResult, setFilteredResult] = useState(
|
||||||
|
props.relationships.map((t) => {
|
||||||
|
return t.name;
|
||||||
|
})
|
||||||
|
);
|
||||||
|
|
||||||
|
const handleStringSearch = (value) => {
|
||||||
|
setFilteredResult(
|
||||||
|
props.relationships
|
||||||
|
.map((t) => {
|
||||||
|
return t.name;
|
||||||
|
})
|
||||||
|
.filter((i) => i.includes(value))
|
||||||
|
);
|
||||||
|
};
|
||||||
return (
|
return (
|
||||||
<Collapse>
|
<>
|
||||||
{props.relationships.map((r, i) => (
|
<AutoComplete
|
||||||
<Collapse.Panel key={i} header={<div>{r.name}</div>} itemKey={`${i}`}>
|
data={filteredResult}
|
||||||
<Form
|
value={value}
|
||||||
onChange={(value) =>
|
showClear
|
||||||
props.setRelationships((prev) =>
|
prefix={<IconSearch />}
|
||||||
prev.map((e, idx) =>
|
placeholder="Search..."
|
||||||
idx === i ? { ...e, ...value.values } : e
|
emptyContent={<div className="p-3">No relationships found</div>}
|
||||||
)
|
onSearch={(v) => handleStringSearch(v)}
|
||||||
)
|
onChange={(v) => setValue(v)}
|
||||||
}
|
onSelect={(v) => {
|
||||||
>
|
const { id } = props.relationships.find((t) => t.name === v);
|
||||||
<div className="flex justify-between items-center my-1">
|
setRefActiveIndex(`${id}`);
|
||||||
<div className="me-3">
|
document
|
||||||
<strong>Primary: </strong>
|
.getElementById(`scroll_ref_${id}`)
|
||||||
{props.tables[r.endTableId].name}
|
.scrollIntoView({ behavior: "smooth" });
|
||||||
</div>
|
}}
|
||||||
<div className="mx-1">
|
className="w-full"
|
||||||
<strong>Foreign: </strong>
|
/>
|
||||||
{props.tables[r.startTableId].name}
|
<Collapse
|
||||||
</div>
|
activeKey={refActiveIndex}
|
||||||
<div className="ms-1">
|
onChange={(k) => setRefActiveIndex(k)}
|
||||||
<Popover
|
accordion
|
||||||
content={
|
>
|
||||||
<div className="p-2 w-[260px]">
|
{props.relationships.length <= 0 ? (
|
||||||
<Table
|
<div className="select-none">
|
||||||
columns={columns}
|
<Empty
|
||||||
dataSource={[
|
image={
|
||||||
{
|
<IllustrationNoContent style={{ width: 160, height: 160 }} />
|
||||||
key: "1",
|
}
|
||||||
foreign: props.tables[r.startTableId].name,
|
darkModeImage={
|
||||||
primary: props.tables[r.endTableId].name,
|
<IllustrationNoContentDark
|
||||||
},
|
style={{ width: 160, height: 160 }}
|
||||||
{
|
/>
|
||||||
key: "2",
|
}
|
||||||
foreign:
|
title="No relationships"
|
||||||
props.tables[r.startTableId].fields[
|
description="Drag to connect fields and form relationships!"
|
||||||
r.startFieldId
|
/>
|
||||||
].name,
|
</div>
|
||||||
primary:
|
) : (
|
||||||
props.tables[r.endTableId].fields[r.endFieldId]
|
props.relationships.map((r, i) => (
|
||||||
.name,
|
<div id={`scroll_ref_${r.id}`} key={i}>
|
||||||
},
|
<Collapse.Panel header={<div>{r.name}</div>} itemKey={`${i}`}>
|
||||||
]}
|
<Form
|
||||||
pagination={false}
|
onChange={(value) =>
|
||||||
bordered
|
props.setRelationships((prev) =>
|
||||||
/>
|
prev.map((e, idx) =>
|
||||||
<div className="mt-2">
|
idx === i ? { ...e, ...value.values } : e
|
||||||
<Button icon={<IconLoopTextStroked />} block>
|
)
|
||||||
Swap
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
trigger="click"
|
|
||||||
position="rightTop"
|
|
||||||
showArrow
|
|
||||||
>
|
|
||||||
<Button icon={<IconMore />} type="tertiary"></Button>
|
|
||||||
</Popover>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<Form.Input initValue={r.name} field="name" label="Name" />
|
|
||||||
<Form.Select
|
|
||||||
optionList={Object.values(Cardinality).map((v) => ({
|
|
||||||
label: v,
|
|
||||||
value: v,
|
|
||||||
}))}
|
|
||||||
field="cardinality"
|
|
||||||
label="Cardinality"
|
|
||||||
initValue={r.cardinality}
|
|
||||||
className="w-full"
|
|
||||||
></Form.Select>
|
|
||||||
<Row gutter={6}>
|
|
||||||
<Col span={12}>
|
|
||||||
<Form.Select
|
|
||||||
optionList={Object.values(Constraint).map((v) => ({
|
|
||||||
label: v,
|
|
||||||
value: v,
|
|
||||||
}))}
|
|
||||||
field="updateConstraint"
|
|
||||||
label="On update"
|
|
||||||
initValue={r.updateConstraint}
|
|
||||||
className="w-full"
|
|
||||||
></Form.Select>
|
|
||||||
</Col>
|
|
||||||
<Col span={12}>
|
|
||||||
<Form.Select
|
|
||||||
optionList={Object.values(Constraint).map((v) => ({
|
|
||||||
label: v,
|
|
||||||
value: v,
|
|
||||||
}))}
|
|
||||||
field="deleteConstraint"
|
|
||||||
label="On delete"
|
|
||||||
initValue={r.deleteConstraint}
|
|
||||||
className="w-full"
|
|
||||||
></Form.Select>
|
|
||||||
</Col>
|
|
||||||
</Row>
|
|
||||||
<div className="flex justify-between items-center my-3">
|
|
||||||
<label htmlFor="unique" className="font-medium text-black">
|
|
||||||
Mandetory
|
|
||||||
</label>
|
|
||||||
<Checkbox
|
|
||||||
value="mandetory"
|
|
||||||
defaultChecked={r.mandetory}
|
|
||||||
onChange={(checkedValues) =>
|
|
||||||
props.setRelationships((prev) =>
|
|
||||||
prev.map((e, idx) =>
|
|
||||||
idx === i
|
|
||||||
? {
|
|
||||||
...e,
|
|
||||||
[checkedValues.target.value]:
|
|
||||||
checkedValues.target.checked,
|
|
||||||
}
|
|
||||||
: e
|
|
||||||
)
|
)
|
||||||
)
|
}
|
||||||
}
|
>
|
||||||
></Checkbox>
|
<div className="flex justify-between items-center my-1">
|
||||||
|
<div className="me-3">
|
||||||
|
<strong>Primary: </strong>
|
||||||
|
{props.tables[r.endTableId].name}
|
||||||
|
</div>
|
||||||
|
<div className="mx-1">
|
||||||
|
<strong>Foreign: </strong>
|
||||||
|
{props.tables[r.startTableId].name}
|
||||||
|
</div>
|
||||||
|
<div className="ms-1">
|
||||||
|
<Popover
|
||||||
|
content={
|
||||||
|
<div className="p-2 w-[260px]">
|
||||||
|
<Table
|
||||||
|
columns={columns}
|
||||||
|
dataSource={[
|
||||||
|
{
|
||||||
|
key: "1",
|
||||||
|
foreign: props.tables[r.startTableId].name,
|
||||||
|
primary: props.tables[r.endTableId].name,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "2",
|
||||||
|
foreign:
|
||||||
|
props.tables[r.startTableId].fields[
|
||||||
|
r.startFieldId
|
||||||
|
].name,
|
||||||
|
primary:
|
||||||
|
props.tables[r.endTableId].fields[
|
||||||
|
r.endFieldId
|
||||||
|
].name,
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
pagination={false}
|
||||||
|
bordered
|
||||||
|
/>
|
||||||
|
<div className="mt-2">
|
||||||
|
<Button icon={<IconLoopTextStroked />} block>
|
||||||
|
Swap
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
trigger="click"
|
||||||
|
position="rightTop"
|
||||||
|
showArrow
|
||||||
|
>
|
||||||
|
<Button icon={<IconMore />} type="tertiary"></Button>
|
||||||
|
</Popover>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<Form.Input initValue={r.name} field="name" label="Name" />
|
||||||
|
<Form.Select
|
||||||
|
optionList={Object.values(Cardinality).map((v) => ({
|
||||||
|
label: v,
|
||||||
|
value: v,
|
||||||
|
}))}
|
||||||
|
field="cardinality"
|
||||||
|
label="Cardinality"
|
||||||
|
initValue={r.cardinality}
|
||||||
|
className="w-full"
|
||||||
|
></Form.Select>
|
||||||
|
<Row gutter={6}>
|
||||||
|
<Col span={12}>
|
||||||
|
<Form.Select
|
||||||
|
optionList={Object.values(Constraint).map((v) => ({
|
||||||
|
label: v,
|
||||||
|
value: v,
|
||||||
|
}))}
|
||||||
|
field="updateConstraint"
|
||||||
|
label="On update"
|
||||||
|
initValue={r.updateConstraint}
|
||||||
|
className="w-full"
|
||||||
|
></Form.Select>
|
||||||
|
</Col>
|
||||||
|
<Col span={12}>
|
||||||
|
<Form.Select
|
||||||
|
optionList={Object.values(Constraint).map((v) => ({
|
||||||
|
label: v,
|
||||||
|
value: v,
|
||||||
|
}))}
|
||||||
|
field="deleteConstraint"
|
||||||
|
label="On delete"
|
||||||
|
initValue={r.deleteConstraint}
|
||||||
|
className="w-full"
|
||||||
|
></Form.Select>
|
||||||
|
</Col>
|
||||||
|
</Row>
|
||||||
|
<div className="flex justify-between items-center my-3">
|
||||||
|
<label htmlFor="unique" className="font-medium text-black">
|
||||||
|
Mandetory
|
||||||
|
</label>
|
||||||
|
<Checkbox
|
||||||
|
value="mandetory"
|
||||||
|
defaultChecked={r.mandetory}
|
||||||
|
onChange={(checkedValues) =>
|
||||||
|
props.setRelationships((prev) =>
|
||||||
|
prev.map((e, idx) =>
|
||||||
|
idx === i
|
||||||
|
? {
|
||||||
|
...e,
|
||||||
|
[checkedValues.target.value]:
|
||||||
|
checkedValues.target.checked,
|
||||||
|
}
|
||||||
|
: e
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
></Checkbox>
|
||||||
|
</div>
|
||||||
|
</Form>
|
||||||
|
<Row gutter={6} className="mt-1">
|
||||||
|
<Col span={12}>
|
||||||
|
<Button
|
||||||
|
icon={<IconRowsStroked />}
|
||||||
|
disabled={r.cardinality === Cardinality.ONE_TO_ONE}
|
||||||
|
block
|
||||||
|
>
|
||||||
|
Extract to table
|
||||||
|
</Button>
|
||||||
|
</Col>
|
||||||
|
<Col span={12}>
|
||||||
|
<Button
|
||||||
|
icon={<IconDeleteStroked />}
|
||||||
|
block
|
||||||
|
type="danger"
|
||||||
|
onClick={() =>
|
||||||
|
props.setRelationships((prev) =>
|
||||||
|
prev
|
||||||
|
.filter((e) => e.id !== i)
|
||||||
|
.map((e, idx) => ({ ...e, id: idx }))
|
||||||
|
)
|
||||||
|
}
|
||||||
|
>
|
||||||
|
Delete
|
||||||
|
</Button>
|
||||||
|
</Col>
|
||||||
|
</Row>
|
||||||
|
</Collapse.Panel>
|
||||||
</div>
|
</div>
|
||||||
</Form>
|
))
|
||||||
<Row gutter={6} className="mt-1">
|
)}
|
||||||
<Col span={12}>
|
</Collapse>
|
||||||
<Button
|
</>
|
||||||
icon={<IconRowsStroked />}
|
|
||||||
disabled={r.cardinality === Cardinality.ONE_TO_ONE}
|
|
||||||
block
|
|
||||||
>
|
|
||||||
Extract to table
|
|
||||||
</Button>
|
|
||||||
</Col>
|
|
||||||
<Col span={12}>
|
|
||||||
<Button
|
|
||||||
icon={<IconDeleteStroked />}
|
|
||||||
block
|
|
||||||
type="danger"
|
|
||||||
onClick={() =>
|
|
||||||
props.setRelationships((prev) =>
|
|
||||||
prev
|
|
||||||
.filter((e) => e.id !== i)
|
|
||||||
.map((e, idx) => ({ ...e, id: idx }))
|
|
||||||
)
|
|
||||||
}
|
|
||||||
>
|
|
||||||
Delete
|
|
||||||
</Button>
|
|
||||||
</Col>
|
|
||||||
</Row>
|
|
||||||
</Collapse.Panel>
|
|
||||||
))}
|
|
||||||
</Collapse>
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -80,67 +80,65 @@ export default function TableOverview(props) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div className="p-2">
|
<Row gutter={6}>
|
||||||
<Row gutter={6}>
|
<Col span={16}>
|
||||||
<Col span={16}>
|
<AutoComplete
|
||||||
<AutoComplete
|
data={filteredResult}
|
||||||
data={filteredResult}
|
value={value}
|
||||||
value={value}
|
showClear
|
||||||
showClear
|
prefix={<IconSearch />}
|
||||||
prefix={<IconSearch />}
|
placeholder="Search..."
|
||||||
placeholder="Search..."
|
emptyContent={<div className="p-3">No tables found</div>}
|
||||||
emptyContent={<div className="p-3">No tables found</div>}
|
onSearch={(v) => handleStringSearch(v)}
|
||||||
onSearch={(v) => handleStringSearch(v)}
|
onChange={(v) => setValue(v)}
|
||||||
onChange={(v) => setValue(v)}
|
onSelect={(v) => {
|
||||||
onSelect={(v) => {
|
const { id } = props.tables.find((t) => t.name === v);
|
||||||
const { id, name } = props.tables.find((t) => t.name === v);
|
setTableActiveKey(`${id}`);
|
||||||
setTableActiveKey(`${id}`);
|
document
|
||||||
document
|
.getElementById(`scroll_table_${id}`)
|
||||||
.getElementById(`${name}_scroll_id`)
|
.scrollIntoView({ behavior: "smooth" });
|
||||||
.scrollIntoView({ behavior: "smooth" });
|
}}
|
||||||
}}
|
className="w-full"
|
||||||
className="w-full"
|
/>
|
||||||
/>
|
</Col>
|
||||||
</Col>
|
<Col span={8}>
|
||||||
<Col span={8}>
|
<Button
|
||||||
<Button
|
icon={<IconPlus />}
|
||||||
icon={<IconPlus />}
|
block
|
||||||
block
|
onClick={() => {
|
||||||
onClick={() => {
|
const id =
|
||||||
const id =
|
props.tables.length === 0
|
||||||
props.tables.length === 0
|
? 0
|
||||||
? 0
|
: props.tables[props.tables.length - 1].id + 1;
|
||||||
: props.tables[props.tables.length - 1].id + 1;
|
const newTable = {
|
||||||
const newTable = {
|
id: id,
|
||||||
id: id,
|
name: `table_${id}`,
|
||||||
name: `table_${id}`,
|
x: 0,
|
||||||
x: 0,
|
y: 0,
|
||||||
y: 0,
|
fields: [
|
||||||
fields: [
|
{
|
||||||
{
|
name: "id",
|
||||||
name: "id",
|
type: "UUID",
|
||||||
type: "UUID",
|
default: "",
|
||||||
default: "",
|
check: "",
|
||||||
check: "",
|
primary: true,
|
||||||
primary: true,
|
unique: true,
|
||||||
unique: true,
|
notNull: true,
|
||||||
notNull: true,
|
increment: true,
|
||||||
increment: true,
|
comment: "",
|
||||||
comment: "",
|
},
|
||||||
},
|
],
|
||||||
],
|
comment: "",
|
||||||
comment: "",
|
indices: [],
|
||||||
indices: [],
|
color: defaultTableTheme,
|
||||||
color: defaultTableTheme,
|
};
|
||||||
};
|
props.setTables((prev) => [...prev, newTable]);
|
||||||
props.setTables((prev) => [...prev, newTable]);
|
}}
|
||||||
}}
|
>
|
||||||
>
|
Add table
|
||||||
Add table
|
</Button>
|
||||||
</Button>
|
</Col>
|
||||||
</Col>
|
</Row>
|
||||||
</Row>
|
|
||||||
</div>
|
|
||||||
<Collapse
|
<Collapse
|
||||||
activeKey={tableActiveKey}
|
activeKey={tableActiveKey}
|
||||||
onChange={(k) => setTableActiveKey(k)}
|
onChange={(k) => setTableActiveKey(k)}
|
||||||
@ -163,7 +161,7 @@ export default function TableOverview(props) {
|
|||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
props.tables.map((t, i) => (
|
props.tables.map((t, i) => (
|
||||||
<div id={`${t.name}_scroll_id`} key={t.id}>
|
<div id={`scroll_table_${t.id}`} key={t.id}>
|
||||||
<Collapse.Panel header={<div>{t.name}</div>} itemKey={`${t.id}`}>
|
<Collapse.Panel header={<div>{t.name}</div>} itemKey={`${t.id}`}>
|
||||||
{t.fields.map((f, j) => (
|
{t.fields.map((f, j) => (
|
||||||
<Form
|
<Form
|
||||||
|
@ -12,12 +12,12 @@ export default function Editor(props) {
|
|||||||
const [relationships, setRelationships] = useState([]);
|
const [relationships, setRelationships] = useState([]);
|
||||||
const [areas, setAreas] = useState([]);
|
const [areas, setAreas] = useState([]);
|
||||||
const [resize, setResize] = useState(false);
|
const [resize, setResize] = useState(false);
|
||||||
const [width, setWidth] = useState(320);
|
const [width, setWidth] = useState(340);
|
||||||
|
|
||||||
const dragHandler = (e) => {
|
const dragHandler = (e) => {
|
||||||
if (!resize) return;
|
if (!resize) return;
|
||||||
const w = e.clientX;
|
const w = e.clientX;
|
||||||
if (w > 320) setWidth(w);
|
if (w > 340) setWidth(w);
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
Loading…
Reference in New Issue
Block a user