Compare commits
No commits in common. "079a89fcd6d111f0b4528a2403296ce5f9d27709" and "1c23e04075255c2dabaff748c71be261fb449a9b" have entirely different histories.
079a89fcd6
...
1c23e04075
7
components.d.ts
vendored
7
components.d.ts
vendored
@ -56,13 +56,6 @@ declare module 'vue' {
|
|||||||
CollapsibleTrigger: typeof import('./src/components/ui/collapsible/CollapsibleTrigger.vue')['default']
|
CollapsibleTrigger: typeof import('./src/components/ui/collapsible/CollapsibleTrigger.vue')['default']
|
||||||
CoolBack: typeof import('./src/components/CoolBack.vue')['default']
|
CoolBack: typeof import('./src/components/CoolBack.vue')['default']
|
||||||
DenseFramework: typeof import('./src/components/DenseFramework.vue')['default']
|
DenseFramework: typeof import('./src/components/DenseFramework.vue')['default']
|
||||||
Drawer: typeof import('./src/components/ui/drawer/Drawer.vue')['default']
|
|
||||||
DrawerContent: typeof import('./src/components/ui/drawer/DrawerContent.vue')['default']
|
|
||||||
DrawerDescription: typeof import('./src/components/ui/drawer/DrawerDescription.vue')['default']
|
|
||||||
DrawerFooter: typeof import('./src/components/ui/drawer/DrawerFooter.vue')['default']
|
|
||||||
DrawerHeader: typeof import('./src/components/ui/drawer/DrawerHeader.vue')['default']
|
|
||||||
DrawerOverlay: typeof import('./src/components/ui/drawer/DrawerOverlay.vue')['default']
|
|
||||||
DrawerTitle: typeof import('./src/components/ui/drawer/DrawerTitle.vue')['default']
|
|
||||||
DropdownMenu: typeof import('./src/components/ui/dropdown-menu/DropdownMenu.vue')['default']
|
DropdownMenu: typeof import('./src/components/ui/dropdown-menu/DropdownMenu.vue')['default']
|
||||||
DropdownMenuCheckboxItem: typeof import('./src/components/ui/dropdown-menu/DropdownMenuCheckboxItem.vue')['default']
|
DropdownMenuCheckboxItem: typeof import('./src/components/ui/dropdown-menu/DropdownMenuCheckboxItem.vue')['default']
|
||||||
DropdownMenuContent: typeof import('./src/components/ui/dropdown-menu/DropdownMenuContent.vue')['default']
|
DropdownMenuContent: typeof import('./src/components/ui/dropdown-menu/DropdownMenuContent.vue')['default']
|
||||||
|
|||||||
@ -25,7 +25,6 @@
|
|||||||
"shadcn-vue": "^0.11.3",
|
"shadcn-vue": "^0.11.3",
|
||||||
"tailwind-merge": "^2.5.5",
|
"tailwind-merge": "^2.5.5",
|
||||||
"tailwindcss-animate": "^1.0.7",
|
"tailwindcss-animate": "^1.0.7",
|
||||||
"vaul-vue": "^0.2.0",
|
|
||||||
"vee-validate": "^4.15.0",
|
"vee-validate": "^4.15.0",
|
||||||
"vue": "^3.5.13",
|
"vue": "^3.5.13",
|
||||||
"vue-router": "^4.5.0",
|
"vue-router": "^4.5.0",
|
||||||
|
|||||||
17
pnpm-lock.yaml
generated
17
pnpm-lock.yaml
generated
@ -48,9 +48,6 @@ importers:
|
|||||||
tailwindcss-animate:
|
tailwindcss-animate:
|
||||||
specifier: ^1.0.7
|
specifier: ^1.0.7
|
||||||
version: 1.0.7
|
version: 1.0.7
|
||||||
vaul-vue:
|
|
||||||
specifier: ^0.2.0
|
|
||||||
version: 0.2.0(radix-vue@1.9.11(vue@3.5.13(typescript@5.6.3)))(vue@3.5.13(typescript@5.6.3))
|
|
||||||
vee-validate:
|
vee-validate:
|
||||||
specifier: ^4.15.0
|
specifier: ^4.15.0
|
||||||
version: 4.15.0(vue@3.5.13(typescript@5.6.3))
|
version: 4.15.0(vue@3.5.13(typescript@5.6.3))
|
||||||
@ -3902,12 +3899,6 @@ packages:
|
|||||||
validate-npm-package-license@3.0.4:
|
validate-npm-package-license@3.0.4:
|
||||||
resolution: {integrity: sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==}
|
resolution: {integrity: sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==}
|
||||||
|
|
||||||
vaul-vue@0.2.0:
|
|
||||||
resolution: {integrity: sha512-YV0zqxc8NiVzr1z/Awwbaty0UDDchxj5BfhFbLiYu+Uz0rCfSaDK2zwmuXZvejBJKLGbWw9I5GLHJRse14lQew==}
|
|
||||||
peerDependencies:
|
|
||||||
radix-vue: ^1.4.0
|
|
||||||
vue: ^3.3.0
|
|
||||||
|
|
||||||
vee-validate@4.15.0:
|
vee-validate@4.15.0:
|
||||||
resolution: {integrity: sha512-PGJh1QCFwCBjbHu5aN6vB8macYVWrajbDvgo1Y/8fz9n/RVIkLmZCJDpUgu7+mUmCOPMxeyq7vXUOhbwAqdXcA==}
|
resolution: {integrity: sha512-PGJh1QCFwCBjbHu5aN6vB8macYVWrajbDvgo1Y/8fz9n/RVIkLmZCJDpUgu7+mUmCOPMxeyq7vXUOhbwAqdXcA==}
|
||||||
peerDependencies:
|
peerDependencies:
|
||||||
@ -8619,14 +8610,6 @@ snapshots:
|
|||||||
spdx-correct: 3.2.0
|
spdx-correct: 3.2.0
|
||||||
spdx-expression-parse: 3.0.1
|
spdx-expression-parse: 3.0.1
|
||||||
|
|
||||||
vaul-vue@0.2.0(radix-vue@1.9.11(vue@3.5.13(typescript@5.6.3)))(vue@3.5.13(typescript@5.6.3)):
|
|
||||||
dependencies:
|
|
||||||
'@vueuse/core': 10.11.1(vue@3.5.13(typescript@5.6.3))
|
|
||||||
radix-vue: 1.9.11(vue@3.5.13(typescript@5.6.3))
|
|
||||||
vue: 3.5.13(typescript@5.6.3)
|
|
||||||
transitivePeerDependencies:
|
|
||||||
- '@vue/composition-api'
|
|
||||||
|
|
||||||
vee-validate@4.15.0(vue@3.5.13(typescript@5.6.3)):
|
vee-validate@4.15.0(vue@3.5.13(typescript@5.6.3)):
|
||||||
dependencies:
|
dependencies:
|
||||||
'@vue/devtools-api': 7.7.0
|
'@vue/devtools-api': 7.7.0
|
||||||
|
|||||||
@ -121,13 +121,9 @@ const data = {
|
|||||||
icon: 'mdi:telescope',
|
icon: 'mdi:telescope',
|
||||||
isActive: true,
|
isActive: true,
|
||||||
items: [
|
items: [
|
||||||
{
|
|
||||||
title: '行星波振幅',
|
|
||||||
url: '/tidi/waves',
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: '行星波月统计',
|
title: '行星波月统计',
|
||||||
url: '/tidi/month_stats',
|
url: '/tidi/waves',
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
|||||||
@ -55,15 +55,6 @@ onFetchError(async (error) => {
|
|||||||
imageResult.result = 'error'
|
imageResult.result = 'error'
|
||||||
imageResult.message = error
|
imageResult.message = error
|
||||||
})
|
})
|
||||||
|
|
||||||
function download() {
|
|
||||||
if (imageResult.result === 'success') {
|
|
||||||
const a = document.createElement('a')
|
|
||||||
a.href = imageResult.resourceId
|
|
||||||
a.download = 'image.png'
|
|
||||||
a.click()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@ -79,7 +70,6 @@ function download() {
|
|||||||
$emit('submit')
|
$emit('submit')
|
||||||
execute()
|
execute()
|
||||||
}"
|
}"
|
||||||
@download="download"
|
|
||||||
>
|
>
|
||||||
<slot />
|
<slot />
|
||||||
</ParamsCard>
|
</ParamsCard>
|
||||||
|
|||||||
@ -7,9 +7,18 @@ export interface ImageResult {
|
|||||||
message?: string
|
message?: string
|
||||||
}
|
}
|
||||||
|
|
||||||
defineProps<{
|
const props = defineProps<{
|
||||||
imageResult: ImageResult
|
imageResult: ImageResult
|
||||||
}>()
|
}>()
|
||||||
|
|
||||||
|
function download() {
|
||||||
|
if (props.imageResult.result === 'success') {
|
||||||
|
const a = document.createElement('a')
|
||||||
|
a.href = props.imageResult.resourceId
|
||||||
|
a.download = 'image.png'
|
||||||
|
a.click()
|
||||||
|
}
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@ -25,5 +34,10 @@ defineProps<{
|
|||||||
<div v-else class="flex flex-1 items-center justify-center text-xl">
|
<div v-else class="flex flex-1 items-center justify-center text-xl">
|
||||||
{{ imageResult.message }}
|
{{ imageResult.message }}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<Button type="submit" size="sm" class="ml-auto gap-1.5" @click.prevent="download">
|
||||||
|
下载图片
|
||||||
|
<CornerDownLeft class="size-3.5" />
|
||||||
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
@ -1,18 +1,19 @@
|
|||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
defineEmits(['submit', 'download'])
|
defineEmits(['submit'])
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<!-- <Drawer>
|
<Drawer>
|
||||||
<DrawerTrigger as-child class="min-w-[20rem]">
|
<DrawerTrigger as-child class="min-w-[20rem]">
|
||||||
<Button variant="ghost" size="icon" class="md:hidden">
|
<Button variant="ghost" size="icon" class="md:hidden">
|
||||||
|
<Settings class="size-4" />
|
||||||
<span class="sr-only">参数设置</span>
|
<span class="sr-only">参数设置</span>
|
||||||
</Button>
|
</Button>
|
||||||
</DrawerTrigger>
|
</DrawerTrigger>
|
||||||
<DrawerContent class="max-h-[80vh]">
|
<DrawerContent class="max-h-[80vh]">
|
||||||
<DrawerHeader>
|
<DrawerHeader>
|
||||||
<DrawerTitle />
|
<DrawerTitle />
|
||||||
</DrawerHeader> -->
|
</DrawerHeader>
|
||||||
<form class="grid min-w-[20rem] w-full items-start gap-6 overflow-auto p-4 pt-0">
|
<form class="grid min-w-[20rem] w-full items-start gap-6 overflow-auto p-4 pt-0">
|
||||||
<fieldset class="grid gap-6 border rounded-lg p-4">
|
<fieldset class="grid gap-6 border rounded-lg p-4">
|
||||||
<legend class="px-1 text-sm font-medium -ml-1">
|
<legend class="px-1 text-sm font-medium -ml-1">
|
||||||
@ -23,12 +24,9 @@ defineEmits(['submit', 'download'])
|
|||||||
<Button type="submit" class="mt-5 w-full" @click.prevent="$emit('submit')">
|
<Button type="submit" class="mt-5 w-full" @click.prevent="$emit('submit')">
|
||||||
绘制
|
绘制
|
||||||
</Button>
|
</Button>
|
||||||
<Button type="submit" class="mt-5 w-full" @click.prevent="$emit('download')">
|
|
||||||
下载
|
|
||||||
</Button>
|
|
||||||
</div>
|
</div>
|
||||||
</fieldset>
|
</fieldset>
|
||||||
</form>
|
</form>
|
||||||
<!-- </DrawerContent>
|
</DrawerContent>
|
||||||
</Drawer> -->
|
</Drawer>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
@ -1,19 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { DrawerRootEmits, DrawerRootProps } from 'vaul-vue'
|
|
||||||
import { useForwardPropsEmits } from 'radix-vue'
|
|
||||||
import { DrawerRoot } from 'vaul-vue'
|
|
||||||
|
|
||||||
const props = withDefaults(defineProps<DrawerRootProps>(), {
|
|
||||||
shouldScaleBackground: true,
|
|
||||||
})
|
|
||||||
|
|
||||||
const emits = defineEmits<DrawerRootEmits>()
|
|
||||||
|
|
||||||
const forwarded = useForwardPropsEmits(props, emits)
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DrawerRoot v-bind="forwarded">
|
|
||||||
<slot />
|
|
||||||
</DrawerRoot>
|
|
||||||
</template>
|
|
||||||
@ -1,28 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { DialogContentEmits, DialogContentProps } from 'radix-vue'
|
|
||||||
import type { HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { useForwardPropsEmits } from 'radix-vue'
|
|
||||||
import { DrawerContent, DrawerPortal } from 'vaul-vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
import DrawerOverlay from './DrawerOverlay.vue'
|
|
||||||
|
|
||||||
const props = defineProps<DialogContentProps & { class?: HtmlHTMLAttributes['class'] }>()
|
|
||||||
const emits = defineEmits<DialogContentEmits>()
|
|
||||||
|
|
||||||
const forwarded = useForwardPropsEmits(props, emits)
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DrawerPortal>
|
|
||||||
<DrawerOverlay />
|
|
||||||
<DrawerContent
|
|
||||||
v-bind="forwarded" :class="cn(
|
|
||||||
'fixed inset-x-0 bottom-0 z-50 mt-24 flex h-auto flex-col rounded-t-[10px] border bg-background',
|
|
||||||
props.class,
|
|
||||||
)"
|
|
||||||
>
|
|
||||||
<div class="mx-auto mt-4 h-2 w-[100px] rounded-full bg-muted" />
|
|
||||||
<slot />
|
|
||||||
</DrawerContent>
|
|
||||||
</DrawerPortal>
|
|
||||||
</template>
|
|
||||||
@ -1,20 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { DrawerDescriptionProps } from 'vaul-vue'
|
|
||||||
import { DrawerDescription } from 'vaul-vue'
|
|
||||||
import { computed, type HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
|
|
||||||
const props = defineProps<DrawerDescriptionProps & { class?: HtmlHTMLAttributes['class'] }>()
|
|
||||||
|
|
||||||
const delegatedProps = computed(() => {
|
|
||||||
const { class: _, ...delegated } = props
|
|
||||||
|
|
||||||
return delegated
|
|
||||||
})
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DrawerDescription v-bind="delegatedProps" :class="cn('text-sm text-muted-foreground', props.class)">
|
|
||||||
<slot />
|
|
||||||
</DrawerDescription>
|
|
||||||
</template>
|
|
||||||
@ -1,14 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
|
|
||||||
const props = defineProps<{
|
|
||||||
class?: HtmlHTMLAttributes['class']
|
|
||||||
}>()
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<div :class="cn('mt-auto flex flex-col gap-2 p-4', props.class)">
|
|
||||||
<slot />
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
@ -1,14 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
|
|
||||||
const props = defineProps<{
|
|
||||||
class?: HtmlHTMLAttributes['class']
|
|
||||||
}>()
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<div :class="cn('grid gap-1.5 p-4 text-center sm:text-left', props.class)">
|
|
||||||
<slot />
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
@ -1,18 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { DialogOverlayProps } from 'radix-vue'
|
|
||||||
import { DrawerOverlay } from 'vaul-vue'
|
|
||||||
import { computed, type HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
|
|
||||||
const props = defineProps<DialogOverlayProps & { class?: HtmlHTMLAttributes['class'] }>()
|
|
||||||
|
|
||||||
const delegatedProps = computed(() => {
|
|
||||||
const { class: _, ...delegated } = props
|
|
||||||
|
|
||||||
return delegated
|
|
||||||
})
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DrawerOverlay v-bind="delegatedProps" :class="cn('fixed inset-0 z-50 bg-black/80', props.class)" />
|
|
||||||
</template>
|
|
||||||
@ -1,20 +0,0 @@
|
|||||||
<script lang="ts" setup>
|
|
||||||
import type { DrawerTitleProps } from 'vaul-vue'
|
|
||||||
import { DrawerTitle } from 'vaul-vue'
|
|
||||||
import { computed, type HtmlHTMLAttributes } from 'vue'
|
|
||||||
import { cn } from '~/lib/utils'
|
|
||||||
|
|
||||||
const props = defineProps<DrawerTitleProps & { class?: HtmlHTMLAttributes['class'] }>()
|
|
||||||
|
|
||||||
const delegatedProps = computed(() => {
|
|
||||||
const { class: _, ...delegated } = props
|
|
||||||
|
|
||||||
return delegated
|
|
||||||
})
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DrawerTitle v-bind="delegatedProps" :class="cn('text-lg font-semibold leading-none tracking-tight', props.class)">
|
|
||||||
<slot />
|
|
||||||
</DrawerTitle>
|
|
||||||
</template>
|
|
||||||
@ -1,8 +0,0 @@
|
|||||||
export { default as Drawer } from './Drawer.vue'
|
|
||||||
export { default as DrawerContent } from './DrawerContent.vue'
|
|
||||||
export { default as DrawerDescription } from './DrawerDescription.vue'
|
|
||||||
export { default as DrawerFooter } from './DrawerFooter.vue'
|
|
||||||
export { default as DrawerHeader } from './DrawerHeader.vue'
|
|
||||||
export { default as DrawerOverlay } from './DrawerOverlay.vue'
|
|
||||||
export { default as DrawerTitle } from './DrawerTitle.vue'
|
|
||||||
export { DrawerClose, DrawerPortal, DrawerTrigger } from 'vaul-vue'
|
|
||||||
@ -8,6 +8,8 @@ meta:
|
|||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import type { ImageResult } from '~/components/ImageContainer.vue'
|
import type { ImageResult } from '~/components/ImageContainer.vue'
|
||||||
|
import { useForm } from 'vee-validate'
|
||||||
|
import { z } from 'zod'
|
||||||
import { API_BASE_URL } from '~/CONSTANT'
|
import { API_BASE_URL } from '~/CONSTANT'
|
||||||
|
|
||||||
const modes = [
|
const modes = [
|
||||||
@ -17,39 +19,41 @@ const modes = [
|
|||||||
'温度-水平风矢量图',
|
'温度-水平风矢量图',
|
||||||
] as const
|
] as const
|
||||||
|
|
||||||
const allPaths = ref([] as string[])
|
const formSchema = shallowRef<z.ZodObject< any, any, any >>(z.object({
|
||||||
const selected = reactive({
|
selectedMode: z.enum(modes).describe('选择一个模式'),
|
||||||
selectedMode: '观测的二阶多项式拟合',
|
selectedDate: z.enum(['no date']).describe('选择一个日期'),
|
||||||
selectedPath: '',
|
}))
|
||||||
station: 'LIN',
|
|
||||||
})
|
const form = useForm()
|
||||||
|
|
||||||
|
const stagedDates = ref<string[]>([])
|
||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
await baseFetch<string []>(`${API_BASE_URL}/balloon/metadata`).json().then(({ data }) => {
|
await baseFetch<string []>(`${API_BASE_URL}/balloon/metadata`).json().then(({ data }) => {
|
||||||
const das = data.value!
|
const das = data.value!
|
||||||
allPaths.value = das
|
stagedDates.value = das
|
||||||
selected.selectedPath = das[0]
|
formSchema.value = z.object({
|
||||||
})
|
selectedMode: z.enum(modes).describe('选择一个模式'),
|
||||||
})
|
selectedDate: z.enum(das.map((d: string) => {
|
||||||
|
const datePattern = /_\d{8}T\d{6}/
|
||||||
function renderDate(str: string) {
|
if (!datePattern.test(d)) {
|
||||||
const datePattern = /_\d{8}T\d{6}_/
|
return ''
|
||||||
const date = str.match(datePattern)![0]
|
|
||||||
const utcstr = date.replaceAll('_', '')
|
|
||||||
const realTime = new Date(utcstr.replace(/(\d{4})(\d{2})(\d{2})T(\d{2})(\d{2})(\d{2})/, '$1-$2-$3T$4:$5:$6'))
|
|
||||||
return realTime.toLocaleString('zh', {
|
|
||||||
year: 'numeric',
|
|
||||||
month: 'long',
|
|
||||||
day: '2-digit',
|
|
||||||
hour: '2-digit',
|
|
||||||
minute: 'numeric',
|
|
||||||
second: 'numeric',
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
const capture = datePattern.exec(d)
|
||||||
|
if (!capture) {
|
||||||
|
return ''
|
||||||
|
}
|
||||||
|
return capture[0]
|
||||||
|
})),
|
||||||
|
}).describe('选择一个日期')
|
||||||
|
form.setFieldValue('selectedDate', data.value![0])
|
||||||
|
form.setFieldValue('selectedMode', modes[0])
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
const queryUrl = computed(() => {
|
const queryUrl = computed(() => {
|
||||||
const selectedMode = selected.selectedMode
|
const selectedMode = form.values.selectedMode
|
||||||
const selectedDate = selected.selectedPath
|
const selectedDate = stagedDates.value.find(d => d.includes(form.values.selectedDate))!
|
||||||
return `${API_BASE_URL}/balloon/render/single?mode=${encodeURIComponent(selectedMode)}&path=${encodeURIComponent(selectedDate)}`
|
return `${API_BASE_URL}/balloon/render/single?mode=${encodeURIComponent(selectedMode)}&path=${encodeURIComponent(selectedDate)}`
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -83,42 +87,15 @@ async function customHandle(resp: Response) {
|
|||||||
|
|
||||||
<template>
|
<template>
|
||||||
<DenseFramework :image-query="queryUrl" :extra-response-handle="customHandle">
|
<DenseFramework :image-query="queryUrl" :extra-response-handle="customHandle">
|
||||||
<Label>选择模式</Label>
|
<AutoForm
|
||||||
<Tabs v-model="selected.selectedMode" default-value="观测的二阶多项式拟合">
|
:form="form"
|
||||||
<TabsList class="grid grid-cols-1 w-full">
|
:field-config="{
|
||||||
<TabsTrigger v-for="m in modes" :key="m" :value="m">
|
selectedMode: {
|
||||||
{{ m }}
|
component: 'radio',
|
||||||
</TabsTrigger>
|
},
|
||||||
</TabsList>
|
}"
|
||||||
</Tabs>
|
:schema="formSchema"
|
||||||
<Label>选择台站</Label>
|
/>
|
||||||
<Select v-model="selected.station">
|
|
||||||
<SelectTrigger>
|
|
||||||
<SelectValue placeholder="选择台站" />
|
|
||||||
</SelectTrigger>
|
|
||||||
<SelectContent>
|
|
||||||
<SelectGroup>
|
|
||||||
<SelectLabel>台站</SelectLabel>
|
|
||||||
<SelectItem value="LIN">
|
|
||||||
LIN
|
|
||||||
</SelectItem>
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
</Select>
|
|
||||||
<Label>选择日期</Label>
|
|
||||||
<Select v-model="selected.selectedPath">
|
|
||||||
<SelectTrigger>
|
|
||||||
<SelectValue placeholder="选择日期" />
|
|
||||||
</SelectTrigger>
|
|
||||||
<SelectContent>
|
|
||||||
<SelectGroup>
|
|
||||||
<SelectLabel>日期</SelectLabel>
|
|
||||||
<SelectItem v-for="path in allPaths" :key="path" :value="path">
|
|
||||||
{{ renderDate(path) }}
|
|
||||||
</SelectItem>
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
</Select>
|
|
||||||
</DenseFramework>
|
</DenseFramework>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
|||||||
@ -40,7 +40,7 @@ const urll = computed(() => {
|
|||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
await refreshPath()
|
await refreshPath()
|
||||||
selected.path = saberPaths.value[1]
|
selected.path = saberPaths.value[0]
|
||||||
})
|
})
|
||||||
|
|
||||||
watch(() => selected.path, async () => {
|
watch(() => selected.path, async () => {
|
||||||
@ -49,7 +49,7 @@ watch(() => selected.path, async () => {
|
|||||||
}
|
}
|
||||||
await refreshCurrentSaberDays(selected.path)
|
await refreshCurrentSaberDays(selected.path)
|
||||||
if (selected.day === '' && currentSaberDays.value.length > 0) {
|
if (selected.day === '' && currentSaberDays.value.length > 0) {
|
||||||
selected.day = currentSaberDays.value[1]
|
selected.day = currentSaberDays.value[0]
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
</script>
|
</script>
|
||||||
@ -94,7 +94,7 @@ watch(() => selected.path, async () => {
|
|||||||
<SelectContent>
|
<SelectContent>
|
||||||
<SelectGroup>
|
<SelectGroup>
|
||||||
<SelectLabel>Day</SelectLabel>
|
<SelectLabel>Day</SelectLabel>
|
||||||
<SelectItem v-for="day in currentSaberDays.slice(1)" :key="day" :value="day">
|
<SelectItem v-for="day in currentSaberDays" :key="day" :value="day">
|
||||||
{{ parseDayOfYear (day.toString()).toLocaleDateString("zh", {
|
{{ parseDayOfYear (day.toString()).toLocaleDateString("zh", {
|
||||||
year: 'numeric',
|
year: 'numeric',
|
||||||
month: 'long',
|
month: 'long',
|
||||||
|
|||||||
@ -43,14 +43,11 @@ const urll = computed(() => {
|
|||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
await refreshPath()
|
await refreshPath()
|
||||||
selected.path = saberPaths.value[1]
|
selected.path = saberPaths.value[0]
|
||||||
})
|
})
|
||||||
|
|
||||||
watch(() => selected.path, async () => {
|
watch(() => selected.path, async () => {
|
||||||
await refreshCurrentSaberDays(selected.path)
|
await refreshCurrentSaberDays(selected.path)
|
||||||
if (selected.day === '' && currentSaberDays.value.length > 0) {
|
|
||||||
selected.day = currentSaberDays.value[1]
|
|
||||||
}
|
|
||||||
})
|
})
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@ -94,7 +91,7 @@ watch(() => selected.path, async () => {
|
|||||||
<SelectContent>
|
<SelectContent>
|
||||||
<SelectGroup>
|
<SelectGroup>
|
||||||
<SelectLabel>Day</SelectLabel>
|
<SelectLabel>Day</SelectLabel>
|
||||||
<SelectItem v-for="day in currentSaberDays.slice(1)" :key="day" :value="day">
|
<SelectItem v-for="day in currentSaberDays" :key="day" :value="day">
|
||||||
{{ parseDayOfYear(day.toString()).toLocaleDateString("zh", {
|
{{ parseDayOfYear(day.toString()).toLocaleDateString("zh", {
|
||||||
year: 'numeric',
|
year: 'numeric',
|
||||||
month: 'long',
|
month: 'long',
|
||||||
|
|||||||
@ -25,7 +25,7 @@ const lat_ranges = [
|
|||||||
const selected = reactive({
|
const selected = reactive({
|
||||||
path: './saber/data\\2012\\SABER_Temp_O3_April2012_v2.0.nc',
|
path: './saber/data\\2012\\SABER_Temp_O3_April2012_v2.0.nc',
|
||||||
day: '',
|
day: '',
|
||||||
height_no: '1',
|
height_no: 1,
|
||||||
lat_ranges: '0,10',
|
lat_ranges: '0,10',
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -40,32 +40,15 @@ const urll = computed(() => {
|
|||||||
|
|
||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
await refreshPath()
|
await refreshPath()
|
||||||
selected.path = saberPaths.value[1]
|
selected.path = saberPaths.value[0]
|
||||||
})
|
})
|
||||||
|
|
||||||
watch(() => selected.path, async () => {
|
watch(() => selected.path, async () => {
|
||||||
await refreshCurrentSaberDays(selected.path)
|
await refreshCurrentSaberDays(selected.path)
|
||||||
if (saberPaths.value.length > 0) {
|
if (saberPaths.value.length > 0) {
|
||||||
selected.path = saberPaths.value[1]
|
selected.path = saberPaths.value[0]
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
function mapHeightValue(input: number) {
|
|
||||||
// Input range: 1 to 157
|
|
||||||
// Output range: 30 to 90
|
|
||||||
const inputMin = 1
|
|
||||||
const inputMax = 157
|
|
||||||
const outputMin = 30
|
|
||||||
const outputMax = 90
|
|
||||||
|
|
||||||
// Calculate slope
|
|
||||||
const m = (outputMax - outputMin) / (inputMax - inputMin)
|
|
||||||
// Calculate y-intercept
|
|
||||||
const b = outputMin - m * inputMin
|
|
||||||
|
|
||||||
// Apply linear mapping
|
|
||||||
return m * input + b
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@ -108,7 +91,7 @@ function mapHeightValue(input: number) {
|
|||||||
<SelectContent>
|
<SelectContent>
|
||||||
<SelectGroup>
|
<SelectGroup>
|
||||||
<SelectLabel>Day</SelectLabel>
|
<SelectLabel>Day</SelectLabel>
|
||||||
<SelectItem v-for="day in currentSaberDays.slice(1)" :key="day" :value="day">
|
<SelectItem v-for="day in currentSaberDays" :key="day" :value="day">
|
||||||
{{ parseDayOfYear(day.toString()).toLocaleDateString("zh", {
|
{{ parseDayOfYear(day.toString()).toLocaleDateString("zh", {
|
||||||
year: 'numeric',
|
year: 'numeric',
|
||||||
month: 'long',
|
month: 'long',
|
||||||
@ -119,19 +102,13 @@ function mapHeightValue(input: number) {
|
|||||||
</SelectContent>
|
</SelectContent>
|
||||||
</Select>
|
</Select>
|
||||||
<Label for="age">高度</Label>
|
<Label for="age">高度</Label>
|
||||||
<Select v-model="selected.height_no">
|
<NumberField id="age" :default-value="18" :min="0">
|
||||||
<SelectTrigger>
|
<NumberFieldContent>
|
||||||
<SelectValue placeholder="选择高度" />
|
<NumberFieldDecrement />
|
||||||
</SelectTrigger>
|
<NumberFieldInput />
|
||||||
<SelectContent>
|
<NumberFieldIncrement />
|
||||||
<SelectGroup>
|
</NumberFieldContent>
|
||||||
<SelectLabel>高度</SelectLabel>
|
</NumberField>
|
||||||
<SelectItem v-for="height_no in 157" :key="height_no" :value="height_no.toString()">
|
|
||||||
{{ mapHeightValue(height_no).toFixed(2) }} km
|
|
||||||
</SelectItem>
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
</Select>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</DenseFramework>
|
</DenseFramework>
|
||||||
|
|||||||
@ -1,92 +0,0 @@
|
|||||||
<route lang="json">
|
|
||||||
{
|
|
||||||
"meta":{
|
|
||||||
"title":"TIDI月统计",
|
|
||||||
"description":"TIDI月统计",
|
|
||||||
"group":"TIDI",
|
|
||||||
"item_name":"月统计"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</route>
|
|
||||||
|
|
||||||
<script setup lang="ts">
|
|
||||||
const selected = reactive({
|
|
||||||
year: '2015',
|
|
||||||
mode: 'v1',
|
|
||||||
lat_range: '0 ~ 20',
|
|
||||||
})
|
|
||||||
|
|
||||||
const allYears = ref([] as string[])
|
|
||||||
const lat_ranges = ['0 ~ 20']
|
|
||||||
|
|
||||||
const queryUrl = computed(() => {
|
|
||||||
const query = new URLSearchParams()
|
|
||||||
query.set('year', selected.year)
|
|
||||||
const mode = selected.mode
|
|
||||||
return `/tidi/render/month_stats_${mode}?${query}`
|
|
||||||
})
|
|
||||||
|
|
||||||
onMounted(async () => {
|
|
||||||
const resp = await baseFetch(`/tidi/metadata`).json()
|
|
||||||
allYears.value = Array.from(new Set(resp.data.value.path.map((a: string) => {
|
|
||||||
const year_pattern = /data\/(\d{4})\//
|
|
||||||
return a.match(year_pattern)?.[1]
|
|
||||||
})))
|
|
||||||
})
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<DenseFramework :image-query="queryUrl">
|
|
||||||
<Label>选择模式</Label>
|
|
||||||
<Tabs v-model="selected.mode" default-value="v1">
|
|
||||||
<TabsList class="grid grid-cols-1 w-full">
|
|
||||||
<TabsTrigger value="v1">
|
|
||||||
重力波势能(取log)随高度变化热力图
|
|
||||||
</TabsTrigger>
|
|
||||||
<TabsTrigger value="v2">
|
|
||||||
重力波势能(取log)变化折线图
|
|
||||||
</TabsTrigger>
|
|
||||||
</TabsList>
|
|
||||||
</Tabs>
|
|
||||||
<Label>纬度带</Label>
|
|
||||||
<Select v-model="selected.lat_range">
|
|
||||||
<SelectTrigger>
|
|
||||||
<SelectValue placeholder="选择纬度带" />
|
|
||||||
</SelectTrigger>
|
|
||||||
<SelectContent>
|
|
||||||
<SelectGroup>
|
|
||||||
<SelectLabel>纬度带</SelectLabel>
|
|
||||||
<SelectItem
|
|
||||||
v-for="lat_range in lat_ranges"
|
|
||||||
:key="lat_range"
|
|
||||||
:value="lat_range"
|
|
||||||
>
|
|
||||||
{{ lat_range }}
|
|
||||||
</SelectItem>
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
<Label>年份</Label>
|
|
||||||
<Select v-model="selected.year">
|
|
||||||
<SelectTrigger>
|
|
||||||
<SelectValue placeholder="选择年份" />
|
|
||||||
</SelectTrigger>
|
|
||||||
<SelectContent>
|
|
||||||
<SelectGroup>
|
|
||||||
<SelectLabel>年份</SelectLabel>
|
|
||||||
<SelectItem
|
|
||||||
v-for="y in allYears"
|
|
||||||
:key="y"
|
|
||||||
:value="y"
|
|
||||||
>
|
|
||||||
{{ y }}
|
|
||||||
</SelectItem>
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
</Select>
|
|
||||||
</select>
|
|
||||||
</DenseFramework>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
<style scoped>
|
|
||||||
|
|
||||||
</style>
|
|
||||||
@ -1,10 +1,10 @@
|
|||||||
<route lang="json">
|
<route lang="json">
|
||||||
{
|
{
|
||||||
"meta":{
|
"meta":{
|
||||||
"title":"TIDI 行星波振幅",
|
"title":"TIDI 行星波月统计",
|
||||||
"icon":"mdi:telescope",
|
"icon":"mdi:telescope",
|
||||||
"group":"TIDI",
|
"group":"TIDI",
|
||||||
"item_name":"行星波振幅"
|
"item_name":"行星波月统计"
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
1
typed-router.d.ts
vendored
1
typed-router.d.ts
vendored
@ -30,7 +30,6 @@ declare module 'vue-router/auto-routes' {
|
|||||||
'/saber/day_fft_ifft_plot': RouteRecordInfo<'/saber/day_fft_ifft_plot', '/saber/day_fft_ifft_plot', Record<never, never>, Record<never, never>>,
|
'/saber/day_fft_ifft_plot': RouteRecordInfo<'/saber/day_fft_ifft_plot', '/saber/day_fft_ifft_plot', Record<never, never>, Record<never, never>>,
|
||||||
'/saber/month_power_wave_plot': RouteRecordInfo<'/saber/month_power_wave_plot', '/saber/month_power_wave_plot', Record<never, never>, Record<never, never>>,
|
'/saber/month_power_wave_plot': RouteRecordInfo<'/saber/month_power_wave_plot', '/saber/month_power_wave_plot', Record<never, never>, Record<never, never>>,
|
||||||
'/saber/plot_wave_fitting': RouteRecordInfo<'/saber/plot_wave_fitting', '/saber/plot_wave_fitting', Record<never, never>, Record<never, never>>,
|
'/saber/plot_wave_fitting': RouteRecordInfo<'/saber/plot_wave_fitting', '/saber/plot_wave_fitting', Record<never, never>, Record<never, never>>,
|
||||||
'/tidi/month_stats': RouteRecordInfo<'/tidi/month_stats', '/tidi/month_stats', Record<never, never>, Record<never, never>>,
|
|
||||||
'/tidi/waves': RouteRecordInfo<'/tidi/waves', '/tidi/waves', Record<never, never>, Record<never, never>>,
|
'/tidi/waves': RouteRecordInfo<'/tidi/waves', '/tidi/waves', Record<never, never>, Record<never, never>>,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user