Commit 48c253ec authored by Clement Ho's avatar Clement Ho

Add vue service

parent e890c45f
export default {
name: 'AssigneeTitle',
props: {
numberOfAssignees: { type: Number, required: true },
},
computed: {
hasMultipleAssignees() {
return this.numberOfAssignees > 1;
}
},
template: `
<div class="title hide-collapsed">
<template v-if="hasMultipleAssignees">
{{numberOfAssignees}} Assignees
</template>
<template v-else>
Assignee
</template>
<i aria-hidden="true" class="fa fa-spinner fa-spin block-loading" style="display: none;"></i>
<a class="edit-link pull-right" href="#">Edit</a>
</div>
`,
};
import ShowMoreAssignees from './show_more_assignees';
export default {
name: 'MultipleAssignees',
data() {
return {
showMore: false
}
},
props: {
assignees: { type: Object, required: true }
},
computed: {
shouldShowMoreAssignees() {
return this.assignees.users.length > 5;
},
numberOfHiddenAssignees() {
return this.showMore ? 0 : this.assignees.users.length - 5;
},
toggleShowMore() {
return function() {
this.showMore = !this.showMore;
}.bind(this);
}
},
components: {
'show-more-assignees': ShowMoreAssignees,
},
template: `
<div class="value hide-collapsed">
<div class="hide-collapsed">
<div class="user-list">
<div class="user-item" v-for="(user, index) in assignees.users" v-if="showMore || (index < 5 && !showMore)">
<a class="user-link has-tooltip" data-placement="bottom" title="" :href="user.url" :data-title="user.name">
<img width="32" class="avatar avatar-inline s32 " alt="" :src="user.avatar_url">
</a>
</div>
</div>
<show-more-assignees v-if="shouldShowMoreAssignees" :hiddenAssignees="numberOfHiddenAssignees" :toggle="toggleShowMore" />
</div>
</div>
`,
};
export default {
name: 'NoAssignee',
props: {
assignees: { type: Object, required: true },
service: { type: Object, required: true },
},
methods: {
assignSelf() {
// const options = {
// }
// this.service.save(options);
this.assignees.addUser();
}
},
template: `
<div class="value hide-collapsed">
<span class="assign-yourself no-value">
No assignee -
<button type="button" class="btn-link" @click="assignSelf">
assign yourself
</button>
</span>
</div>
`,
};
export default {
name: 'ShowMoreAssignees',
props: {
hiddenAssignees: { type: Number, required: true },
toggle: { type: Function, required: true }
},
template: `
<div class="user-list-more">
<button type="button" class="btn-link" @click="toggle">
<template v-if="hiddenAssignees > 0">
+ {{hiddenAssignees}} more
</template>
<template v-else>
- show less
</template>
</button>
</div>
`,
};
export default {
name: 'SingleAssignee',
props: {
user: { type: Object, required: true },
},
template: `
<div class="value hide-collapsed">
<a class="author_link bold" :href="user.url">
<img width="32" class="avatar avatar-inline s32" alt="" :src="user.avatar_url">
<span class="author">{{user.name}}</span>
<span class="username">@{{user.username}}</span>
</a>
</div>
`,
};
import Vue from 'vue';
import AssigneeTitle from './components/assignee_title';
import NoAssignee from './components/no_assignee';
import SingleAssignee from './components/single_assignee';
import MultipleAssignees from './components/multiple_assignees';
import SidebarAssigneesService from './services/sidebar_assignees_service';
import SidebarAssigneesStore from './stores/sidebar_assignees_store';
const sidebarAssigneesOptions = () => ({
el: '#js-vue-sidebar-assignees',
name: 'SidebarAssignees',
data() {
const selector = this.$options.el;
const element = document.querySelector(selector);
const path = element.dataset.path;
const service = new SidebarAssigneesService(path);
const assignees = new SidebarAssigneesStore();
return {
assignees,
service,
};
},
components: {
'no-assignee': NoAssignee,
'single-assignee': SingleAssignee,
'multiple-assignees': MultipleAssignees,
'assignee-title': AssigneeTitle,
},
template: `
<div class="sidebar-assignees">
<assignee-title :numberOfAssignees="assignees.users.length" />
<no-assignee v-if="assignees.users.length === 0" :service="service" :assignees="assignees" />
<single-assignee v-else-if="assignees.users.length === 1" :user="assignees.users[0]" />
<multiple-assignees v-else :assignees="assignees" />
</div>
`,
});
document.addEventListener('DOMContentLoaded', () => {
window.gl.sidebarAssigneesOptions = new Vue(sidebarAssigneesOptions());
});
import Vue from 'vue';
import VueResource from 'vue-resource';
Vue.use(VueResource);
export default class SidebarAssigneesService {
constructor(path) {
this.sidebarAssigneeResource = Vue.resource(path);
}
save(data) {
return this.sidebarAssigneeResource.save(data);
}
}
export default class SidebarAssigneesStore {
constructor() {
this.users = [{
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username',
}, {
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username1',
}, {
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username2',
}, {
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username3',
}, {
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username4',
}, {
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username5',
}];
this.users = [];
}
addUser() {
this.users.push({
avatar_url: 'http://www.gravatar.com/avatar/7e65550957227bd38fe2d7fbc6fd2f7b?s=80&d=identicon',
url: '/user4',
name: 'test',
username: 'username6',
});
}
removeUser(username) {
this.users = this.users.filter((u) => u.username !== username);
}
}
\ No newline at end of file
......@@ -90,10 +90,15 @@
}
.right-sidebar {
a {
a,
.btn-link {
color: inherit;
}
.btn-link {
outline: none;
}
.issuable-header-text {
margin-top: 7px;
}
......@@ -237,6 +242,10 @@
margin-left: 0;
}
.assignee .user-list .avatar {
margin: 0;
}
.username {
display: block;
margin-top: 4px;
......@@ -368,14 +377,17 @@
margin: -5px;
}
.user-list {
display: flex;
display: -webkit-flex;
flex-wrap: wrap;
-webkit-flex-wrap: wrap;
}
.participants-author {
display: inline-block;
padding: 5px;
&:nth-of-type(7n) {
padding-right: 0;
}
.author_link {
display: block;
}
......@@ -385,13 +397,44 @@
}
}
.participants-more {
.user-item {
display: inline-block;
padding: 5px;
flex-basis: 20%;
-webkit-flex-basis: 20%;
.user-link {
display: inline-block;
}
}
.participants-author:nth-of-type(7n) {
padding-right: 0;
}
.participants-more,
.user-list-more {
margin-top: 5px;
margin-left: 5px;
a {
a,
.btn-link {
color: $gl-text-color-secondary;
}
.btn-link {
outline: none;
padding: 0;
}
.btn-link:hover {
@extend a:hover;
text-decoration: none;
}
.btn-link:focus {
text-decoration: none;
}
}
.issuable-form-padding-top {
......
......@@ -3,8 +3,6 @@
= page_specific_javascript_bundle_tag('common_vue')
= page_specific_javascript_bundle_tag('issuable')
- puts issuable.is_a?(Issue)
%aside.right-sidebar.js-right-sidebar{ data: { "offset-top" => "101", "spy" => "affix" }, class: sidebar_gutter_collapsed_class, 'aria-live' => 'polite' }
.issuable-sidebar
- can_edit_issuable = can?(current_user, :"admin_#{issuable.to_ability_name}", @project)
......@@ -25,35 +23,41 @@
= form_for [@project.namespace.becomes(Namespace), @project, issuable], remote: true, format: :json, html: { class: 'issuable-context-form inline-update js-issuable-update' } do |f|
.block.assignee
#js-vue-sidebar-assignees
- content_for :page_specific_javascripts do
= page_specific_javascript_bundle_tag('vue_sidebar_assignees')
-# .sidebar-collapsed-icon.sidebar-collapsed-user{ data: { toggle: "tooltip", placement: "left", container: "body" }, title: (issuable.assignee.name if issuable.assignee) }
-# - if issuable.assignee
-# = link_to_member(@project, issuable.assignee, size: 24)
-# - else
-# = icon('user', 'aria-hidden': 'true')
-# .title.hide-collapsed
-# Assignee
-# = icon('spinner spin', class: 'block-loading', 'aria-hidden': 'true')
-# - if can_edit_issuable
-# = link_to 'Edit', '#', class: 'edit-link pull-right'
-# .value.hide-collapsed
-# - if issuable.assignee
-# = link_to_member(@project, issuable.assignee, size: 32, extra_class: 'bold') do
-# - if issuable.instance_of?(MergeRequest) && !issuable.can_be_merged_by?(issuable.assignee)
-# %span.pull-right.cannot-be-merged{ data: { toggle: 'tooltip', placement: 'left' }, title: 'Not allowed to merge' }
-# = icon('exclamation-triangle', 'aria-hidden': 'true')
-# %span.username
-# = issuable.assignee.to_reference
-# - else
-# %span.assign-yourself.no-value
-# No assignee
-# - if can_edit_issuable
-# \-
-# %a.js-assign-yourself{ href: '#' }
-# assign yourself
- if issuable.instance_of?(Issue)
#js-vue-sidebar-assignees{ data: { path: issuable_json_path(issuable) }}
.title.hide-collapsed
Assignee
= icon('spinner spin', class: 'block-loading', 'aria-hidden': 'true')
- if can_edit_issuable
= link_to 'Edit', '#', class: 'edit-link pull-right'
- content_for :page_specific_javascripts do
= page_specific_javascript_bundle_tag('vue_sidebar_assignees')
- else
.sidebar-collapsed-icon.sidebar-collapsed-user{ data: { toggle: "tooltip", placement: "left", container: "body" }, title: (issuable.assignee.name if issuable.assignee) }
- if issuable.assignee
= link_to_member(@project, issuable.assignee, size: 24)
- else
= icon('user', 'aria-hidden': 'true')
.title.hide-collapsed
Assignee
= icon('spinner spin', class: 'block-loading', 'aria-hidden': 'true')
- if can_edit_issuable
= link_to 'Edit', '#', class: 'edit-link pull-right'
.value.hide-collapsed
- if issuable.assignee
= link_to_member(@project, issuable.assignee, size: 32, extra_class: 'bold') do
- if issuable.instance_of?(MergeRequest) && !issuable.can_be_merged_by?(issuable.assignee)
%span.pull-right.cannot-be-merged{ data: { toggle: 'tooltip', placement: 'left' }, title: 'Not allowed to merge' }
= icon('exclamation-triangle', 'aria-hidden': 'true')
%span.username
= issuable.assignee.to_reference
- else
%span.assign-yourself.no-value
No assignee
- if can_edit_issuable
\-
%a.js-assign-yourself{ href: '#' }
assign yourself
.selectbox.hide-collapsed
= f.hidden_field 'assignee_id', value: issuable.assignee_id, id: 'issue_assignee_id'
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment