Last active
October 7, 2020 06:32
-
-
Save royteusink/ecae35628d609e8a6572789877bbf1b8 to your computer and use it in GitHub Desktop.
immutable.js - Move item in List to a specific location (change sequence, reorder)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
if (action.toindex < 0) return state; | |
var olditem = state.get(action.index); | |
var newlist = state.delete(action.index).insert(action.toindex, olditem); | |
return newlist; |
Don't know what i had copied wrong, but also #comment-2271960 didn't worked for me with v4 immutable.
This is what i now got, also in the need to move items in nested map/array a lot:
import { List, Map } from "immutable";
/**
* Move item inside a list to new index
* @param {List} value
* @param {int} oldI
* @param {int} newI
* @return {List}
*/
const moveItem = (value, oldI, newI) => {
if (!value || 0 > newI || value.size < newI) return value;
const srcItem = value.get(oldI);
return value.splice(oldI, 1).splice(newI, 0, srcItem);
};
/**
* Moves an item in a list which is in a Map/OrderedMap
*
* @param {Map|OrderedMap} state
* @param {List} stateKeys
* @param {int} go if positive will move the number further e.g.: `2` positions further: old is 1, new is 3, go is `2`; when negative will move back: old is 3, new is 1, go is `-2`
* @return {*}
*/
const stateMoveItem = (state, stateKeys, go) => {
const valueStateKeys = stateKeys.slice(0, -1);
const index = stateKeys.slice(-1).get(0);
return state.setIn(
valueStateKeys,
moveItem(state.getIn(valueStateKeys), index, index + go)
);
};
const state = List([
Map({ id: 1 }),
Map({ id: 2 }),
Map({
id: 3,
children: List([Map({ id: 5 }), Map({ id: 6 }), Map({ id: 7 })])
}),
Map({ id: 4 })
]);
let movedFirstLevel1 = moveItem(state, 0, 1); // switch `id:1` and `id:2`
console.log(movedFirstLevel1.toJS());
let movedFirstLevel2 = moveItem(state, 1, 2); // move `id:2` BEFORE `id:4`
console.log(movedFirstLevel2.toJS());
let movedChildren1 = stateMoveItem(state, List([2, "children", 1]), 1); // move `id:6` AFTER `id:7`
console.log(movedChildren1.toJS());
let movedChildren2 = stateMoveItem(state, List([2, "children", 2]), -1); // move `id:7` before `id:6`
console.log(movedChildren2.toJS());
let movedChildren3 = stateMoveItem(state, List([2, "children", 2]), -2); // move `id:7` before `id:5`
console.log(movedChildren3.toJS());
// `go` is not `newIndex`, when using `newIndex`, substract `oldIndex` from `newIndex` and you got `go`
const oldIndex = 1;
const newIndex = 2;
let movedChildren4 = stateMoveItem(state, List([2, "children", oldIndex]), newIndex - oldIndex); // move `id:6` AFTER `id:7`
console.log(movedChildren4.toJS());
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
BTW, how can I move item inside of nested list?
For example:
move item with id
2
in path[2, 1]