diff --git a/src/frontend/src/components/CarRow.vue b/src/frontend/src/components/CarRow.vue index 1b5af09..f0d4d8d 100644 --- a/src/frontend/src/components/CarRow.vue +++ b/src/frontend/src/components/CarRow.vue @@ -51,4 +51,8 @@ tr:hover > * { .rotated { transform: rotate(90deg); } + +tr { + cursor: pointer; +} diff --git a/src/frontend/src/components/CarTable.vue b/src/frontend/src/components/CarTable.vue index 27ce24f..c928102 100644 --- a/src/frontend/src/components/CarTable.vue +++ b/src/frontend/src/components/CarTable.vue @@ -2,8 +2,9 @@ import CarRowGroup from './CarRowGroup.vue'; import LeaveCarModal from './LeaveCarModal.vue'; import Loading from './LoadingWheel.vue'; - -const eventStore = useEventStore(); +import CaretUp from './icons/CaretUp.vue'; +import CaretDown from './icons/CaretDown.vue'; +import BlankIcon from './icons/BlankIcon.vue'; @@ -38,13 +50,22 @@ import { defineComponent } from 'vue'; import { useEventStore } from '@/stores/events'; import { usePopupStore } from '@/stores/popup'; +interface SortingOrder { + fieldName: string; + asc: boolean; +} + export default defineComponent({ props: { eventId: Number }, data() { return { - loading: true + loading: true, + sortingOrder: { + fieldName: 'driver', + asc: true + } as SortingOrder }; }, methods: { @@ -67,10 +88,47 @@ export default defineComponent({ const popupStore = usePopupStore(); popupStore.addPopup(PopupType.Danger, 'Failed to Get Cars. An unknown error occured.'); } + }, + changeSort(field: string) { + if (this.sortingOrder.fieldName === field) { + this.sortingOrder.asc = !this.sortingOrder.asc; + } else { + this.sortingOrder.fieldName = field; + this.sortingOrder.asc = true; + } } }, created() { this.fetchCarData(); // Fetch card data when the component is created + }, + computed: { + sortedCars() { + const eventStore = useEventStore(); + const { fieldName, asc } = this.sortingOrder; + return [...(eventStore.selectedEventCars || [])].sort((a, b) => { + const compare = (valA: string | number, valB: string | number) => { + if (valA < valB) return asc ? -1 : 1; + if (valA > valB) return asc ? 1 : -1; + return 0; + }; + + switch (fieldName) { + case 'driver': + return compare(a.driver.name, b.driver.name); + case 'capacity': + return compare(a.riders.length, b.riders.length); + case 'departure': + return compare( + new Date(a.departureTime).getTime(), + new Date(b.departureTime).getTime() + ); + case 'return': + return compare(new Date(a.returnTime).getTime(), new Date(b.returnTime).getTime()); + default: + return 0; + } + }); + } } }); @@ -97,4 +155,8 @@ export default defineComponent({ opacity: 0; transform: translateY(-30px); } + +th { + cursor: pointer; +} diff --git a/src/frontend/src/components/icons/BlankIcon.vue b/src/frontend/src/components/icons/BlankIcon.vue new file mode 100644 index 0000000..ccb44fd --- /dev/null +++ b/src/frontend/src/components/icons/BlankIcon.vue @@ -0,0 +1,10 @@ + diff --git a/src/frontend/src/components/icons/CaretUp.vue b/src/frontend/src/components/icons/CaretUp.vue new file mode 100644 index 0000000..4ea638f --- /dev/null +++ b/src/frontend/src/components/icons/CaretUp.vue @@ -0,0 +1,14 @@ +