找回密码
 FreeOZ用户注册
楼主: woodheadz

[论坛技术] javascript库求推荐

[复制链接]
 楼主| 发表于 19-1-2012 17:05:58 | 显示全部楼层
原帖由 coredump 于 19-1-2012 16:34 发表

我觉得这个之所以没想像中性能那么差, 是因为hitTest本来就是个慢速,低频率的事情, 现在的机器, 一个满屏的canvas, 重绘的FPS也很快, 如果跑到移动设备上, 硬件是差了, 可是屏幕也小了, 所以,都在可接受 ...

鼠标移动的时候每秒钟还是能有好多个MouseOver事件需要进行HitTest检查,当然对于touch设备比较好办,因为不会随时有那么多MouseOver事件会触发hitTest检查,即便效率低点也无所谓。
我做了个测试,在1900*1000分辨率的canvas上做10000个对象的检查,就会有点慢。我想如果在它做hitTest前再加上绘图对象的矩形边界检查来过滤一下,性能应该能大幅度提高到能够接受的地步了。

现在我的担心就是要在Kinetic现在的基础上加入复合的UI对象支持工作量会有点大,从事件机制到重绘、hitTest机制都需要修改。 我还是先看看其它的框架再决定。
回复  

使用道具 举报

发表于 20-1-2012 18:45:08 | 显示全部楼层

回复 #31 woodheadz 的帖子

在Canvas中检测鼠标事件有很多种有意思的方法, StackOverFlow上这个帖子很有参考价值

http://stackoverflow.com/questio ... thin-an-html-canvas

评分

参与人数 1威望 +20 收起 理由
woodheadz + 20 谢谢分享!

查看全部评分

回复  

使用道具 举报

 楼主| 发表于 20-1-2012 19:10:08 | 显示全部楼层
原帖由 coredump 于 20-1-2012 18:45 发表
在Canvas中检测鼠标事件有很多种有意思的方法, StackOverFlow上这个帖子很有参考价值

http://stackoverflow.com/questio ... thin-an-html-canvas

果然很多人都碰到这个问题。到目前为止,看来那种重绘到隐藏canvas上的方法算是比较不错的方法了
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 17:51:10 | 显示全部楼层
考察了几个JS库,比较起来还是Kinetic和Easel JS最符合我们的需求,但都有各自的问题。
现在决定自己写一个,反正Kinetic和Easel JS都是MIT的授权协议,很多地方大可好好借鉴下他们的方式。

评分

参与人数 2威望 +40 收起 理由
black_zerg + 20 你太有才了!
coredump + 20 恭喜你!

查看全部评分

回复  

使用道具 举报

发表于 24-1-2012 17:54:32 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 16:51 发表
考察了几个JS库,比较起来还是Kinetic和Easel JS最符合我们的需求,但都有各自的问题。
现在决定自己写一个,反正Kinetic和Easel JS都是MIT的授权协议,很多地方大可好好借鉴下他们的方式。

别忘了open source
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 20:15:17 | 显示全部楼层
原帖由 coredump 于 24-1-2012 17:54 发表

别忘了open source

我倒是想开源,但最后能不能开就看老板的了
回复  

使用道具 举报

发表于 24-1-2012 21:58:41 | 显示全部楼层

回复 #4 coredump 的帖子

欢迎老丐开讲座介绍HTML5应用!

评分

参与人数 2威望 +40 收起 理由
coredump + 20 有时间就继续那个帖子
woodheadz + 20 我很赞同!

查看全部评分

回复  

使用道具 举报

 楼主| 发表于 24-1-2012 22:09:57 | 显示全部楼层
搞了这几天,对canvas的强大简直十分满意
IE9现在对canvas的优化支持简直没得说,速度超快不说,还自带2D图形的抗锯齿。相比起来,Chrome绘图效率就明显不如,而且一旦对2d图形进行旋转缩放,最终的效果比ie就差太多了。
MS毕竟积淀深厚,又是自家平台,一旦真的用心搞搞,别人实在是搞不过他的。
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 22:15:50 | 显示全部楼层
发现FireFox也有2d抗锯齿,chrome的效果还真是惨不忍睹啊....
回复  

使用道具 举报

发表于 24-1-2012 22:49:12 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 21:09 发表
搞了这几天,对canvas的强大简直十分满意
IE9现在对canvas的优化支持简直没得说,速度超快不说,还自带2D图形的抗锯齿。相比起来,Chrome绘图效率就明显不如,而且一旦对2d图形进行旋转缩放,最终的效果比ie就差太多 ...

Chrome底层用的是Skia 2D图形库, IE9用的是DirectWrite, 两者都有抗锯齿。

不过IE9默认开启Canvas的硬件加速了,Chrome现在版本要手工启用:
about:flags
打开
GPU Accelerated Compositing
GPU Accelerated Canvas 2D

评分

参与人数 2威望 +40 收起 理由
black_zerg + 20 你太有才了!
woodheadz + 20 你太有才了!

查看全部评分

回复  

使用道具 举报

发表于 24-1-2012 22:51:05 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 21:15 发表
发现FireFox也有2d抗锯齿,chrome的效果还真是惨不忍睹啊....

使用GPU的话,抗锯齿是很轻松的一件事情, 俺们写的canvas也抗锯齿, 其实就是用的OpenGL多重采样设置一下就行了
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 23:04:28 | 显示全部楼层
原帖由 coredump 于 24-1-2012 22:51 发表

使用GPU的话,抗锯齿是很轻松的一件事情, 俺们写的canvas也抗锯齿, 其实就是用的OpenGL多重采样设置一下就行了

开启以后好几个网页都成了大花脸
是不是我用的chrome版本是beta的缘故? 17的beta版
效率问题还好办,总可以通过优化程序解决。但抗锯齿问题就很头痛了... 没有抗锯齿,很多2D图形效果是在是很悲惨...

[ 本帖最后由 woodheadz 于 24-1-2012 23:22 编辑 ]
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 23:16:07 | 显示全部楼层
原帖由 coredump 于 24-1-2012 22:51 发表

使用GPU的话,抗锯齿是很轻松的一件事情, 俺们写的canvas也抗锯齿, 其实就是用的OpenGL多重采样设置一下就行了

对了,还有个问题请教:
我这段时间看的js库基本上都采用每帧全canvas暴力刷新的方式完成动画。在高分辨率下,ie似乎还撑得住,但chrome就有点不行了。
如果修改为每帧刷新前先计算出无效区域,然后清除这个区域,设置clip region后再重绘,效率应该会明显有改善吧?
我打算在自己的实现的框架里用这种方式,但因此必然会增加不少工作量。所以做之前先打听打听
搞不懂为什么没人这么做,难道效率不会有区别?

[ 本帖最后由 woodheadz 于 24-1-2012 23:17 编辑 ]
回复  

使用道具 举报

发表于 24-1-2012 23:41:19 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 22:16 发表

对了,还有个问题请教:
我这段时间看的js库基本上都采用每帧全canvas暴力刷新的方式完成动画。在高分辨率下,ie似乎还撑得住,但chrome就有点不行了。
如果修改为每帧刷新前先计算出无效区域,然后清除这个区域 ...

我写的canvas实现因为不需要严格遵守canvas的规范, 就从实现上用了这个方式, 术语上称作tiled rendering(分片渲染).
有些canvas framework也用了这个概念(比如这个, 还有这个), 特别是在地图和游戏类型的应用中, tiled rendering是很基本的概念.
回复  

使用道具 举报

发表于 24-1-2012 23:51:56 | 显示全部楼层
我的chrome好像没有反锯齿的问题

chrome 18.0.1010.0 on Mac OS 10.7
回复  

使用道具 举报

 楼主| 发表于 24-1-2012 23:59:44 | 显示全部楼层
原帖由 coredump 于 24-1-2012 23:41 发表

我写的canvas实现因为不需要严格遵守canvas的规范, 就从实现上用了这个方式, 术语上称作tiled rendering(分片渲染).
有些canvas framework也用了这个概念(比如这个, 还有这个), 特别是在地图和游戏类型的应用中,  ...

似乎这个和我想的略有不同。
我尝试说说我对这个tiled rendering的理解你看对不:
tiled rendering应该是当所绘制的区域非常庞大时,首先将整个区域分小块存储,然后根据当前的“视区”范围从区域中选出可见的小块绘制。这样可以极大的提高绘制速度。

而我要解决的问题是当“视区”很大(高分辨率)时,为了提高效率,重绘时首先找出整个视区中需要重绘的部分(通常很小),仅仅清除这些部分,然后把这些区域设置为clip region,再调用和这些部分相交的图形对象的绘制代码完成绘制。因为重绘的区域比较小,所以效率会比较高(这点我猜的,以前做GDI编程的时候是这样,不知道对canvas而言是不是这样?)
这段时间我看的JS库基本上是清除整个canvas区域,然后全部重绘。
回复  

使用道具 举报

发表于 25-1-2012 00:08:25 | 显示全部楼层

回复 #46 woodheadz 的帖子

这里有3个概念
1. tile size   每次绘制的小方块的大小
2. canvas size  整个画布的逻辑上的大小
3. canvas window size  canvas这个元素的大小

如果2 > 3 而且 2> 1的时候, 就是你说的第一种的情况, 这个时候1和3谁大谁小无所谓, 根据需要定

如果3 = 2的时候, 把3(2)分成很多个小的1, 那么就是你说的第二种情况

从算法上来说, 这两种情况没有区别
回复  

使用道具 举报

 楼主| 发表于 25-1-2012 00:15:35 | 显示全部楼层
原帖由 coredump 于 24-1-2012 23:51 发表
我的chrome好像没有反锯齿的问题

chrome 18.0.1010.0 on Mac OS 10.7


我用这段代码:
var canvas = document.getElementById("myCanvas");
var context = canvas.getContext("2d");
context.fillStyle = "#FF0000";
context.fillRect(10, 10, 100, 50);
context.rotate(-Math.PI / 20);
context.fillStyle = "blue";
context.fillRect(10, 80, 100, 50);

从左到右分别是Firefox 9,IE9和Chrome17(没开硬件加速):
a.jpg

用浏览器自带的放大功能放大后更是惨不忍睹:
b.jpg
回复  

使用道具 举报

 楼主| 发表于 25-1-2012 00:27:57 | 显示全部楼层
原帖由 coredump 于 25-1-2012 00:08 发表
这里有3个概念
1. tile size   每次绘制的小方块的大小
2. canvas size  整个画布的逻辑上的大小
3. canvas window size  canvas这个元素的大小

如果2 > 3 而且 2> 1的时候, 就是你说的第一种的情况, 这个时候 ...

在算法模型上看,基本没区别。但在实践上区别就很大。
比如这个tile engine,在绝大多数时候canvas,也就是视区是需要整个重绘的,所以我相信他不会去理会部分的重绘的问题。
但在有些图形场景(比如我们的应用)中,多数时候发生变化的区域只占整个canvas可视面积的一小部分,如果减小重绘面积能够提高效率,那么花这个功夫去处理好部分重绘就是值得的。
回复  

使用道具 举报

发表于 25-1-2012 00:33:33 | 显示全部楼层

回复 #49 woodheadz 的帖子

这个只需要根据需要做简单判断就行了, 也就是决定具体的绘制区域上.

context2d 有clip方法, 所以即使具体的绘制没有严格遵守重绘区域的约定也可以剪裁掉, 而大部分底层clip实现可以保证足够的高效, 也就是说被裁减掉的部分, 基本上不影响效率.
回复  

使用道具 举报

发表于 25-1-2012 00:38:18 | 显示全部楼层
强,我最近也在用gwt和canvas搞自己的一个小项目
回复  

使用道具 举报

发表于 25-1-2012 00:45:46 | 显示全部楼层

不知道是不是这个意思

我当时找过检测点在polygon里,最后发现有个 W. Randolph Franklin 的代码 我给整理成了java的:

public static boolean pnpoly(int nvert, double[] vertx, double[] verty,
                        double testx, double testy) {
                int i, j = 0;
                boolean c = false;
                for (i = 0, j = nvert - 1; i < nvert; j = i++) {
                        if (((verty > testy) != (verty[j] > testy))
                                        && (testx < (vertx[j] - vertx) * (testy - verty)
                                                        / (verty[j] - verty) + vertx))
                                c = !c;
                }
                return c;
        }

我其实不确定我明白你的意思,不过我当时每个图形都会保存一个方形的信封,检查的时候先查信封,如果不在信封里就直接排除了,否则就用上面那个方法检查点是否在polygon里面。因为我的模型都是几何模型,也就是说canvas只是绘图的实现而已。如果polygon不复杂,这种计算应该是很快的。

按照我对canvas的理解,canvas最好依赖在后台的一个结构上做成mvc那种模型,因为本身canvas和vml svg什么的差很多,canvas画完了就完了,他也没有一个图形一个对象那种概念。

[ 本帖最后由 black_zerg 于 25-1-2012 00:58 编辑 ]

评分

参与人数 1威望 +20 收起 理由
woodheadz + 20 谢谢分享!

查看全部评分

回复  

使用道具 举报

发表于 25-1-2012 00:46:05 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 23:15 发表


我用这段代码:
var canvas = document.getElementById("myCanvas");
var context = canvas.getContext("2d");
context.fillStyle = "#FF0000";
context.fillRect(10, 10, 100, 50);
context.rotate(-Math. ...
好像的确如此啊, 应该是chrome canvas实现的一个bug, 因为它的skia引擎肯定是支持反锯齿的
回复  

使用道具 举报

发表于 25-1-2012 00:54:03 | 显示全部楼层
原帖由 black_zerg 于 24-1-2012 23:45 发表
我当时找过检测点在polygon里,最后发现有个 W. Randolph Franklin 的代码 我给整理成了java的:

public static boolean pnpoly(int nvert, double[] vertx, double[] verty,
                        double testx, double testy) {
...

PIP有2种经典算法,  一种叫奇偶算法, 一种叫Winding number算法, 维基上有2个很好的图来说明这两个算法

                               
登录/注册后可看大图


                               
登录/注册后可看大图


这个其实受影响最大的是填充时的效果, 不同的算法导致的填充不一样, canvas的fill()方法要求的算法实现是后一种.
回复  

使用道具 举报

发表于 25-1-2012 01:00:47 | 显示全部楼层
果然研究的深刻!我的polygon全部给强制成simple polygon了,所以也不用管那么多 ^_^。
回复  

使用道具 举报

发表于 25-1-2012 01:06:48 | 显示全部楼层
原帖由 black_zerg 于 24-1-2012 23:45 发表
按照我对canvas的理解,canvas最好依赖在后台的一个结构上做成mvc那种模型,因为本身canvas和vml svg什么的差很多,canvas画完了就完了,他也没有一个图形一个对象那种概念。

是滴, canvas和svg正好代表了2d绘图的两种风格
canvas是立即模式的代表, svg是保留模式的代表

直觉上来说, 我们总会觉得保留模式应该更受青睐一点, 可惜事实上相反, canvas这种立即模式成了香饽饽, svg却被打入冷宫.

其实不是保留模式不好(现在大家都在canvas里实现svg早已实现了很久的东西, 就是证明), 而是svg被龟速的DOM给陷害了, 而且出道太早, 那时候所有的DOM实现都比较差, 所以svg是命不好占主要原因.
回复  

使用道具 举报

 楼主| 发表于 25-1-2012 01:07:14 | 显示全部楼层
原帖由 black_zerg 于 25-1-2012 00:45 发表
我当时找过检测点在polygon里,最后发现有个 W. Randolph Franklin 的代码 我给整理成了java的:

public static boolean pnpoly(int nvert, double[] vertx, double[] verty,
                        double testx, double testy) {
...

谢谢分享,只是现在我面临的状况无法使用这种方式。因为第一我们有背景透明的点阵图,第二有非闭合的线条的hittest
回复  

使用道具 举报

 楼主| 发表于 25-1-2012 01:09:42 | 显示全部楼层
原帖由 coredump 于 25-1-2012 01:06 发表

是滴, canvas和svg正好代表了2d绘图的两种风格
canvas是立即模式的代表, svg是保留模式的代表

直觉上来说, 我们总会觉得保留模式应该更受青睐一点, 可惜事实上相反, canvas这种立即模式成了香饽饽, svg却被打入 ...

wpf应该是做得很不错的保留模式的实例了  只可惜命不好

评分

参与人数 1威望 +20 收起 理由
coredump + 20 我很赞同!

查看全部评分

回复  

使用道具 举报

发表于 25-1-2012 01:11:58 | 显示全部楼层
原帖由 woodheadz 于 25-1-2012 00:09 发表

wpf应该是做得很不错的保留模式的实例了  只可惜命不好

我们的Qt QML也是保留模式的经典, JavaFX也算一个了.

评分

参与人数 1威望 +20 收起 理由
woodheadz + 20 恭喜你!

查看全部评分

回复  

使用道具 举报

发表于 25-1-2012 01:21:22 | 显示全部楼层
原帖由 woodheadz 于 24-1-2012 17:51 发表
考察了几个JS库,比较起来还是Kinetic和Easel JS最符合我们的需求,但都有各自的问题。
现在决定自己写一个,反正Kinetic和Easel JS都是MIT的授权协议,很多地方大可好好借鉴下他们的方式。


强啊,我发现我是只能用jquery写短的javascript,写大段的马上就脑残。

评分

参与人数 1威望 +20 收起 理由
woodheadz + 20 我是赶鸭子上架

查看全部评分

回复  

使用道具 举报

您需要登录后才可以回帖 登录 | FreeOZ用户注册

本版积分规则

小黑屋|手机版|Archiver|FreeOZ论坛

GMT+11, 29-3-2024 11:35 , Processed in 0.035516 second(s), 47 queries , Gzip On, Redis On.

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表