image
代碼
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>矩形</title>
<link rel="stylesheet" href="">
<style>
.juxing{
/* 加上css會很奇怪-瓮下。-*/
/* transition:all 0.1s ease-in; */
}
</style>
</head>
<body>
<button type="button" onclick="start()">點擊</button>
<script>
const len = 50;
let array = [];
let time = null;
function start() {
clearInterval(time);
time = setInterval(() => {
huanwei();
}, 100);
}
function huanwei() {
array.unshift(array.pop());
var els = document.querySelectorAll('.juxing');
for (let i = 0; i < len; i++) {
let el = document.getElementById('ip' + (i + 1));
if (array[i] && array[i].point) {
let point = array[i].point;
el.style.left = point.x + 'px';
el.style.top = point.y + 'px';
}
}
}
function createNode(name, p) {
// 填充div
let x = p.x;
let y = p.y;
var createDiv = document.createElement("div");
// 動態(tài)
createDiv.id = name;
createDiv.style.left = p.x + 'px';
createDiv.style.top = p.y + 'px';
createDiv.innerHTML = name;
// 固定
if (name !== 'yuan') {
// 存儲非圓心的所有坐標點
createDiv.className = "juxing"
let obj = {
id: name,
point: { x: p.x, y: p.y }
}
array.push(obj);
}
createDiv.style.position = "absolute";
createDiv.style.width = "30px";
createDiv.style.height = "30px";
createDiv.style.borderRadius = "30px";
// border-radius: 30px;
createDiv.style.background = "pink";
createDiv.style.border = "1pxsolidred";
document.body.appendChild(createDiv);
}
initNode({
len: len,
rectW: 400,
rectH: 300,
p: {
x: 400,
y: 200
}
});
function initNode(params) {
//初始化圓角矩形
// 數(shù)量
let len = params.len || 100;
// 設(shè)置圓角矩形內(nèi)矩形寬高 ,
let rectW = params.rectW || 700;
let rectH = params.rectH || 900;
// 中心
let cx = params.p.x || 0;
let cy = params.p.y || 0;
/*
* 思路:圓角矩形可以看作一個矩形和左右兩個半圓組成,半徑為矩形的一半庄拇;
* 圓周長+矩形兩邊的長度 / 總數(shù)量 計算出各邊應該存放的小車數(shù)量侮腹,以此數(shù)量為基準判斷該繪制哪一塊盗扇;
*
* o = (180 / arcLenSplit) * Math.PI / 180
* l=nπr/180 弧長公式
* l = n(圓心角)× π(圓周率)× r(半徑)/180=α(圓心角弧度數(shù))× r(半徑)
* 這里的象限為4321腌逢,為(1,1),(1,-1),(-1,-1),(-1,1)
*
*/
// 圓半徑
let radius = rectH / 2;
// 兩邊弧長相等為
let arcLength = Math.PI * radius;
// 圓弧*2 + 矩形頂邊底邊長度除以總數(shù)量
let split = ((arcLength * 2) + (rectW * 2)) / len;
// 矩形邊長可以存放數(shù)量莲兢,均分
let sideLenCount = Math.round(rectW / split);
//弧長可以存放小車數(shù)量
let arcLenSplit = Math.round(arcLength / split);
//
let lineSplit = rectW / sideLenCount
//每一個BOX對應的角度;
// var avd = 180 / arcLenSplit;
//每一個BOX對應的弧度;
// let o = avd * Math.PI / 180;
// 再次嘗試聚唐,改掉以角度劃分為以數(shù)量來劃分庆锦,
var count = 0;
var count2 = 0;
// 畫圓心,主要繪制的時候觀察使用捅位,后期刪除
createNode('yuan', { x: cx, y: cy });
// 左下角
let p1 = { x: -rectW / 2, y: rectH / 2, i: 0 };
let p2 = { x: rectW / 2, y: -rectH / 2, i: 0 }
//思路:計算矩形周長,處以數(shù)量值;先從左下角開始艇搀,每次疊加x尿扯,如果超過矩形下方長度,則切換至圓形弧度繪制焰雕,還是只能以是否在矩形上來判斷該繪制矩形橫軸或者圓形
for (var j = 1; j <= len; j++) {
if (j <= sideLenCount) {
//繪制矩形底邊 外面為計算總共拆分衷笋,里面重新計算分到的 邊長/數(shù)量
let x = p1.x + getSplit(lineSplit, p1.i)
let y = p1.y;
p1.i++;
createNode('ip' + j, { x: x + cx, y: y + cy });
} else if (j > sideLenCount && j <= (sideLenCount + arcLenSplit)) {
// 繪制右側(cè)圓弧
let ang = 180 / arcLenSplit;
let hd = getSplit(ang, count) * Math.PI / 180;
count++;
let yuanx = radius * Math.sin(hd) + cx + (rectW / 2);
let yuany = radius * Math.cos(hd) + cy;
createNode('ip' + j, { x: yuanx, y: yuany });
} else if (j > (sideLenCount + arcLenSplit) && j <= (sideLenCount + sideLenCount + arcLenSplit)) {
// 矩形頂部
let x = p2.x - getSplit(lineSplit, p2.i)
y = p2.y;
p2.i++;
createNode('ip' + j, { x: x + cx, y: y + cy });
} else {
//剩余
let remaining = len - (sideLenCount * 2) - arcLenSplit;
let ang = getSplit(180 / remaining, count2) * Math.PI / 180;
// 貌似是加上180度弧度的意思?
let hd = ang + (Math.PI / 180 * 180);
count2++;
let yuanx = radius * Math.sin(hd) + cx - (rectW / 2);
let yuany = radius * Math.cos(hd) + cy;
createNode('ip' + j, { x: yuanx, y: yuany });
}
}
function getSplit(split, count) {
// 2,6,10,14方式均分排列
return (split / 2) + (count * split)
}
}
</script>
</body>
</html>