You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将对象列表插入GoJs?Java控制器传参至JSP页面展示方案

我来一步步帮你搞定这个需求,从后端传数据到前端用GoJS渲染再到详情展示,全流程给你捋清楚:

1. 后端Java控制器:把对象列表转成JSON传到JSP

首先得把你的对象列表转换成JSON格式——毕竟前端JavaScript能直接处理JSON。假设你的实体类是Entity,包含id、name、description、parentId这类字段(你可以根据实际结构调整),用Jackson库来序列化列表到JSON字符串就很方便:

import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.servlet.ModelAndView;
import java.util.List;

@Controller
public class EntityController {

    @GetMapping("/show-diagram")
    public ModelAndView showDiagram() {
        ModelAndView mav = new ModelAndView("diagram-page"); // 你的JSP页面名称
        List<Entity> entityList = getEntityList(); // 从数据库/业务层获取对象列表
        
        // 转成JSON字符串
        ObjectMapper mapper = new ObjectMapper();
        String jsonData = mapper.writeValueAsString(entityList);
        
        mav.addObject("entityJson", jsonData);
        return mav;
    }
    
    // 模拟数据获取逻辑,替换成你的实际业务代码
    private List<Entity> getEntityList() {
        return List.of(
            new Entity(1, "用户管理模块", "负责系统用户的增删改查", null),
            new Entity(2, "权限配置", "分配用户角色与操作权限", 1),
            new Entity(3, "日志记录", "记录用户操作行为", 1)
        );
    }
}
2. JSP页面:接收JSON并初始化GoJS

在JSP里先引入GoJS脚本,接着把后端传的JSON转成JS变量,然后构建GoJS图、定义节点模板,最后处理节点点击展示详情的逻辑:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
    <title>GoJS 实体详情展示</title>
    <!-- 引入GoJS -->
    <script src="https://unpkg.com/gojs/release/go.js"></script>
    <style>
        #myDiagramDiv {
            width: 800px;
            height: 500px;
            border: 1px solid #ccc;
            float: left;
        }
        #detailPanel {
            width: 300px;
            height: 500px;
            border: 1px solid #ccc;
            float: left;
            margin-left: 20px;
            padding: 15px;
            box-sizing: border-box;
        }
    </style>
</head>
<body>
    <div id="myDiagramDiv"></div>
    <div id="detailPanel">点击任意节点查看详情</div>

    <script>
        // 从后端获取JSON数据,用<c:out>转义避免语法错误和XSS风险
        const entityData = JSON.parse('<c:out value="${entityJson}" />');
        
        // 初始化GoJS Diagram
        const $ = go.GraphObject.make;
        const diagram = $(go.Diagram, "myDiagramDiv", {
            layout: $(go.TreeLayout, { angle: 90, layerSpacing: 80 }), // 树形布局,可按需更换
            "undoManager.isEnabled": true
        });
        
        // 定义节点模板,可自定义样式
        diagram.nodeTemplate = $(go.Node, "Auto",
            $(go.Shape, "RoundedRectangle", {
                fill: "#5B9BD5",
                stroke: "#1E4D72",
                strokeWidth: 2
            },
                new go.Binding("fill", "isSelected", sel => sel ? "#FFA500" : "#5B9BD5").ofObject()),
            $(go.TextBlock, {
                margin: 12,
                font: "14px sans-serif",
                stroke: "white",
                wrap: go.TextBlock.WrapFit
            },
                new go.Binding("text", "name"))
        );
        
        // 定义链接模板(如果是关联结构需要,无关联可删除)
        diagram.linkTemplate = $(go.Link,
            $(go.Shape, { stroke: "#1E4D72", strokeWidth: 2 }),
            $(go.Shape, { toArrow: "Standard", fill: "#1E4D72", stroke: "#1E4D72" })
        );
        
        // 把实体数据转换成GoJS需要的节点/链接格式
        const nodeDataArray = [];
        const linkDataArray = [];
        
        entityData.forEach(entity => {
            // 把所有详情字段存入节点数据,方便后续展示
            nodeDataArray.push({
                key: entity.id,
                name: entity.name,
                detail: {
                    id: entity.id,
                    name: entity.name,
                    description: entity.description
                    // 这里添加你需要展示的其他字段
                }
            });
            
            // 存在父节点时添加链接
            if (entity.parentId != null) {
                linkDataArray.push({ from: entity.parentId, to: entity.id });
            }
        });
        
        // 加载数据到Diagram
        diagram.model = new go.GraphLinksModel(nodeDataArray, linkDataArray);
        
        // 节点点击事件:展示详情到右侧面板
        diagram.addDiagramListener("ObjectSingleClicked", e => {
            const detailPanel = document.getElementById("detailPanel");
            const clickedNode = e.subject.part;
            
            if (clickedNode instanceof go.Node) {
                const detail = clickedNode.data.detail;
                // 渲染详情HTML
                let detailHtml = `<h3>${detail.name}</h3>`;
                detailHtml += `<p><strong>ID:</strong> ${detail.id}</p>`;
                detailHtml += `<p><strong>描述:</strong> ${detail.description}</p>`;
                // 其他字段继续补充...
                detailPanel.innerHTML = detailHtml;
            } else {
                detailPanel.innerHTML = "点击任意节点查看详情";
            }
        });
    </script>
</body>
</html>
3. 关键注意事项
  • JSON转义:必须用<c:out>输出后端传的JSON,避免引号、换行等字符导致JS语法错误,同时防止XSS攻击。
  • GoJS数据格式:GraphLinksModel需要节点数组(每个节点要有唯一key)和链接数组(每个链接要有from/to对应节点key);如果只是单纯展示列表,不用链接的话,换成Model即可。
  • 布局选择:示例用的是树形布局,你可以换成GridLayout(网格布局)、ForceDirectedLayout(力导向布局)等,根据你的展示需求调整。
  • 详情展示:直接把所有详情字段存入节点数据,点击时就能快速渲染,比AJAX请求更高效;如果数据量极大,再考虑按需请求详情。

内容的提问来源于stack exchange,提问作者DILSHAD

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 06:52:35