mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-02-03 06:47:33 +00:00
* [refactor] Move update-related functionality to platform/updates domain Reorganizes release management, version compatibility, and notification functionality following Domain-Driven Design principles, mirroring VSCode's architecture pattern. - Move releaseService.ts to platform/updates/common/ - Move releaseStore.ts to platform/updates/common/ - Move versionCompatibilityStore.ts to platform/updates/common/ - Move useFrontendVersionMismatchWarning.ts to platform/updates/common/ - Move toastStore.ts to platform/updates/common/ - Move ReleaseNotificationToast.vue to platform/updates/components/ - Move WhatsNewPopup.vue to platform/updates/components/ - Update 25+ import paths across codebase and tests This creates a cohesive "updates" domain containing all functionality related to software updates, version checking, release notifications, and user communication about application state changes. 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com> * fix imports --------- Co-authored-by: Claude <noreply@anthropic.com>
104 lines
2.4 KiB
Vue
104 lines
2.4 KiB
Vue
<template>
|
|
<div class="flex gap-2">
|
|
<InputText
|
|
v-model="modelValue"
|
|
class="flex-1"
|
|
:placeholder="$t('g.imageUrl')"
|
|
/>
|
|
<Button
|
|
v-tooltip="$t('g.upload')"
|
|
:icon="isUploading ? 'pi pi-spin pi-spinner' : 'pi pi-upload'"
|
|
size="small"
|
|
:disabled="isUploading"
|
|
@click="triggerFileInput"
|
|
/>
|
|
<Button
|
|
v-tooltip="$t('g.clear')"
|
|
outlined
|
|
icon="pi pi-trash"
|
|
severity="danger"
|
|
size="small"
|
|
:disabled="!modelValue"
|
|
@click="clearImage"
|
|
/>
|
|
<input
|
|
ref="fileInput"
|
|
type="file"
|
|
class="hidden"
|
|
accept="image/*"
|
|
@change="handleFileUpload"
|
|
/>
|
|
</div>
|
|
</template>
|
|
|
|
<script setup lang="ts">
|
|
import Button from 'primevue/button'
|
|
import InputText from 'primevue/inputtext'
|
|
import { ref } from 'vue'
|
|
|
|
import { useToastStore } from '@/platform/updates/common/toastStore'
|
|
import { api } from '@/scripts/api'
|
|
|
|
const modelValue = defineModel<string>()
|
|
|
|
const fileInput = ref<HTMLInputElement | null>(null)
|
|
const isUploading = ref(false)
|
|
|
|
const triggerFileInput = () => {
|
|
fileInput.value?.click()
|
|
}
|
|
|
|
const uploadFile = async (file: File): Promise<string | null> => {
|
|
const body = new FormData()
|
|
body.append('image', file)
|
|
body.append('subfolder', 'backgrounds')
|
|
|
|
const resp = await api.fetchApi('/upload/image', {
|
|
method: 'POST',
|
|
body
|
|
})
|
|
|
|
if (resp.status !== 200) {
|
|
useToastStore().addAlert(
|
|
`Upload failed: ${resp.status} - ${resp.statusText}`
|
|
)
|
|
return null
|
|
}
|
|
|
|
const data = await resp.json()
|
|
return data.subfolder ? `${data.subfolder}/${data.name}` : data.name
|
|
}
|
|
|
|
const handleFileUpload = async (event: Event) => {
|
|
const target = event.target as HTMLInputElement
|
|
if (target.files && target.files[0]) {
|
|
const file = target.files[0]
|
|
|
|
isUploading.value = true
|
|
try {
|
|
const uploadedPath = await uploadFile(file)
|
|
if (uploadedPath) {
|
|
// Set the value to the API view URL with subfolder parameter
|
|
const params = new URLSearchParams({
|
|
filename: uploadedPath,
|
|
type: 'input',
|
|
subfolder: 'backgrounds'
|
|
})
|
|
modelValue.value = `/api/view?${params.toString()}`
|
|
}
|
|
} catch (error) {
|
|
useToastStore().addAlert(`Upload error: ${String(error)}`)
|
|
} finally {
|
|
isUploading.value = false
|
|
}
|
|
}
|
|
}
|
|
|
|
const clearImage = () => {
|
|
modelValue.value = ''
|
|
if (fileInput.value) {
|
|
fileInput.value.value = ''
|
|
}
|
|
}
|
|
</script>
|