Skip to content

Commit

Permalink
♻️ [so] refactor schoolingOverview.vue to composition API
Browse files Browse the repository at this point in the history
  • Loading branch information
jxn-30 committed Aug 25, 2023
1 parent 31ad88f commit 0626752
Show file tree
Hide file tree
Showing 6 changed files with 205 additions and 266 deletions.
27 changes: 16 additions & 11 deletions src/components/EnhancedTable.vue
Original file line number Diff line number Diff line change
Expand Up @@ -24,18 +24,18 @@
<thead>
<tr>
<th
v-for="item in columns"
:key="item.key"
v-bind="item.attrs"
:class="{ noSort: item.noSort }"
@click="!item.noSort && $emit('sort', item.key)"
:title="titleAttr(item)"
v-for="column in columns"
:key="column.key"
v-bind="column.attrs"
:class="{ noSort: column.noSort }"
@click="!column.noSort && $emit('sort', column.key)"
:title="titleAttr(column)"
>
{{ item.title }}
{{ colTitle(column) }}
<font-awesome-icon
v-if="!item.noSort"
v-if="!column.noSort"
class="pull-right"
:icon="item.key === sort ? sortIcon : faSort"
:icon="column.key === sort ? sortIcon : faSort"
></font-awesome-icon>
</th>
</tr>
Expand Down Expand Up @@ -73,7 +73,8 @@ const showHead = ref<boolean>(true);
const props = withDefaults(
defineProps<{
columns: Column<ColumnKey>[];
columns: Column<ColumnKey, boolean>[];
columnTranslations: Record<ColumnKey, string>;
sort?: ColumnKey;
sortDir?: 'asc' | 'desc';
noSearch?: boolean;
Expand All @@ -83,6 +84,7 @@ const props = withDefaults(
noBody?: boolean;
}>(),
{
columnTranslations: () => {},

This comment has been minimized.

Copy link
@Cr4zyc4k3

Cr4zyc4k3 Sep 21, 2023

Collaborator

Empty function?

This comment has been minimized.

Copy link
@jxn-30

jxn-30 Sep 21, 2023

Author Member

has been fixed in ef51959

sort: '',
sortDir: 'asc',
noSearch: false,
Expand All @@ -101,7 +103,10 @@ const sortIcon = computed(() =>
props.sortDir === 'asc' ? faSortDown : faSortUp
);
const titleAttr = (col: Column<ColumnKey>) => col.titleAttr ?? col.title;
const colTitle = (col: Column<ColumnKey, boolean>) =>
props.columnTranslations[col.key] ?? col.title;
const titleAttr = (col: Column<ColumnKey, boolean>) =>
col.titleAttr ?? colTitle(col);
const $emit = defineEmits<{
(event: 'mounted'): void;
Expand Down
173 changes: 173 additions & 0 deletions src/modules/schoolingOverview/SchoolingOverview.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,173 @@
<template>
<div>
<span
class="glyphicon glyphicon-info-sign"
@click="hidden = !hidden"
></span>
<div class="alert alert-info row" :class="{ hidden }">
<button class="close" type="button" @click="hidden = !hidden">
×
</button>
<h3>{{ $m('name') }}</h3>
<div class="col-lg-6">
<h4>{{ $m('own') }}</h4>
<enhanced-table
:columns="[{ key: 'key' }, { key: 'amount' }]"
:column-translations="$cols"
:table-attrs="{ class: 'table table-striped' }"
@sort="setOwnSort"
:sort="sortOwn"
:sort-dir="sortOwnDir"
:search="ownSearch"
@search="s => (ownSearch = s)"
>
<tr v-for="schooling in ownSorted" :key="schooling.key">
<td>{{ schooling.key }}</td>
<td>{{ schooling.amount }}</td>
</tr>
</enhanced-table>
</div>
<div class="col-lg-6">
<h4>{{ $m('open') }}</h4>
<enhanced-table
:columns="[
{ key: 'key' },
{ key: 'amount' },
{ key: 'seats' },
]"
:column-translations="$cols"
:table-attrs="{ class: 'table table-striped' }"
@sort="setOpenSort"
:sort="sortOpen"
:sort-dir="sortOpenDir"
:search="openSearch"
@search="s => (openSearch = s)"
>
<tr
v-for="schooling in openSorted"
:key="schooling.key"
:class="{ 'empty-schooling': !schooling.amount }"
>
<td>{{ schooling.key }}</td>
<td>{{ schooling.amount }}</td>
<td>{{ schooling.seats }}</td>
</tr>
</enhanced-table>
</div>
</div>
</div>
</template>

<script setup lang="ts">
import { computed, ref } from 'vue';
import EnhancedTable from '../../components/EnhancedTable.vue';
import { useI18nModule } from '../../i18n';
import type {
OpenSchoolings,
OwnSchoolings,
} from 'typings/modules/SchoolingOverview/main';
type SortDir = 'asc' | 'desc';
const { $m } = useI18nModule('schoolingOverview');
const hidden = ref<boolean>(true);
const sortOwn = ref<'amount' | 'key'>('key');
const sortOwnDir = ref<SortDir>('asc');
const sortOpen = ref<'amount' | 'key' | 'seats'>('key');
const sortOpenDir = ref<SortDir>('asc');
const ownSearch = ref<string>('');
const openSearch = ref<string>('');
const props = defineProps<{
ownSchoolings: OwnSchoolings['amounts'];
openSchoolings: OpenSchoolings['amounts'];
}>();
const $cols = computed(() => ({
key: $m('schooling'),
amount: $m('amount'),
seats: $m('seats'),
}));
const ownSchoolings = computed(() =>
Object.entries(props.ownSchoolings).map(([schooling, amount]) => ({
amount,
key: schooling,
}))
);
const ownFiltered = computed(() =>
ownSearch.value
? ownSchoolings.value.filter(schooling =>
JSON.stringify(Object.values(schooling))
.toLowerCase()
.match(ownSearch.value.toLowerCase())
)
: ownSchoolings.value
);
const ownSorted = computed(() =>
ownFiltered.value.toSorted((a, b) => {
let modifier = 1;
if (sortOwnDir.value === 'desc') modifier = -1;
if (a[sortOwn.value] < b[sortOwn.value]) return -1 * modifier;
if (a[sortOwn.value] > b[sortOwn.value]) return modifier;
return 0;
})
);
const setOwnSort = (key: (typeof sortOwn)['value']) => {
sortOwnDir.value =
key === sortOwn.value && sortOwnDir.value === 'asc' ? 'desc' : 'asc';
sortOwn.value = key;
};
const openSchoolings = computed(() =>
Object.entries(props.openSchoolings).map(
([schooling, { amount, seats }]) => ({
amount,
seats,
key: schooling,
})
)
);
const openFiltered = computed(() =>
openSearch.value
? openSchoolings.value.filter(schooling =>
JSON.stringify(Object.values(schooling))
.toLowerCase()
.match(openSearch.value.toLowerCase())
)
: openSchoolings.value
);
const openSorted = computed(() =>
openFiltered.value.toSorted((a, b) => {
let modifier = 1;
if (sortOpenDir.value === 'desc') modifier = -1;
if (a[sortOpen.value] < b[sortOpen.value]) return -1 * modifier;
if (a[sortOpen.value] > b[sortOpen.value]) return modifier;
return 0;
})
);
const setOpenSort = (key: (typeof sortOpen)['value']) => {
sortOpenDir.value =
key === sortOpen.value && sortOpenDir.value === 'asc' ? 'desc' : 'asc';
sortOpen.value = key;
};
</script>

<style scoped lang="sass">
th,
.glyphicon
cursor: pointer
.alert
&.external
margin: 0
.empty-schooling
td:not(:first-of-type)
color: red
</style>
4 changes: 2 additions & 2 deletions src/modules/schoolingOverview/main.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import getSchoolings from './assets/getSchoolings';
import openSchoolingTabs from './components/openSchoolingTabs.vue';
import ownSchoolingTabs from './components/ownSchoolingTabs.vue';
import schoolingOverview from './schoolingOverview.vue';
import SchoolingOverview from './SchoolingOverview.vue';

import type { ModuleMainFunction } from 'typings/Module';

Expand All @@ -14,7 +14,7 @@ export default <ModuleMainFunction>(({ LSSM }) => {
pinia: LSSM.$pinia,
i18n: LSSM.$i18n,
render: h =>
h(schoolingOverview, {
h(SchoolingOverview, {
props: {
ownSchoolings: ownSchoolings.amounts,
openSchoolings: openSchoolings.amounts,
Expand Down
Loading

0 comments on commit 0626752

Please sign in to comment.