2

我正在加载超过 7000 条记录并将它们显示在我的页面上。

Firefox 运行良好,但使用 Chrome 时出错

部分代码:

<tbody>
    {{each(i, item) value}}
    <tr>
        <td class="item_action">
            <a class="edit_item" data-item="${item.id}">
                <img src="path/to/image_edit.png" />
            </a>

            <img src="path/to/image_separator.png" />

            <a class="delete_item" data-item="${item.id}">
                <img src="path/to/image_delete.png" />
            </a>
        </td>
        <td class="item_name">${item.name}</td>
    </tr>
    {{/each}}
</tbody>

如果不是上面我呈现这个:

<tbody>
    {{each(i, item) value}}
    <tr>
        <td class="item_name">${item.name}</td>
    </tr>
    {{/each}}
</tbody>

那么Chrome就没有问题了。因此,我想这与我在此处阅读时尝试渲染的 HTML 的大小有关。

这个问题有解决方案吗?一世

4

1 回答 1

10

我遇到过同样的问题。如果您查看 jquery.tmpl 代码,您可以找到

function build( tmplItem, nested, content ) { ... 

问题出在

jQuery.map( content, function( item ) {

对于“内容”数组中的每个项目(我猜这里有超过 50000 个元素)应该被称为函数。这对于 Webkit 浏览器来说太过分了。这段代码稍作修改以解决我的问题:

function build( tmplItem, nested, content ) {
    // Convert hierarchical content into flat string array
    // and finally return array of fragments ready for DOM insertion
    var processMap = function(){
        var result = [];
        var items = [];
        for(var i = 0; i<content.length; (i = i+10000)){
            var subcontent = content.slice(i, i+10000);
            items =  jQuery.map( subcontent, function( item ) {
                        return (typeof item === "string") ?
                            // Insert template item annotations, to be converted to jQuery.data( "tmplItem" ) when elems are inserted into DOM.
                            (tmplItem.key ? item.replace( /(<\w+)(?=[\s>])(?![^>]*_tmplitem)([^>]*)/g, "$1 " + tmplItmAtt + "=\"" + tmplItem.key + "\" $2" ) : item) :
                            // This is a child template item. Build nested template.
                            build( item, tmplItem, item._ctnt );
            });
            result = result.concat(items);
        }
        return result;
    };
    var frag, ret = content ?  processMap():
    // If content is not defined, insert tmplItem directly. Not a template item. May be a string, or a string array, e.g. from {{html $item.html()}}.
    tmplItem;
    if ( nested ) {
        return ret;
    } ...

因此 jQuery.map 函数处理每 10000 个元素,并且不允许“超出最大调用堆栈大小”。

这是一个粗略的解决方案,但希望对您有所帮助:)

于 2013-05-03T15:44:29.057 回答