mirror of https://github.com/bra1n/townsquare.git
finished adding night reminders to fabled
This commit is contained in:
parent
02d7002e34
commit
f10ff968a6
10
src/App.vue
10
src/App.vue
|
@ -148,10 +148,13 @@ body {
|
|||
body {
|
||||
font-size: 1.1em;
|
||||
}
|
||||
.player .night em {
|
||||
.night-order em {
|
||||
width: 30px;
|
||||
height: 30px;
|
||||
}
|
||||
.fabled .night-order.first span {
|
||||
left: 30px;
|
||||
}
|
||||
}
|
||||
|
||||
// Medium devices (tablets, less than 992px)
|
||||
|
@ -163,10 +166,13 @@ body {
|
|||
#controls svg {
|
||||
font-size: 20px;
|
||||
}
|
||||
.player .night em {
|
||||
.night-order em {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
}
|
||||
.fabled .night-order.first span {
|
||||
left: 20px;
|
||||
}
|
||||
#townsquare {
|
||||
padding: 10px;
|
||||
}
|
||||
|
|
|
@ -18,7 +18,7 @@
|
|||
<div class="life" @click="toggleStatus()"></div>
|
||||
|
||||
<div
|
||||
class="night first"
|
||||
class="night-order first"
|
||||
v-if="nightOrder.get(player).first && grimoire.isNightOrder"
|
||||
>
|
||||
<em>{{ nightOrder.get(player).first }}.</em>
|
||||
|
@ -27,7 +27,7 @@
|
|||
}}</span>
|
||||
</div>
|
||||
<div
|
||||
class="night other"
|
||||
class="night-order other"
|
||||
v-if="nightOrder.get(player).other && grimoire.isNightOrder"
|
||||
>
|
||||
<em>{{ nightOrder.get(player).other }}.</em>
|
||||
|
@ -676,137 +676,11 @@ li.move:not(.from) .player .overlay svg.move {
|
|||
}
|
||||
|
||||
/**** Night reminders ****/
|
||||
.player .night {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
z-index: 2;
|
||||
cursor: pointer;
|
||||
opacity: 1;
|
||||
transition: opacity 200ms;
|
||||
display: flex;
|
||||
top: 0;
|
||||
align-items: center;
|
||||
pointer-events: none;
|
||||
|
||||
&:after {
|
||||
content: " ";
|
||||
display: block;
|
||||
padding-top: 100%;
|
||||
}
|
||||
|
||||
#townsquare.public & {
|
||||
opacity: 0;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
&:hover ~ .token .ability {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
span {
|
||||
display: flex;
|
||||
position: absolute;
|
||||
padding: 5px 10px 5px 30px;
|
||||
width: 350px;
|
||||
z-index: 25;
|
||||
font-size: 70%;
|
||||
background: rgba(0, 0, 0, 0.5);
|
||||
border-radius: 10px;
|
||||
border: 3px solid black;
|
||||
filter: drop-shadow(0 4px 6px rgba(0, 0, 0, 0.5));
|
||||
text-align: left;
|
||||
align-items: center;
|
||||
opacity: 0;
|
||||
transition: opacity 200ms ease-in-out;
|
||||
|
||||
&:before {
|
||||
transform: rotate(-90deg);
|
||||
transform-origin: center top;
|
||||
left: -98px;
|
||||
top: 50%;
|
||||
font-size: 100%;
|
||||
position: absolute;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
width: 200px;
|
||||
}
|
||||
|
||||
&:after {
|
||||
content: " ";
|
||||
border: 10px solid transparent;
|
||||
width: 0;
|
||||
height: 0;
|
||||
position: absolute;
|
||||
}
|
||||
}
|
||||
|
||||
&.first span {
|
||||
right: 120%;
|
||||
background: linear-gradient(
|
||||
to right,
|
||||
$townsfolk 0%,
|
||||
rgba(0, 0, 0, 0.5) 20%
|
||||
);
|
||||
&:before {
|
||||
content: "First Night";
|
||||
}
|
||||
&:after {
|
||||
border-left-color: $townsfolk;
|
||||
margin-left: 3px;
|
||||
left: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
&.other span {
|
||||
left: 120%;
|
||||
background: linear-gradient(to right, $demon 0%, rgba(0, 0, 0, 0.5) 20%);
|
||||
&:before {
|
||||
content: "Other Nights";
|
||||
}
|
||||
&:after {
|
||||
right: 100%;
|
||||
margin-right: 3px;
|
||||
border-right-color: $demon;
|
||||
}
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
position: absolute;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 50%;
|
||||
border: 3px solid black;
|
||||
filter: drop-shadow(0 0 6px rgba(0, 0, 0, 0.5));
|
||||
font-weight: bold;
|
||||
opacity: 1;
|
||||
pointer-events: all;
|
||||
transition: opacity 200ms;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
&.first em {
|
||||
left: -10%;
|
||||
background: linear-gradient(180deg, rgba(0, 0, 0, 1) 0%, $townsfolk 100%);
|
||||
}
|
||||
|
||||
&.other em {
|
||||
right: -10%;
|
||||
background: linear-gradient(180deg, rgba(0, 0, 0, 1) 0%, $demon 100%);
|
||||
}
|
||||
|
||||
em:hover + span {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
#app.screenshot & {
|
||||
display: none;
|
||||
}
|
||||
.player .night-order {
|
||||
z-index: 3;
|
||||
}
|
||||
|
||||
.player.dead .night em {
|
||||
.player.dead .night-order em {
|
||||
color: #ddd;
|
||||
background: linear-gradient(180deg, rgba(0, 0, 0, 1) 0%, gray 100%);
|
||||
}
|
||||
|
|
|
@ -56,11 +56,29 @@
|
|||
</h3>
|
||||
<ul>
|
||||
<li
|
||||
v-for="(fabledRole, index) in fabled"
|
||||
v-for="(role, index) in fabled"
|
||||
:key="index"
|
||||
@click="removeFabled(index)"
|
||||
>
|
||||
<Token :role="fabledRole"></Token>
|
||||
<div
|
||||
class="night-order first"
|
||||
v-if="nightOrder.get(role).first && grimoire.isNightOrder"
|
||||
>
|
||||
<em>{{ nightOrder.get(role).first }}.</em>
|
||||
<span v-if="role.firstNightReminder">{{
|
||||
role.firstNightReminder
|
||||
}}</span>
|
||||
</div>
|
||||
<div
|
||||
class="night-order other"
|
||||
v-if="nightOrder.get(role).other && grimoire.isNightOrder"
|
||||
>
|
||||
<em>{{ nightOrder.get(role).other }}.</em>
|
||||
<span v-if="role.otherNightReminder">{{
|
||||
role.otherNightReminder
|
||||
}}</span>
|
||||
</div>
|
||||
<Token :role="role"></Token>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
@ -71,7 +89,7 @@
|
|||
</template>
|
||||
|
||||
<script>
|
||||
import { mapState } from "vuex";
|
||||
import { mapGetters, mapState } from "vuex";
|
||||
import Player from "./Player";
|
||||
import Token from "./Token";
|
||||
import ReminderModal from "./modals/ReminderModal";
|
||||
|
@ -85,6 +103,7 @@ export default {
|
|||
ReminderModal
|
||||
},
|
||||
computed: {
|
||||
...mapGetters({ nightOrder: "players/nightOrder" }),
|
||||
...mapState(["grimoire", "roles", "session"]),
|
||||
...mapState("players", ["players", "bluffs", "fabled"])
|
||||
},
|
||||
|
@ -194,6 +213,8 @@ export default {
|
|||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
@import "../vars.scss";
|
||||
|
||||
#townsquare {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
|
@ -288,7 +309,7 @@ export default {
|
|||
.life,
|
||||
.token,
|
||||
.shroud,
|
||||
.night {
|
||||
.night-order {
|
||||
transition-delay: ($i - 1) * 50ms;
|
||||
}
|
||||
|
||||
|
@ -409,6 +430,9 @@ export default {
|
|||
ul li {
|
||||
width: 0;
|
||||
height: 0;
|
||||
.night-order {
|
||||
opacity: 0;
|
||||
}
|
||||
.token {
|
||||
border-width: 0;
|
||||
}
|
||||
|
@ -424,6 +448,153 @@ export default {
|
|||
z-index: 2;
|
||||
}
|
||||
|
||||
/**** Night reminders ****/
|
||||
.night-order {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
cursor: pointer;
|
||||
opacity: 1;
|
||||
transition: opacity 200ms;
|
||||
display: flex;
|
||||
top: 0;
|
||||
align-items: center;
|
||||
pointer-events: none;
|
||||
|
||||
&:after {
|
||||
content: " ";
|
||||
display: block;
|
||||
padding-top: 100%;
|
||||
}
|
||||
|
||||
#townsquare.public & {
|
||||
opacity: 0;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
&:hover ~ .token .ability {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
span {
|
||||
display: flex;
|
||||
position: absolute;
|
||||
padding: 5px 10px 5px 30px;
|
||||
width: 350px;
|
||||
z-index: 25;
|
||||
font-size: 70%;
|
||||
background: rgba(0, 0, 0, 0.5);
|
||||
border-radius: 10px;
|
||||
border: 3px solid black;
|
||||
filter: drop-shadow(0 4px 6px rgba(0, 0, 0, 0.5));
|
||||
text-align: left;
|
||||
align-items: center;
|
||||
opacity: 0;
|
||||
transition: opacity 200ms ease-in-out;
|
||||
|
||||
&:before {
|
||||
transform: rotate(-90deg);
|
||||
transform-origin: center top;
|
||||
left: -98px;
|
||||
top: 50%;
|
||||
font-size: 100%;
|
||||
position: absolute;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
width: 200px;
|
||||
}
|
||||
|
||||
&:after {
|
||||
content: " ";
|
||||
border: 10px solid transparent;
|
||||
width: 0;
|
||||
height: 0;
|
||||
position: absolute;
|
||||
}
|
||||
}
|
||||
|
||||
&.first span {
|
||||
right: 120%;
|
||||
background: linear-gradient(
|
||||
to right,
|
||||
$townsfolk 0%,
|
||||
rgba(0, 0, 0, 0.5) 20%
|
||||
);
|
||||
&:before {
|
||||
content: "First Night";
|
||||
}
|
||||
&:after {
|
||||
border-left-color: $townsfolk;
|
||||
margin-left: 3px;
|
||||
left: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
&.other span {
|
||||
left: 120%;
|
||||
background: linear-gradient(to right, $demon 0%, rgba(0, 0, 0, 0.5) 20%);
|
||||
&:before {
|
||||
content: "Other Nights";
|
||||
}
|
||||
&:after {
|
||||
right: 100%;
|
||||
margin-right: 3px;
|
||||
border-right-color: $demon;
|
||||
}
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
position: absolute;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 50%;
|
||||
border: 3px solid black;
|
||||
filter: drop-shadow(0 0 6px rgba(0, 0, 0, 0.5));
|
||||
font-weight: bold;
|
||||
opacity: 1;
|
||||
pointer-events: all;
|
||||
transition: opacity 200ms;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
z-index: 3;
|
||||
}
|
||||
|
||||
&.first em {
|
||||
left: -10%;
|
||||
background: linear-gradient(180deg, rgba(0, 0, 0, 1) 0%, $townsfolk 100%);
|
||||
}
|
||||
|
||||
&.other em {
|
||||
right: -10%;
|
||||
background: linear-gradient(180deg, rgba(0, 0, 0, 1) 0%, $demon 100%);
|
||||
}
|
||||
|
||||
em:hover + span {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
#app.screenshot & {
|
||||
display: none;
|
||||
}
|
||||
|
||||
// adjustment for fabled
|
||||
.fabled &.first {
|
||||
span {
|
||||
right: auto;
|
||||
left: 40px;
|
||||
&:after {
|
||||
left: auto;
|
||||
right: 100%;
|
||||
margin-left: 0;
|
||||
margin-right: 3px;
|
||||
border-left-color: transparent;
|
||||
border-right-color: $townsfolk;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#townsquare:not(.spectator) .fabled ul li:hover .token:before {
|
||||
opacity: 1;
|
||||
}
|
||||
|
|
|
@ -24,7 +24,7 @@ const getters = {
|
|||
return Math.min(nonTravelers.length, 15);
|
||||
},
|
||||
// calculate a Map of player => night order
|
||||
nightOrder({ players }) {
|
||||
nightOrder({ players, fabled }) {
|
||||
const firstNight = [0];
|
||||
const otherNight = [0];
|
||||
players.forEach(({ role }) => {
|
||||
|
@ -35,6 +35,14 @@ const getters = {
|
|||
otherNight.push(role.otherNight);
|
||||
}
|
||||
});
|
||||
fabled.forEach(role => {
|
||||
if (role.firstNight && !firstNight.includes(role.firstNight)) {
|
||||
firstNight.push(role.firstNight);
|
||||
}
|
||||
if (role.otherNight && !otherNight.includes(role.otherNight)) {
|
||||
otherNight.push(role.otherNight);
|
||||
}
|
||||
});
|
||||
firstNight.sort((a, b) => a - b);
|
||||
otherNight.sort((a, b) => a - b);
|
||||
const nightOrder = new Map();
|
||||
|
@ -43,6 +51,11 @@ const getters = {
|
|||
const other = Math.max(otherNight.indexOf(player.role.otherNight), 0);
|
||||
nightOrder.set(player, { first, other });
|
||||
});
|
||||
fabled.forEach(role => {
|
||||
const first = Math.max(firstNight.indexOf(role.firstNight), 0);
|
||||
const other = Math.max(otherNight.indexOf(role.otherNight), 0);
|
||||
nightOrder.set(role, { first, other });
|
||||
});
|
||||
return nightOrder;
|
||||
}
|
||||
};
|
||||
|
|
|
@ -18,14 +18,14 @@ module.exports = store => {
|
|||
}
|
||||
if (localStorage.bluffs !== undefined) {
|
||||
JSON.parse(localStorage.bluffs).forEach((role, index) => {
|
||||
store.commit("setBluff", {
|
||||
store.commit("players/setBluff", {
|
||||
index,
|
||||
role: store.state.roles.get(role) || {}
|
||||
});
|
||||
});
|
||||
}
|
||||
if (localStorage.fabled !== undefined) {
|
||||
store.commit("setFabled", {
|
||||
store.commit("players/setFabled", {
|
||||
fabled: JSON.parse(localStorage.fabled).map(id =>
|
||||
store.state.fabled.get(id)
|
||||
)
|
||||
|
@ -88,13 +88,13 @@ module.exports = store => {
|
|||
localStorage.setItem("roles", JSON.stringify(payload));
|
||||
}
|
||||
break;
|
||||
case "setBluff":
|
||||
case "players/setBluff":
|
||||
localStorage.setItem(
|
||||
"bluffs",
|
||||
JSON.stringify(state.players.bluffs.map(({ id }) => id))
|
||||
);
|
||||
break;
|
||||
case "setFabled":
|
||||
case "players/setFabled":
|
||||
localStorage.setItem(
|
||||
"fabled",
|
||||
JSON.stringify(state.players.fabled.map(({ id }) => id))
|
||||
|
|
Loading…
Reference in New Issue