diff options
5 files changed, 175 insertions, 138 deletions
diff --git a/app/assets/javascripts/boards/components/board.js b/app/assets/javascripts/boards/components/board.js index 35b3205cca7..98d64cd6870 100644 --- a/app/assets/javascripts/boards/components/board.js +++ b/app/assets/javascripts/boards/components/board.js @@ -1,5 +1,6 @@ /* eslint-disable comma-dangle, space-before-function-paren, one-var */ /* global Sortable */ +import boardList from './board_list'; import Vue from 'vue'; import boardBlankState from './board_blank_state'; @@ -16,7 +17,7 @@ require('./board_list'); gl.issueBoards.Board = Vue.extend({ template: '#js-board-template', components: { - 'board-list': gl.issueBoards.BoardList, + boardList, 'board-delete': gl.issueBoards.BoardDelete, boardBlankState, }, diff --git a/app/assets/javascripts/boards/components/board_list.js b/app/assets/javascripts/boards/components/board_list.js index 86e6c26e570..f833cede8e9 100644 --- a/app/assets/javascripts/boards/components/board_list.js +++ b/app/assets/javascripts/boards/components/board_list.js @@ -1,131 +1,192 @@ -/* eslint-disable comma-dangle, space-before-function-paren, max-len */ /* global Sortable */ import Vue from 'vue'; import boardNewIssue from './board_new_issue'; import boardCard from './board_card'; +import eventHub from '../eventhub'; -(() => { - const Store = gl.issueBoards.BoardsStore; +const Store = gl.issueBoards.BoardsStore; - window.gl = window.gl || {}; - window.gl.issueBoards = window.gl.issueBoards || {}; - - gl.issueBoards.BoardList = Vue.extend({ - template: '#js-board-list-template', - components: { - boardCard, - boardNewIssue, +export default { + template: ` + <div class="board-list-component"> + <div + class="board-list-loading text-center" + v-if="loading"> + <i class="fa fa-spinner fa-spin"></i> + </div> + <board-new-issue + :list="list" + v-if="list.type !== 'closed' && showIssueForm"/> + <ul + class="board-list" + v-show="!loading" + ref="list" + :data-board="list.id" + :class="{ 'is-smaller': showIssueForm }"> + <board-card + v-for="(issue, index) in issues" + ref="issue" + :index="index" + :list="list" + :issue="issue" + :issue-link-base="issueLinkBase" + :root-path="rootPath" + :disabled="disabled" + :key="issue.id" /> + <li + class="board-list-count text-center" + v-if="showCount" + data-id="-1"> + <i + class="fa fa-spinner fa-spin" + v-show="list.loadingMore"> + </i> + <span v-if="list.issues.length === list.issuesSize"> + Show all issues + </span> + <span v-else> + Showing {{ list.issues.length }} of {{ list.issuesSize }} issues + </span> + </li> + </ul> + </div> + `, + components: { + boardCard, + boardNewIssue, + }, + props: { + disabled: { + type: Boolean, + required: true, }, - props: { - disabled: Boolean, - list: Object, - issues: Array, - loading: Boolean, - issueLinkBase: String, - rootPath: String, + list: { + type: Object, + required: true, }, - data () { - return { - scrollOffset: 250, - filters: Store.state.filters, - showCount: false, - showIssueForm: false - }; + issues: { + type: Array, + required: true, }, - watch: { - filters: { - handler () { - this.list.loadingMore = false; - this.$refs.list.scrollTop = 0; - }, - deep: true + loading: { + type: Boolean, + required: true, + }, + issueLinkBase: { + type: String, + required: true, + }, + rootPath: { + type: String, + required: true, + }, + }, + data() { + return { + scrollOffset: 250, + filters: Store.state.filters, + showCount: false, + showIssueForm: false, + }; + }, + watch: { + filters: { + handler() { + this.list.loadingMore = false; + this.$refs.list.scrollTop = 0; }, - issues () { - this.$nextTick(() => { - if (this.scrollHeight() <= this.listHeight() && this.list.issuesSize > this.list.issues.length) { - this.list.page += 1; - this.list.getIssues(false); - } + deep: true, + }, + issues() { + this.$nextTick(() => { + if (this.scrollHeight() <= this.listHeight() && + this.list.issuesSize > this.list.issues.length) { + this.list.page += 1; + this.list.getIssues(false); + } + + if (this.scrollHeight() > Math.ceil(this.listHeight())) { + this.showCount = true; + } else { + this.showCount = false; + } + }); + }, + }, + methods: { + listHeight() { + return this.$refs.list.getBoundingClientRect().height; + }, + scrollHeight() { + return this.$refs.list.scrollHeight; + }, + scrollTop() { + return this.$refs.list.scrollTop + this.listHeight(); + }, + loadNextPage() { + const getIssues = this.list.nextPage(); - if (this.scrollHeight() > Math.ceil(this.listHeight())) { - this.showCount = true; - } else { - this.showCount = false; - } + if (getIssues) { + this.list.loadingMore = true; + getIssues.then(() => { + this.list.loadingMore = false; }); } }, - methods: { - listHeight () { - return this.$refs.list.getBoundingClientRect().height; - }, - scrollHeight () { - return this.$refs.list.scrollHeight; - }, - scrollTop () { - return this.$refs.list.scrollTop + this.listHeight(); - }, - loadNextPage () { - const getIssues = this.list.nextPage(); - - if (getIssues) { - this.list.loadingMore = true; - getIssues.then(() => { - this.list.loadingMore = false; - }); - } - }, - toggleForm() { - this.showIssueForm = !this.showIssueForm; - }, + toggleForm() { + this.showIssueForm = !this.showIssueForm; }, - created() { - gl.IssueBoardsApp.$on(`hide-issue-form-${this.list.id}`, this.toggleForm); + onScroll() { + if ((this.scrollTop() > this.scrollHeight() - this.scrollOffset) && !this.list.loadingMore) { + this.loadNextPage(); + } }, - mounted () { - const options = gl.issueBoards.getBoardSortableDefaultOptions({ - scroll: document.querySelectorAll('.boards-list')[0], - group: 'issues', - disabled: this.disabled, - filter: '.board-list-count, .is-disabled', - dataIdAttr: 'data-issue-id', - onStart: (e) => { - const card = this.$refs.issue[e.oldIndex]; + }, + created() { + eventHub.$on(`hide-issue-form-${this.list.id}`, this.toggleForm); + }, + mounted() { + const options = gl.issueBoards.getBoardSortableDefaultOptions({ + scroll: document.querySelectorAll('.boards-list')[0], + group: 'issues', + disabled: this.disabled, + filter: '.board-list-count, .is-disabled', + dataIdAttr: 'data-issue-id', + onStart: (e) => { + const card = this.$refs.issue[e.oldIndex]; - card.showDetail = false; - Store.moving.list = card.list; - Store.moving.issue = Store.moving.list.findIssue(+e.item.dataset.issueId); + card.showDetail = false; + Store.moving.list = card.list; + Store.moving.issue = Store.moving.list.findIssue(+e.item.dataset.issueId); - gl.issueBoards.onStart(); - }, - onAdd: (e) => { - gl.issueBoards.BoardsStore.moveIssueToList(Store.moving.list, this.list, Store.moving.issue, e.newIndex); + gl.issueBoards.onStart(); + }, + onAdd: (e) => { + gl.issueBoards.BoardsStore + .moveIssueToList(Store.moving.list, this.list, Store.moving.issue, e.newIndex); - this.$nextTick(() => { - e.item.remove(); - }); - }, - onUpdate: (e) => { - const sortedArray = this.sortable.toArray().filter(id => id !== '-1'); - gl.issueBoards.BoardsStore.moveIssueInList(this.list, Store.moving.issue, e.oldIndex, e.newIndex, sortedArray); - }, - onMove(e) { - return !e.related.classList.contains('board-list-count'); - } - }); + this.$nextTick(() => { + e.item.remove(); + }); + }, + onUpdate: (e) => { + const sortedArray = this.sortable.toArray().filter(id => id !== '-1'); + gl.issueBoards.BoardsStore + .moveIssueInList(this.list, Store.moving.issue, e.oldIndex, e.newIndex, sortedArray); + }, + onMove(e) { + return !e.related.classList.contains('board-list-count'); + }, + }); - this.sortable = Sortable.create(this.$refs.list, options); + this.sortable = Sortable.create(this.$refs.list, options); - // Scroll event on list to load more - this.$refs.list.onscroll = () => { - if ((this.scrollTop() > this.scrollHeight() - this.scrollOffset) && !this.list.loadingMore) { - this.loadNextPage(); - } - }; - }, - beforeDestroy() { - gl.IssueBoardsApp.$off(`hide-issue-form-${this.list.id}`, this.toggleForm); - }, - }); -})(); + // Scroll event on list to load more + this.$refs.list.addEventListener('scroll', this.onScroll); + }, + beforeDestroy() { + eventHub.$off(`hide-issue-form-${this.list.id}`, this.toggleForm); + this.$refs.list.removeEventListener('scroll', this.onScroll); + }, +}; diff --git a/app/assets/javascripts/boards/components/board_new_issue.js b/app/assets/javascripts/boards/components/board_new_issue.js index b88f59dd6d4..0fa85b6fe14 100644 --- a/app/assets/javascripts/boards/components/board_new_issue.js +++ b/app/assets/javascripts/boards/components/board_new_issue.js @@ -1,4 +1,6 @@ /* global ListIssue */ +import eventHub from '../eventhub'; + const Store = gl.issueBoards.BoardsStore; export default { @@ -49,7 +51,7 @@ export default { }, cancel() { this.title = ''; - gl.IssueBoardsApp.$emit(`hide-issue-form-${this.list.id}`); + eventHub.$emit(`hide-issue-form-${this.list.id}`); }, }, mounted() { diff --git a/app/views/projects/boards/_show.html.haml b/app/views/projects/boards/_show.html.haml index d93eac63bd3..7ca0ec8ed2b 100644 --- a/app/views/projects/boards/_show.html.haml +++ b/app/views/projects/boards/_show.html.haml @@ -8,7 +8,6 @@ = page_specific_javascript_bundle_tag('boards') %script#js-board-template{ type: "text/x-template" }= render "projects/boards/components/board" - %script#js-board-list-template{ type: "text/x-template" }= render "projects/boards/components/board_list" %script#js-board-modal-filter{ type: "text/x-template" }= render "shared/issuable/search_bar", type: :boards_modal = render "projects/issues/head" diff --git a/app/views/projects/boards/components/_board_list.html.haml b/app/views/projects/boards/components/_board_list.html.haml deleted file mode 100644 index 4a0b2110601..00000000000 --- a/app/views/projects/boards/components/_board_list.html.haml +++ /dev/null @@ -1,26 +0,0 @@ -.board-list-component - .board-list-loading.text-center{ "v-if" => "loading" } - = icon("spinner spin") - - if can? current_user, :create_issue, @project - %board-new-issue{ ":list" => "list", - "v-if" => 'list.type !== "closed" && showIssueForm' } - %ul.board-list{ "ref" => "list", - "v-show" => "!loading", - ":data-board" => "list.id", - ":class" => '{ "is-smaller": showIssueForm }' } - %board-card{ "v-for" => "(issue, index) in issues", - "ref" => "issue", - ":index" => "index", - ":list" => "list", - ":issue" => "issue", - ":issue-link-base" => "issueLinkBase", - ":root-path" => "rootPath", - ":disabled" => "disabled", - ":key" => "issue.id" } - %li.board-list-count.text-center{ "v-if" => "showCount", - "data-issue-id" => "-1" } - = icon("spinner spin", "v-show" => "list.loadingMore" ) - %span{ "v-if" => "list.issues.length === list.issuesSize" } - Showing all issues - %span{ "v-else" => true } - Showing {{ list.issues.length }} of {{ list.issuesSize }} issues |