Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use AsyncComponentLoader with mini-widgets #840

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
70 changes: 15 additions & 55 deletions src/components/MiniWidgetInstantiator.vue
@@ -1,63 +1,11 @@
<template>
<template v-if="miniWidget.component === MiniWidgetType.RelativeAltitudeIndicator">
<RelativeAltitudeIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.ChangeAltitudeCommander">
<ChangeAltitudeCommander :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.TakeoffLandCommander">
<TakeoffLandCommander :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.ArmerButton">
<ArmerButton :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.BaseCommIndicator">
<BaseCommIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.BatteryIndicator">
<BatteryIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.DepthIndicator">
<DepthIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.VeryGenericIndicator">
<VeryGenericIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.JoystickCommIndicator">
<JoystickCommIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.MiniVideoRecorder">
<MiniVideoRecorder :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.ModeSelector">
<ModeSelector :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.SatelliteIndicator">
<SatelliteIndicator :mini-widget="miniWidget" />
</template>
<template v-if="miniWidget.component === MiniWidgetType.ViewSelector">
<ViewSelector :mini-widget="miniWidget" />
</template>
<component :is="componentFromType(miniWidget.component)" :mini-widget="miniWidget" />
</template>

<script setup lang="ts">
import { toRefs } from 'vue'
import { type AsyncComponentLoader, defineAsyncComponent, toRefs } from 'vue'

import { type MiniWidget, MiniWidgetType } from '@/types/miniWidgets'

import ArmerButton from './mini-widgets/ArmerButton.vue'
import BaseCommIndicator from './mini-widgets/BaseCommIndicator.vue'
import BatteryIndicator from './mini-widgets/BatteryIndicator.vue'
import ChangeAltitudeCommander from './mini-widgets/ChangeAltitudeCommander.vue'
import DepthIndicator from './mini-widgets/DepthIndicator.vue'
import JoystickCommIndicator from './mini-widgets/JoystickCommIndicator.vue'
import MiniVideoRecorder from './mini-widgets/MiniVideoRecorder.vue'
import ModeSelector from './mini-widgets/ModeSelector.vue'
import RelativeAltitudeIndicator from './mini-widgets/RelativeAltitudeIndicator.vue'
import SatelliteIndicator from './mini-widgets/SatelliteIndicator.vue'
import TakeoffLandCommander from './mini-widgets/TakeoffLandCommander.vue'
import VeryGenericIndicator from './mini-widgets/VeryGenericIndicator.vue'
import ViewSelector from './mini-widgets/ViewSelector.vue'
import type { MiniWidget, MiniWidgetType } from '@/types/miniWidgets'

const props = defineProps<{
/**
Expand All @@ -67,4 +15,16 @@ const props = defineProps<{
}>()

const miniWidget = toRefs(props).miniWidget

const componentCache: Record<string, AsyncComponentLoader> = {}

const componentFromType = (componentType: MiniWidgetType): AsyncComponentLoader => {
if (componentCache[componentType] === undefined) {
componentCache[componentType] = defineAsyncComponent(
() => import(`../components/mini-widgets/${componentType}.vue`)
)
}

return componentCache[componentType]
}
</script>
19 changes: 17 additions & 2 deletions src/tests/libs/widgets-loader.test.ts
@@ -1,10 +1,25 @@
import { expect, test } from 'vitest'

import { MiniWidgetType } from '@/types/miniWidgets'
import { WidgetType } from '@/types/widgets'

test('Test widgets exist', async () => {
await enum_to_files_checker(WidgetType, '@/components/widgets/${name}.vue')
})

test('Test mini-widgets exist', async () => {
await enum_to_files_checker(MiniWidgetType, '@/components/mini-widgets/${name}.vue')
})

/**
* Test helper to verify if all enums names matches with a file list in a path
* @param {T} enum_type Enum type with values as filenames
* @param {string} path_template Path template as string, where name should be used as filename
*/
async function enum_to_files_checker<T>(enum_type: T, path_template: string): Promise<void> {
const loader = await Promise.allSettled(
Object.values(WidgetType).map((name) => import(`@/components/widgets/${name}.vue`))
/* eslint-disable @typescript-eslint/no-unused-vars */
Object.values(enum_type).map((name) => import(eval('`' + path_template + '`'))) // Please, have marcy of my soul
)
const found_all_files = loader.every((file) => {
if (file.status == 'fulfilled') {
Expand All @@ -17,4 +32,4 @@ test('Test widgets exist', async () => {
return !failed_to_find
})
expect(found_all_files).toBe(true)
})
}