feat: move lists between namespaces #1430

Merged
konrad merged 3 commits from feature/move-list into main 2022-01-29 21:12:46 +00:00
2 changed files with 21 additions and 15 deletions

View File

@ -90,13 +90,15 @@
v-bind="dragOptions"
:modelValue="activeLists[nk]"
@update:modelValue="(lists) => updateActiveLists(n, lists)"
:group="`namespace-${n.id}-lists`"
group="namespace-lists"
@start="() => drag = true"
@end="e => saveListPosition(e, nk)"
@end="saveListPosition"
handle=".handle"
:disabled="n.id < 0 || null"
tag="transition-group"
item-key="id"
:data-namespace-id="n.id"
:data-namespace-index="nk"
:component-data="{
type: 'transition',
tag: 'ul',
@ -198,7 +200,7 @@ export default {
loading: state => state[LOADING] && state[LOADING_MODULE] === 'namespaces',
}),
activeLists() {
return this.namespaces.map(({lists}) => lists?.filter(item => !item.isArchived))
return this.namespaces.map(({lists}) => lists?.filter(item => typeof item !== 'undefined' && !item.isArchived))
},
namespaceTitles() {
return this.namespaces.map((namespace) => this.getNamespaceTitle(namespace))
@ -241,15 +243,15 @@ export default {
this.listsVisible[namespaceId] = !this.listsVisible[namespaceId]
},
updateActiveLists(namespace, activeLists) {
// this is a bit hacky: since we do have to filter out the archived items from the list
// This is a bit hacky: since we do have to filter out the archived items from the list
// for vue draggable updating it is not as simple as replacing it.
// instead we iterate over the non archived items in the old list and replace them with the ones in their new order
const lists = namespace.lists.map((item) => {
if (item.isArchived) {
return item
}
return activeLists.shift()
})
// To work around this, we merge the active lists with the archived ones. Doing so breaks the order
// because now all archived lists are sorted after the active ones. This is fine because they are sorted
// later when showing them anyway, and it makes the merging happening here a lot easier.
const lists = [
...activeLists,
konrad marked this conversation as resolved
Review

spread this directly in newNamespace

spread this directly in `newNamespace`
Review

You mean spreading the contents of archivedFromNamespace directly instead of using a new variable?

You mean spreading the contents of `archivedFromNamespace` directly instead of using a new variable?
Review

Yes or even creating the object directly inline with the commit.

Yes or even creating the object directly inline with the commit.
Review

Done.

Done.
...namespace.lists.filter(l => l.isArchived),
]
const newNamespace = {
...namespace,
@ -259,8 +261,11 @@ export default {
this.$store.commit('namespaces/setNamespaceById', newNamespace)
},
async saveListPosition(e, namespaceIndex) {
const listsActive = this.activeLists[namespaceIndex]
async saveListPosition(e) {
const namespaceId = parseInt(e.to.dataset.namespaceId)
const newNamespaceIndex = parseInt(e.to.dataset.namespaceIndex)
dpschen marked this conversation as resolved
Review

Why the switch to data attributes?

Why the switch to data attributes?
Review

Because I need to get the attributes of the target element. The @drop handler is called from the source element, hence it won't contain the new data if I'd pass it in directly like @drop="e => saveListPosition(e, namespaceId)".

This is in line with how we're passing the data when moving tasks between kanban buckets.

Because I need to get the attributes of the target element. The `@drop` handler is called from the source element, hence it won't contain the new data if I'd pass it in directly like `@drop="e => saveListPosition(e, namespaceId)"`. This is in line with how we're passing the data when moving tasks between kanban buckets.
Review

What I don't understand is, why did the original line work @end="e => saveListPosition(e, nk)" / why was nk updated?

What I don't understand is, why did the original line work `@end="e => saveListPosition(e, nk)"` / why was `nk` updated?
Review

It was not updated, but is wasn't possible to move a list between namespaces (solved with sortable.js groups for each namespace). So nk was always the same for all lists in a namespace.

It was not updated, but is wasn't possible to move a list between namespaces (solved with sortable.js groups for each namespace). So `nk` was always the same for all lists in a namespace.
Review

That makes sense =) Thanks for explaining.

That makes sense =) Thanks for explaining.
const listsActive = this.activeLists[newNamespaceIndex]
const list = listsActive[e.newIndex]
const listBefore = listsActive[e.newIndex - 1] ?? null
const listAfter = listsActive[e.newIndex + 1] ?? null
@ -273,6 +278,7 @@ export default {
await this.$store.dispatch('lists/updateList', {
...list,
position,
namespaceId,
})
} finally {
this.listUpdating[list.id] = false

View File

@ -134,8 +134,8 @@ export default {
},
loadNamespacesIfFavoritesDontExist(ctx) {
// The first namespace should be the one holding all favorites
if (ctx.state.namespaces[0].id !== -2) {
// The first or second namespace should be the one holding all favorites
if (ctx.state.namespaces[0].id !== -2 && ctx.state.namespaces[1]?.id !== -2) {
return ctx.dispatch('loadNamespaces')
dpschen marked this conversation as resolved Outdated

Quick thought:
I think for the frontend we should save the "special ids" in some constant and import them when we use them.

Quick thought: I think for the frontend we should save the "special ids" in some constant and import them when we use them.
}
},