问题描述
我创建了一个圆圈,我可以在圆圈周围选择两个点。
I have created a circle in which I can choose two points along the circumference of of circle.
我想填充这两个点之间的部分。
I want to fill the portion between those two points.
如果您看到演示,我想填补两点之间的角度。
If you see the demo, I want to fill the angle between two points.
JS:
(function (Raphael) {
Raphael.colorwheel = function (x, y, size, initcolor, element) {
return new ColorWheel(x, y, size, initcolor, element);
};
var pi = Math.PI,
doc = document,
win = window,
ColorWheel = function (x, y, size, initcolor, element) {
size = size || 200;
var w3 = 3 * size / 200,
w1 = size / 200,
fi = 1.6180339887,
segments = 3,//pi * size / 50,
size20 = size / 20,
size2 = size / 2,
padding = 2 * size / 200,
t = this;
var H = 1, S = 1, B = 1, s = size - (size20 * 4);
var r = element ? Raphael(element, size, size) : Raphael(x, y, size, size),
xy = s / 6 + size20 * 2 + padding,
wh = s * 2 / 3 - padding * 2;
w1 < 1 && (w1 = 1);
w3 < 1 && (w3 = 1);
// ring drawing
var a = pi / 2 - pi * 2 / segments * 1.3,
R = size2 - padding,
R2 = size2 - padding - size20 * 2,
path = ["M", size2, padding, "A", R, R, 0, 0, 1, R * Math.cos(a) + R + padding, R - R * Math.sin(a) + padding, "L", R2 * Math.cos(a) + R + padding, R - R2 * Math.sin(a) + padding, "A", R2, R2, 0, 0, 0, size2, padding + size20 * 2, "z"].join();
for (var i = 0; i < segments; i++) {
r.path(path).attr({
stroke: "none",
fill: "#8fd117",
transform: "r" + [(360 / segments) * i, size2, size2]
});
}
r.path(["M", size2, padding, "A", R, R, 0, 1, 1, size2 - 1, padding, "l1,0", "M", size2, padding + size20 * 2, "A", R2, R2, 0, 1, 1, size2 - 1, padding + size20 * 2, "l1,0"]).attr({
"stroke-width": w3,
stroke: "#fff"
});
t.startCursor = r.set();
var h = size20 * 2 + 2;
t.startCursor.push(r.rect(size2 - h / fi / 2, padding - 1, h / fi, h, 3 * size / 200).attr({
stroke: "#00A0C6",
opacity: .5,
"stroke-width": w3
}));
t.startCursor.push(t.startCursor[0].clone().attr({
stroke: "#00A0C6",
opacity: 1,
"stroke-width": w1
}));
t.endCursor = r.set();
var h = size20 * 2 + 2;
t.endCursor.push(r.rect(size2 - h / fi / 2, padding - 1, h / fi, h, 3 * size / 200).attr({
stroke: "#F96E5B",
opacity: .5,
"stroke-width": w3
}));
t.endCursor.push(t.endCursor[0].clone().attr({
stroke: "#F96E5B",
opacity: 1,
"stroke-width": w1
}));
t.ring = r.path(["M", size2, padding, "A", R, R, 0, 1, 1, size2 - 1, padding, "l1,0M", size2, padding + size20 * 2, "A", R2, R2, 0, 1, 1, size2 - 1, padding + size20 * 2, "l1,0"]).attr({
fill: "#000",
opacity: 0,
stroke: "none"
});
t.H = t.S = t.B = 1;
t.raphael = r;
t.size2 = size2;
t.wh = wh;
t.x = x;
t.xy = xy;
t.y = y;
t.endCursor.attr({transform: "r" + [50, t.size2, t.size2]});
// events
t.ring.drag(function (dx, dy, x, y) {
t.docOnMove(dx, dy, x, y);
}, function (x, y) {
// Rotate on click
t.setH(x - t.x - t.size2, y - t.y - t.size2);
}, function () {
});
},
proto = ColorWheel.prototype;
proto.setH = function (x, y) {
var d = Raphael.angle(x, y, 0, 0);
this.H = (d + 90) / 360;
var a = 0;
if(d > 270) {
d = d - 270;
}
else {
d = d + 90;
}
var m = Math.abs(d - this.startCursor[0]._.deg);
var n = Math.abs(d - this.endCursor[0]._.deg);
if(m > 180) {
m = 360 - m ;
}
if(n > 180) {
n = 360 - n;
}
if( m <= n) {
this.startCursor.attr({transform: "r" + [d, this.size2, this.size2]});
}
else {
this.endCursor.attr({transform: "r" + [d, this.size2, this.size2]});
}
m = this.startCursor[0]._.deg ;
n = this.endCursor[0]._.deg;
if(m > 360) {
m = m - 360;
}
if( n > 360 ) {
n = n - 360;
}
var diff = m > n ? m - n : n - m;
this.onchange(m,n,diff);
};
proto.docOnMove = function (dx, dy, x, y) {
this.setH(x - this.x - this.size2, y - this.y - this.size2);
};
})(window.Raphael);
window.onload = function () {
var cp2 = Raphael.colorwheel(60, 20, 200, "#eee");
var X = document.getElementById('x');
var Y = document.getElementById('y');
var angle = document.getElementById('angle');
cp2.onchange = function (x, y, ang) {
X.innerHTML = Math.round(x * 100) / 100;
Y.innerHTML = Math.round(y * 100) / 100;
angle.innerHTML = Math.round(ang * 100) / 100;
}
};
HTML:
<div id="wrapper">X : <span id="x">0</span>
<br>Y: <span id="y">50</span>
<br>Angle: <span id="angle">50</span>
</div>
CSS:
body {
background: #e6e6e6;
}
#wrapper {
position: absolute;
top: 240px;
left: 100px;
}
更新:
在Chris的帮助下,
With Chris's help,
我取得了一些成功。
参见
错误:
1.如果你先开始绿色,红色突破,
2.如果你先开始红色并使角度大于180度,当绿色减少到180度以下时,它再次破裂。
更新2
BUGS:
1.如果你先开始红色并制作大于180度的角度,当绿色降低到180度以下时,它会再次破裂。
2.有时弧线方向相反。
I have got some success.
See
Bugs :
1. If you start green first, red breaks,
2. If you start red first and makes angle of greater than 180 degree and when green reduces that below 180 degree, it breaks again.
UPDATE 2
BUGS:
1. If you start red first and makes angle of greater than 180 degree and when green reduces that below 180 degree, it breaks again.
2. Sometimes arcs in opposite direction.
推荐答案
以下是可行的解决方案:
Here's working solution:
(function (Raphael) {
Raphael.colorwheel = function (x, y, size, initcolor, element) {
return new ColorWheel(x, y, size, initcolor, element);
};
var pi = Math.PI,
doc = document,
win = window,
ColorWheel = function (x, y, size, initcolor, element) {
size = size || 200;
var w3 = 3 * size / 200,
w1 = size / 200,
fi = 1.6180339887,
segments = 3,//pi * size / 50,
size20 = size / 20,
size2 = size / 2,
padding = 2 * size / 200,
t = this;
var H = 1, S = 1, B = 1, s = size - (size20 * 4);
var r = element ? Raphael(element, size, size) : Raphael(x, y, size, size),
xy = s / 6 + size20 * 2 + padding,
wh = s * 2 / 3 - padding * 2;
w1 < 1 && (w1 = 1);
w3 < 1 && (w3 = 1);
// ring drawing
var a = pi / 2 - pi * 2 / segments * 1.3,
R = size2 - padding,
R2 = size2 - padding - size20 * 2,
path = ["M", size2, padding, "A", R, R, 0, 0, 1, R * Math.cos(a) + R + padding, R - R * Math.sin(a) + padding, "L", R2 * Math.cos(a) + R + padding, R - R2 * Math.sin(a) + padding, "A", R2, R2, 0, 0, 0, size2, padding + size20 * 2, "z"].join();
for (var i = 0; i < segments; i++) {
r.path(path).attr({
stroke: "none",
fill: "#8fd117",
transform: "r" + [(360 / segments) * i, size2, size2]
});
}
r.path(["M", size2, padding, "A", R, R, 0, 1, 1, size2 - 1, padding, "l1,0", "M", size2, padding + size20 * 2, "A", R2, R2, 0, 1, 1, size2 - 1, padding + size20 * 2, "l1,0"]).attr({
"stroke-width": w3,
stroke: "#fff"
});
t.startCursor = r.set();
var h = size20 * 2 + 2;
t.startCursor.push(r.rect(size2 - h / fi / 2, padding - 1, h / fi, h, 3 * size / 200).attr({
stroke: "#00A0C6",
opacity: 1,
"stroke-width": w3
}));
t.startCursor.push(t.startCursor[0].clone().attr({
stroke: "#00A0C6",
fill : "#8fd117",
opacity: 1,
"stroke-width": w1
}));
t.endCursor = r.set();
var h = size20 * 2 + 2;
t.endCursor.push(r.rect(size2 - h / fi / 2, padding - 1, h / fi, h, 3 * size / 200).attr({
stroke: "#F96E5B",
opacity: 1,
"stroke-width": w3,
}));
t.endCursor.push(t.endCursor[0].clone().attr({
stroke: "#F96E5B",
fill : "#8fd117",
opacity: 1,
"stroke-width": w1
}));
t.ring = r.path(["M", size2, padding, "A", R, R, 0, 1, 1, size2 - 1, padding, "l1,0M", size2, padding + size20 * 2, "A", R2, R2, 0, 1, 1, size2 - 1, padding + size20 * 2, "l1,0"]).attr({
fill: "#000",
opacity: 0,
stroke: "none"
});
t.H = t.S = t.B = 1;
t.raphael = r;
t.size2 = size2;
t.wh = wh;
t.x = x;
t.xy = xy;
t.y = y;
t.endCursor.attr({transform: "r" + [50, t.size2, t.size2]});
t.x0 = t.startCursor[0].attr("x") + t.startCursor[0].attr("width") / 2;
t.y0 = t.startCursor[0].attr("y") + t.startCursor[0].attr("height") / 2;
t.initX0 = t.x0;
t.initY0 = t.y0;
t.R1 = (R2 + R) / 2;
t.x1 = t.x0 + t.R1 * Math.sin(50 * Math.PI / 180);
t.y1 = t.y0 + t.R1 - t.R1 * Math.cos(50 * Math.PI / 180);
t.initX1 = t.x1;
t.initY1 = t.y1;
var path = "M" + t.x0 + "," + t.y0 + "A" + t.R1 + "," + t.R1 + " 50 0,1 " + t.x1 + "," + t.y1;
t.arc = r.path(path)
.attr({
stroke: "#009900",
"stroke-width": 10
});
t.startCursor.drag(function (dx, dy, x, y) {
t.docOnMove(dx, dy, x, y,'startCursor');
}, function (x, y) {
t.setH(x - t.x - t.size2, y - t.y - t.size2,'startCursor');
}, function () {
});
t.endCursor.drag(function (dx, dy, x, y) {
t.docOnMove(dx, dy, x, y,'endCursor');
}, function (x, y) {
t.setH(x - t.x - t.size2, y - t.y - t.size2,'endCursor');
}, function () {
});
t.startCursor.toFront();
t.endCursor.toFront();
},
proto = ColorWheel.prototype;
proto.setH = function (x, y,cursor) {
var d = Raphael.angle(x, y, 0, 0);
if(d > 270) {
d = d - 270;
}
else {
d = d + 90;
}
if((cursor === 'startCursor' && d > this.endCursor[0]._.deg) || (cursor === 'endCursor' && d <= this.startCursor[0]._.deg)) {
return;
}
if(cursor === 'startCursor') {
this.startCursor.attr({transform: "r" + [d, this.size2, this.size2]});
}
else {
this.endCursor.attr({transform: "r" + [d, this.size2, this.size2]});
}
var m = this.startCursor[0]._.deg ;
var n = this.endCursor[0]._.deg;
var t = this;
var flag = 0;
if(m > 360) {
m = m - 360;
flag = 1;
}
if( n > 360 ) {
n = n - 360;
}
var diff = Math.abs(m - n);
if (diff > 180) {
flag = 1;
}
var path = "";
var sweep = 1;
if(cursor === 'endCursor') {
t.x1 = t.initX0 + t.R1 * Math.sin(n * Math.PI / 180);
t.y1 = t.initY0 + t.R1 - t.R1 * Math.cos(n * Math.PI / 180);
}
else {
t.x0 = t.initX0 + t.R1 * Math.sin(m * Math.PI / 180);
t.y0 = t.initY0 + t.R1 - t.R1 * Math.cos(m * Math.PI / 180);
}
console.log(m,t.x0,t.y0,t.x1,t.y1);
path = "M" + t.x0 + "," + t.y0 + "A" + t.R1 + "," + t.R1 + " " + diff + " " + flag + "," + sweep + " " + t.x1 + "," + t.y1;
t.arc = t.arc.attr("path", path );
this.onchange(m,n,diff);
};
proto.docOnMove = function (dx, dy, x, y,cursor) {
this.setH(x - this.x - this.size2, y - this.y - this.size2,cursor);
};
})(window.Raphael);
window.onload = function () {
var cp2 = Raphael.colorwheel(60, 20, 200, "#eee");
var X = document.getElementById('x');
var Y = document.getElementById('y');
var angle = document.getElementById('angle');
cp2.onchange = function (x, y, ang) {
X.innerHTML = Math.round(x * 100) / 100;
Y.innerHTML = Math.round(y * 100) / 100;
angle.innerHTML = Math.round(ang * 100) / 100;
}
};
这篇关于拉斐尔js。沿曲线填充颜色的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!