diff --git a/assets/controllers/preferred_sources_controller.js b/assets/controllers/preferred_sources_controller.js new file mode 100644 index 0000000..3a4c6e1 --- /dev/null +++ b/assets/controllers/preferred_sources_controller.js @@ -0,0 +1,101 @@ +// assets/controllers/preferred-sources_controller.js + +import {Controller} from "@hotwired/stimulus" +import Sortable from 'sortablejs' + +export default class extends Controller { + static targets = ["preferredList", "availableList"] + static values = { + mangaId: Number, + preferredSources: Array, + allSources: Array + } + + connect() { + this.initSortable() + } + + initSortable() { + new Sortable(this.preferredListTarget, { + animation: 150, + ghostClass: 'bg-gray-300', + onEnd: this.handleDragEnd.bind(this) + }) + } + + handleDragEnd() { + this.updatePreferredSources() + } + + addSource(event) { + const sourceId = parseInt(event.currentTarget.dataset.sourceId) + if (!this.preferredSourcesValue.includes(sourceId)) { + this.preferredSourcesValue = [...this.preferredSourcesValue, sourceId] + this.updateLists() + this.save() + } + } + + removeSource(event) { + const sourceId = parseInt(event.currentTarget.dataset.sourceId) + this.preferredSourcesValue = this.preferredSourcesValue.filter(id => id !== sourceId) + this.updateLists() + this.save() + } + + updatePreferredSources() { + this.preferredSourcesValue = Array.from(this.preferredListTarget.children).map(li => parseInt(li.dataset.id)) + this.save() + } + + updateLists() { + this.preferredListTarget.innerHTML = this.preferredSourcesValue + .map(id => this.allSourcesValue.find(s => s.id === id)) + .map(source => this.sourceTemplate(source, true)) + .join('') + + this.availableListTarget.innerHTML = this.allSourcesValue + .filter(source => !this.preferredSourcesValue.includes(source.id)) + .map(source => this.sourceTemplate(source, false)) + .join('') + + this.initSortable() + } + + sourceTemplate(source, isPreferred) { + return ` +