mlpcardgame/src/components/DeckBuilder/CardPicker.vue

99 lines
1.9 KiB
Vue

<template>
<section class="cardpicker" :style="grid">
<article
@click="() => _picked(card)"
:class="cardClass(card)"
v-for="(card, i) in cards"
:key="i + card.data.ID"
>
<CardImage :id="card.data.ID" />
</article>
</section>
</template>
<style lang="scss" scoped>
$padding: 10px;
.cardpicker {
max-height: 100%;
display: grid;
gap: $padding;
padding: $padding;
place-items: stretch;
}
.ccgcard {
display: flex;
align-items: center;
transition: 100ms all;
cursor: pointer;
img {
max-width: 100%;
max-height: 100%;
transition: box-shadow 60ms;
}
&.available:hover img {
box-shadow: 0 0 15px 5px rgba(200, 210, 255, 0.5);
}
&.disabled {
opacity: 0.5;
cursor: not-allowed;
}
}
</style>
<script lang="ts">
import { Component, Vue, Prop } from "vue-property-decorator";
import { Card, CardSlot, cardImageURL } from "@/mlpccg";
import CardImage from "@/components/Cards/CardImage.vue";
@Component({
components: {
CardImage
}
})
export default class CardPicker extends Vue {
@Prop()
public cards!: CardSlot[];
@Prop({ default: 2 })
public rows!: number;
@Prop({ default: 5 })
public columns!: number;
@Prop({ default: false })
public ignoreLimit!: boolean;
private get grid() {
return {
gridTemplateRows: "1fr ".repeat(this.rows).trim(),
gridTemplateColumns: "1fr ".repeat(this.columns).trim()
};
}
private imageURL(id: string) {
return cardImageURL(id);
}
private _picked(card: CardSlot) {
if (this.isAvailable(card)) {
this.$emit("picked", card.data);
}
}
private cardClass(card: CardSlot) {
const available = this.isAvailable(card);
return {
ccgcard: true,
available,
disabled: !available
};
}
private isAvailable(card: CardSlot) {
return card.limit == 0 || card.howmany < card.limit || this.ignoreLimit;
}
}
</script>