123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191 |
- import {
- FileAddOutlined,
- LayoutOutlined,
- PlusCircleFilled,
- ZoomInOutlined,
- ZoomOutOutlined,
- } from "@ant-design/icons";
- import { Button, Divider, Dropdown, Tooltip, Popover } from "antd";
- import NodeMenu from "@/components/NodeMenu";
- import type { MenuProps } from "antd/lib";
- import { useRef, useEffect, useState } from "react";
- import { MiniMap } from "@antv/x6-plugin-minimap";
- import { useModel } from "umi";
- import { DagreLayout } from "@antv/layout";
- export default function index() {
- const minimapRef = useRef<HTMLDivElement>(null);
- const { graph } = useModel("flowModel");
- const [scale, setScale] = useState(100);
- const zoomItems: MenuProps["items"] = [
- { key: "1", label: "25%" },
- { key: "2", label: "75%" },
- { key: "3", label: "100%" },
- { key: "4", label: "200%" },
- { key: "5", type: "divider" },
- { key: "6", label: "自适应" },
- ];
- useEffect(() => {
- if (graph && minimapRef.current) {
- const minimap = new MiniMap({
- container: minimapRef.current,
- width: 144,
- height: 100,
- padding: 10,
- scalable: true,
- minScale: 0.2,
- maxScale: 2,
- graphOptions: {
- background: {
- color: "#e9ebf0",
- },
- },
- });
- graph.use(minimap);
- }
- }, [graph, minimapRef.current]);
- // 添加备注节点
- const handleAddNotice = () => {
- const { width = 100, height = 100 } = graph?.getGraphArea() || {};
- graph?.addNode({
- shape: "notice-node",
- zIndex: -1,
- position: {
- x: width / 2 - 150,
- y: height / 2 - 100,
- },
- data: {
- name: "",
- text: "",
- },
- });
- };
- useEffect(() => {
- graph?.on("scale", (scaleInfo) => {
- setScale(parseInt(scaleInfo.sx * 100 + ""));
- });
- }, [graph]);
- const handleZoom = (value: number) => {
- graph?.zoomTo(value / 100);
- };
- const handleZoomFit = () => {
- graph?.zoomToFit({});
- };
- // 设置缩放值
- const handleOnChange = (value: number) => {
- setScale(Math.round(value));
- handleZoom(value);
- };
- // 自动布局
- const handleAutoLayout = () => {
- // 获取全部元素
- const nodes = graph?.getNodes();
- const edges = graph?.getEdges();
- const dagreLayout = new DagreLayout({
- type: "dagre",
- rankdir: "LR",
- align: "UR",
- ranksep: 35,
- nodesep: 15,
- // begin: [0, 0]
- });
- const model = dagreLayout.layout({
- nodes,
- edges
- });
- // graph?.fromJSON(model);
- console.log( nodes, edges, model);
- };
- return (
- <div className="absolute left-32px bottom-32px z-2 flex gap-12px">
- <div className="w-120px h-40px rounded-12px bg-#fff box-shadow-sm flex items-center justify-between px-12px">
- <Button
- type="text"
- icon={<ZoomOutOutlined />}
- disabled={scale <= 50}
- onClick={() => handleOnChange(scale - 10)}
- />
- <Dropdown
- menu={{
- items: zoomItems,
- style: { width: "160px", transform: "translate(-65px, -10px)" },
- }}
- >
- <span>{scale}%</span>
- </Dropdown>
- <Button
- type="text"
- icon={<ZoomInOutlined />}
- disabled={scale >= 200}
- onClick={() => handleOnChange(scale + 10)}
- />
- </div>
- <div
- className="absolute w-144px h-100px bg-#e9ebf0 top--110px rounded-12px overflow-hidden"
- ref={minimapRef}
- ></div>
- <div className="w-60px h-40px rounded-12px bg-#fff box-shadow-sm flex items-center justify-between px-12px">
- <Button
- type="text"
- icon={<i className="iconfont icon-undo" />}
- disabled={true}
- />
- <Button type="text" icon={<i className="iconfont icon-redo" />} />
- </div>
- <div className="h-40px rounded-12px bg-#fff box-shadow-sm flex items-center justify-between px-12px">
- {/* <Popover
- content={<NodeMenu graph={graph} />}
- trigger="click"
- placement="top"
- arrow={false}
- >
- <Button type="text" icon={<PlusCircleFilled />}>
- 添加节点
- </Button>
- </Popover> */}
- <Tooltip title="添加文本">
- <Button
- type="text"
- icon={<FileAddOutlined />}
- onClick={handleAddNotice}
- />
- </Tooltip>
- <Divider type="vertical" />
- <Tooltip title="指针模式">
- <Button
- type="text"
- icon={<i className="iconfont icon-24gl-pointer" />}
- />
- </Tooltip>
- <Tooltip title="手模式">
- <Button type="text" icon={<i className="iconfont icon-shou1" />} />
- </Tooltip>
- <Divider type="vertical" />
- <Tooltip title="自动布局">
- <Button
- type="text"
- icon={<LayoutOutlined />}
- onClick={handleAutoLayout}
- />
- </Tooltip>
- </div>
- </div>
- );
- }
|