3

I am using Raphael.js to create polygons, (or actually closed paths) over an image. I want to put text inside the polygons. Is there any way to create a text element and then adjust its size and position so that the whole thing will be within the bounds of a polygon?

Are there at least any algorithms that can give me good guesses that I could manually adjust?

4

1 回答 1

3

好的,我在一天的过程中对此进行了一些思考,终于有机会将一些演示代码放在一起。它在很多方面都明显不完美,但可能是一个很好的起点,并且似乎与我的大多数随机生成的多边形一起工作得很好。

第 1 部分:在多边形上居中文本。使用边界框被证明非常不令人满意,所以我没有设计一种技术来平均给定路径中的所有点container

            //  Determine the *weighted* center of this figure
            var segments = Raphael.parsePathString( container.attr( 'path' ) );
            var count = 0, sum_x = 0, sum_y = 0;
            for ( var i = 0; i < segments.length; i++ )
            {
                if ( segments[i][0] == 'L' || segments[i][0] == 'M' )
                {
                    count++;
                    sum_x += segments[i][1];
                    sum_y += segments[i][2];
                }
            }

            var cx = sum_x / count, cy = sum_y / count;

第 2 部分:碰撞检测。我需要一种机制来检查给定对象是否在当前形状内。由于懒惰,我只是在创建画布之前扩展了 Raphael 元素对象。

        Raphael.el.isObjectInside = function( obj )
        {
            var box = obj.getBBox();
            return this.isPointInside( box.x, box.y ) 
                        &&
                    this.isPointInside( box.x2, box.y )
                        &&
                    this.isPointInside( box.x, box.y2 )
                        &&
                    this.isPointInside( box.x2, box.y2 );
        }

第 3 部分:迭代调整大小。基本上,我们使用上面生成的坐标并将它们应用于生成的标签文本。我们每次迭代都会减少一次规模,直到我们低于某个阈值,此时我的代码会简单地放弃(你的代码可能不应该):

            var s = 1.0;
            if ( ibox.width >= cbox.width * 0.7 )
            {
                s = ( cbox.width * 0.7 ) / ibox.width;
            }

            while ( s > 0.1 )
            {
                insert.attr( { transform: [ "S", s, s, ibox.x + ibox.width / 2, ibox.y + ibox.height / 2, "T", 
                if ( container.isObjectInside( insert ) )
                    return;
                s *= 0.65;
            }

            console.log("Warning: NOT a clean fit" );

对于我扔给它的大多数纯随机多边形,结果看起来都很好。我确信它的计算量远远超过它需要的量。我的代码在这里上演——只需单击多边形即可生成一个新的。

快乐编码。

于 2012-09-21T23:51:36.910 回答