重构添加背景页面右边栏背景标签页

This commit is contained in:
jingrow 2026-01-22 00:45:07 +08:00
parent 380e226949
commit a58d4e8080
2 changed files with 107 additions and 35 deletions

View File

@ -1204,7 +1204,7 @@
"Background removed successfully": "背景去除成功",
"Background Image": "背景图片",
"Upload Custom Background": "上传自定义背景",
"My Backgrounds": "我的背景图",
"Custom Backgrounds": "自定义背景",
"Background Images": "背景图",
"No images found": "未找到图片",
"Failed to load background images": "加载背景图片失败",

View File

@ -370,25 +370,23 @@ favorite-colors-grid<template>
</n-tab-pane>
<n-tab-pane name="image" :tab="t('Background')">
<div class="background-images-section">
<h4 class="section-title">{{ t('Upload Custom Background') }}</h4>
<n-upload
:custom-request="handleCustomBackgroundUpload"
<div class="custom-backgrounds-section">
<h4 class="section-title">{{ t('Custom Backgrounds') }}</h4>
<input
ref="bgFileInputRef"
type="file"
accept="image/*"
:show-file-list="false"
>
<n-upload-dragger>
<div class="upload-dragger-content">
<i class="fa fa-cloud-upload" style="font-size: 32px; color: #1fc76f;"></i>
<div class="upload-text">{{ t('Click or drag to upload') }}</div>
</div>
</n-upload-dragger>
</n-upload>
</div>
<div v-if="customBackgrounds.length > 0" class="custom-backgrounds-section">
<h4 class="section-title">{{ t('My Backgrounds') }}</h4>
style="display: none"
@change="handleBgFileSelect"
/>
<div class="background-images-grid">
<div
class="background-image-item upload-placeholder"
@click="triggerBgFileInput"
:title="t('Upload Image')"
>
<i class="fa fa-plus"></i>
</div>
<div
v-for="(bgImage, index) in customBackgrounds"
:key="index"
@ -542,25 +540,23 @@ favorite-colors-grid<template>
<n-tab-pane name="image" :tab="t('Background Image')">
<div class="sidebar-content">
<div class="background-images-section">
<h4 class="section-title">{{ t('Upload Custom Background') }}</h4>
<n-upload
:custom-request="handleCustomBackgroundUpload"
<div class="custom-backgrounds-section">
<h4 class="section-title">{{ t('Custom Backgrounds') }}</h4>
<input
ref="bgFileInputRef"
type="file"
accept="image/*"
:show-file-list="false"
>
<n-upload-dragger>
<div class="upload-dragger-content">
<i class="fa fa-cloud-upload" style="font-size: 32px; color: #1fc76f;"></i>
<div class="upload-text">{{ t('Click or drag to upload') }}</div>
</div>
</n-upload-dragger>
</n-upload>
</div>
<div v-if="customBackgrounds.length > 0" class="custom-backgrounds-section">
<h4 class="section-title">{{ t('My Backgrounds') }}</h4>
style="display: none"
@change="handleBgFileSelect"
/>
<div class="background-images-grid">
<div
class="background-image-item upload-placeholder"
@click="triggerBgFileInput"
:title="t('Upload Image')"
>
<i class="fa fa-plus"></i>
</div>
<div
v-for="(bgImage, index) in customBackgrounds"
:key="index"
@ -663,6 +659,7 @@ interface HistoryItem {
const fileInputRef = ref<HTMLInputElement | null>(null)
const urlInputRef = ref<HTMLInputElement | null>(null)
const bgFileInputRef = ref<HTMLInputElement | null>(null)
const canvasRef = ref<HTMLCanvasElement | null>(null)
const uploadedImage = ref<File | null>(null)
const uploadedImageUrl = ref<string>('')
@ -989,6 +986,54 @@ const removeCustomBackground = (index: number) => {
saveCustomBackgrounds()
}
// Trigger background file input
const triggerBgFileInput = () => {
bgFileInputRef.value?.click()
}
// Handle background file select
const handleBgFileSelect = (event: Event) => {
const target = event.target as HTMLInputElement
const file = target.files?.[0]
if (!file) return
const validTypes = ['image/jpeg', 'image/jpg', 'image/png', 'image/webp']
if (!validTypes.includes(file.type)) {
message.warning(t('Unsupported image format. Please use JPG, PNG, or WebP'))
return
}
const maxSize = 10 * 1024 * 1024
if (file.size > maxSize) {
message.warning(t('Image size exceeds 10MB limit'))
return
}
try {
const reader = new FileReader()
reader.onload = (e) => {
const dataUrl = e.target?.result as string
if (dataUrl) {
// Add to custom backgrounds
customBackgrounds.value.unshift(dataUrl)
// Limit to 20 custom backgrounds
if (customBackgrounds.value.length > 20) {
customBackgrounds.value = customBackgrounds.value.slice(0, 20)
}
saveCustomBackgrounds()
message.success(t('Background uploaded successfully'))
}
}
reader.readAsDataURL(file)
// Reset input value to allow selecting the same file again
target.value = ''
} catch (error) {
message.error(t('Failed to upload background'))
}
}
// 36 common background colors - light to dark gradient
const commonColors = ref([
// Pure Whites (3)
@ -3411,6 +3456,33 @@ const removeHistoryItem = (index: number) => {
}
}
.background-image-item.upload-placeholder {
background: white;
border: 2px dashed #cbd5e1;
display: flex;
align-items: center;
justify-content: center;
color: #64748b;
transition: all 0.2s ease;
cursor: pointer;
i {
font-size: 24px;
pointer-events: none;
}
&:hover {
border-color: #1fc76f;
color: #1fc76f;
background: #f0fdf4;
box-shadow: 0 2px 8px rgba(31, 199, 111, 0.3);
}
&:active {
transform: scale(0.95);
}
}
.load-more-container {
display: flex;
justify-content: center;