Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
pleroma-fe
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Incidents
Environments
Packages & Registries
Packages & Registries
Container Registry
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Hau Vo
pleroma-fe
Commits
d7b75ba0
Commit
d7b75ba0
authored
Jun 10, 2019
by
Shpuld Shpludson
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
combine the 2 poll components, do the footer
parent
6bc1d10a
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
298 additions
and
55 deletions
+298
-55
src/components/poll/poll.js
src/components/poll/poll.js
+90
-0
src/components/poll/poll.vue
src/components/poll/poll.vue
+114
-29
src/components/poll/poll_form/poll_form.vue
src/components/poll/poll_form/poll_form.vue
+2
-2
src/components/poll/poll_vote/poll_vote.vue
src/components/poll/poll_vote/poll_vote.vue
+88
-23
src/i18n/en.json
src/i18n/en.json
+4
-1
No files found.
src/components/poll/poll.js
0 → 100644
View file @
d7b75ba0
import
Timeago
from
'
../timeago/timeago.vue
'
export
default
{
name
:
'
Poll
'
,
props
:
[
'
poll
'
,
'
statusId
'
],
components
:
{
Timeago
},
data
()
{
return
{
loading
:
false
,
multipleChoices
:
[],
singleChoiceIndex
:
null
,
refreshInterval
:
null
}
},
created
()
{
this
.
refreshInterval
=
setTimeout
(
this
.
refreshPoll
,
30
*
1000
)
},
destroyed
()
{
clearTimeout
(
this
.
refreshInterval
)
},
computed
:
{
expired
()
{
return
Date
.
now
()
>
Date
.
parse
(
this
.
poll
.
expires_at
)
},
showResults
()
{
return
this
.
poll
.
voted
||
this
.
expired
},
totalVotesCount
()
{
return
this
.
poll
.
votes_count
},
expiresAt
()
{
return
Date
.
parse
(
this
.
poll
.
expires_at
).
toLocaleString
()
},
containerClass
()
{
return
{
loading
:
this
.
loading
}
},
choiceIndices
()
{
return
this
.
multipleChoices
.
map
((
entry
,
index
)
=>
index
)
.
filter
(
value
=>
typeof
value
===
'
number
'
)
},
isDisabled
()
{
const
noChoice
=
this
.
poll
.
multiple
?
this
.
choiceIndices
.
length
===
0
:
this
.
singleChoiceIndex
===
undefined
return
this
.
loading
||
noChoice
}
},
methods
:
{
refreshPoll
()
{
if
(
this
.
expired
)
return
this
.
fetchPoll
()
this
.
refreshInterval
=
setTimeout
(
this
.
refreshPoll
,
30
*
1000
)
},
percentageForOption
(
count
)
{
return
this
.
totalVotesCount
===
0
?
0
:
Math
.
round
((
count
+
5
)
/
(
this
.
totalVotesCount
+
10
)
*
100
)
},
resultTitle
(
option
)
{
return
`
${
option
.
votes_count
}
/
${
this
.
totalVotesCount
}
${
this
.
$t
(
'
polls.votes
'
)}
`
},
fetchPoll
()
{
this
.
$store
.
dispatch
(
'
refreshPoll
'
,
{
id
:
this
.
statusId
,
pollId
:
this
.
poll
.
id
})
},
optionId
(
index
)
{
return
`poll
${
this
.
poll
.
id
}
-
${
index
}
`
},
vote
()
{
this
.
loading
=
true
if
(
this
.
poll
.
multiple
)
{
if
(
this
.
choiceIndices
.
length
===
0
)
return
this
.
$store
.
dispatch
(
'
votePoll
'
,
{
id
:
this
.
statusId
,
pollId
:
this
.
poll
.
id
,
choices
:
this
.
choiceIndices
}
).
then
(
poll
=>
{
this
.
loading
=
false
})
}
else
{
if
(
this
.
singleChoiceIndex
===
undefined
)
return
this
.
$store
.
dispatch
(
'
votePoll
'
,
{
id
:
this
.
statusId
,
pollId
:
this
.
poll
.
id
,
choices
:
[
this
.
singleChoiceIndex
]
}
).
then
(
poll
=>
{
this
.
loading
=
false
})
}
}
}
}
\ No newline at end of file
src/components/poll/poll.vue
View file @
d7b75ba0
<
template
>
<poll-results
v-if=
"currentUserHasVoted"
:poll=
"poll"
:status-id=
"statusId"
/>
<poll-vote
v-else
:poll=
"poll"
:status-id=
"statusId"
/>
<div
class=
"poll"
v-bind:class=
"containerClass"
>
<div
class=
"poll-option"
v-for=
"(option, index) in poll.options"
:key=
"index"
>
<div
v-if=
"showResults"
:title=
"resultTitle(option)"
class=
"option-result"
>
<div
class=
"option-result-label"
>
<span
class=
"result-percentage"
>
{{
percentageForOption
(
option
.
votes_count
)
}}
%
</span>
<span>
{{
option
.
title
}}
</span>
</div>
<div
class=
"result-fill"
:style=
"
{ 'width': `${percentageForOption(option.votes_count)}%` }"
>
</div>
</div>
<div
v-else
>
<input
v-if=
"poll.multiple"
type=
"checkbox"
:id=
"optionId(index)"
:disabled=
"loading"
:value=
"option.title"
v-model=
"multipleChoices[index]"
>
<input
v-else
type=
"radio"
:id=
"optionId(index)"
:disabled=
"loading"
:value=
"index"
v-model=
"singleChoiceIndex"
>
<label
:for=
"optionId(index)"
>
{{
option
.
title
}}
</label>
</div>
</div>
<div
class=
"footer faint"
>
<button
v-if=
"!showResults"
class=
"btn btn-default poll-vote-button"
type=
"button"
@
click=
"vote"
:disabled=
"isDisabled"
>
{{
$t
(
'
polls.vote
'
)
}}
</button>
<div
class=
"total"
>
{{
totalVotesCount
}}
{{
$t
(
"
polls.votes
"
)
}}
·
</div>
<i18n
:path=
"expired ? 'polls.expired' : 'polls.expires_in'"
>
<Timeago
:time=
"this.poll.expires_at"
:auto-update=
"60"
/>
</i18n>
</div>
</div>
</
template
>
<
script
>
import
PollResults
from
'
./poll_results/poll_results.vue
'
import
PollVote
from
'
./poll_vote/poll_vote.vue
'
<
script
src=
"./poll.js"
></
script
>
export
default
{
name
:
'
Poll
'
,
props
:
[
'
poll
'
,
'
statusId
'
],
components
:
{
PollResults
,
PollVote
},
computed
:
{
currentUserHasVoted
()
{
return
this
.
poll
.
voted
},
voted
()
{
return
this
.
poll
.
voted
}
},
<
style
lang=
"scss"
>
@import
'../../_variables.scss'
;
.poll
{
.votes
{
display
:
flex
;
flex-direction
:
column
;
margin
:
0
0
0
.5em
;
}
.poll-option
{
margin
:
0
.5em
0
;
height
:
1
.5em
;
}
.option-result
{
height
:
100%
;
display
:
flex
;
flex-direction
:
row
;
position
:
relative
;
}
.option-result-label
{
display
:
flex
;
align-items
:
center
;
padding
:
0
.1em
0
.25em
;
z-index
:
1
;
}
.result-percentage
{
width
:
3
.5em
;
}
.result-fill
{
height
:
100%
;
position
:
absolute
;
background-color
:
$fallback--lightBg
;
background-color
:
var
(
--
faintLink
,
$fallback--lightBg
);
border-radius
:
$fallback--panelRadius
;
border-radius
:
var
(
--
panelRadius
,
$fallback--panelRadius
);
top
:
0
;
left
:
0
;
transition
:
width
0
.5s
;
}
input
{
width
:
3
.5em
;
}
.footer
{
display
:
flex
;
align-items
:
center
;
}
&
.loading
*
{
cursor
:
progress
;
}
.poll-vote-button
{
padding
:
0
0
.5em
;
margin-right
:
0
.5em
;
}
}
</
s
cript
>
</
s
tyle
>
src/components/poll/poll_form/poll_form.vue
View file @
d7b75ba0
...
...
@@ -66,8 +66,8 @@ export default {
data
:
()
=>
({
pollType
:
'
single
'
,
options
:
[
''
,
''
],
expiryAmount
:
1
,
expiryUnit
:
'
minute
s
'
,
expiryAmount
:
2
,
expiryUnit
:
'
hour
s
'
,
expiryUnits
:
[
'
minutes
'
,
'
hours
'
,
'
days
'
]
}
),
computed
:
{
...
...
src/components/poll/poll_vote/poll_vote.vue
View file @
d7b75ba0
<
template
>
<
form
class=
"poll-vote"
v-bind:class=
"containerClass"
>
<
div
class=
"poll-vote"
v-bind:class=
"containerClass"
>
<div
class=
"poll-choice"
v-for=
"(option, index) in poll.options"
:key=
"index"
>
<input
v-if=
"poll.multiple"
type=
"checkbox"
name=
"choice"
:id=
"index"
:disabled=
"loading"
:value=
"option.title"
v-model=
"multipleChoices[index]"
>
<input
v-else
type=
"radio"
name=
"choice"
:id=
"index"
:disabled=
"loading"
:value=
"index"
v-model=
"singleChoiceIndex"
>
<label
:for=
"index"
>
{{
option
.
title
}}
</label>
<div
v-if=
"showResults"
:title=
"resultTitle(option)"
>
<div
class=
"vote-label"
>
<span>
{{
percentageForOption
(
option
.
votes_count
)
}}
%
</span>
<span>
{{
option
.
title
}}
</span>
</div>
<div
class=
"fill"
:style=
"
{ 'width': `${percentageForOption(option.votes_count)}%` }">
</div>
</div>
<div
v-else
>
<input
v-if=
"poll.multiple"
type=
"checkbox"
:id=
"optionId(index)"
:disabled=
"loading"
:value=
"option.title"
v-model=
"multipleChoices[index]"
>
<input
v-else
type=
"radio"
:id=
"optionId(index)"
:disabled=
"loading"
:value=
"index"
v-model=
"singleChoiceIndex"
>
<label
:for=
"optionId(index)"
>
{{
option
.
title
}}
</label>
</div>
</div>
<div
class=
"footer"
>
<button
...
...
@@ -38,7 +45,7 @@
</button>
<Timeago
:time=
"this.poll.expires_at"
:auto-update=
"1"
></Timeago>
</div>
</
form
>
</
div
>
</
template
>
<
script
>
...
...
@@ -59,6 +66,12 @@ export default {
expired
()
{
return
new
Date
()
>
this
.
poll
.
expires_at
},
showResults
()
{
return
this
.
poll
.
voted
||
this
.
expired
},
totalVotesCount
()
{
return
this
.
poll
.
votes_count
},
timeleft
()
{
const
expiresAt
=
new
Date
(
this
.
poll
.
expires_at
)
return
expiresAt
...
...
@@ -80,6 +93,18 @@ export default {
}
},
methods
:
{
percentageForOption
(
count
)
{
return
this
.
totalVotesCount
===
0
?
0
:
Math
.
round
(
count
/
this
.
totalVotesCount
*
100
)
},
resultTitle
(
option
)
{
return
`
${
option
.
votes_count
}
/
${
this
.
totalVotesCount
}
${
this
.
$t
(
'
polls.votes
'
)}
`
},
fetchPoll
()
{
this
.
$store
.
dispatch
(
'
refreshPoll
'
,
{
id
:
this
.
statusId
,
pollId
:
this
.
poll
.
id
})
},
optionId
(
index
)
{
return
`poll
${
this
.
poll
.
id
}
-
${
index
}
`
},
vote
()
{
this
.
loading
=
true
if
(
this
.
poll
.
multiple
)
{
...
...
@@ -105,6 +130,46 @@ export default {
</
script
>
<
style
lang=
"scss"
>
@import
'../../../_variables.scss'
;
.poll-results
{
.votes
{
display
:
flex
;
flex-direction
:
column
;
margin
:
0
0
0
.5em
;
}
.poll-option
{
position
:
relative
;
display
:
flex
;
flex-direction
:
row
;
margin-top
:
0
.25em
;
margin-bottom
:
0
.25em
;
}
.fill
{
height
:
100%
;
position
:
absolute
;
background-color
:
$fallback--lightBg
;
background-color
:
var
(
--
faintLink
,
$fallback--lightBg
);
border-radius
:
$fallback--panelRadius
;
border-radius
:
var
(
--
panelRadius
,
$fallback--panelRadius
);
top
:
0
;
left
:
0
;
transition
:
width
0
.5s
;
}
.vote-label
{
display
:
flex
;
align-items
:
center
;
padding
:
0
.1em
0
.25em
;
z-index
:
1
;
span
{
margin-right
:
0
.5em
;
}
}
footer
{
display
:
flex
;
}
}
.poll-vote
{
margin
:
0
.7em
0
0
;
...
...
src/i18n/en.json
View file @
d7b75ba0
...
...
@@ -85,7 +85,10 @@
"votes"
:
"votes"
,
"vote"
:
"Vote"
,
"single_choice"
:
"Single choice"
,
"multiple_choices"
:
"Multiple choices"
"multiple_choices"
:
"Multiple choices"
,
"expiry"
:
"Poll age"
,
"expires_in"
:
"Ends in {0}"
,
"expired"
:
"Poll ended {0} ago"
},
"interactions"
:
{
"favs_repeats"
:
"Repeats and Favorites"
,
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment