- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
这段代码是我的项目的一部分,我试图在其中制作力布局图。节点之间的所有链接都应该有一个标记,我通过 defs 模式制作它们(标记)。
在此代码中,我希望在 defs
中看到已定义的标记,我已通过 url(#id)
调用它们,但我没有看到它,但我没有收到任何错误。它以前是工作的,但突然间我的代码中所有的 defs
都被禁用了。在这里你可以看到结果 svg:
<!DOCTYPE html>
<meta charset="utf-8">
<style>
body {
font: 10px sans-serif;
shape-rendering: crispEdges;
}
.link.flow {
opacity: 1!important;
/*stroke-width: 1.5px;*/
}
#licensing {
fill: green;
}
.link.flow.licensing {
stroke: green;
}
.link.flow.resolved {
stroke-dasharray: 0,2 1;
}
circle.flow {
fill: #ff2575;
stroke: #ff2575;
/*stroke-width: 1.5px;*/
}
text.flow {
font: 10px sans-serif;
pointer-events: none;
text-shadow: 0 1px 0 #fff, 1px 0 0 #fff, 0 -1px 0 #fff, -1px 0 0 #fff;
}
path.link.flow {
fill: none;
stroke: blue;
}
</style>
<body>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script>
<script>
var maxWeight = 0;
var maxSize = 0;
// new graph: start
var margin = 10;
var width = 455,
height = 350;
var svgMaster = d3.select("body").append("svg") // initiate svg
.attr("id","flow")
.attr("width", width)
.attr("height", height)
.style("margin-right",margin+"px")
.style("margin-left",margin+"px");
var svg = svgMaster.append('svg:g')
.attr('id','groupFlow');
var link = svg.selectAll(".link"),
node = svg.selectAll(".node"); // nodes and links
// :end new graph
var jsonData = {
"nodes": [
{"username": "S_Christophorus", "social_net_id": "55641120cdfa6618acdd1952", "last_name":
"Christophorus", "first_name": "Stanly", "avatar": "/media/avatars/C02.png", "person_id": "556431f3cdfa661108325774"
, "id": "55641120cdfa6618acdd1a8e"},
{"username": "A_Field", "social_net_id": "55641120cdfa6618acdd1952"
, "last_name": "Field", "first_name": "Abdul", "avatar": "/media/avatars/B01.png", "person_id": "556431f3cdfa6611083257f6"
, "id": "55641120cdfa6618acdd1b94"},
{"username": "B_Hugh", "social_net_id": "55641120cdfa6618acdd1952"
, "last_name": "Hugh", "first_name": "Beale", "avatar": "/media/avatars/B02.png", "person_id": "556431f3cdfa6611083257f7"
, "id": "55641120cdfa6618acdd1b96"},
{"username": "M_Kennedy", "social_net_id": "55641120cdfa6618acdd1952"
, "last_name": "Kennedy", "first_name": "Mordy", "avatar": "/media/avatars/B05.png", "person_id": "556431facdfa661108327e21"
, "id": "55641128cdfa6618acdd9fed"}
],
"edges": [
{"source": 0, "target": 1, "weight": 1.5},
{"source": 2, "target": 0, "weight": 46.5},
{"source": 0, "target": 2, "weight": 6.0},
{"source": 2, "target": 1, "weight": 1.5},
{"source": 2, "target": 3, "weight": 3.0}
]
}
/*
* refresh graph based on given data
*/
var refreshForceFlow = function(json){
clearGraphFlow();
var maxWeight = 0;
for(var edgeIndex = 0; edgeIndex < json.edges.length; edgeIndex++){
if(json.edges[edgeIndex].weight > maxWeight) maxWeight = json.edges[edgeIndex];
}
console.log(json);
var force = d3.layout.force()
.nodes(d3.values(json.nodes))
.links(json.edges)
.size([width, height])
.linkDistance(60)
.charge(-300)
.on("tick", tickFlow)
.start();
// Per-type markers, as they don't inherit styles.
svg.append("defs").selectAll("marker")
.data(json.edges)
.enter().append("marker")
.attr("id", function(d) { return ("weight_"+d.weight).replace(".","_"); })
.attr("viewBox", "0 -5 10 10")
.attr("refX", 13) // 15
.attr("refY", 0) // -1.5
.attr("markerWidth", 6)
.attr("markerHeight", 6)
.attr("orient", "auto")
.append("path")
.style("fill", function(d){
var color = 'FF';
var c = Math.floor((d.weight*99)/maxWeight);
c = 100 - c;
if( c < 10) c = '0'+c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#'+color;
})
.style("stroke", function(d){
var color = 'FF';
var c = Math.floor((d.weight*99)/maxWeight);
c = 100 - c;
if( c < 10) c = '0'+c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#'+color;
})
.style("stroke-width", "1px")
.attr("d", "M0,-5L10,0L0,5");
var path = svg.append("g").selectAll("path")
.data(force.links())
.enter().append("path")
.attr("class", function(d) { return "link flow "; })
.style("stroke-width", function(d) {
var res = 1 + ((d.weight * 2.5) / maxWeight);
return res + 'px';
})
.style("stroke", function(d){
var color = 'FF';
var c = Math.floor((d.weight*99)/maxWeight);
c = 100 - c;
if( c < 10) c = '0'+c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#'+color;
})
.attr("marker-end", function(d) { return "url(#" + ("weight_"+d.weight).replace(".","_") + ")"; });
var circle = svg.append("g").selectAll("circle")
.data(force.nodes())
.enter().append("circle")
.attr("r", 6)
.attr("class", "flow")
.call(force.drag);
var text = svg.append("g").selectAll("text")
.data(force.nodes())
.enter().append("text")
.attr("class", "flow")
.attr("x", 8)
.attr("y", ".31em")
.text(function(d) { return d.username; });
// Use elliptical arc path segments to doubly-encode directionality.
function tickFlow() {
path.attr("d", linkArc);
circle.attr("transform", transform);
text.attr("transform", transform);
}
function linkArc(d) {
var tx = d.target.x - 0;
var ty = d.target.y - 0;
var sx = d.source.x - 0;
var sy = d.source.y - 0;
var dx = tx - sx,
dy = ty - sy,
dr = Math.sqrt(dx * dx + dy * dy);
return "M" + d.source.x + "," + d.source.y + "A" + dr + "," + dr + " 0 0,1 " + d.target.x + "," + d.target.y;
}
function transform(d) {
return "translate(" + d.x + "," + d.y + ")";
}
}; // end of function
/*
* clear gragh
*/
var clearGraphFlow = function(){
svg.selectAll("g").remove();
svg.selectAll("defs").remove();
};
refreshForceFlow(jsonData);
</script>
最佳答案
我在之前的回答中指出的问题是 refs 问题的原因,但在整个代码中也存在其他问题。请参阅下面更正后的代码...
//debug panel///////////////////////////////////////////////////////////////////////////////////////////
var update = d3.select("#update")
.on("click", (function() {
var dataSet = false;
return function() {
refreshForceFlow(JSON.parse(JSON.stringify(jsonData[(dataSet = !dataSet, +dataSet)])))
}
})());
////////////////////////////////////////////////////////////////////////////////////////////////////////
var maxWeight = 0;
var maxSize = 0;
// new graph: start
var margin = 10;
var width = 500,
height = 150;
var svgMaster = d3.select("body").append("svg") // initiate svg
.attr("id", "flow")
.attr("width", width)
.attr("height", height)
.style("margin-right", margin + "px")
.style("margin-left", margin + "px");
var svg = svgMaster.append('svg:g')
.attr('id', 'groupFlow');
var link = svg.selectAll(".link"),
node = svg.selectAll(".node"); // nodes and links
// :end new graph
var jsonData = [{
"nodes": [{
"username": "S_Christophorus",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Christophorus",
"first_name": "Stanly",
"avatar": "/media/avatars/C02.png",
"person_id": "556431f3cdfa661108325774",
"id": "55641120cdfa6618acdd1a8e"
}, {
"username": "A_Field",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Field",
"first_name": "Abdul",
"avatar": "/media/avatars/B01.png",
"person_id": "556431f3cdfa6611083257f6",
"id": "55641120cdfa6618acdd1b94"
}, {
"username": "B_Hugh",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Hugh",
"first_name": "Beale",
"avatar": "/media/avatars/B02.png",
"person_id": "556431f3cdfa6611083257f7",
"id": "55641120cdfa6618acdd1b96"
}, {
"username": "M_Kennedy",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Kennedy",
"first_name": "Mordy",
"avatar": "/media/avatars/B05.png",
"person_id": "556431facdfa661108327e21",
"id": "55641128cdfa6618acdd9fed"
}],
"edges": [{
"source": "0",
"target": "1",
"weight": 1.5
}, {
"source": "2",
"target": "0",
"weight": 46.5
}, {
"source": "0",
"target": "2",
"weight": 6.0
}, {
"source": "2",
"target": "1",
"weight": 1.5
}, {
"source": "2",
"target": "3",
"weight": 3.0
}]
}, {
"nodes": [{
"username": "A_Field",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Christophorus",
"first_name": "Stanly",
"avatar": "/media/avatars/C02.png",
"person_id": "556431f3cdfa661108325774",
"id": "55641120cdfa6618acdd1a8e"
}, {
"username": "B_Hugh",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Field",
"first_name": "Abdul",
"avatar": "/media/avatars/B01.png",
"person_id": "556431f3cdfa6611083257f6",
"id": "55641120cdfa6618acdd1b94"
}, {
"username": "M_Kennedy",
"social_net_id": "55641120cdfa6618acdd1952",
"last_name": "Hugh",
"first_name": "Beale",
"avatar": "/media/avatars/B02.png",
"person_id": "556431f3cdfa6611083257f7",
"id": "55641120cdfa6618acdd1b96"
}],
"edges": [{
"source": "0",
"target": "1",
"weight": 1.5
}, {
"source": "2",
"target": "0",
"weight": 26.5
}, {
"source": "0",
"target": "2",
"weight": 16.0
}, {
"source": "2",
"target": "1",
"weight": 1.5
}]
}];
/*
* refresh graph based on given data
*/
var refreshForceFlow = (function() {
// Need to use a single instance of force because of
// this bug https://github.com/mbostock/d3/issues/2468
// hence the closure...
var force = d3.layout.force()
.size([width, height])
.linkDistance(60)
.charge(-300)
return function(json) {
// clearGraphFlow(); ***d3 does this for you if you do it right***
// var maxWeight = 0;
//***this code is already written for you: you just need to wire it up***
// for(var edgeIndex = 0; edgeIndex < json.edges.length; edgeIndex++){
// if(json.edges[edgeIndex].weight > maxWeight) maxWeight = json.edges[edgeIndex];
// }
var maxWeight = d3.max(json.edges, function(d) {
return d.weight
});
//clean up the data: force needs type Number on link.source/destination
json.edges.forEach(function(d) {
d.source = +d.source;
d.target = +d.target
});
console.log(json);
force
.nodes(json.nodes) //***don't need to wrap in d3.value***
.links(json.edges)
.on("tick", tickFlow)
.start();
// Per-type markers, as they don't inherit styles.
// UPDATE
var defs = svg.selectAll("defs").data([json.edges]);
// EXIT
defs.exit().remove();
// ENTER
defs.enter().append("defs");
// UPDATE+ENTER for defs
// UPDATE for markers
var markers = defs.selectAll("marker")
.data(function(d) {
return d
}); //get the data elements from the defs datum
//ENTER
markers.enter().append("marker") //new markers only
.attr("viewBox", "0 -5 10 10")
.attr("refX", 13) // 15
.attr("refY", 0) // -1.5
.attr("markerWidth", 6)
.attr("markerHeight", 6)
.attr("orient", "auto")
.append("path");
// UPDATE+ENTER
markers.attr("id", function(d) {
return ("weight_" + d.weight).replace(".", "_");
})
.select("path")
.style("fill", function(d) {
var color = 'FF';
var c = Math.floor((d.weight * 99) / maxWeight);
c = 100 - c;
if (c < 10) c = '0' + c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#' + color;
})
.style("stroke", function(d) {
var color = 'FF';
var c = Math.floor((d.weight * 99) / maxWeight);
c = 100 - c;
if (c < 10) c = '0' + c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#' + color;
})
.style("stroke-width", "1px")
.attr("d", "M0,-5L10,0L0,5");
// EXIT
markers.exit().remove();
var link = svg.selectAll("g.link").data(force.links());
link.enter().insert("g", ".link").attr("class", "link")
.append("path")
.attr("class", "link flow"); //***don't need a function for constant value***;
link.exit().remove();
path = link.select("path")
.style("stroke-width", function(d) {
var res = 1 + ((d.weight * 2.5) / maxWeight);
return Math.round(res) + 'px';
})
.style("stroke", function(d) {
var color = 'FF';
var c = Math.floor((d.weight * 99) / maxWeight);
c = 100 - c;
if (c < 10) c = '0' + c;
color = c + color;
color = c + color;
//console.log('#'+color);
return '#' + color;
})
.attr("marker-end", function(d) {
return "url(#" + ("weight_" + d.weight).replace(".", "_") + ")";
});
var node = svg.selectAll("g.node")
.data(force.nodes()), //node is the node container: includes circle and text
nodeEnter = node.enter().append("g").call(force.drag),
//append the circle and the text inside the node g
//ENTER
circle = nodeEnter.attr("class", "node")
.append("circle")
.attr("r", 6)
.attr("class", "flow"),
// .on("contextmenu", d3.contextMenu(menu)),
text = nodeEnter.append("text")
.attr("class", "flow")
.attr("x", 8)
.attr("y", ".31em")
.style({
"pointer-events": "all",
cursor: "default"
}) //***include dragging by text***
//ENTER+UPDATE
text.text(function(d) {
return d.username;
});
// EXIT
node.exit().remove();
// Use elliptical arc path segments to doubly-encode directionality.
function tickFlow(e) {
path.attr("d", linkArc);
node.attr("transform", transform); //circle and text is wrapped by node
}
function linkArc(d) {
var tx = d.target.x - 0;
var ty = d.target.y - 0;
var sx = d.source.x - 0;
var sy = d.source.y - 0;
var dx = tx - sx,
dy = ty - sy,
dr = Math.sqrt(dx * dx + dy * dy);
return "M" + d.source.x + "," + d.source.y + "A" + dr + "," + dr + " 0 0,1 " + d.target.x + "," + d.target.y;
}
function transform(d) {
return "translate(" + d.x + "," + d.y + ")";
}
}; // end of function
})();
/*
* clear gragh
*/
// var clearGraphFlow = function(){ // ***Not required***
// svg.selectAll("g").remove();
// svg.selectAll("defs").remove();
// };
refreshForceFlow(JSON.parse(JSON.stringify(jsonData[0])));
body {
font: 10px sans-serif;
shape-rendering: crispEdges;
}
svg {
outline: 1px solid red;
overflow: visible;
}
.link.flow {
opacity: 1!important;
/*stroke-width: 1.5px;*/
}
#licensing {
fill: green;
}
.link.flow.licensing {
stroke: green;
}
.link.flow.resolved {
stroke-dasharray: 0, 2 1;
}
circle.flow {
fill: #ff2575;
stroke: #ff2575;
stroke-width: 1.5px;
}
text.flow {
font: 10px sans-serif;
pointer-events: none;
text-shadow: 0 1px 0 #fff, 1px 0 0 #fff, 0 -1px 0 #fff, -1px 0 0 #fff;
}
path.link.flow {
fill: none;
stroke: blue;
}
div#panel {
display: block;
}
input {
margin: 10px;
}
<div id="panel">
<input id="update" type="button" value="update">
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script>
关于javascript - D3.js defs 和 url() 不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31317837/
我正在学习构建单页应用程序 (SPA) 所需的所有技术。总而言之,我想将我的应用程序实现为单独的层,其中前端仅使用 API Web 服务(json 通过 socket.io)与后端通信。前端基本上是
当我看到存储在我的数据库中的日期时。 这是 正常 。日期和时间就是这样。 但是当我运行 get 请求来获取数据时。 此格式与存储在数据库 中的格式不同。为什么会发生这种情况? 最佳答案 我认为您可以将
就目前而言,这个问题不适合我们的问答形式。我们希望答案得到事实、引用资料或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visit the
我正在尝试使用backbone.js 实现一些代码 和 hogan.js (http://twitter.github.com/hogan.js/) Hogan.js was developed ag
我正在使用 Backbone.js、Node.js 和 Express.js 制作一个 Web 应用程序,并且想要添加用户功能(登录、注销、配置文件、显示内容与该用户相关)。我打算使用 Passpor
关闭。这个问题需要多问focused 。目前不接受答案。 想要改进此问题吗?更新问题,使其仅关注一个问题 editing this post . 已关闭 8 年前。 Improve this ques
我尝试在 NodeJS 中加载数据,然后将其传递给 ExpressJS 以在浏览器中呈现 d3 图表。 我知道我可以通过这种方式加载数据 - https://github.com/mbostock/q
在 node.js 中,我似乎遇到了相同的 3 个文件名来描述应用程序的主要入口点: 使用 express-generator 包时,会创建一个 app.js 文件作为生成应用的主要入口点。 通过 n
最近,我有机会观看了 john papa 关于构建单页应用程序的精彩类(class)。我会喜欢的。它涉及服务器端和客户端应用程序的方方面面。 我更喜欢客户端。在他的实现过程中,papa先生在客户端有类
就目前而言,这个问题不适合我们的问答形式。我们希望答案得到事实、引用资料或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visit the
我是一个图形新手,需要帮助了解各种 javascript 2D 库的功能。 . . 我从 Pixi.js 中得到了什么,而我没有从 Konva 等基于 Canvas 的库中得到什么? 我从 Konva
我正在尝试将一些 LESS 代码(通过 ember-cli-less)构建到 CSS 文件中。 1) https://almsaeedstudio.com/ AdminLTE LESS 文件2) Bo
尝试查看 Express Passport 中所有登录用户的所有 session ,并希望能够查看当前登录的用户。最好和最快的方法是什么? 我在想也许我可以在登录时执行此操作并将用户模型数据库“在线”
我有一个 React 应用程序,但我需要在组件加载完成后运行一些客户端 js。一旦渲染函数完成并加载,运行与 DOM 交互的 js 的最佳方式是什么,例如 $('div').mixItUp() 。对
请告诉我如何使用bodyparser.raw()将文件上传到express.js服务器 客户端 // ... onFilePicked(file) { const url = 'upload/a
我正在尝试从 Grunt 迁移到 Gulp。这个项目在 Grunt 下运行得很好,所以我一定是在 Gulp 中做错了什么。 除脚本外,所有其他任务均有效。我现在厌倦了添加和注释部分。 我不断收到与意外
我正在尝试更改我的网站名称。找不到可以设置标题或应用程序名称的位置。 最佳答案 您可以在 config/ 目录中创建任何文件,例如 config/app.js 包含如下内容: module.expor
经过多年的服务器端 PHP/MySQL 开发,我正在尝试探索用于构建现代 Web 应用程序的新技术。 我正在尝试对所有 JavaScript 内容进行排序,如果我理解得很好,一个有效的解决方案可以是服
我是 Nodejs 的新手。我在 route 目录中有一个 app.js 和一个 index.js。我有一个 app.use(multer....)。我还定义了 app.post('filter-re
我正在使用 angular-seed用于构建我的应用程序的模板。最初,我将所有 JavaScript 代码放入一个文件 main.js。该文件包含我的模块声明、 Controller 、指令、过滤器和
我是一名优秀的程序员,十分优秀!