Skip to content
This repository was archived by the owner on May 7, 2021. It is now read-only.

Commit 01c5835

Browse files
committed
[WIP] コントリビューショングラフ
1 parent 7a4e506 commit 01c5835

File tree

5 files changed

+221
-0
lines changed

5 files changed

+221
-0
lines changed
+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import api from '@/api';
2+
import getHeader from '@/api/utils/get-header';
3+
4+
export default {
5+
async getContributionsCollection(sessionID) {
6+
let option = null;
7+
if (sessionID) {
8+
option = getHeader(sessionID);
9+
}
10+
const contributionsCollectionData = (await api.client.get('/contribution_collections', option)).data;
11+
return contributionsCollectionData;
12+
},
13+
};
+173
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
<template>
2+
<div class="container">
3+
<div class="wrapper">
4+
<div class="contributions-graph">
5+
<div class="user" id="user1">
6+
<div class="user-info">
7+
<dl>
8+
<dt>USER NAME</dt>
9+
<dd class="user-name">{{ contributionsCollection.contribution_collections[0].user.github_user_name }}</dd>
10+
<dt>TOTAL CONTRIBUTIONS</dt>
11+
<dd class="total-contributions">{{ contributionsCollection.contribution_collections[0].total_count }}</dd>
12+
</dl>
13+
</div>
14+
<div class="graph">
15+
<svg viewbox="0 0 25 300" width="25" height="300">
16+
<line x1=0 v-bind:y1="index * 5 + 2"
17+
v-bind:x2="item.count" v-bind:y2="index * 5 + 2"
18+
stroke-width="4" v-bind:opacity="item.count / 10"
19+
v-for="(item, index) in contributionsCollection.contribution_collections[0].days"
20+
v-bind:key="item.date"></line>
21+
</svg>
22+
</div>
23+
</div>
24+
<div class="user" id="user2">
25+
<div class="user-info">
26+
<dl>
27+
<dt>USER NAME</dt>
28+
<dd class="user-name">{{ contributionsCollection.contribution_collections[1].user.github_user_name }}</dd>
29+
<dt>TOTAL CONTRIBUTIONS</dt>
30+
<dd class="total-contributions">{{ contributionsCollection.contribution_collections[1].total_count }}</dd>
31+
</dl>
32+
</div>
33+
<div class="graph">
34+
<svg viewbox="0 0 25 300" width="25" height="300">
35+
<line x1=0 v-bind:y1="index * 5 + 2"
36+
v-bind:x2="item.count" v-bind:y2="index * 5 + 2"
37+
stroke-width="4" v-bind:opacity="item.count / 10"
38+
v-for="(item, index) in contributionsCollection.contribution_collections[1].days"
39+
v-bind:key="item.date"></line>
40+
</svg>
41+
</div>
42+
</div>
43+
<div class="user" id="user3">
44+
<div class="user-info">
45+
<dl>
46+
<dt>USER NAME</dt>
47+
<dd class="user-name">{{ contributionsCollection.contribution_collections[2].user.github_user_name }}</dd>
48+
<dt>TOTAL CONTRIBUTIONS</dt>
49+
<dd class="total-contributions">{{ contributionsCollection.contribution_collections[2].total_count }}</dd>
50+
</dl>
51+
</div>
52+
<svg viewbox="0 0 25 300" width="25" height="300">
53+
<line x1=0 v-bind:y1="index * 5 + 2"
54+
v-bind:x2="item.count" v-bind:y2="index * 5 + 2"
55+
stroke-width="4" v-bind:opacity="item.count / 10"
56+
v-for="(item, index) in contributionsCollection.contribution_collections[2].days"
57+
v-bind:key="item.date"></line>
58+
</svg>
59+
</div>
60+
</div>
61+
</div>
62+
</div>
63+
</div>
64+
</template>
65+
66+
<script>
67+
import { mapState, mapActions } from 'vuex';
68+
69+
export default {
70+
name: 'GitHubContributionsGraph',
71+
computed: mapState(
72+
'contributionsCollection', ['contributionsCollection'],
73+
),
74+
methods: {
75+
...mapActions(
76+
'contributionsCollection', ['getContributionsCollection'],
77+
),
78+
},
79+
async created() {
80+
this.getContributionsCollection();
81+
},
82+
};
83+
</script>
84+
85+
<style scoped>
86+
@keyframes rotate {
87+
from { transform: rotateY(0deg); }
88+
to { transform: rotateY(360deg); }
89+
}
90+
@keyframes inverse-rotate {
91+
from { transform: rotateY(0deg); }
92+
to { transform: rotateY(-360deg); }
93+
}
94+
@keyframes dash {
95+
to {
96+
stroke-dashoffset: 1000;
97+
}
98+
}
99+
.contributions-graph {
100+
animation: rotate 60s infinite linear;
101+
transform-style: preserve-3d;
102+
}
103+
.graph {
104+
transform-style: preserve-3d;
105+
border-top: 1px solid black;
106+
padding-top: 20px;
107+
}
108+
svg {
109+
width: 100%;
110+
transform-origin: top left;
111+
transform: scale(30, 2);
112+
}
113+
#user1 {
114+
transform: rotateY(0deg);
115+
stroke: rgb(24, 112, 228);
116+
}
117+
#user2 {
118+
transform: rotateY(120deg);
119+
stroke: rgb(0, 110, 24);
120+
}
121+
#user3 {
122+
transform: rotateY(240deg);
123+
stroke: rgb(212, 127, 0);
124+
}
125+
#user4 {
126+
transform: rotateY(270deg);
127+
}
128+
#user2 .user-info {
129+
animation-delay: -20s;
130+
}
131+
#user3 .user-info {
132+
animation-delay: -40s;
133+
}
134+
dl {
135+
letter-spacing: -1px;
136+
}
137+
dt {
138+
font-size: 0.7em;
139+
line-height: 1px;
140+
}
141+
.user-name {
142+
font-size: 3rem;
143+
}
144+
.total-contributions {
145+
font-size: 3rem;
146+
}
147+
.container {
148+
perspective: 1000px;
149+
}
150+
.wrapper {
151+
font-family: 'Barlow';
152+
font-weight: bold;
153+
height: 700px;
154+
155+
transform: rotateX(-20deg);
156+
transform-style: preserve-3d;
157+
width: 60%;
158+
margin: 50px auto;
159+
}
160+
.user {
161+
width: 50%;
162+
margin-left: 50%;
163+
position: absolute;
164+
transform-origin: 0;
165+
transform-style: preserve-3d;
166+
}
167+
.user-info {
168+
margin-left: 70%;
169+
animation: inverse-rotate 60s infinite linear;
170+
border-top: 1px solid black;
171+
padding-top: 20px;
172+
}
173+
</style>

src/store/index.js

+2
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import emailConfirmations from './modules/emailConfirmations';
1111
import memberIntroduction from './modules/memberIntroduction';
1212
import editUser from './modules/editUser';
1313
import invitation from './modules/invitation';
14+
import contributionsCollection from './modules/githubContributionsCollection';
1415

1516
Vue.use(Vuex);
1617

@@ -27,6 +28,7 @@ export default new Vuex.Store({
2728
memberIntroduction,
2829
editUser,
2930
invitation,
31+
contributionsCollection,
3032
},
3133
plugins: [
3234
createPersistedState({
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import ContributionsCollectionClient from '@/api/contributions_collection';
2+
3+
export default {
4+
namespaced: true,
5+
state: {
6+
contributionsCollection: null,
7+
},
8+
/* eslint-disable no-param-reassign */
9+
mutations: {
10+
setContributionsCollection(state, contributionsCollection) {
11+
state.contributionsCollection = contributionsCollection;
12+
},
13+
},
14+
/* eslint-enable no-param-reassign */
15+
actions: {
16+
async getContributionsCollection({ commit, dispatch }, sessionID) {
17+
try {
18+
commit('setContributionsCollection', await ContributionsCollectionClient.getContributionsCollection(sessionID));
19+
} catch (e) {
20+
dispatch('criticalError/createError', e, { root: true });
21+
}
22+
},
23+
},
24+
};

src/views/Home.vue

+9
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,13 @@
2323
</div>
2424
</section>
2525

26+
<section class="github-contributions-graph">
27+
<h2>GitHub Contributions Graph</h2>
28+
<div>
29+
<GitHubContributionsGraph/>
30+
</div>
31+
</section>
32+
2633
<footer>
2734
<div v-if="loggedIn">
2835
<router-link to="/editprofile">プロフィール編集</router-link>
@@ -42,6 +49,7 @@ import { mapGetters } from 'vuex';
4249
import AchievementsList from '@/components/AchievementsList.vue';
4350
import Logout from '@/components/Logout.vue';
4451
import publicMemberList from '@/components/PublicMemberList.vue';
52+
import GitHubContributionsGraph from '@/components/GitHubContributionsGraph.vue';
4553
4654
export default {
4755
name: 'home',
@@ -53,6 +61,7 @@ export default {
5361
AchievementsList,
5462
Logout,
5563
publicMemberList,
64+
GitHubContributionsGraph,
5665
},
5766
computed: {
5867
...mapGetters('session', ['loggedIn']),

0 commit comments

Comments
 (0)