我想创建 JSON 表模式的可视化。这些可视化将在 p5.js 画布上生成。我已经为此任务编写了一些代码,包括架构之间的连接、拖动功能等等。然而,当我使用不同的 JSON 结构(包括复杂的嵌套结构)对其进行测试时,我发现我的渲染方法无法正常工作。这是我的渲染方法:
createTable({title, uid, isBase}) {
return this.handler.addTable(uid,title,isBase)
}
createColumn(table, title, isSub = false) {
return table.addColumn(title, isSub)
}
render(data, uid, isBase, ptable = null) {
if(ptable == null) {
ptable = this.createTable({
title: uid,
isBase,
uid: uid,
inside: true,
parent: uid
})
}
for(let i in data) {
if (Array.isArray(data[i])) {
this.render(data[i][0], uid, isBase, ptable);
}
else if(typeof data[i] == 'object') {
this.createColumn(ptable, data[i] + " (sub)", true);
Object.keys(data[i]).forEach(key => {
this.createColumn(ptable, key);
this.render(data[key], uid, isBase, ptable);
});
} else {
console.log(typeof data)
this.createColumn(ptable, i);
}
}
}
此代码无法与此 JSON 完美配合。我截了一些截图来说明问题。
例如这个 JSON
{
"id": "0001",
"type": "donut",
"name": "Cake",
"ppu": 0.55,
"batters":
{
"batter":
[
{ "id": "1001", "type": "Regular" },
{ "id": "1002", "type": "Chocolate" },
{ "id": "1003", "type": "Blueberry" },
{ "id": "1004", "type": "Devil's Food" }
]
},
"topping":
[
{ "id": "5001", "type": "None" },
{ "id": "5002", "type": "Glazed" },
{ "id": "5005", "type": "Sugar" },
{ "id": "5007", "type": "Powdered Sugar" },
{ "id": "5006", "type": "Chocolate with Sprinkles" },
{ "id": "5003", "type": "Chocolate" },
{ "id": "5004", "type": "Maple" }
]
}
我想要的结果是这样的:
"id"
"type"
"name"
"ppu"
"batters (sub table)"
"batter (sub table)"
"id"
"type"
"topping (sub table)"
"id"
"type"
非常感谢您的关注...
function extractFields(obj, parentKey = '') {
let fields = [];
for (let key in obj) {
let currentKey = parentKey ? `${parentKey}.${key}` : key;
currentKey = currentKey.replace(/^\d+(\.)*/, "")
if (typeof obj[key] === 'object' && !Array.isArray(obj[key])) {
fields.push(currentKey);
fields = fields.concat(this.extractFields(obj[key], currentKey));
} else if (Array.isArray(obj[key])) {
if (obj[key].length > 0 && typeof obj[key][0] === 'object') {
fields.push(currentKey);
fields = fields.concat(this.extractFields(obj[key][0], currentKey));
} else {
fields.push(currentKey);
}
} else {
fields.push(currentKey);
}
}
return [...new Set(fields.filter(Boolean))];
}
console.log(extractFields([{
"id": "0001",
"type": "donut",
"name": "Cake",
"ppu": 0.55,
"batters":
{
"batter":
[
{ "id": "1001", "type": "Regular" },
]
},
"topping":
[
{ "id": "5001", "type": "None" },
{ "id": "5004", "type": "Maple" }
]
},
{
"id": "0002",
"type": "donut",
"name": "Raised",
"ppu": 0.55,
"batters":
{
"batter":
[
{ "id": "1001", "type": "Regular" }
]
},
"topping":
[
{ "id": "5001", "type": "None" },
]
}
]))