- Java 双重比较
- java - 比较器与 Apache BeanComparator
- Objective-C 完成 block 导致额外的方法调用?
- database - RESTful URI 是否应该公开数据库主键?
我想在 Canvas 中将几条腿显示为矩形。基于将我的腿的英里数分组的数组,我制定了算法以在给定的 Canvas 上按比例表示它们。
var c = document.getElementById("myCanvas");
var ctx = c.getContext("2d");
var width = c.width;
var somme = 0;
var prevValue = 0;
var recapProp = [];
function drawArrow(fromx, fromy, tox, toy){
//variables to be used when creating the arrow
var headlen = 5;
var angle = Math.atan2(toy-fromy,tox-fromx);
//starting path of the arrow from the start square to the end square and drawing the stroke
ctx.beginPath();
ctx.moveTo(fromx, fromy);
ctx.lineTo(tox, toy);
ctx.strokeStyle = "blue";
ctx.lineWidth = 2;
ctx.stroke();
//starting a new path from the head of the arrow to one of the sides of the point
ctx.beginPath();
ctx.moveTo(tox, toy);
ctx.lineTo(tox-headlen*Math.cos(angle-Math.PI/7),toy-headlen*Math.sin(angle-Math.PI/7));
//path from the side point of the arrow, to the other side point
ctx.lineTo(tox-headlen*Math.cos(angle+Math.PI/7),toy-headlen*Math.sin(angle+Math.PI/7));
//path from the side point back to the tip of the arrow, and then again to the opposite side point
ctx.lineTo(tox, toy);
ctx.lineTo(tox-headlen*Math.cos(angle-Math.PI/7),toy-headlen*Math.sin(angle-Math.PI/7));
//draws the paths created above
ctx.strokeStyle = "blue";
ctx.lineWidth = 2;
ctx.stroke();
ctx.fillStyle = "blue";
ctx.fill();
}
function drawCircle(centerXFrom, centerYFrom){
var radius = 3;
ctx.beginPath();
ctx.arc(centerXFrom, centerYFrom, radius, 0, 2 * Math.PI, false);
ctx.fillStyle = 'green';
ctx.fill();
ctx.lineWidth = 1;
ctx.strokeStyle = '#003300';
ctx.stroke();
ctx.beginPath();
}
function sumTab(tabTT){
for (var i = 0; i < tabTT.length; i++){
somme += tabTT[i];
}
return somme;
}
function findProportion(tabTT){
var tailleMax = tabTT.length;
sumTab(tabTT);
for(var i = 0; i < tabTT.length; i++){
var percentLeg = (tabTT[i]/somme)*100;
var tailleLeg = ((width- 20)*percentLeg)/100 ;
recapProp.push(tailleLeg);
}
for(var i = 0; i <= recapProp.length; ++i){
console.log(prevValue);
drawCircle(prevValue +5, 5);
drawArrow(prevValue + 7, 5, prevValue+recapProp[i],5);
prevValue += recapProp[i];
}
}
var tabTT = [0,5,1,8,2];
findProportion(tabTT);
<canvas id="myCanvas" height="200" width="500"></canvas>
然后,我想把then以矩形的形式显示出来,做一个循环(下面不是矩形,但是可以帮助大家理解):
我已经尝试操纵 quadracticCurveTo()
但这并不是真正决定性的..
var c=document.getElementById("myCanvas");
var ctx=c.getContext("2d");
function drawArrow(fromx, fromy, tox, toy, radius){
//variables to be used when creating the arrow
var headlen = 5;
var r = fromx + tox;
var b = fromy + toy;
var angle = Math.atan2(r,b);
//starting path of the arrow from the start square to the end square and drawing the stroke
ctx.beginPath();
ctx.moveTo(fromx+radius, fromy);
ctx.lineTo(r-radius, fromy);
ctx.quadraticCurveTo(r, fromy, r, fromy+radius);
ctx.lineWidth = "2";
ctx.strokeStyle = '#ff0000';
ctx.stroke();
//starting a new path from the head of the arrow to one of the sides of the point
ctx.beginPath();
ctx.moveTo(r, b);
ctx.lineTo(r-headlen*Math.cos(angle-Math.PI/7),b-headlen*Math.sin(angle-Math.PI/7));
//path from the side point of the arrow, to the other side point
ctx.lineTo(r-headlen*Math.cos(angle+Math.PI/7),b-headlen*Math.sin(angle+Math.PI/7));
//path from the side point back to the tip of the arrow, and then again to the opposite side point
ctx.lineTo(r, b);
ctx.lineTo(r-headlen*Math.cos(angle-Math.PI/7),b-headlen*Math.sin(angle-Math.PI/7));
//draws the paths created above
ctx.strokeStyle = "blue";
ctx.lineWidth = 2;
ctx.stroke();
ctx.fillStyle = "blue";
ctx.fill();
}
drawArrow(50,5, 80,25, 25);
<canvas id="myCanvas" height="2000" width="2000"></canvas>
最后,我创建了当我知道如何弯曲我的线条并保持其长度时需要的片段!。我已经计算了我的 Canvas 表面的周长,以便重新计算我的腿的比例。
var c = document.getElementById("myCanvas");
var ctx = c.getContext("2d");
var width = c.width;
var height = c.height;
var perimetre = (width*2 + height*2);
var up = 0;
var right = 0;
var left = 0;
var bot = 0;
var somme = 0;
var prevValue = 0;
var recapProp = [];
/**********************************/
/*****<<Straight>> Arrows*********/
/********************************/
function drawArrow(fromx, fromy, tox, toy){
var headlen = 5;
var angle = Math.atan2(toy-fromy,tox-fromx);
ctx.beginPath();
ctx.moveTo(fromx, fromy);
ctx.lineTo(tox, toy);
ctx.strokeStyle = "blue";
ctx.lineWidth = 2;
ctx.stroke();
ctx.beginPath();
ctx.moveTo(tox, toy);
ctx.lineTo(tox-headlen*Math.cos(angle-Math.PI/7),toy-headlen*Math.sin(angle-Math.PI/7));
ctx.lineTo(tox-headlen*Math.cos(angle+Math.PI/7),toy-headlen*Math.sin(angle+Math.PI/7));
ctx.lineTo(tox, toy);
ctx.lineTo(tox-headlen*Math.cos(angle-Math.PI/7),toy-headlen*Math.sin(angle-Math.PI/7));
ctx.strokeStyle = "blue";
ctx.lineWidth = 2;
ctx.stroke();
ctx.fillStyle = "blue";
ctx.fill();
}
/**********************************/
/************Points***************/
/********************************/
function drawCircle(centerXFrom, centerYFrom){
var radius = 3;
ctx.beginPath();
ctx.arc(centerXFrom, centerYFrom, radius, 0, 2 * Math.PI, false);
ctx.fillStyle = 'green';
ctx.fill();
ctx.lineWidth = 1;
ctx.strokeStyle = '#003300';
ctx.stroke();
ctx.beginPath();
}
function sumTab(tabTT){
for (var i = 0; i < tabTT.length; i++){
somme += tabTT[i];
}
return somme;
}
/***************************************************/
/************Get length for each leg***************/
/*************************************************/
function findProportion(tabTT){
var tailleMax = tabTT.length;
sumTab(tabTT);
for(var i = 0; i < tabTT.length; i++){
var percentLeg = (tabTT[i]/somme)*100;
var tailleLeg = ((perimetre - 20)*percentLeg)/100 ;
recapProp.push(tailleLeg);
}
/* For each leg I draw the circle and the arrow, due to the length calculated previously. If the length > the width of the canva, the arrow has to be curved */
for(var i = 0; i <= recapProp.length; ++i){
if(prevValue > width && top == 1){
drawCircle(prevValue +5, 5);
drawArrowBot(prevValue + 7, 5, prevValue+recapProp[i],5);
right = 1;
top = 0;
}
else if(prevValue > height && right == 1){
drawCircle(prevValue +5, 5);
drawArrowLeft(prevValue + 7, 5, prevValue+recapProp[i],5);
bot = 1;
right = 0;
}
else if (prevValue > width && bot == 1){
drawCircle(prevValue +5, 5);
drawArrowTop(prevValue + 7, 5, prevValue+recapProp[i],5);
bot = 0;
left = 0;
}
else {
drawCircle(prevValue +5, 5);
drawArrow(prevValue + 7, 5, prevValue+recapProp[i],5);
}
prevValue += recapProp[i];
}
}
var tabTT = [0,5,1,8,2];
findProportion(tabTT);
<canvas id="myCanvas" height="200" width="500" style="border:1px solid #000000;"></canvas>
我已经对我的所有代码进行了注释,以帮助您理解逻辑和我想要的内容。
那么,是否有可能以通用方式弯曲线条?
最佳答案
我可能会做这样的事情:
现在您可以将线条制作成您想要的几乎任何形状和形式。
提示:您当然可以通过第一次直接映射来跳过一个形状。
技巧 2:可以在标准化坐标中定义形状,这样可以更轻松地平移和缩放它们。
在这里我们定义了一个圆 Angular 正方形和圆形,然后将线条映射到其中一个上,我们可以在形状之间变形以找到我们喜欢的组合并使用它(注意:因为这个例子中的正方形从“右上角”开始 Angular 而不是圆圈为 0° 的地方也会有一个小的旋转,这可以作为练习单独处理)。
就此而言,圆 Angular 正方形可能是一只兔子(对于更“紧凑”的圆 Angular 正方形,您可以使用立方贝塞尔曲线而不是此处的二次方)。关键是可以独立于线条本身来定义形状。这可能有点矫枉过正,但它并不复杂,而且用途广泛,即。通用。
参见 this answer一种向线条添加箭头的方法。
var ctx = document.querySelector("canvas").getContext("2d"),
resolution = 2000,
raster = new Uint8Array(resolution), // line raster array
shape = new Float32Array(resolution * 2), // target shape array (x2 for x/y)
shape2 = new Float32Array(resolution * 2),// target shape array 2
lines = [100, 70, 180, 35], // lines, lengths only
tLen = 0, // total length of lines + gaps
gap = 20, // gap in pixels
gapNorm, // normalized gap value for mapping
p = 0, // position in lines array
radius = 100, // target circle radius
angleStep = Math.PI * 2 / resolution, // angle step to reach circle / res.
cx = 150, cy = 150, // circle center
interpolation = 0.5, // t for interpolation
i;
// get total length of lines + gaps so we can normalize
for(i = 0; i < lines.length; i++) tLen += lines[i];
tLen += (lines.length - 2) * gap;
gapNorm = gap / tLen * 0.5;
// convert line and gap ranges to "on" in the lines array
for(i = 0; i < lines.length; i++) {
var sx = p, // start position in lines array
ex = p + ((lines[i] / tLen) * resolution)|0; // end position in lines array (int)
// fill array
while(sx <= ex) raster[sx++] = 1;
// update arrqay pointer incl. gap
p = ex + ((gapNorm * resolution)|0);
}
// Create a circle target shape split into same amount of segments as lines array:
p = 0; // reset pointer for shape array
for(var angle = 0; angle < Math.PI*2; angle += angleStep) {
shape[p++] = cx + radius * Math.cos(angle);
shape[p++] = cy + radius * Math.sin(angle);
}
// create a rounded rectangle
p = i = 0;
var corners = [
{x1: 250, y1: 150, cx: 250, cy: 250, x2: 150, y2: 250}, // bottom-right
{x1: 150, y1: 250, cx: 50, cy: 250, x2: 50, y2: 150}, // bottom-left
{x1: 50, y1: 150, cx: 50, cy: 50, x2: 150, y2: 50}, // upper-left
{x1: 150, y1: 50, cx: 250, cy: 50, x2: 250, y2: 150} // upper-right
],
c, cres = resolution * 0.25;
while(c = corners[i++]) {
for(var t = 0; t < cres; t++) {
var pos = getQuadraticPoint(c.x1, c.y1, c.cx, c.cy, c.x2, c.y2, t / cres);
shape2[p++] = pos.x;
shape2[p++] = pos.y;
}
}
// now we can map the lines array onto our shape depending on the values
// interpolation. Make it a reusable function so we can regulate the "morph"
function map(raster, shape, shape2, t) {
ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);
ctx.beginPath();
for(var i = 0, x, y, x1, y1, x2, y2, prev = 0; i < resolution; i++) {
x1 = shape[i*2];
y1 = shape[i*2 + 1];
x2 = shape2[i*2];
y2 = shape2[i*2 + 1];
x = x1 + (x2 - x1) * t;
y = y1 + (y2 - y1) * t;
// do we have a change?
if (prev !== raster[i]) {
if (raster[i]) { // it's on, was off. create sub-path
ctx.moveTo(x, y);
}
else { // it's off, was on, render and reset path
ctx.stroke();
ctx.beginPath();
// create "arrow"
ctx.moveTo(x + 3, y);
ctx.arc(x, y, 3, 0, 6.28);
ctx.fill();
ctx.beginPath();
}
}
// add segment if on
else if (raster[i]) {
ctx.lineTo(x, y);
}
prev = raster[i];
}
}
ctx.fillStyle = "red";
map(raster, shape, shape2, interpolation);
document.querySelector("input").onchange = function() {
map(raster, shape, shape2, +this.value / 100);
};
function getQuadraticPoint(z0x, z0y, cx, cy, z1x, z1y, t) {
var t1 = (1 - t), // (1 - t)
t12 = t1 * t1, // (1 - t) ^ 2
t2 = t * t, // t ^ 2
t21tt = 2 * t1 * t; // 2(1-t)t
return {
x: t12 * z0x + t21tt * cx + t2 * z1x,
y: t12 * z0y + t21tt * cy + t2 * z1y
}
}
<script src="https://cdn.rawgit.com/epistemex/slider-feedback/master/sliderfeedback.min.js"></script>
<label>Interpolation: <input type="range" min=0 max=400 value=50></label><br>
<canvas width=400 height=400></canvas>
关于javascript - 当长度超过时,将直线变为曲线,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30596861/
将 KLV 字符串拆分为键、长度、值作为元素的列表/元组的更有效方法是什么? 为了添加一点背景,前 3 位数字作为键,接下来的 2 位表示值的长度。 我已经能够使用以下代码解决该问题。但我不认为我的代
首先,我试图从文件中提取视频持续时间,然后在无需实际上传文件的情况下显示它。 当用户选择视频时 - 信息将显示在其下方,包括文件名、文件大小、文件类型。不管我的技能多么糟糕 - 我无法显示持续时间。我
我是 Scala 编程新手,这是我的问题:如何计算每行的字符串数量?我的数据框由一列 Array[String] 类型组成。 friendsDF: org.apache.spark.sql.DataF
我有一个React Web应用程序(create-react-app),该应用程序使用react-hook-forms上传歌曲并使用axios将其发送到我的Node / express服务器。 我想确
如果给你一个网络掩码(例如 255.255.255.0),你如何在 Java 中获得它的长度/位(例如 8)? 最佳答案 如果您想找出整数低端有多少个零位,请尝试 Integer.numberOfTr
我需要使用 jQuery 获取 div 数量的长度。 我可以得到它,但在两个单击事件中声明变量,但这似乎是错误的,然后我还需要使用它来根据数字显示隐藏按钮。我觉得我不必将代码加倍。 在这里摆弄 htt
我对此感到非常绝望,到目前为止我在 www 上找不到任何东西。 情况如下: 我正在使用 Python。 我有 3 个数组:x 坐标、y 坐标和半径。 我想使用给定的 x 和 y 坐标创建散点图。 到目
我有一个表单,我通过 jQuery 的加载函数动态添加新的输入和选择元素。有时加载的元素故意为空,在这种情况下我想隐藏容器 div,这样它就不会破坏样式。 问题是,我似乎无法计算加载的元素,因此不知道
我决定通过替换来使我的代码更清晰 if (wrappedSet.length > 0) 类似 if (wrappedSet.exists()) 是否有任何 native jq 函数可以实现此目的?或者
简单的问题。如果我有一个如下表: CREATE TABLE `exampletable` ( `id` int(11) NOT NULL AUTO_INCREMENT, `textfield`
我正在使用经典 ASP/MySQL 将长用户输入插入到我的数据库中,该输入是从富文本编辑器生成的。该列设置为 LONG-TEXT。 作为参数化查询(准备语句)的新手,我不确定用于此特定查询的数据长度。
我正在获取 Stripe 交易费用的值(value)并通过禁用的文本字段显示它。 由于输入文本域,句子出现较大空隙 This is the amount $3.50____________that n
我有一个 div,其背景图像的大小设置为包含。但是,图像是视网膜计算机(Macbook Pro 等)的双分辨率图像,所以我希望能够以某种方式让页面知道即使我说的是背景大小:包含 200x200 图像,
我正在开发一个具有“已保存”和“已完成”模块的小部件。当我删除元素时,它会从 dom 中删除/淡化它,但是当我将其标记为完成时,它会将其克隆到已完成的选项卡。这工作很棒,但顶部括号内的数字不适合我。这
我有一个来自 json 提要的数组,我知道在 jArray 中有一个联盟,但我需要计算出该数组的计数,以防稍后将第二个添加到提要中。目前 log cat 没有注销“teamFeedStructure”
目标:给定一个混合类型的数组,确定每个级别的元素数量。如果同一层有两个子数组,则它们的每个元素都计入该层元素的总数。 方法: Array.prototype.elementsAtLevels = fu
我需要帮助为 Java 中的单链表制作 int size(); 方法。 这是我目前所拥有的,但它没有返回正确的列表大小。 public int size() { int size = 0;
我正在为学校作业创建一个文件服务器应用程序。我目前拥有的是一个简单的 Client 类,它通过 TCP 发送图像,还有一个 Server 类接收图像并将其写入文件。 这是我的客户端代码 import
我有这对功能 (,) length :: Foldable t => t a -> b -> (Int, b) 和, head :: [a] -> a 我想了解的类型 (,) length he
我正在GitHub Pages上使用Jekyll来构建博客,并希望获得传递给YAML前题中Liquid模板的page.title字符串的长度,该字符串在每个帖子的YAML主题中。我还没有找到一种简单的
我是一名优秀的程序员,十分优秀!