支持无级缩放的360展示技术实现之四

改造OpenSeadragon用于360展示

本节主要介绍改造OpenSeadragon,使其适用于360度展示。

过去的一年,我曾经对360展示的插件进行选型,商用的插件,我认为目前最成熟的是:

http://www.ajax-zoom.com/examples/,我用它做了一个项目实施,虽然遇到一些官网例程之外的麻烦,

总的来说,只要官网例子已经有的,依葫芦画瓢就好。官网的例子已经比较丰富了,作者的售后也很给力。

 

而开源方面情况就比较让人灰心了,我甚至没有找到一款同时具备360度旋转和无级缩放的开源插件。

OpenSeadragon Sequence Mode

OpenSeadragon在无级缩放方面已经做到足够好了,能不能再进一步,让它成为我的360展示插件呢,

我开始浏览官方的example,当看到这个例子之后,信心大增,心里想它离我要的那个目标已经不远了。

这就是:Sequence Mode,而其中这个例子最接近我的要求:

Preserving the Viewport Zoom Level and Position for Image Sequences


支持无级缩放的360展示技术实现之四_第1张图片
 

改造策略 

对比下我最终想要的效果:

http://v.youku.com/v_show/id_XMTM5ODE0MjI0NA==.html

 

即:既然OpenSeadragon已经能够做到:在加载系列帧时,保持住缩放局部的设定,那么需要做的就是:

不断优化加载系列帧的性能,做到在加载连续帧对应的切片时流畅显示。——这个就是我改造OpenSeadragon的原则。

 

前端缓存

缓存策略涉及前端缓存,和服务端缓存两部分,先讨论前端缓存。

OpenSeadragon本身对于当前加载的切片是进行了缓存处理的,它在进行缩放和平移时,如果不是利用缓存中的image直接进行绘制,是不可能做到平滑的。

OpenSeadragon在tiledImage层次进行缓存,相关代码如下:

写入缓存:

function completionCallback() {
        increment--;
        if (increment === 0) {
            tile.loading = false;
            tile.loaded = true;
            if (!tile.context2D) {
                tiledImage._tileCache.cacheTile({
                    image: image,
                    tile: tile,
                    cutoff: cutoff,
                    tiledImage: tiledImage
                });
            }
            tiledImage._needsDraw = true;
        }
    }

 

获取缓存:

 

if (!tile.loaded) {
        if (tile.context2D) {
            setTileLoaded(tiledImage, tile);
        } else {
            var imageRecord = tiledImage._tileCache.getImageRecord(tile.url);
            if (imageRecord) {
                var image = imageRecord.getImage();
                setTileLoaded(tiledImage, tile, image);
            }
        }
    }

 

  然而不幸的是,在加载新的一帧影像时,这个缓存被清除了(该reset在tiledImage的destroy时被调用。):

 

reset: function() {
        this._tileCache.clearTilesFor(this);
        this.lastResetTime = $.now();
        this._needsDraw = true;
    },
 

 

对于OpenDragon的功能定位来说,这是非常合理的处理,载入下一帧影像时,当然应该清除当前帧所占用的内存,否则随着加载的帧不断增加,内存开销会越来越大。

而对于360展示来说,为了实现连续帧之间的平滑切换,需要预先将所有的帧加载到内存,当然代价是:内存开销会达到所有帧的总和。

 

针对上述分析,我们实施的第一个改动是:

 

加载下一帧保持缓存

虽然涉及到的代码还不少,但清楚其逻辑之后,只需要注释掉reset函数的两行即可:

reset: function() {
    	//c4w commet 加载下一张图时并不清除上一张缓存
        //this._tileCache.clearTilesFor(this);
        //this.lastResetTime = $.now();
        this._needsDraw = true;
    },

 

 由于缓存部分篇幅较长,就此结束本节,下节继续。

 

 

 

你可能感兴趣的:(支持无级缩放的360展示技术实现之四)