html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因


Posted in HTML / CSS onJanuary 09, 2013

接上一篇canvas画线条教程
上次我们讲到,canvas有时候会出现1像素的线条模糊不清且好像更宽的情况,如下图:
html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因 
这样的线条显然不是我们想要的。
这篇文章的目的就是弄清楚里面的原理,以及解决它。
大家都知道屏幕上最小的显示尺寸就是1像素,虽然小于1像素的东西可能显示不出来,但计算机可不管,他会试着画一下。
其实像素终究来说也是一个单位,假如我们把画布放大到足够大,足以看清楚每个像素,会是什么情况呢?大概是这个样子:

html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因


每个像素都有起止范围,如图所示,他们的范围从左起,跨过1像素,到右止。
如果我们画1像素线条的时候,遵循像素的起止范围,那么我们肯定能得到一个很标准的细线。如下:

html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因


但遗憾的是canvas的线条画法不一样,上一篇文章我们已经说了,canvas的每条线都有一条无限细的“中线”,线条的宽度是从中线向两侧延伸的。如果我们还是从第2个像素点画一条线,那么线条的中线就会靠齐到第2个像素的起点,然后我们开始画了,问题也就来了:Canvas 的线条以中线向两侧延伸,而不是向某一边延伸(比如这里,如果只是往右侧延伸,那么我们的问题就不再是问题了),延伸过后我们的线条实际上是这样的:

html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因


此时又有个问题:计算机不允许出现小于1px的图形,所以他做了一个折中的事:把这两个像素都绘制了。
所以,如此一来,本来1px的线条,就成了看起来2px宽的线条。
失败的原因找到了:Canvas中的line把中线与像素的起点对齐了,而不是像素的中间点。
那么我们怎么解决这个蛋疼的问题?也许有人已经想到了:既然是因为两个的起点不一样,那我们就把他们的起点变得一样吧!
我们让线条的中线和像素的中间点对齐就行了!
像素的中间点很好找,比如第2像素的中间点,依据图上的解释就是1.5像素的位置,那么x像素的中间点就是(x-0.5)px。
html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因
 
当然,在不很严谨的场合,你使用x+0.5也是可以的。
现在我们在canvas上试试我们的研究结果。
复制代码
代码如下:

ctx.moveTo(100.5,100.5);
ctx.lineTo(200.5,100.5);
ctx.lineTo(200.5,200.5);
ctx.lineTo(100.5,200.5);
ctx.lineTo(100.5,100.5);
ctx.closePath();
ctx.lineWidth = 1;
ctx.strokeStyle = 'rgba(255,0,0,0.5)';
ctx.stroke();

html5 Canvas画图教程(3)—canvas出现1像素线条模糊不清的原因


看起来对了吧?
不过貌似这样一来我们画线的时候就非常纠结,难道每次都去加这个让人郁闷的0.5?当然不是,因为我们大部分时间都是用变量保存值的,就不用给每个值加0.5 了
而且,对于lineWidth>1 的线,我们也不用管它:因为只有线条宽1px的时候,这个问题才最明显。
HTML / CSS 相关文章推荐
纯CSS3实现Material Design效果
Mar 09 HTML / CSS
多重CSS背景动画实现方法示例
Apr 04 HTML / CSS
五款漂亮的纯CSS3动画按钮的实例教程
Nov 21 HTML / CSS
css3 中的新特性加强记忆详解
Apr 16 HTML / CSS
使用CSS变量实现炫酷惊人的悬浮效果
Apr 26 HTML / CSS
HTML5打开本地app应用的方法
Mar 31 HTML / CSS
HTML5的结构和语义(5):交互
Oct 17 HTML / CSS
图片上传插件ImgUploadJS:用HTML5 File API 实现截图粘贴上传、拖拽上传
Jan 20 HTML / CSS
HTML5实现预览本地图片
Feb 17 HTML / CSS
HTML5移动端开发中的Viewport标签及相关CSS用法解析
Apr 15 HTML / CSS
Canvas实现保存图片到本地的示例代码
Jun 28 HTML / CSS
POST提交数据常见的四种方式
Jan 18 HTML / CSS
html5 Canvas画图教程(2)—画直线与设置线条的样式如颜色/端点/交汇点
Jan 09 #HTML / CSS
html5 Canvas画图教程(1)—画图的基本常识
Jan 09 #HTML / CSS
使用html5+css3来实现slider切换效果告别javascript+css
Jan 08 #HTML / CSS
几个解决兼容IE6\7\8不支持html5标签的几个方法
Jan 07 #HTML / CSS
html5 canvas-2.用canvas制作一个猜字母的小游戏
Jan 07 #HTML / CSS
html5 canvas-1.canvas介绍(hello canvas)
Jan 07 #HTML / CSS
html5指南-1.html5全局属性(html5 global attributes)深入理解
Jan 07 #HTML / CSS
You might like
PHP会话控制:Session与Cookie详解
2014/09/27 PHP
php找出指定范围内回文数且平方根也是回文数的方法
2015/03/23 PHP
深入理解php printf() 输出格式化的字符串
2016/05/23 PHP
PHP仿微信发红包领红包效果
2016/10/30 PHP
jQuery插件原来如此简单 jQuery插件的机制及实战
2012/02/07 Javascript
Javascript生成json的函数代码(可以用php的json_decode解码)
2012/06/11 Javascript
前端开发过程中浏览器版本的两种判定方法
2013/10/30 Javascript
Javascript中document.referrer隐藏来源的方法
2017/01/16 Javascript
jQuery插件echarts实现的去掉X轴、Y轴和网格线效果示例【附demo源码下载】
2017/03/04 Javascript
修改UA在PC中访问只能在微信中打开的链接方法
2017/11/27 Javascript
vue+webpack实现异步加载三种用法示例详解
2018/04/24 Javascript
原生JS实现旋转轮播图+文字内容切换效果【附源码】
2018/09/29 Javascript
AJAX在JQuery中的应用详解
2019/01/30 jQuery
学习LayUI时自研的表单参数校验框架案例分析
2019/07/29 Javascript
vue实现微信浏览器左上角返回按钮拦截功能
2020/01/18 Javascript
python多进程和多线程究竟谁更快(详解)
2017/05/29 Python
python中Matplotlib实现绘制3D图的示例代码
2017/09/04 Python
通过实例解析Python调用json模块
2019/12/11 Python
Python判断变量是否是None写法代码实例
2020/10/09 Python
详解Anaconda安装tensorflow报错问题解决方法
2020/11/01 Python
Python解析微信dat文件的方法
2020/11/30 Python
英国花园家具中心:Garden Furniture Centre
2017/08/24 全球购物
海滩咖啡馆:Beach Cafe
2018/02/02 全球购物
美国球鞋寄卖网站:Stadium Goods
2018/05/09 全球购物
详解如何解决使用JSON.stringify时遇到的循环引用问题
2021/03/23 Javascript
客房主管岗位职责
2013/12/09 职场文书
回门宴父母答谢词
2014/01/26 职场文书
英文自荐信常用句子
2014/03/26 职场文书
集团财务总监岗位职责
2015/04/03 职场文书
2015年世界环境日活动方案
2015/05/05 职场文书
2015大学党建带团建工作总结
2015/07/23 职场文书
李白经典诗之一:全文无一“月”字,却句句有月
2019/07/12 职场文书
2019年年中职场激励人心语录30条
2019/08/07 职场文书
Pytest allure 命令行参数的使用
2021/04/18 Python
Python可视化动图组件ipyvizzu绘制惊艳的可视化动图
2022/04/21 Python
Python+DeOldify实现老照片上色功能
2022/06/21 Python