如何使用canvas绘制椭圆,扩展非chrome浏览器中的ellipse方法
这篇博文主要针对浏览器中绘制椭圆的方法扩展。在网上搜索了很多,发现他们绘制椭圆的方式都有缺陷。其中有压缩法,计算法,贝塞尔曲线法等多种方式。但是都不能很好的绘制出椭圆。所有我就对这个绘制椭圆的方式进行了研究,发现压缩法是可以完美实现椭圆绘制的。废话不多说,直接上代码了。
if (!CanvasRenderingContext2D.prototype.ellipse) {
CanvasRenderingContext2D.prototype.ellipse = function(x, y, radiusX, radiusY, rotation, startAngle, endAngle,
anticlockwise) {
var r = radiusX > radiusY ? radiusX : radiusY; //用打的数为半径
var scaleX = radiusX / r; //计算缩放的x轴比例
var scaleY = radiusY / r; //计算缩放的y轴比例
this.save(); //保存副本
this.translate(x, y); //移动到圆心位置
this.rotate(rotation); //进行旋转
this.scale(scaleX, scaleY); //进行缩放
this.arc(0, 0, r, startAngle, endAngle, anticlockwise); //绘制圆形
this.restore(); //还原副本
}
}
这里给解释一下别的博文里面中的压缩法为啥不正确.下面我抄袭别人一段代码,来解析一下为啥错误.
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>椭圆</title>
</head>
<body>
<canvas id="canvas" style="border:1px solid #aaa;display:block;margin:50px auto;">
当前浏览器不支持Canvas,请更换浏览器后再试
</canvas>
<script>
var canvas = document.getElementById("canvas");
canvas.width = 600;
canvas.height = 600;
var context = canvas.getContext("2d");
context.lineWidth = 10;
context.strokeStyle="black";
EvenCompEllipse(context, 130, 200, 100, 20); //椭圆
function EvenCompEllipse(context, x, y, a, b){
context.save();
//选择a、b中的较大者作为arc方法的半径参数
var r = (a > b) ? a : b;
var ratioX = a / r; //横轴缩放比率
var ratioY = b / r; //纵轴缩放比率
context.scale(ratioX, ratioY); //进行缩放(均匀压缩)
context.beginPath();
//从椭圆的左端点开始逆时针绘制
context.moveTo((x + a) / ratioX, y / ratioY);
context.arc(x / ratioX, y / ratioY, r, 0, 2 * Math.PI);
context.closePath();
context.stroke();
context.restore();
};
</script>
</body>
</html>
他绘制的效果如下

为什么会出现这种情况呢.因为他在绘制的时候先绘制了,然后才还原.这样的话是压缩的一个路径,在绘制的时候就会连线条也进行压缩.而我的那段代码中并没有直接进行绘制.而是进行了还原操作.下面我给一段示例代码.大家可以直接进行试验.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>canvas绘制椭圆</title>
</head>
<body>
<canvas id="canvas" width='500' height='500'></canvas>
<script>
if (!CanvasRenderingContext2D.prototype.ellipse) {
CanvasRenderingContext2D.prototype.ellipse = function(x, y, radiusX, radiusY, rotation, startAngle, endAngle,
anticlockwise) {
var r = radiusX > radiusY ? radiusX : radiusY; //用打的数为半径
var scaleX = radiusX / r; //计算缩放的x轴比例
var scaleY = radiusY / r; //计算缩放的y轴比例
this.save(); //保存副本
this.translate(x, y); //移动到圆心位置
this.rotate(rotation); //进行旋转
this.scale(scaleX, scaleY); //进行缩放
this.arc(0, 0, r, startAngle, endAngle, anticlockwise); //绘制圆形
this.restore(); //还原副本
}
}
var ctx = document.getElementById("canvas").getContext("2d");
ctx.beginPath();
ctx.ellipse(300, 300, 150, 100, 30 * Math.PI / 180, 0, Math.PI * 2);
ctx.lineWidth = 10; //设定线宽为10
ctx.stroke();
ctx.closePath();
</script>
</body>
</html>
实际效果如下:

由此可见,其实压缩法是完全可以实现椭圆绘制的.只是大部分博文里面使用的都不太对而已.
如果觉得我这种方式不是你想要的的,也可以参考:https://www.cnblogs.com/fangsmile/p/9923532.html
如果 你觉得我的方式对的话,希望你能够进行转发.让更多的人知道这种绘制椭圆的方法.谢谢.
原文地址:https://www.cnblogs.com/flybeijing/p/canvas_ellipse.html
如何使用canvas绘制椭圆,扩展非chrome浏览器中的ellipse方法的更多相关文章
- 将Chrome浏览器中的扩展程序导出为crx插件文件
将Chrome浏览器中安装的插件程序导出为crx插件文件 以360急速浏览器为例进行导出crx插件程序 1.在Chrom商店中找到需要的插件,安装到浏览器的扩展程序里面()IDM Integratio ...
- Google Chrome浏览器中如何使用命令
Google Chrome浏览器中如何使用命令 | 浏览:2974 | 更新:2014-02-23 23:12 | 标签:chrome 1 2 3 分步阅读 Google Chrome浏览器有很多的特 ...
- 使用Chrome浏览器设置XX-net的方法
以下介绍使用Chrome浏览器设置XX-net的方法 1.下载并安装谷歌浏览器. 2.打开https://github.com/XX-net/XX-Net/blob/master/code/d ...
- 在Chrome浏览器中保存的密码有多安全?
本文由 伯乐在线 - 黄利民 翻译.未经许可,禁止转载!英文出处:howtogeek.欢迎加入翻译组. [2013-08-09 更新]:最近又开始讨论“Chrome浏览器明文保存密码这个话题了,国外一 ...
- Jmeter在chrome浏览器中录制脚本
利用blazemeter插件可以录制chrome浏览器中的操作,并生成jmx文件,导入到jmeter中使用 1. 下载blazemeter 地址:https://pan.baidu.com/s/1V ...
- 【js】IE、FF、Chrome浏览器中的JS差异介绍
如何判断浏览器类型 转:http://www.cnblogs.com/carekee/articles/1854674.html 1.通过浏览器特有的对象 如ie 的ActiveXObject ff ...
- 去掉chrome浏览器中input获得焦点时的带颜色边框呢
可以设置表单控件的outline属性为none值, 来去掉Chrome浏览器中输入框以及其它表单控件获得焦点时的带颜色边框. css代码如下: input{outline:none}
- [转]chrome浏览器中 F12 功能的简单介绍
本文转自:https://www.cnblogs.com/zhuzhubaoya/p/9758648.html chrome浏览器中 F12 功能的简单介绍 由于F12是前端开发人员的利器,所以我自己 ...
- 查看 chrome 浏览器中的 Headers
查看 chrome 浏览器中的 Headers, Response 信息:
随机推荐
- [NOIP2017(TG/PJ)] 真题选做
[NOIPTG2017] 小凯的疑惑 题意 小凯有两种面值的金币,每种金币有无数个,求在无法准确支付的物品中,最贵的价值是多少金币. 分析 设两种金币面值分别为 $a$ 和 $b \; (a<b ...
- python之路之生成器和的迭代器
生成器的基本原理 生成器实现xrange 迭代器
- 「题解」「CF853B」Jury Meeting
目录 题目 思路 代码 题目 传送门 思路 十分巧妙的差分前缀和好题. 题目板块完结之后,我看到有很多处理此题的方法,但总感觉差分前缀和比较巧妙. 首先,通过输入我们可以将每个人能在 \(0\) 号点 ...
- 概念理解_L2范数(欧几里得范数)
L1范数 L1范数是指向量中各个元素绝对值之和 L2范数 L2范数.欧几里得范数一些概念. 首先,明确一点,常用到的几个概念,含义相同. 欧几里得范数(Euclidean norm) ==欧式长度 = ...
- js中float失精
https://juejin.im/post/5aa1395c6fb9a028df223516 把小数转为整数,然后计算 https://www.html.cn/archives/7340
- 题解【UVA839】天平 Not so Mobile
Description Input Output Examples Input 1 0 2 0 4 0 3 0 1 1 1 1 1 2 4 4 2 1 6 3 2 Output YES Transla ...
- MyEcplise中编码格式的修改问题
1.如果是在Run Configurations中修改编码格式的话,只能是修改当前java文件的编码格式,把改文件中的代码复制到 另一新建 的java文件中会出现异常,所以就会出现相同的代码在两个不同 ...
- JS 数组克隆方法总结
ES5 方法总结 1.slice let arr = [2,4,434,43] let arr1= arr.slice() arr[0] = 'a' console.log(arr,arr1) // ...
- 字符串判空有空格报错:binary operator expected
使用-z或-n对一个变量判空时,需要注意若直接使用[ -n ${ARG} ]这种形式,若${ARG}中有空格将会报错, #!/bin/bash ARG="sd dd" if [ - ...
- IntelliJ IDEA 2017.3尚硅谷-----设置超过指定 import 个数,改为*
(可忽略)