refactor: 修改确认框

This commit is contained in:
zerosaturation 2026-04-13 11:30:05 +08:00
parent 58a2aa4668
commit 3cb06033e2
7 changed files with 421 additions and 14 deletions

View File

@ -0,0 +1,143 @@
<template>
<view v-show="visible" class="modal-overlay" :class="{ 'modal-visible': visible }" @tap="handleCancel">
<view class="modal-box" @tap.stop>
<!-- 标题 -->
<view v-if="title" class="modal-title">
<text>{{ title }}</text>
</view>
<!-- 内容 -->
<view class="modal-body">
<text class="modal-content">{{ content }}</text>
</view>
<!-- 按钮区 -->
<view class="modal-actions">
<view v-if="showCancel" class="btn btn-cancel" @tap="handleCancel">
<text>{{ cancelText }}</text>
</view>
<view class="btn btn-confirm" @tap="handleConfirm">
<text>{{ confirmText }}</text>
</view>
</view>
</view>
</view>
</template>
<script setup>
const props = defineProps({
visible: {
type: Boolean,
default: false
},
title: {
type: String,
default: ''
},
content: {
type: String,
default: ''
},
confirmText: {
type: String,
default: '确认'
},
cancelText: {
type: String,
default: '取消'
},
showCancel: {
type: Boolean,
default: true
}
})
const emit = defineEmits(['confirm', 'cancel'])
function handleConfirm() {
emit('confirm', { confirm: true })
}
function handleCancel() {
emit('cancel', { confirm: false })
}
</script>
<style scoped>
.modal-overlay {
position: fixed;
top: 0; left: 0; right: 0; bottom: 0;
background: rgba(0, 0, 0, 0.5);
z-index: 999;
display: flex;
align-items: center;
justify-content: center;
opacity: 0;
transition: opacity 0.25s ease;
pointer-events: none;
}
.modal-overlay.modal-visible {
opacity: 1;
pointer-events: auto;
}
.modal-box {
width: 560rpx;
background: #fff;
border-radius: 24rpx;
overflow: hidden;
padding: 48rpx 40rpx 32rpx;
display: flex;
flex-direction: column;
align-items: center;
}
.modal-title {
font-size: 34rpx;
font-weight: bold;
color: #333;
margin-bottom: 32rpx;
}
.modal-body {
display: flex;
flex-direction: column;
align-items: center;
gap: 12rpx;
margin-bottom: 40rpx;
}
.modal-content {
font-size: 28rpx;
color: #555;
text-align: center;
white-space: pre-line;
}
.modal-actions {
width: 100%;
display: flex;
gap: 24rpx;
}
.btn {
flex: 1;
height: 80rpx;
border-radius: 40rpx;
display: flex;
align-items: center;
justify-content: center;
font-size: 30rpx;
}
.btn-cancel {
background: #f0f0f0;
color: #666;
}
.btn-confirm {
background: linear-gradient(to right, #F08399, #B94E73);
color: #fff;
}
</style>

View File

@ -86,16 +86,69 @@
</scroll-view>
</view>
<!-- 通用确认弹窗 -->
<ConfirmModal
:visible="confirmModal.visible"
:title="confirmModal.title"
:content="confirmModal.content"
:confirmText="confirmModal.confirmText"
:cancelText="confirmModal.cancelText"
:showCancel="confirmModal.showCancel"
@confirm="onConfirmModal"
@cancel="onCancelModal"
/>
</template>
<script setup>
import { ref, onMounted } from 'vue';
import { getOssSignatureApi, createMintOrderApi } from '@/utils/api.js';
import ConfirmModal from '@/components/ConfirmModal.vue';
//
const pageType = ref('');
const pageName = ref('');
//
const confirmModal = ref({
visible: false,
title: '',
content: '',
confirmText: '确认',
cancelText: '取消',
showCancel: true,
confirmCallback: null
});
//
const onConfirmModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: true });
}
confirmModal.value.visible = false;
};
//
const onCancelModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: false });
}
confirmModal.value.visible = false;
};
//
const showConfirmModal = (options) => {
confirmModal.value = {
visible: true,
title: options.title || '',
content: options.content || '',
confirmText: options.confirmText || '确认',
cancelText: options.cancelText || '取消',
showCancel: options.showCancel !== false,
confirmCallback: options.success || null
};
};
//
const uploadedImage = ref('');
const uploadedImageBase64 = ref('');
@ -419,7 +472,7 @@ const uploadImageToOss = async (base64Data, ossData) => {
//
const handleBack = async () => {
if (uploadedImage.value || nftInfo.value || aiDescription.value) {
uni.showModal({
showConfirmModal({
title: '提示',
content: '确定要返回吗?未保存的数据将会丢失',
success: async (res) => {

View File

@ -85,16 +85,69 @@
<BottomNav :activeTab="2" @update:activeTab="handleTabChange" :isExpanded="navExpanded" @update:isExpanded="navExpanded = $event" />
</view>
<!-- 通用确认弹窗 -->
<ConfirmModal
:visible="confirmModal.visible"
:title="confirmModal.title"
:content="confirmModal.content"
:confirmText="confirmModal.confirmText"
:cancelText="confirmModal.cancelText"
:showCancel="confirmModal.showCancel"
@confirm="onConfirmModal"
@cancel="onCancelModal"
/>
</template>
<script setup>
import { ref } from 'vue';
import Header from "../components/Header.vue";
import ConfirmModal from '@/components/ConfirmModal.vue';
import BottomNav from "../components/BottomNav.vue";
import { getOssSignatureApi, deleteMintOrderApi } from '@/utils/api.js';
const navExpanded = ref(false);
//
const confirmModal = ref({
visible: false,
title: '',
content: '',
confirmText: '确认',
cancelText: '取消',
showCancel: true,
confirmCallback: null
});
//
const onConfirmModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: true });
}
confirmModal.value.visible = false;
};
//
const onCancelModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: false });
}
confirmModal.value.visible = false;
};
//
const showConfirmModal = (options) => {
confirmModal.value = {
visible: true,
title: options.title || '',
content: options.content || '',
confirmText: options.confirmText || '确认',
cancelText: options.cancelText || '取消',
showCancel: options.showCancel !== false,
confirmCallback: options.success || null
};
};
//
const uploadedImage = ref(''); //
const uploadedImageUrl = ref(''); // OSSURL
@ -436,7 +489,7 @@ const selectMaterialType = (index) => {
const handleBack = async () => {
//
if (uploadedImage.value || nftName.value || nftEvent.value || nftRemark.value) {
uni.showModal({
showConfirmModal({
title: '提示',
content: '确定要返回吗?未保存的数据将会丢失',
success: async (res) => {

View File

@ -71,10 +71,23 @@
</view>
</view>
</view>
<!-- 通用确认弹窗 -->
<ConfirmModal
:visible="confirmModal.visible"
:title="confirmModal.title"
:content="confirmModal.content"
:confirmText="confirmModal.confirmText"
:cancelText="confirmModal.cancelText"
:showCancel="confirmModal.showCancel"
@confirm="onConfirmModal"
@cancel="onCancelModal"
/>
</template>
<script setup>
import { ref, onMounted, nextTick } from 'vue';
import ConfirmModal from '@/components/ConfirmModal.vue';
//
const dreamInput = ref('');
@ -291,7 +304,7 @@ const initRecorderManager = () => {
if (err.errMsg && err.errMsg.includes('permission')) {
errorMsg = '请授予录音权限';
//
uni.showModal({
showConfirmModal({
title: '需要录音权限',
content: '请在设置中开启录音权限后重试',
confirmText: '去设置',
@ -363,7 +376,7 @@ const startRecording = () => {
} catch (error) {
console.error('[CreateFeed] 开始录音失败:', error);
stopSpeechRecognition();
uni.showModal({
showConfirmModal({
title: '录音失败',
content: '请确保已授予录音权限',
confirmText: '去设置',
@ -533,7 +546,7 @@ const handleLongPress = () => {
// #endif
// #ifndef APP-PLUS
uni.showModal({
showConfirmModal({
title: '提示',
content: '语音输入功能仅支持 App 端使用',
showCancel: false
@ -549,7 +562,7 @@ const handleTouchStart = () => {
// #endif
// #ifndef APP-PLUS
uni.showModal({
showConfirmModal({
title: '提示',
content: '语音输入功能仅支持 App 端使用',
showCancel: false
@ -562,6 +575,46 @@ let isStopping = false;
// onStop
let savedDuration = 0;
//
const confirmModal = ref({
visible: false,
title: '',
content: '',
confirmText: '确认',
cancelText: '取消',
showCancel: true,
confirmCallback: null
});
//
const onConfirmModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: true });
}
confirmModal.value.visible = false;
};
//
const onCancelModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: false });
}
confirmModal.value.visible = false;
};
//
const showConfirmModal = (options) => {
confirmModal.value = {
visible: true,
title: options.title || '',
content: options.content || '',
confirmText: options.confirmText || '确认',
cancelText: options.cancelText || '取消',
showCancel: options.showCancel !== false,
confirmCallback: options.success || null
};
};
//
const handleTouchEnd = () => {
console.log('[CreateFeed] ========== touchend 触发 ==========');
@ -658,7 +711,7 @@ const handleVoiceInput = () => {
// #endif
// #ifndef APP-PLUS
uni.showModal({
showConfirmModal({
title: '提示',
content: '语音输入功能仅支持 App 端使用',
showCancel: false
@ -712,7 +765,7 @@ const handleInputConfirm = () => {
}
//
uni.showModal({
showConfirmModal({
title: '确认发送',
content: `藏品名称: ${castloveFormData.value.name}\nAI描述: ${fullText}`,
success: (res) => {

View File

@ -53,11 +53,24 @@
</view>
</view>
</view>
<!-- 通用确认弹窗 -->
<ConfirmModal
:visible="confirmModal.visible"
:title="confirmModal.title"
:content="confirmModal.content"
:confirmText="confirmModal.confirmText"
:cancelText="confirmModal.cancelText"
:showCancel="confirmModal.showCancel"
@confirm="onConfirmModal"
@cancel="onCancelModal"
/>
</template>
<script setup>
import { ref, computed } from 'vue';
import { useStore } from 'vuex';
import ConfirmModal from '@/components/ConfirmModal.vue';
const props = defineProps({
isWelcome: {
@ -75,6 +88,46 @@ const currentIndex = ref(0);
const startX = ref(0);
const startY = ref(0);
const isDragging = ref(false);
//
const confirmModal = ref({
visible: false,
title: '',
content: '',
confirmText: '确认',
cancelText: '取消',
showCancel: true,
confirmCallback: null
});
//
const onConfirmModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: true });
}
confirmModal.value.visible = false;
};
//
const onCancelModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: false });
}
confirmModal.value.visible = false;
};
//
const showConfirmModal = (options) => {
confirmModal.value = {
visible: true,
title: options.title || '',
content: options.content || '',
confirmText: options.confirmText || '确认',
cancelText: options.cancelText || '取消',
showCancel: options.showCancel !== false,
confirmCallback: options.success || null
};
};
const stars = ref([
{
id: 1,
@ -269,7 +322,7 @@ const handleNext = async () => {
// 409
if (error.code === 409 || error.message.includes('昵称') || error.message.includes('已存在')) {
uni.showModal({
showConfirmModal({
title: '昵称已存在',
content: '该昵称已被使用,请返回修改昵称',
showCancel: true,

View File

@ -157,11 +157,24 @@
</view>
</view>
</view>
<!-- 通用确认弹窗 -->
<ConfirmModal
:visible="confirmModal.visible"
:title="confirmModal.title"
:content="confirmModal.content"
:confirmText="confirmModal.confirmText"
:cancelText="confirmModal.cancelText"
:showCancel="confirmModal.showCancel"
@confirm="onConfirmModal"
@cancel="onCancelModal"
/>
</template>
<script setup>
import { ref, computed } from 'vue'
import { GRID_CONFIG, generateGridCoordinates, IMAGE_W, IMAGE_H } from './config/cabin.js'
import ConfirmModal from '@/components/ConfirmModal.vue'
const config = ref(JSON.parse(JSON.stringify(GRID_CONFIG)))
const selectedIndex = ref(null)
@ -175,7 +188,46 @@ const scale = ref(1)
//
const bgOffsetX = ref(0)
let touchStartX = 0
let lastMoveX = 0
//
const confirmModal = ref({
visible: false,
title: '',
content: '',
confirmText: '确认',
cancelText: '取消',
showCancel: true,
confirmCallback: null
})
//
const onConfirmModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: true })
}
confirmModal.value.visible = false
}
//
const onCancelModal = () => {
if (confirmModal.value.confirmCallback) {
confirmModal.value.confirmCallback({ confirm: false })
}
confirmModal.value.visible = false
}
//
const showConfirmModal = (options) => {
confirmModal.value = {
visible: true,
title: options.title || '',
content: options.content || '',
confirmText: options.confirmText || '确认',
cancelText: options.cancelText || '取消',
showCancel: options.showCancel !== false,
confirmCallback: options.success || null
}
}
//
const originalCoords = computed(() => {
@ -354,7 +406,7 @@ const exportConfig = () => {
console.log('}')
}
uni.showModal({
showConfirmModal({
title: '配置已导出',
content: '请查看控制台输出,复制到 config/cabin.js',
showCancel: false
@ -362,7 +414,7 @@ const exportConfig = () => {
}
const resetConfig = () => {
uni.showModal({
showConfirmModal({
title: '确认重置',
content: '将重置所有参数和调整,是否继续?',
success: (res) => {

View File

@ -181,7 +181,7 @@ const handleCabinClick = (cabin) => {
if (!cabin.userId || !cabin.showNickname) return
uni.navigateTo({
url: cabin.isMine
url: (cabin.isMine || cabin.nickname === currentUserNickname.value)
? '/pages/exhibition/exhibition'
: `/pages/exhibition/exhibition?target_uid=${cabin.userId}`,
})