flicker after one row removed?
Any advice here regarding a "flicker" I see across the whole list when I delete just one row from the list. I have tried the same thing with the react-native "flatlist" and I don't see this flicker. The more interesting thing also is that this "flicker" doesn't occur every time. When I say flicker, whilst the 4th item is being removed, when the flicker occurs I see the "redraw" of all items including the 1st/2nd/3rd too.
Reproducing: I took the basic example and added a button at the bottom to trigger removing the 4th item in the list. I should point out my testing is on the IOS simulator. Code below.
onPressLearnMore() {
console.log('onPressLearnMore', this.state.data);
let newObject = {};
Object.keys(this.state.data).forEach((k, index) => {
if (index !== 3) {
newObject[k] = this.state.data[k];
};
});
this.setState({
data: newObject,
});
};
Any updates on this?
I think it's about uniqueRowKey.id, it changes in componentWillReceiveProps func, which leads to rerender because key has changed After some test and experiment, I find a way to make delete & add item without filcker possible. The basic idea is to manipulate order while the real order of data remains unchanged(reuse key).
I hope there's a better way. What I do gives me a headache :(
- stop changing uniqueRowKey.id, use you own keyExtractor.
- container pass order(manipulated, decr every order value by 1 if it's larger than the deletedOrder) and data(order unchanged, item added or removed) props to SortableList, container also need to pass deletedOrder(for example, order=[5, 4, 0, 1, 3, 2], pass 3 if you want to delete the 5th item, and the new order should be [4, 3, 0, 1, 2] ) prop when delete happens.
- update the related _rowsLayouts and _resolveRowLayout.
- the code below only handle one item change at a time.
- keep this.order up to date in _setOrderOnMove, somewhere near this.props.onChangeOrder (unnecessary)
removeAndAdjustKey(source, deletedKey) {
let result = {}
deletedKey = parseInt(deletedKey);
for (key in source) {
key = parseInt(key);
if (key < deletedKey) {
result[key] = source[key];
} else if (key > deletedKey) {
let old = key - 1;
result[old] = source[old];
}
}
return result;
}
componentWillReceiveProps(nextProps) {
let {order: nextOrder} = nextProps;
let curOrder = this.order;
if (curOrder && nextOrder && curOrder.length != nextOrder.length) {
if (curOrder.length > nextOrder.length) {
let deletedOrder = nextProps.deletedOrder;
this._rowsLayouts = this.removeAndAdjustKey(this._rowsLayouts, deletedOrder);
this._resolveRowLayout = this.removeAndAdjustKey(this._resolveRowLayout, deletedOrder);
} else {
let key = nextOrder[curOrder.length];
this._rowsLayouts[key] = new Promise((resolve) => {
this._resolveRowLayout[key] = resolve;
});
}
LayoutAnimation.configureNext(LayoutAnimation.create(220,
LayoutAnimation.Types.easeInEaseOut,
LayoutAnimation.Properties.opacity
));
this._onUpdateLayouts();
}
this.order = [...nextOrder];
}