简体   繁体   English

如何不重新渲染秘银中的整个列表

[英]How to not re-render the whole list in Mithril

I've used react for quite some time and wanted to try out Mithril.js. 我已经使用React一段时间了,想尝试一下Mithril.js。

Went through the documentation and the examples and liked what I saw, so I said I should get my hands dirty and start coding! 浏览了文档和示例并喜欢我所看到的内容,所以我说我应该动手开始编码!

I have a smiple API call that receives a JSON data and then outputs ul list with all the items. 我有一个简单的API调用,它接收JSON数据,然后输出包含所有项目的ul列表。 I've integrated GSAP TweenMax for animations and what I'm trying to achieve is very simple - I fade everything in, on onload and then onclick I want to fade to fade an element out and remove it from DOM / data. 我已经将GSAP TweenMax集成到动画中,并且我想要实现的目标非常简单-我先淡入所有内容,然后在onload加载,然后在onclick上淡入淡出,以淡出一个元素并将其从DOM /数据中删除。

What seems to be happening is that the element is fading out, the whole ul list is being re-rendered and that element remains in the DOM with 0 opacity: 似乎正在发生的事情是该元素正在逐渐消失,整个ul列表正在重新呈现,并且该元素以0不透明度保留在DOM中:

var Item = {
    list: function() {
        return m.request({method: 'GET', url: '/api/items'});
    }
}

var dm = {
    controller: function(data) {                
        var items = Item.list();
        return {
            items: items,
            remove: function(item) {                
                items().data.splice(items().data.indexOf(item), 1);
            }
        }
    },

    view: function(ctrl) {      
        return m('ul', [
            ctrl.items().data.map(function(item, id){
                return m('li',{
                    key: id,
                    config: fadesIn,
                    onclick: fadeOut(ctrl.remove.bind(this, item))
                }, item.title);
            })
        ]);
    }
}

var fadesIn = function(element){
    var tl = new TimelineMax();
    tl.from(element, .5, {opacity: 0});
}

var fadeOut = function(callback) {
    return function(e) {
        m.redraw.strategy('none');
        TweenMax.to(e.target, .5, {opacity: 0, onComplete: function() {
            m.startComputation();           
            callback();         
            m.endComputation();
        }});
    }
}

m.mount(document.getElementById('test'), dm);

I'm very new.. started reading up just yesterday. 我很新..从昨天开始阅读。

Getting animation libraries to work with Mithril can be tricky. 使动画库与Mithril配合使用可能会很棘手。 When libraries manipulate DOM state the synchronization with Mithril state can be broken. 当库处理DOM状态时,与Mithril状态的同步可能会中断。

Fortunately that wasn't the case: What you're missing is the isInitialized parameter for the config function, which is false only on the first call. 幸运的是,事实并非如此:您缺少的是config函数的isInitialized参数,该参数仅在第一次调用时为false。 Testing for that makes the fade-in only happen once: 经过测试,淡入仅发生一次:

var fadesIn = function(element, isInit){
    if(isInit) return;
    var tl = new TimelineMax();
    tl.from(element, .5, {opacity: 0});
}

In this simple example the redrawing can also be simplified, I've made a fiddle with a working example: 在这个简单的示例中,重绘也可以简化,我用一个有效的示例进行了摆弄:

http://jsfiddle.net/ciscoheat/dkyc0ryc/ http://jsfiddle.net/ciscoheat/dkyc0ryc/

Since there are no DOM manipulations a call to m.redraw is enough to remove the div from DOM, but you're probably right in using start/endComputation when things get more complex. 由于没有DOM操作,因此对m.redraw的调用足以将div从DOM中删除,但是当事情变得更加复杂时,使用start/endComputation可能是正确的。 I would even move m.startComputation above the TweenMax.to call to make it extra safe, but if many other things are happening at the same time, that may block other redraws. 我什至将m.startComputation移到TweenMax.to上方以使其更加安全,但是如果同时发生其他许多事情,则可能会阻止其他重绘。 You have to find a balance. 您必须找到一个平衡点。 :) :)

The call to m.redraw.strategy isn't needed in any case, I think. 我认为在任何情况下都不需要调用m.redraw.strategy It's mostly used when you want nothing at all to happen (synchronously as well), but an async animation is starting so it won't have any effect. 当您不希望任何事情发生(同步)时,通常使用它,但是异步动画正在开始,因此不会产生任何效果。

Edit: Found another problem, the key cannot be set to the index of the map function, then it will change when an item is removed, messing up the redraw. 编辑:发现另一个问题,不能将key设置为map函数的索引,然后在删除项目时它将更改,从而使重绘混乱。 I've updated the fiddle to use item.title as key instead. 我更新了小提琴,改为使用item.title作为键。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM