master
lzq 2025-12-23 18:40:58 +08:00
parent 589f7cf26a
commit 8578d1164e
14 changed files with 1070 additions and 118 deletions

View File

@ -1,6 +1,6 @@
import mitt, { type EventType } from 'mitt'
interface EventList extends Record<EventType, unknown> {
export interface EventList extends Record<EventType, unknown> {
login?: string
logout?: string
connect_ws?: string

View File

@ -1,83 +0,0 @@
<script generic="D extends Record<string, any>,S extends G.PageParam" lang="ts" setup>
import type {
Column,
DataSource,
} from '@/components/data-list/data-list.ts'
import Page from '@/components/page/Page.vue'
const props = withDefaults(defineProps<{
dataSource: DataSource<D, S>
searchForm: S
columns: Column[]
treeTable?: boolean
}>(), {
treeTable: false,
})
const emits = defineEmits([ 'update:searchForm' ])
const searching = ref(false)
const tableData = ref<Record<string, any>[]>([])
const pagination = reactive<G.Pagination>({
total: 0,
pages: 0,
current: 1,
size: 20,
})
function searchHandler() {
searching.value = true
props.dataSource.paging(props.searchForm)
.then(res => {
console.log(res, 3333)
tableData.value = res.records ?? []
Object.assign(pagination, {
total: res.total ?? 0,
pages: res.pages ?? 0,
current: res.current ?? 1,
size: res.size ?? 20,
})
})
.finally(() => {
searching.value = false
})
}
onMounted(() => {
searchHandler()
})
</script>
<template>
<Page>
<slot name="searchForm">
<ElForm :model="searchForm">
<slot name="searchFormItem"/>
<ElFormItem>
<ElButton :loading="searching" @click="searchHandler"></ElButton>
<ElButton :loading="searching" @click="searchHandler"></ElButton>
</ElFormItem>
</ElForm>
</slot>
<slot name="dataTable">0
<ElTable :data="tableData" :load="dataSource.treeLoad" :tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
lazy
row-key="id">
<ElTableColumn v-for="col in columns" :key="col.prop"
:prop="col.prop"
:width="col.width"
/>
</ElTable>
<!-- <ElPagination
layout="prev, pager, next"
:page-size="pagination.size"
:pager-count="pagination.pages"
:total="pagination.total"/> -->
</slot>
</Page>
</template>
<style lang="stylus" scoped>
</style>

View File

@ -1,31 +0,0 @@
import type { R } from '@/common/utils/http-util.ts'
/* export interface SearchForm extends Record<string, any> {
keywords?: string
}
export interface AddForm extends Record<string, any> {
}
export interface ModifyForm extends Record<string, any> {
id: string
}
export interface Data extends Record<string, any> {
id: string
} */
export interface DataSource<D extends Record<string, any>, S extends G.PageParam> {
paging: (searchForm: S) => Promise<G.PageResult<D>>
del: (ids: string[]) => Promise<R>
detail: (id: string) => Promise<R<D>>
add: (addForm: Record<string, any>) => Promise<R>
modify: (modifyForm: Record<string, any>) => Promise<R>
treeLoad?: (row: D, treeNode: unknown, resolve: (data: D[]) => void) => void
}
export interface Column {
prop: string
label: string
width?: string
}

View File

@ -5,7 +5,6 @@
// ------
// Generated by unplugin-vue-components
// Read more: https://github.com/vuejs/core/pull/3399
import { GlobalComponents } from 'vue'
export {}
@ -33,6 +32,7 @@ declare module 'vue' {
ElHeader: typeof import('element-plus/es')['ElHeader']
ElIcon: typeof import('element-plus/es')['ElIcon']
ElIconPicture: typeof import('@element-plus/icons-vue')['Picture']
ElIconTimer: typeof import('@element-plus/icons-vue')['Timer']
ElImage: typeof import('element-plus/es')['ElImage']
ElInput: typeof import('element-plus/es')['ElInput']
ElInputNumber: typeof import('element-plus/es')['ElInputNumber']
@ -40,6 +40,8 @@ declare module 'vue' {
ElOption: typeof import('element-plus/es')['ElOption']
ElPagination: typeof import('element-plus/es')['ElPagination']
ElPopconfirm: typeof import('element-plus/es')['ElPopconfirm']
ElRadio: typeof import('element-plus/es')['ElRadio']
ElRadioGroup: typeof import('element-plus/es')['ElRadioGroup']
ElSelect: typeof import('element-plus/es')['ElSelect']
ElSwitch: typeof import('element-plus/es')['ElSwitch']
ElTable: typeof import('element-plus/es')['ElTable']
@ -83,6 +85,7 @@ declare global {
const ElHeader: typeof import('element-plus/es')['ElHeader']
const ElIcon: typeof import('element-plus/es')['ElIcon']
const ElIconPicture: typeof import('@element-plus/icons-vue')['Picture']
const ElIconTimer: typeof import('@element-plus/icons-vue')['Timer']
const ElImage: typeof import('element-plus/es')['ElImage']
const ElInput: typeof import('element-plus/es')['ElInput']
const ElInputNumber: typeof import('element-plus/es')['ElInputNumber']
@ -90,6 +93,8 @@ declare global {
const ElOption: typeof import('element-plus/es')['ElOption']
const ElPagination: typeof import('element-plus/es')['ElPagination']
const ElPopconfirm: typeof import('element-plus/es')['ElPopconfirm']
const ElRadio: typeof import('element-plus/es')['ElRadio']
const ElRadioGroup: typeof import('element-plus/es')['ElRadioGroup']
const ElSelect: typeof import('element-plus/es')['ElSelect']
const ElSwitch: typeof import('element-plus/es')['ElSwitch']
const ElTable: typeof import('element-plus/es')['ElTable']

View File

@ -22,7 +22,17 @@
</ElSelect>
</ElFormItem>
<ElFormItem label="调度配置" v-if="taskFormData.scheduleType != 'Manually'">
<ElInput v-model="taskFormData.scheduleConf" :disabled="status === 'view'" placeholder="调度配置"/>
<Cron v-model="taskFormData.scheduleConf" :disabled="status === 'view'" placeholder="调度配置"/>
<!-- <ElInput v-model="taskFormData.scheduleConf" :disabled="status === 'view'" placeholder="调度配置">
<template #suffix>
<ElDropdown trigger="click">
<ElButton :icon="elIcons.Timer" type="text"/>
<template #dropdown>
<CronPanel/>
</template>
</ElDropdown>
</template>
</ElInput> -->
</ElFormItem>
<ElFormItem label="是否禁用">
<ElSwitch v-model="taskFormData.disabled" active-text="" inactive-text=""/>
@ -41,6 +51,7 @@
import TaskApi from '@/pages/sys/task/task-api.ts'
import Strings from '@/common/utils/strings.ts'
import { ElMessage } from 'element-plus'
import Cron from '@/pages/sys/task/cron/Cron.vue'
const emits = defineEmits([ 'editSucc' ])
const scheduleTypeList = [
@ -104,6 +115,7 @@ defineExpose({
})
} else {
status.value = 'add'
data.scheduleConf = '* * * * * ? ?'
taskFormData.value = data
// taskFormData = {}
// for (const key in taskFormData) {

View File

@ -0,0 +1,39 @@
<script lang="ts" setup>
import { elIcons } from '@/common/element/element.ts'
import CronPanel from '@/pages/sys/task/cron/cron-panel/CronPanel.vue'
defineProps<{
modelValue?: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const showDialog = ref(false)
function openPanel() {
showDialog.value = true
}
</script>
<template>
<ElInput :model-value="modelValue" v-bind="$attrs" @update:model-value="val=>emits('update:modelValue',val)">
<template #suffix>
<ElButton :icon="elIcons.Timer" type="text" @click="openPanel"/>
</template>
</ElInput>
<ElDialog v-model="showDialog"
:close-on-click-modal="false"
destroy-on-close width="50vw">
<CronPanel :model-value="modelValue" @update:model-value="val=>emits('update:modelValue',val)"/>
<template #footer>
<div class="current-val">{{ modelValue }}</div>
</template>
</ElDialog>
</template>
<style lang="stylus" scoped>
.current-val {
width 100%;
font-weight: 700;
text-align center
}
</style>

View File

@ -0,0 +1,83 @@
<script lang="ts" setup>
import SecondPanel from '@/pages/sys/task/cron/cron-panel/SecondPanel.vue'
import MinutePanel from '@/pages/sys/task/cron/cron-panel/MinutePanel.vue'
import HourPanel from '@/pages/sys/task/cron/cron-panel/HourPanel.vue'
import DayPanel from '@/pages/sys/task/cron/cron-panel/DayPanel.vue'
import MonthPanel from '@/pages/sys/task/cron/cron-panel/MonthPanel.vue'
import WeekPanel from '@/pages/sys/task/cron/cron-panel/WeekPanel.vue'
import YearPanel from '@/pages/sys/task/cron/cron-panel/YearPanel.vue'
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const cronKernels = reactive({
second: '*',
minute: '*',
hour: '*',
day: '*',
month: '*',
week: '?',
year: '?',
})
watch(cronKernels, newVal => {
console.log(`${newVal.second} ${newVal.minute} ${newVal.hour} ${newVal.day} ${newVal.month} ${newVal.week} ${newVal.year}`)
emits('update:modelValue', `${newVal.second} ${newVal.minute} ${newVal.hour} ${newVal.day} ${newVal.month} ${newVal.week} ${newVal.year}`)
})
onMounted(() => {
let sections = props.modelValue.split(' ')
cronKernels.second = sections[0]
cronKernels.minute = sections[1]
cronKernels.hour = sections[2]
cronKernels.day = sections[3]
cronKernels.month = sections[4]
cronKernels.week = sections[5]
cronKernels.year = sections[6]
})
</script>
<template>
<div class="cron-panel">
<ElTabs type="border-card">
<ElTabPane :label="`秒(${cronKernels.second}`">
<SecondPanel v-model="cronKernels.second"/>
</ElTabPane>
<ElTabPane :label="`分(${cronKernels.minute}`">
<MinutePanel v-model="cronKernels.minute"/>
</ElTabPane>
<ElTabPane :label="`时(${cronKernels.hour}`">
<HourPanel v-model="cronKernels.hour"/>
</ElTabPane>
<ElTabPane :label="`日(${cronKernels.day}`">
<DayPanel v-model="cronKernels.day"/>
</ElTabPane>
<ElTabPane :label="`月(${cronKernels.month}`">
<MonthPanel v-model="cronKernels.month"/>
</ElTabPane>
<ElTabPane :label="`周(${cronKernels.week}`">
<WeekPanel v-model="cronKernels.week"/>
</ElTabPane>
<ElTabPane :label="`年(${cronKernels.year}`">
<YearPanel v-model="cronKernels.year"/>
</ElTabPane>
</ElTabs>
</div>
</template>
<style lang="stylus" scoped>
.cron-panel {
box-sizing border-box
width 100%
height 475px
padding 20px
& > div {
width: 100%;
height: 100%;
}
}
</style>

View File

@ -0,0 +1,153 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('every')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const near = ref<number>(1)
const fn = {
none() {
emits('update:modelValue', '?')
},
every() {
emits('update:modelValue', '*')
},
last() {
emits('update:modelValue', 'L')
},
near() {
emits('update:modelValue', near.value + 'W')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}/${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'none' | 'every' | 'last' | 'near' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'none' | 'every' | 'last' | 'near' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue === '?') {
newModuleData = 'none'
} else if (props.modelValue === 'L') {
newModuleData = 'last'
} else if (props.modelValue.includes('W')) {
const s = props.modelValue.split('W')
near.value = s[0]
newModuleData = 'near'
} else if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('/')) {
const s = props.modelValue.split('/')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="none">不指定</ElRadio>
<ElRadio value="every">每天</ElRadio>
<ElRadio value="last">每月最后一天</ElRadio>
<ElRadio value="near">
<span>每月</span>
<ElInputNumber v-model="near" :controls="false" :max="59" :min="1" size="small" @change="valueChange('near')"/>
<span>号最近的那个工作日</span>
</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
</ElRadio>
<ElRadio value="period2">
<span>周期从第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>天开始</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="60" :min="1" size="small" @change="valueChange('period2')"/>
<span>天执行一次</span>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 31" :key="'DayPanel' + i" :label="i" :value="i"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,129 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('every')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const fn = {
every() {
emits('update:modelValue', '*')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}/${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'every' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'every' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('/')) {
const s = props.modelValue.split('/')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="every">每小时</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span>时到</span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
</ElRadio>
<ElRadio value="period2">
<span>周期从第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>时开始</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>小时执行一次</span>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 24" :key="'HourPanel' + i" :label="(i-1)+''" :value="i-1"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,130 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('every')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const fn = {
every() {
emits('update:modelValue', '*')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}/${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'every' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'every' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('/')) {
const s = props.modelValue.split('/')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="every">每分钟</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
</ElRadio>
<ElRadio value="period2">
<span>周期从第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>分钟开始</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>分钟执行一次</span>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 60" :key="'MinutePanel' + i" :label="(i-1)+''" :value="i-1"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//width 600px;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,135 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('every')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const fn = {
none() {
emits('update:modelValue', '?')
},
every() {
emits('update:modelValue', '*')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}/${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'none' | 'every' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'none' | 'every' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue === '?') {
newModuleData = 'none'
} else if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('/')) {
const s = props.modelValue.split('/')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="none">不指定</ElRadio>
<ElRadio value="every">每月</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
</ElRadio>
<ElRadio value="period2">
<span>周期从第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>月开始</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="60" :min="1" size="small" @change="valueChange('period2')"/>
<span>月执行一次</span>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 12" :key="'MonthPanel' + i" :label="i" :value="i"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//width 600px;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,129 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('every')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const fn = {
every() {
emits('update:modelValue', '*')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}/${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'every' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'every' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('/')) {
const s = props.modelValue.split('/')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="every">每秒</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="0" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="0" size="small" @change="valueChange('period1')"/>
</ElRadio>
<ElRadio value="period2">
<span>周期从第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>秒开始</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>秒执行一次</span>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 60" :key="'SecondPanel' + i" :label="(i-1)+''" :value="i-1"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,148 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('none')
const period1 = reactive({
start: undefined,
end: undefined,
})
const period2 = reactive({
start: undefined,
end: undefined,
})
const specify = ref<number[]>([])
const last = ref<number>(1)
const fn = {
none() {
emits('update:modelValue', '?')
},
every() {
emits('update:modelValue', '*')
},
last() {
emits('update:modelValue', last.value + 'L')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
period2() {
emits('update:modelValue', `${period2.start}#${period2.end}`)
},
specify() {
emits('update:modelValue', specify.value.join(','))
},
}
function moduleChange(val: 'none' | 'every' | 'last' | 'period1' | 'period2' | 'specify') {
fn[val]?.()
}
function valueChange(module: 'none' | 'every' | 'last' | 'period1' | 'period2' | 'specify') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue === '?') {
newModuleData = 'none'
} else if (props.modelValue.includes('L')) {
const s = props.modelValue.split('L')
newModuleData = 'last'
last.value = +s[0]
} else if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
} else if (props.modelValue.includes('#')) {
const s = props.modelValue.split('#')
period2.start = +s[0]
period2.end = +s[1]
newModuleData = 'period2'
} else if (props.modelValue.includes(',')) {
specify.value = props.modelValue.split(',').map(it => +it)
newModuleData = 'specify'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="none">不指定</ElRadio>
<ElRadio value="every">每周</ElRadio>
<ElRadio value="last">
<span>每月最后一个星期</span>
<ElInputNumber v-model="last" :controls="false" :max="59" :min="1" size="small" @change="valueChange('last')"/>
</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
</ElRadio>
<ElRadio value="period2">
<span>每月第</span>
<ElInputNumber v-model="period2.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period2')"/>
<span>周的星期</span>
<ElInputNumber v-model="period2.end" :controls="false" :max="60" :min="1" size="small" @change="valueChange('period2')"/>
</ElRadio>
<ElRadio value="specify">
<div>指定</div>
<ElCheckboxGroup v-model="specify" @change="valueChange('specify')">
<ElCheckbox v-for="i in 7" :key="'WeekPanel' + i" :label="i" :value="i"/>
</ElCheckboxGroup>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//width 600px;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>

View File

@ -0,0 +1,103 @@
<script lang="ts" setup>
const props = defineProps<{
modelValue: string
}>()
const emits = defineEmits([ 'update:modelValue' ])
const moduleData = ref('none')
const period1 = reactive({
start: undefined,
end: undefined,
})
const fn = {
none() {
emits('update:modelValue', '?')
},
every() {
emits('update:modelValue', '*')
},
period1() {
emits('update:modelValue', `${period1.start}-${period1.end}`)
},
}
function moduleChange(val: 'none' | 'every' | 'period1') {
fn[val]?.()
}
function valueChange(module: 'none' | 'every' | 'period1') {
if (moduleData.value !== module) {
moduleData.value = module
}
moduleChange(module)
}
onMounted(() => {
let newModuleData = 'every'
if (props.modelValue === '?') {
newModuleData = 'none'
} else if (props.modelValue.includes('-')) {
const s = props.modelValue.split('-')
period1.start = +s[0]
period1.end = +s[1]
newModuleData = 'period1'
}
moduleData.value = newModuleData
})
</script>
<template>
<ElRadioGroup v-model="moduleData" class="select-panel" @change="moduleChange">
<ElRadio value="none">不指定</ElRadio>
<ElRadio value="every">每年</ElRadio>
<ElRadio value="period1">
<span>周期</span>
<ElInputNumber v-model="period1.start" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
<span></span>
<ElInputNumber v-model="period1.end" :controls="false" :max="59" :min="1" size="small" @change="valueChange('period1')"/>
</ElRadio>
</ElRadioGroup>
</template>
<style lang="stylus" scoped>
.select-panel {
flex-direction column
align-items start
gap 10px
width 100%;
//width 600px;
//overflow auto
flex-wrap nowrap
:deep(.el-input-number) {
margin 0 5px
width: 60px
}
:deep(.el-radio):nth-child(4) {
position relative
}
.second-item {
position relative
}
:deep(.el-checkbox-group) {
position absolute
top 0
left 60px
display flex
flex-wrap wrap
gap 10px
width 500px
.el-checkbox {
width 40px;
margin 0
}
}
}
</style>