当Meteor更新集合时,如何防止内容滚动

时间:2013-02-08 09:00:47

标签: meteor

我的问题与this onethat one非常相似,但不完全相同。

我的Meteor应用程序中有以下模板:

<template name="items">
    <div class="mainframe">
    <h3>Available items:</h3>
        <div class="items-table-container">
            <table class="table table-hover">
                <tbody>
                    {{#each all_items}}
                       {{> item}}
                    {{/each}}
                </tbody>
            </table>
        </div>
    </div>
    <div class="btn-group">
    <button id="create" class="btn">Create new item</button>
    </div>
</template>

模板功能很简单:

Template.items.all_items = function () {
    return Items.find({}, {sort: {name: 1}}).fetch();
}

还有一个绑定到#create按钮的事件,它将一个新项目插入到Items集合中,并且工作正常。

现在最重要的部分是CSS:

.items-table-container {
    height:340px;
    overflow-y: scroll;
}

所以基本上我希望我的表在固定大小的区域内具有可滚动内容。 当我在一个浏览器中向下滚动项目表的内容然后在另一个浏览器中我添加一个新项目时,问题就出现了。第一个浏览器更新项目列表并将内容滚动回到顶部位置。

问题是如何阻止单个模板的自动更新?我认为在这种特殊情况下,我实际上需要像传统网页更新这样的东西:如果用户没有立即看到新添加的项目,而是在重新加载页面之后,那就没问题了。

另一个想法是做一些分页而不是可滚动的内容。我认为这样可以解决问题,但这会更复杂,我想避免这种情况。

我认为理想情况下,我希望能够告诉Meteor我希望Meteor更新模板,而不是在模型更改时,而是通过请求。

4 个答案:

答案 0 :(得分:4)

将您的项目列表放在可滚动div容器内的另一个模板中:

<template name="items">
    <div class="mainframe">
    <h3>Available items:</h3>
        <div class="items-table-container">
            <table class="table table-hover">
                <tbody>
                    {{> myitems}}
                </tbody>
            </table>
        </div>
    </div>
    <div class="btn-group">
        <button id="create" class="btn">Create new item</button>
    </div>
</template>

<template name="myitems">
    {{#each all_items}}
        {{> item}}
    {{/each}}
</template>

使用Javascript:

Template.myitems.all_items = function () {
    return Items.find({}, {sort: {name: 1}}).fetch();
}

//Template.items.all_items = function () {
// remove this helper
//}

通过这种方式,您可以保持反应性而无需更新请求。只重新渲染可滚动框内的部分,保持滚动容器滚动到的位置。

编辑:要保留/冻结您的内容,您可以使用preserve功能,它需要一个css选择器作为输入。 e.g

Template.items.preserve(['.items-table-container']);

答案 1 :(得分:3)

隔离数组迭代。

{{#isolate}}
  {{#each all_items}}
    {{> item}}
  {{/each}}
{{/isolate}}

答案 2 :(得分:1)

要使整个区域保持不变以便不重新渲染,可以使用块助手{{#constant}}。

如果要保留特定的DOM元素,可以使用Template.myTemplate.preserve(),它将要保留的节点选择器作为参数。

答案 3 :(得分:-1)

您还可以使用jquery句柄来修复滚动位置。我的用例是在主体文档中滚动文本较低的当前滚动点上方插入了一些内容。

不确定如何在每次更新发布集时让meteor运行回调,但你应该明白这一点:

before = document.body.scrollHeight
// insert your elements
after = document.body.scrollHeight

if $(document).scrollTop() != 0
  # scroll us equal to the amount of scroll height added
  window.scrollTo(0, $(document).scrollTop()+(after-before) )