【前端学习svg实例】绘制直角坐标+切线圆

【前端学习svg实例】绘制直角坐标+切线圆


所有想法,代码,方法参考网络
参考链接: HTML5 SVG 刻度线/圆形拼盘.
实现的非常简陋。

效果图:

请添加图片描述
请添加图片描述

知识补充:

  • document.querySelector("#demo");获取文档中 id=“demo” 的元素

  • parseInt()函数可解析一个字符串,并返回一个整数。

  • window.getComputedStyle()方法返回一个对象,该对象在应用活动样式表并解析这些值可能包含的任何基本计算后,报告元素的所有CSS属性的值。
    Element.setAttribute方法用于为当前元素节点新增属性。如果同名属性已存在,则相当于编辑已存在的属性。
    document.querySelectorAll方法与querySelector用法类似,区别是返回一个NodeList对象,包含所有匹配给定选择器的节点。

  • var element = document.createElementNS(namespaceURI, qualifiedName[,
    options]); 一个字符串,指定命名空间URI与元素关联。namespaceURI创建的元素的属性使用namespaceURI的值进行初始化 。
    qualifiedName指定要创建的元素类型的字符串,nodeName为所创建元素的属性被初始化为qualifiedName 的值。

  • appendChild() 方法可向节点的子节点列表的末尾添加新的子节点。

  • innerHTML 属性设置或返回表格行的开始和结束标签之间的 HTML。

1.html

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8" />
		<title></title>
		<link type="text/css" rel="stylesheet" href="style.css" />
		<style type="text/css">
			.box {
				position: fixed;
				width: 50px;
				height: 250px;
				right: 430px;
			}

			.form-group {
				margin-bottom: 15px
			}

			.form-control {
				display: block;
				width: 100%;
				height: 34px;
				padding: 6px 12px;
				font-size: 14px;
				line-height: 1.42857143;
				color: #555;
				background-color: #fff;
				background-image: none;
				border: 1px solid #ccc;
				border-radius: 4px;
				-webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
				box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
				-webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
				-o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
				-webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
				transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
				transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
				transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s, -webkit-box-shadow ease-in-out .15s
			}
		</style>
	</head>
	<body>
		<!--数据部分-->
		<div class="box">
			<div class="form-group">
				<label for="">k1</label>
				<input type="text" class="form-control" name="k1" style="color:black;">
			</div>
			<div class="form-group">
				<label for="">b1</label>
				<input type="text" class="form-control" name="b1" style="color:black;">
			</div>
			<div class="form-group">
				<label for="">k2</label>
				<input type="text" class="form-control" name="k2" style="color:black;">
			</div>
			<div class="form-group">
				<label for="">b2</label>
				<input type="text" class="form-control" name="b2" style="color:black;">
			</div>
			<div class="form-group">
				<label for="">r</label>
				<input type="text" class="form-control" name="r" style="color:black;">
			</div>
			<button onclick="f()">提交</button><!--触发-->
		</div>
		
		<!--画图-->
		<pre>&lt;svg width="<span id="preW"></span>" height="<span id="preH"></span>" viewBox="<span id="preFromX"> </span> <span id="preFromY"> </span> <span id="preToX"></span> <span id="preToY"></span>" preserveAspectRatio="<span id="preAR">xMaxYMax</span>" &gt;&lt;/svg&gt;</pre>
		<svg width="800" height="800" transform="scale(1,-1)"></svg><!-- 要转一下才能对于现实直角坐标的方向-->

		<!--控制svg-->
		<form>
			<fieldset>
				<legend>preserveAspectRatio ="&lt;align&gt; [meet|slice|none] "</legend>

				<p id="msn">
					<input type="radio" name="msn" value="none" checked> none
					<input type="radio" name="msn" value="meet"> meet
					<input type="radio" name="msn" value="slice"> slice
				</p>
				<p id="xctrl">
					<input type="radio" name="xctrl" value="xMax" checked> <em>xMax</em>
					<input type="radio" name="xctrl" value="xMid"> <em>xMid</em>
					<input type="radio" name="xctrl" value="xMin"> <em>xMin</em>
				</p>
				<p id="yctrl">
					<input type="radio" name="yctrl" value="YMax" checked> <em>YMax</em>
					<input type="radio" name="yctrl" value="YMid"> <em>YMid</em>
					<input type="radio" name="yctrl" value="YMin"> <em>YMin</em>
				</p>

			</fieldset>

			<fieldset>
				<legend>viewBox="fromX fromY toX toY"</legend>
				<p>
					<label>fromX: </label>
					<input type="range" id="fromX"> <span id="spanFromX"></span>
				</p>
				<p>
					<label>fromY: </label>
					<input type="range" id="fromY"> <span id="spanFromY"></span>
				</p>

				<p>
					<label>toX: </label>
					<input type="range" min="100" max="1000" value="600" id="toX"> <span id="spanToX"></span>
				</p>
				<p>
					<label>toY: </label>
					<input type="range" min="100" max="1000" value="350" id="toY"> <span id="spanToY"></span>
				</p>
			</fieldset>
		</form>
		<script type="text/javascript" src="1.js"></script>
	</body>
</html>

1.js

var svgCanvas = document.querySelector("svg");
var svgW = parseInt(window.getComputedStyle(svgCanvas, null).getPropertyValue("width")); //console.log(svgW)
var svgH = parseInt(window.getComputedStyle(svgCanvas, null).getPropertyValue("height")); //console.log(svgH)
document.querySelector("form").style.width = svgW + "px";
document.querySelector("#toX").value = svgW;
document.querySelector("#toY").value = svgH;
document.querySelector("#preW").innerHTML = svgW;
document.querySelector("#preH").innerHTML = svgH;

var preToX = document.querySelector("#preToX");
var preToY = document.querySelector("#preToY");
var preFromX = document.querySelector("#preFromX");
var preFromY = document.querySelector("#preFromY");
var preAR = document.querySelector("#preAR");

var spanFromX = document.querySelector("#spanFromX");
var spanFromY = document.querySelector("#spanFromY");
var spanToX = document.querySelector("#spanToX");
var spanToY = document.querySelector("#spanToY");

var inputFromX = document.querySelector("#fromX");
var inputFromY = document.querySelector("#fromY");
inputFromX.setAttribute("min", -svgW);
inputFromX.setAttribute("max", svgW);
inputFromX.setAttribute("value", -300);
inputFromY.setAttribute("min", -svgH);
inputFromY.setAttribute("max", svgH);
inputFromY.setAttribute("value", -140);

var inputToX = document.querySelector("#toX");
var inputToY = document.querySelector("#toY");

var radioXctrl = document.querySelectorAll("input[name='xctrl']");
var radioYctrl = document.querySelectorAll("input[name='yctrl']");


// svg动态画图
function f() {
	try {
		// 画一次清空一次
		clearRect();
		// 获得数据
		let k1 = document.getElementsByName('k1')[0];
		let b1 = document.getElementsByName('b1')[0];
		let k2 = document.getElementsByName('k2')[0];
		let b2 = document.getElementsByName('b2')[0];
		let r = document.getElementsByName('r')[0];

		// 计算圆心位置
		var p0y = 100 * Number(k1.value) + Number(b1.value);
		var p1y = Number(b1.value) - 100 * Number(k1.value);
		var p2y = 100 * Number(k2.value) + Number(b2.value);
		var p3y = Number(b2.value) - 100 * Number(k2.value);

		var d1 = Math.pow(Math.pow(Number(r.value), 2) + Math.pow(Number(r.value) * Number(k1.value), 2), 0.5);
		var d2 = Math.pow(Math.pow(Number(r.value), 2) + Math.pow(Number(r.value) * Number(k2.value), 2), 0.5);

		var dx = (Number(b1.value) + d1 - Number(b2.value) - d2) / (Number(k2.value) - Number(k1.value));
		var dy = Number(k1.value) * dx + Number(b1.value) + d1;

		var dx1 = (Number(b1.value) + d1 - Number(b2.value) + d2) / (Number(k2.value) - Number(k1.value));
		var dy1 = Number(k1.value) * dx1 + Number(b1.value) + d1;

		var dx2 = (Number(b1.value) - d1 - Number(b2.value) - d2) / (Number(k2.value) - Number(k1.value));
		var dy2 = Number(k1.value) * dx2 + Number(b1.value) - d1;

		var dx3 = (Number(b1.value) - d1 - Number(b2.value) + d2) / (Number(k2.value) - Number(k1.value));
		var dy3 = Number(k1.value) * dx3 + Number(b1.value) - d1;

		// svg画图
		var newLine = document.createElementNS("http:\/\/www.w3.org/2000/svg", "line");
		newLine.setAttributeNS(null, "x1", 100);
		newLine.setAttributeNS(null, "y1", p0y);
		newLine.setAttributeNS(null, "x2", -100);
		newLine.setAttributeNS(null, "y2", p1y);
		newLine.setAttributeNS(null, "stroke", "rgb(0, 0, 255)");
		newLine.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newLine);
		
		var newLine = document.createElementNS("http:\/\/www.w3.org/2000/svg", "line");
		newLine.setAttributeNS(null, "x1", 100);
		newLine.setAttributeNS(null, "y1", p2y);
		newLine.setAttributeNS(null, "x2", -100);
		newLine.setAttributeNS(null, "y2", p3y);
		newLine.setAttributeNS(null, "stroke", "rgb(0, 0, 255)");
		newLine.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newLine);

		var newLine = document.createElementNS("http:\/\/www.w3.org/2000/svg", "line");
		newLine.setAttributeNS(null, "x1", 300);
		newLine.setAttributeNS(null, "y1", 0);
		newLine.setAttributeNS(null, "x2", -300);
		newLine.setAttributeNS(null, "y2", 0);
		newLine.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newLine.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newLine);

		var newLine = document.createElementNS("http:\/\/www.w3.org/2000/svg", "line");
		newLine.setAttributeNS(null, "x1", 0);
		newLine.setAttributeNS(null, "y1", 300);
		newLine.setAttributeNS(null, "x2", 0);
		newLine.setAttributeNS(null, "y2", -300);
		newLine.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newLine.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newLine);

		var newcircle = document.createElementNS("http:\/\/www.w3.org/2000/svg", "circle");
		newcircle.setAttributeNS(null, "cx", dx);
		newcircle.setAttributeNS(null, "cy", dy);
		newcircle.setAttributeNS(null, "r", Number(r.value));
		newcircle.setAttributeNS(null, "fill", "red");
		newcircle.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newcircle.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newcircle);
		
		var newcircle = document.createElementNS("http:\/\/www.w3.org/2000/svg", "circle");
		newcircle.setAttributeNS(null, "cx", dx1);
		newcircle.setAttributeNS(null, "cy", dy1);
		newcircle.setAttributeNS(null, "r", Number(r.value));
		newcircle.setAttributeNS(null, "fill", "yellow");
		newcircle.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newcircle.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newcircle);
		
		var newcircle = document.createElementNS("http:\/\/www.w3.org/2000/svg", "circle");
		newcircle.setAttributeNS(null, "cx", dx2);
		newcircle.setAttributeNS(null, "cy", dy2);
		newcircle.setAttributeNS(null, "r", Number(r.value));
		newcircle.setAttributeNS(null, "fill", "blue");
		newcircle.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newcircle.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newcircle);
		
		var newcircle = document.createElementNS("http:\/\/www.w3.org/2000/svg", "circle");
		newcircle.setAttributeNS(null, "cx", dx3);
		newcircle.setAttributeNS(null, "cy", dy3);
		newcircle.setAttributeNS(null, "r", Number(r.value));
		newcircle.setAttributeNS(null, "fill", "green");
		newcircle.setAttributeNS(null, "stroke", "rgb(0, 0, 3)");
		newcircle.setAttributeNS(null, "stroke-width", "1");
		svgCanvas.appendChild(newcircle);

	} catch (e) {
		alert(e);
	}
}

function clearRect() {
	while (svgCanvas.firstChild) {
		svgCanvas.removeChild(svgCanvas.firstChild);
	}
}
// svg控制
function drawMarkers(e) {
	console.log(inputFromX);

	apX = document.querySelector('input[name="xctrl"]:checked').value;
	apY = document.querySelector('input[name="yctrl"]:checked').value;
	msn = document.querySelector('input[name="msn"]:checked').value;

	// viewBox
	if (e.type == "load") {
		fromX = document.querySelector("#fromX").getAttribute("value");
		fromY = document.querySelector("#fromY").getAttribute("value");
	} else {
		fromX = document.querySelector("#fromX").value;
		fromY = document.querySelector("#fromY").value;
	}
	toX = document.querySelector("#toX").value;
	toY = document.querySelector("#toY").value;

	// preserveAspectRatio
	if (msn == "none") {
		alignParam = "none";

		for (var i = 0; i < radioXctrl.length; i++) {
			radioXctrl[i].disabled = true;
		}
		for (var j = 0; j < radioYctrl.length; j++) {
			radioYctrl[j].disabled = true;
		}
	} else {
		alignParam = apX + apY + " " + msn;
		for (var i = 0; i < radioXctrl.length; i++) {
			radioXctrl[i].disabled = false;
		}
		for (var j = 0; j < radioYctrl.length; j++) {
			radioYctrl[j].disabled = false;
		}

	}

	// <pre>
	preFromX.innerHTML = fromX;
	spanFromX.innerHTML = fromX;
	preFromY.innerHTML = fromY;
	spanFromY.innerHTML = fromY;
	preToX.innerHTML = toX;
	spanToX.innerHTML = toX;
	preToY.innerHTML = toY;
	spanToY.innerHTML = toY;
	preAR.innerHTML = alignParam;

	svgCanvas.setAttributeNS(null, "viewBox", fromX + " " + fromY + " " + toX + " " + toY);
	svgCanvas.setAttributeNS(null, "preserveAspectRatio", alignParam);

}
// 监听动作
window.addEventListener("load", drawMarkers, false);
xctrl.addEventListener("change", drawMarkers, false);
yctrl.addEventListener("change", drawMarkers, false);
msn.addEventListener("change", drawMarkers, false);
inputFromX.addEventListener("input", drawMarkers, false);
inputFromY.addEventListener("input", drawMarkers, false);
inputToX.addEventListener("input", drawMarkers, false);
inputToY.addEventListener("input", drawMarkers, false);

style.css

* {
    font-family: "Courier New", Courier, monospace;
    font-size: 14px;
    padding: 0;
    margin: 0;
}
body {
    background-color: GhostWhite;
}
p,
legend {
    margin: 1em;
}
em {
    font-style: normal;
}
svg {
    border: 1px solid #d4d4d4;
    display: block;
    margin: 5em auto;
    background-color: white;
}
pre {
    background: black;
    color: white;
    padding: 1em;
    margin: 0.5em;
    text-align: center;
}
form {
    margin: 1em auto;
}
fieldset {
    margin: 2em 0;
    border: 1px solid #d4d4d4;
    background-color: white;
}
legend {
    padding: 0 1em;
    text-align: center;
}
label {
    display: inline-block;
    width: 10%;
}
[type='range'] {
    width: 74%;
}
[type='radio']:disabled {
    opacity: 0.2;
}
[type='radio']:disabled + em {
    color: #d9d9d9;
}
form span {
    display: inline-block;
    width: 10%;
    padding-left: 1em;
}

注意事项

链接: jquery 的 append 不适用于 svg 元素.
js文件不能有错,一点都不行。
理解参考网站:
链接: 图解SVG的核心概念
链接: SVG画布,坐标系统,视窗
拓展:
链接: 模板参考1
链接: 模板参考2

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值