mirror of
https://github.com/Kuingsmile/PicList.git
synced 2026-05-11 01:49:55 +08:00
🚧 WIP(custom): optimize UI of uploader config page
This commit is contained in:
@@ -1054,7 +1054,7 @@
|
|||||||
"setAsDefault": "Set as Default PicBed",
|
"setAsDefault": "Set as Default PicBed",
|
||||||
"setSuccess": "Set Success",
|
"setSuccess": "Set Success",
|
||||||
"subtitle": "{count} configurations available",
|
"subtitle": "{count} configurations available",
|
||||||
"title": "Uploader Configurations"
|
"title": "Configurations"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"settings": {
|
"settings": {
|
||||||
|
|||||||
@@ -1049,7 +1049,7 @@
|
|||||||
"setAsDefault": "设为默认图床",
|
"setAsDefault": "设为默认图床",
|
||||||
"setSuccess": "设置成功",
|
"setSuccess": "设置成功",
|
||||||
"subtitle": "共 {count} 个配置",
|
"subtitle": "共 {count} 个配置",
|
||||||
"title": "上传配置"
|
"title": "配置"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"settings": {
|
"settings": {
|
||||||
|
|||||||
@@ -1049,7 +1049,7 @@
|
|||||||
"setAsDefault": "設為預設圖床",
|
"setAsDefault": "設為預設圖床",
|
||||||
"setSuccess": "設定成功",
|
"setSuccess": "設定成功",
|
||||||
"subtitle": "共 {count} 個配置",
|
"subtitle": "共 {count} 個配置",
|
||||||
"title": "上傳配置"
|
"title": "配置"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"settings": {
|
"settings": {
|
||||||
|
|||||||
@@ -12,7 +12,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="header-text">
|
<div class="header-text">
|
||||||
<h1 class="page-title">
|
<h1 class="page-title">
|
||||||
{{ `${type} ${t('pages.uploaderConfig.title')}` }}
|
{{ `${picBedName || type} ${t('pages.uploaderConfig.title')}` }}
|
||||||
</h1>
|
</h1>
|
||||||
<p class="page-subtitle">
|
<p class="page-subtitle">
|
||||||
{{ t('pages.uploaderConfig.subtitle', { count: curConfigList.length }) }}
|
{{ t('pages.uploaderConfig.subtitle', { count: curConfigList.length }) }}
|
||||||
@@ -50,6 +50,18 @@
|
|||||||
<Cloud :size="20" />
|
<Cloud :size="20" />
|
||||||
</div>
|
</div>
|
||||||
<div class="card-actions">
|
<div class="card-actions">
|
||||||
|
<button
|
||||||
|
class="action-btn"
|
||||||
|
:class="{ 'is-favorited': isConfigFavorited(item._id) }"
|
||||||
|
:title="
|
||||||
|
isConfigFavorited(item._id)
|
||||||
|
? t('pages.uploaderConfig.removeFromFavorites')
|
||||||
|
: t('pages.uploaderConfig.addToFavorites')
|
||||||
|
"
|
||||||
|
@click.stop="() => toggleConfigFavorite(item._id)"
|
||||||
|
>
|
||||||
|
<Heart :size="14" :fill="isConfigFavorited(item._id) ? 'currentColor' : 'none'" />
|
||||||
|
</button>
|
||||||
<button class="action-btn" :title="t('pages.uploaderConfig.edit')" @click.stop="openEditPage(item._id)">
|
<button class="action-btn" :title="t('pages.uploaderConfig.edit')" @click.stop="openEditPage(item._id)">
|
||||||
<Pencil :size="14" />
|
<Pencil :size="14" />
|
||||||
</button>
|
</button>
|
||||||
@@ -76,20 +88,18 @@
|
|||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<h3 class="config-name">{{ item._configName }}</h3>
|
<h3 class="config-name">{{ item._configName }}</h3>
|
||||||
<div class="config-meta">
|
<div class="config-meta">
|
||||||
<Clock :size="12" />
|
<div style="display: flex; align-items: center; gap: 4px">
|
||||||
<span>{{ formatTime(item._updatedAt) }}</span>
|
<Clock :size="12" />
|
||||||
</div>
|
<span>{{ formatTime(item._updatedAt) }}</span>
|
||||||
</div>
|
</div>
|
||||||
|
<div v-if="defaultConfigId === item._id" class="status-badge active">
|
||||||
<!-- Card Footer -->
|
<CheckCircle2 :size="14" />
|
||||||
<div class="card-footer">
|
<span>{{ t('pages.uploaderConfig.selected') }}</span>
|
||||||
<div v-if="defaultConfigId === item._id" class="status-badge active">
|
</div>
|
||||||
<CheckCircle2 :size="14" />
|
<div v-else class="status-badge inactive">
|
||||||
<span>{{ t('pages.uploaderConfig.selected') }}</span>
|
<Circle :size="14" />
|
||||||
</div>
|
<span>{{ t('pages.uploaderConfig.clickToSelect') }}</span>
|
||||||
<div v-else class="status-badge inactive">
|
</div>
|
||||||
<Circle :size="14" />
|
|
||||||
<span>{{ t('pages.uploaderConfig.clickToSelect') }}</span>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -119,9 +129,10 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
|
import { useStorage } from '@vueuse/core'
|
||||||
import dayjs from 'dayjs'
|
import dayjs from 'dayjs'
|
||||||
import { CheckCircle2, Circle, Clock, Cloud, Copy, Pencil, Plus, Settings2, Star, Trash2 } from 'lucide-vue-next'
|
import { CheckCircle2, Circle, Clock, Cloud, Copy, Heart, Pencil, Plus, Settings2, Star, Trash2 } from 'lucide-vue-next'
|
||||||
import { onBeforeMount, ref } from 'vue'
|
import { computed, onBeforeMount, ref } from 'vue'
|
||||||
import { useI18n } from 'vue-i18n'
|
import { useI18n } from 'vue-i18n'
|
||||||
import { onBeforeRouteUpdate, useRoute, useRouter } from 'vue-router'
|
import { onBeforeRouteUpdate, useRoute, useRouter } from 'vue-router'
|
||||||
|
|
||||||
@@ -140,11 +151,40 @@ const message = useMessage()
|
|||||||
const { confirm } = useConfirm()
|
const { confirm } = useConfirm()
|
||||||
const router = useRouter()
|
const router = useRouter()
|
||||||
const route = useRoute()
|
const route = useRoute()
|
||||||
const { defaultPicBedG } = usePicBed()
|
const { defaultPicBedG, picBedG } = usePicBed()
|
||||||
|
const favoritePicbeds = useStorage<IFavoritePicbedItem[]>('favorite-picbeds', [])
|
||||||
|
|
||||||
const type = ref('')
|
const type = ref('')
|
||||||
const curConfigList = ref<IStringKeyMap[]>([])
|
const curConfigList = ref<IStringKeyMap[]>([])
|
||||||
const defaultConfigId = ref('')
|
const defaultConfigId = ref('')
|
||||||
|
const favoriteConfigs = useStorage<string[]>('favorite-configs', [])
|
||||||
|
|
||||||
|
const picBedName = computed(() => {
|
||||||
|
if (!picBedG.value || picBedG.value.length === 0) {
|
||||||
|
return ''
|
||||||
|
}
|
||||||
|
const target = picBedG.value.find(item => item.type === type.value)
|
||||||
|
return target ? target.name : ''
|
||||||
|
})
|
||||||
|
|
||||||
|
const isFavorited = computed(() => {
|
||||||
|
return favoritePicbeds.value.some(item => item.type === type.value)
|
||||||
|
})
|
||||||
|
|
||||||
|
function isConfigFavorited(configId: string): boolean {
|
||||||
|
return favoriteConfigs.value.includes(configId)
|
||||||
|
}
|
||||||
|
|
||||||
|
function toggleConfigFavorite(configId: string) {
|
||||||
|
const index = favoriteConfigs.value.indexOf(configId)
|
||||||
|
if (index > -1) {
|
||||||
|
favoriteConfigs.value.splice(index, 1)
|
||||||
|
message.success(t('pages.uploaderConfig.removedFromFavorites'))
|
||||||
|
} else {
|
||||||
|
favoriteConfigs.value.push(configId)
|
||||||
|
message.success(t('pages.uploaderConfig.addedToFavorites'))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
async function selectItem(id: string) {
|
async function selectItem(id: string) {
|
||||||
await window.electron.triggerRPC<void>(IRPCActionType.UPLOADER_SELECT, type.value, id)
|
await window.electron.triggerRPC<void>(IRPCActionType.UPLOADER_SELECT, type.value, id)
|
||||||
@@ -272,6 +312,16 @@ function setDefaultPicBed(type: string) {
|
|||||||
[configPaths.picBed.uploader]: type,
|
[configPaths.picBed.uploader]: type,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
function toggleFavorite() {
|
||||||
|
const index = favoritePicbeds.value.findIndex(item => item.type === type.value)
|
||||||
|
if (index > -1) {
|
||||||
|
favoritePicbeds.value.splice(index, 1)
|
||||||
|
message.success(t('pages.uploaderConfig.removedFromFavorites'))
|
||||||
|
} else {
|
||||||
|
favoritePicbeds.value.push({ type: type.value })
|
||||||
|
message.success(t('pages.uploaderConfig.addedToFavorites'))
|
||||||
|
}
|
||||||
|
}
|
||||||
const currentConfigName = curConfigList.value.find(item => item._id === defaultConfigId.value)?._configName
|
const currentConfigName = curConfigList.value.find(item => item._id === defaultConfigId.value)?._configName
|
||||||
window.electron.sendRPC(IRPCActionType.TRAY_SET_TOOL_TIP, `${type} ${currentConfigName || ''}`)
|
window.electron.sendRPC(IRPCActionType.TRAY_SET_TOOL_TIP, `${type} ${currentConfigName || ''}`)
|
||||||
message.success(t('pages.uploaderConfig.setSuccess'))
|
message.success(t('pages.uploaderConfig.setSuccess'))
|
||||||
|
|||||||
@@ -186,6 +186,21 @@
|
|||||||
left: 100%;
|
left: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.btn.is-favorited {
|
||||||
|
background: linear-gradient(135deg, #ef4444 0%, #dc2626 100%);
|
||||||
|
box-shadow:
|
||||||
|
0 4px 14px rgb(239 68 68 / 35%),
|
||||||
|
0 2px 4px rgb(0 0 0 / 10%),
|
||||||
|
inset 0 1px 0 rgb(255 255 255 / 15%);
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn.is-favorited:hover:not(:disabled) {
|
||||||
|
box-shadow:
|
||||||
|
0 8px 24px rgb(239 68 68 / 45%),
|
||||||
|
0 4px 8px rgb(0 0 0 / 15%),
|
||||||
|
inset 0 1px 0 rgb(255 255 255 / 20%);
|
||||||
|
}
|
||||||
|
|
||||||
/* ============================================
|
/* ============================================
|
||||||
Main Content Area
|
Main Content Area
|
||||||
============================================ */
|
============================================ */
|
||||||
@@ -340,7 +355,8 @@
|
|||||||
|
|
||||||
/* Card Actions */
|
/* Card Actions */
|
||||||
.config-card .card-actions {
|
.config-card .card-actions {
|
||||||
display: flex;
|
display: grid;
|
||||||
|
grid-template-columns: repeat(2, 1fr);
|
||||||
opacity: 0;
|
opacity: 0;
|
||||||
transform: translateY(-4px);
|
transform: translateY(-4px);
|
||||||
transition: all 0.25s ease;
|
transition: all 0.25s ease;
|
||||||
@@ -381,6 +397,19 @@
|
|||||||
|
|
||||||
.action-btn.disabled {
|
.action-btn.disabled {
|
||||||
cursor: not-allowed;
|
cursor: not-allowed;
|
||||||
|
}
|
||||||
|
|
||||||
|
.action-btn.is-favorited {
|
||||||
|
color: #ef4444;
|
||||||
|
border-color: #ef4444;
|
||||||
|
background: rgb(239 68 68 / 10%);
|
||||||
|
}
|
||||||
|
|
||||||
|
.action-btn.is-favorited:hover {
|
||||||
|
color: #dc2626;
|
||||||
|
border-color: #dc2626;
|
||||||
|
background: rgb(239 68 68 / 20%);
|
||||||
|
transform: scale(1.08);
|
||||||
opacity: 0.4;
|
opacity: 0.4;
|
||||||
pointer-events: none;
|
pointer-events: none;
|
||||||
}
|
}
|
||||||
@@ -410,12 +439,6 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Card Footer */
|
/* Card Footer */
|
||||||
.card-footer {
|
|
||||||
position: relative;
|
|
||||||
z-index: 1;
|
|
||||||
margin-top: auto;
|
|
||||||
padding-top: 1rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.status-badge {
|
.status-badge {
|
||||||
display: inline-flex;
|
display: inline-flex;
|
||||||
|
|||||||
Reference in New Issue
Block a user